Prabogo Documentation

Welcome to the Prabogo documentation. This guide will help you understand the framework and how to use it effectively in your projects.

Getting Started

Prabogo is a Go framework designed to simplify project development by providing an interactive command interface and built-in instructions for AI assistance. This framework streamlines common engineering tasks, making it easier for software engineers to scaffold, generate, and manage project components efficiently.

Requirements

  • Go version >= 1.24.0
  • Docker and Docker Compose (optional, for running external services)
  • fzf (optional, for enhanced interactive command selection)

Installation

# Install the installer tool
go install github.com/prabogo/prabogo-install@latest

# Create a new project
prabogo-install my-project-name

# Setup the project
cd my-project-name
cp .env.example .env
go mod tidy
docker-compose up -d

Running the Application

You have several options to run your Prabogo application:

# Using the interactive command selector
make run

# Running in HTTP server mode
make http

# Running in message consumer mode
make message SUB=upsert_client

# Executing a specific command
make command CMD=publish_upsert_client VAL=name

# Running directly without Makefile
go run cmd/main.go http

Architecture

Prabogo uses Hexagonal Architecture (also known as Ports and Adapters pattern) to keep the business logic separate from external dependencies like databases, UI frameworks, and messaging systems.

Hexagonal Architecture

Key Components

  • Port: Interface defining how the application communicates with the outside world.
  • Adapter: Component implementing a port to connect external systems or technologies to the core.
  • Domain: Core business logic and rules, independent of external systems or frameworks.
  • Application: Layer that coordinates activities and orchestrates domain logic.

This architecture allows you to:

  • Replace infrastructure components with minimal changes
  • Test business logic in isolation
  • Develop features without being constrained by external dependencies
  • Maintain a clean separation of concerns

Read more about Prabogo's architecture

Authorization

Prabogo supports multiple authorization strategies to secure your applications. You can choose between internal bearer key authentication or integrate with external identity providers like Authentik for enhanced security.

Configuration Overview

Authorization is configured through the AUTH_DRIVER environment variable. Prabogo supports two main authorization methods:

1. Internal Bearer Key Authentication

This method uses internal client bearer keys stored in your database. While simple to implement, it's recommended to use mTLS (mutual TLS) when using this approach for enhanced security.

Configuration

# Set AUTH_DRIVER to empty/blank for internal authentication
AUTH_DRIVER=

# Other required configurations
DATABASE_USERNAME=prabogo
DATABASE_PASSWORD=prabogo
DATABASE_HOST=localhost
DATABASE_PORT=5432
DATABASE_NAME=prabogo

Security Recommendations

⚠️ Security Note: When using internal bearer key authentication, it's highly recommended to implement mTLS (mutual TLS) for additional security. This ensures both client and server authentication through certificates.

Benefits of using mTLS with internal authentication:

  • Mutual authentication between client and server
  • Certificate-based identity verification
  • Protection against man-in-the-middle attacks
  • Enhanced encryption for data in transit

2. Authentik JWT Authentication (Recommended)

For enhanced security, Prabogo integrates with Authentik using JWT (JSON Web Token) client credentials flow. This method provides enterprise-grade authentication and authorization capabilities.

Configuration

# Set AUTH_DRIVER to "authentik" for JWT authentication
AUTH_DRIVER=authentik

# Configure the JWKS URL for token validation
AUTH_JWKS_URL=https://your-authentik-server.com/application/o/your-app/jwks/

# Example configuration
# AUTH_JWKS_URL=https://authentik-server.prabogo.orb.local/application/o/prabogo/jwks/

Authentik Setup Requirements

