Back to list
PlosinBen

api-conventions

by PlosinBen

0🍴 0📅 Jan 22, 2026

SKILL.md


name: api-conventions description: API design conventions and patterns for backend development

API Conventions

Guidelines for designing and implementing Backend APIs.

URL Naming

  • Use plural nouns for resources: /trips, /ledgers, /transactions
  • Use kebab-case for multi-word resources: /trip-members
  • Nested resources follow parent: /ledgers/{id}/transactions
  • Use path parameters for IDs: /trips/{id}
  • Use query parameters for filtering: /transactions?category=food

HTTP Methods

MethodUsageResponse Code
GETRetrieve resource(s)200 OK
POSTCreate resource201 Created
PUTUpdate resource (full)200 OK
PATCHUpdate resource (partial)200 OK
DELETEDelete resource200 OK

Request Body

Create Request

type CreateTripRequest struct {
    Name        string     `json:"name" binding:"required,min=1,max=100"`
    Description string     `json:"description"`
    StartDate   *time.Time `json:"start_date"`
}

Update Request

type UpdateTripRequest struct {
    Name        string     `json:"name" binding:"omitempty,min=1,max=100"`
    Description string     `json:"description"`
}

Rules:

  • Create requests: use binding:"required" for mandatory fields
  • Update requests: use binding:"omitempty" for optional fields
  • Use pointers for optional fields that distinguish between "not provided" and "zero value"

Response Format

Success Response

Return the resource directly (no wrapper):

// Single resource
c.JSON(http.StatusOK, trip)

// List of resources
c.JSON(http.StatusOK, trips)

// Created resource
c.JSON(http.StatusCreated, trip)

Error Response

Use consistent error format:

c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid input"})
c.JSON(http.StatusNotFound, gin.H{"error": "Trip not found"})
c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to create trip"})

Delete Response

c.JSON(http.StatusOK, gin.H{"message": "Trip deleted"})

HTTP Status Codes

CodeWhen to Use
200Success (GET, PUT, DELETE)
201Resource created (POST)
400Bad request, validation error
401Unauthorized (not logged in)
403Forbidden (no permission)
404Resource not found
500Internal server error

Handler Structure

type TripHandler struct {
    db *gorm.DB
}

func NewTripHandler(db *gorm.DB) *TripHandler {
    return &TripHandler{db: db}
}

func (h *TripHandler) Create(c *gin.Context) {
    userID := c.MustGet("userID").(uuid.UUID)
    
    // 1. Parse request
    var req CreateTripRequest
    if err := c.ShouldBindJSON(&req); err != nil {
        c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
        return
    }
    
    // 2. Business logic
    trip := &models.Trip{...}
    
    // 3. Database operation
    if err := h.db.Create(trip).Error; err != nil {
        c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to create trip"})
        return
    }
    
    // 4. Return response
    c.JSON(http.StatusCreated, trip)
}

Validation

Use Gin binding tags for validation:

`binding:"required"`           // Field is required
`binding:"required,min=1"`     // Required with min length
`binding:"omitempty,max=100"`  // Optional with max length
`binding:"email"`              // Must be valid email

ID Generation

Use short IDs that automatically grow on collision.

Configuration (internal/utils/id.go)

const (
    DefaultIDLength = 5      // Initial length
    MaxRetries      = 3      // Collisions before growing
    IDCharset       = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
)

Usage

// Generate short ID with collision check
tripID, err := utils.NewShortID(h.db, "trips", "id")

// For internal entities, use UUID
memberID := uuid.New()

ID Type by Resource

ID TypeUsageExample
Short IDURL-exposed (trips, transactions, stores)abc12
UUIDInternal (users, members, items)550e8400-e29b-41d4-a716-446655440000

Authorization

Always verify ownership/access before operations:

func (h *TripHandler) verifyTripAccess(tripID string, userID uuid.UUID) (*models.Trip, error) {
    // Check ownership or membership
}

Summary

AspectConvention
URLPlural nouns, kebab-case
SuccessReturn resource directly
Errorgin.H{"error": "message"}
CreateReturn 201 + created resource
UpdateReturn 200 + updated resource
DeleteReturn 200 + gin.H{"message": "..."}

Score

Total Score

40/100

Based on repository quality metrics

SKILL.md

SKILL.mdファイルが含まれている

+20
LICENSE

ライセンスが設定されている

0/10
説明文

100文字以上の説明がある

0/10
人気

GitHub Stars 100以上

0/15
最近の活動

3ヶ月以内に更新がある

0/10
フォーク

10回以上フォークされている

0/5
Issue管理

オープンIssueが50未満

+5
言語

プログラミング言語が設定されている

+5
タグ

1つ以上のタグが設定されている

0/5

Reviews

💬

Reviews coming soon