Isdhexgalka qaabka BPM

Isdhexgalka qaabka BPM

Hello, Habr!

Shirkadeena waxay ku takhasustay horumarinta xalalka ERP-class software, kaas oo qaybta libaaxa ay ku jiraan nidaamyada macaamilka oo leh qadar aad u badan oo caqli-gal ganacsi iyo shaqo-socodka a la EDMS. Noocyada casriga ah ee badeecadaheena waxay ku saleysan yihiin tignoolajiyada JavaEE, laakiin sidoo kale waxaan si firfircoon u tijaabineynaa adeegaha yar yar. Mid ka mid ah meelaha ugu dhibka badan ee xalalka noocan oo kale ah waa is-dhexgalka nidaamyada hoosaadyada kala duwan ee la xidhiidha qaybaha ku xiga. Hawlaha is-dhexgalka ayaa had iyo jeer ina siinaya madax-xanuun aad u weyn, iyadoon loo eegin qaababka dhismaha, tignoolajiyada iyo qaab-dhismeedka aan isticmaalno, laakiin dhawaanahan waxaa jiray horumar xagga xallinta dhibaatooyinkan oo kale ah.

Maqaalka loo keenay dareenkaaga, waxaan ka hadli doonaa khibrada iyo cilmi baarista qaab dhismeedka NPO Krista ee aagga loo qoondeeyay. Waxaan sidoo kale tixgelin doonaa tusaale ahaan xal fudud oo lagu xallinayo dhibaatada isdhexgalka marka laga eego aragtida horumariyaha arjiga oo aan ogaano waxa qarsoon ee ka dambeeya fududaantan.

Afeef

Xalalka dhismaha iyo farsamada ee lagu qeexay maqaalka waxaa bixiya aniga oo ku salaysan khibrad shakhsi ahaaneed oo ku saabsan hawlaha gaarka ah. Xalalkani ma sheeganayaan inay yihiin caalami waxaana laga yaabaa inaysan ku fiicnayn shuruudaha kale ee isticmaalka.

Maxay BPM ka leedahay?

Si aan uga jawaabno su'aashan, waxaan u baahannahay inaan wax yar ka tagno dhibaatooyinka gaarka ah ee xalalkayaga. Qaybta ugu muhiimsan ee macquulka ganacsiga ee nidaamkayaga macaamil ganacsi ee caadiga ah waa gelitaanka xogta xogta iyada oo loo marayo isdhexgalka isticmaalaha, gacanta iyo si toos ah u hubinaya xogtan, u gudubta qaar ka mid ah socodka shaqada, u daabacaadda nidaam kale / xogta falanqaynta / kaydka, soo saarista warbixinnada. Sidaa darteed, shaqada muhiimka ah ee nidaamka macaamiisha waa otomatiga hababka ganacsi ee gudaha.

Si ay ugu habboonaato, waxaan u isticmaalnaa ereyga "document" xagga isgaarsiinta sida qaar ka mid ah soo saarista xogta, oo ay ku midoobeen fure caadi ah, kaas oo socodka shaqada gaarka ah lagu "ku lifaaqi karo".
Laakiin ka waran macquulka isdhexgalka? Ka dib oo dhan, hawsha is-dhexgalka waxaa soo saaray qaab dhismeedka nidaamka, kaas oo "lagu sawiray" qaybo MA codsiga macaamilka, laakiin iyada oo ay saameynayso arrimo gebi ahaanba kala duwan:

  • iyada oo la adeegsanayo sharciga Conway;
  • iyada oo ay sabab u tahay dib-u-isticmaalka nidaamyada-hoosaadka ee hore loogu sameeyay alaabada kale;
  • sida uu go'aamiyay naqshadeeyaha, oo ku salaysan shuruudaha aan shaqaynayn.

Waxaa jira tijaabin weyn oo lagu kala soocayo caqli-galnimada is-dhexgalka iyo caqli-galnimada ganacsiga ee qulqulka shaqada ee ugu weyn si aan loo nijaasayn caqli-galnimada ganacsiga ee farshaxannada is-dhexgalka oo laga badbaadiyo soo-saare arji si uu u dhexgalo sifooyinka muuqaalka dhismaha ee nidaamka. Habkani wuxuu leeyahay faa'iidooyin dhowr ah, laakiin ku-dhaqanku wuxuu muujinayaa waxtarla'aantiisa:

  • xallinta mashaakilaadka isdhexgalka sida caadiga ah waxay hoos ugu dhacaysaa xulashooyinka ugu fudud qaab wicitaano isku mid ah sababtoo ah dhibcaha fidinta xaddidan ee hirgelinta socodka shaqada ee ugu muhiimsan (wax badan oo ku saabsan cilladaha isdhexgalka isku midka ah ee hoose);
  • artifacts is-dhexgalka ayaa weli dhex galaya macquulka ganacsiga ugu weyn marka jawaab-celinta nidaam-hoosaad kale loo baahan yahay;
  • horumariyaha arjigu wuu iska indhatiraa isdhexgalka wuxuuna si fudud u jebin karaa isagoo bedelaya socodka shaqada;
  • Nidaamku wuxuu joojinayaa inuu ahaado hal dhan oo ka soo jeeda aragtida isticmaalaha, "seams" ee u dhexeeya nidaamyada hoose waxay noqdaan kuwo la dareemo, hawlgallada isticmaalaha ee aan caadiga ahayn waxay muuqdaan kuwaas oo bilaabaya wareejinta xogta hal nidaam hoosaad oo kale.

Hab kale ayaa ah in la tixgeliyo isdhexgalka isdhexgalka oo ah qayb muhiim ah oo ka mid ah macquulnimada ganacsiga asaasiga ah iyo socodka shaqada. Si loo ilaaliyo shuruudaha xirfadeed ee soo-saareyaasha dalabka inay cirka isku shareeraan, abuurista isdhexgalka cusub waa in si fudud oo dabiici ah loo sameeyaa, iyada oo leh xulashooyin yar oo lagu dooranayo xalka. Tani way ka adag tahay sida ay u muuqato: qalabku waa inuu noqdaa mid awood leh oo ku filan si uu u siiyo isticmaalaha kala duwanaanshaha lagama maarmaanka ah ee isticmaalka iyo isla mar ahaantaana aan u oggolaan in naftooda lagu toogto cagta. Waxaa jira su'aalo badan oo ay tahay in injineerku uu ka jawaabo macnaha guud ee hawlaha isdhexgalka, laakiin horumariyaha codsiyada waa inuusan ka fikirin shaqadooda maalinlaha ah: xuduudaha macaamilka, joogtaynta, atomity, amniga, miisaanka, qaybinta rarka iyo qaybinta kheyraadka, marin-u-socodka, marshaling, Faafinta iyo beddelka xaaladaha, iwm. Waa lagama maarmaan in la bixiyo soo-saareyaasha arjiyada qaab go'aan fudud oo caddaalad ah, kuwaas oo jawaabaha dhammaan su'aalahan oo kale ay yihiin kuwo horeba u qarsoon. Nidaamyadani waa inay ahaadaan kuwo aamin ah oo ku filan: caqli-galnimada ganacsigu marar badan ayuu isbeddelaa, taas oo kordhisa khatarta soo-saarka khaladaadka, kharashka khaladaadka waa inuu ahaadaa heer aad u hooseeya.

Laakiin weli, maxay BPM ku leedahay? Waxaa jira doorashooyin badan oo lagu hirgelinayo socodka shaqada...
Runtii, hirgalinta kale ee hababka ganacsigu aad ayay caan ugu yihiin xalalkeena - iyada oo loo marayo goobta caddaynta ee jaantuska kala-guurka ee gobolka iyo isku xidhka maamulayaasha caqli-gal ganacsi ee kala-guurka. Isla mar ahaantaana, gobolka go'aaminaya booska hadda jira ee "dokumentiga" ee habka ganacsiga waa sifo "document" laftiisa.

Isdhexgalka qaabka BPM
Tani waa sida hawshu u egtahay bilawga mashruuca

Caannimada hirgelinta noocan oo kale ah waxaa sabab u ah fududaynta qaraabada iyo xawaaraha abuurista hababka ganacsiga tooska ah. Si kastaba ha noqotee, marka nidaamyada software-ku noqdaan kuwo aad u adag, qaybta otomaatiga ah ee habka ganacsigu way koraan oo noqotaa mid aad u adag. Waxaa jira baahi loo qabo burburka, dib u isticmaalka qaybo ka mid ah geeddi-socodka, iyo sidoo kale hababka fargeetada si laan kasta loo fuliyo si siman. Xaaladahan oo kale, qalabku wuxuu noqdaa mid aan habooneyn, iyo jaantuska kala-guurka ee gobolka ayaa luminaya nuxurka macluumaadka (isdhexgalka isdhexgalka ayaan ka muuqan jaantuska gabi ahaanba).

Isdhexgalka qaabka BPM
Tani waa sida hawshu u egtahay ka dib dhowr soo noqnoqosho oo caddaynaya shuruudaha

Sida looga baxo xaaladdan waxay ahayd is-dhexgalka matoorka jBPM Alaabooyinka qaarkood oo leh hababka ganacsi ee ugu adag. Muddada gaaban, xalkani wuxuu lahaa xoogaa guulo ah: waxaa suurtogal ah in la hirgeliyo habab ganacsi oo adag iyadoo la ilaalinayo jaantuska saxda ah ee macluumaadka iyo casriga ah ee qoraalka. BPMN2.

Isdhexgalka qaabka BPM
Qayb yar oo ka mid ah habka ganacsiga adag

Muddada dheer, xalku ma uusan ku noolaanin filashooyinka: xoogga sare ee shaqada ee abuurista hababka ganacsiga iyada oo loo marayo qalab muuqaal ah ma ogola in la gaaro tilmaamayaasha wax soo saarka ee la aqbali karo, iyo qalabka laftiisa ayaa noqday mid ka mid ah kuwa ugu neceb horumarinta. Waxaa sidoo kale jiray cabashooyin ku saabsan qaab dhismeedka gudaha ee mishiinka, taas oo keentay muuqaal badan oo ah "boosiyo" iyo "curyaan".

Arrinta ugu wanaagsan ee isticmaalka jBPM waxay ahayd xaqiijinta faa'iidooyinka iyo waxyeelada ay leedahay in la yeesho xaaladdeeda joogtada ah ee tusaale ahaan habka ganacsiga. Waxaan sidoo kale aragnay suurtagalnimada isticmaalka habka habraaca si loo hirgeliyo borotokoolka isdhexgalka adag ee u dhexeeya codsiyada kala duwan iyadoo la adeegsanayo isdhexgalka asynchronous iyada oo loo marayo calaamadaha iyo fariimaha. Joogitaanka dawlad joogta ah ayaa door muhiim ah ka ciyaartaa tan.

Anagoo ka duulayna arrimaha kore, waxaan ku soo gabagabeyn karnaa: Habka habka ee qaabka BPM wuxuu noo ogolaanayaa inaan xallino hawlo badan oo kala duwan si loo habeeyo habab ganacsi oo aad u adag, si isku mid ah ugu habboon hawlaha isdhexgalka ee hababkan oo aan sii wadno awoodda aan ku muujin karno habka la hirgeliyey ee qoraal ku habboon.

Khasaaraha wicitaanada isku midka ah sida qaabka isdhexgalka

Is dhexgalka isku midka ah waxaa loola jeedaa xannibaadda ugu fudud ee wicitaanka. Mid ka mid ah nidaamka hoose wuxuu u shaqeeyaa sidii dhinaca server-ka wuxuuna soo bandhigay API-ga habka la rabo. Nidaam hoose oo kale wuxuu u shaqeeyaa sidii dhinaca macmiilka oo, wakhtiga saxda ah, wuxuu sameeyaa wicitaan iyadoo la filayo natiijada. Iyadoo ku xiran qaab dhismeedka nidaamka, macmiilka iyo dhinacyada server-ka waxaa lagu martigelin karaa codsi isku mid ah iyo habka, ama kuwa kala duwan. Xaaladda labaad, waxaad u baahan tahay inaad dalbato qaar ka mid ah hirgelinta RPC oo aad bixisid cabbirrada iyo natiijada wicitaanka.

Isdhexgalka qaabka BPM

Habka isdhexgalka ee noocan oo kale ah wuxuu leeyahay dib-u-dhacyo aad u ballaaran, laakiin si aad ah ayaa loo adeegsadaa ficil ahaan sababtoo ah fududaantiisa. Xawaaraha fulinta ayaa soo jiidanaya oo kaa dhigaya inaad mar kale iyo mar kale ku codsato xaaladaha "gubanaya" waqtiyada kama dambaysta ah, qorista xalka deynta farsamada. Laakiin sidoo kale waxay dhacdaa in horumariyayaal aan khibrad lahayn ay u isticmaalaan si miyir la'aan ah, oo aan si fudud u ogaanin cawaaqibta xun.

Marka lagu daro kororka ugu cad ee isku xirnaanta nidaamyada hoose, waxaa jira dhibaatooyin aan muuqan oo aan muuqan oo ku saabsan "fidinta" iyo "fidinta" macaamilada. Runtii, haddii macquulka ganacsigu uu sameeyo isbeddel kasta, markaa wax kala beddelashadu waa lama huraan, wax kala beddelashaduna, beddelkeeda, waxay xidhaan agabka codsiyada qaarkood ee ay saameeyeen isbeddelladan. Taasi waa, ilaa hal nidaam hoosaad ka sugayo jawaabta mid kale, ma awoodi doonto inay dhamaystirto wax kala iibsiga iyo sii deynta qufulyada. Tani waxay si weyn u kordhineysaa halista saameyno kala duwan:

  • U jawaabida nidaamka waa lumay, isticmaalayaashu waxay sugaan waqti dheer jawaabaha codsiyada;
  • Server-ku guud ahaan waxa uu joojiyaa ka jawaabista codsiyada isticmaalaha sababta oo ah barkad dun buux dhaaftay: inta badan duntu waxa ay ku taagan yihiin qufulka kheyraadka uu hayo wax kala iibsiga;
  • xidhidhayaashu waxay bilaabaan inay soo baxaan: suurtogalnimada inay dhacaan si xoog leh waxay ku xiran tahay muddada macaamilada, qadarka macquulka ganacsiga iyo qufulka ku lug leh macaamilka;
  • Khaladaadka dhicitaanka wakhtiga wax kala iibsiga ayaa muuqda;
  • Seerfarku "ku dhaco" OutOfMemory haddii hawshu u baahan tahay habayn iyo beddelaad tiro badan oo xog ah, iyo joogitaanka isku-dhafka isku-dhafka ah ayaa aad u adkeynaya in loo kala qaybiyo hab-socodka "fudud" macaamil ganacsi.

Marka laga eego aragtida qaab-dhismeedka, isticmaalka xannibaadda wicitaannada inta lagu jiro is-dhexgalka waxay keenaysaa lumitaanka xakamaynta tayada ee nidaamyada hoose ee shakhsi ahaaneed: waa wax aan suurtagal ahayn in la hubiyo bartilmaameedyada tayada ee hal nidaam hoose oo ka soocaya bartilmaameedyada tayada ee nidaam hoosaad kale. Haddii nidaamyada hoose ay soo saaraan kooxo kala duwan, tani waa dhibaato weyn.

Arrimuhu aad ayay u xiiso badan yihiin haddii nidaamyada hoose ee la isku daray ay ku jiraan codsiyo kala duwan iyo isbeddello isku mid ah ayaa loo baahan yahay in lagu sameeyo labada dhinacba. Sidee looga dhigayaa isbeddeladan ganacsi?

Haddii isbeddelada lagu sameeyo macaamilo kala duwan, ka dib maarayn adag oo ka reeban iyo magdhow ayaa loo baahan doonaa in la bixiyo, tani waxay si buuxda u tirtiraysaa faa'iidada ugu weyn ee isdhexgalka isku midka ah - fududaanta.

Wax kala iibsiga qaybsan ayaa sidoo kale maskaxda ku soo dhaca, laakiin kuma isticmaalno xalalkayaga: way adag tahay in la hubiyo isku halaynta.

"Saga" sida xal u ah dhibaatada wax kala iibsiga

Iyada oo caannimada sii kordheysa ee adeeg-yaraha, waxaa jira baahi sii kordheysa Habka Saga.

Habkani wuxuu si fiican u xalliyaa dhibaatooyinka kor ku xusan ee macaamil ganacsi dheer, iyo sidoo kale ballaariyo fursadaha lagu maareeyo gobolka nidaamka ka dhanka ah macquulka ganacsiga: magdhow ka dib markii macaamil ganacsi oo aan lagu guulaysan laga yaabaa in aan dib u soo celin nidaamka in ay asal ahaan, laakiin waxay bixiyaan beddelka ah. dariiqa habaynta xogta. Waxay sidoo kale kuu ogolaaneysaa inaadan ku celin si guul leh oo la dhammeeyey tillaabooyinka habaynta xogta markaad isku daydo inaad keento habka "dhammaadka" wanaagsan.

Waxa xiiso leh, nidaamyada monolithic, qaabkani wuxuu sidoo kale khuseeyaa marka ay timaado isdhexgalka nidaamyada hoose ee dabacsan waxaana jira saameyn taban oo ay sababaan wax kala iibsiga dheer iyo qufulka kheyraadka u dhigma.

Marka la eego habraacyadayada ganacsi ee qaabka BPM, waxa ay soo baxday in ay aad u fududahay in la hirgeliyo Sagas-ka: tillaabooyinka shaqsiga ah ee Sagas-ku waxa loo dejin karaa hawlo ka mid ah geeddi-socodka ganacsiga, iyo xaaladda joogtada ah ee habka ganacsiga ayaa go'aamisa, waxyaabo kale, xaaladda gudaha ee Sagas. Taasi waa, uma baahnid hab iskudubarid dheeraad ah. Waxa kaliya ee aad u baahan tahay waa dillaal fariin ah oo leh taageero "ugu yaraan hal mar" dammaanad qaad ahaan.

