Java микросервистерін аудару және бейімдеу : практикалық нұсқаулық . Нұсқаулықтың алдыңғы бөліктері:
Абстрактілі заттардан бастап нақты кітапханалармен аяқталатын Java-дағы микросервистердің тән мәселелерін қарастырайық.
Java микросервисін қалай төзімді етуге болады?
Микросервистерді жасаған кезде сіз синхронды HTTP қоңырауларына немесе асинхронды хабар алмасуға арналған JVM әдісі қоңырауларын саудалайтыныңызды еске түсіріңіз. Әдіс шақыруы негізінен аяқталуға кепілдік берілгенімен (күтпеген JVM өшірілуіне тыйым салу), желілік қоңырау әдепкі бойынша сенімсіз. Ол жұмыс істеуі мүмкін, бірақ әртүрлі себептермен жұмыс істемеуі мүмкін: желі шамадан тыс жүктелген, жаңа желіаралық қалқан ережесі енгізілген және т.б. Мұның қалай өзгеретінін көру үшін BillingService мысалын қарастырайық.HTTP/REST төзімділік үлгілері
Клиенттер электрондық кітаптарды компанияңыздың веб-сайтынан сатып ала алады делік. Мұны істеу үшін сіз нақты PDF шот-фактураларын жасау үшін интернет-дүкеніңізге қоңырау шала алатын есепшот микросервисін ендірдіңіз. Әзірге біз бұл қоңырауды HTTP арқылы синхронды түрде жасаймыз (бірақ бұл қызметті асинхронды түрде шақыру орындырақ, өйткені PDF құру пайдаланушының көзқарасы бойынша лезде болуы міндетті емес. Біз келесі мысалда бірдей мысалды қолданамыз. бөлімін ашып, айырмашылықтарды қараңыз).@Service
class BillingService {
@Autowired
private HttpClient client;
public void bill(User user, Plan plan) {
Invoice invoice = createInvoice(user, plan);
httpClient.send(invoiceRequest(user.getEmail(), invoice), responseHandler());
// ...
}
}
Қорытындылай келе, бұл HTTP қоңырауының үш ықтимал нәтижесі.
- Жарайды: қоңырау өтті, тіркелгі сәтті жасалды.
- КЕШІКТІРУ: Қоңырау орындалды, бірақ аяқталуға тым көп уақыт кетті.
- ҚАТЕ. Қоңырау сәтсіз аяқталды, сіз үйлеспейтін сұрау жіберген болуыңыз мүмкін немесе жүйе жұмыс істемеуі мүмкін.
Хабар алмасу тұрақтылығы үлгілері
Асинхронды байланысты толығырақ қарастырайық. Хабар алмасу үшін Spring және RabbitMQ пайдаланамыз деп есептесек, біздің BillingService бағдарламамыз енді осылай көрінуі мүмкін. Тіркелгіні жасау үшін біз енді RabbitMQ хабарлама брокеріне хабарлама жібереміз, онда жаңа хабарларды күтіп тұрған бірнеше жұмысшы бар. Бұл жұмысшылар PDF шот-фактураларын жасайды және оларды тиісті пайдаланушыларға жібереді.@Service
class BillingService {
@Autowired
private RabbitTemplate rabbitTemplate;
public void bill(User user, Plan plan) {
Invoice invoice = createInvoice(user, plan);
// преобразует счет, например, в json и использует его How тело messages
rabbitTemplate.convertAndSend(exchange, routingkey, invoice);
// ...
}
}
Ықтимал қателер қазір сәл басқаша көрінеді, өйткені сіз синхронды HTTP қосылымы сияқты бірден ОК немесе ҚАТЕ жауаптарын алмайсыз. Оның орнына бізде қате болуы мүмкін үш ықтимал сценарий болуы мүмкін, бұл келесі сұрақтарды тудыруы мүмкін:
- Менің хабарламамды қызметкер жеткізіп, пайдаланды ма? Әлде жоғалып кетті ме? (Пайдаланушы шот-фактураны алмайды).
- Менің хабарламам тек бір рет жеткізілді ме? Немесе бірнеше рет жеткізіліп, тек бір рет өңделді ме? (Пайдаланушы бірнеше шот-фактураларды алады).
- Конфигурация: "Мен алмасу үшін дұрыс бағыттау кілттерін/аттарын пайдаландым ба" дегеннен "Менің хабарлама брокерім дұрыс конфигурацияланған және дұрыс сақталған ба немесе оның кезектері толы ма?" (Пайдаланушы шот-фактураны алмайды).
- ActiveMQ сияқты JMS енгізулерін пайдалансаңыз, екі фазалы (XA) міндеттемелердің кепілдігі үшін жылдамдықты айырбастауға болады.
- Егер сіз RabbitMQ қолданып жатсаңыз, алдымен осы нұсқаулықты оқып шығыңыз, содан кейін растаулар, ақауларға төзімділік және жалпы хабар сенімділігі туралы мұқият ойластырыңыз.
- Мүмкін біреу Active немесе RabbitMQ serverлерін конфигурациялауды жақсы біледі, әсіресе кластерлеу және Docker (кез келген адам? ;))
Java микросервистері үшін қай фреймворк ең жақсы шешім болар еді?
Бір жағынан, сіз Spring Boot сияқты өте танымал опцияны орнатуға болады . Ол .jar файлдарын жасауды өте жеңілдетеді, Tomcat немесе Jetty сияқты кірістірілген веб-serverмен бірге келеді және оны тез және кез келген жерде іске қосуға болады. Микросервис қолданбаларын құру үшін өте қолайлы. Жақында жартылай реактивті бағдарламалаудан шабыт алған Kubernetes немесе GraalVM мамандандырылған бірнеше микросервис құрылымдары пайда болды. Міне, тағы бірнеше қызықты үміткерлер: Quarkus , Micronaut , Vert.x , Helidon . Ақыр соңында, сіз өзіңіз таңдауыңыз керек, бірақ біз сізге мүлдем стандартты болмауы мүмкін бірнеше ұсынымдар бере аламыз: Spring Boot қолданбасынан басқа, барлық микросервис құрылымдары әдетте бірден іске қосылатын керемет жылдам ретінде сатылады. , жадты аз пайдалану, шексіздікке дейін масштабтау. Маркетингтік материалдарда әдетте бегемот Spring Boot жанында немесе бір-біріне платформаны көрсететін әсерлі графика бар. Бұл, теориялық тұрғыдан, жүктеп салуға кейде бірнеше minutes кететін ескі жобаларды қолдайтын әзірлеушілердің жүйкесін босатады. Немесе бұлтта жұмыс істейтін әзірлеушілер 50 мс ішінде қажет болғанша микроконтейнерлерді іске қосуды/тоқтатуды қалайды. Мәселе мынада: бұл (жасанды) жалаңаш металды іске қосу уақыттары мен қайта орналастыру уақыттары жобаның жалпы табысына әрең ықпал етеді. Кем дегенде, олар күшті құрылымдық инфрақұрылымға, күшті құжаттамаға, қауымдастыққа және әзірлеушілердің күшті дағдыларына қарағанда әлдеқайда аз әсер етеді. Сондықтан оған былай қараған дұрыс: Егер әлі:- Қарапайым жұмыс процестері үшін жүздеген сұраулар жасай отырып, ORM-ның кең таралуына мүмкіндік бересіз.
- Орташа күрделі монолитті іске қосу үшін шексіз гигаbyteтар қажет.
- Сізде codeтың көптігі және күрделілігі соншалықты жоғары (біз қазір Hibernate сияқты ықтимал баяу бастаушылар туралы айтып отырған жоқпыз), қолданбаны жүктеуге бірнеше minutes кетеді.
Синхронды Java REST қоңыраулары үшін қай кітапханалар жақсы?
Төмен деңгейлі техникалық жағынан сіз келесі HTTP клиенттік кітапханаларының бірімен аяқталуы мүмкін: Java-ның жергілікті HttpClient (Java 11-тен бастап), Apache-дің HttpClient немесе OkHttp . Мен бұл жерде «мүмкін» деп айтатынымды ескеріңіз, себебі жақсы ескі JAX-RS клиенттерінен қазіргі WebSocket клиенттеріне дейінгі басқа опциялар бар . Қалай болғанда да, HTTP клиентін құру үрдісі HTTP қоңырауларымен өз бетіңізше араласудан бас тартады. Мұны істеу үшін сіз одан әрі оқу үшін бастапқы нүкте ретінде OpenFeign жобасын және оның құжаттамасын қарауыңыз керек .Асинхронды Java хабар алмасуына арналған ең жақсы брокерлер қандай?
Сіз танымал ActiveMQ (Classic немесе Artemis) , RabbitMQ немесе Kafka- ны кездестіресіз .- ActiveMQ және RabbitMQ - дәстүрлі, толыққанды хабар брокерлері. Олар «ақылды брокер» мен «ақымақ пайдаланушылардың» өзара әрекетін қамтиды.
- Тарихи түрде ActiveMQ оңай кірістіру (тестілеу үшін) артықшылығына ие болды, оны RabbitMQ/Docker/TestContainer параметрлерімен азайтуға болады.
- Кафканы дәстүрлі «ақылды» брокер деп атауға болмайды. Оның орнына, бұл ақылды тұтынушыларды өңдеуді талап ететін салыстырмалы түрде «мылқау» хабарламалар қоймасы (журнал файлы).
Микросервистерді тексеру үшін қандай кітапханаларды пайдалана аламын?
Бұл сіздің стекіңізге байланысты. Егер сізде Spring экожүйесі орнатылған болса, құрылымның арнайы құралдарын пайдаланған дұрыс болар еді . Егер JavaEE Arquillian сияқты нәрсе болса . Docker және шынымен жақсы Testcontainers кітапханасын қарастырған жөн болар еді , ол әсіресе жергілікті әзірлеу немесе интеграция сынақтары үшін Oracle дерекқорын оңай және жылдам орнатуға көмектеседі. Толық HTTP serverлерін жалған сынау үшін Wiremock бөлімін тексеріңіз . Асинхронды хабар алмасуды тексеру үшін ActiveMQ немесе RabbitMQ енгізіп көріңіз, содан кейін Awaitility DSL арқылы сынақтар жазыңыз . Сонымен қатар, барлық әдеттегі құралдар пайдаланылады - Junit , TestNG for AssertJ және Mockito . Бұл толық тізім емес екенін ескеріңіз. Егер сіз өзіңіздің сүйікті құралыңызды осы жерден таппасаңыз, оны түсініктемелер бөлімінде қалдырыңыз.Барлық Java микросервистері үшін журналды қалай қосуға болады?
Микросервис жағдайында тіркеу - бұл қызықты және өте күрделі тақырып. Аз немесе grep пәрмендерімен өңдеуге болатын бір журнал файлының орнына енді сізде n журнал файлдары бар және олардың тым шашыраңқы болмауын қалайсыз. Ағаш кесу экожүйесінің ерекшеліктері осы мақалада жақсы сипатталған (ағылшын тілінде). Оны міндетті түрде оқып шығыңыз және микросервис тұрғысынан орталықтандырылған тіркеу бөліміне назар аударыңыз . Іс жүзінде сіз әртүрлі тәсілдерді кездестіресіз: Жүйе әкімшісі әртүрлі serverлерден журнал файлдарын бір журнал файлына жинайтын және біріктіретін белгілі сценарийлерді жазады және оларды жүктеп алу үшін FTP serverлеріне қояды. Cat/grep/unig/sort комбинацияларын параллель SSH сеанстарында іске қосу. Amazon AWS дәл осылай жасайды және сіз менеджеріңізге хабарлай аласыз. Graylog немесе ELK Stack (Elasticsearch, Logstash, Kibana) сияқты құралды пайдаланыңыз.Менің микросервистерім бір-бірін қалай табады?
Осы уақытқа дейін біздің микросервистер бір-бірін біледі және сәйкес IPS біледі деп есептедік. Статикалық конфигурация туралы сөйлесейік. Сонымен, біздің банктік монолит [ip = 192.168.200.1] сипаттар файлында қатты codeталған тәуекел serverімен [ip = 192.168.200.2] сөйлесу керек екенін біледі. Дегенмен, сіз нәрселерді динамикалық ете аласыз:- Микросервистерінде application.properties файлдарын орналастырудың орнына барлық микросервистер конфигурацияларын алатын бұлтқа негізделген конфигурация serverін пайдаланыңыз.
- Қызмет көрсету даналары орналасқан жерін динамикалық түрде өзгерте алатындықтан, қызметтеріңіз қайда тұратынын, олардың IP мекенжайлары қандай екенін және оларды қалай бағыттау керектігін білетін қызметтерді қарастырған жөн.
- Енді бәрі серпінді болғандықтан, көшбасшыны автоматты түрде сайлау сияқты жаңа мәселелер туындайды: мысалы, екі рет өңделмейтіндей белгілі бір тапсырмаларды орындайтын шебер кім? Көшбасшы сәтсіздікке ұшыраған кезде оны кім ауыстырады? Ауыстыру ненің негізінде жүзеге асырылады?
Java микросервистерін пайдаланып авторизация мен аутентификацияны қалай ұйымдастыруға болады?
Бұл тақырып та бөлек әңгімеге лайық. Тағы да, опциялар реттелетін қауіпсіздік құрылымдары бар қатты codeталған негізгі HTTPS аутентификациясынан бастап, өзінің авторизация serverімен Oauth2 орнатуын іске қосуға дейін ауытқиды.Менің барлық орталарымның бірдей көрінетініне қалай көз жеткізуге болады?
Микросервиссіз орналастыруларға қатысты нәрсе біреуі бар орналастыруларға да қатысты. Docker/Testcontainers және Scripting/Ansible тіркесімін қолданып көріңіз.Сұрақ жоқ: YAML туралы қысқаша
Бір сәтке кітапханалардан және қатысты мәселелерден алшақтап, Yaml-ге жылдам көз жүгіртейік. Бұл файл пішімі де-факто «конфигурацияны code ретінде жазу» пішімі ретінде пайдаланылады. Оны Ansible және Kubernetes сияқты алыптар сияқты қарапайым құралдар да пайдаланады. YAML шегінісінің ауыртпалығын сезіну үшін қарапайым Ansible файлын жазып көріңіз және ол күткендей жұмыс істемес бұрын файлды қанша өңдеу керек екенін көріңіз. Бұл форматты барлық негізгі IDE қолдайтынына қарамастан! Осыдан кейін осы нұсқаулықты оқуды аяқтау үшін оралыңыз.Yaml:
- is:
- so
- great
Бөлінген транзакциялар туралы не деуге болады? Өнімділік сынағы? Басқа тақырыптар?
Мүмкін бір күні нұсқаулықтың болашақ басылымдарында. Әзірге, бұл бәрі. Бізбен бірге болыңыздар!Микросервистердің тұжырымдамалық мәселелері
Java-дағы микросервистердің нақты мәселелерінен басқа, басқа да проблемалар бар, айталық, кез келген микросервис жобасында пайда болады. Олар негізінен ұйымға, командаға және басқаруға қатысты.Frontend және Backend сәйкессіздігі
Frontend және Backend сәйкес келмеуі көптеген микросервис жобаларында жиі кездесетін мәселе болып табылады. Ол нені білдіреді? Тек жақсы ескі монолиттерде веб-интерфейс әзірлеушілерінде деректерді алудың бір нақты көзі болған. Микросервис жобаларында, фронтальды әзірлеушілер кенеттен деректерді алу үшін n көзге ие болады. Сіз Java тілінде IoT (Internet of Things) микросервис жобасын жасап жатырсыз деп елестетіңіз. Сіз бүкіл Еуропада геодезиялық машиналар мен өнеркәсіптік пештерді басқарасыз делік. Және бұл пештер сізге температуралары және т.б. туралы тұрақты жаңартулар жібереді. Ерте ме, кеш пе, "пеш іздеу" микросервистерін пайдаланып, әкімші интерфейсінде пештерді тапқыңыз келуі мүмкін. Сервердегі әріптестер доменге негізделген дизайнды немесе микросервис заңдарын қаншалықты қатаң қолданатынына байланысты «пешті табу» микросервисі түрі, үлгісі немесе орны сияқты басқа деректерді емес, тек пеш идентификаторларын қайтара алады. Бұл әрекетті орындау үшін, фронтенді әзірлеушілер бірінші микросервистен алған идентификаторларымен «пеш деректерін алу» микросервисінде бір немесе n қосымша қоңырауды (пейджингті іске асыруға байланысты) жасауы керек. Бұл қарапайым мысал болса да, нақты (!) жобадан алынғанымен, ол келесі мәселені көрсетеді: супермаркеттер өте танымал болды. Себебі олармен көкөніс, лимонад, мұздатылған пицца және дәретхана қағазын сатып алу үшін 10 түрлі жерге барудың қажеті жоқ. Оның орнына сіз бір жерге барасыз. Бұл оңай әрі жылдам. Бұл алдыңғы қатарлы және микросервис әзірлеушілеріне де қатысты.Басқарудың күтулері
Менеджмент енді (жалпы) жоба үшін әзірлеушілердің шексіз санын жалдау керек деген қате пікірде, өйткені әзірлеушілер енді бір-бірінен толығымен тәуелсіз, әрқайсысы өз микросервисінде жұмыс істей алады. Ең соңында (іске қосудан аз уақыт бұрын) аз ғана интеграциялық жұмыс қажет. Шын мәнінде, бұл тәсіл өте проблемалы. Келесі тармақтарда біз мұның себебін түсіндіруге тырысамыз.«Кішкентай бөліктер» «жақсы бөліктерге» тең емес
20 бөлікке бөлінген code бір тұтас бөлікке қарағанда міндетті түрде жоғарырақ болады деп болжау үлкен қателік болар еді. Сапаны таза техникалық тұрғыдан алсақ та, біздің жеке қызметтеріміз әлі де қолдау көрсетілмейтін code қабаттарын аралап, дерекқордан пайдаланушыны таңдау үшін 400 күту режимін сұрауды орындауы мүмкін. Біз Саймон Браунның дәйексөзіне қайта ораламыз: егер сіз монолиттерді дұрыс құрастыра алмасаңыз, тиісті микросервистерді құру қиын болады. Микросервис жобаларындағы ақауларға төзімділік туралы айту өте кеш. Микросервистердің нақты жобаларда қалай жұмыс істейтінін көру кейде қорқынышты. Мұның себебі Java әзірлеушілері ақауларға төзімділік, желіні құру және басқа да қатысты тақырыптарды тиісті деңгейде зерттеуге әрқашан дайын емес. «Бөлшектердің» өздері кішірек, бірақ «техникалық бөліктер» үлкенірек. Елестетіп көріңізші, сіздің микросервис тобыңыздан дерекқор жүйесіне кіру үшін техникалық микросервис жазу сұралады, мысалы:@Controller
class LoginController {
// ...
@PostMapping("/login")
public boolean login(String username, String password) {
User user = userDao.findByUserName(username);
if (user == null) {
// обработка варианта с несуществующим пользователем
return false;
}
if (!user.getPassword().equals(hashed(password))) {
// обработка неверного пароля
return false;
}
// 'Ю-ху, залогинorсь!';
// установите cookies, делайте, что угодно
return true;
}
}
Енді сіздің командаңыз мұның бәрі тым қарапайым және қызықсыз екенін шешуі мүмкін (тіпті іскер адамдарды да сендіре алады), логин қызметін жазудың орнына, нақты және нақты іскерлік талаптарсыз шынымен пайдалы UserStateChanged микросервисін жазған дұрыс. Қазіргі уақытта кейбір адамдар Java-ға динозавр сияқты қарайтындықтан, UserStateChanged микросервисімізді сәнді Erlang тілінде жазайық. Бір жерде қызыл-қара ағаштарды қолданып көрейік, өйткені Стив Йегге Google-ға өтініш беру үшін оларды іштей білу керек деп жазды. Интеграция, техникалық қызмет көрсету және жалпы дизайн тұрғысынан бұл бір монолит ішінде спагетти codeының қабаттарын жазу сияқты жаман. Жасанды және қарапайым мысал? Дәл солай. Дегенмен, бұл іс жүзінде болуы мүмкін.
Аз бөліктер - аз түсіну
Содан кейін табиғи түрде жүйені, оның процестерін және жұмыс ағындарын түсіну туралы сұрақ туындайды, бірақ сонымен бірге сіз әзірлеуші ретінде оқшауланған микросервисіңізде жұмыс істеуге ғана жауаптысыз [95: login-101: updateUserProfile]. Ол алдыңғы абзацпен үйлеседі, бірақ ұйымыңызға, сенім деңгейіне және байланыс деңгейіне байланысты бұл микросервис тізбегінде кездейсоқ бұзылу орын алса, көп шатасуға, иығын көтеруге және кінәлауға әкелуі мүмкін. Ал болған оқиға үшін жауапкершілікті өз мойнына алатын ешкім жоқ. Және бұл мүлдем арамдық емес. Шындығында, әртүрлі бөліктерді біріктіру және олардың жобаның жалпы суретіндегі орнын түсіну өте қиын.Байланыс және қызмет көрсету
Байланыс және қызмет көрсету деңгейі компанияның көлеміне байланысты айтарлықтай өзгереді. Дегенмен, жалпы байланыс айқын: неғұрлым көп болса, соғұрлым проблемалық.- №47 микросервисті кім басқарады?
- Олар микросервистің жаңа, үйлеспейтін нұсқасын жай ғана қолданды ма? Бұл қайда құжатталған?
- Жаңа мүмкіндікті сұрау үшін кіммен сөйлесуім керек?
- Осы тілді білетін жалғыз адам компаниядан кеткеннен кейін Ерлангтағы микросервисті кім қолдайды?
- Біздің барлық микросервис командалары әртүрлі бағдарламалау тілдерінде ғана емес, сонымен қатар әртүрлі уақыт белдеуінде де жұмыс істейді! Осының бәрін қалай дұрыс үйлестіреміз?
GO TO FULL VERSION