CodeGym /Kursy /ChatGPT Apps /Cache i warstwa edge: CDN, edge‑cache, ETag, SWR, funkcje...

Cache i warstwa edge: CDN, edge‑cache, ETag, SWR, funkcje edge (Vercel) i ich limity

ChatGPT Apps
Poziom 16 , Lekcja 4
Dostępny

1. Po co w ogóle myśleć o cache i edge w ChatGPT App

W klasycznej aplikacji webowej też zależy ci na szybkości, ale użytkownik przynajmniej widzi spinner. W ChatGPT App sytuacja jest ciekawsza. Użytkownik rozmawia z modelem, a ten czasem decyduje się wywołać twój App. Widżet powinien się pojawić i dość szybko pokazać coś użytecznego.

Praktyka jest dość jednoznaczna: latency = pieniądze. Im dłużej odpowiadasz, tym większa szansa, że użytkownik odejdzie, a dodatkowe wywołania LLM/backendu to bezpośrednie koszty modeli i infrastruktury. Cache zmniejsza jedno i drugie.

Plus specyfika ChatGPT Apps:

  • Żądania od ChatGPT do twojego App idą przez sieć i różne warstwy pośrednie. Każda milisekunda na każdym kroku się sumuje.
  • Endpointy MCP/HTTP mają realne timeouty (w tym funkcje serverless i funkcje edge w Vercel). Jeśli się nie wyrobisz, ChatGPT zobaczy błąd i może nawet zacząć „halucynować” odpowiedź.
  • Wiele danych w GiftGenius nie zmienia się co sekundę: struktura katalogu prezentów, zbiory „top‑pomysłów” dla różnych segmentów, ustawienia funkcji. Głupio za każdym razem bić w bazę lub zewnętrzne API.

I tu właśnie wchodzą na scenę:

  • CDN i edge‑cache, aby szybko serwować statyczne zasoby i cache’owalny JSON.
  • HTTP‑cache z Cache-Control/ETag/SWR, aby kolejne żądania były szybsze i tańsze.
  • Funkcje edge Vercel, aby wykonywać lekką logikę jak najbliżej ChatGPT i użytkownika, ale nie przerabiać ich na „mini‑backend”.

2. Anatomia opóźnień w GiftGenius i punkty cache’owania

Najpierw warto uczciwie narysować, gdzie w ogóle rodzi się latency.

sequenceDiagram
    participant User as Użytkownik
    participant ChatGPT as ChatGPT
    participant App as ChatGPT App (Apps SDK)
    participant GW as MCP Gateway / Edge
    participant GiftAPI as Gift REST API / mikroserwis prezentów
    participant DB as Katalog/Baza

    User->>ChatGPT: "Dobierz prezent dla brata"
    ChatGPT->>App: Wywołanie narzędzia + render widżetu
    App->>GW: HTTP / MCP żądanie (kategorie, zbiory)
    GW->>GiftAPI: HTTP (REST)
    GiftAPI->>DB: Zapytanie o katalog/rekomendacje
    DB-->>GiftAPI: Odpowiedź
    GiftAPI-->>GW: Odpowiedź (JSON)
    GW-->>App: Odpowiedź (JSON)
    App-->>ChatGPT: Widżet z wynikami
    ChatGPT-->>User: Wiadomość + UI

Gdzie można tu „ściąć zakręt”?

  1. Między ChatGPT a twoim perymetrem — CDN/edge‑cache (Vercel CDN/Edge Network), który może serwować niezmienne assety widżetu i cache’owalny JSON bez wchodzenia na twój serwer origin.
  2. Między Gateway a wewnętrznymi usługami REST/HTTP (Gift REST API, Commerce REST API itd.) i bazą — cache aplikacji (Redis/w pamięci/cache bazy), aby nie wołać tych samych zapytań (np. „lista kategorii prezentów”) po dziesięć razy.

W tym wykładzie skupiamy się właśnie na warstwie HTTP/edge, bo jest najbliżej ChatGPT i Vercel.

3. Rodzaje cache’u w naszej architekturze

Skoro mamy architekturę „warstwowego tortu”, to i cache’y jest kilka.

