Polski poeta AI (GPT-2 na Google Colab)

Polski Poeta AI (Google Colab)

– Księżniczko, rezerwować w tym roku na Walentynki miejsce w restauracji z naszej pierwszej randki? – zapytałem moją żonę Elwirkę.

– Hmm… w tym roku nie będzie tak łatwo. Wymyśl coś oryginalnego i wyjątkowego – odpowiedziała z uśmiechem na twarzy rzucając mi wyzwanie.

– Cokolwiek? – dopytałem.

– Nie cokolwiek, bo znów jakąś głupotę wymyślisz. Chciałabym, aby było to coś romantycznego i coś stworzonego specjalnie dla mnie – doprecyzowała.

– Potrzymaj mi Skarbie piwo.  – zażartowałem. – Mam pewien pomysł…

cytat banksterzy
(GPT-2 na Google Colab)

Z tą myślą stworzyłem wspólnie z Krystianem kod, który każdego może zamienić  w poetę. Każdy facet będzie mógł zostać romantycznym bohaterem w swoim domu w najbliższe Walentynki! Jak? Przygotowaliśmy prosty skrypt na Google Colab. Wystarczy powiedzieć jedno zdanie do mikrofonu komputera, które zostanie zarejestrowane,  a następnie potraktowane jako pierwszy wers nowego dzieła lirycznego. Słowa przekazane zostaną do modelu GPT-2, który napisze resztę nowego i unikalnego utworu.

Polski AI - model GPT-2 na Google Cloud idea działania
(GPT-2 na Google Colab)

TUTAJ możesz odpalić kod (klikając Shift+Enter wykonujesz kod w danej komórce): https://colab.research.google.com/drive/1erm8iva3PpTh6OmPNj5Mlg8Djlz-fMpK?usp=sharing

A jeśli chcesz zobaczyć, od czego naprawdę się wszystko zaczęło i jak działa model to zapraszam do dalszej lektury…

Wstęp, czyli jak to się zaczęło

Pewnego wieczoru, leżąc zmęczony i ledwo żywy w swoim łóżku po walce z usypianiem dwóch córek cierpiących na bezsenność, przeglądałem LinkedIn. Tam znalazłem post Piotrka (TUTAJ link). Zapraszał w nim do udziału w pierwszym w Polsce konkursie ze sztuk audiowizualnych z AI pod nazwą Digital-Ars.

Pomyślałem, że to super ciekawy konkurs i biorąc w nim udział będę mógł nauczyć się nowych rzeczy. Jednak, aby chęci i power był większy nie chciałem brać w nim udziału sam. Podpytałem kilku znajomych, co o tym myślą i … znalazłem drugą osobę równie mocno zajaraną jak ja na udział  w nim. Dosłownie napaliliśmy się, jak Reksio na szynkę!

jaram się jak reksio szynką

Na początku mieliśmy wiele pomysłów na różne projekty. Natomiast, jak w regulaminie doczytaliśmy, że najlepsze prace będą wystawiane w Narodowej Galerii Sztuki, to nasza wyobraźnia zaczęła jeszcze bardziej płynąć. Ostatecznie postanowiliśmy stworzyć projekt, który można byłoby potraktować jako eksponat. Wyobraziliśmy sobie, że w Galerii stoi komputer, za pomocą którego każdy gość będzie mógł stworzyć dla siebie lub kogoś bliskiego wiersz.  Dlatego ostatecznie postanowiliśmy przygotować prosty kod, który będzie można prosto odpalić na każdym komputerze.

Przygotowywanie danych

Jak w każdym projekcie związanym z uczeniem maszynowym najważniejsze są dane.  I zawsze będę podkreślał zasadę „Shit in, shit out”. Wiersze pobraliśmy z dwóch źródeł:

Oba zbiory danych połączyliśmy w jedną całość. Troszkę czasu zajęło nam napisanie ogólnych reguł do oczyszczania danych. Mając kilkadziesiąt tysięcy poematów zescrapowanych z sieci, czasami naprawdę trafia się na dziwne „kwiatki”. Dla przykładu niektóre wiersze miały wersy co 3 linijkę, inne zawierały tylko tytuł, a jeszcze inne były napisane w obcych językach. Pracując nad dopieszczeniem danych przyjęliśmy kilka założeń:

  • usunęliśmy utwory, które miały średnio w wersie powyżej 50 znaków; chcieliśmy raczej nauczyć model pisania krótszych wersów. Dodatkowo wycięliśmy prozę, która się załapała przy ściąganiu danych;
  • wybraliśmy wiersze z rymami AABB, ABAB. Dlaczego podeszliśmy w ten sposób? Intuicja podpowiadała, że trenując model będzie miał większą szansę na nauczenie się rymów;
  • model  GPT-2 potrzebuje dużej liczby danych, by się fajnie nauczyć. Zatem nie ograniczaliśmy się do konkretnych epok, tylko wzięliśmy wszystko jak leci. Troszkę nad tym dyskutowaliśmy, ale dzięki temu mieliśmy nadzieję, że model będzie w stanie spróbować przenikać między stylami różnych epok. A to sprawi, że będzie w unikalny sposób i tylko dla siebie tworzył wyjątkową poezję.

Ostateczne wyczyszczone dane, na których trenowaliśmy model możecie pobrać TUTAJ.

sprzątanie śnieżka

Co to są modele GPT?

Modele GPT (ang. Generative Pretrained Transformer) są modelami językowymi, które wykorzystują głębokie uczenie do tworzenia tekstu podobnego do człowieka. Zostały one stworzone przez laboratorium badawcze sztucznej inteligencji OpenAI z siedzibą w San Francisco.  Modele na podstawie kilku krótkich słów lub zdań są w stanie wygenerować często imponująco wyglądające całe akapity spójnego tekstu. Wyjaśnijmy sobie najpierw znaczenie skrótu GPT:

  • Generatywny (ang. Generative)  – oznacza, że model został przeszkolony, aby przewidywać (lub „generować”) następny token w sekwencji tokenów w sposób nienadzorowany. Innymi słowy, do modelu wrzucono całe mnóstwo surowych danych tekstowych i poproszono o określenie statystycznych cech tekstu w celu stworzenia większej ilości tekstu.
  • Wstępnie wyszkolony (ang. Pretrained) – oznacza, że OpenAI stworzyło duży i potężny model językowy, który później dostosował do określonych zadań, takich jak tłumaczenie maszynowe. To trochę jak transfer learning z modelu Imagenet do zadań związanych ze zdjęciami, z wyjątkiem tego, że dotyczy NLP.
  • Transformer – oznacza, że OpenAI użył architektury transformatora. O transformerach pisałem szerzej w ostatnim artykule (TUTAJ link).
  • 1 / 2 / 3 – cyfra przy modelu to jego kolejna wersja.
its ok joey friends

Czym się różni GPT-2 od GPT-3?

W 2019 OpenAI udostępnił model GPT-2, który na podstawie kilku zdań mógł wygenerować całkowicie nowy tekst trzymający pierwotny kontekst. Od razu takie wyniki rozbudziły wyobraźnię ludzi, w którym kierunku zaczną się takie modele rozwijać i jak będą w stanie zmienić świat (oby na lepsze!). Aby stworzyć obszerny i dobrej jakości zbiór danych, autorzy zeskrobali platformę Reddit i pobrali dane z linków wychodzących z wysoko ocenianych artykułów. Wynikowy zbiór danych o nazwie WebText zawierał 40 GB danych tekstowych z ponad 8 milionów dokumentów składających się z 50.257 tokenów! Największy model GPT-2 miał aż 1.5 miliarda parametrów.

Rok później OpenAI zadziwił świat przedstawiając kolejną wersję GPT-3. Największa wersja modelu GPT-3 ma 175 miliardów parametrów, czyli ponad 100 razy więcej niż w GPT-2. Dla przykładu język polski ma około 140.000 słów. Czyli do każdego słowa można byłoby przypisać po …1.250.000 parametrów! GPT-3 zostało przeszkolone na setkach miliardów słów i jest w stanie rozumieć również składnie języków takich jak html, SQL czy Python. Największą magią jest to, że dane treningowe GPT-3 obejmowały niemal wszystko co zostało zapisane,  więc nie wymagają dalszego szkolenia w zakresie różnych zadań językowych. Po prostu pokazujesz kilka przykładów, a model sam szybko zrozumie, co ma wygenerować.

Tutaj masz przykład wykorzystania GPT-3, który kiedyś wysyłałem w newsletterze (jak się nie zapisałeś to możesz zrobić to TUTAJ).

