Skip to content

Commit c7b1328

Browse files
committed
use defaults for expected proccess envs
1 parent 4b37ed5 commit c7b1328

9 files changed

+119
-143
lines changed

.env_example

+4-1
Original file line numberDiff line numberDiff line change
@@ -2,4 +2,7 @@ PORT=3000
22
ADDRESS=laidrivm.com
33
SOURCE=local
44
# SOURCE=https://github.com/laidrivm/articles
5-
# GITHUB_TOKEN=unath
5+
GITHUB_TOKEN=unath
6+
# GITHUB_TOKEN=ghp_...
7+
ARTICLES=articles
8+
PUBLIC=public

build.js

-72
This file was deleted.

package.json

+3-3
Original file line numberDiff line numberDiff line change
@@ -33,13 +33,13 @@
3333
"scripts": {
3434
"format": "prettier --write 'src/**/*.{css,html,ts,tsx}'",
3535
"lint": "eslint 'src/**/*.{css,html,ts,tsx}' --fix",
36-
"build": "bun run build.js",
36+
"build": "bun run src/build.ts",
3737
"test": "bun test --watch --timeout 1000 --rerun-each 2 --coverage",
3838
"generate_dev": "bun src/generate.tsx",
3939
"server_dev": "bun run --watch src/index.ts",
4040
"dev": "bun run build && bun run generate_dev && bun run server_dev",
41-
"generate": "bun out/generate.js",
42-
"server": "bun out/index.js",
41+
"generate": "bun run out/generate.js",
42+
"server": "bun run out/index.js",
4343
"prod": "bun run generate && bun run server",
4444
"clean": "bun run src/public-clean-up.ts"
4545
}

src/build.ts

+58
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
import path from 'path'
2+
import {mkdir} from 'node:fs/promises'
3+
4+
import esbuild from 'esbuild'
5+
import cssModulesPlugin from 'esbuild-css-modules-plugin'
6+
7+
import * as EnvUtils from './envutils.ts'
8+
9+
esbuild
10+
.build({
11+
entryPoints: ['./src/index.ts', './src/generate.tsx'],
12+
bundle: true,
13+
metafile: true,
14+
outdir: './out',
15+
outbase: 'src',
16+
platform: 'node',
17+
format: 'esm',
18+
target: 'esnext',
19+
external: [],
20+
nodePaths: ['node_modules']
21+
})
22+
.catch(() => process.exit(1))
23+
24+
EnvUtils.initDefaults()
25+
26+
const pub = Bun.file(process.env.PUBLIC)
27+
28+
if (!(await pub.exists())) {
29+
await mkdir(process.env.PUBLIC, {recursive: true})
30+
}
31+
32+
const fonts = Bun.file(path.join(process.env.PUBLIC, 'fonts'))
33+
if (!(await fonts.exists('./public/fonts'))) {
34+
await mkdir(path.join(process.env.PUBLIC, 'fonts'), {recursive: true})
35+
}
36+
37+
esbuild
38+
.build({
39+
entryPoints: ['./src/styles/main.css'],
40+
bundle: true,
41+
outfile: './public/main.css',
42+
minify: true,
43+
metafile: true,
44+
loader: {
45+
'.ttf.woff2': 'file',
46+
'.woff2': 'file'
47+
},
48+
plugins: [
49+
cssModulesPlugin({
50+
inject: true,
51+
minify: true,
52+
targets: '>= 0.25%'
53+
})
54+
],
55+
publicPath: '/', // Set public path for file references
56+
assetNames: 'fonts/[name]' // Output assets to the fonts directory
57+
})
58+
.catch(() => process.exit(1))

src/envutils.ts

+30
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
export function initDefaults(): void {
2+
if (!process.env.PORT) {
3+
process.env.PORT = '3000'
4+
console.log(`Using default port: ${process.env.PORT}`)
5+
}
6+
if (!process.env.ADDRESS) {
7+
process.env.ADDRESS = 'localhost'
8+
console.log(`Using default site address: ${process.env.ADDRESS}`)
9+
}
10+
if (!process.env.SOURCE) {
11+
process.env.SOURCE = 'local'
12+
console.log(`Using default source for the content: ${process.env.SOURCE}`)
13+
}
14+
if (!process.env.GITHUB_TOKEN) {
15+
process.env.GITHUB_TOKEN = 'unauth'
16+
console.log(`Using default token for GitHub: ${process.env.GITHUB_TOKEN}`)
17+
}
18+
if (!process.env.ARTICLES) {
19+
process.env.ARTICLES = 'articles'
20+
console.log(
21+
`Using default directory to store content sources: ${process.env.ARTICLES}`
22+
)
23+
}
24+
if (!process.env.PUBLIC) {
25+
process.env.PUBLIC = 'public'
26+
console.log(
27+
`Using default directory to render and serve pages: ${process.env.PUBLIC}`
28+
)
29+
}
30+
}

src/generate.tsx

+4-32
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import {join} from 'path'
22
import {rm} from 'node:fs/promises'
33

