toolkit

package module
v0.0.0-...-fa578fc Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 23, 2025 License: Apache-2.0 Imports: 5 Imported by: 4

README ΒΆ

LastBackend Toolkit

License GoDev Go Report Card Discord

A comprehensive Go framework for building production-ready microservices with automatic code generation, multi-protocol support, and modular plugin architecture.

LastBackend Toolkit eliminates microservice boilerplate through protobuf-first development, enabling developers to focus on business logic while the framework handles infrastructure concerns.


✨ Key Features

  • πŸ”§ Protobuf-First Development - Define services in .proto files, get everything else generated
  • 🌐 Multi-Protocol Support - gRPC, HTTP REST, WebSocket from single definition
  • πŸ”Œ Rich Plugin Ecosystem - PostgreSQL, Redis, RabbitMQ, and more plugins
  • πŸ—οΈ Automatic Code Generation - Service interfaces, clients, mocks, and infrastructure
  • πŸ’‰ Dependency Injection - Built on Uber FX with automatic plugin registration
  • βš™οΈ Environment Configuration - Hierarchical configuration with validation
  • πŸ§ͺ Testing Ready - Generated mocks and testing utilities
  • πŸ“Š Production Features - Metrics, tracing, health checks, graceful shutdown

πŸš€ Quick Start

Installation
# Install the toolkit CLI
go install github.com/lastbackend/toolkit/cli@latest

# Install protoc plugins
go install google.golang.org/protobuf/cmd/protoc-gen-go@latest
go install google.golang.org/grpc/cmd/protoc-gen-go-grpc@latest
go install github.com/envoyproxy/protoc-gen-validate@latest
go install github.com/lastbackend/toolkit/protoc-gen-toolkit@latest
Create Your First Service
# Generate a new microservice with PostgreSQL and Redis
toolkit init service github.com/yourorg/user-service --postgres-gorm --redis

cd user-service

# Initialize and generate code
make init proto update tidy

# Run the service
go run main.go
Define Your Service

apis/user-service.proto:

syntax = "proto3";
package userservice;

option go_package = "github.com/yourorg/user-service/gen;servicepb";

import "github.com/lastbackend/toolkit/protoc-gen-toolkit/toolkit/options/annotations.proto";
import "google/api/annotations.proto";
import "validate/validate.proto";

// Database plugin
option (toolkit.plugins) = {
  prefix: "pgsql"
  plugin: "postgres_gorm"
};

// Cache plugin  
option (toolkit.plugins) = {
  prefix: "cache"
  plugin: "redis"
};

service UserService {
  option (toolkit.runtime) = {
    servers: [GRPC, HTTP]  // Multi-protocol support
  };
  
  rpc CreateUser(CreateUserRequest) returns (CreateUserResponse) {
    option (google.api.http) = {
      post: "/users"
      body: "*"
    };
  };
  
  rpc GetUser(GetUserRequest) returns (GetUserResponse) {
    option (google.api.http) = {
      get: "/users/{user_id}"
    };
  };
}

message CreateUserRequest {
  string name = 1 [(validate.rules).string.min_len = 1];
  string email = 2 [(validate.rules).string.pattern = "^[^@]+@[^@]+\\.[^@]+$"];
}

message CreateUserResponse {
  string user_id = 1;
  string status = 2;
}

message GetUserRequest {
  string user_id = 1 [(validate.rules).string.uuid = true];
}

message GetUserResponse {
  string user_id = 1;
  string name = 2;
  string email = 3;
  google.protobuf.Timestamp created_at = 4;
}
Generated Code Usage

The toolkit generates everything you need:

main.go:

package main

import (
    "context"
    servicepb "github.com/yourorg/user-service/gen"
    "github.com/yourorg/user-service/internal/server"
    "github.com/lastbackend/toolkit/pkg/runtime"
)

