{"id":42305419,"url":"https://github.com/gilbsgilbs/jwit","last_synced_at":"2026-01-27T11:07:53.781Z","repository":{"id":48672783,"uuid":"299663247","full_name":"gilbsgilbs/jwit","owner":"gilbsgilbs","description":"JWIT makes it easy to work with JWKS and asymmetric JWTs in your apps.","archived":false,"fork":false,"pushed_at":"2025-02-24T23:33:40.000Z","size":50,"stargazers_count":5,"open_issues_count":3,"forks_count":1,"subscribers_count":3,"default_branch":"master","last_synced_at":"2025-02-25T00:28:04.017Z","etag":null,"topics":["auth","authentication","go","golang","jwk","jwks","jwt","server","stateless"],"latest_commit_sha":null,"homepage":"https://pkg.go.dev/github.com/gilbsgilbs/jwit","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/gilbsgilbs.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2020-09-29T15:44:16.000Z","updated_at":"2024-04-25T03:18:22.000Z","dependencies_parsed_at":"2022-08-27T08:21:52.396Z","dependency_job_id":"2805310f-cd80-4212-bff8-b23d6bcb9ec4","html_url":"https://github.com/gilbsgilbs/jwit","commit_stats":null,"previous_names":[],"tags_count":1,"template":false,"template_full_name":null,"purl":"pkg:github/gilbsgilbs/jwit","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gilbsgilbs%2Fjwit","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gilbsgilbs%2Fjwit/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gilbsgilbs%2Fjwit/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gilbsgilbs%2Fjwit/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/gilbsgilbs","download_url":"https://codeload.github.com/gilbsgilbs/jwit/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gilbsgilbs%2Fjwit/sbom","scorecard":{"id":426760,"data":{"date":"2025-08-11","repo":{"name":"github.com/gilbsgilbs/jwit","commit":"f1733f97afb44ff198281a836dd00779b38a497f"},"scorecard":{"version":"v5.2.1-40-gf6ed084d","commit":"f6ed084d17c9236477efd66e5b258b9d4cc7b389"},"score":3.3,"checks":[{"name":"Maintained","score":0,"reason":"0 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 0","details":null,"documentation":{"short":"Determines if the project is \"actively maintained\".","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#maintained"}},{"name":"Code-Review","score":0,"reason":"Found 0/23 approved changesets -- score normalized to 0","details":null,"documentation":{"short":"Determines if the project requires human code review before pull requests (aka merge requests) are merged.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#code-review"}},{"name":"Binary-Artifacts","score":10,"reason":"no binaries found in the repo","details":null,"documentation":{"short":"Determines if the project has generated executable (binary) artifacts in the source repository.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#binary-artifacts"}},{"name":"Packaging","score":-1,"reason":"packaging workflow not detected","details":["Warn: no GitHub/GitLab publishing workflow detected."],"documentation":{"short":"Determines if the project is published as a package that others can easily download, install, easily update, and uninstall.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#packaging"}},{"name":"Pinned-Dependencies","score":0,"reason":"dependency not pinned by hash detected -- score normalized to 0","details":["Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test.yml:9: update your workflow using https://app.stepsecurity.io/secureworkflow/gilbsgilbs/jwit/test.yml/master?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/test.yml:11: update your workflow using https://app.stepsecurity.io/secureworkflow/gilbsgilbs/jwit/test.yml/master?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test.yml:21: update your workflow using https://app.stepsecurity.io/secureworkflow/gilbsgilbs/jwit/test.yml/master?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test.yml:25: update your workflow using https://app.stepsecurity.io/secureworkflow/gilbsgilbs/jwit/test.yml/master?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/test.yml:30: update your workflow using https://app.stepsecurity.io/secureworkflow/gilbsgilbs/jwit/test.yml/master?enable=pin","Info:   0 out of   3 GitHub-owned GitHubAction dependencies pinned","Info:   0 out of   2 third-party GitHubAction dependencies pinned"],"documentation":{"short":"Determines if the project has declared and pinned the dependencies of its build process.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#pinned-dependencies"}},{"name":"Dangerous-Workflow","score":10,"reason":"no dangerous workflow patterns detected","details":null,"documentation":{"short":"Determines if the project's GitHub Action workflows avoid dangerous patterns.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#dangerous-workflow"}},{"name":"Token-Permissions","score":0,"reason":"detected GitHub workflow tokens with excessive permissions","details":["Warn: no topLevel permission defined: .github/workflows/test.yml:1","Info: no jobLevel write permissions found"],"documentation":{"short":"Determines if the project's workflows follow the principle of least privilege.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#token-permissions"}},{"name":"CII-Best-Practices","score":0,"reason":"no effort to earn an OpenSSF best practices badge detected","details":null,"documentation":{"short":"Determines if the project has an OpenSSF (formerly CII) Best Practices Badge.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#cii-best-practices"}},{"name":"Security-Policy","score":0,"reason":"security policy file not detected","details":["Warn: no security policy file detected","Warn: no security file to analyze","Warn: no security file to analyze","Warn: no security file to analyze"],"documentation":{"short":"Determines if the project has published a security policy.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#security-policy"}},{"name":"Fuzzing","score":0,"reason":"project is not fuzzed","details":["Warn: no fuzzer integrations found"],"documentation":{"short":"Determines if the project uses fuzzing.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#fuzzing"}},{"name":"License","score":10,"reason":"license file detected","details":["Info: project has a license file: LICENSE:0","Info: FSF or OSI recognized license: Apache License 2.0: LICENSE:0"],"documentation":{"short":"Determines if the project has defined a license.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#license"}},{"name":"Signed-Releases","score":-1,"reason":"no releases found","details":null,"documentation":{"short":"Determines if the project cryptographically signs release artifacts.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#signed-releases"}},{"name":"Branch-Protection","score":0,"reason":"branch protection not enabled on development/release branches","details":["Warn: branch protection not enabled for branch 'master'"],"documentation":{"short":"Determines if the default and release branches are protected with GitHub's branch protection settings.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#branch-protection"}},{"name":"Vulnerabilities","score":9,"reason":"1 existing vulnerabilities detected","details":["Warn: Project is vulnerable to: GO-2025-3485 / GHSA-c6gw-w398-hv78"],"documentation":{"short":"Determines if the project has open, known unfixed vulnerabilities.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#vulnerabilities"}},{"name":"SAST","score":0,"reason":"SAST tool is not run on all commits -- score normalized to 0","details":["Warn: 0 commits out of 8 are checked with a SAST tool"],"documentation":{"short":"Determines if the project uses static code analysis.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#sast"}}]},"last_synced_at":"2025-08-19T02:23:46.610Z","repository_id":48672783,"created_at":"2025-08-19T02:23:46.610Z","updated_at":"2025-08-19T02:23:46.610Z"},"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28812369,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-27T07:41:26.337Z","status":"ssl_error","status_checked_at":"2026-01-27T07:41:08.776Z","response_time":168,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["auth","authentication","go","golang","jwk","jwks","jwt","server","stateless"],"created_at":"2026-01-27T11:07:53.025Z","updated_at":"2026-01-27T11:07:53.776Z","avatar_url":"https://github.com/gilbsgilbs.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"[![License Apache 2.0](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](https://opensource.org/licenses/Apache-2.0)\n[![Godoc](https://godoc.org/github.com/gilbsgilbs/jwit?status.svg)](https://pkg.go.dev/github.com/gilbsgilbs/jwit)\n[![Actions Status](https://github.com/gilbsgilbs/jwit/workflows/Test/badge.svg)](https://github.com/gilbsgilbs/jwit/actions)\n[![Coverage Status](https://coveralls.io/repos/github/gilbsgilbs/jwit/badge.svg?branch=master)](https://coveralls.io/github/gilbsgilbs/jwit?branch=master)\n\n# JWIT\n\nJWIT is a tiny Go library built around [go-jose](https://github.com/square/go-jose) that brings\n[JSON Web Tokens (JWTs)](https://auth0.com/learn/json-web-tokens/) and [JSON Web Key Sets (JWKS)](\nhttps://auth0.com/docs/tokens/json-web-tokens/json-web-key-sets) into your apps.\n\nJWIT features:\n\n- A high-level API to sign and verify your asymmetric JWTs.\n- A high-level API to publish your public JWKS.\n\n\u003e 💡 As JWIT sticks to the standards and is not tight to any framework, you can actually pick which\n\u003e features you want to use. You can use it to just sign JWTs, just verify JWTs you get from a\n\u003e third-party and your own servers, or just expose your public JWKS.\n\nOne neat use-case:\n\n1. Your authorization server uses JWIT to sign new JWTs.\n1. Your authorization server uses JWIT to expose its public keys as a JWKS (usually at\n   `/.well-known/jwks.json`).\n1. Your resource server uses JWIT to unmarshal incoming JWTs and validate them against your\n   authorization server's JWKS.\n\n\u003e 🤯 JWIT will automatically catch changes to the JWKS. Rotating your secrets has never been so\n\u003e easy.\n\n## Installation\n\n\u003e go get github.com/gilbsgilbs/jwit\n\n## Overview\n\nThis section shows a few basic examples that'll give you a sneak peak of how simple it is to work\nwith JWIT. For more in-depth examples (such as working with private claims, loading keys from PEM,\n…), please head to [the godoc page](https://pkg.go.dev/github.com/gilbsgilbs/jwit).\n\n### Create a signed JWT\n\n```go\n// 1. Create a signer from a JSON Web Key Set (JWKS). The JWKS payload will typically reside your\n//    authorization server's config or in a secure vault.\nsigner, err := jwit.NewSigner([]byte(`{\"keys\": [ ... ]}`))\n\n// 2. Create a JWT that expires in one hour.\nrawJWT, err := signer.SignJWT(jwit.C{Duration: 1 * time.Hour})\n\n// 3. That's it, simple as that. rawJWT is a signed JWT token that is ready to serve.\nfmt.Println(rawJWT)\n```\n\n### Verify a JWT\n\n```go\n// 1. Create a verifier\nverifier, err := jwit.NewVerifier(\n    // Specify an URL to the issuer's public JWKS.\n    \u0026jwit.Issuer{\n        // This should correspond to the \"iss\" claims of the JWTs\n        Name: \"myVeryOwnIssuer\",\n\n        // This is an HTTP(S) URL where the authorization server publishes its public keys.\n        // It will be queried the first time a JWT is verified and then periodically.\n        // If this URL is let empty, remote JWKS are disabled.\n        JWKSURL: \"https://my-very-own-issuer.com/.well-known/jwks.json\",\n\n        // You can specify how long the issuer's public keys should be kept in cache.\n        // Passed that delay, the JWKS will be re-fetched once asynchronously.\n        // Defaults to 24 hours.\n        TTL: 10 * time.Hour,\n\n        // Alternatively, you can specify a set of public keys directly:\n        PublicKeys: []interface{}{\n            rsaPublicKey, ecdsaPublicKey,\n            []byte(`--- BEGIN RSA PUBLIC KEY --- ...`),\n            []byte(`{\"keys\":[ ... JWKS ... ]}`),\n        },\n    },\n    // ... you can specify as many issuers as you want\n)\n\n// 2. Verify the JWT using its \"iss\" claim.\nisValid, err := verifier.VerifyJWT(rawJWT)\n\n// Alternatively, if your JWT doesn't have an \"iss\" claim, you can also pass public keys explicitely.\nisValid, err := verifier.VerifyJWTWithKeys(rawJWT, []crypto.PublicKey{ecdsaPublicKey, rsaPublicKey})\n```\n\n### Expose the public JWKS\n\n```go\nhttp.HandleFunc(\n    \"/.well-known/jwks.json\",\n    func (w http.ResponseWriter, req *http.Request) {\n        // Just get the public JWKS from the signer.\n        jwks, err := signer.DumpPublicJWKS()\n\n        // And write it to the response body.\n        w.Write(jwks)\n    },\n)\n```\n\n## 🔒 Security\n\nIf you found a security vulnerability in JWIT itslef, **do not reveal it publicly** and adopt a\n[responsible disclosure](https://en.wikipedia.org/wiki/Responsible_disclosure). You may open a\nGitHub issue stating that you found a vulnerability and specifying a safe way to get in touch with\nyou.\n\nNote that JWIT is **not** another JWT/JWKS implementation by any mean. JWIT relies on\n[go-jose](https://github.com/square/go-jose), a popular JWx implementation by Square. On top of\nthat, go-jose and Go's stdlib are the only dependencies to this library. This greatly reduces the\nattack surface of JWIT. If you found a security vulnerability in go-jose, please refer to\n[their bug bounty program](https://github.com/square/go-jose/blob/master/BUG-BOUNTY.md).\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgilbsgilbs%2Fjwit","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgilbsgilbs%2Fjwit","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgilbsgilbs%2Fjwit/lists"}