Mi się stasznie podoba przykład drugi, który pokazuje jak tego rodzaju modele będą mogły wspomóc developerów w najprostszych elemetach architektury. Nie będą musieli pisać sami kodu, tylko poproszą pewną aplikację o przygotowanie im jakiegoś wsadu.

Dlaczego wybraliśmy GPT-2?

22 września 2020 Microsoft ogłosił, że zakupił licencje na „wyłączne” używanie GPT-3. Oczywiście wspomnieli, że inni mogą nadal używać publicznego API do odbierania danych wyjściowych, ale tylko Microsoft ma kontrolę nad kodem źródłowym.  Niestety wszystkie nasze podania o dostęp do GPT-3 pozostały bez odzewu 😞.

GPT-3 ciągle czekam na odpowiedź

TUTAJ oficjalny link, pod którym się zgłaszaliśmy. Z powodu braku innej możliwości wykorzystaliśmy GPT-2, który można bardzo łatwo zaimportować. Do wyboru są 4 dostępne wersje modelu GPT-2:

GPT-2 wielkości modelu

My wybraliśmy wersję „MEDIUM”, bo nie było problemu z przeliczeniem na platformie, którą wybraliśmy.

Co to jest Google Colab?

Google Colab (jako skrót od Colaboratory), to produkt firmy Google Research, który umożliwia każdemu pisanie i wykonywanie dowolnego kodu Python za pośrednictwem przeglądarki. Jest szczególnie dobrze przystosowany do uczenia maszynowego, analizy danych i … edukacji. Jest bardzo prosty w użyciu i nie wymaga żadnej konfiguracji ze strony użytkownika. A co najciekawsze zapewnia darmowy dostęp do obliczeń (w tym GPU oraz TPU).

(GPT-2 na Google Colab)

Jeśli nie pracowałeś wcześniej z Jupyter Notebook, to i tak jestem pewien, że szybko się odnajdziesz. Interfejs jest bardzo prosty i intuicyjny. W górnej części znajdziesz menu do zapisywania czy udostępniania Notebooków. Możesz też prosto zmienić środowisko (np. na GPU) lub uruchomić wszystkie komórki z komendami jednocześnie. W dolnej części jest zwykły Jupyter Notebook. Czasami po prawej stronie może znaleźć się również spis treści lub plików.

Dlaczego wybraliśmy Google Colab?

Ponieważ ma według mnie wiele zalet!

  1. Po pierwsze jest to framework, z którego wcześniej już korzystałem.  Zatem próg wejścia był w miarę prosty. A przyznam, że wystartowaliśmy z pisaniem kodu na konkurs w listopadzie, więc nie było zbyt dużo czasu na zastanawianie się jak dowieść projekt!
  2. Jest to miejsce, które zupełnie za darmo można wykorzystywać przez określony czas GPUGIF!
  3. Kolejną zaletą jest to, że nic nie trzeba konfigurować. Wchodzisz tutaj: https://colab.research.google.com/  i od  razu działasz.
  4. W internecie możesz znaleźć setki tutoriali (pl. samouczków :P) w Google Colab. Wchodzisz i od razu możesz zobaczyć kod i skopiować go na swoje potrzeby.

Przyznam Ci się do czegoś jeszcze – nie mam jeszcze doświadczenia z pracą w chmurze: czy to na AWS, Azure czy Google Cloud. W związku z presją czasu (termin oddawania prac na koniec listopada) nie mieliśmy czasu z Krystianem wchodzić w nowe technologie. Pracując w Banku nie korzystamy za bardzo z rozwiązań chmurowych ze względu na brak możliwości przetwarzania wrażliwych danych klientów na zewnętrze serwery. Natomiast bankowość też się zmienia i niedługo zaczynam projekt na AWS, więc możesz spodziewać się jakichś informacji w tym temacie na blogu w drugiej połowie roku!

A czy Google Colab ma wady?

