Skip to content

Commit f391bf0

Browse files
feat: Migrate to dotenv package and add pm2 for production
1 parent 766aeba commit f391bf0

File tree

5 files changed

+24
-37
lines changed

5 files changed

+24
-37
lines changed

package.json

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,9 @@
99
"build": "pnpm build:client && pnpm build:server",
1010
"build:client": "tsc -b && vite build",
1111
"build:server": "rollup -c --configPlugin \"rollup-plugin-esbuild\" && node -e \"require('fs').renameSync('dist/index.js', 'dist/server.cjs')\"",
12-
"preview": "node dist/server.cjs"
12+
"preview": "pm2 start ./dist/server.cjs --name server --watch",
13+
"stop": "pm2 stop server",
14+
"monitor": "pm2 monit"
1315
},
1416
"dependencies": {
1517
"@fastify/static": "latest",
@@ -27,6 +29,7 @@
2729
"rollup": "latest",
2830
"rollup-plugin-esbuild": "latest",
2931
"tsx": "latest",
32+
"pm2": "latest",
3033
"typescript": "latest",
3134
"vite": "latest",
3235
"vite-plugin-solid": "latest"

rollup.config.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,9 @@ import resolve from '@rollup/plugin-node-resolve'
22
import commonjs from '@rollup/plugin-commonjs'
33
import json from '@rollup/plugin-json'
44
import esbuild from 'rollup-plugin-esbuild'
5-
import { dotenv } from './src/server/util'
5+
import { config } from 'dotenv'
66

7-
const env = dotenv()
7+
config()
88

99
export default {
1010
input: 'src/server/index.ts',
@@ -16,8 +16,8 @@ export default {
1616
resolve({ preferBuiltins: true }),
1717
commonjs(),
1818
esbuild({
19-
minify: env?.NODE_ENV === 'production',
20-
sourceMap: env?.NODE_ENV === 'development',
19+
minify: process.env.NODE_ENV === 'production',
20+
sourceMap: process.env.NODE_ENV === 'development',
2121
}),
2222
json(),
2323
],

src/server/index.ts

Lines changed: 11 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,12 @@ import { readFileSync } from 'fs'
22
import { join } from 'path'
33
import { fastify } from 'fastify'
44
import serveStatic from '@fastify/static'
5-
import { dotenv, probablyBrowser } from './util'
5+
import { probablyBrowser } from './util'
6+
import { config } from 'dotenv'
67

7-
const env = dotenv() // It's optional whether you might prefer `config()` method
8-
const API = new URL(env?.API_ENDPOINT || 'http://localhost:3000/api')
8+
config()
9+
10+
const API = new URL(process.env.API_ENDPOINT || 'http://localhost:3000/api')
911

1012
// Optional, read more the docs
1113
const schema = {
@@ -24,12 +26,12 @@ const schema = {
2426
}
2527

2628
const app = fastify({
27-
logger: env?.NODE_ENV === 'development',
29+
logger: process.env.NODE_ENV === 'development',
2830
})
29-
const fallback = readFileSync(join(env?.ROOT || process.cwd(), 'index.html')) // SPA entry point
31+
const fallback = readFileSync(join(process.env.ROOT || process.cwd(), 'index.html')) // SPA entry point
3032

3133
// Serve vite generated html
32-
app.register(serveStatic, { root: env?.ROOT || process.cwd() })
34+
app.register(serveStatic, { root: process.env.ROOT || process.cwd() })
3335

3436
app.setNotFoundHandler((request, reply) => {
3537
if (probablyBrowser(request.headers)) {
@@ -58,16 +60,16 @@ app.get(API.pathname, schema, async function () {
5860

5961
async function main() {
6062
app.listen({ port: Number(API.port || 80), host: API.hostname })
61-
if (env?.NODE_ENV === 'production') console.log('Server running at', API.toString().replace(API.pathname, ''))
62-
console.log('Press `r` to restart, `q` to quit, `c` to clear.')
63+
if (process.env.NODE_ENV === 'production') console.log('Server running at', API.toString().replace(API.pathname, ''))
64+
console.log('Press `q` to quit, `c` to clear.')
6365
}
6466

6567
// Console input handler
6668
process.stdin.on('data', (data) => {
6769
switch (data.toString().trim()) {
6870
case 'q':
6971
console.log('Closing server...') // Restart is probably impossible: https://github.com/fastify/fastify/issues/2411
70-
process.exit(0)
72+
process.exit(0) // You can respawn by using `pm2` or implement platform-specific logic using `start` command in Windows for example.
7173
break
7274
case 'c':
7375
process.stdout.write('\u001b[2J\u001b[0;0H')

src/server/util.ts

Lines changed: 1 addition & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,26 +1,8 @@
1-
import { existsSync, readFileSync } from 'fs'
2-
import { join } from 'path'
3-
import { parse } from 'dotenv'
41
import { IncomingHttpHeaders } from 'http'
52

6-
export function dotenv() {
7-
try {
8-
const envPath = join(process.cwd(), '.env')
9-
const env = existsSync(envPath) ? parse(readFileSync(envPath)) : {}
10-
if (env) {
11-
console.log('Loaded `.env` configuration:', env)
12-
env.NODE_ENV = env.NODE_ENV || 'production' // Default
13-
console.log(`\nYou're in ${env.NODE_ENV}.\n`)
14-
}
15-
return env
16-
} catch (error) {
17-
console.error(error)
18-
}
19-
}
20-
213
export function probablyBrowser(headers: IncomingHttpHeaders): boolean {
224
return !!(
23-
headers['user-agent']?.includes('Mozilla/5.0') &&
5+
headers['user-agent']?.includes('Gecko') && // Modern browser tries to be like Gecko
246
headers['accept']?.includes('text/html') &&
257
headers['sec-ch-ua']
268
)

vite.config.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
import { defineConfig } from 'vite'
22
import solid from 'vite-plugin-solid'
3-
import { dotenv } from './src/server/util'
3+
import { config } from 'dotenv'
44

5-
const env = dotenv()
5+
config
66

7-
const DEV = new URL(env?.DEV_URL || 'http://localhost:5173')
8-
const API = new URL(env?.API_ENDPOINT || 'http://localhost:3000/api')
7+
const DEV = new URL(process.env.DEV_URL || 'http://localhost:5173')
8+
const API = new URL(process.env.API_ENDPOINT || 'http://localhost:3000/api')
99

1010
export default defineConfig({
1111
plugins: [solid()],

0 commit comments

Comments
 (0)