
TĂ€napĂ€eval on raske ette kujutada Kubernetes'e projekti ilma ELK stack'ita, mis salvestab nii rakenduste kui ka klastrisĂŒsteemi komponentide logisid. Oma praktikas kasutame me EFK stack'i, kus Fluentd on Logstashi asemel.
Fluentd on kaasaegne universaalne logikogujate tööriist, mis on ĂŒha populaarsem ja liitunud Cloud Native Computing Foundation'iga, mistĂ”ttu on selle arenduse suund suunatud koostöölle Kubernetes'ega.
Fluentdi kasutamine Logstashi asemel ei muuda programmi kompleks ĂŒldiselt, kuid Fluentd'il on oma spetsiifilised nĂŒansid, mis tulenevad selle mitmeotstarbelisusest.
NÀiteks, alustades EFK kasutamist suure koormusega projektis, kus logide kirjutamise intensiivsus on kÔrge, seisime silmitsi probleemiga, et Kibanas kuvatakse mÔned sÔnumid mitu korda. KÀesolevas artiklis rÀÀgime teile, miks see nÀhtus toimub ja kuidas probleemi lahendada.
Dokumentide dubleerimise probleem
Meie projektides on Fluentd juurutatud kui DaemonSet (automaatne kÀivitamine igas Kubernetes klastrites sÔlmes) ja jÀlgib konteinerite stdout logisid asukohas /var/log/containers. PÀrast kogumist ja töötlemist saadetakse logid JSON-dokumentidena ElasticSearchi, mis töötab klastris vÔi iseseisvalt, sÔltuvalt projekti ulatusest ja jÔudlus- ning talitlushÀire nÔuetest. Graafilise liidese jaoks kasutatakse Kibanat.
Fluentd kasutamisel puhversĂŒsteemi pistikprogrammiga meil tekkis olukord, kus mĂ”ned dokumendid ElasticSearchis omasid tĂ€iesti identset sisu, erinedes vaid tuvastamisnumbri poolest. Veenduda, et tegemist on korduva teatega, saab tuua Nginxi logi nĂ€ite. Logifailis on see teade ainus eksemplar:
127.0.0.1 192.168.0.1 - [28/Feb/2013:12:00:00 +0900] "GET / HTTP/1.1" 200 777 "-" "Opera/12.0" -Kuid ElasticSearchis eksisteerivad mitmed dokumendid, mis sisaldavad seda teavet:
{
"_index": "test-custom-prod-example-2020.01.02",
"_type": "_doc",
"_id": "HgGl_nIBR8C-2_33RlQV",
"_version": 1,
"_score": 0,
"_source": {
"service": "test-custom-prod-example",
"container_name": "nginx",
"namespace": "test-prod",
"@timestamp": "2020-01-14T05:29:47.599052886 00:00",
"log": "127.0.0.1 192.168.0.1 - [28/Feb/2013:12:00:00 0900] "GET / HTTP/1.1" 200 777 "-" "Opera/12.0" -",
"tag": "custom-log"
}
}
{
"_index": "test-custom-prod-example-2020.01.02",
"_type": "_doc",
"_id": "IgGm_nIBR8C-2_33e2ST",
"_version": 1,
"_score": 0,
"_source": {
"service": "test-custom-prod-example",
"container_name": "nginx",
"namespace": "test-prod",
"@timestamp": "2020-01-14T05:29:47.599052886 00:00",
"log": "127.0.0.1 192.168.0.1 - [28/Feb/2013:12:00:00 0900] "GET / HTTP/1.1" 200 777 "-" "Opera/12.0" -",
"tag": "custom-log"
}
}Kordusa vÔib olla rohkem kui kaks.
Fluentd logides seda probleemi fikseerides vÔib nÀha suurt hulka jÀrgmise sisuga hoiatuseid:
2020-01-16 01:46:46 +0000 [warn]: [test-prod] ei Ă”nnestunud vahemĂ€lu tĂŒhjendada. retry_time=4 next_retry_seconds=2020-01-16 01:46:53 +0000 chunk="59c37fc3fb320608692c352802b973ce" error_class=Fluent::Plugin::ElasticsearchOutput::RecoverableRequestFailure error="ei suutnud logisid Elasticsearch klastrisse saata ({:host="elasticsearch", :port=9200, :scheme="http", :user="elastic", :password="obfuscated"}): lugemiseks saavutatav aeg ĂŒletatud"Needless warnings occur when ElasticSearch cannot return a response to the request within the configured request_timeout period, which prevents the buffered chunk from being cleared. After this, Fluentd attempts to resend the buffered chunk to ElasticSearch, and after an arbitrary number of attempts, the operation is successful.
2020-01-16 01:47:05 +0000 [warn]: [test-prod] retry succeeded. chunk_id="59c37fc3fb320608692c352802b973ce"
2020-01-16 01:47:05 +0000 [warn]: [test-prod] retry succeeded. chunk_id="59c37fad241ab300518b936e27200747"
2020-01-16 01:47:05 +0000 [warn]: [test-dev] retry succeeded. chunk_id="59c37fc11f7ab707ca5de72a88321cc2"
2020-01-16 01:47:05 +0000 [warn]: [test-dev] retry succeeded. chunk_id="59c37fb5adb70c06e649d8c108318c9b"
2020-01-16 01:47:15 +0000 [warn]: [kube-system] retry succeeded. chunk_id="59c37f63a9046e6dff7e9987729be66f"However, ElasticSearch treats each of the resent buffer chunks as unique and assigns them unique _id field values upon indexing. This is how message duplicates arise.
In Kibana, it looks like this:

Probleemi lahendamine
Probleemi lahendamiseks on mitu vĂ”imalust. Ăks neist on pluginas fluent-plugin-elasticsearch sisseehitatud mehhanism, mis genereerib iga dokumendi jaoks unikaalse hash'i. Kui seda mehhanismi kasutada, suudab ElasticSearch tuvastada kordused edastamise etapis ja vĂ€ltida dokumentide dubleerimist. Kuid tuleb arvestada, et see lahendus tegeleb toime, mitte pĂ”hjusega, mistĂ”ttu ei kĂ”rvalda see timeout'i puudumise vead ja seetĂ”ttu loobusime selle kasutamisest.
Kasutame Fluentd-vĂ€ljalöögi puhverdamispluginat, et vĂ€ltida logide kadumist lĂŒhikeste vĂ”rguprobleemide vĂ”i logide kirjutamise intensiivsuse suurenemise korral. Kui mingil pĂ”hjusel ei suuda ElasticSearch dokumenti indeksisse kohe salvestada, satub dokument jĂ€rjekorda, mis hoitakse kettal. SeetĂ”ttu on meie puhul vajalik, et probleemiallikad, mis pĂ”hjustavad eespool kirjeldatud viga, kĂ”rvaldada ja seetĂ”ttu mÀÀrata puhverdamise parameetritele Ă”iged vÀÀrtused, mille korral on Fluentd-vĂ€ljund puhver piisava mahuga, et selle tĂŒhjendamine Ă€ra mahuks ettenĂ€htud aja jooksul.
Oluline on mĂ€rkida, et allpool arutatavate parameetrite vÀÀrtused on iga konkreetse pufferdamise kasutusjuhtumi jaoks individuaalsed, kuna need sĂ”ltuvad paljuski erinevatest teguritest: teenuste logide kirjutamise intensiivsusest, kettasĂŒsteemi jĂ”udlusest, vĂ”rguĂŒhenduse koormusest ja selle lĂ€bivusest. SeetĂ”ttu, et saada iga konkreetse juhtumi jaoks sobivad, kuid mitte liialdavad pufferdusese seadistused, vĂ€ltides pikka pimemĂ€ngu, on soovitatav kasutada silumineinfot, mida Fluentd oma logisse kirjutab tööprotsessi kĂ€igus, ja vĂ”rreldes kiiresti Ă”iged vÀÀrtused kĂ€tte saada.
Probleemi fikseerimise hetkel nÀgi konfigureerimine vÀlja jÀrgmiselt:
@type file
path /var/log/fluentd-buffers/kubernetes.test.buffer
flush_mode interval
retry_type exponential_backoff
flush_thread_count 2
flush_interval 5s
retry_forever
retry_max_interval 30
chunk_limit_size 8M
queue_limit_length 8
overflow_action blockProbleemi lahendamise kÀigus valiti kÀsitsi jÀrgmiste parameetrite vÀÀrtused:
chunk_limit_size â pufferis sĂ”numid, millesse jagatakse.
- flush_interval â ajakava, mille möödumisel toimub puhverdamise puhastus.
- queue_limit_length â maksimaalne chunks arv jĂ€rjekorras.
- request_timeout â aeg, mille jooksul luuakse ĂŒhendus Fluentd ja ElasticSearch vahel.
Puhversuuruse arvutamiseks tuleb korrutada parameetrid queue_limit_length ja chunk_limit_size, mida saab tĂ”lgendada kui «maksimaalne chunks arv jĂ€rjekorras, igaĂŒhel on mÀÀratud maht». Kui puhver on liiga vĂ€ike, ilmub logides jĂ€rgmine hoiatusteade:
2020-01-21 10:22:57 +0000 [warn]: [test-prod] failed to write data into buffer by buffer overflow action=:blockSee tÀhendab, et puhver ei suuda ettenÀhtud ajaks kustuda ja tÀidetud puhvri sisse tulevad andmed blokeeritakse, mis toob kaasa osa logide kadumise.
Puhvrit saab suurendada kahel viisil: suurendades kas iga jÀrjekorra chunk'i suurust vÔi chunks'i arvu, mis vÔivad jÀrjekorras olla.
Kui chunk_limit_size seadistada ĂŒle 32 megabaiti, siis ElasticSearch ei aktsepteeri seda, kuna sissetulev pakett oleks liiga suur. SeetĂ”ttu, kui puhvrit on vaja veelgi suurendada, on parem suurendada maksimaalset jĂ€rjekorra pikkust queue_limit_length.
Kui puhver enam ei ĂŒleta piiri ja alles on vaid teade ajavahemiku vĂ€henemisest, saab hakata suurendama parameetrit request_timeout. Siiski, kui seadistada vÀÀrtus ĂŒle 20 sekundi, hakkavad Fluentd logides ilmuma jĂ€rgmised hoiatusteated:
2020-01-21 09:55:33 +0000 [warn]: [test-dev] puhvri tĂŒhjendamine vĂ”ttis kaua aega, kui on ĂŒletatud slow_flush_log_threshold:elapsed_time=20.85753920301795 slow_flush_log_threshold=20.0 plugin_id="postgresql-dev" See teade ei mĂ”juta sĂŒsteemi toimimist ja tĂ€hendab, et puhvri tĂŒhjendamise aeg ĂŒletas slow_flush_log_threshold parameetriga mÀÀratud vÀÀrtuse. See on silumisinfo, mille kasutame request_timeout parameetri vÀÀrtuse mÀÀramisel.
Ăldine algoritm mÀÀramiseks nĂ€eb vĂ€lja jĂ€rgmiselt:
- Seada request_timeout vÀÀrtus kindlasti suuremaks kui vajalik (sajaid sekundeid). Seadistamise ajal on peamine kriteerium, kas see parameeter on Ôigesti seadistatud, hoiatuste kadumine ajavahemiku vÀhenemisest.
- Oodata sĂ”numeid, mis ĂŒletavad slow_flush_log_threshold-i piiri. Hoiatuste tekstis, vĂ€lja elapsed_time, on nĂ€idatud puhvri tĂŒhjendamise tegelik aeg.
- Seadmise request_timeout vÀÀrtus peab olema suurem kui perioodi jooksul saadud maksimaalne elapsed_time vÀÀrtus. Arvutame request_timeout vÀÀrtuse kui elapsed_time + 50%.
- Logi pika puhastusprotsessi hoiatustest vabanemiseks on vÔimalik tÔsta slow_flush_log_threshold vÀÀrtust. Arvutame selle vÀÀrtuse kui elapsed_time + 25%.
Nende parameetrite lĂ”ppvÀÀrtused, nagu eelnevalt mainitud, on igas ĂŒksikjuhus isikupĂ€rased. JĂ€rgides eespool toodud algoritmi, kĂ”rvaldame vead, mis pĂ”hjustavad sĂ”numite kordumist.
Allolevas tabelis on nÀidatud, kuidas muutub vead pÀevas, mis toovad kaasa sÔnumite dubleerimise, kÔigi eespool mainitud parameetrite vÀÀrtuste valimise protsessis:
node-1
node-2
node-3
node-4
Enne/PĂ€rast
Enne/PĂ€rast
Enne/PĂ€rast
Enne/PĂ€rast
puhastamise ebaÔnnestumine
1749/2
694/2
47/0
1121/2
katsed Ônnestusid
410/2
205/1
24/0
241/2
Oluline on mĂ€rkida, et saadud seaded vĂ”ivad projekti kasvu ja logide arvu suurenemise tĂ”ttu kaotada oma aktuaalsuse. Esmane mĂ€rk seadistustest, kus puudub ajapiirang, on Fluentd logides pikka puhastusprotsessi kĂ€sitlevad teated, see tĂ€hendab, et on ĂŒletatud slow_flush_log_threshold kĂŒnnis. Alates sellest hetkest on tĂ”eliselt vĂ€ike varu kuni request_timeout ĂŒletamiseni, seetĂ”ttu tuleb nendele sĂ”numitele Ă”igel ajal reageerida ja korrata eelpool toodud optimaalse seadistuse otsimise protsessi.
KokkuvÔte
Fluentd vĂ€ljundpuhvri tĂ€pne seadistamine on ĂŒks peamisi EFK steki konfigureerimise etappe, mis mÀÀrab selle toimimise stabiilsuse ja dokumendi korrektse paigutamise indeksitesse. JĂ€rgides kirjeldatud seadistamisalgoritmi, vĂ”ib olla kindel, et kĂ”ik logid salvestatakse ElasticSearchi indeksi Ă”iges jĂ€rjestuses, ilma kordusteta ja kaotusteta.
Vaata ka teisi artikleid meie blogis:
Allikas: habr.com