Typ cache’u Gdzie działa Do czego się nadaje
Cache przeglądarki Wewnątrz klienta ChatGPT (przeglądarka/desktop) Statyki widżetu, ikony, fonty (ograniczona kontrola)
CDN / edge‑cache Na węzłach edge Vercel/Cloudflare Statyki + wspólny JSON (kategorie, konfiguracje, ogólne zbiory)
Cache aplikacji Wewnątrz MCP Gateway lub usług backendowych (Redis, in‑memory) Wyniki ciężkich zapytań do bazy/zewnętrznych API
Cache bazy danych/materializacja W samej bazie (widoki zmaterializowane itd.) Wstępnie wyliczone agregaty, analityka

Teraz skupimy się na pierwszych dwóch: HTTP‑cache + CDN/edge.

4. HTTP‑cache: Cache-Control, max-age i s-maxage

HTTP‑cache jest sterowany przede wszystkim nagłówkiem Cache-Control. To od niego zależy, czy przeglądarka/klient ChatGPT i/lub CDN może cache’ować twoją odpowiedź i jak długo.

Kluczowe elementy:

  • max-age — ile sekund przeglądarka może cache’ować odpowiedź.
  • s-maxage — ile sekund może cache’ować shared cache (CDN/proxy).
  • public — odpowiedź można cache’ować we wspólnym cache’u.
  • private — odpowiedź tylko dla konkretnego klienta; CDN jej nie cache’uje.

W GiftGenius, na przykład:

  • Pliki JS/CSS/fonty widżetu — wersjonowane pliki (z hashem w nazwie), można je śmiało zwracać z Cache-Control: max-age=31536000, immutable.
  • JSON z listą kategorii prezentów — taki sam dla wszystkich użytkowników, tutaj ma sens public, s-maxage=60 (albo dłużej).

Najprostszy Route Handler Next.js dla GET /api/gifts/categories, cache’owany w CDN przez 60 sekund:

// app/api/gifts/categories/route.ts
import { NextResponse } from "next/server";

export const runtime = "nodejs"; // zwykła funkcja serverless

export async function GET() {
  // tutaj moglibyśmy iść do bazy danych/zewnętrznego API
  const categories = [
    { id: "for_brother", title: "Prezenty dla brata" },
    { id: "for_mom", title: "Prezenty dla mamy" },
  ];

  return NextResponse.json(categories, {
    headers: {
      // pozwalamy CDN-owi cache’ować przez 60 sekund
      "Cache-Control": "public, s-maxage=60",
    },
  });
}

Vercel CDN będzie przechowywać odpowiedź 60 sekund, a wszystkie żądania ChatGPT po ten JSON w tym oknie w ogóle nie dojdą do twojej funkcji. To natychmiastowe i tanie.

5. ETag: odcisk treści i 304 Not Modified

ETag to warunkowy „odcisk palca” zasobu, zwykle hash treści. Schemat działania:

  1. Serwer zwraca odpowiedź z nagłówkiem ETag: "v1-abc123".
  2. Przy następnym razie klient wysyła nagłówek If-None-Match: "v1-abc123".
  3. Jeśli serwer uzna, że treść się nie zmieniła, odpowiada 304 Not Modified bez ciała.

Ważne: ETag oszczędza transfer, ale niekoniecznie zmniejsza latency, bo i tak potrzebny jest round trip do serwera. W kontekście ChatGPT Apps jest to przydatne dla ciężkich odpowiedzi JSON, ale nie należy oczekiwać cudownej szybkości wyłącznie od ETag — do tego lepsze są SWR i edge‑cache.

Przykład prostego ETag w handlerze Next.js (bez crypto‑hashy, żeby nie komplikować):

// app/api/gifts/config/route.ts
import { NextRequest, NextResponse } from "next/server";

const CONFIG = { version: 1, showExperimentalIdeas: true };
const ETAG = `"v${CONFIG.version}"`;

export async function GET(req: NextRequest) {
  const ifNoneMatch = req.headers.get("if-none-match");
  if (ifNoneMatch === ETAG) {
    // Treść się nie zmieniła — zwracamy 304
    return new NextResponse(null, { status: 304, headers: { ETag: ETAG } });
  }

  return NextResponse.json(CONFIG, {
    headers: {
      ETag: ETAG,
      "Cache-Control": "public, s-maxage=300",
    },
  });
}

W praktyce oczywiście policzysz ETag z hasha danych albo użyjesz wersji rekordu w bazie.

6. Stale‑While‑Revalidate (SWR): szybko i wystarczająco świeżo

