A simple CLI tool for quickly deploying and re-deploying your application on a Portainer environment.
- A
docker-compose.ymlfile in your project directory - Portainer instance with API access
- Portainer API token (generate in Portainer: Settings > API Keys)
pctl initInteractive setup to configure your Portainer connection (URL, API token, environment). This creates a pctl.yml configuration file.
pctl deployDeploy your Docker Compose stack to Portainer. The tool reads your docker-compose.yml file and creates a new stack.
Build Support: If your compose file contains build: directives, pctl will automatically build the images before deployment. See the Build Configuration section for details.
pctl redeployUpdate an existing stack with latest images.
Force Rebuild: Use the -f or --force-rebuild flag to force rebuild images even if they haven't changed:
pctl redeploy -fThis sets force_build=true for this run, which includes no-cache behavior, ensuring a complete rebuild of all images.
pctl psView stack status and running containers.
pctl logsStream real-time logs from your containers.
Log Options:
-t, --tail N: Show the last N lines from the end of logs (default: 50)-s, --service NAME: Show logs from a specific service only--non-interactive: Force non-interactive mode (useful for testing and automation)
Examples:
# Show last 100 lines from all containers
pctl logs -t 100
# Show logs from a specific service
pctl logs -s web
# Show last 20 lines from the database service
pctl logs -s database -t 20
# Force non-interactive mode (useful for testing)
pctl logs --non-interactive
# Non-interactive mode with specific service and tail count
pctl logs -s web -t 10 --non-interactivepctl versionDisplay version information including version number, git commit hash, build timestamp, Go version, and target platform.
pctl uses a pctl.yml configuration file created during initialization:
portainer_url: https://portainer.example.com
api_token: ptr_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
environment_id: 1
stack_name: pctl_myproject
compose_file: docker-compose.yml
skip_tls_verify: trueThe configuration includes:
- portainer_url: Your Portainer instance URL
- api_token: Portainer API token (starts with
ptr_) - environment_id: Portainer environment ID
- stack_name: Name for your stack in Portainer
- compose_file: Path to your Docker Compose file
- skip_tls_verify: Skip TLS verification for self-hosted instances
When using build: directives in your compose file, pctl can automatically build images before deployment. Add a build section to your pctl.yml:
build:
mode: remote-build # remote-build (default) or load
parallel: auto # concurrent builds (auto or number)
tag_format: "pctl-{{stack}}-{{service}}:{{hash}}"
platforms: ["linux/amd64"] # for load mode
extra_build_args: {} # global build args
force_build: false # force rebuild even if unchanged
warn_threshold_mb: 50 # warn if context > 50MB- remote-build (default): Builds images on the remote Docker engine via Portainer's Docker proxy. Most bandwidth-efficient.
- load: Builds images locally and uploads them to the remote engine. Useful when the remote has poor internet access.
version: '3.8'
services:
web:
build:
context: ./web
dockerfile: Dockerfile
args:
NODE_ENV: production
ports:
- "3000:3000"
api:
build: ./api
ports:
- "8080:8080"When you run pctl deploy, it will:
- Detect the
build:directives - Build the images according to your build configuration
- Transform the compose file to use the built images
- Deploy the stack to Portainer
Download the latest release for your platform from GitHub Releases:
wget https://github.com/deviantony/pctl/releases/latest/download/pctl_1.2.2_linux_amd64.tar.gz
tar -xzf pctl_1.2.2_linux_amd64.tar.gz
chmod +x pctl
sudo mv pctl /usr/local/bin/wget https://github.com/deviantony/pctl/releases/latest/download/pctl_1.2.2_linux_arm64.tar.gz
tar -xzf pctl_1.2.2_linux_arm64.tar.gz
chmod +x pctl
sudo mv pctl /usr/local/bin/wget https://github.com/deviantony/pctl/releases/latest/download/pctl_1.2.2_darwin_amd64.tar.gz
tar -xzf pctl_1.2.2_darwin_amd64.tar.gz
chmod +x pctl
sudo mv pctl /usr/local/bin/wget https://github.com/deviantony/pctl/releases/latest/download/pctl_1.2.2_darwin_arm64.tar.gz
tar -xzf pctl_1.2.2_darwin_arm64.tar.gz
chmod +x pctl
sudo mv pctl /usr/local/bin/wget https://github.com/deviantony/pctl/releases/latest/download/pctl_1.2.2_windows_amd64.zip
# Extract the zip file and move pctl.exe to your PATHpctl includes both unit tests and integration tests to ensure reliability and correctness.
Run the unit test suite:
# Run all unit tests
make test
# Run tests with coverage report
make test-coverageUnit tests cover:
- Configuration loading and validation
- Compose file parsing and transformation
- Build system components (tagging, context handling, orchestration)
- Portainer API client functionality
- Error handling and formatting
Integration tests run against a real Portainer instance to validate end-to-end functionality.
Prerequisites:
- Access to a Portainer instance
- Portainer API token
- Valid environment ID in Portainer
Setup:
- Copy the example configuration:
cp integration_test_config.json.example integration_test_config.json- Edit
integration_test_config.jsonwith your Portainer details:
{
"portainer_url": "https://your-portainer-instance.com",
"api_token": "ptr_your_api_token_here",
"environment_id": 1
}Running Integration Tests:
# Run integration tests
make test-integrationIntegration tests cover:
- Deploying simple stacks (images only)
- Redeploying existing stacks
- Force rebuild with
-fflag - Stack status checking (
pctl ps) - Container logs (
pctl logs) - Build functionality (both remote-build and load modes)
- Error handling for non-existent stacks
Note: Integration tests will create and clean up test stacks automatically. The tests use unique stack names to avoid conflicts.
Releases are automated using GoReleaser and GitHub Actions. To create a new release:
# Create a new release (e.g., version 1.1.1)
./scripts/release.sh 1.1.1
# Dry run to see what would happen
./scripts/release.sh 1.1.1 --dry-runThis will:
- Create a git tag
v1.1.1 - Push the tag to GitHub
- GoReleaser automatically builds binaries for all platforms
- Creates a GitHub release with all binaries, checksums, and release notes
See RELEASE.md for detailed release process documentation.
- Docker Standalone environments only - Full support for Kubernetes environments is planned for future versions.