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
29 changes: 29 additions & 0 deletions .github/workflows/lint.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
name: Lint

on:
push:
branches:
- main
pull_request:
branches:
- '**'

permissions:
contents: read
pull-requests: read

jobs:
golangci-lint:
name: golangci-lint
runs-on: ubuntu-latest
timeout-minutes: 5
steps:
- uses: actions/checkout@v6
- uses: actions/setup-go@v6
with:
go-version: stable
cache: false
- name: golangci-lint
uses: golangci/golangci-lint-action@v9
with:
version: v2.12.2
100 changes: 100 additions & 0 deletions .golangci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
version: "2"

run:
timeout: 5m
modules-download-mode: readonly

linters:
default: standard
enable:
- bodyclose
- copyloopvar
- errorlint
- gocritic
- gosec
- misspell
- nolintlint
- revive
- unconvert
- unparam
- usestdlibvars
- whitespace

settings:
errcheck:
exclude-functions:
- (*github.com/olekukonko/tablewriter.Table).Bulk
- (*github.com/olekukonko/tablewriter.Table).Render
- (*os/exec.Cmd).Wait
- github.com/joho/godotenv.Load
gocritic:
enabled-tags:
- diagnostic
- performance
- style
disabled-checks:
- appendCombine
- commentedOutCode
- hugeParam
- ifElseChain
- importShadow
- paramTypeCombine
- rangeValCopy
- unlambda # test seams use this pattern
- unnamedResult
gosec:
excludes:
- G104 # duplicated by errcheck
- G115 # int->int32 narrowing for proto/API fields is intentional
revive:
rules:
- name: blank-imports
- name: context-as-argument
- name: context-keys-type
- name: error-return
- name: error-strings
- name: error-naming
- name: increment-decrement
- name: range
- name: receiver-naming
- name: redefines-builtin-id
- name: superfluous-else
- name: time-naming
- name: unexported-return
disabled: true # CLI internals return unexported result types
- name: unreachable-code
- name: unused-parameter
disabled: true
- name: var-naming
disabled: true # conflicts with generated proto identifiers (Id, Url, …)

exclusions:
generated: lax
presets:
- comments
- common-false-positives
- legacy
- std-error-handling
rules:
- path: _test\.go
linters:
- errcheck
- gocritic
- gosec
- unparam
- path: internal/cli/pager\.go
linters:
- gosec # G204: PAGER env var is the standard CLI pattern
# int(cmd.Int(...)) idiom from urfave/cli/v3 and int64() casts of proto ints
- linters:
- unconvert
text: unnecessary conversion

formatters:
enable:
- gofumpt
- goimports
settings:
goimports:
local-prefixes:
- github.com/openstatusHQ/cli
3 changes: 2 additions & 1 deletion cmd/docs/docs.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,9 @@ package main
import (
"os"

cmd "github.com/openstatusHQ/cli/internal/cmd"
docs "github.com/urfave/cli-docs/v3"

cmd "github.com/openstatusHQ/cli/internal/cmd"
)

func main() {
Expand Down
4 changes: 3 additions & 1 deletion cmd/openstatus/main.go
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
package main

import (
"log"

"github.com/joho/godotenv"

cmd "github.com/openstatusHQ/cli/internal/cmd"
"log"
)

func main() {
Expand Down
1 change: 1 addition & 0 deletions internal/api/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import (
"time"

"connectrpc.com/connect"

output "github.com/openstatusHQ/cli/internal/cli"
)

Expand Down
7 changes: 4 additions & 3 deletions internal/auth/auth.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,9 @@ import (
"os"
"strings"

"github.com/openstatusHQ/cli/internal/config"
clilib "github.com/urfave/cli/v3"

"github.com/openstatusHQ/cli/internal/config"
)

// ResolveAccessToken extracts the access token from CLI flags or falls back to saved token.
Expand Down Expand Up @@ -40,7 +41,7 @@ func SaveToken(token string) error {
if err != nil {
return fmt.Errorf("failed to determine config directory: %w", err)
}
if err := os.MkdirAll(dir, 0700); err != nil {
if err := os.MkdirAll(dir, 0o700); err != nil {
return fmt.Errorf("failed to create config directory: %w", err)
}

Expand All @@ -64,7 +65,7 @@ func SaveToken(token string) error {
os.Remove(tmpPath)
return fmt.Errorf("failed to close temp file: %w", err)
}
if err := os.Chmod(tmpPath, 0600); err != nil {
if err := os.Chmod(tmpPath, 0o600); err != nil {
os.Remove(tmpPath)
return fmt.Errorf("failed to set token file permissions: %w", err)
}
Expand Down
2 changes: 2 additions & 0 deletions internal/cli/output.go
Original file line number Diff line number Diff line change
Expand Up @@ -26,9 +26,11 @@ func IsDebug() bool { return debugMode.Load() }
func IsTerminal() bool {
return isatty.IsTerminal(os.Stdout.Fd()) || isatty.IsCygwinTerminal(os.Stdout.Fd())
}

func IsStdinTerminal() bool {
return isatty.IsTerminal(os.Stdin.Fd()) || isatty.IsCygwinTerminal(os.Stdin.Fd())
}

func IsStderrTerminal() bool {
return isatty.IsTerminal(os.Stderr.Fd()) || isatty.IsCygwinTerminal(os.Stderr.Fd())
}
Expand Down
3 changes: 2 additions & 1 deletion internal/cmd/app.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@ import (
"os/signal"
"syscall"

"github.com/urfave/cli/v3"

output "github.com/openstatusHQ/cli/internal/cli"
"github.com/openstatusHQ/cli/internal/login"
"github.com/openstatusHQ/cli/internal/maintenance"
Expand All @@ -16,7 +18,6 @@ import (
"github.com/openstatusHQ/cli/internal/statusreport"
"github.com/openstatusHQ/cli/internal/terraform"
"github.com/openstatusHQ/cli/internal/whoami"
"github.com/urfave/cli/v3"
)

func NewApp() *cli.Command {
Expand Down
9 changes: 5 additions & 4 deletions internal/config/config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import (
"testing"

"github.com/google/go-cmp/cmp"

"github.com/openstatusHQ/cli/internal/config"
)

Expand All @@ -24,7 +25,7 @@ func Test_ReadConfig(t *testing.T) {
t.Fatal(err)
}

if _, err := f.Write([]byte(configFile)); err != nil {
if _, err := f.WriteString(configFile); err != nil {
t.Fatal(err)
}
if err := f.Close(); err != nil {
Expand Down Expand Up @@ -60,7 +61,7 @@ func Test_ReadConfig(t *testing.T) {
t.Fatal(err)
}

if _, err := f.Write([]byte("invalid: yaml: content: [")); err != nil {
if _, err := f.WriteString("invalid: yaml: content: ["); err != nil {
t.Fatal(err)
}
if err := f.Close(); err != nil {
Expand All @@ -78,12 +79,12 @@ func Test_ReadConfig_NoStatePollution(t *testing.T) {
dir := t.TempDir()

file1 := filepath.Join(dir, "config1.yaml")
if err := os.WriteFile(file1, []byte("tests:\n ids:\n - 1\n - 2\n - 3\n"), 0600); err != nil {
if err := os.WriteFile(file1, []byte("tests:\n ids:\n - 1\n - 2\n - 3\n"), 0o600); err != nil {
t.Fatal(err)
}

file2 := filepath.Join(dir, "config2.yaml")
if err := os.WriteFile(file2, []byte("tests:\n ids:\n - 4\n - 5\n - 6\n"), 0600); err != nil {
if err := os.WriteFile(file2, []byte("tests:\n ids:\n - 4\n - 5\n - 6\n"), 0o600); err != nil {
t.Fatal(err)
}

Expand Down
5 changes: 1 addition & 4 deletions internal/config/lock.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,17 +17,15 @@ type Lock struct {
type MonitorsLock map[string]Lock

func ReadLockFile(filename string) (MonitorsLock, error) {

var out MonitorsLock
if _, err := os.Stat(filename); errors.Is(err, os.ErrNotExist) {
return MonitorsLock{}, nil
}

file := file.Provider(filename)
var k = koanf.New(".")
k := koanf.New(".")

err := k.Load(file, yaml.Parser())

if err != nil {
return nil, err
}
Expand All @@ -41,5 +39,4 @@ func ReadLockFile(filename string) (MonitorsLock, error) {
}

return out, nil

}
4 changes: 2 additions & 2 deletions internal/config/lock_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import (
"testing"

"github.com/google/go-cmp/cmp"

"github.com/openstatusHQ/cli/internal/config"
)

Expand Down Expand Up @@ -43,7 +44,7 @@ func Test_getMonitorTrigger(t *testing.T) {
}
defer os.Remove(f.Name()) // clean up

if _, err := f.Write([]byte(lockfile)); err != nil {
if _, err := f.WriteString(lockfile); err != nil {
t.Fatal(err)
}
if err := f.Close(); err != nil {
Expand Down Expand Up @@ -89,7 +90,6 @@ func Test_getMonitorTrigger(t *testing.T) {
})

t.Run("No Lock file", func(t *testing.T) {

out, err := config.ReadLockFile("doesnotexist")
if err != nil {
t.Fatal(err)
Expand Down
1 change: 1 addition & 0 deletions internal/config/monitor_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import (
"testing"

"github.com/google/go-cmp/cmp"

"github.com/openstatusHQ/cli/internal/config"
)

Expand Down
10 changes: 5 additions & 5 deletions internal/config/openstatus_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ func Test_ReadOpenStatus(t *testing.T) {
t.Fatal(err)
}

if _, err := f.Write([]byte(openstatusConfig)); err != nil {
if _, err := f.WriteString(openstatusConfig); err != nil {
t.Fatal(err)
}
if err := f.Close(); err != nil {
Expand Down Expand Up @@ -114,7 +114,7 @@ func Test_ReadOpenStatus_FollowRedirects(t *testing.T) {
t.Fatal(err)
}

if _, err := f.Write([]byte(yaml)); err != nil {
if _, err := f.WriteString(yaml); err != nil {
t.Fatal(err)
}
if err := f.Close(); err != nil {
Expand Down Expand Up @@ -157,7 +157,7 @@ func Test_ReadOpenStatus_FollowRedirects(t *testing.T) {
t.Fatal(err)
}

if _, err := f.Write([]byte(yaml)); err != nil {
if _, err := f.WriteString(yaml); err != nil {
t.Fatal(err)
}
if err := f.Close(); err != nil {
Expand Down Expand Up @@ -272,7 +272,7 @@ func Test_ReadOpenStatus_NoStatePollution(t *testing.T) {
request:
method: GET
url: https://a.example.com
`), 0600); err != nil {
`), 0o600); err != nil {
t.Fatal(err)
}

Expand All @@ -288,7 +288,7 @@ func Test_ReadOpenStatus_NoStatePollution(t *testing.T) {
request:
method: POST
url: https://b.example.com
`), 0600); err != nil {
`), 0o600); err != nil {
t.Fatal(err)
}

Expand Down
5 changes: 3 additions & 2 deletions internal/login/login.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,12 @@ import (
"os"
"strings"

"github.com/urfave/cli/v3"
"golang.org/x/term"

"github.com/openstatusHQ/cli/internal/api"
"github.com/openstatusHQ/cli/internal/auth"
"github.com/openstatusHQ/cli/internal/whoami"
"github.com/urfave/cli/v3"
"golang.org/x/term"
)

func LoginCmd() *cli.Command {
Expand Down
3 changes: 2 additions & 1 deletion internal/maintenance/maintenance.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,9 @@ import (
"buf.build/gen/go/openstatus/api/connectrpc/gosimple/openstatus/maintenance/v1/maintenancev1connect"
"connectrpc.com/connect"
"github.com/fatih/color"
"github.com/openstatusHQ/cli/internal/api"
"github.com/urfave/cli/v3"

"github.com/openstatusHQ/cli/internal/api"
)

func NewMaintenanceClient(apiKey string) maintenancev1connect.MaintenanceServiceClient {
Expand Down
Loading
Loading