Kurs Next.js · Moduł 1: Konfiguracja Next.js

Inicjalizacja projektu i dostępne startery

9 min czytania
W tej lekcji10

W Metropolii Quantum inżynierowie często korzystają z predefiniowanych schematów kwantowych, aby przyspieszyć rozwój nowych systemów miejskich. Podobnie w świecie Next.js możemy wykorzystać różne szablony startowe i konfiguracje, które pozwalają nam szybciej rozpocząć pracę nad nową aplikacją. W tym module poznamy dostępne startery dla Next.js 16 i nauczymy się, jak skutecznie inicjalizować nowe projekty.

Podstawowa inicjalizacja projektu

Jak już wiemy z poprzedniej lekcji, najprostszym sposobem rozpoczęcia nowego projektu Next.js jest użycie narzędzia create-next-app:

1npx create-next-app@latest my-quantum-project

To polecenie tworzy nowy projekt Next.js z domyślną konfiguracją. Jest to jak uruchomienie podstawowego modułu mieszkalnego w Metropolii Quantum - funkcjonalny, ale możesz chcieć go dostosować do swoich specyficznych potrzeb.

Opcje konfiguracyjne create-next-app

Podczas tworzenia nowego projektu create-next-app najpierw zapyta, czy chcesz użyć zalecanych ustawień domyślnych (TypeScript, ESLint, Tailwind CSS, App Router i AGENTS.md). Jeśli wybierzesz własne ustawienia, zobaczysz kolejne pytania. Przyjrzyjmy się im bliżej:

1Would you like to use the recommended Next.js defaults? No, customize settings
2Would you like to use TypeScript? Yes
3Which linter would you like to use? ESLint
4Would you like to use React Compiler? No
5Would you like to use Tailwind CSS? Yes
6Would you like your code inside a `src/` directory? Yes
7Would you like to use App Router? (recommended) Yes
8Would you like to customize the import alias (`@/*` by default)? No
9Would you like to include AGENTS.md to guide coding agents to write up-to-date Next.js code? Yes

TypeScript

TypeScript dodaje statyczne typowanie do JavaScript, co pomaga wychwytywać błędy już podczas pisania kodu. W Metropolii Quantum byłoby to podobne do systemów wczesnego ostrzegania, które wykrywają problemy, zanim staną się krytyczne.

1// JavaScript
2function addEnergy(reactor, amount) {
3  return reactor.level + amount;
4}
5
6// TypeScript
7interface Reactor {
8  level: number;
9  maxCapacity: number;
10  status: 'active' | 'inactive' | 'maintenance';
11}
12
13function addEnergy(reactor: Reactor, amount: number): number {
14  if (reactor.status !== 'active') {
15    throw new Error('Reaktor musi być aktywny aby dodać energię');
16  }
17  return reactor.level + amount;
18}

ESLint

ESLint to narzędzie do analizy statycznej kodu, które pomaga utrzymać spójny styl i wykrywać potencjalne problemy. Jest jak automatyczny kontroler jakości w fabrykach Metropolii Quantum. W Next.js 16 kreator pozwala wybrać zamiast niego Biome, czyli szybki linter i formatter w jednym narzędziu, albo zrezygnować z lintera.

React Compiler

React Compiler automatycznie memoizuje komponenty, więc rzadziej musisz ręcznie sięgać po useMemo i useCallback. W Next.js 16 jego obsługa jest stabilna, ale domyślnie wyłączona, bo wydłuża kompilację; na początek możesz odpowiedzieć "No".

Tailwind CSS

Tailwind CSS to framework CSS oparty na klasach użytkowych. Zamiast pisać własne style CSS, używasz predefiniowanych klas bezpośrednio w HTML. Jest to jak modułowy system konstrukcyjny w Metropolii Quantum - zamiast projektować każdy budynek od podstaw, inżynierowie łączą gotowe moduły.

1// Bez Tailwind
2<button className="login-button">Zaloguj</button>
3
4// Z Tailwind
5<button className="bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded">
6  Zaloguj
7</button>

Katalog src/

Używanie katalogu src/ to dobra praktyka organizacyjna, która oddziela kod źródłowy od plików konfiguracyjnych. Jest to jak oddzielenie centrum zarządzania od infrastruktury w Metropolii Quantum.

App Router

App Router to nowoczesne podejście do routingu w Next.js, oparte na React Server Components. Jest to kluczowa funkcja Next.js 16, której zdecydowanie zalecamy używać w nowych projektach.

Alias importu @/*

Alias importu @/* pozwala na używanie skrótowej ścieżki do importowania modułów z katalogu src/ (w projekcie bez src/ z katalogu głównego). Jest to jak system szybkiego transportu w Metropolii Quantum - skrót, który oszczędza czas.

1// Bez aliasu
2import { Button } from '../../../components/ui/Button';
3
4// Z aliasem @/*
5import { Button } from '@/components/ui/Button';

AGENTS.md

Ostatnie pytanie dotyczy pliku AGENTS.md z instrukcjami dla asystentów AI, takich jak Claude czy Cursor. Plik kieruje ich do dokumentacji dołączonej do zainstalowanej wersji Next.js, dzięki czemu podpowiadany kod pasuje do Twojego projektu, a nie do starszych wersji frameworka.

Oficjalne szablony startowe

Next.js oferuje kilka oficjalnych szablonów startowych, których możesz użyć jako podstawy swojego projektu. Aby z nich skorzystać, użyj flagi --example:

1npx create-next-app@latest my-quantum-blog --example blog-starter

Oto niektóre z najpopularniejszych oficjalnych szablonów:

1. Tailwind CSS bez szablonu

Osobnego przykładu with-tailwindcss nie ma już w repozytorium Next.js: Tailwind CSS instaluje sam create-next-app (w zalecanych ustawieniach albo z flagą --tailwind).

1npx create-next-app@latest my-tailwind-app --tailwind

2. with-typescript

Szablon z TypeScript już skonfigurowanym.

1npx create-next-app@latest --example with-typescript my-ts-app

3. blog-starter

Szablon bloga z Markdown, gotowy do użycia.

1npx create-next-app@latest --example blog-starter my-blog

4. Next.js Commerce

Pełny sklep e-commerce na App Routerze, rozwijany w osobnym repozytorium vercel/commerce.

1npx create-next-app@latest --example https://github.com/vercel/commerce my-store

Next.js Templates - zaawansowane startery

Vercel, firma stojąca za Next.js, oferuje też bardziej zaawansowane szablony na stronie vercel.com/templates. Są to gotowe projekty dla konkretnych przypadków użycia. Przypomina to sposób, w jaki architekci Metropolii Quantum mogą wybrać gotowe plany dla różnych typów struktur miejskich.

Niektóre z godnych uwagi szablonów:

Chatbot (dawniej Next.js AI Chatbot)

Chatbot AI podobny do ChatGPT, zbudowany na Next.js i AI SDK; modele (np. OpenAI, Anthropic, Google, xAI) podłącza przez Vercel AI Gateway.

1npx create-next-app@latest ai-chatbot \
2  --use-pnpm \
3  --example "https://github.com/vercel/chatbot"

Next.js + Supabase

Starter Next.js z Supabase: logowanie przez Supabase Auth z sesją w cookies, Tailwind CSS i komponenty shadcn/ui.

1npx create-next-app@latest supabase-app \
2  --use-pnpm \
3  --example "https://github.com/vercel/next.js/tree/canary/examples/with-supabase"

Startery społeczności

Oprócz oficjalnych szablonów społeczność Next.js stworzyła wiele własnych starterów. Przypominają one eksperymentalne projekty architektoniczne w Metropolii Quantum - nie są częścią oficjalnej infrastruktury, ale mogą oferować innowacyjne rozwiązania.

T3 Stack

T3 Stack to popularny zestaw narzędzi do budowy aplikacji Next.js z TypeScript, tRPC, Tailwind CSS i Prisma.

1npm create t3-app@latest

Next.js Nextra

Nextra to framework do tworzenia stron statycznych i dokumentacji oparty na Next.js.

1npx create-next-app@latest my-docs-site \
2  --use-pnpm \
3  --example "https://github.com/shuding/nextra-docs-template"

Struktura projektu po inicjalizacji

Po zainicjalizowaniu projektu Next.js 16 z App Routerem zobaczysz następującą strukturę plików:

1my-quantum-project/
2├── src/                 # Kod źródłowy aplikacji
3│   └── app/             # Katalog App Router
4│       ├── favicon.ico  # Ikona strony
5│       ├── globals.css  # Globalne style CSS
6│       ├── layout.tsx   # Główny układ aplikacji
7│       └── page.tsx     # Strona główna
8├── public/              # Statyczne pliki
9│   └── next.svg         # Logo Next.js
10├── AGENTS.md            # Wskazówki dla asystentów AI
11├── CLAUDE.md            # Odsyła do AGENTS.md
12├── eslint.config.mjs    # Konfiguracja ESLint
13├── next.config.ts       # Konfiguracja Next.js
14├── package.json         # Zależności i skrypty
15├── postcss.config.mjs   # Konfiguracja PostCSS (Tailwind CSS 4)
16└── tsconfig.json        # Konfiguracja TypeScript

Przyjrzyjmy się niektórym z tych plików bliżej:

src/app/page.tsx

Jest to główna strona Twojej aplikacji, dostępna pod adresem /.

1export default function Home() {
2  return (
3    <main className="flex min-h-screen flex-col items-center justify-between p-24">
4      <h1 className="text-4xl font-bold">Witaj w Metropolii Quantum</h1>
5      <p className="text-xl">Przyszłość zaczyna się tutaj.</p>
6    </main>
7  );
8}

src/app/layout.tsx

Ten plik definiuje układ, który będzie współdzielony przez wszystkie strony w Twojej aplikacji.

1import './globals.css';
2import type { Metadata } from 'next';
3
4export const metadata: Metadata = {
5  title: 'Metropolia Quantum',
6  description: 'Portal zarządzania systemami miasta przyszłości',
7};
8
9export default function RootLayout({
10  children,
11}: {
12  children: React.ReactNode;
13}) {
14  return (
15    <html lang="pl">
16      <body>{children}</body>
17    </html>
18  );
19}

next.config.ts

Ten plik zawiera konfigurację Next.js; create-next-app tworzy go od razu w TypeScript. Możesz go rozszerzyć o własne ustawienia, np. o listę serwerów, z których wolno ładować obrazy:

1import type { NextConfig } from 'next';
2
3const nextConfig: NextConfig = {
4  // Twoje konfiguracje
5  images: {
6    remotePatterns: [
7      { protocol: 'https', hostname: 'quantum-metropolis.example.com' },
8    ],
9  },
10};
11
12export default nextConfig;

Opcja remotePatterns zastąpiła dawne images.domains, które w Next.js 16 jest przestarzałe. Wzorce pozwalają dokładnie określić protokół i adres serwera, dlatego są bezpieczniejsze.

Modyfikacja istniejącego projektu

Po inicjalizacji projektu zazwyczaj będziesz chciał dostosować go do swoich potrzeb. Oto kilka typowych zmian:

1. Aktualizacja metadanych

Zaktualizuj plik src/app/layout.tsx, aby zmienić tytuł i opis aplikacji:

1export const metadata: Metadata = {
2  title: 'System Zarządzania Metropolią Quantum',
3  description: 'Zaawansowany interfejs do monitorowania i kontroli systemów miejskich',
4};

2. Dodawanie zależności

Zainstaluj dodatkowe biblioteki, których potrzebujesz:

1npm install axios @tanstack/react-query zustand

3. Konfiguracja struktury folderów

Utwórz foldery dla typowych elementów aplikacji:

1mkdir -p src/components/ui
2mkdir -p src/lib
3mkdir -p src/hooks
4mkdir -p src/utils

4. Dostosowanie stylów

Jeśli używasz Tailwind CSS 4, który instaluje create-next-app, motyw dostosowujesz bezpośrednio w pliku globals.css za pomocą dyrektywy @theme:

1/* src/app/globals.css */
2@import "tailwindcss";
3
4@theme {
5  --color-quantum-primary: #3B82F6;
6  --color-quantum-secondary: #10B981;
7  --color-quantum-accent: #8B5CF6;
8  --color-quantum-dark: #1F2937;
9  --font-sans: "Inter", sans-serif;
10  --font-mono: "Fira Code", monospace;
11}

Każda zmienna z przedrostkiem --color- tworzy nowe klasy, np. bg-quantum-primary czy text-quantum-accent, a --font-sans zmienia krój używany przez klasę font-sans. W starszym Tailwind CSS 3 te same ustawienia trafiały do pliku tailwind.config.ts, który wciąż spotkasz w wielu istniejących projektach:

1import type { Config } from 'tailwindcss';
2
3const config: Config = {
4  content: [
5    './src/pages/**/*.{js,ts,jsx,tsx,mdx}',
6    './src/components/**/*.{js,ts,jsx,tsx,mdx}',
7    './src/app/**/*.{js,ts,jsx,tsx,mdx}',
8  ],
9  theme: {
10    extend: {
11      colors: {
12        quantum: {
13          primary: '#3B82F6',
14          secondary: '#10B981',
15          accent: '#8B5CF6',
16          dark: '#1F2937',
17        },
18      },
19      fontFamily: {
20        sans: ['Inter', 'sans-serif'],
21        mono: ['Fira Code', 'monospace'],
22      },
23    },
24  },
25  plugins: [],
26};
27export default config;

W nowym projekcie Next.js 16 z Tailwind CSS 4 taki plik nie jest potrzebny, więc nie twórz go bez powodu.

Konfiguracja git i .gitignore

Gdy inicjalizujesz projekt przy użyciu create-next-app, git zostanie automatycznie zainicjalizowany, a plik .gitignore zostanie utworzony. Jest to jak system kontroli i archiwizacji planów w Metropolii Quantum - pozwala śledzić zmiany i współpracować z innymi inżynierami.

create-next-app tworzy też pierwszy commit („Initial commit from Create Next App”). Swoje zmiany zapiszesz kolejnym:

1git add .
2git commit -m "Inicjalizacja projektu Next.js 16"

Dostosowanie skryptów npm

Możesz dostosować skrypty w pliku package.json, aby uprościć często wykonywane zadania:

1"scripts": {
2  "dev": "next dev",
3  "build": "next build",
4  "start": "next start",
5  "lint": "eslint",
6  "format": "prettier --write \"**/*.{js,ts,tsx,md}\"",
7  "update-deps": "npm update"
8}

Zwróć uwagę na skrypt lint: w Next.js 16 uruchamia on bezpośrednio eslint, bo dawne polecenie next lint zostało usunięte. Skrypty dev i build nie potrzebują żadnych flag, ponieważ Turbopack jest teraz domyślnym bundlerem.

Podsumowanie

Inicjalizacja projektu Next.js 16 i wybór odpowiedniego startera to fundament sukcesu Twojej aplikacji, podobnie jak solidne fundamenty są kluczowe dla każdego budynku w Metropolii Quantum. W tym module poznaliśmy różne opcje inicjalizacji projektu, od podstawowego create-next-app po zaawansowane szablony społeczności.

Wybór właściwego startera zależy od Twoich konkretnych potrzeb. Dla prostszych projektów domyślny szablon create-next-app może być wystarczający. Dla bardziej złożonych aplikacji rozważ użycie jednego z oficjalnych szablonów lub rozwiązań społeczności.

Pamiętaj, że dobrze zorganizowany początek projektu oszczędzi Ci wiele czasu i problemów w przyszłości, podobnie jak dokładne planowanie infrastruktury miejskiej w Metropolii Quantum zapobiega problemom z jej rozbudową.

W następnej lekcji zagłębimy się w strukturę katalogów i plików w Next.js, porównując nowy App Router z tradycyjnym Pages Routerem.

Kod do tej lekcji: App.tsx
1// JSX i Komponenty - Metropolis Quantum
2import React from 'react';
3
4console.log("JSX i Komponenty w React");
5console.log("Tworzymy interfejs Quantum City\n");
6
7// ==========================================
8// 1. Czym jest JSX?
9// ==========================================
10console.log("=== 1. JSX (JavaScript XML) ===");
11
12// JSX to rozszerzenie składni JavaScript
13// Pozwala pisać HTML-podobny kod w JavaScript
14const quantumTitle = <h1>Metropolis Quantum</h1>;
15
16console.log("Element JSX:", quantumTitle);
17
18// JSX z wyrażeniami JavaScript
19const cityName = "Quantum City";
20const population = 2470000;
21
22const cityInfo = (
23  <div>
24    <h2>Witaj w {cityName}!</h2>
25    <p>Populacja: {population.toLocaleString()} mieszkańców</p>
26    <p>Status: {population > 2000000 ? "Megalopolis" : "Miasto"}</p>
27  </div>
28);
29
30// ==========================================
31// 2. Komponenty Funkcyjne
32// ==========================================
33console.log("\n=== 2. Komponenty Funkcyjne ===");
34
35// Prosty komponent
36function WelcomeMessage() {
37  return (
38    <div style={{
39      background: 'linear-gradient(45deg, #7c4dff, #64ffda)',
40      padding: '20px',
41      borderRadius: '10px',
42      color: 'white',
43      textAlign: 'center'
44    }}>
45      <h2>Witaj w Przyszłości!</h2>
46      <p>Metropolis Quantum - Miasto Technologii</p>
47    </div>
48  );
49}
50
51// Komponent z props
52interface BuildingCardProps {
53  name: string;
54  height: number;
55  type: 'residential' | 'commercial' | 'industrial';
56  lights: boolean;
57}
58
59const BuildingCard: React.FC<BuildingCardProps> = ({ name, height, type, lights }) => {
60  const getTypeIcon = () => {
61    switch(type) {
62      case 'residential': return '●';
63      case 'commercial': return '■';
64      case 'industrial': return '▲';
65      default: return '□';
66    }
67  };
68
69  const getTypeColor = () => {
70    switch(type) {
71      case 'residential': return '#4caf50';
72      case 'commercial': return '#2196f3';
73      case 'industrial': return '#ff9800';
74      default: return '#9e9e9e';
75    }
76  };
77
78  return (
79    <div style={{
80      background: 'rgba(255, 255, 255, 0.1)',
81      padding: '15px',
82      borderRadius: '8px',
83      border: `2px solid ${getTypeColor()}`,
84      marginBottom: '10px'
85    }}>
86      <h3 style={{ color: getTypeColor() }}>
87        {getTypeIcon()} {name}
88      </h3>
89      <p>Wysokość: {height}m</p>
90      <p>Typ: {type}</p>
91      <p>Status świateł: {lights ? 'Włączone' : 'Wyłączone'}</p>
92    </div>
93  );
94};
95
96// ==========================================
97// 3. Kompozycja Komponentów
98// ==========================================
99console.log("\n=== 3. Kompozycja Komponentów ===");
100
101function CityDashboard() {
102  const buildings = [
103    { id: 1, name: 'Quantum Tower', height: 850, type: 'commercial' as const, lights: true },
104    { id: 2, name: 'Neural Apartments', height: 450, type: 'residential' as const, lights: true },
105    { id: 3, name: 'Cyber Factory', height: 320, type: 'industrial' as const, lights: false }
106  ];
107
108  return (
109    <div style={{
110      padding: '20px',
111      background: 'linear-gradient(135deg, #0f0f23 0%, #1a1a2e 100%)',
112      minHeight: '100vh',
113      color: 'white'
114    }}>
115      <WelcomeMessage />
116
117      <div style={{ marginTop: '30px' }}>
118        <h2 style={{ color: '#64ffda' }}>Budynki Metropolii</h2>
119        {buildings.map(building => (
120          <BuildingCard
121            key={building.id}
122            name={building.name}
123            height={building.height}
124            type={building.type}
125            lights={building.lights}
126          />
127        ))}
128      </div>
129
130      <div style={{
131        marginTop: '30px',
132        background: 'rgba(124, 77, 255, 0.2)',
133        padding: '15px',
134        borderRadius: '8px',
135        borderLeft: '4px solid #7c4dff'
136      }}>
137        <h3>Wskazówki do JSX:</h3>
138        <ul style={{ lineHeight: '1.8' }}>
139          <li>JSX to nie string, nie HTML - to JavaScript!</li>
140          <li>Używaj {} dla wyrażeń JavaScript</li>
141          <li>className zamiast class (słowo kluczowe JS)</li>
142          <li>camelCase dla atrybutów (onClick, onChange)</li>
143          <li>Każdy element musi być zamknięty</li>
144        </ul>
145      </div>
146    </div>
147  );
148}
149
150// Render aplikacji
151function App() {
152  console.log("Renderowanie CityDashboard...");
153  return <CityDashboard />;
154}
155
156export default App;

Widzisz błąd w tej lekcji?

Sprawdź się

Odpowiedz na pytania z tej lekcji. Wybierz odpowiedź, a od razu zobaczysz, czy jest poprawna.

  1. 1. Server-Side Rendering (SSR) w Next.js oznacza:

  2. 2. Static Site Generation (SSG) w Next.js to:

Zadania praktyczne w grze

  • Układanie w pionie

    Ułóż kroki uruchomienia nowego projektu Next.js

  • Klikanie w kolejności

    Ułóż składnię importu biblioteki React

Przydatne artykuły