A wizard-style CLI tool for setting up nullplatform infrastructure with Terraform file generation.
- Interactive wizard interface with keyboard navigation
- YAML-based question configuration with conditional logic
- Multiple question types: select, multi-select, text input, and more
- Configuration management with local storage and environment variable overrides
- Review and edit functionality before generation
- Automatic Terraform file generation
- Support for multiple setup wizards (cluster, organization, scope)
- Go 1.21 or higher
- Terminal with color support
# Clone the repository
git clone https://github.com/nullplatform/nullplatform-setup-cli.git
cd nullplatform-setup-cli
# Install dependencies
go mod download
# Build the application
go build -o nullplatform-setup .The application requires two pieces of configuration:
- Organization ID - Your nullplatform organization ID
- API Key - Your nullplatform API key
-
Environment variables:
NP_ORGANIZATION_IDNP_API_KEY
-
Local configuration file:
- Stored in
~/.np/nullplatform-setup-cli/config.json
- Stored in
If no configuration is found, the application will prompt you to set it up on first run.
export NP_ORGANIZATION_ID="your-org-id"
export NP_API_KEY="your-api-key"
./nullplatform-setup./nullplatform-setupThe main menu presents three wizard options:
- Setup my organization on nullplatform - Configure organization settings
- Setup a cluster (K8s) - Configure a Kubernetes cluster with full options
- Setup a scope - Configure an application scope
↑/↓orj/k- Navigate through optionsEnter- Select wizardC- Change organization/API key configurationQ- Quit
↑/↓orj/k- Navigate through optionsSpace- Toggle selection (for multi-select questions)Enter- Confirm selection and move to next questionEsc- Go back to previous questionCtrl+C- Cancel and return to main menu
Enter- Generate Terraform filesE- Edit (return to first question)X- Cancel
Questions are defined in YAML format in the schemas/wizards.yaml file.
wizards:
- id: setup-cluster
name: Setup a cluster (K8s)
description: Configure a Kubernetes cluster
questions:
- id: cluster_provider
type: select
prompt: "Select the cluster provider:"
required: true
options:
- value: aws-eks
label: AWS EKS
- value: azure-aks
label: Azure AKS
- id: dns_provider
type: select
prompt: "Which DNS provider will be used?"
required: true
options:
- value: route53
label: AWS Route 53
condition:
question: cluster_provider
equals: aws-eks
- value: cloudflare
label: Cloudflareselect- Single selection from optionsmulti-select- Multiple selections from optionsinput- Text inputmultiple-input- Multiple text inputs (e.g., for forms)confirm- Yes/No confirmation
Options and questions can have conditions based on previous answers:
condition:
question: cluster_provider
equals: aws-eks # Show only if cluster_provider equals "aws-eks"Or:
condition:
question: cluster_provider
oneOf: [aws-eks, aws-openshift] # Show if value is one of theseThe application generates Terraform files in a timestamped directory:
setup-a-cluster-k8s-20240115-143022/
├── main.tf
├── variables.tf
└── providers.tf
main.tf- Main resource definitions based on your answersvariables.tf- Variable definitions including organization IDproviders.tf- Provider configuration for nullplatform and other providers
.
├── main.go # Application entry point
├── go.mod # Go module definition
├── schemas/
│ └── wizards.yaml # Question definitions
├── internal/
│ ├── app/
│ │ └── app.go # Application orchestration
│ ├── config/
│ │ └── config.go # Configuration management
│ ├── schema/
│ │ └── schema.go # Schema loading and validation
│ ├── ui/
│ │ ├── config_setup.go # Configuration setup screen
│ │ ├── main_menu.go # Main menu screen
│ │ └── wizard.go # Wizard flow implementation
│ └── generator/
│ └── generator.go # Terraform file generation
└── README.md
- Add a new wizard definition to
schemas/wizards.yaml - Implement the Terraform generation logic in
internal/generator/generator.go - The wizard will automatically appear in the main menu
To add custom validation for organization ID and API key:
Edit internal/config/config.go in the IsValid() method:
func (c *Config) IsValid() (bool, error) {
// Add your validation logic here
// Example: Call an API to verify credentials
if err := validateWithAPI(c.OrganizationID, c.APIKey); err != nil {
return false, fmt.Errorf("invalid credentials: %w", err)
}
return true, nil
}- Bubble Tea - Terminal UI framework
- Lip Gloss - Terminal styling
- yaml.v3 - YAML parsing
MIT
Contributions are welcome! Please feel free to submit a Pull Request.