DEV Community

Alex Spinov
Alex Spinov

Posted on

Bun Shell Has a Free API That Replaces Bash Scripts With TypeScript

Bun Shell lets you write shell scripts in TypeScript. Cross-platform, type-safe, and faster than bash. Pipe commands, glob files, use template literals.

What Is Bun Shell?

Bun Shell (Bun.$) is a built-in shell that lets you run system commands using tagged template literals. Write bash-like scripts in TypeScript with proper error handling.

Quick Start

import { $ } from 'bun'

// Run commands like bash
await $`echo Hello, World!`

// Variables are safely escaped
const name = 'my project'
await $`mkdir -p ${name}/src`

// Get output as text
const result = await $`ls -la`.text()
console.log(result)

// Get as JSON
const pkg = await $`cat package.json`.json()
console.log(pkg.name)
Enter fullscreen mode Exit fullscreen mode

Piping

// Pipe between commands
await $`cat data.csv | sort | uniq -c | sort -rn | head -10`

// Pipe to file
await $`echo "Hello" > output.txt`
await $`echo "World" >> output.txt`

// Pipe from JavaScript
const data = JSON.stringify({ name: 'Alice', age: 30 })
await $`echo ${data} | jq .name`
Enter fullscreen mode Exit fullscreen mode

Error Handling

import { $ } from 'bun'

try {
  await $`git status`
} catch (err) {
  console.error(`Exit code: ${err.exitCode}`)
  console.error(`Stderr: ${err.stderr.toString()}`)
}

// Or use .nothrow() to not throw on non-zero exit
const result = await $`grep -r "TODO" src/`.nothrow()
if (result.exitCode !== 0) {
  console.log('No TODOs found')
}
Enter fullscreen mode Exit fullscreen mode

Glob Files

import { Glob } from 'bun'

const glob = new Glob('**/*.ts')
for await (const file of glob.scan('.')) {
  console.log(file)
}

// Count lines in all TypeScript files
const files = Array.from(glob.scanSync('src'))
for (const file of files) {
  const lines = await $`wc -l src/${file}`.text()
  console.log(lines.trim())
}
Enter fullscreen mode Exit fullscreen mode

Real Use Case: Deploy Script

import { $ } from 'bun'

const VERSION = process.argv[2] || 'latest'
const REGISTRY = 'ghcr.io/myorg'

console.log(`Deploying version ${VERSION}...`)

// Build
await $`bun run build`

// Test
await $`bun test`

// Docker build and push
await $`docker build -t ${REGISTRY}/myapp:${VERSION} .`
await $`docker push ${REGISTRY}/myapp:${VERSION}`

// Deploy
await $`kubectl set image deployment/myapp myapp=${REGISTRY}/myapp:${VERSION}`
await $`kubectl rollout status deployment/myapp`

console.log(`Deployed ${VERSION} successfully!`)
Enter fullscreen mode Exit fullscreen mode

Cross-Platform

Bun Shell works on macOS, Linux, and Windows — same script, no changes needed. It implements common shell commands natively.

Bun Shell vs Alternatives

Feature Bun Shell Bash zx (Google)
Language TypeScript Bash JavaScript
Type safety Yes No Partial
Cross-platform Yes No (Linux/Mac) Yes
Speed Fastest Fast Slow (Node)
Error handling try/catch set -e try/catch
Package manager Built-in N/A npm

Automating web scraping scripts? Scrapfly handles the hard parts. Email spinov001@gmail.com for TypeScript scraping automation.

Top comments (0)