vestauth 0.3.2 → 0.3.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "vestauth",
3
- "version": "0.3.2",
3
+ "version": "0.3.3",
4
4
  "description": "auth for agents–from the creator of dotenvx",
5
5
  "keywords": [
6
6
  "vestauth"
@@ -43,7 +43,7 @@
43
43
  "commander": "^11.1.0",
44
44
  "eciesjs": "^0.4.16",
45
45
  "execa": "^5.1.1",
46
- "http-message-sig": "^0.2.0",
46
+ "structured-headers": "^2.0.2",
47
47
  "undici": "7.11.0",
48
48
  "web-bot-auth": "^0.1.2"
49
49
  },
@@ -1,9 +1,8 @@
1
1
  const { logger } = require('./../../../shared/logger')
2
2
 
3
- const { verify } = require('web-bot-auth')
4
- const { verifierFromJWK } = require('web-bot-auth/crypto')
3
+ const provider = require('./../../../lib/provider')
5
4
 
6
- async function _verify (httpMethod, uri, signatureHeader, signatureInputHeader, publicKey) {
5
+ async function verify (httpMethod, uri, signatureHeader, signatureInputHeader, publicKey) {
7
6
  logger.debug(`httpMethod: ${httpMethod}`)
8
7
  logger.debug(`uri: ${uri}`)
9
8
  logger.debug(`signatureHeader: ${signatureHeader}`)
@@ -13,19 +12,8 @@ async function _verify (httpMethod, uri, signatureHeader, signatureInputHeader,
13
12
  const options = this.opts()
14
13
  logger.debug(`options: ${JSON.stringify(options)}`)
15
14
 
16
- const verifier = await verifierFromJWK(JSON.parse(publicKey))
17
- const headers = {
18
- Signature: signatureHeader,
19
- 'Signature-Input': signatureInputHeader
20
- }
21
-
22
- const signedRequest = new Request(uri, { headers: headers })
23
- const r = await verify(signedRequest, verifier)
24
- console.log(r)
25
-
26
- const output = {
27
- implement: 'todo'
28
- }
15
+ const output = await provider.verify(httpMethod, uri, signatureHeader, signatureInputHeader, JSON.parse(publicKey))
16
+ // const output = await provider.verifyWebBotAuth(httpMethod, uri, signatureHeader, signatureInputHeader, JSON.parse(publicKey))
29
17
 
30
18
  let space = 0
31
19
  if (options.prettyPrint) {
@@ -35,4 +23,4 @@ async function _verify (httpMethod, uri, signatureHeader, signatureInputHeader,
35
23
  console.log(JSON.stringify(output, null, space))
36
24
  }
37
25
 
38
- module.exports = _verify
26
+ module.exports = verify
@@ -6,13 +6,6 @@ primitives
6
6
  .description('🔩 primitives')
7
7
  .allowUnknownOption()
8
8
 
9
- // vestauth primitives challenge
10
- const challengeAction = require('./../actions/primitives/challenge')
11
- primitives.command('challenge')
12
- .description('generate challenge')
13
- .option('-pp, --pretty-print', 'pretty print output')
14
- .action(challengeAction)
15
-
16
9
  // vestauth primitives hash [message]
17
10
  const hashAction = require('./../actions/primitives/hash')
18
11
  primitives.command('hash')
@@ -18,11 +18,4 @@ provider.command('verify')
18
18
  .option('-pp, --pretty-print', 'pretty print output')
19
19
  .action(verifyAction)
20
20
 
21
- // vestauth provider challenge
22
- const challengeAction = require('./../actions/provider/challenge')
23
- provider.command('challenge')
24
- .description('generate challenge')
25
- .option('-pp, --pretty-print', 'pretty print output')
26
- .action(challengeAction)
27
-
28
21
  module.exports = provider
@@ -1,7 +1,5 @@
1
1
  const headers = require('./headers')
2
2
  const dotenvx = require('@dotenvx/dotenvx')
3
- const { verify } = require('web-bot-auth')
4
- const { verifierFromJWK } = require('web-bot-auth/crypto')
5
3
 
6
4
  async function agentHeaders (httpMethod, uri, tag = 'vestauth', nonce = null) {
7
5
  let publicKey = null
@@ -11,15 +9,7 @@ async function agentHeaders (httpMethod, uri, tag = 'vestauth', nonce = null) {
11
9
 
12
10
  if (!publicKey && !privateKey) throw new Error('missing AGENT_PUBLIC_KEY and AGENT_PRIVATE_KEY. Run [vestauth agent init]')
13
11
 
14
- const _headers = await headers(httpMethod, uri, privateKey, tag, nonce)
15
-
16
- // verification (temp testing)
17
- const verifier = await verifierFromJWK(JSON.parse(publicKey))
18
- const signedRequest = new Request(uri, { headers: _headers })
19
- const r = await verify(signedRequest, verifier)
20
- console.log(r)
21
-
22
- return _headers
12
+ return await headers(httpMethod, uri, privateKey, tag, nonce)
23
13
  }
24
14
 
25
15
  module.exports = agentHeaders
@@ -0,0 +1,11 @@
1
+ function authorityMessage (uri, signatureParams) {
2
+ const u = new URL(uri)
3
+ const authority = u.host // includes port if present
4
+
5
+ return [
6
+ `"@authority": ${authority}`,
7
+ `"@signature-params": ${signatureParams}`
8
+ ].join('\n')
9
+ }
10
+
11
+ module.exports = authorityMessage
@@ -0,0 +1,7 @@
1
+ const crypto = require('crypto')
2
+
3
+ function edPublicKeyObject (keyJson) {
4
+ return crypto.createPublicKey({ key: keyJson, format: 'jwk' })
5
+ }
6
+
7
+ module.exports = edPublicKeyObject
@@ -2,11 +2,7 @@ const thumbprint = require('./thumbprint')
2
2
  const signatureParams = require('./signatureParams')
3
3
  const webBotAuthSignature = require('./webBotAuthSignature')
4
4
 
5
- // const { signatureHeaders } = require('web-bot-auth')
6
- // const { signerFromJWK } = require('web-bot-auth/crypto')
7
-
8
5
  async function headers (httpMethod, uri, privateKeyString, tag = 'vestauth', nonce = null) {
9
- // shared
10
6
  const privateKey = JSON.parse(privateKeyString)
11
7
  const kid = thumbprint(privateKey)
12
8
  privateKey.kid = kid
@@ -14,7 +10,7 @@ async function headers (httpMethod, uri, privateKeyString, tag = 'vestauth', non
14
10
  // // theirs
15
11
  // const request = new Request(uri)
16
12
  // const now = new Date()
17
- // const headersTheirs = await signatureHeaders(
13
+ // return await signatureHeaders(
18
14
  // request,
19
15
  // await signerFromJWK(JSON.parse(privateKeyString)),
20
16
  // {
@@ -24,15 +20,13 @@ async function headers (httpMethod, uri, privateKeyString, tag = 'vestauth', non
24
20
  // )
25
21
 
26
22
  // ours
27
- const signature = signatureParams(privateKey.kid, tag, nonce)
28
- const sig1 = webBotAuthSignature(httpMethod, uri, signature, privateKey)
23
+ const signatureInput = signatureParams(privateKey.kid, tag, nonce)
24
+ const signature = webBotAuthSignature(httpMethod, uri, signatureInput, privateKey)
29
25
 
30
- const headersOurs = {
31
- Signature: `sig1=:${sig1}:`,
32
- 'Signature-Input': `sig1=${signature}`
26
+ return {
27
+ Signature: `sig1=:${signature}:`,
28
+ 'Signature-Input': `sig1=${signatureInput}`
33
29
  }
34
-
35
- return headersOurs
36
30
  }
37
31
 
38
32
  module.exports = headers
@@ -0,0 +1,22 @@
1
+ const { parseDictionary } = require('structured-headers')
2
+
3
+ // example: sig1=(\"@authority\");created=1769707366;keyid=\"xWuYtVgVV_ZQcfEWexUoln9ynA56PmfF4tAvWQ_Bf_o\";alg=\"ed25519\";expires=1769707666;nonce=\"RtdaKawQVJxEAJwCfI_5-7oVTmfjFkz-rGGifYZ2o2MdAMwJF2nYG3713rL1f9FJmPp8T2j4Sqcmh8H8p8TkRA\";tag=\"web-bot-auth\"
4
+ function parseSignatureInputHeader (signatureInputHeader) {
5
+ const dictionary = parseDictionary(signatureInputHeader)
6
+ const entry = dictionary.entries().next()
7
+ const [key, innerlist] = entry.value
8
+ const [cwp, params] = innerlist
9
+ const values = Object.fromEntries(params)
10
+ const components = []
11
+ for (const entry of cwp) {
12
+ components.push(entry[0])
13
+ }
14
+
15
+ return {
16
+ key,
17
+ values,
18
+ components
19
+ }
20
+ }
21
+
22
+ module.exports = parseSignatureInputHeader
@@ -0,0 +1,36 @@
1
+ const crypto = require('crypto')
2
+
3
+ const parseSignatureInputHeader = require('./parseSignatureInputHeader')
4
+ const stripDictionaryKey = require('./stripDictionaryKey')
5
+ const authorityMessage = require('./authorityMessage')
6
+ const edPublicKeyObject = require('./edPublicKeyObject')
7
+ const epoch = require('./epoch')
8
+
9
+ function providerVerify (httpMetod, uri, signatureHeader, signatureInputHeader, publicKey) {
10
+ const { values } = parseSignatureInputHeader(signatureInputHeader)
11
+
12
+ // return early false, since expired
13
+ if (values.expires && values.expires < epoch(new Date())) {
14
+ return {
15
+ success: false
16
+ }
17
+ }
18
+
19
+ const signatureParams = stripDictionaryKey(signatureInputHeader)
20
+ const signature = stripDictionaryKey(signatureHeader)
21
+ const message = authorityMessage(uri, signatureParams)
22
+ const publicKeyObject = edPublicKeyObject(publicKey)
23
+
24
+ const success = crypto.verify(
25
+ null,
26
+ Buffer.from(message, 'utf8'),
27
+ publicKeyObject,
28
+ Buffer.from(signature, 'base64')
29
+ )
30
+
31
+ return {
32
+ success
33
+ }
34
+ }
35
+
36
+ module.exports = providerVerify
@@ -0,0 +1,25 @@
1
+ const { verify } = require('web-bot-auth')
2
+ const { verifierFromJWK } = require('web-bot-auth/crypto')
3
+
4
+ async function providerVerifyWebBotAuth (httpMetod, uri, signatureHeader, signatureInputHeader, publicKey) {
5
+ let success = false
6
+
7
+ const verifier = await verifierFromJWK(publicKey)
8
+ const signedRequest = new Request(uri, {
9
+ headers: {
10
+ Signature: signatureHeader,
11
+ 'Signature-Input': signatureInputHeader
12
+ }
13
+ })
14
+
15
+ try {
16
+ await verify(signedRequest, verifier)
17
+ success = true
18
+ } catch (_e) {}
19
+
20
+ return {
21
+ success
22
+ }
23
+ }
24
+
25
+ module.exports = providerVerifyWebBotAuth
@@ -0,0 +1,7 @@
1
+ function stripDictionaryKey (signatureInputHeader) {
2
+ // sig1=("@authority");created=1769;keyid="abc";alg="ed25519"
3
+ // strip sig1=
4
+ return signatureInputHeader.toString().replace(/^[^=]+=/, '')
5
+ }
6
+
7
+ module.exports = stripDictionaryKey
@@ -1,4 +1,4 @@
1
- const verify = require('./verify')
1
+ const verify = require('./verifyOld')
2
2
 
3
3
  function verifyAuthorizationHeader (challenge, authorizationHeader) {
4
4
  const raw = authorizationHeader.replace(/^Agent\s+/i, '').trim() // remove 'Agent ' prefix
@@ -2,7 +2,7 @@ const secp = require('@noble/secp256k1')
2
2
  const hash = require('./hash')
3
3
  const stripFormatting = require('./stripFormatting')
4
4
 
5
- function verify (challenge, signatureBase64, publicKeyHexPossiblyFormatted) {
5
+ function verifyOld (challenge, signatureBase64, publicKeyHexPossiblyFormatted) {
6
6
  const publicKeyHex = stripFormatting(publicKeyHexPossiblyFormatted)
7
7
  const hashChallenge = hash(challenge)
8
8
  const signature = Buffer.from(signatureBase64, 'base64url')
@@ -11,4 +11,4 @@ function verify (challenge, signatureBase64, publicKeyHexPossiblyFormatted) {
11
11
  return secp.verify(signature, hashChallenge, publicKeyBytes)
12
12
  }
13
13
 
14
- module.exports = verify
14
+ module.exports = verifyOld
@@ -1,14 +1,9 @@
1
1
  const crypto = require('crypto')
2
2
  const edPrivateKeyObject = require('./edPrivateKeyObject')
3
+ const authorityMessage = require('./authorityMessage')
3
4
 
4
5
  function webBotAuthSignature (method = 'GET', uri = '', signatureParams, privateKey) {
5
- const u = new URL(uri)
6
- const authority = u.host // includes port if present
7
-
8
- const message = [
9
- `"@authority": ${authority}`,
10
- `"@signature-params": ${signatureParams}`
11
- ].join('\n')
6
+ const message = authorityMessage(uri, signatureParams)
12
7
 
13
8
  // const message = [
14
9
  // `"@method": ${method.toUpperCase()}`,
@@ -4,7 +4,7 @@ const keypair = require('./helpers/keypair')
4
4
  const keypairOld = require('./helpers/keypairOld')
5
5
  const headers = require('./helpers/headers')
6
6
  const sign = require('./helpers/sign')
7
- const verify = require('./helpers/verify')
7
+ const verifyOld = require('./helpers/verifyOld')
8
8
 
9
9
  module.exports = {
10
10
  challenge,
@@ -13,5 +13,5 @@ module.exports = {
13
13
  keypairOld,
14
14
  headers,
15
15
  sign,
16
- verify
16
+ verifyOld
17
17
  }
@@ -1,5 +1,7 @@
1
- const providerChallenge = require('./helpers/providerChallenge')
1
+ const providerVerify = require('./helpers/providerVerify')
2
+ const providerVerifyWebBotAuth = require('./helpers/providerVerifyWebBotAuth')
2
3
 
3
4
  module.exports = {
4
- challenge: providerChallenge
5
+ verify: providerVerify,
6
+ verifyWebBotAuth: providerVerifyWebBotAuth
5
7
  }
@@ -1,23 +0,0 @@
1
- const { logger } = require('./../../../shared/logger')
2
-
3
- const primitives = require('./../../../lib/primitives')
4
-
5
- function challenge () {
6
- const options = this.opts()
7
- logger.debug(`options: ${JSON.stringify(options)}`)
8
-
9
- const chal = primitives.challenge()
10
-
11
- const output = {
12
- challenge: chal
13
- }
14
-
15
- let space = 0
16
- if (options.prettyPrint) {
17
- space = 2
18
- }
19
-
20
- console.log(JSON.stringify(output, null, space))
21
- }
22
-
23
- module.exports = challenge
@@ -1,19 +0,0 @@
1
- const { logger } = require('./../../../shared/logger')
2
-
3
- const prov = require('./../../../lib/provider')
4
-
5
- async function provider (website) {
6
- const options = this.opts()
7
- logger.debug(`options: ${JSON.stringify(options)}`)
8
-
9
- const output = await prov.challenge()
10
-
11
- let space = 0
12
- if (options.prettyPrint) {
13
- space = 2
14
- }
15
-
16
- console.log(JSON.stringify(output, null, space))
17
- }
18
-
19
- module.exports = provider