Installation
Quick Install
Run this command in your project directory:
curl -fsSL https://project-actions.org/install.sh | bash
With Starter Commands
Include example commands to get started quickly:
curl -fsSL https://project-actions.org/install.sh | bash -s -- --with-starter-commands
What Gets Installed
.project/— Directory for your commands.project/.runtime/— Runner binaries (auto-downloaded)project— Executable wrapper script
Requirements
- macOS (Intel or Apple Silicon) or Linux
- Bash shell
- curl or wget
- Internet connection (for initial download)
Command Structure
Commands are YAML files in the .project/ directory:
# .project/command-name.yaml help: short: One-line description (required) long: | Multi-line detailed description (optional) Shown when user runs: project command-name --help order: 10 # Display order (optional) context: outside-container # or inside-container:service steps: - echo: "Hello World" - run: "echo 'Shell command'"
Help Section
short— Required. Brief one-line descriptionlong— Optional. Detailed multi-line descriptionorder— Optional. Controls display order (1–99)
Context
outside-container— Run on host machineinside-container:service— Run inside Docker container
Primitives
Primitives are always available and use shorthand syntax — the YAML key is the step type.
echo
Print messages to the console.
steps: - echo: "Simple message" - echo: | Multi-line message with multiple lines
run
Execute shell commands. Fails the step on non-zero exit.
steps: - run: "npm install" - run: | echo "Running multiple commands" npm test echo "Tests complete"
<args> — Argument Interpolation
Use <args> anywhere in the command string to pass all positional CLI arguments through to the shell command. Individual arguments are accessible as <args.0>, <args.1>, etc. Use <args.length> to get the argument count.
steps: - run: <args> # ./project run foo bar → foo bar - run: php <args> # ./project run artisan migrate → php artisan migrate - run: composer <args> # ./project run install → composer install
If <args> or <args.N> is present but the required arguments are not given, the runner exits with a usage error. <args.length> never errors — it evaluates to 0 when no arguments are given.
Context-Aware Routing
When a command declares context: inside-container:<service>, run: steps automatically route through docker-compose exec when the runner is outside the container. This applies to all run: steps in the command, not just steps using <args>.
| Condition | Execution |
|---|---|
| No service set, or already inside container | sh -c "<cmd>" |
| Outside container, service set | docker-compose exec <service> sh -c "<cmd>" |
help: short: Run a script or binary inside the web container context: inside-container:web steps: - run: <args>
Usage: ./project run artisan migrate, ./project run composer install, etc. Add this command with ./project init docker.
command
Call other Project Actions commands.
steps: - command: setup - command: build
check-for
Verify that a tool exists in PATH.
steps: - check-for: docker if-missing: | Docker is required but not found. Install from https://docker.com
Conditionals
Conditional primitives use the same shorthand syntax and control which steps execute based on CLI flags or filesystem state.
if-option
Execute steps when a command-line option is provided.
steps: - if-option: production then: - echo: "Production mode" - run: "npm run build:prod" # OR logic with pipe - if-option: debug|trace|verbose then: - echo: "Debug logging enabled"
Usage: ./project command-name --production
if-no-option
Execute steps when an option is NOT provided.
steps: - if-no-option: skip-tests then: - echo: "Running tests..." - run: "npm test"
if-missing
Execute steps when a file or directory doesn't exist.
steps: - if-missing: node_modules then: - echo: "Installing dependencies..." - run: "npm install" - if-missing: .env then: - run: "cp .env.example .env"
Nested Conditionals
Conditionals can be nested for complex logic.
steps: - if-option: production then: - echo: "Production deployment" - if-missing: dist then: - echo: "Building..." - run: "npm run build"
Docker Integration
Built-in actions are shipped with the runner and invoked via the action: key.
compose-up
Start Docker Compose services.
steps: - action: compose-up detached: true # default
compose-stop
Stop Docker Compose services (without removing).
steps: - action: compose-stop
compose-down
Stop and remove Docker Compose services.
steps: - action: compose-down volumes: false # Keep volumes (default) - action: compose-down volumes: true # Remove volumes too
compose-exec
Execute commands in running containers.
steps: # Interactive shell - action: compose-exec service: web command: /bin/bash interactive: true # Non-interactive command - action: compose-exec service: web command: "php artisan migrate" interactive: false
CLI Reference
./project
List all available commands
./project <command>
Run a specific command
./project <command> --option
Run command with options
./project <command> --help
Show help for a command
./project --version
Show version information
Troubleshooting
Command not found
Make sure the command file exists in .project/ and has a .yaml or .yml extension.
ls -la .project/*.yaml
Permission denied
Ensure the project script is executable:
chmod +x ./project
Runner download fails
Check your internet connection and ensure curl or wget is installed:
which curl wget
Docker commands fail
Verify Docker is installed and running:
docker --version docker-compose --version
YAML parsing errors
Check your YAML syntax. Common issues:
- Incorrect indentation (use spaces, not tabs)
- Missing colons after keys
- Unquoted strings with special characters
Need More Help?
Community Support
Documentation