func main() {
    // Service with automatic plugin initialization
    app, err := servicepb.NewUserServiceService("user-service",
        runtime.WithVersion("1.0.0"),
        runtime.WithEnvPrefix("USER_SERVICE"),
    )
    if err != nil {
        panic(err)
    }

    // Register your business logic
    app.Server().GRPC().SetService(server.NewUserServer)

    // Start with gRPC and HTTP servers
    if err := app.Start(context.Background()); err != nil {
        panic(err)
    }
}

internal/server/server.go:

package server

import (
    "context"
    servicepb "github.com/yourorg/user-service/gen"
)

type UserServer struct {
    servicepb.UserServiceRpcServer
    
    app    toolkit.Service
    pgsql  servicepb.PgsqlPlugin  // Auto-injected PostgreSQL
    cache  servicepb.CachePlugin  // Auto-injected Redis
}

// Constructor with automatic dependency injection
func NewUserServer(
    app toolkit.Service,
    pgsql servicepb.PgsqlPlugin,
    cache servicepb.CachePlugin,
) servicepb.UserServiceRpcServer {
    return &UserServer{app: app, pgsql: pgsql, cache: cache}
}

func (s *UserServer) CreateUser(ctx context.Context, req *CreateUserRequest) (*CreateUserResponse, error) {
    // Use plugins directly - they're ready to go
    user := &User{Name: req.Name, Email: req.Email}
    
    // Save to PostgreSQL
    if err := s.pgsql.DB().WithContext(ctx).Create(user).Error; err != nil {
        return nil, err
    }
    
    // Cache the user
    s.cache.Client().Set(ctx, fmt.Sprintf("user:%s", user.ID), user, time.Hour)
    
    return &CreateUserResponse{
        UserId: user.ID,
        Status: "created",
    }, nil
}
Configuration via Environment Variables
# Service configuration
USER_SERVICE_APP_NAME=user-service
USER_SERVICE_ENVIRONMENT=production

# PostgreSQL plugin configuration (auto-parsed)
USER_SERVICE_PGSQL_HOST=localhost
USER_SERVICE_PGSQL_PORT=5432
USER_SERVICE_PGSQL_USERNAME=user
USER_SERVICE_PGSQL_PASSWORD=secret
USER_SERVICE_PGSQL_DATABASE=users_db

# Redis plugin configuration (auto-parsed)
USER_SERVICE_CACHE_HOST=localhost
USER_SERVICE_CACHE_PORT=6379
USER_SERVICE_CACHE_PASSWORD=redispass

πŸ“š Documentation

For AI Agents

πŸ”Œ Plugin Ecosystem

LastBackend Toolkit includes a rich set of plugins from toolkit-plugins:

Plugin Purpose Interface
postgres_gorm PostgreSQL with GORM Plugin.DB() *gorm.DB
postgres_pg PostgreSQL with go-pg Plugin.DB() *pg.DB
redis Redis cache/pub-sub Plugin.Client() redis.Cmdable
rabbitmq Message queue Plugin.Publish/Subscribe
centrifuge Real-time messaging Plugin.Node() *centrifuge.Node
sentry Error monitoring Error tracking integration
Using Plugins
// Declare plugins in your .proto file
option (toolkit.plugins) = {
  prefix: "pgsql"
  plugin: "postgres_gorm"
};

option (toolkit.plugins) = {
  prefix: "cache"  
  plugin: "redis"
};

Plugins are automatically:

  • βœ… Initialized with environment configuration
  • βœ… Registered for dependency injection
  • βœ… Managed through lifecycle hooks
  • βœ… Available as typed interfaces in your code

πŸ—οΈ Examples

Explore real-world examples in the examples/ directory:

πŸ”„ Multi-Protocol Support

Define once, serve everywhere:

service UserService {
  option (toolkit.runtime) = {
    servers: [GRPC, HTTP, WEBSOCKET]  // All protocols from one definition
  };
  
  rpc GetUser(GetUserRequest) returns (GetUserResponse) {
    // Available as gRPC call
    option (google.api.http) = {
      get: "/users/{user_id}"  // Also as HTTP GET
    };
  };
  
  rpc StreamUsers(StreamRequest) returns (StreamResponse) {
    option (toolkit.route).websocket = true;  // And WebSocket
  };
}

