lokstra Package

Main entry point for Lokstra framework

Overview

The lokstra package is the main entry point for building Lokstra applications. It provides convenience functions and type aliases for creating routers, apps, and servers.

This package re-exports the most commonly used types and functions from sub-packages, giving you a clean import path for basic application development.

Import Path

import "github.com/primadi/lokstra"

Type Aliases

Server

type Server = server.Server

Server container that manages one or more Apps. See Server documentation for details.

Example:

server := lokstra.NewServer("my-server", app1, app2)

App

type App = app.App

HTTP listener that serves routers. See App documentation for details.

Example:

app := lokstra.NewApp("api", ":8080", router)

Router

type Router = router.Router

HTTP router interface for registering routes and middleware. See Router documentation for details.

Example:

router := lokstra.NewRouter("api")
router.GET("/users", getUsersHandler)

RequestContext

type RequestContext = request.Context

Request context passed to handlers and middleware. See Request Context documentation for details.

Example:

func handler(c *lokstra.RequestContext) error {
    userID := c.Req.Param("id")
    return c.Api.Success(user)
}

HandlerFunc

type HandlerFunc = request.HandlerFunc

Handler function signature for middleware and interceptors.

Signature:

type HandlerFunc func(*Context) error

Example:

func loggingMiddleware(c *lokstra.RequestContext) error {
    log.Printf("Request: %s %s", c.R.Method, c.R.URL.Path)
    return c.Next()
}

Handler

type Handler = request.Handler

Interface for HTTP handlers that can be registered with Router.


Functions

NewRouter

Creates a new Router instance with default engine.

Signature:

func NewRouter(name string) Router

Parameters:

Returns:

Example:

api := lokstra.NewRouter("api-v1")
api.GET("/health", healthCheckHandler)
api.POST("/users", createUserHandler)

app := lokstra.NewApp("api", ":8080", api)

See Also:


NewRouterWithEngine

Creates a new Router instance with specific engine type.

Signature:

func NewRouterWithEngine(name string, engineType string) Router

Parameters:

Returns:

Example:

// Use Go's standard ServeMux engine
router := lokstra.NewRouterWithEngine("api", "servemux")

// Use default Lokstra engine
router := lokstra.NewRouterWithEngine("api", "default")

Engine Types:

Notes:


NewApp

Creates a new App instance with given routers.

Signature:

func NewApp(name string, addr string, routers ...Router) *App

Parameters:

Returns:

Example:

// Single router
apiRouter := lokstra.NewRouter("api")
app := lokstra.NewApp("my-app", ":8080", apiRouter)

// Multiple routers (chained automatically)
apiV1 := lokstra.NewRouter("api-v1")
apiV2 := lokstra.NewRouter("api-v2")
app := lokstra.NewApp("my-app", ":8080", apiV1, apiV2)

// TCP listener
app := lokstra.NewApp("api", ":8080", router)

// Unix socket
app := lokstra.NewApp("api", "unix:/tmp/api.sock", router)

// Specific interface
app := lokstra.NewApp("api", "127.0.0.1:8080", router)

Address Formats:

See Also:


NewAppWithConfig

Creates a new App instance with custom listener configuration.

Signature:

func NewAppWithConfig(name string, addr string, listenerType string, 
    config map[string]any, routers ...Router) *App

Parameters:

Returns:

Example:

// HTTPS with TLS
tlsConfig := map[string]any{
    "cert-file": "/path/to/cert.pem",
    "key-file":  "/path/to/key.pem",
}
app := lokstra.NewAppWithConfig("api", ":443", "tls", tlsConfig, router)

// HTTP/2 Cleartext (h2c)
h2cConfig := map[string]any{
    "read-timeout":  "30s",
    "write-timeout": "30s",
}
app := lokstra.NewAppWithConfig("api", ":8080", "h2c", h2cConfig, router)

// Custom timeouts
config := map[string]any{
    "read-timeout":       "10s",
    "write-timeout":      "10s",
    "idle-timeout":       "60s",
    "read-header-timeout": "5s",
}
app := lokstra.NewAppWithConfig("api", ":8080", "default", config, router)

