path and process
Two built-in features you’ll use in almost every Node.js project: the path module for working with file system paths, and the process global for runtime information.
The path module
Section titled “The path module”File paths look different on Windows (C:\Users\alice\file.txt) and Unix (/home/alice/file.txt). The path module handles this automatically.
import { join, resolve, dirname, basename, extname } from 'path'path.join
Section titled “path.join”Joins path segments with the correct separator for the OS:
import { join } from 'path'
const dbPath = join(process.cwd(), 'data', 'bulletin.db')// Unix: '/home/user/project/data/bulletin.db'// Windows: 'C:\Users\user\project\data\bulletin.db'Always use path.join instead of string concatenation for paths.
path.resolve
Section titled “path.resolve”Resolves a sequence of paths into an absolute path, starting from the current working directory:
import { resolve } from 'path'
resolve('src', 'index.ts')// → '/absolute/path/to/project/src/index.ts'path.dirname, path.basename, path.extname
Section titled “path.dirname, path.basename, path.extname”import { dirname, basename, extname } from 'path'
const filePath = '/home/alice/project/src/index.ts'
dirname(filePath) // '/home/alice/project/src'basename(filePath) // 'index.ts'extname(filePath) // '.ts'basename(filePath, extname(filePath)) // 'index' (name without extension)The process object
Section titled “The process object”process is a global available in every Node.js file — no import needed. It provides information about the running process.
process.cwd()
Section titled “process.cwd()”The current working directory — the directory from which you ran node:
console.log(process.cwd())// → '/home/user/bulletin-api'Use this to build absolute paths that work regardless of where you require/import from:
const dbPath = join(process.cwd(), 'bulletin.db')process.env
Section titled “process.env”A dictionary of environment variables. This is how configuration values (database paths, JWT secrets, ports) are passed to Node.js without hardcoding them:
const port = process.env.PORT || '3000'const jwtSecret = process.env.JWT_SECRET
if (!jwtSecret) { throw new Error('JWT_SECRET environment variable is required')}process.argv
Section titled “process.argv”Command-line arguments passed to the script:
// node script.ts --migrate --seedconsole.log(process.argv)// ['node', '/path/to/script.ts', '--migrate', '--seed']Useful for build scripts and migration utilities.
process.exit()
Section titled “process.exit()”Exits the Node.js process with a status code:
process.exit(0) // successprocess.exit(1) // error (non-zero = failure for CI/CD)process.on('uncaughtException')
Section titled “process.on('uncaughtException')”Handle unexpected errors that weren’t caught anywhere:
process.on('uncaughtException', (error) => { console.error('Uncaught exception:', error) process.exit(1)})In production, use a proper error monitoring service — but this prevents silent crashes during development.
In the Bulletin API
Section titled “In the Bulletin API”The API uses path and process throughout:
import { join } from 'path'import Database from 'better-sqlite3'
const dbPath = process.env.DATABASE_PATH || join(process.cwd(), 'bulletin.db')const db = new Database(dbPath)const PORT = parseInt(process.env.PORT || '3000', 10)app.listen(PORT, () => console.log(`API running on port ${PORT}`))Exercise
Section titled “Exercise”- Create
src/utils/paths.tsthat exports apathsobject with absolute paths for common project directories:root,src,db. - Use
process.cwd()andpath.jointo build these. - Log the paths and verify they’re correct absolute paths.
- Add a check: if
process.env.NODE_ENVisn’t set, log a warning.
path.join(...)builds cross-platform paths — always use it instead of string concatenation.path.resolve(...)creates absolute paths from the current directory.process.cwd()is the directory from which the script was run.process.envholds environment variables — use it for configuration.process.argvhas command-line arguments;process.exit(code)terminates the process.