Laakiin xalka noocan oo kale ah wuxuu kaloo leeyahay "qiimaha" u gaar ah:

  • caqliga ganacsigu wuxuu noqdaa mid aad u adag: waxaad u baahan tahay inaad ka shaqeyso magdhow;
  • waxay noqon doontaa lagama maarmaan in la iska dhaafo joogtaynta buuxda, taas oo si gaar ah xasaasi ugu noqon karta nidaamyada monolithic;
  • qaab-dhismeedku wuxuu noqdaa mid aad u dhib badan, waxaa jira baahi dheeraad ah oo loo qabo fariinta fariinta;
  • qalab dheeraad ah oo la socodka iyo maamulka ayaa loo baahan doonaa (inkastoo guud ahaan tani ay tahay xitaa wanaagsan: tayada adeegga nidaamka ayaa kordhin doona).

Nidaamyada monolithic, xaq u yeelashada isticmaalka "Sags" maaha mid iska cad. Adeegga-yaraha iyo SOA-yada kale, halkaas oo, ay u badan tahay, waxaa horay u jiray dilaaliye, iyo joogteynta buuxda ayaa la huray bilowga mashruuca, faa'iidooyinka isticmaalka qaabkan ayaa si weyn uga miisaan weynaan kara khasaarooyinka, gaar ahaan haddii ay jirto API ku habboon heerka macquulka ganacsiga.

Soo koobida macquulka ganacsiga ee adeegyadda yar yar

Markii aan bilownay tijaabinta adeeg-yaraha, su'aal macquul ah ayaa kacday: halkee la dhigayaa macquulka ganacsiga domain ee la xiriira adeegga bixiya joogteynta xogta domain?

Markaad eegto qaab dhismeedka BPMS kala duwan, waxay u ekaan kartaa mid macquul ah in la kala saaro macquulka ganacsiga iyo joogteynta: samee lakabka madal iyo adeeg-yaro madax-bannaan oo domain ah kuwaas oo sameeya jawiga iyo weelka lagu fulinayo macquulka ganacsiga domain, oo u habeeya ku adkaysiga xogta domain si gooni ah lakabka adeegyo yar yar oo aad u fudud oo fudud. Nidaamyada ganacsi ee kiiskan ayaa abaabula adeegyada lakabka adkaysiga.

Isdhexgalka qaabka BPM

Habkani wuxuu leeyahay faa'iido aad u weyn: waxaad kordhin kartaa shaqeynta goobta inta aad rabto, oo kaliya lakabka u dhigma ee microservices madal ayaa "dufan doona" tan. Nidaamyada ganacsi ee ka socda domain kasta isla markiiba waxay helayaan fursad ay ku isticmaalaan shaqeynta cusub ee madal isla marka la cusboonaysiiyo.

Daraasad aad u tifaftiran ayaa muujisay cilladaha la taaban karo ee habkan:

  • adeeg madal ah oo fulinaya macquulka ganacsiga ee goobo badan oo hal mar ah ayaa wata khataro waaweyn sida hal dhibic oo guul darro ah. Isbeddellada soo noqnoqda ee caqli-galnimada ganacsigu waxay kordhiyaan khatarta dhiqlaha u horseedaya guul-darrooyinka nidaamka-ballaaran;
  • arrimaha waxqabadka: caqli-gal ganacsigu wuxuu ku shaqeeyaa xogtiisa iyada oo loo marayo interface cidhiidhi ah oo gaabis ah:
    • xogta ayaa mar kale la miiray oo lagu shubi doonaa iyada oo la dhex gelinayo xirmooyinka shabakadda;
    • adeega domain ayaa inta badan soo celin doona xog ka badan inta macquulka ganacsigu u baahan yahay habaynta,sabato ah awoodaha cabbiraadda weydiinta oo aan ku filnayn heerka API dibadda ee adeega;
    • dhowr qaybood oo madax-bannaan oo caqli-gal ganacsi ah ayaa si isdaba-joog ah u codsan kara xog isku mid ah si loo farsameeyo (waxaad yareyn kartaa dhibaatadan adigoo ku daraya digirta fadhiga ee kaydinta xogta, laakiin tani waxay sii adkeyneysaa dhismaha waxayna abuurtaa dhibaatooyinka cusub ee xogta iyo khasnad la'aanta);
  • arrimaha wax kala iibsiga:
    • Nidaamyada ganacsi ee leh xaalad joogto ah oo lagu kaydiyo adeegga madalku waa kuwo aan waafaqsanayn xogta domain, mana jiraan siyaabo sahlan oo lagu xalliyo dhibaatadan;
    • ka wareejinta qufulka xogta domain ee ka baxsan macaamilka: haddii macquulka ganacsiga domain u baahan yahay inuu isbedel sameeyo, ka dib marka ugu horeysa ee la hubiyo saxnaanta xogta dhabta ah, waxaa lagama maarmaan ah in laga saaro suurtagalnimada isbeddel tartan ah ee xogta la farsameeyay. Xakamaynta dibadda ee xogta waxay kaa caawin kartaa xalinta dhibaatada, laakiin xalka noocan oo kale ah wuxuu xambaarsan yahay khataro dheeraad ah wuxuuna yareeyaa isku halaynta guud ee nidaamka;
  • dhibaatooyin dheeri ah marka la cusboonaysiinayo: xaaladaha qaarkood, waxaad u baahan tahay inaad cusboonaysiiso adeegga adkaysiga iyo caqliga ganacsiga si isku mid ah ama isku xigxig adag.

Dhammaadkii, waa inaan dib ugu noqdaa aasaaska: ku duub xogta domainka iyo macquulka ganacsiga domain ee hal adeeg yar yar. Habkani wuxuu fududeeyaa aragtida adeeg-yaraha oo ah qayb muhiim ah oo ka mid ah nidaamka mana keenayso dhibaatooyinka kor ku xusan. Tani sidoo kale bilaash maaha:

  • Halbeegga API ayaa looga baahan yahay isdhexgalka macquulka ganacsiga (gaar ahaan, si loo bixiyo waxqabadyada isticmaalaha iyada oo qayb ka ah hababka ganacsiga) iyo adeegyada goobta API; Fiiro gaar ah u leh isbeddelada API, waafaqid horay iyo gadaalba ayaa loo baahan yahay;
  • waxaa loo baahan yahay in lagu daro maktabado runtime dheeraad ah si loo hubiyo shaqeynta macquulka ganacsiga sida qayb ka mid ah adeeg kasta oo yar yar, tani waxay dhalinaysaa shuruudaha cusub ee maktabadaha sida: khafiif ah iyo ugu yaraan ku tiirsanaanta ku-meel-gaadhka ah;
  • Horumarinta macquulka ganacsiga waxay u baahan yihiin inay la socdaan noocyada maktabadda: haddii adeeg-yaraha aan la dhamaystirin wakhti dheer, markaa waxay u badan tahay inay ku jiraan nooc duugoobay oo maktabadaha ah. Tani waxay caqabad lama filaan ah ku noqon kartaa in lagu daro sifo cusub waxaana laga yaabaa inay u baahato caqli-galkii ganacsi ee hore ee adeegan oo kale in loo haajiro nuucyada cusub ee maktabadaha hadii ay jiraan isbedelo aan ku haboonayn oo u dhexeeya noocyada.

Isdhexgalka qaabka BPM

Lakabka adeegyada madal ayaa sidoo kale ku jira qaab-dhismeedka noocan oo kale ah, laakiin lakabkani hadda ma sameeyo weel lagu fulinayo macquulka ganacsiga domain, laakiin kaliya deegaankiisa, oo bixiya hawlaha "madal" caawiya. Lakabka noocan oo kale ah ayaa loo baahan yahay ma aha oo kaliya in la ilaaliyo iftiinka domain-ka microservices, laakiin sidoo kale in la dhexdhexaadiyo maamulka.

Tusaale ahaan, hawlaha isticmaalaha ee hababka ganacsiga waxay abuuraan hawlo. Si kastaba ha noqotee, marka la shaqeynayo hawlaha, isticmaaluhu waa inuu arko hawlaha dhammaan xayndaabyada liiska guud, taas oo macnaheedu yahay in ay jirto adeeg ku habboon diiwaangelinta shaqada, oo laga nadiifiyay macquulka ganacsiga domain. Ku haysashada soo koobida macquulka ganacsiga ee macnaha guud waa dhibaato, tanina waa tanaasul kale oo dhismahan ah.

Isdhexgalka hababka ganacsiga iyada oo loo marayo indhaha horumariyaha codsiga

Sida kor ku xusan, soo-saare arji waa in laga soo saaraa sifooyinka farsamada iyo injineernimada ee hirgelinta isdhexgalka codsiyada dhowr ah si loo awoodo in lagu tiriyo wax soo saarka horumarinta wanaagsan.

Aan isku dayno inaan xalino mushkilad adag oo is dhexgalka ah, oo si gaar ah loogu hindisay maqaalka. Tani waxay noqon doontaa hawl "ciyaar" ah oo ku lug leh saddex codsi, halkaas oo mid kasta oo iyaga ka mid ahi uu qeexayo magac domain: "app1", "app2", "app3".

Codsi kasta dhexdiisa, habab ganacsi ayaa bilaabmaya oo bilaabaya in lagu "ciyaaro kubbadda" baska isdhexgalka. Farimaha lagu magacaabo "Kubad" waxay u dhaqmi doonaan sida kubbadda.

Xeerarka ciyaarta:

  • Ciyaaryahanka ugu horreeya waa hindise. Ciyaartoyda kale ayuu ku casuumaa ciyaarta, ciyaarta ayuu bilaabaa oo wuu dhamayn karaa wakhti kasta;
  • ciyaartoyda kale waxay ku dhawaaqaan ka qaybgalka ciyaarta, "isbartaan" midba midka kale iyo ciyaaryahanka ugu horreeya;
  • Ka dib marka uu helo kubada, ciyaaryahanka ayaa dooranaya ciyaaryahan kale oo ka qayb qaadanaya oo u dhiiba kubada. Wadarta tirada baasaska waa la tiriyaa;
  • ciyaaryahan kastaa wuxuu leeyahay "tamar", kaas oo hoos u dhigaya baas kasta oo kubbada ah ee ciyaaryahankaas. Marka tamartu dhammaato, ciyaartoyga ayaa laga saaray ciyaarta, isagoo ku dhawaaqaya inuu ka fariistay;
  • haddii ciyaartoygu keligiis laga tago, isla markiiba wuxuu ku dhawaaqay inuu baxayo;
  • marka dhammaan ciyaartoyda la ciribtiro, ciyaaryahanka ugu horreeya wuxuu ku dhawaaqaa dhamaadka ciyaarta. Haddii uu hore uga tagay ciyaarta, markaas way ku hadhaysaa in la raaco ciyaarta si loo dhamaystiro.

Si loo xalliyo dhibaatadan, waxaan u isticmaali doonaa DSL-kayaga hababka ganacsiga, kaas oo kuu ogolaanaya inaad si kooban u sharaxdo macquulka ah ee Kotlin, oo leh ugu yaraan biyo kululeeyaha.

Codsiga app1, habka ganacsi ee ciyaartoyga ugu horreeya (isaga sidoo kale waa bilawga ciyaarta) ayaa shaqayn doona:

fasalka InitialPlayer

import ru.krista.bpm.ProcessInstance
import ru.krista.bpm.runtime.ProcessImpl
import ru.krista.bpm.runtime.constraint.UniqueConstraints
import ru.krista.bpm.runtime.dsl.processModel
import ru.krista.bpm.runtime.dsl.taskOperation
import ru.krista.bpm.runtime.instance.MessageSendInstance

data class PlayerInfo(val name: String, val domain: String, val id: String)

class PlayersList : ArrayList<PlayerInfo>()

// Π­Ρ‚ΠΎ класс экзСмпляра процСсса: инкапсулируСт Π΅Π³ΠΎ Π²Π½ΡƒΡ‚Ρ€Π΅Π½Π½Π΅Π΅ состояниС
class InitialPlayer : ProcessImpl<InitialPlayer>(initialPlayerModel) {
    var playerName: String by persistent("Player1")
    var energy: Int by persistent(30)
    var players: PlayersList by persistent(PlayersList())
    var shotCounter: Int = 0
}

// Π­Ρ‚ΠΎ дСкларация ΠΌΠΎΠ΄Π΅Π»ΠΈ процСсса: создаСтся ΠΎΠ΄ΠΈΠ½ Ρ€Π°Π·, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ΡΡ всСми
// экзСмплярами процСсса ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰Π΅Π³ΠΎ класса
val initialPlayerModel = processModel<InitialPlayer>(name = "InitialPlayer",
                                                     version = 1) {

    // По ΠΏΡ€Π°Π²ΠΈΠ»Π°ΠΌ, ΠΏΠ΅Ρ€Π²Ρ‹ΠΉ ΠΈΠ³Ρ€ΠΎΠΊ являСтся ΠΈΠ½ΠΈΡ†ΠΈΠ°Ρ‚ΠΎΡ€ΠΎΠΌ ΠΈΠ³Ρ€Ρ‹ ΠΈ Π΄ΠΎΠ»ΠΆΠ΅Π½ Π±Ρ‹Ρ‚ΡŒ СдинствСнным
    uniqueConstraint = UniqueConstraints.singleton

    // ОбъявляСм активности, ΠΈΠ· ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Ρ… состоит бизнСс-процСсс
    val sendNewGameSignal = signal<String>("NewGame")
    val sendStopGameSignal = signal<String>("StopGame")
    val startTask = humanTask("Start") {
        taskOperation {
            processCondition { players.size > 0 }
            confirmation { "ΠŸΠΎΠ΄ΠΊΠ»ΡŽΡ‡ΠΈΠ»ΠΎΡΡŒ ${players.size} ΠΈΠ³Ρ€ΠΎΠΊΠΎΠ². НачинаСм?" }
        }
    }
    val stopTask = humanTask("Stop") {
        taskOperation {}
    }
    val waitPlayerJoin = signalWait<String>("PlayerJoin") { signal ->
        players.add(PlayerInfo(
                signal.data!!,
                signal.sender.domain,
                signal.sender.processInstanceId))
        println("... join player ${signal.data} ...")
    }
    val waitPlayerOut = signalWait<String>("PlayerOut") { signal ->
        players.remove(PlayerInfo(
                signal.data!!,
                signal.sender.domain,
                signal.sender.processInstanceId))
        println("... player ${signal.data} is out ...")
    }
    val sendPlayerOut = signal<String>("PlayerOut") {
        signalData = { playerName }
    }
    val sendHandshake = messageSend<String>("Handshake") {
        messageData = { playerName }
        activation = {
            receiverDomain = process.players.last().domain
            receiverProcessInstanceId = process.players.last().id
        }
    }
    val throwStartBall = messageSend<Int>("Ball") {
        messageData = { 1 }
        activation = { selectNextPlayer() }
    }
    val throwBall = messageSend<Int>("Ball") {
        messageData = { shotCounter + 1 }
        activation = { selectNextPlayer() }
        onEntry { energy -= 1 }
    }
    val waitBall = messageWaitData<Int>("Ball") {
        shotCounter = it
    }

    // Π’Π΅ΠΏΠ΅Ρ€ΡŒ конструируСм Π³Ρ€Π°Ρ„ процСсса ΠΈΠ· ΠΎΠ±ΡŠΡΠ²Π»Π΅Π½Π½Ρ‹Ρ… активностСй
    startFrom(sendNewGameSignal)
            .fork("mainFork") {
                next(startTask)
                next(waitPlayerJoin).next(sendHandshake).next(waitPlayerJoin)
                next(waitPlayerOut)
                        .branch("checkPlayers") {
                            ifTrue { players.isEmpty() }
                                    .next(sendStopGameSignal)
                                    .terminate()
                            ifElse().next(waitPlayerOut)
                        }
            }
    startTask.fork("afterStart") {
        next(throwStartBall)
                .branch("mainLoop") {
                    ifTrue { energy < 5 }.next(sendPlayerOut).next(waitBall)
                    ifElse().next(waitBall).next(throwBall).loop()
                }
        next(stopTask).next(sendStopGameSignal)
    }

    // НавСшаСм Π½Π° активности Π΄ΠΎΠΏΠΎΠ»Π½ΠΈΡ‚Π΅Π»ΡŒΠ½Ρ‹Π΅ ΠΎΠ±Ρ€Π°Π±ΠΎΡ‚Ρ‡ΠΈΠΊΠΈ для логирования
    sendNewGameSignal.onExit { println("Let's play!") }
    sendStopGameSignal.onExit { println("Stop!") }
    sendPlayerOut.onExit { println("$playerName: I'm out!") }
}

private fun MessageSendInstance<InitialPlayer, Int>.selectNextPlayer() {
    val player = process.players.random()
    receiverDomain = player.domain
    receiverProcessInstanceId = player.id
    println("Step ${process.shotCounter + 1}: " +
            "${process.playerName} >>> ${player.name}")
}

Marka lagu daro fulinta macquulka ganacsiga, koodhka sare wuxuu soo saari karaa qaabka shayga ee habka ganacsiga kaas oo loo arki karo jaantus ahaan. Weli ma aanan hirgelin muuqaal-sameeyaha, markaa waxay ahayd inaan waqti yar ku qaadanno sawirista (halkan waxaan xoogaa fududeeyay qoraalka BPMN ee ku saabsan adeegsiga irdaha si loo hagaajiyo joogtaynta jaantuska leh koodka sare):

Isdhexgalka qaabka BPM

app2 waxa ku jiri doona habka ganacsi ee ciyaaryahan kale:

fasalka RandomPlayer

import ru.krista.bpm.ProcessInstance
import ru.krista.bpm.runtime.ProcessImpl
import ru.krista.bpm.runtime.dsl.processModel
import ru.krista.bpm.runtime.instance.MessageSendInstance

data class PlayerInfo(val name: String, val domain: String, val id: String)

class PlayersList: ArrayList<PlayerInfo>()

class RandomPlayer : ProcessImpl<RandomPlayer>(randomPlayerModel) {

    var playerName: String by input(persistent = true, 
                                    defaultValue = "RandomPlayer")
    var energy: Int by input(persistent = true, defaultValue = 30)
    var players: PlayersList by persistent(PlayersList())
    var allPlayersOut: Boolean by persistent(false)
    var shotCounter: Int = 0

    val selfPlayer: PlayerInfo
        get() = PlayerInfo(playerName, env.eventDispatcher.domainName, id)
}

val randomPlayerModel = processModel<RandomPlayer>(name = "RandomPlayer", 
                                                   version = 1) {

    val waitNewGameSignal = signalWait<String>("NewGame")
    val waitStopGameSignal = signalWait<String>("StopGame")
    val sendPlayerJoin = signal<String>("PlayerJoin") {
        signalData = { playerName }
    }
    val sendPlayerOut = signal<String>("PlayerOut") {
        signalData = { playerName }
    }
    val waitPlayerJoin = signalWaitCustom<String>("PlayerJoin") {
        eventCondition = { signal ->
            signal.sender.processInstanceId != process.id 
                && !process.players.any { signal.sender.processInstanceId == it.id}
        }
        handler = { signal ->
            players.add(PlayerInfo(
                    signal.data!!,
                    signal.sender.domain,
                    signal.sender.processInstanceId))
        }
    }
    val waitPlayerOut = signalWait<String>("PlayerOut") { signal ->
        players.remove(PlayerInfo(
                signal.data!!,
                signal.sender.domain,
                signal.sender.processInstanceId))
        allPlayersOut = players.isEmpty()
    }
    val sendHandshake = messageSend<String>("Handshake") {
        messageData = { playerName }
        activation = {
            receiverDomain = process.players.last().domain
            receiverProcessInstanceId = process.players.last().id
        }
    }
    val receiveHandshake = messageWait<String>("Handshake") { message ->
        if (!players.any { message.sender.processInstanceId == it.id}) {
            players.add(PlayerInfo(
                    message.data!!, 
                    message.sender.domain, 
                    message.sender.processInstanceId))
        }
    }
    val throwBall = messageSend<Int>("Ball") {
        messageData = { shotCounter + 1 }
        activation = { selectNextPlayer() }
        onEntry { energy -= 1 }
    }
    val waitBall = messageWaitData<Int>("Ball") {
        shotCounter = it
    }

    startFrom(waitNewGameSignal)
            .fork("mainFork") {
                next(sendPlayerJoin)
                        .branch("mainLoop") {
                            ifTrue { energy < 5 || allPlayersOut }
                                    .next(sendPlayerOut)
                                    .next(waitBall)
                            ifElse()
                                    .next(waitBall)
                                    .next(throwBall)
                                    .loop()
                        }
                next(waitPlayerJoin).next(sendHandshake).next(waitPlayerJoin)
                next(waitPlayerOut).next(waitPlayerOut)
                next(receiveHandshake).next(receiveHandshake)
                next(waitStopGameSignal).terminate()
            }

    sendPlayerJoin.onExit { println("$playerName: I'm here!") }
    sendPlayerOut.onExit { println("$playerName: I'm out!") }
}

private fun MessageSendInstance<RandomPlayer, Int>.selectNextPlayer() {
    val player = if (process.players.isNotEmpty()) 
        process.players.random() 
    else 
        process.selfPlayer
    receiverDomain = player.domain
    receiverProcessInstanceId = player.id
    println("Step ${process.shotCounter + 1}: " +
            "${process.playerName} >>> ${player.name}")
}

Jaantuska:

Isdhexgalka qaabka BPM

Codsiga 3-aad, waxaanu ka dhigi doonaa ciyaartoyga dhaqan ka duwan kii hore: Halkii uu si aan kala sooc lahayn u dooran lahaa ciyaartoyga soo socda, waxa uu u dhaqmi doonaa si waafaqsan algorithm-robin-ka:

fasalka RoundRobinPlayer

import ru.krista.bpm.ProcessInstance
import ru.krista.bpm.runtime.ProcessImpl
import ru.krista.bpm.runtime.dsl.processModel
import ru.krista.bpm.runtime.instance.MessageSendInstance

data class PlayerInfo(val name: String, val domain: String, val id: String)

class PlayersList: ArrayList<PlayerInfo>()

class RoundRobinPlayer : ProcessImpl<RoundRobinPlayer>(roundRobinPlayerModel) {

    var playerName: String by input(persistent = true, 
                                    defaultValue = "RoundRobinPlayer")
    var energy: Int by input(persistent = true, defaultValue = 30)
    var players: PlayersList by persistent(PlayersList())
    var nextPlayerIndex: Int by persistent(-1)
    var allPlayersOut: Boolean by persistent(false)
    var shotCounter: Int = 0

    val selfPlayer: PlayerInfo
        get() = PlayerInfo(playerName, env.eventDispatcher.domainName, id)
}

val roundRobinPlayerModel = processModel<RoundRobinPlayer>(
        name = "RoundRobinPlayer", 
        version = 1) {

    val waitNewGameSignal = signalWait<String>("NewGame")
    val waitStopGameSignal = signalWait<String>("StopGame")
    val sendPlayerJoin = signal<String>("PlayerJoin") {
        signalData = { playerName }
    }
    val sendPlayerOut = signal<String>("PlayerOut") {
        signalData = { playerName }
    }
    val waitPlayerJoin = signalWaitCustom<String>("PlayerJoin") {
        eventCondition = { signal ->
            signal.sender.processInstanceId != process.id 
                && !process.players.any { signal.sender.processInstanceId == it.id}
        }
        handler = { signal ->
            players.add(PlayerInfo(
                    signal.data!!, 
                    signal.sender.domain, 
                    signal.sender.processInstanceId))
        }
    }
    val waitPlayerOut = signalWait<String>("PlayerOut") { signal ->
        players.remove(PlayerInfo(
                signal.data!!, 
                signal.sender.domain, 
                signal.sender.processInstanceId))
        allPlayersOut = players.isEmpty()
    }
    val sendHandshake = messageSend<String>("Handshake") {
        messageData = { playerName }
        activation = {
            receiverDomain = process.players.last().domain
            receiverProcessInstanceId = process.players.last().id
        }
    }
    val receiveHandshake = messageWait<String>("Handshake") { message ->
        if (!players.any { message.sender.processInstanceId == it.id}) {
            players.add(PlayerInfo(
                    message.data!!, 
                    message.sender.domain, 
                    message.sender.processInstanceId))
        }
    }
    val throwBall = messageSend<Int>("Ball") {
        messageData = { shotCounter + 1 }
        activation = { selectNextPlayer() }
        onEntry { energy -= 1 }
    }
    val waitBall = messageWaitData<Int>("Ball") {
        shotCounter = it
    }

    startFrom(waitNewGameSignal)
            .fork("mainFork") {
                next(sendPlayerJoin)
                        .branch("mainLoop") {
                            ifTrue { energy < 5 || allPlayersOut }
                                    .next(sendPlayerOut)
                                    .next(waitBall)
                            ifElse()
                                    .next(waitBall)
                                    .next(throwBall)
                                    .loop()
                        }
                next(waitPlayerJoin).next(sendHandshake).next(waitPlayerJoin)
                next(waitPlayerOut).next(waitPlayerOut)
                next(receiveHandshake).next(receiveHandshake)
                next(waitStopGameSignal).terminate()
            }

    sendPlayerJoin.onExit { println("$playerName: I'm here!") }
    sendPlayerOut.onExit { println("$playerName: I'm out!") }
}

private fun MessageSendInstance<RoundRobinPlayer, Int>.selectNextPlayer() {
    var idx = process.nextPlayerIndex + 1
    if (idx >= process.players.size) {
        idx = 0
    }
    process.nextPlayerIndex = idx
    val player = if (process.players.isNotEmpty()) 
        process.players[idx] 
    else 
        process.selfPlayer
    receiverDomain = player.domain
    receiverProcessInstanceId = player.id
    println("Step ${process.shotCounter + 1}: " +
            "${process.playerName} >>> ${player.name}")
}

Haddii kale, hab-dhaqanka ciyaartoygu kama duwana kii hore, markaa jaantusku isma beddelo.

Hadda waxaan u baahanahay tijaabo si aan u wada wadno. Waxaan ku siin doonaa oo kaliya koodhka imtixaanka laftiisa, si aan u dhicin maqaalka kuleyliyaha (xaqiiqda, waxaan isticmaalay jawiga tijaabada ah ee hore loo abuuray si aan u tijaabiyo isdhexgalka hababka ganacsiga kale):

Ciyaarta tijaabada()

@Test
public void testGame() throws InterruptedException {
    String pl2 = startProcess(app2, "RandomPlayer", playerParams("Player2", 20));
    String pl3 = startProcess(app2, "RandomPlayer", playerParams("Player3", 40));
    String pl4 = startProcess(app3, "RoundRobinPlayer", playerParams("Player4", 25));
    String pl5 = startProcess(app3, "RoundRobinPlayer", playerParams("Player5", 35));
    String pl1 = startProcess(app1, "InitialPlayer");
    // Π’Π΅ΠΏΠ΅Ρ€ΡŒ Π½ΡƒΠΆΠ½ΠΎ Π½Π΅ΠΌΠ½ΠΎΠ³ΠΎ ΠΏΠΎΠ΄ΠΎΠΆΠ΄Π°Ρ‚ΡŒ, ΠΏΠΎΠΊΠ° ΠΈΠ³Ρ€ΠΎΠΊΠΈ "познакомятся" Π΄Ρ€ΡƒΠ³ с Π΄Ρ€ΡƒΠ³ΠΎΠΌ.
    // Π–Π΄Π°Ρ‚ΡŒ Ρ‡Π΅Ρ€Π΅Π· sleep - ΠΏΠ»ΠΎΡ…ΠΎΠ΅ Ρ€Π΅ΡˆΠ΅Π½ΠΈΠ΅, Π·Π°Ρ‚ΠΎ самоС простоС. 
    // НС Π΄Π΅Π»Π°ΠΉΡ‚Π΅ Ρ‚Π°ΠΊ Π² ΡΠ΅Ρ€ΡŒΠ΅Π·Π½Ρ‹Ρ… тСстах!
    Thread.sleep(1000);
    // ЗапускаСм ΠΈΠ³Ρ€Ρƒ, закрывая ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»ΡŒΡΠΊΡƒΡŽ Π°ΠΊΡ‚ΠΈΠ²Π½ΠΎΡΡ‚ΡŒ
    assertTrue(closeTask(app1, pl1, "Start"));
    app1.getWaiting().waitProcessFinished(pl1);
    app2.getWaiting().waitProcessFinished(pl2);
    app2.getWaiting().waitProcessFinished(pl3);
    app3.getWaiting().waitProcessFinished(pl4);
    app3.getWaiting().waitProcessFinished(pl5);
}

private Map<String, Object> playerParams(String name, int energy) {
    Map<String, Object> params = new HashMap<>();
    params.put("playerName", name);
    params.put("energy", energy);
    return params;
}

Orod imtixaanka, fiiri log:

soosaarka console

Взята Π±Π»ΠΎΠΊΠΈΡ€ΠΎΠ²ΠΊΠ° ΠΊΠ»ΡŽΡ‡Π° lock://app1/process/InitialPlayer
Let's play!
Бнята Π±Π»ΠΎΠΊΠΈΡ€ΠΎΠ²ΠΊΠ° ΠΊΠ»ΡŽΡ‡Π° lock://app1/process/InitialPlayer
Player2: I'm here!
Player3: I'm here!
Player4: I'm here!
Player5: I'm here!
... join player Player2 ...
... join player Player4 ...
... join player Player3 ...
... join player Player5 ...
Step 1: Player1 >>> Player3
Step 2: Player3 >>> Player5
Step 3: Player5 >>> Player3
Step 4: Player3 >>> Player4
Step 5: Player4 >>> Player3
Step 6: Player3 >>> Player4
Step 7: Player4 >>> Player5
Step 8: Player5 >>> Player2
Step 9: Player2 >>> Player5
Step 10: Player5 >>> Player4
Step 11: Player4 >>> Player2
Step 12: Player2 >>> Player4
Step 13: Player4 >>> Player1
Step 14: Player1 >>> Player4
Step 15: Player4 >>> Player3
Step 16: Player3 >>> Player1
Step 17: Player1 >>> Player2
Step 18: Player2 >>> Player3
Step 19: Player3 >>> Player1
Step 20: Player1 >>> Player5
Step 21: Player5 >>> Player1
Step 22: Player1 >>> Player2
Step 23: Player2 >>> Player4
Step 24: Player4 >>> Player5
Step 25: Player5 >>> Player3
Step 26: Player3 >>> Player4
Step 27: Player4 >>> Player2
Step 28: Player2 >>> Player5
Step 29: Player5 >>> Player2
Step 30: Player2 >>> Player1
Step 31: Player1 >>> Player3
Step 32: Player3 >>> Player4
Step 33: Player4 >>> Player1
Step 34: Player1 >>> Player3
Step 35: Player3 >>> Player4
Step 36: Player4 >>> Player3
Step 37: Player3 >>> Player2
Step 38: Player2 >>> Player5
Step 39: Player5 >>> Player4
Step 40: Player4 >>> Player5
Step 41: Player5 >>> Player1
Step 42: Player1 >>> Player5
Step 43: Player5 >>> Player3
Step 44: Player3 >>> Player5
Step 45: Player5 >>> Player2
Step 46: Player2 >>> Player3
Step 47: Player3 >>> Player2
Step 48: Player2 >>> Player5
Step 49: Player5 >>> Player4
Step 50: Player4 >>> Player2
Step 51: Player2 >>> Player5
Step 52: Player5 >>> Player1
Step 53: Player1 >>> Player5
Step 54: Player5 >>> Player3
Step 55: Player3 >>> Player5
Step 56: Player5 >>> Player2
Step 57: Player2 >>> Player1
Step 58: Player1 >>> Player4
Step 59: Player4 >>> Player1
Step 60: Player1 >>> Player4
Step 61: Player4 >>> Player3
Step 62: Player3 >>> Player2
Step 63: Player2 >>> Player5
Step 64: Player5 >>> Player4
Step 65: Player4 >>> Player5
Step 66: Player5 >>> Player1
Step 67: Player1 >>> Player5
Step 68: Player5 >>> Player3
Step 69: Player3 >>> Player4
Step 70: Player4 >>> Player2
Step 71: Player2 >>> Player5
Step 72: Player5 >>> Player2
Step 73: Player2 >>> Player1
Step 74: Player1 >>> Player4
Step 75: Player4 >>> Player1
Step 76: Player1 >>> Player2
Step 77: Player2 >>> Player5
Step 78: Player5 >>> Player4
Step 79: Player4 >>> Player3
Step 80: Player3 >>> Player1
Step 81: Player1 >>> Player5
Step 82: Player5 >>> Player1
Step 83: Player1 >>> Player4
Step 84: Player4 >>> Player5
Step 85: Player5 >>> Player3
Step 86: Player3 >>> Player5
Step 87: Player5 >>> Player2
Step 88: Player2 >>> Player3
Player2: I'm out!
Step 89: Player3 >>> Player4
... player Player2 is out ...
Step 90: Player4 >>> Player1
Step 91: Player1 >>> Player3
Step 92: Player3 >>> Player1
Step 93: Player1 >>> Player4
Step 94: Player4 >>> Player3
Step 95: Player3 >>> Player5
Step 96: Player5 >>> Player1
Step 97: Player1 >>> Player5
Step 98: Player5 >>> Player3
Step 99: Player3 >>> Player5
Step 100: Player5 >>> Player4
Step 101: Player4 >>> Player5
Player4: I'm out!
... player Player4 is out ...
Step 102: Player5 >>> Player1
Step 103: Player1 >>> Player3
Step 104: Player3 >>> Player1
Step 105: Player1 >>> Player3
Step 106: Player3 >>> Player5
Step 107: Player5 >>> Player3
Step 108: Player3 >>> Player1
Step 109: Player1 >>> Player3
Step 110: Player3 >>> Player5
Step 111: Player5 >>> Player1
Step 112: Player1 >>> Player3
Step 113: Player3 >>> Player5
Step 114: Player5 >>> Player3
Step 115: Player3 >>> Player1
Step 116: Player1 >>> Player3
Step 117: Player3 >>> Player5
Step 118: Player5 >>> Player1
Step 119: Player1 >>> Player3
Step 120: Player3 >>> Player5
Step 121: Player5 >>> Player3
Player5: I'm out!
... player Player5 is out ...
Step 122: Player3 >>> Player5
Step 123: Player5 >>> Player1
Player5: I'm out!
Step 124: Player1 >>> Player3
... player Player5 is out ...
Step 125: Player3 >>> Player1
Step 126: Player1 >>> Player3
Player1: I'm out!
... player Player1 is out ...
Step 127: Player3 >>> Player3
Player3: I'm out!
Step 128: Player3 >>> Player3
... player Player3 is out ...
Player3: I'm out!
Stop!
Step 129: Player3 >>> Player3
Player3: I'm out!

Dhawr gabagabo oo muhiim ah ayaa laga soo saari karaa kuwan oo dhan:

  • haddii qalabka lagama maarmaanka ah la heli karo, horumarinta arjiyada waxay abuuri karaan isdhexgalka isdhexgalka ee codsiyada iyada oo aan ka go'in macquulnimada ganacsiga;
  • kakanaanta (kakanaanta) hawsha isku-dhafka ah ee u baahan xirfadaha injineernimada ayaa lagu qarin karaa gudaha qaabka haddii markii hore lagu dhejiyay qaab-dhismeedka qaab-dhismeedka. Dhibka hawsha (dhibnaanta) lama qarin karo, markaa xalinta hawsha adag ee koodhka ayaa sidiisa u eegi doonta;
  • marka la horumarinayo macquulka isdhexgalka, waxaa lagama maarmaan ah in la tixgeliyo ugu dambeyntii joogtaynta iyo la'aanta linearizability ee isbeddelka gobolka ee dhammaan ka qaybgalayaasha isdhexgalka. Tani waxay nagu qasbaysaa in aan caqli galno si aan u dareenno sida ay u kala horreeyaan dhacdooyinka dibadda. Tusaalaheena, ciyaaryahanku wuxuu ku qasban yahay inuu ka qayb qaato ciyaarta ka dib markii uu ku dhawaaqay inuu ka baxayo ciyaarta: ciyaartoyda kale waxay sii wadi doonaan inay kubada u gudbiyaan ilaa macluumaadka ku saabsan bixitaankiisa ay gaaraan oo ay maamulaan dhammaan ka qaybgalayaasha. Caqligani kama raacayo xeerarka ciyaarta waana xal tanaasul ah oo ka dhex jira qaabka qaab dhismeedka la doortay.

Marka xigta, aan ka hadalno khiyaanada kala duwan ee xalkeena, tanaasul iyo qodobbo kale.

Dhammaan fariimaha ku jira hal saf

Dhammaan codsiyada isku dhafan waxay la shaqeeyaan hal bas oo isdhexgalka, kaas oo loo soo bandhigay sida dilaaliinta dibadda, hal BPMQueue ee fariimaha iyo hal mawduuc BPMTopic ee calaamadaha (dhacdooyinka). Gudbinta dhammaan fariimaha iyada oo saf keliya laftigeedu waa tanaasul. Heerka macquulka ah ee ganacsiga, waxaad hadda soo bandhigi kartaa noocyo badan oo farriimo ah oo cusub inta aad rabto adiga oo aan isbeddel ku samayn qaabka nidaamka. Tani waa fududayn la taaban karo, laakiin waxay xambaarsan tahay khataro gaar ah, kuwaas oo, marka la eego macnaha hawlaheenna caadiga ah, ay noogu muuqatay mid aan sidaas u weynayn.

Isdhexgalka qaabka BPM

Si kastaba ha ahaatee, waxaa jira hal qarsoodi ah halkan: codsi kastaa wuxuu shaandheeyaa farriimaha "tiisa" ee safka albaabka, magaca domainka. Sidoo kale, domainka waxaa lagu qeexi karaa calaamadaha, haddii aad u baahan tahay inaad xaddido "xadka" calaamadda hal codsi. Tani waa inay kordhisaa xawaaraha baska, laakiin caqli-galnimada ganacsigu waa inay hadda ku shaqeysaa magacyo domain: waa qasab in farriimaha wax looga qabto, lagana helo calaamadaha.

Hubinta isku halaynta baska isdhexgalka

Kalsoonidu waxay ka kooban tahay dhawr waxyaalood:

  • Dhexdhexaadiyaha fariinta la doortay waa qayb muhiim ah oo ka mid ah qaab-dhismeedka iyo hal dhibic oo guul darro ah: waa inay noqotaa mid si ku filan u dulqaadanaysa. Waa inaad isticmaashaa oo kaliya hirgelinta wakhtiga la tijaabiyay oo leh taageero wanaagsan iyo bulsho weyn;
  • waxaa lagama maarmaan ah in la hubiyo helitaanka sare ee fariinta fariinta, taas oo ay tahay in ay jir ahaan ka soocdo codsiyada isku dhafan (helitaanka sare ee codsiyada leh caqli-gal ganacsi oo la dabaqay ayaa aad u adag oo qaali ah in la bixiyo);
  • Dallaalku waxa uu ku qasban yahay in uu bixiyo "ugu yaraan hal mar" dammaanad gaarsiinta. Tani waa shuruudo qasab ah oo loogu talagalay hawlgal la isku halayn karo ee baska isdhexgalka. Looma baahna dammaanad heer "si sax ah hal mar": hababka ganacsigu inta badan maaha kuwo xasaasi u ah imaatinka soo noqnoqda ee fariimaha ama dhacdooyinka, iyo hawlaha gaarka ah ee ay tani muhiim u tahay, way sahlan tahay in lagu daro jeegag dheeraad ah oo ku saabsan macquulka ganacsiga halkii si joogto ah loo isticmaali lahaa. halkii "qaali ah" "dammaanadaha;
  • dirista fariimaha iyo calaamadaha waa in ay ku lug yeeshaan macaamil ganacsi oo caadi ah oo leh isbeddel ku yimaada xaaladda hababka ganacsiga iyo xogta domainka. Doorashada la door biday waxay noqon doontaa in la isticmaalo qaabka Sanduuqa Macaamilka ah, laakiin waxay u baahan doontaa shax dheeraad ah oo ku jira kaydka xogta iyo gudbinta. Codsiyada JEE, tan waxaa lagu fududayn karaa iyadoo la isticmaalayo maareeyaha JTA ee deegaanka, laakiin xidhiidhka dilaaliinta la doortay waa inuu awood u yeeshaa inuu ku shaqeeyo qaab ahaan. XA;
  • maamulayaasha fariimaha soo socda iyo dhacdooyinka waa inay sidoo kale la shaqeeyaan macaamilka beddelka xaaladda habka ganacsiga: haddii macaamilka noocaas ah dib loo rogo, markaa rasiidka farriinta waa in sidoo kale la tirtiro;
  • fariimaha aan la gudbin karin khaladaadka dartiis waa in lagu kaydiyaa bakhaar gaar ah D.L.Q. ( safka warqadda dhintay). Si tan loo sameeyo, waxaanu abuurnay adeeg-yar oo gooni ah oo kaydiya fariimahan oo kale kaydintiisa, ku tilmaamaya sifada (kooxaynta degdega ah iyo raadinta), oo soo bandhigta API-ga si loo daawado, dib loogu diro ciwaanka loo socdo, iyo tirtirida fariimaha. Maamulayaasha nidaamku waxay la shaqayn karaan adeeggan iyaga oo adeegsanaya shabakadooda internetka;
  • goobaha dallaalka, waxaad u baahan tahay inaad hagaajiso tirada isku dayga keenista iyo dib u dhigista u dhexeeya bixinta si loo yareeyo suurtagalnimada fariimaha gelaya DLQ (waa wax aan macquul aheyn in la xisaabiyo cabbirada ugu fiican, laakiin waxaad u dhaqmi kartaa si macquul ah oo aad hagaajin kartaa inta lagu jiro hawlgalka);
  • dukaanka DLQ waa in si joogto ah loola socdo, nidaamka la socodka waa in uu ogeysiiyaa maamulayaasha nidaamka si ay uga jawaabaan sida ugu dhakhsaha badan ee suurtogalka ah marka fariimaha aan la gudbin ay dhacaan. Tani waxay yaraynaysaa "aagga dhaawaca" ee fashilka ama khaladka macquulka ganacsiga;
  • baska isdhexgalka waa in uu ahaado mid aan dareensanayn maqnaanshaha ku meel gaadhka ah ee codsiyada: isdiiwaangelinta mawduuca waa in ay ahaataa mid waara, iyo magaca domainka codsigu waa inuu noqdaa mid gaar ah si qof kale aanu isku dayin inuu fariintiisa ka farsameeyo safka inta lagu jiro maqnaanshaha codsiga.

Xaqiijinta badbaadada dunta ee macquulka ganacsiga

Isla tusaale ahaan habka ganacsigu waxa uu heli karaa fariimo iyo dhacdooyin dhowr ah hal mar, habaynta kuwaas oo si barbar socda u bilaaban doona. Isla mar ahaantaana, horumariyaha arjiga, wax walba waa inay ahaadaan kuwo fudud oo dun-ammaan ah.

Habka caqli-gal ganacsigu waxa uu habeeyaa dhacdo kasta oo dibadda ah oo saamaynaysa habkan ganacsi si gaar ah. Dhacdooyinkani waxay noqon karaan:

  • bilaabida tusaale ahaan habka ganacsiga;
  • ficil isticmaale oo la xidhiidha hawl ka dhex jirta habka ganacsiga;
  • rasiidka fariinta ama calaamada kaas oo tusaale ahaan nidaamka ganacsigu u qoran yahay;
  • dhicitaanka wakhtiga u dejiyay habka ganacsiga tusaale ahaan;
  • xakamaynta ficilka iyada oo loo marayo API (tusaale, habsocodka ilmo iska soo rididda).

Dhacdo kasta oo noocan oo kale ah waxay bedeli kartaa xaaladda habka ganacsiga tusaale ahaan: waxqabadyada qaarkood way dhammaan karaan kuwa kalena waxay bilaabaan, qiyamka guryaha joogtada ah ayaa isbeddeli kara. Xiritaan kasta oo hawl ah waxa laga yaabaa in ay keento firfircoonida mid ama in ka badan oo ka mid ah hawlahan soo socda. Kuwaas, iyaguna, waxay joojin karaan sugidda dhacdooyinka kale, ama, haddii aysan u baahnayn xog dheeraad ah, waxay ku dhammaystiri karaan isla macaamilka. Ka hor inta aan la xidhin macaamil ganacsi, xaaladda cusub ee habka ganacsiga ayaa lagu kaydiyaa kaydka xogta, halkaas oo ay sugi doonto dhacdada soo socota ee dibadda.

Xogta habka ganacsiga ee joogtada ah ee lagu kaydiyo xogta la xidhiidha waa meel habayn aad ugu haboon marka la isticmaalayo XUL UPDATE. Haddii mid ka mid ah macaamil ganacsi uu ku guuleystey inuu helo xaaladda habka ganacsiga ee xogta si uu u beddelo, ka dibna ma jiro macaamil kale oo isku mid ah ma awoodi doono inuu helo isla gobolka isbeddel kale, ka dib marka la dhammeeyo macaamilka koowaad, kan labaad waa kan labaad. dammaanad qaadaysa in la helo xaaladdii hore loo beddelay.

Isticmaalka quful rajo-xumo leh oo dhinaca DBMS ah, waxaan buuxineynaa dhammaan shuruudaha lagama maarmaanka ah AASHITO, iyo sidoo kale in la sii wado awoodda lagu cabbiro arjiga iyadoo la adeegsanayo caqli-gal ganacsi iyadoo la kordhinayo tirada dhacdooyinka socodsiinta.

Si kastaba ha ahaatee, qufullada rajo-xumada leh waxay noogu hanjabaan xidhidhooyin, taas oo macnaheedu yahay in XULASHADA CUSBOONAYSIINTA ay wali ku koobnaan doonto wakhti macquul ah oo wakhti go'an ah haddii ay dhacdo xidhitaanno ku saabsan xaaladaha halista ah ee caqliga ganacsiga.

Dhibaato kale ayaa ah is-waafajinta bilawga habka ganacsiga. Inkastoo aysan jirin tusaale ahaan habka ganacsiga, ma jiro gobol ku jira xogta sidoo kale, markaa habka lagu tilmaamay ma shaqeyn doono. Haddii aad rabto in aad hubiso gaar ahaanshaha geeddi-socodka ganacsiga ee baaxad gaar ah, markaa waxaad u baahan tahay nooc ka mid ah shay isku-dubarid oo la xidhiidha fasalka habka iyo baaxadda u dhiganta. Si loo xaliyo dhibaatadan, waxaanu isticmaalnaa hab lagu xidho oo ka duwan kaas oo noo ogolaanaya inaanu ku xidhno kaydka kheyraadka macmalka ah ee lagu qeexay furaha qaabka URI iyada oo loo marayo adeeg dibadda ah.

Tusaalooyinkayada, habka ganacsiga InitialPlayer wuxuu ka kooban yahay caddayn

uniqueConstraint = UniqueConstraints.singleton

Sidaa darteed, loggu wuxuu ka kooban yahay fariimo ku saabsan qaadashada iyo sii deynta qufulka furaha u dhigma. Ma jiraan farriimahan oo kale oo loogu talagalay hababka kale ee ganacsiga: xannibaad gaar ah lama dejin.

Dhibaatooyinka habka ganacsiga ee xaalad joogto ah

Mararka qaarkood inaad haysato xaalad joogto ah ma aha oo kaliya inay caawiso, laakiin sidoo kale waxay dhab ahaantii hor istaagtaa horumarka.
Dhibaatooyinku waxay bilaabmaan markaad u baahan tahay inaad isbeddel ku samayso macquulka ganacsiga iyo/ama qaabka habka ganacsiga. Wax isbeddel ah oo noocaas ah lama helin inuu ku habboon yahay xaaladdii hore ee geeddi-socodka ganacsiga. Haddii ay jiraan xaalado badan oo "nool" oo ku jira xogta, ka dibna samaynta isbeddelada aan ku habboonayn waxay keeni kartaa dhibaato badan, taas oo aan inta badan la kulanno marka la isticmaalayo jBPM.

Iyada oo ku xidhan qoto dheer ee isbeddelka, waxaad u dhaqmi kartaa laba siyaabood:

  1. in la abuuro hab cusub oo ganacsi si aanu is badal aan ku haboonayn ugu samayn kii hore, isticmaalna halkii kii hore marka aad bilaabayso xaalado cusub. Xaaladihii hore waxay sii wadi doonaan inay shaqeeyaan "habkii hore";
  2. u haajiraan xaalada joogtada ah ee geedi socodka ganacsiga marka la cusboonaysiinayo macquulka ganacsiga.

Habka koowaad waa ka fudud yahay, laakiin wuxuu leeyahay xaddidaaddiisa iyo faa'iido darrooyinkeeda, tusaale ahaan:

  • nuqul ka mid ah macquulka ganacsiga ee qaabab badan oo ganacsi oo ganacsi, korodhka mugga macquulka ganacsiga;
  • inta badan waxaa loo baahan yahay u gudub degdeg ah oo loo galo caqli-gal ganacsi oo cusub (ku dhawaad ​​had iyo jeer marka la eego hawlaha isdhexgalka);
  • horumariyuhu ma garanayo meesha ay suurtogal tahay in la tirtiro moodooyinka duugoobay.

Ficil ahaan, waxaan isticmaalnaa labada qaab, laakiin waxaan gaarnay go'aano dhowr ah si aan u fududeyno nolosheena:

  • kaydka xogta, xaalada joogtada ah ee habka ganacsigu waxa lagu kaydiyaa qaab si sahal ah loo akhriyi karo oo si sahal ah loo habeeyey: oo ah qaabka JSON. Tani waxay kuu ogolaanaysaa inaad samayso guuritaanka gudaha codsiga iyo dibaddaba. Xaaladaha ba'an, waxaad sidoo kale ku dhejin kartaa gacmaha (gaar ahaan waxtar u leh horumarinta inta lagu jiro cilladaha);
  • macquulka ganacsiga isdhexgalka ma isticmaalo magacyada hababka ganacsiga, si wakhti kasta ay suurtogal u tahay in lagu beddelo hirgelinta mid ka mid ah hababka ka qaybqaadashada mid cusub, oo leh magac cusub (tusaale, "InitialPlayerV2"). Xiritaanku wuxuu ku dhacaa magacyada fariimaha iyo calaamadaha;
  • Qaabka habraacku waxa uu leeyahay nambarka nooca, kaas oo aanu kordhinayno hadii aanu ku samayno isbedelo aan ku haboonayn qaabkan, lambarkan waxa lagu kaydiyaa xaalada tusaale ahaan habka;
  • xaaladda joogtada ah ee habka ayaa marka hore laga akhriyaa saldhigga oo loo akhriyaa qaabka shay ku habboon oo habka socdaalka uu ku shaqeyn karo haddii nambarka nooca qaabku isbeddelo;
  • nidaamka socdaalka waxaa la dhigayaa ag si ay macquulka ganacsiga iyo waxaa loo yaqaan "caajis" tusaale kasta oo ka mid ah habka ganacsiga wakhtiga ay dib u soo celinta xogta;
  • Haddii aad u baahan tahay inaad u haajirto xaaladda dhammaan tusaalooyinka geeddi-socodka si dhakhso ah oo isku mid ah, xalal badan oo xog guuritaan ah ayaa la isticmaalaa, laakiin waa inaad JSON kala shaqeysaa halkaas.

Miyaan u baahanahay qaab-dhismeedka kale ee hababka ganacsiga?

Xalalka lagu sharraxay maqaalku waxay noo oggolaadeen inaan si weyn u fududeyno nolosheena, ballaariyo arrimaha kala duwan ee lagu xalliyo heerka horumarinta codsiga, oo aan ka dhigno fikradda kala-soocidda macquulka ganacsiga ee microservices soo jiidasho leh. Tani, shaqo badan ayaa la sameeyay, qaab aad u "fudud" ah oo loogu talagalay hababka ganacsiga ayaa la sameeyay, iyo sidoo kale qaybaha adeegga ee lagu xalliyo dhibaatooyinka la aqoonsaday ee ku jira hawlo badan oo la dabaqay. Waxaan rabnaa inaan wadaagno natiijooyinkaan, si aan u keeno horumarinta qaybaha guud ee gelitaanka furan ee hoos yimaada shatiga bilaashka ah. Tani waxay u baahan doontaa xoogaa dadaal iyo waqti. Fahamka baahida xalalka noocaas ah waxay noo noqon kartaa dhiirigelin dheeraad ah. Maqaalka la soo jeediyay, dareenka aad u yar ayaa la bixiyaa awoodaha qaabka laftiisa, laakiin qaar ka mid ah ayaa ka muuqda tusaalooyinka la soo bandhigay. Si kastaba ha ahaatee, haddii aan daabacno qaab-dhismeedkayaga, maqaal gaar ah ayaa loo go'aamin doonaa. Dhanka kale, waanu ku mahad naqaynaa haddii aad wax yar kaga tagto jawaab celin adigoo ka jawaabaya su'aasha:

Isticmaalayaasha diiwaangashan oo keliya ayaa ka qaybqaadan kara sahanka. Soo gal, soo dhawoow.

Miyaan u baahanahay qaab-dhismeedka kale ee hababka ganacsiga?

  • 18,8%Haa, wax sidan oo kale ah ayaan raadinayay muddo dheer.

  • 12,5%waxaa xiiso leh inaad wax badan ka barato hirgelintaaga, waxaa laga yaabaa inay faa'iido leedahay2

  • 6,2%Waxaan isticmaalnaa mid ka mid ah qaab-dhismeedka jira, laakiin waxaan ka fekereynaa inaan bedelno1

  • 18,8%Waxaan isticmaalnaa mid ka mid ah qaab-dhismeedka jira, wax kasta oo ku habboon3

  • 18,8%la qabsiga qaab la'aan3

  • 25,0%qor kaaga4

16 isticmaale ayaa u codeeyay. 7 isticmaale ayaa ka aamusay.

Source: www.habr.com

Add a comment