Listener Types:

Configuration Keys:


NewServer

Creates a new Server instance with given apps.

Signature:

func NewServer(name string, apps ...*App) *Server

Parameters:

Returns:

Example:

// Single app
app := lokstra.NewApp("api", ":8080", router)
server := lokstra.NewServer("my-server", app)

// Multiple apps on different ports
apiApp := lokstra.NewApp("api", ":8080", apiRouter)
adminApp := lokstra.NewApp("admin", ":9000", adminRouter)
server := lokstra.NewServer("my-server", apiApp, adminApp)

// Run server
if err := server.Run(30 * time.Second); err != nil {
    fmt.Println("Error starting server:", err)
}

See Also:


FetchAndCast

Generic HTTP client function for making requests with automatic type casting.

Signature:

func FetchAndCast[T any](client *api_client.ClientRouter, path string, 
    opts ...api_client.FetchOption) (T, error)

Type Parameters:

Parameters:

Returns:

Example:

import (
    "github.com/primadi/lokstra"
    "github.com/primadi/lokstra/api_client"
)

client := api_client.NewClientRouter("https://api.example.com")

// GET request
user, err := lokstra.FetchAndCast[*User](client, "/users/123")
if err != nil {
    log.Fatal(err)
}

// With query parameters
users, err := lokstra.FetchAndCast[[]User](client, "/users",
    api_client.WithMethod("GET"),
    api_client.WithQuery(map[string]string{
        "status": "active",
        "limit":  "10",
    }),
)

// POST request
newUser := &User{Name: "John", Email: "john@example.com"}
created, err := lokstra.FetchAndCast[*User](client, "/users",
    api_client.WithMethod("POST"),
    api_client.WithBody(newUser),
)

// With headers
user, err := lokstra.FetchAndCast[*User](client, "/users/123",
    api_client.WithHeaders(map[string]string{
        "Authorization": "Bearer token123",
        "X-Request-ID":  "req-456",
    }),
)

Supported Types:

See Also:


Complete Example

package main

import (
    "time"
    "github.com/primadi/lokstra"
)

func main() {
    // Create router
    api := lokstra.NewRouter("api")
    
    // Register routes
    api.GET("/health", healthCheck)
    api.GET("/users/:id", getUser)
    api.POST("/users", createUser)
    api.PUT("/users/:id", updateUser)
    api.DELETE("/users/:id", deleteUser)
    
    // Add middleware
    api.Use(loggingMiddleware, authMiddleware)
    
    // Create app
    app := lokstra.NewApp("api", ":8080", api)
    
    // Create server
    server := lokstra.NewServer("my-server", app)
    
    // Run with 30s graceful shutdown
    if err := server.Run(30 * time.Second); err != nil {
        fmt.Println("Error starting server:", err)
    }    
}

func healthCheck(c *lokstra.RequestContext) error {
    return c.Api.Success(map[string]string{"status": "ok"})
}

func getUser(c *lokstra.RequestContext) error {
    id := c.Req.Param("id")
    // ... fetch user from database
    return c.Api.Success(user)
}

func createUser(c *lokstra.RequestContext, input *CreateUserInput) error {
    // Input automatically bound from request body
    // ... create user
    return c.Api.Created(user)
}

func updateUser(c *lokstra.RequestContext, input *UpdateUserInput) error {
    id := c.Req.Param("id")
    // ... update user
    return c.Api.Success(user)
}

func deleteUser(c *lokstra.RequestContext) error {
    id := c.Req.Param("id")
    // ... delete user
    return c.Api.NoContent()
}

func loggingMiddleware(c *lokstra.RequestContext) error {
    log.Printf("%s %s", c.R.Method, c.R.URL.Path)
    return c.Next()
}

func authMiddleware(c *lokstra.RequestContext) error {
    token := c.Req.Header("Authorization")
    if token == "" {
        return c.Api.Unauthorized("Missing authorization token")
    }
    // ... validate token
    return c.Next()
}

See Also