SWR to podejście „pokaż stare od razu, a nowe dociągnij w tle”. Można je zrealizować:

  • Na poziomie nagłówka HTTP Cache-Control z parametrem stale-while-revalidate.
  • Na poziomie UI, używając bibliotek typu swr/react-query, które trzymają lokalny cache i robią odświeżenia w tle.

SWR w nagłówku HTTP

Typowy nagłówek:

Cache-Control: public, s-maxage=60, stale-while-revalidate=300

Sens:

  • W pierwszych 60 sekundach CDN zwraca świeżą wersję.
  • Od 61 do 360 sekundy CDN może zwrócić przeterminowaną odpowiedź natychmiast, a w tle uruchomić żądanie do origin po nową wersję.
  • Po 360 sekundach żądanie po nową treść staje się blokujące.

Użytkownik (i ChatGPT) dostaje odpowiedź natychmiast nawet w szczycie obciążenia, a ty w tle łagodnie odświeżasz cache. Dla GiftGenius to idealne np. dla „top‑zestawień prezentów na Nowy Rok” — nie zmieniają się co sekundę.

Przykład:

// app/api/gifts/top/route.ts
import { NextResponse } from "next/server";

export async function GET() {
  const topGifts = [
    { id: "coffee_mug", title: "Kubek z napisem" },
    { id: "smart_led", title: "Inteligentna lampa" },
  ];

  return NextResponse.json(topGifts, {
    headers: {
      "Cache-Control": "public, s-maxage=60, stale-while-revalidate=300",
    },
  });
}

SWR w widżecie UI (React)

Widżet GiftGenius żyje w piaskownicy ChatGPT i może używać dowolnego kodu React. Już umiesz wywoływać swoje API przez window.fetch. Dodajmy bibliotekę swr i zorganizujmy cache po stronie widżetu:

// widget/GiftTopList.tsx
import useSWR from "swr";

const fetcher = (url: string) => fetch(url).then((r) => r.json());

export function GiftTopList() {
  const { data, isLoading } = useSWR(
    "https://api.giftgenius.com/api/gifts/top",
    fetcher,
    { revalidateOnFocus: false } // w czacie focus zmienia się dziwnie, wyłączmy
  );

  if (isLoading && !data) return <div>Wczytujemy pomysły...</div>;

  return (
    <ul>
      {data?.map((gift: any) => (
        <li key={gift.id}>{gift.title}</li>
      ))}
    </ul>
  );
}

Jak to działa:

  • Przy pierwszym renderze idzie żądanie do naszego API.
  • Wynik trafia do cache swr wewnątrz widżetu.
  • Przy kolejnych renderach (albo nowych odpowiedziach, gdzie ChatGPT znów wstawi ten widżet z tym samym kluczem) dane są brane z cache. Użytkownik nie widzi „migania” ani spinnerów, a w tle może pójść odświeżenie.

W ten sposób łączymy dwa poziomy SWR:

  • Na CDN/HTTP — aby nie obciążać origin.
  • W UI — aby nie obciążać użytkownika.

Jeśli zebrać wszystko razem:

  • Prosty Cache-Control (max-age/s-maxage) — warstwa bazowa: dajemy CDN i klientom prawo cache’owania odpowiedzi i redukujemy obciążenie.
  • ETag + If-None-Match — dokładamy, gdy ważna jest oszczędność transferu dla ciężkich JSON, ale godzimy się na sieciowy round trip.
  • stale-while-revalidate — włączamy, gdy liczy się natychmiastowy zwrot nawet lekko przeterminowanych danych (katalogi, top‑zestawienia).
  • SWR w UI (biblioteka swr/react-query) — osobna warstwa do wygładzania przerysowań widżetu i lokalnego cache w piaskownicy ChatGPT.

7. Co cache’ować w GiftGenius i jak długo

Spróbujmy rozłożyć dane GiftGenius na „warstwy cache’owalności”.

Można cache’ować na poziomie CDN/edge

Wszystko, co jest jednakowe dla wszystkich (lub szerokich segmentów) i rzadko się zmienia:

  • Statyki widżetu: JS/CSS, fonty, ikony — „na zawsze” (rok) z immutable.
  • Struktura katalogów prezentów: kategorie, sekcje, filtry — minuty/godziny.
  • Ogólne zestawienia („najlepsze pomysły dla kolegów do 50 $”) — minuty/kilkadziesiąt minut, zwłaszcza w szczytowych sezonach.

