Cześć! 👋
Słowo „MCP” słyszałeś już nieraz - w Cursorze, w Claude, na LinkedInie. Definicję pewnie znasz: standard, który łączy AI z narzędziami i danymi. Często pada porównanie, że to takie API dla AI. Ale jak to właściwie działa?
No to spróbujmy rozłożyć MCP na czynniki pierwsze:
CZĘŚĆ 1: Jak MCP działa pod spodem i czym naprawdę różni się od zwykłego API. Na konkretnym przykładzie 👈
CZĘŚĆ 2: Zastosowanie MCP w pracy produktowej - miejsca, w których to dla PM-a ma znaczenie.
Pierwsza część dzisiaj, kolejna za tydzień.
📆 W sierpniu startuję zapisy na XII edycję Product Management Academy. Klasycznie poprowadzę tam 3 warsztaty, a kolejne 2 dorzuci Senior PM w Atlassianie - Olga ;) 👉 Zapisz się na listę, by nie przegapić.
W dzisiejszym wydaniu:
Czym właściwie jest (serwer) MCP?
Jak serwer MCP wygląda w środka?
Co się dzieje krok po kroku?
Dlaczego nie skorzystać po prostu z API?
W drugiej części…
1. Czym właściwie jest (serwer) MCP?
Zacznijmy od początku:
MCP to protokół, czyli umowa o tym, jak dwie strony mają ze sobą rozmawiać.
MCP to nie jest system/program. Nikt nie „instaluje MCP” - dokładnie tak samo, jak nikt nie instaluje HTTP. Instalujesz przeglądarkę i stawiasz stronę, a HTTP jest tylko protokołem - ustaleniem, w jakim formacie mają ze sobą gadać.
Z MCP jest identycznie - to protokół do komunikacji. Rzeczy, które realnie widzisz, gdy “używasz MCP” mają swoje osobne nazwy
Host to aplikacja, w której siedzisz i która korzystać z serwera MCP (np. Cursor, ChatGPT, Twój produkt / agent). To ona rozmawia z modelem i faktycznie wykonuje wywołania. Tu też znajduje się zwykle model LLM (albo przynajmniej połączenie z jego chmurowym API)
Serwer MCP to tłumacz postawiony przy konkretnym systemie - np. Jirze, PostHogu, czy Waszej bazie danych SQL. Mówi „oto co potrafię”, a potem zamienia prośby modelu na realne operacje w tym systemie..
Klasyczne API / Dane systemu - realny dostęp do danych, czy akcji systemu.
W praktyce warstwowo wygląda to tak:
1.1. Zobaczmy to na konkretnym przykładzie
Jesteś PMem, wyobraź sobie sytuację, że chcesz sprawdzić, dlaczego użytkownicy narzekają na płatności w Twoim produkcie.
Dziś robisz to mniej więcej tak:
Wchodzisz do Intercoma, filtrujesz zgłoszenia z ostatniego miesiąca i eksportujesz najciekawsze do analizy
Potem Jira - sprawdzasz, czy ktoś już tego nie zgłaszał problemów, przeklejasz treści zadań.
Na końcu wrzucasz to wszystko do Claude’a i prosisz o syntezę.
A teraz wyobraź sobie, że Wasz zespół stawia jeden skrypt - nazwijmy go „Product Insights” - który ma dostęp do Intercoma i do Jiry, i który potrafi się przedstawić Twojej aplikacji AI: „umiem przeszukać zgłoszenia klientów i umiem przeszukać backlog”.
To jest właśnie serwer MCP:
1.2. Serwer? Brzmi jak coś dużego
Kiedy PM słyszy „musimy wystawić serwer MCP”, w głowie zapala się czerwona lampka: infrastruktura, deployment, rozmowa z zespołem platformowym. Potrzebujemy na to kwartał ;).
Tymczasem serwer MCP to najczęściej jeden niewielki plik ze skryptem. Kilkadziesiąt linijek w Pythonie (albo TypeScripcie), uruchamiane lokalnie na Twoim laptopie, albo jako mała usługa w chmurze.
Co taki skrypt zawiera? Definicje tego, co serwer udostępnia modelowi. Protokół przewiduje trzy rodzaje rzeczy:
Narzędzia (“tools”) - akcje, o których wywołaniu decyduje model. W „Product Insights” są dwie:
szukaj_zgloszen_intercomiszukaj_zadan_jira. To model w trakcie rozmowy uznaje, że czas po którąś sięgnąć.Zasoby (resources) - dane, o których dołączeniu decyduje aplikacja, nie model. Plik, obrazek, log. Tutaj byłby to na przykład słownik tagów używanych w Intercomie.
Prompty (prompts) - gotowe szablony - polecenia, które świadomie odpalasz. Tutaj mogłoby to być
/analiza-skarg: jedno polecenie robiące za każdym razem ten sam przegląd - zbierz zgłoszenia z ostatniego miesiąca, zestaw je z backlogiem, pokaż to, czego w Jirze jeszcze nie ma.
W praktyce 90% tego, o czym się mówi, to narzędzia.
2. Jak serwer MCP wygląda od środka?
Cały kod „Product Insights” to mniej więcej tyle:
mcp = FastMCP("Product Insights")
@mcp.tool()
def szukaj_zgloszen_intercom(fraza: str) -> str:
"""Przeszukuje zgłoszenia klientów w Intercomie po słowie kluczowym."""
# tu leci zwykłe wywołanie API Intercoma
...
@mcp.tool()
def szukaj_zadan_jira(fraza: str) -> str:
"""Szuka otwartych zadań w Jirze po słowie kluczowym."""
# tu leci zwykłe wywołanie API Jiry
response = requests.get(
f"https://twoja-firma.atlassian.net/rest/api/3/issue/{issue_key}",
headers={"Authorization": "Bearer TWÓJ_TOKEN"}
)
data = response.json()
return f"Tytuł: {data['fields']['summary']}, Status: {data['fields']['status']['name']}"
# Uruchomienie serwera
if __name__ == "__main__":
mcp.run()
```Spójrz na zdania w cudzysłowach ("""). Wyglądają jak komentarze porgramistów, ale to jest dokładnie ten tekst, który trafia do modelu i na którego podstawie model decyduje, czy w ogóle sięgnąć po to narzędzie.
I tu pomału zaczyna się praca produktowca - precyzyjne nazwanie, co dane narzędzie robi, kiedy się go używa, a kiedy nie. To bardziej nasza robota, niż inżnierska. Jeśli w Waszej firmie powstaje serwer MCP, a opisy narzędzi pisze ktoś, kto nigdy nie rozmawiał z użytkownikiem, to wróci do Was w postaci agenta AI, który sięga nie tam, gdzie trzeba.
2.1. Jak podłączać serwer MCP to swojej aplikacji AI?
Podłączenie serwera MCP do Twojej aplikacji AI to zwykle kilka linijek w pliku konfiguracyjnym w formacie JSON. Dzięki temu Twoja aplikacja AI (host) wie o istnieniu tego serwera, gdzie leży skrypt i jakie klucze API ma użyć.
{
"mcpServers": {
"product-insights": {
"command": "python",
"args": ["/Users/jan/scripts/product_mcp_server.py"],
"env": {
"JIRA_API_KEY": "tajny_token_jira",
"INTERCOM_API_KEY": "tajny_token_intercom"
}
}
}
}
commandiargs: mówią aplikacji AI, jak uruchomić Twój skrypt.env: przechowuje bezpiecznie klucze dostępowe (API keys), dzięki czemu nie trzeba ich wpisywać w chacie ani zaszywać na stałe w kodzie.
Od tego momentu model sam decyduje, kiedy po które narzędzie sięgnąć.
3. Co się dzieje krok po kroku?
Wróćmy do pytania o błędach w płatności i zobaczmy jak by to działało krok po kroku.
Piszesz do swojego agenta (np. w Cursorze / Claude Code):
„Zbierz zgłoszenia z Intercoma o błędach przy płatnościach z ostatnich 30 dni i sprawdź, czy mamy już na to otwarte zadania w Jirze.”
Na początku, przy podłączeniu serwera MCP:
Host (Cursor / Claude Code) pyta serwer „co potrafisz?” - to się nazywa capability discovery.
Serwer odsyła listę narzędzi wraz z opisami. Od tej pory host wie, czym dysponuje. Nie musi już o to pytać.
A potem przy każdym pytaniu, od nowa:
Zadajesz pytanie. Host pakuje je razem z opisami wszystkich dostępnych narzędzi i wysyła do modelu. Tak, przy każdym pytaniu od nowa - model nie pamięta niczego między zapytaniami, więc za każdym razem musi dostać listę tego, czym dysponuje.
Model wybiera narzędzie na podstawie opisu. Widzi, że
szukaj_zgloszen_intercompasuje do pierwszej połowy pytania, i odsyła hostowi: „użyj tego, z takim argumentem”.Host prosi Cię o zgodę, jeśli tak to skonfigurowano - krótkie okno „czy mogę wykonać tę akcję?”.
Host wywołuje narzędzie na serwerze, a serwer tłumaczy to na zwykłe zapytanie do API Intercoma i je wykonuje. To tutaj żyje cała logika i faktyczny kod.
Wynik wraca do hosta, a host dokłada go jako dane do rozmowy z modelem. I tu pętla kręci się od nowa: model widzi wynik z Intercoma i stwierdza, że potrzebuje jeszcze Jiry, więc kroki 4-7 powtarzają się dla drugiego narzędzia.
Model składa odpowiedź z obu źródeł: tyle zgłoszeń o płatnościach, z czego na tyle jest już zadanie w Jirze, a te nie mają pokrycia w backlogu.
Zwróć uwagę, że sam model nigdy nie rozmawia z serwerem MCP. Model po prostu dostaje tekst i zwraca tekst. Nie ma dostępu do sieci, nie potrafi niczego uruchomić. Jedyne, co może zrobić, to napisać: „chcę użyć szukaj_zgloszen_intercom z frazą »płatności«”.
Całą resztę robi host. To on czyta tę prośbę, on ją wykonuje i on wkleja wynik z powrotem do rozmowy. Model widzi w całym tym procesie dokładnie dwie rzeczy: opisy narzędzi, którymi dysponuje, i wyniki tego, co host wywołał w jego imieniu. Samego MCP nigdy nie dotyka.
Jeśli czytałeś poprzednie wydanie o harnessie: patrzysz właśnie na niego, tylko od innej strony. Harness siedzi w hoście i osługuje ten proces:
Korzystasz z Cursor, Claude Desktop, Claude Code - to on zapewnia to, żeby te dane odpowiednio przekazać
Budujesz własnego agenta od zera → Ty budujesz tę część.
Z takich ważnych, a mniej oczywistych momentów:
w kroku 2 model wybiera narzędzie na podstawie jego opisu - to znaczy, że jakość tych opisów decyduje o tym, czy agent w ogóle trafi we właściwe narzędzie.
w krok 4 - tam masz realną kontrola nad tym, co agent robi bez pytania. Większości hostów można to ustawić raz na „zawsze pozwalaj”, co bywa wygodne i jednocześnie jest najczęstszym sposobem, w jaki ludzie przypadkiem tę kontrolę tracą.
4. Dlaczego nie skorzystać po prostu z API?
Skoro serwer MCP w środku i tak woła zwykłe API Intercoma i Jiry - to po co mi w ogóle ten osobny standard? To pytanie pewnie samo Ci się nasunęło po przeczytaniu poprzedniej sekcji…
Zacznę od odpowiedzi, której się raczej nie spodziewasz: bardzo często rzeczywiście nie warto ;)
Jeśli macie jedno API i jednego agenta, możesz opisać modelowi funkcje API wprost, bez żadnego MCP.
Samo to, że model wybiera narzędzie w locie, nie jest wynalazkiem MCP - piszę to wprost, bo w wielu tekstach jedno bywa podawane za drugie.
Problem zaczyna się gdy mamy więcej aplikacji AI (hostów) chcących korzystać z większej liczby dostępnych API.
4.1. I tu pojawia nam się problem N × M.
Masz trzy aplikacje AI (np. Cursor, Claude Desktop, własny agent) i cztery usługi, z którymi mają się łączyć (baza danych, GitHub, Jira, Google Drive). Bez wspólnego standardu to 3 × 4 = 12 osobnych integracji, każda pisana i utrzymywana z osobna.
Z MCP twórca bazy danych pisze jeden serwer, twórca GitHuba pisze jeden serwer - i każda z trzech aplikacji od razu wie, jak z nich korzystać, bez dopisania choćby linijki kodu. Z 12 integracji robi się 3 + 4 = 7 połączeń.
I to jest właściwa odpowiedź na pytanie z nagłówka. MCP nie daje Ci niczego, czego nie dałoby się napisać samemu. Daje to, że nie musisz pisać tego samego po raz piąty - i że ktoś inny nie musi pisać tego pod Was.
Najkrócej: MCP nie zastępuje API. Stoi na nim.
Zobaczmy to na konkretnym przykładzie. Budujesz agenta do obsługi zgłoszeń, podłączonego do Gmaila, Notion i Jiry.
Z samym API - piszesz osobny kod integracyjny dla każdego z tych trzech narzędzi. Obsługujesz autoryzację, paginację wyników, błędy, limity zapytań - osobno dla każdego. Do tego uczysz model przez rozbudowany prompt: „żeby założyć ticket w Jirze, wywołaj ten endpoint z tymi polami; żeby odpowiedzieć na maila, wywołaj Gmail z tym payloadem”. Cała logika „co wywołać i kiedy” siedzi w Twoim kodzie.
Z MCP - Gmail, Notion i Jira wystawiają interfejs zgodny z MCP (własny albo społecznościowy). Model sam odkrywa te narzędzia i rozumie ich funkcje jako część swojego środowiska pracy. Nie programujesz drzewka decyzyjnego - dajesz kontekst i opisy, a model sam rozgrywa, co i kiedy wywołać.
4.2. MCP daje wartość dodaną (bo jest pisany pod LLMy)
Jest i drugi, mniej oczywisty powód: warstwa narzędzi w MCP to nie musi być 1:1 z endpointami API.
I często to nie jest. A wynika to z tego, że serwer MCP jest pisany “pod użycie przez LLM”, a API raczej “pod programistów”. Jak to w produkcie - inny odbiorca, inne potrzeby:
Typowe API jest atomowe. Najpierw
GET /projects, potemGET /projects/{id}/tasks, potem jeszcze filtr, paginacja, obsługa błędów.Programista ogarnia i programuje tę sekwencję, bo ma dokumentację, czas i che żeby kod był deterministyczny. Decyzja zapada raz, zanim ktokolwiek uruchomi aplikację.
Model - niekoniecznie. Każde kolejne wywołanie to osobna decyzja, osobne tokeny i osobna okazja, żeby wybrać źle.
W serwerze MCP możesz zbudować narzędzie, które łączy kilka takich wywołań w jedną akcję: „daj mi otwarte zadania z projektu X, pogrupowane po statusie”.
W środku lecą trzy requesty do API - pobranie danych, grupowanie i obsługa błędów.
Na zewnątrz model widzi jedno narzędzie z sensownym opisem.
Mniej narzędzi w kontekście, mniej decyzji, mniej pomyłek - i często niższy rachunek.
Dawanie modelowi czystego API to trochę jak dawanie komuś dokumentacji zamiast aplikacji. Przy małym API da radę. Przy skomplikowanym API najwięcej czasu zjada samo zastanawianie się, co wybrać.
✅ Co z tym możesz zrobić w najbliższym tygodniu?
Jeśli z tego wydania masz wynieść jedną rzecz:
👉 Sprawdź, czy Twój asystent AI ma integrację z narzędziem, którego już używasz - narzędziem analitycznym, systemem zgłoszeń, bazą wiedzy. Większość popularnych narzędzi ma już gotowy serwer MCP albo natywny konektor. To zwykle kilka kliknięć w sekcji connectors, nie projekt na sprint.
5. W drugiej części…
W kolejnej części zobaczymy gdzie produktowo warto używać MCP, dwa konkretne zastosowania oraz wyzwania związane z MCP.






Fajnie - jak zwykle podnosisz poprzeczkę :) swego czasu zatrudniłem AI do wytłumaczenia mi konceptu, niby nie było źle ale Ty lepiej sobie z tym radzisz niż AI ;)
Warto tutaj podkreślić trochę to co było na końcu. Tak jak dobrze zrobione API sprawia, że korzystanie z narzędzia jest łatwe i przyjemne, tak dobrze zaprojektowane MCP, a nie zwykłe proxowanie tego co jest po API, będzie miało znaczenie jak skutecznie modele będą z tego MCP korzystać.