To use Authentik JWT authentication, you need to:

  1. Run Authentik Server (Development)

    For development and testing purposes, you can run Authentik locally using the provided Docker Compose file:

    # Start Authentik services (PostgreSQL, Redis, Server, Worker)
    docker-compose -f docker-compose.authentik.yml up -d
    
    # Check if all services are running
    docker-compose -f docker-compose.authentik.yml ps
    
    # Access Authentik web interface
    # Navigate to: http://localhost:9080

    Default Access:

    • HTTP: http://localhost:9080
    • Initial Setup: http://localhost:9080/if/flow/initial-setup
    💡 Development Note: The docker-compose.authentik.yml file includes all necessary services (PostgreSQL on port 5433, Redis on port 6380, and Authentik server). Make sure these ports are available on your system.
  2. Create an Application in Authentik
    • Configure OAuth2/OpenID provider
    • Configure Application
    • Configure appropriate scopes and permissions (necessary)
  3. Create Service Account (Recommended)
    • Create a user with service account type in Authentik
    • Generate an app password for the service account
    • Use username/password authentication to obtain JWT tokens
    • This approach provides better security and token management compared to client credentials

    Once you have created a service account and app password, you can obtain JWT tokens using a curl request:

    curl --location 'https://your-authentik-server.com/application/o/token/' \
    --header 'Content-Type: application/x-www-form-urlencoded' \
    --data-urlencode 'grant_type=client_credentials' \
    --data-urlencode 'client_id=your-client-id' \
    --data-urlencode 'scope=openid' \
    --data-urlencode 'username=your-service-account' \
    --data-urlencode 'password=your-generated-app-password'

    Response: The API will return a JSON response containing the access_token (JWT) and other token information:

    {
      "access_token": "eyJhbGciOiJSUzI1NiIsImtpZCI6IjE2NzM...",
      "token_type": "Bearer",
      "expires_in": 300,
      "id_token": "eyJhbGciOiJSUzI1NiIsImtpZCI6IjE2NzM..."
    }
  4. Configure JWKS Endpoint
    • Obtain the JWKS URL from your Authentik application
    • Ensure the endpoint is accessible from your Prabogo application
  5. Set Environment Variables
    • Update AUTH_DRIVER=authentik
    • Set the correct AUTH_JWKS_URL

Benefits of Authentik JWT Authentication

  • Enhanced Security: Industry-standard JWT tokens with digital signatures
  • Centralized Identity Management: Single sign-on (SSO) capabilities
  • Scalability: Stateless authentication suitable for microservices
  • Token Validation: Automatic token validation using JWKS
  • Fine-grained Access Control: Role-based and attribute-based access control
  • Audit Trail: Comprehensive logging of authentication events

Choosing the Right Method

Feature Internal Bearer Key Authentik JWT
Setup Complexity Simple Moderate
Security Level Good (with mTLS) Excellent
Scalability Limited High
External Dependencies Database only Authentik server
Token Management Manual Automatic
SSO Support No Yes

Migration Between Methods

You can easily switch between authentication methods by updating the environment variables:

# Switch to internal authentication
AUTH_DRIVER=
# Remove or comment out AUTH_JWKS_URL

# Switch to Authentik authentication
AUTH_DRIVER=authentik
AUTH_JWKS_URL=https://your-authentik-server.com/application/o/your-app/jwks/

After changing the configuration, restart your application to apply the new authentication method.

Makefile Commands

Prabogo provides a comprehensive Makefile with various helpful commands for code generation and development tasks.

Interactive Command Runner

You can use the interactive target selector to choose and run Makefile targets:

make run
Interactive Command Runner

Code Generation Commands

  • make model VAL=name

    Creates a model/entity with necessary structures

  • make migration-postgres VAL=name

    Creates a PostgreSQL migration file

  • make inbound-http-fiber VAL=name

    Creates HTTP handlers using Fiber framework

  • make inbound-message-rabbitmq VAL=name

    Creates RabbitMQ message consumers

  • make inbound-command VAL=name

    Creates command line interface handlers

  • make inbound-workflow-temporal VAL=name

    Creates Temporal workflow worker

  • make outbound-database-postgres VAL=name

    Creates PostgreSQL database adapter

  • make outbound-http VAL=name

    Creates HTTP adapter

  • make outbound-message-rabbitmq VAL=name

    Creates RabbitMQ message publisher adapter

  • make outbound-cache-redis VAL=name

    Creates Redis cache adapter

  • make outbound-workflow-temporal VAL=name

    Creates Temporal workflow starter adapter

  • make generate-mocks

    Generates mock implementations from all go:generate directives in registry files

Runtime Commands

  • make build

    Builds the Docker image for the application

  • make http

    Runs the application in HTTP server mode inside Docker

  • make message SUB=upsert_client

    Runs the application in message consumer mode inside Docker

  • make command CMD=publish_upsert_client VAL=name

    Executes a specific command in the application

  • make workflow WFL=upsert_client

    Runs the application in workflow worker mode inside Docker

Development Workflow

