Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Mikhail Salosin (aurrerantzean - MS): - Kaixo guztioi! Nire izena Michael da. Backend garatzaile gisa lan egiten dut MC2 Software-n, eta Go erabiltzeari buruz hitz egingo dut Look+ aplikazio mugikorren backend-ean.

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Hemen inori gustatzen al zaio hockeya?

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Orduan aplikazio hau zuretzat da. Android eta iOSerako da eta hainbat kirol-ekitaldiren emankizunak sarean eta grabatuta ikusteko erabiltzen da. Aplikazioak hainbat estatistika, testu-emisioak, hitzaldietarako taulak, txapelketak eta zaleentzako erabilgarria den beste informazio batzuk ere baditu.

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Aplikazioan ere bideo uneak bezalako gauza bat dago, hau da, partiden une garrantzitsuenak (golak, borrokak, tiroketak, etab.) ikus ditzakezu. Emisio osoa ikusi nahi ez baduzu, interesgarrienak soilik ikus ditzakezu.

Zer erabili duzu garapenean?

Zati nagusia Go-n idatzi zen. Bezero mugikorrekin komunikatzen ziren APIa Go-n idatzi zen. Telefono mugikorretara push jakinarazpenak bidaltzeko zerbitzua ere idatzi zen Go-n. Gure ORMa ere idatzi behar izan genuen, eta hortaz hitz egingo genezake noizbait. Tira, zerbitzu txiki batzuk idatzi ziren Go-n: tamaina aldatu eta editoreentzako irudiak kargatzea...

PostgreSQL erabili dugu datu-base gisa. Editorearen interfazea Ruby on Rails-en idatzi zen ActiveAdmin harribitxia erabiliz. Estatistika-hornitzaile batetik estatistikak inportatzea Ruby-n ere idatzita dago.

Sistemaren API probetarako, Python unittest erabili dugu. Memcached API ordainketa-deiak murrizteko erabiltzen da, "Chef" konfigurazioa kontrolatzeko erabiltzen da, Zabbix sistema barneko estatistikak biltzeko eta kontrolatzeko erabiltzen da. Graylog2 erregistroak biltzeko da, Slate bezeroentzako API dokumentazioa da.

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Protokoloa hautatzea

Topatu genuen lehen arazoa: backend eta mugikorreko bezeroen arteko interakziorako protokolo bat aukeratu behar genuen, honako puntu hauetan oinarrituta...

  • Baldintza garrantzitsuena: bezeroei buruzko datuak denbora errealean eguneratu behar dira. Hau da, emisioa ikusten ari diren guztiek eguneratzeak ia berehala jaso beharko lituzkete.
  • Gauzak sinplifikatzeko, bezeroekin sinkronizatuta dauden datuak ez direla ezabatzen, bandera bereziak erabiliz ezkutatzen direla suposatu dugu.
  • Mota guztietako eskaera arraroak (adibidez, estatistikak, taldeen osaera, taldeen estatistikak) GET eskaera arruntek lortzen dituzte.
  • Gainera, sistemak erraz lagundu behar izan zituen 100 mila erabiltzaile aldi berean.

Horren arabera, bi protokolo aukera izan genituen:

  1. Websocketak. Baina ez genuen bezerotik zerbitzarirako kanalik behar. Zerbitzaritik bezeroari eguneraketak bidali besterik ez genuen behar, beraz, websocket aukera erredundantea da.
  2. Zerbitzariak bidalitako gertaerak (SSE) ondo sortu ziren! Nahiko sinplea da eta funtsean behar dugun guztia asetzen du.

Zerbitzariak bidalitako gertaerak

Gauza honek funtzionatzen duenari buruzko hitz batzuk...

http konexio baten gainean exekutatzen da. Bezeroak eskaera bat bidaltzen du, zerbitzariak Content-Type: text/evento-stream-ekin erantzuten du eta ez du bezeroarekin konexioa ixten, baina datuak idazten jarraitzen du konexioan:

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Datuak bezeroekin adostutako formatuan bidal daitezke. Gure kasuan, formulario honetan bidali dugu: aldatutako egituraren izena (pertsona, jokalaria) gertaeraren eremura bidali zen, eta jokalariarentzat eremu berriekin aldatutako JSON datuen eremura bidali zen.