Tutaj idealnie pasują public, s-maxage + stale-while-revalidate.

Lepiej cache’ować w aplikacji/Redis

Bardziej dynamiczne, ale jednak powtarzalne dane:

  • Wyniki ciężkich zewnętrznych API (np. kursy walut, aktualne ceny ze sklepu zewnętrznego).
  • Często żądane segmenty rekomendacji (wg płci/wieku/okazji).

Tutaj CDN nie zawsze się sprawdzi, bo dane mogą zależeć od tokena/organizacji/tenanta. Cache’ujemy na poziomie MCP Gateway lub usług wewnętrznych REST: masz nad tym pełną kontrolę i nie mieszają się dane różnych użytkowników.

Nie wolno cache’ować (w cache’ach wspólnych)

To, co jest związane z konkretnym użytkownikiem:

  • Osobiste zamówienia i ich statusy.
  • Informacje płatnicze, adresy, email.
  • Konkretnie dobrane rekomendacje na podstawie prywatnej historii zamówień (jeśli to wrażliwe).

To można cache’ować wyłącznie na poziomie aplikacji z ostrożną semantyką (i koniecznie bez wycieku między użytkownikami), ale na pewno nie w public cache CDN.

8. Warstwa edge: CDN kontra funkcje edge

Ważne, by nie mylić dwóch podobnych, ale różnych bytów:

  • CDN / edge‑cache — przechowuje wcześniej policzone odpowiedzi, logiki tam prawie nie ma.
  • Funkcje edge (Vercel Edge / Cloudflare Workers) — małe kawałki kodu wykonywane na węzłach edge.

Doświadczenie pokazuje: Edge ≠ Serverless. Wielu deweloperów próbuje wepchnąć tam ciężką logikę biznesową, wywołania LLM i obróbkę BLOB, a potem dziwi się timeoutom i limitom. Funkcje edge:

  • Startują bardzo szybko (cold start prawie zerowy).
  • Ale są mocno ograniczone CPU, czasem wykonania i dostępnością API (często bez pełnego Node.js, bez długich socketów itd.).

Kiedy funkcja edge — dobry pomysł

W kontekście GiftGenius i ChatGPT App funkcje edge są przydatne do:

  • Lekkiego routingu: po nagłówkach locale, x-openai-user-location albo tenant ID zdecydować, do którego regionalnego klastra backendowego wysłać żądanie.
  • Dodania prostych nagłówków, feature‑flagów, A/B‑routingu.
  • Szybkich endpointów read‑only, które czytają dane z edge‑KV albo z cache CDN i praktycznie nic nie liczą.

Kiedy funkcja edge — zły pomysł

  • Długie zapytania do zewnętrznych API.
  • Wywołania modeli LLM.
  • Złożona logika checkoutu.
  • Narzędzia MCP z ciężką logiką biznesową.

Do tego masz zwykłe funkcje serverless Next.js (na przykład runtime = "nodejs") albo osobne usługi/klastry.

Przykład funkcji edge w Next.js 16

Zróbmy małą trasę GET /api/geo-router, która na podstawie nagłówka x-openai-user-location (umownie) zwróci, do którego regionalnego klastra uderzać.

// app/api/geo-router/route.ts
import { NextRequest, NextResponse } from "next/server";

export const runtime = "edge"; // uruchamiamy na edge

export function GET(req: NextRequest) {
  const userLocation = req.headers.get("x-openai-user-location") ?? "US";
  const cluster =
    userLocation.startsWith("EU") ? "eu-gift-api" : "us-gift-api";

  return NextResponse.json({ cluster }, {
    headers: {
      "Cache-Control": "public, s-maxage=300",
    },
  });
}

Taki endpoint:

  • Działa bardzo szybko (edge).
  • Nie robi nic skomplikowanego.
  • Może być cache’owany w CDN.

9. Edge i cache w ogólnej architekturze GiftGenius

Zbierzmy wszystko w jeden obrazek.

