# 📘 Go Specific Coding Rules

### 📘 Rule G001 – Explicitly check ALL errors

- **Objective**: Prevent silent failures and ensure robust error recovery.
- **Details**:
    - In Go, errors are values and must be handled explicitly.
    - Avoid ignoring errors using `_`.
    - Always handle the error before proceeding.
- **Applies to**: Go
- **Tool**: errcheck, golangci-lint
- **Principle**: CODE_QUALITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: critical

**Good example**:
```go
file, err := os.Open("config.json")
if err != nil {
    return fmt.Errorf("failed to open config: %w", err)
}
defer file.Close()
```

**Bad example**:
```go
file, _ := os.Open("config.json") // Error ignored
defer file.Close()
```

### 📘 Rule G002 – Context MUST be the first argument

- **Objective**: Follow Go idiomatic patterns for cancellation and timeouts.
- **Details**:
    - `context.Context` should always be the first parameter of a function, typically named `ctx`.
    - Improving observability and standardizing API signatures.
- **Applies to**: Go
- **Tool**: golangci-lint, contextcheck
- **Principle**: CODE_QUALITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: major

**Good example**:
```go
func (s *Service) FetchUser(ctx context.Context, userID string) (*User, error) {
    return s.repo.Get(ctx, userID)
}
```

**Bad example**:
```go
func (s *Service) FetchUser(userID string, ctx context.Context) (*User, error) {
    return s.repo.Get(ctx, userID)
}
```

### 📘 Rule G003 – Consistent Receiver Naming

- **Objective**: Improve readability and consistency across methods.
- **Details**:
    - Receiver names should be short (1-2 letters) and consistent across all methods of a type.
    - Avoid generic names like `this`, `self`, or `me`.
- **Applies to**: Go
- **Tool**: golangci-lint, stylecheck
- **Principle**: CODE_QUALITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: minor

**Good example**:
```go
func (r *UserRepository) Get(id string) (*User, error) { ... }
func (r *UserRepository) List() ([]*User, error) { ... }
```

**Bad example**:
```go
func (this *UserRepository) Get(id string) (*User, error) { ... }
func (self *UserRepository) List() ([]*User, error) { ... }
```

### 📘 Rule G004 – No panic() in production business logic

- **Objective**: Prevent application crashes and enable graceful recovery.
- **Details**:
    - Avoid using `panic()` for normal error handling.
    - Reserve `panic()` for unrecoverable errors during initialization.
- **Applies to**: Go
- **Tool**: golangci-lint, staticcheck
- **Principle**: RELIABILITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: critical

**Good example**:
```go
func GetUser(id string) (*User, error) {
    user, err := db.Find(id)
    if err != nil {
        return nil, fmt.Errorf("failed to find user: %w", err)
    }
    return user, nil
}
```

**Bad example**:
```go
func GetUser(id string) *User {
    user, err := db.Find(id)
    if err != nil {
        panic(err) // Crash!
    }
    return user
}
```

### 📘 Rule G005 – Goroutine Leak Prevention

- **Objective**: Prevent memory exhaustion and zombie processes.
- **Details**:
    - Always ensure that a goroutine has a clear termination path.
    - Use `context.Context` or a close channel to stop goroutines.
- **Applies to**: Go
- **Tool**: goleak, golangci-lint
- **Principle**: PERFORMANCE, RELIABILITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: major

**Good example**:
```go
func StartWatcher(ctx context.Context, ch chan string) {
    go func() {
        for {
            select {
            case <-ctx.Done():
                return
            case msg, ok := <-ch:
                if !ok { return }
                fmt.Println(msg)
            }
        }
    }()
}
```

### 📘 Rule G006 – Define interfaces at consumer side

- **Objective**: Promote decoupling and simplify testing.
- **Details**:
    - Define interfaces in the package that requires the dependency (consumer side).
    - Do not define interfaces in the same package where the implementation is defined.
- **Applies to**: Go
- **Tool**: Manual Review, Architecture rules
- **Principle**: MAINTAINABILITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: major

**Good example**:
```go
// package handler (consumer)
type AuthProvider interface {
    Login(user, pass string) (string, error)
}
```

### 📘 Rule GN001 – Use Gin binding for validation

- **Objective**: Simplify input handling and ensure consistent validation.
- **Details**:
    - Leverage Gin's `ShouldBindJSON` with struct tags for validation.
    - Avoid manual parsing and validation in handlers.
- **Applies to**: Go, Gin
- **Tool**: Gin, validator
- **Principle**: CODE_QUALITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: major

**Good example**:
```go
type CreateUserRequest struct {
    Email string `json:"email" binding:"required,email"`
}
if err := c.ShouldBindJSON(&req); err != nil {
    c.JSON(400, gin.H{"error": err.Error()})
    return
}
```

### 📘 Rule GN002 – Abort with status for fatal errors

- **Objective**: Ensure middleware chain is interrupted and consistent response is sent.
- **Details**:
    - When a fatal error occurs, use `c.AbortWithStatusJSON` to stop the chain.
    - Prevents security bypasses in middleware.
- **Applies to**: Go, Gin
- **Tool**: Gin
- **Principle**: SECURITY, CODE_QUALITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: major

### 📘 Rule GN003 – Implement Graceful Shutdown

- **Objective**: Prevent data loss and ensure clean connection handling.
- **Details**:
    - Handle termination signals (`SIGINT`, `SIGTERM`) to allow inflight requests to finish.
    - Use `http.Server.Shutdown(ctx)` instead of just `r.Run()`.
- **Applies to**: Go, Gin
- **Tool**: Go Standard Library, Gin
- **Principle**: RELIABILITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: major

### 📘 Rule GN004 – Logical Route Grouping

- **Objective**: Improve code organization and shared middleware management.
- **Details**:
    - Use `RouterGroup` to organize routes logically (e.g., by version or resource).
    - Apply middleware once to the entire group.
- **Applies to**: Go, Gin
- **Tool**: Gin
- **Principle**: MAINTAINABILITY
- **Version**: 1.0
- **Status**: activated
- **Severity**: major
