codingstairs
NotesEDULifeContact
⌕Search⌘K
koen

Navigation

  • Intro
  • Blog
  • Life

Get in touch

Send without signing in. Add your email if you'd like a reply.

  • Leave a message anonymously →
  • ✉ warragon112@gmail.com
  • KakaoTalk Open Chat ↗

© 2026 codingstairs

  • Notes
  • EDU
  • Search
  • Life
  • Contact
  • Legal
  • RSS
  • GitHub
Notes›environment

Cross-platform scripts

Published 2026-04-28· Updated 2026-05-18·0 views

Cross-platform scripts

When a project targets users on Windows, macOS, and Linux all at once, the choice of tool for automation scripts becomes a recurring question. There is no single right answer — environment constraints and team familiarity steer the pick.

1. bash everywhere + Git Bash · WSL guidance

Write all automation in bash and tell Windows users to run it inside Git Bash (bundled with Git for Windows) or WSL2.

  • Pros — most natural on macOS · Linux. Plenty of online material. Standard shell tools (grep, awk, sed) are right there.
  • Cons — extra installs for native Windows users. Path mismatches (/c/Users/... vs C:\Users\...). Won't run directly under cmd or PowerShell.
  • Good fit — backend, data, and DevOps-centric teams.

2. Node-based scripts

Write automation on top of Node.js. JavaScript/TypeScript front-end projects already have Node, so there is little extra dependency.

Notable tools:

  • zx (Google) — a Node library for running commands with a bash-like feel. Syntax such as await $\ls``.
  • tsx — runs TypeScript files directly. tsx scripts/build.ts.
  • Plain .mjs — no external deps, just ESM. node scripts/clean.mjs.
// scripts/clean.mjs
import { rm } from "node:fs/promises";
await rm("dist", { recursive: true, force: true });
console.log("cleaned");

The strength is OS abstraction in the standard library (fs, path, os). The downside is that without Node nothing runs, and non-CLI work can balloon in code volume.

3. PowerShell 7+

PowerShell 7+ runs on Windows, macOS, and Linux. Object pipes and the .NET library underneath.

  • Pros — most natural for Windows users. Rich admin/automation cmdlets. 7+ is genuinely cross-platform.
  • Cons — a separate install for macOS and Linux users (brew install powershell, apt install powershell). The shell itself has lower mindshare in the Unix camp.
  • Good fit — Windows-led teams adding macOS · Linux compatibility.

4. Python scripts

Python ships a thick standard library with solid OS abstractions (pathlib, subprocess, shutil).

  • Pros — broad standard library. Readable. Data, HTTP, file handling each fit on a single line.
  • Cons — needs the interpreter and version management (virtual envs). For simple command launching, the code is longer than a shell line.
  • Good fit — projects already centered on Python, or scripts dealing with data and networking.

5. Make · Just

make is the classic Unix build automation tool. just is a modern simplification of the same idea.

  • make — bundled on macOS · Linux. Windows needs a separate install (MSYS2, GnuWin). Makefile tab/space syntax is finicky.
  • just — written in Rust. A flat command collection without dependency graphs. Friendlier to cross-platform than make. cargo install just or brew install just.
# Makefile
build:
	npm run build

test:
	npm test
# justfile
build:
    npm run build

test:
    npm test

The strength is gathering commands in one file. The downside is that internally each rule still calls a shell command, so OS differences come back.

6. package.json scripts

For JS · TS projects, package.json's scripts is the de facto entry point.

{
  "scripts": {
    "dev": "next dev",
    "build": "next build",
    "lint": "eslint ."
  }
}

Works under npm, pnpm, or yarn. Calls tools from node_modules/.bin without global installs. OS-sensitive commands get smoothed with helpers like cross-env (env vars), rimraf (directory removal), or npm-run-all.

Once a scripts entry grows long, splitting it out into zx or a separate .mjs becomes friendlier to maintenance.

7. Comparison summary

Approach Windows fit macOS · Linux fit Extra install Suitable scale
bash Moderate (Git Bash needed) High Git Bash · WSL Any size
Node (zx, .mjs) High High Node Small to medium
PowerShell 7 High Moderate pwsh Small to medium
Python High High Python Medium to large
Make Moderate High (separate on Windows) Small to medium
Just High High just binary Small to medium

8. The same task in four flavors

# bash
rm -rf dist
# PowerShell
Remove-Item -Recurse -Force dist -ErrorAction SilentlyContinue
// Node .mjs
import { rm } from "node:fs/promises";
await rm("dist", { recursive: true, force: true });
# Python
import shutil; shutil.rmtree("dist", ignore_errors=True)

9. Common pitfalls

bash scripts saved with CRLF break on Linux — declare *.sh text eol=lf in .gitattributes.

Node scripts hard-coding "a/b/c" instead of path.join — works on Windows but logs and outputs look off.

Calling pwsh assuming PowerShell 7+ is installed when only 5.1 is — detect first and guide.

Makefiles indented with spaces breaking make — Make requires literal tabs.

Calling && from PowerShell 5.1 (instead of cmd) on Windows — parser error.

Closing thoughts

There is no single right answer for cross-platform scripts. The team's environment mix (Windows · Unix) and the project's nature (front-end · backend · data) decide. Either keeping three OS-equivalent scripts side by side or unifying on a Node .mjs set are the two shapes that show up most often.

Next

  • markdown
  • text-encoding-line-endings

google/zx · tsx · PowerShell install · casey/just · npm Docs scripts for reference.

More in environment

All in this category →
  • WSL2 — Linux on top of Windows
  • Data formats — JSON · YAML · TOML · XML
  • First day with the terminal
  • Text encoding and line endings
  • Markdown
  • cmd.exe and batch files