flowchart TD
    ChatGPT[(ChatGPT / User)]
    CDN["CDN / Edge Cache (Vercel)"]
    EdgeFn["Edge Functions (routing, feature‑flagi)"]
    GW[MCP Gateway]
    GiftAPI["Gift REST API Cluster"]
    CommerceAPI["Commerce REST API Cluster"]
    DB[(DB/External APIs)]
    
    ChatGPT --> CDN
    CDN -->|cache hit| ChatGPT
    CDN -->|cache miss| EdgeFn
    EdgeFn --> GW
    GW --> GiftAPI
    GW --> CommerceAPI
    GiftAPI --> DB
    CommerceAPI --> DB

Typowy scenariusz:

  1. Widżet ChatGPT żąda /api/gifts/categories.
  2. CDN sprawdza cache. Jeśli jest świeża lub „stale, ale jeszcze do użycia” wersja — od razu ją zwraca, nawet nie dotykając EdgeFn/GW.
  3. Jeśli cache’u nie ma — żądanie wpada do EdgeFn (jeśli włączony) i/lub od razu do GW.
  4. GW w razie potrzeby używa wewnętrznego cache Redis do ciężkich operacji albo woła wewnętrzne usługi REST, a dalej bazę.
  5. Odpowiedź wraca, trafia do CDN/edge‑cache i jest serwowana innym użytkownikom.

Takie ułożenie:

  • Obniża latency dla widżetu i ChatGPT.
  • Zmniejsza obciążenie MCP Gateway i klastrów backendowych.
  • Redukuje koszt wywołań LLM/bazy (mniej powtórnych zapytań).

10. Niewielkie praktyczne fragmenty dla GiftGenius

Cache kategorii + Next.js revalidate

Dotąd mówiliśmy tylko o endpointach API. Ale Next.js daje podobne mechanizmy także dla samych stron — przez ISR (revalidate).

Przykład server component, który pobiera listę kategorii z revalidate = 60:

// app/(widget)/categories/page.tsx
export const revalidate = 60; // ISR: przebudowa co 60 s

async function fetchCategories() {
  const res = await fetch("https://api.giftgenius.com/api/gifts/categories");
  return res.json();
}

export default async function CategoriesPage() {
  const categories = await fetchCategories();
  return (
    <ul>
      {categories.map((c: any) => (
        <li key={c.id}>{c.title}</li>
      ))}
    </ul>
  );
}

W produkcji Vercel będzie generować i cache’ować HTML tej strony, co jest przydatne w przypadkach, gdy twój widżet/interfejs jest otwierany nie tylko przez ChatGPT, lecz także jako zwykła strona WWW (np. panel debug lub landing).

Prosta aplikacja‑cache w usłudze backend

To już nie warstwa edge, lecz cache aplikacji (Redis/in‑memory wewnątrz twojego Gift REST API lub innej usługi backend). Ale warto pokazać, jak wygląda w najprostszym wydaniu:

// pseudokod wewnątrz Gift REST API
const cache = new Map<string, any>();

async function getGiftCategories() {
  const key = "gift_categories_v1";
  const cached = cache.get(key);
  if (cached && Date.now() - cached.ts < 60_000) {
    return cached.data; // 60 sekund cache
  }
  const data = await fetchRealCategories();
  cache.set(key, { ts: Date.now(), data });
  return data;
}

W boju oczywiście zamienisz Map na Redis/Memcached, ale idea jest ta sama: rzadziej chodzimy do bazy/zewnętrznego API.

Jeśli to wszystko ścisnąć do jednego zdania: najpierw jasno zdecyduj, co można cache’ować i gdzie (CDN, edge, Redis, baza), a dopiero potem włączaj „magiczne” flagi platformy. Cache to nie checkbox w konfigu — to część architektury: wpływa i na szybkość, i na stabilność, i na koszty.

11. Typowe błędy przy pracy z cache i warstwą edge

Błąd nr 1: „Cache’ujemy wszystko jak leci, byle szybciej”.
Klasyk: deweloper ustawia Cache-Control: public, s-maxage=3600 na wszystkie odpowiedzi JSON. Po paru godzinach okazuje się, że jeden użytkownik widzi zamówienia innego, a ChatGPT operuje starymi danymi o dostępności. Dla danych personalnych lub wrażliwych potrzebny jest albo private‑cache, albo całkowite wyłączenie cache CDN i trzymanie cache na poziomie aplikacji z ostrożną izolacją.

Błąd nr 2: Pomyłka między max-age i s-maxage.
Niektórzy ustawiają tylko max-age i oczekują, że CDN będzie cache’ował dokładnie tyle samo. W rzeczywistości max-age dotyczy przede wszystkim przeglądarki, a dla cache’u współdzielonego potrzebny jest s-maxage. Efekt: przeglądarka cache’uje, a CDN — nie, i origin dalej się dusi pod obciążeniem, chociaż „przecież włączyliśmy cache”. Właściwa droga — jawnie podawać s-maxage dla CDN.

Błąd nr 3: Oczekiwanie, że ETag wszystko przyspieszy.
ETag świetnie oszczędza transfer, zwłaszcza dla dużych plików JSON, ale sieciowy round trip i tak zostaje. W świecie ChatGPT App oznacza to: model i tak czeka na odpowiedź twojego serwera, choćby to było 304 bez ciała. Jeśli liczy się opóźnienie, potrzebne są edge‑cache + SWR, a ETag to mechanizm pomocniczy.

Błąd nr 4: Próba wciśnięcia ciężkiej logiki biznesowej do funkcji edge.
„Wywołujmy zewnętrzną LLM, liczmy skomplikowane zestawienia i chodźmy do trzech zewnętrznych API prosto z Vercel Edge — przecież tam jest szybko!” A potem zaczyna się ból: limity czasu wykonania, brak pełnego Node.js, dziwne błędy. Edge jest dobry do lekkiego routingu i A/B, a cała ciężka praca powinna iść do zwykłych funkcji serverless lub osobnych klastrów backend.

Błąd nr 5: Brak strategii unieważniania cache.
Zrobiliśmy cache „na godzinę”, wszystko lata. Potem biznes mówi: „zmieniliśmy ceny/kategorie/ograniczenia, czemu w ChatGPT wszystko po staremu?” Deweloperzy zaczynają ręcznie kręcić wajchami, czyścić cache i restartować serwisy. Dla ważnych danych trzeba z góry przemyśleć: jak będziesz zrzucać cache (po webhooku z panelu, po wersji, po kluczu), a nie liczyć na „samo się za godzinę odświeży”.

Błąd nr 6: Ignorowanie związku cache ↔ koszt.
Czasem deweloperzy myślą o cache tylko w kontekście szybkości. W ekosystemie LLM to także kwestia pieniędzy: każde zbędne wywołanie modelu i zewnętrznego API kosztuje. Bez cache MCP‑serwer może zacząć tłuc zewnętrzną usługę/model tak często, że miesięczny rachunek niemiło zaskoczy. Właściwe cache’owanie obniża i latency, i rachunek.

Błąd nr 7: Mieszanie danych różnych lokalizacji/regionów w jednym cache.
GiftGenius działa w kilku krajach, ale w cache używany jest jeden klucz top_gifts. Efekt: użytkownik z USA widzi ruble i sklepy z Rosji, a użytkownik z Europy — dolary i sklepy z USA. Przy cache’owaniu zawsze uwzględniaj klucze typu locale, currency, tenant w nazwie klucza cache albo w trasie (np. /api/{locale}/gifts/top).

Błąd nr 8: Pełna zależność od „magii” Next.js/platformy.
ISR, revalidate, automatyczny CDN — to wszystko świetne. Ale jeśli nie rozumiesz, co dokładnie dzieje się pod spodem, łatwo o niespodzianki. Na przykład strona pokazuje stary content, a API zwraca nowy; ChatGPT widzi jedno, a użytkownicy w przeglądarce — drugie. Warto poświęcić czas i zrozumieć, jak działają Cache-Control, ETag i wzorzec SWR, a Next.js traktować jako wygodną otoczkę, nie czarną skrzynkę.

Błąd nr 9: Brak rozróżnienia dev/staging/production w kwestii cache.
W środowisku deweloperskim cache często przeszkadza w debugowaniu („przecież zmieniłem dane, czemu ChatGPT wciąż widzi stare zestawienia?”). Warto mieć konfigurację, która w dev prawie wyłącza cache (albo daje TTL kilka sekund), a w production — włącza agresywne cache’owanie. W przeciwnym razie albo oszalejesz przy developmencie, albo przypadkiem wypchniesz produkcję bez cache i złapiesz sztorm żądań do wewnętrznych klastrów backend za MCP Gateway.

1
Ankieta/quiz
Produkcja i skalowanie, poziom 16, lekcja 4
Niedostępny
Produkcja i skalowanie
Produkcja, sieć i skalowanie
Komentarze
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION