Skip to content

Commit 581296e

Browse files
Merge pull request #17 from Boxuan-Matty-Lin/feat/mvp-dockerfile-setting
Finish updating README for the project, finish setting docker for the project
2 parents 851795a + 1822112 commit 581296e

File tree

6 files changed

+201
-23
lines changed

6 files changed

+201
-23
lines changed

.dockerignore

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
# Git / VCS
2+
.git
3+
.gitignore
4+
5+
# Node dependencies & caches
6+
node_modules
7+
.pnpm-store
8+
.npm
9+
.cache
10+
.next/cache
11+
12+
# Build outputs & coverage
13+
.next
14+
dist
15+
coverage
16+
17+
# Logs & editor settings
18+
*.log
19+
logs
20+
*.swp
21+
*.swo
22+
.vscode
23+
.idea
24+
25+
# Env files (改为在运行容器时注入)
26+
.env
27+
.env.*

Dockerfile

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
# ===== 0) Dev stage =====
2+
FROM node:22-alpine AS dev
3+
WORKDIR /app
4+
# Install base tools and pin pnpm via Corepack
5+
RUN apk add --no-cache libc6-compat ca-certificates \
6+
&& corepack enable && corepack prepare pnpm@9.12.0 --activate
7+
# Pre-install dependencies to speed up first run (source code will be bind-mounted in compose)
8+
COPY package.json pnpm-lock.yaml ./
9+
RUN pnpm install --frozen-lockfile
10+
# Expose dev server port and run Next.js in dev mode (HMR enabled)
11+
EXPOSE 3000
12+
CMD ["pnpm", "dev"]
13+
14+
15+
# ===== 1) Build stage =====
16+
FROM node:22-alpine AS builder
17+
WORKDIR /app
18+
19+
# Install musl compatibility libs for common native deps (e.g., sharp)
20+
RUN apk add --no-cache libc6-compat
21+
22+
# Pin pnpm via corepack to avoid version drift
23+
RUN corepack enable && corepack prepare pnpm@9.12.0 --activate
24+
25+
# Install dependencies
26+
COPY package.json pnpm-lock.yaml ./
27+
RUN pnpm install --frozen-lockfile
28+
29+
# Copy source code and build
30+
COPY . .
31+
# Important: ensure next.config.js has { output: 'standalone' }
32+
ENV NODE_ENV=production
33+
RUN pnpm build
34+
35+
# ===== 2) Runtime stage =====
36+
FROM node:22-alpine AS runner
37+
WORKDIR /app
38+
RUN apk add --no-cache libc6-compat
39+
40+
ENV NODE_ENV=production
41+
ENV NEXT_TELEMETRY_DISABLED=1
42+
ENV HOSTNAME=0.0.0.0
43+
ENV PORT=3000
44+
45+
# Run as non-root user
46+
RUN addgroup -g 1001 nodejs && adduser -S nextjs -u 1001
47+
USER nextjs
48+
49+
# Copy only the runtime artifacts
50+
COPY --from=builder --chown=nextjs:nodejs /app/.next/standalone ./
51+
COPY --from=builder --chown=nextjs:nodejs /app/.next/static ./.next/static
52+
COPY --from=builder --chown=nextjs:nodejs /app/public ./public
53+
54+
EXPOSE 3000
55+
CMD ["node", "server.js"]

README.md

Lines changed: 85 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,36 +1,98 @@
1-
This is a [Next.js](https://nextjs.org) project bootstrapped with [`create-next-app`](https://nextjs.org/docs/app/api-reference/cli/create-next-app).
1+
# Currency Converter
22

3-
## Getting Started
3+
## Project Overview
4+
This is a currency conversion web application that allows users to input an amount in Australian dollars (AUD) and instantly convert it into five target currencies: USD, EUR, JPY, GBP, and CNY. The interface also provides a 14-day time series chart that visualizes historical exchange rates for the selected currency pair.
45

5-
First, run the development server:
6+
**Tech Stack:** ui:next.js 16 + react 19 + tailwindcss 4 + lucide / data:open exchange rates API / charts:recharts / testing:vitest + testing-library + happy-dom / tooling:pnpm + TypeScript + eslint
67

7-
```bash
8-
npm run dev
9-
# or
10-
yarn dev
11-
# or
12-
pnpm dev
13-
# or
14-
bun dev
15-
```
168

17-
Open [http://localhost:3000](http://localhost:3000) with your browser to see the result.
9+
## Quick Start (Local Development)
10+
11+
1. **Clone the repository**
12+
```bash
13+
git clone <repository-url>
14+
cd currency_converter
15+
```
16+
17+
2. **Install dependencies**
18+
```bash
19+
pnpm install
20+
```
21+
22+
3. **Configure environment variables**
23+
Create a file named `.env.development` in the project root and specify required credentials. Example:
24+
```dotenv
25+
OXR_BASE_URL=https://openexchangerates.org/api
26+
OXR_APP_ID=your-openexchangerates-app-id
27+
```
1828

19-
You can start editing the page by modifying `app/page.tsx`. The page auto-updates as you edit the file.
29+
4. **Run the development server**
30+
```bash
31+
pnpm dev
32+
```
2033

21-
This project uses [`next/font`](https://nextjs.org/docs/app/building-your-application/optimizing/fonts) to automatically optimize and load [Geist](https://vercel.com/font), a new font family for Vercel.
34+
5. **Access the app**
35+
Navigate to [http://localhost:3000](http://localhost:3000). Hot module replacement is enabled, so the UI updates automatically when you edit files.
2236

23-
## Learn More
37+
## Running via Docker (Development)
2438

25-
To learn more about Next.js, take a look at the following resources:
39+
1. Ensure Docker is running on your machine.
40+
2. Copy `.env.development` (with the required `OXR_BASE_URL` and `OXR_APP_ID`) into the project root.
41+
3. Build and start the dev container using the provided compose file:
42+
```bash
43+
docker compose -f compose.dev.yml up --build
44+
```
45+
4. Your app will be available at [http://localhost:3000](http://localhost:3000), and code changes on the host filesystem will be hot-reloaded inside the container.
46+
5. To stop the container, press `Ctrl+C` or run `docker compose -f compose.dev.yml down`.
2647

27-
- [Next.js Documentation](https://nextjs.org/docs) - learn about Next.js features and API.
28-
- [Learn Next.js](https://nextjs.org/learn) - an interactive Next.js tutorial.
48+
## Deploying with Docker Compose (Production)
49+
50+
1. Prepare a production env file (e.g. `.env.production`) with the required secrets:
51+
```dotenv
52+
OXR_BASE_URL=https://openexchangerates.org/api
53+
OXR_APP_ID=your-openexchangerates-app-id
54+
```
55+
2. Build and start the runtime container using the production compose file:
56+
```bash
57+
docker compose -f compose.production.yml up --build -d
58+
```
59+
This will build the multi-stage Dockerfile and run the `runner` stage, exposing port 3000.
60+
3. Verify the app at [http://localhost:3000](http://localhost:3000) or on your chosen host.
61+
4. To inspect logs:
62+
```bash
63+
docker compose -f compose.production.yml logs -f
64+
```
65+
5. To stop the service:
66+
```bash
67+
docker compose -f compose.production.yml down
68+
```
69+
70+
## Testing
71+
72+
Before running integration tests locally, create a `.env.test` file in the project root with your Open Exchange Rates credentials:
73+
```dotenv
74+
OXR_BASE_URL=https://openexchangerates.org/api
75+
OXR_APP_ID=your-openexchangerates-app-id
76+
```
2977

30-
You can check out [the Next.js GitHub repository](https://github.com/vercel/next.js) - your feedback and contributions are welcome!
78+
1. **Run all tests (unit + integration)**
79+
```bash
80+
pnpm test
81+
```
3182

32-
## Deploy on Vercel
83+
2. **Unit tests only** (fast feedback, no external calls)
84+
```bash
85+
pnpm test:unit
86+
```
3387

34-
The easiest way to deploy your Next.js app is to use the [Vercel Platform](https://vercel.com/new?utm_medium=default-template&filter=next.js&utm_source=create-next-app&utm_campaign=create-next-app-readme) from the creators of Next.js.
88+
3. **Integration tests only** (hits real OXR API)
89+
```bash
90+
pnpm test:integration
91+
```
92+
Requires the `.env.test` file (or equivalent environment variables) described above.
3593

36-
Check out our [Next.js deployment documentation](https://nextjs.org/docs/app/building-your-application/deploying) for more details.
94+
4. **Continuous integration run with coverage**
95+
```bash
96+
pnpm test:ci
97+
```
98+
Generates coverage reports under `coverage/`.

compose.dev.yml

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
services:
2+
web:
3+
build:
4+
context: .
5+
target: dev
6+
command: pnpm dev
7+
ports: ["3000:3000"]
8+
env_file:
9+
- .env.development
10+
environment:
11+
NODE_ENV: development
12+
CHOKIDAR_USEPOLLING: "1"
13+
volumes:
14+
- .:/app
15+
- node-mod:/app/node_modules
16+
volumes:
17+
node-mod:

compose.production.yml

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
services:
2+
web:
3+
build:
4+
context: .
5+
target: runner # build the minimal runtime image
6+
env_file:
7+
- .env.production # runtime-only envs for the server
8+
environment:
9+
NODE_ENV: production
10+
NEXT_TELEMETRY_DISABLED: "1"
11+
HOSTNAME: 0.0.0.0
12+
PORT: "3000"
13+
ports:
14+
- "3000:3000"
15+
restart: unless-stopped
16+

next.config.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import type { NextConfig } from "next";
22

33
const nextConfig: NextConfig = {
44
/* config options here */
5+
output: "standalone",
56
};
67

78
export default nextConfig;

0 commit comments

Comments
 (0)