Oczywiście, że Google Colab nie jest idealny i ma też kilka wad, o których warto wspomnieć:

  1. Dane trzymamy na dysku Google (do 15 GB), więc jeśli mocno go eksplorujesz, wówczas będziesz miał mało miejsca. Ale Polak potrafi – zawsze można utworzyć nowe konto pod projekt🙂
  2. Pamięć jest używana tylko z bieżącą sesją. Zatem jeśli chcesz jakiś plik wykorzystać w przyszłości należy pamiętać, by go zapisać!
  3. To co nam najbardziej przeszkadzało w projekcie to brak dostępu do GPU przez cały czas. Jeśli wszystkie zasoby GPU są potrzebne dla użytkowników PRO (płatna wersja), to nie ma możliwości skorzystania. Również GPU nie można używać przez dłuższy czas (>12h).  Dlatego chcąc wykorzystać GPU trenując dłużej model należy o to dodatkowo zadbać.

Jak trenowaliśmy model GPT-2 na Google Colab?

Tak jak wspomniałem wyżej Google Colab ma swoje ograniczenia. Dlatego musieliśmy wykorzystać ciekawą właściwość sieci neuronowych.  Jaką?

Tak naprawdę trenując sieć neuronową optymalizujemy funkcję straty. Każde kolejne przeliczenie (epoka) po prostu nadpisuje stare wagi nowymi. Zatem wystarczy trenować sieć przez odpowiednią ilość czasu, na jaką platforma nam pozwala i zapisać wagi naszego modelu. Następnie możemy kontynuować liczenie naszego modelu GPT-2 na Google Colab zaczynając od nowa wczytując wagi, które zapisaliśmy. Ot cała filozofia.

Przejdźmy wszystko po kolei, abyś potrafił sam wytrenować model dla własnego zbioru danych (np. scenogramów sejmowych gdybyś chciał stworzyć własną wersję obrad).

Wczytanie bibliotek do modelu GPT-2 na Google Colab

Zaczynamy od wczytania odpowiednich bibliotek i wcześniejszej wersji Tensorflow by pobrany model działał.

%tensorflow_version 1.x
!pip install -q gpt-2-simple
import gpt_2_simple as gpt2
from datetime import datetime
from google.colab import files
#import tensorflow as tf
import time

Warto jeszcze sprawdzić w opcjach czy masz włączone GPU!

(GPT-2 na Google Colab)
Pobranie danych

Teraz za pomocą krótkiej komendy:

gpt2.download_gpt2(model_name="355M")

pobieramy model GPT-2 Medium. A w kolejnym kroku nawiązujemy połączenie z naszym dyskiem Googla

gpt2.mount_gdrive()

by pobrać odpowiednie dane do trenowania modelu

file_name = "model_v01_clean.txt"
gpt2.copy_file_from_gdrive(file_name)
Pierwsze trenowanie modelu GPT-2 na Google Colab

Teraz za pomocą poniższego kodu rozpoczynamy trenowanie modelu GPT-2 na naszych danych.

sess = gpt2.start_tf_sess()
start = time.time()
gpt2.finetune(sess,
              dataset=file_name,
              model_name='355M',
              steps=15000,
              restore_from='fresh',
              run_name='mm_model_355M_v01',
              print_every=10,
              sample_every=2000,
              save_every=1000
              )
 
print(time.time() - start)

Zwróć uwagę, że nie ma zbyt wielu parametrów. Mamy ich kilka:

  • dataset – po prostu nasz pliczek z danymi do trenowania pobrany z dysku Googla;
  • steps – nasza liczba epok (jak nie wiesz co to epoka zapraszam TUTAJ)
  • restore_from – możemy tutaj ustawić parametr na dwa sposoby. Jako „fresh” by zacząć trenowanie na nowo modelu GPT-2 na Google Colab dla naszych danych lub jako „latest” aby wczytać model z ostatniego punktu kontrolnego (checkpoint’a);
  • print_every – liczba co ile epok ma nas informować;
  • sample_every – liczba co ile epok pokaże przykładowe dane wygenerowane przez model. Miej na uwadze, że zbyt częste wyświetlanie wydłuży proces uczenia;
  • run_name – ważne by zdefiniować ten parametr! Jest to tak naprawdę nazwa podfolderu, gdzie będzie zapisywany nasz model. Jak będziemy chcieli wczytać nasz wcześniejszy model i dalej go trenować będzie należało podać tę samą nazwę.;
  • save_every – informacja co ile epok chcemy zapisywać nasz model (checkpoint);
  • learning_rate – domyślnie ustawione jest 0.001. Dla małych zbiorów danych spokojnie możesz tą wartość obniżyć.

