{"id":18359603,"url":"https://github.com/starkware-libs/starkware-crypto-utils","last_synced_at":"2025-04-13T06:41:04.298Z","repository":{"id":38359126,"uuid":"457381608","full_name":"starkware-libs/starkware-crypto-utils","owner":"starkware-libs","description":"Signatures, keys and Pedersen hash on STARK friendly elliptic curve","archived":false,"fork":false,"pushed_at":"2023-11-15T07:54:47.000Z","size":401,"stargazers_count":54,"open_issues_count":2,"forks_count":37,"subscribers_count":3,"default_branch":"dev","last_synced_at":"2025-03-26T23:07:44.202Z","etag":null,"topics":["cryptography","curve","ec","elliptic","javascript","signature","stark","starkex","starkex-crypto","starkware","wallet"],"latest_commit_sha":null,"homepage":"","language":"TypeScript","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/starkware-libs.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","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":"2022-02-09T13:59:34.000Z","updated_at":"2025-02-04T02:45:22.000Z","dependencies_parsed_at":"2024-06-18T16:41:49.886Z","dependency_job_id":"13c95568-bf34-45d4-881c-f63d3866a994","html_url":"https://github.com/starkware-libs/starkware-crypto-utils","commit_stats":{"total_commits":7,"total_committers":4,"mean_commits":1.75,"dds":0.5714285714285714,"last_synced_commit":"1a945b2ffbdf56c68bb7606c45341c9d117422ad"},"previous_names":[],"tags_count":15,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/starkware-libs%2Fstarkware-crypto-utils","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/starkware-libs%2Fstarkware-crypto-utils/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/starkware-libs%2Fstarkware-crypto-utils/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/starkware-libs%2Fstarkware-crypto-utils/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/starkware-libs","download_url":"https://codeload.github.com/starkware-libs/starkware-crypto-utils/tar.gz/refs/heads/dev","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248675434,"owners_count":21143763,"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":["cryptography","curve","ec","elliptic","javascript","signature","stark","starkex","starkex-crypto","starkware","wallet"],"created_at":"2024-11-05T22:23:42.366Z","updated_at":"2025-04-13T06:41:04.273Z","avatar_url":"https://github.com/starkware-libs.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003c!-- logo --\u003e\n\u003ch1 align='center'\u003eStarkWare Crypto Utils\u003c/h1\u003e\n\n\u003c!-- tag line --\u003e\n\u003ch4 align='center'\u003e Signatures, keys and Pedersen hash on STARK friendly elliptic curve\u003c/h4\u003e\n\n\u003c!-- primary badges --\u003e\n\u003cp align=\"center\"\u003e\n  \u003ca href=\"https://www.w3schools.com/js/\"\u003e\n    \u003cimg src='https://badges.aleen42.com/src/javascript.svg' /\u003e\n  \u003c/a\u003e \n  \u003ca href=\"https://www.npmjs.com/package/@starkware-industries/starkware-crypto-utils\"\u003e\n    \u003cimg src='https://img.shields.io/npm/v/@starkware-industries/starkware-crypto-utils?label=npm' /\u003e\n  \u003c/a\u003e\n  \u003ca href=\"https://starkware.co/\"\u003e\n    \u003cimg src=\"https://img.shields.io/badge/powered_by-StarkWare-navy\"\u003e\n  \u003c/a\u003e\n\u003c/p\u003e\n\n## Installation\n\n```bash\n// using npm\nnpm i @starkware-industries/starkware-crypto-utils\n\n// using yarn\nyarn add @starkware-industries/starkware-crypto-utils\n```\n\n## How to use it\n\n```js\nconst starkwareCrypto = require('@starkware-industries/starkware-crypto-utils');\n```\n\n## API\n\n```javascript\n\n{\n    prime,\n    ec: starkEc,\n    constantPoints,\n    shiftPoint,\n    maxEcdsaVal, // Data.\n    pedersen,\n    getLimitOrderMsgHash,\n    getTransferMsgHash,\n    sign,\n    verify,\n    assertInRange,\n    getTransferMsgHashWithFee,\n    getLimitOrderMsgHashWithFee // Function.\n\n    asset: {\n      getAssetType,\n      getAssetId // Function.\n    },\n\n    keyDerivation: {\n      StarkExEc: ec.n, // Data.\n      getPrivateKeyFromEthSignature,\n      privateToStarkKey,\n      getKeyPairFromPath,\n      getAccountPath,\n      grindKey // Function.\n    },\n\n    messageUtils: {\n      assertInRange // Function.\n    }\n}\n```\n\n## Usage\n\n### Signing a StarkEx order\n\n```javascript\nconst starkwareCrypto = require('@starkware-libs/starkware-crypto-utils');\nconst testData = require('test/config/signature_test_data.json');\n\nconst privateKey = testData.meta_data.party_a_order.private_key.substring(2);\nconst keyPair = starkwareCrypto.ec.keyFromPrivate(privateKey, 'hex');\nconst publicKey = starkwareCrypto.ec.keyFromPublic(\n  keyPair.getPublic(true, 'hex'),\n  'hex'\n);\nconst publicKeyX = publicKey.pub.getX();\n\nassert(\n  publicKeyX.toString(16) ===\n    testData.settlement.party_a_order.public_key.substring(2),\n  `Got: ${publicKeyX.toString(16)}.\n        Expected: ${testData.settlement.party_a_order.public_key.substring(2)}`\n);\n\nconst {party_a_order: partyAOrder} = testData.settlement;\nconst msgHash = starkwareCrypto.getLimitOrderMsgHash(\n  partyAOrder.vault_id_sell, // - vault_sell (uint31)\n  partyAOrder.vault_id_buy, // - vault_buy (uint31)\n  partyAOrder.amount_sell, // - amount_sell (uint63 decimal str)\n  partyAOrder.amount_buy, // - amount_buy (uint63 decimal str)\n  partyAOrder.token_sell, // - token_sell (hex str with 0x prefix \u003c prime)\n  partyAOrder.token_buy, // - token_buy (hex str with 0x prefix \u003c prime)\n  partyAOrder.nonce, // - nonce (uint31)\n  partyAOrder.expiration_timestamp // - expiration_timestamp (uint22)\n);\n\nassert(\n  msgHash === testData.meta_data.party_a_order.message_hash.substring(2),\n  `Got: ${msgHash}. Expected: ` +\n    testData.meta_data.party_a_order.message_hash.substring(2)\n);\n\nconst msgSignature = starkwareCrypto.sign(keyPair, msgHash);\nconst {r, s} = msgSignature;\n\nassert(starkwareCrypto.verify(publicKey, msgHash, msgSignature));\nassert(\n  r.toString(16) === partyAOrder.signature.r.substring(2),\n  `Got: ${r.toString(16)}. Expected: ${partyAOrder.signature.r.substring(2)}`\n);\nassert(\n  s.toString(16) === partyAOrder.signature.s.substring(2),\n  `Got: ${s.toString(16)}. Expected: ${partyAOrder.signature.s.substring(2)}`\n);\n\n// The following is the JSON representation of an order:\nconsole.log('Order JSON representation: ');\nconsole.log(partyAOrder);\nconsole.log('\\n');\n```\n\n### StarkEx key serialization\n\n```javascript\nconst starkwareCrypto = require('@starkware-libs/starkware-crypto-utils');\n\nconst pubXStr = publicKey.pub.getX().toString('hex');\nconst pubYStr = publicKey.pub.getY().toString('hex');\n\n// Verify Deserialization.\nconst pubKeyDeserialized = starkwareCrypto.ec.keyFromPublic(\n  {x: pubXStr, y: pubYStr},\n  'hex'\n);\nassert(starkwareCrypto.verify(pubKeyDeserialized, msgHash, msgSignature));\n```\n\n### Signing a StarkEx order with fee\n\n```javascript\nconst privateKey = testData.meta_data.party_a_order.private_key.substring(2);\nconst keyPair = starkwareCrypto.ec.keyFromPrivate(privateKey, 'hex');\nconst publicKey = starkwareCrypto.ec.keyFromPublic(\n  keyPair.getPublic(true, 'hex'),\n  'hex'\n);\nconst publicKeyX = publicKey.pub.getX();\n\nassert(\n  publicKeyX.toString(16) ===\n    testData.settlement.party_a_order.public_key.substring(2),\n  `Got: ${publicKeyX.toString(16)}.\n        Expected: ${testData.settlement.party_a_order.public_key.substring(2)}`\n);\n\nconst {party_a_order: partyAOrder} = testData.settlement;\nconst feeInfo = testData.fee_info_user;\nconst msgHash = starkwareCrypto.getLimitOrderMsgHashWithFee(\n  partyAOrder.vault_id_sell, // - vault_sell (uint64)\n  partyAOrder.vault_id_buy, // - vault_buy (uint64)\n  partyAOrder.amount_sell, // - amount_sell (uint63 decimal str)\n  partyAOrder.amount_buy, // - amount_buy (uint63 decimal str)\n  partyAOrder.token_sell, // - token_sell (hex str with 0x prefix \u003c prime)\n  partyAOrder.token_buy, // - token_buy (hex str with 0x prefix \u003c prime)\n  partyAOrder.nonce, // - nonce (uint31)\n  partyAOrder.expiration_timestamp, // - expiration_timestamp (uint22)\n  feeInfo.token_id, // - token (hex str with 0x prefix \u003c prime)\n  feeInfo.source_vault_id, // - fee_source_vault_id (uint31)\n  feeInfo.fee_limit // - amount (uint63 decimal str)\n);\n\nassert(\n  msgHash ===\n    testData.meta_data.party_a_order_with_fee.message_hash.substring(2),\n  `Got: ${msgHash}. Expected: ` +\n    testData.meta_data.party_a_order_with_fee.message_hash.substring(2)\n);\n\n// The following is the JSON representation of an order:\nconsole.log('Order With Fee JSON representation: ');\n// Fee info is added to the order, and will be also be seen in the JSON of Settlement.\npartyAOrder.fee_info = feeInfo; // eslint-disable-line\nconsole.log(partyAOrder);\nconsole.log('\\n');\n```\n\n### StarkEx transfer\n\n```javascript\nconst starkwareCrypto = require('@starkware-libs/starkware-crypto-utils');\nconst testData = require('test/config/signature_test_data.json');\n\nconst privateKey = testData.meta_data.transfer_order.private_key.substring(2);\nconst keyPair = starkwareCrypto.ec.keyFromPrivate(privateKey, 'hex');\nconst publicKey = starkwareCrypto.ec.keyFromPublic(\n  keyPair.getPublic(true, 'hex'),\n  'hex'\n);\nconst publicKeyX = publicKey.pub.getX();\n\nassert(\n  publicKeyX.toString(16) === testData.transfer_order.public_key.substring(2),\n  `Got: ${publicKeyX.toString(16)}.\n            Expected: ${testData.transfer_order.public_key.substring(2)}`\n);\n\nconst transfer = testData.transfer_order;\nconst msgHash = starkwareCrypto.getTransferMsgHash(\n  transfer.amount, // - amount (uint63 decimal str)\n  transfer.nonce, // - nonce (uint31)\n  transfer.sender_vault_id, // - sender_vault_id (uint31)\n  transfer.token, // - token (hex str with 0x prefix \u003c prime)\n  transfer.target_vault_id, // - target_vault_id (uint31)\n  transfer.target_public_key, // - target_public_key (hex str with 0x prefix \u003c prime)\n  transfer.expiration_timestamp // - expiration_timestamp (uint22)\n);\n\nassert(\n  msgHash === testData.meta_data.transfer_order.message_hash.substring(2),\n  `Got: ${msgHash}. Expected: ` +\n    testData.meta_data.transfer_order.message_hash.substring(2)\n);\n\n// The following is the JSON representation of a transfer:\nconsole.log('Transfer JSON representation: ');\nconsole.log(transfer);\nconsole.log('\\n');\n```\n\n### StarkEx conditional transfer\n\n```javascript\nconst starkwareCrypto = require('@starkware-libs/starkware-crypto-utils');\nconst testData = require('test/config/signature_test_data.json');\n\nconst privateKey =\n  testData.meta_data.conditional_transfer_order.private_key.substring(2);\nconst keyPair = starkwareCrypto.ec.keyFromPrivate(privateKey, 'hex');\nconst publicKey = starkwareCrypto.ec.keyFromPublic(\n  keyPair.getPublic(true, 'hex'),\n  'hex'\n);\nconst publicKeyX = publicKey.pub.getX();\n\nassert(\n  publicKeyX.toString(16) ===\n    testData.conditional_transfer_order.public_key.substring(2),\n  `Got: ${publicKeyX.toString(16)}.\n        Expected: ${testData.conditional_transfer_order.public_key.substring(\n          2\n        )}`\n);\n\nconst transfer = testData.conditional_transfer_order;\nconst msgHash = starkwareCrypto.getTransferMsgHash(\n  transfer.amount, // - amount (uint63 decimal str)\n  transfer.nonce, // - nonce (uint31)\n  transfer.sender_vault_id, // - sender_vault_id (uint31)\n  transfer.token, // - token (hex str with 0x prefix \u003c prime)\n  transfer.target_vault_id, // - target_vault_id (uint31)\n  transfer.target_public_key, // - target_public_key (hex str with 0x prefix \u003c prime)\n  transfer.expiration_timestamp, // - expiration_timestamp (uint22)\n  transfer.condition // - condition (hex str with 0x prefix \u003c prime)\n);\n\nassert(\n  msgHash ===\n    testData.meta_data.conditional_transfer_order.message_hash.substring(2),\n  `Got: ${msgHash}. Expected: ` +\n    testData.meta_data.conditional_transfer_order.message_hash.substring(2)\n);\n\n// The following is the JSON representation of a transfer:\nconsole.log('Conditional Transfer JSON representation: ');\nconsole.log(transfer);\nconsole.log('\\n');\n```\n\n### StarkEx transfer with fee\n\n```javascript\nconst privateKey = testData.meta_data.transfer_order.private_key.substring(2);\nconst keyPair = starkwareCrypto.ec.keyFromPrivate(privateKey, 'hex');\nconst publicKey = starkwareCrypto.ec.keyFromPublic(\n  keyPair.getPublic(true, 'hex'),\n  'hex'\n);\nconst publicKeyX = publicKey.pub.getX();\n\nassert(\n  publicKeyX.toString(16) === testData.transfer_order.public_key.substring(2),\n  `Got: ${publicKeyX.toString(16)}.\n        Expected: ${testData.transfer_order.public_key.substring(2)}`\n);\n\nconst transfer = testData.transfer_order;\nconst feeInfo = testData.fee_info_user;\nconst msgHash = starkwareCrypto.getTransferMsgHashWithFee(\n  transfer.amount, // - amount (uint63 decimal str)\n  transfer.nonce, // - nonce (uint31)\n  transfer.sender_vault_id, // - sender_vault_id (uint64)\n  transfer.token, // - token (hex str with 0x prefix \u003c prime)\n  transfer.target_vault_id, // - target_vault_id (uint64)\n  transfer.target_public_key, // - target_public_key (hex str with 0x prefix \u003c prime)\n  transfer.expiration_timestamp, // - expiration_timestamp (uint22)\n  feeInfo.token_id, // - token (hex str with 0x prefix \u003c prime)\n  feeInfo.source_vault_id, // - fee_source_vault_id (uint64)\n  feeInfo.fee_limit // - amount (uint63 decimal str)\n);\n\nassert(\n  msgHash ===\n    testData.meta_data.transfer_order_with_fee.message_hash.substring(2),\n  `Got: ${msgHash}. Expected: ` +\n    testData.meta_data.transfer_order.message_hash.substring(2)\n);\n\n// The following is the JSON representation of a transfer:\nconsole.log('Transfer With Fee JSON representation: ');\nconsole.log(transfer);\nconsole.log('\\n');\n```\n\n### StarkEx conditional Transfer with fee\n\n```javascript\nconst privateKey =\n  testData.meta_data.conditional_transfer_order.private_key.substring(2);\nconst keyPair = starkwareCrypto.ec.keyFromPrivate(privateKey, 'hex');\nconst publicKey = starkwareCrypto.ec.keyFromPublic(\n  keyPair.getPublic(true, 'hex'),\n  'hex'\n);\nconst publicKeyX = publicKey.pub.getX();\n\nassert(\n  publicKeyX.toString(16) ===\n    testData.conditional_transfer_order.public_key.substring(2),\n  `Got: ${publicKeyX.toString(16)}.\n        Expected: ${testData.conditional_transfer_order.public_key.substring(\n          2\n        )}`\n);\n\nconst transfer = testData.conditional_transfer_order;\nconst feeInfo = testData.fee_info_user;\nconst msgHash = starkwareCrypto.getTransferMsgHashWithFee(\n  transfer.amount, // - amount (uint63 decimal str)\n  transfer.nonce, // - nonce (uint31)\n  transfer.sender_vault_id, // - sender_vault_id (uint64)\n  transfer.token, // - token (hex str with 0x prefix \u003c prime)\n  transfer.target_vault_id, // - target_vault_id (uint64)\n  transfer.target_public_key, // - target_public_key (hex str with 0x prefix \u003c prime)\n  transfer.expiration_timestamp, // - expiration_timestamp (uint22)\n  feeInfo.token_id, // - token (hex str with 0x prefix \u003c prime)\n  feeInfo.source_vault_id, // - fee_source_vault_id (uint64)\n  feeInfo.fee_limit, // - amount (uint63 decimal str)\n  transfer.condition // - condition (hex str with 0x prefix \u003c prime)\n);\n\nassert(\n  msgHash ===\n    testData.meta_data.conditional_transfer_order_with_fee.message_hash.substring(\n      2\n    ),\n  `Got: ${msgHash}. Expected: ` +\n    testData.meta_data.conditional_transfer_order.message_hash.substring(2)\n);\n\n// The following is the JSON representation of a transfer:\nconsole.log('Conditional Transfer With Fee JSON representation: ');\nconsole.log(transfer);\nconsole.log('\\n');\n```\n\n### Adding a matching order to create a settlement\n\n```javascript\nconst starkwareCrypto = require('@starkware-libs/starkware-crypto-utils');\nconst testData = require('test/config/signature_test_data.json');\n\nconst privateKey = testData.meta_data.party_b_order.private_key.substring(2);\nconst keyPair = starkwareCrypto.ec.keyFromPrivate(privateKey, 'hex');\nconst publicKey = starkwareCrypto.ec.keyFromPublic(\n  keyPair.getPublic(true, 'hex'),\n  'hex'\n);\nconst publicKeyX = publicKey.pub.getX();\n\nassert(\n  publicKeyX.toString(16) ===\n    testData.settlement.party_b_order.public_key.substring(2),\n  `Got: ${publicKeyX.toString(16)}.\n        Expected: ${testData.settlement.party_b_order.public_key.substring(2)}`\n);\n\nconst {party_b_order: partyBOrder} = testData.settlement;\nconst msgHash = starkwareCrypto.getLimitOrderMsgHash(\n  partyBOrder.vault_id_sell, // - vault_sell (uint31)\n  partyBOrder.vault_id_buy, // - vault_buy (uint31)\n  partyBOrder.amount_sell, // - amount_sell (uint63 decimal str)\n  partyBOrder.amount_buy, // - amount_buy (uint63 decimal str)\n  partyBOrder.token_sell, // - token_sell (hex str with 0x prefix \u003c prime)\n  partyBOrder.token_buy, // - token_buy (hex str with 0x prefix \u003c prime)\n  partyBOrder.nonce, // - nonce (uint31)\n  partyBOrder.expiration_timestamp // - expiration_timestamp (uint22)\n);\n\nassert(\n  msgHash === testData.meta_data.party_b_order.message_hash.substring(2),\n  `Got: ${msgHash}. Expected: ` +\n    testData.meta_data.party_b_order.message_hash.substring(2)\n);\n\nconst msgSignature = starkwareCrypto.sign(keyPair, msgHash);\nconst {r, s} = msgSignature;\n\nassert(starkwareCrypto.verify(publicKey, msgHash, msgSignature));\nassert(\n  r.toString(16) === partyBOrder.signature.r.substring(2),\n  `Got: ${r.toString(16)}. Expected: ${partyBOrder.signature.r.substring(2)}`\n);\nassert(\n  s.toString(16) === partyBOrder.signature.s.substring(2),\n  `Got: ${s.toString(16)}. Expected: ${partyBOrder.signature.s.substring(2)}`\n);\n\n// The following is the JSON representation of a settlement:\nconsole.log('Settlement JSON representation: ');\nconsole.log(testData.settlement);\n```\n\n## Valid transfer with sender_vault_id=2\\*\\*63+10\n\n```javascript\nconst transfer = testData.transfer_order_2nd_valid_range;\nconst feeInfo = testData.fee_info_user;\n\nconst msgHash = starkwareCrypto.getTransferMsgHashWithFee(\n  transfer.amount, // - amount (uint63 decimal str)\n  transfer.nonce, // - nonce (uint31)\n  transfer.sender_vault_id, // - sender_vault_id (uint64)\n  transfer.token, // - token (hex str with 0x prefix \u003c prime)\n  transfer.target_vault_id, // - target_vault_id (uint64)\n  transfer.target_public_key, // - target_public_key (hex str with 0x prefix \u003c prime)\n  transfer.expiration_timestamp, // - expiration_timestamp (uint22)\n  feeInfo.token_id, // - token (hex str with 0x prefix \u003c prime)\n  feeInfo.source_vault_id, // - fee_source_vault_id (uint64)\n  feeInfo.fee_limit, // - amount (uint63 decimal str)\n  transfer.condition // - condition (hex str with 0x prefix \u003c prime)\n);\n\nassert(\n  msgHash ===\n    testData.meta_data.transfer_order_2nd_valid_range.message_hash.substring(2),\n  `Got: ${msgHash}. Expected: ` +\n    testData.meta_data.transfer_order_2nd_valid_range.message_hash.substring(2)\n);\n\n// The following is the JSON representation of a transfer with sender_vault_id in the second\n// valid range:\nconsole.log('Transfer JSON representation: ');\nconsole.log(transfer);\nconsole.log('\\n');\n```\n\n## License\n\n[Apache License 2.0](LICENSE.md)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fstarkware-libs%2Fstarkware-crypto-utils","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fstarkware-libs%2Fstarkware-crypto-utils","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fstarkware-libs%2Fstarkware-crypto-utils/lists"}