News Server Example
A simple CRUD API demonstrating tygor's basic features.
Features Demonstrated
- Type-safe handlers: Go generics for compile-time safety
- Mixed HTTP methods: GET for queries, POST for mutations
- Query parameter decoding: Automatic parsing from URL query strings
- JSON request/response: Seamless serialization
- TypeScript client: Auto-generated types and client code
- Branded types: Custom DateTime type with helper functions
- Type-safe enums: NewsStatus enum with constants
Running the Example
1. Start the server
cd examples/newsserver
go run main.go
Server starts on http://localhost:8080
2. Try the API
List news items:
curl "http://localhost:8080/News/List?limit=10&offset=0"
Create a news item:
curl -X POST http://localhost:8080/News/Create \
-H 'Content-Type: application/json' \
-d '{"title":"Breaking News","body":"Something happened!"}'
3. Run the TypeScript client
The client demonstrates type-safe RPC calls with branded types and enums.
cd client
npm install # or: bun install
bun run index.ts
Note: The server must be running for the client to work.
Client Setup
The TypeScript client uses @tygor/client from npm:
import { createClient } from '@tygor/client';
import { registry } from './src/rpc/manifest';
const client = createClient(
registry,
{ baseUrl: 'http://localhost:8080' }
);
// Type-safe calls
const news = await client.News.List({ limit: 10, offset: 0 });
For Contributors
If you're working on tygor itself, the monorepo setup automatically symlinks @tygor/client to the local /client directory. Just run npm install at the repo root.
Code Structure
examples/newsserver/
├── api/
│ └── types.go # Request/Response types
├── client/
│ ├── index.ts # TypeScript client example
│ ├── package.json # Depends on @tygor/client
│ └── src/rpc/ # Generated types (run main.go to generate)
├── main.go # Server implementation
└── README.md # This file
API Endpoints
GET /News/List
Query parameters:
limit (int32, required)
offset (int32, required)
Returns: Array of news items
POST /News/Create
Request body:
{
"title": "string (required)",
"body": "string (optional)"
}
Returns: Created news item with ID and timestamp
Type Generation
The TypeScript types are generated by running the Go server:
go run main.go
This creates:
client/src/rpc/types.ts - TypeScript interfaces matching Go types
client/src/rpc/manifest.ts - API endpoint metadata and manifest
Key Concepts
Branded Types
The example demonstrates branded types for additional type safety:
// DateTime is a branded string type
const dt: DateTime = DateTime.from("2024-01-01T00:00:00Z");
// Helper functions
DateTime.format(dt); // Formatted string
DateTime.toDate(dt); // JavaScript Date object
DateTime.from(isoString); // Create from string
Type-safe Enums
import { NewsStatusPublished, NewsStatusDraft } from './src/rpc/types';
if (item.status === NewsStatusPublished) {
console.log("Published!");
}
Next Steps
For a more complex example with authentication and authorization, see the blog example.