A co jakiś czas możesz spojrzeć na przykładowy wynik z modelu i czy wszystko się zapisało:

I jak widzisz wytrenowanie modelu GPT-2 na Google Colab nie jest wcale trudne :).

UWAGA! Po zakończonym treningu nie zapomnij zapisać modelu na dysku Google, byś mógł do niego później wrócić. Możesz zapisać go w ten sposób:

gpt2.copy_checkpoint_to_gdrive(run_name='mm_model_355M_v01')
Predykcja modelu GPT-2

A żeby wyświetlić predykcję wystarczy odpalić:

gpt2.generate(sess,
              run_name='mm_model_355M_v01',
              length=150,
              temperature=0.7,
              prefix="Mój wszechmocny Mirosławie",
              nsamples=5,
              batch_size=5
              )

gdzie:

  • run_name – to nazwa podfolderu, gdzie zapisany jest model
  • length – liczba tokenów do wygenerowania. Domyślna wartość jest maksymalna i wynosi 1023.
  • temperature – odpowiada za poziom „odjechania” tekstów. Im wyższa tym może pojawić się więcej nowych słów. Utrzymuje się by parametr był pomiędzy 0.7 a 1.0.
  • prefix – czyli dane wejściowe. W naszym przypadku pierwszy wers.
  • nsamples – liczba zwracanych rekordów. Jak szukaliśmy najładniejszego wiersza na konkurs to ustawiałem z 50 i brałem się za lekturę 😉
  • top_k – ogranicza generowane słowa do k najczęściej występujących (jeśli powstają dziwne słowa to można zwiększyć parametr). My przyjęliśmy domyślny parametr;
Dotrenowywanie modelu GPT-2 na Google Colab

Tak jak wspominałem jedną z wad na Google Colab jest to, że po określonym czasie przeliczenia notebook się wyłączy. Natomiast wyżej pokazałem Ci, jak zapisać przeliczenie modelu (checkpoint) na dysku Googla.

Zatem jak chcesz trenować dalej model (czyli dotrenonywać), to należy dodatkowo wczytać zapisany model:

gpt2.copy_checkpoint_from_gdrive(run_name='mm_model_355M_v01')

a następnie rozpoczynając trenowanie modelu zmienić parametr … i dodać …

tf.reset_default_graph()
sess = gpt2.start_tf_sess()
gpt2.finetune(sess,
              dataset=file_name,
              model_name='355M',
              restore_from = 'latest',
              steps=10000,
              run_name='mm_model_355M_v01',
              print_every=10,
              sample_every=2000,
              save_every=1000
              )
Uff... zrobiłem GPT-2 na Google Colab tworzący wiersze :)

Dopieszczanie „produktu”

Pomyśleliśmy, że zostało nam kilka dni, więc można jeszcze produkt dopieścić. Dlatego postanowiliśmy dodać jeszcze dwa elementy:

  1. Pierwszy to zczytywanie pierwszego wersu z mikrofonu. Dlaczego? Bo sobie wyobraziłem sam siebie jak stoję w Galerii i zamiast pisać na klawiaturze pierwszy wiersz (bo Covid) to mówię go i po chwili eksponat zwraca mi mój wiersz! Ah… brzmiało to ciekawie. Na szczęscie znaleźliśmy przykłady jak można to w miarę prosto rozwiązać. I co najciekawsze – super działa to dla języka polskiego!
  2. Jaka to epoka? Chcieliśmy jeszcze dać informacje, jaką epokę najbardziej przypomina wiersz. Do tego wytrenowaliśmy prosty model zwracający prawdopodbieństwa per każda epoka. Mała wtopa jest taka, że przygotowaliśmy to na szybko bez wielkiego przemyślenia… i wynik z modelu jest bardzo podobny do rozkładu ilości wierszy z danych epok. No cóż – mało użyteczny dodatek.
  3. Na koniec pomyśleliśmy, że odwiedzający Galerię chciałby wydrukować swój wiersz. Dlatego szybciutko zamknęliśmy wszystko w formie slajdu, który można zapisać🙂

Warto trenować dodawanie wisienek na torcie🙂.

Ostateczny wiersz