A typical development workflow in a Prabogo project follows these steps:

  1. Create Models

    Define your domain models that represent your business entities:

    make model VAL=product
  2. Create Database Migrations

    Define database schema for your models:

    make migration-postgres VAL=product
  3. Implement Domain Logic

    Add your business logic in the domain layer, focusing on the core functionality without external dependencies.

  4. Create Inbound Adapters

    Create adapters for handling incoming requests:

    # For HTTP endpoints
    make inbound-http-fiber VAL=product
    
    # For message consumers
    make inbound-message-rabbitmq VAL=product
    
    # For CLI commands
    make inbound-command VAL=product
    
    # For Temporal workflows
    make inbound-workflow-temporal VAL=product
  5. Create Outbound Adapters

    Create adapters for external dependencies:

    # For database access
    make outbound-database-postgres VAL=product
    
    # For HTTP clients
    make outbound-http VAL=product_api
    
    # For cache
    make outbound-cache-redis VAL=product
    
    # For Temporal workflows
    make outbound-workflow-temporal VAL=product
  6. Write Tests

    Write tests for your domain logic and generate mocks for your ports:

    make generate-mocks
  7. Run the Application

    Start your application in the appropriate mode:

    # Start your application in the appropriate mode:
    make http
    
    # Or run in workflow worker mode
    make workflow WFL=product_workflow

Code Generation

Prabogo provides powerful code generation capabilities to streamline development. When you use the Makefile commands to generate code, Prabogo creates:

  • Appropriate interfaces (ports) in the port directory
  • Implementation files in the adapter directory
  • Necessary registrations in registry files
  • Tests and mocks as needed

This ensures consistency across your codebase and reduces the boilerplate code you need to write.

Testing

Prabogo promotes writing unit tests for your domain logic. The hexagonal architecture makes it easy to test your business logic in isolation by mocking external dependencies.

Running Tests

# Run unit tests
go test -cover ./internal/domain/...

# Generate coverage report
go test -coverprofile=coverage.profile -cover ./internal/domain/...
go tool cover -html coverage.profile -o coverage.html

# Check for intermittent test failures
retry -d 0 -t 100 -u fail -- go test -coverprofile=coverage.profile -cover ./internal/domain/... -count=1

Deployment

Prabogo projects come with Docker support out of the box, making deployment straightforward:

Building a Docker Image

make build

Deployment Options

You can deploy your Prabogo application in various ways:

  • Docker Compose: Ideal for development and simple deployments
  • Kubernetes: For container orchestration in production
  • Cloud Platforms: Deploy to AWS, GCP, or Azure with their respective container services

AI Agents for Development

Prabogo includes three specialized AI agents designed to streamline your development workflow by breaking down complex tasks into manageable steps while following hexagonal architecture principles.

🔍 Clarifier Agent

Prabogo Clarifier

Purpose: Understands and defines problems clearly before any solution is discussed.

Usage: Reference @.github/agents/prabogo_clarifier.agent.md when you need to:

  • Clarify vague requirements
  • Define problem scope and boundaries
  • Identify which Prabogo components are involved
  • Establish measurable success criteria

📋 Task Designer Agent

Prabogo Task Designer

Purpose: Breaks down clarified problems into executable, reviewable tasks following Prabogo's architecture.

Usage: Reference @.github/agents/prabogo_task_designer.agent.md when you need to:

  • Create task breakdowns from problem definitions
  • Plan development work with proper dependencies
  • Design tasks that respect hexagonal architecture boundaries
  • Reference appropriate Makefile targets for code generation

⚡ Executor Agent

Prabogo Executor

Purpose: Executes tasks precisely as designed without changing scope or adding features.

Usage: Reference @.github/agents/prabogo_executor.agent.md when you need to:

  • Implement tasks exactly as specified
  • Follow Definition of Done criteria strictly
  • Execute one task at a time with proper completion validation
  • Maintain focus on requirements without scope creep

Quick Start with Agents

Follow this three-step workflow to ensure clear requirements, proper planning, and precise execution while maintaining Prabogo's architectural integrity:

# 1. Start with Clarifier
@prabogo_clarifier.agent.md "I want to add user authentication"

# 2. Design Tasks (use clarifier output)
@prabogo_task_designer.agent.md

# 3. Execute Tasks (use task designer output)
@prabogo_executor.agent.md
💡 Pro Tip: This three-agent workflow ensures clear requirements, proper planning, and precise execution while maintaining Prabogo's architectural integrity.

Best Practices

Project Structure

Follow the provided directory structure to maintain a clean organization:

  • cmd/: Application entry points
  • internal/: Application code not meant to be imported by other projects
    • domain/: Core business logic and rules
    • port/: Interfaces defining how the application communicates
    • adapter/: Implementations of the ports connecting to external systems
    • model/: Data structures and entities
    • migration/: Database migration scripts
  • utils/: Utility functions and helpers
  • tests/: Test helpers and mocks

Domain-Driven Design

Prabogo works well with DDD principles:

  • Keep business logic in the domain layer
  • Use domain models to represent business entities
  • Define clear boundaries between different domains
  • Use domain events for communication between domains

Testing

  • Write unit tests for all domain logic
  • Use mocks for external dependencies
  • Aim for high test coverage of domain code
  • Consider integration tests for adapter implementations