An open API service indexing awesome lists of open source software.

https://github.com/goliatone/go-command

Go commands
https://github.com/goliatone/go-command

Last synced: 4 months ago
JSON representation

Go commands

Awesome Lists containing this project

README

        

# Go Commands

## Universal Message Handlers

This package implements a pattern for handling messages through commands and queries with type safety and flexible execution strategies.

## Core Components

### Message Interface

Messages carry data and identify their type:

```go
type Message interface {
Type() string
}
```

### Command Pattern

Commands handle operations with side effects:

```go
type Commander[T Message] interface {
Execute(ctx context.Context, msg T) error
}

type CommandFunc[T Message] func(ctx context.Context, msg T) error
```

### Query Pattern

Queries retrieve data without side effects:

```go
type Querier[T Message, R any] interface {
Query(ctx context.Context, msg T) (R, error)
}

type QueryFunc[T Message, R any] func(ctx context.Context, msg T) (R, error)
```

## Execution Strategies

The package provides three execution strategies:

### Runner

Manages retries, timeouts, and execution control:

```go
handler := runner.NewHandler(
runner.WithMaxRetries(3),
runner.WithTimeout(time.Minute),
)

err := runner.RunCommand(ctx, handler, cmd, msg)
```

### Cron

Schedules commands to run periodically:

```go
scheduler := cron.NewScheduler()

id, err := cron.RegisterHandler(scheduler, &MyHandler{}, cron.HandlerOptions{
Expression: "*/5 * * * *",
ExecutionOptions: types.ExecutionOptions{
MaxRetries: 3,
Timeout: time.Minute,
},
})
```

## Error Handling

All strategies use a common error handler:

```go
type ErrorHandler func(error)
```

Configure error handling through options:

```go
WithErrorHandler(func(err error) {
log.Printf("error: %v", err)
})
```

## Message Implementation

Create messages as data carriers:

```go
type CreateUserCommand struct {
Name string
Email string
}

func (c CreateUserCommand) Type() string {
return "create_user"
}
```

## Handler Implementation

Implement handlers either as structs or functions:

```go
// Struct implementation
type UserHandler struct {
db Database
}

func (h *UserHandler) Execute(ctx context.Context, cmd CreateUserCommand) error {
return h.db.CreateUser(ctx, cmd.Name, cmd.Email)
}

// Function implementation
func handleCreateUser(ctx context.Context, cmd CreateUserCommand) error {
// Implementation
}
```

## Design Benefits

- Type-safe message handling through generics
- Consistent error handling across execution strategies
- Context propagation for cancellation and timeouts
- Clear separation between commands and queries
- Flexible execution options (retry, timeout, scheduling)
- Thread-safe operations