{"id":17068930,"url":"https://github.com/localnerve/hmac-symmetric","last_synced_at":"2025-04-12T19:10:12.777Z","repository":{"id":193196699,"uuid":"688301619","full_name":"localnerve/hmac-symmetric","owner":"localnerve","description":"A library for symmetric encryption with hmac digests","archived":false,"fork":false,"pushed_at":"2025-01-14T17:06:07.000Z","size":459,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"main","last_synced_at":"2025-03-26T13:21:18.290Z","etag":null,"topics":["bot-mitigation","crypto","cryptography","encryption","hmac","nodejs","symmetric-encryption"],"latest_commit_sha":null,"homepage":"","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"bsd-3-clause","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/localnerve.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"license.md","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":"2023-09-07T04:24:55.000Z","updated_at":"2025-01-14T17:02:02.000Z","dependencies_parsed_at":"2025-01-14T18:19:38.784Z","dependency_job_id":"73d1e3a2-c354-4bbd-81d6-670d162e6a58","html_url":"https://github.com/localnerve/hmac-symmetric","commit_stats":null,"previous_names":["localnerve/hmac-symmetric"],"tags_count":17,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/localnerve%2Fhmac-symmetric","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/localnerve%2Fhmac-symmetric/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/localnerve%2Fhmac-symmetric/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/localnerve%2Fhmac-symmetric/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/localnerve","download_url":"https://codeload.github.com/localnerve/hmac-symmetric/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248618277,"owners_count":21134200,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","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":["bot-mitigation","crypto","cryptography","encryption","hmac","nodejs","symmetric-encryption"],"created_at":"2024-10-14T11:15:35.878Z","updated_at":"2025-04-12T19:10:12.748Z","avatar_url":"https://github.com/localnerve.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# hmac-symmetric\n\n\u003e A library for simple symmetric encryption with HMAC digests\n\n[![npm version](https://badge.fury.io/js/@localnerve%2Fhmac-symmetric.svg)](https://badge.fury.io/js/@localnerve%2Fhmac-symmetric)\n![Verify](https://github.com/localnerve/hmac-symmetric/workflows/Verify/badge.svg)\n[![Coverage Status](https://coveralls.io/repos/github/localnerve/hmac-symmetric/badge.svg?branch=main)](https://coveralls.io/github/localnerve/hmac-symmetric?branch=main)\n\n## Summary\nA zero dependency node library with basic functions for using symmetric encryption with HMAC digests. A a simple, small, configurable, and reusable set of functions for payload integrity and authentication.  \n\nTLDR; Skip to the [example](#example)...\n\n## Applications\nThis is a general purpose library that can be used in any application where an HMAC'd symmetrically encrypted payload is useful. Here's a quick reminder of a couple of useful applications for this library:\n1. Bot Mitigation  \n  When the payload is a simple timestamp, roundtripping (get at the beginning and send at the end of input) can be used to force bots to take a \"human\" amount of time to submit a form or field. This is a deal breaker for any serious bot network. In my experience, this is the biggest step you can take to destroy bots and maintain user trust, but you have to procure/measure an accurate minimum human usage time.  \n2. Integrity and Authenticity  \n  The base function of a hashcode is to ensure payload integrity (that it has been unaltered). When combined with a shared secret (HMAC), this also ensures authtenticity. If there are services on your network that will receive a data block that originated from the a trusted source, this can be used to verify the integrity and authenticity of that data block, no matter how many hands it went through in between.  \n  \n## API\nThis library uses the environment variables  \n  + `HS_HMAC_SECRET`\n  + `HS_ENCRYPTION_KEY`\n\nAs the default source for keys for cryptographic functions.  \nFor more information see:  \n  1. For HMAC secret [key](https://nodejs.org/api/crypto.html#cryptocreatehmacalgorithm-key-options)\n  2. For Encryption/Decryption [key](https://nodejs.org/api/crypto.html#cryptocreatecipherivalgorithm-key-iv-options)\n  3. And [caveats for using strings as inputs for cryptographic APIs](https://nodejs.org/api/crypto.html#using-strings-as-inputs-to-cryptographic-apis)\n\nTo **NOT** use environment variables, supply options `hmacSecret` and `encryptionKey`.\n\nMethods this library exports:\n\n### encryptAndDigest\nSymmetrically encrypt data and generate an HMAC digest for it.  \n`encryptAndDigest (input [, options]) : { payload, digest }`  \n  * {String|Buffer|TypedArray|DataView} input - The data to encrypt\n  * {Object} [options] - Optional options for [generateHmac](#generatehmac) and [symmetricEncrypt](#symmetricencrypt)\n  * Returns {Object} with `payload` and `digest` properties for the encrypted payload and the hmac digest.\n\n### decryptAndTest  \nSymmetrically decrypt data and test it's HMAC digest against an original.   \n`decryptAndTest (originalDigest, encryptedInput [, options]) : { ok, decrypted }`  \n  * {String} originalDigest - The original hmac digest to test against.\n  * {String} encryptedInput - The encrypted input data string.\n  * {Object} [options] - Optional options for [generateHmac](#generatehmac) and [symmetricDecrypt](#symmetricdecrypt)\n  * Returns {Object} with `ok` and `decrypted` properties for the test result and the decrypted payload.\n\n### generateHmac\nGenerate an HMAC digest using the HMAC secret.  \n`generateHmac (input [, options]) : String`  \n * {String|Buffer|TypedArray|DataView} input - Input data.\n * {Object} [options] - Optional options.\n * {String} [options.inputEncoding] - Applied if input is a String. Default 'utf8'.\n * {String} [options.hmacAlgo] - Algo used to create HMAC. Default 'sha256'.\n * {String} [options.hmacSecret] - Secret to use. Defaults to environment variable `HS_HMAC_SECRET`.\n * Returns {String} of a hex encoded HMAC digest.\n\n### symmetricEncrypt\nSymmetrically encrypt the input using an encryption key.  \n`symmetricEncrypt (input [, options]) : String`  \n  * {String|Buffer|TypedArray|DataView} input - The data to encrypt.\n  * {Object} [options] - Optional options.\n  * {String} [options.encryptionAlgo] - Symmetric cipher algo, defaults to 'aes-256-cbc'.\n  * {String} [options.encryptionKey] - Symmetric cipher key. Defaults to environment variable `HS_ENCRYPTION_KEY`.\n  * {String} [options.inputEncoding] - Encoding if the input is a String. Defaults to 'utf8'.\n  * Returns {String} hex encoded encryption of the input.\n\n### symmetricDecrypt\nSymmetrically decrypt an encrypted input using an encryption key.  \n`symmetricDecrypt (input [, options]) : String`  \n  * {String} input - The encrypted data.\n  * {Object} [options] - Optional options.\n  * {String} [options.encryptionAlgo] - Symmetric cipher algo, defaults to 'aes-256-cbc'.\n  * {String} [options.encryptionKey] - Symmetric cipher key. Defaults to environment `HS_ENCRYPTION_KEY`.\n  * {Boolean} [options.outputBuffer] - true to return the Buffer result, false to convert buffer to string. Defaults to false.\n  * Returns {String|Buffer} for the decrypted data as requested.\n\n### HSError\nThe class used by this library to throw errors.  \nUseful for determining hmac-symmetric specific error source.  \n`class HSError, constructor (hsErrorType, originalError)`\n\n#### HSError.HSE_HMAC\nError property `hseType` will be equal to `HSError.HSE_HMAC` if error occurred during HMAC generation.\n\n#### HSError.HSE_ENCRYPT\nError property `hseType` will be equal to `HSError.HSE_ENCRYPT` if error occurred during encryption.\n\n#### HSError.HSE_DECRYPT\nError property `hseType` will be equal to `HSError.HSE_DECRYPT` if error occurred during decryption.\n\n## Example\n\nEncryption/decryption usage with top level helper API using `hmacSecret` and `encryptionKey` (instead of using environment variables `HS_HMAC_SECRET` and `HS_ENCRYPTION_KEY`).\n\n```javascript\nimport crypto from 'node:crypto';\nimport { HSError, encryptAndDigest, decryptAndTest } from '@localnerve/hmac-symmetric';\n\n// Create demo input and phony keys for demo only.\nconst input = 'hello world';\nconst hmacSecret = crypto.randomBytes(32);\nconst encryptionKey = crypto.randomBytes(32);  \nconsole.log(input);\n  // hello world\n\ntry {\n  const encrypted = encryptAndDigest(input, {\n    hmacSecret,\n    encryptionKey\n  });\n  console.log(encrypted);\n    // {\n    //   digest: 'd3d6a6f1b2723f001c8c4ff4b28d0b310899c5eefbdbece184d62fcd8a4d712e',\n    //   payload: '1f59ccab850189d7906db63f7f087d0f:957c9fe80c93033a8f9a9de0c0d73729'\n    // }\n\n  const decrypted = decryptAndTest(encrypted.digest, encrypted.payload, {\n    hmacSecret,\n    encryptionKey\n  });\n  console.log(decrypted);\n    // { \n    //   ok: true,\n    //   decrypted: 'hello world'\n    // }\n\n} catch (e) {\n  console.log(e.hseType);\n    // HSE_HMAC, HSE_ENCRYPT, or HSE_DECRYPT\n  console.log('hmac error', e.hseType === HSError.HSE_HMAC);\n  console.log('encryption error', e.hseType === HSError.HSE_ENCRYPT);\n  console.log('decryption error', e.hseType === HSError.HSE_DECRYPT);\n}\n```\n## LICENSE\n\n* [BSD 3-Clause, Alex Grant, LocalNerve, LLC](LICENSE.md)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flocalnerve%2Fhmac-symmetric","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Flocalnerve%2Fhmac-symmetric","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flocalnerve%2Fhmac-symmetric/lists"}