Do konkursu należało zgłosić nie tyle projekt, ile samo pojedyncze dzieło. Dlatego usiedliśmy z Krystianem, wpisaliśmy pierwszy wers „Ma miłość dla Ciebie jest wieczna” i każdy z nas wygenerował po 100 wierszy. Następnie wybraliśmy niezależnie po 3 najlepsze i potem wybraliśmy ten jedyny poemat. Wyjątkowo odstawał od reszty, bo całkiem ładnie trzymał kontekst. Krystian pokazał go koleżance humanistce, która oceniła go dość wysoko pod względem poezji! I jakoś z niedowierzaniem przyjęła, że to nie Krystek go napisał, tylko „jakaś” maszyna🙂

A oto nasz wiersz zgłoszony na konkurs:

banksterzy & GPT-2 - ma miłość do Ciebie jest wieczna
(GPT-2 na Google Colab)

Podsumowanie

Podczas trenowania modelu mieliśmy kilka podejść na początkowym etapie. Przede wszystkim żonglowaliśmy zbiorem danych wejściowych. To, co zauważyliśmy, że im więcej pierwotnego tekstu, tym lepsze daje rezultaty. Dlatego zdecydowaliśmy się dać wszystkie oczyszczone wiersze.

Dodatkowo w internecie jest wiele ciekawych przykładów jak za pomocą GPT-2 można stworzyć ciekawe modele do np. pisania artykułów na podstawie pierwszego paragrafu. Natomiast w naszym przypadku zbiór wejściowy jest mocno zróżnicowany i ciężko było model tak dostroić, by trzymał kontekst pierwszego wersu. Czasami udaje się, że cały wiersz trzyma informacje z pierwszego wersu (głównie pisząc o miłości, bo chyba ten wątek najczęściej jest poruszany). Niestety w większości przypadków model dość szybko traci kontekst i skleca kolejne wersy jak mu się uda.

Niemniej jednak przyznam, że była to bardzo ciekawa przygoda i wiele się nauczyłem! Polecam Ci (jeśli jeszcze będzie) wziąć udział w konkursie tworząc sztukę AI!

Pozdrawiam serdecznie z całego serducha!

podpis Mirek

PS. Zachęcam do wygenerowania wiersza za pomocą GPT-2 na Google Colab. Zostaw w komentarzu co Ci wyszło. A jak wymyślisz inne zastosowanie też daj znać! 🙂

Image by andreas160578 from Pixabay

.

8 Comments on “Polski poeta AI (GPT-2 na Google Colab)”

  1. Dzień dobry. Mam problem z „pobraniem do pamięci Colab wytrenowanych modeli i plików”.
    Wyrzuca mi monit: permission denied.

    1. Hej Łukasz,
      dziwna sprawa. Do tej pory nikt nie zgłaszał takiego problemu.
      Dodatkowo dzisiaj kilka osób z pracy dla zabawy używało notebooków i nikt nie miał takich problemów 🙁
      Może chwilowo coś nie działało. Spróbuj jeszcze raz!
      Pamiętaj by zalogować się na swoje konto Googlowe w Google Colab!
      Pozdrawia serdercznie,
      Mirek

    1. Hmm… nie wiedziałem, że jest jakaś taka moda :P. Po prostu lubię taki styl pisania artykułów. To wszystko 🙂
      Miłego dnia!

      1. Przez twe oczy zielone zielone oszalałem,
        Tak jest wiele, żeby się zgodzić wśród tych pokus,
        Bym mógł ustami róży zakwitnąć nad jeziorem,
        Lecz czemuż rozstaje się twa potworna chęć zmytana
        O każdy punkt z błota wbiłby się w nie, jak sen, głęboki?
        Nie ma gdzie widzenia na zniszczenie sumienia,
        Jak gdyby na łup obecne są pismo onego,
        Lecz wyschłe byłby mojej pamięci mogły wieśc..
        😉

    1. Hej Łukasz – ten wiersz co zgłaszaliśmy na konkurs daliśmy koleżance co studiuje polonistykę i wyszukała się jakichś wyszukanych rzeczy.
      Chociaż szczerze trzeba troszkę spędzić czasu, by maszynka wypluła całkiem rozsądny wiersz. Cóż – jest to pole do popisu dla osób, które chciałyby zrobić model na większej liczbie danych i mocniejszym modelu, niż ten, który my wybraliśmy 😉

Dodaj komentarz

Twój adres email nie zostanie opublikowany. Pola, których wypełnienie jest wymagane, są oznaczone symbolem *