vandor add
Add domain layer components to your Vandor project
vandor add
Add bounded contexts, domains, use cases, services, and value objects to your project.
Synopsis
vandor add <component-type> <args...> [flags]Description
The vandor add command creates domain layer components following Domain-Driven Design principles. Every subcommand uses space-separated positional arguments -- not slash notation. After adding a component, Vandor automatically triggers a sync to keep your wiring code up to date.
Auto-sync on add. You do not need to manually run vandor sync after every vandor add. The add command takes care of it. If you want to skip the automatic sync, you can use the --tidy never flag.
Subcommands
context Add a new bounded context
domain Add a domain to an existing context
usecase Add a use case to a context
service Add a domain service to a context
valueobject Add a value object to a contextvandor add context
Create a new bounded context. A context is a self-contained area of your application that groups related domains, use cases, and services together.
Usage
vandor add context <name> [flags]Flags
--minimal Create a minimal context (fewer generated files)
--full Create a full context with all directories (default)
--with-builder Include a builder pattern for the context module
--without-read-repo Skip generating the read repository port
--tidy auto|always|never When to run go mod tidy (default: auto)Examples
# Create a context with default settings
vandor add context order
# Create a minimal context
vandor add context notification --minimal
# Full context with builder pattern
vandor add context identity --full --with-builder
# Context without read repository
vandor add context analytics --without-read-repoWhat Gets Created
internal/context/order/
core/
domain/ Domain models
port/ Port interfaces (repository, services)
service/ Domain services
usecase/ Use cases
module.go FX module wiring (your code)
module_gen.go Generated FX module wiring (auto-generated)vandor add domain
Add a domain model to an existing context. Domains represent your core business entities -- the things your application manages and the rules around them.
Usage
vandor add domain <context> <name> [flags]Note the space-separated arguments: the context name comes first, then the domain name.
Flags
--with-builder Include a builder pattern for the domainExamples
# Add an Order domain to the order context
vandor add domain order Order
# Add a User domain to the identity context
vandor add domain identity User
# Add a domain with builder pattern
vandor add domain order Order --with-builder
# Add multiple domains to the same context
vandor add domain catalog Product
vandor add domain catalog CategoryWhat Gets Created
internal/context/order/core/domain/
order.go Domain model with fields and constructorIf --with-builder is used, a builder file is also created for fluent construction of the domain object.
Domains are business capabilities, not database tables. Do not create a domain for every table in your database. Instead, think about what business concepts your application manages. An order context might contain Order, OrderItem, and ShippingAddress domains -- all part of the same business capability.
vandor add usecase
Add a use case to a context. Use cases represent application-level operations -- the things your users can do. They orchestrate domain logic and coordinate between different parts of your system.
Usage
vandor add usecase <context> <name>Examples
# Add a CreateOrder use case to the order context
vandor add usecase order CreateOrder
# Add more use cases
vandor add usecase order CancelOrder
vandor add usecase order GetOrderByID
vandor add usecase identity RegisterUser
vandor add usecase identity AuthenticateUserWhat Gets Created
internal/context/order/usecase/
create_order.go Use case implementation with Input/Output typesGenerated Code Structure
The generated use case follows a consistent pattern:
package usecase
import "context"
type CreateOrderInput struct {
// Define your input fields here
}
type CreateOrderOutput struct {
// Define your output fields here
}
type CreateOrder struct {
// Inject dependencies via constructor
}
func NewCreateOrder(/* dependencies */) *CreateOrder {
return &CreateOrder{}
}
func (uc *CreateOrder) Execute(ctx context.Context, input CreateOrderInput) (*CreateOrderOutput, error) {
// Implement your business logic here
return &CreateOrderOutput{}, nil
}vandor add service
Add a domain service to a context. Domain services handle business logic that does not naturally belong to a single domain entity -- for example, pricing calculations that depend on multiple domains or cross-cutting validation rules.
Usage
vandor add service <context> <name>Examples
# Add a PriceCalculator service to the order context
vandor add service order PriceCalculator
# Add other services
vandor add service order ShippingCalculator
vandor add service order InventoryChecker
vandor add service identity PasswordHasherWhat Gets Created
internal/context/order/core/service/
price_calculator.go Service implementationGenerated Code Structure
package service
import "context"
type PriceCalculator struct {
// Dependencies
}
func NewPriceCalculator(/* dependencies */) *PriceCalculator {
return &PriceCalculator{}
}
func (s *PriceCalculator) Calculate(ctx context.Context /* params */) (float64, error) {
// Domain logic here
return 0.0, nil
}vandor add valueobject
Add a value object to a context. Value objects are immutable types that represent concepts in your domain -- things like status codes, currency amounts, email addresses, or any typed constant.
Usage
vandor add valueobject <context> <name> [flags]Flags
--kind string Underlying Go type: string, int, float64, bool, time (default: string)
--enum A,B,C Comma-separated enum values for this value objectExamples
# String-based enum value object
vandor add valueobject order Status --kind string --enum pending,processing,completed,cancelled
# Integer-based value object
vandor add valueobject order Priority --kind int --enum 1,2,3
# Boolean value object
vandor add valueobject identity IsVerified --kind bool
# Simple string value object without enum
vandor add valueobject identity Email --kind string
# Time-based value object
vandor add valueobject order ShipByDate --kind timeWhat Gets Created
For a string enum value object:
internal/context/order/core/domain/
order_status.go Value object with enum values and validationGenerated Code (String Enum Example)
package domain
type OrderStatus string
const (
OrderStatusPending OrderStatus = "pending"
OrderStatusProcessing OrderStatus = "processing"
OrderStatusCompleted OrderStatus = "completed"
OrderStatusCancelled OrderStatus = "cancelled"
)
func (s OrderStatus) IsValid() bool {
switch s {
case OrderStatusPending, OrderStatusProcessing, OrderStatusCompleted, OrderStatusCancelled:
return true
default:
return false
}
}
func (s OrderStatus) String() string {
return string(s)
}Component Naming Conventions
| Component | Naming Style | Example |
|---|---|---|
| Context | lowercase | order, identity, catalog |
| Domain | PascalCase | Order, User, Product |
| Use case | PascalCase | CreateOrder, RegisterUser |
| Service | PascalCase | PriceCalculator, PasswordHasher |
| Value object | PascalCase | Status, PaymentMethod, Email |
The --tidy Flag
The --tidy flag controls when go mod tidy runs after adding a component:
- auto (default): Runs
go mod tidywhen it appears necessary. - always: Always runs
go mod tidy. - never: Skips
go mod tidy.
Workflow Example
Here is a typical workflow for building out a new feature area:
# 1. Create the bounded context
vandor add context order
# 2. Add domain models
vandor add domain order Order --with-builder
vandor add domain order OrderItem
# 3. Add value objects
vandor add valueobject order Status --kind string --enum pending,processing,completed,cancelled
vandor add valueobject order PaymentMethod --kind string --enum credit_card,debit_card,bank_transfer
# 4. Add domain services
vandor add service order PriceCalculator
# 5. Add use cases
vandor add usecase order CreateOrder
vandor add usecase order CancelOrder
vandor add usecase order GetOrderByID
# 6. Install infrastructure packages
vandor vpkg add @official/http-humachi
vandor vpkg add @official/entgo
# 7. Start developing
vandor dev:appTroubleshooting
Context not found
Error: context "catalog" not foundYou need to create the context before adding components to it:
vandor add context catalog
vandor add domain catalog ProductInvalid naming
Error: invalid component name "create-order"Use PascalCase for domains, use cases, services, and value objects. Use lowercase for context names.
Domain already exists
Error: domain "Order" already exists in context "order"Choose a different name, or remove the existing domain file manually if you want to recreate it.
Related Commands
- vandor sync - Regenerate wiring code (auto-triggered by add)
- vandor vpkg - Install infrastructure packages
- vandor new - Create a new project