Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 22 additions & 0 deletions pkg/linters/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ This package currently provides custom Go analyzers in the following subpackages
- `fprintlnsprintf` — reports `fmt.Fprintln(..., fmt.Sprintf(...))` patterns and recommends direct formatting calls.
- `hardcodedfilepath` — reports hard-coded file path string literals that match known path constants or should be extracted into named constants; also annotates paths that appear in log/print calls.
- `httpnoctx` — reports HTTP client and package-level HTTP calls that do not accept a `context.Context`.
- `httprespbodyclose` — reports HTTP responses whose `Body.Close()` call is missing or not deferred.
- `httpstatuscode` — reports raw HTTP status-code integer literals that should use `net/http` named constants.
- `jsonmarshalignoredeerror` — reports `json.Marshal` and `json.Unmarshal` calls where the error return is discarded.
- `largefunc` — reports function bodies that exceed a configurable line-count threshold.
Expand All @@ -36,6 +37,7 @@ This package currently provides custom Go analyzers in the following subpackages
- `sortslice` — reports `sort.Slice` / `sort.SliceStable` calls that should use `slices.SortFunc` / `slices.SortStableFunc`.
- `sprintferrdot` — reports redundant `.Error()` calls on error values passed to `fmt` format functions where the fmt package calls `.Error()` automatically.
- `sprintferrorsnew` — reports `errors.New(fmt.Sprintf(...))` calls that should use `fmt.Errorf` instead.
- `sprintfint` — reports `fmt.Sprintf("%d", ...)` and related conversions that should use `strconv` helpers.
- `ssljson` — validates `ssl.json` skill artifacts found in `.github/skills/` against the SSL spec (enum membership, graph integrity, transition targets, entry pointer validity).
- `strconvparseignorederror` — reports `strconv` parsing calls (`Atoi`, `ParseInt`, etc.) where the error return is discarded with `_`.
- `stringreplaceminusone` — reports `strings.Replace` calls whose `n` argument is `-1`, which should use the more readable `strings.ReplaceAll`.
Expand Down Expand Up @@ -66,6 +68,7 @@ This package currently provides custom Go analyzers in the following subpackages
| `fprintlnsprintf` | Custom `go/analysis` analyzer that flags `fmt.Fprintln(..., fmt.Sprintf(...))` patterns |
| `hardcodedfilepath` | Custom `go/analysis` analyzer that flags hard-coded file path string literals that match known path constants or should be extracted as named constants; annotates paths in log/print calls |
| `httpnoctx` | Custom `go/analysis` analyzer that flags HTTP calls that do not accept a `context.Context` |
| `httprespbodyclose` | Custom `go/analysis` analyzer that flags HTTP response bodies that are not closed (or not deferred) |
| `httpstatuscode` | Custom `go/analysis` analyzer that flags raw HTTP status-code integer literals that should use `net/http` named constants |
| `jsonmarshalignoredeerror` | Custom `go/analysis` analyzer that flags `json.Marshal`/`json.Unmarshal` calls where the error return is discarded |
| `largefunc` | Custom `go/analysis` analyzer that flags large functions with actionable diagnostics |
Expand All @@ -82,6 +85,7 @@ This package currently provides custom Go analyzers in the following subpackages
| `sortslice` | Custom `go/analysis` analyzer that flags `sort.Slice` / `sort.SliceStable` calls that should use `slices.SortFunc` / `slices.SortStableFunc` |
| `sprintferrdot` | Custom `go/analysis` analyzer that flags redundant `.Error()` calls on error values passed to `fmt` format functions |
| `sprintferrorsnew` | Custom `go/analysis` analyzer that flags `errors.New(fmt.Sprintf(...))` calls that should use `fmt.Errorf` instead |
| `sprintfint` | Custom `go/analysis` analyzer that flags `fmt.Sprintf` integer conversions that should use `strconv` helpers |
| `ssljson` | Custom `go/analysis` analyzer that validates SSL JSON skill artifacts in `.github/skills/` |
| `strconvparseignorederror` | Custom `go/analysis` analyzer that flags `strconv` parsing calls where the error return is discarded with `_` |
| `stringreplaceminusone` | Custom `go/analysis` analyzer that flags `strings.Replace` calls with `n=-1` that should use `strings.ReplaceAll` |
Expand All @@ -102,13 +106,17 @@ This package currently provides custom Go analyzers in the following subpackages

```go
import (
"github.com/github/gh-aw/pkg/linters/deferinloop"
"github.com/github/gh-aw/pkg/linters/errorfwrapv"
"github.com/github/gh-aw/pkg/linters/ctxbackground"
"github.com/github/gh-aw/pkg/linters/excessivefuncparams"
"github.com/github/gh-aw/pkg/linters/errormessage"
"github.com/github/gh-aw/pkg/linters/errstringmatch"
"github.com/github/gh-aw/pkg/linters/execcommandwithoutcontext"
"github.com/github/gh-aw/pkg/linters/fileclosenotdeferred"
"github.com/github/gh-aw/pkg/linters/hardcodedfilepath"
"github.com/github/gh-aw/pkg/linters/httpnoctx"
"github.com/github/gh-aw/pkg/linters/httprespbodyclose"
"github.com/github/gh-aw/pkg/linters/httpstatuscode"
"github.com/github/gh-aw/pkg/linters/largefunc"
"github.com/github/gh-aw/pkg/linters/lenstringzero"
Expand All @@ -119,17 +127,23 @@ import (
"github.com/github/gh-aw/pkg/linters/rawloginlib"
"github.com/github/gh-aw/pkg/linters/regexpcompileinfunction"
"github.com/github/gh-aw/pkg/linters/sortslice"
"github.com/github/gh-aw/pkg/linters/sprintfint"
"github.com/github/gh-aw/pkg/linters/ssljson"
"github.com/github/gh-aw/pkg/linters/timesleepnocontext"
)

// Use with multichecker, singlechecker, or custom go/analysis driver.
_ = ctxbackground.Analyzer
_ = deferinloop.Analyzer
_ = errorfwrapv.Analyzer
_ = excessivefuncparams.Analyzer
_ = errormessage.Analyzer
_ = errstringmatch.Analyzer
_ = execcommandwithoutcontext.Analyzer
_ = fileclosenotdeferred.Analyzer
_ = hardcodedfilepath.Analyzer
_ = httpnoctx.Analyzer
_ = httprespbodyclose.Analyzer
_ = httpstatuscode.Analyzer
_ = largefunc.Analyzer
_ = lenstringzero.Analyzer
Expand All @@ -140,14 +154,18 @@ _ = panicinlibrarycode.Analyzer
_ = rawloginlib.Analyzer
_ = regexpcompileinfunction.Analyzer
_ = sortslice.Analyzer
_ = sprintfint.Analyzer
_ = ssljson.Analyzer
_ = timesleepnocontext.Analyzer
```

## Dependencies

**Internal**:
- `github.com/github/gh-aw/pkg/linters/contextcancelnotdeferred` — context-cancel-not-deferred analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/ctxbackground` — context-background analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/deferinloop` — defer-in-loop analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/errorfwrapv` — fmt-errorf-wrap-v analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/errormessage` — error-message analyzer subpackage (also re-exported as `ErrorMessageAnalyzer`)
- `github.com/github/gh-aw/pkg/linters/errortypeassertion` — error-type-assertion analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/errstringmatch` — err-string-match analyzer subpackage
Expand All @@ -157,6 +175,8 @@ _ = ssljson.Analyzer
- `github.com/github/gh-aw/pkg/linters/fmterrorfnoverbs` — fmt-errorf-no-verbs analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/fprintlnsprintf` — fprintln-sprintf analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/hardcodedfilepath` — hard-coded-file-path analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/httpnoctx` — HTTP-no-context analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/httprespbodyclose` — HTTP-response-body-close analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/httpstatuscode` — http-status-code analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/jsonmarshalignoredeerror` — json-marshal-ignored-error analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/largefunc` — large-func analyzer subpackage
Expand All @@ -173,10 +193,12 @@ _ = ssljson.Analyzer
- `github.com/github/gh-aw/pkg/linters/sortslice` — sort-slice analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/sprintferrdot` — sprintf-err-dot analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/sprintferrorsnew` — sprintf-errors-new analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/sprintfint` — sprintf-int analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/ssljson` — ssl-json analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/strconvparseignorederror` — strconv-parse-ignored-error analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/stringreplaceminusone` — string-replace-minus-one analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/timeafterleak` — time-after-leak analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/timesleepnocontext` — time-sleep-no-context analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/tolowerequalfold` — to-lower-equal-fold analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/uncheckedtypeassertion` — unchecked-type-assertion analyzer subpackage
- `github.com/github/gh-aw/pkg/linters/wgdonenotdeferred` — wg-done-not-deferred analyzer subpackage
Expand Down
52 changes: 52 additions & 0 deletions pkg/modelsdev/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
# modelsdev Package

The `modelsdev` package provides model pricing lookup backed by the public `models.dev` catalog.

## Overview

This package downloads and parses `https://models.dev/catalog.json`, normalizes provider/model identifiers, and exposes per-token pricing for callers that need cost-aware behavior.

The catalog is loaded once per process via a singleton cache (`syncutil.OnceLoader`) to avoid repeated network fetches.

## Public API

### Functions

| Function | Signature | Description |
|----------|-----------|-------------|
| `FindPricing` | `func(ctx context.Context, provider, model string) (map[string]float64, bool)` | Returns normalized per-token pricing for a provider/model pair. Falls back to cross-provider matching when provider lookup fails. Returns `(nil, false)` when no pricing is available |
Comment on lines +15 to +17

## Usage Examples

```go
import "github.com/github/gh-aw/pkg/modelsdev"

pricing, ok := modelsdev.FindPricing(ctx, "github", "gpt-4.1")
Comment on lines +22 to +24
if !ok {
// pricing unavailable
return
}

inputUSD := pricing["input"] // per token
outputUSD := pricing["output"] // per token
_ = inputUSD
_ = outputUSD
```

## Dependencies

**Internal**:
- `github.com/github/gh-aw/pkg/logger` — debug logging
- `github.com/github/gh-aw/pkg/syncutil` — one-time catalog load/cache primitive

## Design Notes

- Provider aliases such as `github`, `copilot`, and `github_models` are normalized to `github-copilot`.
- Comparable model matching normalizes separators (`.` and `_` to `-`) to improve lookup robustness.
- Numeric catalog costs are interpreted as per-million-token values and converted to per-token units.
- String catalog costs are treated as already normalized per-token values.
- Network or parsing failures degrade gracefully to an empty cache so callers can continue without pricing data.

---

*This specification is automatically maintained by the [spec-extractor](../../.github/workflows/spec-extractor.md) workflow.*