Orain hitz egin dezagun elkarrekintza bera nola funtzionatzen duen.

  • Bezeroak egiten duen lehenengo gauza zerbitzuarekin sinkronizazioa egin den azken aldian zehaztea da: bertako datu-baseari begiratzen dio eta hark erregistratutako azken aldaketaren data zehazten du.
  • Data honekin eskaera bat bidaltzen du.
  • Horren harira, data horretatik aurrera gertatu diren eguneratze guztiak bidaltzen dizkiogu.
  • Horren ostean, zuzeneko kanalarekin konexioa egiten du eta ez da ixten eguneratze hauek behar dituen arte:

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Aldaketen zerrenda bidaltzen diogu: norbaitek gol bat sartzen badu, partidako puntuazioa aldatzen dugu, lesionatzen bada, hau ere denbora errealean bidaltzen da. Horrela, bezeroek berehala jasotzen dituzte datu eguneratuak partida-gertaeren jarioan. Aldian-aldian, bezeroak zerbitzaria ez dela hil, ez zaiola ezer gertatu uler dezan, denbora-zigilu bat bidaltzen dugu 15 segundoro, dena ondo dagoela jakin dezan eta ez dagoela berriro konektatu beharrik.

Nola ematen da zuzeneko konexioa?

  • В первую очередь мы создаём канал, в который будут приходить обновления с буфером.
  • Horren ostean, kanal honetara harpidetzen gara eguneraketak jasotzeko.
  • Goiburu egokia ezarri dugu, bezeroak dena ondo dagoela jakin dezan.
  • Bidali lehenengo ping-a. Uneko konexioaren denbora-zigilua besterik ez dugu grabatzen.
  • Horren ostean, kanaletik irakurtzen dugu begizta batean eguneratze kanala itxi arte. Kanalak aldizka uneko denbora-zigilua edo konexioak irekitzeko idazten ari garen aldaketak jasotzen ditu.

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Topatu genuen lehenengo arazoa honako hau izan zen: bezeroarekin irekitako konexio bakoitzeko, 15 segundoro behin markatzen zuen tenporizadore bat sortu genuen - 6 mila konexio irekita bagenitu makina batekin (API zerbitzari batekin), 6. mila tenporizadore sortu ziren. Honek makinak beharrezko karga ez eustea ekarri zuen. Arazoa ez zitzaigun horren agerikoa izan, baina laguntza pixka bat lortu eta konpondu genuen.

Ondorioz, orain gure ping-a eguneratzea datorren kanal beretik dator.

Horren arabera, tenporizadore bakarra dago 15 segundoan behin markatzen duena.

Hainbat funtzio laguntzaile daude hemen - goiburua, ping-a eta egitura bera bidaltzea. Hau da, mahaiaren izena (pertsona, partida, denboraldia) eta sarrera honi buruzko informazioa hemen transmititzen dira:

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Eguneraketak bidaltzeko mekanismoa

Orain pixka bat aldaketak nondik datozen. Hainbat pertsona ditugu, editoreak, emisioa denbora errealean ikusten dutenak. Gertaera guztiak sortzen dituzte: norbait kanporatua, norbait zauritua, ordezkapen moduko bat...

CMS bat erabiliz, datuak datu-basean sartzen dira. Horren ondoren, datu-baseak API zerbitzariei horren berri ematen die Entzun/Jakinarazpen mekanismoa erabiliz. API zerbitzariek dagoeneko bidaltzen diete informazio hori bezeroei. Horrela, funtsean, datu-basera zerbitzari batzuk baino ez ditugu konektatuta eta ez dago datu-basean karga berezirik, bezeroak ez baitu zuzenean datu-basearekin inola ere elkarreragin:

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

PostgreSQL: Entzun/Jakinarazpena

Postgres-en Entzun/Abisatu mekanismoak gertaeraren bat aldatu dela jakinarazteko aukera ematen die gertaera harpidedunei - datu-basean erregistro batzuk sortu dira. Horretarako, abiarazle eta funtzio sinple bat idatzi dugu:

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Erregistro bat txertatzean edo aldatzean, data_updates kanaleko jakinarazpen funtzioari deitzen diogu, bertan taularen izena eta aldatu edo txertatu den erregistroaren identifikatzailea pasatuz.

Bezeroarekin sinkronizatu behar diren taula guztietarako, abiarazle bat definitzen dugu, zeinak, erregistro bat aldatu/eguneratu ondoren, beheko diapositiban adierazitako funtzioari deitzen diona.
Nola harpidetzen da APIa aldaketa horietara?

