![Search icon](https://hackernoon.imgix.net/search-new.png?w=19&h=19)
Ohjelmiston joustavuus viittaa sovelluksen kykyyn jatkaa toimintaansa sujuvasti ja luotettavasti myös odottamattomien ongelmien tai vikojen edessä. Fintech-projekteissa joustavuus on erityisen tärkeää useista syistä. Ensinnäkin yritysten on täytettävä sääntelyvaatimukset, ja finanssialan sääntelyviranomaiset korostavat toiminnan joustavuutta ylläpitääkseen järjestelmän vakauden. Lisäksi digitaalisten työkalujen yleistyminen ja riippuvuus kolmansien osapuolien palveluntarjoajista altistaa Fintech-yritykset kohonneille turvallisuusuhkille. Resilience auttaa myös vähentämään eri tekijöiden, kuten kyberuhkien, pandemioiden tai geopoliittisten tapahtumien aiheuttamia katkosriskejä, turvaamalla ydinliiketoiminnan ja kriittisen omaisuuden.
Resilienssimalleilla ymmärrämme joukon parhaita käytäntöjä ja strategioita, jotka on suunniteltu varmistamaan, että ohjelmisto kestää häiriöt ja ylläpitää toimintaansa. Nämä mallit toimivat kuin turvaverkkoja, jotka tarjoavat mekanismeja virheiden käsittelyyn, kuormituksen hallintaan ja vioista toipumiseen, mikä varmistaa, että sovellukset pysyvät kestävinä ja luotettavina epäsuotuisissa olosuhteissa.
Yleisimpiä joustavuusstrategioita ovat laipio, välimuisti, varmistus, uudelleenyritys ja katkaisija. Tässä artikkelissa käsittelen niitä yksityiskohtaisemmin ja esitän esimerkkejä ongelmista, joita ne voivat auttaa ratkaisemaan.
Katsotaanpa yllä olevaa asetusta. Meillä on hyvin tavallinen sovellus, jossa on takanamme useita taustaohjelmia, joista saa tietoa. Näihin taustajärjestelmiin on liitetty useita HTTP-asiakkaita. Osoittautuu, että heillä kaikilla on sama yhteyspooli! Ja myös muita resursseja, kuten CPU ja RAM.
Mitä tapahtuu, jos jokin taustaohjelmista kohtaa jonkinlaisia ongelmia, jotka johtavat korkeaan pyyntöviiveeseen? Korkean vasteajan vuoksi koko yhteyspooli on täysin varattu pyyntöihin, jotka odottavat vastauksia backend1:ltä. Tämän seurauksena terveelle backend2:lle ja backend3:lle tarkoitetut pyynnöt eivät voi jatkaa, koska pooli on käytetty loppuun. Tämä tarkoittaa, että vika jossakin taustajärjestelmistämme voi aiheuttaa koko sovelluksen vian. Ihannetapauksessa haluamme vain vialliseen taustajärjestelmään liittyvien toimintojen heikkenevän, kun taas muu sovellus jatkaa toimintaansa normaalisti.
Mikä on laipiokuvio?
Termi Bulkhead pattern on peräisin laivanrakennuksesta, ja se sisältää useiden erillisten osastojen luomisen laivaan. Jos yhdessä osastossa tapahtuu vuoto, se täyttyy vedellä, mutta muut osastot säilyvät ennallaan. Tämä eristys estää koko aluksen uppoamisen yhden rikkoutumisen vuoksi.
Bulkhead-kuviota voidaan käyttää eristämään erityyppisiä resursseja sovelluksen sisällä, mikä estää yhden osan vikaa vaikuttamasta koko järjestelmään. Näin voimme soveltaa sitä ongelmaamme:
Oletetaan, että taustajärjestelmillämme on pieni todennäköisyys kohdata virheitä yksitellen. Kuitenkin, kun operaatioon kuuluu kaikkien näiden taustaohjelmien rinnakkainen kysely, jokainen voi itsenäisesti palauttaa virheen. Koska nämä virheet tapahtuvat itsenäisesti, sovelluksemme virheen kokonaistodennäköisyys on suurempi kuin minkä tahansa yksittäisen taustaohjelman virhetodennäköisyys. Kumulatiivinen virhetodennäköisyys voidaan laskea kaavalla P_total=1−(1−p)^n, jossa n on taustajärjestelmien lukumäärä.
Jos meillä on esimerkiksi kymmenen taustaohjelmaa, joiden jokaisen virhetodennäköisyys on p=0,001 (vastaa SLA:ta 99,9 %), tuloksena oleva virhetodennäköisyys on:
P_total=1−(1−0,001)^10=0,009955
Tämä tarkoittaa, että yhdistetty SLA-arvomme putoaa noin 99 prosenttiin, mikä osoittaa, kuinka yleinen luotettavuus heikkenee, kun kyselyä tehdään useilta taustaohjelmilta rinnakkain. Tämän ongelman lieventämiseksi voimme ottaa käyttöön muistissa olevan välimuistin.
Muistissa oleva välimuisti toimii nopeana tietopuskurina, joka tallentaa usein käytettyjä tietoja ja poistaa tarpeen hakea niitä mahdollisesti hitaista lähteistä joka kerta. Koska muistiin tallennetuilla välimuistilla on 0 % virhetodennäköisyys verrattuna tietojen hakemiseen verkon kautta, ne lisäävät merkittävästi sovelluksemme luotettavuutta. Lisäksi välimuisti vähentää verkkoliikennettä, mikä vähentää edelleen virheiden mahdollisuutta. Näin ollen käyttämällä muistin sisäistä välimuistia voimme saavuttaa sovelluksessamme vielä pienemmän virhesuhteen taustajärjestelmiimme verrattuna. Lisäksi muistissa olevat välimuistit tarjoavat nopeamman tiedonhaun kuin verkkopohjainen nouto, mikä vähentää sovelluksen viivettä - huomattava etu.
Muistettujen tietojen, kuten käyttäjäprofiilien tai suositusten, osalta muistissa olevien välimuistien käyttö voi olla myös erittäin tehokasta. Meidän on kuitenkin varmistettava, että kaikki käyttäjän pyynnöt menevät johdonmukaisesti samaan sovellusesiintymään, jotta voimme käyttää välimuistiin tallennettuja tietoja, mikä edellyttää pysyviä istuntoja. Kiinnittyvien istuntojen toteuttaminen voi olla haastavaa, mutta tässä skenaariossa emme tarvitse monimutkaisia mekanismeja. Pieni liikenteen tasapainottaminen on hyväksyttävää, joten vakaa kuormituksen tasapainotusalgoritmi, kuten johdonmukainen hajautus, riittää.
Lisäksi solmun vian sattuessa johdonmukainen hajautus varmistaa, että vain epäonnistuneeseen solmuun liittyvät käyttäjät käyvät läpi tasapainotuksen, mikä minimoi järjestelmän häiriöt. Tämä lähestymistapa yksinkertaistaa henkilökohtaisten välimuistien hallintaa ja parantaa sovelluksemme yleistä vakautta ja suorituskykyä.
Jos tiedot, jotka aiomme tallentaa välimuistiin, ovat tärkeitä ja niitä käytetään kaikissa järjestelmämme käsittelemissä pyynnöissä, kuten käyttöoikeuskäytännöissä, tilaussuunnitelmissa tai muissa toimialueemme elintärkeissä kokonaisuuksissa, näiden tietojen lähde voi muodostaa merkittävän vikakohdan järjestelmässämme. Tämän haasteen ratkaisemiseksi yksi tapa on kopioida nämä tiedot kokonaan suoraan sovelluksemme muistiin.
Tässä skenaariossa, jos lähteen datamäärä on hallittavissa, voimme aloittaa prosessin lataamalla tilannevedoksen näistä tiedoista sovelluksemme alussa. Myöhemmin voimme vastaanottaa päivitystapahtumia varmistaaksemme, että välimuistissa olevat tiedot pysyvät synkronoituina lähteen kanssa. Ottamalla käyttöön tämän menetelmän parannamme näiden tärkeiden tietojen käytön luotettavuutta, koska jokainen haku tapahtuu suoraan muistista 0 %:n virhetodennäköisyydellä. Lisäksi tietojen hakeminen muistista on poikkeuksellisen nopeaa, mikä optimoi sovelluksemme suorituskyvyn. Tämä strategia vähentää tehokkaasti riskiä, joka liittyy ulkoiseen tietolähteeseen luottamiseen ja varmistaa johdonmukaisen ja luotettavan pääsyn kriittisiin tietoihin sovelluksemme toiminnan kannalta.
Tarve ladata tietoja sovelluksen käynnistyksestä, mikä hidastaa käynnistysprosessia, rikkoo kuitenkin yhtä "12-faktorisen sovelluksen" periaatteesta, joka puoltaa sovelluksen nopeaa käynnistystä. Emme kuitenkaan halua menettää välimuistin käytön etuja. Tämän ongelman ratkaisemiseksi tutkitaan mahdollisia ratkaisuja.
Nopea käynnistys on ratkaisevan tärkeää erityisesti Kubernetesin kaltaisille alustoille, jotka luottavat nopeaan sovellusten siirtymiseen eri fyysisiin solmuihin. Onneksi Kubernetes voi hallita hitaasti käynnistyviä sovelluksia käyttämällä ominaisuuksia, kuten käynnistysantureita.
Toinen haaste, jonka saatamme kohdata, on asetusten päivittäminen sovelluksen ollessa käynnissä. Usein välimuistiaikojen tai pyyntöjen aikakatkaisujen säätäminen on tarpeen tuotantoongelmien ratkaisemiseksi. Vaikka voimme nopeasti ottaa päivitetyt määritystiedostot käyttöön sovelluksessamme, näiden muutosten käyttöönotto vaatii yleensä uudelleenkäynnistyksen. Kunkin sovelluksen pidennetyn käynnistysajan myötä jatkuva uudelleenkäynnistys voi viivästyttää merkittävästi korjausten käyttöönottoa käyttäjillemme.
Tämän ratkaisemiseksi yksi ratkaisu on tallentaa kokoonpanot samanaikaiseen muuttujaan ja päivittää taustasäie säännöllisesti. Tietyt parametrit, kuten HTTP-pyynnön aikakatkaisut, voivat kuitenkin vaatia HTTP- tai tietokantaasiakkaiden alustamista uudelleen, kun vastaava kokoonpano muuttuu, mikä voi aiheuttaa haasteen. Jotkut asiakkaat, kuten Java-ajuri Cassandra, tukevat kuitenkin asetusten automaattista uudelleenlatausta, mikä yksinkertaistaa tätä prosessia.
Uudelleenladattavien kokoonpanojen käyttöönotto voi lieventää sovellusten pitkien käynnistysaikojen kielteisiä vaikutuksia ja tarjota lisäetuja, kuten helpottaa ominaisuuslippujen käyttöönottoa. Tämän lähestymistavan avulla voimme ylläpitää sovellusten luotettavuutta ja reagointikykyä samalla kun hallitsemme kokoonpanopäivityksiä tehokkaasti.
Tarkastellaan nyt toista ongelmaa: järjestelmässämme, kun käyttäjäpyyntö vastaanotetaan ja käsitellään lähettämällä kysely taustajärjestelmään tai tietokantaan, toisinaan vastaanotetaan virhevastaus odotettujen tietojen sijaan. Tämän jälkeen järjestelmämme vastaa käyttäjälle "virheellä".
Monissa skenaarioissa saattaa kuitenkin olla parempi näyttää hieman vanhentuneita tietoja yhdessä viestin kanssa, joka ilmaisee tietojen päivitysviiveen, sen sijaan, että käyttäjä saisi suuren punaisen virheilmoituksen.
Tämän ongelman ratkaisemiseksi ja järjestelmämme toiminnan parantamiseksi voimme ottaa käyttöön varamallin. Tämän mallin taustalla oleva konsepti sisältää toissijaisen tietolähteen, joka voi sisältää dataa, joka on heikompilaatuista tai tuoreempaa kuin ensisijainen lähde. Jos ensisijainen tietolähde ei ole käytettävissä tai palauttaa virheen, järjestelmä voi palata hakemaan tietoja tästä toissijaisesta lähteestä ja varmistaa, että käyttäjälle esitetään jonkinlainen tieto virheilmoituksen näyttämisen sijaan.
Jos katsot yllä olevaa kuvaa, huomaat samankaltaisuuden nyt kohtaamamme ongelman ja välimuistiesimerkin yhteydessä havaitseman ongelman välillä.
Sen ratkaisemiseksi voimme harkita uudelleenyritysnä tunnetun mallin toteuttamista. Sen sijaan, että luottaisi välimuistiin, järjestelmä voidaan suunnitella lähettämään pyyntö automaattisesti uudelleen virheen sattuessa. Tämä uudelleenyritysmalli tarjoaa yksinkertaisemman vaihtoehdon ja voi tehokkaasti vähentää virheiden todennäköisyyttä sovelluksessamme. Toisin kuin välimuisti, joka vaatii usein monimutkaisia välimuistin mitätöintimekanismeja tietojen muutosten käsittelemiseksi, epäonnistuneiden pyyntöjen uudelleenyritys on suhteellisen yksinkertaista toteuttaa. Koska välimuistin mitätöintiä pidetään laajalti yhtenä haastavimmista tehtävistä ohjelmistosuunnittelussa, uudelleenyritysstrategian ottaminen käyttöön voi virtaviivaistaa virheiden käsittelyä ja parantaa järjestelmän kestävyyttä.
Uudelleenyritysstrategian hyväksyminen ottamatta huomioon mahdollisia seurauksia voi kuitenkin johtaa lisäongelmiin.
Kuvitellaan, että yksi taustaohjelmistamme kokee epäonnistumisen. Tällaisessa skenaariossa uudelleenyritysten aloittaminen epäonnistuneeseen taustajärjestelmään voi johtaa liikenteen määrän merkittävään kasvuun. Tämä äkillinen liikenteen lisääntyminen voi ylittää taustajärjestelmän, pahentaa vikaa ja mahdollisesti aiheuttaa kaskadiefektin koko järjestelmään.
Tämän haasteen ratkaisemiseksi on tärkeää täydentää uudelleenyrityskuviota katkaisijakuviolla. Katkaisija toimii suojamekanismina, joka valvoo alavirran palvelujen virhetasoa. Kun virhesuhde ylittää ennalta määritellyn kynnyksen, katkaisija keskeyttää pyynnöt kyseiselle palvelulle määritetyksi ajaksi. Tänä aikana järjestelmä pidättäytyy lähettämästä lisäpyyntöjä, jotta epäonnistuneen palvelun palautuminen kestää. Määritellyn aikavälin jälkeen katkaisija päästää varovasti rajoitetun määrän pyyntöjä läpi ja varmistaa, että palvelu on vakiintunut. Jos palvelu on palautunut, normaali liikenne palautuu vähitellen; muussa tapauksessa piiri pysyy auki ja jatkaa pyyntöjen estämistä, kunnes palvelu palaa normaaliin toimintaan. Integroimalla katkaisijakuvion uudelleenyrityslogiikan rinnalle voimme tehokkaasti hallita virhetilanteita ja estää järjestelmän ylikuormituksen taustajärjestelmän vikojen aikana.
Yhteenvetona voidaan todeta, että ottamalla nämä joustavuusmallit käyttöön voimme vahvistaa sovelluksiamme hätätilanteita vastaan, ylläpitää korkeaa käytettävyyttä ja tarjota saumattoman käyttökokemuksen käyttäjille. Lisäksi haluan korostaa, että telemetria on jälleen yksi työkalu, jota ei pidä unohtaa projektin kestävyyden tarjoamisessa. Hyvät lokit ja mittarit voivat parantaa merkittävästi palvelujen laatua ja antaa arvokasta tietoa niiden suorituskyvystä, mikä auttaa tekemään tietoon perustuvia päätöksiä niiden parantamiseksi edelleen.