Your service automatically provides:

  • πŸ”§ gRPC - High-performance RPC
  • 🌐 HTTP REST - Web-friendly APIs
  • ⚑ WebSocket - Real-time communication
  • πŸ”€ Proxying - HTTP-to-gRPC and WebSocket-to-gRPC

πŸ§ͺ Testing Support

Generated testing utilities:

// Generated mocks for all interfaces
mockPlugin := new(tests.MockPgsqlPlugin)
mockPlugin.On("DB").Return(mockDB)

// Generated client for integration tests
client := servicepb.NewUserServiceClient(conn)
resp, err := client.GetUser(ctx, &GetUserRequest{UserId: "123"})

🏒 Production Ready

Built-in production features:

  • πŸ“Š Metrics - Prometheus integration
  • πŸ” Tracing - Distributed tracing support
  • πŸ₯ Health Checks - Kubernetes-ready health endpoints
  • πŸ›‘οΈ Graceful Shutdown - Clean resource cleanup
  • βš™οΈ Configuration Validation - Environment variable validation
  • πŸ“ Structured Logging - Contextual logging throughout

🀝 Contributing

We welcome contributions! Please see:

Development
# Clone the repository
git clone https://github.com/lastbackend/toolkit.git
cd toolkit

# Install dependencies
make init

# Run tests
make test

# Generate examples
make examples

πŸ“„ License

This project is licensed under the Apache 2.0 License - see the LICENSE file for details.

🌟 Why LastBackend Toolkit?

Before:

// Hundreds of lines of boilerplate
server := grpc.NewServer()
mux := http.NewServeMux()
db, _ := gorm.Open(postgres.Open(dsn))
redis := redis.NewClient(&redis.Options{})
// ... setup middleware, routing, health checks, etc.

After:

// Just describe what you want
option (toolkit.plugins) = {
  prefix: "pgsql" 
  plugin: "postgres_gorm"
};

service UserService {
  option (toolkit.runtime) = {
    servers: [GRPC, HTTP]
  };
  // ... your business logic
}

Focus on what matters: Your business logic, not infrastructure setup.


Get Started β€’ Examples β€’ Discord β€’ Documentation

Made with ❀️ by the LastBackend team

Documentation ΒΆ

Index ΒΆ

Constants ΒΆ

This section is empty.

Variables ΒΆ

This section is empty.

Functions ΒΆ

This section is empty.

Types ΒΆ

type Client ΒΆ

type Client interface {
	GRPC() client.GRPCClient
	HTTP() client.HTTPClient
}

type Config ΒΆ

type Config any

type Package ΒΆ

type Package any

type PackageItem ΒΆ

type PackageItem struct {
	Index  int
	Source any
}

type Plugin ΒΆ

type Plugin any

type Server ΒΆ

type Server interface {
	HTTP() server.HTTPServer
	GRPC() server.GRPCServer

	HTTPGet(name string) server.HTTPServer
	HTTPNew(name string, options *server.HTTPServerOptions) server.HTTPServer

	GRPCGet(name string) server.GRPCServer
	GRPCNew(name string, options *server.GRPCServerOptions) server.GRPCServer
}

type Service ΒΆ

type Service interface {
	Meta() *meta.Meta

	Log() logger.Logger
	Client() Client
	Server() Server

	RegisterConfig(config ...any) error
	RegisterPlugin(constructor ...any)
	RegisterPackage(constructor ...any)

	Start(ctx context.Context) error
	Stop(ctx context.Context, err error)

	RegisterOnStartHook(...func(ctx context.Context) error)
	RegisterOnStartSyncHook(...func(ctx context.Context) error)

	RegisterOnStopHook(...func(ctx context.Context) error)
	RegisterOnStopSyncHook(...func(ctx context.Context) error)
}

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL