diff --git a/.github/dependabot.yml b/.github/dependabot.yml index 32efae2c4..ef321ab96 100644 --- a/.github/dependabot.yml +++ b/.github/dependabot.yml @@ -1,12 +1,16 @@ -# To get started with Dependabot version updates, you'll need to specify which -# package ecosystems to update and where the package manifests are located. -# Please see the documentation for all configuration options: -# https://help.github.com/github/administering-a-repository/configuration-options-for-dependency-updates - version: 2 updates: - - package-ecosystem: "gomod" # See documentation for possible values - directory: "/" # Location of package manifests + - package-ecosystem: "gomod" + directory: "/" + schedule: + interval: "daily" + target-branch: "develop/v3" + labels: + - "go" + - "dependencies" + - "dependabot" + - package-ecosystem: "gomod" + directory: "/" schedule: interval: "daily" target-branch: "develop/v2" @@ -14,8 +18,8 @@ updates: - "go" - "dependencies" - "dependabot" - - package-ecosystem: "gomod" # See documentation for possible values - directory: "/" # Location of package manifests + - package-ecosystem: "gomod" + directory: "/" schedule: interval: "daily" target-branch: "develop/v1" @@ -23,6 +27,11 @@ updates: - "go" - "dependencies" - "dependabot" + - package-ecosystem: "github-actions" + directory: "/" + schedule: + interval: "daily" + target-branch: "develop/v3" - package-ecosystem: "github-actions" directory: "/" schedule: diff --git a/.github/workflows/assign-issue.yml b/.github/workflows/assign-issue.yml index c0f1a5534..2a2de0602 100644 --- a/.github/workflows/assign-issue.yml +++ b/.github/workflows/assign-issue.yml @@ -8,6 +8,6 @@ jobs: runs-on: ubuntu-latest steps: - name: 'Auto-assign issue' - uses: pozil/auto-assign-issue@v2 + uses: pozil/auto-assign-issue@c5bca5027e680b9e8411b826d16947afd8c76b32 # v2.0.0 with: assignees: lestrrat diff --git a/.github/workflows/assign-pr.yml b/.github/workflows/assign-pr.yml index 3dcb2ed63..7afe436ac 100644 --- a/.github/workflows/assign-pr.yml +++ b/.github/workflows/assign-pr.yml @@ -7,6 +7,6 @@ jobs: add-reviews: runs-on: ubuntu-latest steps: - - uses: kentaro-m/auto-assign-action@v2.0.0 + - uses: kentaro-m/auto-assign-action@f4648c0a9fdb753479e9e75fc251f507ce17bb7e # v2.0.0 with: configuration-path: .github/auto-assign-pr.yml diff --git a/.github/workflows/autodoc.yml b/.github/workflows/autodoc.yml index 4e747f824..cde98b7f4 100644 --- a/.github/workflows/autodoc.yml +++ b/.github/workflows/autodoc.yml @@ -13,7 +13,7 @@ jobs: if: github.event.pull_request.merged == true steps: - name: Checkout repository - uses: actions/checkout@v4 + uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 - name: Process markdown files run: | find . -name '*.md' | xargs perl tools/autodoc.pl diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index c56f59867..88684e141 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -11,13 +11,13 @@ jobs: strategy: matrix: go_tags: [ 'stdlib', 'goccy', 'es256k', 'secp256k1-pem', 'asmbase64', 'alltags'] - go: [ '1.22', '1.21', '1.20' ] + go: [ '1.23', '1.22', '1.21' ] name: "Test [ Go ${{ matrix.go }} / Tags ${{ matrix.go_tags }} ]" steps: - name: Checkout repository - uses: actions/checkout@v4 + uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 - name: Cache Go modules - uses: actions/cache@v4 + uses: actions/cache@0c45773b623bea8c8e75f6c82b208c3cf94ea4f9 # v4.0.2 with: path: | ~/go/pkg/mod @@ -27,20 +27,10 @@ jobs: restore-keys: | ${{ runner.os }}-go- - name: Install Go stable version - if: matrix.go != 'tip' - uses: actions/setup-go@v5 + uses: actions/setup-go@0a12ed9d6a96ab950c8f026ed9f722fe0da7ef32 # v5.0.2 with: go-version: ${{ matrix.go }} check-latest: true - - name: Install Go tip - if: matrix.go == 'tip' - run: | - git clone --depth=1 https://go.googlesource.com/go $HOME/gotip - cd $HOME/gotip/src - ./make.bash - echo "::set-env name=GOROOT::$HOME/gotip" - echo "::add-path::$HOME/gotip/bin" - echo "::add-path::$(go env GOPATH)/bin" - name: Install stringer run: go install golang.org/x/tools/cmd/stringer@latest - name: Install tparse @@ -52,11 +42,6 @@ jobs: run: make tidy - name: Test with coverage run: make cover-${{ matrix.go_tags }} - - name: Upload code coverage to codecov - if: matrix.go == '1.19' - uses: codecov/codecov-action@v4 - with: - file: ./coverage.out - uses: bazelbuild/setup-bazelisk@v3 - run: bazel run //:gazelle-update-repos - name: Check difference between generation code and commit code diff --git a/.github/workflows/codeql.yml b/.github/workflows/codeql.yml index b72cdc545..9739d3287 100644 --- a/.github/workflows/codeql.yml +++ b/.github/workflows/codeql.yml @@ -40,7 +40,7 @@ jobs: steps: - name: Checkout repository - uses: actions/checkout@v4 + uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 # Initializes the CodeQL tools for scanning. - name: Initialize CodeQL diff --git a/.github/workflows/dependabot.yml b/.github/workflows/dependabot.yml index 12b44f305..01e60bcd3 100644 --- a/.github/workflows/dependabot.yml +++ b/.github/workflows/dependabot.yml @@ -9,7 +9,7 @@ jobs: runs-on: ubuntu-latest steps: - - uses: actions/checkout@v4 + - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 - name: Install tparse run: go install github.com/mfridman/tparse@v0.12.2 - run: | @@ -25,7 +25,7 @@ jobs: git config --local user.email '41898282+github-actions[bot]@users.noreply.github.com' git add . git commit -m "Run tidy / bazel+gazelle" - git push + git push origin HEAD:"$GITHUB_HEAD_REF" gh pr review --approve "$PR_URL" gh pr merge --auto --merge "$PR_URL" env: diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index 5278cad4f..887591585 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -5,14 +5,11 @@ jobs: name: lint runs-on: ubuntu-latest steps: - - uses: actions/checkout@v4 - - uses: actions/setup-go@v5 + - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 + - uses: actions/setup-go@0a12ed9d6a96ab950c8f026ed9f722fe0da7ef32 # v5.0.2 with: - go-version: "1.20" - check-latest: true - - uses: golangci/golangci-lint-action@v6 - with: - version: v1.59 + go-version-file: "go.mod" + - uses: golangci/golangci-lint-action@971e284b6050e8a5849b72094c50ab08da042db8 # v6.1.1 - name: Run go vet run: | go vet ./... diff --git a/.github/workflows/smoke.yml b/.github/workflows/smoke.yml index c5892cbf1..a0303346b 100644 --- a/.github/workflows/smoke.yml +++ b/.github/workflows/smoke.yml @@ -14,16 +14,16 @@ jobs: strategy: matrix: go_tags: [ 'stdlib', 'goccy', 'es256k', 'alltags' ] - go: [ '1.22', '1.21', '1.20' ] + go: [ '1.23', '1.22', '1.21' ] name: "Smoke [ Go ${{ matrix.go }} / Tags ${{ matrix.go_tags }} ]" steps: - name: Checkout repository - uses: actions/checkout@v4 + uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 - name: Check documentation generator run: | find . -name '*.md' | xargs env AUTODOC_DRYRUN=1 perl tools/autodoc.pl - name: Cache Go modules - uses: actions/cache@v4 + uses: actions/cache@0c45773b623bea8c8e75f6c82b208c3cf94ea4f9 # v4.0.20 with: path: | ~/go/pkg/mod @@ -33,7 +33,7 @@ jobs: restore-keys: | ${{ runner.os }}-go- - name: Install Go stable version - uses: actions/setup-go@v5 + uses: actions/setup-go@0a12ed9d6a96ab950c8f026ed9f722fe0da7ef32 # v5.0.2 with: go-version: ${{ matrix.go }} check-latest: true @@ -50,6 +50,6 @@ jobs: run: make tidy - name: Run smoke tests run: make smoke-${{ matrix.go_tags }} - - uses: bazelbuild/setup-bazelisk@v3 + - uses: bazelbuild/setup-bazelisk@b39c379c82683a5f25d34f0d062761f62693e0b2 # v3.0.0 - run: bazel build //... diff --git a/.github/workflows/stale.yml b/.github/workflows/stale.yml index f2bee296c..1b8e5f5dd 100644 --- a/.github/workflows/stale.yml +++ b/.github/workflows/stale.yml @@ -7,7 +7,7 @@ jobs: stale: runs-on: ubuntu-latest steps: - - uses: actions/stale@v9 + - uses: actions/stale@28ca1036281a5e5922ead5184a1bbf96e5fc984e # v9.0.0 with: stale-issue-message: 'This issue is stale because it has been open 14 days with no activity. Remove stale label or comment or this will be closed in 7 days.' stale-pr-message: 'This PR is stale because it has been open 14 days with no activity. Remove stale label or comment or this will be closed in 14 days.' diff --git a/.golangci.yml b/.golangci.yml index f7f07deeb..b6cc945a2 100644 --- a/.golangci.yml +++ b/.golangci.yml @@ -60,6 +60,9 @@ issues: text: "don't use an underscore in package name" linters: - revive + - linters: + - staticcheck + text: 'SA1019' - path: /*.go linters: - contextcheck diff --git a/Changes b/Changes index d0ca6c847..70006f112 100644 --- a/Changes +++ b/Changes @@ -4,6 +4,14 @@ Changes v2 has many incompatibilities with v1. To see the full list of differences between v1 and v2, please read the Changes-v2.md file (https://github.com/lestrrat-go/jwx/blob/develop/v2/Changes-v2.md) +v2.1.2 25 Oct 2024 + * [jwt] `jwt.ParseRequest` now uses %w to embed errors returned from + `jwt.ParseHeader`, `jwt.ParseCookie`, and `jwt.ParseForm`, allowing + users to correctly call `errors.Is(err, jwt.ErrTokenExpired)` and the + like. Previously the error returned from `jwt.ParseRequest` showed + in human readable format what the problem was, but it was not programmatically + possible to determine the error type using `errors.Is` (#1175) + v2.1.1 Jul 28 2024 * Update minimum required go version to go 1.20 * Update tests to work on 32-bit systems. diff --git a/cmd/jwx/README.md b/cmd/jwx/README.md index 864126f4b..8dc163f3a 100644 --- a/cmd/jwx/README.md +++ b/cmd/jwx/README.md @@ -165,17 +165,15 @@ Given a PEM encoded ASN.1 DER format key in a file `ec.pem`: ``` -----BEGIN PUBLIC KEY----- -MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDMYfnvWtC8Id5bPKae5yXSxQTt -+Zpul6AnnZWfI2TtIarvjHBFUtXRo96y7hoL4VWOPKGCsRqMFDkrbeUjRrx8iL91 -4/srnyf6sh9c8Zk04xEOpK1ypvBz+Ks4uZObtjnnitf0NBGdjMKxveTq+VE7BWUI -yQjtQ8mbDOsiLLvh7wIDAQAB +MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAESVqB4JcUD6lsfvqMr+OKUNUphdNn +64Eay60978ZlL76V/S7SkyPiUYDNmLHm7gKbkIxAiAw2mTDLXrfC0phUog== -----END PUBLIC KEY----- ``` You can get the JSON representation by: ```shell -% jwx jwk parse --input-format pem ec.pem +% jwx jwk format --input-format pem --output-format json ec.pem { "crv": "P-256", "d": "0g5vAEKzugrXaRbgKG0Tj2qJ5lMP4Bezds1_sTybkfk", diff --git a/deps.bzl b/deps.bzl index 260ca129d..ff3ba256e 100644 --- a/deps.bzl +++ b/deps.bzl @@ -115,8 +115,8 @@ def go_dependencies(): name = "org_golang_x_crypto", build_file_proto_mode = "disable_global", importpath = "golang.org/x/crypto", - sum = "h1:ypSNr+bnYL2YhwoMt2zPxHFmbAN1KZs/njMG3hxUp30=", - version = "v0.25.0", + sum = "h1:GBDwsMXVQi34v5CCYUm2jkJvu4cbtru2U4TN2PSyQnw=", + version = "v0.28.0", ) go_repository( @@ -131,21 +131,21 @@ def go_dependencies(): name = "org_golang_x_sys", build_file_proto_mode = "disable_global", importpath = "golang.org/x/sys", - sum = "h1:RI27ohtqKCnwULzJLqkv897zojh5/DwS/ENaMzUOaWI=", - version = "v0.22.0", + sum = "h1:KHjCJyddX0LoSTb3J+vWpupP9p0oznkqVk/IfjymZbo=", + version = "v0.26.0", ) go_repository( name = "org_golang_x_term", build_file_proto_mode = "disable_global", importpath = "golang.org/x/term", - sum = "h1:BbsgPEJULsl2fV/AT3v15Mjva5yXKQDyKf+TbDz7QJk=", - version = "v0.22.0", + sum = "h1:WtHI/ltw4NvSUig5KARz9h521QvRC8RmF/cuYqifU24=", + version = "v0.25.0", ) go_repository( name = "org_golang_x_text", build_file_proto_mode = "disable_global", importpath = "golang.org/x/text", - sum = "h1:a94ExnEXNtEwYLGJSIUxnWoxoRz/ZcCsV63ROupILh4=", - version = "v0.16.0", + sum = "h1:kTxAhCbGbxhK0IwgSKiMO5awPoDQ0RpfiVYBfK860YM=", + version = "v0.19.0", ) diff --git a/examples/go.sum b/examples/go.sum index ba53a1f10..631b1e03b 100644 --- a/examples/go.sum +++ b/examples/go.sum @@ -42,8 +42,8 @@ golang.org/x/crypto v0.13.0/go.mod h1:y6Z2r+Rw4iayiXXAIxJIDAJ1zMW4yaTpebo8fPOliY golang.org/x/crypto v0.17.0/go.mod h1:gCAAfMLgwOJRpTjQ2zCCt2OcSfYMTeZVSRtQlPC7Nq4= golang.org/x/crypto v0.19.0/go.mod h1:Iy9bg/ha4yyC70EfRS8jz+B6ybOBKMaSxLj6P6oBDfU= golang.org/x/crypto v0.23.0/go.mod h1:CKFgDieR+mRhux2Lsu27y0fO304Db0wZe70UKqHu0v8= -golang.org/x/crypto v0.25.0 h1:ypSNr+bnYL2YhwoMt2zPxHFmbAN1KZs/njMG3hxUp30= -golang.org/x/crypto v0.25.0/go.mod h1:T+wALwcMOSE0kXgUAnPAHqTLW+XHgcELELW8VaDgm/M= +golang.org/x/crypto v0.28.0 h1:GBDwsMXVQi34v5CCYUm2jkJvu4cbtru2U4TN2PSyQnw= +golang.org/x/crypto v0.28.0/go.mod h1:rmgy+3RHxRZMyY0jjAJShp2zgEdOqj2AO7U0pYmeQ7U= golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/mod v0.12.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= @@ -63,6 +63,7 @@ golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= golang.org/x/sync v0.6.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= golang.org/x/sync v0.7.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= +golang.org/x/sync v0.8.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= @@ -75,8 +76,8 @@ golang.org/x/sys v0.12.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.15.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.17.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.20.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/sys v0.22.0 h1:RI27ohtqKCnwULzJLqkv897zojh5/DwS/ENaMzUOaWI= -golang.org/x/sys v0.22.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= +golang.org/x/sys v0.26.0 h1:KHjCJyddX0LoSTb3J+vWpupP9p0oznkqVk/IfjymZbo= +golang.org/x/sys v0.26.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/telemetry v0.0.0-20240228155512-f48c80bd79b2/go.mod h1:TeRTkGYfJXctD9OcfyVLyj2J3IxLnKwHJR8f4D8a3YE= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= @@ -86,7 +87,7 @@ golang.org/x/term v0.12.0/go.mod h1:owVbMEjm3cBLCHdkQu9b1opXd4ETQWc3BhuQGKgXgvU= golang.org/x/term v0.15.0/go.mod h1:BDl952bC7+uMoWR75FIrCDx79TPU9oHkTZ9yRbYOrX0= golang.org/x/term v0.17.0/go.mod h1:lLRBjIVuehSbZlaOtGMbcMncT+aqLLLmKrsjNrUguwk= golang.org/x/term v0.20.0/go.mod h1:8UkIAJTvZgivsXaD6/pH6U9ecQzZ45awqEOzuCvwpFY= -golang.org/x/term v0.22.0/go.mod h1:F3qCibpT5AMpCRfhfT53vVJwhLtIVHhB9XDjfFvnMI4= +golang.org/x/term v0.25.0/go.mod h1:RPyXicDX+6vLxogjjRxjgD2TKtmAO6NZBsBRfrOLu7M= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= @@ -95,7 +96,7 @@ golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU= golang.org/x/text v0.15.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU= -golang.org/x/text v0.16.0/go.mod h1:GhwF1Be+LQoKShO3cGOHzqOgRrGaYc9AvblQOmPVHnI= +golang.org/x/text v0.19.0/go.mod h1:BuEKDfySbSR4drPmRPG/7iBdf8hvFMuRexcpahXilzY= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= diff --git a/go.mod b/go.mod index 9a996a32a..af41a724c 100644 --- a/go.mod +++ b/go.mod @@ -11,13 +11,13 @@ require ( github.com/lestrrat-go/option v1.0.1 github.com/segmentio/asm v1.2.0 github.com/stretchr/testify v1.9.0 - golang.org/x/crypto v0.25.0 + golang.org/x/crypto v0.28.0 ) require ( github.com/davecgh/go-spew v1.1.1 // indirect github.com/lestrrat-go/httpcc v1.0.1 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect - golang.org/x/sys v0.22.0 // indirect + golang.org/x/sys v0.26.0 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect ) diff --git a/go.sum b/go.sum index 8844858fc..4898defa3 100644 --- a/go.sum +++ b/go.sum @@ -24,10 +24,10 @@ github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/ github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -golang.org/x/crypto v0.25.0 h1:ypSNr+bnYL2YhwoMt2zPxHFmbAN1KZs/njMG3hxUp30= -golang.org/x/crypto v0.25.0/go.mod h1:T+wALwcMOSE0kXgUAnPAHqTLW+XHgcELELW8VaDgm/M= -golang.org/x/sys v0.22.0 h1:RI27ohtqKCnwULzJLqkv897zojh5/DwS/ENaMzUOaWI= -golang.org/x/sys v0.22.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= +golang.org/x/crypto v0.28.0 h1:GBDwsMXVQi34v5CCYUm2jkJvu4cbtru2U4TN2PSyQnw= +golang.org/x/crypto v0.28.0/go.mod h1:rmgy+3RHxRZMyY0jjAJShp2zgEdOqj2AO7U0pYmeQ7U= +golang.org/x/sys v0.26.0 h1:KHjCJyddX0LoSTb3J+vWpupP9p0oznkqVk/IfjymZbo= +golang.org/x/sys v0.26.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/jwe/jwe_test.go b/jwe/jwe_test.go index d2a22ec92..3581974df 100644 --- a/jwe/jwe_test.go +++ b/jwe/jwe_test.go @@ -318,12 +318,12 @@ func TestRoundtrip_RSAES_OAEP_AES_GCM(t *testing.T) { 110, 97, 116, 105, 111, 110, 46, } - max := 100 + iterations := 100 if testing.Short() { - max = 1 + iterations = 1 } - for i := 0; i < max; i++ { + for i := 0; i < iterations; i++ { encrypted, err := jwe.Encrypt(plaintext, jwe.WithKey(jwa.RSA_OAEP, &rsaPrivKey.PublicKey)) if !assert.NoError(t, err, "Encrypt should succeed") { return @@ -346,12 +346,12 @@ func TestRoundtrip_RSA1_5_A128CBC_HS256(t *testing.T) { 112, 114, 111, 115, 112, 101, 114, 46, } - max := 100 + iterations := 100 if testing.Short() { - max = 1 + iterations = 1 } - for i := 0; i < max; i++ { + for i := 0; i < iterations; i++ { encrypted, err := jwe.Encrypt(plaintext, jwe.WithKey(jwa.RSA1_5, &rsaPrivKey.PublicKey), jwe.WithContentEncryption(jwa.A128CBC_HS256)) if !assert.NoError(t, err, "Encrypt is successful") { return @@ -379,12 +379,12 @@ func TestEncode_A128KW_A128CBC_HS256(t *testing.T) { 25, 172, 32, 130, 225, 114, 26, 181, 138, 106, 254, 192, 95, 133, 74, 82, } - max := 100 + iterations := 100 if testing.Short() { - max = 1 + iterations = 1 } - for i := 0; i < max; i++ { + for i := 0; i < iterations; i++ { encrypted, err := jwe.Encrypt(plaintext, jwe.WithKey(jwa.A128KW, sharedkey), jwe.WithContentEncryption(jwa.A128CBC_HS256)) if !assert.NoError(t, err, "Encrypt is successful") { return diff --git a/jwk/jwk_test.go b/jwk/jwk_test.go index 1365a3204..8a15c09b4 100644 --- a/jwk/jwk_test.go +++ b/jwk/jwk_test.go @@ -887,35 +887,35 @@ func TestPublicKeyOf(t *testing.T) { }{ { Key: rsakey, - PublicKeyType: reflect.PtrTo(reflect.TypeOf(rsakey.PublicKey)), + PublicKeyType: reflect.PointerTo(reflect.TypeOf(rsakey.PublicKey)), }, { Key: *rsakey, - PublicKeyType: reflect.PtrTo(reflect.TypeOf(rsakey.PublicKey)), + PublicKeyType: reflect.PointerTo(reflect.TypeOf(rsakey.PublicKey)), }, { Key: rsakey.PublicKey, - PublicKeyType: reflect.PtrTo(reflect.TypeOf(rsakey.PublicKey)), + PublicKeyType: reflect.PointerTo(reflect.TypeOf(rsakey.PublicKey)), }, { Key: &rsakey.PublicKey, - PublicKeyType: reflect.PtrTo(reflect.TypeOf(rsakey.PublicKey)), + PublicKeyType: reflect.PointerTo(reflect.TypeOf(rsakey.PublicKey)), }, { Key: ecdsakey, - PublicKeyType: reflect.PtrTo(reflect.TypeOf(ecdsakey.PublicKey)), + PublicKeyType: reflect.PointerTo(reflect.TypeOf(ecdsakey.PublicKey)), }, { Key: *ecdsakey, - PublicKeyType: reflect.PtrTo(reflect.TypeOf(ecdsakey.PublicKey)), + PublicKeyType: reflect.PointerTo(reflect.TypeOf(ecdsakey.PublicKey)), }, { Key: ecdsakey.PublicKey, - PublicKeyType: reflect.PtrTo(reflect.TypeOf(ecdsakey.PublicKey)), + PublicKeyType: reflect.PointerTo(reflect.TypeOf(ecdsakey.PublicKey)), }, { Key: &ecdsakey.PublicKey, - PublicKeyType: reflect.PtrTo(reflect.TypeOf(ecdsakey.PublicKey)), + PublicKeyType: reflect.PointerTo(reflect.TypeOf(ecdsakey.PublicKey)), }, { Key: octets, @@ -1636,9 +1636,9 @@ func TestTypedFields(t *testing.T) { func TestGH412(t *testing.T) { base := jwk.NewSet() - const max = 5 + const iterations = 5 kids := make(map[string]struct{}) - for i := 0; i < max; i++ { + for i := 0; i < iterations; i++ { k, err := jwxtest.GenerateRsaJwk() if !assert.NoError(t, err, `jwxttest.GenerateRsaJwk() should succeed`) { return @@ -1650,7 +1650,7 @@ func TestGH412(t *testing.T) { kids[kid] = struct{}{} } - for i := 0; i < max; i++ { + for i := 0; i < iterations; i++ { idx := i currentKid := "key-" + strconv.Itoa(i) t.Run(fmt.Sprintf("Remove at position %d", i), func(t *testing.T) { @@ -1659,7 +1659,7 @@ func TestGH412(t *testing.T) { return } - if !assert.Equal(t, max, set.Len(), `set.Len should be %d`, max) { + if !assert.Equal(t, iterations, set.Len(), `set.Len should be %d`, iterations) { return } @@ -1673,7 +1673,7 @@ func TestGH412(t *testing.T) { } t.Logf("deleted key %s", k.KeyID()) - if !assert.Equal(t, max-1, set.Len(), `set.Len should be %d`, max-1) { + if !assert.Equal(t, iterations-1, set.Len(), `set.Len should be %d`, iterations-1) { return } diff --git a/jws/jws.go b/jws/jws.go index 3c7e13fcf..2b18b35fe 100644 --- a/jws/jws.go +++ b/jws/jws.go @@ -345,6 +345,7 @@ func Verify(buf []byte, options ...VerifyOption) ([]byte, error) { case identKeyUsed{}: keyUsed = option.Value() case identContext{}: + //nolint:fatcontext ctx = option.Value().(context.Context) case identValidateKey{}: validateKey = option.Value().(bool) diff --git a/jwt/http.go b/jwt/http.go index 149136f15..db0e03147 100644 --- a/jwt/http.go +++ b/jwt/http.go @@ -224,6 +224,7 @@ func ParseRequest(req *http.Request, options ...ParseOption) (Token, error) { lmhdrs := len(mhdrs) lmfrms := len(mfrms) lmcookies := len(mcookies) + var errors []interface{} if lmhdrs > 0 || lmfrms > 0 || lmcookies > 0 { b.WriteString(". Additionally, errors were encountered during attempts to parse") @@ -236,9 +237,8 @@ func ParseRequest(req *http.Request, options ...ParseOption) (Token, error) { } b.WriteString("[header key: ") b.WriteString(strconv.Quote(hdrkey)) - b.WriteString(", error: ") - b.WriteString(strconv.Quote(err.Error())) - b.WriteString("]") + b.WriteString(", error: %w]") + errors = append(errors, err) count++ } b.WriteString(")") @@ -253,9 +253,8 @@ func ParseRequest(req *http.Request, options ...ParseOption) (Token, error) { } b.WriteString("[cookie key: ") b.WriteString(strconv.Quote(cookiekey)) - b.WriteString(", error: ") - b.WriteString(strconv.Quote(err.Error())) - b.WriteString("]") + b.WriteString(", error: %w]") + errors = append(errors, err) count++ } } @@ -269,12 +268,11 @@ func ParseRequest(req *http.Request, options ...ParseOption) (Token, error) { } b.WriteString("[form key: ") b.WriteString(strconv.Quote(formkey)) - b.WriteString(", error: ") - b.WriteString(strconv.Quote(err.Error())) - b.WriteString("]") + b.WriteString(", error: %w]") + errors = append(errors, err) count++ } } } - return nil, fmt.Errorf(b.String()) + return nil, fmt.Errorf(b.String(), errors...) } diff --git a/jwt/jwt_test.go b/jwt/jwt_test.go index 5fd0984e7..ecad2cae3 100644 --- a/jwt/jwt_test.go +++ b/jwt/jwt_test.go @@ -595,10 +595,10 @@ func TestGH52(t *testing.T) { if !assert.NoError(t, err) { return } - const max = 100 + const iterations = 100 var wg sync.WaitGroup - wg.Add(max) - for i := 0; i < max; i++ { + wg.Add(iterations) + for i := 0; i < iterations; i++ { // Do not use t.Run here as it will clutter up the outpuA go func(t *testing.T, priv *ecdsa.PrivateKey, i int) { defer wg.Done() @@ -1853,3 +1853,20 @@ func TestParseJSON(t *testing.T) { }) } } + +func TestGH1175(t *testing.T) { + token, err := jwt.NewBuilder(). + Expiration(time.Now().Add(-1 * time.Hour)). + Build() + require.NoError(t, err, `jwt.NewBuilder should succeed`) + secret := []byte("secret") + signed, err := jwt.Sign(token, jwt.WithKey(jwa.HS256, secret)) + require.NoError(t, err, `jwt.Sign should succeed`) + + req := httptest.NewRequest(http.MethodGet, `http://example.com`, nil) + req.Header.Set("Authorization", "Bearer "+string(signed)) + + _, err = jwt.ParseRequest(req, jwt.WithKey(jwa.HS256, secret)) + require.Error(t, err, `jwt.ParseRequest should fail`) + require.ErrorIs(t, err, jwt.ErrTokenExpired(), `jwt.ParseRequest should fail with jwt.ErrTokenExpired`) +} diff --git a/jwt/options.yaml b/jwt/options.yaml index bd59bb08d..c7453c691 100644 --- a/jwt/options.yaml +++ b/jwt/options.yaml @@ -45,7 +45,7 @@ options: interface: ValidateOption argument_type: time.Duration comment: | - WithAcceptableSkew specifies the duration in which exp and nbf + WithAcceptableSkew specifies the duration in which exp, iat and nbf claims may differ by. This value should be positive - ident: Truncation interface: ValidateOption @@ -61,7 +61,7 @@ options: argument_type: Clock comment: | WithClock specifies the `Clock` to be used when verifying - exp and nbf claims. + exp, iat and nbf claims. - ident: Context interface: ValidateOption argument_type: context.Context diff --git a/jwt/options_gen.go b/jwt/options_gen.go index 5486b3ef3..61f074d5a 100644 --- a/jwt/options_gen.go +++ b/jwt/options_gen.go @@ -239,14 +239,14 @@ func (identVerify) String() string { return "WithVerify" } -// WithAcceptableSkew specifies the duration in which exp and nbf +// WithAcceptableSkew specifies the duration in which exp, iat and nbf // claims may differ by. This value should be positive func WithAcceptableSkew(v time.Duration) ValidateOption { return &validateOption{option.New(identAcceptableSkew{}, v)} } // WithClock specifies the `Clock` to be used when verifying -// exp and nbf claims. +// exp, iat and nbf claims. func WithClock(v Clock) ValidateOption { return &validateOption{option.New(identClock{}, v)} } diff --git a/jwt/validate.go b/jwt/validate.go index b11634857..7cfa63b6f 100644 --- a/jwt/validate.go +++ b/jwt/validate.go @@ -65,6 +65,7 @@ func Validate(t Token, options ...ValidateOption) error { case identTruncation{}: trunc = o.Value().(time.Duration) case identContext{}: + //nolint:fatcontext ctx = o.Value().(context.Context) case identResetValidators{}: resetValidators = o.Value().(bool) diff --git a/jwx_test.go b/jwx_test.go index 7145ee45d..f100e8c33 100644 --- a/jwx_test.go +++ b/jwx_test.go @@ -128,16 +128,10 @@ func TestJoseCompatibility(t *testing.T) { Name: "RSA Private Key with Private Parameters", Raw: rsa.PrivateKey{}, Template: `{"alg": "RS256", "x-jwx": 1234}`, - VerifyKey: func(ctx context.Context, t *testing.T, key jwk.Key) bool { - m, err := key.AsMap(ctx) - if !assert.NoError(t, err, `key.AsMap() should succeed`) { - return false - } - - if !assert.Equal(t, float64(1234), m["x-jwx"], `private parameters should match`) { - return false - } - + VerifyKey: func(_ context.Context, t *testing.T, key jwk.Key) bool { + v, ok := key.Get(`x-jwx`) + require.True(t, ok, `key.Get should succeed`) + require.Equal(t, float64(1234), v, `private parameters should match`) return true }, },