4+
import * as EnvUtils from './envutils.ts'
45
import type {Indexes, PageEntry, ArticleProcessingConfig} from './types.ts'
56
import pullArticles from './pullarticles.ts'
67
import {processArticles, processIndexes} from './processpages.tsx'
@@ -68,7 +69,7 @@ interface SiteGenerationConfig {
6869
* Generate static site with configurable options
6970
* @param config Site generation configuration
7071
*/
71-
async function generateSite(config: SiteGenerationConfig = {}): Promise<void> {
72+
async function generateSite(config: SiteGenerationConfig = {}): void {
7273
const {
7374
articlesPath = process.env.ARTICLES,
7475
publicPath = process.env.PUBLIC,
@@ -106,34 +107,5 @@ async function generateSite(config: SiteGenerationConfig = {}): Promise<void> {
106107
}
107108
}
108109

109-
/**
110-
* Validate if arguments are already loaded in the environment
111-
*/
112-
function hasRequiredEnvVars(): boolean {
113-
const requiredVars = [
114-
'PORT',
115-
'ADDRESS',
116-
'SOURCE',
117-
'GITHUB_TOKEN',
118-
'ARTICLES',
119-
'PUBLIC'
120-
]
121-
return requiredVars.every(varName => !!process.env[varName])
122-
}
123-
124-
async function initializeSiteGeneration(): Promise<void> {
125-
try {
126-
if (!hasRequiredEnvVars()) {
127-
const dotEnv = await Bun.file('.env')
128-
if (!(await dotEnv.exists())) {
129-
throw new Error('No .env file found')
130-
}
131-
}
132-
await generateSite()
133-
} catch (error) {
134-
console.error('Site generation initialization error:', error)
135-
process.exit(1)
136-
}
137-
}
138-
139-
initializeSiteGeneration()
110+
EnvUtils.initDefaults()
111+
await generateSite()

src/index.ts

+3-23
Original file line numberDiff line numberDiff line change
@@ -1,32 +1,12 @@
11
import {Elysia} from 'elysia'
22
import {staticPlugin} from '@elysiajs/static'
33

4+
import * as EnvUtils from './envutils.ts'
5+
46
const key = await Bun.file('certs/key.pem').text()
57
const cert = await Bun.file('certs/cert.pem').text()
68

7-
function hasRequiredEnvVars(): boolean {
8-
const requiredVars = [
9-
'PORT',
10-
'ADDRESS',
11-
'SOURCE',
12-
'GITHUB_TOKEN',
13-
'ARTICLES',
14-
'PUBLIC'
15-
]
16-
return requiredVars.every(varName => !!process.env[varName])
17-
}
18-
19-
try {
20-
if (!hasRequiredEnvVars()) {
21-
const dotEnv = await Bun.file('.env')
22-
if (!(await dotEnv.exists())) {
23-
throw new Error('No .env file found')
24-
}
25-
}
26-
} catch (error) {
27-
console.error('Site serving initialization error:', error)
28-
process.exit(1)
29-
}
9+
EnvUtils.initDefaults()
3010

3111
const app = new Elysia()
3212
.use(

src/public-clean-up.ts

+5-3
Original file line numberDiff line numberDiff line change
@@ -2,14 +2,16 @@ import {existsSync, statSync, rmdirSync} from 'node:fs'
22
import {readdir} from 'node:fs/promises'
33
import path from 'path'
44

5+
import * as EnvUtils from './envutils.ts'
6+
57
const EXCEPTIONS = [
68
'favicon.png',
79
'mellon-for-incubators.pdf',
810
'og_image-min.jpg',
911
'robots.txt'
1012
]
1113

12-
async function deleteRecursively(dirPath: string) {
14+
async function deleteRecursively(dirPath: string): void {
1315
if (!existsSync(dirPath)) return
1416

1517
const items = await readdir(dirPath)
@@ -44,8 +46,8 @@ async function deleteRecursively(dirPath: string) {
4446
}
4547
}
4648

47-
async function cleanupPublicDirectory() {
48-
process.env.PUBLIC = process.env.PUBLIC ? process.env.PUBLIC : 'public'
49+
async function cleanupPublicDirectory(): void {
50+
EnvUtils.initDefaults()
4951
const publicDir = process.env.PUBLIC
5052

5153
if (!existsSync(publicDir)) {

src/pullarticles.ts

+12-9
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,14 @@ import {Octokit} from 'octokit'
55
import {Buffer} from 'buffer/'
66

77
const IGNORE_LIST: string[] = ['README.md', '.git', '.gitignore']
8-
const IMAGE_EXTENSIONS: string[] = ['.png', '.jpg', '.jpeg', '.gif', '.svg', '.webp']
8+
const IMAGE_EXTENSIONS: string[] = [
9+
'.png',
10+
'.jpg',
11+
'.jpeg',
12+
'.gif',
13+
'.svg',
14+
'.webp'
15+
]
916

1017
/**
1118
* Parse GitHub repository details from URL
@@ -68,10 +75,10 @@ async function downloadFile(
6875

6976
// Decode file content (GitHub API returns base64 encoded content)
7077
const fileContent = Buffer.from(data.content, 'base64')
71-
78+
7279
const localFilePath = path.join(articlesDir, item.path)
7380
await fs.mkdir(path.dirname(localFilePath), {recursive: true})
74-
81+
7582
if (item.name.endsWith('.md')) {
7683
// For markdown files, convert to utf-8 string before writing
7784
await fs.writeFile(localFilePath, fileContent.toString('utf-8'))
@@ -120,7 +127,7 @@ async function processRepoContents(
120127
if (item.type === 'dir') {
121128
await processRepoContents(octokit, owner, repo, item.path, articlesDir)
122129
} else if (
123-
item.type === 'file' &&
130+
item.type === 'file' &&
124131
(item.name.endsWith('.md') || isImage(item.name))
125132
) {
126133
await downloadFile(octokit, owner, repo, item, articlesDir)
@@ -148,10 +155,6 @@ async function pullArticles(
148155
const githubToken = config?.githubToken || process.env.GITHUB_TOKEN
149156
const sourceUrl = config?.sourceUrl || process.env.SOURCE
150157

151-
if (!sourceUrl) {
152-
throw new Error('Missing SOURCE environment variable')
153-
}
154-
155158
const octokit = createOctokitClient(githubToken)
156159

157160
const {owner, repo} = parseRepoDetails(sourceUrl)
@@ -168,4 +171,4 @@ async function pullArticles(
168171
}
169172
}
170173

171-
export default pullArticles
174+
export default pullArticles

0 commit comments

Comments
 (0)