Fanout mekanismo bat sortzen da - bezeroari mezuak bidaltzen dizkio. Bezeroen kanal guztiak biltzen ditu eta jasotako eguneraketak kanal hauen bidez bidaltzen ditu:

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Hemen pq liburutegi estandarrak, datu-basera konektatzen dena eta kanala entzun nahi duela esaten duena (data_updates), konexioa irekita dagoela eta dena ondo dagoela egiaztatzen du. Erroreak egiaztatzea baztertzen ari naiz lekua aurrezteko (ez egiaztatzea arriskutsua da).

Jarraian, Ticker modu asinkronoan ezarriko dugu, ping bat bidaliko duena 15 segundoro, eta harpidetu garen kanala entzuten hasiko gara. Ping bat jasotzen badugu, ping hau argitaratzen dugu. Sarrera motaren bat jasotzen badugu, sarrera hau Fanout honetako harpidedun guztiei argitaratzen diegu.

Nola funtzionatzen du Fan-out-ak?

Errusieraz hau "splitter" gisa itzultzen da. Eguneratze batzuk jaso nahi dituzten harpidedunak erregistratzen dituen objektu bat dugu. Eta objektu honetara eguneratze bat iristen den bezain laster, eguneratze hori bere harpidedun guztiei banatzen die. Nahikoa sinplea:

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Nola inplementatzen den Go-n:

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Egitura bat dago, Mutexak erabiliz sinkronizatuta dago. Fanout-en datu-baserako konexioaren egoera gordetzen duen eremu bat du, hau da, une honetan entzuten ari da eta eguneraketak jasoko ditu, baita eskuragarri dauden kanal guztien zerrenda ere - mapa, zeinaren gakoa kanala eta egitura moduan. balioak (funtsean ez da inola ere erabiltzen).

Bi metodok - Konektatua eta Deskonektatua - Fanout-i oinarriarekin konexioa dugula, agertu dela eta oinarriarekiko konexioa hautsi dela esatea ahalbidetzen digu. Bigarren kasuan, bezero guztiak deskonektatu behar dituzu eta esan ezin dutela ezer entzun eta berriro konektatzen direla haiekiko konexioa itxi delako.

Kanala "entzuleei" gehitzen dien Harpidetza metodo bat ere badago:

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Harpidetza kendu metodo bat dago, entzuleei kanala kentzen diena bezeroa deskonektatzen bada, baita Publish metodo bat ere, harpidedun guztiei mezu bat bidaltzeko aukera ematen diena.

Galdera: – Zer transmititzen da kanal honen bidez?

ANDEREA: – Aldatu den eredua edo ping-a transmititzen da (funtsean zenbaki bat besterik ez, zenbaki oso bat).

ANDEREA: - Edozer bidali dezakezu, edozein egitura bidali, argitaratu - JSON bihurtzen da eta kito.

ANDEREA: – Postgres-en jakinarazpen bat jasotzen dugu – taularen izena eta identifikatzailea ditu. Taularen izenaren eta identifikatzailearen arabera, behar dugun erregistroa lortzen dugu eta, ondoren, egitura hau bidaltzen dugu argitaratzeko.

Azpiegitura

Nolakoa da hori azpiegituren ikuspegitik? 7 hardware zerbitzari ditugu: horietako bat datu-basera guztiz dedikatuta dago, beste seik makina birtualak exekutatzen dituzte. APIaren 6 kopia daude: APIa duen makina birtual bakoitza hardware zerbitzari batean exekutatzen da - hau fidagarritasuna da.

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Irisgarritasuna hobetzeko Keepalived duten bi frontend ditugu instalatuta, zerbait gertatuz gero frontend batek bestea ordezkatu ahal izateko. Gainera - CMSaren bi kopia.

Estatistiken inportatzaile bat ere badago. DB Slave bat dago eta bertatik babeskopiak egiten dira aldian-aldian. Pigeon Pusher dago, bezeroei push jakinarazpenak bidaltzen dizkien aplikazioa, baita azpiegitura gauzak ere: Zabbix, Graylog2 eta Chef.

Izan ere, azpiegitura hau erredundantea da, 100 mila zerbitzari gutxiagorekin zerbitza daitezkeelako. Baina bazegoen burdina - erabili genuen (posible zela esan ziguten - zergatik ez).

Go-ren abantailak

Aplikazio honetan lan egin ondoren, Go-ren abantaila nabariak agertu ziren.

  • Cool http liburutegia. Harekin kaxatik kanpo dezente sor ditzakezu.
  • Gainera, bezeroei jakinarazpenak bidaltzeko mekanismo bat oso erraz ezartzea ahalbidetu diguten kanalak.
  • Gauza zoragarria Race detektagailuak hainbat akats kritiko ezabatzeko aukera eman zigun (eszenaratzeko azpiegitura). Eszenaratzean lan egiten duen guztia martxan jartzen da, Lasterketa gakoarekin bildua; eta guk, horren arabera, eszenaratze-azpiegiturari erreparatu diezaiokegu zer arazo potentzial ditugun ikusteko.
  • Minimalismoa eta hizkuntzaren sinpletasuna.

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

Garatzaileen bila gabiltza! Norbaitek nahi badu, mesedez.

Zure galderak

Entzuleen galdera (aurrerantzean – B): – Fan-out-ari buruzko puntu garrantzitsu bat galdu duzula iruditzen zait. Ondo nago ulertzean bezero bati erantzuna bidaltzen diozunean blokeatzen duzula bezeroak irakurri nahi ez badu?

ANDEREA: - Ez, ez gara blokeatzen ari. Lehenik eta behin, hau guztia dugu nginx atzean, hau da, ez dago arazorik bezero motelekin. Bigarrenik, bezeroak buffer bat duen kanal bat dauka, hain zuzen ere, ehun eguneraketa jar ditzakegu bertan... Ezin badugu kanalean idatzi, orduan ezabatzen du. Kanala blokeatuta dagoela ikusten badugu, kanala itxiko dugu, eta kito - bezeroa berriro konektatuko da arazoren bat sortzen bada. Horregatik, printzipioz, hemen ez dago blokeorik.

V: – Ezin al da berehala bidaltzea Entzun/Jakinaraztera erregistro bat, eta ez identifikatzaile-taula bat?

ANDEREA: – Entzun/Jakinarazpenak 8 mila byteko muga du bidaltzen duen aurrekargan. Printzipioz, datu kopuru txiki batekin arituko bagina bidaltzea posible izango litzateke, baina iruditzen zait horrela [egiteko modua] fidagarriagoa dela besterik gabe. Mugak Postgresen bertan daude.

V: – Bezeroek interesatzen ez zaizkien partidei buruzko eguneraketak jasotzen al dituzte?

ANDEREA: - Orokorrean bai. Oro har, 2-3 partidak paralelo izaten dira, eta orduan ere oso gutxitan. Bezero bat zerbait ikusten ari bada, normalean gertatzen ari den partida ikusten ari da. Ondoren, bezeroak tokiko datu-base bat du eta bertan eguneratze horiek guztiak gehitzen dira, eta Interneteko konexiorik gabe ere, bezeroak eguneratzeak dituen iraganeko partida guztiak ikus ditzake. Funtsean, gure datu-basea zerbitzarian sinkronizatzen dugu bezeroaren datu-base lokalarekin, lineaz kanpo lan egin dezan.

V: – Zergatik egin zenuen zure ORM?

Alexey (Lore+-ren garatzaileetako bat): – Garai hartan (duela urtebete zen) orain baino ORM gutxiago zeuden, dezente baitaude. ORM gehienetan gehien gustatzen zaidan gauzarik gehienak interfaze hutsetan exekutatzen direla da. Hau da, ORM horietako metodoak edozer gauza hartzeko prest daude: egitura bat, egitura erakuslea, zenbaki bat, guztiz garrantzirik gabeko zerbait...

Gure ORMak datu-ereduan oinarritutako egiturak sortzen ditu. Neure burua. Eta, beraz, metodo guztiak konkretuak dira, ez dute hausnarketarik erabiltzen, etab. Egiturak onartzen dituzte eta datozen egitura horiek erabiltzea espero dute.

V: – Zenbat lagunek hartu dute parte?

ANDEREA: – Hasierako fasean, bi lagunek hartu zuten parte. Ekainean nonbait hasi ginen, eta abuztuan zati nagusia prest zegoen (lehen bertsioa). Irailean kaleratu zen.

V: – SSE deskribatzen duzun tokian, ez duzu denbora-mugarik erabiltzen. Zergatik da hori?

ANDEREA: – Egia esateko, SSE oraindik html5 protokoloa da: SSE estandarra nabigatzaileekin komunikatzeko diseinatuta dago, nik ulertzen dudanez. Ezaugarri gehigarriak ditu, nabigatzaileak berriro konektatzeko (eta abar), baina ez ditugu behar, informazioa konektatzeko eta jasotzeko edozein logika inplementa dezaketen bezeroak genituelako. Ez genuen SSE egin, SSEren antzeko zerbait baizik. Hau ez da protokoloa bera.
Ez zegoen beharrik. Ulertzen dudanez, bezeroek konexio mekanismoa ia hutsetik inplementatu zuten. Ez zitzaien benetan axola.

V: - Zein erabilgarritasun gehigarri erabili zenituen?

ANDEREA: – Govet eta golint modu aktiboan erabili ditugu estiloa bateratzeko, baita gofmt ere. Ez zen beste ezer erabili.

V: - Zer erabili zenuen arazketa egiteko?

ANDEREA: – Arazketa, neurri handi batean, probak erabiliz egin zen. Ez dugu arazterik edo GOPrik erabili.

V: – Argitaratu funtzioa inplementatuta dagoen diapositiba itzuli al dezakezu? Letra bakarreko aldagaien izenek nahasten zaituzte?

ANDEREA: - Ez. Ikusgarritasun esparru nahiko "estu" dute. Ez dira beste inon erabiltzen hemen izan ezik (klase honen barnekoak izan ezik), eta oso trinkoa da - 7 lerro bakarrik hartzen ditu.

V: - Nolabait oraindik ez da intuitiboa...

ANDEREA: - Ez, ez, hau benetako kodea da! Ez da estiloa. Klase utilitarista eta oso txikia da - klase barruan 3 eremu bakarrik...

Mikhail Salosin. Golang Topaketa. Go erabiliz Look+ aplikazioaren backend-ean

ANDEREA: – Oro har, bezeroekin sinkronizatzen diren datu guztiak (denboraldiko partidak, jokalariak) ez dira aldatzen. Gutxi gorabehera, partida aldatu behar dugun beste kirol bat egiten badugu, bezeroaren bertsio berrian dena kontuan hartuko dugu, eta bezeroaren bertsio zaharrak debekatu egingo dira.

V: – Ba al dago hirugarrenen mendekotasunak kudeatzeko paketerik?

ANDEREA: – Go dep erabiltzen genuen.

V: – Erreportajearen gaian bideoari buruzko zerbait zegoen, baina erreportajean ez zegoen ezer bideoari buruz.

ANDEREA: – Ez, ez daukat gaian bideoari buruzko ezer. "Begira +" deitzen da - hori da aplikazioaren izena.

V: – Bezeroei igortzen zaiela esan duzu?...

ANDEREA: – Ez ginen bideoak streaming-ean parte hartzen. Megafonek egin zuen erabat. Bai, ez nuen esan aplikazioa MegaFon zenik.

ANDEREA: – Joan – datu guztiak bidaltzeko – puntuazioari, partiden ekitaldiei, estatistikei buruz... Go aplikazioaren backend osoa da. Bezeroak nonbaitetik jakin behar du zein esteka erabili jokalariarentzat, erabiltzaileak partida ikusi ahal izateko. Prestatu diren bideo eta korronteetarako estekak ditugu.

Iragarki batzuk 🙂

Eskerrik asko gurekin geratzeagatik. Gustuko dituzu gure artikuluak? Eduki interesgarri gehiago ikusi nahi? Lagun iezaguzu eskaera bat eginez edo lagunei gomendatuz, Garatzaileentzako hodeiko VPS 4.99 $-tik aurrera, sarrera-mailako zerbitzarien analogo paregabea, guk zuretzat asmatu duguna: VPS (KVM) E5-2697 v3 (6 Nukleoak) 10GB DDR4 480GB SSD 1Gbps 19Gbps-ri buruzko egia osoa XNUMX $-tik edo zerbitzari bat nola partekatu? (RAID1 eta RAID10-ekin erabilgarri, 24 nukleoraino eta 40 GB DDR4 arte).

Dell R730xd 2 aldiz merkeagoa Amsterdameko Equinix Tier IV datu-zentroan? Hemen bakarrik 2 x Intel TetraDeca-Core Xeon 2x E5-2697v3 2.6GHz 14C 64GB DDR4 4x960GB SSD 1Gbps 100 telebista 199 $-tik aurrera Herbehereetan! Dell R420 - 2x E5-2430 2.2Ghz 6C 128GB DDR3 2x960GB SSD 1Gbps 100TB - 99 $-tik aurrera! Irakurri buruz Nola eraiki azpiegitura korporazioa. klasea Dell R730xd E5-2650 v4 zerbitzarien erabilerarekin 9000 euroko balioa duten zentimo baten truke?

Iturria: www.habr.com

Gehitu iruzkin berria