All skills
cxuu avatar

/go-error-handling

@91f0c2e
by Charles Xucxuu/golang-skills165 stars
19

Use when writing Go code that returns, wraps, or handles errors — choosing between sentinel errors, custom types, and fmt.Errorf (%w vs %v), structuring error flow, or deciding whether to log or return. Also use when propagating errors across package boundaries or using errors.Is/As, even if the user doesn't ask about error strategy. Does not cover panic/recover patterns (see go-defensive).

Use this Skill: https://skilld.dev/gh/cxuu/golang-skills/go-error-handling

This session only. Nothing lands on disk.

referencesERROR-TYPES.md

≈892 tokens on demand. Your agent reads this file only when SKILL.md points to it.

Error Types Reference

This reference covers structured error types, sentinel errors, and how to choose the right error type for your use case.


Error Structure

The error-type decision table is in the parent skill (SKILL.md § Error Types). This reference covers: expanded code examples, sentinel errors, error checking with errors.Is/errors.As, and structured error types.

Key considerations:

  • Does the caller need to match the error with errors.Is or errors.As?
  • Is the error message static or does it require runtime values?
  • Exported error variables/types become part of your public API
// No matching needed, static message
func Open() error {
    return errors.New("could not open")
}

// Matching needed, static message - export a sentinel
var ErrCouldNotOpen = errors.New("could not open")

func Open() error {
    return ErrCouldNotOpen
}

// Matching needed, dynamic message - use custom type
type NotFoundError struct {
    File string
}

func (e *NotFoundError) Error() string {
    return fmt.Sprintf("file %q not found", e.File)
}

func Open(file string) error {
    return &NotFoundError{File: file}
}

Sentinel Errors

The simplest structured errors are unparameterized global values:

// Good: Sentinel errors for programmatic checking
var (
    // ErrDuplicate occurs if this animal has already been seen.
    ErrDuplicate = errors.New("duplicate")

    // ErrMarsupial occurs because we're allergic to marsupials.
    ErrMarsupial = errors.New("marsupials are not supported")
)

func process(animal Animal) error {
    switch {
    case seen[animal]:
        return ErrDuplicate
    case marsupial(animal):
        return ErrMarsupial
    }
    seen[animal] = true
    return nil
}

Checking Errors

For direct comparison (when errors are not wrapped):

// Good: Direct comparison with sentinel
switch err := process(an); err {
case ErrDuplicate:
    return fmt.Errorf("feed %q: %v", an, err)
case ErrMarsupial:
    alternate := an.BackupAnimal()
    return handlePet(alternate)
}

When errors may be wrapped, use errors.Is:

// Good: Works with wrapped errors
switch err := process(an); {
case errors.Is(err, ErrDuplicate):
    return fmt.Errorf("feed %q: %v", an, err)
case errors.Is(err, ErrMarsupial):
    // Try to recover...
}

Never match errors based on string content:

// Bad: Fragile string matching
if regexp.MatchString(`duplicate`, err.Error()) {...}
if regexp.MatchString(`marsupial`, err.Error()) {...}

Structured Error Types

For errors needing additional programmatic information, use struct types:

// Good: Structured error with accessible fields
type PathError struct {
    Op   string
    Path string
    Err  error
}

func (e *PathError) Error() string {
    return e.Op + " " + e.Path + ": " + e.Err.Error()
}

func (e *PathError) Unwrap() error { return e.Err }

Callers can use errors.As to extract the structured error:

var pathErr *os.PathError
if errors.As(err, &pathErr) {
    fmt.Println("Failed path:", pathErr.Path)
}

Quick Reference

Scenario Error Type
No matching needed, static message errors.New("message")
No matching needed, dynamic message fmt.Errorf("msg: %v", val)
Matching needed, static message var ErrFoo = errors.New(...)
Matching needed, dynamic message custom struct type
Checking sentinel errors errors.Is(err, ErrFoo)
Extracting structured errors errors.As(err, &target)

Source: SKILL.md on GitHub

No alerts17d5 checks · Risk SAFE
  • Gen Agent Trust Hub17d

    The skill is safe to use. It provides guidelines and a localized utility for verifying Go error handling conventions through AST analysis without any network activity or external dependencies.

  • Socket17d

    No alerts

  • Snyk17d

    Risk: LOW · No issues

  • Runlayer6mo

    1/5 files flagged

  • ZeroLeaks5mo

    Score: 93/100 · 2 sections analyzed

Signed by skilld at 91f0c2e. This ties the file your Agent reads to that commit on GitHub. It does not review the instructions.

Last checked against GitHub 2 months ago.

Steadyupdated 3 months ago
What it can do
Runs commands
All 1 allowed tools
Bash(bash:*)

README badge

README badge for cxuu/golang-skills/go-error-handling