{"id":1370,"date":"2026-04-09T13:20:36","date_gmt":"2026-04-09T11:20:36","guid":{"rendered":"https:\/\/trzykody.pl\/?p=1370"},"modified":"2026-04-20T13:24:51","modified_gmt":"2026-04-20T11:24:51","slug":"slowniki-tlumaczen","status":"publish","type":"post","link":"https:\/\/trzykody.pl\/index.php\/2026\/04\/09\/slowniki-tlumaczen\/","title":{"rendered":"S\u0142owniki t\u0142umacze\u0144"},"content":{"rendered":"\n<p class=\"wp-block-paragraph\">W systemach wieloj\u0119zycznych bardzo szybko pojawia si\u0119 ten sam problem: ta sama informacja musi zosta\u0107 pokazana u\u017cytkownikowi w r\u00f3\u017cnych j\u0119zykach, bez przepisywania ca\u0142ej logiki programu. Nie chodzi tylko o interfejs aplikacji, ale te\u017c komunikaty b\u0142\u0119d\u00f3w, opisy produkt\u00f3w, statusy zam\u00f3wie\u0144, raporty czy dokumenty generowane automatycznie. Je\u015bli ten mechanizm nie jest uporz\u0105dkowany, projekt zaczyna si\u0119 rozpada\u0107 przy ka\u017cdej zmianie tekstu. Najpro\u015bciej porz\u0105dkuje si\u0119 to przez <strong>S\u0142owniki t\u0142umacze\u0144<\/strong>.<\/p>\n\n\n\n<div class=\"wp-block-rank-math-toc-block\" id=\"rank-math-toc\"><h2>Spis Tre\u015bci<\/h2><nav><ol><li><a href=\"#slowniki-tlumaczen-jako-warstwa-posrednia-miedzy-kodem-programu-a-trescia-widoczna-dla-uzytkownika\">S\u0142owniki t\u0142umacze\u0144 jako warstwa po\u015brednia mi\u0119dzy kodem programu a tre\u015bci\u0105 widoczn\u0105 dla u\u017cytkownika<\/a><\/li><li><a href=\"#struktura-danych-i-sposob-przechowywania-map-klucz-wartosc-w-pamieci-oraz-na-dysku\">Struktura danych i spos\u00f3b przechowywania map klucz\u2013warto\u015b\u0107 w pami\u0119ci oraz na dysku<\/a><\/li><li><a href=\"#slowniki-tlumaczen-w-pythonie-c-oraz-c-na-prostych-przykladach-akademickich\">S\u0142owniki t\u0142umacze\u0144 w Pythonie, C oraz C++ na prostych przyk\u0142adach akademickich<\/a><ol><li><a href=\"#python\">Python<\/a><\/li><li><a href=\"#c\">C++<\/a><\/li><li><a href=\"#c-1\">C<\/a><\/li><\/ol><\/li><li><a href=\"#slowniki-tlumaczen-a-problem-odmiany-jezykowej-liczby-mnogiej-i-parametrow-dynamicznych\">S\u0142owniki t\u0142umacze\u0144 a problem odmiany j\u0119zykowej liczby mnogiej i parametr\u00f3w dynamicznych<\/a><ol><li><a href=\"#przyklad-logiczny\">Przyk\u0142ad logiczny<\/a><\/li><\/ol><\/li><li><a href=\"#wydajnosc-wyszukiwania-oraz-koszt-operacyjny-przy-duzych-systemach-wielojezycznych\">Wydajno\u015b\u0107 wyszukiwania oraz koszt operacyjny przy du\u017cych systemach wieloj\u0119zycznych<\/a><ol><li><a href=\"#slowniki-tlumaczen-w-systemach-produkcyjnych-i-problemy-ktore-naprawde-psuja-projekty\">S\u0142owniki t\u0142umacze\u0144 w systemach produkcyjnych i problemy, kt\u00f3re naprawd\u0119 psuj\u0105 projekty<\/a><\/li><li><a href=\"#1-duplikacja-kluczy\">1. Duplikacja kluczy<\/a><\/li><li><a href=\"#2-brak-fallback-language\">2. Brak fallback language<\/a><\/li><li><a href=\"#3-tlumaczenie-klucza-zamiast-wartosci\">3. T\u0142umaczenie klucza zamiast warto\u015bci<\/a><\/li><li><a href=\"#4-brak-wersjonowania\">4. Brak wersjonowania<\/a><\/li><li><a href=\"#5-reczna-edycja-bez-walidacji\">5. R\u0119czna edycja bez walidacji<\/a><\/li><\/ol><\/li><li><a href=\"#krotkie-wzory-i-zaleznosci-uzywane-przy-analizie-wydajnosci-wyszukiwania\">Kr\u00f3tkie wzory i zale\u017cno\u015bci u\u017cywane przy analizie wydajno\u015bci wyszukiwania<\/a><\/li><li><a href=\"#faq\">FAQ<\/a><ol><li><a href=\"#czy-klucze-powinny-byc-po-angielsku\">Czy klucze powinny by\u0107 po angielsku?<\/a><\/li><li><a href=\"#czy-baza-danych-jest-lepsza-niz-pliki-json\">Czy baza danych jest lepsza ni\u017c pliki JSON?<\/a><\/li><li><a href=\"#czy-warto-trzymac-tlumaczenia-w-frontendzie-i-backendzie-osobno\">Czy warto trzyma\u0107 t\u0142umaczenia w frontendzie i backendzie osobno?<\/a><\/li><li><a href=\"#co-zrobic-gdy-brakuje-tlumaczenia\">Co zrobi\u0107, gdy brakuje t\u0142umaczenia?<\/a><\/li><li><a href=\"#czy-nazwa-klucza-moze-sie-zmieniac\">Czy nazwa klucza mo\u017ce si\u0119 zmienia\u0107?<\/a><\/li><li><a href=\"#czy-tlumaczenia-powinny-byc-cacheowane\">Czy t\u0142umaczenia powinny by\u0107 cache\u2019owane?<\/a><\/li><\/ol><\/li><li><a href=\"#zakonczenie\">Zako\u0144czenie<\/a><\/li><\/ol><\/nav><\/div>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"slowniki-tlumaczen-jako-warstwa-posrednia-miedzy-kodem-programu-a-trescia-widoczna-dla-uzytkownika\">S\u0142owniki t\u0142umacze\u0144 jako warstwa po\u015brednia mi\u0119dzy kodem programu a tre\u015bci\u0105 widoczn\u0105 dla u\u017cytkownika<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Najwa\u017cniejsza zasada jest prosta: w kodzie nie zapisuje si\u0119 tekst\u00f3w ko\u0144cowych typu \u201eB\u0142\u0105d logowania\u201d albo \u201eZapisano poprawnie\u201d, tylko u\u017cywa si\u0119 kluczy logicznych, na przyk\u0142ad:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><code>login.error<\/code><\/li>\n\n\n\n<li><code>user.saved<\/code><\/li>\n\n\n\n<li><code>cart.empty<\/code><\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">Program operuje na kluczach, a dopiero osobna struktura danych zamienia klucz na tekst w odpowiednim j\u0119zyku.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Dzi\u0119ki temu:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>programista nie edytuje tre\u015bci j\u0119zykowych w logice aplikacji,<\/li>\n\n\n\n<li>t\u0142umacz nie musi zna\u0107 kodu,<\/li>\n\n\n\n<li>zmiana jednego komunikatu nie wymaga przebudowy programu,<\/li>\n\n\n\n<li>mo\u017cna \u0142atwo doda\u0107 kolejny j\u0119zyk.<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">To jest podstawowy wzorzec stosowany w systemach i18n (internationalization) i l10n (localization).<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Przyk\u0142ad dzia\u0142ania:<\/p>\n\n\n\n<ol class=\"wp-block-list\">\n<li>Program wywo\u0142uje klucz <code>payment.success<\/code><\/li>\n\n\n\n<li>System sprawdza aktywny j\u0119zyk u\u017cytkownika, np. <code>pl<\/code><\/li>\n\n\n\n<li>Odczytywana jest warto\u015b\u0107 z mapy:<br><code>payment.success -> P\u0142atno\u015b\u0107 zako\u0144czona poprawnie<\/code><\/li>\n\n\n\n<li>U\u017cytkownik widzi gotowy komunikat<\/li>\n<\/ol>\n\n\n\n<p class=\"wp-block-paragraph\">Bez tego przy wi\u0119kszym projekcie zaczyna si\u0119 chaos: ten sam komunikat wyst\u0119puje w 12 miejscach, cz\u0119\u015b\u0107 po polsku, cz\u0119\u015b\u0107 po angielsku, cz\u0119\u015b\u0107 w starej wersji.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"struktura-danych-i-sposob-przechowywania-map-klucz-wartosc-w-pamieci-oraz-na-dysku\">Struktura danych i spos\u00f3b przechowywania map klucz\u2013warto\u015b\u0107 w pami\u0119ci oraz na dysku<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Najcz\u0119\u015bciej u\u017cywa si\u0119 struktury typu:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>hash map<\/li>\n\n\n\n<li>associative array<\/li>\n\n\n\n<li>dictionary<\/li>\n\n\n\n<li>map<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">czyli relacji:<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><code>klucz -&gt; warto\u015b\u0107<\/code><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Przyk\u0142ad logiczny:<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Klucz<\/th><th>Polski<\/th><th>Angielski<\/th><\/tr><\/thead><tbody><tr><td>login.error<\/td><td>B\u0142\u0105d logowania<\/td><td>Login error<\/td><\/tr><tr><td>cart.empty<\/td><td>Koszyk jest pusty<\/td><td>Cart is empty<\/td><\/tr><tr><td>user.saved<\/td><td>Zapisano u\u017cytkownika<\/td><td>User saved<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">Klucz powinien by\u0107:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>stabilny<\/li>\n\n\n\n<li>czytelny<\/li>\n\n\n\n<li>niezmienny w czasie<\/li>\n\n\n\n<li>niezale\u017cny od j\u0119zyka<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">Z\u0142y przyk\u0142ad:<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><code>B\u0142\u0105d_logowania<\/code><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Dobry przyk\u0142ad:<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><code>auth.login.error<\/code><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Drugi wariant jest lepszy, bo porz\u0105dkuje system modu\u0142owo.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Popularne formaty zapisu:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>JSON<\/li>\n\n\n\n<li>YAML<\/li>\n\n\n\n<li>XML<\/li>\n\n\n\n<li>CSV<\/li>\n\n\n\n<li>pliki <code>.po<\/code> i <code>.mo<\/code><\/li>\n\n\n\n<li>bazy SQL<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">Najcz\u0119\u015bciej w praktyce webowej u\u017cywa si\u0119 JSON lub YAML, bo s\u0105 szybkie do edycji i \u0142atwe do \u0142adowania.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Przyk\u0142ad JSON:<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Format<\/th><th>Przyk\u0142ad<\/th><\/tr><\/thead><tbody><tr><td>JSON<\/td><td><code>{ \"login.error\": \"B\u0142\u0105d logowania\", \"user.saved\": \"Zapisano u\u017cytkownika\" }<\/code><\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">Przyk\u0142ad YAML:<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Format<\/th><th>Przyk\u0142ad<\/th><\/tr><\/thead><tbody><tr><td>YAML<\/td><td><code>login.error: \"B\u0142\u0105d logowania\"<\/code><\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">JSON jest wygodniejszy dla parser\u00f3w, YAML dla ludzi.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"slowniki-tlumaczen-w-pythonie-c-oraz-c-na-prostych-przykladach-akademickich\">S\u0142owniki t\u0142umacze\u0144 w Pythonie, C oraz C++ na prostych przyk\u0142adach akademickich<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Najprostszy przyk\u0142ad to r\u0119czna mapa klucz\u2013warto\u015b\u0107.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"python\">Python<\/h3>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>J\u0119zyk<\/th><th>Kod<\/th><\/tr><\/thead><tbody><tr><td>Python<\/td><td><code>python\\ntranslations = {\\n \\\"login.error\\\": \\\"B\u0142\u0105d logowania\\\",\\n \\\"user.saved\\\": \\\"Zapisano u\u017cytkownika\\\"\\n}\\n\\nkey = \\\"login.error\\\"\\nprint(translations.get(key, \\\"Brak t\u0142umaczenia\\\"))\\n<\/code><\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">Metoda <code>get()<\/code> jest wa\u017cna, bo zabezpiecza przed b\u0142\u0119dem braku klucza.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"c\">C++<\/h3>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>J\u0119zyk<\/th><th>Kod<\/th><\/tr><\/thead><tbody><tr><td>C++<\/td><td><code>cpp\\n#include &lt;iostream&gt;\\n#include &lt;map&gt;\\nusing namespace std;\\n\\nint main() {\\n map&lt;string, string&gt; translations;\\n\\n translations[\\\"login.error\\\"] = \\\"B\u0142\u0105d logowania\\\";\\n translations[\\\"user.saved\\\"] = \\\"Zapisano u\u017cytkownika\\\";\\n\\n string key = \\\"login.error\\\";\\n cout &lt;&lt; translations[key] &lt;&lt; endl;\\n\\n return 0;\\n}\\n<\/code><\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">W nowoczesnym C++ cz\u0119sto u\u017cywa si\u0119 <code>unordered_map<\/code>, bo jest szybsze dla wyszukiwania.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"c-1\">C<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">C nie ma wbudowanego s\u0142ownika, wi\u0119c najcz\u0119\u015bciej robi si\u0119 tablic\u0119 struktur.<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>J\u0119zyk<\/th><th>Kod<\/th><\/tr><\/thead><tbody><tr><td>C<\/td><td><code>c\\n#include &lt;stdio.h&gt;\\n#include &lt;string.h&gt;\\n\\nstruct Translation {\\n char key[50];\\n char value[100];\\n};\\n\\nint main() {\\n struct Translation dict[] = {\\n {\\\"login.error\\\", \\\"B\u0142\u0105d logowania\\\"},\\n {\\\"user.saved\\\", \\\"Zapisano u\u017cytkownika\\\"}\\n };\\n\\n int size = 2;\\n char search[] = \\\"login.error\\\";\\n\\n for(int i = 0; i &lt; size; i++) {\\n if(strcmp(dict[i].key, search) == 0) {\\n printf(\\\"%s\\\\n\\\", dict[i].value);\\n }\\n }\\n\\n return 0;\\n}\\n<\/code><\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">To rozwi\u0105zanie jest wolniejsze, ale dobrze pokazuje ide\u0119.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"slowniki-tlumaczen-a-problem-odmiany-jezykowej-liczby-mnogiej-i-parametrow-dynamicznych\">S\u0142owniki t\u0142umacze\u0144 a problem odmiany j\u0119zykowej liczby mnogiej i parametr\u00f3w dynamicznych<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Prosty tekst to dopiero pocz\u0105tek. Problem zaczyna si\u0119 przy takich komunikatach:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>\u201eMasz 1 wiadomo\u015b\u0107\u201d<\/li>\n\n\n\n<li>\u201eMasz 2 wiadomo\u015bci\u201d<\/li>\n\n\n\n<li>\u201eMasz 5 wiadomo\u015bci\u201d<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">Polski jest tu znacznie trudniejszy ni\u017c angielski.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Nie wystarczy jeden wpis.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Potrzebne s\u0105 regu\u0142y pluralizacji.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"przyklad-logiczny\">Przyk\u0142ad logiczny<\/h3>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Liczba<\/th><th>Wersja<\/th><\/tr><\/thead><tbody><tr><td>1<\/td><td>wiadomo\u015b\u0107<\/td><\/tr><tr><td>2\u20134<\/td><td>wiadomo\u015bci<\/td><\/tr><tr><td>5+<\/td><td>wiadomo\u015bci \/ wiadomo\u015bci zale\u017cnie od regu\u0142y<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">Jeszcze trudniejsze s\u0105 parametry dynamiczne:<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><code>Witaj, {name}<\/code><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">albo:<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><code>Zam\u00f3wienie nr {id} zosta\u0142o wys\u0142ane<\/code><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Wtedy s\u0142ownik przechowuje szablon, a program podstawia dane.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Przyk\u0142ad Python:<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>J\u0119zyk<\/th><th>Kod<\/th><\/tr><\/thead><tbody><tr><td>Python<\/td><td><code>python\\nmessage = \\\"Witaj, {name}\\\"\\nprint(message.format(name=\\\"Anna\\\"))\\n<\/code><\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">To trzeba robi\u0107 ostro\u017cnie. Z\u0142y placeholder potrafi zepsu\u0107 ca\u0142y ekran albo wygenerowa\u0107 b\u0142\u0119dny dokument.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"wydajnosc-wyszukiwania-oraz-koszt-operacyjny-przy-duzych-systemach-wielojezycznych\">Wydajno\u015b\u0107 wyszukiwania oraz koszt operacyjny przy du\u017cych systemach wieloj\u0119zycznych<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Przy 20 komunikatach problemu nie wida\u0107.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Przy:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>50 000 kluczy<\/li>\n\n\n\n<li>12 j\u0119zykach<\/li>\n\n\n\n<li>wielu mikroserwisach<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">zaczyna mie\u0107 znaczenie:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>czas \u0142adowania<\/li>\n\n\n\n<li>zu\u017cycie pami\u0119ci<\/li>\n\n\n\n<li>cache<\/li>\n\n\n\n<li>synchronizacja wersji<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">Hash map ma \u015brednio z\u0142o\u017cono\u015b\u0107:<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Operacja<\/th><th>Z\u0142o\u017cono\u015b\u0107<\/th><\/tr><\/thead><tbody><tr><td>wyszukiwanie<\/td><td>O(1)<\/td><\/tr><tr><td>wstawianie<\/td><td>O(1)<\/td><\/tr><tr><td>usuwanie<\/td><td>O(1)<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">Tablica liniowa:<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Operacja<\/th><th>Z\u0142o\u017cono\u015b\u0107<\/th><\/tr><\/thead><tbody><tr><td>wyszukiwanie<\/td><td>O(n)<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">Dlatego r\u0119czne przeszukiwanie tablic w du\u017cych systemach jest z\u0142ym pomys\u0142em.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Cz\u0119sto stosuje si\u0119:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>preload przy starcie aplikacji<\/li>\n\n\n\n<li>cache Redis<\/li>\n\n\n\n<li>pami\u0119\u0107 lokaln\u0105 procesu<\/li>\n\n\n\n<li>wersjonowanie plik\u00f3w t\u0142umacze\u0144<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">B\u0142\u0105d spotykany bardzo cz\u0119sto: ka\u017cde t\u0142umaczenie pobierane osobnym zapytaniem SQL. Przy wi\u0119kszym ruchu to zabija wydajno\u015b\u0107.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"slowniki-tlumaczen-w-systemach-produkcyjnych-i-problemy-ktore-naprawde-psuja-projekty\">S\u0142owniki t\u0142umacze\u0144 w systemach produkcyjnych i problemy, kt\u00f3re naprawd\u0119 psuj\u0105 projekty<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Najcz\u0119stsze problemy nie s\u0105 algorytmiczne, tylko organizacyjne.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"1-duplikacja-kluczy\">1. Duplikacja kluczy<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\"><code>save.button<\/code><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">i r\u00f3wnolegle<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><code>button.save<\/code><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Po roku nikt nie wie, kt\u00f3rego u\u017cywa\u0107.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"2-brak-fallback-language\">2. Brak fallback language<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Je\u015bli brakuje t\u0142umaczenia dla <code>de<\/code>, system powinien umie\u0107 wr\u00f3ci\u0107 np. do <code>en<\/code>.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Bez tego u\u017cytkownik widzi pusty ekran albo sam klucz.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"3-tlumaczenie-klucza-zamiast-wartosci\">3. T\u0142umaczenie klucza zamiast warto\u015bci<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Klucz ma by\u0107 techniczny, nie j\u0119zykowy.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">\u0179le:<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><code>blad_logowania<\/code><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Dobrze:<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><code>auth.login.error<\/code><\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"4-brak-wersjonowania\">4. Brak wersjonowania<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Zmiana tekstu prawnego bez historii mo\u017ce oznacza\u0107 realny problem biznesowy albo prawny.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"5-reczna-edycja-bez-walidacji\">5. R\u0119czna edycja bez walidacji<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Jeden brakuj\u0105cy przecinek w JSON i produkcja przestaje dzia\u0142a\u0107.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">To kosztuje realne pieni\u0105dze, nie tylko czas.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"krotkie-wzory-i-zaleznosci-uzywane-przy-analizie-wydajnosci-wyszukiwania\">Kr\u00f3tkie wzory i zale\u017cno\u015bci u\u017cywane przy analizie wydajno\u015bci wyszukiwania<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Przy analizie struktur danych warto pami\u0119ta\u0107 o podstawowych zale\u017cno\u015bciach.<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><thead><tr><th>Zagadnienie<\/th><th>Wz\u00f3r<\/th><\/tr><\/thead><tbody><tr><td>wyszukiwanie liniowe<\/td><td><math xmlns=\"http:\/\/www.w3.org\/1998\/Math\/MathML\"><semantics><mrow><mi>T<\/mi><mo stretchy=\"false\">(<\/mo><mi>n<\/mi><mo stretchy=\"false\">)<\/mo><mo>=<\/mo><mi>n<\/mi><\/mrow><annotation encoding=\"application\/x-tex\">T(n) = n<\/annotation><\/semantics><\/math>T(n)=n<\/td><\/tr><tr><td>wyszukiwanie w hash map<\/td><td><math xmlns=\"http:\/\/www.w3.org\/1998\/Math\/MathML\"><semantics><mrow><mi>T<\/mi><mo stretchy=\"false\">(<\/mo><mi>n<\/mi><mo stretchy=\"false\">)<\/mo><mo>\u2248<\/mo><mn>1<\/mn><\/mrow><annotation encoding=\"application\/x-tex\">T(n) \\approx 1<\/annotation><\/semantics><\/math>T(n)\u22481<\/td><\/tr><tr><td>pami\u0119\u0107 dla n wpis\u00f3w<\/td><td><math xmlns=\"http:\/\/www.w3.org\/1998\/Math\/MathML\"><semantics><mrow><mi>M<\/mi><mo stretchy=\"false\">(<\/mo><mi>n<\/mi><mo stretchy=\"false\">)<\/mo><mo>=<\/mo><mi>n<\/mi><mo>\u22c5<\/mo><mo stretchy=\"false\">(<\/mo><mi>k<\/mi><mo>+<\/mo><mi>v<\/mi><mo>+<\/mo><mi>o<\/mi><mo stretchy=\"false\">)<\/mo><\/mrow><annotation encoding=\"application\/x-tex\">M(n) = n \\cdot (k + v + o)<\/annotation><\/semantics><\/math>M(n)=n\u22c5(k+v+o)<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<p class=\"wp-block-paragraph\">gdzie:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><code>k<\/code> &#8211; rozmiar klucza<\/li>\n\n\n\n<li><code>v<\/code> &#8211; rozmiar warto\u015bci<\/li>\n\n\n\n<li><code>o<\/code> &#8211; narzut struktury<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">Przy 100 000 wpis\u00f3w r\u00f3\u017cnica pami\u0119ciowa mi\u0119dzy naiwn\u0105 implementacj\u0105 a dobrze zaprojektowan\u0105 map\u0105 jest ju\u017c zauwa\u017calna.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"faq\">FAQ<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"czy-klucze-powinny-byc-po-angielsku\">Czy klucze powinny by\u0107 po angielsku?<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Najcz\u0119\u015bciej tak, bo projekty techniczne zwykle s\u0105 rozwijane mi\u0119dzynarodowo. Wa\u017cniejsze od j\u0119zyka jest jednak zachowanie sp\u00f3jno\u015bci.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"czy-baza-danych-jest-lepsza-niz-pliki-json\">Czy baza danych jest lepsza ni\u017c pliki JSON?<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Nie zawsze. Dla statycznych t\u0142umacze\u0144 pliki s\u0105 prostsze i szybsze. Baza ma sens przy dynamicznej edycji przez panel administracyjny.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"czy-warto-trzymac-tlumaczenia-w-frontendzie-i-backendzie-osobno\">Czy warto trzyma\u0107 t\u0142umaczenia w frontendzie i backendzie osobno?<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Tak, je\u015bli zakres odpowiedzialno\u015bci jest r\u00f3\u017cny. Wsp\u00f3lny system bywa wygodny, ale cz\u0119sto komplikuje deployment.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"co-zrobic-gdy-brakuje-tlumaczenia\">Co zrobi\u0107, gdy brakuje t\u0142umaczenia?<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Najlepiej zastosowa\u0107 fallback do j\u0119zyka domy\u015blnego i logowa\u0107 brakuj\u0105cy klucz do monitoringu.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"czy-nazwa-klucza-moze-sie-zmieniac\">Czy nazwa klucza mo\u017ce si\u0119 zmienia\u0107?<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Technicznie tak, ale praktycznie lepiej tego unika\u0107. Zmiana klucza cz\u0119sto wymaga zmian w wielu us\u0142ugach naraz.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"czy-tlumaczenia-powinny-byc-cacheowane\">Czy t\u0142umaczenia powinny by\u0107 cache\u2019owane?<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Tak. Wielokrotne odczytywanie tych samych danych z pliku lub bazy bez cache jest niepotrzebnym obci\u0105\u017ceniem.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"zakonczenie\">Zako\u0144czenie<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Dobrze zaprojektowany system t\u0142umacze\u0144 nie wygl\u0105da efektownie, ale ratuje projekt wtedy, gdy aplikacja zaczyna rosn\u0105\u0107. To jedna z tych rzeczy, kt\u00f3re wydaj\u0105 si\u0119 drobiazgiem na pocz\u0105tku, a p\u00f3\u017aniej decyduj\u0105 o kosztach utrzymania, czasie wdro\u017ce\u0144 i liczbie b\u0142\u0119d\u00f3w na produkcji. Porz\u0105dek w kluczach, przewidywalna struktura i rozs\u0105dne regu\u0142y fallback s\u0105 znacznie wa\u017cniejsze ni\u017c wyb\u00f3r konkretnego formatu pliku.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><em>\u0179r\u00f3d\u0142o Foto: Freepik<\/em><\/p>\n","protected":false},"excerpt":{"rendered":"<p>W systemach wieloj\u0119zycznych bardzo szybko pojawia si\u0119 ten sam problem: ta sama informacja musi zosta\u0107 pokazana u\u017cytkownikowi w r\u00f3\u017cnych j\u0119zykach, bez przepisywania ca\u0142ej logiki programu. Nie chodzi tylko o interfejs aplikacji, ale te\u017c komunikaty b\u0142\u0119d\u00f3w, opisy produkt\u00f3w, statusy zam\u00f3wie\u0144, raporty czy dokumenty generowane automatycznie. Je\u015bli ten mechanizm nie jest uporz\u0105dkowany, projekt zaczyna si\u0119 rozpada\u0107 przy ka\u017cdej zmianie tekstu. Najpro\u015bciej porz\u0105dkuje si\u0119 to przez S\u0142owniki t\u0142umacze\u0144. S\u0142owniki t\u0142umacze\u0144 jako warstwa po\u015brednia mi\u0119dzy kodem programu a tre\u015bci\u0105 widoczn\u0105 dla u\u017cytkownika Najwa\u017cniejsza zasada jest prosta: w kodzie nie zapisuje si\u0119 tekst\u00f3w ko\u0144cowych typu \u201eB\u0142\u0105d logowania\u201d albo \u201eZapisano poprawnie\u201d, tylko u\u017cywa si\u0119 kluczy logicznych, na przyk\u0142ad: Program operuje na kluczach, a dopiero osobna struktura danych zamienia klucz na tekst w odpowiednim j\u0119zyku. Dzi\u0119ki temu: To jest podstawowy wzorzec stosowany w systemach i18n (internationalization) i l10n (localization). Przyk\u0142ad dzia\u0142ania: Bez tego przy wi\u0119kszym projekcie zaczyna si\u0119 chaos: ten sam komunikat wyst\u0119puje w 12 miejscach, cz\u0119\u015b\u0107 po polsku, cz\u0119\u015b\u0107 po angielsku, cz\u0119\u015b\u0107 w starej wersji. Struktura danych i spos\u00f3b przechowywania map klucz\u2013warto\u015b\u0107 w pami\u0119ci oraz na dysku Najcz\u0119\u015bciej u\u017cywa si\u0119 struktury typu: czyli relacji: klucz -&gt; warto\u015b\u0107 Przyk\u0142ad logiczny: Klucz Polski Angielski login.error B\u0142\u0105d logowania Login error cart.empty Koszyk jest pusty Cart is empty user.saved Zapisano u\u017cytkownika User saved Klucz powinien by\u0107: Z\u0142y przyk\u0142ad: B\u0142\u0105d_logowania Dobry przyk\u0142ad: auth.login.error Drugi wariant jest lepszy, bo porz\u0105dkuje system modu\u0142owo. Popularne formaty zapisu: Najcz\u0119\u015bciej w praktyce webowej u\u017cywa si\u0119 JSON lub YAML, bo s\u0105 szybkie do edycji i \u0142atwe do \u0142adowania. Przyk\u0142ad JSON: Format Przyk\u0142ad JSON { &#8222;login.error&#8221;: &#8222;B\u0142\u0105d logowania&#8221;, &#8222;user.saved&#8221;: &#8222;Zapisano u\u017cytkownika&#8221; } Przyk\u0142ad YAML: Format Przyk\u0142ad YAML login.error: &#8222;B\u0142\u0105d logowania&#8221; JSON jest wygodniejszy dla parser\u00f3w, YAML dla ludzi. S\u0142owniki t\u0142umacze\u0144 w Pythonie, C oraz C++ na prostych przyk\u0142adach akademickich Najprostszy przyk\u0142ad to r\u0119czna mapa klucz\u2013warto\u015b\u0107. Python J\u0119zyk Kod Python python\\ntranslations = {\\n \\&#8221;login.error\\&#8221;: \\&#8221;B\u0142\u0105d logowania\\&#8221;,\\n \\&#8221;user.saved\\&#8221;: \\&#8221;Zapisano u\u017cytkownika\\&#8221;\\n}\\n\\nkey = \\&#8221;login.error\\&#8221;\\nprint(translations.get(key, \\&#8221;Brak t\u0142umaczenia\\&#8221;))\\n Metoda get() jest wa\u017cna, bo zabezpiecza przed b\u0142\u0119dem braku klucza. C++ J\u0119zyk Kod C++ cpp\\n#include &lt;iostream&gt;\\n#include &lt;map&gt;\\nusing namespace std;\\n\\nint main() {\\n map&lt;string, string&gt; translations;\\n\\n translations[\\&#8221;login.error\\&#8221;] = \\&#8221;B\u0142\u0105d logowania\\&#8221;;\\n translations[\\&#8221;user.saved\\&#8221;] = \\&#8221;Zapisano u\u017cytkownika\\&#8221;;\\n\\n string key = \\&#8221;login.error\\&#8221;;\\n cout &lt;&lt; translations[key] &lt;&lt; endl;\\n\\n return 0;\\n}\\n W nowoczesnym C++ cz\u0119sto u\u017cywa si\u0119 unordered_map, bo jest szybsze dla wyszukiwania. C C nie ma wbudowanego s\u0142ownika, wi\u0119c najcz\u0119\u015bciej robi si\u0119 tablic\u0119 struktur. J\u0119zyk Kod C c\\n#include &lt;stdio.h&gt;\\n#include &lt;string.h&gt;\\n\\nstruct Translation {\\n char key[50];\\n char value[100];\\n};\\n\\nint main() {\\n struct Translation dict[] = {\\n {\\&#8221;login.error\\&#8221;, \\&#8221;B\u0142\u0105d logowania\\&#8221;},\\n {\\&#8221;user.saved\\&#8221;, \\&#8221;Zapisano u\u017cytkownika\\&#8221;}\\n };\\n\\n int size = 2;\\n char search[] = \\&#8221;login.error\\&#8221;;\\n\\n for(int i = 0; i &lt; size; i++) {\\n if(strcmp(dict[i].key, search) == 0) {\\n printf(\\&#8221;%s\\\\n\\&#8221;, dict[i].value);\\n }\\n }\\n\\n return 0;\\n}\\n To rozwi\u0105zanie jest wolniejsze, ale dobrze pokazuje ide\u0119. S\u0142owniki t\u0142umacze\u0144 a problem odmiany j\u0119zykowej liczby mnogiej i parametr\u00f3w dynamicznych Prosty tekst to dopiero pocz\u0105tek. Problem zaczyna si\u0119 przy takich komunikatach: Polski jest tu znacznie trudniejszy ni\u017c angielski. Nie wystarczy jeden wpis. Potrzebne s\u0105 regu\u0142y pluralizacji. Przyk\u0142ad logiczny Liczba Wersja 1 wiadomo\u015b\u0107 2\u20134 wiadomo\u015bci 5+ wiadomo\u015bci \/ wiadomo\u015bci zale\u017cnie od regu\u0142y Jeszcze trudniejsze s\u0105 parametry dynamiczne: Witaj, {name} albo: Zam\u00f3wienie nr {id} zosta\u0142o wys\u0142ane Wtedy s\u0142ownik przechowuje szablon, a program podstawia dane. Przyk\u0142ad Python: J\u0119zyk Kod Python python\\nmessage = \\&#8221;Witaj, {name}\\&#8221;\\nprint(message.format(name=\\&#8221;Anna\\&#8221;))\\n To trzeba robi\u0107 ostro\u017cnie. Z\u0142y placeholder potrafi zepsu\u0107 ca\u0142y ekran albo wygenerowa\u0107 b\u0142\u0119dny dokument. Wydajno\u015b\u0107 wyszukiwania oraz koszt operacyjny przy du\u017cych systemach wieloj\u0119zycznych Przy 20 komunikatach problemu nie wida\u0107. Przy: zaczyna mie\u0107 znaczenie: Hash map ma \u015brednio z\u0142o\u017cono\u015b\u0107: Operacja Z\u0142o\u017cono\u015b\u0107 wyszukiwanie O(1) wstawianie O(1) usuwanie O(1) Tablica liniowa: Operacja Z\u0142o\u017cono\u015b\u0107 wyszukiwanie O(n) Dlatego r\u0119czne przeszukiwanie tablic w du\u017cych systemach jest z\u0142ym pomys\u0142em. Cz\u0119sto stosuje si\u0119: B\u0142\u0105d spotykany bardzo cz\u0119sto: ka\u017cde t\u0142umaczenie pobierane osobnym zapytaniem SQL. Przy wi\u0119kszym ruchu to zabija wydajno\u015b\u0107. S\u0142owniki t\u0142umacze\u0144 w systemach produkcyjnych i problemy, kt\u00f3re naprawd\u0119 psuj\u0105 projekty Najcz\u0119stsze problemy nie s\u0105 algorytmiczne, tylko organizacyjne. 1. Duplikacja kluczy save.button i r\u00f3wnolegle button.save Po roku nikt nie wie, kt\u00f3rego u\u017cywa\u0107. 2. Brak fallback language Je\u015bli brakuje t\u0142umaczenia dla de, system powinien umie\u0107 wr\u00f3ci\u0107 np. do en. Bez tego u\u017cytkownik widzi pusty ekran albo sam klucz. 3. T\u0142umaczenie klucza zamiast warto\u015bci Klucz ma by\u0107 techniczny, nie j\u0119zykowy. \u0179le: blad_logowania Dobrze: auth.login.error 4. Brak wersjonowania Zmiana tekstu prawnego bez historii mo\u017ce oznacza\u0107 realny problem biznesowy albo prawny. 5. R\u0119czna edycja bez walidacji Jeden brakuj\u0105cy przecinek w JSON i produkcja przestaje dzia\u0142a\u0107. To kosztuje realne pieni\u0105dze, nie tylko czas. Kr\u00f3tkie wzory i zale\u017cno\u015bci u\u017cywane przy analizie wydajno\u015bci wyszukiwania Przy analizie struktur danych warto pami\u0119ta\u0107 o podstawowych zale\u017cno\u015bciach. Zagadnienie Wz\u00f3r wyszukiwanie liniowe T(n)=nT(n) = nT(n)=n wyszukiwanie w hash map T(n)\u22481T(n) \\approx 1T(n)\u22481 pami\u0119\u0107 dla n wpis\u00f3w M(n)=n\u22c5(k+v+o)M(n) = n \\cdot (k + v + o)M(n)=n\u22c5(k+v+o) gdzie: Przy 100 000 wpis\u00f3w r\u00f3\u017cnica pami\u0119ciowa mi\u0119dzy naiwn\u0105 implementacj\u0105 a dobrze zaprojektowan\u0105 map\u0105 jest ju\u017c zauwa\u017calna. FAQ Czy klucze powinny by\u0107 po angielsku? Najcz\u0119\u015bciej tak, bo projekty techniczne zwykle s\u0105 rozwijane mi\u0119dzynarodowo. Wa\u017cniejsze od j\u0119zyka jest jednak zachowanie sp\u00f3jno\u015bci. Czy baza danych jest lepsza ni\u017c pliki JSON? Nie zawsze. Dla statycznych t\u0142umacze\u0144 pliki s\u0105 prostsze i szybsze. Baza ma sens przy dynamicznej edycji przez panel administracyjny. Czy warto trzyma\u0107 t\u0142umaczenia w frontendzie i backendzie osobno? Tak, je\u015bli zakres odpowiedzialno\u015bci jest r\u00f3\u017cny. Wsp\u00f3lny system bywa wygodny, ale cz\u0119sto komplikuje deployment. Co zrobi\u0107, gdy brakuje t\u0142umaczenia? Najlepiej zastosowa\u0107 fallback do j\u0119zyka domy\u015blnego i logowa\u0107 brakuj\u0105cy klucz do monitoringu. Czy nazwa klucza mo\u017ce si\u0119 zmienia\u0107? Technicznie tak, ale praktycznie lepiej tego unika\u0107. Zmiana klucza cz\u0119sto wymaga zmian w wielu us\u0142ugach naraz. Czy t\u0142umaczenia powinny by\u0107 cache\u2019owane? Tak. Wielokrotne odczytywanie tych samych danych z pliku lub bazy bez cache jest niepotrzebnym obci\u0105\u017ceniem. Zako\u0144czenie Dobrze zaprojektowany system t\u0142umacze\u0144 nie wygl\u0105da efektownie, ale ratuje projekt wtedy, gdy aplikacja zaczyna rosn\u0105\u0107. To jedna z tych rzeczy, kt\u00f3re wydaj\u0105 si\u0119 drobiazgiem na pocz\u0105tku, a p\u00f3\u017aniej decyduj\u0105 o kosztach utrzymania, czasie wdro\u017ce\u0144 i liczbie b\u0142\u0119d\u00f3w na produkcji. Porz\u0105dek w kluczach, przewidywalna struktura i rozs\u0105dne regu\u0142y fallback s\u0105 znacznie wa\u017cniejsze ni\u017c wyb\u00f3r konkretnego formatu pliku. \u0179r\u00f3d\u0142o Foto: Freepik<\/p>\n","protected":false},"author":1,"featured_media":1371,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[24,1],"tags":[],"class_list":["post-1370","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-kodowanie","category-poradnik"],"_links":{"self":[{"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/posts\/1370","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/comments?post=1370"}],"version-history":[{"count":1,"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/posts\/1370\/revisions"}],"predecessor-version":[{"id":1372,"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/posts\/1370\/revisions\/1372"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/media\/1371"}],"wp:attachment":[{"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/media?parent=1370"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/categories?post=1370"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/trzykody.pl\/index.php\/wp-json\/wp\/v2\/tags?post=1370"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}