diff --git a/package-lock.json b/package-lock.json index 475dd1a6..c6149b18 100644 --- a/package-lock.json +++ b/package-lock.json @@ -17,7 +17,7 @@ "@meshsdk/core-cst": "^1.9.0-beta.77", "@meshsdk/react": "^1.9.0-beta.77", "@octokit/core": "^6.1.2", - "@prisma/client": "^6.4.1", + "@prisma/client": "^6.17.1", "@radix-ui/react-accordion": "^1.2.0", "@radix-ui/react-checkbox": "^1.1.1", "@radix-ui/react-collapsible": "^1.1.0", @@ -99,7 +99,7 @@ "postcss": "^8.4.39", "prettier": "^3.3.2", "prettier-plugin-tailwindcss": "^0.6.5", - "prisma": "^6.4.1", + "prisma": "^6.17.1", "tailwindcss": "^3.4.3", "ts-jest": "^29.4.4", "typescript": "^5.5.3" @@ -107,8 +107,6 @@ }, "node_modules/@alloc/quick-lru": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/@alloc/quick-lru/-/quick-lru-5.2.0.tgz", - "integrity": "sha512-UrcABB+4bUrFABwbluTIBErXwvbsU/V7TZWfmbgJfbkwiBuziS9gxdODUyuiecfdGQ85jglMW6juS3+z5TsKLw==", "license": "MIT", "engines": { "node": ">=10" @@ -119,8 +117,6 @@ }, "node_modules/@apidevtools/json-schema-ref-parser": { "version": "9.1.2", - "resolved": "https://registry.npmjs.org/@apidevtools/json-schema-ref-parser/-/json-schema-ref-parser-9.1.2.tgz", - "integrity": "sha512-r1w81DpR+KyRWd3f+rk6TNqMgedmAxZP5v5KWlXQWlgMUUtyEJch0DKEci1SorPMiSeM8XPl7MZ3miJ60JIpQg==", "license": "MIT", "dependencies": { "@jsdevtools/ono": "^7.1.3", @@ -131,8 +127,6 @@ }, "node_modules/@apidevtools/openapi-schemas": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@apidevtools/openapi-schemas/-/openapi-schemas-2.1.0.tgz", - "integrity": "sha512-Zc1AlqrJlX3SlpupFGpiLi2EbteyP7fXmUOGup6/DnkRgjP9bgMM/ag+n91rsv0U1Gpz0H3VILA/o3bW7Ua6BQ==", "license": "MIT", "engines": { "node": ">=10" @@ -140,14 +134,10 @@ }, "node_modules/@apidevtools/swagger-methods": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/@apidevtools/swagger-methods/-/swagger-methods-3.0.2.tgz", - "integrity": "sha512-QAkD5kK2b1WfjDS/UQn/qQkbwF31uqRjPTrsCs5ZG9BQGAkjwvqGFjjPqAuzac/IYzpPtRzjCP1WrTuAIjMrXg==", "license": "MIT" }, "node_modules/@apidevtools/swagger-parser": { "version": "10.0.3", - "resolved": "https://registry.npmjs.org/@apidevtools/swagger-parser/-/swagger-parser-10.0.3.tgz", - "integrity": "sha512-sNiLY51vZOmSPFZA5TF35KZ2HbgYklQnTSDnkghamzLb3EkNtcQnrBQEj5AOCxHpTtXpqMCRM1CrmV2rG6nw4g==", "license": "MIT", "dependencies": { "@apidevtools/json-schema-ref-parser": "^9.0.6", @@ -163,8 +153,6 @@ }, "node_modules/@auth/core": { "version": "0.34.2", - "resolved": "https://registry.npmjs.org/@auth/core/-/core-0.34.2.tgz", - "integrity": "sha512-KywHKRgLiF3l7PLyL73fjLSIBe1YNcA6sMeew4yMP6cfCWGXZrkkXd32AjRi1hlJ9nvovUBGZHvbn+LijO6ZeQ==", "license": "ISC", "optional": true, "peer": true, @@ -196,8 +184,6 @@ }, "node_modules/@auth/prisma-adapter": { "version": "1.6.0", - "resolved": "https://registry.npmjs.org/@auth/prisma-adapter/-/prisma-adapter-1.6.0.tgz", - "integrity": "sha512-PQU8/Oi5gfjzb0MkhMGVX0Dg877phPzsQdK54+C7ubukCeZPjyvuSAx1vVtWEYVWp2oQvjgG/C6QiDoeC7S10A==", "license": "ISC", "dependencies": { "@auth/core": "0.29.0" @@ -208,8 +194,6 @@ }, "node_modules/@auth/prisma-adapter/node_modules/@auth/core": { "version": "0.29.0", - "resolved": "https://registry.npmjs.org/@auth/core/-/core-0.29.0.tgz", - "integrity": "sha512-MdfEjU6WRjUnPG1+XeBWrTIlAsLZU6V0imCIqVDDDPxLI6UZWldXVqAA2EsDazGofV78jqiCLHaN85mJITDqdg==", "license": "ISC", "dependencies": { "@panva/hkdf": "^1.1.1", @@ -239,8 +223,6 @@ }, "node_modules/@babel/code-frame": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.27.1.tgz", - "integrity": "sha512-cjQ7ZlQ0Mv3b47hABuTevyTuYN4i+loJKGeV9flcCgIK37cCXRh+L1bd3iBHlynerhQ7BhCkn2BPbQUL+rGqFg==", "license": "MIT", "dependencies": { "@babel/helper-validator-identifier": "^7.27.1", @@ -253,8 +235,6 @@ }, "node_modules/@babel/compat-data": { "version": "7.28.4", - "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.28.4.tgz", - "integrity": "sha512-YsmSKC29MJwf0gF8Rjjrg5LQCmyh+j/nD8/eP7f+BeoQTKYqs9RoWbjGOdy0+1Ekr68RJZMUOPVQaQisnIo4Rw==", "license": "MIT", "engines": { "node": ">=6.9.0" @@ -262,8 +242,6 @@ }, "node_modules/@babel/core": { "version": "7.28.4", - "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.28.4.tgz", - "integrity": "sha512-2BCOP7TN8M+gVDj7/ht3hsaO/B/n5oDbiAyyvnRlNOs+u1o+JWNYTQrmpuNp1/Wq2gcFrI01JAW+paEKDMx/CA==", "license": "MIT", "dependencies": { "@babel/code-frame": "^7.27.1", @@ -292,8 +270,6 @@ }, "node_modules/@babel/generator": { "version": "7.28.3", - "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.28.3.tgz", - "integrity": "sha512-3lSpxGgvnmZznmBkCRnVREPUFJv2wrv9iAoFDvADJc0ypmdOxdUtcLeBgBJ6zE0PMeTKnxeQzyk0xTBq4Ep7zw==", "license": "MIT", "dependencies": { "@babel/parser": "^7.28.3", @@ -308,8 +284,6 @@ }, "node_modules/@babel/helper-compilation-targets": { "version": "7.27.2", - "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.27.2.tgz", - "integrity": "sha512-2+1thGUUWWjLTYTHZWK1n8Yga0ijBz1XAhUXcKy81rd5g6yh7hGqMp45v7cadSbEHc9G3OTv45SyneRN3ps4DQ==", "license": "MIT", "dependencies": { "@babel/compat-data": "^7.27.2", @@ -324,8 +298,6 @@ }, "node_modules/@babel/helper-globals": { "version": "7.28.0", - "resolved": "https://registry.npmjs.org/@babel/helper-globals/-/helper-globals-7.28.0.tgz", - "integrity": "sha512-+W6cISkXFa1jXsDEdYA8HeevQT/FULhxzR99pxphltZcVaugps53THCeiWA8SguxxpSp3gKPiuYfSWopkLQ4hw==", "license": "MIT", "engines": { "node": ">=6.9.0" @@ -333,8 +305,6 @@ }, "node_modules/@babel/helper-module-imports": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.27.1.tgz", - "integrity": "sha512-0gSFWUPNXNopqtIPQvlD5WgXYI5GY2kP2cCvoT8kczjbfcfuIljTbcWrulD1CIPIX2gt1wghbDy08yE1p+/r3w==", "license": "MIT", "dependencies": { "@babel/traverse": "^7.27.1", @@ -346,8 +316,6 @@ }, "node_modules/@babel/helper-module-transforms": { "version": "7.28.3", - "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.28.3.tgz", - "integrity": "sha512-gytXUbs8k2sXS9PnQptz5o0QnpLL51SwASIORY6XaBKF88nsOT0Zw9szLqlSGQDP/4TljBAD5y98p2U1fqkdsw==", "license": "MIT", "dependencies": { "@babel/helper-module-imports": "^7.27.1", @@ -363,8 +331,6 @@ }, "node_modules/@babel/helper-plugin-utils": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/helper-plugin-utils/-/helper-plugin-utils-7.27.1.tgz", - "integrity": "sha512-1gn1Up5YXka3YYAHGKpbideQ5Yjf1tDa9qYcgysz+cNCXukyLl6DjPXhD3VRwSb8c0J9tA4b2+rHEZtc6R0tlw==", "license": "MIT", "engines": { "node": ">=6.9.0" @@ -372,8 +338,6 @@ }, "node_modules/@babel/helper-string-parser": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.27.1.tgz", - "integrity": "sha512-qMlSxKbpRlAridDExk92nSobyDdpPijUq2DW6oDnUqd0iOGxmQjyqhMIihI9+zv4LPyZdRje2cavWPbCbWm3eA==", "license": "MIT", "engines": { "node": ">=6.9.0" @@ -381,8 +345,6 @@ }, "node_modules/@babel/helper-validator-identifier": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.27.1.tgz", - "integrity": "sha512-D2hP9eA+Sqx1kBZgzxZh0y1trbuU+JoDkiEwqhQ36nodYqJwyEIhPSdMNd7lOm/4io72luTPWH20Yda0xOuUow==", "license": "MIT", "engines": { "node": ">=6.9.0" @@ -390,8 +352,6 @@ }, "node_modules/@babel/helper-validator-option": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.27.1.tgz", - "integrity": "sha512-YvjJow9FxbhFFKDSuFnVCe2WxXk1zWc22fFePVNEaWJEu8IrZVlda6N0uHwzZrUM1il7NC9Mlp4MaJYbYd9JSg==", "license": "MIT", "engines": { "node": ">=6.9.0" @@ -399,8 +359,6 @@ }, "node_modules/@babel/helpers": { "version": "7.28.4", - "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.28.4.tgz", - "integrity": "sha512-HFN59MmQXGHVyYadKLVumYsA9dBFun/ldYxipEjzA4196jpLZd8UjEEBLkbEkvfYreDqJhZxYAWFPtrfhNpj4w==", "license": "MIT", "dependencies": { "@babel/template": "^7.27.2", @@ -412,8 +370,6 @@ }, "node_modules/@babel/parser": { "version": "7.28.4", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.28.4.tgz", - "integrity": "sha512-yZbBqeM6TkpP9du/I2pUZnJsRMGGvOuIrhjzC1AwHwW+6he4mni6Bp/m8ijn0iOuZuPI2BfkCoSRunpyjnrQKg==", "license": "MIT", "dependencies": { "@babel/types": "^7.28.4" @@ -427,8 +383,6 @@ }, "node_modules/@babel/plugin-syntax-async-generators": { "version": "7.8.4", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-async-generators/-/plugin-syntax-async-generators-7.8.4.tgz", - "integrity": "sha512-tycmZxkGfZaxhMRbXlPXuVFpdWlXpir2W4AMhSJgRKzk/eDlIXOhb2LHWoLpDF7TEHylV5zNhykX6KAgHJmTNw==", "dev": true, "license": "MIT", "dependencies": { @@ -440,8 +394,6 @@ }, "node_modules/@babel/plugin-syntax-bigint": { "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-bigint/-/plugin-syntax-bigint-7.8.3.tgz", - "integrity": "sha512-wnTnFlG+YxQm3vDxpGE57Pj0srRU4sHE/mDkt1qv2YJJSeUAec2ma4WLUnUPeKjyrfntVwe/N6dCXpU+zL3Npg==", "dev": true, "license": "MIT", "dependencies": { @@ -453,8 +405,6 @@ }, "node_modules/@babel/plugin-syntax-class-properties": { "version": "7.12.13", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-class-properties/-/plugin-syntax-class-properties-7.12.13.tgz", - "integrity": "sha512-fm4idjKla0YahUNgFNLCB0qySdsoPiZP3iQE3rky0mBUtMZ23yDJ9SJdg6dXTSDnulOVqiF3Hgr9nbXvXTQZYA==", "dev": true, "license": "MIT", "dependencies": { @@ -466,8 +416,6 @@ }, "node_modules/@babel/plugin-syntax-class-static-block": { "version": "7.14.5", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-class-static-block/-/plugin-syntax-class-static-block-7.14.5.tgz", - "integrity": "sha512-b+YyPmr6ldyNnM6sqYeMWE+bgJcJpO6yS4QD7ymxgH34GBPNDM/THBh8iunyvKIZztiwLH4CJZ0RxTk9emgpjw==", "dev": true, "license": "MIT", "dependencies": { @@ -494,8 +442,6 @@ }, "node_modules/@babel/plugin-syntax-import-attributes": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-attributes/-/plugin-syntax-import-attributes-7.27.1.tgz", - "integrity": "sha512-oFT0FrKHgF53f4vOsZGi2Hh3I35PfSmVs4IBFLFj4dnafP+hIWDLg3VyKmUHfLoLHlyxY4C7DGtmHuJgn+IGww==", "dev": true, "license": "MIT", "dependencies": { @@ -510,8 +456,6 @@ }, "node_modules/@babel/plugin-syntax-import-meta": { "version": "7.10.4", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-meta/-/plugin-syntax-import-meta-7.10.4.tgz", - "integrity": "sha512-Yqfm+XDx0+Prh3VSeEQCPU81yC+JWZ2pDPFSS4ZdpfZhp4MkFMaDC1UqseovEKwSUpnIL7+vK+Clp7bfh0iD7g==", "dev": true, "license": "MIT", "dependencies": { @@ -523,8 +467,6 @@ }, "node_modules/@babel/plugin-syntax-json-strings": { "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-json-strings/-/plugin-syntax-json-strings-7.8.3.tgz", - "integrity": "sha512-lY6kdGpWHvjoe2vk4WrAapEuBR69EMxZl+RoGRhrFGNYVK8mOPAW8VfbT/ZgrFbXlDNiiaxQnAtgVCZ6jv30EA==", "dev": true, "license": "MIT", "dependencies": { @@ -536,8 +478,6 @@ }, "node_modules/@babel/plugin-syntax-jsx": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-jsx/-/plugin-syntax-jsx-7.27.1.tgz", - "integrity": "sha512-y8YTNIeKoyhGd9O0Jiyzyyqk8gdjnumGTQPsz0xOZOQ2RmkVJeZ1vmmfIvFEKqucBG6axJGBZDE/7iI5suUI/w==", "dev": true, "license": "MIT", "dependencies": { @@ -552,8 +492,6 @@ }, "node_modules/@babel/plugin-syntax-logical-assignment-operators": { "version": "7.10.4", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-logical-assignment-operators/-/plugin-syntax-logical-assignment-operators-7.10.4.tgz", - "integrity": "sha512-d8waShlpFDinQ5MtvGU9xDAOzKH47+FFoney2baFIoMr952hKOLp1HR7VszoZvOsV/4+RRszNY7D17ba0te0ig==", "dev": true, "license": "MIT", "dependencies": { @@ -565,8 +503,6 @@ }, "node_modules/@babel/plugin-syntax-nullish-coalescing-operator": { "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-nullish-coalescing-operator/-/plugin-syntax-nullish-coalescing-operator-7.8.3.tgz", - "integrity": "sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ==", "dev": true, "license": "MIT", "dependencies": { @@ -578,8 +514,6 @@ }, "node_modules/@babel/plugin-syntax-numeric-separator": { "version": "7.10.4", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-numeric-separator/-/plugin-syntax-numeric-separator-7.10.4.tgz", - "integrity": "sha512-9H6YdfkcK/uOnY/K7/aA2xpzaAgkQn37yzWUMRK7OaPOqOpGS1+n0H5hxT9AUw9EsSjPW8SVyMJwYRtWs3X3ug==", "dev": true, "license": "MIT", "dependencies": { @@ -591,8 +525,6 @@ }, "node_modules/@babel/plugin-syntax-object-rest-spread": { "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-object-rest-spread/-/plugin-syntax-object-rest-spread-7.8.3.tgz", - "integrity": "sha512-XoqMijGZb9y3y2XskN+P1wUGiVwWZ5JmoDRwx5+3GmEplNyVM2s2Dg8ILFQm8rWM48orGy5YpI5Bl8U1y7ydlA==", "dev": true, "license": "MIT", "dependencies": { @@ -604,8 +536,6 @@ }, "node_modules/@babel/plugin-syntax-optional-catch-binding": { "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-catch-binding/-/plugin-syntax-optional-catch-binding-7.8.3.tgz", - "integrity": "sha512-6VPD0Pc1lpTqw0aKoeRTMiB+kWhAoT24PA+ksWSBrFtl5SIRVpZlwN3NNPQjehA2E/91FV3RjLWoVTglWcSV3Q==", "dev": true, "license": "MIT", "dependencies": { @@ -617,8 +547,6 @@ }, "node_modules/@babel/plugin-syntax-optional-chaining": { "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-chaining/-/plugin-syntax-optional-chaining-7.8.3.tgz", - "integrity": "sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg==", "dev": true, "license": "MIT", "dependencies": { @@ -630,8 +558,6 @@ }, "node_modules/@babel/plugin-syntax-private-property-in-object": { "version": "7.14.5", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-private-property-in-object/-/plugin-syntax-private-property-in-object-7.14.5.tgz", - "integrity": "sha512-0wVnp9dxJ72ZUJDV27ZfbSj6iHLoytYZmh3rFcxNnvsJF3ktkzLDZPy/mA17HGsaQT3/DQsWYX1f1QGWkCoVUg==", "dev": true, "license": "MIT", "dependencies": { @@ -646,8 +572,6 @@ }, "node_modules/@babel/plugin-syntax-top-level-await": { "version": "7.14.5", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-top-level-await/-/plugin-syntax-top-level-await-7.14.5.tgz", - "integrity": "sha512-hx++upLv5U1rgYfwe1xBQUhRmU41NEvpUvrp8jkrSCdvGSnM5/qdRMtylJ6PG5OFkBaHkbTAKTnd3/YyESRHFw==", "dev": true, "license": "MIT", "dependencies": { @@ -662,8 +586,6 @@ }, "node_modules/@babel/plugin-syntax-typescript": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-typescript/-/plugin-syntax-typescript-7.27.1.tgz", - "integrity": "sha512-xfYCBMxveHrRMnAWl1ZlPXOZjzkN82THFvLhQhFXFt81Z5HnN+EtUkZhv/zcKpmT3fzmWZB0ywiBrbC3vogbwQ==", "dev": true, "license": "MIT", "dependencies": { @@ -678,8 +600,6 @@ }, "node_modules/@babel/runtime": { "version": "7.26.7", - "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.26.7.tgz", - "integrity": "sha512-AOPI3D+a8dXnja+iwsUqGRjr1BbZIe771sXdapOtYI531gSqpi92vXivKcq2asu/DFpdl1ceFAKZyRzK2PCVcQ==", "license": "MIT", "dependencies": { "regenerator-runtime": "^0.14.0" @@ -690,8 +610,6 @@ }, "node_modules/@babel/runtime-corejs3": { "version": "7.27.1", - "resolved": "https://registry.npmjs.org/@babel/runtime-corejs3/-/runtime-corejs3-7.27.1.tgz", - "integrity": "sha512-909rVuj3phpjW6y0MCXAZ5iNeORePa6ldJvp2baWGcTjwqbBDDz6xoS5JHJ7lS88NlwLYj07ImL/8IUMtDZzTA==", "license": "MIT", "dependencies": { "core-js-pure": "^3.30.2" @@ -702,8 +620,6 @@ }, "node_modules/@babel/template": { "version": "7.27.2", - "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.27.2.tgz", - "integrity": "sha512-LPDZ85aEJyYSd18/DkjNh4/y1ntkE5KwUHWTiqgRxruuZL2F1yuHligVHLvcHY2vMHXttKFpJn6LwfI7cw7ODw==", "license": "MIT", "dependencies": { "@babel/code-frame": "^7.27.1", @@ -716,8 +632,6 @@ }, "node_modules/@babel/traverse": { "version": "7.28.4", - "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.28.4.tgz", - "integrity": "sha512-YEzuboP2qvQavAcjgQNVgsvHIDv6ZpwXvcvjmyySP2DIMuByS/6ioU5G9pYrWHM6T2YDfc7xga9iNzYOs12CFQ==", "license": "MIT", "dependencies": { "@babel/code-frame": "^7.27.1", @@ -734,8 +648,6 @@ }, "node_modules/@babel/types": { "version": "7.28.4", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.28.4.tgz", - "integrity": "sha512-bkFqkLhh3pMBUQQkpVgWDWq/lqzc2678eUyDlTBhRqhCHFguYYGM0Efga7tYk4TogG/3x0EEl66/OQ+WGbWB/Q==", "license": "MIT", "dependencies": { "@babel/helper-string-parser": "^7.27.1", @@ -749,6 +661,7 @@ "version": "1.2.10", "resolved": "https://registry.npmjs.org/@basementuniverse/commonjs/-/commonjs-1.2.10.tgz", "integrity": "sha512-hmqEAGVCdsyQWJ5PwweFegOZ19gBm5Ppw48/l8mOexcjubyuhmgRt6SB8BoLF9C4lzRemG816hH77w7hJRrDMA==", + "deprecated": "Package no longer supported. Contact Support at https://www.npmjs.com/support for more info.", "license": "MIT" }, "node_modules/@basementuniverse/marble-identicons": { @@ -763,8 +676,6 @@ }, "node_modules/@bcoe/v8-coverage": { "version": "0.2.3", - "resolved": "https://registry.npmjs.org/@bcoe/v8-coverage/-/v8-coverage-0.2.3.tgz", - "integrity": "sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw==", "dev": true, "license": "MIT" }, @@ -800,7 +711,8 @@ "node_modules/@bufbuild/protobuf": { "version": "1.10.1", "resolved": "https://registry.npmjs.org/@bufbuild/protobuf/-/protobuf-1.10.1.tgz", - "integrity": "sha512-wJ8ReQbHxsAfXhrf9ixl0aYbZorRuOWpBNzm8pL8ftmSxQx/wnJD5Eg861NwJU/czy2VXFIebCeZnZrI9rktIQ==" + "integrity": "sha512-wJ8ReQbHxsAfXhrf9ixl0aYbZorRuOWpBNzm8pL8ftmSxQx/wnJD5Eg861NwJU/czy2VXFIebCeZnZrI9rktIQ==", + "license": "(Apache-2.0 AND BSD-3-Clause)" }, "node_modules/@cardano-ogmios/client": { "version": "6.9.0", @@ -833,9 +745,9 @@ } }, "node_modules/@cardano-sdk/core": { - "version": "0.45.5", - "resolved": "https://registry.npmjs.org/@cardano-sdk/core/-/core-0.45.5.tgz", - "integrity": "sha512-4rml64h4Wo1bqAZ2dN1Jnu6REiztGeYxY/Xp/uUoJVg27sUrsC4sA/KTVlgdnh60btAI/XOCXTQZ8RTm9V+JEA==", + "version": "0.45.10", + "resolved": "https://registry.npmjs.org/@cardano-sdk/core/-/core-0.45.10.tgz", + "integrity": "sha512-PU/onQuPgsy0CtFKDlHcozGHMTHrigWztTmKq54tL0TdWRcClXbMh5Q63ALcP388ZouPC1nKomOAooVgyrrEfw==", "license": "Apache-2.0", "dependencies": { "@biglup/is-cid": "^1.0.3", @@ -935,14 +847,14 @@ } }, "node_modules/@cardano-sdk/dapp-connector": { - "version": "0.13.19", - "resolved": "https://registry.npmjs.org/@cardano-sdk/dapp-connector/-/dapp-connector-0.13.19.tgz", - "integrity": "sha512-MxXaV48HgxnR1EpqrEke/SFHsFafUQt+rGpGcuoEnGLu0a0HJmP0o4sXN/KfLwM5CPXD+0T71uBiWxcvHWDAGA==", + "version": "0.13.24", + "resolved": "https://registry.npmjs.org/@cardano-sdk/dapp-connector/-/dapp-connector-0.13.24.tgz", + "integrity": "sha512-sgUko8wpLT1iF0ySeSIJIn5f696iuj6TC7E+0CmPApcGy+gpY5ECNRgXx8vus2Cq15EuE/Jtxe6on+9HJX90uw==", "license": "Apache-2.0", "dependencies": { - "@cardano-sdk/core": "~0.46.5", - "@cardano-sdk/crypto": "~0.4.3", - "@cardano-sdk/util": "~0.17.0", + "@cardano-sdk/core": "~0.46.10", + "@cardano-sdk/crypto": "~0.4.4", + "@cardano-sdk/util": "~0.17.1", "ts-custom-error": "^3.2.0", "ts-log": "^2.2.4", "webextension-polyfill": "^0.8.0" @@ -952,16 +864,16 @@ } }, "node_modules/@cardano-sdk/dapp-connector/node_modules/@cardano-sdk/core": { - "version": "0.46.5", - "resolved": "https://registry.npmjs.org/@cardano-sdk/core/-/core-0.46.5.tgz", - "integrity": "sha512-Z+iCU8jS1qej5sS2WOVJvpH8r3cclPvuCVkMshQjls+5igoJfsCbZWzxx6tYpXhDzr9hmhlUjXz1rBquefzxrA==", + "version": "0.46.10", + "resolved": "https://registry.npmjs.org/@cardano-sdk/core/-/core-0.46.10.tgz", + "integrity": "sha512-QgEg8EHbGrbGmVfHhkJAG3GLrgReJXr0K7SM/HjhgbvWJDIz3NRrgS3k2NWk7BmaElT4hQX7HFokMaKoV2WeYQ==", "license": "Apache-2.0", "dependencies": { "@biglup/is-cid": "^1.0.3", "@cardano-ogmios/client": "6.9.0", "@cardano-ogmios/schema": "6.9.0", - "@cardano-sdk/crypto": "~0.4.3", - "@cardano-sdk/util": "~0.17.0", + "@cardano-sdk/crypto": "~0.4.4", + "@cardano-sdk/util": "~0.17.1", "@foxglove/crc": "^0.0.3", "@scure/base": "^1.1.1", "fraction.js": "4.0.1", @@ -984,12 +896,12 @@ } }, "node_modules/@cardano-sdk/dapp-connector/node_modules/@cardano-sdk/crypto": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/@cardano-sdk/crypto/-/crypto-0.4.3.tgz", - "integrity": "sha512-PLyTBqWfXrbaOF3v5PsYgm14ApM7rOa2vhqoPZSJANxXlam4G98U1TRngv4Kh0unKxetp/NwbOYy575ou0F8ug==", + "version": "0.4.4", + "resolved": "https://registry.npmjs.org/@cardano-sdk/crypto/-/crypto-0.4.4.tgz", + "integrity": "sha512-jvElFox4TPlTZRtjfw0HlkucRD90EeijfhMT0uD0N6ptkn8sRQXUFO+z+1Zcp9v9L2V324N7+2ThpjjBEoUdXQ==", "license": "Apache-2.0", "dependencies": { - "@cardano-sdk/util": "~0.17.0", + "@cardano-sdk/util": "~0.17.1", "blake2b": "^2.1.4", "i": "^0.3.7", "libsodium-wrappers-sumo": "^0.7.5", @@ -1019,9 +931,9 @@ } }, "node_modules/@cardano-sdk/dapp-connector/node_modules/@cardano-sdk/util": { - "version": "0.17.0", - "resolved": "https://registry.npmjs.org/@cardano-sdk/util/-/util-0.17.0.tgz", - "integrity": "sha512-0o9OraegP7t69hnLFP9gAOYimETPWrg6y+OAN2zHmIikVbl4cp2GUnr7xJkd0T5wWC988ylxfrNC5PfEl/DGxA==", + "version": "0.17.1", + "resolved": "https://registry.npmjs.org/@cardano-sdk/util/-/util-0.17.1.tgz", + "integrity": "sha512-TCYe+wRguW1WgRlbWqhGPhcSBkzVzdIcCVgDDN7wiQk2dew0EWVqjsKeqDZdfwzy/s2kr/ZOgXIGywBn/Bzu/Q==", "license": "Apache-2.0", "dependencies": { "bech32": "^2.0.0", @@ -1229,12 +1141,12 @@ } }, "node_modules/@cardanosolutions/json-bigint": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/@cardanosolutions/json-bigint/-/json-bigint-1.0.1.tgz", - "integrity": "sha512-mbYL6jtHqMFCZnTFhmkmoeDzHMBino0gMiGQnOJE7CwzZzkK2HCpH0MTBk+84QDadMEGX7iFt7uB+levm1a+bQ==", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@cardanosolutions/json-bigint/-/json-bigint-1.0.2.tgz", + "integrity": "sha512-hRgKDFRR5zW6vv6KoymE1PuhKk8hxA/F5YsH37ghIFIYnWAMbVoQ7xRKAT5AEy9HrqWM6HxNQLIZ3r3omg96/w==", "license": "MIT", "dependencies": { - "bignumber.js": "^9.0.0" + "bignumber.js": "^9.3.1" } }, "node_modules/@chainsafe/is-ip": { @@ -1256,6 +1168,7 @@ "version": "1.4.0", "resolved": "https://registry.npmjs.org/@connectrpc/connect/-/connect-1.4.0.tgz", "integrity": "sha512-vZeOkKaAjyV4+RH3+rJZIfDFJAfr+7fyYr6sLDKbYX3uuTVszhFe9/YKf5DNqrDb5cKdKVlYkGn6DTDqMitAnA==", + "license": "Apache-2.0", "peerDependencies": { "@bufbuild/protobuf": "^1.4.2" } @@ -1264,6 +1177,7 @@ "version": "1.4.0", "resolved": "https://registry.npmjs.org/@connectrpc/connect-node/-/connect-node-1.4.0.tgz", "integrity": "sha512-0ANnrr6SvsjevsWEgdzHy7BaHkluZyS6s4xNoVt7RBHFR5V/kT9lPokoIbYUOU9JHzdRgTaS3x5595mwUsu15g==", + "license": "Apache-2.0", "dependencies": { "undici": "^5.28.3" }, @@ -1279,492 +1193,58 @@ "version": "1.4.0", "resolved": "https://registry.npmjs.org/@connectrpc/connect-web/-/connect-web-1.4.0.tgz", "integrity": "sha512-13aO4psFbbm7rdOFGV0De2Za64DY/acMspgloDlcOKzLPPs0yZkhp1OOzAQeiAIr7BM/VOHIA3p8mF0inxCYTA==", - "peerDependencies": { - "@bufbuild/protobuf": "^1.4.2", - "@connectrpc/connect": "1.4.0" - } - }, - "node_modules/@digitalbazaar/http-client": { - "version": "3.4.1", - "resolved": "https://registry.npmjs.org/@digitalbazaar/http-client/-/http-client-3.4.1.tgz", - "integrity": "sha512-Ahk1N+s7urkgj7WvvUND5f8GiWEPfUw0D41hdElaqLgu8wZScI8gdI0q+qWw5N1d35x7GCRH2uk9mi+Uzo9M3g==", - "license": "BSD-3-Clause", - "dependencies": { - "ky": "^0.33.3", - "ky-universal": "^0.11.0", - "undici": "^5.21.2" - }, - "engines": { - "node": ">=14.0" - } - }, - "node_modules/@emnapi/core": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/@emnapi/core/-/core-1.5.0.tgz", - "integrity": "sha512-sbP8GzB1WDzacS8fgNPpHlp6C9VZe+SJP3F90W9rLemaQj2PzIuTEl1qDOYQf58YIpyjViI24y9aPWCjEzY2cg==", - "dev": true, - "license": "MIT", - "optional": true, - "dependencies": { - "@emnapi/wasi-threads": "1.1.0", - "tslib": "^2.4.0" - } - }, - "node_modules/@emnapi/runtime": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.5.0.tgz", - "integrity": "sha512-97/BJ3iXHww3djw6hYIfErCZFee7qCtrneuLa20UXFCOTCfBM2cvQHjWJ2EG0s0MtdNwInarqCTz35i4wWXHsQ==", - "license": "MIT", - "optional": true, - "dependencies": { - "tslib": "^2.4.0" - } - }, - "node_modules/@emnapi/wasi-threads": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@emnapi/wasi-threads/-/wasi-threads-1.1.0.tgz", - "integrity": "sha512-WI0DdZ8xFSbgMjR1sFsKABJ/C5OnRrjT06JXbZKexJGrDuPTzZdDYfFlsgcCXCyf+suG5QU2e/y1Wo2V/OapLQ==", - "dev": true, - "license": "MIT", - "optional": true, - "dependencies": { - "tslib": "^2.4.0" - } - }, - "node_modules/@emurgo/cardano-message-signing-nodejs": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@emurgo/cardano-message-signing-nodejs/-/cardano-message-signing-nodejs-1.1.0.tgz", - "integrity": "sha512-PQRc8K8wZshEdmQenNUzVtiI8oJNF/1uAnBhidee5C4o1l2mDLOW+ur46HWHIFKQ6x8mSJTllcjMscHgzju0gQ==" - }, - "node_modules/@esbuild/aix-ppc64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.25.0.tgz", - "integrity": "sha512-O7vun9Sf8DFjH2UtqK8Ku3LkquL9SZL8OLY1T5NZkA34+wG3OQF7cl4Ql8vdNzM6fzBbYfLaiRLIOZ+2FOCgBQ==", - "cpu": [ - "ppc64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "aix" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/android-arm": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.25.0.tgz", - "integrity": "sha512-PTyWCYYiU0+1eJKmw21lWtC+d08JDZPQ5g+kFyxP0V+es6VPPSUhM6zk8iImp2jbV6GwjX4pap0JFbUQN65X1g==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "android" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/android-arm64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.25.0.tgz", - "integrity": "sha512-grvv8WncGjDSyUBjN9yHXNt+cq0snxXbDxy5pJtzMKGmmpPxeAmAhWxXI+01lU5rwZomDgD3kJwulEnhTRUd6g==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "android" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/android-x64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.25.0.tgz", - "integrity": "sha512-m/ix7SfKG5buCnxasr52+LI78SQ+wgdENi9CqyCXwjVR2X4Jkz+BpC3le3AoBPYTC9NHklwngVXvbJ9/Akhrfg==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "android" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/darwin-arm64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.25.0.tgz", - "integrity": "sha512-mVwdUb5SRkPayVadIOI78K7aAnPamoeFR2bT5nszFUZ9P8UpK4ratOdYbZZXYSqPKMHfS1wdHCJk1P1EZpRdvw==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/darwin-x64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.25.0.tgz", - "integrity": "sha512-DgDaYsPWFTS4S3nWpFcMn/33ZZwAAeAFKNHNa1QN0rI4pUjgqf0f7ONmXf6d22tqTY+H9FNdgeaAa+YIFUn2Rg==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/freebsd-arm64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.25.0.tgz", - "integrity": "sha512-VN4ocxy6dxefN1MepBx/iD1dH5K8qNtNe227I0mnTRjry8tj5MRk4zprLEdG8WPyAPb93/e4pSgi1SoHdgOa4w==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "freebsd" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/freebsd-x64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.25.0.tgz", - "integrity": "sha512-mrSgt7lCh07FY+hDD1TxiTyIHyttn6vnjesnPoVDNmDfOmggTLXRv8Id5fNZey1gl/V2dyVK1VXXqVsQIiAk+A==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "freebsd" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/linux-arm": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.25.0.tgz", - "integrity": "sha512-vkB3IYj2IDo3g9xX7HqhPYxVkNQe8qTK55fraQyTzTX/fxaDtXiEnavv9geOsonh2Fd2RMB+i5cbhu2zMNWJwg==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/linux-arm64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.25.0.tgz", - "integrity": "sha512-9QAQjTWNDM/Vk2bgBl17yWuZxZNQIF0OUUuPZRKoDtqF2k4EtYbpyiG5/Dk7nqeK6kIJWPYldkOcBqjXjrUlmg==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/linux-ia32": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.25.0.tgz", - "integrity": "sha512-43ET5bHbphBegyeqLb7I1eYn2P/JYGNmzzdidq/w0T8E2SsYL1U6un2NFROFRg1JZLTzdCoRomg8Rvf9M6W6Gg==", - "cpu": [ - "ia32" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/linux-loong64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.25.0.tgz", - "integrity": "sha512-fC95c/xyNFueMhClxJmeRIj2yrSMdDfmqJnyOY4ZqsALkDrrKJfIg5NTMSzVBr5YW1jf+l7/cndBfP3MSDpoHw==", - "cpu": [ - "loong64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/linux-mips64el": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.25.0.tgz", - "integrity": "sha512-nkAMFju7KDW73T1DdH7glcyIptm95a7Le8irTQNO/qtkoyypZAnjchQgooFUDQhNAy4iu08N79W4T4pMBwhPwQ==", - "cpu": [ - "mips64el" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/linux-ppc64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.25.0.tgz", - "integrity": "sha512-NhyOejdhRGS8Iwv+KKR2zTq2PpysF9XqY+Zk77vQHqNbo/PwZCzB5/h7VGuREZm1fixhs4Q/qWRSi5zmAiO4Fw==", - "cpu": [ - "ppc64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/linux-riscv64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.25.0.tgz", - "integrity": "sha512-5S/rbP5OY+GHLC5qXp1y/Mx//e92L1YDqkiBbO9TQOvuFXM+iDqUNG5XopAnXoRH3FjIUDkeGcY1cgNvnXp/kA==", - "cpu": [ - "riscv64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/linux-s390x": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.25.0.tgz", - "integrity": "sha512-XM2BFsEBz0Fw37V0zU4CXfcfuACMrppsMFKdYY2WuTS3yi8O1nFOhil/xhKTmE1nPmVyvQJjJivgDT+xh8pXJA==", - "cpu": [ - "s390x" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/linux-x64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.25.0.tgz", - "integrity": "sha512-9yl91rHw/cpwMCNytUDxwj2XjFpxML0y9HAOH9pNVQDpQrBxHy01Dx+vaMu0N1CKa/RzBD2hB4u//nfc+Sd3Cw==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/netbsd-arm64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/netbsd-arm64/-/netbsd-arm64-0.25.0.tgz", - "integrity": "sha512-RuG4PSMPFfrkH6UwCAqBzauBWTygTvb1nxWasEJooGSJ/NwRw7b2HOwyRTQIU97Hq37l3npXoZGYMy3b3xYvPw==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "netbsd" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/netbsd-x64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.25.0.tgz", - "integrity": "sha512-jl+qisSB5jk01N5f7sPCsBENCOlPiS/xptD5yxOx2oqQfyourJwIKLRA2yqWdifj3owQZCL2sn6o08dBzZGQzA==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "netbsd" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/openbsd-arm64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.25.0.tgz", - "integrity": "sha512-21sUNbq2r84YE+SJDfaQRvdgznTD8Xc0oc3p3iW/a1EVWeNj/SdUCbm5U0itZPQYRuRTW20fPMWMpcrciH2EJw==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "openbsd" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/openbsd-x64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.25.0.tgz", - "integrity": "sha512-2gwwriSMPcCFRlPlKx3zLQhfN/2WjJ2NSlg5TKLQOJdV0mSxIcYNTMhk3H3ulL/cak+Xj0lY1Ym9ysDV1igceg==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "openbsd" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@esbuild/sunos-x64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.25.0.tgz", - "integrity": "sha512-bxI7ThgLzPrPz484/S9jLlvUAHYMzy6I0XiU1ZMeAEOBcS0VePBFxh1JjTQt3Xiat5b6Oh4x7UC7IwKQKIJRIg==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "sunos" - ], - "engines": { - "node": ">=18" + "license": "Apache-2.0", + "peerDependencies": { + "@bufbuild/protobuf": "^1.4.2", + "@connectrpc/connect": "1.4.0" } }, - "node_modules/@esbuild/win32-arm64": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.25.0.tgz", - "integrity": "sha512-ZUAc2YK6JW89xTbXvftxdnYy3m4iHIkDtK3CLce8wg8M2L+YZhIvO1DKpxrd0Yr59AeNNkTiic9YLf6FTtXWMw==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "win32" - ], + "node_modules/@digitalbazaar/http-client": { + "version": "3.4.1", + "license": "BSD-3-Clause", + "dependencies": { + "ky": "^0.33.3", + "ky-universal": "^0.11.0", + "undici": "^5.21.2" + }, "engines": { - "node": ">=18" + "node": ">=14.0" } }, - "node_modules/@esbuild/win32-ia32": { - "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.25.0.tgz", - "integrity": "sha512-eSNxISBu8XweVEWG31/JzjkIGbGIJN/TrRoiSVZwZ6pkC6VX4Im/WV2cz559/TXLcYbcrDN8JtKgd9DJVIo8GA==", - "cpu": [ - "ia32" - ], - "dev": true, + "node_modules/@emnapi/runtime": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.6.0.tgz", + "integrity": "sha512-obtUmAHTMjll499P+D9A3axeJFlhdjOWdKUNs/U6QIGT7V5RjcUW1xToAzjvmgTSQhDbYn/NwfTRoJcQ2rNBxA==", "license": "MIT", "optional": true, - "os": [ - "win32" - ], - "engines": { - "node": ">=18" + "dependencies": { + "tslib": "^2.4.0" } }, - "node_modules/@esbuild/win32-x64": { + "node_modules/@emurgo/cardano-message-signing-nodejs": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@emurgo/cardano-message-signing-nodejs/-/cardano-message-signing-nodejs-1.1.0.tgz", + "integrity": "sha512-PQRc8K8wZshEdmQenNUzVtiI8oJNF/1uAnBhidee5C4o1l2mDLOW+ur46HWHIFKQ6x8mSJTllcjMscHgzju0gQ==", + "license": "MIT" + }, + "node_modules/@esbuild/darwin-arm64": { "version": "0.25.0", - "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.25.0.tgz", - "integrity": "sha512-ZENoHJBxA20C2zFzh6AI4fT6RraMzjYw4xKWemRTRmRVtN9c5DcH9r/f2ihEkMjOW5eGgrwCslG/+Y/3bL+DHQ==", "cpu": [ - "x64" + "arm64" ], "dev": true, "license": "MIT", "optional": true, "os": [ - "win32" + "darwin" ], + "peer": true, "engines": { "node": ">=18" } }, "node_modules/@eslint-community/eslint-utils": { "version": "4.4.1", - "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.4.1.tgz", - "integrity": "sha512-s3O3waFUrMV8P/XaF/+ZTp1X9XBZW1a4B97ZnjQF2KYWaFD2A8KyFBsrsfSjEmjn3RGWAIuvlneuZm3CUK3jbA==", "dev": true, "license": "MIT", "dependencies": { @@ -1782,8 +1262,6 @@ }, "node_modules/@eslint-community/regexpp": { "version": "4.12.1", - "resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.12.1.tgz", - "integrity": "sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==", "dev": true, "license": "MIT", "engines": { @@ -1792,8 +1270,6 @@ }, "node_modules/@eslint/eslintrc": { "version": "2.1.4", - "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-2.1.4.tgz", - "integrity": "sha512-269Z39MS6wVJtsoUl10L60WdkhJVdPG24Q4eZTH3nnF6lpvSShEK3wQjDX9JRWAUPvPh7COouPpU9IrqaZFvtQ==", "dev": true, "license": "MIT", "dependencies": { @@ -1816,8 +1292,6 @@ }, "node_modules/@eslint/eslintrc/node_modules/brace-expansion": { "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "dev": true, "license": "MIT", "dependencies": { @@ -1827,8 +1301,6 @@ }, "node_modules/@eslint/eslintrc/node_modules/globals": { "version": "13.24.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-13.24.0.tgz", - "integrity": "sha512-AhO5QUcj8llrbG09iWhPU2B204J1xnPeL8kQmVorSsy+Sjj1sk8gIyh6cUocGmH4L0UuhAJy+hJMRA4mgA4mFQ==", "dev": true, "license": "MIT", "dependencies": { @@ -1843,8 +1315,6 @@ }, "node_modules/@eslint/eslintrc/node_modules/minimatch": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", "dev": true, "license": "ISC", "dependencies": { @@ -1856,8 +1326,6 @@ }, "node_modules/@eslint/eslintrc/node_modules/type-fest": { "version": "0.20.2", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", - "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", "dev": true, "license": "(MIT OR CC0-1.0)", "engines": { @@ -1869,8 +1337,6 @@ }, "node_modules/@eslint/js": { "version": "8.57.1", - "resolved": "https://registry.npmjs.org/@eslint/js/-/js-8.57.1.tgz", - "integrity": "sha512-d9zaMRSTIKDLhctzH12MtXvJKSSUhaHcjV+2Z+GK+EEY7XKpP5yR4x+N3TAcHTcu963nIr+TMcCb4DBCYX1z6Q==", "dev": true, "license": "MIT", "engines": { @@ -1906,8 +1372,6 @@ }, "node_modules/@fastify/busboy": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/@fastify/busboy/-/busboy-2.1.1.tgz", - "integrity": "sha512-vBZP4NlzfOlerQTnba4aqZoMhE/a9HY7HRqoOPaETQcSQuWEIyZMHGfVu6w9wGtGK5fED5qRs2DteVCjOH60sA==", "license": "MIT", "engines": { "node": ">=14" @@ -1915,8 +1379,6 @@ }, "node_modules/@floating-ui/core": { "version": "1.6.9", - "resolved": "https://registry.npmjs.org/@floating-ui/core/-/core-1.6.9.tgz", - "integrity": "sha512-uMXCuQ3BItDUbAMhIXw7UPXRfAlOAvZzdK9BWpE60MCn+Svt3aLn9jsPTi/WNGlRUu2uI0v5S7JiIUsbsvh3fw==", "license": "MIT", "dependencies": { "@floating-ui/utils": "^0.2.9" @@ -1924,8 +1386,6 @@ }, "node_modules/@floating-ui/dom": { "version": "1.6.13", - "resolved": "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.6.13.tgz", - "integrity": "sha512-umqzocjDgNRGTuO7Q8CU32dkHkECqI8ZdMZ5Swb6QAM0t5rnlrN3lGo1hdpscRd3WS8T6DKYK4ephgIH9iRh3w==", "license": "MIT", "dependencies": { "@floating-ui/core": "^1.6.0", @@ -1934,8 +1394,6 @@ }, "node_modules/@floating-ui/react-dom": { "version": "2.1.2", - "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.1.2.tgz", - "integrity": "sha512-06okr5cgPzMNBy+Ycse2A6udMi4bqwW/zgBF/rwjcNqWkyr82Mcg8b0vjX8OJpZFy/FKjJmw6wV7t44kK6kW7A==", "license": "MIT", "dependencies": { "@floating-ui/dom": "^1.0.0" @@ -1947,8 +1405,6 @@ }, "node_modules/@floating-ui/utils": { "version": "0.2.9", - "resolved": "https://registry.npmjs.org/@floating-ui/utils/-/utils-0.2.9.tgz", - "integrity": "sha512-MDWhGtE+eHw5JW7lq4qhc5yRLS11ERl1c7Z6Xd0a58DozHES6EnNNwUWbMiG4J9Cgj053Bhk8zvlhFYKVhULwg==", "license": "MIT" }, "node_modules/@foxglove/crc": { @@ -2071,8 +1527,6 @@ }, "node_modules/@hookform/resolvers": { "version": "3.10.0", - "resolved": "https://registry.npmjs.org/@hookform/resolvers/-/resolvers-3.10.0.tgz", - "integrity": "sha512-79Dv+3mDF7i+2ajj7SkypSKHhl1cbln1OGavqrsF7p6mbUv11xpqpacPsGDCTRvCSjEEIez2ef1NveSVL3b0Ag==", "license": "MIT", "peerDependencies": { "react-hook-form": "^7.0.0" @@ -2080,9 +1534,6 @@ }, "node_modules/@humanwhocodes/config-array": { "version": "0.13.0", - "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.13.0.tgz", - "integrity": "sha512-DZLEEqFWQFiyK6h5YIeynKx7JlvCYWL0cImfSRXZ9l4Sg2efkFGTuFf6vzXjK1cq6IYkU+Eg/JizXw+TD2vRNw==", - "deprecated": "Use @eslint/config-array instead", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -2096,8 +1547,6 @@ }, "node_modules/@humanwhocodes/config-array/node_modules/brace-expansion": { "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "dev": true, "license": "MIT", "dependencies": { @@ -2107,8 +1556,6 @@ }, "node_modules/@humanwhocodes/config-array/node_modules/minimatch": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", "dev": true, "license": "ISC", "dependencies": { @@ -2120,8 +1567,6 @@ }, "node_modules/@humanwhocodes/module-importer": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz", - "integrity": "sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==", "dev": true, "license": "Apache-2.0", "engines": { @@ -2134,9 +1579,6 @@ }, "node_modules/@humanwhocodes/object-schema": { "version": "2.0.3", - "resolved": "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-2.0.3.tgz", - "integrity": "sha512-93zYdMES/c1D69yZiKDBj0V24vqNzB/koF26KPaagAfd3P/4gUlh3Dys5ogAK+Exi9QyzlD8x/08Zt7wIKcDcA==", - "deprecated": "Use @eslint/object-schema instead", "dev": true, "license": "BSD-3-Clause" }, @@ -2144,6 +1586,7 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/@img/colour/-/colour-1.0.0.tgz", "integrity": "sha512-A5P/LfWGFSl6nsckYtjw9da+19jB8hkJ6ACTGcDfEJ0aE+l2n2El7dsVM7UVHZQ9s2lmYMWlrS21YLy2IR1LUw==", + "license": "MIT", "optional": true, "engines": { "node": ">=18" @@ -2156,6 +1599,7 @@ "cpu": [ "arm64" ], + "license": "Apache-2.0", "optional": true, "os": [ "darwin" @@ -2177,6 +1621,7 @@ "cpu": [ "x64" ], + "license": "Apache-2.0", "optional": true, "os": [ "darwin" @@ -2198,6 +1643,7 @@ "cpu": [ "arm64" ], + "license": "LGPL-3.0-or-later", "optional": true, "os": [ "darwin" @@ -2213,6 +1659,7 @@ "cpu": [ "x64" ], + "license": "LGPL-3.0-or-later", "optional": true, "os": [ "darwin" @@ -2228,6 +1675,7 @@ "cpu": [ "arm" ], + "license": "LGPL-3.0-or-later", "optional": true, "os": [ "linux" @@ -2243,6 +1691,7 @@ "cpu": [ "arm64" ], + "license": "LGPL-3.0-or-later", "optional": true, "os": [ "linux" @@ -2258,6 +1707,7 @@ "cpu": [ "ppc64" ], + "license": "LGPL-3.0-or-later", "optional": true, "os": [ "linux" @@ -2273,6 +1723,7 @@ "cpu": [ "s390x" ], + "license": "LGPL-3.0-or-later", "optional": true, "os": [ "linux" @@ -2288,6 +1739,7 @@ "cpu": [ "x64" ], + "license": "LGPL-3.0-or-later", "optional": true, "os": [ "linux" @@ -2303,6 +1755,7 @@ "cpu": [ "arm64" ], + "license": "LGPL-3.0-or-later", "optional": true, "os": [ "linux" @@ -2318,6 +1771,7 @@ "cpu": [ "x64" ], + "license": "LGPL-3.0-or-later", "optional": true, "os": [ "linux" @@ -2333,6 +1787,7 @@ "cpu": [ "arm" ], + "license": "Apache-2.0", "optional": true, "os": [ "linux" @@ -2354,6 +1809,7 @@ "cpu": [ "arm64" ], + "license": "Apache-2.0", "optional": true, "os": [ "linux" @@ -2375,6 +1831,7 @@ "cpu": [ "ppc64" ], + "license": "Apache-2.0", "optional": true, "os": [ "linux" @@ -2396,6 +1853,7 @@ "cpu": [ "s390x" ], + "license": "Apache-2.0", "optional": true, "os": [ "linux" @@ -2417,6 +1875,7 @@ "cpu": [ "x64" ], + "license": "Apache-2.0", "optional": true, "os": [ "linux" @@ -2438,6 +1897,7 @@ "cpu": [ "arm64" ], + "license": "Apache-2.0", "optional": true, "os": [ "linux" @@ -2459,6 +1919,7 @@ "cpu": [ "x64" ], + "license": "Apache-2.0", "optional": true, "os": [ "linux" @@ -2480,6 +1941,7 @@ "cpu": [ "wasm32" ], + "license": "Apache-2.0 AND LGPL-3.0-or-later AND MIT", "optional": true, "dependencies": { "@emnapi/runtime": "^1.5.0" @@ -2498,6 +1960,7 @@ "cpu": [ "arm64" ], + "license": "Apache-2.0 AND LGPL-3.0-or-later", "optional": true, "os": [ "win32" @@ -2516,6 +1979,7 @@ "cpu": [ "ia32" ], + "license": "Apache-2.0 AND LGPL-3.0-or-later", "optional": true, "os": [ "win32" @@ -2534,6 +1998,7 @@ "cpu": [ "x64" ], + "license": "Apache-2.0 AND LGPL-3.0-or-later", "optional": true, "os": [ "win32" @@ -2547,8 +2012,6 @@ }, "node_modules/@isaacs/cliui": { "version": "8.0.2", - "resolved": "https://registry.npmjs.org/@isaacs/cliui/-/cliui-8.0.2.tgz", - "integrity": "sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==", "license": "ISC", "dependencies": { "string-width": "^5.1.2", @@ -2564,8 +2027,6 @@ }, "node_modules/@isaacs/cliui/node_modules/ansi-regex": { "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz", - "integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==", "license": "MIT", "engines": { "node": ">=12" @@ -2576,8 +2037,6 @@ }, "node_modules/@isaacs/cliui/node_modules/strip-ansi": { "version": "7.1.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", - "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", "license": "MIT", "dependencies": { "ansi-regex": "^6.0.1" @@ -2591,8 +2050,6 @@ }, "node_modules/@istanbuljs/load-nyc-config": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@istanbuljs/load-nyc-config/-/load-nyc-config-1.1.0.tgz", - "integrity": "sha512-VjeHSlIzpv/NyD3N0YuHfXOPDIixcA1q2ZV98wsMqcYlPmv2n3Yb2lYP9XMElnaFVXg5A7YLTeLu6V84uQDjmQ==", "dev": true, "license": "ISC", "dependencies": { @@ -2608,8 +2065,6 @@ }, "node_modules/@istanbuljs/load-nyc-config/node_modules/argparse": { "version": "1.0.10", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", - "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", "dev": true, "license": "MIT", "dependencies": { @@ -2618,8 +2073,6 @@ }, "node_modules/@istanbuljs/load-nyc-config/node_modules/find-up": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", - "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", "dev": true, "license": "MIT", "dependencies": { @@ -2632,8 +2085,6 @@ }, "node_modules/@istanbuljs/load-nyc-config/node_modules/js-yaml": { "version": "3.14.1", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.1.tgz", - "integrity": "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==", "dev": true, "license": "MIT", "dependencies": { @@ -2646,8 +2097,6 @@ }, "node_modules/@istanbuljs/load-nyc-config/node_modules/locate-path": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", - "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", "dev": true, "license": "MIT", "dependencies": { @@ -2659,8 +2108,6 @@ }, "node_modules/@istanbuljs/load-nyc-config/node_modules/p-limit": { "version": "2.3.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", - "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", "dev": true, "license": "MIT", "dependencies": { @@ -2675,8 +2122,6 @@ }, "node_modules/@istanbuljs/load-nyc-config/node_modules/p-locate": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", - "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", "dev": true, "license": "MIT", "dependencies": { @@ -2688,8 +2133,6 @@ }, "node_modules/@istanbuljs/load-nyc-config/node_modules/resolve-from": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", - "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==", "dev": true, "license": "MIT", "engines": { @@ -2698,15 +2141,11 @@ }, "node_modules/@istanbuljs/load-nyc-config/node_modules/sprintf-js": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==", "dev": true, "license": "BSD-3-Clause" }, "node_modules/@istanbuljs/schema": { "version": "0.1.3", - "resolved": "https://registry.npmjs.org/@istanbuljs/schema/-/schema-0.1.3.tgz", - "integrity": "sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA==", "dev": true, "license": "MIT", "engines": { @@ -2715,8 +2154,6 @@ }, "node_modules/@jest/console": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/@jest/console/-/console-30.1.2.tgz", - "integrity": "sha512-BGMAxj8VRmoD0MoA/jo9alMXSRoqW8KPeqOfEo1ncxnRLatTBCpRoOwlwlEMdudp68Q6WSGwYrrLtTGOh8fLzw==", "dev": true, "license": "MIT", "dependencies": { @@ -2733,8 +2170,6 @@ }, "node_modules/@jest/core": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/@jest/core/-/core-30.1.3.tgz", - "integrity": "sha512-LIQz7NEDDO1+eyOA2ZmkiAyYvZuo6s1UxD/e2IHldR6D7UYogVq3arTmli07MkENLq6/3JEQjp0mA8rrHHJ8KQ==", "dev": true, "license": "MIT", "dependencies": { @@ -2781,8 +2216,6 @@ }, "node_modules/@jest/core/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -2794,8 +2227,6 @@ }, "node_modules/@jest/core/node_modules/jest-config": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest-config/-/jest-config-30.1.3.tgz", - "integrity": "sha512-M/f7gqdQEPgZNA181Myz+GXCe8jXcJsGjCMXUzRj22FIXsZOyHNte84e0exntOvdPaeh9tA0w+B8qlP2fAezfw==", "dev": true, "license": "MIT", "dependencies": { @@ -2846,8 +2277,6 @@ }, "node_modules/@jest/core/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -2861,15 +2290,11 @@ }, "node_modules/@jest/core/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/@jest/diff-sequences": { "version": "30.0.1", - "resolved": "https://registry.npmjs.org/@jest/diff-sequences/-/diff-sequences-30.0.1.tgz", - "integrity": "sha512-n5H8QLDJ47QqbCNn5SuFjCRDrOLEZ0h8vAHCK5RL9Ls7Xa8AQLa/YxAc9UjFqoEDM48muwtBGjtMY5cr0PLDCw==", "dev": true, "license": "MIT", "engines": { @@ -2878,8 +2303,6 @@ }, "node_modules/@jest/environment": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/@jest/environment/-/environment-30.1.2.tgz", - "integrity": "sha512-N8t1Ytw4/mr9uN28OnVf0SYE2dGhaIxOVYcwsf9IInBKjvofAjbFRvedvBBlyTYk2knbJTiEjEJ2PyyDIBnd9w==", "dev": true, "license": "MIT", "dependencies": { @@ -2894,8 +2317,6 @@ }, "node_modules/@jest/expect": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/@jest/expect/-/expect-30.1.2.tgz", - "integrity": "sha512-tyaIExOwQRCxPCGNC05lIjWJztDwk2gPDNSDGg1zitXJJ8dC3++G/CRjE5mb2wQsf89+lsgAgqxxNpDLiCViTA==", "dev": true, "license": "MIT", "dependencies": { @@ -2908,8 +2329,6 @@ }, "node_modules/@jest/expect-utils": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/@jest/expect-utils/-/expect-utils-30.1.2.tgz", - "integrity": "sha512-HXy1qT/bfdjCv7iC336ExbqqYtZvljrV8odNdso7dWK9bSeHtLlvwWWC3YSybSPL03Gg5rug6WLCZAZFH72m0A==", "dev": true, "license": "MIT", "dependencies": { @@ -2921,8 +2340,6 @@ }, "node_modules/@jest/fake-timers": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/@jest/fake-timers/-/fake-timers-30.1.2.tgz", - "integrity": "sha512-Beljfv9AYkr9K+ETX9tvV61rJTY706BhBUtiaepQHeEGfe0DbpvUA5Z3fomwc5Xkhns6NWrcFDZn+72fLieUnA==", "dev": true, "license": "MIT", "dependencies": { @@ -2939,8 +2356,6 @@ }, "node_modules/@jest/get-type": { "version": "30.1.0", - "resolved": "https://registry.npmjs.org/@jest/get-type/-/get-type-30.1.0.tgz", - "integrity": "sha512-eMbZE2hUnx1WV0pmURZY9XoXPkUYjpc55mb0CrhtdWLtzMQPFvu/rZkTLZFTsdaVQa+Tr4eWAteqcUzoawq/uA==", "dev": true, "license": "MIT", "engines": { @@ -2949,8 +2364,6 @@ }, "node_modules/@jest/globals": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/@jest/globals/-/globals-30.1.2.tgz", - "integrity": "sha512-teNTPZ8yZe3ahbYnvnVRDeOjr+3pu2uiAtNtrEsiMjVPPj+cXd5E/fr8BL7v/T7F31vYdEHrI5cC/2OoO/vM9A==", "dev": true, "license": "MIT", "dependencies": { @@ -2965,8 +2378,6 @@ }, "node_modules/@jest/pattern": { "version": "30.0.1", - "resolved": "https://registry.npmjs.org/@jest/pattern/-/pattern-30.0.1.tgz", - "integrity": "sha512-gWp7NfQW27LaBQz3TITS8L7ZCQ0TLvtmI//4OwlQRx4rnWxcPNIYjxZpDcN4+UlGxgm3jS5QPz8IPTCkb59wZA==", "dev": true, "license": "MIT", "dependencies": { @@ -2979,8 +2390,6 @@ }, "node_modules/@jest/reporters": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/@jest/reporters/-/reporters-30.1.3.tgz", - "integrity": "sha512-VWEQmJWfXMOrzdFEOyGjUEOuVXllgZsoPtEHZzfdNz18RmzJ5nlR6kp8hDdY8dDS1yGOXAY7DHT+AOHIPSBV0w==", "dev": true, "license": "MIT", "dependencies": { @@ -3022,8 +2431,6 @@ }, "node_modules/@jest/schemas": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-30.0.5.tgz", - "integrity": "sha512-DmdYgtezMkh3cpU8/1uyXakv3tJRcmcXxBOcO0tbaozPwpmh4YMsnWrQm9ZmZMfa5ocbxzbFk6O4bDPEc/iAnA==", "dev": true, "license": "MIT", "dependencies": { @@ -3035,8 +2442,6 @@ }, "node_modules/@jest/snapshot-utils": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/@jest/snapshot-utils/-/snapshot-utils-30.1.2.tgz", - "integrity": "sha512-vHoMTpimcPSR7OxS2S0V1Cpg8eKDRxucHjoWl5u4RQcnxqQrV3avETiFpl8etn4dqxEGarBeHbIBety/f8mLXw==", "dev": true, "license": "MIT", "dependencies": { @@ -3051,8 +2456,6 @@ }, "node_modules/@jest/source-map": { "version": "30.0.1", - "resolved": "https://registry.npmjs.org/@jest/source-map/-/source-map-30.0.1.tgz", - "integrity": "sha512-MIRWMUUR3sdbP36oyNyhbThLHyJ2eEDClPCiHVbrYAe5g3CHRArIVpBw7cdSB5fr+ofSfIb2Tnsw8iEHL0PYQg==", "dev": true, "license": "MIT", "dependencies": { @@ -3066,8 +2469,6 @@ }, "node_modules/@jest/test-result": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/@jest/test-result/-/test-result-30.1.3.tgz", - "integrity": "sha512-P9IV8T24D43cNRANPPokn7tZh0FAFnYS2HIfi5vK18CjRkTDR9Y3e1BoEcAJnl4ghZZF4Ecda4M/k41QkvurEQ==", "dev": true, "license": "MIT", "dependencies": { @@ -3082,8 +2483,6 @@ }, "node_modules/@jest/test-sequencer": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/@jest/test-sequencer/-/test-sequencer-30.1.3.tgz", - "integrity": "sha512-82J+hzC0qeQIiiZDThh+YUadvshdBswi5nuyXlEmXzrhw5ZQSRHeQ5LpVMD/xc8B3wPePvs6VMzHnntxL+4E3w==", "dev": true, "license": "MIT", "dependencies": { @@ -3098,8 +2497,6 @@ }, "node_modules/@jest/transform": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/@jest/transform/-/transform-30.1.2.tgz", - "integrity": "sha512-UYYFGifSgfjujf1Cbd3iU/IQoSd6uwsj8XHj5DSDf5ERDcWMdJOPTkHWXj4U+Z/uMagyOQZ6Vne8C4nRIrCxqA==", "dev": true, "license": "MIT", "dependencies": { @@ -3125,8 +2522,6 @@ }, "node_modules/@jest/types": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/@jest/types/-/types-30.0.5.tgz", - "integrity": "sha512-aREYa3aku9SSnea4aX6bhKn4bgv3AXkgijoQgbYV3yvbiGt6z+MQ85+6mIhx9DsKW2BuB/cLR/A+tcMThx+KLQ==", "dev": true, "license": "MIT", "dependencies": { @@ -3144,8 +2539,6 @@ }, "node_modules/@jinglescode/nostr-chat-plugin": { "version": "0.0.11", - "resolved": "https://registry.npmjs.org/@jinglescode/nostr-chat-plugin/-/nostr-chat-plugin-0.0.11.tgz", - "integrity": "sha512-teAjUTPqbfI353M+Ip/QcT7LnA4VpUh4jHbbo0xryhajAXlNIYpUDs5bbTa0M4IroU/aMA65Ba8iaqhIta0D0g==", "license": "Apache-2.0", "dependencies": { "nostr-tools": "^2.8.0" @@ -3156,8 +2549,6 @@ }, "node_modules/@jridgewell/gen-mapping": { "version": "0.3.13", - "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.13.tgz", - "integrity": "sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA==", "license": "MIT", "dependencies": { "@jridgewell/sourcemap-codec": "^1.5.0", @@ -3166,8 +2557,6 @@ }, "node_modules/@jridgewell/remapping": { "version": "2.3.5", - "resolved": "https://registry.npmjs.org/@jridgewell/remapping/-/remapping-2.3.5.tgz", - "integrity": "sha512-LI9u/+laYG4Ds1TDKSJW2YPrIlcVYOwi2fUC6xB43lueCjgxV4lffOCZCtYFiH6TNOX+tQKXx97T4IKHbhyHEQ==", "license": "MIT", "dependencies": { "@jridgewell/gen-mapping": "^0.3.5", @@ -3176,8 +2565,6 @@ }, "node_modules/@jridgewell/resolve-uri": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", - "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", "license": "MIT", "engines": { "node": ">=6.0.0" @@ -3185,14 +2572,10 @@ }, "node_modules/@jridgewell/sourcemap-codec": { "version": "1.5.0", - "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.0.tgz", - "integrity": "sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==", "license": "MIT" }, "node_modules/@jridgewell/trace-mapping": { "version": "0.3.31", - "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.31.tgz", - "integrity": "sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw==", "license": "MIT", "dependencies": { "@jridgewell/resolve-uri": "^3.1.0", @@ -3201,8 +2584,6 @@ }, "node_modules/@jsdevtools/ono": { "version": "7.1.3", - "resolved": "https://registry.npmjs.org/@jsdevtools/ono/-/ono-7.1.3.tgz", - "integrity": "sha512-4JQNk+3mVzK3xh2rqd6RB4J46qUR19azEHBneZyTZM+c456qOrbbM/5xcR8huNCCcbVt7+UmizG6GuUvPvKUYg==", "license": "MIT" }, "node_modules/@leichtgewicht/ip-codec": { @@ -3213,17 +2594,15 @@ }, "node_modules/@mediapipe/tasks-vision": { "version": "0.10.17", - "resolved": "https://registry.npmjs.org/@mediapipe/tasks-vision/-/tasks-vision-0.10.17.tgz", - "integrity": "sha512-CZWV/q6TTe8ta61cZXjfnnHsfWIdFhms03M9T7Cnd5y2mdpylJM0rF1qRq+wsQVRMLz1OYPVEBU9ph2Bx8cxrg==", "license": "Apache-2.0" }, "node_modules/@meshsdk/bitcoin": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/bitcoin/-/bitcoin-1.9.0-beta.77.tgz", - "integrity": "sha512-GqBatQtOYXvrNXgaCDXYuXHDgE7fJhD8Yof26eZUGg1BIpzqP4P58tLGUWYsUXRNyLBBYmFtJfCZk2RFPz3cDw==", + "version": "1.9.0-beta.83", + "resolved": "https://registry.npmjs.org/@meshsdk/bitcoin/-/bitcoin-1.9.0-beta.83.tgz", + "integrity": "sha512-zKY+6liYizOm/afgqPdfqdlkpf90K9t07o1fsWp51s88llEasnppjbYb4jdKKxhaOqsQlJMGEZAAloMFkSSaGA==", "dependencies": { "@bitcoin-js/tiny-secp256k1-asmjs": "^2.2.3", - "bip174": "^3.0.0-rc.1", + "bip174": "^3.0.0", "bip32": "^4.0.0", "bip39": "^3.1.0", "bitcoinjs-lib": "^6.1.7", @@ -3231,9 +2610,9 @@ } }, "node_modules/@meshsdk/common": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/common/-/common-1.9.0-beta.77.tgz", - "integrity": "sha512-8s7mkB2Nl74NJ9zp6ZzfKOO05LOqYoSOi4U+g5Pf46d9c7m1ZgX9A/rvFrAZ8wxVUPRfs0NLp+7Q0K14Tu/xxg==", + "version": "1.9.0-beta.83", + "resolved": "https://registry.npmjs.org/@meshsdk/common/-/common-1.9.0-beta.83.tgz", + "integrity": "sha512-eoOaCqrxUtzJ25ZKo6mKQ33T+rR2DFv+BF6wwsZEsQzdvQjMxUKxk5WB9ix/Ow0NuEsUSSX1u6HhZnQkBfYCnw==", "license": "Apache-2.0", "dependencies": { "bech32": "^2.0.0", @@ -3243,27 +2622,28 @@ } }, "node_modules/@meshsdk/core": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/core/-/core-1.9.0-beta.77.tgz", - "integrity": "sha512-OGHsMxlU8M5fIDJxhZ8aFTp/R6krDGZ1g4eYac+LMQfjs1snHhCX7SdAYGnZHiHK4QF4NM/rpsm1nAzwn5oJQA==", + "version": "1.9.0-beta.83", + "resolved": "https://registry.npmjs.org/@meshsdk/core/-/core-1.9.0-beta.83.tgz", + "integrity": "sha512-eCMvwpCo7lpBpIP5FaIazp0yeLhPSU9w2FFERmuo/jHBEiY/IWKv0I47Fa0Ygi78BCIHeRAZ9SDrlyVqvPk6kw==", + "license": "Apache-2.0", "dependencies": { - "@meshsdk/common": "1.9.0-beta.77", - "@meshsdk/core-cst": "1.9.0-beta.77", - "@meshsdk/provider": "1.9.0-beta.77", - "@meshsdk/react": "1.9.0-beta.77", - "@meshsdk/transaction": "1.9.0-beta.77", - "@meshsdk/wallet": "1.9.0-beta.77" + "@meshsdk/common": "1.9.0-beta.83", + "@meshsdk/core-cst": "1.9.0-beta.83", + "@meshsdk/provider": "1.9.0-beta.83", + "@meshsdk/react": "1.9.0-beta.83", + "@meshsdk/transaction": "1.9.0-beta.83", + "@meshsdk/wallet": "1.9.0-beta.83" } }, "node_modules/@meshsdk/core-csl": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/core-csl/-/core-csl-1.9.0-beta.77.tgz", - "integrity": "sha512-AxDudJbrB49xYAU9K8DEyZD/l3sdnP2/Bi7qYJreIV+i9VUpRtTDZPKlXB/KYibQpvEbOdUZEF2+AivxOBR4pQ==", + "version": "1.9.0-beta.83", + "resolved": "https://registry.npmjs.org/@meshsdk/core-csl/-/core-csl-1.9.0-beta.83.tgz", + "integrity": "sha512-9lMVvSpP8Mg7MoQ7fg0eY28oJTSlqig33OGMWRovbsvX0re1S4xx8HIZzA86PTyINY3m71/HV2o/dZ3gPnT50g==", "license": "Apache-2.0", "dependencies": { - "@meshsdk/common": "1.9.0-beta.77", - "@sidan-lab/whisky-js-browser": "^1.0.9", - "@sidan-lab/whisky-js-nodejs": "^1.0.9", + "@meshsdk/common": "1.9.0-beta.83", + "@sidan-lab/whisky-js-browser": "^1.0.11", + "@sidan-lab/whisky-js-nodejs": "^1.0.11", "@types/base32-encoding": "^1.0.2", "base32-encoding": "^1.0.0", "bech32": "^2.0.0", @@ -3271,9 +2651,10 @@ } }, "node_modules/@meshsdk/core-cst": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/core-cst/-/core-cst-1.9.0-beta.77.tgz", - "integrity": "sha512-2Qz2bI4eY/KLFw+uAqZvLx5Dxf5aTPCC7dIR1chMrTfl8vFu0OP9tslVI7iK6T54Z3YcV7sh1f3bcE/8N3Hmjw==", + "version": "1.9.0-beta.83", + "resolved": "https://registry.npmjs.org/@meshsdk/core-cst/-/core-cst-1.9.0-beta.83.tgz", + "integrity": "sha512-4BflalwqS+gfE9I0Wi6ZkkSsZWEESXKqbmYSgHMzK3EHZ6pA/KVp7MFJ3Nf3ctZXu9YmelWI2rA7gNrWJxU74A==", + "license": "Apache-2.0", "dependencies": { "@cardano-sdk/core": "^0.45.5", "@cardano-sdk/crypto": "^0.2.2", @@ -3283,7 +2664,7 @@ "@harmoniclabs/pair": "^1.0.0", "@harmoniclabs/plutus-data": "1.2.4", "@harmoniclabs/uplc": "1.2.4", - "@meshsdk/common": "1.9.0-beta.77", + "@meshsdk/common": "1.9.0-beta.83", "@types/base32-encoding": "^1.0.2", "base32-encoding": "^1.0.0", "bech32": "^2.0.0", @@ -3291,42 +2672,15 @@ "bn.js": "^5.2.0" } }, - "node_modules/@meshsdk/core/node_modules/@meshsdk/transaction": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/transaction/-/transaction-1.9.0-beta.77.tgz", - "integrity": "sha512-qfzl3g8fuHRZWCr+7Oy8MgvAoGjz2sDVhXlvapSOpXH8cNIKIEOuv6IirihSFmO5Yhm4aD9pwMnl5Rg5Fjwwew==", - "dependencies": { - "@cardano-sdk/core": "^0.45.5", - "@cardano-sdk/input-selection": "^0.13.33", - "@cardano-sdk/util": "^0.15.5", - "@meshsdk/common": "1.9.0-beta.77", - "@meshsdk/core-cst": "1.9.0-beta.77", - "json-bigint": "^1.0.0" - } - }, - "node_modules/@meshsdk/core/node_modules/@meshsdk/wallet": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/wallet/-/wallet-1.9.0-beta.77.tgz", - "integrity": "sha512-Lus7goOYSddCo5R0ZRGyno7ymoFbgVtepdAgZGE+u+V3D37XFefxDTaDj9pDwJyRFjl3XVV881dmZVY5HOnmCg==", - "dependencies": { - "@meshsdk/common": "1.9.0-beta.77", - "@meshsdk/core-cst": "1.9.0-beta.77", - "@meshsdk/transaction": "1.9.0-beta.77", - "@simplewebauthn/browser": "^13.0.0" - } - }, - "node_modules/@meshsdk/core/node_modules/@simplewebauthn/browser": { - "version": "13.2.0", - "resolved": "https://registry.npmjs.org/@simplewebauthn/browser/-/browser-13.2.0.tgz", - "integrity": "sha512-N3fuA1AAnTo5gCStYoIoiasPccC+xPLx2YU88Dv0GeAmPQTWHETlZQq5xZ0DgUq1H9loXMWQH5qqUjcI7BHJ1A==" - }, "node_modules/@meshsdk/provider": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/provider/-/provider-1.9.0-beta.77.tgz", - "integrity": "sha512-xc6mXuUhgODOVPvOBq0++lRDujgoFY5NYp3XHuXrA6EWBSkWaVhc1ZKnzIa00WFBb2ofYTpw4BbJEC/5VyyyZA==", + "version": "1.9.0-beta.83", + "resolved": "https://registry.npmjs.org/@meshsdk/provider/-/provider-1.9.0-beta.83.tgz", + "integrity": "sha512-UipX6IDalkqrq+yYoM7wFXHlDSVyAOChrMeM3b8FNZgnXYWcBFFCe+fgKQpxwGK0fOy6kIKWPs5jDccZydGNKA==", + "license": "Apache-2.0", "dependencies": { - "@meshsdk/common": "1.9.0-beta.77", - "@meshsdk/core-cst": "1.9.0-beta.77", + "@meshsdk/bitcoin": "1.9.0-beta.83", + "@meshsdk/common": "1.9.0-beta.83", + "@meshsdk/core-cst": "1.9.0-beta.83", "@utxorpc/sdk": "^0.6.7", "@utxorpc/spec": "^0.16.0", "axios": "^1.7.2", @@ -3334,15 +2688,16 @@ } }, "node_modules/@meshsdk/react": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/react/-/react-1.9.0-beta.77.tgz", - "integrity": "sha512-SitSTTA409mWv7zgBqz7tCAwsAiwVyKiZS+TSj00y0hFb4hivuZ6YYci0PHlyOgSgr+bVdxNPNxQ5ZnUDTFAaA==", + "version": "1.9.0-beta.83", + "resolved": "https://registry.npmjs.org/@meshsdk/react/-/react-1.9.0-beta.83.tgz", + "integrity": "sha512-9M2BM3nX4spHA6hSdDQt+NptI3PXJePl5hIVA8GNcj8i8eOJIYPFwP42wL7Ee202uuVQ9boWeAcEDpVl3JKotQ==", + "license": "Apache-2.0", "dependencies": { "@fabianbormann/cardano-peer-connect": "^1.2.18", - "@meshsdk/bitcoin": "1.9.0-beta.77", - "@meshsdk/common": "1.9.0-beta.77", - "@meshsdk/transaction": "1.9.0-beta.77", - "@meshsdk/wallet": "1.9.0-beta.77", + "@meshsdk/bitcoin": "1.9.0-beta.83", + "@meshsdk/common": "1.9.0-beta.83", + "@meshsdk/transaction": "1.9.0-beta.83", + "@meshsdk/wallet": "1.9.0-beta.83", "@meshsdk/web3-sdk": "0.0.50", "@radix-ui/react-dialog": "^1.1.2", "@radix-ui/react-dropdown-menu": "^2.1.2", @@ -3358,133 +2713,36 @@ "react-dom": ">=16.0.0 <20.0.0 || >=16.0.0-rc <20.0.0-rc || >=19.0.0-rc" } }, - "node_modules/@meshsdk/react/node_modules/@meshsdk/transaction": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/transaction/-/transaction-1.9.0-beta.77.tgz", - "integrity": "sha512-qfzl3g8fuHRZWCr+7Oy8MgvAoGjz2sDVhXlvapSOpXH8cNIKIEOuv6IirihSFmO5Yhm4aD9pwMnl5Rg5Fjwwew==", - "dependencies": { - "@cardano-sdk/core": "^0.45.5", - "@cardano-sdk/input-selection": "^0.13.33", - "@cardano-sdk/util": "^0.15.5", - "@meshsdk/common": "1.9.0-beta.77", - "@meshsdk/core-cst": "1.9.0-beta.77", - "json-bigint": "^1.0.0" - } - }, - "node_modules/@meshsdk/react/node_modules/@meshsdk/wallet": { - "version": "1.9.0-beta.77", - "resolved": "https://registry.npmjs.org/@meshsdk/wallet/-/wallet-1.9.0-beta.77.tgz", - "integrity": "sha512-Lus7goOYSddCo5R0ZRGyno7ymoFbgVtepdAgZGE+u+V3D37XFefxDTaDj9pDwJyRFjl3XVV881dmZVY5HOnmCg==", - "dependencies": { - "@meshsdk/common": "1.9.0-beta.77", - "@meshsdk/core-cst": "1.9.0-beta.77", - "@meshsdk/transaction": "1.9.0-beta.77", - "@simplewebauthn/browser": "^13.0.0" - } - }, - "node_modules/@meshsdk/react/node_modules/@simplewebauthn/browser": { - "version": "13.2.0", - "resolved": "https://registry.npmjs.org/@simplewebauthn/browser/-/browser-13.2.0.tgz", - "integrity": "sha512-N3fuA1AAnTo5gCStYoIoiasPccC+xPLx2YU88Dv0GeAmPQTWHETlZQq5xZ0DgUq1H9loXMWQH5qqUjcI7BHJ1A==" - }, "node_modules/@meshsdk/transaction": { - "version": "1.9.0-beta.68", - "resolved": "https://registry.npmjs.org/@meshsdk/transaction/-/transaction-1.9.0-beta.68.tgz", - "integrity": "sha512-FsVKqtCyAGrk3IRzEKIr4R6SNYFEGClwCPzM6LlfuC1z97lScM7yP9FgwkOMe4ZPXn4BS32i62X7EdQVIaQwMg==", + "version": "1.9.0-beta.83", + "resolved": "https://registry.npmjs.org/@meshsdk/transaction/-/transaction-1.9.0-beta.83.tgz", + "integrity": "sha512-B7zIjJT/v5IfyPvY1+peeo8mPgIWASbEi3bjX03iusVpixoESRb1ZAompsEJiJJDn/Q2hSVX9mqH+WTWoUFkgQ==", "license": "Apache-2.0", "dependencies": { "@cardano-sdk/core": "^0.45.5", "@cardano-sdk/input-selection": "^0.13.33", "@cardano-sdk/util": "^0.15.5", - "@meshsdk/common": "1.9.0-beta.68", - "@meshsdk/core-cst": "1.9.0-beta.68", + "@meshsdk/common": "1.9.0-beta.83", + "@meshsdk/core-cst": "1.9.0-beta.83", "json-bigint": "^1.0.0" } }, - "node_modules/@meshsdk/transaction/node_modules/@meshsdk/common": { - "version": "1.9.0-beta.68", - "resolved": "https://registry.npmjs.org/@meshsdk/common/-/common-1.9.0-beta.68.tgz", - "integrity": "sha512-rmL2uZzSTEW52OYNCdRF1mBdL4pXLcMwjNZrK3Np/6E1zl2to0pArMfuc2bUl5urTIDfTqa2CsuWpgzZQ47N6Q==", - "license": "Apache-2.0", - "dependencies": { - "bech32": "^2.0.0", - "bip39": "3.1.0", - "blake2b": "^2.1.4", - "blakejs": "^1.2.1" - } - }, - "node_modules/@meshsdk/transaction/node_modules/@meshsdk/core-cst": { - "version": "1.9.0-beta.68", - "resolved": "https://registry.npmjs.org/@meshsdk/core-cst/-/core-cst-1.9.0-beta.68.tgz", - "integrity": "sha512-7KXr9k+Cpg/g2Fwj/opwHl6/yw5fkPxDXe0yCBuX3IeOSwM1lfjaENVdBGUtxz+opkbg+0a8RyPt3wKQG+tiJA==", - "license": "Apache-2.0", - "dependencies": { - "@cardano-sdk/core": "^0.45.5", - "@cardano-sdk/crypto": "^0.2.2", - "@cardano-sdk/input-selection": "^0.13.33", - "@cardano-sdk/util": "^0.15.5", - "@harmoniclabs/cbor": "1.3.0", - "@harmoniclabs/pair": "^1.0.0", - "@harmoniclabs/plutus-data": "1.2.4", - "@harmoniclabs/uplc": "1.2.4", - "@meshsdk/common": "1.9.0-beta.68", - "@types/base32-encoding": "^1.0.2", - "base32-encoding": "^1.0.0", - "bech32": "^2.0.0", - "blakejs": "^1.2.1", - "bn.js": "^5.2.0" - } - }, "node_modules/@meshsdk/wallet": { - "version": "1.9.0-beta.68", - "resolved": "https://registry.npmjs.org/@meshsdk/wallet/-/wallet-1.9.0-beta.68.tgz", - "integrity": "sha512-7rxU2MD4cDYDoS6soIOqeS+2HVW8ONm/j11+sgoMvLiUbPCpfogWLGLklRKxvZhgzAipUKbPNjak24AoD0Tq6g==", + "version": "1.9.0-beta.83", + "resolved": "https://registry.npmjs.org/@meshsdk/wallet/-/wallet-1.9.0-beta.83.tgz", + "integrity": "sha512-F02jZP0QE3UzABn/D5k+A6MXwH9DMYVkNSmiSbcEV7ZDLMQ0fdMpOU+MlyCgd8yCOlDM/Nxdk8oI/PaTrV6aYw==", "license": "Apache-2.0", "dependencies": { - "@meshsdk/common": "1.9.0-beta.68", - "@meshsdk/core-cst": "1.9.0-beta.68", - "@meshsdk/transaction": "1.9.0-beta.68", + "@meshsdk/common": "1.9.0-beta.83", + "@meshsdk/core-cst": "1.9.0-beta.83", + "@meshsdk/transaction": "1.9.0-beta.83", "@simplewebauthn/browser": "^13.0.0" } }, - "node_modules/@meshsdk/wallet/node_modules/@meshsdk/common": { - "version": "1.9.0-beta.68", - "resolved": "https://registry.npmjs.org/@meshsdk/common/-/common-1.9.0-beta.68.tgz", - "integrity": "sha512-rmL2uZzSTEW52OYNCdRF1mBdL4pXLcMwjNZrK3Np/6E1zl2to0pArMfuc2bUl5urTIDfTqa2CsuWpgzZQ47N6Q==", - "license": "Apache-2.0", - "dependencies": { - "bech32": "^2.0.0", - "bip39": "3.1.0", - "blake2b": "^2.1.4", - "blakejs": "^1.2.1" - } - }, - "node_modules/@meshsdk/wallet/node_modules/@meshsdk/core-cst": { - "version": "1.9.0-beta.68", - "resolved": "https://registry.npmjs.org/@meshsdk/core-cst/-/core-cst-1.9.0-beta.68.tgz", - "integrity": "sha512-7KXr9k+Cpg/g2Fwj/opwHl6/yw5fkPxDXe0yCBuX3IeOSwM1lfjaENVdBGUtxz+opkbg+0a8RyPt3wKQG+tiJA==", - "license": "Apache-2.0", - "dependencies": { - "@cardano-sdk/core": "^0.45.5", - "@cardano-sdk/crypto": "^0.2.2", - "@cardano-sdk/input-selection": "^0.13.33", - "@cardano-sdk/util": "^0.15.5", - "@harmoniclabs/cbor": "1.3.0", - "@harmoniclabs/pair": "^1.0.0", - "@harmoniclabs/plutus-data": "1.2.4", - "@harmoniclabs/uplc": "1.2.4", - "@meshsdk/common": "1.9.0-beta.68", - "@types/base32-encoding": "^1.0.2", - "base32-encoding": "^1.0.0", - "bech32": "^2.0.0", - "blakejs": "^1.2.1", - "bn.js": "^5.2.0" - } - }, "node_modules/@meshsdk/wallet/node_modules/@simplewebauthn/browser": { - "version": "13.1.2", - "resolved": "https://registry.npmjs.org/@simplewebauthn/browser/-/browser-13.1.2.tgz", - "integrity": "sha512-aZnW0KawAM83fSBUgglP5WofbrLbLyr7CoPqYr66Eppm7zO86YX6rrCjRB3hQKPrL7ATvY4FVXlykZ6w6FwYYw==", + "version": "13.2.2", + "resolved": "https://registry.npmjs.org/@simplewebauthn/browser/-/browser-13.2.2.tgz", + "integrity": "sha512-FNW1oLQpTJyqG5kkDg5ZsotvWgmBaC6jCHR7Ej0qUNep36Wl9tj2eZu7J5rP+uhXgHaLk+QQ3lqcw2vS5MX1IA==", "license": "MIT" }, "node_modules/@meshsdk/web3-sdk": { @@ -3533,6 +2791,7 @@ "version": "1.9.0-beta.68", "resolved": "https://registry.npmjs.org/@meshsdk/core/-/core-1.9.0-beta.68.tgz", "integrity": "sha512-/1ul9u+WDGylfICcX0Kj1FIDjH4lYyvDae3xmo+X/0DLXDCC9FwgWtpxIyJYXWJUTlsVfjvdqeLbPUeeQEniSw==", + "license": "Apache-2.0", "dependencies": { "@meshsdk/common": "1.9.0-beta.68", "@meshsdk/core-cst": "1.9.0-beta.68", @@ -3568,6 +2827,7 @@ "version": "1.9.0-beta.68", "resolved": "https://registry.npmjs.org/@meshsdk/provider/-/provider-1.9.0-beta.68.tgz", "integrity": "sha512-FzcPet8fDBT37CNc2cD/iYGhYsHar6E1dQtt/p2P+DGqnKd7IYp7L6T98fbEBzrJJZI8S0BuhLmRSdAQ0OTqSg==", + "license": "Apache-2.0", "dependencies": { "@meshsdk/common": "1.9.0-beta.68", "@meshsdk/core-cst": "1.9.0-beta.68", @@ -3581,6 +2841,7 @@ "version": "1.9.0-beta.68", "resolved": "https://registry.npmjs.org/@meshsdk/react/-/react-1.9.0-beta.68.tgz", "integrity": "sha512-6LPeyj8qChVBpE+ulBah/WS2N5loLpxnrvYFQ6i4po0kRpLDta13jxF7qE4lQ00olsU5qnjEh5KOCbnhhCxSmw==", + "license": "Apache-2.0", "dependencies": { "@fabianbormann/cardano-peer-connect": "^1.2.18", "@meshsdk/bitcoin": "1.9.0-beta.68", @@ -3602,10 +2863,37 @@ "react-dom": ">=16.0.0 <20.0.0 || >=16.0.0-rc <20.0.0-rc || >=19.0.0-rc" } }, + "node_modules/@meshsdk/web3-sdk/node_modules/@meshsdk/transaction": { + "version": "1.9.0-beta.68", + "resolved": "https://registry.npmjs.org/@meshsdk/transaction/-/transaction-1.9.0-beta.68.tgz", + "integrity": "sha512-FsVKqtCyAGrk3IRzEKIr4R6SNYFEGClwCPzM6LlfuC1z97lScM7yP9FgwkOMe4ZPXn4BS32i62X7EdQVIaQwMg==", + "license": "Apache-2.0", + "dependencies": { + "@cardano-sdk/core": "^0.45.5", + "@cardano-sdk/input-selection": "^0.13.33", + "@cardano-sdk/util": "^0.15.5", + "@meshsdk/common": "1.9.0-beta.68", + "@meshsdk/core-cst": "1.9.0-beta.68", + "json-bigint": "^1.0.0" + } + }, + "node_modules/@meshsdk/web3-sdk/node_modules/@meshsdk/wallet": { + "version": "1.9.0-beta.68", + "resolved": "https://registry.npmjs.org/@meshsdk/wallet/-/wallet-1.9.0-beta.68.tgz", + "integrity": "sha512-7rxU2MD4cDYDoS6soIOqeS+2HVW8ONm/j11+sgoMvLiUbPCpfogWLGLklRKxvZhgzAipUKbPNjak24AoD0Tq6g==", + "license": "Apache-2.0", + "dependencies": { + "@meshsdk/common": "1.9.0-beta.68", + "@meshsdk/core-cst": "1.9.0-beta.68", + "@meshsdk/transaction": "1.9.0-beta.68", + "@simplewebauthn/browser": "^13.0.0" + } + }, "node_modules/@meshsdk/web3-sdk/node_modules/@meshsdk/web3-sdk": { "version": "0.0.37", "resolved": "https://registry.npmjs.org/@meshsdk/web3-sdk/-/web3-sdk-0.0.37.tgz", "integrity": "sha512-uRG0jLjsa83JbPZqnVkec3gjvi0LEMiu1E6ItUALEnKUTTuhDOe3Cx4Ov1PbPTsYVsGRq61DCgzCNHSh2bXy+Q==", + "license": "Apache-2.0", "dependencies": { "@meshsdk/bitcoin": "1.9.0-beta.53", "@meshsdk/common": "1.9.0-beta.53", @@ -3634,6 +2922,7 @@ "version": "1.9.0-beta.53", "resolved": "https://registry.npmjs.org/@meshsdk/common/-/common-1.9.0-beta.53.tgz", "integrity": "sha512-GH75W2P4LPb8MS/F+ftP1wmf2UhSYsug9Naq09bvEU1woohJLmpkJ6JJ1e9fBbAK/N3VRVQEGvv+yM4zs634rQ==", + "license": "Apache-2.0", "dependencies": { "bech32": "^2.0.0", "bip39": "3.1.0", @@ -3645,6 +2934,7 @@ "version": "1.9.0-beta.53", "resolved": "https://registry.npmjs.org/@meshsdk/core-cst/-/core-cst-1.9.0-beta.53.tgz", "integrity": "sha512-u8I1g8EqfI+ysCtMg258NrMZ+uoSdM5RlrfVRuss0a7jsrSB64ae1kZXDaO2HROycpwz+muZbCVN5JywSVKmTQ==", + "license": "Apache-2.0", "dependencies": { "@cardano-sdk/core": "^0.45.5", "@cardano-sdk/crypto": "^0.2.2", @@ -3666,6 +2956,7 @@ "version": "1.9.0-beta.53", "resolved": "https://registry.npmjs.org/@meshsdk/transaction/-/transaction-1.9.0-beta.53.tgz", "integrity": "sha512-U53sj8Qve9/XQPqy6gaO7Sm57Fq0tGcYcTlIUq2XUOZtVV0ad88qvCakj9AG0uSq0WnrvPk+L0ExmnnzyL/akw==", + "license": "Apache-2.0", "dependencies": { "@cardano-sdk/core": "^0.45.5", "@cardano-sdk/input-selection": "^0.13.33", @@ -3679,6 +2970,7 @@ "version": "1.9.0-beta.53", "resolved": "https://registry.npmjs.org/@meshsdk/wallet/-/wallet-1.9.0-beta.53.tgz", "integrity": "sha512-UyvcRbh3StEowkjTyuomDqG5Pykgbz3PU84gB9LdbxGuX46ZUaqHa5+zq+TfOreJ9CVvIEPkg7YwLas6c1HqMw==", + "license": "Apache-2.0", "dependencies": { "@meshsdk/common": "1.9.0-beta.53", "@meshsdk/core-cst": "1.9.0-beta.53", @@ -3687,14 +2979,13 @@ } }, "node_modules/@meshsdk/web3-sdk/node_modules/@simplewebauthn/browser": { - "version": "13.2.0", - "resolved": "https://registry.npmjs.org/@simplewebauthn/browser/-/browser-13.2.0.tgz", - "integrity": "sha512-N3fuA1AAnTo5gCStYoIoiasPccC+xPLx2YU88Dv0GeAmPQTWHETlZQq5xZ0DgUq1H9loXMWQH5qqUjcI7BHJ1A==" + "version": "13.2.2", + "resolved": "https://registry.npmjs.org/@simplewebauthn/browser/-/browser-13.2.2.tgz", + "integrity": "sha512-FNW1oLQpTJyqG5kkDg5ZsotvWgmBaC6jCHR7Ej0qUNep36Wl9tj2eZu7J5rP+uhXgHaLk+QQ3lqcw2vS5MX1IA==", + "license": "MIT" }, "node_modules/@monogrid/gainmap-js": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/@monogrid/gainmap-js/-/gainmap-js-3.1.0.tgz", - "integrity": "sha512-Obb0/gEd/HReTlg8ttaYk+0m62gQJmCblMOjHSMHRrBP2zdfKMHLCRbh/6ex9fSUJMKdjjIEiohwkbGD3wj2Nw==", "license": "MIT", "dependencies": { "promise-worker-transferable": "^1.0.4" @@ -3704,16 +2995,15 @@ } }, "node_modules/@multiformats/dns": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/@multiformats/dns/-/dns-1.0.6.tgz", - "integrity": "sha512-nt/5UqjMPtyvkG9BQYdJ4GfLK3nMqGpFZOzf4hAmIa0sJh2LlS9YKXZ4FgwBDsaHvzZqR/rUFIywIc7pkHNNuw==", + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/@multiformats/dns/-/dns-1.0.10.tgz", + "integrity": "sha512-6X200ceQLns0b/CU0S/So16tGjB5eIXHJ1xvJMPoWaKFHWSgfpW2EhkWJrqap4U3+c37zcowVR0ToPXeYEL7Vw==", "license": "Apache-2.0 OR MIT", "dependencies": { - "@types/dns-packet": "^5.6.5", "buffer": "^6.0.3", "dns-packet": "^5.6.1", "hashlru": "^2.3.0", - "p-queue": "^8.0.1", + "p-queue": "^9.0.0", "progress-events": "^1.0.0", "uint8arrays": "^5.0.2" } @@ -3728,41 +3018,28 @@ } }, "node_modules/@multiformats/multiaddr": { - "version": "12.4.0", - "resolved": "https://registry.npmjs.org/@multiformats/multiaddr/-/multiaddr-12.4.0.tgz", - "integrity": "sha512-FL7yBTLijJ5JkO044BGb2msf+uJLrwpD6jD6TkXlbjA9N12+18HT40jvd4o5vL4LOJMc86dPX6tGtk/uI9kYKg==", + "version": "12.5.1", + "resolved": "https://registry.npmjs.org/@multiformats/multiaddr/-/multiaddr-12.5.1.tgz", + "integrity": "sha512-+DDlr9LIRUS8KncI1TX/FfUn8F2dl6BIxJgshS/yFQCNB5IAF0OGzcwB39g5NLE22s4qqDePv0Qof6HdpJ/4aQ==", "license": "Apache-2.0 OR MIT", "dependencies": { "@chainsafe/is-ip": "^2.0.1", "@chainsafe/netmask": "^2.0.0", "@multiformats/dns": "^1.0.3", + "abort-error": "^1.0.1", "multiformats": "^13.0.0", "uint8-varint": "^2.0.1", "uint8arrays": "^5.0.0" } }, - "node_modules/@napi-rs/wasm-runtime": { - "version": "0.2.12", - "resolved": "https://registry.npmjs.org/@napi-rs/wasm-runtime/-/wasm-runtime-0.2.12.tgz", - "integrity": "sha512-ZVWUcfwY4E/yPitQJl481FjFo3K22D6qF0DuFH6Y/nbnE11GY5uguDxZMGXPQ8WQ0128MXQD7TnfHyK4oWoIJQ==", - "dev": true, - "license": "MIT", - "optional": true, - "dependencies": { - "@emnapi/core": "^1.4.3", - "@emnapi/runtime": "^1.4.3", - "@tybys/wasm-util": "^0.10.0" - } - }, "node_modules/@next/env": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/@next/env/-/env-15.5.4.tgz", - "integrity": "sha512-27SQhYp5QryzIT5uO8hq99C69eLQ7qkzkDPsk3N+GuS2XgOgoYEeOav7Pf8Tn4drECOVDsDg8oj+/DVy8qQL2A==" + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/@next/env/-/env-15.5.6.tgz", + "integrity": "sha512-3qBGRW+sCGzgbpc5TS1a0p7eNxnOarGVQhZxfvTdnV0gFI61lX7QNtQ4V1TSREctXzYn5NetbUsLvyqwLFJM6Q==", + "license": "MIT" }, "node_modules/@next/eslint-plugin-next": { "version": "14.2.23", - "resolved": "https://registry.npmjs.org/@next/eslint-plugin-next/-/eslint-plugin-next-14.2.23.tgz", - "integrity": "sha512-efRC7m39GoiU1fXZRgGySqYbQi6ZyLkuGlvGst7IwkTTczehQTJA/7PoMg4MMjUZvZEGpiSEu+oJBAjPawiC3Q==", "dev": true, "license": "MIT", "dependencies": { @@ -3770,12 +3047,13 @@ } }, "node_modules/@next/swc-darwin-arm64": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-15.5.4.tgz", - "integrity": "sha512-nopqz+Ov6uvorej8ndRX6HlxCYWCO3AHLfKK2TYvxoSB2scETOcfm/HSS3piPqc3A+MUgyHoqE6je4wnkjfrOA==", + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-15.5.6.tgz", + "integrity": "sha512-ES3nRz7N+L5Umz4KoGfZ4XX6gwHplwPhioVRc25+QNsDa7RtUF/z8wJcbuQ2Tffm5RZwuN2A063eapoJ1u4nPg==", "cpu": [ "arm64" ], + "license": "MIT", "optional": true, "os": [ "darwin" @@ -3785,12 +3063,13 @@ } }, "node_modules/@next/swc-darwin-x64": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-15.5.4.tgz", - "integrity": "sha512-QOTCFq8b09ghfjRJKfb68kU9k2K+2wsC4A67psOiMn849K9ZXgCSRQr0oVHfmKnoqCbEmQWG1f2h1T2vtJJ9mA==", + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-15.5.6.tgz", + "integrity": "sha512-JIGcytAyk9LQp2/nuVZPAtj8uaJ/zZhsKOASTjxDug0SPU9LAM3wy6nPU735M1OqacR4U20LHVF5v5Wnl9ptTA==", "cpu": [ "x64" ], + "license": "MIT", "optional": true, "os": [ "darwin" @@ -3800,12 +3079,13 @@ } }, "node_modules/@next/swc-linux-arm64-gnu": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-15.5.4.tgz", - "integrity": "sha512-eRD5zkts6jS3VfE/J0Kt1VxdFqTnMc3QgO5lFE5GKN3KDI/uUpSyK3CjQHmfEkYR4wCOl0R0XrsjpxfWEA++XA==", + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-15.5.6.tgz", + "integrity": "sha512-qvz4SVKQ0P3/Im9zcS2RmfFL/UCQnsJKJwQSkissbngnB/12c6bZTCB0gHTexz1s6d/mD0+egPKXAIRFVS7hQg==", "cpu": [ "arm64" ], + "license": "MIT", "optional": true, "os": [ "linux" @@ -3815,12 +3095,13 @@ } }, "node_modules/@next/swc-linux-arm64-musl": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-15.5.4.tgz", - "integrity": "sha512-TOK7iTxmXFc45UrtKqWdZ1shfxuL4tnVAOuuJK4S88rX3oyVV4ZkLjtMT85wQkfBrOOvU55aLty+MV8xmcJR8A==", + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-15.5.6.tgz", + "integrity": "sha512-FsbGVw3SJz1hZlvnWD+T6GFgV9/NYDeLTNQB2MXoPN5u9VA9OEDy6fJEfePfsUKAhJufFbZLgp0cPxMuV6SV0w==", "cpu": [ "arm64" ], + "license": "MIT", "optional": true, "os": [ "linux" @@ -3830,12 +3111,13 @@ } }, "node_modules/@next/swc-linux-x64-gnu": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-15.5.4.tgz", - "integrity": "sha512-7HKolaj+481FSW/5lL0BcTkA4Ueam9SPYWyN/ib/WGAFZf0DGAN8frNpNZYFHtM4ZstrHZS3LY3vrwlIQfsiMA==", + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-15.5.6.tgz", + "integrity": "sha512-3QnHGFWlnvAgyxFxt2Ny8PTpXtQD7kVEeaFat5oPAHHI192WKYB+VIKZijtHLGdBBvc16tiAkPTDmQNOQ0dyrA==", "cpu": [ "x64" ], + "license": "MIT", "optional": true, "os": [ "linux" @@ -3845,12 +3127,13 @@ } }, "node_modules/@next/swc-linux-x64-musl": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-15.5.4.tgz", - "integrity": "sha512-nlQQ6nfgN0nCO/KuyEUwwOdwQIGjOs4WNMjEUtpIQJPR2NUfmGpW2wkJln1d4nJ7oUzd1g4GivH5GoEPBgfsdw==", + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-15.5.6.tgz", + "integrity": "sha512-OsGX148sL+TqMK9YFaPFPoIaJKbFJJxFzkXZljIgA9hjMjdruKht6xDCEv1HLtlLNfkx3c5w2GLKhj7veBQizQ==", "cpu": [ "x64" ], + "license": "MIT", "optional": true, "os": [ "linux" @@ -3860,12 +3143,13 @@ } }, "node_modules/@next/swc-win32-arm64-msvc": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-15.5.4.tgz", - "integrity": "sha512-PcR2bN7FlM32XM6eumklmyWLLbu2vs+D7nJX8OAIoWy69Kef8mfiN4e8TUv2KohprwifdpFKPzIP1njuCjD0YA==", + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-15.5.6.tgz", + "integrity": "sha512-ONOMrqWxdzXDJNh2n60H6gGyKed42Ieu6UTVPZteXpuKbLZTH4G4eBMsr5qWgOBA+s7F+uB4OJbZnrkEDnZ5Fg==", "cpu": [ "arm64" ], + "license": "MIT", "optional": true, "os": [ "win32" @@ -3875,12 +3159,13 @@ } }, "node_modules/@next/swc-win32-x64-msvc": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-15.5.4.tgz", - "integrity": "sha512-1ur2tSHZj8Px/KMAthmuI9FMp/YFusMMGoRNJaRZMOlSkgvLjzosSdQI0cJAKogdHl3qXUQKL9MGaYvKwA7DXg==", + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-15.5.6.tgz", + "integrity": "sha512-pxK4VIjFRx1MY92UycLOOw7dTdvccWsNETQ0kDHkBlcFH1GrTLUjSiHU1ohrznnux6TqRHgv5oflhfIWZwVROQ==", "cpu": [ "x64" ], + "license": "MIT", "optional": true, "os": [ "win32" @@ -3891,8 +3176,6 @@ }, "node_modules/@noble/ciphers": { "version": "0.5.3", - "resolved": "https://registry.npmjs.org/@noble/ciphers/-/ciphers-0.5.3.tgz", - "integrity": "sha512-B0+6IIHiqEs3BPMT0hcRmHvEj2QHOLu+uwt+tqDDeVd0oyVzh7BPrDcPjRnV1PV/5LaknXJJQvOuRGR0zQJz+w==", "license": "MIT", "funding": { "url": "https://paulmillr.com/funding/" @@ -3900,8 +3183,6 @@ }, "node_modules/@noble/curves": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/@noble/curves/-/curves-1.2.0.tgz", - "integrity": "sha512-oYclrNgRaM9SsBUBVbb8M6DTV7ZHRTKugureoYEncY5c65HOmRzvSiTE3y5CYaPYJA/GVkrhXEoF0M3Ya9PMnw==", "license": "MIT", "dependencies": { "@noble/hashes": "1.3.2" @@ -3912,8 +3193,6 @@ }, "node_modules/@noble/curves/node_modules/@noble/hashes": { "version": "1.3.2", - "resolved": "https://registry.npmjs.org/@noble/hashes/-/hashes-1.3.2.tgz", - "integrity": "sha512-MVC8EAQp7MvEcm30KWENFjgR+Mkmf+D189XJTkFIlwohU5hcBbn1ZkKq7KVTi2Hme3PMGF390DaL52beVrIihQ==", "license": "MIT", "engines": { "node": ">= 16" @@ -3923,9 +3202,9 @@ } }, "node_modules/@noble/hashes": { - "version": "1.7.1", - "resolved": "https://registry.npmjs.org/@noble/hashes/-/hashes-1.7.1.tgz", - "integrity": "sha512-B8XBPsn4vT/KJAGqDzbwztd+6Yte3P4V7iafm24bxgDe/mlRuK6xmWPuCNrKt2vDafZ8MfJLlchDG/vYafQEjQ==", + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/@noble/hashes/-/hashes-1.8.0.tgz", + "integrity": "sha512-jCs9ldd7NwzpgXDIf6P3+NrHh9/sD6CQdxHyjQI+h/6rDNo88ypBxxz45UDuZHz9r3tNz7N/VInSVoVdtXEI4A==", "license": "MIT", "engines": { "node": "^14.21.3 || >=16" @@ -3936,8 +3215,6 @@ }, "node_modules/@nodelib/fs.scandir": { "version": "2.1.5", - "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", - "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", "license": "MIT", "dependencies": { "@nodelib/fs.stat": "2.0.5", @@ -3949,8 +3226,6 @@ }, "node_modules/@nodelib/fs.stat": { "version": "2.0.5", - "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", - "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", "license": "MIT", "engines": { "node": ">= 8" @@ -3958,8 +3233,6 @@ }, "node_modules/@nodelib/fs.walk": { "version": "1.2.8", - "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", - "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", "license": "MIT", "dependencies": { "@nodelib/fs.scandir": "2.1.5", @@ -3971,8 +3244,6 @@ }, "node_modules/@nolyfill/is-core-module": { "version": "1.0.39", - "resolved": "https://registry.npmjs.org/@nolyfill/is-core-module/-/is-core-module-1.0.39.tgz", - "integrity": "sha512-nn5ozdjYQpUCZlWGuxcJY/KpxkWQs4DcbMCmKojjyrYDEAGy4Ce19NN4v5MduafTwJlbKc99UA8YhSVqq9yPZA==", "dev": true, "license": "MIT", "engines": { @@ -3981,8 +3252,6 @@ }, "node_modules/@octokit/auth-token": { "version": "5.1.2", - "resolved": "https://registry.npmjs.org/@octokit/auth-token/-/auth-token-5.1.2.tgz", - "integrity": "sha512-JcQDsBdg49Yky2w2ld20IHAlwr8d/d8N6NiOXbtuoPCqzbsiJgF633mVUw3x4mo0H5ypataQIX7SFu3yy44Mpw==", "license": "MIT", "engines": { "node": ">= 18" @@ -3990,8 +3259,6 @@ }, "node_modules/@octokit/core": { "version": "6.1.3", - "resolved": "https://registry.npmjs.org/@octokit/core/-/core-6.1.3.tgz", - "integrity": "sha512-z+j7DixNnfpdToYsOutStDgeRzJSMnbj8T1C/oQjB6Aa+kRfNjs/Fn7W6c8bmlt6mfy3FkgeKBRnDjxQow5dow==", "license": "MIT", "dependencies": { "@octokit/auth-token": "^5.0.0", @@ -4008,8 +3275,6 @@ }, "node_modules/@octokit/endpoint": { "version": "10.1.2", - "resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-10.1.2.tgz", - "integrity": "sha512-XybpFv9Ms4hX5OCHMZqyODYqGTZ3H6K6Vva+M9LR7ib/xr1y1ZnlChYv9H680y77Vd/i/k+thXApeRASBQkzhA==", "license": "MIT", "dependencies": { "@octokit/types": "^13.6.2", @@ -4021,8 +3286,6 @@ }, "node_modules/@octokit/graphql": { "version": "8.1.2", - "resolved": "https://registry.npmjs.org/@octokit/graphql/-/graphql-8.1.2.tgz", - "integrity": "sha512-bdlj/CJVjpaz06NBpfHhp4kGJaRZfz7AzC+6EwUImRtrwIw8dIgJ63Xg0OzV9pRn3rIzrt5c2sa++BL0JJ8GLw==", "license": "MIT", "dependencies": { "@octokit/request": "^9.1.4", @@ -4035,14 +3298,10 @@ }, "node_modules/@octokit/openapi-types": { "version": "23.0.1", - "resolved": "https://registry.npmjs.org/@octokit/openapi-types/-/openapi-types-23.0.1.tgz", - "integrity": "sha512-izFjMJ1sir0jn0ldEKhZ7xegCTj/ObmEDlEfpFrx4k/JyZSMRHbO3/rBwgE7f3m2DHt+RrNGIVw4wSmwnm3t/g==", "license": "MIT" }, "node_modules/@octokit/request": { "version": "9.2.0", - "resolved": "https://registry.npmjs.org/@octokit/request/-/request-9.2.0.tgz", - "integrity": "sha512-kXLfcxhC4ozCnAXy2ff+cSxpcF0A1UqxjvYMqNuPIeOAzJbVWQ+dy5G2fTylofB/gTbObT8O6JORab+5XtA1Kw==", "license": "MIT", "dependencies": { "@octokit/endpoint": "^10.0.0", @@ -4057,8 +3316,6 @@ }, "node_modules/@octokit/request-error": { "version": "6.1.6", - "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-6.1.6.tgz", - "integrity": "sha512-pqnVKYo/at0NuOjinrgcQYpEbv4snvP3bKMRqHaD9kIsk9u1LCpb2smHZi8/qJfgeNqLo5hNW4Z7FezNdEo0xg==", "license": "MIT", "dependencies": { "@octokit/types": "^13.6.2" @@ -4069,8 +3326,6 @@ }, "node_modules/@octokit/types": { "version": "13.7.0", - "resolved": "https://registry.npmjs.org/@octokit/types/-/types-13.7.0.tgz", - "integrity": "sha512-BXfRP+3P3IN6fd4uF3SniaHKOO4UXWBfkdR3vA8mIvaoO/wLjGN5qivUtW0QRitBHHMcfC41SLhNVYIZZE+wkA==", "license": "MIT", "dependencies": { "@octokit/openapi-types": "^23.0.1" @@ -4078,8 +3333,6 @@ }, "node_modules/@panva/hkdf": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/@panva/hkdf/-/hkdf-1.2.1.tgz", - "integrity": "sha512-6oclG6Y3PiDFcoyk8srjLfVKyMfVCKJ27JwNPViuXziFpmdz+MZnZN/aKY0JGXgYuO/VghU0jcOAZgWXZ1Dmrw==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/panva" @@ -4089,14 +3342,15 @@ "version": "2.2.2", "resolved": "https://registry.npmjs.org/@paralleldrive/cuid2/-/cuid2-2.2.2.tgz", "integrity": "sha512-ZOBkgDwEdoYVlSeRbYYXs0S9MejQofiVYoTbKzy/6GQa39/q5tQU2IX46+shYnUkpEl3wc+J6wRlar7r2EK2xA==", + "license": "MIT", "dependencies": { "@noble/hashes": "^1.1.5" } }, "node_modules/@peculiar/asn1-schema": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/@peculiar/asn1-schema/-/asn1-schema-2.4.0.tgz", - "integrity": "sha512-umbembjIWOrPSOzEGG5vxFLkeM8kzIhLkgigtsOrfLKnuzxWxejAcUX+q/SoZCdemlODOcr5WiYa7+dIEzBXZQ==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@peculiar/asn1-schema/-/asn1-schema-2.5.0.tgz", + "integrity": "sha512-YM/nFfskFJSlHqv59ed6dZlLZqtZQwjRVJ4bBAiWV08Oc+1rSd5lDZcBEx0lGDHfSoH3UziI2pXt2UM33KerPQ==", "license": "MIT", "dependencies": { "asn1js": "^3.0.6", @@ -4134,8 +3388,6 @@ }, "node_modules/@pkgjs/parseargs": { "version": "0.11.0", - "resolved": "https://registry.npmjs.org/@pkgjs/parseargs/-/parseargs-0.11.0.tgz", - "integrity": "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==", "license": "MIT", "optional": true, "engines": { @@ -4144,8 +3396,6 @@ }, "node_modules/@pkgr/core": { "version": "0.2.9", - "resolved": "https://registry.npmjs.org/@pkgr/core/-/core-0.2.9.tgz", - "integrity": "sha512-QNqXyfVS2wm9hweSYD2O7F0G06uurj9kZ96TRQE5Y9hU7+tgdZwIkbAKc5Ocy1HxEY2kuDQa6cQ1WRs/O5LFKA==", "dev": true, "license": "MIT", "engines": { @@ -4156,9 +3406,7 @@ } }, "node_modules/@prisma/client": { - "version": "6.4.1", - "resolved": "https://registry.npmjs.org/@prisma/client/-/client-6.4.1.tgz", - "integrity": "sha512-A7Mwx44+GVZVexT5e2GF/WcKkEkNNKbgr059xpr5mn+oUm2ZW1svhe+0TRNBwCdzhfIZ+q23jEgsNPvKD9u+6g==", + "version": "6.17.1", "hasInstallScript": true, "license": "Apache-2.0", "engines": { @@ -4177,72 +3425,67 @@ } } }, + "node_modules/@prisma/config": { + "version": "6.17.1", + "devOptional": true, + "license": "Apache-2.0", + "dependencies": { + "c12": "3.1.0", + "deepmerge-ts": "7.1.5", + "effect": "3.16.12", + "empathic": "2.0.0" + } + }, "node_modules/@prisma/debug": { - "version": "6.4.1", - "resolved": "https://registry.npmjs.org/@prisma/debug/-/debug-6.4.1.tgz", - "integrity": "sha512-Q9xk6yjEGIThjSD8zZegxd5tBRNHYd13GOIG0nLsanbTXATiPXCLyvlYEfvbR2ft6dlRsziQXfQGxAgv7zcMUA==", + "version": "6.17.1", "devOptional": true, "license": "Apache-2.0" }, "node_modules/@prisma/engines": { - "version": "6.4.1", - "resolved": "https://registry.npmjs.org/@prisma/engines/-/engines-6.4.1.tgz", - "integrity": "sha512-KldENzMHtKYwsOSLThghOIdXOBEsfDuGSrxAZjMnimBiDKd3AE4JQ+Kv+gBD/x77WoV9xIPf25GXMWffXZ17BA==", + "version": "6.17.1", "devOptional": true, "hasInstallScript": true, "license": "Apache-2.0", "dependencies": { - "@prisma/debug": "6.4.1", - "@prisma/engines-version": "6.4.0-29.a9055b89e58b4b5bfb59600785423b1db3d0e75d", - "@prisma/fetch-engine": "6.4.1", - "@prisma/get-platform": "6.4.1" + "@prisma/debug": "6.17.1", + "@prisma/engines-version": "6.17.1-1.272a37d34178c2894197e17273bf937f25acdeac", + "@prisma/fetch-engine": "6.17.1", + "@prisma/get-platform": "6.17.1" } }, "node_modules/@prisma/engines-version": { - "version": "6.4.0-29.a9055b89e58b4b5bfb59600785423b1db3d0e75d", - "resolved": "https://registry.npmjs.org/@prisma/engines-version/-/engines-version-6.4.0-29.a9055b89e58b4b5bfb59600785423b1db3d0e75d.tgz", - "integrity": "sha512-Xq54qw55vaCGrGgIJqyDwOq0TtjZPJEWsbQAHugk99hpDf2jcEeQhUcF+yzEsSqegBaDNLA4IC8Nn34sXmkiTQ==", + "version": "6.17.1-1.272a37d34178c2894197e17273bf937f25acdeac", "devOptional": true, "license": "Apache-2.0" }, "node_modules/@prisma/fetch-engine": { - "version": "6.4.1", - "resolved": "https://registry.npmjs.org/@prisma/fetch-engine/-/fetch-engine-6.4.1.tgz", - "integrity": "sha512-uZ5hVeTmDspx7KcaRCNoXmcReOD+84nwlO2oFvQPRQh9xiFYnnUKDz7l9bLxp8t4+25CsaNlgrgilXKSQwrIGQ==", + "version": "6.17.1", "devOptional": true, "license": "Apache-2.0", "dependencies": { - "@prisma/debug": "6.4.1", - "@prisma/engines-version": "6.4.0-29.a9055b89e58b4b5bfb59600785423b1db3d0e75d", - "@prisma/get-platform": "6.4.1" + "@prisma/debug": "6.17.1", + "@prisma/engines-version": "6.17.1-1.272a37d34178c2894197e17273bf937f25acdeac", + "@prisma/get-platform": "6.17.1" } }, "node_modules/@prisma/get-platform": { - "version": "6.4.1", - "resolved": "https://registry.npmjs.org/@prisma/get-platform/-/get-platform-6.4.1.tgz", - "integrity": "sha512-gXqZaDI5scDkBF8oza7fOD3Q3QMD0e0rBynlzDDZdTWbWmzjuW58PRZtj+jkvKje2+ZigCWkH8SsWZAsH6q1Yw==", + "version": "6.17.1", "devOptional": true, "license": "Apache-2.0", "dependencies": { - "@prisma/debug": "6.4.1" + "@prisma/debug": "6.17.1" } }, "node_modules/@radix-ui/number": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/number/-/number-1.1.0.tgz", - "integrity": "sha512-V3gRzhVNU1ldS5XhAPTom1fOIo4ccrjjJgmE+LI2h/WaFpHmx0MQApT+KZHnx8abG6Avtfcz4WoEciMnpFT3HQ==", "license": "MIT" }, "node_modules/@radix-ui/primitive": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/primitive/-/primitive-1.1.1.tgz", - "integrity": "sha512-SJ31y+Q/zAyShtXJc8x83i9TYdbAfHZ++tUZnvjJJqFjzsdUnKsxPL6IEtBlxKkU7yzer//GQtZSV4GbldL3YA==", "license": "MIT" }, "node_modules/@radix-ui/react-accordion": { "version": "1.2.2", - "resolved": "https://registry.npmjs.org/@radix-ui/react-accordion/-/react-accordion-1.2.2.tgz", - "integrity": "sha512-b1oh54x4DMCdGsB4/7ahiSrViXxaBwRPotiZNnYXjLha9vfuURSAZErki6qjDoSIV0eXx5v57XnTGVtGwnfp2g==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4272,8 +3515,6 @@ }, "node_modules/@radix-ui/react-arrow": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-arrow/-/react-arrow-1.1.1.tgz", - "integrity": "sha512-NaVpZfmv8SKeZbn4ijN2V3jlHA9ngBG16VnIIm22nUR0Yk8KUALyBxT3KYEUnNuch9sTE8UTsS3whzBgKOL30w==", "license": "MIT", "dependencies": { "@radix-ui/react-primitive": "2.0.1" @@ -4295,8 +3536,6 @@ }, "node_modules/@radix-ui/react-checkbox": { "version": "1.1.3", - "resolved": "https://registry.npmjs.org/@radix-ui/react-checkbox/-/react-checkbox-1.1.3.tgz", - "integrity": "sha512-HD7/ocp8f1B3e6OHygH0n7ZKjONkhciy1Nh0yuBgObqThc3oyx+vuMfFHKAknXRHHWVE9XvXStxJFyjUmB8PIw==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4325,8 +3564,6 @@ }, "node_modules/@radix-ui/react-collapsible": { "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@radix-ui/react-collapsible/-/react-collapsible-1.1.2.tgz", - "integrity": "sha512-PliMB63vxz7vggcyq0IxNYk8vGDrLXVWw4+W4B8YnwI1s18x7YZYqlG9PLX7XxAJUi0g2DxP4XKJMFHh/iVh9A==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4355,8 +3592,6 @@ }, "node_modules/@radix-ui/react-collection": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-collection/-/react-collection-1.1.1.tgz", - "integrity": "sha512-LwT3pSho9Dljg+wY2KN2mrrh6y3qELfftINERIzBUO9e0N+t0oMTyn3k9iv+ZqgrwGkRnLpNJrsMv9BZlt2yuA==", "license": "MIT", "dependencies": { "@radix-ui/react-compose-refs": "1.1.1", @@ -4381,8 +3616,6 @@ }, "node_modules/@radix-ui/react-compose-refs": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-compose-refs/-/react-compose-refs-1.1.1.tgz", - "integrity": "sha512-Y9VzoRDSJtgFMUCoiZBDVo084VQ5hfpXxVE+NgkdNsjiDBByiImMZKKhxMwCbdHvhlENG6a833CbFkOQvTricw==", "license": "MIT", "peerDependencies": { "@types/react": "*", @@ -4396,8 +3629,6 @@ }, "node_modules/@radix-ui/react-context": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-context/-/react-context-1.1.1.tgz", - "integrity": "sha512-UASk9zi+crv9WteK/NU4PLvOoL3OuE6BWVKNF6hPRBtYBDXQ2u5iu3O59zUlJiTVvkyuycnqrztsHVJwcK9K+Q==", "license": "MIT", "peerDependencies": { "@types/react": "*", @@ -4411,8 +3642,6 @@ }, "node_modules/@radix-ui/react-dialog": { "version": "1.1.5", - "resolved": "https://registry.npmjs.org/@radix-ui/react-dialog/-/react-dialog-1.1.5.tgz", - "integrity": "sha512-LaO3e5h/NOEL4OfXjxD43k9Dx+vn+8n+PCFt6uhX/BADFflllyv3WJG6rgvvSVBxpTch938Qq/LGc2MMxipXPw==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4447,8 +3676,6 @@ }, "node_modules/@radix-ui/react-direction": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/react-direction/-/react-direction-1.1.0.tgz", - "integrity": "sha512-BUuBvgThEiAXh2DWu93XsT+a3aWrGqolGlqqw5VU1kG7p/ZH2cuDlM1sRLNnY3QcBS69UIz2mcKhMxDsdewhjg==", "license": "MIT", "peerDependencies": { "@types/react": "*", @@ -4462,8 +3689,6 @@ }, "node_modules/@radix-ui/react-dismissable-layer": { "version": "1.1.4", - "resolved": "https://registry.npmjs.org/@radix-ui/react-dismissable-layer/-/react-dismissable-layer-1.1.4.tgz", - "integrity": "sha512-XDUI0IVYVSwjMXxM6P4Dfti7AH+Y4oS/TB+sglZ/EXc7cqLwGAmp1NlMrcUjj7ks6R5WTZuWKv44FBbLpwU3sA==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4489,8 +3714,6 @@ }, "node_modules/@radix-ui/react-dropdown-menu": { "version": "2.1.5", - "resolved": "https://registry.npmjs.org/@radix-ui/react-dropdown-menu/-/react-dropdown-menu-2.1.5.tgz", - "integrity": "sha512-50ZmEFL1kOuLalPKHrLWvPFMons2fGx9TqQCWlPwDVpbAnaUJ1g4XNcKqFNMQymYU0kKWR4MDDi+9vUQBGFgcQ==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4518,8 +3741,6 @@ }, "node_modules/@radix-ui/react-focus-guards": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-focus-guards/-/react-focus-guards-1.1.1.tgz", - "integrity": "sha512-pSIwfrT1a6sIoDASCSpFwOasEwKTZWDw/iBdtnqKO7v6FeOzYJ7U53cPzYFVR3geGGXgVHaH+CdngrrAzqUGxg==", "license": "MIT", "peerDependencies": { "@types/react": "*", @@ -4533,8 +3754,6 @@ }, "node_modules/@radix-ui/react-focus-scope": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-focus-scope/-/react-focus-scope-1.1.1.tgz", - "integrity": "sha512-01omzJAYRxXdG2/he/+xy+c8a8gCydoQ1yOxnWNcRhrrBW5W+RQJ22EK1SaO8tb3WoUsuEw7mJjBozPzihDFjA==", "license": "MIT", "dependencies": { "@radix-ui/react-compose-refs": "1.1.1", @@ -4558,8 +3777,6 @@ }, "node_modules/@radix-ui/react-hover-card": { "version": "1.1.5", - "resolved": "https://registry.npmjs.org/@radix-ui/react-hover-card/-/react-hover-card-1.1.5.tgz", - "integrity": "sha512-0jPlX3ZrUIhtMAY0m1SBn1koI4Yqsizq2UwdUiQF1GseSZLZBPa6b8tNS+m32K94Yb4wxtWFSQs85wujQvwahg==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4589,8 +3806,6 @@ }, "node_modules/@radix-ui/react-icons": { "version": "1.3.2", - "resolved": "https://registry.npmjs.org/@radix-ui/react-icons/-/react-icons-1.3.2.tgz", - "integrity": "sha512-fyQIhGDhzfc9pK2kH6Pl9c4BDJGfMkPqkyIgYDthyNYoNg3wVhoJMMh19WS4Up/1KMPFVpNsT2q3WmXn2N1m6g==", "license": "MIT", "peerDependencies": { "react": "^16.x || ^17.x || ^18.x || ^19.0.0 || ^19.0.0-rc" @@ -4598,8 +3813,6 @@ }, "node_modules/@radix-ui/react-id": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/react-id/-/react-id-1.1.0.tgz", - "integrity": "sha512-EJUrI8yYh7WOjNOqpoJaf1jlFIH2LvtgAl+YcFqNCa+4hj64ZXmPkAKOFs/ukjz3byN6bdb/AVUqHkI8/uWWMA==", "license": "MIT", "dependencies": { "@radix-ui/react-use-layout-effect": "1.1.0" @@ -4616,8 +3829,6 @@ }, "node_modules/@radix-ui/react-label": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-label/-/react-label-2.1.1.tgz", - "integrity": "sha512-UUw5E4e/2+4kFMH7+YxORXGWggtY6sM8WIwh5RZchhLuUg2H1hc98Py+pr8HMz6rdaYrK2t296ZEjYLOCO5uUw==", "license": "MIT", "dependencies": { "@radix-ui/react-primitive": "2.0.1" @@ -4639,8 +3850,6 @@ }, "node_modules/@radix-ui/react-menu": { "version": "2.1.5", - "resolved": "https://registry.npmjs.org/@radix-ui/react-menu/-/react-menu-2.1.5.tgz", - "integrity": "sha512-uH+3w5heoMJtqVCgYOtYVMECk1TOrkUn0OG0p5MqXC0W2ppcuVeESbou8PTHoqAjbdTEK19AGXBWcEtR5WpEQg==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4679,8 +3888,6 @@ }, "node_modules/@radix-ui/react-popper": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-popper/-/react-popper-1.2.1.tgz", - "integrity": "sha512-3kn5Me69L+jv82EKRuQCXdYyf1DqHwD2U/sxoNgBGCB7K9TRc3bQamQ+5EPM9EvyPdli0W41sROd+ZU1dTCztw==", "license": "MIT", "dependencies": { "@floating-ui/react-dom": "^2.0.0", @@ -4711,8 +3918,6 @@ }, "node_modules/@radix-ui/react-portal": { "version": "1.1.3", - "resolved": "https://registry.npmjs.org/@radix-ui/react-portal/-/react-portal-1.1.3.tgz", - "integrity": "sha512-NciRqhXnGojhT93RPyDaMPfLH3ZSl4jjIFbZQ1b/vxvZEdHsBZ49wP9w8L3HzUQwep01LcWtkUvm0OVB5JAHTw==", "license": "MIT", "dependencies": { "@radix-ui/react-primitive": "2.0.1", @@ -4735,8 +3940,6 @@ }, "node_modules/@radix-ui/react-presence": { "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@radix-ui/react-presence/-/react-presence-1.1.2.tgz", - "integrity": "sha512-18TFr80t5EVgL9x1SwF/YGtfG+l0BS0PRAlCWBDoBEiDQjeKgnNZRVJp/oVBl24sr3Gbfwc/Qpj4OcWTQMsAEg==", "license": "MIT", "dependencies": { "@radix-ui/react-compose-refs": "1.1.1", @@ -4759,8 +3962,6 @@ }, "node_modules/@radix-ui/react-primitive": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-primitive/-/react-primitive-2.0.1.tgz", - "integrity": "sha512-sHCWTtxwNn3L3fH8qAfnF3WbUZycW93SM1j3NFDzXBiz8D6F5UTTy8G1+WFEaiCdvCVRJWj6N2R4Xq6HdiHmDg==", "license": "MIT", "dependencies": { "@radix-ui/react-slot": "1.1.1" @@ -4782,8 +3983,6 @@ }, "node_modules/@radix-ui/react-roving-focus": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-roving-focus/-/react-roving-focus-1.1.1.tgz", - "integrity": "sha512-QE1RoxPGJ/Nm8Qmk0PxP8ojmoaS67i0s7hVssS7KuI2FQoc/uzVlZsqKfQvxPE6D8hICCPHJ4D88zNhT3OOmkw==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4813,8 +4012,6 @@ }, "node_modules/@radix-ui/react-select": { "version": "2.1.5", - "resolved": "https://registry.npmjs.org/@radix-ui/react-select/-/react-select-2.1.5.tgz", - "integrity": "sha512-eVV7N8jBXAXnyrc+PsOF89O9AfVgGnbLxUtBb0clJ8y8ENMWLARGMI/1/SBRLz7u4HqxLgN71BJ17eono3wcjA==", "license": "MIT", "dependencies": { "@radix-ui/number": "1.1.0", @@ -4856,8 +4053,6 @@ }, "node_modules/@radix-ui/react-separator": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-separator/-/react-separator-1.1.1.tgz", - "integrity": "sha512-RRiNRSrD8iUiXriq/Y5n4/3iE8HzqgLHsusUSg5jVpU2+3tqcUFPJXHDymwEypunc2sWxDUS3UC+rkZRlHedsw==", "license": "MIT", "dependencies": { "@radix-ui/react-primitive": "2.0.1" @@ -4879,8 +4074,6 @@ }, "node_modules/@radix-ui/react-slot": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-slot/-/react-slot-1.1.1.tgz", - "integrity": "sha512-RApLLOcINYJA+dMVbOju7MYv1Mb2EBp2nH4HdDzXTSyaR5optlm6Otrz1euW3HbdOR8UmmFK06TD+A9frYWv+g==", "license": "MIT", "dependencies": { "@radix-ui/react-compose-refs": "1.1.1" @@ -4897,8 +4090,6 @@ }, "node_modules/@radix-ui/react-tabs": { "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@radix-ui/react-tabs/-/react-tabs-1.1.2.tgz", - "integrity": "sha512-9u/tQJMcC2aGq7KXpGivMm1mgq7oRJKXphDwdypPd/j21j/2znamPU8WkXgnhUaTrSFNIt8XhOyCAupg8/GbwQ==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4927,8 +4118,6 @@ }, "node_modules/@radix-ui/react-toast": { "version": "1.2.5", - "resolved": "https://registry.npmjs.org/@radix-ui/react-toast/-/react-toast-1.2.5.tgz", - "integrity": "sha512-ZzUsAaOx8NdXZZKcFNDhbSlbsCUy8qQWmzTdgrlrhhZAOx2ofLtKrBDW9fkqhFvXgmtv560Uj16pkLkqML7SHA==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4961,8 +4150,6 @@ }, "node_modules/@radix-ui/react-toggle": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-toggle/-/react-toggle-1.1.1.tgz", - "integrity": "sha512-i77tcgObYr743IonC1hrsnnPmszDRn8p+EGUsUt+5a/JFn28fxaM88Py6V2mc8J5kELMWishI0rLnuGLFD/nnQ==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -4986,8 +4173,6 @@ }, "node_modules/@radix-ui/react-toggle-group": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-toggle-group/-/react-toggle-group-1.1.1.tgz", - "integrity": "sha512-OgDLZEA30Ylyz8YSXvnGqIHtERqnUt1KUYTKdw/y8u7Ci6zGiJfXc02jahmcSNK3YcErqioj/9flWC9S1ihfwg==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -5015,8 +4200,6 @@ }, "node_modules/@radix-ui/react-tooltip": { "version": "1.1.7", - "resolved": "https://registry.npmjs.org/@radix-ui/react-tooltip/-/react-tooltip-1.1.7.tgz", - "integrity": "sha512-ss0s80BC0+g0+Zc53MvilcnTYSOi4mSuFWBPYPuTOFGjx+pUU+ZrmamMNwS56t8MTFlniA5ocjd4jYm/CdhbOg==", "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.1", @@ -5049,8 +4232,6 @@ }, "node_modules/@radix-ui/react-use-callback-ref": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/react-use-callback-ref/-/react-use-callback-ref-1.1.0.tgz", - "integrity": "sha512-CasTfvsy+frcFkbXtSJ2Zu9JHpN8TYKxkgJGWbjiZhFivxaeW7rMeZt7QELGVLaYVfFMsKHjb7Ak0nMEe+2Vfw==", "license": "MIT", "peerDependencies": { "@types/react": "*", @@ -5064,8 +4245,6 @@ }, "node_modules/@radix-ui/react-use-controllable-state": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/react-use-controllable-state/-/react-use-controllable-state-1.1.0.tgz", - "integrity": "sha512-MtfMVJiSr2NjzS0Aa90NPTnvTSg6C/JLCV7ma0W6+OMV78vd8OyRpID+Ng9LxzsPbLeuBnWBA1Nq30AtBIDChw==", "license": "MIT", "dependencies": { "@radix-ui/react-use-callback-ref": "1.1.0" @@ -5082,8 +4261,6 @@ }, "node_modules/@radix-ui/react-use-escape-keydown": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/react-use-escape-keydown/-/react-use-escape-keydown-1.1.0.tgz", - "integrity": "sha512-L7vwWlR1kTTQ3oh7g1O0CBF3YCyyTj8NmhLR+phShpyA50HCfBFKVJTpshm9PzLiKmehsrQzTYTpX9HvmC9rhw==", "license": "MIT", "dependencies": { "@radix-ui/react-use-callback-ref": "1.1.0" @@ -5100,8 +4277,6 @@ }, "node_modules/@radix-ui/react-use-layout-effect": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/react-use-layout-effect/-/react-use-layout-effect-1.1.0.tgz", - "integrity": "sha512-+FPE0rOdziWSrH9athwI1R0HDVbWlEhd+FR+aSDk4uWGmSJ9Z54sdZVDQPZAinJhJXwfT+qnj969mCsT2gfm5w==", "license": "MIT", "peerDependencies": { "@types/react": "*", @@ -5115,8 +4290,6 @@ }, "node_modules/@radix-ui/react-use-previous": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/react-use-previous/-/react-use-previous-1.1.0.tgz", - "integrity": "sha512-Z/e78qg2YFnnXcW88A4JmTtm4ADckLno6F7OXotmkQfeuCVaKuYzqAATPhVzl3delXE7CxIV8shofPn3jPc5Og==", "license": "MIT", "peerDependencies": { "@types/react": "*", @@ -5130,8 +4303,6 @@ }, "node_modules/@radix-ui/react-use-rect": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/react-use-rect/-/react-use-rect-1.1.0.tgz", - "integrity": "sha512-0Fmkebhr6PiseyZlYAOtLS+nb7jLmpqTrJyv61Pe68MKYW6OWdRE2kI70TaYY27u7H0lajqM3hSMMLFq18Z7nQ==", "license": "MIT", "dependencies": { "@radix-ui/rect": "1.1.0" @@ -5148,8 +4319,6 @@ }, "node_modules/@radix-ui/react-use-size": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/react-use-size/-/react-use-size-1.1.0.tgz", - "integrity": "sha512-XW3/vWuIXHa+2Uwcc2ABSfcCledmXhhQPlGbfcRXbiUQI5Icjcg19BGCZVKKInYbvUCut/ufbbLLPFC5cbb1hw==", "license": "MIT", "dependencies": { "@radix-ui/react-use-layout-effect": "1.1.0" @@ -5166,8 +4335,6 @@ }, "node_modules/@radix-ui/react-visually-hidden": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@radix-ui/react-visually-hidden/-/react-visually-hidden-1.1.1.tgz", - "integrity": "sha512-vVfA2IZ9q/J+gEamvj761Oq1FpWgCDaNOOIfbPVp2MVPLEomUr5+Vf7kJGwQ24YxZSlQVar7Bes8kyTo5Dshpg==", "license": "MIT", "dependencies": { "@radix-ui/react-primitive": "2.0.1" @@ -5189,14 +4356,10 @@ }, "node_modules/@radix-ui/rect": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@radix-ui/rect/-/rect-1.1.0.tgz", - "integrity": "sha512-A9+lCBZoaMJlVKcRBz2YByCG+Cp2t6nAnMnNba+XiWxnj6r4JUFqfsgwocMBZU9LPtdxC6wB56ySYpc7LQIoJg==", "license": "MIT" }, "node_modules/@react-spring/animated": { "version": "9.7.5", - "resolved": "https://registry.npmjs.org/@react-spring/animated/-/animated-9.7.5.tgz", - "integrity": "sha512-Tqrwz7pIlsSDITzxoLS3n/v/YCUHQdOIKtOJf4yL6kYVSDTSmVK1LI1Q3M/uu2Sx4X3pIWF3xLUhlsA6SPNTNg==", "license": "MIT", "dependencies": { "@react-spring/shared": "~9.7.5", @@ -5208,8 +4371,6 @@ }, "node_modules/@react-spring/core": { "version": "9.7.5", - "resolved": "https://registry.npmjs.org/@react-spring/core/-/core-9.7.5.tgz", - "integrity": "sha512-rmEqcxRcu7dWh7MnCcMXLvrf6/SDlSokLaLTxiPlAYi11nN3B5oiCUAblO72o+9z/87j2uzxa2Inm8UbLjXA+w==", "license": "MIT", "dependencies": { "@react-spring/animated": "~9.7.5", @@ -5226,14 +4387,10 @@ }, "node_modules/@react-spring/rafz": { "version": "9.7.5", - "resolved": "https://registry.npmjs.org/@react-spring/rafz/-/rafz-9.7.5.tgz", - "integrity": "sha512-5ZenDQMC48wjUzPAm1EtwQ5Ot3bLIAwwqP2w2owG5KoNdNHpEJV263nGhCeKKmuA3vG2zLLOdu3or6kuDjA6Aw==", "license": "MIT" }, "node_modules/@react-spring/shared": { "version": "9.7.5", - "resolved": "https://registry.npmjs.org/@react-spring/shared/-/shared-9.7.5.tgz", - "integrity": "sha512-wdtoJrhUeeyD/PP/zo+np2s1Z820Ohr/BbuVYv+3dVLW7WctoiN7std8rISoYoHpUXtbkpesSKuPIw/6U1w1Pw==", "license": "MIT", "dependencies": { "@react-spring/rafz": "~9.7.5", @@ -5245,8 +4402,6 @@ }, "node_modules/@react-spring/three": { "version": "9.7.5", - "resolved": "https://registry.npmjs.org/@react-spring/three/-/three-9.7.5.tgz", - "integrity": "sha512-RxIsCoQfUqOS3POmhVHa1wdWS0wyHAUway73uRLp3GAL5U2iYVNdnzQsep6M2NZ994BlW8TcKuMtQHUqOsy6WA==", "license": "MIT", "dependencies": { "@react-spring/animated": "~9.7.5", @@ -5262,14 +4417,10 @@ }, "node_modules/@react-spring/types": { "version": "9.7.5", - "resolved": "https://registry.npmjs.org/@react-spring/types/-/types-9.7.5.tgz", - "integrity": "sha512-HVj7LrZ4ReHWBimBvu2SKND3cDVUPWKLqRTmWe/fNY6o1owGOX0cAHbdPDTMelgBlVbrTKrre6lFkhqGZErK/g==", "license": "MIT" }, "node_modules/@react-three/drei": { "version": "9.121.4", - "resolved": "https://registry.npmjs.org/@react-three/drei/-/drei-9.121.4.tgz", - "integrity": "sha512-cxP1ulffISS0ICHJeZjBH7cbfNGKM4kJi6dzV6DK2Ld1jUsR1ejAsKsA+4A3TAO7ubxd4C0NhAe1g8RXpJglPA==", "license": "MIT", "dependencies": { "@babel/runtime": "^7.26.0", @@ -5309,8 +4460,6 @@ }, "node_modules/@react-three/drei/node_modules/zustand": { "version": "5.0.3", - "resolved": "https://registry.npmjs.org/zustand/-/zustand-5.0.3.tgz", - "integrity": "sha512-14fwWQtU3pH4dE0dOpdMiWjddcH+QzKIgk1cl8epwSE7yag43k/AD/m4L6+K7DytAOr9gGBe3/EXj9g7cdostg==", "license": "MIT", "engines": { "node": ">=12.20.0" @@ -5338,8 +4487,6 @@ }, "node_modules/@react-three/fiber": { "version": "8.17.12", - "resolved": "https://registry.npmjs.org/@react-three/fiber/-/fiber-8.17.12.tgz", - "integrity": "sha512-rjV/ZtCr69y+aWEOsAhBQzsxYyvZHUanYfo9eMXNp/dxTj3ZrRvK44DkIdSLV1xcPidq8p2YeU2oWP2czY+ZVA==", "license": "MIT", "dependencies": { "@babel/runtime": "^7.17.8", @@ -5388,8 +4535,6 @@ }, "node_modules/@react-three/fiber/node_modules/zustand": { "version": "3.7.2", - "resolved": "https://registry.npmjs.org/zustand/-/zustand-3.7.2.tgz", - "integrity": "sha512-PIJDIZKtokhof+9+60cpockVOq05sJzHCriyvaLBmEJixseQ1a5Kdov6fWZfWOu5SK9c+FhH1jU0tntLxRJYMA==", "license": "MIT", "engines": { "node": ">=12.7.0" @@ -5405,15 +4550,11 @@ }, "node_modules/@rtsao/scc": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@rtsao/scc/-/scc-1.1.0.tgz", - "integrity": "sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==", "dev": true, "license": "MIT" }, "node_modules/@rushstack/eslint-patch": { "version": "1.10.5", - "resolved": "https://registry.npmjs.org/@rushstack/eslint-patch/-/eslint-patch-1.10.5.tgz", - "integrity": "sha512-kkKUDVlII2DQiKy7UstOR1ErJP8kUKAQ4oa+SQtM0K+lPdmmjj0YnnxBgtTVYH7mUKtbsxeFC9y0AmK7Yb78/A==", "dev": true, "license": "MIT" }, @@ -5425,15 +4566,13 @@ }, "node_modules/@scarf/scarf": { "version": "1.4.0", - "resolved": "https://registry.npmjs.org/@scarf/scarf/-/scarf-1.4.0.tgz", - "integrity": "sha512-xxeapPiUXdZAE3che6f3xogoJPeZgig6omHEy1rIY5WVsB3H2BHNnZH+gHG6x91SCWyQCzWGsuL2Hh3ClO5/qQ==", "hasInstallScript": true, "license": "Apache-2.0" }, "node_modules/@scure/base": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/@scure/base/-/base-1.2.4.tgz", - "integrity": "sha512-5Yy9czTO47mqz+/J8GM6GIId4umdCk1wc1q8rKERQulIoc8VP9pzDcghv10Tl2E7R96ZUx/PhND3ESYUQX8NuQ==", + "version": "1.2.6", + "resolved": "https://registry.npmjs.org/@scure/base/-/base-1.2.6.tgz", + "integrity": "sha512-g/nm5FgUa//MCj1gV09zTJTaM6KBAHqLN907YVQqf7zC49+DcO4B1so4ZX07Ef10Twr6nuqYEH9GEggFXA4Fmg==", "license": "MIT", "funding": { "url": "https://paulmillr.com/funding/" @@ -5441,8 +4580,6 @@ }, "node_modules/@scure/bip32": { "version": "1.3.1", - "resolved": "https://registry.npmjs.org/@scure/bip32/-/bip32-1.3.1.tgz", - "integrity": "sha512-osvveYtyzdEVbt3OfwwXFr4P2iVBL5u1Q3q4ONBfDY/UpOuXmOlbgwc1xECEboY8wIays8Yt6onaWMUdUbfl0A==", "license": "MIT", "dependencies": { "@noble/curves": "~1.1.0", @@ -5455,8 +4592,6 @@ }, "node_modules/@scure/bip32/node_modules/@noble/curves": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@noble/curves/-/curves-1.1.0.tgz", - "integrity": "sha512-091oBExgENk/kGj3AZmtBDMpxQPDtxQABR2B9lb1JbVTs6ytdzZNwvhxQ4MWasRNEzlbEH8jCWFCwhF/Obj5AA==", "license": "MIT", "dependencies": { "@noble/hashes": "1.3.1" @@ -5467,8 +4602,6 @@ }, "node_modules/@scure/bip32/node_modules/@noble/curves/node_modules/@noble/hashes": { "version": "1.3.1", - "resolved": "https://registry.npmjs.org/@noble/hashes/-/hashes-1.3.1.tgz", - "integrity": "sha512-EbqwksQwz9xDRGfDST86whPBgM65E0OH/pCgqW0GBVzO22bNE+NuIbeTb714+IfSjU3aRk47EUvXIb5bTsenKA==", "license": "MIT", "engines": { "node": ">= 16" @@ -5479,8 +4612,6 @@ }, "node_modules/@scure/bip32/node_modules/@noble/hashes": { "version": "1.3.3", - "resolved": "https://registry.npmjs.org/@noble/hashes/-/hashes-1.3.3.tgz", - "integrity": "sha512-V7/fPHgl+jsVPXqqeOzT8egNj2iBIVt+ECeMMG8TdcnTikP3oaBtUVqpT/gYCR68aEBJSF+XbYUxStjbFMqIIA==", "license": "MIT", "engines": { "node": ">= 16" @@ -5491,8 +4622,6 @@ }, "node_modules/@scure/bip32/node_modules/@scure/base": { "version": "1.1.9", - "resolved": "https://registry.npmjs.org/@scure/base/-/base-1.1.9.tgz", - "integrity": "sha512-8YKhl8GHiNI/pU2VMaofa2Tor7PJRAjwQLBBuilkJ9L5+13yVbC7JO/wS7piioAvPSwR3JKM1IJ/u4xQzbcXKg==", "license": "MIT", "funding": { "url": "https://paulmillr.com/funding/" @@ -5500,8 +4629,6 @@ }, "node_modules/@scure/bip39": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/@scure/bip39/-/bip39-1.2.1.tgz", - "integrity": "sha512-Z3/Fsz1yr904dduJD0NpiyRHhRYHdcnyh73FZWiV+/qhWi83wNJ3NWolYqCEN+ZWsUz2TWwajJggcRE9r1zUYg==", "license": "MIT", "dependencies": { "@noble/hashes": "~1.3.0", @@ -5513,8 +4640,6 @@ }, "node_modules/@scure/bip39/node_modules/@noble/hashes": { "version": "1.3.3", - "resolved": "https://registry.npmjs.org/@noble/hashes/-/hashes-1.3.3.tgz", - "integrity": "sha512-V7/fPHgl+jsVPXqqeOzT8egNj2iBIVt+ECeMMG8TdcnTikP3oaBtUVqpT/gYCR68aEBJSF+XbYUxStjbFMqIIA==", "license": "MIT", "engines": { "node": ">= 16" @@ -5525,37 +4650,35 @@ }, "node_modules/@scure/bip39/node_modules/@scure/base": { "version": "1.1.9", - "resolved": "https://registry.npmjs.org/@scure/base/-/base-1.1.9.tgz", - "integrity": "sha512-8YKhl8GHiNI/pU2VMaofa2Tor7PJRAjwQLBBuilkJ9L5+13yVbC7JO/wS7piioAvPSwR3JKM1IJ/u4xQzbcXKg==", "license": "MIT", "funding": { "url": "https://paulmillr.com/funding/" } }, "node_modules/@sidan-lab/whisky-js-browser": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/@sidan-lab/whisky-js-browser/-/whisky-js-browser-1.0.10.tgz", - "integrity": "sha512-Y6wf0+/uODEKr1gwVAISRuPwb/3yJpRGgYcZW7TkROqCvdpFsIBSLuf7AH2nYDJifduviIypmphKNmI+/S4/rg==", + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/@sidan-lab/whisky-js-browser/-/whisky-js-browser-1.0.11.tgz", + "integrity": "sha512-2deLmdRBJisehbCvAGZqUuPlRXvU5yHuN5cmwPSputbGRb2lfjTb+Nep9ViL93j01/XoDvIn9orXZGqMeIDddQ==", "license": "Apache-2.0" }, "node_modules/@sidan-lab/whisky-js-nodejs": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/@sidan-lab/whisky-js-nodejs/-/whisky-js-nodejs-1.0.10.tgz", - "integrity": "sha512-aUmMcF0+5vvK+JtmuMYDh1ys9RkinvJ2zRuUUocmqKpJ31s8wu8D34opjE9mECE5A8GQBrdOV6Dvghf0v5fGSA==", + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/@sidan-lab/whisky-js-nodejs/-/whisky-js-nodejs-1.0.11.tgz", + "integrity": "sha512-YB6O7GT0aVQltWxeAJDFOscK5SDMxf8EUhjTFq36OWUP4S7GdyWHqu2P4aRZmTLyd6L7+/aWfgI2W8pQZ+Wl8Q==", "license": "Apache-2.0" }, "node_modules/@silentbot1/nat-api": { - "version": "0.4.7", - "resolved": "https://registry.npmjs.org/@silentbot1/nat-api/-/nat-api-0.4.7.tgz", - "integrity": "sha512-6aKXUf4AY6ETBdwjswQOekY6HGj3eZTAUhJx1oYicBqpMJcsphIydEQKp/Hooz6Y070MOI6tD/oT1MgS7bP3Vg==", + "version": "0.4.8", + "resolved": "https://registry.npmjs.org/@silentbot1/nat-api/-/nat-api-0.4.8.tgz", + "integrity": "sha512-DBz/1gGzaYIbUdGTBQ7l4NrI7a+DFZgdZShmjmBGgJR4PvQ64wKNMwle2rrW8pdiOesN+DV6/8ZN/PLuksNyTg==", "license": "MIT", "dependencies": { "chrome-dgram": "^3.0.6", "cross-fetch-ponyfill": "^1.0.3", - "debug": "^4.3.4", - "default-gateway": "^6.0.3", + "debug": "^4.4.0", + "default-gateway": "^7.2.2", "unordered-array-remove": "^1.0.2", - "xml2js": "^0.6.0" + "xml2js": "^0.6.2" }, "engines": { "node": ">=10.0.0" @@ -5563,8 +4686,6 @@ }, "node_modules/@simplewebauthn/browser": { "version": "9.0.1", - "resolved": "https://registry.npmjs.org/@simplewebauthn/browser/-/browser-9.0.1.tgz", - "integrity": "sha512-wD2WpbkaEP4170s13/HUxPcAV5y4ZXaKo1TfNklS5zDefPinIgXOpgz1kpEvobAsaLPa2KeH7AKKX/od1mrBJw==", "license": "MIT", "optional": true, "peer": true, @@ -5574,23 +4695,17 @@ }, "node_modules/@simplewebauthn/types": { "version": "9.0.1", - "resolved": "https://registry.npmjs.org/@simplewebauthn/types/-/types-9.0.1.tgz", - "integrity": "sha512-tGSRP1QvsAvsJmnOlRQyw/mvK9gnPtjEc5fg2+m8n+QUa+D7rvrKkOYyfpy42GTs90X3RDOnqJgfHt+qO67/+w==", "license": "MIT", "optional": true, "peer": true }, "node_modules/@sinclair/typebox": { "version": "0.34.41", - "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.34.41.tgz", - "integrity": "sha512-6gS8pZzSXdyRHTIqoqSVknxolr1kzfy4/CeDnrzsVz8TTIWUbOBr6gnzOmTYJ3eXQNh4IYHIGi5aIL7sOZ2G/g==", "dev": true, "license": "MIT" }, "node_modules/@sinonjs/commons": { "version": "3.0.1", - "resolved": "https://registry.npmjs.org/@sinonjs/commons/-/commons-3.0.1.tgz", - "integrity": "sha512-K3mCHKQ9sVh8o1C9cxkwxaOmXoAMlDxC1mYyHrjqOWEcBjYr76t96zL2zlj5dUGZ3HSw240X1qgH3Mjf1yJWpQ==", "dev": true, "license": "BSD-3-Clause", "dependencies": { @@ -5599,18 +4714,19 @@ }, "node_modules/@sinonjs/fake-timers": { "version": "13.0.5", - "resolved": "https://registry.npmjs.org/@sinonjs/fake-timers/-/fake-timers-13.0.5.tgz", - "integrity": "sha512-36/hTbH2uaWuGVERyC6da9YwGWnzUZXuPro/F2LfsdOsLnCojz/iSH8MxUt/FD2S5XBSVPhmArFUXcpCQ2Hkiw==", "dev": true, "license": "BSD-3-Clause", "dependencies": { "@sinonjs/commons": "^3.0.1" } }, + "node_modules/@standard-schema/spec": { + "version": "1.0.0", + "devOptional": true, + "license": "MIT" + }, "node_modules/@swagger-api/apidom-ast": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ast/-/apidom-ast-1.0.0-beta.39.tgz", - "integrity": "sha512-EWeSOtvI8XpbYMRkDyu4qAIlivhcplrskpau2cbrWfXGBjrqEtmHqWlbJ9xoXJbNshbIcZ0Z77QdxicimGjs0w==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5623,8 +4739,6 @@ }, "node_modules/@swagger-api/apidom-core": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-core/-/apidom-core-1.0.0-beta.39.tgz", - "integrity": "sha512-tYZSVA+uDFvBJmnP104d8Qb/mye8B6ykNviohHAngHsy8ElcOPzSi5GKwwmJgf3taWzipMqWNM0ch5KytbXTqw==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5640,8 +4754,6 @@ }, "node_modules/@swagger-api/apidom-error": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-error/-/apidom-error-1.0.0-beta.39.tgz", - "integrity": "sha512-vQ3xQaRQGP9kNNBEDcFCmUd2PT9rCtYdkCyqYWZMxHBm5dXSBC/dQaC5VN1DbqQygE16fSQC+c5sqOrwg5d5WQ==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.20.7" @@ -5649,8 +4761,6 @@ }, "node_modules/@swagger-api/apidom-json-pointer": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-json-pointer/-/apidom-json-pointer-1.0.0-beta.39.tgz", - "integrity": "sha512-gPDNT+MCs/B1XYuNpmnz0rOHQ0ssN9YjVDqeGkX61v03BLJUF/JZKMo3J3FA2mgKb6ap+kRHzpzw5PpHLwRKAw==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5661,8 +4771,6 @@ }, "node_modules/@swagger-api/apidom-ns-api-design-systems": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-api-design-systems/-/apidom-ns-api-design-systems-1.0.0-beta.39.tgz", - "integrity": "sha512-MpdCb8KS3Tz1mGTrU0XC0Q2OcsrUWKB+buFPzLFOv0dU36ArARERX+Mz6aCJQ1CqnkFVM49uMe2NECO93ZR52w==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5678,8 +4786,6 @@ }, "node_modules/@swagger-api/apidom-ns-arazzo-1": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-arazzo-1/-/apidom-ns-arazzo-1-1.0.0-beta.39.tgz", - "integrity": "sha512-gIiZhlt51JxEZBAZ5PfHV1c73SMQJiwJX5DnazGehMO+ojR4HyLPFh1lc6mChMxPyPlRFOfqnmx/hmNcJ/XRiA==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5694,8 +4800,6 @@ }, "node_modules/@swagger-api/apidom-ns-asyncapi-2": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-asyncapi-2/-/apidom-ns-asyncapi-2-1.0.0-beta.39.tgz", - "integrity": "sha512-Jtdo+6MgVhf8HynjRo5pIj+aYYICAQGwRkd0n0YtOhvvKoI0gWEMpcRkDbJrNcNYOHaSxMlQfotGlTCaMl7QJQ==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5710,8 +4814,6 @@ }, "node_modules/@swagger-api/apidom-ns-json-schema-2019-09": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-json-schema-2019-09/-/apidom-ns-json-schema-2019-09-1.0.0-beta.39.tgz", - "integrity": "sha512-I/XP4zbrWAmnq2KWPtbb9DKLWgzYFovIiSQOyh47bJqbYgz64/IhoZb/uGihZojVVHSqeeJH9o6JOahqHQzKOw==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5726,8 +4828,6 @@ }, "node_modules/@swagger-api/apidom-ns-json-schema-2020-12": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-json-schema-2020-12/-/apidom-ns-json-schema-2020-12-1.0.0-beta.39.tgz", - "integrity": "sha512-9bpMp96fb76lOqeggtyCU457K/XBLyw3O9fxdVS3Tevhf8P3SJ6QpabmweRb6kFt4vI3+DiBschJGn0iqmlcXw==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5742,8 +4842,6 @@ }, "node_modules/@swagger-api/apidom-ns-json-schema-draft-4": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-json-schema-draft-4/-/apidom-ns-json-schema-draft-4-1.0.0-beta.39.tgz", - "integrity": "sha512-F25tm/nwPl1rRnUHzaVw4SAeASodO60oAtWX+GF3K61WEx/Aao4Maldv3CQtAoUk8L0Ml0l1KZL00sgfikwqlw==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5757,8 +4855,6 @@ }, "node_modules/@swagger-api/apidom-ns-json-schema-draft-6": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-json-schema-draft-6/-/apidom-ns-json-schema-draft-6-1.0.0-beta.39.tgz", - "integrity": "sha512-E2fQQHWIRtbM5C1m1EL95MQNDPL98mlgYomPQDDUEFbYrH3u9BQGAgpIu4KuYasKquyuhx9YXqS/jLRhMCRfAQ==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5773,8 +4869,6 @@ }, "node_modules/@swagger-api/apidom-ns-json-schema-draft-7": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-json-schema-draft-7/-/apidom-ns-json-schema-draft-7-1.0.0-beta.39.tgz", - "integrity": "sha512-mhzb7n3pm0yfYuM9bZowYMp6L61Cz+HrbjBowUIt5iOMMAATQd6x209pj81hnSmgHmEJCgv+8IO9dvweme698A==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5789,8 +4883,6 @@ }, "node_modules/@swagger-api/apidom-ns-openapi-2": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-openapi-2/-/apidom-ns-openapi-2-1.0.0-beta.39.tgz", - "integrity": "sha512-/Cjggp0eAM1GfKeLu53sLjCV9lFVUMucFruXJnD1TWdCKv5S5JAKsGBASbchw8hvwrfx6sPHslzZFV+tZKbn2Q==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5806,8 +4898,6 @@ }, "node_modules/@swagger-api/apidom-ns-openapi-3-0": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-openapi-3-0/-/apidom-ns-openapi-3-0-1.0.0-beta.39.tgz", - "integrity": "sha512-lvNlUtCmyHH8+52qOhgXXdzy4HEYA+t7xnFNvDb6dtP+epXCexux3uRs8+xEYBHo/WqUGzjdwd0qKFRgyP7Lrw==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5822,8 +4912,6 @@ }, "node_modules/@swagger-api/apidom-ns-openapi-3-1": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-ns-openapi-3-1/-/apidom-ns-openapi-3-1-1.0.0-beta.39.tgz", - "integrity": "sha512-sXMJxTGL2F36Uyv9iqvPwvzsD5NJM/dJ52tUuiJP8h4RqXwjrOC86hqf1/Xk/rxgpZShhW4PNEqifvPq/Mto3w==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -5840,8 +4928,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-api-design-systems-json": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-api-design-systems-json/-/apidom-parser-adapter-api-design-systems-json-1.0.0-beta.39.tgz", - "integrity": "sha512-jrPxZMvE6I2X8FUx4ri7VTMy2wTNOLLz+qXSx9sSXWULImqwdscvEwSVug8zdBQYMy8HXwt0wHpxlGLXBEmL8Q==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5856,8 +4942,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-api-design-systems-yaml": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-api-design-systems-yaml/-/apidom-parser-adapter-api-design-systems-yaml-1.0.0-beta.39.tgz", - "integrity": "sha512-JKyRYc4cBajPkIpO0YTJnxI+p8ubXfA+/1L8Fpq5kDPAI5Wh744iZ/scVHTgpgY8g+GbPqIoWB0ilQbEdlF5Sg==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5872,8 +4956,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-arazzo-json-1": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-arazzo-json-1/-/apidom-parser-adapter-arazzo-json-1-1.0.0-beta.39.tgz", - "integrity": "sha512-qlQuj4jsEPpLRH4wpkMjbR3Id3qb4n/oerv4cKCi1TYJJphC7DG7QRS90tYjaAF7n2YA8HxUcEIu2+Y5QZKyMw==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5888,8 +4970,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-arazzo-yaml-1": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-arazzo-yaml-1/-/apidom-parser-adapter-arazzo-yaml-1-1.0.0-beta.39.tgz", - "integrity": "sha512-MUChnj6dJZRGDtIIVItIojzDNBEdan8KkuV+3U1l8bBA4eJQIq7yzHYk7fq6bl4Yd17HG0HT+1xckbUnj5Ay4A==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5904,8 +4984,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-asyncapi-json-2": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-asyncapi-json-2/-/apidom-parser-adapter-asyncapi-json-2-1.0.0-beta.39.tgz", - "integrity": "sha512-G+xIeYGetnCM3ylsWSwSyqCntpT6gt2Bv3f6hu/IonZxxCy2HqUl9JS41XF/cJHCoBchJU3G+bjOZXN22W3Xzw==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5920,8 +4998,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-asyncapi-yaml-2": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-asyncapi-yaml-2/-/apidom-parser-adapter-asyncapi-yaml-2-1.0.0-beta.39.tgz", - "integrity": "sha512-VPwlMRwtMQtPmEv6JXNefBBjAK/IxPsq9XWP/7kJZQ6CDp6ljHrMJDPAHZNundSL09xu7Wbz6KVGcpruUPiWmA==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5936,8 +5012,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-json": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-json/-/apidom-parser-adapter-json-1.0.0-beta.39.tgz", - "integrity": "sha512-Rg2SgI06CDTdm3qs3A5pNvhonVxa2jOcwypxyhKngelIHaTuOPgaFA6qyCIvX0oIhwTcKcvV+5tPlGIR3vshpA==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5955,8 +5029,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-json/node_modules/tree-sitter": { "version": "0.22.1", - "resolved": "https://registry.npmjs.org/tree-sitter/-/tree-sitter-0.22.1.tgz", - "integrity": "sha512-gRO+jk2ljxZlIn20QRskIvpLCMtzuLl5T0BY6L9uvPYD17uUrxlxWkvYCiVqED2q2q7CVtY52Uex4WcYo2FEXw==", "hasInstallScript": true, "license": "MIT", "optional": true, @@ -5967,8 +5039,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-openapi-json-2": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-openapi-json-2/-/apidom-parser-adapter-openapi-json-2-1.0.0-beta.39.tgz", - "integrity": "sha512-DYB3jGcSnTu1ykbAKkMo550QW0BjnHlGxi1NaBbVYzdMfPYbBSQnDB3zYAwgakpoQx89OztFSlrNQ+3P8wuuSw==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5983,8 +5053,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-openapi-json-3-0": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-openapi-json-3-0/-/apidom-parser-adapter-openapi-json-3-0-1.0.0-beta.39.tgz", - "integrity": "sha512-4ueWFNc3N4YZb7fTwsgrhWzdCo3TnZ7HgK5fPW3m0+Hm2wko2WYIUCIxU33Ef4DB+0Hd8y4Abjv8Mz0CCxRaeg==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -5999,8 +5067,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-openapi-json-3-1": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-openapi-json-3-1/-/apidom-parser-adapter-openapi-json-3-1-1.0.0-beta.39.tgz", - "integrity": "sha512-8K/9J1CnQAwVqN+pvP9PH607WKA7WimNmZiyczgfnOgq93PUozNavrK97lwUUOQcZUmQra8pG2XrOrZZwd/M5w==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -6015,8 +5081,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-openapi-yaml-2": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-openapi-yaml-2/-/apidom-parser-adapter-openapi-yaml-2-1.0.0-beta.39.tgz", - "integrity": "sha512-EfzVZrYTnwNGXUXIOrZkigQxdze+VdXxJWp55t3CWTy0CA7w9eM+PDpzHu7iqJgXqTOixMGy02Gzyv6N6sDj8A==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -6031,8 +5095,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-openapi-yaml-3-0": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-openapi-yaml-3-0/-/apidom-parser-adapter-openapi-yaml-3-0-1.0.0-beta.39.tgz", - "integrity": "sha512-ElHueuGdwB35VeZaJnmhZE3ILGE8F74ThJqgTbY+F2JcNo4O8cBkoCq9syw1pJ+l2JoAUErmxaTOR+zNA/wK+g==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -6047,8 +5109,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-openapi-yaml-3-1": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-openapi-yaml-3-1/-/apidom-parser-adapter-openapi-yaml-3-1-1.0.0-beta.39.tgz", - "integrity": "sha512-lNSXp+vGcsA/d/3ukXJeovAnO5oxcTJ5OvFBL84grJvK1C6E2v0AOfsMlUEipIRNhIHq3zYKpUnhFJyE13VqXA==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -6063,8 +5123,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-yaml-1-2": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-parser-adapter-yaml-1-2/-/apidom-parser-adapter-yaml-1-2-1.0.0-beta.39.tgz", - "integrity": "sha512-30Lhgkg2ZrHY7tQ5h9umjWWhy0Fqcoi28SXJ9vtdj1cLSnFvclaLe5ZGbXP3wdW4sXZO0As3+msL9tMwrUJ/7w==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -6082,8 +5140,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-yaml-1-2/node_modules/@tree-sitter-grammars/tree-sitter-yaml": { "version": "0.7.0", - "resolved": "https://registry.npmjs.org/@tree-sitter-grammars/tree-sitter-yaml/-/tree-sitter-yaml-0.7.0.tgz", - "integrity": "sha512-GOMIK3IaDvECD0eZEhAsLl03RMtM1E8StxuGMn6PpMKFg7jyQ+jSzxJZ4Jmc/tYitah9/AECt8o4tlRQ5yEZQg==", "hasInstallScript": true, "license": "MIT", "optional": true, @@ -6102,8 +5158,6 @@ }, "node_modules/@swagger-api/apidom-parser-adapter-yaml-1-2/node_modules/tree-sitter": { "version": "0.22.1", - "resolved": "https://registry.npmjs.org/tree-sitter/-/tree-sitter-0.22.1.tgz", - "integrity": "sha512-gRO+jk2ljxZlIn20QRskIvpLCMtzuLl5T0BY6L9uvPYD17uUrxlxWkvYCiVqED2q2q7CVtY52Uex4WcYo2FEXw==", "hasInstallScript": true, "license": "MIT", "optional": true, @@ -6114,8 +5168,6 @@ }, "node_modules/@swagger-api/apidom-reference": { "version": "1.0.0-beta.39", - "resolved": "https://registry.npmjs.org/@swagger-api/apidom-reference/-/apidom-reference-1.0.0-beta.39.tgz", - "integrity": "sha512-PrV2/3Z6XGJPj4fv1JazY1dKjlnAg/BN22UQdUOzA5/A0TkfbImt8uVQuVzQSL2P8RA6G9TDsdpOalj80N47rw==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.26.10", @@ -6153,8 +5205,6 @@ }, "node_modules/@swagger-api/apidom-reference/node_modules/minimatch": { "version": "7.4.6", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-7.4.6.tgz", - "integrity": "sha512-sBz8G/YjVniEz6lKPNpKxXwazJe4c19fEfV2GDMX6AjFz+MX9uDWIZW8XreVhkFW3fkIdTv/gxWr/Kks5FFAVw==", "license": "ISC", "dependencies": { "brace-expansion": "^2.0.1" @@ -6168,8 +5218,6 @@ }, "node_modules/@swaggerexpert/cookie": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/@swaggerexpert/cookie/-/cookie-2.0.2.tgz", - "integrity": "sha512-DPI8YJ0Vznk4CT+ekn3rcFNq1uQwvUHZhH6WvTSPD0YKBIlMS9ur2RYKghXuxxOiqOam/i4lHJH4xTIiTgs3Mg==", "license": "Apache-2.0", "dependencies": { "apg-lite": "^1.0.3" @@ -6180,8 +5228,6 @@ }, "node_modules/@swaggerexpert/json-pointer": { "version": "2.10.2", - "resolved": "https://registry.npmjs.org/@swaggerexpert/json-pointer/-/json-pointer-2.10.2.tgz", - "integrity": "sha512-qMx1nOrzoB+PF+pzb26Q4Tc2sOlrx9Ba2UBNX9hB31Omrq+QoZ2Gly0KLrQWw4Of1AQ4J9lnD+XOdwOdcdXqqw==", "license": "Apache-2.0", "dependencies": { "apg-lite": "^1.0.4" @@ -6194,14 +5240,13 @@ "version": "0.5.15", "resolved": "https://registry.npmjs.org/@swc/helpers/-/helpers-0.5.15.tgz", "integrity": "sha512-JQ5TuMi45Owi4/BIMAJBoSQoOJu12oOk/gADqlcUL9JEdHB8vyjUSsxqeNXnmXHjYKMi2WcYtezGEEhqUI/E2g==", + "license": "Apache-2.0", "dependencies": { "tslib": "^2.8.0" } }, "node_modules/@t3-oss/env-core": { "version": "0.10.1", - "resolved": "https://registry.npmjs.org/@t3-oss/env-core/-/env-core-0.10.1.tgz", - "integrity": "sha512-GcKZiCfWks5CTxhezn9k5zWX3sMDIYf6Kaxy2Gx9YEQftFcz8hDRN56hcbylyAO3t4jQnQ5ifLawINsNgCDpOg==", "license": "MIT", "peerDependencies": { "typescript": ">=5.0.0", @@ -6215,8 +5260,6 @@ }, "node_modules/@t3-oss/env-nextjs": { "version": "0.10.1", - "resolved": "https://registry.npmjs.org/@t3-oss/env-nextjs/-/env-nextjs-0.10.1.tgz", - "integrity": "sha512-iy2qqJLnFh1RjEWno2ZeyTu0ufomkXruUsOZludzDIroUabVvHsrSjtkHqwHp1/pgPUzN3yBRHMILW162X7x2Q==", "license": "MIT", "dependencies": { "@t3-oss/env-core": "0.10.1" @@ -6233,8 +5276,6 @@ }, "node_modules/@tanstack/query-core": { "version": "5.65.0", - "resolved": "https://registry.npmjs.org/@tanstack/query-core/-/query-core-5.65.0.tgz", - "integrity": "sha512-Bnnq/1axf00r2grRT6gUyIkZRKzhHs+p4DijrCQ3wMlA3D3TTT71gtaSLtqnzGddj73/7X5JDGyjiSLdjvQN4w==", "license": "MIT", "funding": { "type": "github", @@ -6243,8 +5284,6 @@ }, "node_modules/@tanstack/react-query": { "version": "5.65.1", - "resolved": "https://registry.npmjs.org/@tanstack/react-query/-/react-query-5.65.1.tgz", - "integrity": "sha512-BSpjo4RQdJ75Mw3pqM1AJYNhanNxJE3ct7RmCZUAv9cUJg/Qmonzc/Xy2kKXeQA1InuKATSuc6pOZciWOF8TYQ==", "license": "MIT", "dependencies": { "@tanstack/query-core": "5.65.0" @@ -6258,9 +5297,9 @@ } }, "node_modules/@thaunknown/simple-peer": { - "version": "10.0.11", - "resolved": "https://registry.npmjs.org/@thaunknown/simple-peer/-/simple-peer-10.0.11.tgz", - "integrity": "sha512-A5MdmtZ6HUzRa4gwPOS4jG+09HvpTv2rFo4kk7Vwveo2ELm+WmbO124ZrJrQnZc2D7z2Q3AWKSitjl9OKXO88g==", + "version": "10.0.12", + "resolved": "https://registry.npmjs.org/@thaunknown/simple-peer/-/simple-peer-10.0.12.tgz", + "integrity": "sha512-sDrkkOdzlJL8+FXQqYcBb2THHQU+Yrar92SjfW4ZLs877/4QA2kFejuA6DVepsoMpoIbXShc7OCXCwYt4AtGdQ==", "license": "MIT", "dependencies": { "debug": "^4.3.7", @@ -6284,9 +5323,9 @@ } }, "node_modules/@thaunknown/simple-websocket/node_modules/ws": { - "version": "8.18.1", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.1.tgz", - "integrity": "sha512-RKW2aJZMXeMxVpnZ6bck+RswznaxmzdULiBr6KY7XkTnW8uvt0iT9H5DkHUChXrc+uurzwa0rVI16n/Xzjdz1w==", + "version": "8.18.3", + "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.3.tgz", + "integrity": "sha512-PEIGCY5tSlUt50cqyMXfCzX+oOPqN0vuGqWzbcJ2xvnkzkq46oOpz7dQaTDBdfICb4N14+GARUDw2XV2N4tvzg==", "license": "MIT", "engines": { "node": ">=10.0.0" @@ -6317,9 +5356,7 @@ } }, "node_modules/@trpc/client": { - "version": "11.0.0-rc.730", - "resolved": "https://registry.npmjs.org/@trpc/client/-/client-11.0.0-rc.730.tgz", - "integrity": "sha512-OFt98CtSq9KCiD7odFYP92MMVhgT4NCAy50gvsd8syVXAtKgyo6itmUuq5fcxwUYjiDwHOQvlWgA0IIQWSvLxQ==", + "version": "11.0.0-rc.730+776d07336", "funding": [ "https://trpc.io/sponsor" ], @@ -6330,9 +5367,7 @@ } }, "node_modules/@trpc/next": { - "version": "11.0.0-rc.730", - "resolved": "https://registry.npmjs.org/@trpc/next/-/next-11.0.0-rc.730.tgz", - "integrity": "sha512-QqsPHlPH9A8twgzKHsv6tLMdOFnRPDphz459JV8ipsIfXkucaz/LaSsvAjJKvIzOALzs4Qo/EDaRnQnseOi+Og==", + "version": "11.0.0-rc.730+776d07336", "funding": [ "https://trpc.io/sponsor" ], @@ -6357,9 +5392,7 @@ } }, "node_modules/@trpc/react-query": { - "version": "11.0.0-rc.730", - "resolved": "https://registry.npmjs.org/@trpc/react-query/-/react-query-11.0.0-rc.730.tgz", - "integrity": "sha512-bVUNg5CMfoph3B7BRA4NYza+xEKzYL8j69wSGIZ2j+757HPrvBfSFo6TCuYyYnChbqtjW2sEoqVBb0rgefcwYQ==", + "version": "11.0.0-rc.730+776d07336", "funding": [ "https://trpc.io/sponsor" ], @@ -6374,9 +5407,7 @@ } }, "node_modules/@trpc/server": { - "version": "11.0.0-rc.730", - "resolved": "https://registry.npmjs.org/@trpc/server/-/server-11.0.0-rc.730.tgz", - "integrity": "sha512-pRdPGqU1LkIq6kZ1ST9fmFaFnsl7IZ6h3eEIG6cbAkUHha/oTlmDXZZAIpunBPQ1ugi5uwFClvfTY8ZapemBKA==", + "version": "11.0.0-rc.730+776d07336", "funding": [ "https://trpc.io/sponsor" ], @@ -6387,8 +5418,6 @@ }, "node_modules/@turf/boolean-point-in-polygon": { "version": "7.2.0", - "resolved": "https://registry.npmjs.org/@turf/boolean-point-in-polygon/-/boolean-point-in-polygon-7.2.0.tgz", - "integrity": "sha512-lvEOjxeXIp+wPXgl9kJA97dqzMfNexjqHou+XHVcfxQgolctoJiRYmcVCWGpiZ9CBf/CJha1KmD1qQoRIsjLaA==", "license": "MIT", "dependencies": { "@turf/helpers": "^7.2.0", @@ -6403,8 +5432,6 @@ }, "node_modules/@turf/helpers": { "version": "7.2.0", - "resolved": "https://registry.npmjs.org/@turf/helpers/-/helpers-7.2.0.tgz", - "integrity": "sha512-cXo7bKNZoa7aC7ydLmUR02oB3IgDe7MxiPuRz3cCtYQHn+BJ6h1tihmamYDWWUlPHgSNF0i3ATc4WmDECZafKw==", "license": "MIT", "dependencies": { "@types/geojson": "^7946.0.10", @@ -6416,39 +5443,22 @@ }, "node_modules/@turf/invariant": { "version": "7.2.0", - "resolved": "https://registry.npmjs.org/@turf/invariant/-/invariant-7.2.0.tgz", - "integrity": "sha512-kV4u8e7Gkpq+kPbAKNC21CmyrXzlbBgFjO1PhrHPgEdNqXqDawoZ3i6ivE3ULJj2rSesCjduUaC/wyvH/sNr2Q==", "license": "MIT", "dependencies": { "@turf/helpers": "^7.2.0", "@types/geojson": "^7946.0.10", "tslib": "^2.8.1" }, - "funding": { - "url": "https://opencollective.com/turf" - } - }, - "node_modules/@tweenjs/tween.js": { - "version": "23.1.3", - "resolved": "https://registry.npmjs.org/@tweenjs/tween.js/-/tween.js-23.1.3.tgz", - "integrity": "sha512-vJmvvwFxYuGnF2axRtPYocag6Clbb5YS7kLL+SO/TeVFzHqDIWrNKYtcsPMibjDx9O+bu+psAy9NKfWklassUA==", - "license": "MIT" - }, - "node_modules/@tybys/wasm-util": { - "version": "0.10.1", - "resolved": "https://registry.npmjs.org/@tybys/wasm-util/-/wasm-util-0.10.1.tgz", - "integrity": "sha512-9tTaPJLSiejZKx+Bmog4uSubteqTvFrVrURwkmHixBo0G4seD0zUxp98E1DzUBJxLQ3NPwXrGKDiVjwx/DpPsg==", - "dev": true, - "license": "MIT", - "optional": true, - "dependencies": { - "tslib": "^2.4.0" + "funding": { + "url": "https://opencollective.com/turf" } }, + "node_modules/@tweenjs/tween.js": { + "version": "23.1.3", + "license": "MIT" + }, "node_modules/@types/babel__core": { "version": "7.20.5", - "resolved": "https://registry.npmjs.org/@types/babel__core/-/babel__core-7.20.5.tgz", - "integrity": "sha512-qoQprZvz5wQFJwMDqeseRXWv3rqMvhgpbXFfVyWhbx9X47POIA6i/+dXefEmZKoAgOaTdaIgNSMqMIU61yRyzA==", "dev": true, "license": "MIT", "dependencies": { @@ -6461,8 +5471,6 @@ }, "node_modules/@types/babel__generator": { "version": "7.27.0", - "resolved": "https://registry.npmjs.org/@types/babel__generator/-/babel__generator-7.27.0.tgz", - "integrity": "sha512-ufFd2Xi92OAVPYsy+P4n7/U7e68fex0+Ee8gSG9KX7eo084CWiQ4sdxktvdl0bOPupXtVJPY19zk6EwWqUQ8lg==", "dev": true, "license": "MIT", "dependencies": { @@ -6471,8 +5479,6 @@ }, "node_modules/@types/babel__template": { "version": "7.4.4", - "resolved": "https://registry.npmjs.org/@types/babel__template/-/babel__template-7.4.4.tgz", - "integrity": "sha512-h/NUaSyG5EyxBIp8YRxo4RMe2/qQgvyowRwVMzhYhBCONbW8PUsg4lkFMrhgZhUe5z3L3MiLDuvyJ/CaPa2A8A==", "dev": true, "license": "MIT", "dependencies": { @@ -6482,8 +5488,6 @@ }, "node_modules/@types/babel__traverse": { "version": "7.28.0", - "resolved": "https://registry.npmjs.org/@types/babel__traverse/-/babel__traverse-7.28.0.tgz", - "integrity": "sha512-8PvcXf70gTDZBgt9ptxJ8elBeBjcLOAcOtoO/mPJjtji1+CdGbHgm77om1GrsPxsiE+uXIpNSK64UYaIwQXd4Q==", "dev": true, "license": "MIT", "dependencies": { @@ -6492,8 +5496,6 @@ }, "node_modules/@types/base32-encoding": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@types/base32-encoding/-/base32-encoding-1.0.2.tgz", - "integrity": "sha512-6kXiZ8gETqBU/B9ddcw15nwacX4iX9mLZTU0kghWK5u+OdjfJg6vxHh/vXoURWTyLSzs2jKgcq1lS3S/Tvl4mw==", "license": "MIT", "dependencies": { "@types/node": "*" @@ -6501,8 +5503,6 @@ }, "node_modules/@types/busboy": { "version": "1.5.4", - "resolved": "https://registry.npmjs.org/@types/busboy/-/busboy-1.5.4.tgz", - "integrity": "sha512-kG7WrUuAKK0NoyxfQHsVE6j1m01s6kMma64E+OZenQABMQyTJop1DumUWcLwAQ2JzpefU7PDYoRDKl8uZosFjw==", "dev": true, "license": "MIT", "dependencies": { @@ -6511,14 +5511,10 @@ }, "node_modules/@types/cookie": { "version": "0.6.0", - "resolved": "https://registry.npmjs.org/@types/cookie/-/cookie-0.6.0.tgz", - "integrity": "sha512-4Kh9a6B2bQciAhf7FSuMRRkUWecJgJu9nPnx3yzpsfXX/c50REIqpHY4C82bXP90qrLtXtkDxTZosYO3UpOwlA==", "license": "MIT" }, "node_modules/@types/cors": { "version": "2.8.18", - "resolved": "https://registry.npmjs.org/@types/cors/-/cors-2.8.18.tgz", - "integrity": "sha512-nX3d0sxJW41CqQvfOzVG1NCTXfFDrDWIghCZncpHeWlVFd81zxB/DLhg7avFg6eHLCRX7ckBmoIIcqa++upvJA==", "dev": true, "license": "MIT", "dependencies": { @@ -6527,26 +5523,18 @@ }, "node_modules/@types/d3-array": { "version": "3.2.1", - "resolved": "https://registry.npmjs.org/@types/d3-array/-/d3-array-3.2.1.tgz", - "integrity": "sha512-Y2Jn2idRrLzUfAKV2LyRImR+y4oa2AntrgID95SHJxuMUrkNXmanDSed71sRNZysveJVt1hLLemQZIady0FpEg==", "license": "MIT" }, "node_modules/@types/d3-color": { "version": "3.1.3", - "resolved": "https://registry.npmjs.org/@types/d3-color/-/d3-color-3.1.3.tgz", - "integrity": "sha512-iO90scth9WAbmgv7ogoq57O9YpKmFBbmoEoCHDB2xMBY0+/KVrqAaCDyCE16dUspeOvIxFFRI+0sEtqDqy2b4A==", "license": "MIT" }, "node_modules/@types/d3-ease": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/@types/d3-ease/-/d3-ease-3.0.2.tgz", - "integrity": "sha512-NcV1JjO5oDzoK26oMzbILE6HW7uVXOHLQvHshBUW4UMdZGfiY6v5BeQwh9a9tCzv+CeefZQHJt5SRgK154RtiA==", "license": "MIT" }, "node_modules/@types/d3-interpolate": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/d3-interpolate/-/d3-interpolate-3.0.4.tgz", - "integrity": "sha512-mgLPETlrpVV1YRJIglr4Ez47g7Yxjl1lj7YKsiMCb27VJH9W8NVM6Bb9d8kkpG/uAQS5AmbA48q2IAolKKo1MA==", "license": "MIT", "dependencies": { "@types/d3-color": "*" @@ -6554,14 +5542,10 @@ }, "node_modules/@types/d3-path": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/@types/d3-path/-/d3-path-3.1.0.tgz", - "integrity": "sha512-P2dlU/q51fkOc/Gfl3Ul9kicV7l+ra934qBFXCFhrZMOL6du1TM0pm1ThYvENukyOn5h9v+yMJ9Fn5JK4QozrQ==", "license": "MIT" }, "node_modules/@types/d3-scale": { "version": "4.0.8", - "resolved": "https://registry.npmjs.org/@types/d3-scale/-/d3-scale-4.0.8.tgz", - "integrity": "sha512-gkK1VVTr5iNiYJ7vWDI+yUFFlszhNMtVeneJ6lUTKPjprsvLLI9/tgEGiXJOnlINJA8FyA88gfnQsHbybVZrYQ==", "license": "MIT", "dependencies": { "@types/d3-time": "*" @@ -6569,8 +5553,6 @@ }, "node_modules/@types/d3-shape": { "version": "3.1.7", - "resolved": "https://registry.npmjs.org/@types/d3-shape/-/d3-shape-3.1.7.tgz", - "integrity": "sha512-VLvUQ33C+3J+8p+Daf+nYSOsjB4GXp19/S/aGo60m9h1v6XaxjiT82lKVWJCfzhtuZ3yD7i/TPeC/fuKLLOSmg==", "license": "MIT", "dependencies": { "@types/d3-path": "*" @@ -6578,50 +5560,29 @@ }, "node_modules/@types/d3-time": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/d3-time/-/d3-time-3.0.4.tgz", - "integrity": "sha512-yuzZug1nkAAaBlBBikKZTgzCeA+k1uy4ZFwWANOfKw5z5LRhV0gNA7gNkKm7HoK+HRN0wX3EkxGk0fpbWhmB7g==", "license": "MIT" }, "node_modules/@types/d3-timer": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/@types/d3-timer/-/d3-timer-3.0.2.tgz", - "integrity": "sha512-Ps3T8E8dZDam6fUyNiMkekK3XUsaUEik+idO9/YjPtfj2qruF8tFBXS7XhtE4iIXBLxhmLjP3SXpLhVf21I9Lw==", "license": "MIT" }, "node_modules/@types/debounce": { "version": "1.2.4", - "resolved": "https://registry.npmjs.org/@types/debounce/-/debounce-1.2.4.tgz", - "integrity": "sha512-jBqiORIzKDOToaF63Fm//haOCHuwQuLa2202RK4MozpA6lh93eCBc+/8+wZn5OzjJt3ySdc+74SXWXB55Ewtyw==", "license": "MIT" }, "node_modules/@types/debug": { "version": "4.1.12", - "resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.12.tgz", - "integrity": "sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ==", "license": "MIT", "dependencies": { "@types/ms": "*" } }, - "node_modules/@types/dns-packet": { - "version": "5.6.5", - "resolved": "https://registry.npmjs.org/@types/dns-packet/-/dns-packet-5.6.5.tgz", - "integrity": "sha512-qXOC7XLOEe43ehtWJCMnQXvgcIpv6rPmQ1jXT98Ad8A3TB1Ue50jsCbSSSyuazScEuZ/Q026vHbrOTVkmwA+7Q==", - "license": "MIT", - "dependencies": { - "@types/node": "*" - } - }, "node_modules/@types/draco3d": { "version": "1.4.10", - "resolved": "https://registry.npmjs.org/@types/draco3d/-/draco3d-1.4.10.tgz", - "integrity": "sha512-AX22jp8Y7wwaBgAixaSvkoG4M/+PlAcm3Qs4OW8yT9DM4xUpWKeFhLueTAyZF39pviAdcDdeJoACapiAceqNcw==", "license": "MIT" }, "node_modules/@types/eslint": { "version": "8.56.12", - "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-8.56.12.tgz", - "integrity": "sha512-03ruubjWyOHlmljCVoxSuNDdmfZDzsrrz0P2LeJsOXr+ZwFQ+0yQIwNCwt/GYhV7Z31fgtXJTAEs+FYlEL851g==", "dev": true, "license": "MIT", "dependencies": { @@ -6631,14 +5592,10 @@ }, "node_modules/@types/estree": { "version": "1.0.6", - "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.6.tgz", - "integrity": "sha512-AYnb1nQyY49te+VRAVgmzfcgjYS91mY5P0TKUDCLEM+gNnA+3T6rWITXRLYCpahpqSQbN5cE+gHpnPyXjHWxcw==", "license": "MIT" }, "node_modules/@types/estree-jsx": { "version": "1.0.5", - "resolved": "https://registry.npmjs.org/@types/estree-jsx/-/estree-jsx-1.0.5.tgz", - "integrity": "sha512-52CcUVNFyfb1A2ALocQw/Dd1BQFNmSdkuC3BkZ6iqhdMfQz7JWOFRuJFloOzjk+6WijU56m9oKXFAXc7o3Towg==", "license": "MIT", "dependencies": { "@types/estree": "*" @@ -6646,8 +5603,6 @@ }, "node_modules/@types/formidable": { "version": "3.4.5", - "resolved": "https://registry.npmjs.org/@types/formidable/-/formidable-3.4.5.tgz", - "integrity": "sha512-s7YPsNVfnsng5L8sKnG/Gbb2tiwwJTY1conOkJzTMRvJAlLFW1nEua+ADsJQu8N1c0oTHx9+d5nqg10WuT9gHQ==", "dev": true, "license": "MIT", "dependencies": { @@ -6656,14 +5611,10 @@ }, "node_modules/@types/geojson": { "version": "7946.0.16", - "resolved": "https://registry.npmjs.org/@types/geojson/-/geojson-7946.0.16.tgz", - "integrity": "sha512-6C8nqWur3j98U6+lXDfTUWIfgvZU+EumvpHKcYjujKH7woYyLj2sUmff0tRhrqM7BohUw7Pz3ZB1jj2gW9Fvmg==", "license": "MIT" }, "node_modules/@types/hast": { "version": "2.3.10", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-2.3.10.tgz", - "integrity": "sha512-McWspRw8xx8J9HurkVBfYj0xKoE25tOFlHGdx4MJ5xORQrMGZNqJhVQWaIbm6Oyla5kYOXtDiopzKRJzEOkwJw==", "license": "MIT", "dependencies": { "@types/unist": "^2" @@ -6671,15 +5622,11 @@ }, "node_modules/@types/istanbul-lib-coverage": { "version": "2.0.6", - "resolved": "https://registry.npmjs.org/@types/istanbul-lib-coverage/-/istanbul-lib-coverage-2.0.6.tgz", - "integrity": "sha512-2QF/t/auWm0lsy8XtKVPG19v3sSOQlJe/YHZgfjb/KBBHOGSV+J2q/S671rcq9uTBrLAXmZpqJiaQbMT+zNU1w==", "dev": true, "license": "MIT" }, "node_modules/@types/istanbul-lib-report": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/istanbul-lib-report/-/istanbul-lib-report-3.0.3.tgz", - "integrity": "sha512-NQn7AHQnk/RSLOxrBbGyJM/aVQ+pjj5HCgasFxc0K/KhoATfQ/47AyUl15I2yBUpihjmas+a+VJBOqecrFH+uA==", "dev": true, "license": "MIT", "dependencies": { @@ -6688,8 +5635,6 @@ }, "node_modules/@types/istanbul-reports": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/istanbul-reports/-/istanbul-reports-3.0.4.tgz", - "integrity": "sha512-pk2B1NWalF9toCRu6gjBzR69syFjP4Od8WRAX+0mmf9lAjCRicLOWc+ZrxZHx/0XRjotgkF9t6iaMJ+aXcOdZQ==", "dev": true, "license": "MIT", "dependencies": { @@ -6698,8 +5643,6 @@ }, "node_modules/@types/jest": { "version": "30.0.0", - "resolved": "https://registry.npmjs.org/@types/jest/-/jest-30.0.0.tgz", - "integrity": "sha512-XTYugzhuwqWjws0CVz8QpM36+T+Dz5mTEBKhNs/esGLnCIlGdRy+Dq78NRjd7ls7r8BC8ZRMOrKlkO1hU0JOwA==", "dev": true, "license": "MIT", "dependencies": { @@ -6709,8 +5652,6 @@ }, "node_modules/@types/jest/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -6722,8 +5663,6 @@ }, "node_modules/@types/jest/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -6737,8 +5676,6 @@ }, "node_modules/@types/jest/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, @@ -6750,28 +5687,20 @@ }, "node_modules/@types/json-schema": { "version": "7.0.15", - "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", - "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", "license": "MIT" }, "node_modules/@types/json5": { "version": "0.0.29", - "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", - "integrity": "sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==", "dev": true, "license": "MIT" }, "node_modules/@types/jsonld": { "version": "1.5.15", - "resolved": "https://registry.npmjs.org/@types/jsonld/-/jsonld-1.5.15.tgz", - "integrity": "sha512-PlAFPZjL+AuGYmwlqwKEL0IMP8M8RexH0NIPGfCVWSQ041H2rR/8OlyZSD7KsCVoN8vCfWdtWDBxX8yBVP+xow==", "dev": true, "license": "MIT" }, "node_modules/@types/jsonwebtoken": { "version": "9.0.9", - "resolved": "https://registry.npmjs.org/@types/jsonwebtoken/-/jsonwebtoken-9.0.9.tgz", - "integrity": "sha512-uoe+GxEuHbvy12OUQct2X9JenKM3qAscquYymuQN4fMWG9DBQtykrQEFcAbVACF7qaLw9BePSodUL0kquqBJpQ==", "dev": true, "license": "MIT", "dependencies": { @@ -6781,8 +5710,6 @@ }, "node_modules/@types/mdast": { "version": "4.0.4", - "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-4.0.4.tgz", - "integrity": "sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==", "license": "MIT", "dependencies": { "@types/unist": "*" @@ -6790,14 +5717,10 @@ }, "node_modules/@types/ms": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@types/ms/-/ms-2.1.0.tgz", - "integrity": "sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA==", "license": "MIT" }, "node_modules/@types/node": { "version": "20.17.16", - "resolved": "https://registry.npmjs.org/@types/node/-/node-20.17.16.tgz", - "integrity": "sha512-vOTpLduLkZXePLxHiHsBLp98mHGnl8RptV4YAO3HfKO5UHjDvySGbxKtpYfy8Sx5+WKcgc45qNreJJRVM3L6mw==", "license": "MIT", "dependencies": { "undici-types": "~6.19.2" @@ -6805,14 +5728,10 @@ }, "node_modules/@types/offscreencanvas": { "version": "2019.7.3", - "resolved": "https://registry.npmjs.org/@types/offscreencanvas/-/offscreencanvas-2019.7.3.tgz", - "integrity": "sha512-ieXiYmgSRXUDeOntE1InxjWyvEelZGP63M+cGuquuRLuIKKT1osnkXjxev9B7d1nXSug5vpunx+gNlbVxMlC9A==", "license": "MIT" }, "node_modules/@types/papaparse": { "version": "5.3.16", - "resolved": "https://registry.npmjs.org/@types/papaparse/-/papaparse-5.3.16.tgz", - "integrity": "sha512-T3VuKMC2H0lgsjI9buTB3uuKj3EMD2eap1MOuEQuBQ44EnDx/IkGhU6EwiTf9zG3za4SKlmwKAImdDKdNnCsXg==", "dev": true, "license": "MIT", "dependencies": { @@ -6821,14 +5740,10 @@ }, "node_modules/@types/prop-types": { "version": "15.7.14", - "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.14.tgz", - "integrity": "sha512-gNMvNH49DJ7OJYv+KAKn0Xp45p8PLl6zo2YnvDIbTd4J6MER2BmWN49TG7n9LvkyihINxeKW8+3bfS2yDC9dzQ==", "license": "MIT" }, "node_modules/@types/ramda": { "version": "0.30.2", - "resolved": "https://registry.npmjs.org/@types/ramda/-/ramda-0.30.2.tgz", - "integrity": "sha512-PyzHvjCalm2BRYjAU6nIB3TprYwMNOUY/7P/N8bSzp9W/yM2YrtGtAnnVtaCNSeOZ8DzKyFDvaqQs7LnWwwmBA==", "license": "MIT", "dependencies": { "types-ramda": "^0.30.1" @@ -6836,8 +5751,6 @@ }, "node_modules/@types/react": { "version": "18.3.18", - "resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.18.tgz", - "integrity": "sha512-t4yC+vtgnkYjNSKlFx1jkAhH8LgTo2N/7Qvi83kdEaUtMDiwpbLAktKDaAMlRcJ5eSxZkH74eEGt1ky31d7kfQ==", "license": "MIT", "dependencies": { "@types/prop-types": "*", @@ -6846,8 +5759,6 @@ }, "node_modules/@types/react-dom": { "version": "18.3.5", - "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-18.3.5.tgz", - "integrity": "sha512-P4t6saawp+b/dFrUr2cvkVsfvPguwsxtH6dNIYRllMsefqFzkZk5UIjzyDOv5g1dXIPdG4Sp1yCR4Z6RCUsG/Q==", "devOptional": true, "license": "MIT", "peerDependencies": { @@ -6856,8 +5767,6 @@ }, "node_modules/@types/react-reconciler": { "version": "0.26.7", - "resolved": "https://registry.npmjs.org/@types/react-reconciler/-/react-reconciler-0.26.7.tgz", - "integrity": "sha512-mBDYl8x+oyPX/VBb3E638N0B7xG+SPk/EAMcVPeexqus/5aTpTphQi0curhhshOqRrc9t6OPoJfEUkbymse/lQ==", "license": "MIT", "dependencies": { "@types/react": "*" @@ -6865,28 +5774,20 @@ }, "node_modules/@types/stack-utils": { "version": "2.0.3", - "resolved": "https://registry.npmjs.org/@types/stack-utils/-/stack-utils-2.0.3.tgz", - "integrity": "sha512-9aEbYZ3TbYMznPdcdr3SmIrLXwC/AKZXQeCf9Pgao5CKb8CyHuEX5jzWPTkvregvhRJHcpRO6BFoGW9ycaOkYw==", "dev": true, "license": "MIT" }, "node_modules/@types/stats.js": { "version": "0.17.3", - "resolved": "https://registry.npmjs.org/@types/stats.js/-/stats.js-0.17.3.tgz", - "integrity": "sha512-pXNfAD3KHOdif9EQXZ9deK82HVNaXP5ZIF5RP2QG6OQFNTaY2YIetfrE9t528vEreGQvEPRDDc8muaoYeK0SxQ==", "license": "MIT" }, "node_modules/@types/swagger-jsdoc": { "version": "6.0.4", - "resolved": "https://registry.npmjs.org/@types/swagger-jsdoc/-/swagger-jsdoc-6.0.4.tgz", - "integrity": "sha512-W+Xw5epcOZrF/AooUM/PccNMSAFOKWZA5dasNyMujTwsBkU74njSJBpvCCJhHAJ95XRMzQrrW844Btu0uoetwQ==", "dev": true, "license": "MIT" }, "node_modules/@types/swagger-ui-react": { "version": "5.18.0", - "resolved": "https://registry.npmjs.org/@types/swagger-ui-react/-/swagger-ui-react-5.18.0.tgz", - "integrity": "sha512-c2M9adVG7t28t1pq19K9Jt20VLQf0P/fwJwnfcmsVVsdkwCWhRmbKDu+tIs0/NGwJ/7GY8lBx+iKZxuDI5gDbw==", "dev": true, "license": "MIT", "dependencies": { @@ -6895,8 +5796,6 @@ }, "node_modules/@types/three": { "version": "0.172.0", - "resolved": "https://registry.npmjs.org/@types/three/-/three-0.172.0.tgz", - "integrity": "sha512-LrUtP3FEG26Zg5WiF0nbg8VoXiKokBLTcqM2iLvM9vzcfEiYmmBAPGdBgV0OYx9fvWlY3R/3ERTZcD9X5sc0NA==", "license": "MIT", "dependencies": { "@tweenjs/tween.js": "~23.1.3", @@ -6909,33 +5808,23 @@ }, "node_modules/@types/trusted-types": { "version": "2.0.7", - "resolved": "https://registry.npmjs.org/@types/trusted-types/-/trusted-types-2.0.7.tgz", - "integrity": "sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==", "license": "MIT", "optional": true }, "node_modules/@types/unist": { "version": "2.0.11", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.11.tgz", - "integrity": "sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==", "license": "MIT" }, "node_modules/@types/use-sync-external-store": { "version": "0.0.6", - "resolved": "https://registry.npmjs.org/@types/use-sync-external-store/-/use-sync-external-store-0.0.6.tgz", - "integrity": "sha512-zFDAD+tlpf2r4asuHEj0XH6pY6i0g5NeAHPn+15wk3BV6JA69eERFXC1gyGThDkVa1zCyKr5jox1+2LbV/AMLg==", "license": "MIT" }, "node_modules/@types/webxr": { "version": "0.5.21", - "resolved": "https://registry.npmjs.org/@types/webxr/-/webxr-0.5.21.tgz", - "integrity": "sha512-geZIAtLzjGmgY2JUi6VxXdCrTb99A7yP49lxLr2Nm/uIK0PkkxcEi4OGhoGDO4pxCf3JwGz2GiJL2Ej4K2bKaA==", "license": "MIT" }, "node_modules/@types/yargs": { "version": "17.0.33", - "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-17.0.33.tgz", - "integrity": "sha512-WpxBCKWPLr4xSsHgz511rFJAM+wS28w2zEO1QDNY5zM/S8ok70NNfztH0xwhqKyaK0OHCbN98LDAZuy1ctxDkA==", "dev": true, "license": "MIT", "dependencies": { @@ -6944,15 +5833,11 @@ }, "node_modules/@types/yargs-parser": { "version": "21.0.3", - "resolved": "https://registry.npmjs.org/@types/yargs-parser/-/yargs-parser-21.0.3.tgz", - "integrity": "sha512-I4q9QU9MQv4oEOz4tAHJtNz1cwuLxn2F3xcc2iV5WdqLPpUnj30aUuxt1mAxYTG+oe8CZMV/+6rU4S4gRDzqtQ==", "dev": true, "license": "MIT" }, "node_modules/@typescript-eslint/eslint-plugin": { "version": "8.22.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.22.0.tgz", - "integrity": "sha512-4Uta6REnz/xEJMvwf72wdUnC3rr4jAQf5jnTkeRQ9b6soxLxhDEbS/pfMPoJLDfFPNVRdryqWUIV/2GZzDJFZw==", "dev": true, "license": "MIT", "dependencies": { @@ -6981,8 +5866,6 @@ }, "node_modules/@typescript-eslint/parser": { "version": "8.22.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.22.0.tgz", - "integrity": "sha512-MqtmbdNEdoNxTPzpWiWnqNac54h8JDAmkWtJExBVVnSrSmi9z+sZUt0LfKqk9rjqmKOIeRhO4fHHJ1nQIjduIQ==", "dev": true, "license": "MIT", "dependencies": { @@ -7006,8 +5889,6 @@ }, "node_modules/@typescript-eslint/scope-manager": { "version": "8.22.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.22.0.tgz", - "integrity": "sha512-/lwVV0UYgkj7wPSw0o8URy6YI64QmcOdwHuGuxWIYznO6d45ER0wXUbksr9pYdViAofpUCNJx/tAzNukgvaaiQ==", "dev": true, "license": "MIT", "dependencies": { @@ -7024,8 +5905,6 @@ }, "node_modules/@typescript-eslint/type-utils": { "version": "8.22.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.22.0.tgz", - "integrity": "sha512-NzE3aB62fDEaGjaAYZE4LH7I1MUwHooQ98Byq0G0y3kkibPJQIXVUspzlFOmOfHhiDLwKzMlWxaNv+/qcZurJA==", "dev": true, "license": "MIT", "dependencies": { @@ -7045,401 +5924,126 @@ "eslint": "^8.57.0 || ^9.0.0", "typescript": ">=4.8.4 <5.8.0" } - }, - "node_modules/@typescript-eslint/types": { - "version": "8.22.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.22.0.tgz", - "integrity": "sha512-0S4M4baNzp612zwpD4YOieP3VowOARgK2EkN/GBn95hpyF8E2fbMT55sRHWBq+Huaqk3b3XK+rxxlM8sPgGM6A==", - "dev": true, - "license": "MIT", - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/typescript-estree": { - "version": "8.22.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.22.0.tgz", - "integrity": "sha512-SJX99NAS2ugGOzpyhMza/tX+zDwjvwAtQFLsBo3GQxiGcvaKlqGBkmZ+Y1IdiSi9h4Q0Lr5ey+Cp9CGWNY/F/w==", - "dev": true, - "license": "MIT", - "dependencies": { - "@typescript-eslint/types": "8.22.0", - "@typescript-eslint/visitor-keys": "8.22.0", - "debug": "^4.3.4", - "fast-glob": "^3.3.2", - "is-glob": "^4.0.3", - "minimatch": "^9.0.4", - "semver": "^7.6.0", - "ts-api-utils": "^2.0.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.8.0" - } - }, - "node_modules/@typescript-eslint/typescript-estree/node_modules/semver": { - "version": "7.6.3", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", - "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", - "dev": true, - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/@typescript-eslint/utils": { - "version": "8.22.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.22.0.tgz", - "integrity": "sha512-T8oc1MbF8L+Bk2msAvCUzjxVB2Z2f+vXYfcucE2wOmYs7ZUwco5Ep0fYZw8quNwOiw9K8GYVL+Kgc2pETNTLOg==", - "dev": true, - "license": "MIT", - "dependencies": { - "@eslint-community/eslint-utils": "^4.4.0", - "@typescript-eslint/scope-manager": "8.22.0", - "@typescript-eslint/types": "8.22.0", - "@typescript-eslint/typescript-estree": "8.22.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.8.0" - } - }, - "node_modules/@typescript-eslint/visitor-keys": { - "version": "8.22.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.22.0.tgz", - "integrity": "sha512-AWpYAXnUgvLNabGTy3uBylkgZoosva/miNd1I8Bz3SjotmQPbVqhO4Cczo8AsZ44XVErEBPr/CRSgaj8sG7g0w==", - "dev": true, - "license": "MIT", - "dependencies": { - "@typescript-eslint/types": "8.22.0", - "eslint-visitor-keys": "^4.2.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/visitor-keys/node_modules/eslint-visitor-keys": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.0.tgz", - "integrity": "sha512-UyLnSehNt62FFhSwjZlHmeokpRK59rcz29j+F1/aDgbkbRTk7wIc9XzdoasMUbRNKDM0qQt/+BJ4BrpFeABemw==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" - } - }, - "node_modules/@ungap/structured-clone": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/@ungap/structured-clone/-/structured-clone-1.3.0.tgz", - "integrity": "sha512-WmoN8qaIAo7WTYWbAZuG8PYEhn5fkz7dZrqTBZ7dtt//lL2Gwms1IcnQ5yHqjDfX8Ft5j4YzDM23f87zBfDe9g==", - "license": "ISC" - }, - "node_modules/@unrs/resolver-binding-android-arm-eabi": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-android-arm-eabi/-/resolver-binding-android-arm-eabi-1.11.1.tgz", - "integrity": "sha512-ppLRUgHVaGRWUx0R0Ut06Mjo9gBaBkg3v/8AxusGLhsIotbBLuRk51rAzqLC8gq6NyyAojEXglNjzf6R948DNw==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "android" - ] - }, - "node_modules/@unrs/resolver-binding-android-arm64": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-android-arm64/-/resolver-binding-android-arm64-1.11.1.tgz", - "integrity": "sha512-lCxkVtb4wp1v+EoN+HjIG9cIIzPkX5OtM03pQYkG+U5O/wL53LC4QbIeazgiKqluGeVEeBlZahHalCaBvU1a2g==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "android" - ] - }, - "node_modules/@unrs/resolver-binding-darwin-arm64": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-darwin-arm64/-/resolver-binding-darwin-arm64-1.11.1.tgz", - "integrity": "sha512-gPVA1UjRu1Y/IsB/dQEsp2V1pm44Of6+LWvbLc9SDk1c2KhhDRDBUkQCYVWe6f26uJb3fOK8saWMgtX8IrMk3g==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ] - }, - "node_modules/@unrs/resolver-binding-darwin-x64": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-darwin-x64/-/resolver-binding-darwin-x64-1.11.1.tgz", - "integrity": "sha512-cFzP7rWKd3lZaCsDze07QX1SC24lO8mPty9vdP+YVa3MGdVgPmFc59317b2ioXtgCMKGiCLxJ4HQs62oz6GfRQ==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ] - }, - "node_modules/@unrs/resolver-binding-freebsd-x64": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-freebsd-x64/-/resolver-binding-freebsd-x64-1.11.1.tgz", - "integrity": "sha512-fqtGgak3zX4DCB6PFpsH5+Kmt/8CIi4Bry4rb1ho6Av2QHTREM+47y282Uqiu3ZRF5IQioJQ5qWRV6jduA+iGw==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "freebsd" - ] - }, - "node_modules/@unrs/resolver-binding-linux-arm-gnueabihf": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm-gnueabihf/-/resolver-binding-linux-arm-gnueabihf-1.11.1.tgz", - "integrity": "sha512-u92mvlcYtp9MRKmP+ZvMmtPN34+/3lMHlyMj7wXJDeXxuM0Vgzz0+PPJNsro1m3IZPYChIkn944wW8TYgGKFHw==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@unrs/resolver-binding-linux-arm-musleabihf": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm-musleabihf/-/resolver-binding-linux-arm-musleabihf-1.11.1.tgz", - "integrity": "sha512-cINaoY2z7LVCrfHkIcmvj7osTOtm6VVT16b5oQdS4beibX2SYBwgYLmqhBjA1t51CarSaBuX5YNsWLjsqfW5Cw==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@unrs/resolver-binding-linux-arm64-gnu": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm64-gnu/-/resolver-binding-linux-arm64-gnu-1.11.1.tgz", - "integrity": "sha512-34gw7PjDGB9JgePJEmhEqBhWvCiiWCuXsL9hYphDF7crW7UgI05gyBAi6MF58uGcMOiOqSJ2ybEeCvHcq0BCmQ==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@unrs/resolver-binding-linux-arm64-musl": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-arm64-musl/-/resolver-binding-linux-arm64-musl-1.11.1.tgz", - "integrity": "sha512-RyMIx6Uf53hhOtJDIamSbTskA99sPHS96wxVE/bJtePJJtpdKGXO1wY90oRdXuYOGOTuqjT8ACccMc4K6QmT3w==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@unrs/resolver-binding-linux-ppc64-gnu": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-ppc64-gnu/-/resolver-binding-linux-ppc64-gnu-1.11.1.tgz", - "integrity": "sha512-D8Vae74A4/a+mZH0FbOkFJL9DSK2R6TFPC9M+jCWYia/q2einCubX10pecpDiTmkJVUH+y8K3BZClycD8nCShA==", - "cpu": [ - "ppc64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@unrs/resolver-binding-linux-riscv64-gnu": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-riscv64-gnu/-/resolver-binding-linux-riscv64-gnu-1.11.1.tgz", - "integrity": "sha512-frxL4OrzOWVVsOc96+V3aqTIQl1O2TjgExV4EKgRY09AJ9leZpEg8Ak9phadbuX0BA4k8U5qtvMSQQGGmaJqcQ==", - "cpu": [ - "riscv64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@unrs/resolver-binding-linux-riscv64-musl": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-riscv64-musl/-/resolver-binding-linux-riscv64-musl-1.11.1.tgz", - "integrity": "sha512-mJ5vuDaIZ+l/acv01sHoXfpnyrNKOk/3aDoEdLO/Xtn9HuZlDD6jKxHlkN8ZhWyLJsRBxfv9GYM2utQ1SChKew==", - "cpu": [ - "riscv64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@unrs/resolver-binding-linux-s390x-gnu": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-s390x-gnu/-/resolver-binding-linux-s390x-gnu-1.11.1.tgz", - "integrity": "sha512-kELo8ebBVtb9sA7rMe1Cph4QHreByhaZ2QEADd9NzIQsYNQpt9UkM9iqr2lhGr5afh885d/cB5QeTXSbZHTYPg==", - "cpu": [ - "s390x" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@unrs/resolver-binding-linux-x64-gnu": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-x64-gnu/-/resolver-binding-linux-x64-gnu-1.11.1.tgz", - "integrity": "sha512-C3ZAHugKgovV5YvAMsxhq0gtXuwESUKc5MhEtjBpLoHPLYM+iuwSj3lflFwK3DPm68660rZ7G8BMcwSro7hD5w==", - "cpu": [ - "x64" - ], + }, + "node_modules/@typescript-eslint/types": { + "version": "8.22.0", "dev": true, "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } }, - "node_modules/@unrs/resolver-binding-linux-x64-musl": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-linux-x64-musl/-/resolver-binding-linux-x64-musl-1.11.1.tgz", - "integrity": "sha512-rV0YSoyhK2nZ4vEswT/QwqzqQXw5I6CjoaYMOX0TqBlWhojUf8P94mvI7nuJTeaCkkds3QE4+zS8Ko+GdXuZtA==", - "cpu": [ - "x64" - ], + "node_modules/@typescript-eslint/typescript-estree": { + "version": "8.22.0", "dev": true, "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "dependencies": { + "@typescript-eslint/types": "8.22.0", + "@typescript-eslint/visitor-keys": "8.22.0", + "debug": "^4.3.4", + "fast-glob": "^3.3.2", + "is-glob": "^4.0.3", + "minimatch": "^9.0.4", + "semver": "^7.6.0", + "ts-api-utils": "^2.0.0" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "typescript": ">=4.8.4 <5.8.0" + } }, - "node_modules/@unrs/resolver-binding-wasm32-wasi": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-wasm32-wasi/-/resolver-binding-wasm32-wasi-1.11.1.tgz", - "integrity": "sha512-5u4RkfxJm+Ng7IWgkzi3qrFOvLvQYnPBmjmZQ8+szTK/b31fQCnleNl1GgEt7nIsZRIf5PLhPwT0WM+q45x/UQ==", - "cpu": [ - "wasm32" - ], + "node_modules/@typescript-eslint/typescript-estree/node_modules/semver": { + "version": "7.6.3", + "dev": true, + "license": "ISC", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@typescript-eslint/utils": { + "version": "8.22.0", "dev": true, "license": "MIT", - "optional": true, "dependencies": { - "@napi-rs/wasm-runtime": "^0.2.11" + "@eslint-community/eslint-utils": "^4.4.0", + "@typescript-eslint/scope-manager": "8.22.0", + "@typescript-eslint/types": "8.22.0", + "@typescript-eslint/typescript-estree": "8.22.0" }, "engines": { - "node": ">=14.0.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^8.57.0 || ^9.0.0", + "typescript": ">=4.8.4 <5.8.0" } }, - "node_modules/@unrs/resolver-binding-win32-arm64-msvc": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-win32-arm64-msvc/-/resolver-binding-win32-arm64-msvc-1.11.1.tgz", - "integrity": "sha512-nRcz5Il4ln0kMhfL8S3hLkxI85BXs3o8EYoattsJNdsX4YUU89iOkVn7g0VHSRxFuVMdM4Q1jEpIId1Ihim/Uw==", - "cpu": [ - "arm64" - ], + "node_modules/@typescript-eslint/visitor-keys": { + "version": "8.22.0", "dev": true, "license": "MIT", - "optional": true, - "os": [ - "win32" - ] + "dependencies": { + "@typescript-eslint/types": "8.22.0", + "eslint-visitor-keys": "^4.2.0" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } }, - "node_modules/@unrs/resolver-binding-win32-ia32-msvc": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-win32-ia32-msvc/-/resolver-binding-win32-ia32-msvc-1.11.1.tgz", - "integrity": "sha512-DCEI6t5i1NmAZp6pFonpD5m7i6aFrpofcp4LA2i8IIq60Jyo28hamKBxNrZcyOwVOZkgsRp9O2sXWBWP8MnvIQ==", - "cpu": [ - "ia32" - ], + "node_modules/@typescript-eslint/visitor-keys/node_modules/eslint-visitor-keys": { + "version": "4.2.0", "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "win32" - ] + "license": "Apache-2.0", + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/@ungap/structured-clone": { + "version": "1.3.0", + "license": "ISC" }, - "node_modules/@unrs/resolver-binding-win32-x64-msvc": { + "node_modules/@unrs/resolver-binding-darwin-arm64": { "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@unrs/resolver-binding-win32-x64-msvc/-/resolver-binding-win32-x64-msvc-1.11.1.tgz", - "integrity": "sha512-lrW200hZdbfRtztbygyaq/6jP6AKE8qQN2KvPcJ+x7wiD038YtnYtZ82IMNJ69GJibV7bwL3y9FgK+5w/pYt6g==", "cpu": [ - "x64" + "arm64" ], "dev": true, "license": "MIT", "optional": true, "os": [ - "win32" + "darwin" ] }, "node_modules/@use-gesture/core": { "version": "10.3.1", - "resolved": "https://registry.npmjs.org/@use-gesture/core/-/core-10.3.1.tgz", - "integrity": "sha512-WcINiDt8WjqBdUXye25anHiNxPc0VOrlT8F6LLkU6cycrOGUDyY/yyFmsg3k8i5OLvv25llc0QC45GhR/C8llw==", "license": "MIT" }, "node_modules/@use-gesture/react": { "version": "10.3.1", - "resolved": "https://registry.npmjs.org/@use-gesture/react/-/react-10.3.1.tgz", - "integrity": "sha512-Yy19y6O2GJq8f7CHf7L0nxL8bf4PZCPaVOCgJrusOeFHY1LvHgYXnmnXg6N5iwAnbgbZCDjo60SiM6IPJi9C5g==", "license": "MIT", "dependencies": { "@use-gesture/core": "10.3.1" @@ -7452,6 +6056,7 @@ "version": "0.6.8", "resolved": "https://registry.npmjs.org/@utxorpc/sdk/-/sdk-0.6.8.tgz", "integrity": "sha512-Mff6q2o7R2aam85KmjtAZDKPhJesMmnGFbk2M54lPO0FwrrWRfUf6DYezqWfYcjXgKQSHDuklAcdtF0weEENRA==", + "license": "MIT", "dependencies": { "@connectrpc/connect": "1.4", "@connectrpc/connect-node": "1.4", @@ -7464,6 +6069,7 @@ "version": "0.16.0", "resolved": "https://registry.npmjs.org/@utxorpc/spec/-/spec-0.16.0.tgz", "integrity": "sha512-EK2M0TBp14MrRCYDuFeJ+bAS39RxxLLh+CD08h/YvAgxSv/4ZOBCf1/sxHAGCBGGndB4heZYFeuQ+i1i8vP5lw==", + "license": "MIT", "dependencies": { "@bufbuild/protobuf": "^1.10.0" }, @@ -7473,8 +6079,6 @@ }, "node_modules/@vercel/blob": { "version": "0.23.4", - "resolved": "https://registry.npmjs.org/@vercel/blob/-/blob-0.23.4.tgz", - "integrity": "sha512-cOU2e01RWZXFyc/OVRq+zZg38m34bcxpQk5insKp3Td9akNWThrXiF2URFHpRlm4fbaQ/l7pPSOB5nkLq+t6pw==", "license": "Apache-2.0", "dependencies": { "async-retry": "^1.3.3", @@ -7489,8 +6093,6 @@ }, "node_modules/@webgpu/types": { "version": "0.1.53", - "resolved": "https://registry.npmjs.org/@webgpu/types/-/types-0.1.53.tgz", - "integrity": "sha512-x+BLw/opaz9LiVyrMsP75nO1Rg0QfrACUYIbVSfGwY/w0DiWIPYYrpte6us//KZXinxFAOJl0+C17L1Vi2vmDw==", "license": "BSD-3-Clause" }, "node_modules/@webtorrent/http-node": { @@ -7512,8 +6114,6 @@ }, "node_modules/abort-controller": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", - "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", "license": "MIT", "dependencies": { "event-target-shim": "^5.0.0" @@ -7522,10 +6122,14 @@ "node": ">=6.5" } }, + "node_modules/abort-error": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/abort-error/-/abort-error-1.0.1.tgz", + "integrity": "sha512-fxqCblJiIPdSXIUrxI0PL+eJG49QdP9SQ70qtB65MVAoMr2rASlOyAbJFOylfB467F/f+5BCLJJq58RYi7mGfg==", + "license": "Apache-2.0 OR MIT" + }, "node_modules/accessor-fn": { "version": "1.5.1", - "resolved": "https://registry.npmjs.org/accessor-fn/-/accessor-fn-1.5.1.tgz", - "integrity": "sha512-zZpFYBqIL1Aqg+f2qmYHJ8+yIZF7/tP6PUGx2/QM0uGPSO5UegpinmkNwDohxWtOj586BpMPVRUjce2HI6xB3A==", "license": "MIT", "engines": { "node": ">=12" @@ -7533,8 +6137,6 @@ }, "node_modules/acorn": { "version": "8.14.0", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.14.0.tgz", - "integrity": "sha512-cl669nCJTZBsL97OF4kUQm5g5hC2uihk0NxY3WENAC0TYdILVkAyHymAntgxGkl7K+t0cXIrH5siy5S4XkFycA==", "dev": true, "license": "MIT", "bin": { @@ -7546,8 +6148,6 @@ }, "node_modules/acorn-jsx": { "version": "5.3.2", - "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", - "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", "dev": true, "license": "MIT", "peerDependencies": { @@ -7565,8 +6165,6 @@ }, "node_modules/ajv": { "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", "dev": true, "license": "MIT", "dependencies": { @@ -7582,8 +6180,6 @@ }, "node_modules/ansi-escapes": { "version": "4.3.2", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-4.3.2.tgz", - "integrity": "sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ==", "dev": true, "license": "MIT", "dependencies": { @@ -7598,8 +6194,6 @@ }, "node_modules/ansi-escapes/node_modules/type-fest": { "version": "0.21.3", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.21.3.tgz", - "integrity": "sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w==", "dev": true, "license": "(MIT OR CC0-1.0)", "engines": { @@ -7611,8 +6205,6 @@ }, "node_modules/ansi-regex": { "version": "5.0.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", - "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", "license": "MIT", "engines": { "node": ">=8" @@ -7620,8 +6212,6 @@ }, "node_modules/ansi-styles": { "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", "license": "MIT", "dependencies": { "color-convert": "^2.0.1" @@ -7635,14 +6225,10 @@ }, "node_modules/any-promise": { "version": "1.3.0", - "resolved": "https://registry.npmjs.org/any-promise/-/any-promise-1.3.0.tgz", - "integrity": "sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A==", "license": "MIT" }, "node_modules/anymatch": { "version": "3.1.3", - "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", - "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", "license": "ISC", "dependencies": { "normalize-path": "^3.0.0", @@ -7654,26 +6240,18 @@ }, "node_modules/apg-lite": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/apg-lite/-/apg-lite-1.0.4.tgz", - "integrity": "sha512-B32zCN3IdHIc99Vy7V9BaYTUzLeRA8YXYY1aQD1/5I2aqIrO0coi4t6hJPqMisidlBxhyME8UexkHt31SlR6Og==", "license": "BSD-2-Clause" }, "node_modules/arg": { "version": "5.0.2", - "resolved": "https://registry.npmjs.org/arg/-/arg-5.0.2.tgz", - "integrity": "sha512-PYjyFOLKQ9y57JvQ6QLo8dAgNqswh8M1RMJYdQduT6xbWSgK36P/Z/v+p888pM69jMMfS8Xd8F6I1kQ/I9HUGg==", "license": "MIT" }, "node_modules/argparse": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", - "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", "license": "Python-2.0" }, "node_modules/aria-hidden": { "version": "1.2.4", - "resolved": "https://registry.npmjs.org/aria-hidden/-/aria-hidden-1.2.4.tgz", - "integrity": "sha512-y+CcFFwelSXpLZk/7fMB2mUbGtX9lKycf1MWJ7CaTIERyitVlyQx6C+sxcROU2BAJ24OiZyK+8wj2i8AlBoS3A==", "license": "MIT", "dependencies": { "tslib": "^2.0.0" @@ -7684,8 +6262,6 @@ }, "node_modules/aria-query": { "version": "5.3.2", - "resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.3.2.tgz", - "integrity": "sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw==", "dev": true, "license": "Apache-2.0", "engines": { @@ -7694,8 +6270,6 @@ }, "node_modules/array-buffer-byte-length": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/array-buffer-byte-length/-/array-buffer-byte-length-1.0.2.tgz", - "integrity": "sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==", "dev": true, "license": "MIT", "dependencies": { @@ -7711,8 +6285,6 @@ }, "node_modules/array-includes": { "version": "3.1.8", - "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.8.tgz", - "integrity": "sha512-itaWrbYbqpGXkGhZPGUulwnhVf5Hpy1xiCFsGqyIGglbBxmG5vSjxQen3/WGOjPpNEv1RtBLKxbmVXm8HpJStQ==", "dev": true, "license": "MIT", "dependencies": { @@ -7732,8 +6304,6 @@ }, "node_modules/array.prototype.findlast": { "version": "1.2.5", - "resolved": "https://registry.npmjs.org/array.prototype.findlast/-/array.prototype.findlast-1.2.5.tgz", - "integrity": "sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==", "dev": true, "license": "MIT", "dependencies": { @@ -7753,8 +6323,6 @@ }, "node_modules/array.prototype.findlastindex": { "version": "1.2.5", - "resolved": "https://registry.npmjs.org/array.prototype.findlastindex/-/array.prototype.findlastindex-1.2.5.tgz", - "integrity": "sha512-zfETvRFA8o7EiNn++N5f/kaCw221hrpGsDmcpndVupkPzEc1Wuf3VgC0qby1BbHs7f5DVYjgtEU2LLh5bqeGfQ==", "dev": true, "license": "MIT", "dependencies": { @@ -7774,8 +6342,6 @@ }, "node_modules/array.prototype.flat": { "version": "1.3.3", - "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.3.3.tgz", - "integrity": "sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==", "dev": true, "license": "MIT", "dependencies": { @@ -7793,8 +6359,6 @@ }, "node_modules/array.prototype.flatmap": { "version": "1.3.3", - "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.3.tgz", - "integrity": "sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==", "dev": true, "license": "MIT", "dependencies": { @@ -7812,8 +6376,6 @@ }, "node_modules/array.prototype.tosorted": { "version": "1.1.4", - "resolved": "https://registry.npmjs.org/array.prototype.tosorted/-/array.prototype.tosorted-1.1.4.tgz", - "integrity": "sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==", "dev": true, "license": "MIT", "dependencies": { @@ -7829,8 +6391,6 @@ }, "node_modules/arraybuffer.prototype.slice": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.4.tgz", - "integrity": "sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==", "dev": true, "license": "MIT", "dependencies": { @@ -7851,8 +6411,6 @@ }, "node_modules/asap": { "version": "2.0.6", - "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", - "integrity": "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==", "license": "MIT" }, "node_modules/asn1js": { @@ -7871,15 +6429,11 @@ }, "node_modules/ast-types-flow": { "version": "0.0.8", - "resolved": "https://registry.npmjs.org/ast-types-flow/-/ast-types-flow-0.0.8.tgz", - "integrity": "sha512-OH/2E5Fg20h2aPrbe+QL8JZQFko0YZaF+j4mnQ7BGhfavO7OpSLa8a0y9sBwomHdSbkhTS8TQNayBfnW5DwbvQ==", "dev": true, "license": "MIT" }, "node_modules/async-function": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/async-function/-/async-function-1.0.0.tgz", - "integrity": "sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==", "dev": true, "license": "MIT", "engines": { @@ -7888,8 +6442,6 @@ }, "node_modules/async-retry": { "version": "1.3.3", - "resolved": "https://registry.npmjs.org/async-retry/-/async-retry-1.3.3.tgz", - "integrity": "sha512-wfr/jstw9xNi/0teMHrRW7dsz3Lt5ARhYNZ2ewpadnhaIp5mbALhOAP+EAdsC7t4Z6wqsDVv9+W6gm1Dk9mEyw==", "license": "MIT", "dependencies": { "retry": "0.13.1" @@ -7897,14 +6449,10 @@ }, "node_modules/asynckit": { "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", "license": "MIT" }, "node_modules/attr-accept": { "version": "2.2.5", - "resolved": "https://registry.npmjs.org/attr-accept/-/attr-accept-2.2.5.tgz", - "integrity": "sha512-0bDNnY/u6pPwHDMoF0FieU354oBi0a8rD9FcsLwzcGWbc8KS8KPIi7y+s13OlVY+gMWc/9xEMUgNE6Qm8ZllYQ==", "license": "MIT", "engines": { "node": ">=4" @@ -7912,8 +6460,6 @@ }, "node_modules/autolinker": { "version": "3.16.2", - "resolved": "https://registry.npmjs.org/autolinker/-/autolinker-3.16.2.tgz", - "integrity": "sha512-JiYl7j2Z19F9NdTmirENSUUIIL/9MytEWtmzhfmsKPCp9E+G35Y0UNCMoM9tFigxT59qSc8Ml2dlZXOCVTYwuA==", "license": "MIT", "dependencies": { "tslib": "^2.3.0" @@ -7921,8 +6467,6 @@ }, "node_modules/available-typed-arrays": { "version": "1.0.7", - "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.7.tgz", - "integrity": "sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==", "license": "MIT", "dependencies": { "possible-typed-array-names": "^1.0.0" @@ -7936,8 +6480,6 @@ }, "node_modules/axe-core": { "version": "4.10.2", - "resolved": "https://registry.npmjs.org/axe-core/-/axe-core-4.10.2.tgz", - "integrity": "sha512-RE3mdQ7P3FRSe7eqCWoeQ/Z9QXrtniSjp1wUjt5nRC3WIpz5rSCve6o3fsZ2aCpJtrZjSZgjwXAoTO5k4tEI0w==", "dev": true, "license": "MPL-2.0", "engines": { @@ -7946,8 +6488,6 @@ }, "node_modules/axios": { "version": "1.9.0", - "resolved": "https://registry.npmjs.org/axios/-/axios-1.9.0.tgz", - "integrity": "sha512-re4CqKTJaURpzbLHtIi6XpDv20/CnpXOtjRY5/CU32L8gU8ek9UIivcfvSWvmKEngmVbrUtPpdDwWDWL7DNHvg==", "license": "MIT", "dependencies": { "follow-redirects": "^1.15.6", @@ -7957,24 +6497,14 @@ }, "node_modules/axobject-query": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/axobject-query/-/axobject-query-4.1.0.tgz", - "integrity": "sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ==", "dev": true, "license": "Apache-2.0", "engines": { "node": ">= 0.4" } }, - "node_modules/b4a": { - "version": "1.6.7", - "resolved": "https://registry.npmjs.org/b4a/-/b4a-1.6.7.tgz", - "integrity": "sha512-OnAYlL5b7LEkALw87fUVafQw5rVR9RjwGd4KUwNQ6DrrNmaVaUCgLipfVlzrPQ4tWOR9P0IXGNOx50jYCCdSJg==", - "license": "Apache-2.0" - }, "node_modules/babel-jest": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/babel-jest/-/babel-jest-30.1.2.tgz", - "integrity": "sha512-IQCus1rt9kaSh7PQxLYRY5NmkNrNlU2TpabzwV7T2jljnpdHOcmnYYv8QmE04Li4S3a2Lj8/yXyET5pBarPr6g==", "dev": true, "license": "MIT", "dependencies": { @@ -7995,8 +6525,6 @@ }, "node_modules/babel-plugin-istanbul": { "version": "7.0.1", - "resolved": "https://registry.npmjs.org/babel-plugin-istanbul/-/babel-plugin-istanbul-7.0.1.tgz", - "integrity": "sha512-D8Z6Qm8jCvVXtIRkBnqNHX0zJ37rQcFJ9u8WOS6tkYOsRdHBzypCstaxWiu5ZIlqQtviRYbgnRLSoCEvjqcqbA==", "dev": true, "license": "BSD-3-Clause", "workspaces": [ @@ -8015,8 +6543,6 @@ }, "node_modules/babel-plugin-jest-hoist": { "version": "30.0.1", - "resolved": "https://registry.npmjs.org/babel-plugin-jest-hoist/-/babel-plugin-jest-hoist-30.0.1.tgz", - "integrity": "sha512-zTPME3pI50NsFW8ZBaVIOeAxzEY7XHlmWeXXu9srI+9kNfzCUTy8MFan46xOGZY8NZThMqq+e3qZUKsvXbasnQ==", "dev": true, "license": "MIT", "dependencies": { @@ -8030,8 +6556,6 @@ }, "node_modules/babel-preset-current-node-syntax": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/babel-preset-current-node-syntax/-/babel-preset-current-node-syntax-1.2.0.tgz", - "integrity": "sha512-E/VlAEzRrsLEb2+dv8yp3bo4scof3l9nR4lrld+Iy5NyVqgVYUJnDAmunkhPMisRI32Qc4iRiz425d8vM++2fg==", "dev": true, "license": "MIT", "dependencies": { @@ -8057,8 +6581,6 @@ }, "node_modules/babel-preset-jest": { "version": "30.0.1", - "resolved": "https://registry.npmjs.org/babel-preset-jest/-/babel-preset-jest-30.0.1.tgz", - "integrity": "sha512-+YHejD5iTWI46cZmcc/YtX4gaKBtdqCHCVfuVinizVpbmyjO3zYmeuyFdfA8duRqQZfgCAMlsfmkVbJ+e2MAJw==", "dev": true, "license": "MIT", "dependencies": { @@ -8074,8 +6596,6 @@ }, "node_modules/bail": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/bail/-/bail-2.0.2.tgz", - "integrity": "sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==", "license": "MIT", "funding": { "type": "github", @@ -8084,14 +6604,12 @@ }, "node_modules/balanced-match": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", - "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", "license": "MIT" }, "node_modules/bare-addon-resolve": { - "version": "1.9.3", - "resolved": "https://registry.npmjs.org/bare-addon-resolve/-/bare-addon-resolve-1.9.3.tgz", - "integrity": "sha512-0W343p8kVy9KimDMrxJtJct/ILWL8gzC0Wwg/Fn/GgQplHvrllyz4fPobUVG5+gx9BokWttzg8FYypQP7V5nrA==", + "version": "1.9.5", + "resolved": "https://registry.npmjs.org/bare-addon-resolve/-/bare-addon-resolve-1.9.5.tgz", + "integrity": "sha512-XdqrG73zLK9LDfblOJwoAxmJ+7YdfRW4ex46+f4L+wPhk7H7LDrRMAbBw8s8jkxeEFpUenyB7QHnv0ErAWd3Yg==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -8108,29 +6626,47 @@ } }, "node_modules/bare-events": { - "version": "2.5.4", - "resolved": "https://registry.npmjs.org/bare-events/-/bare-events-2.5.4.tgz", - "integrity": "sha512-+gFfDkR8pj4/TrWCGUGWmJIkBwuxPS5F+a5yWjOHQt2hHvNZd5YLzadjmDUtFmMM4y429bnKLa8bYBMHcYdnQA==", - "license": "Apache-2.0" + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/bare-events/-/bare-events-2.8.1.tgz", + "integrity": "sha512-oxSAxTS1hRfnyit2CL5QpAOS5ixfBjj6ex3yTNvXyY/kE719jQ/IjuESJBK2w5v4wwQRAHGseVJXx9QBYOtFGQ==", + "license": "Apache-2.0", + "peerDependencies": { + "bare-abort-controller": "*" + }, + "peerDependenciesMeta": { + "bare-abort-controller": { + "optional": true + } + } }, "node_modules/bare-fs": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/bare-fs/-/bare-fs-4.0.1.tgz", - "integrity": "sha512-ilQs4fm/l9eMfWY2dY0WCIUplSUp7U0CT1vrqMg1MUdeZl4fypu5UP0XcDBK5WBQPJAKP1b7XEodISmekH/CEg==", + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/bare-fs/-/bare-fs-4.5.0.tgz", + "integrity": "sha512-GljgCjeupKZJNetTqxKaQArLK10vpmK28or0+RwWjEl5Rk+/xG3wkpmkv+WrcBm3q1BwHKlnhXzR8O37kcvkXQ==", "license": "Apache-2.0", "dependencies": { - "bare-events": "^2.0.0", + "bare-events": "^2.5.4", "bare-path": "^3.0.0", - "bare-stream": "^2.0.0" + "bare-stream": "^2.6.4", + "bare-url": "^2.2.2", + "fast-fifo": "^1.3.2" }, "engines": { - "bare": ">=1.7.0" + "bare": ">=1.16.0" + }, + "peerDependencies": { + "bare-buffer": "*" + }, + "peerDependenciesMeta": { + "bare-buffer": { + "optional": true + } } }, "node_modules/bare-module-resolve": { - "version": "1.10.2", - "resolved": "https://registry.npmjs.org/bare-module-resolve/-/bare-module-resolve-1.10.2.tgz", - "integrity": "sha512-C9COe/GhWfVXKytW3DElTkiBU+Gb2OXeaVkdGdRB/lp26TVLESHkTGS876iceAGdvtPgohfp9nX8vXHGvN3++Q==", + "version": "1.11.2", + "resolved": "https://registry.npmjs.org/bare-module-resolve/-/bare-module-resolve-1.11.2.tgz", + "integrity": "sha512-HIBu9WacMejg3Dz4X1v6lJjp7ECnwpujvuLub+8I7JJLRwJaGxWMzGYvieOoS9R1n5iRByvTmLtIdPbwjfRgiQ==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -8146,9 +6682,9 @@ } }, "node_modules/bare-os": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/bare-os/-/bare-os-3.6.0.tgz", - "integrity": "sha512-BUrFS5TqSBdA0LwHop4OjPJwisqxGy6JsWVqV6qaFoe965qqtaKfDzHY5T2YA1gUL0ZeeQeA+4BBc1FJTcHiPw==", + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/bare-os/-/bare-os-3.6.2.tgz", + "integrity": "sha512-T+V1+1srU2qYNBmJCXZkUY5vQ0B4FSlL3QDROnKQYOqeiQR8UbjNHlPa+TIbM4cuidiN9GaTaOZgSEgsvPbh5A==", "license": "Apache-2.0", "engines": { "bare": ">=1.14.0" @@ -8164,16 +6700,16 @@ } }, "node_modules/bare-semver": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bare-semver/-/bare-semver-1.0.1.tgz", - "integrity": "sha512-UtggzHLiTrmFOC/ogQ+Hy7VfoKoIwrP1UFcYtTxoCUdLtsIErT8+SWtOC2DH/snT9h+xDrcBEPcwKei1mzemgg==", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/bare-semver/-/bare-semver-1.0.2.tgz", + "integrity": "sha512-ESVaN2nzWhcI5tf3Zzcq9aqCZ676VWzqw07eEZ0qxAcEOAFYBa0pWq8sK34OQeHLY3JsfKXZS9mDyzyxGjeLzA==", "license": "Apache-2.0", "optional": true }, "node_modules/bare-stream": { - "version": "2.6.5", - "resolved": "https://registry.npmjs.org/bare-stream/-/bare-stream-2.6.5.tgz", - "integrity": "sha512-jSmxKJNJmHySi6hC42zlZnq00rga4jjxcgNZjY9N5WlOe/iOoGRtdwGsHzQv2RlH2KOYMwGUXhf2zXd32BA9RA==", + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/bare-stream/-/bare-stream-2.7.0.tgz", + "integrity": "sha512-oyXQNicV1y8nc2aKffH+BUHFRXmx6VrPzlnaEvMhram0nPBrKcEdcyBg5r08D0i8VxngHFAiVyn1QKXpSG0B8A==", "license": "Apache-2.0", "dependencies": { "streamx": "^2.21.0" @@ -8192,11 +6728,10 @@ } }, "node_modules/bare-url": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/bare-url/-/bare-url-2.1.3.tgz", - "integrity": "sha512-c02+eKvn/4esh5E2lSYQFwHL1WoTIL3u3NeFqb9e7ahBVENXw13MWx4/4/wdPyI557GqqB2Cm0bBbOXD0I0qgA==", + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/bare-url/-/bare-url-2.3.1.tgz", + "integrity": "sha512-v2yl0TnaZTdEnelkKtXZGnotiV6qATBlnNuUMrHl6v9Lmmrh9mw9RYyImPU7/4RahumSwQS1k2oKXcRfXcbjJw==", "license": "Apache-2.0", - "optional": true, "dependencies": { "bare-path": "^3.0.0" } @@ -8209,8 +6744,6 @@ }, "node_modules/base32-encoding": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/base32-encoding/-/base32-encoding-1.0.0.tgz", - "integrity": "sha512-k1gA7f00ODLY7YtuEQFz0Kn3huTCmL/JW+oQtw51ID+zxs5chj/YQ1bXN+Q0JsqiKB2Yn0oA0AA8uipFYgpagQ==", "license": "ISC" }, "node_modules/base64-arraybuffer": { @@ -8224,8 +6757,6 @@ }, "node_modules/base64-js": { "version": "1.5.1", - "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", - "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", "funding": [ { "type": "github", @@ -8244,8 +6775,6 @@ }, "node_modules/baseline-browser-mapping": { "version": "2.8.6", - "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.8.6.tgz", - "integrity": "sha512-wrH5NNqren/QMtKUEEJf7z86YjfqW/2uw3IL3/xpqZUC95SSVIFXYQeeGjL6FT/X68IROu6RMehZQS5foy2BXw==", "license": "Apache-2.0", "bin": { "baseline-browser-mapping": "dist/cli.js" @@ -8259,8 +6788,6 @@ }, "node_modules/before-after-hook": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/before-after-hook/-/before-after-hook-3.0.2.tgz", - "integrity": "sha512-Nik3Sc0ncrMK4UUdXQmAnRtzmNQTAAXmXIopizwZ1W1t8QmfJj+zL4OA2I7XPTPW5z5TDqv4hRo/JzouDJnX3A==", "license": "Apache-2.0" }, "node_modules/bencode": { @@ -8286,17 +6813,15 @@ }, "node_modules/bidi-js": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/bidi-js/-/bidi-js-1.0.3.tgz", - "integrity": "sha512-RKshQI1R3YQ+n9YJz2QQ147P66ELpa1FQEg20Dk8oW9t2KgLbpDLLp9aGZ7y8WHSshDknG0bknqGw5/tyCs5tw==", "license": "MIT", "dependencies": { "require-from-string": "^2.0.2" } }, "node_modules/bignumber.js": { - "version": "9.1.2", - "resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.1.2.tgz", - "integrity": "sha512-2/mKyZH9K85bzOEfhXDBFZTGd1CTs+5IHpeFQo9luiBG7hghdC851Pj2WAhb6E3R6b9tZj/XKhbg4fum+Kepug==", + "version": "9.3.1", + "resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.3.1.tgz", + "integrity": "sha512-Ko0uX15oIUS7wJ3Rb30Fs6SkVbLmPBAKdlm7q9+ak9bbIeFf0MwuBsQV6z7+X768/cHsfg+WlysDWJcmthjsjQ==", "license": "MIT", "engines": { "node": "*" @@ -8304,8 +6829,6 @@ }, "node_modules/binary-extensions": { "version": "2.3.0", - "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.3.0.tgz", - "integrity": "sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==", "license": "MIT", "engines": { "node": ">=8" @@ -8325,9 +6848,9 @@ } }, "node_modules/bip174": { - "version": "3.0.0-rc.1", - "resolved": "https://registry.npmjs.org/bip174/-/bip174-3.0.0-rc.1.tgz", - "integrity": "sha512-+8P3BpSairVNF2Nee6Ksdc1etIjWjBOi/MH0MwKtq9YaYp+S2Hk2uvup0e8hCT4IKlS58nXJyyQVmW92zPoD4Q==", + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/bip174/-/bip174-3.0.0.tgz", + "integrity": "sha512-N3vz3rqikLEu0d6yQL8GTrSkpYb35NQKWMR7Hlza0lOj6ZOlvQ3Xr7N9Y+JPebaCVoEUHdBeBSuLxcHr71r+Lw==", "license": "MIT", "dependencies": { "uint8array-tools": "^0.0.9", @@ -8443,9 +6966,9 @@ } }, "node_modules/bittorrent-dht": { - "version": "11.0.9", - "resolved": "https://registry.npmjs.org/bittorrent-dht/-/bittorrent-dht-11.0.9.tgz", - "integrity": "sha512-aM6m9zvIGi8lMANaxUWcF3yytUxloUCc4gzqa0SOvo22FyeNDHecOXccw6FIZyk4I0IN9KDCj7We+n+RpqnYgg==", + "version": "11.0.11", + "resolved": "https://registry.npmjs.org/bittorrent-dht/-/bittorrent-dht-11.0.11.tgz", + "integrity": "sha512-5rWMoK/2XjcPSx9nfqiL6mHxsXLwohX+81aL4a3qUyGU1992mBqARQE/evZ+a6eWb5DeRjeDU+qFZm11rmPZnQ==", "funding": [ { "type": "github", @@ -8463,7 +6986,7 @@ "license": "MIT", "dependencies": { "bencode": "^4.0.0", - "debug": "^4.4.0", + "debug": "^4.4.3", "k-bucket": "^5.1.0", "k-rpc": "^5.1.0", "last-one-wins": "^1.0.4", @@ -8523,9 +7046,9 @@ "license": "MIT" }, "node_modules/bittorrent-protocol": { - "version": "4.1.16", - "resolved": "https://registry.npmjs.org/bittorrent-protocol/-/bittorrent-protocol-4.1.16.tgz", - "integrity": "sha512-93t8h77uAyD8BGSpBo8SqxYyKBA/xgv9N8+WghnXpH2I+JmlmJmddUt8nugPRgj/LNuL1VrWJ26jhYhiVWpRaQ==", + "version": "4.1.21", + "resolved": "https://registry.npmjs.org/bittorrent-protocol/-/bittorrent-protocol-4.1.21.tgz", + "integrity": "sha512-CcuPt6BL7gXa8BF+0GckYcQmr44ARfSPM0rYwMeYgWg+jftekWgy5vuxX6wJDpC5bKFvqNG+74bPBjyM7Swxrw==", "funding": [ { "type": "github", @@ -8543,11 +7066,11 @@ "license": "MIT", "dependencies": { "bencode": "^4.0.0", - "bitfield": "^4.1.0", - "debug": "^4.4.0", + "bitfield": "^4.2.0", + "debug": "^4.4.3", "rc4": "^0.1.5", - "streamx": "^2.15.1", - "throughput": "^1.0.1", + "streamx": "^2.22.1", + "throughput": "^1.0.2", "uint8-util": "^2.2.5", "unordered-array-remove": "^1.0.2" }, @@ -8556,9 +7079,9 @@ } }, "node_modules/bittorrent-tracker": { - "version": "11.2.1", - "resolved": "https://registry.npmjs.org/bittorrent-tracker/-/bittorrent-tracker-11.2.1.tgz", - "integrity": "sha512-SffBgHzNrhn+HBwdRD2st+TYJOs2LhF3ljJFPCYGv592LpGtPxw41UZHTUeY5muWnQl+wopcU8qXM9UEk2WKrA==", + "version": "11.2.2", + "resolved": "https://registry.npmjs.org/bittorrent-tracker/-/bittorrent-tracker-11.2.2.tgz", + "integrity": "sha512-pVjpd6tPtLByrYwtDOo+cVx9zQZ2XUvlaWrlm57+9yvVDKHuNL+TFEAtyfXuIutghG7Bde/uWXGfoVWpPYY+8A==", "funding": [ { "type": "github", @@ -8623,9 +7146,9 @@ } }, "node_modules/bittorrent-tracker/node_modules/ws": { - "version": "8.18.1", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.1.tgz", - "integrity": "sha512-RKW2aJZMXeMxVpnZ6bck+RswznaxmzdULiBr6KY7XkTnW8uvt0iT9H5DkHUChXrc+uurzwa0rVI16n/Xzjdz1w==", + "version": "8.18.3", + "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.3.tgz", + "integrity": "sha512-PEIGCY5tSlUt50cqyMXfCzX+oOPqN0vuGqWzbcJ2xvnkzkq46oOpz7dQaTDBdfICb4N14+GARUDw2XV2N4tvzg==", "license": "MIT", "engines": { "node": ">=10.0.0" @@ -8678,6 +7201,29 @@ "ieee754": "^1.1.13" } }, + "node_modules/bl/node_modules/readable-stream": { + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", + "license": "MIT", + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/bl/node_modules/string_decoder": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", + "license": "MIT", + "dependencies": { + "safe-buffer": "~5.2.0" + } + }, "node_modules/blake2b": { "version": "2.1.4", "resolved": "https://registry.npmjs.org/blake2b/-/blake2b-2.1.4.tgz", @@ -8698,6 +7244,20 @@ "nanoassert": "^2.0.0" } }, + "node_modules/blake2b-wasm/node_modules/b4a": { + "version": "1.7.3", + "resolved": "https://registry.npmjs.org/b4a/-/b4a-1.7.3.tgz", + "integrity": "sha512-5Q2mfq2WfGuFp3uS//0s6baOJLMoVduPYVeNmDYxu5OUA1/cBfvr2RIS7vi62LdNj/urk1hfmj867I3qt6uZ7Q==", + "license": "Apache-2.0", + "peerDependencies": { + "react-native-b4a": "*" + }, + "peerDependenciesMeta": { + "react-native-b4a": { + "optional": true + } + } + }, "node_modules/blakejs": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/blakejs/-/blakejs-1.2.1.tgz", @@ -8711,15 +7271,13 @@ "license": "MIT" }, "node_modules/bn.js": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-5.2.1.tgz", - "integrity": "sha512-eXRvHzWyYPBuB4NBy0cmYQjGitUrtqwbvlzP3G6VFnNRbsZQIxQ10PbKKHt8gZ/HW/D/747aDl+QkDqg3KQLMQ==", + "version": "5.2.2", + "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-5.2.2.tgz", + "integrity": "sha512-v2YAxEmKaBLahNwE1mjp4WON6huMNeuDvagFZW+ASCuA/ku0bXR9hSMw0XpiqMoA3+rmnyck/tPRSFQkoC9Cuw==", "license": "MIT" }, "node_modules/brace-expansion": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", - "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", "license": "MIT", "dependencies": { "balanced-match": "^1.0.0" @@ -8727,8 +7285,6 @@ }, "node_modules/braces": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", - "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", "license": "MIT", "dependencies": { "fill-range": "^7.1.1" @@ -8739,8 +7295,6 @@ }, "node_modules/browserslist": { "version": "4.26.2", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.26.2.tgz", - "integrity": "sha512-ECFzp6uFOSB+dcZ5BK/IBaGWssbSYBHvuMeMt3MMFyhI0Z8SqGgEkBLARgpRH3hutIgPVsALcMwbDrJqPxQ65A==", "funding": [ { "type": "opencollective", @@ -8772,8 +7326,6 @@ }, "node_modules/bs-logger": { "version": "0.2.6", - "resolved": "https://registry.npmjs.org/bs-logger/-/bs-logger-0.2.6.tgz", - "integrity": "sha512-pd8DCoxmbgc7hyPKOvxtqNcjYoOsABPQdcCUjGp3d42VR2CX1ORhk2A87oqqu5R1kk+76nsxZupkmyd+MVtCog==", "dev": true, "license": "MIT", "dependencies": { @@ -8804,8 +7356,6 @@ }, "node_modules/bser": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/bser/-/bser-2.1.1.tgz", - "integrity": "sha512-gQxTNE/GAfIIrmHLUE3oJyp5FO6HRBfhjnw4/wMmA63ZGDJnWBmgY/lyQBpnDUkGmAhbSe39tx2d/iTOAfglwQ==", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -8814,8 +7364,6 @@ }, "node_modules/buffer": { "version": "6.0.3", - "resolved": "https://registry.npmjs.org/buffer/-/buffer-6.0.3.tgz", - "integrity": "sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA==", "funding": [ { "type": "github", @@ -8838,14 +7386,10 @@ }, "node_modules/buffer-equal-constant-time": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz", - "integrity": "sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==", "license": "BSD-3-Clause" }, "node_modules/buffer-from": { "version": "1.1.2", - "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", - "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", "dev": true, "license": "MIT" }, @@ -8865,8 +7409,6 @@ }, "node_modules/busboy": { "version": "1.6.0", - "resolved": "https://registry.npmjs.org/busboy/-/busboy-1.6.0.tgz", - "integrity": "sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA==", "dependencies": { "streamsearch": "^1.1.0" }, @@ -8876,13 +7418,72 @@ }, "node_modules/bytes": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", - "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", "license": "MIT", "engines": { "node": ">= 0.8" } }, + "node_modules/c12": { + "version": "3.1.0", + "devOptional": true, + "license": "MIT", + "dependencies": { + "chokidar": "^4.0.3", + "confbox": "^0.2.2", + "defu": "^6.1.4", + "dotenv": "^16.6.1", + "exsolve": "^1.0.7", + "giget": "^2.0.0", + "jiti": "^2.4.2", + "ohash": "^2.0.11", + "pathe": "^2.0.3", + "perfect-debounce": "^1.0.0", + "pkg-types": "^2.2.0", + "rc9": "^2.1.2" + }, + "peerDependencies": { + "magicast": "^0.3.5" + }, + "peerDependenciesMeta": { + "magicast": { + "optional": true + } + } + }, + "node_modules/c12/node_modules/chokidar": { + "version": "4.0.3", + "devOptional": true, + "license": "MIT", + "dependencies": { + "readdirp": "^4.0.1" + }, + "engines": { + "node": ">= 14.16.0" + }, + "funding": { + "url": "https://paulmillr.com/funding/" + } + }, + "node_modules/c12/node_modules/jiti": { + "version": "2.6.1", + "devOptional": true, + "license": "MIT", + "bin": { + "jiti": "lib/jiti-cli.mjs" + } + }, + "node_modules/c12/node_modules/readdirp": { + "version": "4.1.2", + "devOptional": true, + "license": "MIT", + "engines": { + "node": ">= 14.18.0" + }, + "funding": { + "type": "individual", + "url": "https://paulmillr.com/funding/" + } + }, "node_modules/cache-chunk-store": { "version": "3.2.2", "resolved": "https://registry.npmjs.org/cache-chunk-store/-/cache-chunk-store-3.2.2.tgz", @@ -8909,8 +7510,6 @@ }, "node_modules/call-bind": { "version": "1.0.8", - "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.8.tgz", - "integrity": "sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==", "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.0", @@ -8927,8 +7526,6 @@ }, "node_modules/call-bind-apply-helpers": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.1.tgz", - "integrity": "sha512-BhYE+WDaywFg2TBWYNXAE+8B1ATnThNBqXHP5nQu0jWJdVvY2hvkpyB3qOmtmDePiS5/BDQ8wASEWGMWRG148g==", "license": "MIT", "dependencies": { "es-errors": "^1.3.0", @@ -8940,8 +7537,6 @@ }, "node_modules/call-bound": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/call-bound/-/call-bound-1.0.3.tgz", - "integrity": "sha512-YTd+6wGlNlPxSuri7Y6X8tY2dmm12UMH66RpKMhiX6rsk5wXXnYgbUcOt8kiS31/AjfoTOvCsE+w8nZQLQnzHA==", "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.1", @@ -8956,14 +7551,10 @@ }, "node_modules/call-me-maybe": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/call-me-maybe/-/call-me-maybe-1.0.2.tgz", - "integrity": "sha512-HpX65o1Hnr9HH25ojC1YGs7HCQLq0GCOibSaWER0eNpgJ/Z1MZv2mTc7+xh6WOPxbRVcmgbv4hGU+uSQ/2xFZQ==", "license": "MIT" }, "node_modules/callsites": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", - "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", "dev": true, "license": "MIT", "engines": { @@ -8972,8 +7563,6 @@ }, "node_modules/camelcase": { "version": "5.3.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz", - "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==", "dev": true, "license": "MIT", "engines": { @@ -8982,8 +7571,6 @@ }, "node_modules/camelcase-css": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/camelcase-css/-/camelcase-css-2.0.1.tgz", - "integrity": "sha512-QOSvevhslijgYwRx6Rv7zKdMF8lbRmx+uQGx2+vDc+KI/eBnsy9kit5aj23AgGu3pa4t9AgwbnXWqS+iOY+2aA==", "license": "MIT", "engines": { "node": ">= 6" @@ -8991,8 +7578,6 @@ }, "node_modules/camera-controls": { "version": "2.9.0", - "resolved": "https://registry.npmjs.org/camera-controls/-/camera-controls-2.9.0.tgz", - "integrity": "sha512-TpCujnP0vqPppTXXJRYpvIy0xq9Tro6jQf2iYUxlDpPCNxkvE/XGaTuwIxnhINOkVP/ob2CRYXtY3iVYXeMEzA==", "license": "MIT", "peerDependencies": { "three": ">=0.126.1" @@ -9000,8 +7585,6 @@ }, "node_modules/caniuse-lite": { "version": "1.0.30001745", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001745.tgz", - "integrity": "sha512-ywt6i8FzvdgrrrGbr1jZVObnVv6adj+0if2/omv9cmR2oiZs30zL4DIyaptKcbOrBdOIc74QTMoJvSE2QHh5UQ==", "funding": [ { "type": "opencollective", @@ -9020,14 +7603,13 @@ }, "node_modules/canonicalize": { "version": "1.0.8", - "resolved": "https://registry.npmjs.org/canonicalize/-/canonicalize-1.0.8.tgz", - "integrity": "sha512-0CNTVCLZggSh7bc5VkX5WWPWO+cyZbNd07IHIsSXLia/eAq+r836hgk+8BKoEh7949Mda87VUOitx5OddVj64A==", "license": "Apache-2.0" }, "node_modules/cbor": { "version": "10.0.11", "resolved": "https://registry.npmjs.org/cbor/-/cbor-10.0.11.tgz", "integrity": "sha512-vIwORDd/WyB8Nc23o2zNN5RrtFGlR6Fca61TtjkUXueI3Jf2DOZDl1zsshvBntZ3wZHBM9ztjnkXSmzQDaq3WA==", + "license": "MIT", "dependencies": { "nofilter": "^3.0.2" }, @@ -9037,8 +7619,6 @@ }, "node_modules/ccount": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/ccount/-/ccount-2.0.1.tgz", - "integrity": "sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==", "license": "MIT", "funding": { "type": "github", @@ -9056,50 +7636,23 @@ }, "optionalDependencies": { "chacha-native": "^2.0.0" - } - }, - "node_modules/chacha-native": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/chacha-native/-/chacha-native-2.0.3.tgz", - "integrity": "sha512-93h+osfjhR2sMHAaapTLlL/COoBPEZ6upicPBQ4GfUyadoMb8t9/M0PKK8kC+F+DEA/Oy3Kg9w3HzY3J1foP3g==", - "hasInstallScript": true, - "license": "MIT", - "optional": true, - "dependencies": { - "bindings": "^1.2.1", - "inherits": "^2.0.1", - "nan": "^2.4.0" - } - }, - "node_modules/chacha/node_modules/isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha512-D2S+3GLxWH+uhrNEcoh/fnmYeP8E8/zHl644d/jdA0g2uyXvy3sb0qxotE+ne0LtccHknQzWwZEzhak7oJ0COQ==", - "license": "MIT" - }, - "node_modules/chacha/node_modules/readable-stream": { - "version": "1.1.14", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.1.14.tgz", - "integrity": "sha512-+MeVjFf4L44XUkhM1eYbD8fyEsxcV81pqMSR5gblfcLCHfZvbrqy4/qYHE+/R5HoBUT11WV5O08Cr1n3YXkWVQ==", + } + }, + "node_modules/chacha-native": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/chacha-native/-/chacha-native-2.0.3.tgz", + "integrity": "sha512-93h+osfjhR2sMHAaapTLlL/COoBPEZ6upicPBQ4GfUyadoMb8t9/M0PKK8kC+F+DEA/Oy3Kg9w3HzY3J1foP3g==", + "hasInstallScript": true, "license": "MIT", + "optional": true, "dependencies": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.1", - "isarray": "0.0.1", - "string_decoder": "~0.10.x" + "bindings": "^1.2.1", + "inherits": "^2.0.1", + "nan": "^2.4.0" } }, - "node_modules/chacha/node_modules/string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha512-ev2QzSzWPYmy9GuqfIVildA4OdcGLeFZQrq5ys6RtiuF+RQQiZWr8TZNyAcuVXyQRYfEO+MsoB/1BuQVhOJuoQ==", - "license": "MIT" - }, "node_modules/chalk": { "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dev": true, "license": "MIT", "dependencies": { "ansi-styles": "^4.1.0", @@ -9114,8 +7667,6 @@ }, "node_modules/char-regex": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/char-regex/-/char-regex-1.0.2.tgz", - "integrity": "sha512-kWWXztvZ5SBQV+eRgKFeh8q5sLuZY2+8WUIzlxWVTg+oGwY14qylx1KbKzHd8P6ZYkAg0xyIDU9JMHhyJMZ1jw==", "dev": true, "license": "MIT", "engines": { @@ -9124,8 +7675,6 @@ }, "node_modules/character-entities": { "version": "1.2.4", - "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-1.2.4.tgz", - "integrity": "sha512-iBMyeEHxfVnIakwOuDXpVkc54HijNgCyQB2w0VfGQThle6NXn50zU6V/u+LDhxHcDUPojn6Kpga3PTAD8W1bQw==", "license": "MIT", "funding": { "type": "github", @@ -9134,8 +7683,6 @@ }, "node_modules/character-entities-html4": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/character-entities-html4/-/character-entities-html4-2.1.0.tgz", - "integrity": "sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==", "license": "MIT", "funding": { "type": "github", @@ -9144,8 +7691,6 @@ }, "node_modules/character-entities-legacy": { "version": "1.1.4", - "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-1.1.4.tgz", - "integrity": "sha512-3Xnr+7ZFS1uxeiUDvV02wQ+QDbc55o97tIV5zHScSPJpcLm/r0DFPcoY3tYRp+VZukxuMeKgXYmsXQHO05zQeA==", "license": "MIT", "funding": { "type": "github", @@ -9154,8 +7699,6 @@ }, "node_modules/character-reference-invalid": { "version": "1.1.4", - "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-1.1.4.tgz", - "integrity": "sha512-mKKUkUbhPpQlCOfIuZkvSEgktjPFIsZKRRbC6KWVEMvlzblj3i3asQv5ODsrwt0N3pHAEvjP8KTQPHkp0+6jOg==", "license": "MIT", "funding": { "type": "github", @@ -9164,8 +7707,6 @@ }, "node_modules/chokidar": { "version": "3.6.0", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.6.0.tgz", - "integrity": "sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==", "license": "MIT", "dependencies": { "anymatch": "~3.1.2", @@ -9188,8 +7729,6 @@ }, "node_modules/chokidar/node_modules/glob-parent": { "version": "5.1.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", - "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", "license": "ISC", "dependencies": { "is-glob": "^4.0.1" @@ -9261,9 +7800,9 @@ } }, "node_modules/chunk-store-iterator": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/chunk-store-iterator/-/chunk-store-iterator-1.0.3.tgz", - "integrity": "sha512-JcSaB5h3wQstQKnaJi8sET40f0m+6Kh4mhKIr05lrWKi+EiQzn6XUoi6LipgRGMqXWNZZJaMz2tH4aeg4ptBDA==", + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/chunk-store-iterator/-/chunk-store-iterator-1.0.4.tgz", + "integrity": "sha512-LGjzJNmk7W1mrdaBoJNztPumT2ACmgjHmI1AMm8aeGYOl4+LKaYC/yfnx27i++LiAtoe/dR+3jC8HRzb6gW4/A==", "license": "MIT", "dependencies": { "block-iterator": "^1.1.1" @@ -9271,9 +7810,6 @@ }, "node_modules/ci-info": { "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-4.3.0.tgz", - "integrity": "sha512-l+2bNRMiQgcfILUi33labAZYIWlH1kWDp+ecNo5iisRKrbm0xcRyCww71/YU0Fkw0mAFpz9bJayXPjey6vkmaQ==", - "dev": true, "funding": [ { "type": "github", @@ -9286,29 +7822,34 @@ } }, "node_modules/cipher-base": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/cipher-base/-/cipher-base-1.0.6.tgz", - "integrity": "sha512-3Ek9H3X6pj5TgenXYtNWdaBon1tgYCaebd+XPg0keyjEbEfkD4KkmAxkQ/i1vYvxdcT5nscLBfq9VJRmCBcFSw==", + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/cipher-base/-/cipher-base-1.0.7.tgz", + "integrity": "sha512-Mz9QMT5fJe7bKI7MH31UilT5cEK5EHHRCccw/YRFsRY47AuNgaV6HY3rscp0/I4Q+tTW/5zoqpSeRRI54TkDWA==", "license": "MIT", "dependencies": { "inherits": "^2.0.4", - "safe-buffer": "^5.2.1" + "safe-buffer": "^5.2.1", + "to-buffer": "^1.2.2" }, "engines": { "node": ">= 0.10" } }, + "node_modules/citty": { + "version": "0.1.6", + "devOptional": true, + "license": "MIT", + "dependencies": { + "consola": "^3.2.3" + } + }, "node_modules/cjs-module-lexer": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-2.1.0.tgz", - "integrity": "sha512-UX0OwmYRYQQetfrLEZeewIFFI+wSTofC+pMBLNuH3RUuu/xzG1oz84UCEDOSoQlN3fZ4+AzmV50ZYvGqkMh9yA==", "dev": true, "license": "MIT" }, "node_modules/class-variance-authority": { "version": "0.7.1", - "resolved": "https://registry.npmjs.org/class-variance-authority/-/class-variance-authority-0.7.1.tgz", - "integrity": "sha512-Ka+9Trutv7G8M6WT6SeiRWz792K5qEqIGEGzXKhAE6xOWAY6pPH8U+9IY3oCMv6kqTmLsv7Xh/2w2RigkePMsg==", "license": "Apache-2.0", "dependencies": { "clsx": "^2.1.1" @@ -9319,19 +7860,16 @@ }, "node_modules/classnames": { "version": "2.5.1", - "resolved": "https://registry.npmjs.org/classnames/-/classnames-2.5.1.tgz", - "integrity": "sha512-saHYOzhIQs6wy2sVxTM6bUDsQO4F50V9RQ22qBpEdCW+I+/Wmke2HOl6lS6dTpdxVhb88/I6+Hs+438c3lfUow==", "license": "MIT" }, "node_modules/client-only": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/client-only/-/client-only-0.0.1.tgz", - "integrity": "sha512-IV3Ou0jSMzZrd3pZ48nLkT9DA7Ag1pnPzaiQhpW7c3RbcqqzvzzVu+L8gfqMp/8IM2MQtSiqaCxrrcfu8I8rMA==" + "integrity": "sha512-IV3Ou0jSMzZrd3pZ48nLkT9DA7Ag1pnPzaiQhpW7c3RbcqqzvzzVu+L8gfqMp/8IM2MQtSiqaCxrrcfu8I8rMA==", + "license": "MIT" }, "node_modules/cliui": { "version": "8.0.1", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", - "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", "dev": true, "license": "ISC", "dependencies": { @@ -9345,15 +7883,11 @@ }, "node_modules/cliui/node_modules/emoji-regex": { "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", "dev": true, "license": "MIT" }, "node_modules/cliui/node_modules/string-width": { "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", "dev": true, "license": "MIT", "dependencies": { @@ -9367,8 +7901,6 @@ }, "node_modules/cliui/node_modules/wrap-ansi": { "version": "7.0.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", - "integrity": "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==", "dev": true, "license": "MIT", "dependencies": { @@ -9385,8 +7917,6 @@ }, "node_modules/clsx": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/clsx/-/clsx-2.1.1.tgz", - "integrity": "sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==", "license": "MIT", "engines": { "node": ">=6" @@ -9394,8 +7924,6 @@ }, "node_modules/co": { "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha512-QVb0dM5HvG+uaxitm8wONl7jltx8dqhfU33DcqtOZcLSVIKSDDLDi7+0LbAKiyI8hD9u42m2YxXSkMGWThaecQ==", "dev": true, "license": "MIT", "engines": { @@ -9405,15 +7933,11 @@ }, "node_modules/collect-v8-coverage": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/collect-v8-coverage/-/collect-v8-coverage-1.0.2.tgz", - "integrity": "sha512-lHl4d5/ONEbLlJvaJNtsF/Lz+WvB07u2ycqTYbdrq7UypDXailES4valYb2eWiJFxZlVmpGekfqoxQhzyFdT4Q==", "dev": true, "license": "MIT" }, "node_modules/color-convert": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", "license": "MIT", "dependencies": { "color-name": "~1.1.4" @@ -9424,14 +7948,10 @@ }, "node_modules/color-name": { "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", "license": "MIT" }, "node_modules/combined-stream": { "version": "1.0.8", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", - "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", "license": "MIT", "dependencies": { "delayed-stream": "~1.0.0" @@ -9442,8 +7962,6 @@ }, "node_modules/comma-separated-tokens": { "version": "1.0.8", - "resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-1.0.8.tgz", - "integrity": "sha512-GHuDRO12Sypu2cV70d1dkA2EUmXHgntrzbpvOB+Qy+49ypNfGgFQIC2fhhXbnyrJRynDCAARsT7Ou0M6hirpfw==", "license": "MIT", "funding": { "type": "github", @@ -9452,8 +7970,6 @@ }, "node_modules/commander": { "version": "4.1.1", - "resolved": "https://registry.npmjs.org/commander/-/commander-4.1.1.tgz", - "integrity": "sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==", "license": "MIT", "engines": { "node": ">= 6" @@ -9470,20 +7986,27 @@ }, "node_modules/concat-map": { "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", "license": "MIT" }, + "node_modules/confbox": { + "version": "0.2.2", + "devOptional": true, + "license": "MIT" + }, + "node_modules/consola": { + "version": "3.4.2", + "devOptional": true, + "license": "MIT", + "engines": { + "node": "^14.18.0 || >=16.10.0" + } + }, "node_modules/convert-source-map": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz", - "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==", "license": "MIT" }, "node_modules/cookie": { "version": "0.6.0", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.6.0.tgz", - "integrity": "sha512-U71cyTamuh1CRNCfpGY6to28lxvNwPG4Guz/EVjgf3Jmzv0vlDp1atT9eS5dDjMYHucpHbWns6Lwf3BKz6svdw==", "license": "MIT", "engines": { "node": ">= 0.6" @@ -9491,8 +8014,6 @@ }, "node_modules/copy-anything": { "version": "3.0.5", - "resolved": "https://registry.npmjs.org/copy-anything/-/copy-anything-3.0.5.tgz", - "integrity": "sha512-yCEafptTtb4bk7GLEQoM8KVJpxAfdBJYaXyzQEgQQQgYrZiDp8SJmGKlYza6CYjEDNstAdNdKA3UuoULlEbS6w==", "license": "MIT", "dependencies": { "is-what": "^4.1.8" @@ -9506,8 +8027,6 @@ }, "node_modules/copy-to-clipboard": { "version": "3.3.3", - "resolved": "https://registry.npmjs.org/copy-to-clipboard/-/copy-to-clipboard-3.3.3.tgz", - "integrity": "sha512-2KV8NhB5JqC3ky0r9PMCAZKbUHSwtEo4CwCs0KXgruG43gX5PMqDEBbVU4OUzw2MuAWUfsuFmWvEKG5QRfSnJA==", "license": "MIT", "dependencies": { "toggle-selection": "^1.0.6" @@ -9515,8 +8034,6 @@ }, "node_modules/core-js-pure": { "version": "3.42.0", - "resolved": "https://registry.npmjs.org/core-js-pure/-/core-js-pure-3.42.0.tgz", - "integrity": "sha512-007bM04u91fF4kMgwom2I5cQxAFIy8jVulgr9eozILl/SZE53QOqnW/+vviC+wQWLv+AunBG+8Q0TLoeSsSxRQ==", "hasInstallScript": true, "license": "MIT", "funding": { @@ -9532,8 +8049,6 @@ }, "node_modules/cors": { "version": "2.8.5", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", - "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", "license": "MIT", "dependencies": { "object-assign": "^4", @@ -9632,8 +8147,6 @@ }, "node_modules/cross-env": { "version": "7.0.3", - "resolved": "https://registry.npmjs.org/cross-env/-/cross-env-7.0.3.tgz", - "integrity": "sha512-+/HKd6EgcQCJGh2PSjZuUitQBQynKor4wrFbRg4DtAgS1aWO+gU52xpH7M9ScGgXSYmAVS9bIJ8EzuaGw0oNAw==", "license": "MIT", "dependencies": { "cross-spawn": "^7.0.1" @@ -9687,8 +8200,6 @@ }, "node_modules/cross-spawn": { "version": "7.0.6", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.6.tgz", - "integrity": "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==", "license": "MIT", "dependencies": { "path-key": "^3.1.0", @@ -9701,14 +8212,10 @@ }, "node_modules/css.escape": { "version": "1.5.1", - "resolved": "https://registry.npmjs.org/css.escape/-/css.escape-1.5.1.tgz", - "integrity": "sha512-YUifsXXuknHlUsmlgyY0PKzgPOr7/FjCePfHNt0jxm83wHZi44VDMQ7/fGNkjY3/jV1MC+1CmZbaHzugyeRtpg==", "license": "MIT" }, "node_modules/cssesc": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/cssesc/-/cssesc-3.0.0.tgz", - "integrity": "sha512-/Tb/JcjK111nNScGob5MNtsntNM1aCNUDipB/TkwZFhyDrrE47SOx/18wF2bbjgc3ZzCSKW1T5nt5EbFoAz/Vg==", "license": "MIT", "bin": { "cssesc": "bin/cssesc" @@ -9719,14 +8226,10 @@ }, "node_modules/csstype": { "version": "3.1.3", - "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz", - "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==", "license": "MIT" }, "node_modules/d3-array": { "version": "3.2.4", - "resolved": "https://registry.npmjs.org/d3-array/-/d3-array-3.2.4.tgz", - "integrity": "sha512-tdQAmyA18i4J7wprpYq8ClcxZy3SC31QMeByyCFyRt7BVHdREQZ5lpzoe5mFEYZUWe+oq8HBvk9JjpibyEV4Jg==", "license": "ISC", "dependencies": { "internmap": "1 - 2" @@ -9737,8 +8240,6 @@ }, "node_modules/d3-color": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/d3-color/-/d3-color-3.1.0.tgz", - "integrity": "sha512-zg/chbXyeBtMQ1LbD/WSoW2DpC3I0mpmPdW+ynRTj/x2DAWYrIY7qeZIHidozwV24m4iavr15lNwIwLxRmOxhA==", "license": "ISC", "engines": { "node": ">=12" @@ -9746,8 +8247,6 @@ }, "node_modules/d3-delaunay": { "version": "6.0.4", - "resolved": "https://registry.npmjs.org/d3-delaunay/-/d3-delaunay-6.0.4.tgz", - "integrity": "sha512-mdjtIZ1XLAM8bm/hx3WwjfHt6Sggek7qH043O8KEjDXN40xi3vx/6pYSVTwLjEgiXQTbvaouWKynLBiUZ6SK6A==", "license": "ISC", "dependencies": { "delaunator": "5" @@ -9758,8 +8257,6 @@ }, "node_modules/d3-ease": { "version": "3.0.1", - "resolved": "https://registry.npmjs.org/d3-ease/-/d3-ease-3.0.1.tgz", - "integrity": "sha512-wR/XK3D3XcLIZwpbvQwQ5fK+8Ykds1ip7A2Txe0yxncXSdq1L9skcG7blcedkOX+ZcgxGAmLX1FrRGbADwzi0w==", "license": "BSD-3-Clause", "engines": { "node": ">=12" @@ -9767,8 +8264,6 @@ }, "node_modules/d3-format": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/d3-format/-/d3-format-3.1.0.tgz", - "integrity": "sha512-YyUI6AEuY/Wpt8KWLgZHsIU86atmikuoOmCfommt0LYHiQSPjvX2AcFc38PX0CBpr2RCyZhjex+NS/LPOv6YqA==", "license": "ISC", "engines": { "node": ">=12" @@ -9776,8 +8271,6 @@ }, "node_modules/d3-geo": { "version": "3.1.1", - "resolved": "https://registry.npmjs.org/d3-geo/-/d3-geo-3.1.1.tgz", - "integrity": "sha512-637ln3gXKXOwhalDzinUgY83KzNWZRKbYubaG+fGVuc/dxO64RRljtCTnf5ecMyE1RIdtqpkVcq0IbtU2S8j2Q==", "license": "ISC", "dependencies": { "d3-array": "2.5.0 - 3" @@ -9788,8 +8281,6 @@ }, "node_modules/d3-geo-voronoi": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/d3-geo-voronoi/-/d3-geo-voronoi-2.1.0.tgz", - "integrity": "sha512-kqE4yYuOjPbKdBXG0xztCacPwkVSK2REF1opSNrnqqtXJmNcM++UbwQ8SxvwP6IQTj9RvIjjK4qeiVsEfj0Z2Q==", "license": "ISC", "dependencies": { "d3-array": "3", @@ -9803,8 +8294,6 @@ }, "node_modules/d3-interpolate": { "version": "3.0.1", - "resolved": "https://registry.npmjs.org/d3-interpolate/-/d3-interpolate-3.0.1.tgz", - "integrity": "sha512-3bYs1rOD33uo8aqJfKP3JWPAibgw8Zm2+L9vBKEHJ2Rg+viTR7o5Mmv5mZcieN+FRYaAOWX5SJATX6k1PWz72g==", "license": "ISC", "dependencies": { "d3-color": "1 - 3" @@ -9815,14 +8304,10 @@ }, "node_modules/d3-octree": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/d3-octree/-/d3-octree-1.1.0.tgz", - "integrity": "sha512-F8gPlqpP+HwRPMO/8uOu5wjH110+6q4cgJvgJT6vlpy3BEaDIKlTZrgHKZSp/i1InRpVfh4puY/kvL6MxK930A==", "license": "MIT" }, "node_modules/d3-path": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/d3-path/-/d3-path-3.1.0.tgz", - "integrity": "sha512-p3KP5HCf/bvjBSSKuXid6Zqijx7wIfNW+J/maPs+iwR35at5JCbLUT0LzF1cnjbCHWhqzQTIN2Jpe8pRebIEFQ==", "license": "ISC", "engines": { "node": ">=12" @@ -9830,8 +8315,6 @@ }, "node_modules/d3-scale": { "version": "4.0.2", - "resolved": "https://registry.npmjs.org/d3-scale/-/d3-scale-4.0.2.tgz", - "integrity": "sha512-GZW464g1SH7ag3Y7hXjf8RoUuAFIqklOAq3MRl4OaWabTFJY9PN/E1YklhXLh+OQ3fM9yS2nOkCoS+WLZ6kvxQ==", "license": "ISC", "dependencies": { "d3-array": "2.10.0 - 3", @@ -9846,8 +8329,6 @@ }, "node_modules/d3-scale-chromatic": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/d3-scale-chromatic/-/d3-scale-chromatic-3.1.0.tgz", - "integrity": "sha512-A3s5PWiZ9YCXFye1o246KoscMWqf8BsD9eRiJ3He7C9OBaxKhAd5TFCdEx/7VbKtxxTsu//1mMJFrEt572cEyQ==", "license": "ISC", "dependencies": { "d3-color": "1 - 3", @@ -9859,8 +8340,6 @@ }, "node_modules/d3-shape": { "version": "3.2.0", - "resolved": "https://registry.npmjs.org/d3-shape/-/d3-shape-3.2.0.tgz", - "integrity": "sha512-SaLBuwGm3MOViRq2ABk3eLoxwZELpH6zhl3FbAoJ7Vm1gofKx6El1Ib5z23NUEhF9AsGl7y+dzLe5Cw2AArGTA==", "license": "ISC", "dependencies": { "d3-path": "^3.1.0" @@ -9871,8 +8350,6 @@ }, "node_modules/d3-time": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/d3-time/-/d3-time-3.1.0.tgz", - "integrity": "sha512-VqKjzBLejbSMT4IgbmVgDjpkYrNWUYJnbCGo874u7MMKIWsILRX+OpX/gTk8MqjpT1A/c6HY2dCA77ZN0lkQ2Q==", "license": "ISC", "dependencies": { "d3-array": "2 - 3" @@ -9883,8 +8360,6 @@ }, "node_modules/d3-time-format": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/d3-time-format/-/d3-time-format-4.1.0.tgz", - "integrity": "sha512-dJxPBlzC7NugB2PDLwo9Q8JiTR3M3e4/XANkreKSUxF8vvXKqm1Yfq4Q5dl8budlunRVlUUaDUgFt7eA8D6NLg==", "license": "ISC", "dependencies": { "d3-time": "1 - 3" @@ -9895,8 +8370,6 @@ }, "node_modules/d3-timer": { "version": "3.0.1", - "resolved": "https://registry.npmjs.org/d3-timer/-/d3-timer-3.0.1.tgz", - "integrity": "sha512-ndfJ/JxxMd3nw31uyKoY2naivF+r29V+Lc0svZxe1JvvIRmi8hUsrMvdOwgS1o6uBHmiz91geQ0ylPP0aj1VUA==", "license": "ISC", "engines": { "node": ">=12" @@ -9904,8 +8377,6 @@ }, "node_modules/d3-tricontour": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/d3-tricontour/-/d3-tricontour-1.0.2.tgz", - "integrity": "sha512-HIRxHzHagPtUPNabjOlfcyismJYIsc+Xlq4mlsts4e8eAcwyq9Tgk/sYdyhlBpQ0MHwVquc/8j+e29YjXnmxeA==", "license": "ISC", "dependencies": { "d3-delaunay": "6", @@ -9917,15 +8388,11 @@ }, "node_modules/damerau-levenshtein": { "version": "1.0.8", - "resolved": "https://registry.npmjs.org/damerau-levenshtein/-/damerau-levenshtein-1.0.8.tgz", - "integrity": "sha512-sdQSFB7+llfUcQHUQO3+B8ERRj0Oa4w9POWMI/puGtuf7gFywGmkaLCElnudfTiKZV+NvHqL0ifzdrI8Ro7ESA==", "dev": true, "license": "BSD-2-Clause" }, "node_modules/data-bind-mapper": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/data-bind-mapper/-/data-bind-mapper-1.0.1.tgz", - "integrity": "sha512-xWkgLj/mSDs/Y2flAMXwLKxnCh+rFScf4N8hSOtpsMxXYXui7CbtIUYP52VXQze9HhRND2Ua/AiEHZ8j/vtB0w==", "license": "MIT", "dependencies": { "accessor-fn": "1" @@ -9936,8 +8403,6 @@ }, "node_modules/data-uri-to-buffer": { "version": "4.0.1", - "resolved": "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-4.0.1.tgz", - "integrity": "sha512-0R9ikRb668HB7QDxT1vkpuUBtqc53YyAwMwGeUFKRojY/NWKvdZ+9UYtRfGmhqNbRkTSVpMbmyhXipFFv2cb/A==", "license": "MIT", "engines": { "node": ">= 12" @@ -9945,8 +8410,6 @@ }, "node_modules/data-view-buffer": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/data-view-buffer/-/data-view-buffer-1.0.2.tgz", - "integrity": "sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==", "dev": true, "license": "MIT", "dependencies": { @@ -9963,8 +8426,6 @@ }, "node_modules/data-view-byte-length": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/data-view-byte-length/-/data-view-byte-length-1.0.2.tgz", - "integrity": "sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==", "dev": true, "license": "MIT", "dependencies": { @@ -9981,8 +8442,6 @@ }, "node_modules/data-view-byte-offset": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/data-view-byte-offset/-/data-view-byte-offset-1.0.1.tgz", - "integrity": "sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==", "dev": true, "license": "MIT", "dependencies": { @@ -9999,14 +8458,12 @@ }, "node_modules/debounce": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/debounce/-/debounce-1.2.1.tgz", - "integrity": "sha512-XRRe6Glud4rd/ZGQfiV1ruXSfbvfJedlV9Y6zOlP+2K04vBYiJEte6stfFkCP03aMnY5tsipamumUjL14fofug==", "license": "MIT" }, "node_modules/debug": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", - "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", "license": "MIT", "dependencies": { "ms": "^2.1.3" @@ -10022,14 +8479,10 @@ }, "node_modules/decimal.js-light": { "version": "2.5.1", - "resolved": "https://registry.npmjs.org/decimal.js-light/-/decimal.js-light-2.5.1.tgz", - "integrity": "sha512-qIMFpTMZmny+MMIitAB6D7iVPEorVw6YQRWkvarTkT4tBeSLLiHzcwj6q0MmYSFCiVpiqPJTJEYIrpcPzVEIvg==", "license": "MIT" }, "node_modules/decode-named-character-reference": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.2.0.tgz", - "integrity": "sha512-c6fcElNV6ShtZXmsgNgFFV5tVX2PaV4g+MOAkb8eXHvn6sryJBrZa9r0zV6+dtTyoCKxtDy5tyQ5ZwQuidtd+Q==", "license": "MIT", "dependencies": { "character-entities": "^2.0.0" @@ -10041,8 +8494,6 @@ }, "node_modules/decode-named-character-reference/node_modules/character-entities": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz", - "integrity": "sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==", "license": "MIT", "funding": { "type": "github", @@ -10066,8 +8517,6 @@ }, "node_modules/dedent": { "version": "1.7.0", - "resolved": "https://registry.npmjs.org/dedent/-/dedent-1.7.0.tgz", - "integrity": "sha512-HGFtf8yhuhGhqO07SV79tRp+br4MnbdjeVxotpn1QBl30pcLLCQjX5b2295ll0fv8RKDKsmWYrl05usHM9CewQ==", "dev": true, "license": "MIT", "peerDependencies": { @@ -10081,8 +8530,6 @@ }, "node_modules/deep-extend": { "version": "0.6.0", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", - "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", "license": "MIT", "engines": { "node": ">=4.0.0" @@ -10090,36 +8537,154 @@ }, "node_modules/deep-is": { "version": "0.1.4", - "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", - "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", "dev": true, "license": "MIT" }, "node_modules/deepmerge": { "version": "4.3.1", - "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.1.tgz", - "integrity": "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==", "license": "MIT", "engines": { "node": ">=0.10.0" } }, + "node_modules/deepmerge-ts": { + "version": "7.1.5", + "devOptional": true, + "license": "BSD-3-Clause", + "engines": { + "node": ">=16.0.0" + } + }, "node_modules/default-gateway": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/default-gateway/-/default-gateway-6.0.3.tgz", - "integrity": "sha512-fwSOJsbbNzZ/CUFpqFBqYfYNLj1NbMPm8MMCIzHjC83iSJRBEGmDUxU+WP661BaBQImeC2yHwXtz+P/O9o+XEg==", + "version": "7.2.2", + "resolved": "https://registry.npmjs.org/default-gateway/-/default-gateway-7.2.2.tgz", + "integrity": "sha512-AD7TrdNNPXRZIGw63dw+lnGmT4v7ggZC5NHNJgAYWm5njrwoze1q5JSAW9YuLy2tjnoLUG/r8FEB93MCh9QJPg==", "license": "BSD-2-Clause", "dependencies": { - "execa": "^5.0.0" + "execa": "^7.1.1" }, "engines": { - "node": ">= 10" + "node": ">= 16" + } + }, + "node_modules/default-gateway/node_modules/execa": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/execa/-/execa-7.2.0.tgz", + "integrity": "sha512-UduyVP7TLB5IcAQl+OzLyLcS/l32W/GLg+AhHJ+ow40FOk2U3SAllPwR44v4vmdFwIWqpdwxxpQbF1n5ta9seA==", + "license": "MIT", + "dependencies": { + "cross-spawn": "^7.0.3", + "get-stream": "^6.0.1", + "human-signals": "^4.3.0", + "is-stream": "^3.0.0", + "merge-stream": "^2.0.0", + "npm-run-path": "^5.1.0", + "onetime": "^6.0.0", + "signal-exit": "^3.0.7", + "strip-final-newline": "^3.0.0" + }, + "engines": { + "node": "^14.18.0 || ^16.14.0 || >=18.0.0" + }, + "funding": { + "url": "https://github.com/sindresorhus/execa?sponsor=1" + } + }, + "node_modules/default-gateway/node_modules/human-signals": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-4.3.1.tgz", + "integrity": "sha512-nZXjEF2nbo7lIw3mgYjItAfgQXog3OjJogSbKa2CQIIvSGWcKgeJnQlNXip6NglNzYH45nSRiEVimMvYL8DDqQ==", + "license": "Apache-2.0", + "engines": { + "node": ">=14.18.0" + } + }, + "node_modules/default-gateway/node_modules/is-stream": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-3.0.0.tgz", + "integrity": "sha512-LnQR4bZ9IADDRSkvpqMGvt/tEJWclzklNgSw48V5EAaAeDd6qGvN8ei6k5p0tvxSR171VmGyHuTiAOfxAbr8kA==", + "license": "MIT", + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/default-gateway/node_modules/mimic-fn": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-4.0.0.tgz", + "integrity": "sha512-vqiC06CuhBTUdZH+RYl8sFrL096vA45Ok5ISO6sE/Mr1jRbGH4Csnhi8f3wKVl7x8mO4Au7Ir9D3Oyv1VYMFJw==", + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/default-gateway/node_modules/npm-run-path": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-5.3.0.tgz", + "integrity": "sha512-ppwTtiJZq0O/ai0z7yfudtBpWIoxM8yE6nHi1X47eFR2EWORqfbu6CnPlNsjeN683eT0qG6H/Pyf9fCcvjnnnQ==", + "license": "MIT", + "dependencies": { + "path-key": "^4.0.0" + }, + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/default-gateway/node_modules/onetime": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/onetime/-/onetime-6.0.0.tgz", + "integrity": "sha512-1FlR+gjXK7X+AsAHso35MnyN5KqGwJRi/31ft6x0M194ht7S+rWAvd7PHss9xSKMzE0asv1pyIHaJYq+BbacAQ==", + "license": "MIT", + "dependencies": { + "mimic-fn": "^4.0.0" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/default-gateway/node_modules/path-key": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-4.0.0.tgz", + "integrity": "sha512-haREypq7xkM7ErfgIyA0z+Bj4AGKlMSdlQE2jvJo6huWD1EdkKYV+G/T4nq0YEF2vgTT8kqMFKo1uHn950r4SQ==", + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/default-gateway/node_modules/signal-exit": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", + "license": "ISC" + }, + "node_modules/default-gateway/node_modules/strip-final-newline": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-3.0.0.tgz", + "integrity": "sha512-dOESqjYr96iWYylGObzd39EuNTa5VJxyvVAEm5Jnh7KGo75V43Hk1odPQkNDyXNmUR6k+gEiDVXnjB8HJ3crXw==", + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, "node_modules/define-data-property": { "version": "1.1.4", - "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", - "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", "license": "MIT", "dependencies": { "es-define-property": "^1.0.0", @@ -10135,8 +8700,6 @@ }, "node_modules/define-properties": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz", - "integrity": "sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==", "dev": true, "license": "MIT", "dependencies": { @@ -10151,10 +8714,13 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/defu": { + "version": "6.1.4", + "devOptional": true, + "license": "MIT" + }, "node_modules/delaunator": { "version": "5.0.1", - "resolved": "https://registry.npmjs.org/delaunator/-/delaunator-5.0.1.tgz", - "integrity": "sha512-8nvh+XBe96aCESrGOqMp/84b13H9cdKbG5P2ejQCh4d4sK9RL4371qou9drQjMhvnPmhWl5hnmqbEE0fXr9Xnw==", "license": "ISC", "dependencies": { "robust-predicates": "^3.0.2" @@ -10162,8 +8728,6 @@ }, "node_modules/delayed-stream": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", "license": "MIT", "engines": { "node": ">=0.4.0" @@ -10171,34 +8735,34 @@ }, "node_modules/dequal": { "version": "2.0.3", - "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", - "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", "license": "MIT", "engines": { "node": ">=6" } }, + "node_modules/destr": { + "version": "2.0.5", + "devOptional": true, + "license": "MIT" + }, "node_modules/detect-gpu": { "version": "5.0.66", - "resolved": "https://registry.npmjs.org/detect-gpu/-/detect-gpu-5.0.66.tgz", - "integrity": "sha512-X6b8QYU3EeVEsr5xROLZVdqwoBe6Yg1z4SnJujRBh7BfWd+48FTsMwIqQFUiQSKdkScebtpDwueHZEkAalkbhg==", "license": "MIT", "dependencies": { "webgl-constants": "^1.1.1" } }, "node_modules/detect-libc": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.1.1.tgz", - "integrity": "sha512-ecqj/sy1jcK1uWrwpR67UhYrIFQ+5WlGxth34WquCbamhFA6hkkwiu37o6J5xCHdo1oixJRfVRw+ywV+Hq/0Aw==", + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.1.2.tgz", + "integrity": "sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ==", + "license": "Apache-2.0", "engines": { "node": ">=8" } }, "node_modules/detect-newline": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/detect-newline/-/detect-newline-3.1.0.tgz", - "integrity": "sha512-TLz+x/vEXm/Y7P7wn1EJFNLxYpUD4TgMosxY6fAVJUnJMbupHBOncxyWUG9OpTaH9EBD7uFI5LfEgmMOc54DsA==", "dev": true, "license": "MIT", "engines": { @@ -10207,14 +8771,10 @@ }, "node_modules/detect-node-es": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/detect-node-es/-/detect-node-es-1.1.0.tgz", - "integrity": "sha512-ypdmJU/TbBby2Dxibuv7ZLW3Bs1QEmM7nHjEANfohJLvE0XVujisn1qPJcZxg+qDucsr+bP6fLD1rPS3AhJ7EQ==", "license": "MIT" }, "node_modules/devlop": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/devlop/-/devlop-1.1.0.tgz", - "integrity": "sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==", "license": "MIT", "dependencies": { "dequal": "^2.0.0" @@ -10226,14 +8786,10 @@ }, "node_modules/dexie": { "version": "4.0.11", - "resolved": "https://registry.npmjs.org/dexie/-/dexie-4.0.11.tgz", - "integrity": "sha512-SOKO002EqlvBYYKQSew3iymBoN2EQ4BDw/3yprjh7kAfFzjBYkaMNa/pZvcA7HSWlcKSQb9XhPe3wKyQ0x4A8A==", "license": "Apache-2.0" }, "node_modules/dezalgo": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/dezalgo/-/dezalgo-1.0.4.tgz", - "integrity": "sha512-rXSP0bf+5n0Qonsb+SVVfNfIsimO4HEtmnIpPHY8Q1UCzKlQrDMfdobr8nJOOsRgWCyMRqeSBQzmWUMq7zvVig==", "license": "ISC", "dependencies": { "asap": "^2.0.0", @@ -10242,14 +8798,10 @@ }, "node_modules/didyoumean": { "version": "1.2.2", - "resolved": "https://registry.npmjs.org/didyoumean/-/didyoumean-1.2.2.tgz", - "integrity": "sha512-gxtyfqMg7GKyhQmb056K7M3xszy/myH8w+B4RT+QXBQsvAOdc3XymqDDPHx1BgPgsdAA5SIifona89YtRATDzw==", "license": "Apache-2.0" }, "node_modules/dlv": { "version": "1.1.3", - "resolved": "https://registry.npmjs.org/dlv/-/dlv-1.1.3.tgz", - "integrity": "sha512-+HlytyjlPKnIG8XuRG8WvmBP8xs8P71y+SKKS6ZXWoEgLuePxtDoUEiH7WkdePWrQ5JBpE6aoVqfZfJUQkjXwA==", "license": "MIT" }, "node_modules/dns-packet": { @@ -10266,8 +8818,6 @@ }, "node_modules/doctrine": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", - "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", "license": "Apache-2.0", "dependencies": { "esutils": "^2.0.2" @@ -10278,8 +8828,6 @@ }, "node_modules/dom-helpers": { "version": "5.2.1", - "resolved": "https://registry.npmjs.org/dom-helpers/-/dom-helpers-5.2.1.tgz", - "integrity": "sha512-nRCa7CK3VTrM2NmGkIy4cbK7IZlgBE/PYMn55rrXefr5xXDP0LdtfPnblFDoVdcAfslJ7or6iqAUnx0CCGIWQA==", "license": "MIT", "dependencies": { "@babel/runtime": "^7.8.7", @@ -10293,23 +8841,28 @@ }, "node_modules/dompurify": { "version": "3.2.4", - "resolved": "https://registry.npmjs.org/dompurify/-/dompurify-3.2.4.tgz", - "integrity": "sha512-ysFSFEDVduQpyhzAob/kkuJjf5zWkZD8/A9ywSp1byueyuCfHamrCBa14/Oc2iiB0e51B+NpxSl5gmzn+Ms/mg==", "license": "(MPL-2.0 OR Apache-2.0)", "optionalDependencies": { "@types/trusted-types": "^2.0.7" } }, + "node_modules/dotenv": { + "version": "16.6.1", + "devOptional": true, + "license": "BSD-2-Clause", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://dotenvx.com" + } + }, "node_modules/draco3d": { "version": "1.5.7", - "resolved": "https://registry.npmjs.org/draco3d/-/draco3d-1.5.7.tgz", - "integrity": "sha512-m6WCKt/erDXcw+70IJXnG7M3awwQPAsZvJGX5zY7beBqpELw6RDGkYVU0W43AFxye4pDZ5i2Lbyc/NNGqwjUVQ==", "license": "Apache-2.0" }, "node_modules/drange": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/drange/-/drange-1.1.1.tgz", - "integrity": "sha512-pYxfDYpued//QpnLIm4Avk7rsNtAtQkUES2cwAYSvD/wd2pKD71gN2Ebj3e7klzXwjocvE8c5vx/1fxwpqmSxA==", "license": "MIT", "engines": { "node": ">=4" @@ -10317,8 +8870,6 @@ }, "node_modules/dunder-proto": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz", - "integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==", "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.1", @@ -10331,20 +8882,14 @@ }, "node_modules/earcut": { "version": "3.0.1", - "resolved": "https://registry.npmjs.org/earcut/-/earcut-3.0.1.tgz", - "integrity": "sha512-0l1/0gOjESMeQyYaK5IDiPNvFeu93Z/cO0TjZh9eZ1vyCtZnA7KMZ8rQggpsJHIbGSdrqYq9OhuveadOVHCshw==", "license": "ISC" }, "node_modules/eastasianwidth": { "version": "0.2.0", - "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", - "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==", "license": "MIT" }, "node_modules/ecdsa-sig-formatter": { "version": "1.0.11", - "resolved": "https://registry.npmjs.org/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz", - "integrity": "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==", "license": "Apache-2.0", "dependencies": { "safe-buffer": "^5.0.1" @@ -10364,16 +8909,21 @@ "node": ">=8.0.0" } }, + "node_modules/effect": { + "version": "3.16.12", + "devOptional": true, + "license": "MIT", + "dependencies": { + "@standard-schema/spec": "^1.0.0", + "fast-check": "^3.23.1" + } + }, "node_modules/electron-to-chromium": { "version": "1.5.223", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.223.tgz", - "integrity": "sha512-qKm55ic6nbEmagFlTFczML33rF90aU+WtrJ9MdTCThrcvDNdUHN4p6QfVN78U06ZmguqXIyMPyYhw2TrbDUwPQ==", "license": "ISC" }, "node_modules/emittery": { "version": "0.13.1", - "resolved": "https://registry.npmjs.org/emittery/-/emittery-0.13.1.tgz", - "integrity": "sha512-DeWwawk6r5yR9jFgnDKYt4sLS0LmHJJi3ZOnb5/JdbYwj3nW+FxQnHIjhBKz8YLC7oRNPVM9NQ47I3CVx34eqQ==", "dev": true, "license": "MIT", "engines": { @@ -10385,14 +8935,20 @@ }, "node_modules/emoji-regex": { "version": "9.2.2", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", - "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", "license": "MIT" }, + "node_modules/empathic": { + "version": "2.0.0", + "devOptional": true, + "license": "MIT", + "engines": { + "node": ">=14" + } + }, "node_modules/end-of-stream": { - "version": "1.4.4", - "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", - "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "version": "1.4.5", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.5.tgz", + "integrity": "sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==", "license": "MIT", "dependencies": { "once": "^1.4.0" @@ -10400,8 +8956,6 @@ }, "node_modules/enhanced-resolve": { "version": "5.18.0", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.18.0.tgz", - "integrity": "sha512-0/r0MySGYG8YqlayBZ6MuCfECmHFdJ5qyPh8s8wa5Hnm6SaFLSK1VYCbj+NKp090Nm1caZhD+QTnmxO7esYGyQ==", "dev": true, "license": "MIT", "dependencies": { @@ -10420,8 +8974,6 @@ }, "node_modules/error-ex": { "version": "1.3.4", - "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.4.tgz", - "integrity": "sha512-sqQamAnR14VgCr1A618A3sGrygcpK+HEbenA/HiEAkkUwcZIIB/tgWqHFxWgOyDh4nB4JCRimh79dR5Ywc9MDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -10430,8 +8982,6 @@ }, "node_modules/es-abstract": { "version": "1.23.9", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.23.9.tgz", - "integrity": "sha512-py07lI0wjxAC/DcfK1S6G7iANonniZwTISvdPzk9hzeH0IZIshbuuFxLIU96OyF89Yb9hiqWn8M/bY83KY5vzA==", "dev": true, "license": "MIT", "dependencies": { @@ -10496,8 +9046,6 @@ }, "node_modules/es-define-property": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz", - "integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==", "license": "MIT", "engines": { "node": ">= 0.4" @@ -10505,8 +9053,6 @@ }, "node_modules/es-errors": { "version": "1.3.0", - "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", - "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", "license": "MIT", "engines": { "node": ">= 0.4" @@ -10514,8 +9060,6 @@ }, "node_modules/es-iterator-helpers": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.2.1.tgz", - "integrity": "sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==", "dev": true, "license": "MIT", "dependencies": { @@ -10542,8 +9086,6 @@ }, "node_modules/es-object-atoms": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz", - "integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==", "license": "MIT", "dependencies": { "es-errors": "^1.3.0" @@ -10554,8 +9096,6 @@ }, "node_modules/es-set-tostringtag": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz", - "integrity": "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==", "license": "MIT", "dependencies": { "es-errors": "^1.3.0", @@ -10569,8 +9109,6 @@ }, "node_modules/es-shim-unscopables": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/es-shim-unscopables/-/es-shim-unscopables-1.0.2.tgz", - "integrity": "sha512-J3yBRXCzDu4ULnQwxyToo/OjdMx6akgVC7K6few0a7F/0wLtmKKN7I73AH5T2836UuXRqN7Qg+IIUw/+YJksRw==", "dev": true, "license": "MIT", "dependencies": { @@ -10579,8 +9117,6 @@ }, "node_modules/es-to-primitive": { "version": "1.3.0", - "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.3.0.tgz", - "integrity": "sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==", "dev": true, "license": "MIT", "dependencies": { @@ -10597,11 +9133,11 @@ }, "node_modules/esbuild": { "version": "0.25.0", - "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.25.0.tgz", - "integrity": "sha512-BXq5mqc8ltbaN34cDqWuYKyNhX8D/Z0J1xdtdQ8UcIIIyJyz+ZMKUt58tF3SrZ85jcfN/PZYhjR5uDQAYNVbuw==", - "devOptional": true, + "dev": true, "hasInstallScript": true, "license": "MIT", + "optional": true, + "peer": true, "bin": { "esbuild": "bin/esbuild" }, @@ -10638,10 +9174,10 @@ }, "node_modules/esbuild-register": { "version": "3.6.0", - "resolved": "https://registry.npmjs.org/esbuild-register/-/esbuild-register-3.6.0.tgz", - "integrity": "sha512-H2/S7Pm8a9CL1uhp9OvjwrBh5Pvx0H8qVOxNu8Wed9Y7qv56MPtq+GGM8RJpq6glYJn9Wspr8uw7l55uyinNeg==", - "devOptional": true, + "dev": true, "license": "MIT", + "optional": true, + "peer": true, "dependencies": { "debug": "^4.3.4" }, @@ -10651,8 +9187,6 @@ }, "node_modules/escalade": { "version": "3.2.0", - "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.2.0.tgz", - "integrity": "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==", "license": "MIT", "engines": { "node": ">=6" @@ -10666,8 +9200,6 @@ }, "node_modules/escape-string-regexp": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", - "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", "dev": true, "license": "MIT", "engines": { @@ -10679,9 +9211,6 @@ }, "node_modules/eslint": { "version": "8.57.1", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.57.1.tgz", - "integrity": "sha512-ypowyDxpVSYpkXr9WPv2PAZCtNip1Mv5KTW0SCurXv/9iOpcrH9PaqUElksqEB6pChqHGDRCFTyrZlGhnLNGiA==", - "deprecated": "This version is no longer supported. Please see https://eslint.org/version-support for other options.", "dev": true, "license": "MIT", "dependencies": { @@ -10736,8 +9265,6 @@ }, "node_modules/eslint-config-next": { "version": "14.2.23", - "resolved": "https://registry.npmjs.org/eslint-config-next/-/eslint-config-next-14.2.23.tgz", - "integrity": "sha512-qtWJzOsDZxnLtXLNtnVjbutHmnEp6QTTSZBTlTCge/Wy0AsUaq8nwR91dBcZZvFg3eY3zKFPBhUkLMHu3Qpauw==", "dev": true, "license": "MIT", "dependencies": { @@ -10764,8 +9291,6 @@ }, "node_modules/eslint-import-resolver-node": { "version": "0.3.9", - "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.9.tgz", - "integrity": "sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g==", "dev": true, "license": "MIT", "dependencies": { @@ -10776,8 +9301,6 @@ }, "node_modules/eslint-import-resolver-node/node_modules/debug": { "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", "dev": true, "license": "MIT", "dependencies": { @@ -10786,8 +9309,6 @@ }, "node_modules/eslint-import-resolver-typescript": { "version": "3.7.0", - "resolved": "https://registry.npmjs.org/eslint-import-resolver-typescript/-/eslint-import-resolver-typescript-3.7.0.tgz", - "integrity": "sha512-Vrwyi8HHxY97K5ebydMtffsWAn1SCR9eol49eCd5fJS4O1WV7PaAjbcjmbfJJSMz/t4Mal212Uz/fQZrOB8mow==", "dev": true, "license": "ISC", "dependencies": { @@ -10822,8 +9343,6 @@ }, "node_modules/eslint-module-utils": { "version": "2.12.0", - "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.12.0.tgz", - "integrity": "sha512-wALZ0HFoytlyh/1+4wuZ9FJCD/leWHQzzrxJ8+rebyReSLk7LApMyd3WJaLVoN+D5+WIdJyDK1c6JnE65V4Zyg==", "dev": true, "license": "MIT", "dependencies": { @@ -10840,8 +9359,6 @@ }, "node_modules/eslint-module-utils/node_modules/debug": { "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", "dev": true, "license": "MIT", "dependencies": { @@ -10850,8 +9367,6 @@ }, "node_modules/eslint-plugin-import": { "version": "2.31.0", - "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.31.0.tgz", - "integrity": "sha512-ixmkI62Rbc2/w8Vfxyh1jQRTdRTF52VxwRVHl/ykPAmqG+Nb7/kNn+byLP0LxPgI7zWA16Jt82SybJInmMia3A==", "dev": true, "license": "MIT", "dependencies": { @@ -10884,8 +9399,6 @@ }, "node_modules/eslint-plugin-import/node_modules/brace-expansion": { "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "dev": true, "license": "MIT", "dependencies": { @@ -10895,8 +9408,6 @@ }, "node_modules/eslint-plugin-import/node_modules/debug": { "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", "dev": true, "license": "MIT", "dependencies": { @@ -10905,8 +9416,6 @@ }, "node_modules/eslint-plugin-import/node_modules/doctrine": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", - "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -10918,8 +9427,6 @@ }, "node_modules/eslint-plugin-import/node_modules/minimatch": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", "dev": true, "license": "ISC", "dependencies": { @@ -10931,8 +9438,6 @@ }, "node_modules/eslint-plugin-jsx-a11y": { "version": "6.10.2", - "resolved": "https://registry.npmjs.org/eslint-plugin-jsx-a11y/-/eslint-plugin-jsx-a11y-6.10.2.tgz", - "integrity": "sha512-scB3nz4WmG75pV8+3eRUQOHZlNSUhFNq37xnpgRkCCELU3XMvXAxLk1eqWWyE22Ki4Q01Fnsw9BA3cJHDPgn2Q==", "dev": true, "license": "MIT", "dependencies": { @@ -10961,8 +9466,6 @@ }, "node_modules/eslint-plugin-jsx-a11y/node_modules/brace-expansion": { "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "dev": true, "license": "MIT", "dependencies": { @@ -10972,8 +9475,6 @@ }, "node_modules/eslint-plugin-jsx-a11y/node_modules/minimatch": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", "dev": true, "license": "ISC", "dependencies": { @@ -10985,8 +9486,6 @@ }, "node_modules/eslint-plugin-react": { "version": "7.37.4", - "resolved": "https://registry.npmjs.org/eslint-plugin-react/-/eslint-plugin-react-7.37.4.tgz", - "integrity": "sha512-BGP0jRmfYyvOyvMoRX/uoUeW+GqNj9y16bPQzqAHf3AYII/tDs+jMN0dBVkl88/OZwNGwrVFxE7riHsXVfy/LQ==", "dev": true, "license": "MIT", "dependencies": { @@ -11018,8 +9517,6 @@ }, "node_modules/eslint-plugin-react-hooks": { "version": "5.0.0-canary-7118f5dd7-20230705", - "resolved": "https://registry.npmjs.org/eslint-plugin-react-hooks/-/eslint-plugin-react-hooks-5.0.0-canary-7118f5dd7-20230705.tgz", - "integrity": "sha512-AZYbMo/NW9chdL7vk6HQzQhT+PvTAEVqWk9ziruUoW2kAOcN5qNyelv70e0F1VNQAbvutOC9oc+xfWycI9FxDw==", "dev": true, "license": "MIT", "engines": { @@ -11031,8 +9528,6 @@ }, "node_modules/eslint-plugin-react/node_modules/brace-expansion": { "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "dev": true, "license": "MIT", "dependencies": { @@ -11042,8 +9537,6 @@ }, "node_modules/eslint-plugin-react/node_modules/doctrine": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", - "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -11055,8 +9548,6 @@ }, "node_modules/eslint-plugin-react/node_modules/minimatch": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", "dev": true, "license": "ISC", "dependencies": { @@ -11068,8 +9559,6 @@ }, "node_modules/eslint-plugin-react/node_modules/resolve": { "version": "2.0.0-next.5", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.5.tgz", - "integrity": "sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==", "dev": true, "license": "MIT", "dependencies": { @@ -11086,8 +9575,6 @@ }, "node_modules/eslint-scope": { "version": "7.2.2", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-7.2.2.tgz", - "integrity": "sha512-dOt21O7lTMhDM+X9mB4GX+DZrZtCUJPL/wlcTqxyrx5IvO0IYtILdtrQGQp+8n5S0gwSVmOf9NQrjMOgfQZlIg==", "dev": true, "license": "BSD-2-Clause", "dependencies": { @@ -11103,8 +9590,6 @@ }, "node_modules/eslint-visitor-keys": { "version": "3.4.3", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz", - "integrity": "sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==", "dev": true, "license": "Apache-2.0", "engines": { @@ -11116,8 +9601,6 @@ }, "node_modules/eslint/node_modules/brace-expansion": { "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "dev": true, "license": "MIT", "dependencies": { @@ -11127,8 +9610,6 @@ }, "node_modules/eslint/node_modules/globals": { "version": "13.24.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-13.24.0.tgz", - "integrity": "sha512-AhO5QUcj8llrbG09iWhPU2B204J1xnPeL8kQmVorSsy+Sjj1sk8gIyh6cUocGmH4L0UuhAJy+hJMRA4mgA4mFQ==", "dev": true, "license": "MIT", "dependencies": { @@ -11143,8 +9624,6 @@ }, "node_modules/eslint/node_modules/minimatch": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", "dev": true, "license": "ISC", "dependencies": { @@ -11156,8 +9635,6 @@ }, "node_modules/eslint/node_modules/type-fest": { "version": "0.20.2", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", - "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", "dev": true, "license": "(MIT OR CC0-1.0)", "engines": { @@ -11169,8 +9646,6 @@ }, "node_modules/espree": { "version": "9.6.1", - "resolved": "https://registry.npmjs.org/espree/-/espree-9.6.1.tgz", - "integrity": "sha512-oruZaFkjorTpF32kDSI5/75ViwGeZginGGy2NoOSg3Q9bnwlnmDm4HLnkl0RE3n+njDXR037aY1+x58Z/zFdwQ==", "dev": true, "license": "BSD-2-Clause", "dependencies": { @@ -11187,8 +9662,6 @@ }, "node_modules/esprima": { "version": "4.0.1", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", - "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", "dev": true, "license": "BSD-2-Clause", "bin": { @@ -11201,8 +9674,6 @@ }, "node_modules/esquery": { "version": "1.6.0", - "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.6.0.tgz", - "integrity": "sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==", "dev": true, "license": "BSD-3-Clause", "dependencies": { @@ -11214,8 +9685,6 @@ }, "node_modules/esrecurse": { "version": "4.3.0", - "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", - "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", "dev": true, "license": "BSD-2-Clause", "dependencies": { @@ -11227,8 +9696,6 @@ }, "node_modules/estraverse": { "version": "5.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", - "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", "dev": true, "license": "BSD-2-Clause", "engines": { @@ -11237,8 +9704,6 @@ }, "node_modules/estree-util-is-identifier-name": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/estree-util-is-identifier-name/-/estree-util-is-identifier-name-3.0.0.tgz", - "integrity": "sha512-hFtqIDZTIUZ9BXLb8y4pYGyk6+wekIivNVTcmvk8NoOh+VeRn5y6cEHzbURrWbfp1fIqdVipilzj+lfaadNZmg==", "license": "MIT", "funding": { "type": "opencollective", @@ -11247,8 +9712,6 @@ }, "node_modules/esutils": { "version": "2.0.3", - "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", - "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", "license": "BSD-2-Clause", "engines": { "node": ">=0.10.0" @@ -11256,8 +9719,6 @@ }, "node_modules/event-target-shim": { "version": "5.0.1", - "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", - "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==", "license": "MIT", "engines": { "node": ">=6" @@ -11265,14 +9726,11 @@ }, "node_modules/eventemitter3": { "version": "4.0.7", - "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-4.0.7.tgz", - "integrity": "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==", "license": "MIT" }, "node_modules/execa": { "version": "5.1.1", - "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", - "integrity": "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==", + "dev": true, "license": "MIT", "dependencies": { "cross-spawn": "^7.0.3", @@ -11294,14 +9752,11 @@ }, "node_modules/execa/node_modules/signal-exit": { "version": "3.0.7", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", - "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", + "dev": true, "license": "ISC" }, "node_modules/exit-x": { "version": "0.2.2", - "resolved": "https://registry.npmjs.org/exit-x/-/exit-x-0.2.2.tgz", - "integrity": "sha512-+I6B/IkJc1o/2tiURyz/ivu/O0nKNEArIUB5O7zBrlDVJr22SCLH3xTeEry428LvFhRzIA1g8izguxJ/gbNcVQ==", "dev": true, "license": "MIT", "engines": { @@ -11319,8 +9774,6 @@ }, "node_modules/expect": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/expect/-/expect-30.1.2.tgz", - "integrity": "sha512-xvHszRavo28ejws8FpemjhwswGj4w/BetHIL8cU49u4sGyXDw2+p3YbeDbj6xzlxi6kWTjIRSTJ+9sNXPnF0Zg==", "dev": true, "license": "MIT", "dependencies": { @@ -11335,16 +9788,53 @@ "node": "^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0" } }, + "node_modules/exsolve": { + "version": "1.0.7", + "devOptional": true, + "license": "MIT" + }, "node_modules/extend": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", - "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", + "license": "MIT" + }, + "node_modules/fast-check": { + "version": "3.23.2", + "devOptional": true, + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/dubzzz" + }, + { + "type": "opencollective", + "url": "https://opencollective.com/fast-check" + } + ], + "license": "MIT", + "dependencies": { + "pure-rand": "^6.1.0" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/fast-check/node_modules/pure-rand": { + "version": "6.1.0", + "devOptional": true, + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/dubzzz" + }, + { + "type": "opencollective", + "url": "https://opencollective.com/fast-check" + } + ], "license": "MIT" }, "node_modules/fast-content-type-parse": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/fast-content-type-parse/-/fast-content-type-parse-2.0.1.tgz", - "integrity": "sha512-nGqtvLrj5w0naR6tDPfB4cUmYCqouzyQiz6C5y/LtcDllJdrcc6WaWW6iXyIIOErTa/XRybj28aasdn4LkVk6Q==", "funding": [ { "type": "github", @@ -11359,15 +9849,11 @@ }, "node_modules/fast-deep-equal": { "version": "3.1.3", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", - "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", "dev": true, "license": "MIT" }, "node_modules/fast-equals": { "version": "5.2.2", - "resolved": "https://registry.npmjs.org/fast-equals/-/fast-equals-5.2.2.tgz", - "integrity": "sha512-V7/RktU11J3I36Nwq2JnZEM7tNm17eBJz+u25qdxBZeCKiX6BkVSZQjwWIr+IobgnZy+ag73tTZgZi7tr0LrBw==", "license": "MIT", "engines": { "node": ">=6.0.0" @@ -11381,8 +9867,6 @@ }, "node_modules/fast-glob": { "version": "3.3.3", - "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.3.tgz", - "integrity": "sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==", "license": "MIT", "dependencies": { "@nodelib/fs.stat": "^2.0.2", @@ -11397,8 +9881,6 @@ }, "node_modules/fast-glob/node_modules/glob-parent": { "version": "5.1.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", - "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", "license": "ISC", "dependencies": { "is-glob": "^4.0.1" @@ -11409,21 +9891,15 @@ }, "node_modules/fast-json-patch": { "version": "3.1.1", - "resolved": "https://registry.npmjs.org/fast-json-patch/-/fast-json-patch-3.1.1.tgz", - "integrity": "sha512-vf6IHUX2SBcA+5/+4883dsIjpBTqmfBjmYiWK1savxQmFk4JfBMLa7ynTYOs1Rolp/T1betJxHiGD3g1Mn8lUQ==", "license": "MIT" }, "node_modules/fast-json-stable-stringify": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", - "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", "dev": true, "license": "MIT" }, "node_modules/fast-levenshtein": { "version": "2.0.6", - "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", - "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", "dev": true, "license": "MIT" }, @@ -11435,8 +9911,6 @@ }, "node_modules/fastq": { "version": "1.18.0", - "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.18.0.tgz", - "integrity": "sha512-QKHXPW0hD8g4UET03SdOdunzSouc9N4AuHdsX8XNcTsuz+yYFILVNIX4l9yHABMhiEI9Db0JTTIpu0wB+Y1QQw==", "license": "ISC", "dependencies": { "reusify": "^1.0.4" @@ -11444,8 +9918,6 @@ }, "node_modules/fault": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/fault/-/fault-1.0.4.tgz", - "integrity": "sha512-CJ0HCB5tL5fYTEA7ToAq5+kTwd++Borf1/bifxd9iT70QcXr4MRrO3Llf8Ifs70q+SJcGHFtnIE/Nw6giCtECA==", "license": "MIT", "dependencies": { "format": "^0.2.0" @@ -11457,8 +9929,6 @@ }, "node_modules/fb-watchman": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/fb-watchman/-/fb-watchman-2.0.2.tgz", - "integrity": "sha512-p5161BqbuCaSnB8jIbzQHOlpgsPmK5rJVDfDKO91Axs5NC1uu3HRQm6wt9cd9/+GtQQIO53JdGXXoyDpTAsgYA==", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -11467,8 +9937,6 @@ }, "node_modules/fetch-blob": { "version": "3.2.0", - "resolved": "https://registry.npmjs.org/fetch-blob/-/fetch-blob-3.2.0.tgz", - "integrity": "sha512-7yAQpD2UMJzLi1Dqv7qFYnPbaPx7ZfFK6PiIxQ4PfkGPyNyl2Ugx+a/umUonmKqjhM4DnfbMvdX6otXq83soQQ==", "funding": [ { "type": "github", @@ -11490,14 +9958,10 @@ }, "node_modules/fflate": { "version": "0.8.2", - "resolved": "https://registry.npmjs.org/fflate/-/fflate-0.8.2.tgz", - "integrity": "sha512-cPJU47OaAoCbg0pBvzsgpTPhmhqI5eJjh/JIu8tPj5q+T7iLvW/JAYUqmE7KOB4R1ZyEhzBaIQpQpardBF5z8A==", "license": "MIT" }, "node_modules/file-entry-cache": { "version": "6.0.1", - "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-6.0.1.tgz", - "integrity": "sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg==", "dev": true, "license": "MIT", "dependencies": { @@ -11509,8 +9973,6 @@ }, "node_modules/file-selector": { "version": "2.1.2", - "resolved": "https://registry.npmjs.org/file-selector/-/file-selector-2.1.2.tgz", - "integrity": "sha512-QgXo+mXTe8ljeqUFaX3QVHc5osSItJ/Km+xpocx0aSqWGMSCf6qYs/VnzZgS864Pjn5iceMRFigeAV7AfTlaig==", "license": "MIT", "dependencies": { "tslib": "^2.7.0" @@ -11540,8 +10002,6 @@ }, "node_modules/fill-range": { "version": "7.1.1", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", - "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", "license": "MIT", "dependencies": { "to-regex-range": "^5.0.1" @@ -11552,8 +10012,6 @@ }, "node_modules/find-up": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", - "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==", "dev": true, "license": "MIT", "dependencies": { @@ -11569,8 +10027,6 @@ }, "node_modules/flat-cache": { "version": "3.2.0", - "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.2.0.tgz", - "integrity": "sha512-CYcENa+FtcUKLmhhqyctpclsq7QF38pKjZHsGNiSQF5r4FtoKDWabFDl3hzaEQMvT1LHEysw5twgLvpYYb4vbw==", "dev": true, "license": "MIT", "dependencies": { @@ -11584,15 +10040,11 @@ }, "node_modules/flatted": { "version": "3.3.2", - "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.3.2.tgz", - "integrity": "sha512-AiwGJM8YcNOaobumgtng+6NHuOqC3A7MixFeDafM3X9cIUM+xUXoS5Vfgf+OihAYe20fxqNM9yPBXJzRtZ/4eA==", "dev": true, "license": "ISC" }, "node_modules/follow-redirects": { "version": "1.15.9", - "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.9.tgz", - "integrity": "sha512-gew4GsXizNgdoRyqmyfMHyAmXsZDk6mHkSxZFCzW9gwlbtOW44CDtYavM+y+72qD/Vq2l550kMF52DT8fOLJqQ==", "funding": [ { "type": "individual", @@ -11611,8 +10063,6 @@ }, "node_modules/for-each": { "version": "0.3.4", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.4.tgz", - "integrity": "sha512-kKaIINnFpzW6ffJNDjjyjrk21BkDx38c0xa/klsT8VzLCaMEefv4ZTacrcVR4DmgTeBra++jMDAfS/tS799YDw==", "license": "MIT", "dependencies": { "is-callable": "^1.2.7" @@ -11626,8 +10076,6 @@ }, "node_modules/foreground-child": { "version": "3.3.0", - "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-3.3.0.tgz", - "integrity": "sha512-Ld2g8rrAyMYFXBhEqMz8ZAHBi4J4uS1i/CxGMDnjyFWddMXLVcDp051DZfu+t7+ab7Wv6SMqpWmyFIj5UbfFvg==", "license": "ISC", "dependencies": { "cross-spawn": "^7.0.0", @@ -11642,8 +10090,6 @@ }, "node_modules/form-data": { "version": "4.0.2", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.2.tgz", - "integrity": "sha512-hGfm/slu0ZabnNt4oaRZ6uREyfCj6P4fT/n6A1rGV+Z0VdGXjfOhVUpkn6qVQONHGIFwmveGXyDs75+nr6FM8w==", "license": "MIT", "dependencies": { "asynckit": "^0.4.0", @@ -11657,16 +10103,12 @@ }, "node_modules/format": { "version": "0.2.2", - "resolved": "https://registry.npmjs.org/format/-/format-0.2.2.tgz", - "integrity": "sha512-wzsgA6WOq+09wrU1tsJ09udeR/YZRaeArL9e1wPbFg3GG2yDnC2ldKpxs4xunpFF9DgqCqOIra3bc1HWrJ37Ww==", "engines": { "node": ">=0.4.x" } }, "node_modules/formdata-polyfill": { "version": "4.0.10", - "resolved": "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz", - "integrity": "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==", "license": "MIT", "dependencies": { "fetch-blob": "^3.1.2" @@ -11679,6 +10121,7 @@ "version": "3.5.4", "resolved": "https://registry.npmjs.org/formidable/-/formidable-3.5.4.tgz", "integrity": "sha512-YikH+7CUTOtP44ZTnUhR7Ic2UASBPOqmaRkRKxRbywPTe5VxF7RRCck4af9wutiZ/QKM5nME9Bie2fFaPz5Gug==", + "license": "MIT", "dependencies": { "@paralleldrive/cuid2": "^2.2.2", "dezalgo": "^1.0.4", @@ -11702,8 +10145,6 @@ }, "node_modules/frame-ticker": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/frame-ticker/-/frame-ticker-1.0.3.tgz", - "integrity": "sha512-E0X2u2JIvbEMrqEg5+4BpTqaD22OwojJI63K7MdKHdncjtAhGRbCR8nJCr2vwEt9NWBPCPcu70X9smPviEBy8Q==", "license": "MIT", "dependencies": { "simplesignal": "^2.1.6" @@ -11711,8 +10152,6 @@ }, "node_modules/framer-motion": { "version": "11.18.2", - "resolved": "https://registry.npmjs.org/framer-motion/-/framer-motion-11.18.2.tgz", - "integrity": "sha512-5F5Och7wrvtLVElIpclDT0CBzMVg3dL22B64aZwHtsIY8RB4mXICLrkajK4G9R+ieSAGcgrLeae2SeUTg2pr6w==", "license": "MIT", "dependencies": { "motion-dom": "^11.18.1", @@ -11743,9 +10182,9 @@ "license": "MIT" }, "node_modules/fs-chunk-store": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/fs-chunk-store/-/fs-chunk-store-4.1.0.tgz", - "integrity": "sha512-8apaYPaENIVUjVGqjo+Yg5/Hv7qL2fijWV+XGMCs3MR07o9DZZVMpF7dclxdjYotSjLdUGVPhqaJn+eAx6NLYQ==", + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/fs-chunk-store/-/fs-chunk-store-5.0.0.tgz", + "integrity": "sha512-tKlT0joU9KmsLn0dTbVYVUa7VNqYQhl0X2qPPsN9lPEc3guXOmQJWY5/7kpo34Sk273qyWT5mqEhROCQPF+JKw==", "funding": [ { "type": "github", @@ -11765,9 +10204,9 @@ "filename-reserved-regex": "^3.0.0", "queue-microtask": "^1.2.2", "random-access-file": "^4.0.0", - "randombytes": "^2.0.3", "run-parallel": "^1.1.2", - "thunky": "^1.0.1" + "thunky": "^1.0.1", + "uint8-util": "^2.2.5" }, "engines": { "node": ">=12.20.0" @@ -11780,9 +10219,9 @@ "license": "MIT" }, "node_modules/fs-native-extensions": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/fs-native-extensions/-/fs-native-extensions-1.3.4.tgz", - "integrity": "sha512-ALYLNDtwuQfbQc1tCgcvT9ntP+EN07j9w+W80Y3ofKlKquysI5M/0/05gmfGSoKyc6XwGDxD5kYBRLkXcwmAiQ==", + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/fs-native-extensions/-/fs-native-extensions-1.4.4.tgz", + "integrity": "sha512-iLo3r2ei97thJNoj3DgSdzUF2hZ2yekZpXF98LlHc2eZGPOwiVblyEa6iS68zLu9ayXvlE8/c3CMaagNbHJB1Q==", "license": "Apache-2.0", "optional": true, "dependencies": { @@ -11792,8 +10231,6 @@ }, "node_modules/fs.realpath": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", "license": "ISC" }, "node_modules/fsa-chunk-store": { @@ -11807,9 +10244,6 @@ }, "node_modules/fsevents": { "version": "2.3.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", - "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", - "hasInstallScript": true, "license": "MIT", "optional": true, "os": [ @@ -11821,8 +10255,6 @@ }, "node_modules/function-bind": { "version": "1.1.2", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", - "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/ljharb" @@ -11830,8 +10262,6 @@ }, "node_modules/function.prototype.name": { "version": "1.1.8", - "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.8.tgz", - "integrity": "sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==", "dev": true, "license": "MIT", "dependencies": { @@ -11851,8 +10281,6 @@ }, "node_modules/functions-have-names": { "version": "1.2.3", - "resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz", - "integrity": "sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==", "dev": true, "license": "MIT", "funding": { @@ -11861,8 +10289,6 @@ }, "node_modules/geist": { "version": "1.3.1", - "resolved": "https://registry.npmjs.org/geist/-/geist-1.3.1.tgz", - "integrity": "sha512-Q4gC1pBVPN+D579pBaz0TRRnGA4p9UK6elDY/xizXdFk/g4EKR5g0I+4p/Kj6gM0SajDBZ/0FvDV9ey9ud7BWw==", "license": "SIL OPEN FONT LICENSE", "peerDependencies": { "next": ">=13.2.0" @@ -11870,8 +10296,6 @@ }, "node_modules/gensync": { "version": "1.0.0-beta.2", - "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", - "integrity": "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==", "license": "MIT", "engines": { "node": ">=6.9.0" @@ -11879,8 +10303,6 @@ }, "node_modules/get-caller-file": { "version": "2.0.5", - "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", - "integrity": "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==", "dev": true, "license": "ISC", "engines": { @@ -11889,8 +10311,6 @@ }, "node_modules/get-intrinsic": { "version": "1.2.7", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.7.tgz", - "integrity": "sha512-VW6Pxhsrk0KAOqs3WEd0klDiF/+V7gQOpAvY1jVU/LHmaD/kQO4523aiJuikX/QAKYiW6x8Jh+RJej1almdtCA==", "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.1", @@ -11913,8 +10333,6 @@ }, "node_modules/get-nonce": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/get-nonce/-/get-nonce-1.0.1.tgz", - "integrity": "sha512-FJhYRoDaiatfEkUK8HKlicmu/3SGFD51q3itKDGoSTysQJBnfOcxU5GxnhE1E6soB76MbT0MBtnKJuXyAx+96Q==", "license": "MIT", "engines": { "node": ">=6" @@ -11922,8 +10340,6 @@ }, "node_modules/get-package-type": { "version": "0.1.0", - "resolved": "https://registry.npmjs.org/get-package-type/-/get-package-type-0.1.0.tgz", - "integrity": "sha512-pjzuKtY64GYfWizNAJ0fr9VqttZkNiK2iS430LtIHzjBEr6bX8Am2zm4sW4Ro5wjWW5cAlRL1qAMTcXbjNAO2Q==", "dev": true, "license": "MIT", "engines": { @@ -11932,8 +10348,6 @@ }, "node_modules/get-proto": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz", - "integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==", "license": "MIT", "dependencies": { "dunder-proto": "^1.0.1", @@ -11969,8 +10383,6 @@ }, "node_modules/get-stream": { "version": "6.0.1", - "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-6.0.1.tgz", - "integrity": "sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg==", "license": "MIT", "engines": { "node": ">=10" @@ -11981,8 +10393,6 @@ }, "node_modules/get-symbol-description": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.1.0.tgz", - "integrity": "sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==", "dev": true, "license": "MIT", "dependencies": { @@ -11999,8 +10409,6 @@ }, "node_modules/get-tsconfig": { "version": "4.10.0", - "resolved": "https://registry.npmjs.org/get-tsconfig/-/get-tsconfig-4.10.0.tgz", - "integrity": "sha512-kGzZ3LWWQcGIAmg6iWvXn0ei6WDtV26wzHRMwDSzmAbcXrTEXxHy6IehI6/4eT6VRKyMP1eF1VqwrVUmE/LR7A==", "dev": true, "license": "MIT", "dependencies": { @@ -12010,6 +10418,22 @@ "url": "https://github.com/privatenumber/get-tsconfig?sponsor=1" } }, + "node_modules/giget": { + "version": "2.0.0", + "devOptional": true, + "license": "MIT", + "dependencies": { + "citty": "^0.1.6", + "consola": "^3.4.0", + "defu": "^6.1.4", + "node-fetch-native": "^1.6.6", + "nypm": "^0.6.0", + "pathe": "^2.0.3" + }, + "bin": { + "giget": "dist/cli.mjs" + } + }, "node_modules/github-from-package": { "version": "0.0.0", "resolved": "https://registry.npmjs.org/github-from-package/-/github-from-package-0.0.0.tgz", @@ -12018,8 +10442,6 @@ }, "node_modules/glob": { "version": "10.3.10", - "resolved": "https://registry.npmjs.org/glob/-/glob-10.3.10.tgz", - "integrity": "sha512-fa46+tv1Ak0UPK1TOy/pZrIybNNt4HCv7SDzwyfiOZkvZLEbjsZkJBPtDHVshZjbecAoAGSC20MjLDG/qr679g==", "license": "ISC", "dependencies": { "foreground-child": "^3.1.0", @@ -12040,8 +10462,6 @@ }, "node_modules/glob-parent": { "version": "6.0.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", - "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", "license": "ISC", "dependencies": { "is-glob": "^4.0.3" @@ -12054,6 +10474,7 @@ "version": "4.4.0", "resolved": "https://registry.npmjs.org/global/-/global-4.4.0.tgz", "integrity": "sha512-wv/LAoHdRE3BeTGz53FAamhGlPLhlssK45usmGFThIi4XqnBmjKQ16u+RNbP7WvigRZDxUsM0J3gcQ5yicaL0w==", + "license": "MIT", "dependencies": { "min-document": "^2.19.0", "process": "^0.11.10" @@ -12061,8 +10482,6 @@ }, "node_modules/globalthis": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/globalthis/-/globalthis-1.0.4.tgz", - "integrity": "sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -12078,14 +10497,10 @@ }, "node_modules/glsl-noise": { "version": "0.0.0", - "resolved": "https://registry.npmjs.org/glsl-noise/-/glsl-noise-0.0.0.tgz", - "integrity": "sha512-b/ZCF6amfAUb7dJM/MxRs7AetQEahYzJ8PtgfrmEdtw6uyGOr+ZSGtgjFm6mfsBkxJ4d2W7kg+Nlqzqvn3Bc0w==", "license": "MIT" }, "node_modules/gopd": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", - "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==", "license": "MIT", "engines": { "node": ">= 0.4" @@ -12096,22 +10511,15 @@ }, "node_modules/graceful-fs": { "version": "4.2.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz", - "integrity": "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==", - "dev": true, "license": "ISC" }, "node_modules/graphemer": { "version": "1.4.0", - "resolved": "https://registry.npmjs.org/graphemer/-/graphemer-1.4.0.tgz", - "integrity": "sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==", "dev": true, "license": "MIT" }, "node_modules/h3-js": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/h3-js/-/h3-js-4.1.0.tgz", - "integrity": "sha512-LQhmMl1dRQQjMXPzJc7MpZ/CqPOWWuAvVEoVJM9n/s7vHypj+c3Pd5rLQCkAsOgAoAYKbNCsYFE++LF7MvSfCQ==", "license": "Apache-2.0", "engines": { "node": ">=4", @@ -12121,8 +10529,6 @@ }, "node_modules/handlebars": { "version": "4.7.8", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.8.tgz", - "integrity": "sha512-vafaFqs8MZkRrSX7sFVUdo3ap/eNiLnb4IakshzvP56X5Nr1iGKAIqdX6tMlm6HcNRIkr6AxO5jFEoJzzpT8aQ==", "dev": true, "license": "MIT", "dependencies": { @@ -12143,8 +10549,6 @@ }, "node_modules/has-bigints": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.1.0.tgz", - "integrity": "sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==", "dev": true, "license": "MIT", "engines": { @@ -12156,9 +10560,6 @@ }, "node_modules/has-flag": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true, "license": "MIT", "engines": { "node": ">=8" @@ -12166,8 +10567,6 @@ }, "node_modules/has-property-descriptors": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", - "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", "license": "MIT", "dependencies": { "es-define-property": "^1.0.0" @@ -12178,8 +10577,6 @@ }, "node_modules/has-proto": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.2.0.tgz", - "integrity": "sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==", "dev": true, "license": "MIT", "dependencies": { @@ -12194,8 +10591,6 @@ }, "node_modules/has-symbols": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz", - "integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==", "license": "MIT", "engines": { "node": ">= 0.4" @@ -12206,8 +10601,6 @@ }, "node_modules/has-tostringtag": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz", - "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==", "license": "MIT", "dependencies": { "has-symbols": "^1.0.3" @@ -12220,19 +10613,62 @@ } }, "node_modules/hash-base": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-3.1.0.tgz", - "integrity": "sha512-1nmYp/rhMDiE7AYkDw+lLwlAzz0AntGIe51F3RfFfEqyQ3feY2eI/NcwC6umIQVOASPMsWJLJScWKSSvzL9IVA==", + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-3.1.2.tgz", + "integrity": "sha512-Bb33KbowVTIj5s7Ked1OsqHUeCpz//tPwR+E2zJgJKo9Z5XolZ9b6bdUgjmYlwnWhoOQKoTd1TYToZGn5mAYOg==", "license": "MIT", "dependencies": { "inherits": "^2.0.4", - "readable-stream": "^3.6.0", - "safe-buffer": "^5.2.0" + "readable-stream": "^2.3.8", + "safe-buffer": "^5.2.1", + "to-buffer": "^1.2.1" }, "engines": { - "node": ">=4" + "node": ">= 0.8" + } + }, + "node_modules/hash-base/node_modules/isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", + "license": "MIT" + }, + "node_modules/hash-base/node_modules/readable-stream": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", + "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", + "license": "MIT", + "dependencies": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + } + }, + "node_modules/hash-base/node_modules/readable-stream/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "license": "MIT" + }, + "node_modules/hash-base/node_modules/string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "license": "MIT", + "dependencies": { + "safe-buffer": "~5.1.0" } }, + "node_modules/hash-base/node_modules/string_decoder/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "license": "MIT" + }, "node_modules/hashlru": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/hashlru/-/hashlru-2.3.0.tgz", @@ -12241,8 +10677,6 @@ }, "node_modules/hasown": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", - "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", "license": "MIT", "dependencies": { "function-bind": "^1.1.2" @@ -12253,8 +10687,6 @@ }, "node_modules/hast-util-parse-selector": { "version": "2.2.5", - "resolved": "https://registry.npmjs.org/hast-util-parse-selector/-/hast-util-parse-selector-2.2.5.tgz", - "integrity": "sha512-7j6mrk/qqkSehsM92wQjdIgWM2/BW61u/53G6xmC8i1OmEdKLHbk419QKQUjz6LglWsfqoiHmyMRkP1BGjecNQ==", "license": "MIT", "funding": { "type": "opencollective", @@ -12263,8 +10695,6 @@ }, "node_modules/hast-util-to-jsx-runtime": { "version": "2.3.6", - "resolved": "https://registry.npmjs.org/hast-util-to-jsx-runtime/-/hast-util-to-jsx-runtime-2.3.6.tgz", - "integrity": "sha512-zl6s8LwNyo1P9uw+XJGvZtdFF1GdAkOg8ujOw+4Pyb76874fLps4ueHXDhXWdk6YHQ6OgUtinliG7RsYvCbbBg==", "license": "MIT", "dependencies": { "@types/estree": "^1.0.0", @@ -12290,8 +10720,6 @@ }, "node_modules/hast-util-to-jsx-runtime/node_modules/@types/hast": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", - "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", "license": "MIT", "dependencies": { "@types/unist": "*" @@ -12299,14 +10727,10 @@ }, "node_modules/hast-util-to-jsx-runtime/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/hast-util-to-jsx-runtime/node_modules/comma-separated-tokens": { "version": "2.0.3", - "resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-2.0.3.tgz", - "integrity": "sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==", "license": "MIT", "funding": { "type": "github", @@ -12315,8 +10739,6 @@ }, "node_modules/hast-util-to-jsx-runtime/node_modules/property-information": { "version": "7.1.0", - "resolved": "https://registry.npmjs.org/property-information/-/property-information-7.1.0.tgz", - "integrity": "sha512-TwEZ+X+yCJmYfL7TPUOcvBZ4QfoT5YenQiJuX//0th53DE6w0xxLEtfK3iyryQFddXuvkIk51EEgrJQ0WJkOmQ==", "license": "MIT", "funding": { "type": "github", @@ -12325,8 +10747,6 @@ }, "node_modules/hast-util-to-jsx-runtime/node_modules/space-separated-tokens": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/space-separated-tokens/-/space-separated-tokens-2.0.2.tgz", - "integrity": "sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==", "license": "MIT", "funding": { "type": "github", @@ -12335,8 +10755,6 @@ }, "node_modules/hast-util-whitespace": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/hast-util-whitespace/-/hast-util-whitespace-3.0.0.tgz", - "integrity": "sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==", "license": "MIT", "dependencies": { "@types/hast": "^3.0.0" @@ -12348,8 +10766,6 @@ }, "node_modules/hast-util-whitespace/node_modules/@types/hast": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", - "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", "license": "MIT", "dependencies": { "@types/unist": "*" @@ -12357,8 +10773,6 @@ }, "node_modules/hastscript": { "version": "6.0.0", - "resolved": "https://registry.npmjs.org/hastscript/-/hastscript-6.0.0.tgz", - "integrity": "sha512-nDM6bvd7lIqDUiYEiu5Sl/+6ReP0BMk/2f4U/Rooccxkj0P5nm+acM5PrGJ/t5I8qPGiqZSE6hVAwZEdZIvP4w==", "license": "MIT", "dependencies": { "@types/hast": "^2.0.0", @@ -12374,8 +10788,6 @@ }, "node_modules/highlight.js": { "version": "10.7.3", - "resolved": "https://registry.npmjs.org/highlight.js/-/highlight.js-10.7.3.tgz", - "integrity": "sha512-tzcUFauisWKNHaRkN4Wjl/ZA07gENAjFl3J/c480dprkGTg5EQstgaNFqBfUqCq54kZRIEcreTsAgF/m2quD7A==", "license": "BSD-3-Clause", "engines": { "node": "*" @@ -12383,27 +10795,19 @@ }, "node_modules/highlightjs-vue": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/highlightjs-vue/-/highlightjs-vue-1.0.0.tgz", - "integrity": "sha512-PDEfEF102G23vHmPhLyPboFCD+BkMGu+GuJe2d9/eH4FsCwvgBpnc9n0pGE+ffKdph38s6foEZiEjdgHdzp+IA==", "license": "CC0-1.0" }, "node_modules/hls.js": { "version": "1.5.20", - "resolved": "https://registry.npmjs.org/hls.js/-/hls.js-1.5.20.tgz", - "integrity": "sha512-uu0VXUK52JhihhnN/MVVo1lvqNNuhoxkonqgO3IpjvQiGpJBdIXMGkofjQb/j9zvV7a1SW8U9g1FslWx/1HOiQ==", "license": "Apache-2.0" }, "node_modules/html-escaper": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/html-escaper/-/html-escaper-2.0.2.tgz", - "integrity": "sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg==", "dev": true, "license": "MIT" }, "node_modules/html-url-attributes": { "version": "3.0.1", - "resolved": "https://registry.npmjs.org/html-url-attributes/-/html-url-attributes-3.0.1.tgz", - "integrity": "sha512-ol6UPyBWqsrO6EJySPz2O7ZSr856WDrEzM5zMqp+FJJLGMW35cLYmmZnl0vztAZxRUoNZJFTCohfjuIJ8I4QBQ==", "license": "MIT", "funding": { "type": "opencollective", @@ -12418,8 +10822,7 @@ }, "node_modules/human-signals": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-2.1.0.tgz", - "integrity": "sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==", + "dev": true, "license": "Apache-2.0", "engines": { "node": ">=10.17.0" @@ -12435,14 +10838,10 @@ }, "node_modules/idb-keyval": { "version": "6.2.1", - "resolved": "https://registry.npmjs.org/idb-keyval/-/idb-keyval-6.2.1.tgz", - "integrity": "sha512-8Sb3veuYCyrZL+VBt9LJfZjLUPWVvqn8tG28VqYNFCo43KHcKuq+b4EiXGeuaLAQWL2YmyDgMp2aSpH9JHsEQg==", "license": "Apache-2.0" }, "node_modules/ieee754": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", - "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", "funding": [ { "type": "github", @@ -12461,8 +10860,6 @@ }, "node_modules/ignore": { "version": "5.3.2", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz", - "integrity": "sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==", "dev": true, "license": "MIT", "engines": { @@ -12471,8 +10868,6 @@ }, "node_modules/immediate": { "version": "3.0.6", - "resolved": "https://registry.npmjs.org/immediate/-/immediate-3.0.6.tgz", - "integrity": "sha512-XXOFtyqDjNDAQxVfYxuF7g9Il/IbWmmlQg2MYKOH8ExIT1qg6xc4zyS3HaEEATgs1btfzxq15ciUiY7gjSXRGQ==", "license": "MIT" }, "node_modules/immediate-chunk-store": { @@ -12500,8 +10895,6 @@ }, "node_modules/immutable": { "version": "3.8.2", - "resolved": "https://registry.npmjs.org/immutable/-/immutable-3.8.2.tgz", - "integrity": "sha512-15gZoQ38eYjEjxkorfbcgBKBL6R7T459OuK+CpcWt7O3KF4uPCx2tD0uFETlUDIyo+1789crbMhTvQBSR5yBMg==", "license": "MIT", "engines": { "node": ">=0.10.0" @@ -12509,8 +10902,6 @@ }, "node_modules/import-fresh": { "version": "3.3.0", - "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz", - "integrity": "sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==", "dev": true, "license": "MIT", "dependencies": { @@ -12526,8 +10917,6 @@ }, "node_modules/import-local": { "version": "3.2.0", - "resolved": "https://registry.npmjs.org/import-local/-/import-local-3.2.0.tgz", - "integrity": "sha512-2SPlun1JUPWoM6t3F0dw0FkCF/jWY8kttcY4f599GLTSjh2OCuuhdTkJQsEcZzBqbXZGKMK2OqW1oZsjtf/gQA==", "dev": true, "license": "MIT", "dependencies": { @@ -12546,9 +10935,6 @@ }, "node_modules/imurmurhash": { "version": "0.1.4", - "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==", - "dev": true, "license": "MIT", "engines": { "node": ">=0.8.19" @@ -12556,8 +10942,6 @@ }, "node_modules/index-array-by": { "version": "1.4.2", - "resolved": "https://registry.npmjs.org/index-array-by/-/index-array-by-1.4.2.tgz", - "integrity": "sha512-SP23P27OUKzXWEC/TOyWlwLviofQkCSCKONnc62eItjp69yCZZPqDQtr3Pw5gJDnPeUMqExmKydNZaJO0FU9pw==", "license": "MIT", "engines": { "node": ">=12" @@ -12565,9 +10949,6 @@ }, "node_modules/inflight": { "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", - "deprecated": "This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful.", "license": "ISC", "dependencies": { "once": "^1.3.0", @@ -12576,8 +10957,6 @@ }, "node_modules/inherits": { "version": "2.0.4", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", "license": "ISC" }, "node_modules/ini": { @@ -12588,14 +10967,10 @@ }, "node_modules/inline-style-parser": { "version": "0.2.4", - "resolved": "https://registry.npmjs.org/inline-style-parser/-/inline-style-parser-0.2.4.tgz", - "integrity": "sha512-0aO8FkhNZlj/ZIbNi7Lxxr12obT7cL1moPfE4tg1LkX7LlLfC6DeX4l2ZEud1ukP9jNQyNnfzQVqwbwmAATY4Q==", "license": "MIT" }, "node_modules/internal-slot": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.1.0.tgz", - "integrity": "sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==", "dev": true, "license": "MIT", "dependencies": { @@ -12609,8 +10984,6 @@ }, "node_modules/internmap": { "version": "2.0.3", - "resolved": "https://registry.npmjs.org/internmap/-/internmap-2.0.3.tgz", - "integrity": "sha512-5Hh7Y1wQbvY5ooGgPbDaL5iYLAPzMTUrjMulskHLH6wnv/A+1q5rgEaiuqEjB+oxGXIVZs1FF+R/KPN3ZSQYYg==", "license": "ISC", "engines": { "node": ">=12" @@ -12618,8 +10991,6 @@ }, "node_modules/invariant": { "version": "2.2.4", - "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz", - "integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==", "license": "MIT", "dependencies": { "loose-envify": "^1.0.0" @@ -12664,8 +11035,6 @@ }, "node_modules/is-alphabetical": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-1.0.4.tgz", - "integrity": "sha512-DwzsA04LQ10FHTZuL0/grVDk4rFoVH1pjAToYwBrHSxcrBIGQuXrQMtD5U1b0U2XVgKZCTLLP8u2Qxqhy3l2Vg==", "license": "MIT", "funding": { "type": "github", @@ -12674,8 +11043,6 @@ }, "node_modules/is-alphanumerical": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-1.0.4.tgz", - "integrity": "sha512-UzoZUr+XfVz3t3v4KyGEniVL9BDRoQtY7tOyrRybkVNjDFWyo1yhXNGrrBTQxp3ib9BLAWs7k2YKBQsFRkZG9A==", "license": "MIT", "dependencies": { "is-alphabetical": "^1.0.0", @@ -12704,8 +11071,6 @@ }, "node_modules/is-array-buffer": { "version": "3.0.5", - "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.5.tgz", - "integrity": "sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==", "dev": true, "license": "MIT", "dependencies": { @@ -12722,15 +11087,11 @@ }, "node_modules/is-arrayish": { "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", - "integrity": "sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==", "dev": true, "license": "MIT" }, "node_modules/is-async-function": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-async-function/-/is-async-function-2.1.1.tgz", - "integrity": "sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==", "dev": true, "license": "MIT", "dependencies": { @@ -12749,8 +11110,6 @@ }, "node_modules/is-bigint": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.1.0.tgz", - "integrity": "sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==", "dev": true, "license": "MIT", "dependencies": { @@ -12765,8 +11124,6 @@ }, "node_modules/is-binary-path": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", - "integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==", "license": "MIT", "dependencies": { "binary-extensions": "^2.0.0" @@ -12777,8 +11134,6 @@ }, "node_modules/is-boolean-object": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.2.1.tgz", - "integrity": "sha512-l9qO6eFlUETHtuihLcYOaLKByJ1f+N4kthcU9YjHy3N+B3hWv0y/2Nd0mu/7lTFnRQHTrSdXF50HQ3bl5fEnng==", "dev": true, "license": "MIT", "dependencies": { @@ -12794,8 +11149,6 @@ }, "node_modules/is-buffer": { "version": "2.0.5", - "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-2.0.5.tgz", - "integrity": "sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ==", "funding": [ { "type": "github", @@ -12817,8 +11170,6 @@ }, "node_modules/is-bun-module": { "version": "1.3.0", - "resolved": "https://registry.npmjs.org/is-bun-module/-/is-bun-module-1.3.0.tgz", - "integrity": "sha512-DgXeu5UWI0IsMQundYb5UAOzm6G2eVnarJ0byP6Tm55iZNKceD59LNPA2L4VvsScTtHcw0yEkVwSf7PC+QoLSA==", "dev": true, "license": "MIT", "dependencies": { @@ -12827,8 +11178,6 @@ }, "node_modules/is-bun-module/node_modules/semver": { "version": "7.6.3", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", - "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", "dev": true, "license": "ISC", "bin": { @@ -12840,8 +11189,6 @@ }, "node_modules/is-callable": { "version": "1.2.7", - "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", - "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", "license": "MIT", "engines": { "node": ">= 0.4" @@ -12852,8 +11199,6 @@ }, "node_modules/is-core-module": { "version": "2.16.1", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.16.1.tgz", - "integrity": "sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==", "license": "MIT", "dependencies": { "hasown": "^2.0.2" @@ -12867,8 +11212,6 @@ }, "node_modules/is-data-view": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-data-view/-/is-data-view-1.0.2.tgz", - "integrity": "sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==", "dev": true, "license": "MIT", "dependencies": { @@ -12885,8 +11228,6 @@ }, "node_modules/is-date-object": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.1.0.tgz", - "integrity": "sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==", "dev": true, "license": "MIT", "dependencies": { @@ -12902,8 +11243,6 @@ }, "node_modules/is-decimal": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-1.0.4.tgz", - "integrity": "sha512-RGdriMmQQvZ2aqaQq3awNA6dCGtKpiDFcOzrTWrDAT2MiWrKQVPmxLGHl7Y2nNu6led0kEyoX0enY0qXYsv9zw==", "license": "MIT", "funding": { "type": "github", @@ -12912,8 +11251,6 @@ }, "node_modules/is-extglob": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", "license": "MIT", "engines": { "node": ">=0.10.0" @@ -12927,8 +11264,6 @@ }, "node_modules/is-finalizationregistry": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-finalizationregistry/-/is-finalizationregistry-1.1.1.tgz", - "integrity": "sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==", "dev": true, "license": "MIT", "dependencies": { @@ -12943,8 +11278,6 @@ }, "node_modules/is-fullwidth-code-point": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", - "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", "license": "MIT", "engines": { "node": ">=8" @@ -12952,8 +11285,6 @@ }, "node_modules/is-generator-fn": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-generator-fn/-/is-generator-fn-2.1.0.tgz", - "integrity": "sha512-cTIB4yPYL/Grw0EaSzASzg6bBy9gqCofvWN8okThAYIxKJZC+udlRAmGbM0XLeniEJSs8uEgHPGuHSe1XsOLSQ==", "dev": true, "license": "MIT", "engines": { @@ -12962,8 +11293,6 @@ }, "node_modules/is-generator-function": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-generator-function/-/is-generator-function-1.1.0.tgz", - "integrity": "sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==", "license": "MIT", "dependencies": { "call-bound": "^1.0.3", @@ -12980,8 +11309,6 @@ }, "node_modules/is-glob": { "version": "4.0.3", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", - "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", "license": "MIT", "dependencies": { "is-extglob": "^2.1.1" @@ -12992,8 +11319,6 @@ }, "node_modules/is-hexadecimal": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-1.0.4.tgz", - "integrity": "sha512-gyPJuv83bHMpocVYoqof5VDiZveEoGoFL8m3BXNb2VW8Xs+rz9kqO8LOQ5DH6EsuvilT1ApazU0pyl+ytbPtlw==", "license": "MIT", "funding": { "type": "github", @@ -13002,8 +11327,6 @@ }, "node_modules/is-map": { "version": "2.0.3", - "resolved": "https://registry.npmjs.org/is-map/-/is-map-2.0.3.tgz", - "integrity": "sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==", "dev": true, "license": "MIT", "engines": { @@ -13015,8 +11338,6 @@ }, "node_modules/is-number": { "version": "7.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", - "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", "license": "MIT", "engines": { "node": ">=0.12.0" @@ -13024,8 +11345,6 @@ }, "node_modules/is-number-object": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.1.1.tgz", - "integrity": "sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==", "dev": true, "license": "MIT", "dependencies": { @@ -13041,8 +11360,6 @@ }, "node_modules/is-path-inside": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-3.0.3.tgz", - "integrity": "sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ==", "dev": true, "license": "MIT", "engines": { @@ -13051,8 +11368,6 @@ }, "node_modules/is-plain-obj": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz", - "integrity": "sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==", "license": "MIT", "engines": { "node": ">=12" @@ -13063,8 +11378,6 @@ }, "node_modules/is-plain-object": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-5.0.0.tgz", - "integrity": "sha512-VRSzKkbMm5jMDoKLbltAkFQ5Qr7VDiTFGXxYFXXowVj387GeGNOCsOH6Msy00SGZ3Fp84b1Naa1psqgcCIEP5Q==", "license": "MIT", "engines": { "node": ">=0.10.0" @@ -13072,14 +11385,10 @@ }, "node_modules/is-promise": { "version": "2.2.2", - "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.2.2.tgz", - "integrity": "sha512-+lP4/6lKUBfQjZ2pdxThZvLUAafmZb8OAxFb8XXtiQmS35INgr85hdOGoEs124ez1FCnZJt6jau/T+alh58QFQ==", "license": "MIT" }, "node_modules/is-regex": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.2.1.tgz", - "integrity": "sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==", "license": "MIT", "dependencies": { "call-bound": "^1.0.2", @@ -13096,8 +11405,6 @@ }, "node_modules/is-set": { "version": "2.0.3", - "resolved": "https://registry.npmjs.org/is-set/-/is-set-2.0.3.tgz", - "integrity": "sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==", "dev": true, "license": "MIT", "engines": { @@ -13109,8 +11416,6 @@ }, "node_modules/is-shared-array-buffer": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.4.tgz", - "integrity": "sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==", "dev": true, "license": "MIT", "dependencies": { @@ -13125,8 +11430,7 @@ }, "node_modules/is-stream": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", - "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", + "dev": true, "license": "MIT", "engines": { "node": ">=8" @@ -13137,8 +11441,6 @@ }, "node_modules/is-string": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.1.1.tgz", - "integrity": "sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==", "dev": true, "license": "MIT", "dependencies": { @@ -13154,8 +11456,6 @@ }, "node_modules/is-symbol": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.1.1.tgz", - "integrity": "sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==", "dev": true, "license": "MIT", "dependencies": { @@ -13172,8 +11472,6 @@ }, "node_modules/is-typed-array": { "version": "1.1.15", - "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.15.tgz", - "integrity": "sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==", "license": "MIT", "dependencies": { "which-typed-array": "^1.1.16" @@ -13187,8 +11485,6 @@ }, "node_modules/is-weakmap": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/is-weakmap/-/is-weakmap-2.0.2.tgz", - "integrity": "sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==", "dev": true, "license": "MIT", "engines": { @@ -13200,8 +11496,6 @@ }, "node_modules/is-weakref": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-weakref/-/is-weakref-1.1.0.tgz", - "integrity": "sha512-SXM8Nwyys6nT5WP6pltOwKytLV7FqQ4UiibxVmW+EIosHcmCqkkjViTb5SNssDlkCiEYRP1/pdWUKVvZBmsR2Q==", "dev": true, "license": "MIT", "dependencies": { @@ -13216,8 +11510,6 @@ }, "node_modules/is-weakset": { "version": "2.0.4", - "resolved": "https://registry.npmjs.org/is-weakset/-/is-weakset-2.0.4.tgz", - "integrity": "sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==", "dev": true, "license": "MIT", "dependencies": { @@ -13233,8 +11525,6 @@ }, "node_modules/is-what": { "version": "4.1.16", - "resolved": "https://registry.npmjs.org/is-what/-/is-what-4.1.16.tgz", - "integrity": "sha512-ZhMwEosbFJkA0YhFnNDgTM4ZxDRsS6HqTo7qsZM08fehyRYIYa0yHu5R6mgo1n/8MgaPBXiPimPD77baVFYg+A==", "license": "MIT", "engines": { "node": ">=12.13" @@ -13244,15 +11534,13 @@ } }, "node_modules/isarray": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", - "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", + "integrity": "sha512-D2S+3GLxWH+uhrNEcoh/fnmYeP8E8/zHl644d/jdA0g2uyXvy3sb0qxotE+ne0LtccHknQzWwZEzhak7oJ0COQ==", "license": "MIT" }, "node_modules/isexe": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", "license": "ISC" }, "node_modules/iso-url": { @@ -13275,8 +11563,6 @@ }, "node_modules/istanbul-lib-coverage": { "version": "3.2.2", - "resolved": "https://registry.npmjs.org/istanbul-lib-coverage/-/istanbul-lib-coverage-3.2.2.tgz", - "integrity": "sha512-O8dpsF+r0WV/8MNRKfnmrtCWhuKjxrq2w+jpzBL5UZKTi2LeVWnWOmWRxFlesJONmc+wLAGvKQZEOanko0LFTg==", "dev": true, "license": "BSD-3-Clause", "engines": { @@ -13285,8 +11571,6 @@ }, "node_modules/istanbul-lib-instrument": { "version": "6.0.3", - "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-6.0.3.tgz", - "integrity": "sha512-Vtgk7L/R2JHyyGW07spoFlB8/lpjiOLTjMdms6AFMraYt3BaJauod/NGrfnVG/y4Ix1JEuMRPDPEj2ua+zz1/Q==", "dev": true, "license": "BSD-3-Clause", "dependencies": { @@ -13302,8 +11586,6 @@ }, "node_modules/istanbul-lib-instrument/node_modules/semver": { "version": "7.7.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.2.tgz", - "integrity": "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==", "dev": true, "license": "ISC", "bin": { @@ -13315,8 +11597,6 @@ }, "node_modules/istanbul-lib-report": { "version": "3.0.1", - "resolved": "https://registry.npmjs.org/istanbul-lib-report/-/istanbul-lib-report-3.0.1.tgz", - "integrity": "sha512-GCfE1mtsHGOELCU8e/Z7YWzpmybrx/+dSTfLrvY8qRmaY6zXTKWn6WQIjaAFw069icm6GVMNkgu0NzI4iPZUNw==", "dev": true, "license": "BSD-3-Clause", "dependencies": { @@ -13330,8 +11610,6 @@ }, "node_modules/istanbul-lib-source-maps": { "version": "5.0.6", - "resolved": "https://registry.npmjs.org/istanbul-lib-source-maps/-/istanbul-lib-source-maps-5.0.6.tgz", - "integrity": "sha512-yg2d+Em4KizZC5niWhQaIomgf5WlL4vOOjZ5xGCmF8SnPE/mDWWXgvRExdcpCgh9lLRRa1/fSYp2ymmbJ1pI+A==", "dev": true, "license": "BSD-3-Clause", "dependencies": { @@ -13345,8 +11623,6 @@ }, "node_modules/istanbul-reports": { "version": "3.2.0", - "resolved": "https://registry.npmjs.org/istanbul-reports/-/istanbul-reports-3.2.0.tgz", - "integrity": "sha512-HGYWWS/ehqTV3xN10i23tkPkpH46MLCIMFNCaaKNavAXTF1RkqxawEPtnjnGZ6XKSInBKkiOA5BKS+aZiY3AvA==", "dev": true, "license": "BSD-3-Clause", "dependencies": { @@ -13359,8 +11635,6 @@ }, "node_modules/iterator.prototype": { "version": "1.1.5", - "resolved": "https://registry.npmjs.org/iterator.prototype/-/iterator.prototype-1.1.5.tgz", - "integrity": "sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==", "dev": true, "license": "MIT", "dependencies": { @@ -13377,8 +11651,6 @@ }, "node_modules/its-fine": { "version": "1.2.5", - "resolved": "https://registry.npmjs.org/its-fine/-/its-fine-1.2.5.tgz", - "integrity": "sha512-fXtDA0X0t0eBYAGLVM5YsgJGsJ5jEmqZEPrGbzdf5awjv0xE7nqv3TVnvtUF060Tkes15DbDAKW/I48vsb6SyA==", "license": "MIT", "dependencies": { "@types/react-reconciler": "^0.28.0" @@ -13389,8 +11661,6 @@ }, "node_modules/its-fine/node_modules/@types/react-reconciler": { "version": "0.28.9", - "resolved": "https://registry.npmjs.org/@types/react-reconciler/-/react-reconciler-0.28.9.tgz", - "integrity": "sha512-HHM3nxyUZ3zAylX8ZEyrDNd2XZOnQ0D5XfunJF5FLQnZbHHYq4UWvW1QfelQNXv1ICNkwYhfxjwfnqivYB6bFg==", "license": "MIT", "peerDependencies": { "@types/react": "*" @@ -13398,8 +11668,6 @@ }, "node_modules/jackspeak": { "version": "2.3.6", - "resolved": "https://registry.npmjs.org/jackspeak/-/jackspeak-2.3.6.tgz", - "integrity": "sha512-N3yCS/NegsOBokc8GAdM8UcmfsKiSS8cipheD/nivzr700H+nsMOxJjQnvwOcRYVuFkdH0wGUvW2WbXGmrZGbQ==", "license": "BlueOak-1.0.0", "dependencies": { "@isaacs/cliui": "^8.0.2" @@ -13416,8 +11684,6 @@ }, "node_modules/jest": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest/-/jest-30.1.3.tgz", - "integrity": "sha512-Ry+p2+NLk6u8Agh5yVqELfUJvRfV51hhVBRIB5yZPY7mU0DGBmOuFG5GebZbMbm86cdQNK0fhJuDX8/1YorISQ==", "dev": true, "license": "MIT", "dependencies": { @@ -13443,8 +11709,6 @@ }, "node_modules/jest-changed-files": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/jest-changed-files/-/jest-changed-files-30.0.5.tgz", - "integrity": "sha512-bGl2Ntdx0eAwXuGpdLdVYVr5YQHnSZlQ0y9HVDu565lCUAe9sj6JOtBbMmBBikGIegne9piDDIOeiLVoqTkz4A==", "dev": true, "license": "MIT", "dependencies": { @@ -13458,8 +11722,6 @@ }, "node_modules/jest-circus": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest-circus/-/jest-circus-30.1.3.tgz", - "integrity": "sha512-Yf3dnhRON2GJT4RYzM89t/EXIWNxKTpWTL9BfF3+geFetWP4XSvJjiU1vrWplOiUkmq8cHLiwuhz+XuUp9DscA==", "dev": true, "license": "MIT", "dependencies": { @@ -13490,8 +11752,6 @@ }, "node_modules/jest-circus/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -13503,8 +11763,6 @@ }, "node_modules/jest-circus/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -13518,15 +11776,11 @@ }, "node_modules/jest-circus/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/jest-cli": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest-cli/-/jest-cli-30.1.3.tgz", - "integrity": "sha512-G8E2Ol3OKch1DEeIBl41NP7OiC6LBhfg25Btv+idcusmoUSpqUkbrneMqbW9lVpI/rCKb/uETidb7DNteheuAQ==", "dev": true, "license": "MIT", "dependencies": { @@ -13558,8 +11812,6 @@ }, "node_modules/jest-cli/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -13571,8 +11823,6 @@ }, "node_modules/jest-cli/node_modules/jest-config": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest-config/-/jest-config-30.1.3.tgz", - "integrity": "sha512-M/f7gqdQEPgZNA181Myz+GXCe8jXcJsGjCMXUzRj22FIXsZOyHNte84e0exntOvdPaeh9tA0w+B8qlP2fAezfw==", "dev": true, "license": "MIT", "dependencies": { @@ -13623,8 +11873,6 @@ }, "node_modules/jest-cli/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -13638,15 +11886,11 @@ }, "node_modules/jest-cli/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/jest-diff": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-30.1.2.tgz", - "integrity": "sha512-4+prq+9J61mOVXCa4Qp8ZjavdxzrWQXrI80GNxP8f4tkI2syPuPrJgdRPZRrfUTRvIoUwcmNLbqEJy9W800+NQ==", "dev": true, "license": "MIT", "dependencies": { @@ -13661,8 +11905,6 @@ }, "node_modules/jest-diff/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -13674,8 +11916,6 @@ }, "node_modules/jest-diff/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -13689,15 +11929,11 @@ }, "node_modules/jest-diff/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/jest-docblock": { "version": "30.0.1", - "resolved": "https://registry.npmjs.org/jest-docblock/-/jest-docblock-30.0.1.tgz", - "integrity": "sha512-/vF78qn3DYphAaIc3jy4gA7XSAz167n9Bm/wn/1XhTLW7tTBIzXtCJpb/vcmc73NIIeeohCbdL94JasyXUZsGA==", "dev": true, "license": "MIT", "dependencies": { @@ -13709,8 +11945,6 @@ }, "node_modules/jest-each": { "version": "30.1.0", - "resolved": "https://registry.npmjs.org/jest-each/-/jest-each-30.1.0.tgz", - "integrity": "sha512-A+9FKzxPluqogNahpCv04UJvcZ9B3HamqpDNWNKDjtxVRYB8xbZLFuCr8JAJFpNp83CA0anGQFlpQna9Me+/tQ==", "dev": true, "license": "MIT", "dependencies": { @@ -13726,8 +11960,6 @@ }, "node_modules/jest-each/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -13739,8 +11971,6 @@ }, "node_modules/jest-each/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -13754,15 +11984,11 @@ }, "node_modules/jest-each/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/jest-environment-node": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/jest-environment-node/-/jest-environment-node-30.1.2.tgz", - "integrity": "sha512-w8qBiXtqGWJ9xpJIA98M0EIoq079GOQRQUyse5qg1plShUCQ0Ek1VTTcczqKrn3f24TFAgFtT+4q3aOXvjbsuA==", "dev": true, "license": "MIT", "dependencies": { @@ -13780,8 +12006,6 @@ }, "node_modules/jest-haste-map": { "version": "30.1.0", - "resolved": "https://registry.npmjs.org/jest-haste-map/-/jest-haste-map-30.1.0.tgz", - "integrity": "sha512-JLeM84kNjpRkggcGpQLsV7B8W4LNUWz7oDNVnY1Vjj22b5/fAb3kk3htiD+4Na8bmJmjJR7rBtS2Rmq/NEcADg==", "dev": true, "license": "MIT", "dependencies": { @@ -13805,8 +12029,6 @@ }, "node_modules/jest-leak-detector": { "version": "30.1.0", - "resolved": "https://registry.npmjs.org/jest-leak-detector/-/jest-leak-detector-30.1.0.tgz", - "integrity": "sha512-AoFvJzwxK+4KohH60vRuHaqXfWmeBATFZpzpmzNmYTtmRMiyGPVhkXpBqxUQunw+dQB48bDf4NpUs6ivVbRv1g==", "dev": true, "license": "MIT", "dependencies": { @@ -13819,8 +12041,6 @@ }, "node_modules/jest-leak-detector/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -13832,8 +12052,6 @@ }, "node_modules/jest-leak-detector/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -13847,15 +12065,11 @@ }, "node_modules/jest-leak-detector/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/jest-matcher-utils": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-30.1.2.tgz", - "integrity": "sha512-7ai16hy4rSbDjvPTuUhuV8nyPBd6EX34HkBsBcBX2lENCuAQ0qKCPb/+lt8OSWUa9WWmGYLy41PrEzkwRwoGZQ==", "dev": true, "license": "MIT", "dependencies": { @@ -13870,8 +12084,6 @@ }, "node_modules/jest-matcher-utils/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -13883,8 +12095,6 @@ }, "node_modules/jest-matcher-utils/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -13898,15 +12108,11 @@ }, "node_modules/jest-matcher-utils/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/jest-message-util": { "version": "30.1.0", - "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-30.1.0.tgz", - "integrity": "sha512-HizKDGG98cYkWmaLUHChq4iN+oCENohQLb7Z5guBPumYs+/etonmNFlg1Ps6yN9LTPyZn+M+b/9BbnHx3WTMDg==", "dev": true, "license": "MIT", "dependencies": { @@ -13926,8 +12132,6 @@ }, "node_modules/jest-message-util/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -13939,8 +12143,6 @@ }, "node_modules/jest-message-util/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -13954,15 +12156,11 @@ }, "node_modules/jest-message-util/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/jest-mock": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/jest-mock/-/jest-mock-30.0.5.tgz", - "integrity": "sha512-Od7TyasAAQX/6S+QCbN6vZoWOMwlTtzzGuxJku1GhGanAjz9y+QsQkpScDmETvdc9aSXyJ/Op4rhpMYBWW91wQ==", "dev": true, "license": "MIT", "dependencies": { @@ -13976,8 +12174,6 @@ }, "node_modules/jest-pnp-resolver": { "version": "1.2.3", - "resolved": "https://registry.npmjs.org/jest-pnp-resolver/-/jest-pnp-resolver-1.2.3.tgz", - "integrity": "sha512-+3NpwQEnRoIBtx4fyhblQDPgJI0H1IEIkX7ShLUjPGA7TtUTvI1oiKi3SR4oBR0hQhQR80l4WAe5RrXBwWMA8w==", "dev": true, "license": "MIT", "engines": { @@ -13994,8 +12190,6 @@ }, "node_modules/jest-regex-util": { "version": "30.0.1", - "resolved": "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-30.0.1.tgz", - "integrity": "sha512-jHEQgBXAgc+Gh4g0p3bCevgRCVRkB4VB70zhoAE48gxeSr1hfUOsM/C2WoJgVL7Eyg//hudYENbm3Ne+/dRVVA==", "dev": true, "license": "MIT", "engines": { @@ -14004,8 +12198,6 @@ }, "node_modules/jest-resolve": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest-resolve/-/jest-resolve-30.1.3.tgz", - "integrity": "sha512-DI4PtTqzw9GwELFS41sdMK32Ajp3XZQ8iygeDMWkxlRhm7uUTOFSZFVZABFuxr0jvspn8MAYy54NxZCsuCTSOw==", "dev": true, "license": "MIT", "dependencies": { @@ -14024,8 +12216,6 @@ }, "node_modules/jest-resolve-dependencies": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest-resolve-dependencies/-/jest-resolve-dependencies-30.1.3.tgz", - "integrity": "sha512-DNfq3WGmuRyHRHfEet+Zm3QOmVFtIarUOQHHryKPc0YL9ROfgWZxl4+aZq/VAzok2SS3gZdniP+dO4zgo59hBg==", "dev": true, "license": "MIT", "dependencies": { @@ -14038,8 +12228,6 @@ }, "node_modules/jest-runner": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest-runner/-/jest-runner-30.1.3.tgz", - "integrity": "sha512-dd1ORcxQraW44Uz029TtXj85W11yvLpDuIzNOlofrC8GN+SgDlgY4BvyxJiVeuabA1t6idjNbX59jLd2oplOGQ==", "dev": true, "license": "MIT", "dependencies": { @@ -14072,8 +12260,6 @@ }, "node_modules/jest-runtime": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest-runtime/-/jest-runtime-30.1.3.tgz", - "integrity": "sha512-WS8xgjuNSphdIGnleQcJ3AKE4tBKOVP+tKhCD0u+Tb2sBmsU8DxfbBpZX7//+XOz81zVs4eFpJQwBNji2Y07DA==", "dev": true, "license": "MIT", "dependencies": { @@ -14106,8 +12292,6 @@ }, "node_modules/jest-runtime/node_modules/strip-bom": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-4.0.0.tgz", - "integrity": "sha512-3xurFv5tEgii33Zi8Jtp55wEIILR9eh34FAW00PZf+JnSsTmV/ioewSgQl97JHvgjoRGwPShsWm+IdrxB35d0w==", "dev": true, "license": "MIT", "engines": { @@ -14116,8 +12300,6 @@ }, "node_modules/jest-snapshot": { "version": "30.1.2", - "resolved": "https://registry.npmjs.org/jest-snapshot/-/jest-snapshot-30.1.2.tgz", - "integrity": "sha512-4q4+6+1c8B6Cy5pGgFvjDy/Pa6VYRiGu0yQafKkJ9u6wQx4G5PqI2QR6nxTl43yy7IWsINwz6oT4o6tD12a8Dg==", "dev": true, "license": "MIT", "dependencies": { @@ -14149,8 +12331,6 @@ }, "node_modules/jest-snapshot/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -14162,8 +12342,6 @@ }, "node_modules/jest-snapshot/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -14177,15 +12355,11 @@ }, "node_modules/jest-snapshot/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/jest-snapshot/node_modules/semver": { "version": "7.7.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.2.tgz", - "integrity": "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==", "dev": true, "license": "ISC", "bin": { @@ -14197,8 +12371,6 @@ }, "node_modules/jest-util": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-30.0.5.tgz", - "integrity": "sha512-pvyPWssDZR0FlfMxCBoc0tvM8iUEskaRFALUtGQYzVEAqisAztmy+R8LnU14KT4XA0H/a5HMVTXat1jLne010g==", "dev": true, "license": "MIT", "dependencies": { @@ -14215,8 +12387,6 @@ }, "node_modules/jest-util/node_modules/picomatch": { "version": "4.0.3", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.3.tgz", - "integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==", "dev": true, "license": "MIT", "engines": { @@ -14228,8 +12398,6 @@ }, "node_modules/jest-validate": { "version": "30.1.0", - "resolved": "https://registry.npmjs.org/jest-validate/-/jest-validate-30.1.0.tgz", - "integrity": "sha512-7P3ZlCFW/vhfQ8pE7zW6Oi4EzvuB4sgR72Q1INfW9m0FGo0GADYlPwIkf4CyPq7wq85g+kPMtPOHNAdWHeBOaA==", "dev": true, "license": "MIT", "dependencies": { @@ -14246,8 +12414,6 @@ }, "node_modules/jest-validate/node_modules/ansi-styles": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "dev": true, "license": "MIT", "engines": { @@ -14259,8 +12425,6 @@ }, "node_modules/jest-validate/node_modules/camelcase": { "version": "6.3.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", - "integrity": "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==", "dev": true, "license": "MIT", "engines": { @@ -14272,8 +12436,6 @@ }, "node_modules/jest-validate/node_modules/pretty-format": { "version": "30.0.5", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-30.0.5.tgz", - "integrity": "sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==", "dev": true, "license": "MIT", "dependencies": { @@ -14287,15 +12449,11 @@ }, "node_modules/jest-validate/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "dev": true, "license": "MIT" }, "node_modules/jest-watcher": { "version": "30.1.3", - "resolved": "https://registry.npmjs.org/jest-watcher/-/jest-watcher-30.1.3.tgz", - "integrity": "sha512-6jQUZCP1BTL2gvG9E4YF06Ytq4yMb4If6YoQGRR6PpjtqOXSP3sKe2kqwB6SQ+H9DezOfZaSLnmka1NtGm3fCQ==", "dev": true, "license": "MIT", "dependencies": { @@ -14314,8 +12472,6 @@ }, "node_modules/jest-worker": { "version": "30.1.0", - "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-30.1.0.tgz", - "integrity": "sha512-uvWcSjlwAAgIu133Tt77A05H7RIk3Ho8tZL50bQM2AkvLdluw9NG48lRCl3Dt+MOH719n/0nnb5YxUwcuJiKRA==", "dev": true, "license": "MIT", "dependencies": { @@ -14331,8 +12487,6 @@ }, "node_modules/jest-worker/node_modules/supports-color": { "version": "8.1.1", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", - "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", "dev": true, "license": "MIT", "dependencies": { @@ -14347,8 +12501,6 @@ }, "node_modules/jiti": { "version": "1.21.7", - "resolved": "https://registry.npmjs.org/jiti/-/jiti-1.21.7.tgz", - "integrity": "sha512-/imKNG4EbWNrVjoNC/1H5/9GFy+tqjGBHCaSsN+P2RnPqjsLmv6UD3Ej+Kj8nBWaRAwyk7kK5ZUc+OEatnTR3A==", "license": "MIT", "bin": { "jiti": "bin/jiti.js" @@ -14362,8 +12514,6 @@ }, "node_modules/jose": { "version": "5.9.6", - "resolved": "https://registry.npmjs.org/jose/-/jose-5.9.6.tgz", - "integrity": "sha512-AMlnetc9+CV9asI19zHmrgS/WYsWUwCn2R7RzlbJWD7F9eWYUTGyBmU9o6PxngtLGOiDGPRu+Uc4fhKzbpteZQ==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/panva" @@ -14371,20 +12521,14 @@ }, "node_modules/js-file-download": { "version": "0.4.12", - "resolved": "https://registry.npmjs.org/js-file-download/-/js-file-download-0.4.12.tgz", - "integrity": "sha512-rML+NkoD08p5Dllpjo0ffy4jRHeY6Zsapvr/W86N7E0yuzAO6qa5X9+xog6zQNlH102J7IXljNY2FtS6Lj3ucg==", "license": "MIT" }, "node_modules/js-tokens": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", - "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", "license": "MIT" }, "node_modules/js-yaml": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", - "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", "license": "MIT", "dependencies": { "argparse": "^2.0.1" @@ -14401,8 +12545,6 @@ }, "node_modules/jsesc": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.1.0.tgz", - "integrity": "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==", "license": "MIT", "bin": { "jsesc": "bin/jsesc" @@ -14413,8 +12555,6 @@ }, "node_modules/json-bigint": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-1.0.0.tgz", - "integrity": "sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==", "license": "MIT", "dependencies": { "bignumber.js": "^9.0.0" @@ -14422,36 +12562,25 @@ }, "node_modules/json-buffer": { "version": "3.0.1", - "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", - "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==", "dev": true, "license": "MIT" }, "node_modules/json-parse-even-better-errors": { "version": "2.3.1", - "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", - "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==", - "dev": true, "license": "MIT" }, "node_modules/json-schema-traverse": { "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", "dev": true, "license": "MIT" }, "node_modules/json-stable-stringify-without-jsonify": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", - "integrity": "sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==", "dev": true, "license": "MIT" }, "node_modules/json5": { "version": "2.2.3", - "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", - "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", "license": "MIT", "bin": { "json5": "lib/cli.js" @@ -14462,8 +12591,6 @@ }, "node_modules/jsonld": { "version": "8.3.3", - "resolved": "https://registry.npmjs.org/jsonld/-/jsonld-8.3.3.tgz", - "integrity": "sha512-9YcilrF+dLfg9NTEof/mJLMtbdX1RJ8dbWtJgE00cMOIohb1lIyJl710vFiTaiHTl6ZYODJuBd32xFvUhmv3kg==", "license": "BSD-3-Clause", "dependencies": { "@digitalbazaar/http-client": "^3.4.1", @@ -14477,8 +12604,6 @@ }, "node_modules/jsonld/node_modules/lru-cache": { "version": "6.0.0", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", - "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", "license": "ISC", "dependencies": { "yallist": "^4.0.0" @@ -14489,14 +12614,10 @@ }, "node_modules/jsonld/node_modules/yallist": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", "license": "ISC" }, "node_modules/jsonwebtoken": { "version": "9.0.2", - "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-9.0.2.tgz", - "integrity": "sha512-PRp66vJ865SSqOlgqS8hujT5U4AOgMfhrwYIuIhfKaoSCZcirrmASQr8CX7cUg+RMih+hgznrjp99o+W4pJLHQ==", "license": "MIT", "dependencies": { "jws": "^3.2.2", @@ -14517,8 +12638,6 @@ }, "node_modules/jsonwebtoken/node_modules/semver": { "version": "7.7.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.2.tgz", - "integrity": "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==", "license": "ISC", "bin": { "semver": "bin/semver.js" @@ -14529,8 +12648,6 @@ }, "node_modules/jsx-ast-utils": { "version": "3.3.5", - "resolved": "https://registry.npmjs.org/jsx-ast-utils/-/jsx-ast-utils-3.3.5.tgz", - "integrity": "sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==", "dev": true, "license": "MIT", "dependencies": { @@ -14557,8 +12674,6 @@ }, "node_modules/jwa": { "version": "1.4.2", - "resolved": "https://registry.npmjs.org/jwa/-/jwa-1.4.2.tgz", - "integrity": "sha512-eeH5JO+21J78qMvTIDdBXidBd6nG2kZjg5Ohz/1fpa28Z4CcsWUzJ1ZZyFq/3z3N17aZy+ZuBoHljASbL1WfOw==", "license": "MIT", "dependencies": { "buffer-equal-constant-time": "^1.0.1", @@ -14568,8 +12683,6 @@ }, "node_modules/jws": { "version": "3.2.2", - "resolved": "https://registry.npmjs.org/jws/-/jws-3.2.2.tgz", - "integrity": "sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA==", "license": "MIT", "dependencies": { "jwa": "^1.4.1", @@ -14616,8 +12729,6 @@ }, "node_modules/kapsule": { "version": "1.16.0", - "resolved": "https://registry.npmjs.org/kapsule/-/kapsule-1.16.0.tgz", - "integrity": "sha512-4f/z/Luu0cEXmagCwaFyzvfZai2HKgB4CQLwmsMUA+jlUbW94HfFSX+TWZxzWoMSO6b6aR+FD2Xd5z88VYZJTw==", "license": "MIT", "dependencies": { "lodash-es": "4" @@ -14628,8 +12739,6 @@ }, "node_modules/keyv": { "version": "4.5.4", - "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz", - "integrity": "sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==", "dev": true, "license": "MIT", "dependencies": { @@ -14638,8 +12747,6 @@ }, "node_modules/ky": { "version": "0.33.3", - "resolved": "https://registry.npmjs.org/ky/-/ky-0.33.3.tgz", - "integrity": "sha512-CasD9OCEQSFIam2U8efFK81Yeg8vNMTBUqtMOHlrcWQHqUX3HeCl9Dr31u4toV7emlH8Mymk5+9p0lL6mKb/Xw==", "license": "MIT", "engines": { "node": ">=14.16" @@ -14650,8 +12757,6 @@ }, "node_modules/ky-universal": { "version": "0.11.0", - "resolved": "https://registry.npmjs.org/ky-universal/-/ky-universal-0.11.0.tgz", - "integrity": "sha512-65KyweaWvk+uKKkCrfAf+xqN2/epw1IJDtlyCPxYffFCMR8u1sp2U65NtWpnozYfZxQ6IUzIlvUcw+hQ82U2Xw==", "license": "MIT", "dependencies": { "abort-controller": "^3.0.0", @@ -14675,8 +12780,6 @@ }, "node_modules/ky-universal/node_modules/node-fetch": { "version": "3.3.2", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-3.3.2.tgz", - "integrity": "sha512-dRB78srN/l6gqWulah9SrxeYnxeddIG30+GOqK/9OlLVyLg3HPnr6SqOWTWOXKRwC2eGYCkZ59NNuSgvSrpgOA==", "license": "MIT", "dependencies": { "data-uri-to-buffer": "^4.0.0", @@ -14693,15 +12796,11 @@ }, "node_modules/language-subtag-registry": { "version": "0.3.23", - "resolved": "https://registry.npmjs.org/language-subtag-registry/-/language-subtag-registry-0.3.23.tgz", - "integrity": "sha512-0K65Lea881pHotoGEa5gDlMxt3pctLi2RplBb7Ezh4rRdLEOtgi7n4EwK9lamnUCkKBqaeKRVebTq6BAxSkpXQ==", "dev": true, "license": "CC0-1.0" }, "node_modules/language-tags": { "version": "1.0.9", - "resolved": "https://registry.npmjs.org/language-tags/-/language-tags-1.0.9.tgz", - "integrity": "sha512-MbjN408fEndfiQXbFQ1vnd+1NoLDsnQW41410oQBXiyXDMYH5z505juWa4KUE1LqxRC7DgOgZDbKLxHIwm27hA==", "dev": true, "license": "MIT", "dependencies": { @@ -14719,8 +12818,6 @@ }, "node_modules/leven": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz", - "integrity": "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==", "dev": true, "license": "MIT", "engines": { @@ -14729,8 +12826,6 @@ }, "node_modules/levn": { "version": "0.4.1", - "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", - "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", "dev": true, "license": "MIT", "dependencies": { @@ -14758,8 +12853,6 @@ }, "node_modules/lie": { "version": "3.3.0", - "resolved": "https://registry.npmjs.org/lie/-/lie-3.3.0.tgz", - "integrity": "sha512-UaiMJzeWRlEujzAuw5LokY1L5ecNQYZKfmyZ9L7wDHb/p5etKaxXhohBcrw0EYby+G/NA52vRSN4N39dxHAIwQ==", "license": "MIT", "dependencies": { "immediate": "~3.0.5" @@ -14767,8 +12860,6 @@ }, "node_modules/lilconfig": { "version": "3.1.3", - "resolved": "https://registry.npmjs.org/lilconfig/-/lilconfig-3.1.3.tgz", - "integrity": "sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw==", "license": "MIT", "engines": { "node": ">=14" @@ -14784,8 +12875,6 @@ }, "node_modules/lines-and-columns": { "version": "1.2.4", - "resolved": "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.2.4.tgz", - "integrity": "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==", "license": "MIT" }, "node_modules/load-ip-set": { @@ -14821,8 +12910,6 @@ }, "node_modules/locate-path": { "version": "6.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz", - "integrity": "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==", "dev": true, "license": "MIT", "dependencies": { @@ -14837,102 +12924,68 @@ }, "node_modules/lodash": { "version": "4.17.21", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", - "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", "license": "MIT" }, "node_modules/lodash-es": { "version": "4.17.21", - "resolved": "https://registry.npmjs.org/lodash-es/-/lodash-es-4.17.21.tgz", - "integrity": "sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw==", "license": "MIT" }, "node_modules/lodash.debounce": { "version": "4.0.8", - "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", - "integrity": "sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==", "license": "MIT" }, "node_modules/lodash.get": { "version": "4.4.2", - "resolved": "https://registry.npmjs.org/lodash.get/-/lodash.get-4.4.2.tgz", - "integrity": "sha512-z+Uw/vLuy6gQe8cfaFWD7p0wVv8fJl3mbzXh33RS+0oW2wvUqiRXiQ69gLWSLpgB5/6sU+r6BlQR0MBILadqTQ==", - "deprecated": "This package is deprecated. Use the optional chaining (?.) operator instead.", "license": "MIT" }, "node_modules/lodash.includes": { "version": "4.3.0", - "resolved": "https://registry.npmjs.org/lodash.includes/-/lodash.includes-4.3.0.tgz", - "integrity": "sha512-W3Bx6mdkRTGtlJISOvVD/lbqjTlPPUDTMnlXZFnVwi9NKJ6tiAk6LVdlhZMm17VZisqhKcgzpO5Wz91PCt5b0w==", "license": "MIT" }, "node_modules/lodash.isboolean": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz", - "integrity": "sha512-Bz5mupy2SVbPHURB98VAcw+aHh4vRV5IPNhILUCsOzRmsTmSQ17jIuqopAentWoehktxGd9e/hbIXq980/1QJg==", "license": "MIT" }, "node_modules/lodash.isequal": { "version": "4.5.0", - "resolved": "https://registry.npmjs.org/lodash.isequal/-/lodash.isequal-4.5.0.tgz", - "integrity": "sha512-pDo3lu8Jhfjqls6GkMgpahsF9kCyayhgykjyLMNFTKWrpVdAQtYyB4muAMWozBB4ig/dtWAmsMxLEI8wuz+DYQ==", - "deprecated": "This package is deprecated. Use require('node:util').isDeepStrictEqual instead.", "license": "MIT" }, "node_modules/lodash.isinteger": { "version": "4.0.4", - "resolved": "https://registry.npmjs.org/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz", - "integrity": "sha512-DBwtEWN2caHQ9/imiNeEA5ys1JoRtRfY3d7V9wkqtbycnAmTvRRmbHKDV4a0EYc678/dia0jrte4tjYwVBaZUA==", "license": "MIT" }, "node_modules/lodash.isnumber": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz", - "integrity": "sha512-QYqzpfwO3/CWf3XP+Z+tkQsfaLL/EnUlXWVkIk5FUPc4sBdTehEqZONuyRt2P67PXAk+NXmTBcc97zw9t1FQrw==", "license": "MIT" }, "node_modules/lodash.isplainobject": { "version": "4.0.6", - "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", - "integrity": "sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==", "license": "MIT" }, "node_modules/lodash.isstring": { "version": "4.0.1", - "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", - "integrity": "sha512-0wJxfxH1wgO3GrbuP+dTTk7op+6L41QCXbGINEmD+ny/G/eCqGzxyCsh7159S+mgDDcoarnBw6PC1PS5+wUGgw==", "license": "MIT" }, "node_modules/lodash.memoize": { "version": "4.1.2", - "resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-4.1.2.tgz", - "integrity": "sha512-t7j+NzmgnQzTAYXcsHYLgimltOV1MXHtlOWf6GjL9Kj8GK5FInw5JotxvbOs+IvV1/Dzo04/fCGfLVs7aXb4Ag==", "dev": true, "license": "MIT" }, "node_modules/lodash.merge": { "version": "4.6.2", - "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", - "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", "dev": true, "license": "MIT" }, "node_modules/lodash.mergewith": { "version": "4.6.2", - "resolved": "https://registry.npmjs.org/lodash.mergewith/-/lodash.mergewith-4.6.2.tgz", - "integrity": "sha512-GK3g5RPZWTRSeLSpgP8Xhra+pnjBC56q9FZYe1d5RN3TJ35dbkGy3YqBSMbyCrlbi+CM9Z3Jk5yTL7RCsqboyQ==", "license": "MIT" }, "node_modules/lodash.once": { "version": "4.1.1", - "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz", - "integrity": "sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg==", "license": "MIT" }, "node_modules/longest-streak": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-3.1.0.tgz", - "integrity": "sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==", "license": "MIT", "funding": { "type": "github", @@ -14941,8 +12994,6 @@ }, "node_modules/loose-envify": { "version": "1.4.0", - "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", - "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", "license": "MIT", "dependencies": { "js-tokens": "^3.0.0 || ^4.0.0" @@ -14953,8 +13004,6 @@ }, "node_modules/lowlight": { "version": "1.20.0", - "resolved": "https://registry.npmjs.org/lowlight/-/lowlight-1.20.0.tgz", - "integrity": "sha512-8Ktj+prEb1RoCPkEOrPMYUN/nCggB7qAWe3a7OpMjWQkh3l2RD5wKRQ+o8Q8YuI9RG/xs95waaI/E6ym/7NsTw==", "license": "MIT", "dependencies": { "fault": "^1.0.0", @@ -14979,17 +13028,15 @@ }, "node_modules/lru-cache": { "version": "5.1.1", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", - "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", "license": "ISC", "dependencies": { "yallist": "^3.0.2" } }, "node_modules/lt_donthave": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/lt_donthave/-/lt_donthave-2.0.4.tgz", - "integrity": "sha512-VIKjdxflF8+6vFb3t8LQ4czRYvw6OyxPLDr5YV5qOieu4qwl0wX2DA18WyaHJjBKyKSHXvdo1JcrrUag5MmMiA==", + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/lt_donthave/-/lt_donthave-2.0.6.tgz", + "integrity": "sha512-ZVcaRbZpNB6ugwa5T9gUN0Jg9XGT9cyVjZJvdbN3V27rOQ170rEs//zaQXEQkTCBhh3i/JnCRF472KWHJu74Yg==", "funding": [ { "type": "github", @@ -15015,8 +13062,6 @@ }, "node_modules/lucide-react": { "version": "0.439.0", - "resolved": "https://registry.npmjs.org/lucide-react/-/lucide-react-0.439.0.tgz", - "integrity": "sha512-PafSWvDTpxdtNEndS2HIHxcNAbd54OaqSYJO90/b63rab2HWYqDbH194j0i82ZFdWOAcf0AHinRykXRRK2PJbw==", "license": "ISC", "peerDependencies": { "react": "^16.5.1 || ^17.0.0 || ^18.0.0 || ^19.0.0-rc" @@ -15024,8 +13069,6 @@ }, "node_modules/maath": { "version": "0.10.8", - "resolved": "https://registry.npmjs.org/maath/-/maath-0.10.8.tgz", - "integrity": "sha512-tRvbDF0Pgqz+9XUa4jjfgAQ8/aPKmQdWXilFu2tMy4GWj4NOsx99HlULO4IeREfbO3a0sA145DZYyvXPkybm0g==", "license": "MIT", "peerDependencies": { "@types/three": ">=0.134.0", @@ -15062,8 +13105,6 @@ }, "node_modules/make-dir": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-4.0.0.tgz", - "integrity": "sha512-hXdUTZYIVOt1Ex//jAQi+wTZZpUpwBj/0QsOzqegb3rGMMeJiSEu5xLHnYfBrRV4RH2+OCSOO95Is/7x1WJ4bw==", "dev": true, "license": "MIT", "dependencies": { @@ -15078,8 +13119,6 @@ }, "node_modules/make-dir/node_modules/semver": { "version": "7.7.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.2.tgz", - "integrity": "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==", "dev": true, "license": "ISC", "bin": { @@ -15091,15 +13130,11 @@ }, "node_modules/make-error": { "version": "1.3.6", - "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.6.tgz", - "integrity": "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==", "dev": true, "license": "ISC" }, "node_modules/makeerror": { "version": "1.0.12", - "resolved": "https://registry.npmjs.org/makeerror/-/makeerror-1.0.12.tgz", - "integrity": "sha512-JmqCvUhmt43madlpFzG4BQzG2Z3m6tvQDNKdClZnO3VbIudJYmxsT0FNJMeiB2+JTSlTQTSbU8QdesVmwJcmLg==", "dev": true, "license": "BSD-3-Clause", "dependencies": { @@ -15108,8 +13143,6 @@ }, "node_modules/markdown-table": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/markdown-table/-/markdown-table-3.0.4.tgz", - "integrity": "sha512-wiYz4+JrLyb/DqW2hkFJxP7Vd7JuTDm77fvbM8VfEQdmSMqcImWeeRbHwZjBjIFki/VaMK2BhFi7oUUZeM5bqw==", "license": "MIT", "funding": { "type": "github", @@ -15118,8 +13151,6 @@ }, "node_modules/math-intrinsics": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", - "integrity": "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==", "license": "MIT", "engines": { "node": ">= 0.4" @@ -15138,8 +13169,6 @@ }, "node_modules/mdast-util-find-and-replace": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/mdast-util-find-and-replace/-/mdast-util-find-and-replace-3.0.2.tgz", - "integrity": "sha512-Tmd1Vg/m3Xz43afeNxDIhWRtFZgM2VLyaf4vSTYwudTyeuTneoL3qtWMA5jeLyz/O1vDJmmV4QuScFCA2tBPwg==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -15154,8 +13183,6 @@ }, "node_modules/mdast-util-find-and-replace/node_modules/escape-string-regexp": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-5.0.0.tgz", - "integrity": "sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw==", "license": "MIT", "engines": { "node": ">=12" @@ -15166,8 +13193,6 @@ }, "node_modules/mdast-util-from-markdown": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-2.0.2.tgz", - "integrity": "sha512-uZhTV/8NBuw0WHkPTrCqDOl0zVe1BIng5ZtHoDk49ME1qqcjYmmLmOf0gELgcRMxN4w2iuIeVso5/6QymSrgmA==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -15190,14 +13215,10 @@ }, "node_modules/mdast-util-from-markdown/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/mdast-util-gfm": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm/-/mdast-util-gfm-3.1.0.tgz", - "integrity": "sha512-0ulfdQOM3ysHhCJ1p06l0b0VKlhU0wuQs3thxZQagjcjPrlFRqY215uZGHHJan9GEAXd9MbfPjFJz+qMkVR6zQ==", "license": "MIT", "dependencies": { "mdast-util-from-markdown": "^2.0.0", @@ -15215,8 +13236,6 @@ }, "node_modules/mdast-util-gfm-autolink-literal": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-autolink-literal/-/mdast-util-gfm-autolink-literal-2.0.1.tgz", - "integrity": "sha512-5HVP2MKaP6L+G6YaxPNjuL0BPrq9orG3TsrZ9YXbA3vDw/ACI4MEsnoDpn6ZNm7GnZgtAcONJyPhOP8tNJQavQ==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -15232,8 +13251,6 @@ }, "node_modules/mdast-util-gfm-footnote": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-footnote/-/mdast-util-gfm-footnote-2.1.0.tgz", - "integrity": "sha512-sqpDWlsHn7Ac9GNZQMeUzPQSMzR6Wv0WKRNvQRg0KqHh02fpTz69Qc1QSseNX29bhz1ROIyNyxExfawVKTm1GQ==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -15249,8 +13266,6 @@ }, "node_modules/mdast-util-gfm-strikethrough": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-strikethrough/-/mdast-util-gfm-strikethrough-2.0.0.tgz", - "integrity": "sha512-mKKb915TF+OC5ptj5bJ7WFRPdYtuHv0yTRxK2tJvi+BDqbkiG7h7u/9SI89nRAYcmap2xHQL9D+QG/6wSrTtXg==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -15264,8 +13279,6 @@ }, "node_modules/mdast-util-gfm-table": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-table/-/mdast-util-gfm-table-2.0.0.tgz", - "integrity": "sha512-78UEvebzz/rJIxLvE7ZtDd/vIQ0RHv+3Mh5DR96p7cS7HsBhYIICDBCu8csTNWNO6tBWfqXPWekRuj2FNOGOZg==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -15281,8 +13294,6 @@ }, "node_modules/mdast-util-gfm-task-list-item": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-task-list-item/-/mdast-util-gfm-task-list-item-2.0.0.tgz", - "integrity": "sha512-IrtvNvjxC1o06taBAVJznEnkiHxLFTzgonUdy8hzFVeDun0uTjxxrRGVaNFqkU1wJR3RBPEfsxmU6jDWPofrTQ==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -15297,8 +13308,6 @@ }, "node_modules/mdast-util-mdx-expression": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/mdast-util-mdx-expression/-/mdast-util-mdx-expression-2.0.1.tgz", - "integrity": "sha512-J6f+9hUp+ldTZqKRSg7Vw5V6MqjATc+3E4gf3CFNcuZNWD8XdyI6zQ8GqH7f8169MM6P7hMBRDVGnn7oHB9kXQ==", "license": "MIT", "dependencies": { "@types/estree-jsx": "^1.0.0", @@ -15315,8 +13324,6 @@ }, "node_modules/mdast-util-mdx-expression/node_modules/@types/hast": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", - "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", "license": "MIT", "dependencies": { "@types/unist": "*" @@ -15324,8 +13331,6 @@ }, "node_modules/mdast-util-mdx-jsx": { "version": "3.2.0", - "resolved": "https://registry.npmjs.org/mdast-util-mdx-jsx/-/mdast-util-mdx-jsx-3.2.0.tgz", - "integrity": "sha512-lj/z8v0r6ZtsN/cGNNtemmmfoLAFZnjMbNyLzBafjzikOM+glrjNHPlf6lQDOTccj9n5b0PPihEBbhneMyGs1Q==", "license": "MIT", "dependencies": { "@types/estree-jsx": "^1.0.0", @@ -15348,8 +13353,6 @@ }, "node_modules/mdast-util-mdx-jsx/node_modules/@types/hast": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", - "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", "license": "MIT", "dependencies": { "@types/unist": "*" @@ -15357,14 +13360,10 @@ }, "node_modules/mdast-util-mdx-jsx/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/mdast-util-mdx-jsx/node_modules/character-entities-legacy": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", - "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", "license": "MIT", "funding": { "type": "github", @@ -15373,8 +13372,6 @@ }, "node_modules/mdast-util-mdx-jsx/node_modules/character-reference-invalid": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-2.0.1.tgz", - "integrity": "sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==", "license": "MIT", "funding": { "type": "github", @@ -15383,8 +13380,6 @@ }, "node_modules/mdast-util-mdx-jsx/node_modules/is-alphabetical": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-2.0.1.tgz", - "integrity": "sha512-FWyyY60MeTNyeSRpkM2Iry0G9hpr7/9kD40mD/cGQEuilcZYS4okz8SN2Q6rLCJ8gbCt6fN+rC+6tMGS99LaxQ==", "license": "MIT", "funding": { "type": "github", @@ -15393,8 +13388,6 @@ }, "node_modules/mdast-util-mdx-jsx/node_modules/is-alphanumerical": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-2.0.1.tgz", - "integrity": "sha512-hmbYhX/9MUMF5uh7tOXyK/n0ZvWpad5caBA17GsC6vyuCqaWliRG5K1qS9inmUhEMaOBIW7/whAnSwveW/LtZw==", "license": "MIT", "dependencies": { "is-alphabetical": "^2.0.0", @@ -15407,8 +13400,6 @@ }, "node_modules/mdast-util-mdx-jsx/node_modules/is-decimal": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-2.0.1.tgz", - "integrity": "sha512-AAB9hiomQs5DXWcRB1rqsxGUstbRroFOPPVAomNk/3XHR5JyEZChOyTWe2oayKnsSsr/kcGqF+z6yuH6HHpN0A==", "license": "MIT", "funding": { "type": "github", @@ -15417,8 +13408,6 @@ }, "node_modules/mdast-util-mdx-jsx/node_modules/is-hexadecimal": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-2.0.1.tgz", - "integrity": "sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==", "license": "MIT", "funding": { "type": "github", @@ -15427,8 +13416,6 @@ }, "node_modules/mdast-util-mdx-jsx/node_modules/parse-entities": { "version": "4.0.2", - "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-4.0.2.tgz", - "integrity": "sha512-GG2AQYWoLgL877gQIKeRPGO1xF9+eG1ujIb5soS5gPvLQ1y2o8FL90w2QWNdf9I361Mpp7726c+lj3U0qK1uGw==", "license": "MIT", "dependencies": { "@types/unist": "^2.0.0", @@ -15446,14 +13433,10 @@ }, "node_modules/mdast-util-mdx-jsx/node_modules/parse-entities/node_modules/@types/unist": { "version": "2.0.11", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.11.tgz", - "integrity": "sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==", "license": "MIT" }, "node_modules/mdast-util-mdxjs-esm": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/mdast-util-mdxjs-esm/-/mdast-util-mdxjs-esm-2.0.1.tgz", - "integrity": "sha512-EcmOpxsZ96CvlP03NghtH1EsLtr0n9Tm4lPUJUBccV9RwUOneqSycg19n5HGzCf+10LozMRSObtVr3ee1WoHtg==", "license": "MIT", "dependencies": { "@types/estree-jsx": "^1.0.0", @@ -15470,8 +13453,6 @@ }, "node_modules/mdast-util-mdxjs-esm/node_modules/@types/hast": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", - "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", "license": "MIT", "dependencies": { "@types/unist": "*" @@ -15479,8 +13460,6 @@ }, "node_modules/mdast-util-phrasing": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/mdast-util-phrasing/-/mdast-util-phrasing-4.1.0.tgz", - "integrity": "sha512-TqICwyvJJpBwvGAMZjj4J2n0X8QWp21b9l0o7eXyVJ25YNWYbJDVIyD1bZXE6WtV6RmKJVYmQAKWa0zWOABz2w==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -15493,8 +13472,6 @@ }, "node_modules/mdast-util-to-hast": { "version": "13.2.0", - "resolved": "https://registry.npmjs.org/mdast-util-to-hast/-/mdast-util-to-hast-13.2.0.tgz", - "integrity": "sha512-QGYKEuUsYT9ykKBCMOEDLsU5JRObWQusAolFMeko/tYPufNkRffBAQjIE+99jbA87xv6FgmjLtwjh9wBWajwAA==", "license": "MIT", "dependencies": { "@types/hast": "^3.0.0", @@ -15514,8 +13491,6 @@ }, "node_modules/mdast-util-to-hast/node_modules/@types/hast": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", - "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", "license": "MIT", "dependencies": { "@types/unist": "*" @@ -15523,8 +13498,6 @@ }, "node_modules/mdast-util-to-markdown": { "version": "2.1.2", - "resolved": "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-2.1.2.tgz", - "integrity": "sha512-xj68wMTvGXVOKonmog6LwyJKrYXZPvlwabaryTjLh9LuvovB/KAH+kvi8Gjj+7rJjsFi23nkUxRQv1KqSroMqA==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -15544,14 +13517,10 @@ }, "node_modules/mdast-util-to-markdown/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/mdast-util-to-string": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-4.0.0.tgz", - "integrity": "sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0" @@ -15572,14 +13541,10 @@ }, "node_modules/merge-stream": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", - "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", "license": "MIT" }, "node_modules/merge2": { "version": "1.4.1", - "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", - "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", "license": "MIT", "engines": { "node": ">= 8" @@ -15587,8 +13552,6 @@ }, "node_modules/meshline": { "version": "3.3.1", - "resolved": "https://registry.npmjs.org/meshline/-/meshline-3.3.1.tgz", - "integrity": "sha512-/TQj+JdZkeSUOl5Mk2J7eLcYTLiQm2IDzmlSvYm7ov15anEcDJ92GHqqazxTSreeNgfnYu24kiEvvv0WlbCdFQ==", "license": "MIT", "peerDependencies": { "three": ">=0.137" @@ -15596,14 +13559,10 @@ }, "node_modules/meshoptimizer": { "version": "0.18.1", - "resolved": "https://registry.npmjs.org/meshoptimizer/-/meshoptimizer-0.18.1.tgz", - "integrity": "sha512-ZhoIoL7TNV4s5B6+rx5mC//fw8/POGyNxS/DZyCJeiZ12ScLfVwRE/GfsxwiTkMYYD5DmK2/JXnEVXqL4rF+Sw==", "license": "MIT" }, "node_modules/micromark": { "version": "4.0.2", - "resolved": "https://registry.npmjs.org/micromark/-/micromark-4.0.2.tgz", - "integrity": "sha512-zpe98Q6kvavpCr1NPVSCMebCKfD7CA2NqZ+rykeNhONIJBpc1tFKt9hucLGwha3jNTNI8lHpctWJWoimVF4PfA==", "funding": [ { "type": "GitHub Sponsors", @@ -15637,8 +13596,6 @@ }, "node_modules/micromark-core-commonmark": { "version": "2.0.3", - "resolved": "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-2.0.3.tgz", - "integrity": "sha512-RDBrHEMSxVFLg6xvnXmb1Ayr2WzLAWjeSATAoxwKYJV94TeNavgoIdA0a9ytzDSVzBy2YKFK+emCPOEibLeCrg==", "funding": [ { "type": "GitHub Sponsors", @@ -15671,8 +13628,6 @@ }, "node_modules/micromark-extension-gfm": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm/-/micromark-extension-gfm-3.0.0.tgz", - "integrity": "sha512-vsKArQsicm7t0z2GugkCKtZehqUm31oeGBV/KVSorWSy8ZlNAv7ytjFhvaryUiCUJYqs+NoE6AFhpQvBTM6Q4w==", "license": "MIT", "dependencies": { "micromark-extension-gfm-autolink-literal": "^2.0.0", @@ -15691,8 +13646,6 @@ }, "node_modules/micromark-extension-gfm-autolink-literal": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-autolink-literal/-/micromark-extension-gfm-autolink-literal-2.1.0.tgz", - "integrity": "sha512-oOg7knzhicgQ3t4QCjCWgTmfNhvQbDDnJeVu9v81r7NltNCVmhPy1fJRX27pISafdjL+SVc4d3l48Gb6pbRypw==", "license": "MIT", "dependencies": { "micromark-util-character": "^2.0.0", @@ -15707,8 +13660,6 @@ }, "node_modules/micromark-extension-gfm-footnote": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-footnote/-/micromark-extension-gfm-footnote-2.1.0.tgz", - "integrity": "sha512-/yPhxI1ntnDNsiHtzLKYnE3vf9JZ6cAisqVDauhp4CEHxlb4uoOTxOCJ+9s51bIB8U1N1FJ1RXOKTIlD5B/gqw==", "license": "MIT", "dependencies": { "devlop": "^1.0.0", @@ -15727,8 +13678,6 @@ }, "node_modules/micromark-extension-gfm-strikethrough": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-strikethrough/-/micromark-extension-gfm-strikethrough-2.1.0.tgz", - "integrity": "sha512-ADVjpOOkjz1hhkZLlBiYA9cR2Anf8F4HqZUO6e5eDcPQd0Txw5fxLzzxnEkSkfnD0wziSGiv7sYhk/ktvbf1uw==", "license": "MIT", "dependencies": { "devlop": "^1.0.0", @@ -15745,8 +13694,6 @@ }, "node_modules/micromark-extension-gfm-table": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-table/-/micromark-extension-gfm-table-2.1.1.tgz", - "integrity": "sha512-t2OU/dXXioARrC6yWfJ4hqB7rct14e8f7m0cbI5hUmDyyIlwv5vEtooptH8INkbLzOatzKuVbQmAYcbWoyz6Dg==", "license": "MIT", "dependencies": { "devlop": "^1.0.0", @@ -15762,8 +13709,6 @@ }, "node_modules/micromark-extension-gfm-tagfilter": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-tagfilter/-/micromark-extension-gfm-tagfilter-2.0.0.tgz", - "integrity": "sha512-xHlTOmuCSotIA8TW1mDIM6X2O1SiX5P9IuDtqGonFhEK0qgRI4yeC6vMxEV2dgyr2TiD+2PQ10o+cOhdVAcwfg==", "license": "MIT", "dependencies": { "micromark-util-types": "^2.0.0" @@ -15775,8 +13720,6 @@ }, "node_modules/micromark-extension-gfm-task-list-item": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-task-list-item/-/micromark-extension-gfm-task-list-item-2.1.0.tgz", - "integrity": "sha512-qIBZhqxqI6fjLDYFTBIa4eivDMnP+OZqsNwmQ3xNLE4Cxwc+zfQEfbs6tzAo2Hjq+bh6q5F+Z8/cksrLFYWQQw==", "license": "MIT", "dependencies": { "devlop": "^1.0.0", @@ -15792,8 +13735,6 @@ }, "node_modules/micromark-factory-destination": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-2.0.1.tgz", - "integrity": "sha512-Xe6rDdJlkmbFRExpTOmRj9N3MaWmbAgdpSrBQvCFqhezUn4AHqJHbaEnfbVYYiexVSs//tqOdY/DxhjdCiJnIA==", "funding": [ { "type": "GitHub Sponsors", @@ -15813,8 +13754,6 @@ }, "node_modules/micromark-factory-label": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-2.0.1.tgz", - "integrity": "sha512-VFMekyQExqIW7xIChcXn4ok29YE3rnuyveW3wZQWWqF4Nv9Wk5rgJ99KzPvHjkmPXF93FXIbBp6YdW3t71/7Vg==", "funding": [ { "type": "GitHub Sponsors", @@ -15835,8 +13774,6 @@ }, "node_modules/micromark-factory-space": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.1.tgz", - "integrity": "sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==", "funding": [ { "type": "GitHub Sponsors", @@ -15855,8 +13792,6 @@ }, "node_modules/micromark-factory-title": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-2.0.1.tgz", - "integrity": "sha512-5bZ+3CjhAd9eChYTHsjy6TGxpOFSKgKKJPJxr293jTbfry2KDoWkhBb6TcPVB4NmzaPhMs1Frm9AZH7OD4Cjzw==", "funding": [ { "type": "GitHub Sponsors", @@ -15877,8 +13812,6 @@ }, "node_modules/micromark-factory-whitespace": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-2.0.1.tgz", - "integrity": "sha512-Ob0nuZ3PKt/n0hORHyvoD9uZhr+Za8sFoP+OnMcnWK5lngSzALgQYKMr9RJVOWLqQYuyn6ulqGWSXdwf6F80lQ==", "funding": [ { "type": "GitHub Sponsors", @@ -15899,8 +13832,6 @@ }, "node_modules/micromark-util-character": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", - "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", "funding": [ { "type": "GitHub Sponsors", @@ -15919,8 +13850,6 @@ }, "node_modules/micromark-util-chunked": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-2.0.1.tgz", - "integrity": "sha512-QUNFEOPELfmvv+4xiNg2sRYeS/P84pTW0TCgP5zc9FpXetHY0ab7SxKyAQCNCc1eK0459uoLI1y5oO5Vc1dbhA==", "funding": [ { "type": "GitHub Sponsors", @@ -15938,8 +13867,6 @@ }, "node_modules/micromark-util-classify-character": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-2.0.1.tgz", - "integrity": "sha512-K0kHzM6afW/MbeWYWLjoHQv1sgg2Q9EccHEDzSkxiP/EaagNzCm7T/WMKZ3rjMbvIpvBiZgwR3dKMygtA4mG1Q==", "funding": [ { "type": "GitHub Sponsors", @@ -15959,8 +13886,6 @@ }, "node_modules/micromark-util-combine-extensions": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-2.0.1.tgz", - "integrity": "sha512-OnAnH8Ujmy59JcyZw8JSbK9cGpdVY44NKgSM7E9Eh7DiLS2E9RNQf0dONaGDzEG9yjEl5hcqeIsj4hfRkLH/Bg==", "funding": [ { "type": "GitHub Sponsors", @@ -15979,8 +13904,6 @@ }, "node_modules/micromark-util-decode-numeric-character-reference": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-2.0.2.tgz", - "integrity": "sha512-ccUbYk6CwVdkmCQMyr64dXz42EfHGkPQlBj5p7YVGzq8I7CtjXZJrubAYezf7Rp+bjPseiROqe7G6foFd+lEuw==", "funding": [ { "type": "GitHub Sponsors", @@ -15998,8 +13921,6 @@ }, "node_modules/micromark-util-decode-string": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-2.0.1.tgz", - "integrity": "sha512-nDV/77Fj6eH1ynwscYTOsbK7rR//Uj0bZXBwJZRfaLEJ1iGBR6kIfNmlNqaqJf649EP0F3NWNdeJi03elllNUQ==", "funding": [ { "type": "GitHub Sponsors", @@ -16020,8 +13941,6 @@ }, "node_modules/micromark-util-encode": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-2.0.1.tgz", - "integrity": "sha512-c3cVx2y4KqUnwopcO9b/SCdo2O67LwJJ/UyqGfbigahfegL9myoEFoDYZgkT7f36T0bLrM9hZTAaAyH+PCAXjw==", "funding": [ { "type": "GitHub Sponsors", @@ -16036,8 +13955,6 @@ }, "node_modules/micromark-util-html-tag-name": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-2.0.1.tgz", - "integrity": "sha512-2cNEiYDhCWKI+Gs9T0Tiysk136SnR13hhO8yW6BGNyhOC4qYFnwF1nKfD3HFAIXA5c45RrIG1ub11GiXeYd1xA==", "funding": [ { "type": "GitHub Sponsors", @@ -16052,8 +13969,6 @@ }, "node_modules/micromark-util-normalize-identifier": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-2.0.1.tgz", - "integrity": "sha512-sxPqmo70LyARJs0w2UclACPUUEqltCkJ6PhKdMIDuJ3gSf/Q+/GIe3WKl0Ijb/GyH9lOpUkRAO2wp0GVkLvS9Q==", "funding": [ { "type": "GitHub Sponsors", @@ -16071,8 +13986,6 @@ }, "node_modules/micromark-util-resolve-all": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-2.0.1.tgz", - "integrity": "sha512-VdQyxFWFT2/FGJgwQnJYbe1jjQoNTS4RjglmSjTUlpUMa95Htx9NHeYW4rGDJzbjvCsl9eLjMQwGeElsqmzcHg==", "funding": [ { "type": "GitHub Sponsors", @@ -16090,8 +14003,6 @@ }, "node_modules/micromark-util-sanitize-uri": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-2.0.1.tgz", - "integrity": "sha512-9N9IomZ/YuGGZZmQec1MbgxtlgougxTodVwDzzEouPKo3qFWvymFHWcnDi2vzV1ff6kas9ucW+o3yzJK9YB1AQ==", "funding": [ { "type": "GitHub Sponsors", @@ -16111,8 +14022,6 @@ }, "node_modules/micromark-util-subtokenize": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-2.1.0.tgz", - "integrity": "sha512-XQLu552iSctvnEcgXw6+Sx75GflAPNED1qx7eBJ+wydBb2KCbRZe+NwvIEEMM83uml1+2WSXpBAcp9IUCgCYWA==", "funding": [ { "type": "GitHub Sponsors", @@ -16133,8 +14042,6 @@ }, "node_modules/micromark-util-symbol": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", - "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", "funding": [ { "type": "GitHub Sponsors", @@ -16149,8 +14056,6 @@ }, "node_modules/micromark-util-types": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-2.0.2.tgz", - "integrity": "sha512-Yw0ECSpJoViF1qTU4DC6NwtC4aWGt1EkzaQB8KPPyCRR8z9TWeV0HbEFGTO+ZY1wB22zmxnJqhPyTpOVCpeHTA==", "funding": [ { "type": "GitHub Sponsors", @@ -16165,8 +14070,6 @@ }, "node_modules/micromatch": { "version": "4.0.8", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.8.tgz", - "integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==", "license": "MIT", "dependencies": { "braces": "^3.0.3", @@ -16190,8 +14093,6 @@ }, "node_modules/mime-db": { "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", "license": "MIT", "engines": { "node": ">= 0.6" @@ -16199,8 +14100,6 @@ }, "node_modules/mime-types": { "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", "license": "MIT", "dependencies": { "mime-db": "1.52.0" @@ -16211,8 +14110,7 @@ }, "node_modules/mimic-fn": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz", - "integrity": "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==", + "dev": true, "license": "MIT", "engines": { "node": ">=6" @@ -16240,8 +14138,6 @@ }, "node_modules/minim": { "version": "0.23.8", - "resolved": "https://registry.npmjs.org/minim/-/minim-0.23.8.tgz", - "integrity": "sha512-bjdr2xW1dBCMsMGGsUeqM4eFI60m94+szhxWys+B1ztIt6gWSfeGBdSVCIawezeHYLYn0j6zrsXdQS/JllBzww==", "license": "MIT", "dependencies": { "lodash": "^4.15.0" @@ -16252,8 +14148,6 @@ }, "node_modules/minimatch": { "version": "9.0.5", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz", - "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==", "license": "ISC", "dependencies": { "brace-expansion": "^2.0.1" @@ -16267,8 +14161,6 @@ }, "node_modules/minimist": { "version": "1.2.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz", - "integrity": "sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/ljharb" @@ -16276,8 +14168,6 @@ }, "node_modules/minipass": { "version": "7.1.2", - "resolved": "https://registry.npmjs.org/minipass/-/minipass-7.1.2.tgz", - "integrity": "sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw==", "license": "ISC", "engines": { "node": ">=16 || 14 >=14.17" @@ -16291,8 +14181,6 @@ }, "node_modules/motion-dom": { "version": "11.18.1", - "resolved": "https://registry.npmjs.org/motion-dom/-/motion-dom-11.18.1.tgz", - "integrity": "sha512-g76KvA001z+atjfxczdRtw/RXOM3OMSdd1f4DL77qCTF/+avrRJiawSG4yDibEQ215sr9kpinSlX2pCTJ9zbhw==", "license": "MIT", "dependencies": { "motion-utils": "^11.18.1" @@ -16300,26 +14188,20 @@ }, "node_modules/motion-utils": { "version": "11.18.1", - "resolved": "https://registry.npmjs.org/motion-utils/-/motion-utils-11.18.1.tgz", - "integrity": "sha512-49Kt+HKjtbJKLtgO/LKj9Ld+6vw9BjH5d9sc40R/kVyH8GLAXgT42M2NnuPcJNuA3s9ZfZBUcwIgpmZWGEE+hA==", "license": "MIT" }, "node_modules/ms": { "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", "license": "MIT" }, "node_modules/multiformats": { - "version": "13.3.2", - "resolved": "https://registry.npmjs.org/multiformats/-/multiformats-13.3.2.tgz", - "integrity": "sha512-qbB0CQDt3QKfiAzZ5ZYjLFOs+zW43vA4uyM8g27PeEuXZybUOFyjrVdP93HPBHMoglibwfkdVwbzfUq8qGcH6g==", + "version": "13.4.1", + "resolved": "https://registry.npmjs.org/multiformats/-/multiformats-13.4.1.tgz", + "integrity": "sha512-VqO6OSvLrFVAYYjgsr8tyv62/rCQhPgsZUXLTqoFLSgdkgiUYKYeArbt1uWLlEpkjxQe+P0+sHlbPEte1Bi06Q==", "license": "Apache-2.0 OR MIT" }, "node_modules/mz": { "version": "2.7.0", - "resolved": "https://registry.npmjs.org/mz/-/mz-2.7.0.tgz", - "integrity": "sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q==", "license": "MIT", "dependencies": { "any-promise": "^1.0.0", @@ -16342,8 +14224,6 @@ }, "node_modules/nanoid": { "version": "3.3.8", - "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.8.tgz", - "integrity": "sha512-WNLf5Sd8oZxOm+TzppcYk8gVOgP+l58xNy58D0nbUnOxOWRWvlcCV4kUF7ltmI6PsrLl/BgKEyS4mqsGChFN0w==", "funding": [ { "type": "github", @@ -16373,8 +14253,6 @@ }, "node_modules/napi-postinstall": { "version": "0.3.3", - "resolved": "https://registry.npmjs.org/napi-postinstall/-/napi-postinstall-0.3.3.tgz", - "integrity": "sha512-uTp172LLXSxuSYHv/kou+f6KW3SMppU9ivthaVTXian9sOt3XM/zHYHpRZiLgQoxeWfYUnslNWQHF1+G71xcow==", "dev": true, "license": "MIT", "bin": { @@ -16389,22 +14267,16 @@ }, "node_modules/natural-compare": { "version": "1.4.0", - "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", - "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", "dev": true, "license": "MIT" }, "node_modules/neo-async": { "version": "2.6.2", - "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", - "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", "dev": true, "license": "MIT" }, "node_modules/neotraverse": { "version": "0.6.18", - "resolved": "https://registry.npmjs.org/neotraverse/-/neotraverse-0.6.18.tgz", - "integrity": "sha512-Z4SmBUweYa09+o6pG+eASabEpP6QkQ70yHj351pQoEXIs8uHbaU2DWVmzBANKgflPa47A50PtB2+NgRpQvr7vA==", "license": "MIT", "engines": { "node": ">= 10" @@ -16420,11 +14292,12 @@ } }, "node_modules/next": { - "version": "15.5.4", - "resolved": "https://registry.npmjs.org/next/-/next-15.5.4.tgz", - "integrity": "sha512-xH4Yjhb82sFYQfY3vbkJfgSDgXvBB6a8xPs9i35k6oZJRoQRihZH+4s9Yo2qsWpzBmZ3lPXaJ2KPXLfkvW4LnA==", + "version": "15.5.6", + "resolved": "https://registry.npmjs.org/next/-/next-15.5.6.tgz", + "integrity": "sha512-zTxsnI3LQo3c9HSdSf91O1jMNsEzIXDShXd4wVdg9y5shwLqBXi4ZtUUJyB86KGVSJLZx0PFONvO54aheGX8QQ==", + "license": "MIT", "dependencies": { - "@next/env": "15.5.4", + "@next/env": "15.5.6", "@swc/helpers": "0.5.15", "caniuse-lite": "^1.0.30001579", "postcss": "8.4.31", @@ -16437,14 +14310,14 @@ "node": "^18.18.0 || ^19.8.0 || >= 20.0.0" }, "optionalDependencies": { - "@next/swc-darwin-arm64": "15.5.4", - "@next/swc-darwin-x64": "15.5.4", - "@next/swc-linux-arm64-gnu": "15.5.4", - "@next/swc-linux-arm64-musl": "15.5.4", - "@next/swc-linux-x64-gnu": "15.5.4", - "@next/swc-linux-x64-musl": "15.5.4", - "@next/swc-win32-arm64-msvc": "15.5.4", - "@next/swc-win32-x64-msvc": "15.5.4", + "@next/swc-darwin-arm64": "15.5.6", + "@next/swc-darwin-x64": "15.5.6", + "@next/swc-linux-arm64-gnu": "15.5.6", + "@next/swc-linux-arm64-musl": "15.5.6", + "@next/swc-linux-x64-gnu": "15.5.6", + "@next/swc-linux-x64-musl": "15.5.6", + "@next/swc-win32-arm64-msvc": "15.5.6", + "@next/swc-win32-x64-msvc": "15.5.6", "sharp": "^0.34.3" }, "peerDependencies": { @@ -16472,8 +14345,6 @@ }, "node_modules/next-auth": { "version": "4.24.11", - "resolved": "https://registry.npmjs.org/next-auth/-/next-auth-4.24.11.tgz", - "integrity": "sha512-pCFXzIDQX7xmHFs4KVH4luCjaCbuPRtZ9oBUjUhOk84mZ9WVPf94n87TxYI4rSRf9HmfHEF8Yep3JrYDVOo3Cw==", "license": "ISC", "dependencies": { "@babel/runtime": "^7.20.13", @@ -16504,8 +14375,6 @@ }, "node_modules/next-auth/node_modules/cookie": { "version": "0.7.2", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.7.2.tgz", - "integrity": "sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==", "license": "MIT", "engines": { "node": ">= 0.6" @@ -16513,8 +14382,6 @@ }, "node_modules/next-auth/node_modules/jose": { "version": "4.15.9", - "resolved": "https://registry.npmjs.org/jose/-/jose-4.15.9.tgz", - "integrity": "sha512-1vUQX+IdDMVPj4k8kOxgUqlcK518yluMuGZwqlr44FS1ppZB/5GWh4rZG89erpOBOJjU/OBsnCVFfapsRz6nEA==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/panva" @@ -16522,8 +14389,6 @@ }, "node_modules/next-auth/node_modules/uuid": { "version": "8.3.2", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz", - "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==", "license": "MIT", "bin": { "uuid": "dist/bin/uuid" @@ -16531,8 +14396,6 @@ }, "node_modules/next/node_modules/postcss": { "version": "8.4.31", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.31.tgz", - "integrity": "sha512-PS08Iboia9mts/2ygV3eLpY5ghnUcfLV/EXTOW1E2qYxJKGGBUtNjN76FYHnMs36RmARn41bC0AZmn+rR0OVpQ==", "funding": [ { "type": "opencollective", @@ -16558,9 +14421,9 @@ } }, "node_modules/node-abi": { - "version": "3.74.0", - "resolved": "https://registry.npmjs.org/node-abi/-/node-abi-3.74.0.tgz", - "integrity": "sha512-c5XK0MjkGBrQPGYG24GBADZud0NCbznxNx0ZkS+ebUTrmV1qTDxPxSL8zEAPURXSbLRWVexxmP4986BziahL5w==", + "version": "3.78.0", + "resolved": "https://registry.npmjs.org/node-abi/-/node-abi-3.78.0.tgz", + "integrity": "sha512-E2wEyrgX/CqvicaQYU3Ze1PFGjc4QYPGsjUrlYkqAE0WjHEZwgOsGMPMzkMse4LjJbDmaEuDX3CM036j5K2DSQ==", "license": "MIT", "dependencies": { "semver": "^7.3.5" @@ -16570,9 +14433,9 @@ } }, "node_modules/node-abi/node_modules/semver": { - "version": "7.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.1.tgz", - "integrity": "sha512-hlq8tAfn0m/61p4BVRcPzIGr6LKiMwo4VM6dGi6pt4qcRkmNzTcWq6eCEjEh+qXjkMDvPlOFFSGwQjoEa6gyMA==", + "version": "7.7.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.3.tgz", + "integrity": "sha512-SdsKMrI9TdgjdweUSR9MweHA4EJ8YxHn8DFaDisvhVlUOe4BF1tLD7GAj0lIqWVl+dPb/rExr0Btby5loQm20Q==", "license": "ISC", "bin": { "semver": "bin/semver.js" @@ -16583,14 +14446,10 @@ }, "node_modules/node-abort-controller": { "version": "3.1.1", - "resolved": "https://registry.npmjs.org/node-abort-controller/-/node-abort-controller-3.1.1.tgz", - "integrity": "sha512-AGK2yQKIjRuqnc6VkX2Xj5d+QW8xZ87pa1UK6yA6ouUyuxfHuMP6umE5QK7UmTeOAymo+Zx1Fxiuw9rVx8taHQ==", "license": "MIT" }, "node_modules/node-addon-api": { "version": "8.3.1", - "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-8.3.1.tgz", - "integrity": "sha512-lytcDEdxKjGJPTLEfW4mYMigRezMlyJY8W4wxJK8zE533Jlb8L8dRuObJFWg2P+AuOIxoCgKF+2Oq4d4Zd0OUA==", "license": "MIT", "optional": true, "engines": { @@ -16612,9 +14471,10 @@ } }, "node_modules/node-datachannel/node_modules/node-domexception": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/node-domexception/-/node-domexception-2.0.1.tgz", - "integrity": "sha512-M85rnSC7WQ7wnfQTARPT4LrK7nwCHLdDFOCcItZMhTQjyCebJH8GciKqYJNgaOFZs9nFmTmd/VMyi3OW5jA47w==", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/node-domexception/-/node-domexception-2.0.2.tgz", + "integrity": "sha512-Qf9vHK9c5MGgUXj8SnucCIS4oEPuUstjRaMplLGeZpbWMfNV1rvEcXuwoXfN51dUfD1b4muPHPQtCx/5Dj/QAA==", + "deprecated": "Use your platform's native DOMException instead", "funding": [ { "type": "github", @@ -16632,8 +14492,6 @@ }, "node_modules/node-domexception": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/node-domexception/-/node-domexception-1.0.0.tgz", - "integrity": "sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==", "funding": [ { "type": "github", @@ -16671,8 +14529,6 @@ }, "node_modules/node-fetch-commonjs": { "version": "3.3.2", - "resolved": "https://registry.npmjs.org/node-fetch-commonjs/-/node-fetch-commonjs-3.3.2.tgz", - "integrity": "sha512-VBlAiynj3VMLrotgwOS3OyECFxas5y7ltLcK4t41lMUZeaK15Ym4QRkqN0EQKAFL42q9i21EPKjzLUPfltR72A==", "license": "MIT", "dependencies": { "node-domexception": "^1.0.0", @@ -16686,10 +14542,13 @@ "url": "https://opencollective.com/node-fetch" } }, + "node_modules/node-fetch-native": { + "version": "1.6.7", + "devOptional": true, + "license": "MIT" + }, "node_modules/node-gyp-build": { "version": "4.8.4", - "resolved": "https://registry.npmjs.org/node-gyp-build/-/node-gyp-build-4.8.4.tgz", - "integrity": "sha512-LA4ZjwlnUblHVgq0oBF3Jl/6h/Nvs5fzBLwdEF4nuxnFdsfajde4WfxtJr3CaiH+F6ewcIB/q4jQ4UzPyid+CQ==", "license": "MIT", "optional": true, "bin": { @@ -16700,29 +14559,24 @@ }, "node_modules/node-int64": { "version": "0.4.0", - "resolved": "https://registry.npmjs.org/node-int64/-/node-int64-0.4.0.tgz", - "integrity": "sha512-O5lz91xSOeoXP6DulyHfllpq+Eg00MWitZIbtPfoSEvqIHdl5gfcY6hYzDWnj0qD5tz52PI08u9qUvSVeUBeHw==", "dev": true, "license": "MIT" }, "node_modules/node-releases": { "version": "2.0.21", - "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.21.tgz", - "integrity": "sha512-5b0pgg78U3hwXkCM8Z9b2FJdPZlr9Psr9V2gQPESdGHqbntyFJKFW4r5TeWGFzafGY3hzs1JC62VEQMbl1JFkw==", "license": "MIT" }, "node_modules/nofilter": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/nofilter/-/nofilter-3.1.0.tgz", "integrity": "sha512-l2NNj07e9afPnhAhvgVrCD/oy2Ai1yfLpuo3EpiO1jFTsB4sFz6oIfAfSZyQzVpkZQ9xS8ZS5g1jCBgq4Hwo0g==", + "license": "MIT", "engines": { "node": ">=12.19" } }, "node_modules/normalize-path": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", - "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", "license": "MIT", "engines": { "node": ">=0.10.0" @@ -16730,8 +14584,6 @@ }, "node_modules/nostr-tools": { "version": "2.10.4", - "resolved": "https://registry.npmjs.org/nostr-tools/-/nostr-tools-2.10.4.tgz", - "integrity": "sha512-biU7sk+jxHgVASfobg2T5ttxOGGSt69wEVBC51sHHOEaKAAdzHBLV/I2l9Rf61UzClhliZwNouYhqIso4a3HYg==", "license": "Unlicense", "dependencies": { "@noble/ciphers": "^0.5.1", @@ -16755,8 +14607,6 @@ }, "node_modules/nostr-tools/node_modules/@noble/hashes": { "version": "1.3.1", - "resolved": "https://registry.npmjs.org/@noble/hashes/-/hashes-1.3.1.tgz", - "integrity": "sha512-EbqwksQwz9xDRGfDST86whPBgM65E0OH/pCgqW0GBVzO22bNE+NuIbeTb714+IfSjU3aRk47EUvXIb5bTsenKA==", "license": "MIT", "engines": { "node": ">= 16" @@ -16767,8 +14617,6 @@ }, "node_modules/nostr-tools/node_modules/@scure/base": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@scure/base/-/base-1.1.1.tgz", - "integrity": "sha512-ZxOhsSyxYwLJj3pLZCefNitxsj093tb2vq90mp2txoYeBqbcjDjqFhyM8eUjq/uFm6zJ+mUuqxlS2FkuSY1MTA==", "funding": [ { "type": "individual", @@ -16779,8 +14627,6 @@ }, "node_modules/nostr-wasm": { "version": "0.1.0", - "resolved": "https://registry.npmjs.org/nostr-wasm/-/nostr-wasm-0.1.0.tgz", - "integrity": "sha512-78BTryCLcLYv96ONU8Ws3Q1JzjlAt+43pWQhIl86xZmWeegYCNLPml7yQ+gG3vR6V5h4XGj+TxO+SS5dsThQIA==", "license": "MIT", "optional": true }, @@ -16950,8 +14796,7 @@ }, "node_modules/npm-run-path": { "version": "4.0.1", - "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-4.0.1.tgz", - "integrity": "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==", + "dev": true, "license": "MIT", "dependencies": { "path-key": "^3.0.0" @@ -19820,16 +17665,30 @@ "inBundle": true, "license": "ISC" }, + "node_modules/nypm": { + "version": "0.6.2", + "devOptional": true, + "license": "MIT", + "dependencies": { + "citty": "^0.1.6", + "consola": "^3.4.2", + "pathe": "^2.0.3", + "pkg-types": "^2.3.0", + "tinyexec": "^1.0.1" + }, + "bin": { + "nypm": "dist/cli.mjs" + }, + "engines": { + "node": "^14.16.0 || >=16.10.0" + } + }, "node_modules/oauth": { "version": "0.9.15", - "resolved": "https://registry.npmjs.org/oauth/-/oauth-0.9.15.tgz", - "integrity": "sha512-a5ERWK1kh38ExDEfoO6qUHJb32rd7aYmPHuyCu3Fta/cnICvYmgd2uhuKXvPD+PXB+gCEYYEaQdIRAjCOwAKNA==", "license": "MIT" }, "node_modules/oauth4webapi": { "version": "2.17.0", - "resolved": "https://registry.npmjs.org/oauth4webapi/-/oauth4webapi-2.17.0.tgz", - "integrity": "sha512-lbC0Z7uzAFNFyzEYRIC+pkSVvDHJTbEW+dYlSBAlCYDe6RxUkJ26bClhk8ocBZip1wfI9uKTe0fm4Ib4RHn6uQ==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/panva" @@ -19837,8 +17696,6 @@ }, "node_modules/object-assign": { "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", "license": "MIT", "engines": { "node": ">=0.10.0" @@ -19846,8 +17703,6 @@ }, "node_modules/object-hash": { "version": "2.2.0", - "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-2.2.0.tgz", - "integrity": "sha512-gScRMn0bS5fH+IuwyIFgnh9zBdo4DV+6GhygmWM9HyNJSgS0hScp1f5vjtm7oIIOiT9trXrShAkLFSc2IqKNgw==", "license": "MIT", "engines": { "node": ">= 6" @@ -19855,8 +17710,6 @@ }, "node_modules/object-inspect": { "version": "1.13.3", - "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.3.tgz", - "integrity": "sha512-kDCGIbxkDSXE3euJZZXzc6to7fCrKHNI/hSRQnRuQ+BWjFNzZwiFF8fj/6o2t2G9/jTj8PSIYTfCLelLZEeRpA==", "dev": true, "license": "MIT", "engines": { @@ -19868,8 +17721,6 @@ }, "node_modules/object-keys": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", - "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", "dev": true, "license": "MIT", "engines": { @@ -19878,8 +17729,6 @@ }, "node_modules/object.assign": { "version": "4.1.7", - "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.7.tgz", - "integrity": "sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==", "dev": true, "license": "MIT", "dependencies": { @@ -19899,8 +17748,6 @@ }, "node_modules/object.entries": { "version": "1.1.8", - "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.8.tgz", - "integrity": "sha512-cmopxi8VwRIAw/fkijJohSfpef5PdN0pMQJN6VC/ZKvn0LIknWD8KtgY6KlQdEc4tIjcQ3HxSMmnvtzIscdaYQ==", "dev": true, "license": "MIT", "dependencies": { @@ -19914,8 +17761,6 @@ }, "node_modules/object.fromentries": { "version": "2.0.8", - "resolved": "https://registry.npmjs.org/object.fromentries/-/object.fromentries-2.0.8.tgz", - "integrity": "sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==", "dev": true, "license": "MIT", "dependencies": { @@ -19933,8 +17778,6 @@ }, "node_modules/object.groupby": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/object.groupby/-/object.groupby-1.0.3.tgz", - "integrity": "sha512-+Lhy3TQTuzXI5hevh8sBGqbmurHbbIjAi0Z4S63nthVLmLxfbj4T54a4CfZrXIrt9iP4mVAPYMo/v99taj3wjQ==", "dev": true, "license": "MIT", "dependencies": { @@ -19948,8 +17791,6 @@ }, "node_modules/object.values": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.2.1.tgz", - "integrity": "sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==", "dev": true, "license": "MIT", "dependencies": { @@ -19965,10 +17806,13 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/ohash": { + "version": "2.0.11", + "devOptional": true, + "license": "MIT" + }, "node_modules/oidc-token-hash": { "version": "5.0.3", - "resolved": "https://registry.npmjs.org/oidc-token-hash/-/oidc-token-hash-5.0.3.tgz", - "integrity": "sha512-IF4PcGgzAr6XXSff26Sk/+P4KZFJVuHAJZj3wgO3vX2bMdNVp/QXTP3P7CEm9V1IdG8lDLY3HhiqpsE/nOwpPw==", "license": "MIT", "engines": { "node": "^10.13.0 || >=12.0.0" @@ -19976,8 +17820,6 @@ }, "node_modules/once": { "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", "license": "ISC", "dependencies": { "wrappy": "1" @@ -19985,8 +17827,7 @@ }, "node_modules/onetime": { "version": "5.1.2", - "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", - "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", + "dev": true, "license": "MIT", "dependencies": { "mimic-fn": "^2.1.0" @@ -20000,8 +17841,6 @@ }, "node_modules/openapi-path-templating": { "version": "2.2.1", - "resolved": "https://registry.npmjs.org/openapi-path-templating/-/openapi-path-templating-2.2.1.tgz", - "integrity": "sha512-eN14VrDvl/YyGxxrkGOHkVkWEoPyhyeydOUrbvjoz8K5eIGgELASwN1eqFOJ2CTQMGCy2EntOK1KdtJ8ZMekcg==", "license": "Apache-2.0", "dependencies": { "apg-lite": "^1.0.4" @@ -20012,8 +17851,6 @@ }, "node_modules/openapi-server-url-templating": { "version": "1.3.0", - "resolved": "https://registry.npmjs.org/openapi-server-url-templating/-/openapi-server-url-templating-1.3.0.tgz", - "integrity": "sha512-DPlCms3KKEbjVQb0spV6Awfn6UWNheuG/+folQPzh/wUaKwuqvj8zt5gagD7qoyxtE03cIiKPgLFS3Q8Bz00uQ==", "license": "Apache-2.0", "dependencies": { "apg-lite": "^1.0.4" @@ -20024,15 +17861,11 @@ }, "node_modules/openapi-types": { "version": "12.1.3", - "resolved": "https://registry.npmjs.org/openapi-types/-/openapi-types-12.1.3.tgz", - "integrity": "sha512-N4YtSYJqghVu4iek2ZUvcN/0aqH1kRDuNqzcycDxhOUpg7GdvLa2F3DgS6yBNhInhv2r/6I0Flkn7CqL8+nIcw==", "license": "MIT", "peer": true }, "node_modules/openid-client": { "version": "5.7.1", - "resolved": "https://registry.npmjs.org/openid-client/-/openid-client-5.7.1.tgz", - "integrity": "sha512-jDBPgSVfTnkIh71Hg9pRvtJc6wTwqjRkN88+gCFtYWrlP4Yx2Dsrow8uPi3qLr/aeymPF3o2+dS+wOpglK04ew==", "license": "MIT", "dependencies": { "jose": "^4.15.9", @@ -20046,8 +17879,6 @@ }, "node_modules/openid-client/node_modules/jose": { "version": "4.15.9", - "resolved": "https://registry.npmjs.org/jose/-/jose-4.15.9.tgz", - "integrity": "sha512-1vUQX+IdDMVPj4k8kOxgUqlcK518yluMuGZwqlr44FS1ppZB/5GWh4rZG89erpOBOJjU/OBsnCVFfapsRz6nEA==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/panva" @@ -20055,8 +17886,6 @@ }, "node_modules/openid-client/node_modules/lru-cache": { "version": "6.0.0", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", - "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", "license": "ISC", "dependencies": { "yallist": "^4.0.0" @@ -20067,14 +17896,10 @@ }, "node_modules/openid-client/node_modules/yallist": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", "license": "ISC" }, "node_modules/optionator": { "version": "0.9.4", - "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.4.tgz", - "integrity": "sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==", "dev": true, "license": "MIT", "dependencies": { @@ -20091,8 +17916,6 @@ }, "node_modules/own-keys": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/own-keys/-/own-keys-1.0.1.tgz", - "integrity": "sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==", "dev": true, "license": "MIT", "dependencies": { @@ -20109,8 +17932,6 @@ }, "node_modules/p-limit": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz", - "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==", "dev": true, "license": "MIT", "dependencies": { @@ -20125,8 +17946,6 @@ }, "node_modules/p-locate": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz", - "integrity": "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==", "dev": true, "license": "MIT", "dependencies": { @@ -20140,16 +17959,16 @@ } }, "node_modules/p-queue": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/p-queue/-/p-queue-8.1.0.tgz", - "integrity": "sha512-mxLDbbGIBEXTJL0zEx8JIylaj3xQ7Z/7eEVjcF9fJX4DBiH9oqe+oahYnlKKxm0Ci9TlWTyhSHgygxMxjIB2jw==", + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/p-queue/-/p-queue-9.0.0.tgz", + "integrity": "sha512-KO1RyxstL9g1mK76530TExamZC/S2Glm080Nx8PE5sTd7nlduDQsAfEl4uXX+qZjLiwvDauvzXavufy3+rJ9zQ==", "license": "MIT", "dependencies": { "eventemitter3": "^5.0.1", - "p-timeout": "^6.1.2" + "p-timeout": "^7.0.0" }, "engines": { - "node": ">=18" + "node": ">=20" }, "funding": { "url": "https://github.com/sponsors/sindresorhus" @@ -20162,12 +17981,12 @@ "license": "MIT" }, "node_modules/p-timeout": { - "version": "6.1.4", - "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-6.1.4.tgz", - "integrity": "sha512-MyIV3ZA/PmyBN/ud8vV9XzwTrNtR4jFrObymZYnZqMmW0zA8Z17vnT0rBgFE/TlohB+YCHqXMgZzb3Csp49vqg==", + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-7.0.1.tgz", + "integrity": "sha512-AxTM2wDGORHGEkPCt8yqxOTMgpfbEHqF51f/5fJCmwFC3C/zNcGT63SymH2ttOAaiIws2zVg4+izQCjrakcwHg==", "license": "MIT", "engines": { - "node": ">=14.16" + "node": ">=20" }, "funding": { "url": "https://github.com/sponsors/sindresorhus" @@ -20175,8 +17994,6 @@ }, "node_modules/p-try": { "version": "2.2.0", - "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", - "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==", "dev": true, "license": "MIT", "engines": { @@ -20185,14 +18002,10 @@ }, "node_modules/papaparse": { "version": "5.5.3", - "resolved": "https://registry.npmjs.org/papaparse/-/papaparse-5.5.3.tgz", - "integrity": "sha512-5QvjGxYVjxO59MGU2lHVYpRWBBtKHnlIAcSe1uNFCkkptUh63NFRj0FJQm7nR67puEruUci/ZkjmEFrjCAyP4A==", "license": "MIT" }, "node_modules/parent-module": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", - "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", "dev": true, "license": "MIT", "dependencies": { @@ -20204,8 +18017,6 @@ }, "node_modules/parse-entities": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-2.0.0.tgz", - "integrity": "sha512-kkywGpCcRYhqQIchaWqZ875wzpS/bMKhz5HnN3p7wveJTkTtyAB/AlnS0f8DFSqYW1T82t6yEAkEcB+A1I3MbQ==", "license": "MIT", "dependencies": { "character-entities": "^1.0.0", @@ -20222,8 +18033,6 @@ }, "node_modules/parse-json": { "version": "5.2.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-5.2.0.tgz", - "integrity": "sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==", "dev": true, "license": "MIT", "dependencies": { @@ -20240,9 +18049,9 @@ } }, "node_modules/parse-torrent": { - "version": "11.0.18", - "resolved": "https://registry.npmjs.org/parse-torrent/-/parse-torrent-11.0.18.tgz", - "integrity": "sha512-C1igbmTrQQuKlspAfP1wcLaOPlvtu5qi4pMdPoCCfepHmxDOk8iArJ2J1yblLx11UefZJUaKEPSxIwMdG11SuA==", + "version": "11.0.19", + "resolved": "https://registry.npmjs.org/parse-torrent/-/parse-torrent-11.0.19.tgz", + "integrity": "sha512-T0lEkDdFVQsy0YxHIKjzDHSgt/yl57f3INs5jl7OZqAm77XDF0FgRgrv3LCKgSqsTOrMwYaF0t2761WKdvhgig==", "funding": [ { "type": "github", @@ -20275,8 +18084,6 @@ }, "node_modules/path-exists": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", - "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==", "dev": true, "license": "MIT", "engines": { @@ -20285,8 +18092,6 @@ }, "node_modules/path-is-absolute": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", "license": "MIT", "engines": { "node": ">=0.10.0" @@ -20294,8 +18099,6 @@ }, "node_modules/path-key": { "version": "3.1.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", - "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", "license": "MIT", "engines": { "node": ">=8" @@ -20303,14 +18106,10 @@ }, "node_modules/path-parse": { "version": "1.0.7", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", - "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", "license": "MIT" }, "node_modules/path-scurry": { "version": "1.11.1", - "resolved": "https://registry.npmjs.org/path-scurry/-/path-scurry-1.11.1.tgz", - "integrity": "sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA==", "license": "BlueOak-1.0.0", "dependencies": { "lru-cache": "^10.2.0", @@ -20325,68 +18124,41 @@ }, "node_modules/path-scurry/node_modules/lru-cache": { "version": "10.4.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-10.4.3.tgz", - "integrity": "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==", "license": "ISC" }, + "node_modules/pathe": { + "version": "2.0.3", + "devOptional": true, + "license": "MIT" + }, "node_modules/pbkdf2": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/pbkdf2/-/pbkdf2-3.1.3.tgz", - "integrity": "sha512-wfRLBZ0feWRhCIkoMB6ete7czJcnNnqRpcoWQBLqatqXXmelSRqfdDK4F3u9T2s2cXas/hQJcryI/4lAL+XTlA==", + "version": "3.1.5", + "resolved": "https://registry.npmjs.org/pbkdf2/-/pbkdf2-3.1.5.tgz", + "integrity": "sha512-Q3CG/cYvCO1ye4QKkuH7EXxs3VC/rI1/trd+qX2+PolbaKG0H+bgcZzrTt96mMyRtejk+JMCiLUn3y29W8qmFQ==", "license": "MIT", "dependencies": { - "create-hash": "~1.1.3", + "create-hash": "^1.2.0", "create-hmac": "^1.1.7", - "ripemd160": "=2.0.1", + "ripemd160": "^2.0.3", "safe-buffer": "^5.2.1", - "sha.js": "^2.4.11", - "to-buffer": "^1.2.0" + "sha.js": "^2.4.12", + "to-buffer": "^1.2.1" }, "engines": { - "node": ">=0.12" - } - }, - "node_modules/pbkdf2/node_modules/create-hash": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.1.3.tgz", - "integrity": "sha512-snRpch/kwQhcdlnZKYanNF1m0RDlrCdSKQaH87w1FCFPVPNCQ/Il9QJKAX2jVBZddRdaHBMC+zXa9Gw9tmkNUA==", - "license": "MIT", - "dependencies": { - "cipher-base": "^1.0.1", - "inherits": "^2.0.1", - "ripemd160": "^2.0.0", - "sha.js": "^2.4.0" - } - }, - "node_modules/pbkdf2/node_modules/hash-base": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-2.0.2.tgz", - "integrity": "sha512-0TROgQ1/SxE6KmxWSvXHvRj90/Xo1JvZShofnYF+f6ZsGtR4eES7WfrQzPalmyagfKZCXpVnitiRebZulWsbiw==", - "license": "MIT", - "dependencies": { - "inherits": "^2.0.1" + "node": ">= 0.10" } }, - "node_modules/pbkdf2/node_modules/ripemd160": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.1.tgz", - "integrity": "sha512-J7f4wutN8mdbV08MJnXibYpCOPHR+yzy+iQ/AsjMv2j8cLavQ8VGagDFUwwTAdF8FmRKVeNpbTTEwNHCW1g94w==", - "license": "MIT", - "dependencies": { - "hash-base": "^2.0.0", - "inherits": "^2.0.1" - } + "node_modules/perfect-debounce": { + "version": "1.0.0", + "devOptional": true, + "license": "MIT" }, "node_modules/picocolors": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", - "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", "license": "ISC" }, "node_modules/picomatch": { "version": "2.3.1", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", - "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", "license": "MIT", "engines": { "node": ">=8.6" @@ -20403,8 +18175,6 @@ }, "node_modules/pify": { "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha512-udgsAY+fTnvv7kI7aaxbqwWNb0AHiB0qBO89PZKPkoTmGOgdbrHDKD+0B2X4uTfJ/FT1R09r9gTsjUjNJotuog==", "license": "MIT", "engines": { "node": ">=0.10.0" @@ -20412,8 +18182,6 @@ }, "node_modules/pirates": { "version": "4.0.7", - "resolved": "https://registry.npmjs.org/pirates/-/pirates-4.0.7.tgz", - "integrity": "sha512-TfySrs/5nm8fQJDcBDuUng3VOUKsd7S+zqvbOTiGXHfxX4wK31ard+hoNuvkicM/2YFzlpDgABOevKSsB4G/FA==", "license": "MIT", "engines": { "node": ">= 6" @@ -20421,8 +18189,6 @@ }, "node_modules/pkg-dir": { "version": "4.2.0", - "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-4.2.0.tgz", - "integrity": "sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==", "dev": true, "license": "MIT", "dependencies": { @@ -20434,8 +18200,6 @@ }, "node_modules/pkg-dir/node_modules/find-up": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", - "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", "dev": true, "license": "MIT", "dependencies": { @@ -20448,8 +18212,6 @@ }, "node_modules/pkg-dir/node_modules/locate-path": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", - "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", "dev": true, "license": "MIT", "dependencies": { @@ -20461,8 +18223,6 @@ }, "node_modules/pkg-dir/node_modules/p-limit": { "version": "2.3.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", - "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", "dev": true, "license": "MIT", "dependencies": { @@ -20477,8 +18237,6 @@ }, "node_modules/pkg-dir/node_modules/p-locate": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", - "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", "dev": true, "license": "MIT", "dependencies": { @@ -20488,10 +18246,18 @@ "node": ">=8" } }, + "node_modules/pkg-types": { + "version": "2.3.0", + "devOptional": true, + "license": "MIT", + "dependencies": { + "confbox": "^0.2.2", + "exsolve": "^1.0.7", + "pathe": "^2.0.3" + } + }, "node_modules/point-in-polygon-hao": { "version": "1.2.4", - "resolved": "https://registry.npmjs.org/point-in-polygon-hao/-/point-in-polygon-hao-1.2.4.tgz", - "integrity": "sha512-x2pcvXeqhRHlNRdhLs/tgFapAbSSe86wa/eqmj1G6pWftbEs5aVRJhRGM6FYSUERKu0PjekJzMq0gsI2XyiclQ==", "license": "MIT", "dependencies": { "robust-predicates": "^3.0.2" @@ -20499,8 +18265,6 @@ }, "node_modules/possible-typed-array-names": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/possible-typed-array-names/-/possible-typed-array-names-1.0.0.tgz", - "integrity": "sha512-d7Uw+eZoloe0EHDIYoe+bQ5WXnGMOpmiZFTuMWCwpjzzkL2nTjcKiAk4hh8TjnGye2TwWOk3UXucZ+3rbmBa8Q==", "license": "MIT", "engines": { "node": ">= 0.4" @@ -20508,8 +18272,6 @@ }, "node_modules/postcss": { "version": "8.5.1", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.1.tgz", - "integrity": "sha512-6oz2beyjc5VMn/KV1pPw8fliQkhBXrVn1Z3TVyqZxU8kZpzEKhBdmCFqI6ZbmGtamQvQGuU1sgPTk8ZrXDD7jQ==", "funding": [ { "type": "opencollective", @@ -20536,8 +18298,6 @@ }, "node_modules/postcss-import": { "version": "15.1.0", - "resolved": "https://registry.npmjs.org/postcss-import/-/postcss-import-15.1.0.tgz", - "integrity": "sha512-hpr+J05B2FVYUAXHeK1YyI267J/dDDhMU6B6civm8hSY1jYJnBXxzKDKDswzJmtLHryrjhnDjqqp/49t8FALew==", "license": "MIT", "dependencies": { "postcss-value-parser": "^4.0.0", @@ -20553,8 +18313,6 @@ }, "node_modules/postcss-js": { "version": "4.0.1", - "resolved": "https://registry.npmjs.org/postcss-js/-/postcss-js-4.0.1.tgz", - "integrity": "sha512-dDLF8pEO191hJMtlHFPRa8xsizHaM82MLfNkUHdUtVEV3tgTp5oj+8qbEqYM57SLfc74KSbw//4SeJma2LRVIw==", "license": "MIT", "dependencies": { "camelcase-css": "^2.0.1" @@ -20572,8 +18330,6 @@ }, "node_modules/postcss-load-config": { "version": "4.0.2", - "resolved": "https://registry.npmjs.org/postcss-load-config/-/postcss-load-config-4.0.2.tgz", - "integrity": "sha512-bSVhyJGL00wMVoPUzAVAnbEoWyqRxkjv64tUl427SKnPrENtq6hJwUojroMz2VB+Q1edmi4IfrAPpami5VVgMQ==", "funding": [ { "type": "opencollective", @@ -20607,8 +18363,6 @@ }, "node_modules/postcss-nested": { "version": "6.2.0", - "resolved": "https://registry.npmjs.org/postcss-nested/-/postcss-nested-6.2.0.tgz", - "integrity": "sha512-HQbt28KulC5AJzG+cZtj9kvKB93CFCdLvog1WFLf1D+xmMvPGlBstkpTEZfK5+AN9hfJocyBFCNiqyS48bpgzQ==", "funding": [ { "type": "opencollective", @@ -20632,8 +18386,6 @@ }, "node_modules/postcss-selector-parser": { "version": "6.1.2", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-6.1.2.tgz", - "integrity": "sha512-Q8qQfPiZ+THO/3ZrOrO0cJJKfpYCagtMUkXbnEfmgUjwXg6z/WBeOyS9APBBPCTSiDV+s4SwQGu8yFsiMRIudg==", "license": "MIT", "dependencies": { "cssesc": "^3.0.0", @@ -20645,20 +18397,14 @@ }, "node_modules/postcss-value-parser": { "version": "4.2.0", - "resolved": "https://registry.npmjs.org/postcss-value-parser/-/postcss-value-parser-4.2.0.tgz", - "integrity": "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ==", "license": "MIT" }, "node_modules/potpack": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/potpack/-/potpack-1.0.2.tgz", - "integrity": "sha512-choctRBIV9EMT9WGAZHn3V7t0Z2pMQyl0EZE6pFc/6ml3ssw7Dlf/oAOvFwjm1HVsqfQN8GfeFyJ+d8tRzqueQ==", "license": "ISC" }, "node_modules/preact": { "version": "10.11.3", - "resolved": "https://registry.npmjs.org/preact/-/preact-10.11.3.tgz", - "integrity": "sha512-eY93IVpod/zG3uMF22Unl8h9KkrcKIRs2EGar8hwLZZDU1lkjph303V9HZBwufh2s736U6VXuhD109LYqPoffg==", "license": "MIT", "funding": { "type": "opencollective", @@ -20667,8 +18413,6 @@ }, "node_modules/preact-render-to-string": { "version": "5.2.3", - "resolved": "https://registry.npmjs.org/preact-render-to-string/-/preact-render-to-string-5.2.3.tgz", - "integrity": "sha512-aPDxUn5o3GhWdtJtW0svRC2SS/l8D9MAgo2+AWml+BhDImb27ALf04Q2d+AHqUUOc6RdSXFIBVa2gxzgMKgtZA==", "license": "MIT", "dependencies": { "pretty-format": "^3.8.0" @@ -20705,8 +18449,6 @@ }, "node_modules/prelude-ls": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", - "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", "dev": true, "license": "MIT", "engines": { @@ -20715,8 +18457,6 @@ }, "node_modules/prettier": { "version": "3.4.2", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.4.2.tgz", - "integrity": "sha512-e9MewbtFo+Fevyuxn/4rrcDAaq0IYxPGLvObpQjiZBMAzB9IGmzlnG9RZy3FFas+eBMu2vA0CszMeduow5dIuQ==", "dev": true, "license": "MIT", "bin": { @@ -20731,8 +18471,6 @@ }, "node_modules/prettier-plugin-tailwindcss": { "version": "0.6.11", - "resolved": "https://registry.npmjs.org/prettier-plugin-tailwindcss/-/prettier-plugin-tailwindcss-0.6.11.tgz", - "integrity": "sha512-YxaYSIvZPAqhrrEpRtonnrXdghZg1irNg4qrjboCXrpybLWVs55cW2N3juhspVJiO0JBvYJT8SYsJpc8OQSnsA==", "dev": true, "license": "MIT", "engines": { @@ -20810,21 +18548,16 @@ }, "node_modules/pretty-format": { "version": "3.8.0", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-3.8.0.tgz", - "integrity": "sha512-WuxUnVtlWL1OfZFQFuqvnvs6MiAGk9UNsBostyBOB0Is9wb5uRESevA6rnl/rkksXaGX3GzZhPup5d6Vp1nFew==", "license": "MIT" }, "node_modules/prisma": { - "version": "6.4.1", - "resolved": "https://registry.npmjs.org/prisma/-/prisma-6.4.1.tgz", - "integrity": "sha512-q2uJkgXnua/jj66mk6P9bX/zgYJFI/jn4Yp0aS6SPRrjH/n6VyOV7RDe1vHD0DX8Aanx4MvgmUPPoYnR6MJnPg==", + "version": "6.17.1", "devOptional": true, "hasInstallScript": true, "license": "Apache-2.0", "dependencies": { - "@prisma/engines": "6.4.1", - "esbuild": ">=0.12 <1", - "esbuild-register": "3.6.0" + "@prisma/config": "6.17.1", + "@prisma/engines": "6.17.1" }, "bin": { "prisma": "build/index.js" @@ -20832,9 +18565,6 @@ "engines": { "node": ">=18.18" }, - "optionalDependencies": { - "fsevents": "2.3.3" - }, "peerDependencies": { "typescript": ">=5.1.0" }, @@ -20846,8 +18576,6 @@ }, "node_modules/prismjs": { "version": "1.30.0", - "resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.30.0.tgz", - "integrity": "sha512-DEvV2ZF2r2/63V+tK8hQvrR2ZGn10srHbXviTlcv7Kpzw8jWiNTqbVgjO3IY8RxrrOUF8VPMQQFysYYYv0YZxw==", "license": "MIT", "engines": { "node": ">=6" @@ -20855,13 +18583,17 @@ }, "node_modules/process": { "version": "0.11.10", - "resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz", - "integrity": "sha512-cdGef/drWFoydD1JsMzuFf8100nZl+GT+yacc2bEced5f9Rjk4z+WtFUTBu9PhOi9j/jfmBPu0mMEY4wIdAF8A==", "license": "MIT", "engines": { "node": ">= 0.6.0" } }, + "node_modules/process-nextick-args": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", + "license": "MIT" + }, "node_modules/progress-events": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/progress-events/-/progress-events-1.0.1.tgz", @@ -20870,8 +18602,6 @@ }, "node_modules/promise-worker-transferable": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/promise-worker-transferable/-/promise-worker-transferable-1.0.4.tgz", - "integrity": "sha512-bN+0ehEnrXfxV2ZQvU2PetO0n4gqBD4ulq3MI1WOPLgr7/Mg9yRQkX5+0v1vagr74ZTsl7XtzlaYDo2EuCeYJw==", "license": "Apache-2.0", "dependencies": { "is-promise": "^2.1.0", @@ -20880,8 +18610,6 @@ }, "node_modules/prop-types": { "version": "15.8.1", - "resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz", - "integrity": "sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==", "license": "MIT", "dependencies": { "loose-envify": "^1.4.0", @@ -20891,8 +18619,6 @@ }, "node_modules/property-information": { "version": "5.6.0", - "resolved": "https://registry.npmjs.org/property-information/-/property-information-5.6.0.tgz", - "integrity": "sha512-YUHSPk+A30YPv+0Qf8i9Mbfe/C0hdPXk1s1jPVToV8pk8BQtpw10ct89Eo7OWkutrwqvT0eicAxlOg3dOAu8JA==", "license": "MIT", "dependencies": { "xtend": "^4.0.0" @@ -20904,14 +18630,12 @@ }, "node_modules/proxy-from-env": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", - "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==", "license": "MIT" }, "node_modules/pump": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.2.tgz", - "integrity": "sha512-tUPXtzlGM8FE3P0ZL6DVs/3P58k9nk8/jZeQCurTJylQA8qFYzHFfhBJkuqyE0FifOsQ0uKWekiZ5g8wtr28cw==", + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.3.tgz", + "integrity": "sha512-todwxLMY7/heScKmntwQG8CXVkWUOdYxIvY2s0VWAAMh/nd8SoYiRaKjlr7+iCs984f2P8zvrfWcDDYVb73NfA==", "license": "MIT", "dependencies": { "end-of-stream": "^1.1.0", @@ -20920,8 +18644,6 @@ }, "node_modules/punycode": { "version": "2.3.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", - "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", "dev": true, "license": "MIT", "engines": { @@ -20930,8 +18652,6 @@ }, "node_modules/pure-rand": { "version": "7.0.1", - "resolved": "https://registry.npmjs.org/pure-rand/-/pure-rand-7.0.1.tgz", - "integrity": "sha512-oTUZM/NAZS8p7ANR3SHh30kXB+zK2r2BPcEn/awJIbOvq82WoMN4p62AWWp3Hhw50G0xMsw1mhIBLqHw64EcNQ==", "dev": true, "funding": [ { @@ -20949,6 +18669,7 @@ "version": "1.3.6", "resolved": "https://registry.npmjs.org/pvtsutils/-/pvtsutils-1.3.6.tgz", "integrity": "sha512-PLgQXQ6H2FWCaeRak8vvk1GW462lMxB5s3Jm673N82zI4vqtVUPuZdffdZbPDFRoU8kAhItWFtPCWiPpp4/EDg==", + "license": "MIT", "dependencies": { "tslib": "^2.8.1" } @@ -20957,6 +18678,7 @@ "version": "1.1.3", "resolved": "https://registry.npmjs.org/pvutils/-/pvutils-1.1.3.tgz", "integrity": "sha512-pMpnA0qRdFp32b1sJl1wOJNxZLQ2cbQx+k6tjNtZ8CpvVhNqEPRgivZ2WOUev2YMajecdH7ctUPDvEe87nariQ==", + "license": "MIT", "engines": { "node": ">=6.0.0" } @@ -20972,14 +18694,10 @@ }, "node_modules/querystringify": { "version": "2.2.0", - "resolved": "https://registry.npmjs.org/querystringify/-/querystringify-2.2.0.tgz", - "integrity": "sha512-FIqgj2EUvTa7R50u0rGsyTftzjYmv/a3hO345bZNrqabNqjtgiDMgmo4mkUjd+nzU5oF3dClKqFIPUKybUyqoQ==", "license": "MIT" }, "node_modules/queue-microtask": { "version": "1.2.3", - "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", - "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", "funding": [ { "type": "github", @@ -21004,14 +18722,10 @@ }, "node_modules/rafor": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/rafor/-/rafor-1.0.2.tgz", - "integrity": "sha512-b8e8/srbSbC0FZTxivEz9pj5z1mQM8CpCEv1aAxuaK26ljSOHJk8AjimcTaHpHIZlwH/VPbli12LuKKrJyyGmA==", "license": "MIT" }, "node_modules/ramda": { "version": "0.30.1", - "resolved": "https://registry.npmjs.org/ramda/-/ramda-0.30.1.tgz", - "integrity": "sha512-tEF5I22zJnuclswcZMc8bDIrwRHRzf+NqVEmqg50ShAZMP7MWeR/RGDthfM/p+BlqvF2fXAzpn8i+SJcYD3alw==", "license": "MIT", "funding": { "type": "opencollective", @@ -21020,8 +18734,6 @@ }, "node_modules/ramda-adjunct": { "version": "5.1.0", - "resolved": "https://registry.npmjs.org/ramda-adjunct/-/ramda-adjunct-5.1.0.tgz", - "integrity": "sha512-8qCpl2vZBXEJyNbi4zqcgdfHtcdsWjOGbiNSEnEBrM6Y0OKOT8UxJbIVGm1TIcjaSu2MxaWcgtsNlKlCk7o7qg==", "license": "BSD-3-Clause", "engines": { "node": ">=0.10.3" @@ -21036,8 +18748,6 @@ }, "node_modules/randexp": { "version": "0.5.3", - "resolved": "https://registry.npmjs.org/randexp/-/randexp-0.5.3.tgz", - "integrity": "sha512-U+5l2KrcMNOUPYvazA3h5ekF80FHTUG+87SEAmHZmolh1M+i/WyTCxVzmi+tidIa1tM4BSe8g2Y/D3loWDjj+w==", "license": "MIT", "dependencies": { "drange": "^1.0.2", @@ -21079,8 +18789,6 @@ }, "node_modules/randombytes": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", - "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", "license": "MIT", "dependencies": { "safe-buffer": "^5.1.0" @@ -21128,10 +18836,17 @@ "node": ">=0.10.0" } }, + "node_modules/rc9": { + "version": "2.1.2", + "devOptional": true, + "license": "MIT", + "dependencies": { + "defu": "^6.1.4", + "destr": "^2.0.3" + } + }, "node_modules/rdf-canonize": { "version": "3.4.0", - "resolved": "https://registry.npmjs.org/rdf-canonize/-/rdf-canonize-3.4.0.tgz", - "integrity": "sha512-fUeWjrkOO0t1rg7B2fdyDTvngj+9RlUyL92vOdiB7c0FPguWVsniIMjEtHH+meLBO9rzkUlUzBVXgWrjI8P9LA==", "license": "BSD-3-Clause", "dependencies": { "setimmediate": "^1.0.5" @@ -21142,8 +18857,6 @@ }, "node_modules/react": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react/-/react-18.3.1.tgz", - "integrity": "sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ==", "license": "MIT", "dependencies": { "loose-envify": "^1.1.0" @@ -21154,8 +18867,6 @@ }, "node_modules/react-composer": { "version": "5.0.3", - "resolved": "https://registry.npmjs.org/react-composer/-/react-composer-5.0.3.tgz", - "integrity": "sha512-1uWd07EME6XZvMfapwZmc7NgCZqDemcvicRi3wMJzXsQLvZ3L7fTHVyPy1bZdnWXM4iPjYuNE+uJ41MLKeTtnA==", "license": "MIT", "dependencies": { "prop-types": "^15.6.0" @@ -21166,8 +18877,6 @@ }, "node_modules/react-copy-to-clipboard": { "version": "5.1.0", - "resolved": "https://registry.npmjs.org/react-copy-to-clipboard/-/react-copy-to-clipboard-5.1.0.tgz", - "integrity": "sha512-k61RsNgAayIJNoy9yDsYzDe/yAZAzEbEgcz3DZMhF686LEyukcE1hzurxe85JandPUG+yTfGVFzuEw3xt8WP/A==", "license": "MIT", "dependencies": { "copy-to-clipboard": "^3.3.1", @@ -21179,8 +18888,6 @@ }, "node_modules/react-debounce-input": { "version": "3.3.0", - "resolved": "https://registry.npmjs.org/react-debounce-input/-/react-debounce-input-3.3.0.tgz", - "integrity": "sha512-VEqkvs8JvY/IIZvh71Z0TC+mdbxERvYF33RcebnodlsUZ8RSgyKe2VWaHXv4+/8aoOgXLxWrdsYs2hDhcwbUgA==", "license": "MIT", "dependencies": { "lodash.debounce": "^4", @@ -21192,8 +18899,6 @@ }, "node_modules/react-dom": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.3.1.tgz", - "integrity": "sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw==", "license": "MIT", "dependencies": { "loose-envify": "^1.1.0", @@ -21205,8 +18910,6 @@ }, "node_modules/react-dom/node_modules/scheduler": { "version": "0.23.2", - "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.2.tgz", - "integrity": "sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ==", "license": "MIT", "dependencies": { "loose-envify": "^1.1.0" @@ -21214,8 +18917,6 @@ }, "node_modules/react-dropzone": { "version": "14.3.5", - "resolved": "https://registry.npmjs.org/react-dropzone/-/react-dropzone-14.3.5.tgz", - "integrity": "sha512-9nDUaEEpqZLOz5v5SUcFA0CjM4vq8YbqO0WRls+EYT7+DvxUdzDPKNCPLqGfj3YL9MsniCLCD4RFA6M95V6KMQ==", "license": "MIT", "dependencies": { "attr-accept": "^2.2.4", @@ -21231,8 +18932,6 @@ }, "node_modules/react-hook-form": { "version": "7.54.2", - "resolved": "https://registry.npmjs.org/react-hook-form/-/react-hook-form-7.54.2.tgz", - "integrity": "sha512-eHpAUgUjWbZocoQYUHposymRb4ZP6d0uwUnooL2uOybA9/3tPUvoAKqEWK1WaSiTxxOfTpffNZP7QwlnM3/gEg==", "license": "MIT", "engines": { "node": ">=18.0.0" @@ -21247,8 +18946,6 @@ }, "node_modules/react-immutable-proptypes": { "version": "2.2.0", - "resolved": "https://registry.npmjs.org/react-immutable-proptypes/-/react-immutable-proptypes-2.2.0.tgz", - "integrity": "sha512-Vf4gBsePlwdGvSZoLSBfd4HAP93HDauMY4fDjXhreg/vg6F3Fj/MXDNyTbltPC/xZKmZc+cjLu3598DdYK6sgQ==", "license": "MIT", "dependencies": { "invariant": "^2.2.2" @@ -21259,8 +18956,6 @@ }, "node_modules/react-immutable-pure-component": { "version": "2.2.2", - "resolved": "https://registry.npmjs.org/react-immutable-pure-component/-/react-immutable-pure-component-2.2.2.tgz", - "integrity": "sha512-vkgoMJUDqHZfXXnjVlG3keCxSO/U6WeDQ5/Sl0GK2cH8TOxEzQ5jXqDXHEL/jqk6fsNxV05oH5kD7VNMUE2k+A==", "license": "MIT", "peerDependencies": { "immutable": ">= 2 || >= 4.0.0-rc", @@ -21270,8 +18965,6 @@ }, "node_modules/react-inspector": { "version": "6.0.2", - "resolved": "https://registry.npmjs.org/react-inspector/-/react-inspector-6.0.2.tgz", - "integrity": "sha512-x+b7LxhmHXjHoU/VrFAzw5iutsILRoYyDq97EDYdFpPLcvqtEzk4ZSZSQjnFPbr5T57tLXnHcqFYoN1pI6u8uQ==", "license": "MIT", "peerDependencies": { "react": "^16.8.4 || ^17.0.0 || ^18.0.0" @@ -21279,14 +18972,10 @@ }, "node_modules/react-is": { "version": "16.13.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz", - "integrity": "sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==", "license": "MIT" }, "node_modules/react-markdown": { "version": "10.1.0", - "resolved": "https://registry.npmjs.org/react-markdown/-/react-markdown-10.1.0.tgz", - "integrity": "sha512-qKxVopLT/TyA6BX3Ue5NwabOsAzm0Q7kAPwq6L+wWDwisYs7R8vZ0nRXqq6rkueboxpkjvLGU9fWifiX/ZZFxQ==", "license": "MIT", "dependencies": { "@types/hast": "^3.0.0", @@ -21312,8 +19001,6 @@ }, "node_modules/react-markdown/node_modules/@types/hast": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", - "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", "license": "MIT", "dependencies": { "@types/unist": "*" @@ -21321,8 +19008,6 @@ }, "node_modules/react-reconciler": { "version": "0.27.0", - "resolved": "https://registry.npmjs.org/react-reconciler/-/react-reconciler-0.27.0.tgz", - "integrity": "sha512-HmMDKciQjYmBRGuuhIaKA1ba/7a+UsM5FzOZsMO2JYHt9Jh8reCb7j1eDC95NOyUlKM9KRyvdx0flBuDvYSBoA==", "license": "MIT", "dependencies": { "loose-envify": "^1.1.0", @@ -21337,8 +19022,6 @@ }, "node_modules/react-redux": { "version": "9.2.0", - "resolved": "https://registry.npmjs.org/react-redux/-/react-redux-9.2.0.tgz", - "integrity": "sha512-ROY9fvHhwOD9ySfrF0wmvu//bKCQ6AeZZq1nJNtbDC+kk5DuSuNX/n6YWYF/SYy7bSba4D4FSz8DJeKY/S/r+g==", "license": "MIT", "dependencies": { "@types/use-sync-external-store": "^0.0.6", @@ -21360,8 +19043,6 @@ }, "node_modules/react-remove-scroll": { "version": "2.6.3", - "resolved": "https://registry.npmjs.org/react-remove-scroll/-/react-remove-scroll-2.6.3.tgz", - "integrity": "sha512-pnAi91oOk8g8ABQKGF5/M9qxmmOPxaAnopyTHYfqYEwJhyFrbbBtHuSgtKEoH0jpcxx5o3hXqH1mNd9/Oi+8iQ==", "license": "MIT", "dependencies": { "react-remove-scroll-bar": "^2.3.7", @@ -21385,8 +19066,6 @@ }, "node_modules/react-remove-scroll-bar": { "version": "2.3.8", - "resolved": "https://registry.npmjs.org/react-remove-scroll-bar/-/react-remove-scroll-bar-2.3.8.tgz", - "integrity": "sha512-9r+yi9+mgU33AKcj6IbT9oRCO78WriSj6t/cF8DWBZJ9aOGPOTEDvdUDz1FwKim7QXWwmHqtdHnRJfhAxEG46Q==", "license": "MIT", "dependencies": { "react-style-singleton": "^2.2.2", @@ -21407,8 +19086,6 @@ }, "node_modules/react-smooth": { "version": "4.0.4", - "resolved": "https://registry.npmjs.org/react-smooth/-/react-smooth-4.0.4.tgz", - "integrity": "sha512-gnGKTpYwqL0Iii09gHobNolvX4Kiq4PKx6eWBCYYix+8cdw+cGo3do906l1NBPKkSWx1DghC1dlWG9L2uGd61Q==", "license": "MIT", "dependencies": { "fast-equals": "^5.0.1", @@ -21422,8 +19099,6 @@ }, "node_modules/react-style-singleton": { "version": "2.2.3", - "resolved": "https://registry.npmjs.org/react-style-singleton/-/react-style-singleton-2.2.3.tgz", - "integrity": "sha512-b6jSvxvVnyptAiLjbkWLE/lOnR4lfTtDAl+eUC7RZy+QQWc6wRzIV2CE6xBuMmDxc2qIihtDCZD5NPOFl7fRBQ==", "license": "MIT", "dependencies": { "get-nonce": "^1.0.0", @@ -21444,8 +19119,6 @@ }, "node_modules/react-syntax-highlighter": { "version": "15.6.1", - "resolved": "https://registry.npmjs.org/react-syntax-highlighter/-/react-syntax-highlighter-15.6.1.tgz", - "integrity": "sha512-OqJ2/vL7lEeV5zTJyG7kmARppUjiB9h9udl4qHQjjgEos66z00Ia0OckwYfRxCSFrW8RJIBnsBwQsHZbVPspqg==", "license": "MIT", "dependencies": { "@babel/runtime": "^7.3.1", @@ -21461,8 +19134,6 @@ }, "node_modules/react-transition-group": { "version": "4.4.5", - "resolved": "https://registry.npmjs.org/react-transition-group/-/react-transition-group-4.4.5.tgz", - "integrity": "sha512-pZcd1MCJoiKiBR2NRxeCRg13uCXbydPnmB4EOeRrY7480qNWO8IIgQG6zlDkm6uRMsURXPuKq0GWtiM59a5Q6g==", "license": "BSD-3-Clause", "dependencies": { "@babel/runtime": "^7.5.5", @@ -21477,31 +19148,25 @@ }, "node_modules/read-cache": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/read-cache/-/read-cache-1.0.0.tgz", - "integrity": "sha512-Owdv/Ft7IjOgm/i0xvNDZ1LrRANRfew4b2prF3OWMQLxLfu3bS8FVhCsrSCMK4lR56Y9ya+AThoTpDCTxCmpRA==", "license": "MIT", "dependencies": { "pify": "^2.3.0" } }, "node_modules/readable-stream": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", - "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", + "version": "1.1.14", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.1.14.tgz", + "integrity": "sha512-+MeVjFf4L44XUkhM1eYbD8fyEsxcV81pqMSR5gblfcLCHfZvbrqy4/qYHE+/R5HoBUT11WV5O08Cr1n3YXkWVQ==", "license": "MIT", "dependencies": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" - }, - "engines": { - "node": ">= 6" + "core-util-is": "~1.0.0", + "inherits": "~2.0.1", + "isarray": "0.0.1", + "string_decoder": "~0.10.x" } }, "node_modules/readdirp": { "version": "3.6.0", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", - "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", "license": "MIT", "dependencies": { "picomatch": "^2.2.1" @@ -21512,8 +19177,6 @@ }, "node_modules/recharts": { "version": "2.15.1", - "resolved": "https://registry.npmjs.org/recharts/-/recharts-2.15.1.tgz", - "integrity": "sha512-v8PUTUlyiDe56qUj82w/EDVuzEFXwEHp9/xOowGAZwfLjB9uAy3GllQVIYMWF6nU+qibx85WF75zD7AjqoT54Q==", "license": "MIT", "dependencies": { "clsx": "^2.0.0", @@ -21535,8 +19198,6 @@ }, "node_modules/recharts-scale": { "version": "0.4.5", - "resolved": "https://registry.npmjs.org/recharts-scale/-/recharts-scale-0.4.5.tgz", - "integrity": "sha512-kivNFO+0OcUNu7jQquLXAxz1FIwZj8nrj+YkOKc5694NbjCvcT6aSZiIzNzd2Kul4o4rTto8QVR9lMNtxD4G1w==", "license": "MIT", "dependencies": { "decimal.js-light": "^2.4.1" @@ -21544,8 +19205,6 @@ }, "node_modules/recharts/node_modules/react-is": { "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", "license": "MIT" }, "node_modules/record-cache": { @@ -21557,16 +19216,26 @@ "b4a": "^1.3.1" } }, + "node_modules/record-cache/node_modules/b4a": { + "version": "1.7.3", + "resolved": "https://registry.npmjs.org/b4a/-/b4a-1.7.3.tgz", + "integrity": "sha512-5Q2mfq2WfGuFp3uS//0s6baOJLMoVduPYVeNmDYxu5OUA1/cBfvr2RIS7vi62LdNj/urk1hfmj867I3qt6uZ7Q==", + "license": "Apache-2.0", + "peerDependencies": { + "react-native-b4a": "*" + }, + "peerDependenciesMeta": { + "react-native-b4a": { + "optional": true + } + } + }, "node_modules/redux": { "version": "5.0.1", - "resolved": "https://registry.npmjs.org/redux/-/redux-5.0.1.tgz", - "integrity": "sha512-M9/ELqF6fy8FwmkpnF0S3YKOqMyoWJ4+CS5Efg2ct3oY9daQvd/Pc71FpGZsVsbl3Cpb+IIcjBDUnnyBdQbq4w==", "license": "MIT" }, "node_modules/redux-immutable": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/redux-immutable/-/redux-immutable-4.0.0.tgz", - "integrity": "sha512-SchSn/DWfGb3oAejd+1hhHx01xUoxY+V7TeK0BKqpkLKiQPVFf7DYzEaKmrEVxsWxielKfSK9/Xq66YyxgR1cg==", "license": "BSD-3-Clause", "peerDependencies": { "immutable": "^3.8.1 || ^4.0.0-rc.1" @@ -21574,8 +19243,6 @@ }, "node_modules/reflect.getprototypeof": { "version": "1.0.10", - "resolved": "https://registry.npmjs.org/reflect.getprototypeof/-/reflect.getprototypeof-1.0.10.tgz", - "integrity": "sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==", "dev": true, "license": "MIT", "dependencies": { @@ -21597,8 +19264,6 @@ }, "node_modules/refractor": { "version": "3.6.0", - "resolved": "https://registry.npmjs.org/refractor/-/refractor-3.6.0.tgz", - "integrity": "sha512-MY9W41IOWxxk31o+YvFCNyNzdkc9M20NoZK5vq6jkv4I/uh2zkWcfudj0Q1fovjUQJrNewS9NMzeTtqPf+n5EA==", "license": "MIT", "dependencies": { "hastscript": "^6.0.0", @@ -21612,8 +19277,6 @@ }, "node_modules/refractor/node_modules/prismjs": { "version": "1.27.0", - "resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.27.0.tgz", - "integrity": "sha512-t13BGPUlFDR7wRB5kQDG4jjl7XeuH6jbJGt11JHPL96qwsEHNX2+68tFXqc1/k+/jALsbSWJKUOT/hcYAZ5LkA==", "license": "MIT", "engines": { "node": ">=6" @@ -21621,14 +19284,10 @@ }, "node_modules/regenerator-runtime": { "version": "0.14.1", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.1.tgz", - "integrity": "sha512-dYnhHh0nJoMfnkZs6GmmhFknAGRrLznOu5nc9ML+EJxGvrx6H7teuevqVqCuPcPK//3eDrrjQhehXVx9cnkGdw==", "license": "MIT" }, "node_modules/regexp.prototype.flags": { "version": "1.5.4", - "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.5.4.tgz", - "integrity": "sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==", "dev": true, "license": "MIT", "dependencies": { @@ -21648,8 +19307,6 @@ }, "node_modules/remark-gfm": { "version": "4.0.1", - "resolved": "https://registry.npmjs.org/remark-gfm/-/remark-gfm-4.0.1.tgz", - "integrity": "sha512-1quofZ2RQ9EWdeN34S79+KExV1764+wCUGop5CPL1WGdD0ocPpu91lzPGbwWMECpEpd42kJGQwzRfyov9j4yNg==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -21666,8 +19323,6 @@ }, "node_modules/remark-parse": { "version": "11.0.0", - "resolved": "https://registry.npmjs.org/remark-parse/-/remark-parse-11.0.0.tgz", - "integrity": "sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -21682,8 +19337,6 @@ }, "node_modules/remark-rehype": { "version": "11.1.2", - "resolved": "https://registry.npmjs.org/remark-rehype/-/remark-rehype-11.1.2.tgz", - "integrity": "sha512-Dh7l57ianaEoIpzbp0PC9UKAdCSVklD8E5Rpw7ETfbTl3FqcOOgq5q2LVDhgGCkaBv7p24JXikPdvhhmHvKMsw==", "license": "MIT", "dependencies": { "@types/hast": "^3.0.0", @@ -21699,8 +19352,6 @@ }, "node_modules/remark-rehype/node_modules/@types/hast": { "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", - "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", "license": "MIT", "dependencies": { "@types/unist": "*" @@ -21708,8 +19359,6 @@ }, "node_modules/remark-stringify": { "version": "11.0.0", - "resolved": "https://registry.npmjs.org/remark-stringify/-/remark-stringify-11.0.0.tgz", - "integrity": "sha512-1OSmLd3awB/t8qdoEOMazZkNsfVTeY4fTsgzcQFdXNq8ToTN4ZGwrMnlda4K6smTFKD+GRV6O48i6Z4iKgPPpw==", "license": "MIT", "dependencies": { "@types/mdast": "^4.0.0", @@ -21723,8 +19372,6 @@ }, "node_modules/remarkable": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/remarkable/-/remarkable-2.0.1.tgz", - "integrity": "sha512-YJyMcOH5lrR+kZdmB0aJJ4+93bEojRZ1HGDn9Eagu6ibg7aVZhc3OWbbShRid+Q5eAfsEqWxpe+g5W5nYNfNiA==", "license": "MIT", "dependencies": { "argparse": "^1.0.10", @@ -21739,8 +19386,6 @@ }, "node_modules/remarkable/node_modules/argparse": { "version": "1.0.10", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", - "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", "license": "MIT", "dependencies": { "sprintf-js": "~1.0.2" @@ -21748,14 +19393,10 @@ }, "node_modules/remarkable/node_modules/sprintf-js": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==", "license": "BSD-3-Clause" }, "node_modules/repeat-string": { "version": "1.6.1", - "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", - "integrity": "sha512-PV0dzCYDNfRi1jCDbJzpW7jNNDRuCOG/jI5ctQcGKt/clZD+YcPS3yIlWuTJMmESC8aevCFmWJy5wjAFgNqN6w==", "license": "MIT", "engines": { "node": ">=0.10" @@ -21777,8 +19418,6 @@ }, "node_modules/require-directory": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", - "integrity": "sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q==", "dev": true, "license": "MIT", "engines": { @@ -21787,8 +19426,6 @@ }, "node_modules/require-from-string": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", - "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", "license": "MIT", "engines": { "node": ">=0.10.0" @@ -21796,20 +19433,14 @@ }, "node_modules/requires-port": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz", - "integrity": "sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ==", "license": "MIT" }, "node_modules/reselect": { "version": "5.1.1", - "resolved": "https://registry.npmjs.org/reselect/-/reselect-5.1.1.tgz", - "integrity": "sha512-K/BG6eIky/SBpzfHZv/dd+9JBFiS4SWV7FIujVyJRux6e45+73RaUHXLmIR1f7WOMaQ0U1km6qwklRQxpJJY0w==", "license": "MIT" }, "node_modules/resolve": { "version": "1.22.10", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.10.tgz", - "integrity": "sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==", "license": "MIT", "dependencies": { "is-core-module": "^2.16.0", @@ -21828,8 +19459,6 @@ }, "node_modules/resolve-cwd": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-3.0.0.tgz", - "integrity": "sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg==", "dev": true, "license": "MIT", "dependencies": { @@ -21841,8 +19470,6 @@ }, "node_modules/resolve-cwd/node_modules/resolve-from": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", - "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==", "dev": true, "license": "MIT", "engines": { @@ -21851,8 +19478,6 @@ }, "node_modules/resolve-from": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", - "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", "dev": true, "license": "MIT", "engines": { @@ -21861,8 +19486,6 @@ }, "node_modules/resolve-pkg-maps": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/resolve-pkg-maps/-/resolve-pkg-maps-1.0.0.tgz", - "integrity": "sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==", "dev": true, "license": "MIT", "funding": { @@ -21871,8 +19494,6 @@ }, "node_modules/ret": { "version": "0.2.2", - "resolved": "https://registry.npmjs.org/ret/-/ret-0.2.2.tgz", - "integrity": "sha512-M0b3YWQs7R3Z917WRQy1HHA7Ba7D8hvZg6UE5mLykJxQVE2ju0IXbGlaHPPlkY+WN7wFP+wUMXmBFA0aV6vYGQ==", "license": "MIT", "engines": { "node": ">=4" @@ -21880,8 +19501,6 @@ }, "node_modules/retry": { "version": "0.13.1", - "resolved": "https://registry.npmjs.org/retry/-/retry-0.13.1.tgz", - "integrity": "sha512-XQBQ3I8W1Cge0Seh+6gjj03LbmRFWuoszgK9ooCpwYIrhhoO80pfq4cUkU5DkknwfOfFteRwlZ56PYOGYyFWdg==", "license": "MIT", "engines": { "node": ">= 4" @@ -21889,8 +19508,6 @@ }, "node_modules/reusify": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", - "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", "license": "MIT", "engines": { "iojs": ">=1.0.0", @@ -21899,9 +19516,6 @@ }, "node_modules/rimraf": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", - "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", - "deprecated": "Rimraf versions prior to v4 are no longer supported", "dev": true, "license": "ISC", "dependencies": { @@ -21916,8 +19530,6 @@ }, "node_modules/rimraf/node_modules/brace-expansion": { "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "dev": true, "license": "MIT", "dependencies": { @@ -21927,9 +19539,6 @@ }, "node_modules/rimraf/node_modules/glob": { "version": "7.2.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", - "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", - "deprecated": "Glob versions prior to v9 are no longer supported", "dev": true, "license": "ISC", "dependencies": { @@ -21949,8 +19558,6 @@ }, "node_modules/rimraf/node_modules/minimatch": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", "dev": true, "license": "ISC", "dependencies": { @@ -21961,25 +19568,24 @@ } }, "node_modules/ripemd160": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.2.tgz", - "integrity": "sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA==", + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.3.tgz", + "integrity": "sha512-5Di9UC0+8h1L6ZD2d7awM7E/T4uA1fJRlx6zk/NvdCCVEoAnFqvHmCuNeIKoCeIixBX/q8uM+6ycDvF8woqosA==", "license": "MIT", "dependencies": { - "hash-base": "^3.0.0", - "inherits": "^2.0.1" + "hash-base": "^3.1.2", + "inherits": "^2.0.4" + }, + "engines": { + "node": ">= 0.8" } }, "node_modules/robust-predicates": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/robust-predicates/-/robust-predicates-3.0.2.tgz", - "integrity": "sha512-IXgzBWvWQwE6PrDI05OvmXUIruQTcoMDzRsOd5CDvHCVLcLHMTSYvOK5Cm46kWqlV3yAbuSpBZdJ5oP5OUoStg==", "license": "Unlicense" }, "node_modules/run-parallel": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", - "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", "funding": [ { "type": "github", @@ -22053,8 +19659,6 @@ }, "node_modules/safe-array-concat": { "version": "1.1.3", - "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.1.3.tgz", - "integrity": "sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==", "dev": true, "license": "MIT", "dependencies": { @@ -22071,10 +19675,13 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/safe-array-concat/node_modules/isarray": { + "version": "2.0.5", + "dev": true, + "license": "MIT" + }, "node_modules/safe-buffer": { "version": "5.2.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", - "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", "funding": [ { "type": "github", @@ -22093,8 +19700,6 @@ }, "node_modules/safe-push-apply": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/safe-push-apply/-/safe-push-apply-1.0.0.tgz", - "integrity": "sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==", "dev": true, "license": "MIT", "dependencies": { @@ -22108,10 +19713,13 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/safe-push-apply/node_modules/isarray": { + "version": "2.0.5", + "dev": true, + "license": "MIT" + }, "node_modules/safe-regex-test": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.1.0.tgz", - "integrity": "sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==", "license": "MIT", "dependencies": { "call-bound": "^1.0.2", @@ -22133,8 +19741,6 @@ }, "node_modules/scheduler": { "version": "0.21.0", - "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.21.0.tgz", - "integrity": "sha512-1r87x5fz9MXqswA2ERLo0EbOAU74DpIUO090gIasYTqlVoJeMcl+Z1Rg7WHz+qtPujhS/hGIt9kxZOYBV3faRQ==", "license": "MIT", "dependencies": { "loose-envify": "^1.1.0" @@ -22148,8 +19754,6 @@ }, "node_modules/semver": { "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", "license": "ISC", "bin": { "semver": "bin/semver.js" @@ -22157,8 +19761,6 @@ }, "node_modules/serialize-error": { "version": "8.1.0", - "resolved": "https://registry.npmjs.org/serialize-error/-/serialize-error-8.1.0.tgz", - "integrity": "sha512-3NnuWfM6vBYoy5gZFvHiYsVbafvI9vZv/+jlIigFn4oP4zjNPK3LhcY0xSCgeb1a5L8jO71Mit9LlNoi2UfDDQ==", "license": "MIT", "dependencies": { "type-fest": "^0.20.2" @@ -22172,8 +19774,6 @@ }, "node_modules/serialize-error/node_modules/type-fest": { "version": "0.20.2", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", - "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", "license": "(MIT OR CC0-1.0)", "engines": { "node": ">=10" @@ -22184,8 +19784,6 @@ }, "node_modules/set-function-length": { "version": "1.2.2", - "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", - "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", "license": "MIT", "dependencies": { "define-data-property": "^1.1.4", @@ -22201,8 +19799,6 @@ }, "node_modules/set-function-name": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/set-function-name/-/set-function-name-2.0.2.tgz", - "integrity": "sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==", "dev": true, "license": "MIT", "dependencies": { @@ -22217,8 +19813,6 @@ }, "node_modules/set-proto": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/set-proto/-/set-proto-1.0.0.tgz", - "integrity": "sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==", "dev": true, "license": "MIT", "dependencies": { @@ -22232,21 +19826,26 @@ }, "node_modules/setimmediate": { "version": "1.0.5", - "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz", - "integrity": "sha512-MATJdZp8sLqDl/68LfQmbP8zKPLQNV6BIZoIgrscFDQ+RsvK/BxeDQOgyxKKoh0y/8h3BqVFnCqQ/gd+reiIXA==", "license": "MIT" }, "node_modules/sha.js": { - "version": "2.4.11", - "resolved": "https://registry.npmjs.org/sha.js/-/sha.js-2.4.11.tgz", - "integrity": "sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ==", + "version": "2.4.12", + "resolved": "https://registry.npmjs.org/sha.js/-/sha.js-2.4.12.tgz", + "integrity": "sha512-8LzC5+bvI45BjpfXU8V5fdU2mfeKiQe1D1gIMn7XUlF3OTUrpdJpPPH4EMAnF0DsHHdSZqCdSss5qCmJKuiO3w==", "license": "(MIT AND BSD-3-Clause)", "dependencies": { - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" + "inherits": "^2.0.4", + "safe-buffer": "^5.2.1", + "to-buffer": "^1.2.0" }, "bin": { "sha.js": "bin.js" + }, + "engines": { + "node": ">= 0.10" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, "node_modules/sharp": { @@ -22254,6 +19853,7 @@ "resolved": "https://registry.npmjs.org/sharp/-/sharp-0.34.4.tgz", "integrity": "sha512-FUH39xp3SBPnxWvd5iib1X8XY7J0K0X7d93sie9CJg2PO8/7gmg89Nve6OjItK53/MlAushNNxteBYfM6DEuoA==", "hasInstallScript": true, + "license": "Apache-2.0", "optional": true, "dependencies": { "@img/colour": "^1.0.0", @@ -22292,9 +19892,10 @@ } }, "node_modules/sharp/node_modules/semver": { - "version": "7.7.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.2.tgz", - "integrity": "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==", + "version": "7.7.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.3.tgz", + "integrity": "sha512-SdsKMrI9TdgjdweUSR9MweHA4EJ8YxHn8DFaDisvhVlUOe4BF1tLD7GAj0lIqWVl+dPb/rExr0Btby5loQm20Q==", + "license": "ISC", "optional": true, "bin": { "semver": "bin/semver.js" @@ -22305,8 +19906,6 @@ }, "node_modules/shebang-command": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", - "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", "license": "MIT", "dependencies": { "shebang-regex": "^3.0.0" @@ -22317,8 +19916,6 @@ }, "node_modules/shebang-regex": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", - "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", "license": "MIT", "engines": { "node": ">=8" @@ -22326,8 +19923,6 @@ }, "node_modules/short-unique-id": { "version": "5.3.2", - "resolved": "https://registry.npmjs.org/short-unique-id/-/short-unique-id-5.3.2.tgz", - "integrity": "sha512-KRT/hufMSxXKEDSQujfVE0Faa/kZ51ihUcZQAcmP04t00DvPj7Ox5anHke1sJYUtzSuiT/Y5uyzg/W7bBEGhCg==", "license": "Apache-2.0", "bin": { "short-unique-id": "bin/short-unique-id", @@ -22336,8 +19931,6 @@ }, "node_modules/side-channel": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.1.0.tgz", - "integrity": "sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==", "dev": true, "license": "MIT", "dependencies": { @@ -22356,8 +19949,6 @@ }, "node_modules/side-channel-list": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/side-channel-list/-/side-channel-list-1.0.0.tgz", - "integrity": "sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==", "dev": true, "license": "MIT", "dependencies": { @@ -22373,8 +19964,6 @@ }, "node_modules/side-channel-map": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/side-channel-map/-/side-channel-map-1.0.1.tgz", - "integrity": "sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==", "dev": true, "license": "MIT", "dependencies": { @@ -22392,8 +19981,6 @@ }, "node_modules/side-channel-weakmap": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/side-channel-weakmap/-/side-channel-weakmap-1.0.2.tgz", - "integrity": "sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==", "dev": true, "license": "MIT", "dependencies": { @@ -22412,8 +19999,6 @@ }, "node_modules/signal-exit": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-4.1.0.tgz", - "integrity": "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==", "license": "ISC", "engines": { "node": ">=14" @@ -22469,14 +20054,10 @@ }, "node_modules/simplesignal": { "version": "2.1.7", - "resolved": "https://registry.npmjs.org/simplesignal/-/simplesignal-2.1.7.tgz", - "integrity": "sha512-PEo2qWpUke7IMhlqiBxrulIFvhJRLkl1ih52Rwa+bPjzhJepcd4GIjn2RiQmFSx3dQvsEAgF0/lXMwMN7vODaA==", "license": "MIT" }, "node_modules/slash": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", - "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", "dev": true, "license": "MIT", "engines": { @@ -22494,12 +20075,12 @@ } }, "node_modules/socks": { - "version": "2.8.4", - "resolved": "https://registry.npmjs.org/socks/-/socks-2.8.4.tgz", - "integrity": "sha512-D3YaD0aRxR3mEcqnidIs7ReYJFVzWdd6fXJYUM8ixcQcJRGTka/b3saV0KflYhyVJXKhb947GndU35SxYNResQ==", + "version": "2.8.7", + "resolved": "https://registry.npmjs.org/socks/-/socks-2.8.7.tgz", + "integrity": "sha512-HLpt+uLy/pxB+bum/9DzAgiKS8CX1EvbWxI4zlmgGCExImLdiad2iCwXT5Z4c9c3Eq8rP2318mPW2c+QbtjK8A==", "license": "MIT", "dependencies": { - "ip-address": "^9.0.5", + "ip-address": "^10.0.1", "smart-buffer": "^4.2.0" }, "engines": { @@ -22507,10 +20088,17 @@ "npm": ">= 3.0.0" } }, + "node_modules/socks/node_modules/ip-address": { + "version": "10.0.1", + "resolved": "https://registry.npmjs.org/ip-address/-/ip-address-10.0.1.tgz", + "integrity": "sha512-NWv9YLW4PoW2B7xtzaS3NCot75m6nK7Icdv0o3lfMceJVRfSoQwqD4wEH5rLwoKJwUiZ/rfpiVBhnaF0FK4HoA==", + "license": "MIT", + "engines": { + "node": ">= 12" + } + }, "node_modules/source-map": { "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", "dev": true, "license": "BSD-3-Clause", "engines": { @@ -22519,8 +20107,6 @@ }, "node_modules/source-map-js": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.1.tgz", - "integrity": "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==", "license": "BSD-3-Clause", "engines": { "node": ">=0.10.0" @@ -22528,8 +20114,6 @@ }, "node_modules/source-map-support": { "version": "0.5.13", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.13.tgz", - "integrity": "sha512-SHSKFHadjVA5oR4PPqhtAVdcBWwRYVd6g6cAXnIbRiIwc2EhPrTuKUBdSLvlEKyIP3GCf89fltvcZiP9MMFA1w==", "dev": true, "license": "MIT", "dependencies": { @@ -22539,8 +20123,6 @@ }, "node_modules/space-separated-tokens": { "version": "1.1.5", - "resolved": "https://registry.npmjs.org/space-separated-tokens/-/space-separated-tokens-1.1.5.tgz", - "integrity": "sha512-q/JSVd1Lptzhf5bkYm4ob4iWPjx0KiRe3sRFBNrVqbJkFaBm5vbbowy1mymoPNLRa52+oadOhJ+K49wsSeSjTA==", "license": "MIT", "funding": { "type": "github", @@ -22577,15 +20159,11 @@ }, "node_modules/stable-hash": { "version": "0.0.4", - "resolved": "https://registry.npmjs.org/stable-hash/-/stable-hash-0.0.4.tgz", - "integrity": "sha512-LjdcbuBeLcdETCrPn9i8AYAZ1eCtu4ECAWtP7UleOiZ9LzVxRzzUZEoZ8zB24nhkQnDWyET0I+3sWokSDS3E7g==", "dev": true, "license": "MIT" }, "node_modules/stack-utils": { "version": "2.0.6", - "resolved": "https://registry.npmjs.org/stack-utils/-/stack-utils-2.0.6.tgz", - "integrity": "sha512-XlkWvfIm6RmsWtNJx+uqtKLS8eqFbxUg0ZzLXqY0caEy9l7hruX8IpiDnjsLavoBgqCCR71TqWO8MaXYheJ3RQ==", "dev": true, "license": "MIT", "dependencies": { @@ -22597,8 +20175,6 @@ }, "node_modules/stack-utils/node_modules/escape-string-regexp": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-2.0.0.tgz", - "integrity": "sha512-UpzcLCXolUWcNu5HtVMHYdXJjArjsF9C0aNnquZYY4uW/Vu0miy5YoWvbV345HauVvcAUnpRuhMMcqTcGOY2+w==", "dev": true, "license": "MIT", "engines": { @@ -22607,8 +20183,6 @@ }, "node_modules/stats-gl": { "version": "2.4.2", - "resolved": "https://registry.npmjs.org/stats-gl/-/stats-gl-2.4.2.tgz", - "integrity": "sha512-g5O9B0hm9CvnM36+v7SFl39T7hmAlv541tU81ME8YeSb3i1CIP5/QdDeSB3A0la0bKNHpxpwxOVRo2wFTYEosQ==", "license": "MIT", "dependencies": { "@types/three": "*", @@ -22621,28 +20195,22 @@ }, "node_modules/stats-gl/node_modules/three": { "version": "0.170.0", - "resolved": "https://registry.npmjs.org/three/-/three-0.170.0.tgz", - "integrity": "sha512-FQK+LEpYc0fBD+J8g6oSEyyNzjp+Q7Ks1C568WWaoMRLW+TkNNWmenWeGgJjV105Gd+p/2ql1ZcjYvNiPZBhuQ==", "license": "MIT" }, "node_modules/stats.js": { "version": "0.17.0", - "resolved": "https://registry.npmjs.org/stats.js/-/stats.js-0.17.0.tgz", - "integrity": "sha512-hNKz8phvYLPEcRkeG1rsGmV5ChMjKDAWU7/OJJdDErPBNChQXxCo3WZurGpnWc6gZhAzEPFad1aVgyOANH1sMw==", "license": "MIT" }, "node_modules/streamsearch": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/streamsearch/-/streamsearch-1.1.0.tgz", - "integrity": "sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg==", "engines": { "node": ">=10.0.0" } }, "node_modules/streamx": { - "version": "2.22.0", - "resolved": "https://registry.npmjs.org/streamx/-/streamx-2.22.0.tgz", - "integrity": "sha512-sLh1evHOzBy/iWRiR6d1zRcLao4gGZr3C1kzNz4fopCOKJb6xD9ub8Mpi9Mr1R6id5o43S+d93fI48UC5uM9aw==", + "version": "2.22.1", + "resolved": "https://registry.npmjs.org/streamx/-/streamx-2.22.1.tgz", + "integrity": "sha512-znKXEBxfatz2GBNK02kRnCXjV+AA4kjZIUxeWSr3UGirZMJfTE9uiwKHobnbgxWyL/JWro8tTq+vOqAK1/qbSA==", "license": "MIT", "dependencies": { "fast-fifo": "^1.3.2", @@ -22653,18 +20221,13 @@ } }, "node_modules/string_decoder": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", - "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", - "license": "MIT", - "dependencies": { - "safe-buffer": "~5.2.0" - } + "version": "0.10.31", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", + "integrity": "sha512-ev2QzSzWPYmy9GuqfIVildA4OdcGLeFZQrq5ys6RtiuF+RQQiZWr8TZNyAcuVXyQRYfEO+MsoB/1BuQVhOJuoQ==", + "license": "MIT" }, "node_modules/string-length": { "version": "4.0.2", - "resolved": "https://registry.npmjs.org/string-length/-/string-length-4.0.2.tgz", - "integrity": "sha512-+l6rNN5fYHNhZZy41RXsYptCjA2Igmq4EG7kZAYFQI1E1VTXarr6ZPXBg6eq7Y6eK4FEhY6AJlyuFIb/v/S0VQ==", "dev": true, "license": "MIT", "dependencies": { @@ -22677,8 +20240,6 @@ }, "node_modules/string-width": { "version": "5.1.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz", - "integrity": "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==", "license": "MIT", "dependencies": { "eastasianwidth": "^0.2.0", @@ -22695,8 +20256,6 @@ "node_modules/string-width-cjs": { "name": "string-width", "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", "license": "MIT", "dependencies": { "emoji-regex": "^8.0.0", @@ -22709,14 +20268,10 @@ }, "node_modules/string-width-cjs/node_modules/emoji-regex": { "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", "license": "MIT" }, "node_modules/string-width/node_modules/ansi-regex": { "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz", - "integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==", "license": "MIT", "engines": { "node": ">=12" @@ -22727,8 +20282,6 @@ }, "node_modules/string-width/node_modules/strip-ansi": { "version": "7.1.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", - "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", "license": "MIT", "dependencies": { "ansi-regex": "^6.0.1" @@ -22742,8 +20295,6 @@ }, "node_modules/string.prototype.includes": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/string.prototype.includes/-/string.prototype.includes-2.0.1.tgz", - "integrity": "sha512-o7+c9bW6zpAdJHTtujeePODAhkuicdAryFsfVKwA+wGw89wJ4GTY484WTucM9hLtDEOpOvI+aHnzqnC5lHp4Rg==", "dev": true, "license": "MIT", "dependencies": { @@ -22757,8 +20308,6 @@ }, "node_modules/string.prototype.matchall": { "version": "4.0.12", - "resolved": "https://registry.npmjs.org/string.prototype.matchall/-/string.prototype.matchall-4.0.12.tgz", - "integrity": "sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==", "dev": true, "license": "MIT", "dependencies": { @@ -22785,8 +20334,6 @@ }, "node_modules/string.prototype.repeat": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/string.prototype.repeat/-/string.prototype.repeat-1.0.0.tgz", - "integrity": "sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==", "dev": true, "license": "MIT", "dependencies": { @@ -22796,8 +20343,6 @@ }, "node_modules/string.prototype.trim": { "version": "1.2.10", - "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.2.10.tgz", - "integrity": "sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==", "dev": true, "license": "MIT", "dependencies": { @@ -22818,8 +20363,6 @@ }, "node_modules/string.prototype.trimend": { "version": "1.0.9", - "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.9.tgz", - "integrity": "sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==", "dev": true, "license": "MIT", "dependencies": { @@ -22837,8 +20380,6 @@ }, "node_modules/string.prototype.trimstart": { "version": "1.0.8", - "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.8.tgz", - "integrity": "sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==", "dev": true, "license": "MIT", "dependencies": { @@ -22868,8 +20409,6 @@ }, "node_modules/stringify-entities": { "version": "4.0.4", - "resolved": "https://registry.npmjs.org/stringify-entities/-/stringify-entities-4.0.4.tgz", - "integrity": "sha512-IwfBptatlO+QCJUo19AqvrPNqlVMpW9YEL2LIVY+Rpv2qsjCGxaDLNRgeGsQWJhfItebuJhsGSLjaBbNSQ+ieg==", "license": "MIT", "dependencies": { "character-entities-html4": "^2.0.0", @@ -22882,8 +20421,6 @@ }, "node_modules/stringify-entities/node_modules/character-entities-legacy": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", - "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", "license": "MIT", "funding": { "type": "github", @@ -22892,8 +20429,6 @@ }, "node_modules/strip-ansi": { "version": "6.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", - "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", "license": "MIT", "dependencies": { "ansi-regex": "^5.0.1" @@ -22905,8 +20440,6 @@ "node_modules/strip-ansi-cjs": { "name": "strip-ansi", "version": "6.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", - "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", "license": "MIT", "dependencies": { "ansi-regex": "^5.0.1" @@ -22917,8 +20450,6 @@ }, "node_modules/strip-bom": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", - "integrity": "sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==", "dev": true, "license": "MIT", "engines": { @@ -22927,8 +20458,7 @@ }, "node_modules/strip-final-newline": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-2.0.0.tgz", - "integrity": "sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==", + "dev": true, "license": "MIT", "engines": { "node": ">=6" @@ -22936,8 +20466,6 @@ }, "node_modules/strip-json-comments": { "version": "3.1.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", - "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", "dev": true, "license": "MIT", "engines": { @@ -22949,8 +20477,6 @@ }, "node_modules/style-to-js": { "version": "1.1.17", - "resolved": "https://registry.npmjs.org/style-to-js/-/style-to-js-1.1.17.tgz", - "integrity": "sha512-xQcBGDxJb6jjFCTzvQtfiPn6YvvP2O8U1MDIPNfJQlWMYfktPy+iGsHE7cssjs7y84d9fQaK4UF3RIJaAHSoYA==", "license": "MIT", "dependencies": { "style-to-object": "1.0.9" @@ -22958,8 +20484,6 @@ }, "node_modules/style-to-object": { "version": "1.0.9", - "resolved": "https://registry.npmjs.org/style-to-object/-/style-to-object-1.0.9.tgz", - "integrity": "sha512-G4qppLgKu/k6FwRpHiGiKPaPTFcG3g4wNVX/Qsfu+RqQM30E7Tyu/TEgxcL9PNLF5pdRLwQdE3YKKf+KF2Dzlw==", "license": "MIT", "dependencies": { "inline-style-parser": "0.2.4" @@ -22969,6 +20493,7 @@ "version": "5.1.6", "resolved": "https://registry.npmjs.org/styled-jsx/-/styled-jsx-5.1.6.tgz", "integrity": "sha512-qSVyDTeMotdvQYoHWLNGwRFJHC+i+ZvdBRYosOFgC+Wg1vx4frN2/RG/NA7SYqqvKNLf39P2LSRA2pu6n0XYZA==", + "license": "MIT", "dependencies": { "client-only": "0.0.1" }, @@ -22989,8 +20514,6 @@ }, "node_modules/sucrase": { "version": "3.35.0", - "resolved": "https://registry.npmjs.org/sucrase/-/sucrase-3.35.0.tgz", - "integrity": "sha512-8EbVDiu9iN/nESwxeSxDKe0dunta1GOlHufmSSXxMD2z2/tMZpDMpvXQGsc+ajGo8y2uYUmixaSRUc/QPoQ0GA==", "license": "MIT", "dependencies": { "@jridgewell/gen-mapping": "^0.3.2", @@ -23011,8 +20534,6 @@ }, "node_modules/superjson": { "version": "2.2.2", - "resolved": "https://registry.npmjs.org/superjson/-/superjson-2.2.2.tgz", - "integrity": "sha512-5JRxVqC8I8NuOUjzBbvVJAKNM8qoVuH0O77h4WInc/qC2q5IreqKxYwgkga3PfA22OayK2ikceb/B26dztPl+Q==", "license": "MIT", "dependencies": { "copy-anything": "^3.0.2" @@ -23023,9 +20544,6 @@ }, "node_modules/supports-color": { "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dev": true, "license": "MIT", "dependencies": { "has-flag": "^4.0.0" @@ -23036,8 +20554,6 @@ }, "node_modules/supports-preserve-symlinks-flag": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", - "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", "license": "MIT", "engines": { "node": ">= 0.4" @@ -23048,8 +20564,6 @@ }, "node_modules/suspend-react": { "version": "0.1.3", - "resolved": "https://registry.npmjs.org/suspend-react/-/suspend-react-0.1.3.tgz", - "integrity": "sha512-aqldKgX9aZqpoDp3e8/BZ8Dm7x1pJl+qI3ZKxDN0i/IQTWUwBx/ManmlVJ3wowqbno6c2bmiIfs+Um6LbsjJyQ==", "license": "MIT", "peerDependencies": { "react": ">=17.0" @@ -23057,8 +20571,6 @@ }, "node_modules/swagger-client": { "version": "3.35.3", - "resolved": "https://registry.npmjs.org/swagger-client/-/swagger-client-3.35.3.tgz", - "integrity": "sha512-4bO+dhBbasP485Ak67o46cWNVUnV0/92ypb2997bhvxTO2M+IuQZM1ilkN/7nSaiGuxDKJhkuL54I35PVI3AAw==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.22.15", @@ -23083,8 +20595,6 @@ }, "node_modules/swagger-jsdoc": { "version": "6.2.8", - "resolved": "https://registry.npmjs.org/swagger-jsdoc/-/swagger-jsdoc-6.2.8.tgz", - "integrity": "sha512-VPvil1+JRpmJ55CgAtn8DIcpBs0bL5L3q5bVQvF4tAW/k/9JYSj7dCpaYCAv5rufe0vcCbBRQXGvzpkWjvLklQ==", "license": "MIT", "dependencies": { "commander": "6.2.0", @@ -23103,8 +20613,6 @@ }, "node_modules/swagger-jsdoc/node_modules/brace-expansion": { "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "license": "MIT", "dependencies": { "balanced-match": "^1.0.0", @@ -23113,8 +20621,6 @@ }, "node_modules/swagger-jsdoc/node_modules/commander": { "version": "6.2.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-6.2.0.tgz", - "integrity": "sha512-zP4jEKbe8SHzKJYQmq8Y9gYjtO/POJLgIdKgV7B9qNmABVFVc+ctqSX6iXh4mCpJfRBOabiZ2YKPg8ciDw6C+Q==", "license": "MIT", "engines": { "node": ">= 6" @@ -23122,9 +20628,6 @@ }, "node_modules/swagger-jsdoc/node_modules/glob": { "version": "7.1.6", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", - "integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==", - "deprecated": "Glob versions prior to v9 are no longer supported", "license": "ISC", "dependencies": { "fs.realpath": "^1.0.0", @@ -23143,8 +20646,6 @@ }, "node_modules/swagger-jsdoc/node_modules/minimatch": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", "license": "ISC", "dependencies": { "brace-expansion": "^1.1.7" @@ -23155,8 +20656,6 @@ }, "node_modules/swagger-jsdoc/node_modules/yaml": { "version": "2.0.0-1", - "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.0.0-1.tgz", - "integrity": "sha512-W7h5dEhywMKenDJh2iX/LABkbFnBxasD27oyXWDS/feDsxiw0dD5ncXdYXgkvAsXIY2MpW/ZKkr9IU30DBdMNQ==", "license": "ISC", "engines": { "node": ">= 6" @@ -23164,8 +20663,6 @@ }, "node_modules/swagger-parser": { "version": "10.0.3", - "resolved": "https://registry.npmjs.org/swagger-parser/-/swagger-parser-10.0.3.tgz", - "integrity": "sha512-nF7oMeL4KypldrQhac8RyHerJeGPD1p2xDh900GPvc+Nk7nWP6jX2FcC7WmkinMoAmoO774+AFXcWsW8gMWEIg==", "license": "MIT", "dependencies": { "@apidevtools/swagger-parser": "10.0.3" @@ -23176,8 +20673,6 @@ }, "node_modules/swagger-ui-react": { "version": "5.22.0", - "resolved": "https://registry.npmjs.org/swagger-ui-react/-/swagger-ui-react-5.22.0.tgz", - "integrity": "sha512-Y0TEWg2qD4u/dgZ9q9G16yM/Edvyz0ovkIZlpACN8X/2gzSoIzS/fhSpLSJfCOxRt2UqrKmajMB11VK6cGZk2g==", "license": "Apache-2.0", "dependencies": { "@babel/runtime-corejs3": "^7.27.1", @@ -23221,8 +20716,6 @@ }, "node_modules/synckit": { "version": "0.11.11", - "resolved": "https://registry.npmjs.org/synckit/-/synckit-0.11.11.tgz", - "integrity": "sha512-MeQTA1r0litLUf0Rp/iisCaL8761lKAZHaimlbGK4j0HysC4PLfqygQj9srcs0m2RdtDYnF8UuYyKpbjHYp7Jw==", "dev": true, "license": "MIT", "dependencies": { @@ -23237,8 +20730,6 @@ }, "node_modules/tailwind-merge": { "version": "2.6.0", - "resolved": "https://registry.npmjs.org/tailwind-merge/-/tailwind-merge-2.6.0.tgz", - "integrity": "sha512-P+Vu1qXfzediirmHOC3xKGAYeZtPcV9g76X+xg2FD4tYgR71ewMA35Y3sCz3zhiN/dwefRpJX0yBcgwi1fXNQA==", "license": "MIT", "funding": { "type": "github", @@ -23247,8 +20738,6 @@ }, "node_modules/tailwindcss": { "version": "3.4.17", - "resolved": "https://registry.npmjs.org/tailwindcss/-/tailwindcss-3.4.17.tgz", - "integrity": "sha512-w33E2aCvSDP0tW9RZuNXadXlkHXqFzSkQew/aIa2i/Sj8fThxwovwlXHSPXTbAHwEIhBFXAedUhP2tueAKP8Og==", "license": "MIT", "dependencies": { "@alloc/quick-lru": "^5.2.0", @@ -23284,8 +20773,6 @@ }, "node_modules/tailwindcss-animate": { "version": "1.0.7", - "resolved": "https://registry.npmjs.org/tailwindcss-animate/-/tailwindcss-animate-1.0.7.tgz", - "integrity": "sha512-bl6mpH3T7I3UFxuvDEXLxy/VuFxBk5bbzplh7tXI68mwMokNYd1t9qPBHlnyTwfa4JGC4zP516I1hYYtQ/vspA==", "license": "MIT", "peerDependencies": { "tailwindcss": ">=3.0.0 || insiders" @@ -23293,8 +20780,6 @@ }, "node_modules/tailwindcss/node_modules/object-hash": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-3.0.0.tgz", - "integrity": "sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw==", "license": "MIT", "engines": { "node": ">= 6" @@ -23302,8 +20787,6 @@ }, "node_modules/tapable": { "version": "2.2.1", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", - "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==", "dev": true, "license": "MIT", "engines": { @@ -23311,9 +20794,9 @@ } }, "node_modules/tar-fs": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.2.tgz", - "integrity": "sha512-EsaAXwxmx8UB7FRKqeozqEPop69DXcmYwTQwXvyAPF352HJsPdkVhvTaDPYqfNgruveJIJy3TA2l+2zj8LJIJA==", + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.4.tgz", + "integrity": "sha512-mDAjwmZdh7LTT6pNleZ05Yt65HC3E+NiQzl672vQG38jIrehtJk/J3mNwIg+vShQPcLF/LV7CMnDW6vjj6sfYQ==", "license": "MIT", "dependencies": { "chownr": "^1.1.1", @@ -23338,10 +20821,31 @@ "node": ">=6" } }, + "node_modules/tar-stream/node_modules/readable-stream": { + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", + "license": "MIT", + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/tar-stream/node_modules/string_decoder": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", + "license": "MIT", + "dependencies": { + "safe-buffer": "~5.2.0" + } + }, "node_modules/test-exclude": { "version": "6.0.0", - "resolved": "https://registry.npmjs.org/test-exclude/-/test-exclude-6.0.0.tgz", - "integrity": "sha512-cAGWPIyOHU6zlmg88jwm7VRyXnMN7iV68OGAbYDk/Mh/xC/pzVPlQtY6ngoIH/5/tciuhGfvESU8GrHrcxD56w==", "dev": true, "license": "ISC", "dependencies": { @@ -23355,8 +20859,6 @@ }, "node_modules/test-exclude/node_modules/brace-expansion": { "version": "1.1.12", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.12.tgz", - "integrity": "sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==", "dev": true, "license": "MIT", "dependencies": { @@ -23366,9 +20868,6 @@ }, "node_modules/test-exclude/node_modules/glob": { "version": "7.2.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", - "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", - "deprecated": "Glob versions prior to v9 are no longer supported", "dev": true, "license": "ISC", "dependencies": { @@ -23388,8 +20887,6 @@ }, "node_modules/test-exclude/node_modules/minimatch": { "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", "dev": true, "license": "ISC", "dependencies": { @@ -23408,17 +20905,26 @@ "b4a": "^1.6.4" } }, + "node_modules/text-decoder/node_modules/b4a": { + "version": "1.7.3", + "resolved": "https://registry.npmjs.org/b4a/-/b4a-1.7.3.tgz", + "integrity": "sha512-5Q2mfq2WfGuFp3uS//0s6baOJLMoVduPYVeNmDYxu5OUA1/cBfvr2RIS7vi62LdNj/urk1hfmj867I3qt6uZ7Q==", + "license": "Apache-2.0", + "peerDependencies": { + "react-native-b4a": "*" + }, + "peerDependenciesMeta": { + "react-native-b4a": { + "optional": true + } + } + }, "node_modules/text-table": { "version": "0.2.0", - "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", - "integrity": "sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==", - "dev": true, "license": "MIT" }, "node_modules/thenify": { "version": "3.3.1", - "resolved": "https://registry.npmjs.org/thenify/-/thenify-3.3.1.tgz", - "integrity": "sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw==", "license": "MIT", "dependencies": { "any-promise": "^1.0.0" @@ -23426,8 +20932,6 @@ }, "node_modules/thenify-all": { "version": "1.6.0", - "resolved": "https://registry.npmjs.org/thenify-all/-/thenify-all-1.6.0.tgz", - "integrity": "sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA==", "license": "MIT", "dependencies": { "thenify": ">= 3.1.0 < 4" @@ -23438,14 +20942,10 @@ }, "node_modules/three": { "version": "0.168.0", - "resolved": "https://registry.npmjs.org/three/-/three-0.168.0.tgz", - "integrity": "sha512-6m6jXtDwMJEK/GGMbAOTSAmxNdzKvvBzgd7q8bE/7Tr6m7PaBh5kKLrN7faWtlglXbzj7sVba48Idwx+NRsZXw==", "license": "MIT" }, "node_modules/three-conic-polygon-geometry": { "version": "2.1.2", - "resolved": "https://registry.npmjs.org/three-conic-polygon-geometry/-/three-conic-polygon-geometry-2.1.2.tgz", - "integrity": "sha512-NaP3RWLJIyPGI+zyaZwd0Yj6rkoxm4FJHqAX1Enb4L64oNYLCn4bz1ESgOEYavgcUwCNYINu1AgEoUBJr1wZcA==", "license": "MIT", "dependencies": { "@turf/boolean-point-in-polygon": "^7.2", @@ -23465,8 +20965,6 @@ }, "node_modules/three-geojson-geometry": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/three-geojson-geometry/-/three-geojson-geometry-2.1.1.tgz", - "integrity": "sha512-dC7bF3ri1goDcihYhzACHOBQqu7YNNazYLa2bSydVIiJUb3jDFojKSy+gNj2pMkqZNSVjssSmdY9zlmnhEpr1w==", "license": "MIT", "dependencies": { "d3-geo": "1 - 3", @@ -23482,8 +20980,6 @@ }, "node_modules/three-globe": { "version": "2.41.4", - "resolved": "https://registry.npmjs.org/three-globe/-/three-globe-2.41.4.tgz", - "integrity": "sha512-zyFHP8uFoLnxZwTYYZ7j0D2CFJDeQeHBM9GS+tSMmFHw063vVC3NQhOwl5hA+utEGjlZzAOU0SbEDWNgsHehaA==", "license": "MIT", "dependencies": { "@tweenjs/tween.js": "18 - 25", @@ -23514,9 +21010,6 @@ }, "node_modules/three-mesh-bvh": { "version": "0.7.8", - "resolved": "https://registry.npmjs.org/three-mesh-bvh/-/three-mesh-bvh-0.7.8.tgz", - "integrity": "sha512-BGEZTOIC14U0XIRw3tO4jY7IjP7n7v24nv9JXS1CyeVRWOCkcOMhRnmENUjuV39gktAw4Ofhr0OvIAiTspQrrw==", - "deprecated": "Deprecated due to three.js version incompatibility. Please use v0.8.0, instead.", "license": "MIT", "peerDependencies": { "three": ">= 0.151.0" @@ -23524,8 +21017,6 @@ }, "node_modules/three-slippy-map-globe": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/three-slippy-map-globe/-/three-slippy-map-globe-1.0.3.tgz", - "integrity": "sha512-Y9WCA/tTL8yH8FHVSXVQss/P0V36utTNhuixzFPj0Bs0SXxO+Vui133oAQmMpx4BLXYZpWZwcqHM2i3MfFlYWw==", "license": "MIT", "dependencies": { "d3-geo": "1 - 3", @@ -23541,8 +21032,6 @@ }, "node_modules/three-stdlib": { "version": "2.35.12", - "resolved": "https://registry.npmjs.org/three-stdlib/-/three-stdlib-2.35.12.tgz", - "integrity": "sha512-3Mb3U7gtf1orCb6j2BBcc8BJsBVoCYUjFtwaq9KM8I7ippz4o9G+aDQdT5AF8Sg5FXXZfnPPccP6ufsP8bgG3g==", "license": "MIT", "dependencies": { "@types/draco3d": "^1.4.0", @@ -23558,8 +21047,6 @@ }, "node_modules/three-stdlib/node_modules/fflate": { "version": "0.6.10", - "resolved": "https://registry.npmjs.org/fflate/-/fflate-0.6.10.tgz", - "integrity": "sha512-IQrh3lEPM93wVCEczc9SaAOvkmcoQn/G8Bo1e8ZPlY3X3bnAxWaBdvTdvM1hP62iZp0BXWDy4vTAy4fF0+Dlpg==", "license": "MIT" }, "node_modules/through": { @@ -23569,9 +21056,9 @@ "license": "MIT" }, "node_modules/throughput": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/throughput/-/throughput-1.0.1.tgz", - "integrity": "sha512-4Mvv5P4xyVz6RM07wS3tGyZ/kPAiKtLeqznq3hK4pxDiTUSyQ5xeFlBiWxflCWexvSnxo2aAfedzKajJqihz4Q==", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/throughput/-/throughput-1.0.2.tgz", + "integrity": "sha512-jvK1ZXuhsggjb3qYQjMiU/AVYYiTeqT5thWvYR2yuy2LGM84P5MSSyAinwHahGsdBYKR9m9HncVR/3f3nFKkxg==", "license": "MIT" }, "node_modules/thunky": { @@ -23589,20 +21076,19 @@ }, "node_modules/tiny-invariant": { "version": "1.3.3", - "resolved": "https://registry.npmjs.org/tiny-invariant/-/tiny-invariant-1.3.3.tgz", - "integrity": "sha512-+FbBPE1o9QAYvviau/qC5SE3caw21q3xkvWKBtja5vgqOWIHHJ3ioaq1VPfn/Szqctz2bU/oYeKd9/z5BL+PVg==", "license": "MIT" }, "node_modules/tinycolor2": { "version": "1.6.0", - "resolved": "https://registry.npmjs.org/tinycolor2/-/tinycolor2-1.6.0.tgz", - "integrity": "sha512-XPaBkWQJdsf3pLKJV9p4qN/S+fm2Oj8AIPo1BTUhg5oxkvm9+SVEGFdhyOz7tTdUTfvxMiAs4sp6/eZO2Ew+pw==", + "license": "MIT" + }, + "node_modules/tinyexec": { + "version": "1.0.1", + "devOptional": true, "license": "MIT" }, "node_modules/tmpl": { "version": "1.0.5", - "resolved": "https://registry.npmjs.org/tmpl/-/tmpl-1.0.5.tgz", - "integrity": "sha512-3f0uOEAQwIqGuWW2MVzYg8fV/QNnc/IpuJNG837rLuczAaLVHslWHZQj4IGiEl5Hs3kkbhwL9Ab7Hrsmuj+Smw==", "dev": true, "license": "BSD-3-Clause" }, @@ -23610,6 +21096,7 @@ "version": "1.2.2", "resolved": "https://registry.npmjs.org/to-buffer/-/to-buffer-1.2.2.tgz", "integrity": "sha512-db0E3UJjcFhpDhAF4tLo03oli3pwl3dbnzXOUIlRKrp+ldk/VUxzpWYZENsw2SZiuBjHAk7DfB0VU7NKdpb6sw==", + "license": "MIT", "dependencies": { "isarray": "^2.0.5", "safe-buffer": "^5.2.1", @@ -23619,10 +21106,14 @@ "node": ">= 0.4" } }, + "node_modules/to-buffer/node_modules/isarray": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", + "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", + "license": "MIT" + }, "node_modules/to-regex-range": { "version": "5.0.1", - "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", - "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", "license": "MIT", "dependencies": { "is-number": "^7.0.0" @@ -23633,14 +21124,12 @@ }, "node_modules/toggle-selection": { "version": "1.0.6", - "resolved": "https://registry.npmjs.org/toggle-selection/-/toggle-selection-1.0.6.tgz", - "integrity": "sha512-BiZS+C1OS8g/q2RRbJmy59xpyghNBqrr6k5L/uKBGRsTfxmu3ffiRnd8mlGPUVayg8pvfi5urfnu8TU7DVOkLQ==", "license": "MIT" }, "node_modules/torrent-discovery": { - "version": "11.0.15", - "resolved": "https://registry.npmjs.org/torrent-discovery/-/torrent-discovery-11.0.15.tgz", - "integrity": "sha512-O5kCZ/PDcK0PMD5lH4VdwUrL4Wfe1Kt3pjcrMp3yieNQq/ZcnLuae6jnjSvpzoa7DxpYc5OqhkiIOYGyvj1tbA==", + "version": "11.0.19", + "resolved": "https://registry.npmjs.org/torrent-discovery/-/torrent-discovery-11.0.19.tgz", + "integrity": "sha512-BLhdj7o0px+u72UuhJmq6CB0LBkZOa1nwgbd5ktyTELJlvcRL8EoxSSmSpzMOIScLGgslh1uLaAy/POhLpagtg==", "funding": [ { "type": "github", @@ -23657,10 +21146,10 @@ ], "license": "MIT", "dependencies": { - "bittorrent-dht": "^11.0.9", + "bittorrent-dht": "^11.0.11", "bittorrent-lsd": "^2.0.0", - "bittorrent-tracker": "^11.2.1", - "debug": "^4.4.0", + "bittorrent-tracker": "^11.2.2", + "debug": "^4.4.3", "run-parallel": "^1.2.0" }, "engines": { @@ -23668,9 +21157,9 @@ } }, "node_modules/torrent-piece": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/torrent-piece/-/torrent-piece-3.0.1.tgz", - "integrity": "sha512-EvCqfOkNm3PXqgaGPVVmp0JlGC8fDpH+8Yt5uUiF4oCrAqy3htyUFxK1DJpneWfg1fFdeTKsstxLxQUrHpmocA==", + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/torrent-piece/-/torrent-piece-3.0.2.tgz", + "integrity": "sha512-K1A5tZ3BolFrUtnBpk9iDg8av1na0OgQ7E0IlA9tj0bcsPhLhzvln+oMtMmtkqAwmUsbNCilRm2ymUdZg0rVbQ==", "funding": [ { "type": "github", @@ -23701,8 +21190,6 @@ }, "node_modules/tree-sitter": { "version": "0.21.1", - "resolved": "https://registry.npmjs.org/tree-sitter/-/tree-sitter-0.21.1.tgz", - "integrity": "sha512-7dxoA6kYvtgWw80265MyqJlkRl4yawIjO7S5MigytjELkX43fV2WsAXzsNfO7sBpPPCF5Gp0+XzHk0DwLCq3xQ==", "hasInstallScript": true, "license": "MIT", "optional": true, @@ -23714,8 +21201,6 @@ }, "node_modules/tree-sitter-json": { "version": "0.24.8", - "resolved": "https://registry.npmjs.org/tree-sitter-json/-/tree-sitter-json-0.24.8.tgz", - "integrity": "sha512-Tc9ZZYwHyWZ3Tt1VEw7Pa2scu1YO7/d2BCBbKTx5hXwig3UfdQjsOPkPyLpDJOn/m1UBEWYAtSdGAwCSyagBqQ==", "hasInstallScript": true, "license": "MIT", "optional": true, @@ -23734,8 +21219,6 @@ }, "node_modules/trim-lines": { "version": "3.0.1", - "resolved": "https://registry.npmjs.org/trim-lines/-/trim-lines-3.0.1.tgz", - "integrity": "sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg==", "license": "MIT", "funding": { "type": "github", @@ -23744,8 +21227,6 @@ }, "node_modules/troika-three-text": { "version": "0.52.3", - "resolved": "https://registry.npmjs.org/troika-three-text/-/troika-three-text-0.52.3.tgz", - "integrity": "sha512-jLhiwgV8kEkwWjvK12f2fHVpbOC75p7SgPQ0cgcz+IMtN5Bdyg4EuFdwuTOVu9ga8UeYdKBpzd1AxviyixtYTQ==", "license": "MIT", "dependencies": { "bidi-js": "^1.0.2", @@ -23759,8 +21240,6 @@ }, "node_modules/troika-three-utils": { "version": "0.52.0", - "resolved": "https://registry.npmjs.org/troika-three-utils/-/troika-three-utils-0.52.0.tgz", - "integrity": "sha512-00oxqIIehtEKInOTQekgyknBuRUj1POfOUE2q1OmL+Xlpp4gIu+S0oA0schTyXsDS4d9DkR04iqCdD40rF5R6w==", "license": "MIT", "peerDependencies": { "three": ">=0.125.0" @@ -23768,14 +21247,10 @@ }, "node_modules/troika-worker-utils": { "version": "0.52.0", - "resolved": "https://registry.npmjs.org/troika-worker-utils/-/troika-worker-utils-0.52.0.tgz", - "integrity": "sha512-W1CpvTHykaPH5brv5VHLfQo9D1OYuo0cSBEUQFFT/nBUzM8iD6Lq2/tgG/f1OelbAS1WtaTPQzE5uM49egnngw==", "license": "MIT" }, "node_modules/trough": { "version": "2.2.0", - "resolved": "https://registry.npmjs.org/trough/-/trough-2.2.0.tgz", - "integrity": "sha512-tmMpK00BjZiUyVyvrBK7knerNgmgvcV/KLVyuma/SC+TQN167GrMRciANTz09+k3zW8L8t60jWO1GpfkZdjTaw==", "license": "MIT", "funding": { "type": "github", @@ -23784,8 +21259,6 @@ }, "node_modules/ts-api-utils": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-2.0.0.tgz", - "integrity": "sha512-xCt/TOAc+EOHS1XPnijD3/yzpH6qg2xppZO1YDqGoVsNXfQfzHpOdNuXwrwOU8u4ITXJyDCTyt8w5g1sZv9ynQ==", "dev": true, "license": "MIT", "engines": { @@ -23806,14 +21279,10 @@ }, "node_modules/ts-interface-checker": { "version": "0.1.13", - "resolved": "https://registry.npmjs.org/ts-interface-checker/-/ts-interface-checker-0.1.13.tgz", - "integrity": "sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==", "license": "Apache-2.0" }, "node_modules/ts-jest": { "version": "29.4.4", - "resolved": "https://registry.npmjs.org/ts-jest/-/ts-jest-29.4.4.tgz", - "integrity": "sha512-ccVcRABct5ZELCT5U0+DZwkXMCcOCLi2doHRrKy1nK/s7J7bch6TzJMsrY09WxgUUIP/ITfmcDS8D2yl63rnXw==", "dev": true, "license": "MIT", "dependencies": { @@ -23865,8 +21334,6 @@ }, "node_modules/ts-jest/node_modules/semver": { "version": "7.7.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.2.tgz", - "integrity": "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==", "dev": true, "license": "ISC", "bin": { @@ -23878,8 +21345,6 @@ }, "node_modules/ts-jest/node_modules/type-fest": { "version": "4.41.0", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-4.41.0.tgz", - "integrity": "sha512-TeTSQ6H5YHvpqVwBRcnLDCBnDOHWYu7IvGbHT6N8AOymcr9PJGjc1GTtiWZTYg0NCgYwvnYWEkVChQAr9bjfwA==", "dev": true, "license": "(MIT OR CC0-1.0)", "engines": { @@ -23897,20 +21362,14 @@ }, "node_modules/ts-mixer": { "version": "6.0.4", - "resolved": "https://registry.npmjs.org/ts-mixer/-/ts-mixer-6.0.4.tgz", - "integrity": "sha512-ufKpbmrugz5Aou4wcr5Wc1UUFWOLhq+Fm6qa6P0w0K5Qw2yhaUoiWszhCVuNQyNwrlGiscHOmqYoAox1PtvgjA==", "license": "MIT" }, "node_modules/ts-toolbelt": { "version": "9.6.0", - "resolved": "https://registry.npmjs.org/ts-toolbelt/-/ts-toolbelt-9.6.0.tgz", - "integrity": "sha512-nsZd8ZeNUzukXPlJmTBwUAuABDe/9qtVDelJeT/qW0ow3ZS3BsQJtNkan1802aM9Uf68/Y8ljw86Hu0h5IUW3w==", "license": "Apache-2.0" }, "node_modules/tsconfig-paths": { "version": "3.15.0", - "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.15.0.tgz", - "integrity": "sha512-2Ac2RgzDe/cn48GvOe3M+o82pEFewD3UPbyoUHHdKasHwJKjds4fLXWf/Ux5kATBKN20oaFGu+jbElp1pos0mg==", "dev": true, "license": "MIT", "dependencies": { @@ -23922,8 +21381,6 @@ }, "node_modules/tsconfig-paths/node_modules/json5": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.2.tgz", - "integrity": "sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==", "dev": true, "license": "MIT", "dependencies": { @@ -23935,8 +21392,6 @@ }, "node_modules/tslib": { "version": "2.8.1", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz", - "integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==", "license": "0BSD" }, "node_modules/tunnel-agent": { @@ -23953,8 +21408,6 @@ }, "node_modules/tunnel-rat": { "version": "0.1.2", - "resolved": "https://registry.npmjs.org/tunnel-rat/-/tunnel-rat-0.1.2.tgz", - "integrity": "sha512-lR5VHmkPhzdhrM092lI2nACsLO4QubF0/yoOhzX7c+wIpbN1GjHNzCc91QlpxBi+cnx8vVJ+Ur6vL5cEoQPFpQ==", "license": "MIT", "dependencies": { "zustand": "^4.3.2" @@ -23968,8 +21421,6 @@ }, "node_modules/type-check": { "version": "0.4.0", - "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", - "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", "dev": true, "license": "MIT", "dependencies": { @@ -23981,8 +21432,6 @@ }, "node_modules/type-detect": { "version": "4.0.8", - "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-4.0.8.tgz", - "integrity": "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==", "dev": true, "license": "MIT", "engines": { @@ -24003,8 +21452,6 @@ }, "node_modules/typed-array-buffer": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/typed-array-buffer/-/typed-array-buffer-1.0.3.tgz", - "integrity": "sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==", "license": "MIT", "dependencies": { "call-bound": "^1.0.3", @@ -24017,8 +21464,6 @@ }, "node_modules/typed-array-byte-length": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/typed-array-byte-length/-/typed-array-byte-length-1.0.3.tgz", - "integrity": "sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==", "dev": true, "license": "MIT", "dependencies": { @@ -24037,8 +21482,6 @@ }, "node_modules/typed-array-byte-offset": { "version": "1.0.4", - "resolved": "https://registry.npmjs.org/typed-array-byte-offset/-/typed-array-byte-offset-1.0.4.tgz", - "integrity": "sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==", "dev": true, "license": "MIT", "dependencies": { @@ -24059,8 +21502,6 @@ }, "node_modules/typed-array-length": { "version": "1.0.7", - "resolved": "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.7.tgz", - "integrity": "sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==", "dev": true, "license": "MIT", "dependencies": { @@ -24086,8 +21527,6 @@ }, "node_modules/types-ramda": { "version": "0.30.1", - "resolved": "https://registry.npmjs.org/types-ramda/-/types-ramda-0.30.1.tgz", - "integrity": "sha512-1HTsf5/QVRmLzcGfldPFvkVsAdi1db1BBKzi7iW3KBUlOICg/nKnFS+jGqDJS3YD8VsWbAh7JiHeBvbsw8RPxA==", "license": "MIT", "dependencies": { "ts-toolbelt": "^9.6.0" @@ -24095,8 +21534,6 @@ }, "node_modules/typescript": { "version": "5.7.3", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.7.3.tgz", - "integrity": "sha512-84MVSjMEHP+FQRPy3pX9sTVV/INIex71s9TL2Gm5FG/WG1SqXeKyZ0k7/blY/4FdOzI12CBy1vGc4og/eus0fw==", "license": "Apache-2.0", "bin": { "tsc": "bin/tsc", @@ -24108,8 +21545,6 @@ }, "node_modules/uglify-js": { "version": "3.19.3", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.19.3.tgz", - "integrity": "sha512-v3Xu+yuwBXisp6QYTcH4UbH+xYJXqnq2m/LtQVWKWzYc1iehYnLixoQDN9FH6/j9/oybfd6W9Ghwkl8+UMKTKQ==", "dev": true, "license": "BSD-2-Clause", "optional": true, @@ -24168,8 +21603,6 @@ }, "node_modules/unbox-primitive": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.1.0.tgz", - "integrity": "sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==", "dev": true, "license": "MIT", "dependencies": { @@ -24187,8 +21620,6 @@ }, "node_modules/undici": { "version": "5.28.5", - "resolved": "https://registry.npmjs.org/undici/-/undici-5.28.5.tgz", - "integrity": "sha512-zICwjrDrcrUE0pyyJc1I2QzBkLM8FINsgOrt6WjA+BgajVq9Nxu2PbFFXUrAggLfDXlZGZBVZYw7WNV5KiBiBA==", "license": "MIT", "dependencies": { "@fastify/busboy": "^2.0.0" @@ -24199,14 +21630,10 @@ }, "node_modules/undici-types": { "version": "6.19.8", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.19.8.tgz", - "integrity": "sha512-ve2KP6f/JnbPBFyobGHuerC9g1FYGn/F8n1LWTwNxCEzd6IfqTwUQcNXgEtmmQ6DlRrC1hrSrBnCZPokRrDHjw==", "license": "MIT" }, "node_modules/unified": { "version": "11.0.5", - "resolved": "https://registry.npmjs.org/unified/-/unified-11.0.5.tgz", - "integrity": "sha512-xKvGhPWw3k84Qjh8bI3ZeJjqnyadK+GEFtazSfZv/rKeTkTjOJho6mFqh2SM96iIcZokxiOpg78GazTSg8+KHA==", "license": "MIT", "dependencies": { "@types/unist": "^3.0.0", @@ -24224,14 +21651,10 @@ }, "node_modules/unified/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/unist-util-is": { "version": "6.0.0", - "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-6.0.0.tgz", - "integrity": "sha512-2qCTHimwdxLfz+YzdGfkqNlH0tLi9xjTnHddPmJwtIG9MGsdbutfTc4P+haPD7l7Cjxf/WZj+we5qfVPvvxfYw==", "license": "MIT", "dependencies": { "@types/unist": "^3.0.0" @@ -24243,14 +21666,10 @@ }, "node_modules/unist-util-is/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/unist-util-position": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/unist-util-position/-/unist-util-position-5.0.0.tgz", - "integrity": "sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==", "license": "MIT", "dependencies": { "@types/unist": "^3.0.0" @@ -24262,14 +21681,10 @@ }, "node_modules/unist-util-position/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/unist-util-stringify-position": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-4.0.0.tgz", - "integrity": "sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==", "license": "MIT", "dependencies": { "@types/unist": "^3.0.0" @@ -24281,14 +21696,10 @@ }, "node_modules/unist-util-stringify-position/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/unist-util-visit": { "version": "5.0.0", - "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-5.0.0.tgz", - "integrity": "sha512-MR04uvD+07cwl/yhVuVWAtw+3GOR/knlL55Nd/wAdblk27GCVt3lqpTivy/tkJcZoNPzTwS1Y+KMojlLDhoTzg==", "license": "MIT", "dependencies": { "@types/unist": "^3.0.0", @@ -24302,8 +21713,6 @@ }, "node_modules/unist-util-visit-parents": { "version": "6.0.1", - "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-6.0.1.tgz", - "integrity": "sha512-L/PqWzfTP9lzzEa6CKs0k2nARxTdZduw3zyh8d2NVBnsyvHjSX4TWse388YrrQKbvI8w20fGjGlhgT96WwKykw==", "license": "MIT", "dependencies": { "@types/unist": "^3.0.0", @@ -24316,20 +21725,14 @@ }, "node_modules/unist-util-visit-parents/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/unist-util-visit/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/universal-user-agent": { "version": "7.0.2", - "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-7.0.2.tgz", - "integrity": "sha512-0JCqzSKnStlRRQfCdowvqy3cy0Dvtlb8xecj/H8JFZuCze4rwjPZQOgvFvn0Ws/usCHQFGpyr+pB9adaGwXn4Q==", "license": "ISC" }, "node_modules/unordered-array-remove": { @@ -24347,14 +21750,10 @@ }, "node_modules/unraw": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/unraw/-/unraw-3.0.0.tgz", - "integrity": "sha512-08/DA66UF65OlpUDIQtbJyrqTR0jTAlJ+jsnkQ4jxR7+K5g5YG1APZKQSMCE1vqqmD+2pv6+IdEjmopFatacvg==", "license": "MIT" }, "node_modules/unrs-resolver": { "version": "1.11.1", - "resolved": "https://registry.npmjs.org/unrs-resolver/-/unrs-resolver-1.11.1.tgz", - "integrity": "sha512-bSjt9pjaEBnNiGgc9rUiHGKv5l4/TGzDmYw3RhnkJGtLhbnnA/5qJj7x3dNDCRx/PJxu774LlH8lCOlB4hEfKg==", "dev": true, "hasInstallScript": true, "license": "MIT", @@ -24388,8 +21787,6 @@ }, "node_modules/update-browserslist-db": { "version": "1.1.3", - "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.1.3.tgz", - "integrity": "sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw==", "funding": [ { "type": "opencollective", @@ -24418,8 +21815,6 @@ }, "node_modules/uri-js": { "version": "4.4.1", - "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", - "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", "dev": true, "license": "BSD-2-Clause", "dependencies": { @@ -24428,8 +21823,6 @@ }, "node_modules/url-parse": { "version": "1.5.10", - "resolved": "https://registry.npmjs.org/url-parse/-/url-parse-1.5.10.tgz", - "integrity": "sha512-WypcfiRhfeUP9vvF0j6rw0J3hrWrw6iZv3+22h6iRMJ/8z1Tj6XfLP4DsUix5MhMPnXpiHDoKyoZ/bdCkwBCiQ==", "license": "MIT", "dependencies": { "querystringify": "^2.1.1", @@ -24438,8 +21831,6 @@ }, "node_modules/use-callback-ref": { "version": "1.3.3", - "resolved": "https://registry.npmjs.org/use-callback-ref/-/use-callback-ref-1.3.3.tgz", - "integrity": "sha512-jQL3lRnocaFtu3V00JToYz/4QkNWswxijDaCVNZRiRTO3HQDLsdu1ZtmIUvV4yPp+rvWm5j0y0TG/S61cuijTg==", "license": "MIT", "dependencies": { "tslib": "^2.0.0" @@ -24459,8 +21850,6 @@ }, "node_modules/use-sidecar": { "version": "1.1.3", - "resolved": "https://registry.npmjs.org/use-sidecar/-/use-sidecar-1.1.3.tgz", - "integrity": "sha512-Fedw0aZvkhynoPYlA5WXrMCAMm+nSWdZt6lzJQ7Ok8S6Q+VsHmHpRWndVRJ8Be0ZbkfPc5LRYH+5XrzXcEeLRQ==", "license": "MIT", "dependencies": { "detect-node-es": "^1.1.0", @@ -24481,8 +21870,6 @@ }, "node_modules/use-sync-external-store": { "version": "1.4.0", - "resolved": "https://registry.npmjs.org/use-sync-external-store/-/use-sync-external-store-1.4.0.tgz", - "integrity": "sha512-9WXSPC5fMv61vaupRkCKCxsPxBocVnwakBEkMIHHpkTTg6icbJtg6jzgtLDm4bl3cSHAca52rYWih0k4K3PfHw==", "license": "MIT", "peerDependencies": { "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" @@ -24575,14 +21962,10 @@ }, "node_modules/util-deprecate": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", "license": "MIT" }, "node_modules/utility-types": { "version": "3.11.0", - "resolved": "https://registry.npmjs.org/utility-types/-/utility-types-3.11.0.tgz", - "integrity": "sha512-6Z7Ma2aVEWisaL6TvBCy7P8rm2LQoPv6dJ7ecIaIixHcwfbJ0x7mWdbcwlIM5IGQxPZSFYeqRCqlOOeKoJYMkw==", "license": "MIT", "engines": { "node": ">= 4" @@ -24609,10 +21992,33 @@ "node": ">=8.12" } }, + "node_modules/utp-native/node_modules/readable-stream": { + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", + "license": "MIT", + "optional": true, + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/utp-native/node_modules/string_decoder": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", + "license": "MIT", + "optional": true, + "dependencies": { + "safe-buffer": "~5.2.0" + } + }, "node_modules/uuid": { "version": "11.1.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-11.1.0.tgz", - "integrity": "sha512-0/A9rDy9P7cJ+8w1c9WD9V//9Wj15Ce2MPz8Ri6032usz+NfePxx5AcN3bN+r6ZL6jEo066/yNYB3tn4pQEx+A==", "funding": [ "https://github.com/sponsors/broofa", "https://github.com/sponsors/ctavan" @@ -24624,8 +22030,6 @@ }, "node_modules/v8-to-istanbul": { "version": "9.3.0", - "resolved": "https://registry.npmjs.org/v8-to-istanbul/-/v8-to-istanbul-9.3.0.tgz", - "integrity": "sha512-kiGUalWN+rgBJ/1OHZsBtU4rXZOfj/7rKQxULKlIzwzQSvMJUUNgPwJEEh7gU6xEVxC0ahoOBvN2YI8GH6FNgA==", "dev": true, "license": "ISC", "dependencies": { @@ -24639,8 +22043,6 @@ }, "node_modules/validator": { "version": "13.15.0", - "resolved": "https://registry.npmjs.org/validator/-/validator-13.15.0.tgz", - "integrity": "sha512-36B2ryl4+oL5QxZ3AzD0t5SsMNGvTtQHpjgFO5tbNxfXbMFkY822ktCDe1MnlqV3301QQI9SLHDNJokDI+Z9pA==", "license": "MIT", "engines": { "node": ">= 0.10" @@ -24666,8 +22068,6 @@ }, "node_modules/vary": { "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", "license": "MIT", "engines": { "node": ">= 0.8" @@ -24675,8 +22075,6 @@ }, "node_modules/vfile": { "version": "6.0.3", - "resolved": "https://registry.npmjs.org/vfile/-/vfile-6.0.3.tgz", - "integrity": "sha512-KzIbH/9tXat2u30jf+smMwFCsno4wHVdNmzFyL+T/L3UGqqk6JKfVqOFOZEpZSHADH1k40ab6NUIXZq422ov3Q==", "license": "MIT", "dependencies": { "@types/unist": "^3.0.0", @@ -24689,8 +22087,6 @@ }, "node_modules/vfile-message": { "version": "4.0.3", - "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-4.0.3.tgz", - "integrity": "sha512-QTHzsGd1EhbZs4AsQ20JX1rC3cOlt/IWJruk893DfLRr57lcnOeMaWG4K0JrRta4mIJZKth2Au3mM3u03/JWKw==", "license": "MIT", "dependencies": { "@types/unist": "^3.0.0", @@ -24703,20 +22099,14 @@ }, "node_modules/vfile-message/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/vfile/node_modules/@types/unist": { "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz", - "integrity": "sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==", "license": "MIT" }, "node_modules/victory-vendor": { "version": "36.9.2", - "resolved": "https://registry.npmjs.org/victory-vendor/-/victory-vendor-36.9.2.tgz", - "integrity": "sha512-PnpQQMuxlwYdocC8fIJqVXvkeViHYzotI+NJrCuav0ZYFoq912ZHBk3mCeuj+5/VpodOjPe1z0Fk2ihgzlXqjQ==", "license": "MIT AND ISC", "dependencies": { "@types/d3-array": "^3.0.3", @@ -24743,8 +22133,6 @@ }, "node_modules/walker": { "version": "1.0.8", - "resolved": "https://registry.npmjs.org/walker/-/walker-1.0.8.tgz", - "integrity": "sha512-ts/8E8l5b7kY0vlWLewOkDXMmPdLcVV4GmOQLyxuSswIJsweeFZtAsMF7k1Nszz+TYBQrlYRmzOnr398y1JemQ==", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -24765,8 +22153,6 @@ }, "node_modules/web-streams-polyfill": { "version": "3.3.3", - "resolved": "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-3.3.3.tgz", - "integrity": "sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw==", "license": "MIT", "engines": { "node": ">= 8" @@ -24774,8 +22160,6 @@ }, "node_modules/web-tree-sitter": { "version": "0.24.5", - "resolved": "https://registry.npmjs.org/web-tree-sitter/-/web-tree-sitter-0.24.5.tgz", - "integrity": "sha512-+J/2VSHN8J47gQUAvF8KDadrfz6uFYVjxoxbKWDoXVsH2u7yLdarCnIURnrMA6uSRkgX3SdmqM5BOoQjPdSh5w==", "license": "MIT", "optional": true }, @@ -24799,14 +22183,10 @@ "license": "MPL-2.0" }, "node_modules/webgl-constants": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/webgl-constants/-/webgl-constants-1.1.1.tgz", - "integrity": "sha512-LkBXKjU5r9vAW7Gcu3T5u+5cvSvh5WwINdr0C+9jpzVB41cjQAP5ePArDtk/WHYdVj0GefCgM73BA7FlIiNtdg==" + "version": "1.1.1" }, "node_modules/webgl-sdf-generator": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/webgl-sdf-generator/-/webgl-sdf-generator-1.1.1.tgz", - "integrity": "sha512-9Z0JcMTFxeE+b2x1LJTdnaT8rT8aEp7MVxkNwoycNmJWwPdzoXzMh0BjJSh/AEFP+KPYZUli814h8bJZFIZ2jA==", "license": "MIT" }, "node_modules/webidl-conversions": { @@ -24829,9 +22209,9 @@ } }, "node_modules/webtorrent": { - "version": "2.5.19", - "resolved": "https://registry.npmjs.org/webtorrent/-/webtorrent-2.5.19.tgz", - "integrity": "sha512-5SW5xGlBPIlP7m3f6gecJ83H2BSvoan5gzaAyMnDiQfXxxt5Ja5FAfZ16n1rdnD1WL/Iz+y4fE7or/a9egoF9A==", + "version": "2.8.4", + "resolved": "https://registry.npmjs.org/webtorrent/-/webtorrent-2.8.4.tgz", + "integrity": "sha512-OTzeMVa6r9GXzjj428HC5gSi6oRKFEqOpR5cwQ8+GtbYgQz6PF6y3tzqnVFf6xWvnKcoZiabpHud3gx01Cbt2A==", "funding": [ { "type": "github", @@ -24848,26 +22228,26 @@ ], "license": "MIT", "dependencies": { - "@silentbot1/nat-api": "^0.4.7", + "@silentbot1/nat-api": "^0.4.8", "@thaunknown/simple-peer": "^10.0.11", "@webtorrent/http-node": "^1.3.0", "addr-to-ip-port": "^2.0.0", "bitfield": "^4.2.0", - "bittorrent-dht": "^11.0.9", - "bittorrent-protocol": "^4.1.16", + "bittorrent-dht": "^11.0.10", + "bittorrent-protocol": "^4.1.20", "cache-chunk-store": "^3.2.2", - "chunk-store-iterator": "^1.0.3", + "chunk-store-iterator": "^1.0.4", "cpus": "^1.0.3", "create-torrent": "^6.1.0", "cross-fetch-ponyfill": "^1.0.3", - "debug": "^4.4.0", + "debug": "^4.4.1", "escape-html": "^1.0.3", - "fs-chunk-store": "^4.1.0", + "fs-chunk-store": "^5.0.0", "fsa-chunk-store": "^1.3.0", "immediate-chunk-store": "^2.2.0", "join-async-iterator": "^1.1.1", "load-ip-set": "^3.0.1", - "lt_donthave": "^2.0.4", + "lt_donthave": "^2.0.5", "memory-chunk-store": "^1.3.5", "mime": "^3.0.0", "once": "^1.4.0", @@ -24879,10 +22259,10 @@ "run-parallel": "^1.2.0", "run-parallel-limit": "^1.1.0", "speed-limiter": "^1.0.2", - "streamx": "2.22.0", - "throughput": "^1.0.1", - "torrent-discovery": "^11.0.15", - "torrent-piece": "^3.0.1", + "streamx": "2.22.1", + "throughput": "^1.0.2", + "torrent-discovery": "^11.0.17", + "torrent-piece": "^3.0.2", "uint8-util": "^2.2.5", "unordered-array-remove": "^1.0.2", "ut_metadata": "^4.0.3", @@ -24907,8 +22287,6 @@ }, "node_modules/which": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", - "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", "license": "ISC", "dependencies": { "isexe": "^2.0.0" @@ -24922,8 +22300,6 @@ }, "node_modules/which-boxed-primitive": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.1.1.tgz", - "integrity": "sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==", "dev": true, "license": "MIT", "dependencies": { @@ -24942,8 +22318,6 @@ }, "node_modules/which-builtin-type": { "version": "1.2.1", - "resolved": "https://registry.npmjs.org/which-builtin-type/-/which-builtin-type-1.2.1.tgz", - "integrity": "sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==", "dev": true, "license": "MIT", "dependencies": { @@ -24968,10 +22342,13 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/which-builtin-type/node_modules/isarray": { + "version": "2.0.5", + "dev": true, + "license": "MIT" + }, "node_modules/which-collection": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/which-collection/-/which-collection-1.0.2.tgz", - "integrity": "sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==", "dev": true, "license": "MIT", "dependencies": { @@ -24988,16 +22365,14 @@ } }, "node_modules/which-runtime": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/which-runtime/-/which-runtime-1.2.1.tgz", - "integrity": "sha512-8feIHccQFH/whiA1fD1b4c5+Q7T4ry1g1oHYc2mHnFh81tTQFsCvy3zhS2geUapkFAVBddUT/AM1a3rbqJweFg==", + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/which-runtime/-/which-runtime-1.3.2.tgz", + "integrity": "sha512-5kwCfWml7+b2NO7KrLMhYihjRx0teKkd3yGp1Xk5Vaf2JGdSh+rgVhEALAD9c/59dP+YwJHXoEO7e8QPy7gOkw==", "license": "Apache-2.0", "optional": true }, "node_modules/which-typed-array": { "version": "1.1.18", - "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.18.tgz", - "integrity": "sha512-qEcY+KJYlWyLH9vNbsr6/5j59AXk5ni5aakf8ldzBvGde6Iz4sxZGkJyWSAueTG7QhOvNRYb1lDdFmL5Td0QKA==", "license": "MIT", "dependencies": { "available-typed-arrays": "^1.0.7", @@ -25054,8 +22429,6 @@ }, "node_modules/word-wrap": { "version": "1.2.5", - "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.5.tgz", - "integrity": "sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==", "dev": true, "license": "MIT", "engines": { @@ -25064,15 +22437,11 @@ }, "node_modules/wordwrap": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", - "integrity": "sha512-gvVzJFlPycKc5dZN4yPkP8w7Dc37BtP1yczEneOb4uq34pXZcvrtRTmWV8W+Ume+XCxKgbjM+nevkyFPMybd4Q==", "dev": true, "license": "MIT" }, "node_modules/wrap-ansi": { "version": "8.1.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-8.1.0.tgz", - "integrity": "sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ==", "license": "MIT", "dependencies": { "ansi-styles": "^6.1.0", @@ -25089,8 +22458,6 @@ "node_modules/wrap-ansi-cjs": { "name": "wrap-ansi", "version": "7.0.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", - "integrity": "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==", "license": "MIT", "dependencies": { "ansi-styles": "^4.0.0", @@ -25106,14 +22473,10 @@ }, "node_modules/wrap-ansi-cjs/node_modules/emoji-regex": { "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", "license": "MIT" }, "node_modules/wrap-ansi-cjs/node_modules/string-width": { "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", "license": "MIT", "dependencies": { "emoji-regex": "^8.0.0", @@ -25126,8 +22489,6 @@ }, "node_modules/wrap-ansi/node_modules/ansi-regex": { "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz", - "integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==", "license": "MIT", "engines": { "node": ">=12" @@ -25138,8 +22499,6 @@ }, "node_modules/wrap-ansi/node_modules/ansi-styles": { "version": "6.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-6.2.1.tgz", - "integrity": "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==", "license": "MIT", "engines": { "node": ">=12" @@ -25150,8 +22509,6 @@ }, "node_modules/wrap-ansi/node_modules/strip-ansi": { "version": "7.1.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", - "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", "license": "MIT", "dependencies": { "ansi-regex": "^6.0.1" @@ -25165,15 +22522,10 @@ }, "node_modules/wrappy": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", "license": "ISC" }, "node_modules/write-file-atomic": { "version": "5.0.1", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-5.0.1.tgz", - "integrity": "sha512-+QU2zd6OTD8XWIJCbffaiQeH9U73qIqafo1x6V1snCWYGJf6cVE0cDR4D8xRzcEnfI21IFrUPzPGtcPf8AC+Rw==", - "dev": true, "license": "ISC", "dependencies": { "imurmurhash": "^0.1.4", @@ -25206,14 +22558,10 @@ }, "node_modules/xml": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/xml/-/xml-1.0.1.tgz", - "integrity": "sha512-huCv9IH9Tcf95zuYCsQraZtWnJvBtLVE0QHMOs8bWyZAFZNDcYjsPq1nEx8jKA9y+Beo9v+7OBPRisQTjinQMw==", "license": "MIT" }, "node_modules/xml-but-prettier": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/xml-but-prettier/-/xml-but-prettier-1.0.1.tgz", - "integrity": "sha512-C2CJaadHrZTqESlH03WOyw0oZTtoy2uEg6dSDF6YRg+9GnYNub53RRemLpnvtbHDFelxMx4LajiFsYeR6XJHgQ==", "license": "MIT", "dependencies": { "repeat-string": "^1.5.2" @@ -25243,8 +22591,6 @@ }, "node_modules/xtend": { "version": "4.0.2", - "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", - "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", "license": "MIT", "engines": { "node": ">=0.4" @@ -25252,8 +22598,6 @@ }, "node_modules/y18n": { "version": "5.0.8", - "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", - "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", "dev": true, "license": "ISC", "engines": { @@ -25262,14 +22606,10 @@ }, "node_modules/yallist": { "version": "3.1.1", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", - "integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==", "license": "ISC" }, "node_modules/yaml": { "version": "2.7.0", - "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.7.0.tgz", - "integrity": "sha512-+hSoy/QHluxmC9kCIJyL/uyFmLmc+e5CFR5Wa+bpIhIj85LVb9ZH2nVnqrHoSvKogwODv0ClqZkmiSSaIH5LTA==", "license": "ISC", "bin": { "yaml": "bin.mjs" @@ -25280,8 +22620,6 @@ }, "node_modules/yaot": { "version": "1.1.3", - "resolved": "https://registry.npmjs.org/yaot/-/yaot-1.1.3.tgz", - "integrity": "sha512-AE8LInj21hTuA01RUK+9pSsl0ltQXO+rxn4Q+CJT4+NI/X7dhGGblF7vvzGj6ro0qXRCGAE/7ccEfu6S4DJayw==", "license": "MIT", "dependencies": { "rafor": "^1.0.2" @@ -25289,8 +22627,6 @@ }, "node_modules/yargs": { "version": "17.7.2", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", - "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", "dev": true, "license": "MIT", "dependencies": { @@ -25308,8 +22644,6 @@ }, "node_modules/yargs-parser": { "version": "21.1.1", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", - "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", "dev": true, "license": "ISC", "engines": { @@ -25318,15 +22652,11 @@ }, "node_modules/yargs/node_modules/emoji-regex": { "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", "dev": true, "license": "MIT" }, "node_modules/yargs/node_modules/string-width": { "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", "dev": true, "license": "MIT", "dependencies": { @@ -25340,8 +22670,6 @@ }, "node_modules/yocto-queue": { "version": "0.1.0", - "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", - "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", "dev": true, "license": "MIT", "engines": { @@ -25353,8 +22681,6 @@ }, "node_modules/z-schema": { "version": "5.0.5", - "resolved": "https://registry.npmjs.org/z-schema/-/z-schema-5.0.5.tgz", - "integrity": "sha512-D7eujBWkLa3p2sIpJA0d1pr7es+a7m0vFAnZLlCEKq/Ij2k0MLi9Br2UPxoxdYystm5K1yeBGzub0FlYUEWj2Q==", "license": "MIT", "dependencies": { "lodash.get": "^4.4.2", @@ -25373,8 +22699,6 @@ }, "node_modules/z-schema/node_modules/commander": { "version": "9.5.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-9.5.0.tgz", - "integrity": "sha512-KRs7WVDKg86PWiuAqhDrAQnTXZKraVcCc6vFdL14qrZ/DcWwuRo7VoiYXalXO7S5GKpqYiVEwCbgFDfxNHKJBQ==", "license": "MIT", "optional": true, "engines": { @@ -25383,14 +22707,10 @@ }, "node_modules/zenscroll": { "version": "4.0.2", - "resolved": "https://registry.npmjs.org/zenscroll/-/zenscroll-4.0.2.tgz", - "integrity": "sha512-jEA1znR7b4C/NnaycInCU6h/d15ZzCd1jmsruqOKnZP6WXQSMH3W2GL+OXbkruslU4h+Tzuos0HdswzRUk/Vgg==", "license": "Unlicense" }, "node_modules/zod": { "version": "3.24.1", - "resolved": "https://registry.npmjs.org/zod/-/zod-3.24.1.tgz", - "integrity": "sha512-muH7gBL9sI1nciMZV67X5fTKKBLtwpZ5VBp1vsOQzj1MhrBZ4wlVCm3gedKZWLp0Oyel8sIGfeiz54Su+OVT+A==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/colinhacks" @@ -25398,8 +22718,6 @@ }, "node_modules/zustand": { "version": "4.5.6", - "resolved": "https://registry.npmjs.org/zustand/-/zustand-4.5.6.tgz", - "integrity": "sha512-ibr/n1hBzLLj5Y+yUcU7dYw8p6WnIVzdJbnX+1YpaScvZVF2ziugqHs+LAmHw4lWO9c/zRj+K1ncgWDQuthEdQ==", "license": "MIT", "dependencies": { "use-sync-external-store": "^1.2.2" @@ -25426,8 +22744,6 @@ }, "node_modules/zwitch": { "version": "2.0.4", - "resolved": "https://registry.npmjs.org/zwitch/-/zwitch-2.0.4.tgz", - "integrity": "sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==", "license": "MIT", "funding": { "type": "github", diff --git a/package.json b/package.json index 6ef5a2bf..74bb7675 100644 --- a/package.json +++ b/package.json @@ -29,7 +29,7 @@ "@meshsdk/core-cst": "^1.9.0-beta.77", "@meshsdk/react": "^1.9.0-beta.77", "@octokit/core": "^6.1.2", - "@prisma/client": "^6.4.1", + "@prisma/client": "^6.17.1", "@radix-ui/react-accordion": "^1.2.0", "@radix-ui/react-checkbox": "^1.1.1", "@radix-ui/react-collapsible": "^1.1.0", @@ -111,7 +111,7 @@ "postcss": "^8.4.39", "prettier": "^3.3.2", "prettier-plugin-tailwindcss": "^0.6.5", - "prisma": "^6.4.1", + "prisma": "^6.17.1", "tailwindcss": "^3.4.3", "ts-jest": "^29.4.4", "typescript": "^5.5.3" diff --git a/prisma/migrations/20251017112523_add_migration_target_wallet_id/migration.sql b/prisma/migrations/20251017112523_add_migration_target_wallet_id/migration.sql new file mode 100644 index 00000000..088f2d48 --- /dev/null +++ b/prisma/migrations/20251017112523_add_migration_target_wallet_id/migration.sql @@ -0,0 +1,3 @@ +-- AlterTable +ALTER TABLE "Wallet" ADD COLUMN "migrationTargetWalletId" TEXT; + diff --git a/prisma/schema.prisma b/prisma/schema.prisma index feccdec8..fc50e172 100644 --- a/prisma/schema.prisma +++ b/prisma/schema.prisma @@ -1,6 +1,3 @@ -// This is your Prisma schema file, -// learn more about it in the docs: https://pris.ly/d/prisma-schema - generator client { provider = "prisma-client-js" } @@ -20,20 +17,21 @@ model User { } model Wallet { - id String @id @default(cuid()) - name String - description String? - signersAddresses String[] - signersStakeKeys String[] - signersDRepKeys String[] - signersDescriptions String[] - numRequiredSigners Int? - verified String[] - scriptCbor String - stakeCredentialHash String? - type String - isArchived Boolean @default(false) - clarityApiKey String? + id String @id @default(cuid()) + name String + description String? + signersAddresses String[] + signersStakeKeys String[] + signersDRepKeys String[] + signersDescriptions String[] + numRequiredSigners Int? + verified String[] + scriptCbor String + stakeCredentialHash String? + type String + isArchived Boolean @default(false) + clarityApiKey String? + migrationTargetWalletId String? } model Transaction { @@ -102,6 +100,19 @@ model Ballot { createdAt DateTime @default(now()) } +model Proxy { + id String @id @default(cuid()) + walletId String? + proxyAddress String + authTokenId String + paramUtxo String + description String? + isActive Boolean @default(true) + createdAt DateTime @default(now()) + updatedAt DateTime @updatedAt + userId String? +} + model BalanceSnapshot { id String @id @default(cuid()) walletId String @@ -112,3 +123,23 @@ model BalanceSnapshot { isArchived Boolean snapshotDate DateTime @default(now()) } + +model Migration { + id String @id @default(cuid()) + originalWalletId String // The wallet being migrated from + newWalletId String? // The new wallet being created (null until created) + ownerAddress String // The user who initiated the migration + currentStep Int @default(0) // 0=pre-checks, 1=create wallet, 2=proxy setup, 3=transfer funds, 4=complete + status String @default("pending") // pending, in_progress, completed, failed, cancelled + migrationData Json? // Store any additional migration-specific data + errorMessage String? // Store error details if migration fails + createdAt DateTime @default(now()) + updatedAt DateTime @updatedAt + completedAt DateTime? + + // Indexes for efficient querying + @@index([ownerAddress]) + @@index([originalWalletId]) + @@index([status]) + @@index([createdAt]) +} diff --git a/src/components/common/overall-layout/layout.tsx b/src/components/common/overall-layout/layout.tsx index a23aa539..8b78317b 100644 --- a/src/components/common/overall-layout/layout.tsx +++ b/src/components/common/overall-layout/layout.tsx @@ -296,6 +296,7 @@ export default function RootLayout({ +
state.setWalletAssetMetadata, ); + const { fetchProxyBalance, fetchProxyDrepInfo, fetchProxyDelegatorsInfo, setProxies } = useProxyActions(); const setDrepInfo = useWalletsStore((state) => state.setDrepInfo); @@ -179,6 +181,64 @@ export default function WalletDataLoaderWrapper({ } } + async function fetchProxyData() { + if (appWallet?.id && appWallet?.scriptCbor) { + try { + // Get proxies from API + const proxies = await ctx.proxy.getProxiesByUserOrWallet.fetch({ + walletId: appWallet.id, + }); + + + // First, add proxies to the store + setProxies(appWallet.id, proxies); + + // Fetch balance and DRep info for each proxy + for (const proxy of proxies) { + try { + + // Fetch balance + await fetchProxyBalance( + appWallet.id, + proxy.id, + proxy.proxyAddress, + network.toString() + ); + + // Fetch DRep info with force refresh + await fetchProxyDrepInfo( + appWallet.id, + proxy.id, + proxy.proxyAddress, + proxy.authTokenId, + appWallet.scriptCbor, + network.toString(), + proxy.paramUtxo, + true // Force refresh to bypass cache + ); + + // Fetch delegators info with force refresh + await fetchProxyDelegatorsInfo( + appWallet.id, + proxy.id, + proxy.proxyAddress, + proxy.authTokenId, + appWallet.scriptCbor, + network.toString(), + proxy.paramUtxo, + true // Force refresh to bypass cache + ); + + } catch (error) { + console.error(`WalletDataLoaderWrapper: Error fetching data for proxy ${proxy.id}:`, error); + } + } + } catch (error) { + console.error("WalletDataLoaderWrapper: Error fetching proxy data:", error); + } + } + } + async function refreshWallet() { if (fetchingTransactions.current) return; @@ -188,8 +248,11 @@ export default function WalletDataLoaderWrapper({ await getTransactionsOnChain(); await getWalletAssets(); await getDRepInfo(); + await fetchProxyData(); // Fetch proxy data void ctx.transaction.getPendingTransactions.invalidate(); void ctx.transaction.getAllTransactions.invalidate(); + // Also refresh proxy data + void ctx.proxy.getProxiesByUserOrWallet.invalidate(); setRandomState(); setLoading(false); fetchingTransactions.current = false; @@ -204,6 +267,9 @@ export default function WalletDataLoaderWrapper({ if (appWallet && prevWalletIdRef.current !== appWallet.id) { refreshWallet(); prevWalletIdRef.current = appWallet.id; + } else if (appWallet) { + // If wallet exists but we already have data, still fetch proxy data + fetchProxyData(); } }, [appWallet]); diff --git a/src/components/common/overall-layout/proxy-data-loader.tsx b/src/components/common/overall-layout/proxy-data-loader.tsx new file mode 100644 index 00000000..dd81308b --- /dev/null +++ b/src/components/common/overall-layout/proxy-data-loader.tsx @@ -0,0 +1,111 @@ +import { useEffect } from "react"; +import useAppWallet from "@/hooks/useAppWallet"; +import { useProxyData, useProxyActions } from "@/lib/zustand/proxy"; +import { useSiteStore } from "@/lib/zustand/site"; +import { api } from "@/utils/api"; + +export default function ProxyDataLoader() { + const { appWallet } = useAppWallet(); + const network = useSiteStore((state) => state.network); + const { proxies } = useProxyData(appWallet?.id); + const { + setProxies, + fetchProxyBalance, + fetchProxyDrepInfo, + fetchProxyDelegatorsInfo, + clearProxyData + } = useProxyActions(); + + + + // Get proxies from API + const { data: apiProxies, refetch: refetchProxies } = api.proxy.getProxiesByUserOrWallet.useQuery( + { + walletId: appWallet?.id ?? undefined, + }, + { + enabled: !!appWallet?.id, + refetchOnWindowFocus: false, + staleTime: 30000, // 30 seconds + } + ); + + // Update store when API data changes + useEffect(() => { + if (apiProxies && appWallet?.id) { + const proxyData = apiProxies.map(proxy => ({ + id: proxy.id, + proxyAddress: proxy.proxyAddress, + authTokenId: proxy.authTokenId, + paramUtxo: proxy.paramUtxo, + description: proxy.description, + isActive: proxy.isActive, + createdAt: new Date(proxy.createdAt), + lastUpdated: Date.now(), + })); + + setProxies(appWallet.id, proxyData); + } + }, [apiProxies, appWallet?.id, setProxies]); + + // Fetch additional data for each proxy + useEffect(() => { + if (proxies.length > 0 && appWallet?.id && appWallet?.scriptCbor) { + void (async () => { + for (const proxy of proxies) { + // Only fetch if we don't have recent data (older than 5 minutes) + const isStale = !proxy.lastUpdated || (Date.now() - proxy.lastUpdated) > 5 * 60 * 1000; + if (isStale) { + try { + await fetchProxyBalance(appWallet.id, proxy.id, proxy.proxyAddress, network.toString()); + await fetchProxyDrepInfo( + appWallet.id, + proxy.id, + proxy.proxyAddress, + proxy.authTokenId, + appWallet.scriptCbor, + network.toString(), + proxy.paramUtxo, + true, + ); + await fetchProxyDelegatorsInfo( + appWallet.id, + proxy.id, + proxy.proxyAddress, + proxy.authTokenId, + appWallet.scriptCbor, + network.toString(), + proxy.paramUtxo, + true, + ); + } catch (error) { + console.error(`Error fetching data for proxy ${proxy.id}:`, error); + } + } + } + })(); + } + }, [proxies, appWallet?.id, appWallet?.scriptCbor, network, fetchProxyBalance, fetchProxyDrepInfo, fetchProxyDelegatorsInfo]); + + // Clear proxy data when wallet changes + useEffect(() => { + return () => { + if (appWallet?.id) { + clearProxyData(appWallet.id); + } + }; + }, [appWallet?.id, clearProxyData]); + + // Expose refetch function for manual refresh + useEffect(() => { + // Store refetch function in window for global access if needed + if (typeof window !== 'undefined') { + const w = window as Window & { refetchProxyData?: () => void }; + w.refetchProxyData = () => { + void refetchProxies(); + }; + } + }, [refetchProxies]); + + return null; // This is a data loader component, no UI +} diff --git a/src/components/common/overall-layout/wallet-data-loader.tsx b/src/components/common/overall-layout/wallet-data-loader.tsx index 92dc7284..af28bb11 100644 --- a/src/components/common/overall-layout/wallet-data-loader.tsx +++ b/src/components/common/overall-layout/wallet-data-loader.tsx @@ -7,6 +7,7 @@ import { useWalletsStore } from "@/lib/zustand/wallets"; import { api } from "@/utils/api"; import { OnChainTransaction, TxInfo } from "@/types/transaction"; import { useSiteStore } from "@/lib/zustand/site"; +import { useProxyActions } from "@/lib/zustand/proxy"; export default function WalletDataLoader() { const { appWallet } = useAppWallet(); @@ -19,6 +20,7 @@ export default function WalletDataLoader() { const ctx = api.useUtils(); const network = useSiteStore((state) => state.network); const setRandomState = useSiteStore((state) => state.setRandomState); + const { fetchProxyBalance, fetchProxyDrepInfo, fetchProxyDelegatorsInfo, setProxies } = useProxyActions(); async function fetchUtxos() { if (appWallet) { @@ -53,19 +55,99 @@ export default function WalletDataLoader() { } } + async function fetchProxyData() { + if (appWallet?.id && appWallet?.scriptCbor) { + console.log("WalletDataLoader: Fetching proxy data for wallet", appWallet.id); + + try { + // Get proxies from API + const proxies = await ctx.proxy.getProxiesByUserOrWallet.fetch({ + walletId: appWallet.id, + }); + + console.log("WalletDataLoader: Found proxies", proxies); + + // First, add proxies to the store + setProxies(appWallet.id, proxies); + + // Fetch balance and DRep info for each proxy + for (const proxy of proxies) { + try { + console.log(`WalletDataLoader: Fetching data for proxy ${proxy.id}`); + + // Fetch balance + await fetchProxyBalance( + appWallet.id, + proxy.id, + proxy.proxyAddress, + network.toString() + ); + + // Fetch DRep info with force refresh + await fetchProxyDrepInfo( + appWallet.id, + proxy.id, + proxy.proxyAddress, + proxy.authTokenId, + appWallet.scriptCbor, + network.toString(), + proxy.paramUtxo, + true // Force refresh to bypass cache + ); + + // Fetch delegators info with force refresh + await fetchProxyDelegatorsInfo( + appWallet.id, + proxy.id, + proxy.proxyAddress, + proxy.authTokenId, + appWallet.scriptCbor, + network.toString(), + proxy.paramUtxo, + true // Force refresh to bypass cache + ); + + console.log(`WalletDataLoader: Successfully fetched data for proxy ${proxy.id}`); + } catch (error) { + console.error(`WalletDataLoader: Error fetching data for proxy ${proxy.id}:`, error); + } + } + } catch (error) { + console.error("WalletDataLoader: Error fetching proxy data:", error); + } + } + } + async function refreshWallet() { + console.log("WalletDataLoader: refreshWallet called"); setLoading(true); await fetchUtxos(); await getTransactionsOnChain(); + console.log("WalletDataLoader: About to fetch proxy data"); + await fetchProxyData(); // Fetch proxy data + console.log("WalletDataLoader: Finished fetching proxy data"); void ctx.transaction.getPendingTransactions.invalidate(); void ctx.transaction.getAllTransactions.invalidate(); + // Also refresh proxy data + void ctx.proxy.getProxiesByUserOrWallet.invalidate(); setRandomState(); setLoading(false); } useEffect(() => { + console.log("WalletDataLoader: useEffect triggered", { + hasAppWallet: !!appWallet, + walletId: appWallet?.id, + hasUtxos: appWallet?.id ? walletsUtxos[appWallet.id] !== undefined : false + }); + if (appWallet && walletsUtxos[appWallet?.id] === undefined) { + console.log("WalletDataLoader: Calling refreshWallet"); refreshWallet(); + } else if (appWallet) { + // If wallet exists but we already have UTxOs, still fetch proxy data + console.log("WalletDataLoader: Calling fetchProxyData directly"); + fetchProxyData(); } }, [appWallet]); diff --git a/src/components/pages/wallet/governance/proposal/addBallot.tsx b/src/components/multisig/README.md similarity index 100% rename from src/components/pages/wallet/governance/proposal/addBallot.tsx rename to src/components/multisig/README.md diff --git a/src/components/multisig/inspect-multisig-script.tsx b/src/components/multisig/inspect-multisig-script.tsx index 5d291ae2..86f2e878 100644 --- a/src/components/multisig/inspect-multisig-script.tsx +++ b/src/components/multisig/inspect-multisig-script.tsx @@ -88,28 +88,37 @@ export default function InspectMultisigScript({ } return ( - - {mWallet.stakingEnabled() && {mWallet.getScript().address}} - copyString={mWallet.getScript().address} - />} - {`${balance} ₳`}} /> - {mWallet.stakingEnabled() && ( - {mWallet.getStakeAddress()}} - copyString={mWallet.getStakeAddress()} - /> - )} -{/* add pending rewards like balance */} - {mWallet.isGovernanceEnabled() && {mWallet.getDRepId()}} - copyString={mWallet.getDRepId()} - />} +
+
+

Native Script

+
+
+
+
+ {mWallet.stakingEnabled() && {mWallet.getScript().address}} + copyString={mWallet.getScript().address} + />} + {`${balance} ₳`}} /> + {mWallet.stakingEnabled() && ( + {mWallet.getStakeAddress()}} + copyString={mWallet.getStakeAddress()} + /> + )} + {/* add pending rewards like balance */} + {mWallet.isGovernanceEnabled() && {mWallet.getDRepId()}} + copyString={mWallet.getDRepId()} + />} - - + +
+
+
+
); } diff --git a/src/components/multisig/proxy/ProxyControl.tsx b/src/components/multisig/proxy/ProxyControl.tsx new file mode 100644 index 00000000..c45a8b98 --- /dev/null +++ b/src/components/multisig/proxy/ProxyControl.tsx @@ -0,0 +1,838 @@ +import React, { useState, useEffect, useCallback, useMemo } from "react"; +import { useWallet } from "@meshsdk/react"; +import { MeshProxyContract } from "./offchain"; +import { useUserStore } from "@/lib/zustand/user"; +import { useSiteStore } from "@/lib/zustand/site"; +import { toast } from "@/hooks/use-toast"; +import { getTxBuilder } from "@/utils/get-tx-builder"; +import useAppWallet from "@/hooks/useAppWallet"; +import { api } from "@/utils/api"; +import useTransaction from "@/hooks/useTransaction"; +import ProxyOverview from "./ProxyOverview"; +import ProxySetup from "./ProxySetup"; +import ProxySpend from "./ProxySpend"; +import UTxOSelector from "@/components/pages/wallet/new-transaction/utxoSelector"; +import { getProvider } from "@/utils/get-provider"; +import type { MeshTxBuilder, UTxO } from "@meshsdk/core"; +import { useProxy } from "@/hooks/useProxy"; +import { useProxyData } from "@/lib/zustand/proxy"; + +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { Dialog, DialogContent, DialogHeader, DialogTitle } from "@/components/ui/dialog"; +import { Card, CardContent, CardHeader } from "@/components/ui/card"; +import { Button } from "@/components/ui/button"; +import { Tooltip, TooltipContent, TooltipProvider, TooltipTrigger } from "@/components/ui/tooltip"; +import { AlertCircle, ChevronDown, ChevronUp, Wallet, TrendingUp, Info } from "lucide-react"; + +interface ProxyOutput { + address: string; + unit: string; + amount: string; +} + +interface ProxySetupResult { + tx: MeshTxBuilder; + paramUtxo: { txHash: string; outputIndex: number }; + authTokenId: string; + proxyAddress: string; +} + +export default function ProxyControl() { + const { wallet, connected } = useWallet(); + const userAddress = useUserStore((state) => state.userAddress); + const setLoading = useSiteStore((state) => state.setLoading); + const network = useSiteStore((state) => state.network); + const { appWallet } = useAppWallet(); + const { newTransaction } = useTransaction(); + const { selectedProxyId, setSelectedProxy, clearSelectedProxy } = useProxy(); + + // Get proxies from proxy store (includes balance and DRep info) + const { proxies: storeProxies, loading: storeLoading } = useProxyData(appWallet?.id); + + // Get proxies from API (for mutations) + const { data: apiProxies, refetch: refetchProxies, isLoading: apiLoading } = api.proxy.getProxiesByUserOrWallet.useQuery( + { + walletId: appWallet?.id ?? undefined, + }, + { enabled: !!appWallet?.id } + ); + + // Use store proxies if available, otherwise fall back to API proxies + const proxies = useMemo(() => storeProxies.length > 0 ? storeProxies : (apiProxies ?? []), [storeProxies, apiProxies]); + const proxiesLoading = storeLoading || apiLoading; + + const { mutateAsync: createProxy } = api.proxy.createProxy.useMutation({ + onSuccess: () => { + void refetchProxies(); + }, + }); + + const { mutateAsync: updateProxy } = api.proxy.updateProxy.useMutation({ + onSuccess: () => { + void refetchProxies(); + }, + }); + + // State management + const [proxyContract, setProxyContract] = useState(null); + const [isProxySetup, setIsProxySetup] = useState(false); + const [, setLocalLoading] = useState(false); + const [tvlLoading, setTvlLoading] = useState(false); + + // Setup flow state + const [setupStep, setSetupStep] = useState(0); + const [setupData, setSetupData] = useState<{ + paramUtxo?: { txHash: string; outputIndex: number }; + authTokenId?: string; + proxyAddress?: string; + txHex?: MeshTxBuilder; + description?: string; + }>({}); + + // Tab management + + // Form states + const [setupLoading, setSetupLoading] = useState(false); + const [spendLoading, setSpendLoading] = useState(false); + const [showSetupModal, setShowSetupModal] = useState(false); + const [showSpendSection, setShowSpendSection] = useState(false); + const [isExpanded, setIsExpanded] = useState(false); + + // Spend form + const [spendOutputs, setSpendOutputs] = useState([ + { address: "", unit: "lovelace", amount: "" } + ]); + + // UTxO selection state (UI only). We will still pass all UTxOs from provider to contract. + const [, setSelectedUtxos] = useState([]); + const [, setManualSelected] = useState(false); + + // Helper to resolve inputs for multisig controlled txs + const getMsInputs = useCallback(async (): Promise<{ utxos: UTxO[]; walletAddress: string }> => { + if (!appWallet?.address) { + throw new Error("Multisig wallet address not available"); + } + const provider = getProvider(network); + const utxos = await provider.fetchAddressUTxOs(appWallet.address); + if (!utxos || utxos.length === 0) { + throw new Error("No UTxOs found at multisig wallet address"); + } + + console.log("utxos", utxos); + console.log("walletAddress", appWallet.address); + return { utxos, walletAddress: appWallet.address }; + }, [appWallet?.address, network]); + + // Initialize proxy contract + useEffect(() => { + if (connected && wallet && userAddress) { + try { + const txBuilder = getTxBuilder(network); + const contract = new MeshProxyContract( + { + mesh: txBuilder, + wallet: wallet, + networkId: network, + }, + {}, + appWallet?.scriptCbor ?? undefined, + ); + setProxyContract(contract); + } catch (error) { + console.error("Failed to initialize proxy contract:", error); + toast({ + title: "Error", + description: "Failed to initialize proxy contract", + variant: "destructive", + }); + } + } + }, [connected, wallet, userAddress, network, appWallet?.scriptCbor]); + + // Check if proxy is already set up + const checkProxySetup = useCallback(async () => { + if (!proxyContract) return; + + try { + const balance = await proxyContract.getProxyBalance(); + setIsProxySetup(balance.length > 0); + } catch { + // Proxy not set up yet + setIsProxySetup(false); + } + }, [proxyContract]); + + // Load initial state + useEffect(() => { + void checkProxySetup(); + }, [checkProxySetup]); + + // Step 1: Initialize proxy setup + const handleInitializeSetup = useCallback(async (description?: string) => { + if (!proxyContract || !connected) { + toast({ + title: "Error", + description: "Wallet not connected or proxy contract not initialized", + variant: "destructive", + }); + return; + } + + try { + setSetupLoading(true); + setLocalLoading(true); + + // Reset setup data to prevent conflicts with previous attempts + setSetupData({}); + setSetupStep(0); + + // Reset proxy contract state to prevent policy ID conflicts + proxyContract.reset(); + + // Use multisig wallet inputs: pass all UTxOs and ms wallet address + const { utxos, walletAddress } = await getMsInputs(); + const result: ProxySetupResult = await proxyContract.setupProxy(utxos, walletAddress); + + setSetupData({ + paramUtxo: result.paramUtxo, + authTokenId: result.authTokenId, + proxyAddress: result.proxyAddress, + txHex: result.tx, + description: description ?? undefined, + }); + + setSetupStep(1); + toast({ + title: "Step 1 Complete", + description: "Proxy parameters generated successfully", + variant: "default", + }); + + } catch (error) { + console.error("Initialize setup error:", error); + toast({ + title: "Error", + description: `Failed to initialize proxy setup: ${error instanceof Error ? error.message : 'Unknown error'}`, + variant: "destructive", + }); + } finally { + setSetupLoading(false); + setLocalLoading(false); + } + }, [proxyContract, connected, getMsInputs, newTransaction]); + + // Step 2: Review and confirm setup + const handleConfirmSetup = useCallback(async () => { + if (!setupData.txHex || !setupData.proxyAddress || !setupData.authTokenId) { + toast({ + title: "Error", + description: "Setup data is incomplete", + variant: "destructive", + }); + return; + } + + try { + setSetupLoading(true); + setLocalLoading(true); + + // If msCbor is set, route through useTransaction hook to create a signable + if (appWallet?.scriptCbor && setupData.txHex) { + + await newTransaction({ + txBuilder: setupData.txHex, + description: setupData.description, + toastMessage: "Proxy setup transaction created", + }); + } else if (setupData.txHex) { + // Sign and submit the transaction + const signedTx = await wallet.signTx(await setupData.txHex.complete(), true); + await wallet.submitTx(signedTx); + } else { + throw new Error("No transaction to submit"); + } + + // Store proxy information in the database + if (!appWallet?.id && !userAddress) { + throw new Error("Either wallet ID or user address is required to create proxy"); + } + + await createProxy({ + walletId: appWallet?.id ?? undefined, + userId: undefined, + proxyAddress: setupData.proxyAddress, + authTokenId: setupData.authTokenId, + paramUtxo: JSON.stringify(setupData.paramUtxo), + description: setupData.description ?? undefined, + }); + + // Update local state + setIsProxySetup(true); + + // Refresh the proxies list + await refetchProxies(); + + setSetupStep(2); + toast({ + title: "Setup Complete!", + description: "Proxy has been successfully created and is ready to use", + variant: "default", + }); + + // Close the setup modal after successful completion + setTimeout(() => { + setShowSetupModal(false); + setSetupStep(0); + setSetupData({}); + }, 2000); // Close after 2 seconds to let user see the success message + + } catch (error) { + console.error("Confirm setup error:", error); + + // Handle specific error cases + let errorMessage = "Failed to complete proxy setup"; + if (error instanceof Error) { + if (error.message.includes("No collateral found")) { + errorMessage = "Wallet collateral not set up. Please set up collateral in your wallet settings (requires 5 ADA minimum)."; + } else if (error.message.includes("No UTxOs found")) { + errorMessage = "No UTxOs available in wallet. Please ensure your wallet has sufficient funds."; + } else { + errorMessage = `Failed to complete proxy setup: ${error.message}`; + } + } + + toast({ + title: "Error", + description: errorMessage, + variant: "destructive", + }); + } finally { + setSetupLoading(false); + setLocalLoading(false); + } + }, [setupData, wallet, appWallet, createProxy, refetchProxies, getMsInputs, newTransaction]); + + // Reset setup flow + const handleResetSetup = useCallback(() => { + setSetupStep(0); + setSetupData({}); + }, []); + + // Navigation functions + const handleStartSetup = useCallback(() => { + setShowSetupModal(true); + }, []); + + const handleStartSpending = useCallback(() => { + if (selectedProxyId) { + setShowSpendSection(true); + } + }, [selectedProxyId]); + + const handleCloseSetup = useCallback(() => { + setShowSetupModal(false); + setSetupStep(0); + setSetupData({}); + }, []); + + const handleCloseSpend = useCallback(() => { + setShowSpendSection(false); + }, []); + + const handleUpdateProxy = useCallback(async (proxyId: string, description: string) => { + await updateProxy({ + id: proxyId, + description: description || undefined, + }); + }, [updateProxy]); + + // Get balance for a specific proxy + const getProxyBalance = useCallback(async (proxyAddress: string) => { + if (!proxyContract) return []; + + try { + // Create a temporary contract instance for this proxy + const tempContract = new MeshProxyContract( + { + mesh: getTxBuilder(network), + wallet: wallet, + networkId: network, + }, + {} + ); + tempContract.proxyAddress = proxyAddress; + + const balance = await tempContract.getProxyBalance(); + return balance; + } catch (error) { + console.error("Get proxy balance error:", error); + return []; + } + }, [proxyContract, network, wallet]); + + // Get DRep information for a specific proxy (unused but kept for potential future use) + const getProxyDrepInfo = useCallback(async (proxy: { paramUtxo: string; proxyAddress: string }) => { + if (!proxy) return { drepId: "", status: null }; + + try { + // Create a temporary contract instance for this proxy + const tempContract = new MeshProxyContract( + { + mesh: getTxBuilder(network), + wallet: wallet, + networkId: network, + }, + { + paramUtxo: JSON.parse(proxy.paramUtxo) as { txHash: string; outputIndex: number }, + }, + appWallet?.scriptCbor ?? undefined, + ); + tempContract.proxyAddress = proxy.proxyAddress; + + // Get DRep ID and status + const drepId = tempContract.getDrepId(); + const status = tempContract.getDrepStatus(); + + return { drepId, status }; + } catch (error) { + console.error("Get proxy DRep info error:", error); + return { drepId: "", status: null }; + } finally { + // DRep loading handled elsewhere + } + }, [network, wallet, appWallet?.scriptCbor]); + + // Fetch all proxy balances for TVL calculation + const fetchAllProxyBalances = useCallback(async () => { + if (!proxies || proxies.length === 0 || !proxyContract) return; + + try { + setTvlLoading(true); + const balances: Record> = {}; + + for (const proxy of proxies) { + try { + const balance = await getProxyBalance(proxy.proxyAddress); + balances[proxy.id] = balance; + } catch (error) { + console.error(`Failed to fetch balance for proxy ${proxy.id}:`, error); + balances[proxy.id] = []; + } + } + + // Balances handled elsewhere + } catch (error) { + console.error("Failed to fetch proxy balances:", error); + } finally { + setTvlLoading(false); + } + }, [proxies, proxyContract, getProxyBalance]); + + // Calculate Total Value Locked (TVL) across all proxies + const calculateTVL = useCallback(() => { + if (!proxies || proxies.length === 0) { + return { totalADA: 0, totalAssets: 0, totalProxies: 0 }; + } + + let totalADA = 0; + let totalAssets = 0; + const totalProxies = proxies.length; + + // Calculate TVL from store data + proxies.forEach(proxy => { + if ('balance' in proxy && proxy.balance && proxy.balance.length > 0) { + proxy.balance.forEach((asset: { unit: string; quantity: string }) => { + if (asset.unit === 'lovelace') { + totalADA += parseInt(asset.quantity) / 1000000; // Convert lovelace to ADA + } else { + totalAssets += 1; + } + }); + } + }); + + return { totalADA, totalAssets, totalProxies }; + }, [proxies]); + + const { totalADA, totalAssets } = calculateTVL(); + + // Fetch all proxy balances when proxies change + useEffect(() => { + if (proxies && proxies.length > 0 && proxyContract) { + void fetchAllProxyBalances(); + } + }, [proxies, proxyContract, fetchAllProxyBalances]); + + // Refresh balances when component mounts or wallet changes + useEffect(() => { + if (proxies && proxies.length > 0 && proxyContract && connected) { + // Small delay to ensure everything is initialized + const timer = setTimeout(() => { + void fetchAllProxyBalances(); + }, 1000); + return () => clearTimeout(timer); + } + }, [connected, proxyContract, fetchAllProxyBalances, proxies]); + + // Manual TVL refresh function + const refreshTVL = useCallback(async () => { + if (proxies && proxies.length > 0 && proxyContract) { + await fetchAllProxyBalances(); + } + }, [proxies, proxyContract, fetchAllProxyBalances]); + + // Global refresh function for all proxy balances (unused but kept for potential future use) + const refreshAllBalances = useCallback(async () => { + if (proxies && proxies.length > 0 && proxyContract) { + void fetchAllProxyBalances(); + } + }, [proxies, proxyContract, fetchAllProxyBalances]); + + // Spend outputs management + const handleSpendOutputsChange = useCallback((outputs: ProxyOutput[]) => { + setSpendOutputs(outputs); + }, []); + + // Handle proxy selection + const handleProxySelection = useCallback((proxyId: string) => { + if (selectedProxyId === proxyId) { + // If clicking the same proxy, unselect it + clearSelectedProxy(); + toast({ + title: "Proxy Unselected", + description: "Proxy mode has been disabled. Using standard DRep mode.", + }); + } else { + // Select the new proxy + setSelectedProxy(proxyId); + toast({ + title: "Proxy Selected", + description: "Proxy mode enabled for governance operations.", + }); + } + }, [selectedProxyId, setSelectedProxy, clearSelectedProxy]); + + + // Spend from proxy + const handleSpendFromProxy = useCallback(async () => { + if (!proxyContract || !connected) { + toast({ + title: "Error", + description: "Wallet not connected or proxy contract not initialized", + variant: "destructive", + }); + return; + } + + if (!selectedProxyId) { + toast({ + title: "Error", + description: "Please select a proxy to spend from", + variant: "destructive", + }); + return; + } + + // Validate outputs + const validOutputs = spendOutputs.filter(output => + output.address && output.amount && parseFloat(output.amount) > 0 + ); + + if (validOutputs.length === 0) { + toast({ + title: "Error", + description: "Please provide at least one valid output", + variant: "destructive", + }); + return; + } + + try { + setSpendLoading(true); + setLocalLoading(true); + + // Get the selected proxy + const proxy = proxies?.find((p: { id: string }) => p.id === selectedProxyId); + if (!proxy) { + throw new Error("Selected proxy not found"); + } + + // Create a contract instance for the selected proxy + const selectedProxyContract = new MeshProxyContract( + { + mesh: getTxBuilder(network), + wallet: wallet, + networkId: network, + }, + { + paramUtxo: JSON.parse(proxy.paramUtxo) as { txHash: string; outputIndex: number }, + }, + appWallet?.scriptCbor ?? undefined, + ); + selectedProxyContract.proxyAddress = proxy.proxyAddress; + + // Pass multisig inputs to spend as well + const { utxos, walletAddress } = await getMsInputs(); + const txHex = await selectedProxyContract.spendProxySimple(validOutputs, utxos, walletAddress); + if (appWallet?.scriptCbor) { + await newTransaction({ + txBuilder: txHex, + description: "Proxy spend transaction", + toastMessage: "Proxy spend transaction created", + }); + } else { + await wallet.submitTx(await txHex.complete()); + } + + // Refresh balance after successful spend + handleProxySelection(selectedProxyId); + + // Close the spend modal after successful transaction + setTimeout(() => { + setShowSpendSection(false); + }, 2000); // Close after 2 seconds to let user see the success message + + } catch (error) { + console.error("Spend from proxy error:", error); + + // Handle specific error cases + let errorMessage = "Failed to spend from proxy"; + if (error instanceof Error) { + if (error.message.includes("No collateral found")) { + errorMessage = "Wallet collateral not set up. Please set up collateral in your wallet settings (requires 5 ADA minimum)."; + } else if (error.message.includes("No UTxOs found")) { + errorMessage = "No UTxOs available in wallet. Please ensure your wallet has sufficient funds."; + } else { + errorMessage = `Failed to spend from proxy: ${error.message}`; + } + } + + toast({ + title: "Error", + description: errorMessage, + variant: "destructive", + }); + } finally { + setSpendLoading(false); + setLocalLoading(false); + } + }, [proxyContract, connected, spendOutputs, selectedProxyId, proxies, network, wallet, handleProxySelection, getMsInputs, newTransaction, appWallet?.scriptCbor]); + + + // Copy to clipboard + const copyToClipboard = useCallback((text: string) => { + navigator.clipboard.writeText(text); + toast({ + title: "Copied", + description: "Address copied to clipboard", + variant: "default", + }); + }, []); + + + if (!connected) { + return ( + + + + + + Please connect your wallet to use proxy control features. + + + + + ); + } + + if (proxiesLoading) { + return ( + + +
+
+ +
+
+
+
+
+
+
+
+ ); + } + + + return ( +
+ {/* Single Expanding Proxy Control Card */} + + setIsExpanded(!isExpanded)} + onKeyDown={(e) => { + if (e.key === 'Enter' || e.key === ' ') { + e.preventDefault(); + setIsExpanded(!isExpanded); + } + }} + tabIndex={0} + role="button" + aria-expanded={isExpanded} + aria-label={`${isExpanded ? 'Collapse' : 'Expand'} proxy control panel`} + > +
+
+
+ +
+
+
+ Proxy Contracts +
+
+ Automated transaction management +
+
+
+
+ + {/* TVL Display */} + + + +
+
+ +
+ {tvlLoading ? ( +
+ ) : ( + `${totalADA.toFixed(2)} ADA` + )} +
+ +
+
+ {proxies && proxies.length > 0 + ? `${proxies.length} proxy${proxies.length !== 1 ? 'ies' : ''} • ${totalAssets} asset${totalAssets !== 1 ? 's' : ''}` + : 'Ready to setup' + } +
+
+
+ +
+
+
Total Value Locked (TVL)
+ +
+
+
Total ADA: {totalADA.toFixed(6)} ADA
+
Total Assets: {totalAssets}
+
Active Proxies: {proxies?.length ?? 0}
+ {tvlLoading && ( +
Updating balances...
+ )} +
+
+
+
+
+ + {/* Expand/Collapse Button */} + +
+
+
+ + {/* Expandable Content */} + {isExpanded && ( + +
+ {/* Overview Section */} + + + {/* UTxO Selector for visibility/control. Contract uses all UTxOs from provider. */} + {appWallet && ( +
+ { + setSelectedUtxos(utxos); + setManualSelected(manual); + }} + /> +
+ )} + +
+
+ )} +
+ + {/* Spend Modal */} + + + + Spend from Proxy + + + + + + {/* Setup Modal */} + + + + Setup New Proxy + + + + +
+ ); +} diff --git a/src/components/multisig/proxy/ProxyControlExample.tsx b/src/components/multisig/proxy/ProxyControlExample.tsx new file mode 100644 index 00000000..7c110a04 --- /dev/null +++ b/src/components/multisig/proxy/ProxyControlExample.tsx @@ -0,0 +1,107 @@ +import React from "react"; +import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "@/components/ui/card"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { Info } from "lucide-react"; +import ProxyControl from "./ProxyControl"; + +/** + * Example page demonstrating how to use the ProxyControl component + * + * This component shows how to integrate the ProxyControl into your application + * and provides context about what the proxy system does. + */ +export default function ProxyControlExample() { + return ( +
+
+

Proxy Control System

+

+ Manage your Cardano proxy contract for automated and controlled transactions. +

+
+ + + + + What is a Proxy Contract?
+ A proxy contract allows you to create a controlled address that can be managed through auth tokens. + This enables automated transactions while maintaining security through your multisig wallet. + The proxy can hold assets and execute transactions when you have the required auth tokens. +
+
+ + + + How it Works + + Understanding the proxy system workflow + + + +
+
+

1. Setup

+

+ Initialize the proxy by minting 10 auth tokens. These tokens are sent to your multisig wallet. +

+
+
+

2. Control

+

+ Use auth tokens to authorize spending from the proxy address. Each spend consumes one auth token. +

+
+
+

3. Automate

+

+ The proxy can hold assets and execute transactions automatically when properly authorized. +

+
+
+
+
+ + + + + + Integration Example + + How to use the ProxyControl component in your application + + + +
+

Basic Usage

+
+{`import ProxyControl from "@/components/multisig/proxy/ProxyControl";
+
+export default function MyPage() {
+  return (
+    
+

My Proxy Management

+ +
+ ); +}`} +
+ +

Key Features

+
    +
  • Automatic wallet connection detection
  • +
  • Proxy setup with auth token minting
  • +
  • Real-time balance monitoring
  • +
  • Multi-output spending capabilities
  • +
  • Integration with multisig transaction system
  • +
  • Error handling and loading states
  • +
  • Responsive design for mobile and desktop
  • +
+
+
+
+
+ ); +} + + + diff --git a/src/components/multisig/proxy/ProxyOverview.tsx b/src/components/multisig/proxy/ProxyOverview.tsx new file mode 100644 index 00000000..50412117 --- /dev/null +++ b/src/components/multisig/proxy/ProxyOverview.tsx @@ -0,0 +1,681 @@ +import React, { memo, useState, useEffect } from "react"; +import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "@/components/ui/card"; +import { Badge } from "@/components/ui/badge"; +import { Button } from "@/components/ui/button"; +import { Input } from "@/components/ui/input"; +import { Label } from "@/components/ui/label"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { Tooltip, TooltipContent, TooltipProvider, TooltipTrigger } from "@/components/ui/tooltip"; +import { + AlertCircle, + CheckCircle, + Copy, + Settings, + Send, + Plus, + Wallet, + Activity, + ArrowRight, + ChevronDown, + ChevronUp, + Calendar, + Key, + Hash, + Clock, + TrendingUp, + Edit3, + Save, + X, + UserCheck, + UserX, + Users +} from "lucide-react"; + +// ProxyCard Component +interface ProxyCardProps { + proxy: { + id: string; + proxyAddress: string; + authTokenId: string; + description: string | null; + isActive: boolean; + createdAt: Date; + balance?: Array<{ unit: string; quantity: string }>; + drepId?: string; + drepInfo?: any; + delegatorsInfo?: { + delegators: Array<{ address: string; amount: string }>; + totalDelegation: string; + totalDelegationADA: number; + count: number; + }; + lastUpdated?: number; + }; + isSelected: boolean; + onSelect: () => void; + onCopy: () => void; + onSpend: () => void; + onUpdateProxy: (proxyId: string, description: string) => Promise; + onRefreshBalance?: () => void; + onCopyToClipboard: (text: string, label?: string) => void; +} + +// Component to fetch and display proxy balance +const ProxyCardWithBalance = memo(function ProxyCardWithBalance({ + proxy, + isSelected, + onSelect, + onCopy, + onSpend, + onUpdateProxy, + onCopyToClipboard +}: ProxyCardProps) { + // Use balance and DRep data directly from proxy object + const balance = proxy.balance || []; + const drepId = proxy.drepId; + const drepInfo = proxy.drepInfo; + const lastUpdated = proxy.lastUpdated; + + + + // No need to fetch balance - it's already in the proxy object + + return ( + + ); +}); + +const ProxyCard = memo(function ProxyCard({ + proxy, + isSelected, + onSelect, + onCopy, + onSpend, + onUpdateProxy, + onCopyToClipboard +}: ProxyCardProps) { + // Use balance and DRep data directly from proxy object + const displayBalance = proxy.balance || []; + const drepId = proxy.drepId; + const drepInfo = proxy.drepInfo; + const delegatorsInfo = proxy.delegatorsInfo; + const balanceLoading = false; // No loading state needed since data is already loaded + const [isExpanded, setIsExpanded] = React.useState(false); + const [isEditing, setIsEditing] = React.useState(false); + const [editDescription, setEditDescription] = React.useState(proxy.description || ""); + const [isUpdating, setIsUpdating] = React.useState(false); + + const formatDate = (date: Date) => { + return new Intl.DateTimeFormat('en-US', { + month: 'short', + day: 'numeric', + year: 'numeric', + hour: '2-digit', + minute: '2-digit' + }).format(new Date(date)); + }; + + const copyToClipboard = (text: string, label: string) => { + navigator.clipboard.writeText(text); + // You could add a toast notification here + }; + + const handleSaveDescription = async () => { + if (editDescription.trim() === (proxy.description || "")) { + setIsEditing(false); + return; + } + + setIsUpdating(true); + try { + await onUpdateProxy(proxy.id, editDescription.trim()); + setIsEditing(false); + } catch (error) { + console.error("Failed to update proxy description:", error); + // Reset to original value on error + setEditDescription(proxy.description || ""); + } finally { + setIsUpdating(false); + } + }; + + const handleCancelEdit = () => { + setEditDescription(proxy.description || ""); + setIsEditing(false); + }; + + const handleStartEdit = () => { + setEditDescription(proxy.description || ""); + setIsEditing(true); + }; + + return ( + + +
+ + {proxy.proxyAddress.slice(0, 20)}... + +
+ + {proxy.isActive ? "Active" : "Inactive"} + + +
+
+
+ {isEditing ? ( +
+ setEditDescription(e.target.value)} + placeholder="Enter description..." + className="h-6 text-xs" + onKeyDown={(e) => { + if (e.key === 'Enter') { + handleSaveDescription(); + } else if (e.key === 'Escape') { + handleCancelEdit(); + } + }} + autoFocus + /> + + +
+ ) : ( +
+ + {proxy.description || "Click to add description"} + + +
+ )} +
+
+ + + {/* Balance Display */} +
+
+ + Balance +
+ + {balanceLoading ? ( +
+ ) : displayBalance.length > 0 ? ( + + + +
+ {displayBalance.map((asset: any, index: number) => ( +
+ + {asset.unit === "lovelace" + ? `${(parseFloat(asset.quantity) / 1000000).toFixed(2)} ADA` + : asset.quantity + } + +
+ ))} +
+
+ +
+
Proxy Balance Details
+
+ {displayBalance.map((asset: any, index: number) => ( +
+ {asset.unit === "lovelace" ? "ADA" : asset.unit}: + + {asset.unit === "lovelace" + ? `${(parseFloat(asset.quantity) / 1000000).toFixed(6)} ADA` + : asset.quantity + } + +
+ ))} +
+ Total: {displayBalance.length} asset{displayBalance.length !== 1 ? 's' : ''} +
+
+
+
+
+
+ ) : ( +
No balance
+ )} +
+ + {/* Expanded Details */} + {isExpanded && ( +
+ {/* Full Address */} +
+
+ + Proxy Address + +
+
+ {proxy.proxyAddress} +
+
+ + {/* Auth Token ID */} +
+
+ + Auth Token ID + +
+
+ {proxy.authTokenId} +
+
+ + {/* Creation Date */} +
+
+ + Created +
+
+ + {formatDate(proxy.createdAt)} +
+
+ + {/* Proxy ID */} +
+
+ + Proxy ID + +
+
+ {proxy.id} +
+
+ + {/* DRep Information - Only show when this proxy is selected */} + {isSelected && ( +
+
+ + DRep Information +
+ +
+ {/* DRep ID */} +
+
+ + DRep ID + {drepId && ( + + )} +
+
+ {drepId ? ( + drepId + ) : ( + Not registered + )} +
+
+ + {/* DRep Status */} +
+
+ {drepInfo?.active ? ( + + ) : ( + + )} + Status +
+
+ + {drepInfo?.active ? "Active" : "Inactive"} + + {drepInfo?.amount && ( + + {Math.round(Number(drepInfo.amount) / 1000000)} ₳ + + )} +
+
+
+ + {/* Delegators Information */} + {delegatorsInfo && delegatorsInfo.count > 0 && ( +
+
+ + Delegations +
+ +
+ {/* Total Delegation */} +
+
+ + Total Delegation +
+
+
+ {delegatorsInfo.totalDelegationADA.toLocaleString(undefined, { + minimumFractionDigits: 2, + maximumFractionDigits: 6 + })} ₳ +
+
+ {delegatorsInfo.count} delegator{delegatorsInfo.count !== 1 ? 's' : ''} +
+
+
+ + {/* Top Delegators */} + {delegatorsInfo.delegators.length > 0 && ( +
+
+ + Top Delegators +
+
+ {delegatorsInfo.delegators.slice(0, 5).map((delegator, index) => ( +
+ + {delegator.address.slice(0, 20)}... + + + {(Number(delegator.amount) / 1000000).toFixed(2)} ₳ + +
+ ))} + {delegatorsInfo.delegators.length > 5 && ( +
+ +{delegatorsInfo.delegators.length - 5} more +
+ )} +
+
+ )} +
+
+ )} +
+ )} +
+ )} + + {/* Actions */} +
+ + + {isSelected && ( + + )} +
+
+
+ ); +}); + +interface ProxyOverviewProps { + proxies: Array<{ + id: string; + proxyAddress: string; + authTokenId: string; + description: string | null; + isActive: boolean; + createdAt: Date; + }> | undefined; + selectedProxy: string; + isProxySetup: boolean; + onProxySelection: (proxyId: string) => void; + onCopyToClipboard: (text: string) => void; + onStartSetup: () => void; + onStartSpending: () => void; + onUpdateProxy: (proxyId: string, description: string) => Promise; +} + +const ProxyOverview = memo(function ProxyOverview({ + proxies, + selectedProxy, + isProxySetup, + onProxySelection, + onCopyToClipboard, + onStartSetup, + onStartSpending, + onUpdateProxy, +}: ProxyOverviewProps) { + return ( +
+ {/* General Info and Introduction */} +
+ + {/* Status Card - Only show when proxies are active */} + {isProxySetup && ( + + +
+
+ +
+
+

Proxy system active

+

Ready for automated transactions

+
+
+
+
+ )} + +
+ + {/* Proxy Carousel */} + {proxies && proxies.length > 0 ? ( +
+
+
+ + +
+
+ {proxies.length} proxy{proxies.length !== 1 ? 'ies' : ''} +
+
+ + {!selectedProxy && ( + + + + Select a proxy from the cards below to enable spending functionality. + + + )} + +
+ {proxies.map((proxy) => ( + onProxySelection(proxy.id)} + onCopy={() => onCopyToClipboard(proxy.proxyAddress)} + onSpend={() => onStartSpending()} + onUpdateProxy={onUpdateProxy} + onCopyToClipboard={onCopyToClipboard} + /> + ))} +
+
+ ) : ( + + + +

No Proxies Found

+

+ You haven't set up any proxy contracts yet. Create your first proxy to start managing automated transactions. +

+ +
+
+ )} + + {/* Add New Proxy */} + + +
+
+
+ +
+
+

Add New Proxy

+

Create additional proxy contracts

+
+
+ +
+
+
+
+ ); +}); + +export default ProxyOverview; diff --git a/src/components/multisig/proxy/ProxySetup.tsx b/src/components/multisig/proxy/ProxySetup.tsx new file mode 100644 index 00000000..f99bbc22 --- /dev/null +++ b/src/components/multisig/proxy/ProxySetup.tsx @@ -0,0 +1,324 @@ +import React, { memo } from "react"; +import { Button } from "@/components/ui/button"; +import { Input } from "@/components/ui/input"; +import { Label } from "@/components/ui/label"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { + RefreshCw, + AlertCircle, + CheckCircle, + Copy, + Settings, + ChevronLeft, + Play, + Check +} from "lucide-react"; +import { MeshTxBuilder } from "@meshsdk/core"; + +interface ProxySetupProps { + setupStep: number; + setupData: { + paramUtxo?: { txHash: string; outputIndex: number }; + authTokenId?: string; + proxyAddress?: string; + txHex?: MeshTxBuilder; + description?: string; + }; + setupLoading: boolean; + onInitializeSetup: (description?: string) => void; + onConfirmSetup: () => void; + onResetSetup: () => void; + onCopyToClipboard: (text: string) => void; + onCloseSetup: () => void; +} + +// Step indicator component +const StepIndicator = ({ currentStep, totalSteps }: { currentStep: number; totalSteps: number }) => { + return ( +
+ {Array.from({ length: totalSteps }, (_, index) => ( +
+
+ {index < currentStep ? : index + 1} +
+ {index < totalSteps - 1 && ( +
+ )} +
+ ))} +
+ ); +}; + +const ProxySetup = memo(function ProxySetup({ + setupStep, + setupData, + setupLoading, + onInitializeSetup, + onConfirmSetup, + onResetSetup, + onCopyToClipboard, + onCloseSetup, +}: ProxySetupProps) { + const [description, setDescription] = React.useState(""); + return ( +
+ {/* Header Section */} +
+

+ Follow the steps below to create a new proxy contract. This process will mint 10 auth tokens that you can use to control the proxy. +

+
+ + + + {/* Collateral Requirement Alert */} + + + + Collateral Required: Your wallet needs at least 5 ADA set aside as collateral for smart contract transactions. + If you encounter "No collateral found" errors, please set up collateral in your wallet settings. + + + + {/* Step 0: Introduction */} + {setupStep === 0 && ( +
+
+
+
+ +
+
+

Ready to Setup Proxy

+

+ This process will create a new proxy contract for automated transactions +

+
+
+ +
+
+ + setDescription(e.target.value)} + placeholder="Enter a description for this proxy..." + className="w-full" + /> +

+ Add a description to help identify this proxy later +

+
+ +
+
+
+ +
+ Generate proxy parameters and addresses +
+
+
+ +
+ Create a transaction to mint 10 auth tokens +
+
+
+ +
+ Store proxy information in your wallet +
+
+
+ + + + + You'll need to sign a transaction to complete the setup. Make sure you have sufficient ADA for transaction fees. + + +
+ + +
+ )} + + {/* Step 1: Review Generated Parameters */} + {setupStep === 1 && ( +
+
+

+ + Proxy Parameters Generated +

+

+ Review the generated proxy information before proceeding: +

+
+ +
+
+ +
+ + +
+
+ +
+ +
+ + +
+
+ +
+ +
+ {setupData.paramUtxo ? + `${setupData.paramUtxo.txHash.slice(0, 20)}... (${setupData.paramUtxo.outputIndex})` : + "Not available" + } +
+
+
+ +
+ + +
+
+ )} + + {/* Step 2: Setup Complete */} + {setupStep === 2 && ( +
+
+

+ + Proxy Setup Complete! +

+

+ Your proxy has been successfully created and is ready to use. You can now spend from this proxy using the auth tokens. +

+
+ +
+ +
+
+ Address: + {setupData.proxyAddress?.slice(0, 30)}... +
+
+ Auth Tokens: + 10 tokens minted +
+
+ Status: + Active +
+
+
+ +
+ + +
+
+ )} +
+ ); +}); + +export default ProxySetup; diff --git a/src/components/multisig/proxy/ProxySpend.tsx b/src/components/multisig/proxy/ProxySpend.tsx new file mode 100644 index 00000000..4ecd8af1 --- /dev/null +++ b/src/components/multisig/proxy/ProxySpend.tsx @@ -0,0 +1,249 @@ +import React, { memo } from "react"; +import { Button } from "@/components/ui/button"; +import { Input } from "@/components/ui/input"; +import { Label } from "@/components/ui/label"; +import { Badge } from "@/components/ui/badge"; +import { Separator } from "@/components/ui/separator"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select"; +import { + Send, + RefreshCw, + AlertCircle, + Plus, + Trash2, + Wallet, + Activity, + ArrowRight, + X +} from "lucide-react"; + +interface ProxyOutput { + address: string; + unit: string; + amount: string; +} + +interface ProxySpendProps { + proxies: Array<{ + id: string; + proxyAddress: string; + authTokenId: string; + description: string | null; + isActive: boolean; + createdAt: Date; + }> | undefined; + selectedProxy: string; + selectedProxyBalance: Array<{ unit: string; quantity: string }>; + spendOutputs: ProxyOutput[]; + spendLoading: boolean; + onProxySelection: (proxyId: string) => void; + onSpendOutputsChange: (outputs: ProxyOutput[]) => void; + onSpendFromProxy: () => void; + onCloseSpend: () => void; +} + +const ProxySpend = memo(function ProxySpend({ + proxies, + selectedProxy, + selectedProxyBalance, + spendOutputs, + spendLoading, + onProxySelection, + onSpendOutputsChange, + onSpendFromProxy, + onCloseSpend, +}: ProxySpendProps) { + // Add spend output + const addSpendOutput = () => { + const newOutputs = [...spendOutputs, { address: "", unit: "lovelace", amount: "" }]; + onSpendOutputsChange(newOutputs); + }; + + // Remove spend output + const removeSpendOutput = (index: number) => { + if (spendOutputs.length > 1) { + const newOutputs = spendOutputs.filter((_, i) => i !== index); + onSpendOutputsChange(newOutputs); + } + }; + + // Update spend output + const updateSpendOutput = (index: number, field: keyof ProxyOutput, value: string) => { + const updated = [...spendOutputs]; + if (updated[index]) { + updated[index] = { ...updated[index], [field]: value }; + onSpendOutputsChange(updated); + } + }; + + return ( +
+ {/* Description */} +

+ Create transactions to spend assets from your proxy address +

+ + {/* Collateral Requirement Alert */} + + + + Collateral Required: Your wallet needs at least 5 ADA set aside as collateral for smart contract transactions. + If you encounter "No collateral found" errors, please set up collateral in your wallet settings. + + + + {(!proxies || proxies.length === 0) && ( + + + + No proxies found. Please setup a proxy first before attempting to spend from it. + + + )} + + {proxies && proxies.length > 0 && ( +
+ {/* Proxy Selection */} +
+
+ + +
+ +
+ + {/* Selected Proxy Balance */} + {selectedProxy && selectedProxyBalance.length > 0 && ( +
+
+ + +
+
+ {selectedProxyBalance.map((asset, index) => ( +
+
+ + {asset.unit === "lovelace" ? "ADA" : asset.unit} + + + {asset.unit === "lovelace" + ? `${(parseFloat(asset.quantity) / 1000000).toFixed(6)} ADA` + : asset.quantity + } + +
+
+ ))} +
+
+ )} + + {/* Spend Outputs */} +
+
+
+ + +
+ +
+ + {spendOutputs.map((output, index) => ( +
+
+ + {spendOutputs.length > 1 && ( + + )} +
+ +
+
+ + updateSpendOutput(index, "address", e.target.value)} + placeholder="addr1..." + className="font-mono text-sm" + /> +
+ +
+ + updateSpendOutput(index, "unit", e.target.value)} + placeholder="lovelace or policyId.assetName" + className="font-mono text-sm" + /> +
+ +
+ + updateSpendOutput(index, "amount", e.target.value)} + placeholder="1000000" + type="number" + /> +
+
+
+ ))} +
+ + + + {/* Submit Button */} + +
+ )} +
+ ); +}); + +export default ProxySpend; diff --git a/src/components/multisig/proxy/README.md b/src/components/multisig/proxy/README.md new file mode 100644 index 00000000..f8cef8c6 --- /dev/null +++ b/src/components/multisig/proxy/README.md @@ -0,0 +1,150 @@ +# Proxy Control System + +A comprehensive UI component system for managing Cardano proxy contracts with multisig wallet integration. + +## Overview + +The Proxy Control System provides a user-friendly interface for managing proxy contracts on Cardano. It allows users to: + +- Set up proxy contracts with auth token minting +- Monitor proxy balances in real-time +- Create and manage spending transactions +- Integrate with multisig wallet systems + +## Components + +### ProxyControl + +The main component that provides a complete interface for proxy management. + +**Features:** +- **Setup Tab**: Initialize proxy contracts by minting auth tokens +- **Overview Tab**: Monitor proxy status, address, and balance +- **Spend Tab**: Create multi-output spending transactions + +**Usage:** +```tsx +import { ProxyControl } from "@/components/multisig/proxy"; + +export default function MyPage() { + return ( +
+

Proxy Management

+ +
+ ); +} +``` + +### ProxyControlExample + +A demonstration page showing how to integrate and use the ProxyControl component. + +## Architecture + +### Core Classes + +#### MeshProxyContract + +Located in `offchain.ts`, this class handles all blockchain interactions: + +- **setupProxy()**: Mints 10 auth tokens and sets up the proxy address +- **spendProxySimple()**: Creates spending transactions from the proxy +- **getProxyBalance()**: Fetches current balance of the proxy address + +### Integration Points + +The system integrates with: + +1. **MeshSDK**: For wallet connections and transaction building +2. **Multisig System**: Creates transactions that require multisig approval +3. **Database**: Stores transaction data for multisig workflows +4. **Toast System**: Provides user feedback for all operations + +## Workflow + +### 1. Setup Phase +1. User connects wallet +2. Clicks "Setup Proxy" +3. System mints 10 auth tokens +4. Creates multisig transaction for approval +5. Auth tokens are sent to user's multisig wallet + +### 2. Control Phase +1. User can monitor proxy balance +2. Create spending transactions with multiple outputs +3. Each spend consumes one auth token +4. Transactions require multisig approval + +### 3. Automation Phase +1. Proxy can hold various assets +2. Automated spending when auth tokens are available +3. Full audit trail through multisig system + +## Security Features + +- **Multisig Integration**: All transactions require multisig approval +- **Auth Token System**: Controlled spending through token consumption +- **Address Validation**: Proper Cardano address format checking +- **Error Handling**: Comprehensive error states and user feedback + +## UI/UX Features + +- **Responsive Design**: Works on mobile and desktop +- **Loading States**: Visual feedback during operations +- **Error Handling**: Clear error messages and recovery options +- **Real-time Updates**: Balance and status monitoring +- **Copy Functions**: Easy address and token ID copying + +## Dependencies + +- `@meshsdk/react`: Wallet connection and transaction building +- `@meshsdk/core`: Core Cardano functionality +- `@meshsdk/common`: Common utilities and types +- React hooks for state management +- Custom UI components (shadcn/ui based) + +## Error Handling + +The system handles various error scenarios: + +- Wallet not connected +- Insufficient funds +- Invalid addresses +- Network errors +- Transaction failures + +All errors are displayed to users with actionable feedback. + +## Future Enhancements + +Potential improvements: + +1. **Batch Operations**: Multiple proxy management +2. **Advanced Spending**: Time-locked or conditional spending +3. **Analytics**: Transaction history and analytics +4. **Notifications**: Real-time proxy activity alerts +5. **API Integration**: REST API for proxy management + +## Testing + +The component should be tested with: + +- Different wallet types (Nami, Eternl, etc.) +- Various network conditions +- Edge cases (empty balances, invalid inputs) +- Mobile responsiveness +- Error scenarios + +## Contributing + +When contributing to this system: + +1. Follow existing code patterns +2. Add proper TypeScript types +3. Include error handling +4. Test with real wallets +5. Update documentation + + + diff --git a/src/components/multisig/proxy/aiken-workspace/README.md b/src/components/multisig/proxy/aiken-workspace/README.md new file mode 100644 index 00000000..e76d2249 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/README.md @@ -0,0 +1 @@ +Implement in core mesh repo `mesh-contract` diff --git a/src/components/multisig/proxy/aiken-workspace/aiken.lock b/src/components/multisig/proxy/aiken-workspace/aiken.lock new file mode 100644 index 00000000..2e65bd16 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/aiken.lock @@ -0,0 +1,26 @@ +# This file was generated by Aiken +# You typically do not need to edit this file + +[[requirements]] +name = "aiken-lang/stdlib" +version = "v2.2.0" +source = "github" + +[[requirements]] +name = "sidan-lab/vodka" +version = "0.1.13" +source = "github" + +[[packages]] +name = "aiken-lang/stdlib" +version = "v2.2.0" +requirements = [] +source = "github" + +[[packages]] +name = "sidan-lab/vodka" +version = "0.1.13" +requirements = [] +source = "github" + +[etags] diff --git a/src/components/multisig/proxy/aiken-workspace/aiken.toml b/src/components/multisig/proxy/aiken-workspace/aiken.toml new file mode 100644 index 00000000..c8b0955c --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/aiken.toml @@ -0,0 +1,23 @@ +name = "mesh/proxy" +version = "0.0.0" +compiler = "v1.1.17" +plutus = "v3" +license = "Apache-2.0" +description = "Aiken contracts for project 'aiken-proxy'" + +[repository] +user = "QS" +project = "multisig" +platform = "github" + +[[dependencies]] +name = "aiken-lang/stdlib" +version = "v2.2.0" +source = "github" + +[[dependencies]] +name = "sidan-lab/vodka" +version = "0.1.13" +source = "github" + +[config] diff --git a/src/components/multisig/proxy/aiken-workspace/build/aiken-compile.lock b/src/components/multisig/proxy/aiken-workspace/build/aiken-compile.lock new file mode 100644 index 00000000..e69de29b diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.editorconfig b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.editorconfig new file mode 100644 index 00000000..0759674c --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.editorconfig @@ -0,0 +1,9 @@ +root = true + +[*.ak] +indent_style = space +indent_size = 2 +end_of_line = lf +charset = utf-8 +trim_trailing_whitespace = true +insert_final_newline = true diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.gitattributes b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.gitattributes new file mode 100644 index 00000000..99fefcf4 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.gitattributes @@ -0,0 +1,2 @@ +# Temp hack to get some syntax highlighting on github +*.ak linguist-language=Gleam diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.github/workflows/continuous-integration.yml b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.github/workflows/continuous-integration.yml new file mode 100644 index 00000000..b0081ac7 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.github/workflows/continuous-integration.yml @@ -0,0 +1,64 @@ +name: Continuous Integration + +on: + workflow_dispatch: + push: + branches: ["main"] + tags: ["*.*.*"] + pull_request: + branches: ["main"] + +env: + CARGO_TERM_COLOR: always + +permissions: + contents: read + pages: write + id-token: write + +concurrency: + group: "pages" + cancel-in-progress: true + +jobs: + build: + runs-on: ubuntu-latest + steps: + - name: 📥 Checkout repository + uses: actions/checkout@v3 + + - name: 🧰 Setup Pages + uses: actions/configure-pages@v2 + + - name: 🧰 Install Aiken + uses: aiken-lang/setup-aiken@v1 + with: + version: v1.1.9 + + - name: 📝 Run fmt + run: aiken fmt --check + + - name: 🔬 Run tests + run: aiken check + + - name: 📘 Generate documentation + shell: bash + working-directory: . + run: aiken docs -o docs + + - name: 📦 Upload artifact + uses: actions/upload-pages-artifact@v2 + with: + path: "docs/" + + deploy: + if: ${{ startsWith(github.ref, 'refs/tags') }} + needs: build + runs-on: ubuntu-latest + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + steps: + - name: 🚀 Deploy to GitHub Pages + id: deployment + uses: actions/deploy-pages@v1 diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.gitignore b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.gitignore new file mode 100644 index 00000000..3a3d38e6 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/.gitignore @@ -0,0 +1,3 @@ +build/ +docs/ +.DS_Store \ No newline at end of file diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/CHANGELOG.md b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/CHANGELOG.md new file mode 100644 index 00000000..62345b32 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/CHANGELOG.md @@ -0,0 +1,805 @@ +# Changelog + +## v2.2.0 - 2024-12-13 + +### Added + +- [`aiken/cbor.{deserialise}`](https://aiken-lang.github.io/stdlib/aiken/cbor.html#deserialise): to recover `Data` from CBOR bytes. +- [`aiken/collection/pairs.{insert_with_by_ascending_key}`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html#insert_with_by_ascending_key): for inserting in pairs while specifying how to combine values on key conflict. + +## v2.1.0 - 2024-09-14 + +### Added + +- Various new helper functions: + - [`aiken/collection/list.{for_each}`](https://aiken-lang.github.io/stdlib/aiken/collection/list.html#for_each): for performing many side-effects. + - [`aiken/collection/dict.{pop}`](https://aiken-lang.github.io/stdlib/aiken/collection/dict.html#pop): for accessing and removing a value from a dictionnary in a single op. + - [`aiken/primitive/bytearray.{starts_with}`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#starts_with): for matching bytearray prefixes. + - [`aiken/primitive/math/rational.{pow}`](https://aiken-lang.github.io/stdlib/aiken/primitive/math/rational.html#pow): for computing (int) powers of rational numbers. + - [`cardano/assets.{match}`](https://aiken-lang.github.io/stdlib/cardano/assets.html#match): efficiently compare two value-like. + - [`cardano/assets.{restricted_to}`](https://aiken-lang.github.io/stdlib/cardano/assets.html#restricted_to): extracting value subsets from parent value. + +- Comparison functions for various Cardano types: + - [`cardano/address/credential.{compare}`](https://aiken-lang.github.io/stdlib/cardano/address/credential.html#compare): for ordering credentials. + - [`cardano/governance/voter.{compare}`](https://aiken-lang.github.io/stdlib/cardano/governacen/voter.html#compare): for ordering voters. + - [`cardano/transaction/output_reference.{compare}`](https://aiken-lang.github.io/stdlib/cardano/transaction/output_reference.html#compare): for ordering output references. + - [`cardano/transaction/script_purpose.{compare}`](https://aiken-lang.github.io/stdlib/cardano/transaction/script_purpose.html#compare): for ordering script purpose. + +- New BLS12-381 crypto modules: + - [`aiken/crypto/bls12_381/g1`](https://aiken-lang.github.io/stdlib/aiken/crypto/bls12_381/g1.html) + - [`aiken/crypto/bls12_381/g2`](https://aiken-lang.github.io/stdlib/aiken/crypto/bls12_381/g2.html) + - [`aiken/crypto/bls12_381/scalar`](https://aiken-lang.github.io/stdlib/aiken/crypto/bls12_381/scalar.html) + +### Changed + +- N/A + +### Removed + +- N/A + +## v2.0.0 - 2024-09-01 + +> [!NOTE] +> Significant performance improvements (mostly on CPU) across all boards mostly due to the integration of Plutus V3. +> +>
see benchmarks +> +> test | cpu | mem +> --- | --- | --- +> aiken/cbor.{serialise_1} | -38.20% | ±0.00% +> aiken/cbor.{serialise_2} | -38.20% | ±0.00% +> aiken/cbor.{serialise_3} | -37.25% | ±0.00% +> aiken/cbor.{serialise_4} | -41.95% | ±0.00% +> aiken/cbor.{serialise_5} | -42.77% | ±0.00% +> aiken/cbor.{serialise_6} | -42.63% | ±0.00% +> aiken/cbor.{serialise_7} | -40.51% | ±0.00% +> aiken/cbor.{serialise_8} | -37.25% | ±0.00% +> aiken/cbor.{serialise_9} | -41.95% | ±0.00% +> aiken/cbor.{diagnostic_1} | -47.62% | -4.35% +> aiken/cbor.{diagnostic_2} | -45.16% | -2.87% +> aiken/cbor.{diagnostic_3} | -43.32% | -13.33% +> aiken/cbor.{diagnostic_4} | -38.28% | -8.03% +> aiken/cbor.{diagnostic_5} | -44.15% | -14.59% +> aiken/cbor.{diagnostic_6} | -42.77% | -12.21% +> aiken/cbor.{diagnostic_7} | -43.87% | -16.87% +> aiken/cbor.{diagnostic_7_alt} | -42.99% | -11.56% +> aiken/cbor.{diagnostic_8} | -46.00% | -10.23% +> aiken/cbor.{diagnostic_9} | -42.81% | -2.81% +> aiken/cbor.{diagnostic_10} | -38.28% | -8.03% +> aiken/cbor.{diagnostic_10_alt} | -38.43% | -8.03% +> aiken/cbor.{diagnostic_11} | -44.00% | -8.51% +> aiken/cbor.{diagnostic_12} | -45.65% | -11.56% +> aiken/cbor.{diagnostic_13} | -44.44% | -9.34% +> aiken/cbor.{diagnostic_14} | -43.59% | -19.77% +> aiken/cbor.{diagnostic_15} | -46.50% | -3.67% +> aiken/cbor.{diagnostic_16} | -41.89% | -13.41% +> aiken/collection/dict.{bench_from_ascending_pairs} | -20.48% | ±0.00% +> aiken/collection/dict.{from_list_1} | -20.16% | ±0.00% +> aiken/collection/dict.{from_list_2} | -18.28% | ±0.00% +> aiken/collection/dict.{from_list_3} | -17.83% | ±0.00% +> aiken/collection/dict.{from_list_4} | -18.97% | ±0.00% +> aiken/collection/dict.{bench_from_pairs} | -25.28% | ±0.00% +> aiken/collection/dict.{find_1} | -20.63% | ±0.00% +> aiken/collection/dict.{find_2} | -20.43% | ±0.00% +> aiken/collection/dict.{find_3} | -22.03% | ±0.00% +> aiken/collection/dict.{find_4} | -22.53% | ±0.00% +> aiken/collection/dict.{get_1} | -20.63% | ±0.00% +> aiken/collection/dict.{get_2} | -22.72% | ±0.00% +> aiken/collection/dict.{get_3} | -23.26% | ±0.00% +> aiken/collection/dict.{get_4} | -26.91% | ±0.00% +> aiken/collection/dict.{get_5} | -26.30% | ±0.00% +> aiken/collection/dict.{has_key_1} | -28.07% | ±0.00% +> aiken/collection/dict.{has_key_2} | -30.77% | ±0.00% +> aiken/collection/dict.{has_key_3} | -30.22% | ±0.00% +> aiken/collection/dict.{has_key_4} | -27.25% | ±0.00% +> aiken/collection/dict.{is_empty_1} | -27.86% | ±0.00% +> aiken/collection/dict.{keys_1} | -20.30% | ±0.00% +> aiken/collection/dict.{keys_2} | -17.48% | ±0.00% +> aiken/collection/dict.{size_1} | -37.90% | ±0.00% +> aiken/collection/dict.{size_2} | -32.34% | ±0.00% +> aiken/collection/dict.{size_3} | -27.97% | ±0.00% +> aiken/collection/dict.{values_1} | -20.30% | ±0.00% +> aiken/collection/dict.{values_2} | -17.58% | ±0.00% +> aiken/collection/dict.{delete_1} | -20.16% | ±0.00% +> aiken/collection/dict.{delete_2} | -24.29% | ±0.00% +> aiken/collection/dict.{delete_3} | -21.03% | ±0.00% +> aiken/collection/dict.{delete_4} | -25.03% | ±0.00% +> aiken/collection/dict.{delete_5} | -27.22% | ±0.00% +> aiken/collection/dict.{delete_6} | -25.83% | ±0.00% +> aiken/collection/dict.{filter_1} | -20.16% | ±0.00% +> aiken/collection/dict.{filter_2} | -19.61% | ±0.00% +> aiken/collection/dict.{filter_3} | -20.15% | ±0.00% +> aiken/collection/dict.{insert_1} | -22.83% | ±0.00% +> aiken/collection/dict.{insert_2} | -21.77% | ±0.00% +> aiken/collection/dict.{insert_with_1} | -17.21% | ±0.00% +> aiken/collection/dict.{insert_with_2} | -22.66% | ±0.00% +> aiken/collection/dict.{insert_with_3} | -25.81% | ±0.00% +> aiken/collection/dict.{map_1} | -19.56% | ±0.00% +> aiken/collection/dict.{map_2} | -23.66% | ±0.00% +> aiken/collection/dict.{union_1} | -17.91% | ±0.00% +> aiken/collection/dict.{union_2} | -8.67% | ±0.00% +> aiken/collection/dict.{union_3} | -22.82% | ±0.00% +> aiken/collection/dict.{union_4} | -22.77% | ±0.00% +> aiken/collection/dict.{union_with_1} | -22.90% | ±0.00% +> aiken/collection/dict.{fold_1} | -35.94% | ±0.00% +> aiken/collection/dict.{fold_2} | -22.31% | ±0.00% +> aiken/collection/dict.{foldr_1} | -36.21% | ±0.00% +> aiken/collection/dict.{foldr_2} | -21.93% | ±0.00% +> aiken/collection/dict.{to_list_1} | -98.69% | -66.72% +> aiken/collection/dict.{to_list_2} | -98.91% | -66.72% +> aiken/collection/list.{push_1} | -8.02% | ±0.00% +> aiken/collection/list.{push_2} | 1.25% | ±0.00% +> aiken/collection/list.{range_1} | -27.77% | ±0.00% +> aiken/collection/list.{range_2} | -27.39% | ±0.00% +> aiken/collection/list.{repeat_1} | -23.72% | ±0.00% +> aiken/collection/list.{repeat_2} | -27.96% | ±0.00% +> aiken/collection/list.{all_1} | -28.36% | ±0.00% +> aiken/collection/list.{all_2} | -27.59% | ±0.00% +> aiken/collection/list.{all_3} | -27.94% | ±0.00% +> aiken/collection/list.{any_1} | -28.23% | ±0.00% +> aiken/collection/list.{any_2} | -28.09% | ±0.00% +> aiken/collection/list.{any_3} | -26.95% | ±0.00% +> aiken/collection/list.{at_1} | -27.60% | ±0.00% +> aiken/collection/list.{at_2} | -19.96% | ±0.00% +> aiken/collection/list.{at_3} | -27.60% | ±0.00% +> aiken/collection/list.{at_4} | -20.77% | ±0.00% +> aiken/collection/list.{at_5} | -25.75% | ±0.00% +> aiken/collection/list.{count_empty} | -36.83% | ±0.00% +> aiken/collection/list.{count_all} | -32.37% | ±0.00% +> aiken/collection/list.{count_some} | -31.73% | ±0.00% +> aiken/collection/list.{count_none} | -30.44% | ±0.00% +> aiken/collection/list.{find_1} | -20.59% | ±0.00% +> aiken/collection/list.{find_2} | -25.53% | ±0.00% +> aiken/collection/list.{find_3} | -19.64% | ±0.00% +> aiken/collection/list.{has_1} | -27.88% | ±0.00% +> aiken/collection/list.{has_2} | -27.69% | ±0.00% +> aiken/collection/list.{has_3} | -26.95% | ±0.00% +> aiken/collection/list.{head_1} | -14.03% | ±0.00% +> aiken/collection/list.{head_2} | -16.90% | ±0.00% +> aiken/collection/list.{is_empty_1} | -26.48% | ±0.00% +> aiken/collection/list.{is_empty_2} | -25.35% | ±0.00% +> aiken/collection/list.{index_of_1} | -25.62% | ±0.00% +> aiken/collection/list.{index_of_2} | -27.52% | ±0.00% +> aiken/collection/list.{index_of_3} | -26.65% | ±0.00% +> aiken/collection/list.{index_of_4} | -19.96% | ±0.00% +> aiken/collection/list.{last_1} | -19.18% | ±0.00% +> aiken/collection/list.{last_2} | -16.26% | ±0.00% +> aiken/collection/list.{last_3} | -17.13% | ±0.00% +> aiken/collection/list.{length_1} | -37.90% | ±0.00% +> aiken/collection/list.{length_2} | -30.89% | ±0.00% +> aiken/collection/list.{delete_1} | -20.20% | ±0.00% +> aiken/collection/list.{delete_2} | -15.02% | ±0.00% +> aiken/collection/list.{delete_3} | -20.55% | ±0.00% +> aiken/collection/list.{delete_4} | -22.46% | ±0.00% +> aiken/collection/list.{drop_1} | -24.62% | ±0.00% +> aiken/collection/list.{drop_2} | -28.08% | ±0.00% +> aiken/collection/list.{drop_while_1} | -19.79% | ±0.00% +> aiken/collection/list.{drop_while_2} | -22.25% | ±0.00% +> aiken/collection/list.{drop_while_3} | 0.86% | ±0.00% +> aiken/collection/list.{drop_while_4} | -27.26% | ±0.00% +> aiken/collection/list.{filter_1} | -20.20% | ±0.00% +> aiken/collection/list.{filter_2} | -32.06% | ±0.00% +> aiken/collection/list.{filter_3} | -31.39% | ±0.00% +> aiken/collection/list.{filter_map_1} | -21.10% | ±0.00% +> aiken/collection/list.{filter_map_2} | -28.74% | ±0.00% +> aiken/collection/list.{init_1} | -19.64% | ±0.00% +> aiken/collection/list.{init_2} | -20.01% | ±0.00% +> aiken/collection/list.{init_3} | -13.72% | ±0.00% +> aiken/collection/list.{partition_1} | -14.63% | ±0.00% +> aiken/collection/list.{partition_2} | -16.85% | ±0.00% +> aiken/collection/list.{partition_3} | -16.63% | ±0.00% +> aiken/collection/list.{partition_4} | -16.87% | ±0.00% +> aiken/collection/list.{partition_5} | -22.94% | ±0.00% +> aiken/collection/list.{slice_1} | -29.08% | -2.81% +> aiken/collection/list.{slice_2} | -30.11% | -2.25% +> aiken/collection/list.{slice_3} | -30.29% | -1.46% +> aiken/collection/list.{slice_4} | -28.53% | -1.48% +> aiken/collection/list.{slice_5} | -29.73% | -1.64% +> aiken/collection/list.{slice_6} | -32.01% | -1.80% +> aiken/collection/list.{span_1} | -15.05% | ±0.00% +> aiken/collection/list.{span_2} | -18.03% | ±0.00% +> aiken/collection/list.{span_3} | -12.49% | ±0.00% +> aiken/collection/list.{span_4} | -18.13% | ±0.00% +> aiken/collection/list.{tail_1} | -8.88% | ±0.00% +> aiken/collection/list.{tail_2} | -16.90% | ±0.00% +> aiken/collection/list.{take_1} | -24.98% | ±0.00% +> aiken/collection/list.{take_2} | -24.35% | ±0.00% +> aiken/collection/list.{take_while_1} | -20.20% | ±0.00% +> aiken/collection/list.{take_while_2} | -21.56% | ±0.00% +> aiken/collection/list.{take_while_3} | -22.46% | ±0.00% +> aiken/collection/list.{take_while_4} | -21.02% | ±0.00% +> aiken/collection/list.{unique_1} | -20.20% | ±0.00% +> aiken/collection/list.{unique_2} | -24.34% | ±0.00% +> aiken/collection/list.{flat_map_1} | -19.79% | ±0.00% +> aiken/collection/list.{flat_map_2} | -13.36% | ±0.00% +> aiken/collection/list.{indexed_map_1} | -20.10% | ±0.00% +> aiken/collection/list.{indexed_map_2} | -23.36% | ±0.00% +> aiken/collection/list.{map_1} | -19.79% | ±0.00% +> aiken/collection/list.{map_2} | -16.75% | ±0.00% +> aiken/collection/list.{map2_1} | -20.10% | ±0.00% +> aiken/collection/list.{map2_2} | -17.46% | ±0.00% +> aiken/collection/list.{map2_3} | -15.92% | ±0.00% +> aiken/collection/list.{map3_1} | -20.39% | ±0.00% +> aiken/collection/list.{map3_2} | -19.22% | ±0.00% +> aiken/collection/list.{reverse_1} | -20.10% | ±0.00% +> aiken/collection/list.{reverse_2} | -12.26% | ±0.00% +> aiken/collection/list.{sort_1} | -22.31% | ±0.00% +> aiken/collection/list.{sort_2} | -17.93% | ±0.00% +> aiken/collection/list.{sort_3} | -23.09% | ±0.00% +> aiken/collection/list.{sort_4} | -20.20% | ±0.00% +> aiken/collection/list.{unzip_1} | -14.01% | ±0.00% +> aiken/collection/list.{unzip_2} | -5.48% | ±0.00% +> aiken/collection/list.{concat_1} | -6.56% | ±0.00% +> aiken/collection/list.{concat_2} | -11.25% | ±0.00% +> aiken/collection/list.{concat_3} | -9.35% | ±0.00% +> aiken/collection/list.{difference_1} | -24.23% | ±0.00% +> aiken/collection/list.{difference_2} | -22.59% | ±0.00% +> aiken/collection/list.{difference_3} | -10.64% | ±0.00% +> aiken/collection/list.{difference_4} | -21.68% | ±0.00% +> aiken/collection/list.{zip_1} | -20.10% | ±0.00% +> aiken/collection/list.{zip_2} | -19.17% | ±0.00% +> aiken/collection/list.{zip_3} | -10.35% | ±0.00% +> aiken/collection/list.{foldl_1} | -36.95% | ±0.00% +> aiken/collection/list.{foldl_2} | -26.90% | ±0.00% +> aiken/collection/list.{foldl_3} | -11.27% | ±0.00% +> aiken/collection/list.{foldr_1} | -26.68% | ±0.00% +> aiken/collection/list.{foldr_2} | -38.04% | ±0.00% +> aiken/collection/list.{foldr_3} | -10.14% | ±0.00% +> aiken/collection/list.{indexed_foldr_1} | -36.95% | ±0.00% +> aiken/collection/list.{indexed_foldr_2} | -11.06% | ±0.00% +> aiken/collection/list.{reduce_1} | -36.95% | ±0.00% +> aiken/collection/list.{reduce_2} | -27.99% | ±0.00% +> aiken/collection/list.{reduce_3} | -23.54% | ±0.00% +> aiken/collection/list.{reduce_4} | -24.84% | ±0.00% +> aiken/collection/pairs.{get_all_1} | -21.10% | ±0.00% +> aiken/collection/pairs.{get_all_2} | -18.86% | ±0.00% +> aiken/collection/pairs.{get_all_3} | -19.53% | ±0.00% +> aiken/collection/pairs.{get_all_4} | -18.70% | ±0.00% +> aiken/collection/pairs.{get_all_5} | -21.19% | ±0.00% +> aiken/collection/pairs.{get_first_1} | -20.63% | ±0.00% +> aiken/collection/pairs.{get_first_2} | -18.86% | ±0.00% +> aiken/collection/pairs.{get_first_3} | -18.86% | ±0.00% +> aiken/collection/pairs.{get_first_4} | -18.86% | ±0.00% +> aiken/collection/pairs.{get_first_5} | -21.05% | ±0.00% +> aiken/collection/pairs.{get_last_1} | -20.63% | ±0.00% +> aiken/collection/pairs.{get_last_2} | -21.13% | ±0.00% +> aiken/collection/pairs.{get_last_3} | -21.16% | ±0.00% +> aiken/collection/pairs.{get_last_4} | -21.79% | ±0.00% +> aiken/collection/pairs.{get_last_5} | -21.05% | ±0.00% +> aiken/collection/pairs.{find_all_1} | -21.10% | ±0.00% +> aiken/collection/pairs.{find_all_2} | -18.33% | ±0.00% +> aiken/collection/pairs.{find_all_3} | -20.51% | ±0.00% +> aiken/collection/pairs.{find_all_4} | -17.79% | ±0.00% +> aiken/collection/pairs.{find_first_1} | -20.63% | ±0.00% +> aiken/collection/pairs.{find_first_2} | -18.28% | ±0.00% +> aiken/collection/pairs.{find_first_3} | -20.22% | ±0.00% +> aiken/collection/pairs.{find_first_4} | -18.28% | ±0.00% +> aiken/collection/pairs.{find_last_1} | -20.63% | ±0.00% +> aiken/collection/pairs.{find_last_2} | -20.70% | ±0.00% +> aiken/collection/pairs.{find_last_3} | -20.22% | ±0.00% +> aiken/collection/pairs.{find_last_4} | -20.98% | ±0.00% +> aiken/collection/pairs.{has_key_1} | -28.07% | ±0.00% +> aiken/collection/pairs.{has_key_2} | -25.70% | ±0.00% +> aiken/collection/pairs.{has_key_3} | -25.80% | ±0.00% +> aiken/collection/pairs.{has_key_4} | -24.93% | ±0.00% +> aiken/collection/pairs.{has_key_5} | -25.70% | ±0.00% +> aiken/collection/pairs.{keys_1} | -20.30% | ±0.00% +> aiken/collection/pairs.{keys_2} | -13.89% | ±0.00% +> aiken/collection/pairs.{keys_3} | -10.43% | ±0.00% +> aiken/collection/pairs.{values_1} | -20.30% | ±0.00% +> aiken/collection/pairs.{values_2} | -14.02% | ±0.00% +> aiken/collection/pairs.{values_3} | -10.65% | ±0.00% +> aiken/collection/pairs.{values_4} | -8.53% | ±0.00% +> aiken/collection/pairs.{map_1} | -11.17% | ±0.00% +> aiken/collection/pairs.{map_2} | -12.89% | ±0.00% +> aiken/collection/pairs.{foldl_1} | -35.94% | ±0.00% +> aiken/collection/pairs.{foldl_2} | -22.31% | ±0.00% +> aiken/collection/pairs.{foldr_1} | -36.21% | ±0.00% +> aiken/collection/pairs.{foldr_2} | -21.93% | ±0.00% +> aiken/collection/pairs.{foldr_3} | -20.00% | ±0.00% +> aiken/interval.{contains_1} | -21.08% | -4.01% +> aiken/interval.{contains_2} | -31.22% | -13.95% +> aiken/interval.{contains_3} | -26.80% | -10.08% +> aiken/interval.{contains_4} | -31.02% | -13.67% +> aiken/interval.{contains_5} | -32.32% | -13.59% +> aiken/interval.{contains_6} | -28.15% | -9.81% +> aiken/interval.{contains_7} | -32.11% | -13.32% +> aiken/interval.{contains_8} | -29.56% | -12.59% +> aiken/interval.{contains_9} | -29.68% | -12.78% +> aiken/interval.{contains_10} | -29.68% | -12.78% +> aiken/interval.{contains_11} | -35.17% | -17.77% +> aiken/interval.{contains_12} | -21.09% | -3.86% +> aiken/interval.{is_entirely_after_1} | -29.89% | -13.81% +> aiken/interval.{is_entirely_after_2} | -29.63% | -13.39% +> aiken/interval.{is_entirely_after_3} | -29.63% | -13.39% +> aiken/interval.{is_entirely_after_4} | -29.48% | -11.81% +> aiken/interval.{is_entirely_after_5} | -29.70% | -12.14% +> aiken/interval.{is_entirely_after_6} | -36.09% | -19.77% +> aiken/interval.{is_entirely_after_7} | -24.19% | -3.99% +> aiken/interval.{is_entirely_after_8} | -24.19% | -3.99% +> aiken/interval.{is_entirely_after_9} | -24.19% | -3.99% +> aiken/interval.{is_entirely_before_1} | -28.44% | -13.48% +> aiken/interval.{is_entirely_before_2} | -28.24% | -13.09% +> aiken/interval.{is_entirely_before_3} | -28.24% | -13.09% +> aiken/interval.{is_entirely_before_4} | -28.44% | -11.88% +> aiken/interval.{is_entirely_before_5} | -28.26% | -11.57% +> aiken/interval.{is_entirely_before_6} | -34.63% | -19.34% +> aiken/interval.{is_entirely_before_7} | -22.97% | -4.02% +> aiken/interval.{is_entirely_before_8} | -22.97% | -4.02% +> aiken/interval.{is_entirely_before_9} | -22.97% | -4.02% +> aiken/interval.{hull_1} | -21.51% | -0.73% +> aiken/interval.{hull_2} | -23.06% | -0.80% +> aiken/interval.{hull_3} | -22.00% | -0.86% +> aiken/interval.{intersection_1} | -21.51% | -0.73% +> aiken/interval.{intersection_2} | -21.51% | -0.73% +> aiken/interval.{intersection_3} | -26.55% | -4.65% +> aiken/interval.{intersection_4} | -26.45% | -4.51% +> aiken/interval.{intersection_5} | -22.87% | -0.76% +> aiken/interval.{intersection_6} | -19.73% | -0.98% +> aiken/math.{abs_1} | -61.39% | -21.07% +> aiken/math.{abs_2} | -70.90% | -34.84% +> aiken/math.{clamp_1} | -60.95% | -23.55% +> aiken/math.{clamp_2} | -60.95% | -23.55% +> aiken/math.{clamp_3} | -59.22% | -18.20% +> aiken/math.{gcd_test1} | -47.20% | ±0.00% +> aiken/math.{gcd_test2} | -47.81% | ±0.00% +> aiken/math.{gcd_test3} | -46.10% | ±0.00% +> aiken/math.{is_sqrt1} | -87.41% | -68.64% +> aiken/math.{is_sqrt2} | -87.41% | -68.64% +> aiken/math.{log_10_2} | -51.35% | -8.40% +> aiken/math.{log_42_2} | -51.46% | -8.24% +> aiken/math.{log_42_3} | -51.05% | -7.81% +> aiken/math.{log_5_0} | -54.05% | -12.92% +> aiken/math.{log_4_4} | -50.59% | -9.31% +> aiken/math.{log_4_43} | -49.14% | -7.28% +> aiken/math.{max_1} | -61.39% | -21.07% +> aiken/math.{max_2} | -61.39% | -21.07% +> aiken/math.{max_3} | -61.39% | -21.07% +> aiken/math.{min_1} | -61.39% | -21.07% +> aiken/math.{min_2} | -61.39% | -21.07% +> aiken/math.{min_3} | -61.39% | -21.07% +> aiken/math.{pow_3_5} | -46.34% | ±0.00% +> aiken/math.{pow_7_2} | -46.38% | ±0.00% +> aiken/math.{pow_3__4} | -43.50% | ±0.00% +> aiken/math.{pow_0_0} | -43.95% | ±0.00% +> aiken/math.{pow_513_3} | -45.80% | ±0.00% +> aiken/math.{pow_2_4} | -46.79% | ±0.00% +> aiken/math.{pow_2_42} | -46.77% | ±0.00% +> aiken/math.{pow2_neg} | -44.71% | ±0.00% +> aiken/math.{pow2_0} | -45.00% | ±0.00% +> aiken/math.{pow2_1} | -45.00% | ±0.00% +> aiken/math.{pow2_4} | -45.00% | ±0.00% +> aiken/math.{pow2_42} | -42.01% | ±0.00% +> aiken/math.{pow2_256} | -41.40% | ±0.00% +> aiken/math.{sqrt1} | -32.56% | -17.18% +> aiken/math.{sqrt2} | -32.56% | -17.18% +> aiken/math.{sqrt3} | -49.99% | -8.90% +> aiken/math.{sqrt4} | -51.76% | -3.90% +> aiken/math.{sqrt5} | -52.63% | -1.33% +> aiken/math.{sqrt6} | -28.16% | -15.41% +> aiken/math/rational.{from_int_1} | -14.32% | ±0.00% +> aiken/math/rational.{new_1} | -22.98% | ±0.00% +> aiken/math/rational.{zero_1} | -8.08% | ±0.00% +> aiken/math/rational.{denominator_1} | -28.33% | ±0.00% +> aiken/math/rational.{numerator_1} | -29.34% | ±0.00% +> aiken/math/rational.{abs_examples} | -18.25% | ±0.00% +> aiken/math/rational.{negate_1} | -15.39% | ±0.00% +> aiken/math/rational.{reciprocal_1} | -23.28% | ±0.00% +> aiken/math/rational.{reduce_1} | -31.89% | ±0.00% +> aiken/math/rational.{add_1} | -15.11% | ±0.00% +> aiken/math/rational.{add_2} | -15.11% | ±0.00% +> aiken/math/rational.{div_1} | -22.31% | -2.75% +> aiken/math/rational.{div_2} | -22.37% | -2.79% +> aiken/math/rational.{mul_1} | -13.37% | ±0.00% +> aiken/math/rational.{mul_2} | -13.37% | ±0.00% +> aiken/math/rational.{mul_3} | -26.25% | ±0.00% +> aiken/math/rational.{sub_1} | -15.11% | ±0.00% +> aiken/math/rational.{sub_2} | -15.11% | ±0.00% +> aiken/math/rational.{sub_3} | -15.11% | ±0.00% +> aiken/math/rational.{compare_1} | -21.70% | ±0.00% +> aiken/math/rational.{compare_with_eq} | -23.05% | ±0.00% +> aiken/math/rational.{compare_with_neq} | -22.33% | ±0.00% +> aiken/math/rational.{compare_with_gte} | -22.48% | ±0.00% +> aiken/math/rational.{compare_with_gt} | -23.18% | ±0.00% +> aiken/math/rational.{compare_with_lte} | -22.48% | ±0.00% +> aiken/math/rational.{compare_with_lt} | -23.18% | ±0.00% +> aiken/math/rational.{arithmetic_mean_1} | -23.31% | ±0.00% +> aiken/math/rational.{arithmetic_mean_2} | -23.31% | ±0.00% +> aiken/math/rational.{arithmetic_mean_3} | -20.58% | ±0.00% +> aiken/math/rational.{geometric_mean1} | -29.87% | ±0.00% +> aiken/math/rational.{geometric_mean2} | -24.52% | ±0.00% +> aiken/math/rational.{geometric_mean3} | -24.52% | ±0.00% +> aiken/math/rational.{geometric_mean4} | -33.55% | ±0.00% +> aiken/math/rational.{geometric_mean5} | -45.34% | ±0.00% +> aiken/math/rational.{ceil_1} | -36.26% | ±0.00% +> aiken/math/rational.{floor_1} | -29.49% | ±0.00% +> aiken/math/rational.{proper_fraction_1} | -18.44% | ±0.00% +> aiken/math/rational.{proper_fraction_2} | -18.44% | ±0.00% +> aiken/math/rational.{proper_fraction_3} | -18.44% | ±0.00% +> aiken/math/rational.{round_1} | -25.17% | ±0.00% +> aiken/math/rational.{round_even_1} | -25.91% | ±0.00% +> aiken/math/rational.{truncate_1} | -29.49% | ±0.00% +> aiken/option.{is_none_1} | -26.56% | ±0.00% +> aiken/option.{is_none_2} | -27.52% | ±0.00% +> aiken/option.{is_some_1} | -27.52% | ±0.00% +> aiken/option.{is_some_2} | -26.56% | ±0.00% +> aiken/option.{and_then_1} | -20.19% | ±0.00% +> aiken/option.{and_then_2} | -22.15% | ±0.00% +> aiken/option.{and_then_3} | -21.85% | ±0.00% +> aiken/option.{choice_1} | -17.11% | ±0.00% +> aiken/option.{choice_2} | -19.75% | ±0.00% +> aiken/option.{choice_3} | -18.68% | ±0.00% +> aiken/option.{flatten_1} | -12.25% | ±0.00% +> aiken/option.{flatten_2} | -15.41% | ±0.00% +> aiken/option.{flatten_3} | -19.46% | ±0.00% +> aiken/option.{flatten_4} | -14.31% | ±0.00% +> aiken/option.{map_1} | -19.89% | ±0.00% +> aiken/option.{map_2} | -18.18% | ±0.00% +> aiken/option.{map2_1} | -20.47% | ±0.00% +> aiken/option.{map2_2} | -19.93% | ±0.00% +> aiken/option.{map2_3} | -13.64% | ±0.00% +> aiken/option.{map3_1} | -20.74% | ±0.00% +> aiken/option.{map3_2} | -20.00% | ±0.00% +> aiken/option.{map3_3} | -19.90% | ±0.00% +> aiken/option.{or_try_1} | -14.36% | ±0.00% +> aiken/option.{or_try_2} | -14.36% | ±0.00% +> aiken/option.{or_else_1} | -38.16% | ±0.00% +> aiken/option.{or_else_2} | -27.62% | ±0.00% +> aiken/primitive/bytearray.{from_string_1} | -62.36% | ±0.00% +> aiken/primitive/bytearray.{from_string_2} | -41.62% | ±0.00% +> aiken/primitive/bytearray.{push_1} | -97.51% | -80.06% +> aiken/primitive/bytearray.{push_2} | -97.51% | -80.06% +> aiken/primitive/bytearray.{push_3} | -88.82% | -89.83% +> aiken/primitive/bytearray.{index_of_1} | -39.75% | ±0.00% +> aiken/primitive/bytearray.{index_of_2} | -43.19% | ±0.00% +> aiken/primitive/bytearray.{index_of_3} | -41.70% | ±0.00% +> aiken/primitive/bytearray.{index_of_4} | -37.24% | ±0.00% +> aiken/primitive/bytearray.{index_of_5} | -26.02% | ±0.00% +> aiken/primitive/bytearray.{is_empty_1} | -37.52% | ±0.00% +> aiken/primitive/bytearray.{is_empty_2} | -33.77% | ±0.00% +> aiken/primitive/bytearray.{length_1} | -49.73% | ±0.00% +> aiken/primitive/bytearray.{length_2} | -49.73% | ±0.00% +> aiken/primitive/bytearray.{test_bit_0} | -45.48% | 5.88% +> aiken/primitive/bytearray.{test_bit_1} | -56.22% | -10.85% +> aiken/primitive/bytearray.{test_bit_2} | -56.22% | -10.85% +> aiken/primitive/bytearray.{test_bit_3} | -56.22% | -10.85% +> aiken/primitive/bytearray.{test_bit_7} | -58.31% | -11.81% +> aiken/primitive/bytearray.{test_bit_8} | -56.22% | -10.85% +> aiken/primitive/bytearray.{test_bit_20_21_22_23} | -44.38% | 5.52% +> aiken/primitive/bytearray.{drop_1} | -58.79% | ±0.00% +> aiken/primitive/bytearray.{drop_2} | -58.79% | ±0.00% +> aiken/primitive/bytearray.{drop_3} | -58.79% | ±0.00% +> aiken/primitive/bytearray.{drop_4} | -58.79% | ±0.00% +> aiken/primitive/bytearray.{slice_1} | -98.79% | -90.04% +> aiken/primitive/bytearray.{slice_2} | -98.79% | -90.04% +> aiken/primitive/bytearray.{slice_3} | -98.79% | -90.04% +> aiken/primitive/bytearray.{slice_4} | -98.79% | -90.04% +> aiken/primitive/bytearray.{slice_5} | -98.79% | -90.04% +> aiken/primitive/bytearray.{take_1} | -97.81% | -83.40% +> aiken/primitive/bytearray.{take_2} | -97.81% | -83.40% +> aiken/primitive/bytearray.{take_3} | -97.81% | -83.40% +> aiken/primitive/bytearray.{take_4} | -97.81% | -83.40% +> aiken/primitive/bytearray.{concat_1} | -96.22% | -80.06% +> aiken/primitive/bytearray.{concat_2} | -96.22% | -80.06% +> aiken/primitive/bytearray.{concat_3} | -96.22% | -80.06% +> aiken/primitive/bytearray.{concat_4} | -96.22% | -80.06% +> aiken/primitive/bytearray.{foldl_1} | -40.96% | ±0.00% +> aiken/primitive/bytearray.{foldl_2} | -40.09% | ±0.00% +> aiken/primitive/bytearray.{foldl_3} | -40.29% | ±0.00% +> aiken/primitive/bytearray.{foldl_4} | -44.76% | ±0.00% +> aiken/primitive/bytearray.{foldr_1} | -42.56% | ±0.00% +> aiken/primitive/bytearray.{foldr_2} | -40.93% | ±0.00% +> aiken/primitive/bytearray.{foldr_3} | -45.34% | ±0.00% +> aiken/primitive/bytearray.{reduce_1} | -42.95% | ±0.00% +> aiken/primitive/bytearray.{reduce_2} | -44.60% | ±0.00% +> aiken/primitive/bytearray.{to_string_1} | -69.56% | ±0.00% +> aiken/primitive/bytearray.{to_string_2} | -53.54% | ±0.00% +> aiken/primitive/bytearray.{to_hex_1} | -48.15% | ±0.00% +> aiken/primitive/bytearray.{to_hex_2} | -48.15% | ±0.00% +> aiken/primitive/int.{from_utf8_1} | -37.06% | ±0.00% +> aiken/primitive/int.{from_utf8_2} | -33.40% | ±0.00% +> aiken/primitive/int.{from_utf8_3} | -37.06% | ±0.00% +> aiken/primitive/int.{from_utf8_4} | -32.78% | ±0.00% +> aiken/primitive/int.{from_utf8_5} | -32.05% | ±0.00% +> aiken/primitive/int.{from_utf8_6} | -31.36% | ±0.00% +> aiken/primitive/string.{from_bytearray_1} | -69.56% | ±0.00% +> aiken/primitive/string.{from_bytearray_2} | -53.54% | ±0.00% +> aiken/primitive/string.{from_bytearray_3} | -53.54% | ±0.00% +> aiken/primitive/string.{from_int_1} | -40.54% | -7.05% +> aiken/primitive/string.{from_int_2} | -45.93% | -5.30% +> aiken/primitive/string.{from_int_3} | -47.62% | -4.35% +> aiken/primitive/string.{from_int_4} | -48.58% | -3.69% +> aiken/primitive/string.{concat_1} | -92.30% | -80.10% +> aiken/primitive/string.{concat_2} | -97.34% | -85.87% +> aiken/primitive/string.{concat_3} | -98.67% | -80.35% +> aiken/primitive/string.{join_1} | -42.87% | ±0.00% +> aiken/primitive/string.{join_2} | -37.65% | ±0.00% +> aiken/primitive/string.{to_bytearray_1} | -62.36% | ±0.00% +> aiken/primitive/string.{to_bytearray_2} | -41.62% | ±0.00% +> aiken/primitive/string.{to_bytearray_3} | -41.62% | ±0.00% +> cardano/assets.{from_asset_list_1} | -20.51% | ±0.00% +> cardano/assets.{from_asset_list_2} | -10.09% | ±0.00% +> cardano/assets.{from_asset_list_3} | -12.21% | ±0.00% +> cardano/assets.{from_asset_list_4} | -16.22% | ±0.00% +> cardano/assets.{from_asset_list_5} | -14.60% | ±0.00% +> cardano/assets.{from_asset_list_6} | -20.97% | ±0.00% +> cardano/assets.{from_asset_list_7} | -20.25% | ±0.00% +> cardano/assets.{from_asset_list_8} | -14.51% | ±0.00% +> cardano/assets.{from_asset_list_9} | -16.07% | ±0.00% +> cardano/assets.{add_1} | -27.84% | ±0.00% +> cardano/assets.{add_2} | -27.56% | -0.54% +> cardano/assets.{add_3} | -26.39% | ±0.00% +> cardano/assets.{add_4} | -29.75% | -10.41% +> cardano/assets.{add_5} | -27.80% | ±0.00% +> cardano/assets.{merge_1} | -26.02% | ±0.00% +> cardano/assets.{merge_2} | -19.60% | ±0.00% +> cardano/assets.{merge_3} | -23.80% | ±0.00% +> cardano/assets.{merge_4} | -25.92% | ±0.00% +> cardano/assets.{merge_5} | -27.61% | -1.98% +> cardano/assets.{without_lovelace_1} | -28.00% | -2.24% +> cardano/assets.{without_lovelace_2} | -27.49% | ±0.00% +> cardano/assets.{without_lovelace_3} | -23.40% | -0.34% +> cardano/assets.{flatten_with_1} | -21.10% | ±0.00% +> cardano/assets.{flatten_with_2} | -22.77% | ±0.00% +> cardano/assets.{reduce_1} | -24.31% | ±0.00% +> cardano/assets.{reduce_2} | -20.89% | ±0.00% +> cardano/assets.{reduce_3} | -36.21% | ±0.00% +>
+ +### Added + +- New modules covering Conway-related features (i.e. governance) + - [`cardano/governance`](https://aiken-lang.github.io/stdlib/cardano/governance.html) + - [`cardano/governance/protocol_parameters`](https://aiken-lang.github.io/stdlib/cardano/governance/protocol_parameters.html) + +- New primitives in `aiken/collection/pairs`: + - [`insert_by_ascending_key`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html#insert_by_ascending_key) + - [`repsert_by_ascending_key`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html#repsert_by_ascending_key) + +- New primitives in `aiken/crypto`: + - [`blake2b_224`](https://aiken-lang.github.io/stdlib/aiken/crypto.html#blake2b_224) + - [`keccak_256`](https://aiken-lang.github.io/stdlib/aiken/crypto.html#keccak_256) + +- New primitives in `aiken/math`: + - [`log2`](https://aiken-lang.github.io/stdlib/aiken/math.html#log2) + +- New primitives in `aiken/primitive/bytearray`: + - [`at`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#at) + - [`from_int_big_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#from_int_big_endian) + - [`from_int_little_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#from_int_little_endian) + - [`to_int_big_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#to_int_big_endian) + - [`to_int_little_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#to_int_little_endian) + +- New primitives in `aiken/primitive/int`: + - [`from_bytearray_big_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/int.html#from_bytearray_big_endian) + - [`from_bytearray_little_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/int.html#from_bytearray_little_endian) + +- New primitives in `aiken/crypto`: + - [`verify_ecdsa_signature`](https://aiken-lang.github.io/stdlib/cardano/credential.html#verify_ecdsa_signature) + - [`verify_schnorr_signature`](https://aiken-lang.github.io/stdlib/cardano/credential.html#verify_schnorr_signature) + +### Changed + +- Few modules have been relocated and better organized: + - `aiken/hash` -> [`aiken/crypto`](https://aiken-lang.github.io/stdlib/aiken/crypto.html) + - **collections** + - `aiken/dict` -> [`aiken/collection/dict`](https://aiken-lang.github.io/stdlib/aiken/collection/dict.html) + - `aiken/list` -> [`aiken/collection/list`](https://aiken-lang.github.io/stdlib/aiken/collection/list.html) + - `aiken/pairs` -> [`aiken/collection/pairs`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html) + - **primitive** + - `aiken/bytearray` -> [`aiken/primitive/bytearray`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html) + - `aiken/int` -> [`aiken/primitive/int`](https://aiken-lang.github.io/stdlib/aiken/primitive/int.html) + - `aiken/string` -> [`aiken/primitive/string`](https://aiken-lang.github.io/stdlib/aiken/primitive/string.html) + - **cardano** + - `aiken/transaction` -> [`cardano/transaction`](https://aiken-lang.github.io/stdlib/cardano/transaction.html) + - `aiken/transaction/certificate` -> [`cardano/certificate`](https://aiken-lang.github.io/stdlib/cardano/certificate.html) + - `aiken/transaction/credential` -> [`cardano/address`](https://aiken-lang.github.io/stdlib/cardano/address.html) & `aiken/crypto` + - `aiken/transaction/value` -> [`cardano/assets`](https://aiken-lang.github.io/stdlib/cardano/assets.html) + +- Several zero-argument functions have been turned into top-level constants + - `aiken/dict.new()` -> [`aiken/collection/dict.empty`](https://aiken-lang.github.io/stdlib/aiken/collection/dict.html#empty) + - `aiken/interval.empty()` -> [`aiken/interval.empty`](https://aiken-lang.github.io/stdlib/aiken/interval.html#empty) + - `aiken/interval.everything()` -> [`aiken/interval.everything`](https://aiken-lang.github.io/stdlib/aiken/interval.html#everything) + - `aiken/math/rational.zero()` -> [`aiken/math/rational.zero`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#zero) + - `aiken/transaction/value.zero()` -> [`cardano/assets.zero`](https://aiken-lang.github.io/stdlib/cardano/assets.html#zero) + +- The `Transaction` type from [`cardano/transaction`](https://aiken-lang.github.io/stdlib/cardano/transaction.html) (originally `aiken/transaction`) has been greatly reworked to match the new transaction format in Plutus V3. + +- The `ScriptContext` type has split from `cardano/transaction` (originally `aiken/transaction`) and moved into its own module [`cardano/script_context`](https://aiken-lang.github.io/stdlib/cardano/script_context.html) and adjusted to its new form as per Plutus V3. + +- The constructors of [`Credential`](https://aiken-lang.github.io/stdlib/cardano/address.html#credential) have been renamed from `VerificationKeyCredential` and `ScriptCredential` into `VerificationKey` and `Script` respectively. + +- The function `remove_all`, `remove_first` and `remove_last` from [`aiken/collection/pairs`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html) (originally `aiken/pairs`) have been renamed to `delete_all`, `delete_first` and `delete_last` respectively. + +- The function `verify_signature` from [`aiken/crypto`](https://aiken-lang.github.io/stdlib/aiken/crypto.html) (originally `aiken/credential`) has been renamed to `verify_ed25519_signature`. + +### Removed + +- The module `aiken/time`. The `PosixTime` alias is no longer used anywhere. + +- `MintedValue` (from `aiken/transaction/value` originally) and its associated functions are no longer needed and, therefore, gone. + +## v1.9.0 - 2024-05-24 + +### Added + +- A new module [`aiken/pairs`](https://aiken-lang.github.io/stdlib/aiken/pairs.html) to work with associative lists (a.k.a. `Pairs`). + +### Changed + +- **BREAKING-CHANGE**
+ Specialized all `Dict`'s key to `ByteArray`, and thus remove the need for passing an extra comparison function in many functions. `Dict` are however still specialized with a phantom type for keys. + +- **BREAKING-CHANGE**
+ Few functions from `Dict` have been renamed for consistency: + - `from_list` -> `from_pairs` + - `from_ascending_list` -> `from_ascending_pairs` + - `to_list` -> `to_pairs` + +### Removed + +N/A + +## v1.8.0 - 2024-03-28 + +### Added + +- [`value.reduce`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#reduce) to efficiently fold over a value and its elements. + +- [`value.from_asset_list`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#from_asset_list) to turn an asset list into a Value while enforcing invariants expected of `Value`. + +- [`math.is_sqrt`](https://aiken-lang.github.io/stdlib/aiken/math.html#is_sqrt) as a more efficient alternative to `sqrt`. + +### Changed + +- Disclaimers in documentation to [`bytearray.to_string`](https://aiken-lang.github.io/stdlib/aiken/bytearray.html#to_string) and [`string.from_bytearray`](https://aiken-lang.github.io/stdlib/aiken/string.html#from_bytearray) regarding UTF-8 encoding. + +### Removed + +N/A + +## v1.7.0 - 2023-11-07 + +### Added + +- [`list.index_of`](https://aiken-lang.github.io/stdlib/aiken/list.html#index_of): For getting a values index in a list. +- [`transaction.placeholder`](https://aiken-lang.github.io/stdlib/aiken/transaction.html#placeholder): For constructing test transactions. +- [`transaction.value.is_zero`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#is_zero): For checking whether a value is null. + +### Changed + +- [`value.to_minted_value`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#to_minted_value) now correctly preserves the invariant of `MintedValue`: it always contain a null quantity of Ada. + +### Removed + +N/A + +## v1.6.0 - 2023-09-08 + +### Added + +- [`math.pow2`](https://aiken-lang.github.io/stdlib/aiken/math.html#pow2): For faster exponentions for powers of two. +- [`bytearray.test_bit`](https://aiken-lang.github.io/stdlib/aiken/bytearray.html#test_bit): For testing if a bit is set in a bytearray (MSB). + +## v1.5.0 - 2023-08-16 + +### Removed + +- retired `list.and` and `list.or` because of the new keywords for logical op chaining. + +## v1.4.0 - 2023-07-21 + +### Changed + +- Fixed missing null-check on `value.add`. Adding a null quantity of token is now correctly a no-op. + +## v1.3.0 - 2023-06-30 + +### Added + +- [`math.sqrt`](https://aiken-lang.github.io/stdlib/aiken/math.html#sqrt): For calculating integer square roots using a quadratically convergent method. +- [`math/rational.numerator`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#numerator) & [`math/rational.denominator`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#numerator): For accessing parts of a rational value. +- [`math/rational.arithmetic_mean`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#arithmetic_mean): For computing [arithmetic mean](https://en.wikipedia.org/wiki/Arithmetic_mean) of rational values. +- [`math/rational.geometric_mean`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#geometric_mean): For computing [geometric mean](https://en.wikipedia.org/wiki/Geometric_mean) of two rational values. + +### Changed + +- Clear empty asset lists in [`Value`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#Value) on various operations. Before that fix, it could happen that removing all assets from a given policy would lead to an empty dictionnary of assets still be present in the `Value`. + +## v1.2.0 - 2023-06-17 + +### Added + +- [`transaction/value.MintedValue`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#MintedValue) +- [`transaction/value.from_minted_value`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#from_minted_value): Convert from `MintedValue` to `Value` +- [`transaction/value.to_minted_value`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#to_minted_value): Convert from `Value` to `MintedValue` +- [`transaction/bytearray.to_hex`](https://aiken-lang.github.io/stdlib/aiken/bytearray.html#to_hex): Convert a `ByteArray` to a hex encoded `String` +- [`math/rational`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html): Working with rational numbers. + - [x] `abs` + - [x] `add` + - [x] `ceil` + - [x] `compare` + - [x] `compare_with` + - [x] `div` + - [x] `floor` + - [x] `from_int` + - [x] `mul` + - [x] `negate` + - [x] `new` + - [x] `proper_fraction` + - [x] `reciprocal` + - [x] `reduce` + - [x] `round` + - [x] `round_even` + - [x] `sub` + - [x] `truncate` + - [x] `zero` + +### Removed + +- module `MintedValue` was merged with `Value` + +## v1.1.0 - 2023-06-06 + +### Added + +- [`list.count`](https://aiken-lang.github.io/stdlib/aiken/list.html#count): Count how many items in the list satisfy the given predicate. + +- [`int.from_utf8`](https://aiken-lang.github.io/stdlib/aiken/int.html#from_utf8): Parse an integer from a utf-8 encoded `ByteArray`, when possible. + +- [`dict.foldl`](https://aiken-lang.github.io/stdlib/aiken/dict.html#foldl) & [`dict.foldr`](https://aiken-lang.github.io/stdlib/aiken/dict.html#foldr): for left and right folds over dictionnary elements in ascending key order. + +- [`dict.insert_with`](https://aiken-lang.github.io/stdlib/aiken/dict.html#insert_with): Insert a value in the dictionary at a given key. When the key already exist, the provided merge function is called. + +- [`transaction/value.add`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#add): Add a (positive or negative) quantity of a single token to a value. This is more efficient than `merge` for a single asset. + +- [`transaction/value.to_dict`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#to_dict): Convert a `Value` into a dictionnary of dictionnaries. + +- A new module [`transaction/minted_value`](https://aiken-lang.github.io/stdlib/aiken/transaction/minted_value.html): This is used exclusively for representing values present in the `mint` field of transactions. This allows to simplify some of the implementation for `Value` which no longer needs to handle the special case where null-quantity tokens would be present. It isn't possible to construct `MintedValue` by hand, they come from the script context entirely and are 'read-only'. + +- More documentation for `dict` and `interval` modules. + +### Changed + +> **Warning** +> +> Most of those changes are breaking-changes. Though, given we're still in an +> alpha state, only the `minor` component is bumped from the version number. +> Please forgive us. + +- Rework `list.{foldl, foldr, reduce, indexed_foldr}`, `dict.{fold}`, `bytearray.{foldl, foldr, reduce}` to take the iterator as last argument. For example: + + ``` + fn foldl(self: List, with: fn(a, b) -> b, zero: b) -> b + + ↓ becomes + + fn foldl(self: List, zero: b, with: fn(a, b) -> b) -> b + ``` + +- Fixed implementation of `bytearray.slice`; `slice` would otherwise behave as if the second argument were an offset. + +- Rename `transaction/value.add` into `transaction/value.merge`. + +- Swap arguments of the merge function in `dict.union_with`; the first value received now corresponds to the value already present in the dictionnary. + +- Fixed various examples from the documentation + +### Removed + +- Removed `dict.fold`; replaced with `dict.foldl` and `dict.foldr` to remove ambiguity. + +## v1.0.0 - 2023-04-13 + +### Added + +N/A + +### Changed + +N/A + +### Removed + +N/A diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/LICENSE b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/LICENSE new file mode 100644 index 00000000..4a1de273 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/LICENSE @@ -0,0 +1,201 @@ + Apache License + Version 2.0, January 2004 + http://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + + APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + + Copyright 2022 Lucas Rosa + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/README.md b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/README.md new file mode 100644 index 00000000..4cd6fef2 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/README.md @@ -0,0 +1,71 @@ +
+
+

Aiken Aiken Standard Library

+ +[![Licence](https://img.shields.io/github/license/aiken-lang/stdlib?style=for-the-badge)](https://github.com/aiken-lang/stdlib/blob/main/LICENSE) +[![Continuous Integration](https://img.shields.io/github/actions/workflow/status/aiken-lang/stdlib/continuous-integration.yml?style=for-the-badge)](https://github.com/aiken-lang/stdlib/actions/workflows/continuous-integration.yml) + +
+
+ +## Getting started + +``` +aiken add aiken-lang/stdlib --version v2 +``` + +## Compatibility + +aiken's version | stdlib's version(s) +--- | --- +`v1.1.3`
`v1.1.4`
`v1.1.5`
`v1.1.6`
`v1.1.7` | `>= 2.1.0` +`v1.1.1`
`v1.1.2` | `>= 2.0.0` && `< 2.1.0` +`v1.0.29-alpha`
`v1.0.28-alpha` | `>= 1.9.0` && `< 2.0.0` +`v1.0.26-alpha` | `<= 1.8.0` && `< 1.9.0` + +## Overview + +The official standard library for the [Aiken](https://aiken-lang.org) Cardano +smart-contract language. + +It extends the language builtins with useful data-types, functions, constants +and aliases that make using Aiken a bliss. + +```aiken +use aiken/collection/list +use aiken/crypto.{VerificationKeyHash} +use cardano/transaction.{OutputReference, Transaction} + +pub type Datum { + owner: VerificationKeyHash, +} + +pub type Redeemer { + msg: ByteArray, +} + +/// A simple validator which replicates a basic public/private signature lock. +/// +/// - The key (hash) is set as datum when the funds are sent to the script address. +/// - The spender is expected to provide a signature, and the string 'Hello, World!' as message +/// - The signature is implicitly verified by the ledger, and included as 'extra_signatories' +/// +validator hello_world { + spend(datum: Option, redeemer: Redeemer, _, self: Transaction) { + expect Some(Datum { owner }) = datum + + let must_say_hello = redeemer.msg == "Hello, World!" + + let must_be_signed = list.has(self.extra_signatories, owner) + + and { + must_say_hello, + must_be_signed, + } + } +} +``` + +## Stats + +![Alt](https://repobeats.axiom.co/api/embed/f0a17e7f6133630e165b9e56ec5447bef32fe831.svg "Repobeats analytics image") diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/aiken.lock b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/aiken.lock new file mode 100644 index 00000000..769ac20f --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/aiken.lock @@ -0,0 +1,16 @@ +# This file was generated by Aiken +# You typically do not need to edit this file + +[[requirements]] +name = "aiken-lang/fuzz" +version = "v2" +source = "github" + +[[packages]] +name = "aiken-lang/fuzz" +version = "v2" +requirements = [] +source = "github" + +[etags] +"aiken-lang/fuzz@v2" = [{ secs_since_epoch = 1734106349, nanos_since_epoch = 450591000 }, "64a32283418d58cade34059d3855b857e84505541158c541c460cafa0d355475"] diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/aiken.toml b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/aiken.toml new file mode 100644 index 00000000..cbc76a0b --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/aiken.toml @@ -0,0 +1,15 @@ +name = "aiken-lang/stdlib" +version = "2.2.0" +compiler = "v1.1.9" +plutus = "v3" +description = "The Aiken Standard Library" + +[repository] +user = "aiken-lang" +project = "stdlib" +platform = "github" + +[[dependencies]] +name = "aiken-lang/fuzz" +version = "v2" +source = "github" diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/cbor.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/cbor.ak new file mode 100644 index 00000000..f0c66d69 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/cbor.ak @@ -0,0 +1,293 @@ +use aiken +use aiken/builtin.{decode_utf8, serialise_data} +use aiken/primitive/bytearray + +/// Obtain a String representation of _anything_. This is particularly (and only) useful for tracing +/// and debugging. This function is expensive and should not be used in any production code as it +/// will very likely explodes the validator's budget. +/// +/// The output is a [CBOR diagnostic](https://www.rfc-editor.org/rfc/rfc8949#name-diagnostic-notation) +/// of the underlying on-chain binary representation of the data. It's not as +/// easy to read as plain Aiken code, but it is handy for troubleshooting values +/// _at runtime_. Incidentally, getting familiar with reading CBOR diagnostic is +/// a good idea in the Cardano world. +/// +/// ```aiken +/// cbor.diagnostic(42) == "42" +/// cbor.diagnostic(#"a1b2") == "h'A1B2'" +/// cbor.diagnostic([1, 2, 3]) == "[_ 1, 2, 3]" +/// cbor.diagnostic([]) == "[]" +/// cbor.diagnostic((1, 2)) == "[_ 1, 2]" +/// cbor.diagnostic((1, #"ff", 3)) == "[_ 1, h'FF', 3]" +/// cbor.diagnostic([(1, #"ff")]) == "{_ 1: h'FF' }" +/// cbor.diagnostic(Some(42)) == "121([_ 42])" +/// cbor.diagnostic(None) == "122([])" +/// ``` +pub fn diagnostic(self: Data) -> String { + aiken.diagnostic(self, #"") + |> decode_utf8 +} + +/// Deserialise a [CBOR](https://www.rfc-editor.org/rfc/rfc8949) Data. This is the reverse operation of [serialise](#serialise). +/// In particular, we have the following property: +/// +/// ```aiken +/// cbor.deserialise(cbor.serialise(any_data)) == Some(any_data) +/// ``` +/// +/// > [!CAUTION] +/// > Unfortunately, this function isn't derived from a builtin primitive. It +/// > is therefore an order of magnitude more expensive than its counterpart +/// > and shall be used with care. +/// > +/// > In general, one might prefer avoiding deserialisation unless truly necessary. +/// > Yet, it may come in handy for testing and in rare scenarios. +pub fn deserialise(bytes: ByteArray) -> Option { + let length = bytearray.length(bytes) + + let peek = + fn(offset: Int, callback: fn(Byte) -> Decoder) -> Decoder { + fn(cursor) { + if 0 >= cursor { + deserialise_failure + } else { + callback(bytearray.at(bytes, length - cursor))(cursor - offset) + } + } + } + + let take = + fn(n: Int, callback: fn(ByteArray) -> Decoder) -> Decoder { + fn(cursor) { + if 0 >= cursor { + deserialise_failure + } else { + callback(builtin.slice_bytearray(length - cursor, n, bytes))( + cursor - n, + ) + } + } + } + + if length == 0 { + None + } else { + let Pair(result, consumed) = decode_data(peek, take)(length) + if consumed != 0 { + None + } else { + Some(result) + } + } +} + +/// Serialise any value to binary, encoding using [CBOR](https://www.rfc-editor.org/rfc/rfc8949). +/// +/// This is particularly useful in combination with hashing functions, as a way +/// to obtain a byte representation that matches the serialised representation +/// used by the ledger in the context of on-chain code. +/// +/// Note that the output matches the output of [`diagnostic`](#diagnostic), +/// though with a different encoding. [`diagnostic`](#diagnostic) is merely a +/// textual representation of the CBOR encoding that is human friendly and +/// useful for debugging. +/// +/// ```aiken +/// cbor.serialise(42) == #"182a" +/// cbor.serialise(#"a1b2") == #"42a1b2" +/// cbor.serialise([]) == #"80" +/// cbor.serialise((1, 2)) == #"9f0102ff" +/// cbor.serialise((1, #"ff", 3)) == #"9f0141ff03ff" +/// cbor.serialise([(1, #"ff")]) == #"a10141ff" +/// cbor.serialise(Some(42)) == #"d8799f182aff" +/// cbor.serialise(None) == #"d87a80" +/// ``` +pub fn serialise(self: Data) -> ByteArray { + serialise_data(self) +} + +type Byte = + Int + +type Decoder
= + fn(Int) -> Pair + +type Peek = + fn(Int, fn(Byte) -> Decoder) -> Decoder + +type Take = + fn(Int, fn(ByteArray) -> Decoder) -> Decoder + +fn return(data: Data) -> Decoder { + fn(cursor) { Pair(data, cursor) } +} + +const deserialise_failure: Pair = { + let empty: Data = "" + Pair(empty, -1) + } + +const token_begin_bytes = 0x5f + +const token_begin_list = 0x9f + +const token_begin_map = 0xbf + +const token_break = 0xff + +fn decode_data(peek: Peek, take: Take) -> Decoder { + let next <- peek(1) + let major_type = next / 32 + if major_type <= 2 { + if major_type == 0 { + let i <- decode_uint(peek, take, next) + return(builtin.i_data(i)) + } else if major_type == 1 { + let i <- decode_uint(peek, take, next - 32) + return(builtin.i_data(-i - 1)) + } else { + if next == token_begin_bytes { + let b <- decode_chunks(peek, take) + return(builtin.b_data(b)) + } else { + let b <- decode_bytes(peek, take, next - 64) + return(builtin.b_data(b)) + } + } + } else if major_type == 6 { + let tag <- decode_uint(peek, take, next - 192) + let next <- peek(1) + if tag == 102 { + fn(_) { deserialise_failure } + } else { + let ix = + if tag >= 1280 { + tag - 1280 + 7 + } else { + tag - 121 + } + if next == token_begin_list { + let fields <- decode_indefinite(peek, take, decode_data) + return(builtin.constr_data(ix, fields)) + } else { + let size <- decode_uint(peek, take, next - 128) + let fields <- decode_definite(peek, take, decode_data, size) + return(builtin.constr_data(ix, fields)) + } + } + } else if major_type == 4 { + if next == token_begin_list { + let xs <- decode_indefinite(peek, take, decode_data) + return(builtin.list_data(xs)) + } else { + let size <- decode_uint(peek, take, next - 128) + let xs <- decode_definite(peek, take, decode_data, size) + return(builtin.list_data(xs)) + } + } else if major_type == 5 { + if next == token_begin_map { + let xs <- decode_indefinite(peek, take, decode_pair) + return(builtin.map_data(xs)) + } else { + let size <- decode_uint(peek, take, next - 160) + let xs <- decode_definite(peek, take, decode_pair, size) + return(builtin.map_data(xs)) + } + } else { + fn(_) { deserialise_failure } + } +} + +fn decode_pair(peek: Peek, take: Take) -> Decoder> { + fn(cursor) { + let Pair(k, cursor) = decode_data(peek, take)(cursor) + let Pair(v, cursor) = decode_data(peek, take)(cursor) + Pair(Pair(k, v), cursor) + } +} + +fn decode_uint( + peek: Peek, + take: Take, + header: Int, + and_then: fn(Int) -> Decoder, +) -> Decoder { + if header < 24 { + and_then(header) + } else if header == 24 { + let payload <- peek(1) + and_then(payload) + } else if header < 28 { + let width = bytearray.at(#[2, 4, 8], header - 25) + let payload <- take(width) + and_then(bytearray.to_int_big_endian(payload)) + } else { + fn(_) { deserialise_failure } + } +} + +fn decode_bytes( + peek: Peek, + take: Take, + header: Int, + and_then: fn(ByteArray) -> Decoder, +) -> Decoder { + let width <- decode_uint(peek, take, header) + let bytes <- take(width) + and_then(bytes) +} + +fn decode_chunks( + peek: Peek, + take: Take, + and_then: fn(ByteArray) -> Decoder, +) -> Decoder { + let next <- peek(1) + if next == token_break { + and_then("") + } else { + let chunk <- decode_bytes(peek, take, next - 64) + let chunks <- decode_chunks(peek, take) + and_then(builtin.append_bytearray(chunk, chunks)) + } +} + +fn decode_definite( + peek: Peek, + take: Take, + decode_one: fn(Peek, Take) -> Decoder, + size: Int, + and_then: fn(List) -> Decoder, +) -> Decoder { + if size <= 0 { + and_then([]) + } else { + fn(cursor) { + let Pair(elem, cursor) = decode_one(peek, take)(cursor) + { + let elems <- decode_definite(peek, take, decode_one, size - 1) + and_then([elem, ..elems]) + }(cursor) + } + } +} + +fn decode_indefinite( + peek: Peek, + take: Take, + decode_one: fn(Peek, Take) -> Decoder, + and_then: fn(List) -> Decoder, +) -> Decoder { + let next <- peek(1) + if next == token_break { + and_then([]) + } else { + fn(cursor) { + let Pair(elem, cursor) = decode_one(peek, take)(cursor + 1) + { + let elems <- decode_indefinite(peek, take, decode_one) + and_then([elem, ..elems]) + }(cursor) + } + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/cbor.test.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/cbor.test.ak new file mode 100644 index 00000000..28d9f5bb --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/cbor.test.ak @@ -0,0 +1,297 @@ +use aiken/cbor.{deserialise, diagnostic, serialise} +use aiken/fuzz + +// ------------------------------------------------------------------ diagnostic + +test diagnostic_1() { + diagnostic(42) == @"42" +} + +test diagnostic_2() { + diagnostic(#"a1b2") == @"h'A1B2'" +} + +test diagnostic_3() { + diagnostic([1, 2, 3]) == @"[_ 1, 2, 3]" +} + +test diagnostic_4() { + diagnostic([]) == @"[]" +} + +test diagnostic_5() { + diagnostic((1, 2)) == @"[_ 1, 2]" +} + +test diagnostic_6() { + diagnostic((1, #"ff", 3)) == @"[_ 1, h'FF', 3]" +} + +test diagnostic_7() { + diagnostic([(1, #"ff")]) == @"[_ [_ 1, h'FF']]" +} + +test diagnostic_7_alt() { + diagnostic([Pair(1, #"ff")]) == @"{_ 1: h'FF' }" +} + +test diagnostic_8() { + diagnostic(Some(42)) == @"121([_ 42])" +} + +test diagnostic_9() { + diagnostic(None) == @"122([])" +} + +test diagnostic_10() { + let xs: List<(Int, Int)> = [] + diagnostic(xs) == @"[]" +} + +test diagnostic_10_alt() { + let xs: Pairs = [] + diagnostic(xs) == @"{}" +} + +type Foo { + foo: Bar, +} + +type Bar { + A + B(Int) +} + +test diagnostic_11() { + diagnostic(Foo { foo: A }) == @"121([_ 121([])])" +} + +test diagnostic_12() { + diagnostic(Foo { foo: B(42) }) == @"121([_ 122([_ 42])])" +} + +type Baz { + a0: Int, + b0: ByteArray, +} + +test diagnostic_13() { + diagnostic(Baz { a0: 14, b0: #"ff" }) == @"121([_ 14, h'FF'])" +} + +test diagnostic_14() { + diagnostic([0]) == @"[_ 0]" +} + +test diagnostic_15() { + diagnostic(-42) == @"-42" +} + +test diagnostic_16() { + diagnostic([-1, 0, 1]) == @"[_ -1, 0, 1]" +} + +// ------------------------------------------------------------------ serialise + +test serialise_1() { + serialise(42) == #"182a" +} + +test serialise_2() { + serialise(#"a1b2") == #"42a1b2" +} + +test serialise_3() { + serialise([]) == #"80" +} + +test serialise_4() { + serialise((1, 2)) == #"9f0102ff" +} + +test serialise_5() { + serialise((1, #"ff", 3)) == #"9f0141ff03ff" +} + +test serialise_6() { + serialise([(1, #"ff")]) == #"9f9f0141ffffff" +} + +test serialise_7() { + serialise(Some(42)) == #"d8799f182aff" +} + +test serialise_8() { + serialise(None) == #"d87a80" +} + +test serialise_9() { + serialise([Pair(1, #"ff")]) == #"a10141ff" +} + +// ------------------------------------------------------------------ deserialise + +type AnyData { + AnyInt(Int) + AnyByteArray(ByteArray) + AnyList(List) + AnyPairs(Pairs) + AnyUnaryConstr0(UnaryConstr0) + AnyUnaryConstr1(UnaryConstr1) + AnyUnaryConstr2(UnaryConstr2) + AnyBinaryConstr0(BinaryConstr0) + AnyBinaryConstr1(BinaryConstr1) +} + +type UnaryConstr0 { + UnaryConstr0 +} + +type UnaryConstr1 { + field0: String, +} + +type UnaryConstr2 { + field0: Int, + field1: List>, +} + +type BinaryConstr0 = + Bool + +type BinaryConstr1 = + Option + +fn any_pair(any_key: Fuzzer, any_value: Fuzzer) -> Fuzzer> { + let k <- fuzz.and_then(any_key) + let v <- fuzz.map(any_value) + Pair(k, v) +} + +fn any_data() -> Fuzzer { + fuzz.either6( + { + let i <- fuzz.map(fuzz.int()) + AnyInt(i) + }, + { + let bs <- fuzz.map(fuzz.bytearray()) + AnyByteArray(bs) + }, + { + let xs <- fuzz.map(fuzz.list(fuzz.int())) + AnyList(xs) + }, + { + let ps <- fuzz.map(fuzz.list(any_pair(fuzz.bytearray(), fuzz.int()))) + AnyPairs(ps) + }, + fuzz.either3( + fuzz.constant(AnyUnaryConstr0(UnaryConstr0)), + fuzz.constant(AnyUnaryConstr1(UnaryConstr1(@"lorem ipsum"))), + { + let i <- fuzz.and_then(fuzz.int()) + let xs <- fuzz.map(fuzz.list(fuzz.list(fuzz.bytearray()))) + AnyUnaryConstr2(UnaryConstr2(i, xs)) + }, + ), + fuzz.either( + { + let b <- fuzz.map(fuzz.bool()) + AnyBinaryConstr0(b) + }, + { + let o <- fuzz.map(fuzz.option(fuzz.int())) + AnyBinaryConstr1(o) + }, + ), + ) +} + +test unit_deserialise_not_enough_bytes_1() { + expect None = deserialise(#"") +} + +test unit_deserialise_not_enough_bytes_2() { + expect None = deserialise(#"82") +} + +test unit_deserialise_non_empty_leftovers() { + expect None = deserialise(#"811442") +} + +test unit_deserialise_invalid_header() { + expect None = deserialise(#"f1") +} + +test unit_deserialise_invalid_uint() { + expect None = deserialise(#"1d0013bdae") +} + +/// A full script context with a minting policy and various assets. Meant to be +/// non-trivial and cover many things we might encounter in a transaction. +test bench_deserialise_script_context() { + expect Some(_) = + deserialise( + #"d8799fd8799f9fd8799fd8799f5820000000000000000000000000000000000000000000000000000000000000000000ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffd87a80ffa140a1401a000f4240d87980d87a80ffffff9fd8799fd8799f5820000000000000000000000000000000000000000000000000000000000000000000ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffd87a80ffa140a1401a000f4240d87980d87a80ffffff9fd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffd87a80ffa140a1401a000f4240d87a9f5820923918e403bf43c34b4ef6b48eb2ee04babed17320d8d1b9ff9ad086e86f44ecffd87a80ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffffffffa340a1401a000f4240581c0c8eaf490c53afbf27e3d84a3b57da51fbafe5aa78443fcec2dc262ea14561696b656e182a581c12593b4cbf7fdfd8636db99fe356437cd6af8539aadaa0a401964874a14474756e611b00005af3107a4000d87980d87a80ffd8799fd8799fd87a9f581c00000000000000000000000000000000000000000000000000000000ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffffffffa240a1401a000f4240581c0c8eaf490c53afbf27e3d84a3b57da51fbafe5aa78443fcec2dc262ea14763617264616e6f01d87980d8799f581c68ad54b3a8124d9fe5caaaf2011a85d72096e696a2fb3d7f86c41717ffffff182aa2581c0c8eaf490c53afbf27e3d84a3b57da51fbafe5aa78443fcec2dc262ea24561696b656e2d4763617264616e6f01581c12593b4cbf7fdfd8636db99fe356437cd6af8539aadaa0a401964874a14474756e611b00005af3107a400080a0d8799fd8799fd87980d87a80ffd8799fd87b80d87a80ffff80a2d8799f581c0c8eaf490c53afbf27e3d84a3b57da51fbafe5aa78443fcec2dc262effd87980d8799f581c12593b4cbf7fdfd8636db99fe356437cd6af8539aadaa0a401964874ff182aa15820923918e403bf43c34b4ef6b48eb2ee04babed17320d8d1b9ff9ad086e86f44ecd879805820e757985e48e43a95a185ddba08c814bc20f81cb68544ac937a9b992e4e6c38a0a080d87a80d87a80ff182ad8799f581c12593b4cbf7fdfd8636db99fe356437cd6af8539aadaa0a401964874ffff", + ) +} + +test prop_deserialise_any_data(any via any_data()) { + when any is { + AnyInt(i) -> { + fuzz.label(@"Int") + expect Some(data) = deserialise(serialise(i)) + expect i_decoded: Int = data + i_decoded == i + } + AnyByteArray(bs) -> { + fuzz.label(@"ByteArray") + expect Some(data) = deserialise(serialise(bs)) + expect bs_decoded: ByteArray = data + bs_decoded == bs + } + AnyList(xs) -> { + fuzz.label(@"List") + expect Some(data) = deserialise(serialise(xs)) + expect xs_decoded: List = data + xs_decoded == xs + } + AnyPairs(ps) -> { + fuzz.label(@"Pairs") + expect Some(data) = deserialise(serialise(ps)) + expect ps_decoded: Pairs = data + ps_decoded == ps + } + AnyUnaryConstr0(constr) -> { + fuzz.label(@"(unary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: UnaryConstr0 = data + constr_decoded == constr + } + AnyUnaryConstr1(constr) -> { + fuzz.label(@"(unary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: UnaryConstr1 = data + constr_decoded == constr + } + AnyUnaryConstr2(constr) -> { + fuzz.label(@"(unary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: UnaryConstr2 = data + constr_decoded == constr + } + AnyBinaryConstr0(constr) -> { + fuzz.label(@"(binary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: BinaryConstr0 = data + constr_decoded == constr + } + AnyBinaryConstr1(constr) -> { + fuzz.label(@"(binary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: BinaryConstr1 = data + constr_decoded == constr + } + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection.ak new file mode 100644 index 00000000..3d4d332e --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection.ak @@ -0,0 +1,4 @@ +/// A non negative integer that materializes the position of an element in a +/// collection. +pub type Index = + Int diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection/dict.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection/dict.ak new file mode 100644 index 00000000..681d0bae --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection/dict.ak @@ -0,0 +1,1174 @@ +//// A module for working with bytearray dictionaries. +//// +//// +//// > [!IMPORTANT] +//// > +//// > Dictionaries are **ordered sets** of key-value pairs, which thus +//// > preserve some invariants. Specifically, each key is only present once in +//// > the dictionary and all keys are stored in ascending lexicographic order. +//// > +//// > These invariants allow for more optimized functions to operate on `Dict`, +//// > but as a trade-offs, prevent `Dict` from being serializable. To recover a `Dict` +//// > from an unknown `Data`, you must first recover an `Pairs` and use +//// > [`dict.from_ascending_list`](#from_ascending_list). + +use aiken/builtin + +/// An opaque `Dict`. The type is opaque because the module maintains some +/// invariant, namely: there's only one occurrence of a given key in the dictionary. +/// +/// Note that the `key` parameter is a phantom-type, and only present as a +/// means of documentation. Keys can be any type, yet will need to comparable +/// to use functions like `insert`. +/// +/// See for example: +/// +/// ```aiken +/// pub type Value = +/// Dict> +/// ``` +pub opaque type Dict { + inner: Pairs, +} + +// ## Constructing + +/// An empty dictionnary. +/// ```aiken +/// dict.to_pairs(dict.empty) == [] +/// ``` +pub const empty: Dict = Dict { inner: [] } + +const foo = #"666f6f" + +const bar = #"626172" + +const baz = #"62617a" + +const fixture_1 = + empty + |> insert(foo, 42) + |> insert(bar, 14) + +/// Like ['from_pairs'](#from_pairs), but from an already sorted list by ascending +/// keys. This function fails (i.e. halts the program execution) if the list isn't +/// sorted. +/// +/// ```aiken +/// let pairs = [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// +/// let result = +/// dict.from_ascending_pairs(pairs) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// ``` +/// +/// This is meant to be used to turn a list constructed off-chain into a `Dict` +/// which has taken care of maintaining interval invariants. This function still +/// performs a sanity check on all keys to avoid silly mistakes. It is, however, +/// considerably faster than ['from_pairs'](from_pairs) +pub fn from_ascending_pairs(xs: Pairs) -> Dict { + let Void = check_ascending_list(xs) + Dict { inner: xs } +} + +fn check_ascending_list(xs: Pairs) { + when xs is { + [] -> Void + [_] -> Void + [Pair(x0, _), Pair(x1, _) as e, ..rest] -> + if builtin.less_than_bytearray(x0, x1) { + check_ascending_list([e, ..rest]) + } else { + fail @"keys in associative list aren't in ascending order" + } + } +} + +/// Like [`from_ascending_pairs`](#from_ascending_pairs) but fails if **any** +/// value doesn't satisfy the predicate. +/// +/// ```aiken +/// let pairs = [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// +/// dict.from_ascending_pairs_with(pairs, fn(x) { x <= 250 }) // fail +/// ``` +pub fn from_ascending_pairs_with( + xs: Pairs, + predicate: fn(value) -> Bool, +) -> Dict { + let Void = check_ascending_pairs_with(xs, predicate) + Dict { inner: xs } +} + +fn check_ascending_pairs_with( + xs: Pairs, + predicate: fn(value) -> Bool, +) { + when xs is { + [] -> Void + [Pair(_, v)] -> + if predicate(v) { + Void + } else { + fail @"value doesn't satisfy predicate" + } + [Pair(x0, v0), Pair(x1, _) as e, ..rest] -> + if builtin.less_than_bytearray(x0, x1) { + if predicate(v0) { + check_ascending_pairs_with([e, ..rest], predicate) + } else { + fail @"value doesn't satisfy predicate" + } + } else { + fail @"keys in pairs aren't in ascending order" + } + } +} + +test bench_from_ascending_pairs() { + let dict = + from_ascending_pairs( + [ + Pair("aaaa", 1), Pair("aaab", 9), Pair("aaba", 5), Pair("aabb", 13), + Pair("abaa", 2), Pair("abab", 10), Pair("abba", 6), Pair("abbb", 14), + Pair("baaa", 3), Pair("baab", 11), Pair("baba", 7), Pair("babb", 15), + Pair("bbaa", 4), Pair("bbab", 12), Pair("bbba", 8), Pair("bbbb", 16), + ], + ) + + size(dict) == 16 +} + +/// Construct a dictionary from a list of key-value pairs. Note that when a key is present +/// multiple times, the first occurrence prevails. +/// +/// ```aiken +/// let pairs = [Pair("a", 100), Pair("c", 300), Pair("b", 200)] +/// +/// let result = +/// dict.from_pairs(pairs) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn from_pairs(self: Pairs) -> Dict { + Dict { inner: do_from_pairs(self) } +} + +fn do_from_pairs(xs: Pairs) -> Pairs { + when xs is { + [] -> [] + [Pair(k, v), ..rest] -> do_insert(do_from_pairs(rest), k, v) + } +} + +test from_list_1() { + from_pairs([]) == empty +} + +test from_list_2() { + from_pairs([Pair(foo, 42), Pair(bar, 14)]) == from_pairs( + [Pair(bar, 14), Pair(foo, 42)], + ) +} + +test from_list_3() { + from_pairs([Pair(foo, 42), Pair(bar, 14)]) == fixture_1 +} + +test from_list_4() { + from_pairs([Pair(foo, 42), Pair(bar, 14), Pair(foo, 1337)]) == fixture_1 +} + +test bench_from_pairs() { + let dict = + from_pairs( + [ + Pair("bbba", 8), Pair("bbab", 12), Pair("aabb", 13), Pair("aaab", 9), + Pair("bbbb", 16), Pair("aaaa", 1), Pair("aaba", 5), Pair("abab", 10), + Pair("baba", 7), Pair("baab", 11), Pair("abaa", 2), Pair("baaa", 3), + Pair("bbaa", 4), Pair("babb", 15), Pair("abbb", 14), Pair("abba", 6), + ], + ) + + size(dict) == 16 +} + +// ## Inspecting + +/// Finds a value in the dictionary, and returns the first key found to have that value. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 42) +/// |> dict.insert(key: "b", value: 14) +/// |> dict.insert(key: "c", value: 42) +/// |> dict.find(42) +/// +/// result == Some("a") +/// ``` +pub fn find(self: Dict, value v: value) -> Option { + do_find(self.inner, v) +} + +fn do_find(self: Pairs, value v: value) -> Option { + when self is { + [] -> None + [Pair(k2, v2), ..rest] -> + if v == v2 { + Some(k2) + } else { + do_find(rest, v) + } + } +} + +test find_1() { + find(empty, foo) == None +} + +test find_2() { + find( + empty + |> insert(foo, 14), + 14, + ) == Some(foo) +} + +test find_3() { + find( + empty + |> insert(foo, 14), + 42, + ) == None +} + +test find_4() { + find( + empty + |> insert(foo, 14) + |> insert(bar, 42) + |> insert(baz, 14), + 14, + ) == Some(baz) +} + +/// Get a value in the dict by its key. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: "Aiken") +/// |> dict.get(key: "a") +/// +/// result == Some("Aiken") +/// ``` +pub fn get(self: Dict, key: ByteArray) -> Option { + do_get(self.inner, key) +} + +fn do_get(self: Pairs, key k: ByteArray) -> Option { + when self is { + [] -> None + [Pair(k2, v), ..rest] -> + if builtin.less_than_equals_bytearray(k, k2) { + if k == k2 { + Some(v) + } else { + None + } + } else { + do_get(rest, k) + } + } +} + +test get_1() { + get(empty, foo) == None +} + +test get_2() { + let m = + empty + |> insert(foo, "Aiken") + |> insert(bar, "awesome") + get(m, key: foo) == Some("Aiken") +} + +test get_3() { + let m = + empty + |> insert(foo, "Aiken") + |> insert(bar, "awesome") + get(m, key: baz) == None +} + +test get_4() { + let m = + empty + |> insert("aaa", "1") + |> insert("bbb", "2") + |> insert("ccc", "3") + |> insert("ddd", "4") + |> insert("eee", "5") + |> insert("fff", "6") + |> insert("ggg", "7") + |> insert("hhh", "8") + |> insert("iii", "9") + |> insert("jjj", "10") + + get(m, "bcd") == None +} + +test get_5() { + let m = + empty + |> insert("aaa", "1") + |> insert("bbb", "2") + |> insert("ccc", "3") + |> insert("ddd", "4") + |> insert("eee", "5") + |> insert("fff", "6") + |> insert("ggg", "7") + |> insert("hhh", "8") + |> insert("iii", "9") + |> insert("jjj", "10") + + get(m, "kkk") == None +} + +/// Check if a key exists in the dictionary. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: "Aiken") +/// |> dict.has_key("a") +/// +/// result == True +/// ``` +pub fn has_key(self: Dict, key k: ByteArray) -> Bool { + do_has_key(self.inner, k) +} + +fn do_has_key(self: Pairs, key k: ByteArray) -> Bool { + when self is { + [] -> False + [Pair(k2, _), ..rest] -> + if builtin.less_than_equals_bytearray(k, k2) { + k == k2 + } else { + do_has_key(rest, k) + } + } +} + +test has_key_1() { + !has_key(empty, foo) +} + +test has_key_2() { + has_key( + empty + |> insert(foo, 14), + foo, + ) +} + +test has_key_3() { + !has_key( + empty + |> insert(foo, 14), + bar, + ) +} + +test has_key_4() { + has_key( + empty + |> insert(foo, 14) + |> insert(bar, 42), + bar, + ) +} + +/// Efficiently checks whether a dictionary is empty. +/// ```aiken +/// dict.is_empty(dict.empty) == True +/// ``` +pub fn is_empty(self: Dict) -> Bool { + when self.inner is { + [] -> True + _ -> False + } +} + +test is_empty_1() { + is_empty(empty) +} + +/// Extract all the keys present in a given `Dict`. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 14) +/// |> dict.insert("b", 42) +/// |> dict.insert("a", 1337) +/// |> dict.keys() +/// +/// result == ["a", "b"] +/// ``` +pub fn keys(self: Dict) -> List { + do_keys(self.inner) +} + +fn do_keys(self: Pairs) -> List { + when self is { + [] -> [] + [Pair(k, _), ..rest] -> [k, ..do_keys(rest)] + } +} + +test keys_1() { + keys(empty) == [] +} + +test keys_2() { + keys( + empty + |> insert(foo, 0) + |> insert(bar, 0), + ) == [bar, foo] +} + +/// Return the number of key-value pairs in the dictionary. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 100) +/// |> dict.insert("b", 200) +/// |> dict.insert("c", 300) +/// |> dict.size() +/// +/// result == 3 +/// ``` +pub fn size(self: Dict) -> Int { + do_size(self.inner) +} + +fn do_size(self: Pairs) -> Int { + when self is { + [] -> 0 + [_, ..rest] -> 1 + do_size(rest) + } +} + +test size_1() { + size(empty) == 0 +} + +test size_2() { + size( + empty + |> insert(foo, 14), + ) == 1 +} + +test size_3() { + size( + empty + |> insert(foo, 14) + |> insert(bar, 42), + ) == 2 +} + +/// Extract all the values present in a given `Dict`. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 14) +/// |> dict.insert("b", 42) +/// |> dict.insert("c", 1337) +/// |> dict.values() +/// +/// result == [14, 42, 1337] +/// ``` +pub fn values(self: Dict) -> List { + do_values(self.inner) +} + +fn do_values(self: Pairs) -> List { + when self is { + [] -> [] + [Pair(_, v), ..rest] -> [v, ..do_values(rest)] + } +} + +test values_1() { + values(empty) == [] +} + +test values_2() { + values( + empty + |> insert(foo, 3) + |> insert(bar, 4), + ) == [4, 3] +} + +// ## Modifying + +/// Remove a key-value pair from the dictionary. If the key is not found, no changes are made. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.delete(key: "a") +/// |> dict.to_pairs() +/// +/// result == [Pair("b", 200)] +/// ``` +pub fn delete(self: Dict, key: ByteArray) -> Dict { + Dict { inner: do_delete(self.inner, key) } +} + +fn do_delete( + self: Pairs, + key k: ByteArray, +) -> Pairs { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if builtin.less_than_equals_bytearray(k, k2) { + if k == k2 { + rest + } else { + self + } + } else { + [Pair(k2, v2), ..do_delete(rest, k)] + } + } +} + +test delete_1() { + delete(empty, foo) == empty +} + +test delete_2() { + let m = + empty + |> insert(foo, 14) + delete(m, foo) == empty +} + +test delete_3() { + let m = + empty + |> insert(foo, 14) + delete(m, bar) == m +} + +test delete_4() { + let m = + empty + |> insert(foo, 14) + |> insert(bar, 14) + !has_key(delete(m, foo), foo) +} + +test delete_5() { + let m = + empty + |> insert(foo, 14) + |> insert(bar, 14) + has_key(delete(m, bar), foo) +} + +test delete_6() { + let m = + empty + |> insert("aaa", 1) + |> insert("bbb", 2) + |> insert("ccc", 3) + |> insert("ddd", 4) + |> insert("eee", 5) + |> insert("fff", 6) + |> insert("ggg", 7) + |> insert("hhh", 8) + |> insert("iii", 9) + |> insert("jjj", 10) + + delete(m, "bcd") == m +} + +/// Keep only the key-value pairs that pass the given predicate. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.insert(key: "c", value: 300) +/// |> dict.filter(fn(k, _v) { k != "a" }) +/// |> dict.to_pairs() +/// +/// result == [Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn filter( + self: Dict, + with: fn(ByteArray, value) -> Bool, +) -> Dict { + Dict { inner: do_filter(self.inner, with) } +} + +fn do_filter( + self: Pairs, + with: fn(ByteArray, value) -> Bool, +) -> Pairs { + when self is { + [] -> [] + [Pair(k, v), ..rest] -> + if with(k, v) { + [Pair(k, v), ..do_filter(rest, with)] + } else { + do_filter(rest, with) + } + } +} + +test filter_1() { + filter(empty, fn(_, _) { True }) == empty +} + +test filter_2() { + let expected = + empty + |> insert(foo, 42) + filter(fixture_1, fn(_, v) { v > 14 }) == expected +} + +test filter_3() { + let expected = + empty + |> insert(bar, 14) + filter(fixture_1, fn(k, _) { k == bar }) == expected +} + +/// Insert a value in the dictionary at a given key. If the key already exists, its value is **overridden**. If you need ways to combine keys together, use (`insert_with`)[#insert_with]. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 1) +/// |> dict.insert(key: "b", value: 2) +/// |> dict.insert(key: "a", value: 3) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 3), Pair("b", 2)] +/// ``` +pub fn insert( + self: Dict, + key k: ByteArray, + value v: value, +) -> Dict { + Dict { inner: do_insert(self.inner, k, v) } +} + +fn do_insert( + self: Pairs, + key k: ByteArray, + value v: value, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if builtin.less_than_bytearray(k, k2) { + [Pair(k, v), ..self] + } else { + if k == k2 { + [Pair(k, v), ..rest] + } else { + [Pair(k2, v2), ..do_insert(rest, k, v)] + } + } + } +} + +test insert_1() { + let m1 = + empty + |> insert(foo, 42) + let m2 = + empty + |> insert(foo, 14) + insert(m1, foo, 14) == m2 +} + +test insert_2() { + let m1 = + empty + |> insert(foo, 42) + let m2 = + empty + |> insert(bar, 14) + insert(m1, bar, 14) == insert(m2, foo, 42) +} + +/// Insert a value in the dictionary at a given key. When the key already exist, the provided +/// merge function is called. The value existing in the dictionary is passed as the second argument +/// to the merge function, and the new value is passed as the third argument. +/// +/// ```aiken +/// let sum = +/// fn (_k, a, b) { Some(a + b) } +/// +/// let result = +/// dict.empty +/// |> dict.insert_with(key: "a", value: 1, with: sum) +/// |> dict.insert_with(key: "b", value: 2, with: sum) +/// |> dict.insert_with(key: "a", value: 3, with: sum) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 4), Pair("b", 2)] +/// ``` +pub fn insert_with( + self: Dict, + key k: ByteArray, + value v: value, + with: fn(ByteArray, value, value) -> Option, +) -> Dict { + Dict { + inner: do_insert_with(self.inner, k, v, fn(k, v1, v2) { with(k, v2, v1) }), + } +} + +test insert_with_1() { + let sum = + fn(_k, a, b) { Some(a + b) } + + let result = + empty + |> insert_with(key: "foo", value: 1, with: sum) + |> insert_with(key: "bar", value: 2, with: sum) + |> to_pairs() + + result == [Pair("bar", 2), Pair("foo", 1)] +} + +test insert_with_2() { + let sum = + fn(_k, a, b) { Some(a + b) } + + let result = + empty + |> insert_with(key: "foo", value: 1, with: sum) + |> insert_with(key: "bar", value: 2, with: sum) + |> insert_with(key: "foo", value: 3, with: sum) + |> to_pairs() + + result == [Pair("bar", 2), Pair("foo", 4)] +} + +test insert_with_3() { + let with = + fn(k, a, _b) { + if k == "foo" { + Some(a) + } else { + None + } + } + + let result = + empty + |> insert_with(key: "foo", value: 1, with: with) + |> insert_with(key: "bar", value: 2, with: with) + |> insert_with(key: "foo", value: 3, with: with) + |> insert_with(key: "bar", value: 4, with: with) + |> to_pairs() + + result == [Pair("foo", 1)] +} + +/// Apply a function to all key-value pairs in a Dict. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 100) +/// |> dict.insert("b", 200) +/// |> dict.insert("c", 300) +/// |> dict.map(fn(_k, v) { v * 2 }) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 200), Pair("b", 400), Pair("c", 600)] +/// ``` +pub fn map(self: Dict, with: fn(ByteArray, a) -> b) -> Dict { + Dict { inner: do_map(self.inner, with) } +} + +fn do_map( + self: Pairs, + with: fn(ByteArray, a) -> b, +) -> Pairs { + when self is { + [] -> [] + [Pair(k, v), ..rest] -> [Pair(k, with(k, v)), ..do_map(rest, with)] + } +} + +test map_1() { + let result = + fixture_1 + |> map(with: fn(k, _) { k }) + get(result, foo) == Some(foo) +} + +test map_2() { + let result = + fixture_1 + |> map(with: fn(_, v) { v + 1 }) + get(result, foo) == Some(43) && size(result) == size(fixture_1) +} + +/// Remove a key-value pair from the dictionary and return its value. If the key is not found, no changes are made. +/// +/// ```aiken +/// let (value, _) = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.pop(key: "a") +/// +/// result == 100 +/// ``` +pub fn pop( + self: Dict, + key: ByteArray, +) -> (Option, Dict) { + do_pop(self.inner, key, fn(value, inner) { (value, Dict { inner }) }) +} + +fn do_pop( + self: Pairs, + key k: ByteArray, + return: fn(Option, Pairs) -> result, +) -> result { + when self is { + [] -> return(None, []) + [Pair(k2, v2), ..rest] -> + if builtin.less_than_equals_bytearray(k, k2) { + if k == k2 { + return(Some(v2), rest) + } else { + return(None, self) + } + } else { + do_pop( + rest, + k, + fn(value, inner) { return(value, [Pair(k2, v2), ..inner]) }, + ) + } + } +} + +test pop_1() { + pop(empty, foo) == (None, empty) +} + +test pop_2() { + let m = + empty + |> insert(foo, 14) + pop(m, foo) == (Some(14), empty) +} + +test pop_3() { + let m = + empty + |> insert(foo, 14) + pop(m, bar) == (None, m) +} + +test pop_4() { + let m = + empty + |> insert(foo, 14) + |> insert(bar, 14) + pop(m, foo) == (Some(14), empty |> insert(bar, 14)) +} + +test pop_6() { + let m = + empty + |> insert("aaa", 1) + |> insert("bbb", 2) + |> insert("ccc", 3) + |> insert("ddd", 4) + |> insert("eee", 5) + |> insert("fff", 6) + |> insert("ggg", 7) + |> insert("hhh", 8) + |> insert("iii", 9) + |> insert("jjj", 10) + + pop(m, "bcd") == (None, m) +} + +// ## Combining + +/// Combine two dictionaries. If the same key exist in both the left and +/// right dictionary, values from the left are preferred (i.e. left-biaised). +/// +/// ```aiken +/// let left_dict = dict.from_pairs([Pair("a", 100), Pair("b", 200)]) +/// let right_dict = dict.from_pairs([Pair("a", 150), Pair("c", 300)]) +/// +/// let result = +/// dict.union(left_dict, right_dict) |> dict.to_pairs() +/// +/// result == [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn union( + left: Dict, + right: Dict, +) -> Dict { + Dict { inner: do_union(left.inner, right.inner) } +} + +fn do_union( + left: Pairs, + right: Pairs, +) -> Pairs { + when left is { + [] -> right + [Pair(k, v), ..rest] -> do_union(rest, do_insert(right, k, v)) + } +} + +test union_1() { + union(fixture_1, empty) == fixture_1 +} + +test union_2() { + union(empty, fixture_1) == fixture_1 +} + +test union_3() { + let left = + empty + |> insert(foo, 14) + let right = + empty + |> insert(bar, 42) + |> insert(baz, 1337) + union(left, right) == from_pairs( + [Pair(foo, 14), Pair(baz, 1337), Pair(bar, 42)], + ) +} + +test union_4() { + let left = + empty + |> insert(foo, 14) + let right = + empty + |> insert(bar, 42) + |> insert(foo, 1337) + union(left, right) == from_pairs([Pair(foo, 14), Pair(bar, 42)]) +} + +/// Like [`union`](#union) but allows specifying the behavior to adopt when a key is present +/// in both dictionaries. The first value received correspond to the value in the left +/// dictionnary, whereas the second argument corresponds to the value in the right dictionnary. +/// +/// When passing `None`, the value is removed and not present in the union. +/// +/// ```aiken +/// let left_dict = dict.from_pairs([Pair("a", 100), Pair("b", 200)]) +/// let right_dict = dict.from_pairs([Pair("a", 150), Pair("c", 300)]) +/// +/// let result = +/// dict.union_with( +/// left_dict, +/// right_dict, +/// fn(_k, v1, v2) { Some(v1 + v2) }, +/// ) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 250), Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn union_with( + left: Dict, + right: Dict, + with: fn(ByteArray, value, value) -> Option, +) -> Dict { + Dict { inner: do_union_with(left.inner, right.inner, with) } +} + +fn do_union_with( + left: Pairs, + right: Pairs, + with: fn(ByteArray, value, value) -> Option, +) -> Pairs { + when left is { + [] -> right + [Pair(k, v), ..rest] -> + do_union_with(rest, do_insert_with(right, k, v, with), with) + } +} + +fn do_insert_with( + self: Pairs, + key k: ByteArray, + value v: value, + with: fn(ByteArray, value, value) -> Option, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if builtin.less_than_bytearray(k, k2) { + [Pair(k, v), ..self] + } else { + if k == k2 { + when with(k, v, v2) is { + Some(combined) -> [Pair(k, combined), ..rest] + None -> rest + } + } else { + [Pair(k2, v2), ..do_insert_with(rest, k, v, with)] + } + } + } +} + +test union_with_1() { + let left = + empty + |> insert(foo, 14) + + let right = + empty + |> insert(bar, 42) + |> insert(foo, 1337) + + let result = union_with(left, right, with: fn(_, l, r) { Some(l + r) }) + + result == from_pairs([Pair(foo, 1351), Pair(bar, 42)]) +} + +// ## Transforming + +/// Fold over the key-value pairs in a dictionary. The fold direction follows keys +/// in ascending order and is done from left-to-right. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.insert(key: "c", value: 300) +/// |> dict.foldl(0, fn(_k, v, r) { v + r }) +/// +/// result == 600 +/// ``` +pub fn foldl( + self: Dict, + zero: result, + with: fn(ByteArray, value, result) -> result, +) -> result { + do_foldl(self.inner, zero, with) +} + +fn do_foldl( + self: Pairs, + zero: result, + with: fn(ByteArray, value, result) -> result, +) -> result { + when self is { + [] -> zero + [Pair(k, v), ..rest] -> do_foldl(rest, with(k, v, zero), with) + } +} + +test fold_1() { + foldl(empty, 14, fn(_, _, _) { 42 }) == 14 +} + +test fold_2() { + foldl(fixture_1, zero: 0, with: fn(_, v, total) { v + total }) == 56 +} + +/// Fold over the key-value pairs in a dictionary. The fold direction follows keys +/// in ascending order and is done from right-to-left. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.insert(key: "c", value: 300) +/// |> dict.foldr(0, fn(_k, v, r) { v + r }) +/// +/// result == 600 +/// ``` +pub fn foldr( + self: Dict, + zero: result, + with: fn(ByteArray, value, result) -> result, +) -> result { + do_foldr(self.inner, zero, with) +} + +fn do_foldr( + self: Pairs, + zero: result, + with: fn(ByteArray, value, result) -> result, +) -> result { + when self is { + [] -> zero + [Pair(k, v), ..rest] -> with(k, v, do_foldr(rest, zero, with)) + } +} + +test foldr_1() { + foldr(empty, 14, fn(_, _, _) { 42 }) == 14 +} + +test foldr_2() { + foldr(fixture_1, zero: 0, with: fn(_, v, total) { v + total }) == 56 +} + +/// Get the inner list holding the dictionary data. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 100) +/// |> dict.insert("b", 200) +/// |> dict.insert("c", 300) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn to_pairs(self: Dict) -> Pairs { + self.inner +} + +test to_list_1() { + to_pairs(empty) == [] +} + +test to_list_2() { + to_pairs(fixture_1) == [Pair(bar, 14), Pair(foo, 42)] +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection/list.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection/list.ak new file mode 100644 index 00000000..b8e7f675 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection/list.ak @@ -0,0 +1,1411 @@ +use aiken/builtin +use aiken/primitive/bytearray +use aiken/primitive/int + +// ## Constructing + +/// Add an element in front of the list. Sometimes useful when combined with +/// other functions. +/// +/// ```aiken +/// list.push([2, 3], 1) == [1, ..[2, 3]] == [1, 2, 3] +/// ``` +pub fn push(self: List, elem: a) -> List { + [elem, ..self] +} + +test push_1() { + push([], 0) == [0] +} + +test push_2() { + push([2, 3], 1) == [1, 2, 3] +} + +/// Construct a list of a integer from a given range. +/// +/// ```aiken +/// list.range(0, 3) == [0, 1, 2, 3] +/// list.range(-1, 1) == [-1, 0, 1] +/// ``` +pub fn range(from: Int, to: Int) -> List { + if from > to { + [] + } else { + [from, ..range(from + 1, to)] + } +} + +test range_1() { + range(0, 3) == [0, 1, 2, 3] +} + +test range_2() { + range(-1, 1) == [-1, 0, 1] +} + +/// Construct a list filled with n copies of a value. +/// +/// ```aiken +/// list.repeat("na", 3) == ["na", "na", "na"] +/// ``` +pub fn repeat(elem: a, n_times: Int) -> List { + if n_times <= 0 { + [] + } else { + [elem, ..repeat(elem, n_times - 1)] + } +} + +test repeat_1() { + repeat(42, 0) == [] +} + +test repeat_2() { + repeat(14, 3) == [14, 14, 14] +} + +// ## Inspecting + +/// Determine if all elements of the list satisfy the given predicate. +/// +/// Note: an empty list always satisfies the predicate. +/// +/// ```aiken +/// list.all([], fn(n) { n > 0 }) == True +/// list.all([1, 2, 3], fn(n) { n > 0 }) == True +/// list.all([1, 2, 3], fn(n) { n == 2 }) == False +/// ``` +pub fn all(self: List, predicate: fn(a) -> Bool) -> Bool { + when self is { + [] -> True + [x, ..xs] -> predicate(x) && all(xs, predicate) + } +} + +test all_1() { + all([1, 2, 3], fn(n) { n > 0 }) == True +} + +test all_2() { + all([1, 2, 3], fn(n) { n > 42 }) == False +} + +test all_3() { + all([], fn(n) { n == 42 }) == True +} + +/// Determine if at least one element of the list satisfies the given predicate. +/// +/// Note: an empty list never satisfies the predicate. +/// +/// ```aiken +/// list.any([], fn(n) { n > 2 }) == False +/// list.any([1, 2, 3], fn(n) { n > 0 }) == True +/// list.any([1, 2, 3], fn(n) { n == 2 }) == True +/// list.any([1, 2, 3], fn(n) { n < 0 }) == False +/// ``` +pub fn any(self: List, predicate: fn(a) -> Bool) -> Bool { + when self is { + [] -> False + [x, ..xs] -> predicate(x) || any(xs, predicate) + } +} + +test any_1() { + any([1, 2, 3], fn(n) { n > 0 }) == True +} + +test any_2() { + any([1, 2, 3], fn(n) { n > 42 }) == False +} + +test any_3() { + any([], fn(n) { n == 42 }) == False +} + +/// Return Some(item) at the index or None if the index is out of range. The index is 0-based. +/// +/// ```aiken +/// list.at([1, 2, 3], 1) == Some(2) +/// list.at([1, 2, 3], 42) == None +/// ``` +pub fn at(self: List, index: Int) -> Option { + when self is { + [] -> None + [x, ..xs] -> + if index == 0 { + Some(x) + } else { + at(xs, index - 1) + } + } +} + +test at_1() { + at([1, 2, 3], -1) == None +} + +test at_2() { + at([], 0) == None +} + +test at_3() { + at([1, 2, 3], 3) == None +} + +test at_4() { + at([1], 0) == Some(1) +} + +test at_5() { + at([1, 2, 3], 2) == Some(3) +} + +/// Count how many items in the list satisfy the given predicate. +/// +/// ```aiken +/// list.count([], fn(a) { a > 2}) == 0 +/// list.count([1, 2, 3], fn(a) { n > 0 }) == 3 +/// list.count([1, 2, 3], fn(a) { n >= 2 }) == 2 +/// list.count([1, 2, 3], fn(a) { n > 5 }) == 0 +/// ``` +pub fn count(self: List, predicate: fn(a) -> Bool) -> Int { + foldr( + self, + 0, + fn(item, total) { + if predicate(item) { + total + 1 + } else { + total + } + }, + ) +} + +test count_empty() { + count([], fn(a) { a > 2 }) == 0 +} + +test count_all() { + count([1, 2, 3], fn(a) { a > 0 }) == 3 +} + +test count_some() { + count([1, 2, 3], fn(a) { a >= 2 }) == 2 +} + +test count_none() { + count([1, 2, 3], fn(a) { a > 5 }) == 0 +} + +/// Find the first element satisfying the given predicate, if any. +/// +/// ```aiken +/// list.find([1, 2, 3], fn(x) { x == 2 }) == Some(2) +/// list.find([4, 5, 6], fn(x) { x == 2 }) == None +/// ``` +pub fn find(self: List, predicate: fn(a) -> Bool) -> Option { + when self is { + [] -> None + [x, ..xs] -> + if predicate(x) { + Some(x) + } else { + find(xs, predicate) + } + } +} + +test find_1() { + find([1, 2, 3], fn(x) { x == 1 }) == Some(1) +} + +test find_2() { + find([1, 2, 3], fn(x) { x > 42 }) == None +} + +test find_3() { + find([], fn(_) { True }) == None +} + +/// Figures out whether a list contain the given element. +/// +/// ```aiken +/// list.has([1, 2, 3], 2) == True +/// list.has([1, 2, 3], 14) == False +/// list.has([], 14) == False +/// ``` +pub fn has(self: List, elem: a) -> Bool { + when self is { + [] -> False + [x, ..xs] -> + if x == elem { + True + } else { + has(xs, elem) + } + } +} + +test has_1() { + has([1, 2, 3], 1) == True +} + +test has_2() { + has([1, 2, 3], 14) == False +} + +test has_3() { + has([], 14) == False +} + +/// Get the first element of a list +/// +/// ```aiken +/// list.head([1, 2, 3]) == Some(1) +/// list.head([]) == None +/// ``` +pub fn head(self: List) -> Option { + when self is { + [] -> None + _ -> Some(builtin.head_list(self)) + } +} + +test head_1() { + head([1, 2, 3]) == Some(1) +} + +test head_2() { + head([]) == None +} + +/// Checks whether a list is empty. +/// +/// ```aiken +/// list.is_empty([]) == True +/// list.is_empty([1, 2, 3]) == False +/// ``` +pub fn is_empty(self: List) -> Bool { + when self is { + [] -> True + _ -> False + } +} + +test is_empty_1() { + is_empty([]) == True +} + +test is_empty_2() { + is_empty([1, 2, 3]) == False +} + +/// Gets the index of an element of a list, if any. Otherwise, returns None. +/// +/// ```aiken +/// list.index_of([1, 5, 2], 2) == Some(2) +/// list.index_of([1, 7, 3], 4) == None +/// list.index_of([1, 0, 9, 6], 6) == 3 +/// list.index_of([], 6) == None +/// ``` +pub fn index_of(self: List, elem: a) -> Option { + do_index_of(self, elem, 0) +} + +fn do_index_of(self: List, elem: a, i: Int) -> Option { + when self is { + [] -> None + [x, ..xs] -> + if x == elem { + Some(i) + } else { + do_index_of(xs, elem, i + 1) + } + } +} + +test index_of_1() { + index_of([1, 5, 2], 2) == Some(2) +} + +test index_of_2() { + index_of([1, 7, 3], 4) == None +} + +test index_of_3() { + index_of([1, 0, 9, 6], 6) == Some(3) +} + +test index_of_4() { + index_of([], 6) == None +} + +/// Get the last in the given list, if any. +/// +/// ```aiken +/// list.last([]) == None +/// list.last([1, 2, 3]) == Some(3) +/// ``` +pub fn last(self: List) -> Option { + when self is { + [] -> None + [x] -> Some(x) + [_, ..xs] -> last(xs) + } +} + +test last_1() { + last([]) == None +} + +test last_2() { + last([1]) == Some(1) +} + +test last_3() { + last([1, 2, 3, 4]) == Some(4) +} + +/// Get the number of elements in the given list. +/// +/// ```aiken +/// list.length([]) == 0 +/// list.length([1, 2, 3]) == 3 +/// ``` +pub fn length(self: List) -> Int { + when self is { + [] -> 0 + [_, ..xs] -> 1 + length(xs) + } +} + +test length_1() { + length([]) == 0 +} + +test length_2() { + length([1, 2, 3]) == 3 +} + +// ## Modifying + +// ### Extracting + +/// Remove the first occurrence of the given element from the list. +/// +/// ```aiken +/// list.delete([1, 2, 3, 1], 1) == [2, 3, 1] +/// list.delete([1, 2, 3], 14) == [1, 2, 3] +/// ``` +pub fn delete(self: List, elem: a) -> List { + when self is { + [] -> [] + [x, ..xs] -> + if x == elem { + xs + } else { + [x, ..delete(xs, elem)] + } + } +} + +test delete_1() { + delete([], 42) == [] +} + +test delete_2() { + delete([1, 2, 3, 1], 1) == [2, 3, 1] +} + +test delete_3() { + delete([1, 2, 3], 14) == [1, 2, 3] +} + +test delete_4() { + delete([2], 2) == [] +} + +/// Drop the first `n` elements of a list. +/// +/// ```aiken +/// list.drop([1, 2, 3], 2) == [3] +/// list.drop([], 42) == [] +/// list.drop([1, 2, 3], 42) == [] +/// ``` +pub fn drop(self: List, n: Int) -> List { + if n <= 0 { + self + } else { + when self is { + [] -> [] + [_x, ..xs] -> drop(xs, n - 1) + } + } +} + +test drop_1() { + drop([], 42) == [] +} + +test drop_2() { + drop([1, 2, 3], 2) == [3] +} + +/// Returns the suffix of the given list after removing all elements that satisfy the predicate. +/// +/// ```aiken +/// list.drop_while([1, 2, 3], fn(x) { x < 2 }) == [2, 3] +/// list.drop_while([], fn(x) { x > 2 }) == [] +/// list.drop_while([1, 2, 3], fn(x) { x == 3 }) == [1, 2, 3] +/// ``` +pub fn drop_while(self: List, predicate: fn(a) -> Bool) -> List { + when self is { + [] -> [] + [x, ..xs] -> + if predicate(x) { + drop_while(xs, predicate) + } else { + self + } + } +} + +test drop_while_1() { + drop_while([], fn(x) { x > 2 }) == [] +} + +test drop_while_2() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + drop_while(xs, fn(x) { x > 5 }) == [5, 4, 3, 2, 1] +} + +test drop_while_3() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + drop_while(xs, fn(x) { x == 42 }) == xs +} + +test drop_while_4() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + drop_while(xs, fn(x) { x < 42 }) == [] +} + +/// Produce a list of elements that satisfy a predicate. +/// +/// ```aiken +/// list.filter([1, 2, 3], fn(x) { x >= 2 }) == [2, 3] +/// list.filter([], fn(x) { x > 2 }) == [] +/// list.filter([1, 2, 3], fn(x) { x == 3 }) == [3] +/// ``` +pub fn filter(self: List, predicate: fn(a) -> Bool) -> List { + when self is { + [] -> [] + [x, ..xs] -> + if predicate(x) { + [x, ..filter(xs, predicate)] + } else { + filter(xs, predicate) + } + } +} + +test filter_1() { + filter([], fn(x) { x > 0 }) == [] +} + +test filter_2() { + let xs = [1, 2, 3, 4, 5, 6] + filter(xs, fn(x) { builtin.mod_integer(x, 2) == 0 }) == [2, 4, 6] +} + +test filter_3() { + let filter_foldr = + fn(xs, f) { + foldr( + xs, + [], + fn(x, ys) { + if f(x) { + [x, ..ys] + } else { + ys + } + }, + ) + } + + let is_odd = + fn(n) { builtin.mod_integer(n, 2) != 0 } + + filter_foldr([1, 2, 3], is_odd) == filter([1, 2, 3], is_odd) +} + +/// Produce a list of transformed elements that satisfy a predicate. +/// +/// ```aiken +/// let transform = fn(x) { if x % 2 == 0 { None } else { Some(3*x) } } +/// list.filter_map([1, 2, 3], transform) == [3, 9] +/// ``` +pub fn filter_map(self: List, predicate: fn(a) -> Option) -> List { + when self is { + [] -> [] + [x, ..xs] -> + when predicate(x) is { + None -> filter_map(xs, predicate) + Some(y) -> [y, ..filter_map(xs, predicate)] + } + } +} + +test filter_map_1() { + filter_map([], fn(_) { Some(42) }) == [] +} + +test filter_map_2() { + filter_map( + [1, 2, 3, 4, 5, 6], + fn(x) { + if builtin.mod_integer(x, 2) != 0 { + Some(3 * x) + } else { + None + } + }, + ) == [3, 9, 15] +} + +/// Return all elements except the last one. +/// +/// ```aiken +/// list.init([]) == None +/// list.init([1, 2, 3]) == Some([1, 2]) +/// ``` +pub fn init(self: List) -> Option> { + when self is { + [] -> None + _ -> Some(do_init(self)) + } +} + +fn do_init(self: List) -> List { + when self is { + [] -> fail @"unreachable" + [_] -> [] + [x, ..xs] -> [x, ..do_init(xs)] + } +} + +test init_1() { + init([]) == None +} + +test init_2() { + init([1]) == Some([]) +} + +test init_3() { + init([1, 2, 3, 4]) == Some([1, 2, 3]) +} + +/// Returns a tuple with all elements that satisfy the predicate at first +/// element, and the rest as second element. +/// +/// ```aiken +/// list.partition([1, 2, 3, 4], fn(x) { x % 2 == 0 }) == ([2, 4], [1, 3]) +/// ``` +pub fn partition(self: List, predicate: fn(a) -> Bool) -> (List, List) { + when self is { + [] -> ([], []) + [x, ..xs] -> { + let (left, right) = partition(xs, predicate) + if predicate(x) { + ([x, ..left], right) + } else { + (left, [x, ..right]) + } + } + } +} + +test partition_1() { + partition([], fn(x) { x > 2 }) == ([], []) +} + +test partition_2() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + partition(xs, fn(x) { x > 5 }) == ([10, 9, 8, 7, 6], [5, 4, 3, 2, 1]) +} + +test partition_3() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + partition(xs, fn(x) { x == 42 }) == ([], xs) +} + +test partition_4() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + partition(xs, fn(x) { x < 42 }) == (xs, []) +} + +test partition_5() { + partition([1, 2, 3, 4], fn(x) { x % 2 == 0 }) == ([2, 4], [1, 3]) +} + +/// Extract a sublist from the given list using 0-based indexes. Negative +/// indexes wrap over, so `-1` refers to the last element of the list. +/// +/// ```aiken +/// list.slice([1, 2, 3, 4, 5, 6], from: 2, to: 4) == [3, 4, 5] +/// list.slice([1, 2, 3, 4, 5, 6], from: -2, to: -1) == [5, 6] +/// list.slice([1, 2, 3, 4, 5, 6], from: 1, to: -1) == [2, 3, 4, 5, 6] +/// ``` +pub fn slice(self: List, from: Int, to: Int) -> List { + let (i, l) = + if from >= 0 { + (from, None) + } else { + let l = length(self) + (l + from, Some(l)) + } + + let j = + if to >= 0 { + to - i + 1 + } else { + when l is { + Some(l) -> l + to - i + 1 + None -> length(self) + to - i + 1 + } + } + + self + |> drop(i) + |> take(j) +} + +test slice_1() { + slice([1, 2, 3], 0, 2) == [1, 2, 3] +} + +test slice_2() { + slice([1, 2, 3, 4, 5, 6], from: 2, to: 4) == [3, 4, 5] +} + +test slice_3() { + slice([1, 2, 3, 4, 5, 6], from: -2, to: -1) == [5, 6] +} + +test slice_4() { + slice([1, 2, 3, 4, 5, 6], from: 1, to: -1) == [2, 3, 4, 5, 6] +} + +test slice_5() { + slice([1, 2, 3, 4, 5, 6], from: -4, to: -3) == [3, 4] +} + +test slice_6() { + slice([1, 2, 3, 4, 5, 6], from: -2, to: 1) == [] +} + +/// Cut a list in two, such that the first list contains the given number of / +/// elements and the second list contains the rest. +/// +/// Fundamentally equivalent to (but more efficient): +/// +/// ```aiken +/// // span(xs, n) == (take(xs, n), drop(xs, n)) +/// span([1, 2, 3, 4, 5], 3) == ([1, 2, 3], [4, 5]) +/// ``` +pub fn span(self: List, n: Int) -> (List, List) { + when self is { + [] -> ([], []) + [x, ..xs] -> + if n <= 0 { + ([], self) + } else { + let (left, right) = span(xs, n - 1) + ([x, ..left], right) + } + } +} + +test span_1() { + span([], 2) == ([], []) +} + +test span_2() { + span([1, 2, 3], 2) == ([1, 2], [3]) +} + +test span_3() { + span([1, 2, 3], -1) == ([], [1, 2, 3]) +} + +test span_4() { + span([1, 2, 3], 42) == ([1, 2, 3], []) +} + +/// Get elements of a list after the first one, if any. +/// +/// ```aiken +/// list.tail([]) == None +/// list.tail([1, 2, 3]) == Some([2, 3]) +/// ``` +pub fn tail(self: List) -> Option> { + when self is { + [] -> None + [_, ..xs] -> Some(xs) + } +} + +test tail_1() { + tail([1, 2, 3]) == Some([2, 3]) +} + +test tail_2() { + tail([]) == None +} + +/// Get the first `n` elements of a list. +/// +/// ```aiken +/// list.take([1, 2, 3], 2) == [1, 2] +/// list.take([1, 2, 3], 14) == [1, 2, 3] +/// ``` +pub fn take(self: List, n: Int) -> List { + if n <= 0 { + [] + } else { + when self is { + [] -> [] + [x, ..xs] -> [x, ..take(xs, n - 1)] + } + } +} + +test take_1() { + take([], 42) == [] +} + +test take_2() { + take([1, 2, 3], 2) == [1, 2] +} + +/// Returns the longest prefix of the given list where all elements satisfy the predicate. +/// +/// ```aiken +/// list.take_while([1, 2, 3], fn(x) { x > 2 }) == [] +/// list.take_while([1, 2, 3], fn(x) { x < 2 }) == [1] +/// ``` +pub fn take_while(self: List, predicate: fn(a) -> Bool) -> List { + when self is { + [] -> [] + [x, ..xs] -> + if predicate(x) { + [x, ..take_while(xs, predicate)] + } else { + [] + } + } +} + +test take_while_1() { + take_while([], fn(x) { x > 2 }) == [] +} + +test take_while_2() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + take_while(xs, fn(x) { x > 5 }) == [10, 9, 8, 7, 6] +} + +test take_while_3() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + take_while(xs, fn(x) { x == 42 }) == [] +} + +test take_while_4() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + take_while(xs, fn(x) { x < 42 }) == xs +} + +/// Removes duplicate elements from a list. +/// +/// ```aiken +/// list.unique([1, 2, 3, 1]) == [1, 2, 3] +/// ``` +pub fn unique(self: List) -> List { + when self is { + [] -> [] + [x, ..xs] -> [x, ..unique(filter(xs, fn(y) { y != x }))] + } +} + +test unique_1() { + unique([]) == [] +} + +test unique_2() { + let xs = [1, 2, 3, 1, 1, 3, 4, 1, 2, 3, 2, 4, 5, 6, 7, 8, 9, 10, 9] + unique(xs) == [1, 2, 3, 4, 5, 6, 7, 8, 9, 10] +} + +// ### Mapping + +/// Map elements of a list into a new list and flatten the result. +/// +/// ```aiken +/// list.flat_map([1, 2, 3], fn(a) { [a, 2*a] }) == [1, 2, 2, 4, 3, 6] +/// ``` +pub fn flat_map(self: List, with: fn(a) -> List) -> List { + foldr(self, [], fn(x, xs) { concat(with(x), xs) }) +} + +test flat_map_1() { + flat_map([], fn(a) { [a] }) == [] +} + +test flat_map_2() { + flat_map([1, 2, 3], fn(a) { [a, a] }) == [1, 1, 2, 2, 3, 3] +} + +/// Perform an action for each element of a list. +/// +/// ```aiken +/// list.for_each(labels, do: fn(lbl) { trace lbl Void }) +/// ``` +pub fn for_each(self: List, do: fn(a) -> Void) -> Void { + foldr(self, Void, fn(x, _) { do(x) }) +} + +test for_each_1() { + for_each( + [@"hello", @"world"], + do: fn(lbl) { + trace lbl + Void + }, + ) +} + +/// List [`map`](#map) but provides the position (0-based) of the elements while iterating. +/// +/// ```aiken +/// list.indexed_map([1, 2, 3], fn(i, x) { i + x }) == [1, 3, 5] +/// ``` +pub fn indexed_map(self: List, with: fn(Int, a) -> result) -> List { + do_indexed_map(0, self, with) +} + +fn do_indexed_map( + n: Int, + self: List, + with: fn(Int, a) -> result, +) -> List { + when self is { + [] -> [] + [x, ..xs] -> [with(n, x), ..do_indexed_map(n + 1, xs, with)] + } +} + +test indexed_map_1() { + indexed_map([], fn(i, _n) { i }) == [] +} + +test indexed_map_2() { + indexed_map( + [4, 8, 13, 2], + fn(i, n) { + if n == 8 { + n + } else { + i + } + }, + ) == [0, 8, 2, 3] +} + +/// Apply a function to each element of a list. +/// +/// ```aiken +/// list.map([1, 2, 3, 4], fn(n) { n + 1 }) == [2, 3, 4, 5] +/// ``` +pub fn map(self: List, with: fn(a) -> result) -> List { + when self is { + [] -> [] + [x, ..xs] -> [with(x), ..map(xs, with)] + } +} + +test map_1() { + map([], fn(n) { n + 1 }) == [] +} + +test map_2() { + map([1, 2, 3, 4], fn(n) { n + 1 }) == [2, 3, 4, 5] +} + +/// Apply a function of two arguments, combining elements from two lists. +/// +/// Note: if one list is longer, the extra elements are dropped. +/// +/// ```aiken +/// list.map2([1, 2, 3], [1, 2], fn(a, b) { a + b }) == [2, 4] +/// ``` +pub fn map2( + self: List, + bs: List, + with: fn(a, b) -> result, +) -> List { + when self is { + [] -> [] + [x, ..xs] -> + when bs is { + [] -> [] + [y, ..ys] -> [with(x, y), ..map2(xs, ys, with)] + } + } +} + +test map2_1() { + map2([], [1, 2, 3], fn(a, b) { a + b }) == [] +} + +test map2_2() { + map2([1, 2, 3], [1, 2], fn(a, b) { a + b }) == [2, 4] +} + +test map2_3() { + map2([42], [1, 2, 3], fn(_a, b) { Some(b) }) == [Some(1)] +} + +/// Apply a function of three arguments, combining elements from three lists. +/// +/// Note: if one list is longer, the extra elements are dropped. +/// +/// ```aiken +/// list.map3([1, 2, 3], [1, 2], [1, 2, 3], fn(a, b, c) { a + b + c }) == [3, 6] +/// ``` +pub fn map3( + self: List, + bs: List, + cs: List, + with: fn(a, b, c) -> result, +) -> List { + when self is { + [] -> [] + [x, ..xs] -> + when bs is { + [] -> [] + [y, ..ys] -> + when cs is { + [] -> [] + [z, ..zs] -> [with(x, y, z), ..map3(xs, ys, zs, with)] + } + } + } +} + +test map3_1() { + map3([], [], [1, 2, 3], fn(a, b, c) { a + b + c }) == [] +} + +test map3_2() { + map3([1, 2, 3], [1, 2], [1, 2, 3], fn(a, b, c) { a + b + c }) == [3, 6] +} + +/// Return the list with its elements in the reserve order. +/// +/// ```aiken +/// list.reverse([1, 2, 3]) == [3, 2, 1] +/// ``` +pub fn reverse(self: List) -> List { + foldl(self, [], fn(x, xs) { [x, ..xs] }) +} + +test reverse_1() { + reverse([]) == [] +} + +test reverse_2() { + reverse([1, 2, 3]) == [3, 2, 1] +} + +/// Sort a list in ascending order using the given comparison function. +/// +/// ```aiken +/// use aiken/int +/// +/// sort([3, 1, 4, 0, 2], int.compare) == [0, 1, 2, 3, 4] +/// sort([1, 2, 3], int.compare) == [1, 2, 3] +/// ``` +pub fn sort(self: List, compare: fn(a, a) -> Ordering) -> List { + when self is { + [] -> [] + [x, ..xs] -> insert(sort(xs, compare), x, compare) + } +} + +fn insert(self: List, e: a, compare: fn(a, a) -> Ordering) -> List { + when self is { + [] -> [e] + [x, ..xs] -> + if compare(e, x) == Less { + [e, ..self] + } else { + [x, ..insert(xs, e, compare)] + } + } +} + +test sort_1() { + let xs = [6, 7, 5, 4, 1, 3, 9, 8, 0, 2] + sort(xs, int.compare) == [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] +} + +test sort_2() { + let xs = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] + sort(xs, int.compare) == [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] +} + +test sort_3() { + let xs = [9, 8, 7, 6, 5, 4, 3, 2, 1, 0] + sort(xs, int.compare) == [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] +} + +test sort_4() { + sort([], int.compare) == [] +} + +/// Decompose a list of tuples into a tuple of lists. +/// +/// ``` +/// list.unzip([(1, "a"), (2, "b")]) == ([1, 2], ["a", "b"]) +/// ``` +pub fn unzip(self: List<(a, b)>) -> (List, List) { + when self is { + [] -> ([], []) + [(a, b), ..xs] -> { + let (a_tail, b_tail) = unzip(xs) + ([a, ..a_tail], [b, ..b_tail]) + } + } +} + +test unzip_1() { + unzip([]) == ([], []) +} + +test unzip_2() { + unzip([(1, "a"), (2, "b")]) == ([1, 2], ["a", "b"]) +} + +// ## Combining + +/// Merge two lists together. +/// +/// ```aiken +/// list.concat([], []) == [] +/// list.concat([], [1, 2, 3]) == [1, 2, 3] +/// list.concat([1, 2, 3], [4, 5, 6]) == [1, 2, 3, 4, 5, 6] +/// ``` +pub fn concat(left: List, right: List) -> List { + when left is { + [] -> right + [x, ..xs] -> [x, ..concat(xs, right)] + } +} + +test concat_1() { + concat([1, 2, 3], [4, 5, 6]) == [1, 2, 3, 4, 5, 6] +} + +test concat_2() { + concat([1, 2, 3], []) == [1, 2, 3] +} + +test concat_3() { + concat([], [1, 2, 3]) == [1, 2, 3] +} + +/// Remove the first occurrence of each element of the second list from the first one. +/// +/// ``` +/// list.difference(["h", "e", "l", "l", "o"], ["l", "e", "l"]) == ["h", "o"] +/// list.difference([1, 2, 3, 4, 5], [1, 1, 2]) == [3, 4, 5] +/// list.difference([1, 2, 3], []) == [1, 2, 3] +/// ``` +pub fn difference(self: List, with: List) -> List { + when with is { + [] -> self + [x, ..xs] -> difference(delete(self, x), xs) + } +} + +test difference_1() { + difference(["h", "e", "l", "l", "o"], ["l", "e", "l"]) == ["h", "o"] +} + +test difference_2() { + difference([1, 2, 3, 4, 5], [1, 1, 2]) == [3, 4, 5] +} + +test difference_3() { + difference([1, 2, 3], []) == [1, 2, 3] +} + +test difference_4() { + difference([], [1, 2, 3]) == [] +} + +/// Combine two lists together. +/// +/// Note: if one list is longer, the extra elements are dropped. +/// +/// ```aiken +/// list.zip([1, 2], ["a", "b", "c"]) == [(1, "a"), (2, "b")] +/// ``` +pub fn zip(self: List, bs: List) -> List<(a, b)> { + when self is { + [] -> [] + [x, ..xs] -> + when bs is { + [] -> [] + [y, ..ys] -> [(x, y), ..zip(xs, ys)] + } + } +} + +test zip_1() { + zip([], [1, 2, 3]) == [] +} + +test zip_2() { + zip([1, 2, 3], []) == [] +} + +test zip_3() { + zip([1, 2], ["a", "b", "c"]) == [(1, "a"), (2, "b")] +} + +// ## Transforming + +/// Reduce a list from left to right. +/// +/// ```aiken +/// list.foldl([1, 2, 3], 0, fn(n, total) { n + total }) == 6 +/// list.foldl([1, 2, 3], [], fn(x, xs) { [x, ..xs] }) == [3, 2, 1] +/// ``` +pub fn foldl(self: List, zero: b, with: fn(a, b) -> b) -> b { + when self is { + [] -> zero + [x, ..xs] -> foldl(xs, with(x, zero), with) + } +} + +type Fold2 = + fn(a, b) -> result + +pub fn foldl2( + self: List, + zero_a: a, + zero_b: b, + with: fn(elem, a, b, Fold2) -> result, + return: Fold2, +) -> result { + do_foldl2(self, with, return)(zero_a, zero_b) +} + +fn do_foldl2( + self: List, + with: fn(elem, a, b, Fold2) -> result, + return: Fold2, +) -> Fold2 { + when self is { + [] -> return + [x, ..xs] -> do_foldl2(xs, with, fn(a, b) { with(x, a, b, return) }) + } +} + +test foldl2_optimized() { + let + len, + sum, + <- + foldl2( + [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], + 0, + 0, + fn(n, len, sum, return) { return(len + 1, sum + n) }, + ) + + and { + len == 10, + sum == 55, + } +} + +test foldl2_classic() { + let (len, sum) = + foldl( + [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], + (0, 0), + fn(n, (len, sum)) { (len + 1, sum + n) }, + ) + + and { + len == 10, + sum == 55, + } +} + +type Foo { + Foo(Int, Int) +} + +test foldl2_pair() { + let Pair(len, sum) = + foldl( + [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], + Pair(0, 0), + fn(n, Pair(len, sum)) { Pair(len + 1, sum + n) }, + ) + + and { + len == 10, + sum == 55, + } +} + +test foldl2_foo() { + let Foo(len, sum) = + foldl( + [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], + Foo(0, 0), + fn(n, Foo(len, sum)) { Foo(len + 1, sum + n) }, + ) + + and { + len == 10, + sum == 55, + } +} + +test foldl_1() { + foldl([], 0, fn(_, _) { 1 }) == 0 +} + +test foldl_2() { + foldl([1, 2, 3, 4, 5], 0, fn(n, total) { n + total }) == 15 +} + +test foldl_3() { + foldl([1, 2, 3, 4], [], fn(x, xs) { [x, ..xs] }) == [4, 3, 2, 1] +} + +/// Reduce a list from right to left. +/// +/// ```aiken +/// list.foldr([1, 2, 3], 0, fn(n, total) { n + total }) == 6 +/// list.foldr([1, 2, 3], [], fn(x, xs) { [x, ..xs] }) == [1, 2, 3] +/// ``` +pub fn foldr(self: List, zero: b, with: fn(a, b) -> b) -> b { + when self is { + [] -> zero + [x, ..xs] -> with(x, foldr(xs, zero, with)) + } +} + +test foldr_1() { + foldr([1, 2, 3, 4, 5], 0, fn(n, total) { n + total }) == 15 +} + +test foldr_2() { + foldr( + [1, 2, 3], + "", + fn(n, _str) { + if builtin.mod_integer(n, 2) == 0 { + "foo" + } else { + "bar" + } + }, + ) == "bar" +} + +test foldr_3() { + foldr([1, 2, 3, 4], [], fn(x, xs) { [x, ..xs] }) == [1, 2, 3, 4] +} + +/// Like [`foldr`](#foldr), but also provides the position (0-based) of the elements when iterating. +/// +/// ```aiken +/// let group = fn(i, x, xs) { [(i, x), ..xs] } +/// list.indexed_foldr(["a", "b", "c"], [], group) == [ +/// (0, "a"), +/// (1, "b"), +/// (2, "c") +/// ] +/// ``` +pub fn indexed_foldr( + self: List, + zero: result, + with: fn(Int, a, result) -> result, +) -> result { + do_indexed_foldr(0, self, zero, with) +} + +fn do_indexed_foldr( + n: Int, + self: List, + zero: result, + with: fn(Int, a, result) -> result, +) -> result { + when self is { + [] -> zero + [x, ..xs] -> with(n, x, do_indexed_foldr(n + 1, xs, zero, with)) + } +} + +test indexed_foldr_1() { + indexed_foldr([], 0, fn(i, x, xs) { i + x + xs }) == 0 +} + +test indexed_foldr_2() { + let letters = ["a", "b", "c"] + indexed_foldr(letters, [], fn(i, x, xs) { [(i, x), ..xs] }) == [ + (0, "a"), (1, "b"), (2, "c"), + ] +} + +/// Reduce a list from left to right using the accumulator as left operand. +/// Said differently, this is [`foldl`](#foldl) with callback arguments swapped. +/// +/// ```aiken +/// list.reduce([#[1], #[2], #[3]], #[0], bytearray.concat) == #[0, 1, 2, 3] +/// list.reduce([True, False, True], False, fn(b, a) { or { b, a } }) == True +/// ``` +pub fn reduce(self: List, zero: b, with: fn(b, a) -> b) -> b { + foldl(self, zero, flip(with)) +} + +test reduce_1() { + reduce([], 0, fn(n, total) { n + total }) == 0 +} + +test reduce_2() { + reduce([1, 2, 3], 0, fn(n, total) { n + total }) == 6 +} + +test reduce_3() { + reduce([True, False, True], False, fn(left, right) { left || right }) == True +} + +test reduce_4() { + reduce( + [#[1], #[2], #[3]], + #[9], + fn(left, right) { bytearray.concat(left, right) }, + ) == #[9, 1, 2, 3] +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection/pairs.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection/pairs.ak new file mode 100644 index 00000000..01bfe763 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/collection/pairs.ak @@ -0,0 +1,833 @@ +//// A module for working with associative lists (a.k.a `Pairs`). +//// +//// While any function that works on `List` also work on `Pairs`, this module provides some extra helpers +//// that are specifically tailored to working with associative lists. Fundamentally, a `Pairs` is +//// a type-alias to `List>`. +//// +//// > [!CAUTION] +//// > +//// > Unlike dictionnaries (a.k.a. [`Dict`](./dict.html#Dict), associative lists make no assumption +//// > about the ordering of elements within the list. As a result, lookup +//// > functions do traverse the entire list when invoked. They are also not _sets_, +//// > and thus allow for duplicate keys. This is reflected in the functions used +//// > to interact with them. + +use aiken/builtin +use aiken/primitive/bytearray + +// ## Inspecting + +/// Get all values in the alist associated with a given key. +/// +/// ```aiken +/// pairs.get_all([], "a") == [] +/// pairs.get_all([Pair("a", 1)], "a") == [1] +/// pairs.get_all([Pair("a", 1), Pair("b", 2)], "a") == [1] +/// pairs.get_all([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [1, 3] +/// ``` +pub fn get_all(self: Pairs, key k: key) -> List { + when self is { + [] -> [] + [Pair(k2, v), ..rest] -> + if k == k2 { + [v, ..get_all(rest, k)] + } else { + get_all(rest, k) + } + } +} + +test get_all_1() { + get_all([], "a") == [] +} + +test get_all_2() { + get_all([Pair("a", 1)], "a") == [1] +} + +test get_all_3() { + get_all([Pair("a", 1), Pair("b", 2)], "a") == [1] +} + +test get_all_4() { + get_all([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [1, 3] +} + +test get_all_5() { + get_all([Pair("a", 1), Pair("b", 2), Pair("c", 3)], "d") == [] +} + +/// Get the value in the alist by its key. +/// If multiple values with the same key exist, only the first one is returned. +/// +/// ```aiken +/// pairs.get_first([], "a") == None +/// pairs.get_first([Pair("a", 1)], "a") == Some(1) +/// pairs.get_first([Pair("a", 1), Pair("b", 2)], "a") == Some(1) +/// pairs.get_first([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == Some(1) +/// ``` +pub fn get_first(self: Pairs, key k: key) -> Option { + when self is { + [] -> None + [Pair(k2, v), ..rest] -> + if k == k2 { + Some(v) + } else { + get_first(rest, k) + } + } +} + +test get_first_1() { + get_first([], "a") == None +} + +test get_first_2() { + get_first([Pair("a", 1)], "a") == Some(1) +} + +test get_first_3() { + get_first([Pair("a", 1), Pair("b", 2)], "a") == Some(1) +} + +test get_first_4() { + get_first([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == Some(1) +} + +test get_first_5() { + get_first([Pair("a", 1), Pair("b", 2), Pair("c", 3)], "d") == None +} + +/// Get the value in the alist by its key. +/// If multiple values with the same key exist, only the last one is returned. +/// +/// ```aiken +/// pairs.get_last([], "a") == None +/// pairs.get_last([Pair("a", 1)], "a") == Some(1) +/// pairs.get_last([Pair("a", 1), Pair("b", 2)], "a") == Some(1) +/// pairs.get_last([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == Some(3) +/// ``` +pub fn get_last(self: Pairs, key k: key) -> Option { + when self is { + [] -> None + [Pair(k2, v), ..rest] -> + if k == k2 { + when get_last(rest, k) is { + None -> Some(v) + some -> some + } + } else { + get_last(rest, k) + } + } +} + +test get_last_1() { + get_last([], "a") == None +} + +test get_last_2() { + get_last([Pair("a", 1)], "a") == Some(1) +} + +test get_last_3() { + get_last([Pair("a", 1), Pair("b", 2)], "a") == Some(1) +} + +test get_last_4() { + get_last([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == Some(3) +} + +test get_last_5() { + get_last([Pair("a", 1), Pair("b", 2), Pair("c", 3)], "d") == None +} + +/// Finds all keys in the alist associated with a given value. +/// +/// ```aiken +/// pairs.find_all([], 1) == [] +/// pairs.find_all([Pair("a", 1)], 1) == ["a"] +/// pairs.find_all([Pair("a", 1), Pair("b", 2)], 1) == ["a"] +/// pairs.find_all([Pair("a", 1), Pair("b", 2), Pair("c", 1)], 1) == ["a", "c"] +/// ``` +pub fn find_all(self: Pairs, v: value) -> List { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if v == v2 { + [k2, ..find_all(rest, v)] + } else { + find_all(rest, v) + } + } +} + +test find_all_1() { + find_all([], "a") == [] +} + +test find_all_2() { + find_all([Pair("a", 14)], 14) == ["a"] +} + +test find_all_3() { + find_all([Pair("a", 14)], 42) == [] +} + +test find_all_4() { + find_all([Pair("a", 14), Pair("b", 42), Pair("c", 14)], 14) == ["a", "c"] +} + +/// Finds the first key in the alist associated with a given value, if any. +/// +/// ```aiken +/// pairs.find_first([], 1) == None +/// pairs.find_first([Pair("a", 1)], 1) == Some("a") +/// pairs.find_first([Pair("a", 1), Pair("b", 2)], 1) == Some("a") +/// pairs.find_first([Pair("a", 1), Pair("b", 2), Pair("c", 1)], 1) == Some("a") +/// ``` +pub fn find_first(self: Pairs, v: value) -> Option { + when self is { + [] -> None + [Pair(k2, v2), ..rest] -> + if v == v2 { + Some(k2) + } else { + find_first(rest, v) + } + } +} + +test find_first_1() { + find_first([], "a") == None +} + +test find_first_2() { + find_first([Pair("a", 14)], 14) == Some("a") +} + +test find_first_3() { + find_first([Pair("a", 14)], 42) == None +} + +test find_first_4() { + find_first([Pair("a", 14), Pair("b", 42), Pair("c", 14)], 14) == Some("a") +} + +/// Finds the last key in the alist associated with a given value, if any. +/// +/// ```aiken +/// pairs.find_last([], 1) == None +/// pairs.find_last([Pair("a", 1)], 1) == Some("a") +/// pairs.find_last([Pair("a", 1), Pair("b", 2)], 1) == Some("a") +/// pairs.find_last([Pair("a", 1), Pair("b", 2), Pair("c", 1)], 1) == Some("c") +/// ``` +pub fn find_last(self: Pairs, v: value) -> Option { + when self is { + [] -> None + [Pair(k2, v2), ..rest] -> + if v == v2 { + when find_last(rest, v) is { + None -> Some(k2) + some -> some + } + } else { + find_last(rest, v) + } + } +} + +test find_last_1() { + find_last([], "a") == None +} + +test find_last_2() { + find_last([Pair("a", 14)], 14) == Some("a") +} + +test find_last_3() { + find_last([Pair("a", 14)], 42) == None +} + +test find_last_4() { + find_last([Pair("a", 14), Pair("b", 42), Pair("c", 14)], 14) == Some("c") +} + +/// Check if a key exists in the pairs. +/// +/// ```aiken +/// pairs.has_key([], "a") == False +/// pairs.has_key([Pair("a", 1)], "a") == True +/// pairs.has_key([Pair("a", 1), Pair("b", 2)], "a") == True +/// pairs.has_key([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == True +/// ``` +pub fn has_key(self: Pairs, k: key) -> Bool { + when self is { + [] -> False + // || is lazy so this is fine + [Pair(k2, _), ..rest] -> k == k2 || has_key(rest, k) + } +} + +test has_key_1() { + !has_key([], "a") +} + +test has_key_2() { + has_key([Pair("a", 14)], "a") +} + +test has_key_3() { + !has_key([Pair("a", 14)], "b") +} + +test has_key_4() { + has_key([Pair("a", 14), Pair("b", 42)], "b") +} + +test has_key_5() { + has_key([Pair("a", 14), Pair("b", 42), Pair("a", 42)], "a") +} + +/// Extract all the keys present in a given `Pairs`. +/// +/// ```aiken +/// pairs.keys([]) == [] +/// pairs.keys([Pair("a", 1)]) == ["a"] +/// pairs.keys([Pair("a", 1), Pair("b", 2)]) == ["a", "b"] +/// pairs.keys([Pair("a", 1), Pair("b", 2), Pair("a", 3)]) == ["a", "b", "a"] +/// ``` +pub fn keys(self: Pairs) -> List { + when self is { + [] -> [] + [Pair(k, _), ..rest] -> [k, ..keys(rest)] + } +} + +test keys_1() { + keys([]) == [] +} + +test keys_2() { + keys([Pair("a", 0)]) == ["a"] +} + +test keys_3() { + keys([Pair("a", 0), Pair("b", 0)]) == ["a", "b"] +} + +/// Extract all the values present in a given `Pairs`. +/// +/// ```aiken +/// pairs.values([]) == [] +/// pairs.values([Pair("a", 1)]) == [1] +/// pairs.values([Pair("a", 1), Pair("b", 2)]) == [1, 2] +/// pairs.values([Pair("a", 1), Pair("b", 2), Pair("a", 3)]) == [1, 2, 3] +/// ``` +pub fn values(self: Pairs) -> List { + when self is { + [] -> [] + [Pair(_, v), ..rest] -> [v, ..values(rest)] + } +} + +test values_1() { + values([]) == [] +} + +test values_2() { + values([Pair("a", 1)]) == [1] +} + +test values_3() { + values([Pair("a", 1), Pair("b", 2)]) == [1, 2] +} + +test values_4() { + values([Pair("a", 1), Pair("b", 2), Pair("a", 3)]) == [1, 2, 3] +} + +// ## Modifying + +/// Remove all key-value pairs matching the key from the Pairs. If the key is not found, no changes are made. +/// +/// ```aiken +/// pairs.delete_all([], "a") == [] +/// pairs.delete_all([Pair("a", 1)], "a") == [] +/// pairs.delete_all([Pair("a", 1), Pair("b", 2)], "a") == [Pair("b", 2)] +/// pairs.delete_all([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [Pair("b", 2)] +/// ``` +pub fn delete_all(self: Pairs, key k: key) -> Pairs { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if k == k2 { + delete_all(rest, k) + } else { + [Pair(k2, v2), ..delete_all(rest, k)] + } + } +} + +test delete_all_1() { + delete_all([], "a") == [] +} + +test delete_all_2() { + delete_all([Pair("a", 14)], "a") == [] +} + +test delete_all_3() { + let fixture = [Pair("a", 14)] + delete_all(fixture, "b") == fixture +} + +test delete_all_4() { + let fixture = [Pair("a", 1), Pair("b", 2), Pair("a", 3)] + delete_all(fixture, "a") == [Pair("b", 2)] +} + +/// Remove a single key-value pair from the `Pairs`. If the key is not found, no changes are made. +/// Duplicate keys are not deleted. Only the **first** key found is deleted. +/// +/// ```aiken +/// pairs.delete_first([], "a") == [] +/// pairs.delete_first([Pair("a", 1)], "a") == [] +/// pairs.delete_first([Pair("a", 1), Pair("b", 2)], "a") == [Pair("b", 2)] +/// pairs.delete_first([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [Pair("b", 2), Pair("a", 3)] +/// ``` +pub fn delete_first(self: Pairs, key k: key) -> Pairs { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if k == k2 { + rest + } else { + [Pair(k2, v2), ..delete_first(rest, k)] + } + } +} + +test delete_first_1() { + delete_first([], "a") == [] +} + +test delete_first_2() { + delete_first([Pair("a", 14)], "a") == [] +} + +test delete_first_3() { + let fixture = [Pair("a", 14)] + delete_first(fixture, "b") == fixture +} + +test delete_first_4() { + let fixture = [Pair("a", 1), Pair("b", 2), Pair("a", 3)] + delete_first(fixture, "a") == [Pair("b", 2), Pair("a", 3)] +} + +/// Remove a single key-value pair from the Pairs. If the key is not found, no changes are made. +/// Duplicate keys are not deleted. Only the **last** key found is deleted. +/// +/// ```aiken +/// pairs.delete_last([], "a") == [] +/// pairs.delete_last([Pair("a", 1)], "a") == [] +/// pairs.delete_last([Pair("a", 1), Pair("b", 2)], "a") == [Pair("b", 2)] +/// pairs.delete_last([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [Pair("a", 1), Pair("b", 2)] +/// ``` +pub fn delete_last(self: Pairs, key k: key) -> Pairs { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if k == k2 { + let tail = delete_last(rest, k) + if tail == rest { + rest + } else { + [Pair(k2, v2), ..tail] + } + } else { + [Pair(k2, v2), ..delete_last(rest, k)] + } + } +} + +test delete_last_1() { + delete_last([], "a") == [] +} + +test delete_last_2() { + delete_last([Pair("a", 14)], "a") == [] +} + +test delete_last_3() { + let fixture = [Pair("a", 14)] + delete_last(fixture, "b") == fixture +} + +test delete_last_4() { + let fixture = [Pair("a", 1), Pair("b", 2), Pair("a", 3)] + delete_last(fixture, "a") == [Pair("a", 1), Pair("b", 2)] +} + +/// Insert a value in the `Pairs` at a given key. If the key already exists, +/// the value is added in front. +/// +/// > [!CAUTION] +/// > The list is only traversed up to the given key and the traversal +/// > stops as soon as a higher key is encountered. Said differently, the list +/// > is assumed to **be ordered by ascending keys**! If it is not, expect the +/// > unexpected. +/// +/// ```aiken +/// use aiken/primitive/bytearray +/// +/// let result = +/// [] +/// |> pairs.insert_by_ascending_key(key: "foo", value: 1, compare: bytearray.compare) +/// |> pairs.insert_by_ascending_key(key: "bar", value: 2, compare: bytearray.compare) +/// |> pairs.insert_by_ascending_key(key: "foo", value: 3, compare: bytearray.compare) +/// +/// result == [Pair("bar", 2), Pair("foo", 3), Pair("foo", 1)] +/// ``` +pub fn insert_by_ascending_key( + self: Pairs, + key k: key, + value v: value, + compare: fn(key, key) -> Ordering, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if compare(k, k2) == Less { + [Pair(k, v), ..self] + } else { + if k == k2 { + [Pair(k, v), ..self] + } else { + [Pair(k2, v2), ..insert_by_ascending_key(rest, k, v, compare)] + } + } + } +} + +test insert_by_ascending_key_1() { + let m = + [] + |> insert_by_ascending_key("foo", 42, bytearray.compare) + |> insert_by_ascending_key("foo", 14, bytearray.compare) + + m == [Pair("foo", 14), Pair("foo", 42)] +} + +test insert_by_ascending_key_2() { + let m = + [] + |> insert_by_ascending_key("foo", 42, bytearray.compare) + |> insert_by_ascending_key("bar", 14, bytearray.compare) + |> insert_by_ascending_key("baz", 1337, bytearray.compare) + + m == [Pair("bar", 14), Pair("baz", 1337), Pair("foo", 42)] +} + +/// Like [`insert_by_ascending_key`](#insert_by_ascending_key) but specifies +/// how to combine two values on a key conflict. +/// +/// > [!CAUTION] +/// > The list is only traversed up to the given key and the traversal +/// > stops as soon as a higher key is encountered. Said differently, the list +/// > is assumed to **be ordered by ascending keys**! If it is not, expect the +/// > unexpected. +/// +/// ```aiken +/// use aiken/primitive/bytearray +/// +/// let add_integer = fn(x, y) { x + y } +/// +/// let result = +/// [] +/// |> pairs.insert_with_by_ascending_key(key: "foo", value: 1, compare: bytearray.compare, with: add_integer) +/// |> pairs.insert_with_by_ascending_key(key: "bar", value: 2, compare: bytearray.compare, with: add_integer) +/// |> pairs.insert_with_by_ascending_key(key: "foo", value: 3, compare: bytearray.compare, with: add_integer) +/// +/// result == [Pair("bar", 2), Pair("foo", 4)] +/// ``` +pub fn insert_with_by_ascending_key( + self: Pairs, + key k: key, + value v: value, + compare: fn(key, key) -> Ordering, + with: fn(value, value) -> value, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if compare(k, k2) == Less { + [Pair(k, v), ..self] + } else { + if k == k2 { + [Pair(k, with(v, v2)), ..rest] + } else { + [ + Pair(k2, v2), + ..insert_with_by_ascending_key(rest, k, v, compare, with) + ] + } + } + } +} + +test insert_with_by_ascending_key_1() { + let compare_un_b_data = + fn(l, r) { + bytearray.compare(l |> builtin.un_b_data, r |> builtin.un_b_data) + } + + let m = + [] + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 42, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 14, + compare_un_b_data, + builtin.add_integer, + ) + + m == [Pair("foo" |> builtin.b_data, 56)] +} + +test insert_with_by_ascending_key_2() { + let compare_un_b_data = + fn(l, r) { + bytearray.compare(l |> builtin.un_b_data, r |> builtin.un_b_data) + } + + let m = + [] + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 42, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "bar" |> builtin.b_data, + 14, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "baz" |> builtin.b_data, + 1337, + compare_un_b_data, + builtin.add_integer, + ) + + m == [ + Pair("bar" |> builtin.b_data, 14), + Pair("baz" |> builtin.b_data, 1337), + Pair("foo" |> builtin.b_data, 42), + ] +} + +test insert_with_by_ascending_key_3() { + let compare_un_b_data = + fn(l, r) { + bytearray.compare(l |> builtin.un_b_data, r |> builtin.un_b_data) + } + + let result = + [] + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 1, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "bar" |> builtin.b_data, + 2, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 3, + compare_un_b_data, + builtin.add_integer, + ) + + result == [Pair("bar" |> builtin.b_data, 2), Pair("foo" |> builtin.b_data, 4)] +} + +/// Apply a function to all key-value pairs in a alist, replacing the values. +/// +/// ```aiken +/// let fixture = [Pair("a", 100), Pair("b", 200)] +/// +/// pairs.map(fixture, fn(_k, v) { v * 2 }) == [Pair("a", 200), Pair("b", 400)] +/// ``` +pub fn map( + self: Pairs, + with: fn(key, value) -> result, +) -> Pairs { + when self is { + [] -> [] + [Pair(k, v), ..rest] -> [Pair(k, with(k, v)), ..map(rest, with)] + } +} + +test map_1() { + let fixture = [Pair("a", 1), Pair("b", 2)] + + map(fixture, with: fn(k, _) { k }) == [Pair("a", "a"), Pair("b", "b")] +} + +test map_2() { + let fixture = [Pair("a", 1), Pair("b", 2)] + + map(fixture, with: fn(_, v) { v + 1 }) == [Pair("a", 2), Pair("b", 3)] +} + +/// Insert a value in the `Pairs` at a given key. If the key already exists, +/// its value is replaced. +/// +/// > [!CAUTION] +/// > The list is only traversed up to the given key and the traversal +/// > stops as soon as a higher key is encountered. Said differently, the list +/// > is assumed to **be ordered by ascending keys**! If it is not, expect the +/// > unexpected. +/// +/// ```aiken +/// use aiken/primitive/bytearray +/// +/// let result = +/// [] +/// |> pairs.repsert_by_ascending_key(key: "foo", value: 1, compare: bytearray.compare) +/// |> pairs.repsert_by_ascending_key(key: "bar", value: 2, compare: bytearray.compare) +/// |> pairs.repsert_by_ascending_key(key: "foo", value: 3, compare: bytearray.compare) +/// +/// result == [Pair("bar", 2), Pair("foo", 3)] +/// ``` +pub fn repsert_by_ascending_key( + self: Pairs, + key k: key, + value v: value, + compare: fn(key, key) -> Ordering, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if compare(k, k2) == Less { + [Pair(k, v), ..self] + } else { + if k == k2 { + [Pair(k, v), ..rest] + } else { + [Pair(k2, v2), ..repsert_by_ascending_key(rest, k, v, compare)] + } + } + } +} + +test repsert_by_ascending_key_1() { + let m = + [] + |> repsert_by_ascending_key("foo", 42, bytearray.compare) + |> repsert_by_ascending_key("foo", 14, bytearray.compare) + + m == [Pair("foo", 14)] +} + +test repsert_by_ascending_key_2() { + let m = + [] + |> repsert_by_ascending_key("foo", 42, bytearray.compare) + |> repsert_by_ascending_key("bar", 14, bytearray.compare) + |> repsert_by_ascending_key("baz", 1337, bytearray.compare) + + m == [Pair("bar", 14), Pair("baz", 1337), Pair("foo", 42)] +} + +// ## Transforming + +/// Fold over the key-value pairs in a pairs. The fold direction follows keys +/// in ascending order and is done from left-to-right. +/// +/// ```aiken +/// let fixture = [ +/// Pair(1, 100), +/// Pair(2, 200), +/// Pair(3, 300), +/// ] +/// +/// pairs.foldl(fixture, 0, fn(k, v, result) { k * v + result }) == 1400 +/// ``` +pub fn foldl( + self: Pairs, + zero: result, + with: fn(key, value, result) -> result, +) -> result { + when self is { + [] -> zero + [Pair(k, v), ..rest] -> foldl(rest, with(k, v, zero), with) + } +} + +test foldl_1() { + foldl([], 14, fn(_, _, _) { 42 }) == 14 +} + +test foldl_2() { + foldl( + [Pair("a", 42), Pair("b", 14)], + zero: 0, + with: fn(_, v, total) { v + total }, + ) == 56 +} + +/// Fold over the key-value pairs in a Pairs. The fold direction follows the +/// order of elements in the Pairs and is done from right-to-left. +/// +/// ```aiken +/// let fixture = [ +/// Pair(1, 100), +/// Pair(2, 200), +/// Pair(3, 300), +/// ] +/// +/// pairs.foldr(fixture, 0, fn(k, v, result) { k * v + result }) == 1400 +/// ``` +pub fn foldr( + self: Pairs, + zero: result, + with: fn(key, value, result) -> result, +) -> result { + when self is { + [] -> zero + [Pair(k, v), ..rest] -> with(k, v, foldr(rest, zero, with)) + } +} + +test foldr_1() { + foldr([], 14, fn(_, _, _) { 42 }) == 14 +} + +test foldr_2() { + foldr( + [Pair("a", 42), Pair("b", 14)], + zero: 0, + with: fn(_, v, total) { v + total }, + ) == 56 +} + +test foldr_3() { + let fixture = [Pair(1, 100), Pair(2, 200), Pair(3, 300)] + + foldr(fixture, 0, fn(k, v, result) { k * v + result }) == 1400 +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto.ak new file mode 100644 index 00000000..46a7dda5 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto.ak @@ -0,0 +1,147 @@ +use aiken/builtin + +pub type VerificationKey = + ByteArray + +pub type VerificationKeyHash = + Hash + +pub type Script = + ByteArray + +pub type ScriptHash = + Hash + +pub type Signature = + ByteArray + +pub type DataHash = + Hash + +/// A `Hash` is nothing more than a `ByteArray`, but it carries extra +/// information for readability. +/// +/// On-chain, any hash digest value is represented as a plain 'ByteArray'. +/// Though in practice, hashes come from different sources and have +/// different semantics. +/// +/// Hence, while this type-alias doesn't provide any strong type-guarantees, +/// it helps writing functions signatures with more meaningful types than mere +/// 'ByteArray'. +/// +/// Compare for example: +/// +/// ```aiken +/// pub type Credential { +/// VerificationKey(ByteArray) +/// Script(ByteArray) +/// } +/// ``` +/// +/// with +/// +/// ```aiken +/// pub type Credential { +/// VerificationKey(Hash) +/// Script(Hash) +/// } +/// ``` +/// +/// Both are strictly equivalent, but the second reads much better. +pub type Hash = + ByteArray + +// ## Hashing + +/// A blake2b-224 hash algorithm. +/// +/// Typically used for: +/// +/// - [`Credential`](../cardano/address.html#Credential) +/// - [`PolicyId`](../cardano/assets.html#PolicyId) +/// +/// Note: there's no function to calculate blake2b-224 hash digests on-chain. +pub opaque type Blake2b_224 { + Blake2b_224 +} + +/// Compute the blake2b-224 hash digest (28 bytes) of some data. +pub fn blake2b_224(bytes: ByteArray) -> Hash { + builtin.blake2b_224(bytes) +} + +/// A blake2b-256 hash algorithm. +/// +/// Typically used for: +/// +/// - [`TransactionId`](../cardano/transaction.html#TransactionId) +pub opaque type Blake2b_256 { + Blake2b_256 +} + +/// Compute the blake2b-256 hash digest (32 bytes) of some data. +pub fn blake2b_256(bytes: ByteArray) -> Hash { + builtin.blake2b_256(bytes) +} + +/// A Keccak-256 hash algorithm. +pub opaque type Keccak_256 { + Keccak_256 +} + +/// Compute the keccak-256 hash digest (32 bytes) of some data. +pub fn keccak_256(bytes: ByteArray) -> Hash { + builtin.keccak_256(bytes) +} + +/// A SHA2-256 hash algorithm. +pub opaque type Sha2_256 { + Sha2_256 +} + +/// Compute the sha2-256 hash digest (32 bytes) of some data. +pub fn sha2_256(bytes: ByteArray) -> Hash { + builtin.sha2_256(bytes) +} + +/// A SHA3-256 hash algorithm. +pub opaque type Sha3_256 { + Sha3_256 +} + +/// Compute the sha3-256 hash digest (32 bytes) of some data. +pub fn sha3_256(bytes: ByteArray) -> Hash { + builtin.sha3_256(bytes) +} + +// ## Verifying signatures + +/// Verify an ECDCA signature (over secp256k1) using the given verification key. +/// Returns `True` when the signature is valid. +pub fn verify_ecdsa_signature( + key: VerificationKey, + msg: ByteArray, + sig: Signature, +) -> Bool { + builtin.verify_ecdsa_secp256k1_signature(key, msg, sig) +} + +/// Verify an Ed25519 signature using the given verification key. +/// Returns `True` when the signature is valid. +pub fn verify_ed25519_signature( + key: VerificationKey, + msg: ByteArray, + sig: Signature, +) -> Bool { + builtin.verify_ed25519_signature(key, msg, sig) +} + +/// Verify a Schnorr signature (over secp256k1) using the given verification key. +/// Returns `True` when the signature is valid. +pub fn verify_schnorr_signature( + key: VerificationKey, + msg: ByteArray, + sig: Signature, +) -> Bool { + builtin.verify_schnorr_secp256k1_signature(key, msg, sig) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g1.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g1.ak new file mode 100644 index 00000000..d7b4cc19 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g1.ak @@ -0,0 +1,115 @@ +//// This module is designed for cryptographic operations involving the BLS12-381 elliptic curve, particularly focusing on the G1 group of the curve. +//// +//// The key functionalities provided by this module include: +//// - Defining the generator of the G1 group, which is a fixed base point on the elliptic curve used for various cryptographic computations. +//// - Implementing the additive identity (zero) in the G1 group, which plays a crucial role in elliptic curve arithmetic. +//// - Providing functions to compress and decompress points in the G1 group. Compression reduces the size of the point representation, which is useful for efficient storage and transmission. Decompression restores the original point from its compressed form. +//// - Implementing basic arithmetic operations on the points in the G1 group, such as addition and subtraction. +//// - Enabling the exponentiation of a point in the G1 group with a scalar, which is a fundamental operation in elliptic curve cryptography. +//// - Offering a function to hash arbitrary data to a point in the G1 group, a process important in several cryptographic protocols. +//// +//// This module ensures that all operations respect the properties of the BLS12-381 curve and the mathematical structure of the G1 group. + +use aiken/builtin +use aiken/crypto/bls12_381/scalar.{Scalar} + +/// The compressed generator of the G1 group of the BLS12-381 curve. +/// This constant represents a fixed base point on the elliptic curve. +/// Note that flat encoded plutus does not allow for the direct usage of BLS12-381 points. +/// More explicit, any points in plutus data or scripts must be decompressed before usage onchain. +pub const generator: G1Element = + #"97f1d3a73197d7942695638c4fa9ac0fc3688c4f9774b905a14e3a3f171bac586c55e83ff97a1aeffb3af00adb22c6bb" + +test generator_1() { + builtin.bls12_381_g1_scalar_mul(scalar.field_prime, generator) == #"c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" +} + +/// Represents the additive identity (zero) in the G1 group. +/// Note that flat encoded plutus does not allow for the direct usage of BLS12-381 points. +/// More explicit, any points in plutus data or scripts must be decompressed before usage onchain. +pub const zero: G1Element = + #"c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" + +test zero_1() { + and { + zero == builtin.bls12_381_g1_scalar_mul(scalar.field_prime, generator), + zero == builtin.bls12_381_g1_scalar_mul( + scalar.field_prime, + #"88c7e388ee58f1db9a24d7098b01d13634298bebf2d159254975bd450cb0d287fcc622eb71edde8b469a8513551baf1f", + ), + zero == builtin.bls12_381_g1_scalar_mul( + scalar.field_prime, + #"a6ac32e625dc30b8d31bacf5f4c89c27b0388b15f57ae10de8d5cec02dd1f113c9a31077be05ab587ca57a88d34deb75", + ), + } +} + +/// Compresses a point in the G1 group into a more compact representation. +/// The compressed representation is a 48-byte string, corresponding to a modified `x` coordinate. +/// The leading most significant 3 bits of this string indicate how to reconstruct the `y` coordinate. +/// +/// > [!NOTE] +/// > More explicitly via [Zcash's spec](https://github.com/supranational/blst#serialization-format): +/// > +/// > The most-significant three bits of a G1 or G2 encoding should be masked away before the coordinate(s) are interpreted. These bits are used to unambiguously represent the underlying element: +/// > +/// > - The most significant bit, when set, indicates that the point is in compressed form. Otherwise, the point is in uncompressed form. +/// > - The second-most significant bit indicates that the point is at infinity. If this bit is set, the remaining bits of the group element's encoding should be set to zero. +/// > - The third-most significant bit is set if (and only if) this point is in compressed form and it is not the point at infinity and its y-coordinate is the lexicographically largest of the two associated with the encoded x-coordinate. +pub fn compress(point) { + builtin.bls12_381_g1_compress(point) +} + +test compress_1() { + compress( + #"97f1d3a73197d7942695638c4fa9ac0fc3688c4f9774b905a14e3a3f171bac586c55e83ff97a1aeffb3af00adb22c6bb", + ) == #"97f1d3a73197d7942695638c4fa9ac0fc3688c4f9774b905a14e3a3f171bac586c55e83ff97a1aeffb3af00adb22c6bb" +} + +/// Decompresses a point in the G1 group from its compressed form. +pub fn decompress(bytes) { + builtin.bls12_381_g1_uncompress(bytes) +} + +pub fn equal(left, right) { + builtin.bls12_381_g1_equal(left, right) +} + +test equal_1() { + equal(generator, generator) +} + +/// Adds two points in the G1 group. +pub fn add(left, right) { + builtin.bls12_381_g1_add(left, right) +} + +/// Subtracts one point in the G1 group from another. +pub fn sub(left, right) { + builtin.bls12_381_g1_add(left, builtin.bls12_381_g1_neg(right)) +} + +test sub_1() { + generator == sub(add(generator, generator), generator) +} + +/// Exponentiates a point in the G1 group with a `scalar`. +/// This operation is equivalent to the repeated addition of the point with itself `e` times. +pub fn scale(point, e: Scalar) { + builtin.bls12_381_g1_scalar_mul(scalar.to_int(e), point) +} + +test scale_1() { + expect Some(x) = scalar.new(2) + builtin.bls12_381_g1_add(generator, generator) == scale(generator, x) +} + +/// Hashes arbitrary data to a point in the G1 group. +/// You can use the `domain_separation_tag` parameter to cryptographically separate different uses of the hash function between applications. +pub fn hash_to_group(bytes: ByteArray, domain_separation_tag: ByteArray) { + builtin.bls12_381_g1_hash_to_group(bytes, domain_separation_tag) +} + +test hash_to_group_1() { + hash_to_group("hello", "world") == #"89223b03c629cc6bcbbdccbba46b6679bc6a79db82f2d3bd115899a45a5a38c391587b59d3d1e297f977d1c4ee9e3388" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g2.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g2.ak new file mode 100644 index 00000000..7a2013db --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g2.ak @@ -0,0 +1,124 @@ +//// This module is designed for cryptographic operations involving the BLS12-381 elliptic curve, particularly focusing on the G2 group of the curve. +//// +//// The key functionalities provided by this module include: +//// - Defining the generator of the G2 group, which is a fixed base point on the elliptic curve used for various cryptographic computations. +//// - Implementing the additive identity (zero) in the G2 group, which plays a crucial role in elliptic curve arithmetic. +//// - Providing functions to compress and decompress points in the G2 group. Compression reduces the size of the point representation, which is useful for efficient storage and transmission. Decompression restores the original point from its compressed form. +//// - Implementing basic arithmetic operations on the points in the G2 group, such as addition and subtraction. +//// - Enabling the exponentiation of a point in the G2 group with a scalar, which is a fundamental operation in elliptic curve cryptography. +//// - Offering a function to hash arbitrary data to a point in the G2 group, a process important in several cryptographic protocols. +//// +//// This module ensures that all operations respect the properties of the BLS12-381 curve and the mathematical structure of the G2 group. + +use aiken/builtin +use aiken/crypto/bls12_381/scalar.{Scalar} + +/// The compressed generator of the G2 group of the BLS12-381 curve. +/// This constant represents a fixed base point on the elliptic curve. +/// Note that flat encoded plutus does not allow for the direct usage of BLS12-381 points. +/// More explicit, any points in plutus data or scripts must be decompressed before usage onchain. +pub const generator: G2Element = + #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8" + +test generator_1() { + builtin.bls12_381_g2_scalar_mul(scalar.field_prime, generator) == #"c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" +} + +/// Represents the additive identity (zero) in the G2 group. +/// Note that flat encoded plutus does not allow for the direct usage of BLS12-381 points. +/// More explicit, any points in plutus data or scripts must be decompressed before usage onchain. +pub const zero: G2Element = + #"c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" + +test zero_1() { + and { + zero == builtin.bls12_381_g2_scalar_mul(scalar.field_prime, generator), + zero == builtin.bls12_381_g2_scalar_mul( + scalar.field_prime, + #"9964a9ac2ee28a4dab595ff0970d446373bf46701c5d0b29ce8e1ba995d811a1c7b193c928269192c64ba1fbe4b1940207c251e086b452b920bc72e3cebab46ce672b9b088ca620a471d3b888d9737f6abd165319aa457dbf8835e3d34196051", + ), + zero == builtin.bls12_381_g2_scalar_mul( + scalar.field_prime, + #"a900e25cb53cf1eeb1a82c0c83292937c49c97966351273767a204256a7ef6e95aa391404387075d361e7b13ccd694db03aa73ee0e1bd2c3dd735582b99fdf71696de72e4eda18ae99ea45995f1c9605aa0057008ee9a4da604b5716fb4a345b", + ), + } +} + +/// Compresses a point in the G2 group into a more compact representation. +/// The compressed representation is the concatenation of two 48-byte strings, corresponding to a modified and complexified `x` coordinate. +/// The leading most significant 3 bits of this string indicate how to reconstruct the `y` coordinate. +/// +/// > [!NOTE] +/// > More explicitly via [Zcash's spec](https://github.com/supranational/blst#serialization-format): +/// > +/// > The most-significant three bits of a G1 or G2 encoding should be masked away before the coordinate(s) are interpreted. These bits are used to unambiguously represent the underlying element: +/// > +/// > - The most significant bit, when set, indicates that the point is in compressed form. Otherwise, the point is in uncompressed form. +/// > - The second-most significant bit indicates that the point is at infinity. If this bit is set, the remaining bits of the group element's encoding should be set to zero. +/// > - The third-most significant bit is set if (and only if) this point is in compressed form and it is not the point at infinity and its y-coordinate is the lexicographically largest of the two associated with the encoded x-coordinate. +pub fn compress(point) { + builtin.bls12_381_g2_compress(point) +} + +test compress_1() { + let g2 = + #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8" + compress(g2) == #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8" +} + +/// Decompresses a point in the G2 group from its compressed form. +pub fn decompress(bytes) { + builtin.bls12_381_g2_uncompress(bytes) +} + +test decompress_1() { + let g2 = + #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8" + generator == g2 +} + +pub fn equal(left, right) { + builtin.bls12_381_g2_equal(left, right) +} + +test equal_1() { + equal( + generator, + #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8", + ) +} + +/// Adds two points in the G2 group. +pub fn add(left, right) { + builtin.bls12_381_g2_add(left, right) +} + +/// Subtracts one point in the G2 group from another. +pub fn sub(left, right) { + builtin.bls12_381_g2_add(left, builtin.bls12_381_g2_neg(right)) +} + +test sub_1() { + generator == sub(add(generator, generator), generator) +} + +/// Exponentiates a point in the G2 group with a `scalar`. +/// This operation is equivalent to the repeated addition of the point with itself `e` times. +pub fn scale(point, e: Scalar) { + builtin.bls12_381_g2_scalar_mul(scalar.to_int(e), point) +} + +test scale_1() { + expect Some(x) = scalar.new(2) + builtin.bls12_381_g2_add(generator, generator) == scale(generator, x) +} + +/// Hashes arbitrary data to a point in the G2 group. +/// You can use the `domain_separation_tag` parameter to cryptographically separate different uses of the hash function between applications. +pub fn hash_to_group(bytes, domain_separation_tag) { + builtin.bls12_381_g2_hash_to_group(bytes, domain_separation_tag) +} + +test hash_to_group_1() { + hash_to_group("hello", "world") == #"a18486bba1dc8321f4998ed4268c6df8dfa5618dd5c91595844059d517f8104bf8031d3e766f9c99db1d6f58b201ee9614de92fc08f9e5cc3a6cd814e871857cb6e3924e8a4fa48775116c5f158d58ceda63614d62f6b7bc47db798d656969a5" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/scalar.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/scalar.ak new file mode 100644 index 00000000..cf028ad7 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/scalar.ak @@ -0,0 +1,255 @@ +//// This module implements arithmetic operations in the scalar field associated with the BLS12-381 elliptic curve. +//// The scalar field, defined over a prime number `q`, is derived from the order of the subgroup G1. +//// +//// More explicitly, we have the identity: +//// +//// ```aiken +//// builtin.bls12_381_g1_scalar_mul(q, bls12_381_g1_generator) == 1 +//// ``` +//// +//// where, +//// +//// ```aiken +//// q = 52435875175126190479447740508185965837690552500527637822603658699938581184513 +//// ``` +//// +//// This module provides functionality for basic arithmetic operations (addition, subtraction, multiplication, division) within this scalar field. +//// Additionally, it includes advanced operations such as exponentiation and calculation of multiplicative inverses, tailored for cryptographic applications. + +use aiken/builtin + +/// The prime number defining the scalar field of the BLS12-381 curve. +pub const field_prime = + 52435875175126190479447740508185965837690552500527637822603658699938581184513 + +/// Represents the additive identity (zero) in the `Scalar` field. +pub const zero: Scalar = Scalar(0) + +/// Represents the multiplicative identity (one) in the `Scalar` field. +pub const one: Scalar = Scalar(1) + +/// Opaque type representing an element of the finite field `Scalar`. +pub opaque type Scalar { + integer: Int, +} + +// ## Constructing + +/// Constructs a new `Scalar` element from an integer, ensuring it's within the valid range of the field. +/// Returns `None` if the integer is negative or greater than the prime number defining the field. +pub fn new(n: Int) -> Option { + if n >= 0 && n < field_prime { + Some(Scalar(n)) + } else { + None + } +} + +test new_1() { + and { + new(-1) == None, + new(field_prime) == None, + new(834884848) == Some(Scalar(834884848)), + } +} + +/// Constructs a new `Scalar` element from a Big-Endian (most-significant bits first) `ByteArray`. +pub fn from_bytearray_big_endian(bytes: ByteArray) -> Option { + new(builtin.bytearray_to_integer(True, bytes)) +} + +test from_bytearray_big_endian_1() { + from_bytearray_big_endian(#"ffff00") == Some(Scalar(16776960)) +} + +/// Constructs a new `Scalar` element from a Little-Endian (least-significant bits first) `ByteArray`. +pub fn from_bytearray_little_endian(bytes: ByteArray) -> Option { + new(builtin.bytearray_to_integer(False, bytes)) +} + +test from_bytearray_little_endian_1() { + from_bytearray_little_endian(#"ffff00") == Some(Scalar(65535)) +} + +// ## Modifying + +/// Exponentiates an `Scalar` element by a non-negative integer exponent, using repeated squaring. +/// Note that this function returns `scalar.zero` for negative exponents. +/// A dedicated builtin function for this is in the making, see CIP 109. +pub fn scale(self: Scalar, e: Int) -> Scalar { + if e < 0 { + zero + } else if e == 0 { + one + } else if e % 2 == 0 { + scale(mul(self, self), e / 2) + } else { + mul(self, scale(mul(self, self), ( e - 1 ) / 2)) + } +} + +test scale_1() { + and { + scale(Scalar(834884848), -1) == zero, + scale(Scalar(834884848), 0) == one, + scale(Scalar(834884848), 1) == Scalar(834884848), + scale(Scalar(834884848), 2) == Scalar(697032709419983104), + scale(Scalar(834884848), 3) == Scalar(581942047655130761945608192), + scale(Scalar(field_prime - 4), 200) == Scalar( + 12843927705572658539565969578937286576443167978938369866871449552629978143484, + ), + } +} + +/// A faster version of `scale` for the case where the exponent is a power of two. +/// That is, the exponent `e = 2^k` for some non-negative integer `k`. Which is used alot in zk-SNARKs. +pub fn scale2(self: Scalar, k: Int) -> Scalar { + if k < 0 { + zero + } else { + do_scale2(self, k) + } +} + +fn do_scale2(self: Scalar, k: Int) -> Scalar { + if k == 0 { + self + } else { + do_scale2(mul(self, self), k - 1) + } +} + +test scale2_1() { + and { + scale2(Scalar(834884848), -1) == zero, + scale2(Scalar(834884848), 0) == scale(Scalar(834884848), 1), + scale2(Scalar(834884848), 1) == scale(Scalar(834884848), 2), + scale2(Scalar(834884848), 2) == scale(Scalar(834884848), 4), + scale2(Scalar(834884848), 3) == scale(Scalar(834884848), 8), + scale2(Scalar(834884848), 4) == scale(Scalar(834884848), 16), + } +} + +// ## Combining + +/// Adds two `Scalar` elements, ensuring the result stays within the finite field range. +pub fn add(left: Scalar, right: Scalar) -> Scalar { + Scalar(( left.integer + right.integer ) % field_prime) +} + +test add_1() { + and { + (add(Scalar(834884848), Scalar(834884848)) == Scalar(1669769696))?, + (add(Scalar(field_prime - 1), Scalar(1)) == Scalar(0))?, + (add(Scalar(3), Scalar(field_prime)) == Scalar(3))?, + } +} + +/// Divides one `Scalar` element by another, returning `None` if the divisor is zero. +pub fn div(left: Scalar, right: Scalar) -> Option { + if right == zero { + None + } else { + Some(mul(left, scale(right, field_prime - 2))) + } +} + +test div_1() { + and { + div(Scalar(834884848), Scalar(834884848)) == Some(Scalar(1)), + div(Scalar(834884848), zero) == None, + div(Scalar(field_prime - 1), Scalar(2)) == Some( + Scalar( + 26217937587563095239723870254092982918845276250263818911301829349969290592256, + ), + ), + } +} + +/// Multiplies two `Scalar` elements, with the result constrained within the finite field. +pub fn mul(left: Scalar, right: Scalar) -> Scalar { + Scalar(left.integer * right.integer % field_prime) +} + +test mul_1() { + and { + mul(Scalar(834884848), Scalar(834884848)) == Scalar(697032709419983104), + mul(zero, Scalar(834884848)) == zero, + mul(Scalar(field_prime - 1), Scalar(2)) == Scalar( + 52435875175126190479447740508185965837690552500527637822603658699938581184511, + ), + } +} + +/// Calculates the additive inverse of a `Scalar` element. +pub fn neg(self: Scalar) -> Scalar { + // this is basicly sub(zero, self), but more efficient as it saves one modulo operation + if self.integer == 0 { + self + } else { + Scalar(field_prime - self.integer) + } +} + +test neg_1() { + and { + neg(Scalar(834884848)) == Scalar( + 52435875175126190479447740508185965837690552500527637822603658699937746299665, + ), + neg(zero) == zero, + neg(one) == Scalar(field_prime - 1), + } +} + +/// Calculates the multiplicative inverse of an `Scalar` element, returning `None` if the element is zero. +pub fn recip(self: Scalar) -> Option { + div(one, self) +} + +test recip_1() { + and { + recip(Scalar(834884848)) == Some( + Scalar( + 35891248691642227249400403463796410930702563777316955162085759263735363466421, + ), + ), + recip(zero) == None, + } +} + +/// Subtracts one `Scalar` element from another, with the result wrapped within the finite field range. +pub fn sub(left: Scalar, right: Scalar) -> Scalar { + Scalar(( left.integer - right.integer ) % field_prime) +} + +test sub_1() { + and { + (sub(Scalar(834884848), Scalar(834884848)) == zero)?, + (sub(zero, Scalar(5)) == Scalar(field_prime - 5))?, + } +} + +// ## Transforming + +/// Converts a `Scalar` element back to its integer representation. +pub fn to_int(self: Scalar) -> Int { + self.integer +} + +test to_int_1() { + to_int(Scalar(834884848)) == 834884848 +} + +/// Converts a `Scalar` element to a Big-Endian (most-significant bits first) `ByteArray`. +pub fn to_bytearray_big_endian(self: Scalar, size: Int) -> ByteArray { + builtin.integer_to_bytearray(True, size, self.integer) +} + +/// Converts a `Scalar` element to a Little-Endian (least-significant bits first) `ByteArray`. +pub fn to_bytearray_little_endian(self: Scalar, size: Int) -> ByteArray { + builtin.integer_to_bytearray(False, size, self.integer) +} + +test to_bytearray_1() { + to_bytearray_big_endian(Scalar(16777215), 3) == #"ffffff" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/interval.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/interval.ak new file mode 100644 index 00000000..96179f9b --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/interval.ak @@ -0,0 +1,680 @@ +//// In a eUTxO-based blockchain like Cardano, the management of time can be +//// finicky. +//// +//// Indeed, in order to maintain a complete determinism in the execution of +//// scripts, it is impossible to introduce a notion of _"current time"_ since +//// the execution would then depend on factor that are external to the +//// transaction itself: the ineluctable stream of time flowing in our universe. +//// +//// Hence, to work around that, we typically define time intervals, which gives +//// window -- a.k.a intervals -- within which the transaction can be executed. +//// From within a script, it isn't possible to know when exactly the script is +//// executed, but we can reason about the interval bounds to validate pieces of +//// logic. + +// TODO: Replace 'Int' with a generic 'a' once we have comparable traits. + +/// A type to represent intervals of values. Interval are inhabited by a type +/// `a` which is useful for non-infinite intervals that have a finite +/// lower-bound and/or upper-bound. +/// +/// This allows to represent all kind of mathematical intervals: +/// +/// ```aiken +/// // [1; 10] +/// let i0: Interval = Interval +/// { lower_bound: +/// IntervalBound { bound_type: Finite(1), is_inclusive: True } +/// , upper_bound: +/// IntervalBound { bound_type: Finite(10), is_inclusive: True } +/// } +/// ``` +/// +/// ```aiken +/// // (20; infinity) +/// let i1: Interval = Interval +/// { lower_bound: +/// IntervalBound { bound_type: Finite(20), is_inclusive: False } +/// , upper_bound: +/// IntervalBound { bound_type: PositiveInfinity, is_inclusive: False } +/// } +/// ``` +pub type Interval { + lower_bound: IntervalBound, + upper_bound: IntervalBound, +} + +/// An interval bound, either inclusive or exclusive. +pub type IntervalBound { + bound_type: IntervalBoundType, + is_inclusive: Bool, +} + +/// A type of interval bound. Where finite, a value of type `a` must be +/// provided. `a` will typically be an `Int`, representing a number of seconds or +/// milliseconds. +pub type IntervalBoundType { + NegativeInfinity + Finite(a) + PositiveInfinity +} + +// ## Constructing + +/// Create an interval that includes all values greater than the given bound. i.e [lower_bound, +INF) +/// +/// ```aiken +/// interval.after(10) == Interval { +/// lower_bound: IntervalBound { bound_type: Finite(10), is_inclusive: True }, +/// upper_bound: IntervalBound { bound_type: PositiveInfinity, is_inclusive: True }, +/// } +/// ``` +pub fn after(lower_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: Finite(lower_bound), + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: PositiveInfinity, + is_inclusive: True, + }, + } +} + +/// Create an interval that includes all values after (and not including) the given bound. i.e (lower_bound, +INF) +/// +/// ```aiken +/// interval.entirely_after(10) == Interval { +/// lower_bound: IntervalBound { bound_type: Finite(10), is_inclusive: False }, +/// upper_bound: IntervalBound { bound_type: PositiveInfinity, is_inclusive: True }, +/// } +/// ``` +pub fn entirely_after(lower_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: Finite(lower_bound), + is_inclusive: False, + }, + upper_bound: IntervalBound { + bound_type: PositiveInfinity, + is_inclusive: True, + }, + } +} + +/// Create an interval that includes all values before (and including) the given bound. i.e (-INF, upper_bound] +/// +/// ```aiken +/// interval.before(100) == Interval { +/// lower_bound: IntervalBound { bound_type: NegativeInfinity, is_inclusive: True }, +/// upper_bound: IntervalBound { bound_type: Finite(100), is_inclusive: True }, +/// } +/// ``` +pub fn before(upper_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: NegativeInfinity, + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: Finite(upper_bound), + is_inclusive: True, + }, + } +} + +/// Create an interval that includes all values before (and not including) the given bound. i.e (-INF, upper_bound) +/// +/// ```aiken +/// interval.entirely_before(10) == Interval { +/// lower_bound: IntervalBound { bound_type: NegativeInfinity, is_inclusive: True }, +/// upper_bound: IntervalBound { bound_type: Finite(10), is_inclusive: False }, +/// } +/// ``` +pub fn entirely_before(upper_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: NegativeInfinity, + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: Finite(upper_bound), + is_inclusive: False, + }, + } +} + +/// Create an interval that includes all values between two bounds, including the bounds. i.e. [lower_bound, upper_bound] +/// +/// ```aiken +/// interval.between(10, 100) == Interval { +/// lower_bound: IntervalBound { bound_type: Finite(10), is_inclusive: True }, +/// upper_bound: IntervalBound { bound_type: Finite(100), is_inclusive: True }, +/// } +/// ``` +pub fn between(lower_bound: a, upper_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: Finite(lower_bound), + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: Finite(upper_bound), + is_inclusive: True, + }, + } +} + +/// Create an interval that includes all values between two bounds, excluding the bounds. i.e. (lower_bound, upper_bound) +/// +/// ```aiken +/// interval.entirely_between(10, 100) == Interval { +/// lower_bound: IntervalBound { bound_type: Finite(10), is_inclusive: False }, +/// upper_bound: IntervalBound { bound_type: Finite(100), is_inclusive: False }, +/// } +/// ``` +pub fn entirely_between(lower_bound: a, upper_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: Finite(lower_bound), + is_inclusive: False, + }, + upper_bound: IntervalBound { + bound_type: Finite(upper_bound), + is_inclusive: False, + }, + } +} + +/// Create an empty interval that contains no value. +/// +/// ```aiken +/// interval.contains(empty, 0) == False +/// interval.contains(empty, 1000) == False +/// ``` +pub const empty: Interval = + Interval { + lower_bound: IntervalBound { + bound_type: PositiveInfinity, + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: NegativeInfinity, + is_inclusive: True, + }, + } + +/// Create an interval that contains every possible values. i.e. (-INF, +INF) +/// +/// ```aiken +/// interval.contains(everything, 0) == True +/// interval.contains(everything, 1000) == True +/// ``` +pub const everything: Interval = + Interval { + lower_bound: IntervalBound { + bound_type: NegativeInfinity, + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: PositiveInfinity, + is_inclusive: True, + }, + } + +// ## Inspecting + +/// Checks whether an element is contained within the interval. +/// +/// ```aiken +/// let iv = +/// Interval { +/// lower_bound: IntervalBound { +/// bound_type: Finite(14), +/// is_inclusive: True +/// }, +/// upper_bound: IntervalBound { +/// bound_type: Finite(42), +/// is_inclusive: False +/// }, +/// } +/// +/// interval.contains(iv, 25) == True +/// interval.contains(iv, 0) == False +/// interval.contains(iv, 14) == True +/// interval.contains(iv, 42) == False +/// ``` +pub fn contains(self: Interval, elem: Int) -> Bool { + let is_greater_than_lower_bound = + when self.lower_bound.bound_type is { + NegativeInfinity -> True + Finite(lower_bound) -> + if self.lower_bound.is_inclusive { + elem >= lower_bound + } else { + elem > lower_bound + } + PositiveInfinity -> False + } + + let is_smaller_than_upper_bound = + when self.upper_bound.bound_type is { + NegativeInfinity -> False + Finite(upper_bound) -> + if self.upper_bound.is_inclusive { + elem <= upper_bound + } else { + elem < upper_bound + } + PositiveInfinity -> True + } + + is_greater_than_lower_bound && is_smaller_than_upper_bound +} + +test contains_1() { + let iv = everything + contains(iv, 14) +} + +test contains_2() { + let iv = entirely_before(15) + contains(iv, 14) +} + +test contains_3() { + let iv = before(14) + contains(iv, 14) +} + +test contains_4() { + let iv = entirely_before(14) + !contains(iv, 14) +} + +test contains_5() { + let iv = entirely_after(13) + contains(iv, 14) +} + +test contains_6() { + let iv = after(14) + contains(iv, 14) +} + +test contains_7() { + let iv = entirely_after(14) + !contains(iv, 14) +} + +test contains_8() { + let iv = between(42, 1337) + !contains(iv, 14) +} + +test contains_9() { + let iv = between(0, 42) + contains(iv, 14) +} + +test contains_10() { + let iv = between(0, 42) + contains(iv, 42) +} + +test contains_11() { + let iv = entirely_between(0, 42) + !contains(iv, 0) +} + +test contains_12() { + let iv = empty + !contains(iv, 14) +} + +/// Tells whether an interval is empty; i.e. that is contains no value. +/// +/// ```aiken +/// let iv1 = interval.empty +/// +/// let iv2 = Interval { +/// lower_bound: IntervalBound { bound_type: Finite(0), is_inclusive: False }, +/// upper_bound: IntervalBound { bound_type: Finite(0), is_inclusive: False }, +/// } +/// +/// let iv3 = Interval { +/// lower_bound: IntervalBound { bound_type: Finite(0), is_inclusive: False }, +/// upper_bound: IntervalBound { bound_type: Finite(100), is_inclusive: False }, +/// } +/// +/// interval.is_empty(iv1) == True +/// interval.is_empty(iv2) == True +/// interval.is_empty(iv3) == False +/// +/// // Note: Two empty intervals are not necessarily equal. +/// iv1 != iv2 +/// ``` +pub fn is_empty(self: Interval) -> Bool { + let ordering = + compare_bound_type(self.lower_bound.bound_type, self.upper_bound.bound_type) + + when ordering is { + Greater -> True + Equal -> !(self.lower_bound.is_inclusive && self.upper_bound.is_inclusive) + Less -> { + let is_open_interval = + !self.lower_bound.is_inclusive && !self.upper_bound.is_inclusive + if is_open_interval { + when (self.lower_bound.bound_type, self.upper_bound.bound_type) is { + (Finite(lower_bound), Finite(upper_bound)) -> + lower_bound + 1 == upper_bound + _ -> False + } + } else { + False + } + } + } +} + +/// Check whether the interval is entirely after the point "a" +/// +/// ```aiken +/// interval.is_entirely_after(interval.after(10), 5) == True +/// interval.is_entirely_after(interval.after(10), 10) == False +/// interval.is_entirely_after(interval.after(10), 15) == False +/// interval.is_entirely_after(interval.between(10, 20), 30) == False +/// interval.is_entirely_after(interval.between(10, 20), 5) == True +pub fn is_entirely_after(self: Interval, point: Int) -> Bool { + when self.lower_bound.bound_type is { + Finite(low) -> + if self.lower_bound.is_inclusive { + point < low + } else { + point <= low + } + _ -> False + } +} + +test is_entirely_after_1() { + is_entirely_after(after(10), 5) +} + +test is_entirely_after_2() { + !is_entirely_after(after(10), 10) +} + +test is_entirely_after_3() { + !is_entirely_after(after(10), 15) +} + +test is_entirely_after_4() { + !is_entirely_after(between(10, 20), 30) +} + +test is_entirely_after_5() { + is_entirely_after(between(10, 20), 5) +} + +test is_entirely_after_6() { + is_entirely_after(entirely_after(10), 10) +} + +test is_entirely_after_7() { + !is_entirely_after(before(10), 5) +} + +test is_entirely_after_8() { + !is_entirely_after(before(10), 15) +} + +test is_entirely_after_9() { + !is_entirely_after(entirely_before(10), 5) +} + +/// Check whether the interval is entirely before the point "a" +/// +/// ```aiken +/// interval.is_entirely_before(interval.before(10), 15) == True +/// interval.is_entirely_before(interval.before(10), 10) == False +/// interval.is_entirely_before(interval.before(10), 5) == False +/// interval.is_entirely_before(interval.between(10, 20), 30) == True +/// interval.is_entirely_before(interval.between(10, 20), 5) == False +pub fn is_entirely_before(self: Interval, point: Int) -> Bool { + when self.upper_bound.bound_type is { + Finite(hi) -> + if self.upper_bound.is_inclusive { + hi < point + } else { + hi <= point + } + _ -> False + } +} + +test is_entirely_before_1() { + is_entirely_before(before(10), 15) +} + +test is_entirely_before_2() { + !is_entirely_before(before(10), 10) +} + +test is_entirely_before_3() { + !is_entirely_before(before(10), 5) +} + +test is_entirely_before_4() { + is_entirely_before(between(10, 20), 30) +} + +test is_entirely_before_5() { + !is_entirely_before(between(10, 20), 5) +} + +test is_entirely_before_6() { + is_entirely_before(entirely_before(10), 10) +} + +test is_entirely_before_7() { + !is_entirely_before(after(10), 15) +} + +test is_entirely_before_8() { + !is_entirely_before(after(10), 5) +} + +test is_entirely_before_9() { + !is_entirely_before(entirely_after(10), 5) +} + +// ## Combining + +/// Computes the smallest interval containing the two given intervals, if any +/// +/// ```aiken +/// let iv1 = between(0, 10) +/// let iv2 = between(2, 14) +/// hull(iv1, iv2) == between(0, 14) +/// +/// let iv1 = between(5, 10) +/// let iv2 = before(0) +/// hull(iv1, iv2) == before(10) +/// +/// let iv1 = entirely_after(0) +/// let iv2 = between(10, 42) +/// hull(iv1, iv2) = entirely_after(0) +/// ``` +pub fn hull(iv1: Interval, iv2: Interval) -> Interval { + Interval { + lower_bound: min(iv1.lower_bound, iv2.lower_bound), + upper_bound: max(iv1.upper_bound, iv2.upper_bound), + } +} + +test hull_1() { + let iv1 = between(0, 10) + let iv2 = between(2, 14) + hull(iv1, iv2) == between(0, 14) +} + +test hull_2() { + let iv1 = between(5, 10) + let iv2 = before(0) + hull(iv1, iv2) == before(10) +} + +test hull_3() { + let iv1 = entirely_after(0) + let iv2 = between(10, 42) + hull(iv1, iv2) == entirely_after(0) +} + +/// Computes the largest interval contains in the two given intervals, if any. +/// +/// ```aiken +/// let iv1 = interval.between(0, 10) +/// let iv2 = interval.between(2, 14) +/// interval.intersection(iv1, iv2) == interval.between(2, 10) +/// +/// let iv1 = interval.entirely_before(10) +/// let iv2 = interval.entirely_after(0) +/// interval.intersection(iv1, iv2) == interval.entirely_between(0, 10) +/// +/// let iv1 = interval.between(0, 1) +/// let iv2 = interval.between(2, 3) +/// interval.intersection(iv1, iv2) |> interval.is_empty +/// ``` +pub fn intersection(iv1: Interval, iv2: Interval) -> Interval { + Interval { + lower_bound: max(iv1.lower_bound, iv2.lower_bound), + upper_bound: min(iv1.upper_bound, iv2.upper_bound), + } +} + +test intersection_1() { + let iv1 = between(0, 10) + let iv2 = between(2, 14) + intersection(iv1, iv2) == between(2, 10) +} + +test intersection_2() { + let iv1 = between(0, 1) + let iv2 = between(1, 2) + intersection(iv1, iv2) == between(1, 1) +} + +test intersection_3() { + let iv1 = between(0, 1) + let iv2 = entirely_between(1, 2) + intersection(iv1, iv2) + |> is_empty +} + +test intersection_4() { + let iv1 = entirely_between(0, 1) + let iv2 = entirely_between(1, 2) + intersection(iv1, iv2) + |> is_empty +} + +test intersection_5() { + let iv1 = between(0, 10) + let iv2 = before(4) + intersection(iv1, iv2) == between(0, 4) +} + +test intersection_6() { + let iv1 = entirely_before(10) + let iv2 = entirely_after(0) + intersection(iv1, iv2) == entirely_between(0, 10) +} + +/// Return the highest bound of the two. +/// +/// ```aiken +/// let ib1 = IntervalBound { bound_type: Finite(0), is_inclusive: False } +/// let ib2 = IntervalBound { bound_type: Finite(1), is_inclusive: False } +/// +/// interval.max(ib1, ib2) == ib2 +/// ``` +pub fn max( + left: IntervalBound, + right: IntervalBound, +) -> IntervalBound { + when compare_bound(left, right) is { + Less -> right + Equal -> left + Greater -> left + } +} + +/// Return the smallest bound of the two. +/// +/// ```aiken +/// let ib1 = IntervalBound { bound_type: Finite(0), is_inclusive: False } +/// let ib2 = IntervalBound { bound_type: Finite(1), is_inclusive: False } +/// +/// interval.min(ib1, ib2) == ib1 +/// ``` +pub fn min( + left: IntervalBound, + right: IntervalBound, +) -> IntervalBound { + when compare_bound(left, right) is { + Less -> left + Equal -> left + Greater -> right + } +} + +fn compare_bound( + left: IntervalBound, + right: IntervalBound, +) -> Ordering { + when compare_bound_type(left.bound_type, right.bound_type) is { + Less -> Less + Greater -> Greater + Equal -> + if left.is_inclusive == right.is_inclusive { + Equal + } else if left.is_inclusive { + Greater + } else { + Less + } + } +} + +fn compare_bound_type( + left: IntervalBoundType, + right: IntervalBoundType, +) -> Ordering { + when left is { + NegativeInfinity -> + when right is { + NegativeInfinity -> Equal + _ -> Less + } + PositiveInfinity -> + when right is { + PositiveInfinity -> Equal + _ -> Greater + } + Finite(left) -> + when right is { + NegativeInfinity -> Greater + PositiveInfinity -> Less + Finite(right) -> + if left < right { + Less + } else if left == right { + Equal + } else { + Greater + } + } + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/math.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/math.ak new file mode 100644 index 00000000..dd575e7a --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/math.ak @@ -0,0 +1,424 @@ +//// This module contains some basic Math utilities. Standard arithmetic +//// operations on integers are available through native operators: +//// +//// Operator | Description +//// --- | :--- +//// `+` | Arithmetic sum +//// `-` | Arithmetic difference +//// `/` | Whole division +//// `*` | Arithmetic multiplication +//// `%` | Remainder by whole division +//// +//// Here are a few examples: +//// +//// ```aiken +//// 1 + 1 // 2 +//// 10 - 2 // 8 +//// 40 / 14 // 2 +//// 3 * 4 // 12 +//// 10 % 3 // 1 + +use aiken/builtin + +/// Calculate the absolute value of an integer. +/// +/// ```aiken +/// math.abs(-42) == 42 +/// math.abs(14) == 14 +/// ``` +pub fn abs(self: Int) -> Int { + if self < 0 { + 0 - self + } else { + self + } +} + +test abs_1() { + abs(14) == 14 +} + +test abs_2() { + abs(-42) == 42 +} + +/// Restrict the value of an integer between two min and max bounds +/// +/// ```aiken +/// math.clamp(14, min: 0, max: 10) == 10 +/// ``` +pub fn clamp(self: Int, min: Int, max: Int) -> Int { + if self < min { + min + } else { + if self > max { + max + } else { + self + } + } +} + +test clamp_1() { + clamp(14, min: 0, max: 10) == 10 +} + +test clamp_2() { + clamp(7, min: 0, max: 10) == 7 +} + +test clamp_3() { + clamp(7, min: 10, max: 100) == 10 +} + +/// The greatest common divisor of two integers. +/// +/// ```aiken +/// math.gcd(42, 14) == 14 +/// math.gcd(14, 42) == 14 +/// math.gcd(0, 0) == 0 +/// ``` +pub fn gcd(x: Int, y: Int) -> Int { + abs(do_gcd(x, y)) +} + +fn do_gcd(x: Int, y: Int) -> Int { + when y is { + 0 -> x + _ -> do_gcd(y, x % y) + } +} + +test gcd_test1() { + gcd(10, 300) == 10 +} + +test gcd_test2() { + gcd(-10, 300) == 10 +} + +test gcd_test3() { + gcd(42, 14) == 14 +} + +/// Checks if an integer has a given integer square root x. +/// The check has constant time complexity $O(1)$. +/// +/// ```aiken +/// math.is_sqrt(0, 0) +/// math.is_sqrt(25, 5) +/// !math.is_sqrt(25, -5) +/// math.is_sqrt(44203, 210) +/// ``` +pub fn is_sqrt(self: Int, x: Int) -> Bool { + x * x <= self && ( x + 1 ) * ( x + 1 ) > self +} + +test is_sqrt1() { + is_sqrt(44203, 210) +} + +test is_sqrt2() { + is_sqrt(975461057789971041, 987654321) +} + +/// The logarithm in base `b` of an element using integer divisions. +/// +/// ```aiken +/// math.log(10, base: 2) == 3 +/// math.log(42, base: 2) == 5 +/// math.log(42, base: 3) == 3 +/// math.log(5, base: 0) == 0 +/// math.log(4, base: 4) == 1 +/// math.log(4, base: 42) == 0 +/// ``` +pub fn log(self: Int, base: Int) -> Int { + if base <= 0 { + 0 + } else if self == base { + 1 + } else if self < base { + 0 + } else { + 1 + log(self / base, base) + } +} + +test log_10_2() { + log(10, base: 2) == 3 +} + +test log_42_2() { + log(42, base: 2) == 5 +} + +test log_42_3() { + log(42, base: 3) == 3 +} + +test log_5_0() { + log(5, base: 0) == 0 +} + +test log_4_4() { + log(4, base: 4) == 1 +} + +test log_4_43() { + log(4, base: 43) == 0 +} + +/// The integer logarithm in base 2. Faster than [`log`](#log) in this particular case. +/// +/// ```aiken +/// math.log2(1) == 0 +/// math.log2(2) == 1 +/// math.log2(3) == 1 +/// math.log2(4) == 2 +/// math.log2(256) == 8 +/// math.log2(257) == 8 +/// math.log2(511) == 8 +/// math.log2(1025) == 10 +/// ``` +pub fn log2(x: Int) -> Int { + expect x > 0 + let s = builtin.integer_to_bytearray(True, 0, x) + let len = builtin.length_of_bytearray(s) + let b = builtin.index_bytearray(s, 0) + len * 8 - if b < 2 { + 8 + } else if b < 4 { + 7 + } else if b < 8 { + 6 + } else if b < 16 { + 5 + } else if b < 32 { + 4 + } else if b < 64 { + 3 + } else if b < 128 { + 2 + } else { + 1 + } +} + +test log2_matrix() { + and { + log2(1) == 0, + log2(2) == 1, + log2(3) == 1, + log2(4) == 2, + log2(256) == 8, + log2(257) == 8, + log2(511) == 8, + log2(1025) == 10, + } +} + +/// Return the maximum of two integers. +pub fn max(a: Int, b: Int) -> Int { + if a > b { + a + } else { + b + } +} + +test max_1() { + max(0, 0) == 0 +} + +test max_2() { + max(14, 42) == 42 +} + +test max_3() { + max(42, 14) == 42 +} + +/// Return the minimum of two integers. +pub fn min(a: Int, b: Int) -> Int { + if a > b { + b + } else { + a + } +} + +test min_1() { + min(0, 0) == 0 +} + +test min_2() { + min(14, 42) == 14 +} + +test min_3() { + min(42, 14) == 14 +} + +/// Calculates a number to the power of `e` using the exponentiation by +/// squaring method. +/// +/// ```aiken +/// math.pow(3, 5) == 243 +/// math.pow(7, 2) == 49 +/// math.pow(3, -4) == 0 +/// math.pow(0, 0) == 1 +/// math.pow(513, 3) == 135005697 +/// ``` +pub fn pow(self: Int, e: Int) -> Int { + if e < 0 { + 0 + } else if e == 0 { + 1 + } else if e % 2 == 0 { + pow(self * self, e / 2) + } else { + self * pow(self * self, ( e - 1 ) / 2) + } +} + +test pow_3_5() { + pow(3, 5) == 243 +} + +test pow_7_2() { + pow(7, 2) == 49 +} + +test pow_3__4() { + // negative powers round to zero + pow(3, -4) == 0 +} + +test pow_0_0() { + // sorry math + pow(0, 0) == 1 +} + +test pow_513_3() { + pow(513, 3) == 135005697 +} + +test pow_2_4() { + pow(2, 4) == 16 +} + +test pow_2_42() { + pow(2, 42) == 4398046511104 +} + +/// Calculates the power of 2 for a given exponent `e`. Much cheaper than +/// using `pow(2, _)` for small exponents $0 < e < 256$. +/// +/// ```aiken +/// math.pow2(-2) == 0 +/// math.pow2(0) == 1 +/// math.pow2(1) == 2 +/// math.pow2(4) == 16 +/// math.pow2(42) == 4398046511104 +/// ``` +pub fn pow2(e: Int) -> Int { + // do_pow2(e, 1) + if e < 8 { + if e < 0 { + 0 + } else { + builtin.index_bytearray(#[1, 2, 4, 8, 16, 32, 64, 128], e) + } + } else if e < 32 { + 256 * pow2(e - 8) + } else { + 4294967296 * pow2(e - 32) + } +} + +test pow2_neg() { + pow2(-2) == 0 +} + +test pow2_0() { + pow2(0) == 1 +} + +test pow2_1() { + pow2(1) == 2 +} + +test pow2_4() { + pow2(4) == 16 +} + +test pow2_42() { + pow2(42) == 4398046511104 +} + +test pow2_256() { + pow2(256) == 115792089237316195423570985008687907853269984665640564039457584007913129639936 +} + +/// Calculates the square root of an integer using the [Babylonian +/// method](https://en.wikipedia.org/wiki/Methods_of_computing_square_roots#Babylonian_method). This returns either the exact result or the smallest integer +/// nearest to the square root. +/// +/// Returns `None` for negative values. +/// +/// ```aiken +/// math.sqrt(0) == Some(0) +/// math.sqrt(25) == Some(5) +/// math.sqrt(44203) == Some(210) +/// math.sqrt(-42) == None +/// ``` +/// +/// > [!TIP] +/// > This function can be quite expensive to perform on-chain. Prefer using [`is_sqrt`](#is_sqrt) whenever possible. +pub fn sqrt(self: Int) -> Option { + if self < 0 { + None + } else if self <= 1 { + Some(self) + } else { + Some(sqrt_babylonian(self, self, ( self + 1 ) / 2)) + } +} + +// The basic idea is that if x is an overestimate to the square root of a +// non-negative real number S then S/x will be an underestimate, or vice versa, +// and so the average of these two numbers may reasonably be expected to provide a +// better approximation (though the formal proof of that assertion depends on the +// inequality of arithmetic and geometric means that shows this average is always +// an overestimate of the square root. +fn sqrt_babylonian(self: Int, x: Int, y: Int) -> Int { + if y >= x { + x + } else { + sqrt_babylonian(self, y, ( y + self / y ) / 2) + } +} + +test sqrt1() { + sqrt(0) == Some(0) +} + +test sqrt2() { + sqrt(1) == Some(1) +} + +test sqrt3() { + sqrt(25) == Some(5) +} + +test sqrt4() { + sqrt(44203) == Some(210) +} + +test sqrt5() { + sqrt(975461057789971041) == Some(987654321) +} + +test sqrt6() { + sqrt(-42) == None +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.ak new file mode 100644 index 00000000..88fe7ab7 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.ak @@ -0,0 +1,871 @@ +//// This module implements operations between rational numbers. +//// +//// > [!CAUTION] +//// > Internally, rational aren't automatically reduced as this is **only done on-demand**. +//// > +//// > Thus, for example: +//// > +//// > ```aiken +//// > rational.new(2, 3) != rational.new(4, 6) +//// > ``` +//// > +//// > Comparing rational values should, therefore, only happen after reduction (see [reduce](#reduce)) or via the [compare](#compare) method. + +use aiken/builtin +use aiken/collection/list +use aiken/math +use aiken/option + +/// Opaque type used to ensure the sign of the Rational is managed strictly in the numerator. +pub opaque type Rational { + numerator: Int, + denominator: Int, +} + +// ## Constructing + +/// Create a new `Rational` from an `Int`. +/// +/// ```aiken +/// Some(rational.from_int(14)) == rational.new(14, 1) +/// Some(rational.from_int(-5)) == rational.new(-5, 1) +/// Some(rational.from_int(0)) == rational.new(0, 1) +/// ``` +pub fn from_int(numerator: Int) -> Rational { + Rational { numerator, denominator: 1 } +} + +test from_int_1() { + and { + (from_int(14) == ratio(14, 1))?, + (from_int(-5) == ratio(-5, 1))?, + (from_int(0) == ratio(0, 1))?, + } +} + +/// An unsafe constructor for `Rational` values. Assumes that the following invariants are +/// enforced: +/// +/// - the denominator is positive (the sign is managed in the numerator); +/// - the denominator is not null. +/// +/// This function is mainly used as a quick way to construct rationals from literal values. +fn ratio(numerator: Int, denominator: Int) -> Rational { + Rational { numerator, denominator } +} + +/// Make a `Rational` number from the ratio of two integers. +/// +/// Returns `None` when the denominator is null. +/// +/// ```aiken +/// rational.new(14, 42) == Some(r) +/// rational.new(14, 0) == None +/// ``` +pub fn new(numerator: Int, denominator: Int) -> Option { + if denominator == 0 { + None + } else if denominator < 0 { + Some(Rational { numerator: -numerator, denominator: -denominator }) + } else { + Some(Rational { numerator, denominator }) + } +} + +test new_1() { + and { + (new(2, 0) == None)?, + (new(2, 3) == Some(ratio(2, 3)))?, + (new(-2, 3) == Some(ratio(-2, 3)))?, + (new(2, -3) == Some(ratio(-2, 3)))?, + (new(2, 4) == Some(ratio(2, 4)))?, + (new(-2, -3) == Some(ratio(2, 3)))?, + (new(-2, -4) == Some(ratio(2, 4)))?, + } +} + +/// A null `Rational`. +pub const zero: Rational = Rational { numerator: 0, denominator: 1 } + +test zero_1() { + zero == ratio(0, 1) +} + +// ## Inspecting + +/// Get the denominator of a rational value. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.denominator(x) == 3 +/// ``` +pub fn denominator(self: Rational) -> Int { + self.denominator +} + +test denominator_1() { + expect Some(x) = new(2, 3) + expect Some(y) = new(-2, 3) + expect Some(z) = new(2, -3) + expect Some(w) = new(-2, -3) + and { + (denominator(x) == 3)?, + (denominator(y) == 3)?, + (denominator(z) == 3)?, + (denominator(w) == 3)?, + } +} + +/// Get the numerator of a rational value. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.numerator(x) == 2 +/// ``` +pub fn numerator(self: Rational) -> Int { + self.numerator +} + +test numerator_1() { + expect Some(x) = new(2, 3) + expect Some(y) = new(-2, 3) + expect Some(z) = new(2, -3) + expect Some(w) = new(-2, -3) + + and { + (numerator(x) == 2)?, + (numerator(y) == -2)?, + (numerator(z) == -2)?, + (numerator(w) == 2)?, + } +} + +// ## Modifying + +/// Absolute value of a `Rational`. +/// +/// ```aiken +/// expect Some(x) = rational.new(3, 2) +/// expect Some(y) = rational.new(-3, 2) +/// +/// rational.abs(x) == x +/// rational.abs(y) == x +/// ``` +pub fn abs(self: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = self + Rational { numerator: math.abs(a_n), denominator: a_d } +} + +test abs_examples() { + and { + (abs(ratio(5, 2)) == ratio(5, 2))?, + (abs(ratio(-5, 2)) == ratio(5, 2))?, + (abs(ratio(5, 2)) == abs(ratio(-5, 2)))?, + } +} + +/// Change the sign of a `Rational`. +/// +/// ```aiken +/// expect Some(x) = rational.new(3, 2) +/// expect Some(y) = rational.new(-3, 2) +/// +/// rational.negate(x) == y +/// rational.negate(y) == x +/// ``` +pub fn negate(a: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = a + Rational { numerator: -a_n, denominator: a_d } +} + +test negate_1() { + and { + (negate(ratio(5, 2)) == ratio(-5, 2))?, + (negate(ratio(-5, 2)) == ratio(5, 2))?, + (negate(negate(ratio(5, 2))) == ratio(5, 2))?, + } +} + +/// Reciprocal of a `Rational` number. That is, a new `Rational` where the +/// numerator and denominator have been swapped. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 5) +/// rational.reciprocal(x) == rational.new(5, 2) +/// +/// let y = rational.zero +/// rational.reciprocal(y) == None +/// ``` +pub fn reciprocal(self: Rational) -> Option { + let Rational { numerator: a_n, denominator: a_d } = self + if a_n < 0 { + Some(Rational { numerator: -a_d, denominator: -a_n }) + } else if a_n > 0 { + Some(Rational { numerator: a_d, denominator: a_n }) + } else { + None + } +} + +test reciprocal_1() { + and { + (reciprocal(ratio(5, 2)) == new(2, 5))?, + (reciprocal(ratio(-5, 2)) == new(-2, 5))?, + (reciprocal(ratio(0, 2)) == None)?, + (reciprocal(ratio(2, 3)) == new(3, 2))?, + (reciprocal(ratio(-2, 3)) == new(-3, 2))?, + } +} + +/// Reduce a rational to its irreducible form. This operation makes the +/// numerator and denominator coprime. +/// +/// ```aiken +/// expect Some(x) = rational.new(80, 200) +/// Some(rational.reduce(x)) == rational.new(2, 5) +/// ``` +pub fn reduce(self: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = self + let d = math.gcd(a_n, a_d) + Rational { numerator: a_n / d, denominator: a_d / d } +} + +test reduce_1() { + and { + (reduce(ratio(80, 200)) == ratio(2, 5))?, + (reduce(ratio(-5, 1)) == ratio(-5, 1))?, + (reduce(ratio(0, 3)) == ratio(0, 1))?, + } +} + +// ## Combining + +// ### Arithmetic operations + +/// Addition: sum of two rational values +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// Some(rational.add(x, y)) == rational.new(17, 12) +/// ``` +pub fn add(left: Rational, right: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + Rational { numerator: a_n * b_d + b_n * a_d, denominator: a_d * b_d } +} + +test add_1() { + add(ratio(2, 3), ratio(3, 4)) == ratio(17, 12) +} + +test add_2() { + add(ratio(-2, 3), ratio(3, 4)) == ratio(1, 12) +} + +/// Division: quotient of two rational values. Returns `None` when the second +/// value is null. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// rational.div(x, y) == rational.new(8, 9) +/// ``` +pub fn div(left: Rational, right: Rational) -> Option { + reciprocal(right) |> option.map(mul(left, _)) +} + +test div_1() { + div(ratio(2, 3), ratio(3, 4)) == new(8, 9) +} + +test div_2() { + div(ratio(2, 3), ratio(-3, 4)) == new(-8, 9) +} + +/// Multiplication: the product of two rational values. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// Some(rational.mul(x, y)) == rational.new(6, 12) +/// ``` +pub fn mul(left: Rational, right: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + Rational { numerator: a_n * b_n, denominator: a_d * b_d } +} + +test mul_1() { + mul(ratio(2, 3), ratio(3, 4)) == ratio(6, 12) +} + +test mul_2() { + mul(ratio(-2, 3), ratio(-3, 4)) == ratio(6, 12) +} + +test mul_3() { + let result = + ratio(2, 5) + |> mul(ratio(1, 8)) + |> mul(ratio(3, 10)) + |> mul(ratio(21, 100)) + |> mul(ratio(3, 5)) + |> mul(ratio(2, 8)) + |> mul(ratio(4, 10)) + |> mul(ratio(22, 100)) + |> reduce + + result == ratio(2079, 50000000) +} + +/// Subtraction: difference of two rational values +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// Some(rational.sub(x, y)) == rational.new(-1, 12) +/// ``` +pub fn sub(left: Rational, right: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + Rational { numerator: a_n * b_d - b_n * a_d, denominator: a_d * b_d } +} + +test sub_1() { + sub(ratio(2, 3), ratio(3, 4)) == ratio(-1, 12) +} + +test sub_2() { + sub(ratio(2, 3), ratio(-3, 4)) == ratio(17, 12) +} + +test sub_3() { + sub(ratio(-2, 3), ratio(3, 4)) == ratio(-17, 12) +} + +// ### Ordering + +/// Compare two rationals for an ordering. This is safe to use even for +/// non-reduced rationals. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// expect Some(z) = rational.new(4, 6) +/// +/// compare(x, y) == Less +/// compare(y, x) == Greater +/// compare(x, x) == Equal +/// compare(x, z) == Equal +/// ``` +pub fn compare(left: Rational, right: Rational) -> Ordering { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + + let l = a_n * b_d + let r = b_n * a_d + + if l < r { + Less + } else if l > r { + Greater + } else { + Equal + } +} + +test compare_1() { + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + expect Some(z) = new(4, 6) + and { + compare(x, y) == Less, + compare(y, x) == Greater, + compare(x, x) == Equal, + compare(x, z) == Equal, + } +} + +/// Comparison of two rational values using a chosen heuristic. For example: +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// rational.compare_with(x, >, y) == False +/// rational.compare_with(y, >, x) == True +/// rational.compare_with(x, >, x) == False +/// rational.compare_with(x, >=, x) == True +/// rational.compare_with(x, ==, x) == True +/// rational.compare_with(x, ==, y) == False +/// ``` +pub fn compare_with( + left: Rational, + with: fn(Int, Int) -> Bool, + right: Rational, +) -> Bool { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + with(a_n * b_d, b_n * a_d) +} + +// TODO: Rewrite tests using binary-operator as first-class functions once aiken-lang/aiken#619 is merged. + +test compare_with_eq() { + let eq = + compare_with(_, fn(l, r) { l == r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + !eq(x, y)? && !eq(y, x)? && eq(x, x)? +} + +test compare_with_neq() { + let neq = + compare_with(_, fn(l, r) { l != r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + neq(x, y)? && neq(y, x)? && !neq(x, x)? +} + +test compare_with_gte() { + let gte = + compare_with(_, fn(l, r) { l >= r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + !gte(x, y)? && gte(y, x)? && gte(x, x)? +} + +test compare_with_gt() { + let gt = + compare_with(_, fn(l, r) { l > r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + !gt(x, y)? && gt(y, x)? && !gt(x, x)? +} + +test compare_with_lte() { + let lte = + compare_with(_, fn(l, r) { l <= r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + lte(x, y)? && !lte(y, x)? && lte(x, x)? +} + +test compare_with_lt() { + let lt = + compare_with(_, fn(l, r) { l < r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + lt(x, y)? && !lt(y, x)? && !lt(x, x)? +} + +// ### Means + +/// Calculate the arithmetic mean between two `Rational` values. +/// +/// ```aiken +/// let x = rational.from_int(0) +/// let y = rational.from_int(1) +/// let z = rational.from_int(2) +/// +/// expect Some(result) = rational.arithmetic_mean([x, y, z]) +/// +/// rational.compare(result, y) == Equal +/// ``` +pub fn arithmetic_mean(self: List) -> Option { + div(list.foldr(self, zero, add), from_int(list.length(self))) +} + +test arithmetic_mean_1() { + let x = ratio(1, 2) + let y = ratio(1, 2) + expect Some(z) = arithmetic_mean([x, y]) + reduce(z) == ratio(1, 2) +} + +test arithmetic_mean_2() { + let x = ratio(1, 1) + let y = ratio(2, 1) + expect Some(z) = arithmetic_mean([x, y]) + reduce(z) == ratio(3, 2) +} + +test arithmetic_mean_3() { + let xs = + [ + ratio(1, 1), + ratio(2, 1), + ratio(3, 1), + ratio(4, 1), + ratio(5, 1), + ratio(6, 1), + ] + expect Some(z) = arithmetic_mean(xs) + reduce(z) == ratio(7, 2) +} + +/// Calculate the geometric mean between two `Rational` values. This returns +/// either the exact result or the smallest integer nearest to the square root +/// for the numerator and denominator. +/// +/// ```aiken +/// expect Some(x) = rational.new(1, 3) +/// expect Some(y) = rational.new(1, 6) +/// +/// rational.geometric_mean(x, y) == rational.new(1, 4) +/// ``` +pub fn geometric_mean(left: Rational, right: Rational) -> Option { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + when math.sqrt(a_n * b_n) is { + Some(numerator) -> + when math.sqrt(a_d * b_d) is { + Some(denominator) -> Some(Rational { numerator, denominator }) + None -> None + } + None -> None + } +} + +test geometric_mean1() { + expect Some(x) = new(1, 2) + expect Some(y) = new(1, 2) + geometric_mean(x, y) == new(1, 2) +} + +test geometric_mean2() { + expect Some(x) = new(-1, 2) + expect Some(y) = new(1, 2) + geometric_mean(x, y) == None +} + +test geometric_mean3() { + expect Some(x) = new(1, 2) + expect Some(y) = new(-1, 2) + geometric_mean(x, y) == None +} + +test geometric_mean4() { + expect Some(x) = new(1, 3) + expect Some(y) = new(1, 6) + geometric_mean(x, y) == new(1, 4) +} + +test geometric_mean5() { + expect Some(x) = new(67, 2500) + expect Some(y) = new(35331, 1000) + expect Some(yi) = reciprocal(y) + geometric_mean(x, yi) == new(258, 9398) +} + +// ## Transforming + +/// Returns the smallest `Int` not less than a given `Rational` +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.ceil(x) == 1 +/// +/// expect Some(y) = rational.new(44, 14) +/// rational.ceil(y) == 4 +/// +/// expect Some(z) = rational.new(-14, 3) +/// rational.ceil(z) == -4 +/// ``` +pub fn ceil(self: Rational) -> Int { + let Rational { numerator, denominator } = self + if builtin.remainder_integer(numerator, denominator) > 0 { + builtin.quotient_integer(numerator, denominator) + 1 + } else { + builtin.quotient_integer(numerator, denominator) + } +} + +test ceil_1() { + and { + (ceil(ratio(13, 5)) == 3)?, + (ceil(ratio(15, 5)) == 3)?, + (ceil(ratio(16, 5)) == 4)?, + (ceil(ratio(-3, 5)) == 0)?, + (ceil(ratio(-5, 5)) == -1)?, + (ceil(ratio(-14, 3)) == -4)?, + (ceil(ratio(-14, 6)) == -2)?, + (ceil(ratio(44, 14)) == 4)?, + } +} + +/// Returns the greatest `Int` no greater than a given `Rational` +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.floor(x) == 0 +/// +/// expect Some(y) = rational.new(44, 14) +/// rational.floor(y) == 3 +/// +/// expect Some(z) = rational.new(-14, 3) +/// rational.floor(z) == -5 +/// ``` +pub fn floor(self: Rational) -> Int { + let Rational { numerator: a_n, denominator: a_d } = self + a_n / a_d +} + +test floor_1() { + and { + (floor(ratio(5, 2)) == 2)?, + (floor(ratio(5, 3)) == 1)?, + (floor(ratio(5, 4)) == 1)?, + (floor(ratio(5, 5)) == 1)?, + (floor(ratio(5, 6)) == 0)?, + (floor(ratio(8, 3)) == 2)?, + (floor(ratio(-14, 3)) == -5)?, + } +} + +/// Computes the rational number x raised to the power y. Returns `None` for +/// invalid exponentiation. +/// +/// ```aiken +/// expect Some(x) = rational.new(50, 2500) +/// rational.reduce(rational.pow(x, 3)) == rational.new(1, 125000) +/// +/// expect Some(x) = rational.new(50, 2500) +/// rational.reduce(rational.pow(x, -3)) == rational.new(125000, 1) +/// ``` +pub fn pow(x: Rational, y: Int) -> Option { + let Rational { numerator: a, denominator: b } = x + + if a == 0 && y <= 0 { + None + } else if y > 0 { + Some(Rational { numerator: math.pow(a, y), denominator: math.pow(b, y) }) + } else if y < 0 { + Some(Rational { numerator: math.pow(b, -y), denominator: math.pow(a, -y) }) + } else { + Some(Rational { numerator: 1, denominator: 1 }) + } +} + +test pow_negative_exponent_non_zero_fraction() { + expect Some(base) = new(50, 2500) + expect Some(calculated_result) = pow(base, -3) + expect Some(expected_result) = new(125000, 1) + reduce(calculated_result) == expected_result +} + +test pow_positive_exponent() { + expect Some(base) = new(50, 2500) + expect Some(calculated_result) = pow(base, 3) + expect Some(expected_result) = new(1, 125000) + reduce(calculated_result) == expected_result +} + +test pow_exponent_zero() { + expect Some(base) = new(50, 2500) + pow(base, 0) == new(1, 1) +} + +test pow_rational_zero_exponent_zero() { + expect Some(base) = new(0, 1) + pow(base, 0) == None +} + +/// Returns the proper fraction of a given `Rational` `r`. That is, a 2-tuple of +/// an `Int` and `Rational` (n, f) such that: +/// +/// - `r = n + f`; +/// - `n` and `f` have the same sign as `r`; +/// - `f` has an absolute value less than 1. +pub fn proper_fraction(self: Rational) -> (Int, Rational) { + let Rational { numerator, denominator } = self + ( + builtin.quotient_integer(numerator, denominator), + Rational { + numerator: builtin.remainder_integer(numerator, denominator), + denominator, + }, + ) +} + +test proper_fraction_1() { + let r = ratio(10, 7) + let (n, f) = proper_fraction(r) + and { + (n == 1)?, + (f == ratio(3, 7))?, + (r == add(from_int(n), f))?, + } +} + +test proper_fraction_2() { + let r = ratio(-10, 7) + let (n, f) = proper_fraction(r) + and { + (n == -1)?, + (f == ratio(-3, 7))?, + (r == add(from_int(n), f))?, + } +} + +test proper_fraction_3() { + let r = ratio(4, 2) + let (n, f) = proper_fraction(r) + and { + (n == 2)?, + (f == ratio(0, 2))?, + (r == add(from_int(n), f))?, + } +} + +/// Round the argument to the nearest whole number. If the argument is +/// equidistant between two values, the greater value is returned (it +/// rounds half towards positive infinity). +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.round(x) == 1 +/// +/// expect Some(y) = rational.new(3, 2) +/// rational.round(y) == 2 +/// +/// expect Some(z) = rational.new(-3, 2) +/// rational.round(z) == -1 +/// ``` +/// +/// > [!CAUTION] +/// > This behaves differently than _Haskell_. If you're coming from `PlutusTx`, beware that in Haskell, rounding on equidistant values depends on the whole number being odd or even. +/// > If you need this behaviour, use [`round_even`](#round_even). +pub fn round(self: Rational) -> Int { + let (n, f) = proper_fraction(self) + + let is_negative = f.numerator < 0 + + when compare(abs(f), ratio(1, 2)) is { + Less -> n + Equal -> + if is_negative { + n + } else { + n + 1 + } + Greater -> + if is_negative { + n - 1 + } else { + n + 1 + } + } +} + +test round_1() { + and { + (round(ratio(10, 7)) == 1)?, + (round(ratio(11, 7)) == 2)?, + (round(ratio(3, 2)) == 2)?, + (round(ratio(5, 2)) == 3)?, + (round(ratio(-3, 2)) == -1)?, + (round(ratio(-2, 3)) == -1)?, + (round(ratio(-10, 7)) == -1)?, + (round(ratio(4, 2)) == 2)?, + } +} + +/// Round the argument to the nearest whole number. If the argument is +/// equidistant between two values, it returns the value that is even (it +/// rounds half to even, also known as 'banker's rounding'). +/// +/// ```aiken +/// expect Some(w) = rational.new(2, 3) +/// rational.round_even(w) == 1 +/// +/// expect Some(x) = rational.new(3, 2) +/// rational.round_even(x) == 2 +/// +/// expect Some(y) = rational.new(5, 2) +/// rational.round_even(y) == 2 +/// +/// expect Some(y) = rational.new(-3, 2) +/// rational.round_even(y) == -2 +/// ``` +pub fn round_even(self: Rational) -> Int { + let (n, f) = proper_fraction(self) + + let m = + when compare(f, ratio(0, 1)) is { + Less -> -1 + _ -> 1 + } + + let is_even = n % 2 == 0 + + when compare(abs(f), ratio(1, 2)) is { + Less -> n + Equal -> + if is_even { + n + } else { + n + m + } + Greater -> n + m + } +} + +test round_even_1() { + and { + (round_even(ratio(10, 7)) == 1)?, + (round_even(ratio(11, 7)) == 2)?, + (round_even(ratio(3, 2)) == 2)?, + (round_even(ratio(5, 2)) == 2)?, + (round_even(ratio(-3, 2)) == -2)?, + (round_even(ratio(-2, 3)) == -1)?, + (round_even(ratio(-10, 7)) == -1)?, + (round_even(ratio(4, 2)) == 2)?, + } +} + +/// Returns the nearest `Int` between zero and a given `Rational`. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.truncate(x) == 0 +/// +/// expect Some(y) = rational.new(44, 14) +/// rational.truncate(y) == 3 +/// +/// expect Some(z) = rational.new(-14, 3) +/// rational.truncate(z) == -4 +/// ``` +pub fn truncate(self: Rational) -> Int { + let Rational { numerator: a_n, denominator: a_d } = self + builtin.quotient_integer(a_n, a_d) +} + +test truncate_1() { + and { + (truncate(ratio(5, 2)) == 2)?, + (truncate(ratio(5, 3)) == 1)?, + (truncate(ratio(5, 4)) == 1)?, + (truncate(ratio(5, 5)) == 1)?, + (truncate(ratio(5, 6)) == 0)?, + (truncate(ratio(8, 3)) == 2)?, + (truncate(ratio(-14, 3)) == -4)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.tests.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.tests.ak new file mode 100644 index 00000000..ab8cbc17 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.tests.ak @@ -0,0 +1,65 @@ +use aiken/fuzz.{both, either, map} +use aiken/math/rational.{Rational, new, pow} + +const any_positive_rational: Fuzzer = + either( + map( + both(fuzz.int_at_least(1), fuzz.int_at_least(1)), + fn((num, den)) { + expect Some(new_fraction) = new(num, den) + new_fraction + }, + ), + map( + both(fuzz.int_at_most(-1), fuzz.int_at_most(-1)), + fn((num, den)) { + expect Some(new_fraction) = new(num, den) + new_fraction + }, + ), + ) + +const any_negative_rational: Fuzzer = + either( + map( + both(fuzz.int_at_most(-1), fuzz.int_at_least(1)), + fn((num, den)) { + expect Some(new_fraction) = new(num, den) + new_fraction + }, + ), + map( + both(fuzz.int_at_least(1), fuzz.int_at_most(-1)), + fn((num, den)) { + expect Some(new_fraction) = new(num, den) + new_fraction + }, + ), + ) + +const any_non_zero_rational: Fuzzer = + either(any_negative_rational, any_positive_rational) + +test prop_power_of_zero_returns_one(rational via any_non_zero_rational) { + expect Some(calculated_result) = pow(rational, 0) + expect Some(expected_result) = new(1, 1) + calculated_result == expected_result +} + +test prop_power_of_one_returns_same_fraction(rational via any_non_zero_rational) { + expect Some(calculated_result) = pow(rational, 1) + calculated_result == rational +} + +test prop_power_numerator_zero_exponent_negative_returns_none( + (denominator, exponent) via both(fuzz.int_at_least(1), fuzz.int_at_most(-1)), +) { + expect Some(fraction) = new(0, denominator) + expect None = pow(fraction, exponent) +} + +test prop_power_unit_fraction_is_immutable(exponent via fuzz.int()) { + expect Some(unit) = new(1, 1) + expect Some(calculated_result) = pow(unit, exponent) + calculated_result == unit +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/option.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/option.ak new file mode 100644 index 00000000..cf5ef7dc --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/option.ak @@ -0,0 +1,312 @@ +//// A type to capture optional results; useful for handling errors. +//// +//// Note that the `Option` type and its constructors are readily available in Aiken. They are part of the [Prelude](https://aiken-lang.github.io/prelude/aiken.html#Option) module imported by default in every module. + +// ## Inspecting + +/// Asserts whether an option is `None`. +pub fn is_none(self: Option) -> Bool { + when self is { + Some(_) -> False + _ -> True + } +} + +test is_none_1() { + is_none(Some(0)) == False +} + +test is_none_2() { + is_none(None) == True +} + +/// Asserts whether an option is `Some`, irrespective of the value it contains. +pub fn is_some(self: Option) -> Bool { + when self is { + Some(_) -> True + _ -> False + } +} + +test is_some_1() { + is_some(Some(0)) == True +} + +test is_some_2() { + is_some(None) == False +} + +// ## Combining + +/// Chain together many computations that may fail. +/// +/// ```aiken +/// self +/// |> dict.get(policy_id) +/// |> option.and_then(dict.get(_, asset_name)) +/// |> option.or_else(0) +/// ``` +pub fn and_then( + self: Option, + then: fn(a) -> Option, +) -> Option { + when self is { + None -> None + Some(a) -> then(a) + } +} + +fn try_decrement(n: Int) -> Option { + if n > 0 { + Some(n - 1) + } else { + None + } +} + +test and_then_1() { + let result = + None + |> and_then(try_decrement) + result == None +} + +test and_then_2() { + let result = + Some(14) + |> and_then(try_decrement) + result == Some(13) +} + +test and_then_3() { + let result = + Some(0) + |> and_then(try_decrement) + result == None +} + +/// Picks the first element which is not None. If there's no such element, return None. +/// +/// ```aiken +/// option.choice([]) == None +/// option.choice([Some(14), Some(42)]) == Some(14) +/// option.choice([None, Some(42)]) == Some(42) +/// option.choice([None, None]) == None +/// ``` +pub fn choice(self: List>) -> Option { + when self is { + [] -> None + [head, ..others] -> + when head is { + None -> choice(others) + _ -> head + } + } +} + +test choice_1() { + Some(1) == choice([Some(1), Some(2)]) +} + +test choice_2() { + None == choice([]) +} + +test choice_3() { + Some(1) == choice([None, Some(1)]) +} + +/// Converts from `Option>` to `Option`. +/// +/// ```aiken +/// option.flatten(Some(Some(42))) == Some(42) +/// option.flatten(Some(None)) == None +/// option.flatten(None) == None +/// ``` +/// +/// Flattening only removes one level of nesting at a time: +/// +/// ```aiken +/// flatten(Some(Some(Some(42)))) == Some(Some(42)) +/// Some(Some(Some(42))) |> flatten |> flatten == Some(42) +/// ``` +pub fn flatten(opt: Option>) -> Option { + when opt is { + Some(inner) -> inner + None -> None + } +} + +test flatten_1() { + let x: Option> = Some(Some(6)) + Some(6) == flatten(x) +} + +test flatten_2() { + let x: Option> = Some(None) + None == flatten(x) +} + +test flatten_3() { + let x: Option> = None + None == flatten(x) +} + +test flatten_4() { + let x: Option>> = Some(Some(Some(6))) + + let result = + x + |> flatten + |> flatten + + Some(6) == result +} + +/// Apply a function to the inner value of an [`Option`](#option) +/// +/// ```aiken +/// option.map(None, fn(n) { n * 2 }) == None +/// option.map(Some(14), fn(n) { n * 2 }) == Some(28) +/// ``` +pub fn map(self: Option, with: fn(a) -> result) -> Option { + when self is { + None -> None + Some(a) -> Some(with(a)) + } +} + +test map_1() { + map(None, fn(_) { Void }) == None +} + +test map_2() { + map(Some(14), fn(n) { n + 1 }) == Some(15) +} + +/// Combine two [`Option`](#option) together. +/// +/// ```aiken +/// type Foo { +/// Foo(Int, Int) +/// } +/// +/// option.map2(Some(14), Some(42), Foo) == Some(Foo(14, 42)) +/// option.map2(None, Some(42), Foo) == None +/// option.map2(Some(14), None, Foo) == None +/// ``` +pub fn map2( + opt_a: Option, + opt_b: Option, + with: fn(a, b) -> result, +) -> Option { + when opt_a is { + None -> None + Some(a) -> + when opt_b is { + None -> None + Some(b) -> Some(with(a, b)) + } + } +} + +test map2_1() { + map2(None, Some(42), fn(_, _) { 14 }) == None +} + +test map2_2() { + map2(Some(42), None, fn(_, _) { 14 }) == None +} + +test map2_3() { + map2(Some(14), Some(42), fn(a, b) { (a, b) }) == Some((14, 42)) +} + +/// Combine three [`Option`](#option) together. +/// +/// ```aiken +/// type Foo { +/// Foo(Int, Int, Int) +/// } +/// +/// option.map3(Some(14), Some(42), Some(1337), Foo) == Some(Foo(14, 42, 1337)) +/// option.map3(None, Some(42), Some(1337), Foo) == None +/// option.map3(Some(14), None, None, Foo) == None +/// ``` +pub fn map3( + opt_a: Option, + opt_b: Option, + opt_c: Option, + with: fn(a, b, c) -> result, +) -> Option { + when opt_a is { + None -> None + Some(a) -> + when opt_b is { + None -> None + Some(b) -> + when opt_c is { + None -> None + Some(c) -> Some(with(a, b, c)) + } + } + } +} + +test map3_1() { + map3(None, Some(42), None, fn(_, _, _) { 14 }) == None +} + +test map3_2() { + map3(Some(42), None, None, fn(_, _, _) { 14 }) == None +} + +test map3_3() { + map3(Some(14), Some(42), Some(1337), fn(a, b, c) { c - a + b }) == Some(1365) +} + +/// Like [`or_else`](#or_else) but allows returning an `Option`. +/// This is effectively mapping the error branch. +/// +/// ```aiken +/// option.or_try(None, fn(_) { Some("aiken") }) == Some("aiken") +/// option.or_try(Some(42), fn(_) { Some(14) }) == Some(42) +/// option.or_try(None, fn (_) { fail }) => 💥 +/// ``` +pub fn or_try(self: Option, compute_default: fn() -> Option) -> Option { + when self is { + None -> compute_default() + _ -> self + } +} + +test or_try_1() { + or_try(None, fn() { Some("aiken") }) == Some("aiken") +} + +test or_try_2() { + or_try(Some(42), fn() { fail }) == Some(42) +} + +// ## Transforming + +/// Provide a default value, turning an optional value into a normal value. +/// +/// ```aiken +/// option.or_else(None, "aiken") == "aiken" +/// option.or_else(Some(42), 14) == 42 +/// ``` +pub fn or_else(self: Option, default: a) -> a { + when self is { + None -> default + Some(a) -> a + } +} + +test or_else_1() { + or_else(None, "aiken") == "aiken" +} + +test or_else_2() { + or_else(Some(42), 14) == 42 +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/primitive/bytearray.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/primitive/bytearray.ak new file mode 100644 index 00000000..d2f125f5 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/primitive/bytearray.ak @@ -0,0 +1,668 @@ +use aiken/builtin +use aiken/math +use aiken/option + +pub type Byte = + Int + +// ## Constructing + +/// Encode an integer value as a Big-Endian (most-significant bytes first) `ByteArray`. +/// The size is the expected size in number of bytes. +/// +/// > [!IMPORTANT] +/// > This function fails (i.e. halts the program) if the value cannot fit in the given size. When the +/// > size is _too large_, the array is left-padded with zeroes. +/// +/// ```aiken +/// bytearray.from_int_big_endian(1_000_000, 3) == #"0f4240" +/// bytearray.from_int_big_endian(1_000_000, 5) == #"00000f4240" +/// bytearray.from_int_big_endian(0, 8) == #"0000000000000000" +/// bytearray.from_int_big_endian(1_000_000, 1) => 💥 +/// ``` +pub fn from_int_big_endian(self: Int, size: Int) -> ByteArray { + builtin.integer_to_bytearray(True, size, self) +} + +test from_int_big_endian_1() { + from_int_big_endian(1_000_000, 3) == #"0f4240" +} + +test from_int_big_endian_2() { + from_int_big_endian(1_000_000, 5) == #"00000f4240" +} + +test from_int_big_endian_3() { + from_int_big_endian(0, 8) == #"0000000000000000" +} + +test from_int_big_endian_4() fail { + from_int_big_endian(1_000_000, 1) == #"40" +} + +/// Encode an integer value as a Little-Endian (least-significant bytes first) `ByteArray`. +/// The size is the expected size in number of bytes. +/// +/// > [!IMPORTANT] +/// > This function fails (i.e. halts the program) if the value cannot fit in the given size. When the +/// > size is _too large_, the array is right-padded with zeroes. +/// +/// ```aiken +/// bytearray.from_int_little_endian(1_000_000, 3) == #"40420f" +/// bytearray.from_int_little_endian(1_000_000, 5) == #"40420f0000" +/// bytearray.from_int_little_endian(0, 8) == #"0000000000000000" +/// bytearray.from_int_little_endian(1_000_000, 1) => 💥 +/// ``` +pub fn from_int_little_endian(self: Int, size: Int) -> ByteArray { + builtin.integer_to_bytearray(False, size, self) +} + +test from_int_little_endian_1() { + from_int_little_endian(1_000_000, 3) == #"40420f" +} + +test from_int_little_endian_2() { + from_int_little_endian(1_000_000, 5) == #"40420f0000" +} + +test from_int_little_endian_3() { + from_int_little_endian(0, 8) == #"0000000000000000" +} + +test from_int_little_endian_4() fail { + from_int_little_endian(1_000_000, 1) == #"40" +} + +/// Convert a `String` into a `ByteArray`. +/// +/// ```aiken +/// bytearray.from_string(@"ABC") == #"414243" +/// ``` +pub fn from_string(str: String) -> ByteArray { + builtin.encode_utf8(str) +} + +test from_string_1() { + from_string(@"") == "" +} + +test from_string_2() { + from_string(@"ABC") == #"414243" +} + +/// Add a byte element in front of a `ByteArray`. When the given byte is +/// greater than 255, it wraps-around. **PlutusV2 behavior** So 256 is mapped to 0, 257 to 1, and so +/// forth. +/// In PlutusV3 this will error instead of wrapping around. +/// +/// ```aiken +/// bytearray.push(#"", 0) == #"00" +/// bytearray.push(#"0203", 1) == #"010203" +/// bytearray.push(#"0203", 257) == #"010203" +/// ``` +pub fn push(self: ByteArray, byte: Byte) -> ByteArray { + builtin.cons_bytearray(byte, self) +} + +test push_1() { + push(#[], 0) == #[0] +} + +test push_2() { + push(#[2, 3], 1) == #[1, 2, 3] +} + +test push_3() fail { + let x = 257 + push(#[2, 3], x) == #[1, 2, 3] +} + +// ## Inspecting + +/// Get the `Byte` at the given index, or crash. +/// +/// > [!WARNING] +/// > This functions fails (i.e. halts the program) if there's no byte at the given index. +pub fn at(self: ByteArray, index: Int) -> Byte { + builtin.index_bytearray(self, index) +} + +/// Search the start and end positions of a sub-array in a `ByteArray`. +/// +/// ```aiken +/// bytearray.index_of("Hello, World!", "World") == Some((7, 11)) +/// bytearray.index_of("Hello, World!", "foo") == None +/// bytearray.index_of("Hello, World!", "!") == Some((12, 12)) +/// bytearray.index_of("Hello, World!", "o") == Some((4, 4)) +/// bytearray.index_of("Hello, World!", "Hello, World!") == Some((0, 12)) +/// ``` +pub fn index_of(self: ByteArray, bytes: ByteArray) -> Option<(Int, Int)> { + let offset = length(bytes) + + do_index_of(self, bytes, 0, offset, length(self)) + |> option.map(fn(ix) { (ix, ix + offset - 1) }) +} + +fn do_index_of( + self: ByteArray, + bytes: ByteArray, + cursor: Int, + offset: Int, + size: Int, +) -> Option { + if cursor + offset > size { + None + } else { + if builtin.slice_bytearray(cursor, offset, self) == bytes { + Some(cursor) + } else { + do_index_of(self, bytes, cursor + 1, offset, size) + } + } +} + +test index_of_1() { + index_of("Hello, World!", "World") == Some((7, 11)) +} + +test index_of_2() { + index_of("Hello, World!", "foo") == None +} + +test index_of_3() { + index_of("Hello, World!", "!") == Some((12, 12)) +} + +test index_of_4() { + index_of("Hello, World!", "o") == Some((4, 4)) +} + +test index_of_5() { + index_of("Hello, World!", "Hello, World!") == Some((0, 12)) +} + +/// Returns `True` when the given `ByteArray` is empty. +/// +/// ```aiken +/// bytearray.is_empty(#"") == True +/// bytearray.is_empty(#"00ff") == False +/// ``` +pub fn is_empty(self: ByteArray) -> Bool { + builtin.length_of_bytearray(self) == 0 +} + +test is_empty_1() { + is_empty(#"") == True +} + +test is_empty_2() { + is_empty(#"01") == False +} + +/// Returns the number of bytes in a `ByteArray`. +/// +/// ```aiken +/// bytearray.length(#[1, 2, 3]) == 3 +/// ``` +pub fn length(self: ByteArray) -> Int { + builtin.length_of_bytearray(self) +} + +test length_1() { + length(#"") == 0 +} + +test length_2() { + length(#"010203") == 3 +} + +/// Checks whether a bit (Most-Significant-Bit first) is set in the given 'ByteArray'. +/// +/// For example, consider the following bytearray: `#"8b765f"`. It can also be written as the +/// following bits sequence: +/// +/// `8` | `b` | `7` | `6` | `5` | `f` +/// --- | --- | --- | --- | --- | --- +/// `1000` | `1011` | `0111` | `0110` | `0101` | `1111` +/// +/// And thus, we have: +/// +/// ```aiken +/// test_bit(#"8b765f", 0) == True +/// test_bit(#"8b765f", 1) == False +/// test_bit(#"8b765f", 2) == False +/// test_bit(#"8b765f", 3) == False +/// test_bit(#"8b765f", 7) == True +/// test_bit(#"8b765f", 8) == False +/// test_bit(#"8b765f", 20) == True +/// test_bit(#"8b765f", 21) == True +/// test_bit(#"8b765f", 22) == True +/// test_bit(#"8b765f", 23) == True +/// ``` +pub fn test_bit(self: ByteArray, ix: Int) -> Bool { + builtin.less_than_equals_bytearray( + #[128], + builtin.cons_bytearray( + builtin.index_bytearray(self, ix / 8) * math.pow2(ix % 8) % 256, + "", + ), + ) +} + +test test_bit_0() { + test_bit(#"8b765f", 0) +} + +test test_bit_1() { + !test_bit(#"8b765f", 1) +} + +test test_bit_2() { + !test_bit(#"8b765f", 2) +} + +test test_bit_3() { + !test_bit(#"8b765f", 3) +} + +test test_bit_7() { + test_bit(#"8b765f", 7) +} + +test test_bit_8() { + !test_bit(#"8b765f", 8) +} + +test test_bit_20_21_22_23() { + and { + test_bit(#"8b765f", 20), + test_bit(#"8b765f", 21), + test_bit(#"8b765f", 22), + test_bit(#"8b765f", 23), + } +} + +// ## Modifying + +/// Returns the suffix of a `ByteArray` after `n` elements. +/// +/// ```aiken +/// bytearray.drop(#[1, 2, 3], n: 2) == #[3] +/// ``` +pub fn drop(self: ByteArray, n: Int) -> ByteArray { + builtin.slice_bytearray(n, builtin.length_of_bytearray(self) - n, self) +} + +test drop_1() { + let x = #"01020304050607" + drop(x, 2) == #"0304050607" +} + +test drop_2() { + let x = #"01020304050607" + drop(x, 0) == x +} + +test drop_3() { + let x = #"01" + drop(x, 1) == #"" +} + +test drop_4() { + let x = #"" + drop(x, 2) == #"" +} + +/// Extract a `ByteArray` as a slice of another `ByteArray`. +/// +/// Indexes are 0-based and inclusive. +/// +/// ```aiken +/// bytearray.slice(#[0, 1, 2, 3, 4, 5, 6], start: 1, end: 3) == #[1, 2, 3] +/// ``` +pub fn slice(self: ByteArray, start: Int, end: Int) -> ByteArray { + builtin.slice_bytearray(start, end - start + 1, self) +} + +test slice_1() { + slice(#"", 1, 2) == #"" +} + +test slice_2() { + slice(#"010203", 1, 2) == #"0203" +} + +test slice_3() { + slice(#"010203", 0, 42) == #"010203" +} + +test slice_4() { + slice(#[0, 1, 2, 3, 4], 0, 3) == #[0, 1, 2, 3] +} + +test slice_5() { + slice(#[0, 1, 2, 3, 4], 1, 2) == #[1, 2] +} + +/// Returns the n-length prefix of a `ByteArray`. +/// +/// ```aiken +/// bytearray.take(#[1, 2, 3], n: 2) == #[1, 2] +/// ``` +pub fn take(self: ByteArray, n: Int) -> ByteArray { + builtin.slice_bytearray(0, n, self) +} + +test take_1() { + let x = #"01020304050607" + take(x, 2) == #"0102" +} + +test take_2() { + let x = #"01020304050607" + take(x, 0) == #"" +} + +test take_3() { + let x = #"01" + take(x, 1) == x +} + +test take_4() { + let x = #"010203" + take(x, 0) == #"" +} + +// ## Combining + +/// Combine two `ByteArray` together. +/// +/// ```aiken +/// bytearray.concat(left: #[1, 2, 3], right: #[4, 5, 6]) == #[1, 2, 3, 4, 5, 6] +/// ``` +pub fn concat(left: ByteArray, right: ByteArray) -> ByteArray { + builtin.append_bytearray(left, right) +} + +test concat_1() { + concat(#"", #"") == #"" +} + +test concat_2() { + concat(#"", #"01") == #"01" +} + +test concat_3() { + concat(#"0102", #"") == #"0102" +} + +test concat_4() { + concat(#"0102", #"0304") == #"01020304" +} + +/// Compare two bytearrays lexicographically. +/// +/// ```aiken +/// bytearray.compare(#"00", #"FF") == Less +/// bytearray.compare(#"42", #"42") == Equal +/// bytearray.compare(#"FF", #"00") == Greater +/// ``` +pub fn compare(left: ByteArray, right: ByteArray) -> Ordering { + if builtin.less_than_bytearray(left, right) { + Less + } else if builtin.equals_bytearray(left, right) { + Equal + } else { + Greater + } +} + +// ## Transforming + +/// Left-fold over bytes of a [`ByteArray`](https://aiken-lang.github.io/prelude/aiken.html#ByteArray). Note that every byte given to the callback function is comprised between 0 and 255. +/// +/// ```aiken +/// bytearray.foldl(#"acab", 0, fn(byte, acc) { acc * 256 + byte }) == 44203 +/// bytearray.foldl(#[1, 2, 3], #"", flip(bytearray.push)) == #[3, 2, 1] +/// ``` +pub fn foldl( + self: ByteArray, + zero: result, + with: fn(Int, result) -> result, +) -> result { + do_foldl(self, zero, builtin.length_of_bytearray(self), 0, with) +} + +fn do_foldl( + self: ByteArray, + zero: result, + len: Int, + cursor: Int, + with: fn(Int, result) -> result, +) -> result { + if cursor == len { + zero + } else { + do_foldl( + self, + with(builtin.index_bytearray(self, cursor), zero), + len, + cursor + 1, + with, + ) + } +} + +test foldl_1() { + foldl(#[], 42, fn(byte, acc) { byte + acc }) == 42 +} + +test foldl_2() { + foldl(#"acab", 0, fn(byte, acc) { acc * 256 + byte }) == 44203 +} + +test foldl_3() { + foldl( + #"356cf088720a169dae0ce0bb1df8588944389fa43322f0d6ef4ed8c069bfd405", + 0, + fn(byte, acc) { acc * 256 + byte }, + ) == 24165060555594911913195642527692216679757672038384202527929620681761931383813 +} + +test foldl_4() { + foldl(#[1, 2, 3, 4, 5], #"", flip(push)) == #[5, 4, 3, 2, 1] +} + +/// Right-fold over bytes of a [`ByteArray`](https://aiken-lang.github.io/prelude/aiken.html#ByteArray). Note that every byte given to the callback function is comprised between 0 and 255. +/// +/// ```aiken +/// bytearray.foldr(#"acab", 0, fn(byte, acc) { acc * 256 + byte }) == 43948 +/// bytearray.foldl(#[1, 2, 3], #"", flip(bytearray.push)) == #[1, 2, 3] +/// ``` +pub fn foldr( + self: ByteArray, + zero: result, + with: fn(Int, result) -> result, +) -> result { + do_foldr(self, zero, builtin.length_of_bytearray(self) - 1, with) +} + +fn do_foldr( + self: ByteArray, + zero: result, + cursor: Int, + with: fn(Int, result) -> result, +) -> result { + if cursor < 0 { + zero + } else { + do_foldr( + self, + with(builtin.index_bytearray(self, cursor), zero), + cursor - 1, + with, + ) + } +} + +test foldr_1() { + foldr(#[], 42, fn(byte, acc) { byte + acc }) == 42 +} + +test foldr_2() { + foldr(#"acab", 0, fn(byte, acc) { acc * 256 + byte }) == 43948 +} + +test foldr_3() { + foldr(#[1, 2, 3, 4, 5], #"", flip(push)) == #[1, 2, 3, 4, 5] +} + +/// Reduce bytes in a ByteArray from left to right using the accumulator as left operand. +/// Said differently, this is [`foldl`](#foldl) with callback arguments swapped. +/// +/// ```aiken +/// bytearray.reduce(#[1,2,3], #[], bytearray.push) == #[3, 2, 1] +/// ``` +pub fn reduce( + self: ByteArray, + zero: result, + with: fn(result, Int) -> result, +) -> result { + foldl(self, zero, flip(with)) +} + +test reduce_1() { + reduce(#[], #[], push) == #[] +} + +test reduce_2() { + reduce(#[1, 2, 3], #[], push) == #[3, 2, 1] +} + +/// Interpret a Big-Endian (most-significant bytes first) `ByteArray` as an `Int`. +/// +/// ```aiken +/// bytearray.to_int_big_endian(#"0f4240") == 1_000_000 +/// bytearray.to_int_big_endian(#"00000f4240") == 1_000_000 +/// bytearray.to_int_big_endian(#"0000000000000000") == 0 +/// ``` +pub fn to_int_big_endian(self: ByteArray) -> Int { + builtin.bytearray_to_integer(True, self) +} + +test to_int_big_endian_1() { + to_int_big_endian(#"0f4240") == 1_000_000 +} + +test to_int_big_endian_2() { + to_int_big_endian(#"00000f4240") == 1_000_000 +} + +test to_int_big_endian_3() { + to_int_big_endian(#"0000000000000000") == 0 +} + +/// Interpret a Little-Endian (least-significant bytes first) `ByteArray` as an `Int`. +/// +/// ```aiken +/// bytearray.to_int_big_endian(#"40420f") == 1_000_000 +/// bytearray.to_int_big_endian(#"40420f0000") == 1_000_000 +/// bytearray.to_int_big_endian(#"0000000000000000") == 0 +/// ``` +pub fn to_int_little_endian(self: ByteArray) -> Int { + builtin.bytearray_to_integer(False, self) +} + +test to_int_little_endian_1() { + to_int_little_endian(#"40420f") == 1_000_000 +} + +test to_int_little_endian_2() { + to_int_little_endian(#"40420f0000") == 1_000_000 +} + +test to_int_little_endian_3() { + to_int_little_endian(#"0000000000000000") == 0 +} + +/// Convert a `ByteArray` into a `String`. +/// +/// > [!WARNING] +/// > This functions fails (i.e. halts the program) if the underlying `ByteArray` isn't UTF-8-encoded. In particular, you cannot convert arbitrary hash digests using this function. +/// > +/// > For converting arbitrary `ByteArray`s, use [bytearray.to_hex](#to_hex). +/// +/// ```aiken +/// bytearray.to_string(#"414243") == "ABC" +/// bytearray.to_string(some_hash) => 💥 +/// ``` +pub fn to_string(self: ByteArray) -> String { + builtin.decode_utf8(self) +} + +test to_string_1() { + to_string("") == @"" +} + +test to_string_2() { + to_string("ABC") == @"ABC" +} + +/// Encode a `ByteArray` as a hexidecimal `String`. +/// +/// ```aiken +/// bytearray.to_hex("Hello world!") == @"48656c6c6f20776f726c6421" +/// ``` +pub fn to_hex(self: ByteArray) -> String { + self + |> encode_base16(builtin.length_of_bytearray(self) - 1, "") + |> builtin.decode_utf8 +} + +test to_hex_1() { + to_hex("Hello world!") == @"48656C6C6F20776F726C6421" +} + +test to_hex_2() { + to_hex("The quick brown fox jumps over the lazy dog") == @"54686520717569636B2062726F776E20666F78206A756D7073206F76657220746865206C617A7920646F67" +} + +/// Checks whether a `ByteArray` starts with a given prefix. +/// +/// ```aiken +/// bytearray.starts_with("Hello, World!", prefix: "Hello") == True +/// bytearray.starts_with("", prefix: "") == True +/// bytearray.starts_with("Hello", prefix: "Hello, World!") == False +/// ``` +pub fn starts_with(self: ByteArray, prefix: ByteArray) -> Bool { + let prefix_length = length(prefix) + if length(self) < prefix_length { + False + } else { + take(self, prefix_length) == prefix + } +} + +test starts_with_1() { + starts_with("", "") +} + +test starts_with_2() { + starts_with("Hello, World!", "Hello, World!") +} + +test starts_with_3() { + !starts_with("Hello, World!", "hello") +} + +test starts_with_4() { + !starts_with("", "World") +} + +test starts_with_5() { + starts_with("Hello, World", "Hello") +} + +test starts_with_6() { + !starts_with("foo", "foo_") +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/primitive/int.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/primitive/int.ak new file mode 100644 index 00000000..217749e9 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/primitive/int.ak @@ -0,0 +1,156 @@ +use aiken/builtin.{bytearray_to_integer, decode_utf8} +use aiken/math +use aiken/option +use aiken/primitive/bytearray + +// ## Combining + +/// Compare two integers. +/// +/// ```aiken +/// int.compare(14, 42) == Less +/// int.compare(14, 14) == Equal +/// int.compare(42, 14) == Greater +/// ``` +pub fn compare(left: Int, right: Int) -> Ordering { + if left < right { + Less + } else if left > right { + Greater + } else { + Equal + } +} + +// ## Transforming + +/// Interpret a Big-Endian (most-significant bytes first) `ByteArray` as an `Int`. +/// +/// ```aiken +/// int.from_bytearray_big_endian(#"0f4240") == 1_000_000 +/// int.from_bytearray_big_endian(#"00000f4240") == 1_000_000 +/// int.from_bytearray_big_endian(#"0000000000000000") == 0 +/// ``` +pub fn from_bytearray_big_endian(self: ByteArray) -> Int { + bytearray_to_integer(True, self) +} + +test from_bytearray_big_endian_1() { + from_bytearray_big_endian(#"0f4240") == 1_000_000 +} + +test from_bytearray_big_endian_2() { + from_bytearray_big_endian(#"00000f4240") == 1_000_000 +} + +test from_bytearray_big_endian_3() { + from_bytearray_big_endian(#"0000000000000000") == 0 +} + +/// Interpret a Little-Endian (least-significant bytes first) `ByteArray` as an `Int`. +/// +/// ```aiken +/// int.from_bytearray_big_endian(#"40420f") == 1_000_000 +/// int.from_bytearray_big_endian(#"40420f0000") == 1_000_000 +/// int.from_bytearray_big_endian(#"0000000000000000") == 0 +/// ``` +pub fn from_bytearray_little_endian(self: ByteArray) -> Int { + bytearray_to_integer(False, self) +} + +test from_bytearray_little_endian_1() { + from_bytearray_little_endian(#"40420f") == 1_000_000 +} + +test from_bytearray_little_endian_2() { + from_bytearray_little_endian(#"40420f0000") == 1_000_000 +} + +test from_bytearray_little_endian_3() { + from_bytearray_little_endian(#"0000000000000000") == 0 +} + +/// Parse an integer from a utf-8 encoded `ByteArray`, when possible. +/// +/// ```aiken +/// int.from_utf8("14") == Some(14) +/// int.from_utf8("-42") == Some(-42) +/// int.from_utf8("007") == Some(7) +/// int.from_utf8("foo") == None +/// int.from_utf8("1.0") == None +/// int.from_utf8("1-2") == None +/// ``` +pub fn from_utf8(bytes: ByteArray) -> Option { + bytes + |> bytearray.foldr( + Some((0, 0)), + fn(byte, st) { + when st is { + None -> None + Some((n, e)) -> + if byte < 48 || byte > 57 { + if byte == 45 { + Some((-n, 0)) + } else { + None + } + } else if n < 0 { + None + } else { + let digit = byte - 48 + Some((n + digit * math.pow(10, e), e + 1)) + } + } + }, + ) + |> option.map(fn(tuple) { tuple.1st }) +} + +test from_utf8_1() { + from_utf8("0017") == Some(17) +} + +test from_utf8_2() { + from_utf8("42") == Some(42) +} + +test from_utf8_3() { + from_utf8("1337") == Some(1337) +} + +test from_utf8_4() { + from_utf8("-14") == Some(-14) +} + +test from_utf8_5() { + from_utf8("foo") == None +} + +test from_utf8_6() { + from_utf8("1-2") == None +} + +/// Convert an `Int` to its `String` representation. +/// +/// ```aiken +/// int.to_string(42) == @"42" +/// ``` +pub fn to_string(n: Int) -> String { + diagnostic(n, "") |> decode_utf8 +} + +test to_string_1() { + to_string(0) == @"0" +} + +test to_string_2() { + to_string(5) == @"5" +} + +test to_string_3() { + to_string(42) == @"42" +} + +test to_string_4() { + to_string(200) == @"200" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/primitive/string.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/primitive/string.ak new file mode 100644 index 00000000..35fa5567 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/aiken/primitive/string.ak @@ -0,0 +1,139 @@ +use aiken/builtin.{ + append_bytearray, append_string, decode_utf8, encode_utf8, length_of_bytearray, +} + +// ## Constructing + +/// Convert a `ByteArray` into a `String` +/// +/// > [!WARNING] +/// > This functions fails if the underlying `ByteArray` isn't UTF-8-encoded. In particular, you cannot convert arbitrary hash digests using this function. +/// > +/// > For converting arbitrary `ByteArray`s, use [bytearray.to_hex](./bytearray.html#to_hex). +/// +/// ```aiken +/// string.from_bytearray("foo") == @"foo" +/// string.from_bytearray(#"666f6f") == @"foo" +/// string.from_bytearray(some_hash) -> fail +/// ``` +pub fn from_bytearray(bytes: ByteArray) -> String { + decode_utf8(bytes) +} + +test from_bytearray_1() { + from_bytearray(#[]) == @"" +} + +test from_bytearray_2() { + from_bytearray(#[65, 66, 67]) == @"ABC" +} + +test from_bytearray_3() { + from_bytearray("ABC") == @"ABC" +} + +/// Convert an `Int` to its `String` representation. +/// +/// ```aiken +/// string.from_int(42) == @"42" +/// ``` +pub fn from_int(n: Int) -> String { + diagnostic(n, "") |> decode_utf8 +} + +test from_int_1() { + from_int(0) == @"0" +} + +test from_int_2() { + from_int(5) == @"5" +} + +test from_int_3() { + from_int(42) == @"42" +} + +test from_int_4() { + from_int(200) == @"200" +} + +// ## Combining + +/// Combine two `String` together. +/// +/// ```aiken +/// string.concat(left: @"Hello", right: @", World!") == @"Hello, World!" +/// ``` +pub fn concat(left: String, right: String) -> String { + append_string(left, right) +} + +test concat_1() { + concat(@"", @"") == @"" +} + +test concat_2() { + concat(@"", @"foo") == concat(@"foo", @"") +} + +test concat_3() { + concat(left: @"Hello", right: @", World!") == @"Hello, World!" +} + +/// Join a list of strings, separated by a given _delimiter_. +/// +/// ```aiken +/// string.join([], @"+") == @"" +/// string.join([@"a", @"b", @"c"], @",") == @"a,b,c" +/// ``` +pub fn join(list: List, delimiter: String) -> String { + do_join(list, encode_utf8(delimiter), #"") + |> decode_utf8 +} + +fn do_join(xs, delimiter, bytes) { + when xs is { + [] -> bytes + [x, ..rest] -> + do_join( + rest, + delimiter, + if length_of_bytearray(bytes) == 0 { + encode_utf8(x) + } else { + append_bytearray(bytes, append_bytearray(delimiter, encode_utf8(x))) + }, + ) + } +} + +test join_1() { + join([], @",") == @"" +} + +test join_2() { + join([@"a", @"b", @"c"], @",") == @"a,b,c" +} + +// ## Transforming + +/// Convert a `String` into a `ByteArray` +/// +/// ```aiken +/// string.to_bytearray(@"foo") == "foo" +/// ``` +pub fn to_bytearray(self: String) -> ByteArray { + encode_utf8(self) +} + +test to_bytearray_1() { + to_bytearray(@"") == "" +} + +test to_bytearray_2() { + to_bytearray(@"ABC") == #[65, 66, 67] +} + +test to_bytearray_3() { + to_bytearray(@"ABC") == "ABC" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/address.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/address.ak new file mode 100644 index 00000000..0167b90f --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/address.ak @@ -0,0 +1,86 @@ +use aiken/crypto.{ + Blake2b_224, Hash, Script, ScriptHash, VerificationKey, VerificationKeyHash, +} + +/// A general structure for representing an on-chain `Credential`. +/// +/// Credentials are always one of two kinds: a direct public/private key +/// pair, or a script (native or Plutus). +pub type Credential { + VerificationKey(VerificationKeyHash) + Script(ScriptHash) +} + +// ## Constructing + +/// A Cardano `Address` typically holding one or two credential references. +/// +/// Note that legacy bootstrap addresses (a.k.a. 'Byron addresses') are +/// completely excluded from Plutus contexts. Thus, from an on-chain +/// perspective only exists addresses of type 00, 01, ..., 07 as detailed +/// in [CIP-0019 :: Shelley Addresses](https://github.com/cardano-foundation/CIPs/tree/master/CIP-0019/#shelley-addresses). +pub type Address { + payment_credential: PaymentCredential, + stake_credential: Option, +} + +/// Smart-constructor for an [Address](#Address) from a [script](#Script) hash. The address has no delegation rights whatsoever. +pub fn from_script(script: Hash) -> Address { + Address { payment_credential: Script(script), stake_credential: None } +} + +/// Smart-constructor for an [Address](#Address) from a [verification key](#VerificationKey) hash. The resulting address has no delegation rights whatsoever. +pub fn from_verification_key(vk: Hash) -> Address { + Address { payment_credential: VerificationKey(vk), stake_credential: None } +} + +/// Set (or reset) the delegation part of an [Address](#Address) using a [verification key](#VerificationKey) hash. This is useful when combined with [`from_verification_key`](#from_verification_key) and/or [`from_script`](#from_script). +pub fn with_delegation_key( + self: Address, + vk: Hash, +) -> Address { + Address { + payment_credential: self.payment_credential, + stake_credential: Some(Inline(VerificationKey(vk))), + } +} + +/// Set (or reset) the delegation part of an [Address](#Address) using a [script](#Script) hash. This is useful when combined with [`from_verification_key`](#from_verification_key) and/or [`from_script`](#from_script). +pub fn with_delegation_script( + self: Address, + script: Hash, +) -> Address { + Address { + payment_credential: self.payment_credential, + stake_credential: Some(Inline(Script(script))), + } +} + +/// Represent a type of object that can be represented either inline (by hash) +/// or via a reference (i.e. a pointer to an on-chain location). +/// +/// This is mainly use for capturing pointers to a stake credential +/// registration certificate in the case of so-called pointer addresses. +pub type Referenced { + Inline(a) + Pointer { slot_number: Int, transaction_index: Int, certificate_index: Int } +} + +/// A `StakeCredential` represents the delegation and rewards withdrawal conditions +/// associated with some stake address / account. +/// +/// A `StakeCredential` is either provided inline, or, by reference using an +/// on-chain pointer. +/// +/// Read more about pointers in [CIP-0019 :: Pointers](https://github.com/cardano-foundation/CIPs/tree/master/CIP-0019/#pointers). +pub type StakeCredential = + Referenced + +/// A 'PaymentCredential' represents the spending conditions associated with +/// some output. Hence, +/// +/// - a `VerificationKey` captures an output locked by a public/private key pair; +/// - and a `Script` captures an output locked by a native or Plutus script. +/// +pub type PaymentCredential = + Credential diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/address/credential.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/address/credential.ak new file mode 100644 index 00000000..2ebeaa91 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/address/credential.ak @@ -0,0 +1,30 @@ +use aiken/primitive/bytearray +use cardano/address.{Credential, Script, VerificationKey} + +pub fn compare(left: Credential, right: Credential) -> Ordering { + when left is { + Script(left) -> + when right is { + Script(right) -> bytearray.compare(left, right) + _ -> Less + } + VerificationKey(left) -> + when right is { + Script(_) -> Greater + VerificationKey(right) -> bytearray.compare(left, right) + } + } +} + +test compare_matrix() { + and { + (compare(Script(""), Script("")) == Equal)?, + (compare(VerificationKey(""), VerificationKey("")) == Equal)?, + (compare(Script(""), VerificationKey("")) == Less)?, + (compare(VerificationKey(""), Script("")) == Greater)?, + (compare(Script("01"), Script("02")) == Less)?, + (compare(Script("02"), Script("01")) == Greater)?, + (compare(VerificationKey("01"), VerificationKey("02")) == Less)?, + (compare(VerificationKey("02"), VerificationKey("01")) == Greater)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/assets.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/assets.ak new file mode 100644 index 00000000..664a3983 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/assets.ak @@ -0,0 +1,920 @@ +use aiken/builtin +use aiken/collection/dict.{Dict, from_ascending_pairs_with} +use aiken/collection/list +use aiken/crypto.{Blake2b_224, Hash, Script} +use aiken/option + +/// Lovelace is now a type wrapper for Int. +pub type Lovelace = + Int + +/// A type-alias for a `PolicyId`. A `PolicyId` is always 28-byte long +pub type PolicyId = + Hash + +/// Ada, the native currency, isn't associated with any `PolicyId` (it's not +/// possible to mint Ada!). +/// +/// By convention, it is an empty `ByteArray`. +pub const ada_policy_id = "" + +/// A type-alias for 'AssetName`, which are free-form byte-arrays between +/// 0 and 32 bytes. +pub type AssetName = + ByteArray + +/// Ada, the native currency, isn't associated with any `AssetName` (it's not +/// possible to mint Ada!). +/// +/// By convention, it is an empty `ByteArray`. +pub const ada_asset_name = "" + +/// A multi-asset output `Value`. Contains tokens indexed by [PolicyId](#PolicyId) and [AssetName](#AssetName). +/// +/// > [!IMPORTANT] +/// > This type maintain some invariants by construction; in particular, a `Value` will never contain a +/// zero quantity of a particular token. +pub opaque type Value { + inner: Dict>, +} + +// ## Constructing + +/// Construct a `Value` from an asset identifier (i.e. `PolicyId` + `AssetName`) +/// and a given quantity. +pub fn from_asset( + policy_id: PolicyId, + asset_name: AssetName, + quantity: Int, +) -> Value { + if quantity == 0 { + zero + } else { + let asset = + dict.empty + |> dict.insert(asset_name, quantity) + dict.empty + |> dict.insert(policy_id, asset) + |> Value + } +} + +/// Promote an arbitrary list of assets into a `Value`. This function fails +/// (i.e. halts the program execution) if: +/// +/// - there's any duplicate amongst `PolicyId`; +/// - there's any duplicate amongst `AssetName`; +/// - the `AssetName` aren't sorted in ascending lexicographic order; or +/// - any asset quantity is null. +/// +/// This function is meant to turn arbitrary user-defined `Data` into safe `Value`, +/// while checking for internal invariants. +pub fn from_asset_list(xs: Pairs>) -> Value { + xs + |> list.foldr( + dict.empty, + fn(inner, acc) { + expect Pair(p, [_, ..] as x) = inner + x + |> from_ascending_pairs_with(fn(v) { v != 0 }) + |> dict.insert_with( + acc, + p, + _, + fn(_, _, _) { + fail @"Duplicate policy in the asset list." + }, + ) + }, + ) + |> Value +} + +test from_asset_list_1() { + let v = from_asset_list([]) + v == zero +} + +test from_asset_list_2() fail { + let v = from_asset_list([Pair(#"33", [])]) + v == zero +} + +test from_asset_list_3() fail { + let v = from_asset_list([Pair(#"33", [Pair(#"", 0)])]) + v != zero +} + +test from_asset_list_4() { + let v = from_asset_list([Pair(#"33", [Pair(#"", 1)])]) + flatten(v) == [(#"33", #"", 1)] +} + +test from_asset_list_5() { + let v = from_asset_list([Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)])]) + flatten(v) == [(#"33", #"", 1), (#"33", #"33", 1)] +} + +test from_asset_list_6() fail { + let v = + from_asset_list( + [ + Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + ], + ) + v != zero +} + +test from_asset_list_7() fail { + let v = + from_asset_list( + [ + Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + Pair(#"34", [Pair(#"", 1), Pair(#"", 1)]), + ], + ) + v != zero +} + +test from_asset_list_8() { + let v = + from_asset_list( + [ + Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + Pair(#"34", [Pair(#"31", 1)]), Pair(#"35", [Pair(#"", 1)]), + ], + ) + flatten(v) == [ + (#"33", #"", 1), (#"33", #"33", 1), (#"34", #"31", 1), (#"35", #"", 1), + ] +} + +test from_asset_list_9() { + let v = + from_asset_list( + [ + Pair(#"35", [Pair(#"", 1)]), Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + Pair(#"34", [Pair(#"31", 1)]), + ], + ) + flatten(v) == [ + (#"33", #"", 1), (#"33", #"33", 1), (#"34", #"31", 1), (#"35", #"", 1), + ] +} + +/// Construct a `Value` from a lovelace quantity. +/// +/// Friendly reminder: 1 Ada = 1.000.000 Lovelace +pub fn from_lovelace(quantity: Int) -> Value { + from_asset(ada_policy_id, ada_asset_name, quantity) +} + +/// Construct an empty `Value` with nothing in it. +pub const zero: Value = Value { inner: dict.empty } + +// ## Inspecting + +/// Check is a `Value` is zero. That is, it has no assets and holds no Ada/Lovelace. +pub fn is_zero(self: Value) -> Bool { + self == zero +} + +/// Efficiently compare two values together, allowing a custom behaviour for Ada/Lovelace. +/// The second parameter is provided as `Data`, allowing to conveniently compare serialized +/// datums or similar structurually equivalent types (such as `Pairs>`). +/// +/// The third argument is a callback function to assert the left and right lovelace +/// quantities. Its first argument refers to the quantity of the first argument of +/// `match`, and the second argument of the callback to the quantity of the second +/// argument of `match`. In the absence of lovelace in any value, it defaults to `0`. +/// +/// ```aiken +/// const value: Value = +/// assets.from_lovelace(30) +/// |> assets.add("foo", "bar", 1) +/// |> assets.add("foo", "baz", 42) +/// +/// const datum: Data = +/// assets.from_lovelace(20) +/// |> assets.add("foo", "bar", 1) +/// |> assets.add("foo", "baz", 42) +/// +/// True == assets.match(value, datum, >=) +/// +/// False == assets.match(value, datum, ==) +/// +/// True == assets.match(value, datum, fn(value_lovelace, datum_lovelace) { +/// 2 * datum_lovelace >= value_lovelace +/// }) +/// ``` +pub fn match( + left: Value, + right: Data, + assert_lovelace: fn(Lovelace, Lovelace) -> Bool, +) -> Bool { + builtin.choose_data( + right, + False, + { + let (left_lovelace, left_assets) = dict.pop(left.inner, ada_policy_id) + let left_assets: Data = left_assets + let left_lovelace = + when left_lovelace is { + Some(tokens) -> builtin.head_list(dict.to_pairs(tokens)).2nd + None -> 0 + } + when builtin.un_map_data(right) is { + [] -> left_assets == right && assert_lovelace(left_lovelace, 0) + [first_asset, ..right_assets] -> + if first_asset.1st == builtin.b_data(ada_policy_id) { + and { + assert_lovelace( + left_lovelace, + builtin.un_i_data( + builtin.head_list(builtin.un_map_data(first_asset.2nd)).2nd, + ), + ), + left_assets == builtin.map_data(right_assets), + } + } else { + and { + assert_lovelace(left_lovelace, 0), + left_assets == right, + } + } + } + }, + False, + False, + False, + ) +} + +const fixture_match_value: Value = + zero + |> add(ada_policy_id, ada_asset_name, 42) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + |> add("bar", "01", 42) + +const fixture_match_data: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + |> add("bar", "01", 42) + +const fixture_match_data_missing_foo_02: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("bar", "01", 42) + +const fixture_match_data_altered_foo_01: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 14) + |> add("foo", "02", 1) + |> add("bar", "01", 42) + +const fixture_match_data_missing_bar: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + +const fixture_match_data_extra_policy: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + |> add("bar", "01", 42) + |> add("baz", "01", 1) + +const fixture_match_data_extra_asset: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + |> add("foo", "03", 1) + |> add("bar", "01", 42) + +const fixture_match_data_no_assets: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + +test match_1() { + match(fixture_match_value, fixture_match_data, fn(_, _) { True }) +} + +test match_2() { + !match( + fixture_match_value, + fixture_match_data, + fn(source, target) { source == target }, + ) +} + +test match_3() { + !match( + fixture_match_value, + fixture_match_data_missing_foo_02, + fn(_, _) { True }, + ) +} + +test match_4() { + !match(fixture_match_value, fixture_match_data_missing_bar, fn(_, _) { True }) +} + +test match_5() { + !match( + fixture_match_value, + fixture_match_data_altered_foo_01, + fn(_, _) { True }, + ) +} + +test match_6() { + !match( + fixture_match_value, + fixture_match_data_extra_policy, + fn(_, _) { True }, + ) +} + +test match_7() { + !match(fixture_match_value, fixture_match_data_extra_asset, fn(_, _) { True }) +} + +test match_8() { + !match(fixture_match_value, fixture_match_data_no_assets, fn(_, _) { True }) +} + +test match_9() { + match(zero, zero, ==) +} + +test match_10() { + match( + without_lovelace(fixture_match_value), + without_lovelace(fixture_match_value), + fn(left, right) { left == 0 && right == 0 }, + ) +} + +test match_11() { + match( + without_lovelace(fixture_match_value), + fixture_match_value, + fn(left, right) { left == 0 && right > 0 }, + ) +} + +test match_12() { + match( + fixture_match_value, + without_lovelace(fixture_match_value), + fn(left, right) { left > 0 && right == 0 }, + ) +} + +test match_13() { + match( + zero |> add(ada_policy_id, ada_asset_name, 42), + zero, + fn(left, right) { left == 42 && right == 0 }, + ) +} + +test match_14() { + match( + zero, + zero |> add(ada_policy_id, ada_asset_name, 42), + fn(left, right) { left == 0 && right == 42 }, + ) +} + +const fixture_match_benchmark_left: Value = + zero + |> add(ada_policy_id, ada_asset_name, 1337) + |> add( + #"0246a14d04c3a0e9b65f6b90a3d1aa5faee5d56ab1e30ec7e8b02f29", + "MATTR", + 200, + ) + |> add( + #"0a9e126256cb38c4865cdac6eb2ada51c328ba0df2ebde22ae126c0d", + "ProphecyPoster076", + 1, + ) + |> add( + #"1774343241680e4daef7cbfe3536fc857ce23fb66cd0b66320b2e3dd", + "BISON", + 12_004_999_999, + ) + |> add( + #"279c909f348e533da5808898f87f9a14bb2c3dfbbacccd631d927a3f", + "SNEK", + 1486, + ) + |> add( + #"651dfc074202423585996ffa717cb45237d307e705e2cc3dab1ccabd", + "MAYZSilverFoundersEdition0035", + 1, + ) + |> add( + #"63df49056617dd14034986cf7c250bad6552fd2f0f9c71d797932008", + "CardanoSpaceSession", + 20, + ) + |> add( + #"5b01968867e13432afaa2f814e1d15e332d6cd0aa77e350972b0967d", + "ADAOGovernanceToken", + 1, + ) + |> add( + #"a0028f350aaabe0545fdcb56b039bfb08e4bb4d8c4d7c3c7d481c235", + "HOSKY", + 400_001_000, + ) + |> add( + #"da8c30857834c6ae7203935b89278c532b3995245295456f993e1d24", + "LQ", + 10_635_899, + ) + |> add( + #"95d9a98c2f7999a3d5e0f4d795cb1333837c09eb0f24835cd2ce954c", + "GrandmasterAdventurer659", + 1, + ) + |> add( + #"702cbdb06a81ef2fa4f85f9e32159c03f502539d762a71194fc11eb3", + "AdventurerOfThiolden8105", + 1, + ) + |> add( + #"d0112837f8f856b2ca14f69b375bc394e73d146fdadcc993bb993779", + "DiscoSolaris3725", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld535", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld1213", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld1518", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld1537", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld4199", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld3767", + 1, + ) + |> add( + #"7597444754551a8c17edbf7291cdaeca898ca02ee4e732b09a949396", + "Algae1", + 1, + ) + |> add( + #"7597444754551a8c17edbf7291cdaeca898ca02ee4e732b09a949396", + "Algae2", + 1, + ) + +const fixture_match_benchmark_right: Data = fixture_match_benchmark_left + +test match_benchmark() { + match(fixture_match_benchmark_left, fixture_match_benchmark_right, ==) +} + +test match_benchmark_vs() { + let data: Data = fixture_match_benchmark_right + expect pairs: Pairs> = data + fixture_match_benchmark_left == from_asset_list(pairs) +} + +/// A specialized version of `quantity_of` for the Ada currency. +pub fn lovelace_of(self: Value) -> Int { + quantity_of(self, ada_policy_id, ada_asset_name) +} + +/// A list of all token policies in that Value with non-zero tokens. +pub fn policies(self: Value) -> List { + dict.keys(self.inner) +} + +/// Extract the quantity of a given asset. +pub fn quantity_of( + self: Value, + policy_id: PolicyId, + asset_name: AssetName, +) -> Int { + self.inner + |> dict.get(policy_id) + |> option.and_then(dict.get(_, asset_name)) + |> option.or_else(0) +} + +/// Get all tokens associated with a given policy. +pub fn tokens(self: Value, policy_id: PolicyId) -> Dict { + self.inner + |> dict.get(policy_id) + |> option.or_else(dict.empty) +} + +// ## Combining + +/// Add a (positive or negative) quantity of a single token to a assets. +/// This is more efficient than [`merge`](#merge) for a single asset. +pub fn add( + self: Value, + policy_id: PolicyId, + asset_name: AssetName, + quantity: Int, +) -> Value { + if quantity == 0 { + self + } else { + let helper = + fn(_, left, _right) { + let inner_result = + dict.insert_with( + left, + asset_name, + quantity, + fn(_k, ql, qr) { + let q = ql + qr + if q == 0 { + None + } else { + Some(q) + } + }, + ) + if dict.is_empty(inner_result) { + None + } else { + Some(inner_result) + } + } + + Value( + dict.insert_with( + self.inner, + policy_id, + dict.from_ascending_pairs([Pair(asset_name, quantity)]), + helper, + ), + ) + } +} + +test add_1() { + let v = + zero + |> add(#"acab", #"beef", 321) + |> add(#"acab", #"beef", -321) + v == zero +} + +test add_2() { + let v = + from_lovelace(123) + |> add(#"acab", #"beef", 321) + |> add(#"acab", #"beef", -1 * 321) + v == from_lovelace(123) +} + +test add_3() { + let v = + from_lovelace(1) + |> add(ada_policy_id, ada_asset_name, 2) + |> add(ada_policy_id, ada_asset_name, 3) + v == from_lovelace(6) +} + +test add_4() { + let v = + zero + |> add(#"acab", #"beef", 0) + v == zero +} + +test add_5() { + let v = + zero + |> add(#"acab", #"beef", 0) + |> add(#"acab", #"beef", 0) + v == zero +} + +/// Combine two `Value` together. +pub fn merge(left v0: Value, right v1: Value) -> Value { + Value( + dict.union_with( + v0.inner, + v1.inner, + fn(_, a0, a1) { + let result = + dict.union_with( + a0, + a1, + fn(_, q0, q1) { + let q = q0 + q1 + if q == 0 { + None + } else { + Some(q) + } + }, + ) + if dict.is_empty(result) { + None + } else { + Some(result) + } + }, + ), + ) +} + +test merge_1() { + let v1 = from_lovelace(1) + let v2 = from_lovelace(-1) + merge(v1, v2) == zero +} + +test merge_2() { + let v1 = from_asset(#"00", #"", 1) + let v2 = from_asset(#"01", #"", 2) + let v3 = from_asset(#"02", #"", 3) + let v = + from_lovelace(42) + |> merge(v3) + |> merge(v1) + |> merge(v2) + + flatten(v) == [ + (#"", #"", 42), (#"00", #"", 1), (#"01", #"", 2), (#"02", #"", 3), + ] +} + +test merge_3() { + let v1 = from_asset(#"00", #"", 1) + let v2 = from_asset(#"00", #"", -1) + let v3 = from_asset(#"01", #"", 1) + + let v = + zero + |> merge(v1) + |> merge(v2) + |> merge(v3) + + flatten(v) == [(#"01", #"", 1)] +} + +test merge_4() { + let v1 = from_asset(#"00", #"", 1) + let v2 = from_asset(#"00", #"", -1) + + merge(v1, v2) == zero +} + +test merge_5() { + let v = + zero + |> add(#"acab", #"beef", 0) + + merge(zero, v) == zero +} + +/// Negates quantities of all tokens (including Ada) in that `Value`. +/// +/// ``` +/// v1 +/// |> assets.negate +/// |> assets.merge(v1) +/// |> assets.is_zero +/// // True +/// ``` +pub fn negate(self: Value) -> Value { + dict.map(self.inner, fn(_, a) { dict.map(a, fn(_, q) { 0 - q }) }) + |> Value +} + +/// Get a subset of the assets restricted to the given policies. +pub fn restricted_to(self: Value, mask: List) -> Value { + list.foldr( + policies(self), + zero, + fn(policy_id, value) { + if list.has(mask, policy_id) { + dict.foldr( + tokens(self, policy_id), + value, + fn(asset_name, quantity, value) { + add(value, policy_id, asset_name, quantity) + }, + ) + } else { + value + } + }, + ) +} + +test restricted_to_1() { + let self = from_lovelace(42) |> add("foo", "", 1) + restricted_to(self, []) == zero +} + +test restricted_to_2() { + let self = from_lovelace(42) |> add("foo", "", 1) + restricted_to(self, [ada_policy_id]) == from_lovelace(42) +} + +test restricted_to_3() { + let self = from_lovelace(42) |> add("foo", "", 1) |> add("bar", "", 1) + restricted_to(self, ["foo", "bar"]) == without_lovelace(self) +} + +test restricted_to_4() { + let self = from_lovelace(42) |> add("foo", "bar", 1) |> add("foo", "baz", 1) + restricted_to(self, ["foo"]) == without_lovelace(self) +} + +test restricted_to_5() { + let self = from_lovelace(42) |> add("foo", "bar", 1) |> add("foo", "baz", 1) + restricted_to(self, [ada_policy_id, "foo"]) == self +} + +/// Get a `Value` excluding Ada. +pub fn without_lovelace(self: Value) -> Value { + dict.delete(self.inner, ada_policy_id) + |> Value +} + +test without_lovelace_1() { + let v = from_lovelace(1000000) + without_lovelace(v) == zero +} + +test without_lovelace_2() { + let v = from_lovelace(1000000) + let v2 = from_lovelace(50000000) + without_lovelace(v) == without_lovelace(v2) +} + +test without_lovelace_3() { + let v = + from_asset(#"010203", #"040506", 100) + |> add(ada_policy_id, ada_asset_name, 100000000) + let v2 = from_asset(#"010203", #"040506", 100) + without_lovelace(v) == without_lovelace(v2) && without_lovelace(v) == v2 +} + +// ## Transforming + +/// Flatten a `Value` as list of 3-tuple `(PolicyId, AssetName, Quantity)`. +/// +/// Handy to manipulate values as uniform lists. +pub fn flatten(self: Value) -> List<(PolicyId, AssetName, Int)> { + dict.foldr( + self.inner, + [], + fn(policy_id, asset_list, value) { + dict.foldr( + asset_list, + value, + fn(asset_name, quantity, xs) { + [(policy_id, asset_name, quantity), ..xs] + }, + ) + }, + ) +} + +/// Flatten a `Value` as a list of results, possibly discarding some along the way. +/// +/// When the transform function returns `None`, the result is discarded altogether. +pub fn flatten_with( + self: Value, + with: fn(PolicyId, AssetName, Int) -> Option, +) -> List { + dict.foldr( + self.inner, + [], + fn(policy_id, asset_list, value) { + dict.foldr( + asset_list, + value, + fn(asset_name, quantity, xs) { + when with(policy_id, asset_name, quantity) is { + None -> xs + Some(x) -> [x, ..xs] + } + }, + ) + }, + ) +} + +test flatten_with_1() { + flatten_with(zero, fn(p, a, q) { Some((p, a, q)) }) == [] +} + +test flatten_with_2() { + let v = + zero + |> add("a", "1", 14) + |> add("b", "", 42) + |> add("a", "2", 42) + + flatten_with( + v, + fn(p, a, q) { + if q == 42 { + Some((p, a)) + } else { + None + } + }, + ) == [("a", "2"), ("b", "")] +} + +/// Reduce a value into a single result +/// +/// ``` +/// assets.zero +/// |> assets.add("a", "1", 10) +/// |> assets.add("b", "2", 20) +/// |> assets.reduce(v, 0, fn(_, _, quantity, acc) { acc + quantity }) +/// // 30 +/// ``` +pub fn reduce( + self: Value, + start: result, + with: fn(PolicyId, AssetName, Int, result) -> result, +) -> result { + dict.foldr( + self.inner, + start, + fn(policy_id, asset_list, result) { + dict.foldr(asset_list, result, with(policy_id, _, _, _)) + }, + ) +} + +test reduce_1() { + let v = + zero + |> add("a", "1", 10) + |> add("b", "2", 20) + let result = reduce(v, 0, fn(_, _, quantity, acc) { acc + quantity }) + result == 30 +} + +test reduce_2() { + let v = + zero + |> add("a", "1", 5) + |> add("a", "2", 15) + |> add("b", "", 10) + let result = + reduce( + v, + [], + fn(policy_id, asset_name, _, acc) { [(policy_id, asset_name), ..acc] }, + ) + result == [("a", "1"), ("a", "2"), ("b", "")] +} + +test reduce_3() { + let v = zero + let result = reduce(v, 1, fn(_, _, quantity, acc) { acc + quantity }) + result == 1 +} + +/// Convert the value into a dictionary of dictionaries. +pub fn to_dict(self: Value) -> Dict> { + self.inner +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/certificate.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/certificate.ak new file mode 100644 index 00000000..f0b6d258 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/certificate.ak @@ -0,0 +1,93 @@ +use aiken/crypto.{Blake2b_224, Hash, VerificationKey, VerificationKeyHash} +use cardano/address.{Credential} +use cardano/assets.{Lovelace} + +pub type StakePoolId = + Hash + +/// An on-chain certificate attesting of some operation. Publishing +/// certificates triggers different kind of rules; most of the time, +/// they require signatures from specific keys. +pub type Certificate { + /// Register a stake credential with an optional deposit amount. + /// The deposit is always present when using the new registration certificate + /// format available since the Conway era. + RegisterCredential { + credential: Credential, + /// > [!NOTE] + /// > The `deposit` ought to be an `Option`, but due to unfortunate + /// > circumstances it will always be instantiated to `None` even when set in + /// > the host transaction. This is what the `Never` type captures here. + deposit: Never, + } + /// Un-Register a stake credential with an optional refund amount + /// The deposit is always present when using the new de-registration certificate + /// format available since the Conway era. + UnregisterCredential { + credential: Credential, + /// > [!NOTE] + /// > The `refund` ought to be an `Option`, but due to unfortunate + /// > circumstances it will always be instantiated to `None` even when set in + /// > the host transaction. This is what the `Never` type captures here. + refund: Never, + } + /// Delegate stake to a [Delegate](#Delegate). + DelegateCredential { credential: Credential, delegate: Delegate } + /// Register and delegate staking credential to a Delegatee in one certificate. + RegisterAndDelegateCredential { + credential: Credential, + delegate: Delegate, + deposit: Lovelace, + } + /// Register a delegate representative (a.k.a DRep). The deposit is explicit and + /// is refunded when the delegate steps down (unregister). + RegisterDelegateRepresentative { + delegate_representative: Credential, + deposit: Lovelace, + } + /// Update a delegate representative (a.k.a DRep). The certificate also contains + /// metadata which aren't visible on-chain. + UpdateDelegateRepresentative { delegate_representative: Credential } + /// UnRegister a delegate representative, and refund back its past deposit. + UnregisterDelegateRepresentative { + delegate_representative: Credential, + refund: Lovelace, + } + /// Register a new stake pool + RegisterStakePool { + /// The hash digest of the stake pool's cold (public) key + stake_pool: StakePoolId, + /// The hash digest of the stake pool's VRF (public) key + vrf: VerificationKeyHash, + } + /// Retire a stake pool. 'at_epoch' indicates in which the retirement will take place + RetireStakePool { stake_pool: StakePoolId, at_epoch: Int } + /// Authorize a Hot credential for a specific Committee member's cold credential + AuthorizeConstitutionalCommitteeProxy { + constitutional_committee_member: Credential, + proxy: Credential, + } + /// Step down from the constitutional committee as a member. + RetireFromConstitutionalCommittee { + constitutional_committee_member: Credential, + } +} + +/// A type of stake delegation that can be either block-production, vote or +/// both. Note that delegation types aren't cancelling one another, so it is +/// possible to delegate block production in one transaction, and delegate vote +/// in another. This second delegation **does NOT** invalidate the first one. +pub type Delegate { + DelegateBlockProduction { stake_pool: StakePoolId } + DelegateVote { delegate_representative: DelegateRepresentative } + DelegateBoth { + stake_pool: StakePoolId, + delegate_representative: DelegateRepresentative, + } +} + +pub type DelegateRepresentative { + Registered(Credential) + AlwaysAbstain + AlwaysNoConfidence +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/governance.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/governance.ak new file mode 100644 index 00000000..3ec96800 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/governance.ak @@ -0,0 +1,109 @@ +use aiken/collection.{Index} +use aiken/crypto.{Blake2b_256, Hash, ScriptHash, VerificationKeyHash} +use aiken/math/rational.{Rational} +use cardano/address.{Credential} +use cardano/assets.{Lovelace} +use cardano/governance/protocol_parameters.{ProtocolParametersUpdate} + +pub type ProposalProcedure { + deposit: Lovelace, + return_address: Credential, + governance_action: GovernanceAction, +} + +pub type GovernanceAction { + ProtocolParameters { + /// The last governance action of type 'ProtocolParameters'. They must all + /// form a chain. + ancestor: Option, + /// The new proposed protocol parameters. Only values set to `Some` are relevant. + new_parameters: ProtocolParametersUpdate, + /// The optional guardrails script defined in the constitution. The script + /// is executed by the ledger in addition to the hard-coded ledger rules. + /// + /// It must pass for the new protocol parameters to be deemed valid. + guardrails: Option, + } + HardFork { + /// The last governance action of type `HardFork`. They must all + /// form a chain. + ancestor: Option, + /// The new proposed version. Few rules apply to proposing new versions: + /// + /// - The `major` component, if incremented, must be exactly one more than the current. + /// - The `minor` component, if incremented, must be exactly one more than the current. + /// - If the `major` component is incremented, `minor` must be set to `0`. + /// - Neither `minor` nor `major` can be decremented. + new_version: ProtocolVersion, + } + TreasuryWithdrawal { + /// A collection of beneficiaries, which can be plain verification key + /// hashes or script hashes (e.g. DAO). + beneficiaries: Pairs, + /// The optional guardrails script defined in the constitution. The script + /// is executed by the ledger in addition to the hard-coded ledger rules. + /// + /// It must pass for the withdrawals to be authorized. + guardrails: Option, + } + NoConfidence { + /// The last governance action of type `NoConfidence` or + /// `ConstitutionalCommittee`. They must all / form a chain. + ancestor: Option, + } + ConstitutionalCommittee { + /// The last governance action of type `NoConfidence` or + /// `ConstitutionalCommittee`. They must all / form a chain. + ancestor: Option, + /// Constitutional members to be removed. + evicted_members: List, + /// Constitutional members to be added. + added_members: Pairs, + /// The new quorum value, as a ratio of a numerator and a denominator. The + /// quorum specifies the threshold of 'Yes' votes necessary for the + /// constitutional committee to accept a proposal procedure. + quorum: Rational, + } + NewConstitution { + /// The last governance action of type `Constitution` or + /// `ConstitutionalCommittee`. They must all / form a chain. + ancestor: Option, + /// The new proposed constitution. + constitution: Constitution, + } + NicePoll +} + +pub type Vote { + No + Yes + Abstain +} + +pub type TransactionId = + Hash + +pub type GovernanceActionId { + transaction: TransactionId, + proposal_procedure: Index, +} + +pub type ProtocolVersion { + major: Int, + minor: Int, +} + +pub type Constitution { + guardrails: Option, +} + +/// An epoch number after which constitutional committee member +/// mandate expires. +pub type Mandate = + Int + +pub type Voter { + ConstitutionalCommitteeMember(Credential) + DelegateRepresentative(Credential) + StakePool(VerificationKeyHash) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/governance/protocol_parameters.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/governance/protocol_parameters.ak new file mode 100644 index 00000000..d9e7be95 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/governance/protocol_parameters.ak @@ -0,0 +1,360 @@ +use aiken/math/rational.{Rational} +use cardano/assets.{Lovelace} + +pub opaque type ProtocolParametersUpdate { + inner: Pairs, +} + +pub type ScriptExecutionPrices { + memory: Rational, + cpu: Rational, +} + +pub type ExecutionUnits { + memory: Int, + cpu: Int, +} + +pub type StakePoolOperatorVotingThresholds { + motion_of_no_confidence: Rational, + constitutional_committee: ConstitutionalCommitteeThresholds, + hard_fork: Rational, + protocol_parameters: ProtocolParametersThresholds< + Rational, + Void, + Void, + Void, + Void, + >, +} + +pub type DelegateRepresentativeVotingThresholds { + motion_of_no_confidence: Rational, + constitutional_committee: ConstitutionalCommitteeThresholds, + constitution: Rational, + hard_fork: Rational, + protocol_parameters: ProtocolParametersThresholds< + Void, + Rational, + Rational, + Rational, + Rational, + >, + treasury_withdrawal: Rational, +} + +pub type ProtocolParametersThresholds< + security, + network, + economic, + technical, + governance, +> { + security_group: security, + network_group: network, + economic_group: economic, + technical_group: technical, + governance_group: governance, +} + +pub type ConstitutionalCommitteeThresholds { + default: Rational, + under_no_confidence: Rational, +} + +/// The linear coefficient that intervenes in the transaction fee calculation. +/// It is multiplied by the size of the transaction in bytes to obtain a Lovelace value. +pub fn min_fee_coefficient(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 0, into_int) +} + +/// The constant factor that intervenes in the transaction fee calculation. It is +/// a flat cost of lovelace that is added to every fee calculation. +pub fn min_fee_constant(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 1, into_int) +} + +/// The maximum size of a serialized block body, expressed in bytes. +pub fn max_block_body_size(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 2, into_int) +} + +/// The maximum size of a serialized transaction (body + witnesses), expressed in bytes. +pub fn max_transaction_size(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 3, into_int) +} + +/// The maximum size of a serialized block header, expressed in bytes. +pub fn max_block_header_size(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 4, into_int) +} + +/// The required deposit amount when registering stake credentials, expressed in Lovelace. +pub fn stake_credential_deposit( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 5, into_int) +} + +/// The required deposit amount when registering a stake pool, expressed in Lovelace. +pub fn stake_pool_deposit(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 6, into_int) +} + +/// The maximum number of epoch in the future allowed for a stake pool retirement to be scheduled. +pub fn stake_pool_retirement_horizon( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 7, into_int) +} + +/// The desired/optimal number of fully saturated stake pools in the system. Also known as the _'k-parameter'_. +pub fn desired_number_of_stake_pools( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 8, into_int) +} + +/// A parameter controlling the influence of an pool owner's pledge on the rewards. Also known as _'a0'_. +pub fn stake_pool_pledge_influence( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 9, into_rational) +} + +/// The monetary expansion parameter, controlling the fraction of Ada put in circulation on every epoch through the incentivies model. Also known as _'ρ'_. +pub fn monetary_expansion(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 10, into_rational) +} + +/// The parameter controlling what fraction (%) of available rewards is sent to the treasury on every epoch. Also known as _'τ'_. +pub fn treasury_expansion(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 11, into_rational) +} + +/// Minimum authorized constant cost that stake pools can declare when registering, expressed in Lovelace. +pub fn min_stake_pool_cost(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 16, into_int) +} + +/// The linear coefficient that intervenes in the calculation of the minimum Ada value that any UTxO must hold. It is expressed in Lovelace per Byte, and is also known as the 'coins per utxo byte' parameter. +pub fn min_utxo_deposit_coefficient( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 17, into_int) +} + +/// The costs associated with the various operations of the Plutus Virtual Machine, which can be different for each Plutus version. +pub fn cost_models(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 18, identity) +} + +/// The price, in Lovelace per unit, of the execution units corresponding to cpu and memory usage of on-chain scripts. +pub fn script_execution_prices( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 19, into_script_execution_prices) +} + +/// The maximum execution units allowed for a single transaction. +pub fn max_transaction_execution_units( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 20, into_execution_units) +} + +/// The maximum execution units allowed for a single block. +pub fn max_block_execution_units( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 21, into_execution_units) +} + +/// The maximum size of a serialized value in a transaction output. This effectively limits +/// the maximum kinds of assets that can be sent in a single output. It is expressed in bytes. +pub fn max_value_size(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 22, into_int) +} + +/// The scaling factor applied to the transaction cost for defining the minimum collateral +/// amount. It is expressed in percent points (so 100 = 100%). +pub fn collateral_percentage(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 23, into_int) +} + +/// The maximum number of collateral inputs allowed in the transaction. +pub fn max_collateral_inputs(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 24, into_int) +} + +/// The various governance voting thresholds pertaining to stake pool operators. +pub fn stake_pool_operator_voting_thresholds( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 25, into_spo_voting_thresholds) +} + +/// The various governance voting thresholds pertaining to delegate representatives +/// (a.k.a DReps). +pub fn delegate_representative_voting_thresholds( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 26, into_drep_voting_thresholds) +} + +/// The minimum number of members in the constitutional committee. Any updates of the committee +/// must leave at least this number of members. +pub fn min_constitutional_committee_size( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 27, into_int) +} + +/// The maximum length of a constitutional committee member, expressed in number of epochs. +pub fn max_constitutional_committee_mandate( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 28, into_int) +} + +/// The lifetime of any governance proposal. An action that hasn't been approved beyond that +/// period is considered inactive and discarded. It is expressed in number of epochs. +pub fn governance_proposal_lifetime( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 29, into_int) +} + +/// The required deposit amount for governance proposal procedures, expressed in Lovelace. +pub fn governance_proposal_deposit( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 30, into_int) +} + +/// The required deposit amount when registering as a delegate representative, expressed in +/// Lovelace. +pub fn delegate_representative_deposit( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 31, into_int) +} + +/// The maximum number of epochs that a delegate representative can stay inactive (i.e. no +/// voting) without becoming _inactive_ and removed from thresholds calculations. +pub fn delegate_representative_max_idle_time( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 32, into_int) +} + +/// The base tier fee coefficient for reference scripts. Reference scripts gets increasingly +/// more expensives every ~24KB, the base coefficient is a multiplicating factor which grows +/// exponentially with each tier. +pub fn reference_scripts_tier_fee_initial_factor( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 33, into_rational) +} + +// Internals ------------------------------------------------------------------- + +type ProtocolParametersIndex = + Int + +fn get_protocol_param( + self: Pairs, + ix: ProtocolParametersIndex, + into: fn(Data) -> a, +) -> Option { + when self is { + [] -> None + [Pair(jx, param), ..tail] -> + if ix == jx { + Some(into(param)) + } else { + get_protocol_param(tail, ix, into) + } + } +} + +fn into_int(param: Data) -> Int { + expect param: Int = param + param +} + +fn into_rational(param: Data) -> Rational { + expect [numerator, denominator]: List = param + expect Some(r) = rational.new(numerator, denominator) + r +} + +fn into_execution_units(param: Data) -> ExecutionUnits { + expect [memory, cpu]: List = param + ExecutionUnits { memory, cpu } +} + +fn into_script_execution_prices(param: Data) -> ScriptExecutionPrices { + expect [memory, cpu]: List = param + let memory = into_rational(memory) + let cpu = into_rational(cpu) + ScriptExecutionPrices { memory, cpu } +} + +fn into_spo_voting_thresholds(param: Data) -> StakePoolOperatorVotingThresholds { + expect [ + motion_of_no_confidence, constitutional_committee, + constitutional_committee_under_no_confidence, hard_fork, + protocol_parameters_security_group, + ]: List = param + + StakePoolOperatorVotingThresholds { + motion_of_no_confidence: into_rational(motion_of_no_confidence), + constitutional_committee: ConstitutionalCommitteeThresholds { + default: into_rational(constitutional_committee), + under_no_confidence: into_rational( + constitutional_committee_under_no_confidence, + ), + }, + hard_fork: into_rational(hard_fork), + protocol_parameters: ProtocolParametersThresholds { + security_group: into_rational(protocol_parameters_security_group), + network_group: Void, + economic_group: Void, + technical_group: Void, + governance_group: Void, + }, + } +} + +fn into_drep_voting_thresholds( + param: Data, +) -> DelegateRepresentativeVotingThresholds { + expect [ + motion_of_no_confidence, constitutional_committee, + constitutional_committee_under_no_confidence, constitution, hard_fork, + protocol_parameters_network_group, protocol_parameters_economic_group, + protocol_parameters_technical_group, protocol_parameters_governance_group, + treasury_withdrawal, + ]: List = param + + DelegateRepresentativeVotingThresholds { + motion_of_no_confidence: into_rational(motion_of_no_confidence), + constitutional_committee: ConstitutionalCommitteeThresholds { + default: into_rational(constitutional_committee), + under_no_confidence: into_rational( + constitutional_committee_under_no_confidence, + ), + }, + constitution: into_rational(constitution), + hard_fork: into_rational(hard_fork), + protocol_parameters: ProtocolParametersThresholds { + security_group: Void, + network_group: into_rational(protocol_parameters_network_group), + economic_group: into_rational(protocol_parameters_economic_group), + technical_group: into_rational(protocol_parameters_technical_group), + governance_group: into_rational(protocol_parameters_governance_group), + }, + treasury_withdrawal: into_rational(treasury_withdrawal), + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/governance/voter.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/governance/voter.ak new file mode 100644 index 00000000..e723e2d5 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/governance/voter.ak @@ -0,0 +1,62 @@ +use aiken/primitive/bytearray +use cardano/address.{Script} +use cardano/address/credential +use cardano/governance.{ + ConstitutionalCommitteeMember, DelegateRepresentative, StakePool, Voter, +} + +pub fn compare(left: Voter, right: Voter) -> Ordering { + when left is { + ConstitutionalCommitteeMember(left) -> + when right is { + ConstitutionalCommitteeMember(right) -> credential.compare(left, right) + _ -> Less + } + DelegateRepresentative(left) -> + when right is { + DelegateRepresentative(right) -> credential.compare(left, right) + ConstitutionalCommitteeMember(_) -> Greater + _ -> Less + } + StakePool(left) -> + when right is { + StakePool(right) -> bytearray.compare(left, right) + _ -> Greater + } + } +} + +test compare_matrix() { + let cc0 = ConstitutionalCommitteeMember(Script("0")) + let cc1 = ConstitutionalCommitteeMember(Script("1")) + + let drep0 = DelegateRepresentative(Script("0")) + let drep1 = DelegateRepresentative(Script("1")) + + let spo0 = StakePool("0") + let spo1 = StakePool("1") + + and { + (compare(cc0, cc0) == Equal)?, + (compare(cc0, cc1) == Less)?, + (compare(cc1, cc0) == Greater)?, + (compare(drep0, drep0) == Equal)?, + (compare(drep0, drep1) == Less)?, + (compare(drep1, drep0) == Greater)?, + (compare(spo0, spo0) == Equal)?, + (compare(spo0, spo1) == Less)?, + (compare(spo1, spo0) == Greater)?, + (compare(cc0, drep0) == Less)?, + (compare(cc0, drep1) == Less)?, + (compare(cc0, spo0) == Less)?, + (compare(cc0, spo1) == Less)?, + (compare(drep0, cc0) == Greater)?, + (compare(drep0, cc1) == Greater)?, + (compare(drep0, spo0) == Less)?, + (compare(drep0, spo1) == Less)?, + (compare(spo0, cc0) == Greater)?, + (compare(spo0, cc1) == Greater)?, + (compare(spo0, drep0) == Greater)?, + (compare(spo0, drep1) == Greater)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/script_context.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/script_context.ak new file mode 100644 index 00000000..ff73836a --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/script_context.ak @@ -0,0 +1,62 @@ +//// This module contains utilities for manually dealing with [`ScriptContext`](#ScriptContext). This is only ever useful for writing custom `else` handlers in validators. +//// +//// > [!NOTE] +//// > Unless you know what you're doing, you should prefer using named handlers: +//// > +//// > - `mint` +//// > - `spend` +//// > - `withdraw` +//// > - `publish` +//// > - `vote` +//// > - `propose` + +use aiken/collection.{Index} +use cardano/address.{Credential} +use cardano/assets.{PolicyId} +use cardano/certificate.{Certificate} +use cardano/governance.{ProposalProcedure, Voter} +use cardano/transaction.{OutputReference, Redeemer, Transaction} + +/// A context given to a script by the Cardano ledger when being executed. +/// +/// The context contains information about the entire transaction that contains +/// the script. The transaction may also contain other scripts; to distinguish +/// between multiple scripts, the [`ScriptContext`](#ScriptContext) contains a +/// [`ScriptInfo`](#ScriptInfo) which indicates which script (or, for what +/// purpose) the transaction is being executed. +pub type ScriptContext { + transaction: Transaction, + redeemer: Redeemer, + info: ScriptInfo, +} + +/// Characterizes the script information. The main (and only) difference with [`ScriptPurpose`](./transaction.html#ScriptPurpose) resides in the `Spending` variant which here contains a second field `datum: Option`. +pub type ScriptInfo { + /// For scripts executed as minting/burning policies, to insert + /// or remove assets from circulation. It's parameterized by the identifier + /// of the associated policy. + Minting(PolicyId) + /// For scripts that are used as payment credentials for addresses in + /// transaction outputs. They govern the rule by which the output they + /// reference can be spent. + Spending { output: OutputReference, datum: Option } + /// For scripts that validate reward withdrawals from a reward account. + /// + /// The argument identifies the target reward account. + Withdrawing(Credential) + /// Needed when delegating to a pool using stake credentials defined as a + /// custom script. This purpose is also triggered when de-registering such + /// stake credentials. + /// + /// The Int is a 0-based index of the given `Certificate` in `certificates`. + Publishing { at: Index, certificate: Certificate } + /// Voting for a type of voter using a governance action id to vote + /// yes / no / abstain inside a transaction. + /// + /// The voter is who is doing the governance action. + Voting(Voter) + /// Used to propose a governance action. + /// + /// A 0-based index of the given `ProposalProcedure` in `proposal_procedures`. + Proposing { at: Index, proposal_procedure: ProposalProcedure } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/transaction.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/transaction.ak new file mode 100644 index 00000000..6511a596 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/transaction.ak @@ -0,0 +1,225 @@ +use aiken/builtin +use aiken/collection.{Index} +use aiken/collection/dict.{Dict} +use aiken/collection/list +use aiken/crypto.{ + Blake2b_256, DataHash, Hash, ScriptHash, VerificationKeyHash, blake2b_256, +} +use aiken/interval.{Interval} +use aiken/option +use cardano/address.{Address, Credential, Script, VerificationKey} +use cardano/assets.{Lovelace, PolicyId, Value} +use cardano/certificate.{Certificate} +use cardano/governance.{GovernanceActionId, ProposalProcedure, Vote, Voter} + +pub type TransactionId = + Hash + +/// Characterizes the script purpose. +pub type ScriptPurpose { + /// For scripts executed as minting/burning policies, to insert + /// or remove assets from circulation. It's parameterized by the identifier + /// of the associated policy. + Mint(PolicyId) + /// For scripts that are used as payment credentials for addresses in + /// transaction outputs. They govern the rule by which the output they + /// reference can be spent. + Spend(OutputReference) + /// For scripts that validate reward withdrawals from a reward account. + /// + /// The argument identifies the target reward account. + Withdraw(Credential) + /// Needed when delegating to a pool using stake credentials defined as a + /// custom script. This purpose is also triggered when de-registering such + /// stake credentials. + /// + /// The Int is a 0-based index of the given `Certificate` in `certificates`. + Publish { at: Index, certificate: Certificate } + /// Voting for a type of voter using a governance action id to vote + /// yes / no / abstain inside a transaction. + /// + /// The voter is who is doing the governance action. + Vote(Voter) + /// Used to propose a governance action. + /// + /// A 0-based index of the given `ProposalProcedure` in `proposal_procedures`. + Propose { at: Index, proposal_procedure: ProposalProcedure } +} + +/// A Cardano `Transaction`, as seen by on-chain scripts. +/// +/// Note that this is a representation of a transaction, and not the 1:1 +/// translation of the transaction as seen by the ledger. In particular, +/// on-chain scripts can't see inputs locked by bootstrap addresses, outputs +/// to bootstrap addresses or just transaction metadata. +pub type Transaction { + inputs: List, + reference_inputs: List, + outputs: List, + fee: Lovelace, + mint: Value, + certificates: List, + /// > [!IMPORTANT] + /// > Withdrawals are ordered by ascending [Credential](./credential.html#Credential). Yet, note that [`Script`](./credential.html#Credential) credentials are treated as **lower values** than [`VerificationKey`](./credential.html#Credential) credentials. + withdrawals: Pairs, + validity_range: ValidityRange, + extra_signatories: List, + /// > [!IMPORTANT] + /// > Redeemers are ordered by ascending [ScriptPurpose](./transaction.html#ScriptPurpose). + redeemers: Pairs, + datums: Dict, + id: TransactionId, + /// > [!IMPORTANT] + /// > Votes are ordered by ascending [Voter](./governance.html#Voter) and [GovernanceActionId](./governance.html#GovernanceActionId).
First constructor variants in a type are treated as lower indices; except for [Credential](./credential.html#Credential) where [`Script`](./credential.html#Credential) credentials are treated as **lower values** than [`VerificationKey`](./credential.html#Credential) credentials. + votes: Pairs>, + proposal_procedures: List, + current_treasury_amount: Option, + treasury_donation: Option, +} + +/// An interval of POSIX time, measured in **number of milliseconds** since 1970-01-01T00:00:00Z. +pub type ValidityRange = + Interval + +/// An `Input` made of an output reference and, the resolved value associated with that output. +pub type Input { + output_reference: OutputReference, + output: Output, +} + +/// An `OutputReference` is a unique reference to an output on-chain. The `output_index` +/// corresponds to the position in the output list of the transaction (identified by its id) +/// that produced that output +pub type OutputReference { + transaction_id: Hash, + output_index: Int, +} + +/// A transaction `Output`, with an address, a value and optional datums and script references. +pub type Output { + address: Address, + value: Value, + datum: Datum, + reference_script: Option, +} + +/// An output `Datum`. +pub type Datum { + NoDatum + /// A datum referenced by its hash digest. + DatumHash(DataHash) + /// A datum completely inlined in the output. + InlineDatum(Data) +} + +/// A type-alias for Redeemers, passed to scripts for validation. The `Data` is +/// opaque because it is user-defined and it is the script's responsibility to +/// parse it into its expected form. +pub type Redeemer = + Data + +// ## Querying + +/// Find an input by its [`OutputReference`](#OutputReference). This is typically used in +/// combination with the `Spend` [`ScriptPurpose`](#ScriptPurpose) to find a script's own +/// input. +/// +/// ```aiken +/// validator { +/// spend(datum, redeemer, my_output_reference, self) { +/// expect Some(input) = +/// self.inputs +/// |> transaction.find_input(my_output_reference) +/// } +/// } +/// ``` +pub fn find_input( + inputs: List, + output_reference: OutputReference, +) -> Option { + inputs + |> list.find(fn(input) { input.output_reference == output_reference }) +} + +/// Find a [`Datum`](#Datum) by its hash, if present. The function looks first for +/// datums in the witness set, and then for inline datums if it doesn't find any in +/// witnesses. +pub fn find_datum( + outputs: List, + datums: Dict, + datum_hash: DataHash, +) -> Option { + datums + |> dict.get(datum_hash) + |> option.or_try( + fn() { + outputs + |> list.filter_map( + fn(output) { + when output.datum is { + InlineDatum(data) -> + if blake2b_256(builtin.serialise_data(data)) == datum_hash { + Some(data) + } else { + None + } + _ -> None + } + }, + ) + |> list.head + }, + ) +} + +/// Find all outputs that are paying into the given script hash, if any. This is useful for +/// contracts running over multiple transactions. +pub fn find_script_outputs( + outputs: List, + script_hash: ScriptHash, +) -> List { + outputs + |> list.filter( + fn(output) { + when output.address.payment_credential is { + Script(addr_script_hash) -> script_hash == addr_script_hash + VerificationKey(_) -> False + } + }, + ) +} + +// ## Testing + +/// A placeholder / empty `Transaction` to serve as a base in a transaction +/// builder. This is particularly useful for constructing test transactions. +/// +/// Every field is empty or null, and we have in particular: +/// +/// ```aiken +/// use aiken/interval +/// +/// transaction.placeholder.id == +/// #"0000000000000000000000000000000000000000000000000000000000000000" +/// +/// transaction.placeholder.validity_range == interval.everything +/// ``` +pub const placeholder: Transaction = + Transaction { + inputs: [], + reference_inputs: [], + outputs: [], + fee: 0, + mint: assets.zero, + certificates: [], + withdrawals: [], + validity_range: interval.everything, + extra_signatories: [], + redeemers: [], + datums: dict.empty, + id: #"0000000000000000000000000000000000000000000000000000000000000000", + votes: [], + proposal_procedures: [], + current_treasury_amount: None, + treasury_donation: None, + } diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/transaction/output_reference.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/transaction/output_reference.ak new file mode 100644 index 00000000..70b7550d --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/transaction/output_reference.ak @@ -0,0 +1,23 @@ +use aiken/primitive/bytearray +use aiken/primitive/int +use cardano/transaction.{OutputReference} + +pub fn compare(left: OutputReference, right: OutputReference) -> Ordering { + when bytearray.compare(left.transaction_id, right.transaction_id) is { + Equal -> int.compare(left.output_index, right.output_index) + ordering -> ordering + } +} + +test compare_matrix() { + and { + (compare(OutputReference("", 0), OutputReference("", 0)) == Equal)?, + (compare(OutputReference("00", 42), OutputReference("00", 42)) == Equal)?, + (compare(OutputReference("00", 0), OutputReference("01", 0)) == Less)?, + (compare(OutputReference("01", 0), OutputReference("00", 0)) == Greater)?, + (compare(OutputReference("00", 42), OutputReference("01", 14)) == Less)?, + (compare(OutputReference("01", 14), OutputReference("00", 42)) == Greater)?, + (compare(OutputReference("", 42), OutputReference("", 14)) == Greater)?, + (compare(OutputReference("", 14), OutputReference("", 42)) == Less)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/transaction/script_purpose.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/transaction/script_purpose.ak new file mode 100644 index 00000000..4fef2cbe --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/aiken-lang-stdlib/lib/cardano/transaction/script_purpose.ak @@ -0,0 +1,126 @@ +use aiken/primitive/bytearray +use aiken/primitive/int +use cardano/address.{Script, VerificationKey} +use cardano/address/credential +use cardano/certificate.{RegisterCredential} +use cardano/governance.{NicePoll, ProposalProcedure, StakePool} +use cardano/governance/voter +use cardano/transaction.{ + Mint, OutputReference, Propose, Publish, ScriptPurpose, Spend, Vote, Withdraw, +} +use cardano/transaction/output_reference + +pub fn compare(left: ScriptPurpose, right: ScriptPurpose) -> Ordering { + when left is { + Mint(left) -> + when right is { + Mint(right) -> bytearray.compare(left, right) + _ -> Less + } + + Spend(left) -> + when right is { + Spend(right) -> output_reference.compare(left, right) + Mint(_) -> Greater + _ -> Less + } + + Withdraw(left) -> + when right is { + Withdraw(right) -> credential.compare(left, right) + Spend(_) | Mint(_) -> Greater + _ -> Less + } + + Publish(left, _) -> + when right is { + Publish(right, _) -> int.compare(left, right) + Spend(_) | Mint(_) | Withdraw(_) -> Greater + _ -> Less + } + + Vote(left) -> + when right is { + Vote(right) -> voter.compare(left, right) + Propose(..) -> Less + _ -> Greater + } + + Propose(left, _) -> + when right is { + Propose(right, _) -> int.compare(left, right) + _ -> Greater + } + } +} + +test compare_matrix() { + let mint0 = Mint("0") + let mint1 = Mint("1") + + let spend0 = Spend(OutputReference("", 0)) + let spend1 = Spend(OutputReference("", 1)) + + let withdraw0 = Withdraw(VerificationKey("0")) + let withdraw1 = Withdraw(VerificationKey("1")) + + let publish0 = Publish(0, RegisterCredential(Script(""), Never)) + let publish1 = Publish(1, RegisterCredential(Script(""), Never)) + + let vote0 = Vote(StakePool("0")) + let vote1 = Vote(StakePool("1")) + + let propose0 = Propose(0, ProposalProcedure(0, Script(""), NicePoll)) + let propose1 = Propose(1, ProposalProcedure(0, Script(""), NicePoll)) + + and { + (compare(mint0, mint0) == Equal)?, + (compare(mint0, mint1) == Less)?, + (compare(mint1, mint0) == Greater)?, + (compare(mint0, spend0) == Less)?, + (compare(mint0, withdraw0) == Less)?, + (compare(mint0, publish0) == Less)?, + (compare(mint0, vote0) == Less)?, + (compare(mint0, propose0) == Less)?, + (compare(spend0, spend0) == Equal)?, + (compare(spend0, spend1) == Less)?, + (compare(spend1, spend0) == Greater)?, + (compare(spend0, mint0) == Greater)?, + (compare(spend0, withdraw0) == Less)?, + (compare(spend0, publish0) == Less)?, + (compare(spend0, vote0) == Less)?, + (compare(spend0, propose0) == Less)?, + (compare(withdraw0, withdraw0) == Equal)?, + (compare(withdraw0, withdraw1) == Less)?, + (compare(withdraw1, withdraw0) == Greater)?, + (compare(withdraw0, mint0) == Greater)?, + (compare(withdraw0, spend0) == Greater)?, + (compare(withdraw0, publish0) == Less)?, + (compare(withdraw0, vote0) == Less)?, + (compare(withdraw0, propose0) == Less)?, + (compare(publish0, publish0) == Equal)?, + (compare(publish0, publish1) == Less)?, + (compare(publish1, publish0) == Greater)?, + (compare(publish0, mint0) == Greater)?, + (compare(publish0, spend0) == Greater)?, + (compare(publish0, withdraw0) == Greater)?, + (compare(publish0, vote0) == Less)?, + (compare(publish0, propose0) == Less)?, + (compare(vote0, vote0) == Equal)?, + (compare(vote0, vote1) == Less)?, + (compare(vote1, vote0) == Greater)?, + (compare(vote0, mint0) == Greater)?, + (compare(vote0, spend0) == Greater)?, + (compare(vote0, withdraw0) == Greater)?, + (compare(vote0, publish0) == Greater)?, + (compare(vote0, propose0) == Less)?, + (compare(propose0, propose0) == Equal)?, + (compare(propose0, propose1) == Less)?, + (compare(propose1, propose0) == Greater)?, + (compare(propose0, mint0) == Greater)?, + (compare(propose0, spend0) == Greater)?, + (compare(propose0, withdraw0) == Greater)?, + (compare(propose0, publish0) == Greater)?, + (compare(propose0, vote0) == Greater)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/packages.toml b/src/components/multisig/proxy/aiken-workspace/build/packages/packages.toml new file mode 100644 index 00000000..a0f1cf2a --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/packages.toml @@ -0,0 +1,9 @@ +[[packages]] +name = "aiken-lang/stdlib" +version = "v2.2.0" +source = "github" + +[[packages]] +name = "sidan-lab/vodka" +version = "0.1.13" +source = "github" diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/.github/workflows/build_docs.yml b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/.github/workflows/build_docs.yml new file mode 100644 index 00000000..89cc4e58 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/.github/workflows/build_docs.yml @@ -0,0 +1,50 @@ +# Simple workflow for deploying static content to GitHub Pages +name: Build CI + +on: + # Runs on pushes targeting the default branch + push: + branches: ["main"] + + # Allows you to run this workflow manually from the Actions tab + workflow_dispatch: + +# Sets permissions of the GITHUB_TOKEN to allow deployment to GitHub Pages +permissions: + contents: read + pages: write + id-token: write + +# Allow only one concurrent deployment, skipping runs queued between the run in-progress and latest queued. +# However, do NOT cancel in-progress runs as we want to allow these production deployments to complete. +concurrency: + group: "pages" + cancel-in-progress: false + +jobs: + # Single deploy job since we're just deploying + deploy: + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + - name: Setup Pages + uses: actions/configure-pages@v5 + + - uses: aiken-lang/setup-aiken@v1 + with: + version: v1.1.9 + - run: aiken fmt --check + - run: aiken check -D + - run: aiken docs + - name: Upload artifact + uses: actions/upload-pages-artifact@v3 + with: + # Upload entire repository + path: "./docs" + - name: Deploy to GitHub Pages + id: deployment + uses: actions/deploy-pages@v4 diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/.github/workflows/release.yml b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/.github/workflows/release.yml new file mode 100644 index 00000000..db43ff65 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/.github/workflows/release.yml @@ -0,0 +1,80 @@ +name: Auto Release + +on: + pull_request: + types: + - closed + branches: + - main + +jobs: + build: + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + - uses: aiken-lang/setup-aiken@v1 + with: + version: v1.1.9 + - run: aiken fmt --check + - run: aiken check -D + - run: aiken docs + + check-version: + runs-on: ubuntu-latest + if: github.event.pull_request.merged == true + outputs: + version-updated: ${{ steps.compare-versions.outputs.version-updated }} + version: ${{ steps.compare-versions.outputs.version }} + steps: + - name: Checkout main branch at commit before merge + uses: actions/checkout@v4 + with: + ref: ${{ github.event.pull_request.base.sha }} + + - name: Get package version from main branch before merge + id: pre-merge-version + run: | + PRE_MERGE_VERSION=$(grep -m 1 '^version = ' aiken.toml | sed 's/version = "\(.*\)"/\1/') + echo "pre_merge_version=$PRE_MERGE_VERSION" >> "$GITHUB_OUTPUT" + + - name: Checkout main branch at commit after merge + uses: actions/checkout@v4 + with: + ref: "main" + + - name: Get package version from main branch after merge + id: post-merge-version + run: | + POST_MERGE_VERSION=$(grep -m 1 '^version = ' aiken.toml | sed 's/version = "\(.*\)"/\1/') + echo "post_merge_version=$POST_MERGE_VERSION" >> "$GITHUB_OUTPUT" + + - name: Compare versions + id: compare-versions + run: | + if [[ "${{ steps.pre-merge-version.outputs.pre_merge_version }}" != "${{ steps.post-merge-version.outputs.post_merge_version }}" ]]; then + echo "version-updated=true" >> "$GITHUB_OUTPUT" + echo "version=${{ steps.post-merge-version.outputs.post_merge_version }}" >> "$GITHUB_OUTPUT" + else + echo "version-updated=false" >> "$GITHUB_OUTPUT" + fi + + release: + needs: [build, check-version] + if: needs.check-version.outputs.version-updated == 'true' + runs-on: ubuntu-latest + permissions: + contents: write + steps: + - name: Checkout repository + uses: actions/checkout@v4 + + - name: Create a Release in a GitHub Action + uses: comnoco/create-release-action@v2.0.5 + with: + tag_name: ${{ needs.check-version.outputs.version }} + release_name: ${{ needs.check-version.outputs.version }} + draft: false + prerelease: false + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/.gitignore b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/.gitignore new file mode 100644 index 00000000..7b31be95 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/.gitignore @@ -0,0 +1,16 @@ +# Generated by Cargo +# will have compiled files and executables +debug/ +target/ + +# Remove Cargo.lock from gitignore if creating an executable, leave it for libraries +# More information here https://doc.rust-lang.org/cargo/guide/cargo-toml-vs-cargo-lock.html +Cargo.lock + +# These are backup files generated by rustfmt +**/*.rs.bk + +# MSVC Windows builds of rustc generate these, which store debugging information +*.pdb + +docs \ No newline at end of file diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/LICENSE b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/LICENSE new file mode 100644 index 00000000..261eeb9e --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/LICENSE @@ -0,0 +1,201 @@ + Apache License + Version 2.0, January 2004 + http://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + + APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + + Copyright [yyyy] [name of copyright owner] + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/README.md b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/README.md new file mode 100644 index 00000000..7abc3ead --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/README.md @@ -0,0 +1,136 @@ +
+
+

Aiken Vodka - Library for Aiken Development

+ +[![Licence](https://img.shields.io/github/license/sidan-lab/vodka)](https://github.com/sidan-lab/vodka/blob/main/LICENSE) +[![Continuous Integration](https://github.com/sidan-lab/vodka/actions/workflows/build_docs.yml/badge.svg?branch=main)](https://github.com/sidan-lab/vodka/actions/workflows/build_docs.yml) +[![Twitter/X](https://img.shields.io/badge/Follow%20us-@sidan__lab-blue?logo=x)](https://x.com/sidan_lab) + +
+
+ +Vodka is a library build for [Aiken](https://aiken-lang.org/) development. It offers + +1. [Cocktail](https://sidan-lab.github.io/vodka/cocktail.html) - Validating utils in writing on-chain code in aiken +2. [Mocktail](https://sidan-lab.github.io/vodka/mocktail.html) - Unit test utils for easy building mock value for unit test + +## Start mixing + +Simply run + +```sh +aiken add sidan-lab/vodka --version 0.1.13 +``` + +or putting the below in you `aiken.toml` + +```toml +[[dependencies]] +name = "sidan-lab/vodka" +version = "0.1.13" +source = "github" +``` + +## Version + +Vodka is now upgraded to support latest PlutusV3 with latest version, if you want to use the old version compatible for legacy aiken version, please refer to below's table + +| Vodka | Aiken Compiler | `aiken-lang/stdlib` | +| ---------- | -------------- | ------------------- | +| 0.1.13 | ^v1.1.9 | v2.2.0 | +| 0.1.6 | ^v1.1.5 | v2.1.0 | +| 0.0.1-beta | v1.0.29-alpha | v1.9.0 | + +## Vodka is pure and simple + +For your transaction. + +```rs +let Transaction { inputs, outputs, extra_signatories, .. } = context.transaction +``` + +Locating inputs & outputs: + +```rs +when (inputs_at(inputs, target_address), outputs_at(outputs, target_address)) is { + ([only_input], [only_output]) -> ... + _ -> False +} +``` + +Checking signature with: + +```rs +key_signed(extra_signatories, key_hash_required) +``` + +## Imports and function groups + +All onchain utility functions can be imported from `cocktail` and are grouped with a naming convention of `vodka_`. + +```ak +use cocktail.{} +``` + +| Type | Naming Convention | +| ------------------------------------ | ----------------------------------------- | +| Address | `vodka_address.{}` | +| Value | `vodka_value.{}` | +| transaction.extra_signatories | `vodka_extra_signatories.{}` | +| transaction.inputs | `vodka_inputs.{}` | +| transaction.mints | `vodka_mints.{}` | +| transaction.outputs | `vodka_outputs.{}` | +| transaction.redeemers | `vodka_redeemers.{}` | +| transaction.validity_range | `vodka_validity_range.{}` | +| ByteArray and Int conversion & utils | `vodka_converter.{}` | + +## Taste it before vodka cocktail, mocktail can be mixed, blended and Mesh + +Building unit testing in vodka, easily indicating how you should build in [whisky](https://whisky.sidan.io/) and [Mesh](https://meshjs.dev/). + +You can taste if your transaction can pass your aiken contract validation: + +```rs +# Mock transaction +let mock_tx: Transaction = mocktail_tx() + ... + |> required_signer_hash(is_key_provided, mock_pub_key_hex(1)) + |> complete() +``` + +Then move it to blend a whisky: + +```rs +let mut tx = MeshTxBuilder::new_core() +tx.spending_plutus_script_v2() + ... + .required_signer_hash(key_hash) + .complete(None) + +``` + +Or Mesh: + +```ts +const txBuilder = new MeshTxBuilder(); +await txBuilder + ... + .requiredSignerHash(keyHash) + .complete(); +``` + +## CIP Support + +All CIP supporting utility can be imported under `cip` + +```rs +use cip.{cip68_100} + +let reference_token_name = cip68_100(asset_name) +``` + +## Documentation + +Please refer to the [hosted documentation](https://sidan-lab.github.io/vodka/). + +![Alt](https://repobeats.axiom.co/api/embed/54410212b620c3299be792bde8965a3371348895.svg "Repobeats analytics image") diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/aiken.lock b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/aiken.lock new file mode 100644 index 00000000..31951300 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/aiken.lock @@ -0,0 +1,15 @@ +# This file was generated by Aiken +# You typically do not need to edit this file + +[[requirements]] +name = "aiken-lang/stdlib" +version = "v2.2.0" +source = "github" + +[[packages]] +name = "aiken-lang/stdlib" +version = "v2.2.0" +requirements = [] +source = "github" + +[etags] diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/aiken.toml b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/aiken.toml new file mode 100644 index 00000000..2f35f2fb --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/aiken.toml @@ -0,0 +1,18 @@ +name = "sidan-lab/vodka" +version = "0.1.13" +compiler = "v1.1.9" +plutus = "v3" +license = "Apache-2.0" +description = "Aiken utils for project 'sidan-lab/vodka" + +[repository] +user = "sidan-lab" +project = "vodka" +platform = "github" + +[[dependencies]] +name = "aiken-lang/stdlib" +version = "v2.2.0" +source = "github" + +[config] diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/assets/logo.png b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/assets/logo.png new file mode 100644 index 00000000..2c456908 Binary files /dev/null and b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/assets/logo.png differ diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/aiken-compile.lock b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/aiken-compile.lock new file mode 100644 index 00000000..e69de29b diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.editorconfig b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.editorconfig new file mode 100644 index 00000000..0759674c --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.editorconfig @@ -0,0 +1,9 @@ +root = true + +[*.ak] +indent_style = space +indent_size = 2 +end_of_line = lf +charset = utf-8 +trim_trailing_whitespace = true +insert_final_newline = true diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.gitattributes b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.gitattributes new file mode 100644 index 00000000..99fefcf4 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.gitattributes @@ -0,0 +1,2 @@ +# Temp hack to get some syntax highlighting on github +*.ak linguist-language=Gleam diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.github/workflows/continuous-integration.yml b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.github/workflows/continuous-integration.yml new file mode 100644 index 00000000..b0081ac7 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.github/workflows/continuous-integration.yml @@ -0,0 +1,64 @@ +name: Continuous Integration + +on: + workflow_dispatch: + push: + branches: ["main"] + tags: ["*.*.*"] + pull_request: + branches: ["main"] + +env: + CARGO_TERM_COLOR: always + +permissions: + contents: read + pages: write + id-token: write + +concurrency: + group: "pages" + cancel-in-progress: true + +jobs: + build: + runs-on: ubuntu-latest + steps: + - name: 📥 Checkout repository + uses: actions/checkout@v3 + + - name: 🧰 Setup Pages + uses: actions/configure-pages@v2 + + - name: 🧰 Install Aiken + uses: aiken-lang/setup-aiken@v1 + with: + version: v1.1.9 + + - name: 📝 Run fmt + run: aiken fmt --check + + - name: 🔬 Run tests + run: aiken check + + - name: 📘 Generate documentation + shell: bash + working-directory: . + run: aiken docs -o docs + + - name: 📦 Upload artifact + uses: actions/upload-pages-artifact@v2 + with: + path: "docs/" + + deploy: + if: ${{ startsWith(github.ref, 'refs/tags') }} + needs: build + runs-on: ubuntu-latest + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + steps: + - name: 🚀 Deploy to GitHub Pages + id: deployment + uses: actions/deploy-pages@v1 diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.gitignore b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.gitignore new file mode 100644 index 00000000..3a3d38e6 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/.gitignore @@ -0,0 +1,3 @@ +build/ +docs/ +.DS_Store \ No newline at end of file diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/CHANGELOG.md b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/CHANGELOG.md new file mode 100644 index 00000000..62345b32 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/CHANGELOG.md @@ -0,0 +1,805 @@ +# Changelog + +## v2.2.0 - 2024-12-13 + +### Added + +- [`aiken/cbor.{deserialise}`](https://aiken-lang.github.io/stdlib/aiken/cbor.html#deserialise): to recover `Data` from CBOR bytes. +- [`aiken/collection/pairs.{insert_with_by_ascending_key}`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html#insert_with_by_ascending_key): for inserting in pairs while specifying how to combine values on key conflict. + +## v2.1.0 - 2024-09-14 + +### Added + +- Various new helper functions: + - [`aiken/collection/list.{for_each}`](https://aiken-lang.github.io/stdlib/aiken/collection/list.html#for_each): for performing many side-effects. + - [`aiken/collection/dict.{pop}`](https://aiken-lang.github.io/stdlib/aiken/collection/dict.html#pop): for accessing and removing a value from a dictionnary in a single op. + - [`aiken/primitive/bytearray.{starts_with}`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#starts_with): for matching bytearray prefixes. + - [`aiken/primitive/math/rational.{pow}`](https://aiken-lang.github.io/stdlib/aiken/primitive/math/rational.html#pow): for computing (int) powers of rational numbers. + - [`cardano/assets.{match}`](https://aiken-lang.github.io/stdlib/cardano/assets.html#match): efficiently compare two value-like. + - [`cardano/assets.{restricted_to}`](https://aiken-lang.github.io/stdlib/cardano/assets.html#restricted_to): extracting value subsets from parent value. + +- Comparison functions for various Cardano types: + - [`cardano/address/credential.{compare}`](https://aiken-lang.github.io/stdlib/cardano/address/credential.html#compare): for ordering credentials. + - [`cardano/governance/voter.{compare}`](https://aiken-lang.github.io/stdlib/cardano/governacen/voter.html#compare): for ordering voters. + - [`cardano/transaction/output_reference.{compare}`](https://aiken-lang.github.io/stdlib/cardano/transaction/output_reference.html#compare): for ordering output references. + - [`cardano/transaction/script_purpose.{compare}`](https://aiken-lang.github.io/stdlib/cardano/transaction/script_purpose.html#compare): for ordering script purpose. + +- New BLS12-381 crypto modules: + - [`aiken/crypto/bls12_381/g1`](https://aiken-lang.github.io/stdlib/aiken/crypto/bls12_381/g1.html) + - [`aiken/crypto/bls12_381/g2`](https://aiken-lang.github.io/stdlib/aiken/crypto/bls12_381/g2.html) + - [`aiken/crypto/bls12_381/scalar`](https://aiken-lang.github.io/stdlib/aiken/crypto/bls12_381/scalar.html) + +### Changed + +- N/A + +### Removed + +- N/A + +## v2.0.0 - 2024-09-01 + +> [!NOTE] +> Significant performance improvements (mostly on CPU) across all boards mostly due to the integration of Plutus V3. +> +>
see benchmarks +> +> test | cpu | mem +> --- | --- | --- +> aiken/cbor.{serialise_1} | -38.20% | ±0.00% +> aiken/cbor.{serialise_2} | -38.20% | ±0.00% +> aiken/cbor.{serialise_3} | -37.25% | ±0.00% +> aiken/cbor.{serialise_4} | -41.95% | ±0.00% +> aiken/cbor.{serialise_5} | -42.77% | ±0.00% +> aiken/cbor.{serialise_6} | -42.63% | ±0.00% +> aiken/cbor.{serialise_7} | -40.51% | ±0.00% +> aiken/cbor.{serialise_8} | -37.25% | ±0.00% +> aiken/cbor.{serialise_9} | -41.95% | ±0.00% +> aiken/cbor.{diagnostic_1} | -47.62% | -4.35% +> aiken/cbor.{diagnostic_2} | -45.16% | -2.87% +> aiken/cbor.{diagnostic_3} | -43.32% | -13.33% +> aiken/cbor.{diagnostic_4} | -38.28% | -8.03% +> aiken/cbor.{diagnostic_5} | -44.15% | -14.59% +> aiken/cbor.{diagnostic_6} | -42.77% | -12.21% +> aiken/cbor.{diagnostic_7} | -43.87% | -16.87% +> aiken/cbor.{diagnostic_7_alt} | -42.99% | -11.56% +> aiken/cbor.{diagnostic_8} | -46.00% | -10.23% +> aiken/cbor.{diagnostic_9} | -42.81% | -2.81% +> aiken/cbor.{diagnostic_10} | -38.28% | -8.03% +> aiken/cbor.{diagnostic_10_alt} | -38.43% | -8.03% +> aiken/cbor.{diagnostic_11} | -44.00% | -8.51% +> aiken/cbor.{diagnostic_12} | -45.65% | -11.56% +> aiken/cbor.{diagnostic_13} | -44.44% | -9.34% +> aiken/cbor.{diagnostic_14} | -43.59% | -19.77% +> aiken/cbor.{diagnostic_15} | -46.50% | -3.67% +> aiken/cbor.{diagnostic_16} | -41.89% | -13.41% +> aiken/collection/dict.{bench_from_ascending_pairs} | -20.48% | ±0.00% +> aiken/collection/dict.{from_list_1} | -20.16% | ±0.00% +> aiken/collection/dict.{from_list_2} | -18.28% | ±0.00% +> aiken/collection/dict.{from_list_3} | -17.83% | ±0.00% +> aiken/collection/dict.{from_list_4} | -18.97% | ±0.00% +> aiken/collection/dict.{bench_from_pairs} | -25.28% | ±0.00% +> aiken/collection/dict.{find_1} | -20.63% | ±0.00% +> aiken/collection/dict.{find_2} | -20.43% | ±0.00% +> aiken/collection/dict.{find_3} | -22.03% | ±0.00% +> aiken/collection/dict.{find_4} | -22.53% | ±0.00% +> aiken/collection/dict.{get_1} | -20.63% | ±0.00% +> aiken/collection/dict.{get_2} | -22.72% | ±0.00% +> aiken/collection/dict.{get_3} | -23.26% | ±0.00% +> aiken/collection/dict.{get_4} | -26.91% | ±0.00% +> aiken/collection/dict.{get_5} | -26.30% | ±0.00% +> aiken/collection/dict.{has_key_1} | -28.07% | ±0.00% +> aiken/collection/dict.{has_key_2} | -30.77% | ±0.00% +> aiken/collection/dict.{has_key_3} | -30.22% | ±0.00% +> aiken/collection/dict.{has_key_4} | -27.25% | ±0.00% +> aiken/collection/dict.{is_empty_1} | -27.86% | ±0.00% +> aiken/collection/dict.{keys_1} | -20.30% | ±0.00% +> aiken/collection/dict.{keys_2} | -17.48% | ±0.00% +> aiken/collection/dict.{size_1} | -37.90% | ±0.00% +> aiken/collection/dict.{size_2} | -32.34% | ±0.00% +> aiken/collection/dict.{size_3} | -27.97% | ±0.00% +> aiken/collection/dict.{values_1} | -20.30% | ±0.00% +> aiken/collection/dict.{values_2} | -17.58% | ±0.00% +> aiken/collection/dict.{delete_1} | -20.16% | ±0.00% +> aiken/collection/dict.{delete_2} | -24.29% | ±0.00% +> aiken/collection/dict.{delete_3} | -21.03% | ±0.00% +> aiken/collection/dict.{delete_4} | -25.03% | ±0.00% +> aiken/collection/dict.{delete_5} | -27.22% | ±0.00% +> aiken/collection/dict.{delete_6} | -25.83% | ±0.00% +> aiken/collection/dict.{filter_1} | -20.16% | ±0.00% +> aiken/collection/dict.{filter_2} | -19.61% | ±0.00% +> aiken/collection/dict.{filter_3} | -20.15% | ±0.00% +> aiken/collection/dict.{insert_1} | -22.83% | ±0.00% +> aiken/collection/dict.{insert_2} | -21.77% | ±0.00% +> aiken/collection/dict.{insert_with_1} | -17.21% | ±0.00% +> aiken/collection/dict.{insert_with_2} | -22.66% | ±0.00% +> aiken/collection/dict.{insert_with_3} | -25.81% | ±0.00% +> aiken/collection/dict.{map_1} | -19.56% | ±0.00% +> aiken/collection/dict.{map_2} | -23.66% | ±0.00% +> aiken/collection/dict.{union_1} | -17.91% | ±0.00% +> aiken/collection/dict.{union_2} | -8.67% | ±0.00% +> aiken/collection/dict.{union_3} | -22.82% | ±0.00% +> aiken/collection/dict.{union_4} | -22.77% | ±0.00% +> aiken/collection/dict.{union_with_1} | -22.90% | ±0.00% +> aiken/collection/dict.{fold_1} | -35.94% | ±0.00% +> aiken/collection/dict.{fold_2} | -22.31% | ±0.00% +> aiken/collection/dict.{foldr_1} | -36.21% | ±0.00% +> aiken/collection/dict.{foldr_2} | -21.93% | ±0.00% +> aiken/collection/dict.{to_list_1} | -98.69% | -66.72% +> aiken/collection/dict.{to_list_2} | -98.91% | -66.72% +> aiken/collection/list.{push_1} | -8.02% | ±0.00% +> aiken/collection/list.{push_2} | 1.25% | ±0.00% +> aiken/collection/list.{range_1} | -27.77% | ±0.00% +> aiken/collection/list.{range_2} | -27.39% | ±0.00% +> aiken/collection/list.{repeat_1} | -23.72% | ±0.00% +> aiken/collection/list.{repeat_2} | -27.96% | ±0.00% +> aiken/collection/list.{all_1} | -28.36% | ±0.00% +> aiken/collection/list.{all_2} | -27.59% | ±0.00% +> aiken/collection/list.{all_3} | -27.94% | ±0.00% +> aiken/collection/list.{any_1} | -28.23% | ±0.00% +> aiken/collection/list.{any_2} | -28.09% | ±0.00% +> aiken/collection/list.{any_3} | -26.95% | ±0.00% +> aiken/collection/list.{at_1} | -27.60% | ±0.00% +> aiken/collection/list.{at_2} | -19.96% | ±0.00% +> aiken/collection/list.{at_3} | -27.60% | ±0.00% +> aiken/collection/list.{at_4} | -20.77% | ±0.00% +> aiken/collection/list.{at_5} | -25.75% | ±0.00% +> aiken/collection/list.{count_empty} | -36.83% | ±0.00% +> aiken/collection/list.{count_all} | -32.37% | ±0.00% +> aiken/collection/list.{count_some} | -31.73% | ±0.00% +> aiken/collection/list.{count_none} | -30.44% | ±0.00% +> aiken/collection/list.{find_1} | -20.59% | ±0.00% +> aiken/collection/list.{find_2} | -25.53% | ±0.00% +> aiken/collection/list.{find_3} | -19.64% | ±0.00% +> aiken/collection/list.{has_1} | -27.88% | ±0.00% +> aiken/collection/list.{has_2} | -27.69% | ±0.00% +> aiken/collection/list.{has_3} | -26.95% | ±0.00% +> aiken/collection/list.{head_1} | -14.03% | ±0.00% +> aiken/collection/list.{head_2} | -16.90% | ±0.00% +> aiken/collection/list.{is_empty_1} | -26.48% | ±0.00% +> aiken/collection/list.{is_empty_2} | -25.35% | ±0.00% +> aiken/collection/list.{index_of_1} | -25.62% | ±0.00% +> aiken/collection/list.{index_of_2} | -27.52% | ±0.00% +> aiken/collection/list.{index_of_3} | -26.65% | ±0.00% +> aiken/collection/list.{index_of_4} | -19.96% | ±0.00% +> aiken/collection/list.{last_1} | -19.18% | ±0.00% +> aiken/collection/list.{last_2} | -16.26% | ±0.00% +> aiken/collection/list.{last_3} | -17.13% | ±0.00% +> aiken/collection/list.{length_1} | -37.90% | ±0.00% +> aiken/collection/list.{length_2} | -30.89% | ±0.00% +> aiken/collection/list.{delete_1} | -20.20% | ±0.00% +> aiken/collection/list.{delete_2} | -15.02% | ±0.00% +> aiken/collection/list.{delete_3} | -20.55% | ±0.00% +> aiken/collection/list.{delete_4} | -22.46% | ±0.00% +> aiken/collection/list.{drop_1} | -24.62% | ±0.00% +> aiken/collection/list.{drop_2} | -28.08% | ±0.00% +> aiken/collection/list.{drop_while_1} | -19.79% | ±0.00% +> aiken/collection/list.{drop_while_2} | -22.25% | ±0.00% +> aiken/collection/list.{drop_while_3} | 0.86% | ±0.00% +> aiken/collection/list.{drop_while_4} | -27.26% | ±0.00% +> aiken/collection/list.{filter_1} | -20.20% | ±0.00% +> aiken/collection/list.{filter_2} | -32.06% | ±0.00% +> aiken/collection/list.{filter_3} | -31.39% | ±0.00% +> aiken/collection/list.{filter_map_1} | -21.10% | ±0.00% +> aiken/collection/list.{filter_map_2} | -28.74% | ±0.00% +> aiken/collection/list.{init_1} | -19.64% | ±0.00% +> aiken/collection/list.{init_2} | -20.01% | ±0.00% +> aiken/collection/list.{init_3} | -13.72% | ±0.00% +> aiken/collection/list.{partition_1} | -14.63% | ±0.00% +> aiken/collection/list.{partition_2} | -16.85% | ±0.00% +> aiken/collection/list.{partition_3} | -16.63% | ±0.00% +> aiken/collection/list.{partition_4} | -16.87% | ±0.00% +> aiken/collection/list.{partition_5} | -22.94% | ±0.00% +> aiken/collection/list.{slice_1} | -29.08% | -2.81% +> aiken/collection/list.{slice_2} | -30.11% | -2.25% +> aiken/collection/list.{slice_3} | -30.29% | -1.46% +> aiken/collection/list.{slice_4} | -28.53% | -1.48% +> aiken/collection/list.{slice_5} | -29.73% | -1.64% +> aiken/collection/list.{slice_6} | -32.01% | -1.80% +> aiken/collection/list.{span_1} | -15.05% | ±0.00% +> aiken/collection/list.{span_2} | -18.03% | ±0.00% +> aiken/collection/list.{span_3} | -12.49% | ±0.00% +> aiken/collection/list.{span_4} | -18.13% | ±0.00% +> aiken/collection/list.{tail_1} | -8.88% | ±0.00% +> aiken/collection/list.{tail_2} | -16.90% | ±0.00% +> aiken/collection/list.{take_1} | -24.98% | ±0.00% +> aiken/collection/list.{take_2} | -24.35% | ±0.00% +> aiken/collection/list.{take_while_1} | -20.20% | ±0.00% +> aiken/collection/list.{take_while_2} | -21.56% | ±0.00% +> aiken/collection/list.{take_while_3} | -22.46% | ±0.00% +> aiken/collection/list.{take_while_4} | -21.02% | ±0.00% +> aiken/collection/list.{unique_1} | -20.20% | ±0.00% +> aiken/collection/list.{unique_2} | -24.34% | ±0.00% +> aiken/collection/list.{flat_map_1} | -19.79% | ±0.00% +> aiken/collection/list.{flat_map_2} | -13.36% | ±0.00% +> aiken/collection/list.{indexed_map_1} | -20.10% | ±0.00% +> aiken/collection/list.{indexed_map_2} | -23.36% | ±0.00% +> aiken/collection/list.{map_1} | -19.79% | ±0.00% +> aiken/collection/list.{map_2} | -16.75% | ±0.00% +> aiken/collection/list.{map2_1} | -20.10% | ±0.00% +> aiken/collection/list.{map2_2} | -17.46% | ±0.00% +> aiken/collection/list.{map2_3} | -15.92% | ±0.00% +> aiken/collection/list.{map3_1} | -20.39% | ±0.00% +> aiken/collection/list.{map3_2} | -19.22% | ±0.00% +> aiken/collection/list.{reverse_1} | -20.10% | ±0.00% +> aiken/collection/list.{reverse_2} | -12.26% | ±0.00% +> aiken/collection/list.{sort_1} | -22.31% | ±0.00% +> aiken/collection/list.{sort_2} | -17.93% | ±0.00% +> aiken/collection/list.{sort_3} | -23.09% | ±0.00% +> aiken/collection/list.{sort_4} | -20.20% | ±0.00% +> aiken/collection/list.{unzip_1} | -14.01% | ±0.00% +> aiken/collection/list.{unzip_2} | -5.48% | ±0.00% +> aiken/collection/list.{concat_1} | -6.56% | ±0.00% +> aiken/collection/list.{concat_2} | -11.25% | ±0.00% +> aiken/collection/list.{concat_3} | -9.35% | ±0.00% +> aiken/collection/list.{difference_1} | -24.23% | ±0.00% +> aiken/collection/list.{difference_2} | -22.59% | ±0.00% +> aiken/collection/list.{difference_3} | -10.64% | ±0.00% +> aiken/collection/list.{difference_4} | -21.68% | ±0.00% +> aiken/collection/list.{zip_1} | -20.10% | ±0.00% +> aiken/collection/list.{zip_2} | -19.17% | ±0.00% +> aiken/collection/list.{zip_3} | -10.35% | ±0.00% +> aiken/collection/list.{foldl_1} | -36.95% | ±0.00% +> aiken/collection/list.{foldl_2} | -26.90% | ±0.00% +> aiken/collection/list.{foldl_3} | -11.27% | ±0.00% +> aiken/collection/list.{foldr_1} | -26.68% | ±0.00% +> aiken/collection/list.{foldr_2} | -38.04% | ±0.00% +> aiken/collection/list.{foldr_3} | -10.14% | ±0.00% +> aiken/collection/list.{indexed_foldr_1} | -36.95% | ±0.00% +> aiken/collection/list.{indexed_foldr_2} | -11.06% | ±0.00% +> aiken/collection/list.{reduce_1} | -36.95% | ±0.00% +> aiken/collection/list.{reduce_2} | -27.99% | ±0.00% +> aiken/collection/list.{reduce_3} | -23.54% | ±0.00% +> aiken/collection/list.{reduce_4} | -24.84% | ±0.00% +> aiken/collection/pairs.{get_all_1} | -21.10% | ±0.00% +> aiken/collection/pairs.{get_all_2} | -18.86% | ±0.00% +> aiken/collection/pairs.{get_all_3} | -19.53% | ±0.00% +> aiken/collection/pairs.{get_all_4} | -18.70% | ±0.00% +> aiken/collection/pairs.{get_all_5} | -21.19% | ±0.00% +> aiken/collection/pairs.{get_first_1} | -20.63% | ±0.00% +> aiken/collection/pairs.{get_first_2} | -18.86% | ±0.00% +> aiken/collection/pairs.{get_first_3} | -18.86% | ±0.00% +> aiken/collection/pairs.{get_first_4} | -18.86% | ±0.00% +> aiken/collection/pairs.{get_first_5} | -21.05% | ±0.00% +> aiken/collection/pairs.{get_last_1} | -20.63% | ±0.00% +> aiken/collection/pairs.{get_last_2} | -21.13% | ±0.00% +> aiken/collection/pairs.{get_last_3} | -21.16% | ±0.00% +> aiken/collection/pairs.{get_last_4} | -21.79% | ±0.00% +> aiken/collection/pairs.{get_last_5} | -21.05% | ±0.00% +> aiken/collection/pairs.{find_all_1} | -21.10% | ±0.00% +> aiken/collection/pairs.{find_all_2} | -18.33% | ±0.00% +> aiken/collection/pairs.{find_all_3} | -20.51% | ±0.00% +> aiken/collection/pairs.{find_all_4} | -17.79% | ±0.00% +> aiken/collection/pairs.{find_first_1} | -20.63% | ±0.00% +> aiken/collection/pairs.{find_first_2} | -18.28% | ±0.00% +> aiken/collection/pairs.{find_first_3} | -20.22% | ±0.00% +> aiken/collection/pairs.{find_first_4} | -18.28% | ±0.00% +> aiken/collection/pairs.{find_last_1} | -20.63% | ±0.00% +> aiken/collection/pairs.{find_last_2} | -20.70% | ±0.00% +> aiken/collection/pairs.{find_last_3} | -20.22% | ±0.00% +> aiken/collection/pairs.{find_last_4} | -20.98% | ±0.00% +> aiken/collection/pairs.{has_key_1} | -28.07% | ±0.00% +> aiken/collection/pairs.{has_key_2} | -25.70% | ±0.00% +> aiken/collection/pairs.{has_key_3} | -25.80% | ±0.00% +> aiken/collection/pairs.{has_key_4} | -24.93% | ±0.00% +> aiken/collection/pairs.{has_key_5} | -25.70% | ±0.00% +> aiken/collection/pairs.{keys_1} | -20.30% | ±0.00% +> aiken/collection/pairs.{keys_2} | -13.89% | ±0.00% +> aiken/collection/pairs.{keys_3} | -10.43% | ±0.00% +> aiken/collection/pairs.{values_1} | -20.30% | ±0.00% +> aiken/collection/pairs.{values_2} | -14.02% | ±0.00% +> aiken/collection/pairs.{values_3} | -10.65% | ±0.00% +> aiken/collection/pairs.{values_4} | -8.53% | ±0.00% +> aiken/collection/pairs.{map_1} | -11.17% | ±0.00% +> aiken/collection/pairs.{map_2} | -12.89% | ±0.00% +> aiken/collection/pairs.{foldl_1} | -35.94% | ±0.00% +> aiken/collection/pairs.{foldl_2} | -22.31% | ±0.00% +> aiken/collection/pairs.{foldr_1} | -36.21% | ±0.00% +> aiken/collection/pairs.{foldr_2} | -21.93% | ±0.00% +> aiken/collection/pairs.{foldr_3} | -20.00% | ±0.00% +> aiken/interval.{contains_1} | -21.08% | -4.01% +> aiken/interval.{contains_2} | -31.22% | -13.95% +> aiken/interval.{contains_3} | -26.80% | -10.08% +> aiken/interval.{contains_4} | -31.02% | -13.67% +> aiken/interval.{contains_5} | -32.32% | -13.59% +> aiken/interval.{contains_6} | -28.15% | -9.81% +> aiken/interval.{contains_7} | -32.11% | -13.32% +> aiken/interval.{contains_8} | -29.56% | -12.59% +> aiken/interval.{contains_9} | -29.68% | -12.78% +> aiken/interval.{contains_10} | -29.68% | -12.78% +> aiken/interval.{contains_11} | -35.17% | -17.77% +> aiken/interval.{contains_12} | -21.09% | -3.86% +> aiken/interval.{is_entirely_after_1} | -29.89% | -13.81% +> aiken/interval.{is_entirely_after_2} | -29.63% | -13.39% +> aiken/interval.{is_entirely_after_3} | -29.63% | -13.39% +> aiken/interval.{is_entirely_after_4} | -29.48% | -11.81% +> aiken/interval.{is_entirely_after_5} | -29.70% | -12.14% +> aiken/interval.{is_entirely_after_6} | -36.09% | -19.77% +> aiken/interval.{is_entirely_after_7} | -24.19% | -3.99% +> aiken/interval.{is_entirely_after_8} | -24.19% | -3.99% +> aiken/interval.{is_entirely_after_9} | -24.19% | -3.99% +> aiken/interval.{is_entirely_before_1} | -28.44% | -13.48% +> aiken/interval.{is_entirely_before_2} | -28.24% | -13.09% +> aiken/interval.{is_entirely_before_3} | -28.24% | -13.09% +> aiken/interval.{is_entirely_before_4} | -28.44% | -11.88% +> aiken/interval.{is_entirely_before_5} | -28.26% | -11.57% +> aiken/interval.{is_entirely_before_6} | -34.63% | -19.34% +> aiken/interval.{is_entirely_before_7} | -22.97% | -4.02% +> aiken/interval.{is_entirely_before_8} | -22.97% | -4.02% +> aiken/interval.{is_entirely_before_9} | -22.97% | -4.02% +> aiken/interval.{hull_1} | -21.51% | -0.73% +> aiken/interval.{hull_2} | -23.06% | -0.80% +> aiken/interval.{hull_3} | -22.00% | -0.86% +> aiken/interval.{intersection_1} | -21.51% | -0.73% +> aiken/interval.{intersection_2} | -21.51% | -0.73% +> aiken/interval.{intersection_3} | -26.55% | -4.65% +> aiken/interval.{intersection_4} | -26.45% | -4.51% +> aiken/interval.{intersection_5} | -22.87% | -0.76% +> aiken/interval.{intersection_6} | -19.73% | -0.98% +> aiken/math.{abs_1} | -61.39% | -21.07% +> aiken/math.{abs_2} | -70.90% | -34.84% +> aiken/math.{clamp_1} | -60.95% | -23.55% +> aiken/math.{clamp_2} | -60.95% | -23.55% +> aiken/math.{clamp_3} | -59.22% | -18.20% +> aiken/math.{gcd_test1} | -47.20% | ±0.00% +> aiken/math.{gcd_test2} | -47.81% | ±0.00% +> aiken/math.{gcd_test3} | -46.10% | ±0.00% +> aiken/math.{is_sqrt1} | -87.41% | -68.64% +> aiken/math.{is_sqrt2} | -87.41% | -68.64% +> aiken/math.{log_10_2} | -51.35% | -8.40% +> aiken/math.{log_42_2} | -51.46% | -8.24% +> aiken/math.{log_42_3} | -51.05% | -7.81% +> aiken/math.{log_5_0} | -54.05% | -12.92% +> aiken/math.{log_4_4} | -50.59% | -9.31% +> aiken/math.{log_4_43} | -49.14% | -7.28% +> aiken/math.{max_1} | -61.39% | -21.07% +> aiken/math.{max_2} | -61.39% | -21.07% +> aiken/math.{max_3} | -61.39% | -21.07% +> aiken/math.{min_1} | -61.39% | -21.07% +> aiken/math.{min_2} | -61.39% | -21.07% +> aiken/math.{min_3} | -61.39% | -21.07% +> aiken/math.{pow_3_5} | -46.34% | ±0.00% +> aiken/math.{pow_7_2} | -46.38% | ±0.00% +> aiken/math.{pow_3__4} | -43.50% | ±0.00% +> aiken/math.{pow_0_0} | -43.95% | ±0.00% +> aiken/math.{pow_513_3} | -45.80% | ±0.00% +> aiken/math.{pow_2_4} | -46.79% | ±0.00% +> aiken/math.{pow_2_42} | -46.77% | ±0.00% +> aiken/math.{pow2_neg} | -44.71% | ±0.00% +> aiken/math.{pow2_0} | -45.00% | ±0.00% +> aiken/math.{pow2_1} | -45.00% | ±0.00% +> aiken/math.{pow2_4} | -45.00% | ±0.00% +> aiken/math.{pow2_42} | -42.01% | ±0.00% +> aiken/math.{pow2_256} | -41.40% | ±0.00% +> aiken/math.{sqrt1} | -32.56% | -17.18% +> aiken/math.{sqrt2} | -32.56% | -17.18% +> aiken/math.{sqrt3} | -49.99% | -8.90% +> aiken/math.{sqrt4} | -51.76% | -3.90% +> aiken/math.{sqrt5} | -52.63% | -1.33% +> aiken/math.{sqrt6} | -28.16% | -15.41% +> aiken/math/rational.{from_int_1} | -14.32% | ±0.00% +> aiken/math/rational.{new_1} | -22.98% | ±0.00% +> aiken/math/rational.{zero_1} | -8.08% | ±0.00% +> aiken/math/rational.{denominator_1} | -28.33% | ±0.00% +> aiken/math/rational.{numerator_1} | -29.34% | ±0.00% +> aiken/math/rational.{abs_examples} | -18.25% | ±0.00% +> aiken/math/rational.{negate_1} | -15.39% | ±0.00% +> aiken/math/rational.{reciprocal_1} | -23.28% | ±0.00% +> aiken/math/rational.{reduce_1} | -31.89% | ±0.00% +> aiken/math/rational.{add_1} | -15.11% | ±0.00% +> aiken/math/rational.{add_2} | -15.11% | ±0.00% +> aiken/math/rational.{div_1} | -22.31% | -2.75% +> aiken/math/rational.{div_2} | -22.37% | -2.79% +> aiken/math/rational.{mul_1} | -13.37% | ±0.00% +> aiken/math/rational.{mul_2} | -13.37% | ±0.00% +> aiken/math/rational.{mul_3} | -26.25% | ±0.00% +> aiken/math/rational.{sub_1} | -15.11% | ±0.00% +> aiken/math/rational.{sub_2} | -15.11% | ±0.00% +> aiken/math/rational.{sub_3} | -15.11% | ±0.00% +> aiken/math/rational.{compare_1} | -21.70% | ±0.00% +> aiken/math/rational.{compare_with_eq} | -23.05% | ±0.00% +> aiken/math/rational.{compare_with_neq} | -22.33% | ±0.00% +> aiken/math/rational.{compare_with_gte} | -22.48% | ±0.00% +> aiken/math/rational.{compare_with_gt} | -23.18% | ±0.00% +> aiken/math/rational.{compare_with_lte} | -22.48% | ±0.00% +> aiken/math/rational.{compare_with_lt} | -23.18% | ±0.00% +> aiken/math/rational.{arithmetic_mean_1} | -23.31% | ±0.00% +> aiken/math/rational.{arithmetic_mean_2} | -23.31% | ±0.00% +> aiken/math/rational.{arithmetic_mean_3} | -20.58% | ±0.00% +> aiken/math/rational.{geometric_mean1} | -29.87% | ±0.00% +> aiken/math/rational.{geometric_mean2} | -24.52% | ±0.00% +> aiken/math/rational.{geometric_mean3} | -24.52% | ±0.00% +> aiken/math/rational.{geometric_mean4} | -33.55% | ±0.00% +> aiken/math/rational.{geometric_mean5} | -45.34% | ±0.00% +> aiken/math/rational.{ceil_1} | -36.26% | ±0.00% +> aiken/math/rational.{floor_1} | -29.49% | ±0.00% +> aiken/math/rational.{proper_fraction_1} | -18.44% | ±0.00% +> aiken/math/rational.{proper_fraction_2} | -18.44% | ±0.00% +> aiken/math/rational.{proper_fraction_3} | -18.44% | ±0.00% +> aiken/math/rational.{round_1} | -25.17% | ±0.00% +> aiken/math/rational.{round_even_1} | -25.91% | ±0.00% +> aiken/math/rational.{truncate_1} | -29.49% | ±0.00% +> aiken/option.{is_none_1} | -26.56% | ±0.00% +> aiken/option.{is_none_2} | -27.52% | ±0.00% +> aiken/option.{is_some_1} | -27.52% | ±0.00% +> aiken/option.{is_some_2} | -26.56% | ±0.00% +> aiken/option.{and_then_1} | -20.19% | ±0.00% +> aiken/option.{and_then_2} | -22.15% | ±0.00% +> aiken/option.{and_then_3} | -21.85% | ±0.00% +> aiken/option.{choice_1} | -17.11% | ±0.00% +> aiken/option.{choice_2} | -19.75% | ±0.00% +> aiken/option.{choice_3} | -18.68% | ±0.00% +> aiken/option.{flatten_1} | -12.25% | ±0.00% +> aiken/option.{flatten_2} | -15.41% | ±0.00% +> aiken/option.{flatten_3} | -19.46% | ±0.00% +> aiken/option.{flatten_4} | -14.31% | ±0.00% +> aiken/option.{map_1} | -19.89% | ±0.00% +> aiken/option.{map_2} | -18.18% | ±0.00% +> aiken/option.{map2_1} | -20.47% | ±0.00% +> aiken/option.{map2_2} | -19.93% | ±0.00% +> aiken/option.{map2_3} | -13.64% | ±0.00% +> aiken/option.{map3_1} | -20.74% | ±0.00% +> aiken/option.{map3_2} | -20.00% | ±0.00% +> aiken/option.{map3_3} | -19.90% | ±0.00% +> aiken/option.{or_try_1} | -14.36% | ±0.00% +> aiken/option.{or_try_2} | -14.36% | ±0.00% +> aiken/option.{or_else_1} | -38.16% | ±0.00% +> aiken/option.{or_else_2} | -27.62% | ±0.00% +> aiken/primitive/bytearray.{from_string_1} | -62.36% | ±0.00% +> aiken/primitive/bytearray.{from_string_2} | -41.62% | ±0.00% +> aiken/primitive/bytearray.{push_1} | -97.51% | -80.06% +> aiken/primitive/bytearray.{push_2} | -97.51% | -80.06% +> aiken/primitive/bytearray.{push_3} | -88.82% | -89.83% +> aiken/primitive/bytearray.{index_of_1} | -39.75% | ±0.00% +> aiken/primitive/bytearray.{index_of_2} | -43.19% | ±0.00% +> aiken/primitive/bytearray.{index_of_3} | -41.70% | ±0.00% +> aiken/primitive/bytearray.{index_of_4} | -37.24% | ±0.00% +> aiken/primitive/bytearray.{index_of_5} | -26.02% | ±0.00% +> aiken/primitive/bytearray.{is_empty_1} | -37.52% | ±0.00% +> aiken/primitive/bytearray.{is_empty_2} | -33.77% | ±0.00% +> aiken/primitive/bytearray.{length_1} | -49.73% | ±0.00% +> aiken/primitive/bytearray.{length_2} | -49.73% | ±0.00% +> aiken/primitive/bytearray.{test_bit_0} | -45.48% | 5.88% +> aiken/primitive/bytearray.{test_bit_1} | -56.22% | -10.85% +> aiken/primitive/bytearray.{test_bit_2} | -56.22% | -10.85% +> aiken/primitive/bytearray.{test_bit_3} | -56.22% | -10.85% +> aiken/primitive/bytearray.{test_bit_7} | -58.31% | -11.81% +> aiken/primitive/bytearray.{test_bit_8} | -56.22% | -10.85% +> aiken/primitive/bytearray.{test_bit_20_21_22_23} | -44.38% | 5.52% +> aiken/primitive/bytearray.{drop_1} | -58.79% | ±0.00% +> aiken/primitive/bytearray.{drop_2} | -58.79% | ±0.00% +> aiken/primitive/bytearray.{drop_3} | -58.79% | ±0.00% +> aiken/primitive/bytearray.{drop_4} | -58.79% | ±0.00% +> aiken/primitive/bytearray.{slice_1} | -98.79% | -90.04% +> aiken/primitive/bytearray.{slice_2} | -98.79% | -90.04% +> aiken/primitive/bytearray.{slice_3} | -98.79% | -90.04% +> aiken/primitive/bytearray.{slice_4} | -98.79% | -90.04% +> aiken/primitive/bytearray.{slice_5} | -98.79% | -90.04% +> aiken/primitive/bytearray.{take_1} | -97.81% | -83.40% +> aiken/primitive/bytearray.{take_2} | -97.81% | -83.40% +> aiken/primitive/bytearray.{take_3} | -97.81% | -83.40% +> aiken/primitive/bytearray.{take_4} | -97.81% | -83.40% +> aiken/primitive/bytearray.{concat_1} | -96.22% | -80.06% +> aiken/primitive/bytearray.{concat_2} | -96.22% | -80.06% +> aiken/primitive/bytearray.{concat_3} | -96.22% | -80.06% +> aiken/primitive/bytearray.{concat_4} | -96.22% | -80.06% +> aiken/primitive/bytearray.{foldl_1} | -40.96% | ±0.00% +> aiken/primitive/bytearray.{foldl_2} | -40.09% | ±0.00% +> aiken/primitive/bytearray.{foldl_3} | -40.29% | ±0.00% +> aiken/primitive/bytearray.{foldl_4} | -44.76% | ±0.00% +> aiken/primitive/bytearray.{foldr_1} | -42.56% | ±0.00% +> aiken/primitive/bytearray.{foldr_2} | -40.93% | ±0.00% +> aiken/primitive/bytearray.{foldr_3} | -45.34% | ±0.00% +> aiken/primitive/bytearray.{reduce_1} | -42.95% | ±0.00% +> aiken/primitive/bytearray.{reduce_2} | -44.60% | ±0.00% +> aiken/primitive/bytearray.{to_string_1} | -69.56% | ±0.00% +> aiken/primitive/bytearray.{to_string_2} | -53.54% | ±0.00% +> aiken/primitive/bytearray.{to_hex_1} | -48.15% | ±0.00% +> aiken/primitive/bytearray.{to_hex_2} | -48.15% | ±0.00% +> aiken/primitive/int.{from_utf8_1} | -37.06% | ±0.00% +> aiken/primitive/int.{from_utf8_2} | -33.40% | ±0.00% +> aiken/primitive/int.{from_utf8_3} | -37.06% | ±0.00% +> aiken/primitive/int.{from_utf8_4} | -32.78% | ±0.00% +> aiken/primitive/int.{from_utf8_5} | -32.05% | ±0.00% +> aiken/primitive/int.{from_utf8_6} | -31.36% | ±0.00% +> aiken/primitive/string.{from_bytearray_1} | -69.56% | ±0.00% +> aiken/primitive/string.{from_bytearray_2} | -53.54% | ±0.00% +> aiken/primitive/string.{from_bytearray_3} | -53.54% | ±0.00% +> aiken/primitive/string.{from_int_1} | -40.54% | -7.05% +> aiken/primitive/string.{from_int_2} | -45.93% | -5.30% +> aiken/primitive/string.{from_int_3} | -47.62% | -4.35% +> aiken/primitive/string.{from_int_4} | -48.58% | -3.69% +> aiken/primitive/string.{concat_1} | -92.30% | -80.10% +> aiken/primitive/string.{concat_2} | -97.34% | -85.87% +> aiken/primitive/string.{concat_3} | -98.67% | -80.35% +> aiken/primitive/string.{join_1} | -42.87% | ±0.00% +> aiken/primitive/string.{join_2} | -37.65% | ±0.00% +> aiken/primitive/string.{to_bytearray_1} | -62.36% | ±0.00% +> aiken/primitive/string.{to_bytearray_2} | -41.62% | ±0.00% +> aiken/primitive/string.{to_bytearray_3} | -41.62% | ±0.00% +> cardano/assets.{from_asset_list_1} | -20.51% | ±0.00% +> cardano/assets.{from_asset_list_2} | -10.09% | ±0.00% +> cardano/assets.{from_asset_list_3} | -12.21% | ±0.00% +> cardano/assets.{from_asset_list_4} | -16.22% | ±0.00% +> cardano/assets.{from_asset_list_5} | -14.60% | ±0.00% +> cardano/assets.{from_asset_list_6} | -20.97% | ±0.00% +> cardano/assets.{from_asset_list_7} | -20.25% | ±0.00% +> cardano/assets.{from_asset_list_8} | -14.51% | ±0.00% +> cardano/assets.{from_asset_list_9} | -16.07% | ±0.00% +> cardano/assets.{add_1} | -27.84% | ±0.00% +> cardano/assets.{add_2} | -27.56% | -0.54% +> cardano/assets.{add_3} | -26.39% | ±0.00% +> cardano/assets.{add_4} | -29.75% | -10.41% +> cardano/assets.{add_5} | -27.80% | ±0.00% +> cardano/assets.{merge_1} | -26.02% | ±0.00% +> cardano/assets.{merge_2} | -19.60% | ±0.00% +> cardano/assets.{merge_3} | -23.80% | ±0.00% +> cardano/assets.{merge_4} | -25.92% | ±0.00% +> cardano/assets.{merge_5} | -27.61% | -1.98% +> cardano/assets.{without_lovelace_1} | -28.00% | -2.24% +> cardano/assets.{without_lovelace_2} | -27.49% | ±0.00% +> cardano/assets.{without_lovelace_3} | -23.40% | -0.34% +> cardano/assets.{flatten_with_1} | -21.10% | ±0.00% +> cardano/assets.{flatten_with_2} | -22.77% | ±0.00% +> cardano/assets.{reduce_1} | -24.31% | ±0.00% +> cardano/assets.{reduce_2} | -20.89% | ±0.00% +> cardano/assets.{reduce_3} | -36.21% | ±0.00% +>
+ +### Added + +- New modules covering Conway-related features (i.e. governance) + - [`cardano/governance`](https://aiken-lang.github.io/stdlib/cardano/governance.html) + - [`cardano/governance/protocol_parameters`](https://aiken-lang.github.io/stdlib/cardano/governance/protocol_parameters.html) + +- New primitives in `aiken/collection/pairs`: + - [`insert_by_ascending_key`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html#insert_by_ascending_key) + - [`repsert_by_ascending_key`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html#repsert_by_ascending_key) + +- New primitives in `aiken/crypto`: + - [`blake2b_224`](https://aiken-lang.github.io/stdlib/aiken/crypto.html#blake2b_224) + - [`keccak_256`](https://aiken-lang.github.io/stdlib/aiken/crypto.html#keccak_256) + +- New primitives in `aiken/math`: + - [`log2`](https://aiken-lang.github.io/stdlib/aiken/math.html#log2) + +- New primitives in `aiken/primitive/bytearray`: + - [`at`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#at) + - [`from_int_big_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#from_int_big_endian) + - [`from_int_little_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#from_int_little_endian) + - [`to_int_big_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#to_int_big_endian) + - [`to_int_little_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html#to_int_little_endian) + +- New primitives in `aiken/primitive/int`: + - [`from_bytearray_big_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/int.html#from_bytearray_big_endian) + - [`from_bytearray_little_endian`](https://aiken-lang.github.io/stdlib/aiken/primitive/int.html#from_bytearray_little_endian) + +- New primitives in `aiken/crypto`: + - [`verify_ecdsa_signature`](https://aiken-lang.github.io/stdlib/cardano/credential.html#verify_ecdsa_signature) + - [`verify_schnorr_signature`](https://aiken-lang.github.io/stdlib/cardano/credential.html#verify_schnorr_signature) + +### Changed + +- Few modules have been relocated and better organized: + - `aiken/hash` -> [`aiken/crypto`](https://aiken-lang.github.io/stdlib/aiken/crypto.html) + - **collections** + - `aiken/dict` -> [`aiken/collection/dict`](https://aiken-lang.github.io/stdlib/aiken/collection/dict.html) + - `aiken/list` -> [`aiken/collection/list`](https://aiken-lang.github.io/stdlib/aiken/collection/list.html) + - `aiken/pairs` -> [`aiken/collection/pairs`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html) + - **primitive** + - `aiken/bytearray` -> [`aiken/primitive/bytearray`](https://aiken-lang.github.io/stdlib/aiken/primitive/bytearray.html) + - `aiken/int` -> [`aiken/primitive/int`](https://aiken-lang.github.io/stdlib/aiken/primitive/int.html) + - `aiken/string` -> [`aiken/primitive/string`](https://aiken-lang.github.io/stdlib/aiken/primitive/string.html) + - **cardano** + - `aiken/transaction` -> [`cardano/transaction`](https://aiken-lang.github.io/stdlib/cardano/transaction.html) + - `aiken/transaction/certificate` -> [`cardano/certificate`](https://aiken-lang.github.io/stdlib/cardano/certificate.html) + - `aiken/transaction/credential` -> [`cardano/address`](https://aiken-lang.github.io/stdlib/cardano/address.html) & `aiken/crypto` + - `aiken/transaction/value` -> [`cardano/assets`](https://aiken-lang.github.io/stdlib/cardano/assets.html) + +- Several zero-argument functions have been turned into top-level constants + - `aiken/dict.new()` -> [`aiken/collection/dict.empty`](https://aiken-lang.github.io/stdlib/aiken/collection/dict.html#empty) + - `aiken/interval.empty()` -> [`aiken/interval.empty`](https://aiken-lang.github.io/stdlib/aiken/interval.html#empty) + - `aiken/interval.everything()` -> [`aiken/interval.everything`](https://aiken-lang.github.io/stdlib/aiken/interval.html#everything) + - `aiken/math/rational.zero()` -> [`aiken/math/rational.zero`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#zero) + - `aiken/transaction/value.zero()` -> [`cardano/assets.zero`](https://aiken-lang.github.io/stdlib/cardano/assets.html#zero) + +- The `Transaction` type from [`cardano/transaction`](https://aiken-lang.github.io/stdlib/cardano/transaction.html) (originally `aiken/transaction`) has been greatly reworked to match the new transaction format in Plutus V3. + +- The `ScriptContext` type has split from `cardano/transaction` (originally `aiken/transaction`) and moved into its own module [`cardano/script_context`](https://aiken-lang.github.io/stdlib/cardano/script_context.html) and adjusted to its new form as per Plutus V3. + +- The constructors of [`Credential`](https://aiken-lang.github.io/stdlib/cardano/address.html#credential) have been renamed from `VerificationKeyCredential` and `ScriptCredential` into `VerificationKey` and `Script` respectively. + +- The function `remove_all`, `remove_first` and `remove_last` from [`aiken/collection/pairs`](https://aiken-lang.github.io/stdlib/aiken/collection/pairs.html) (originally `aiken/pairs`) have been renamed to `delete_all`, `delete_first` and `delete_last` respectively. + +- The function `verify_signature` from [`aiken/crypto`](https://aiken-lang.github.io/stdlib/aiken/crypto.html) (originally `aiken/credential`) has been renamed to `verify_ed25519_signature`. + +### Removed + +- The module `aiken/time`. The `PosixTime` alias is no longer used anywhere. + +- `MintedValue` (from `aiken/transaction/value` originally) and its associated functions are no longer needed and, therefore, gone. + +## v1.9.0 - 2024-05-24 + +### Added + +- A new module [`aiken/pairs`](https://aiken-lang.github.io/stdlib/aiken/pairs.html) to work with associative lists (a.k.a. `Pairs`). + +### Changed + +- **BREAKING-CHANGE**
+ Specialized all `Dict`'s key to `ByteArray`, and thus remove the need for passing an extra comparison function in many functions. `Dict` are however still specialized with a phantom type for keys. + +- **BREAKING-CHANGE**
+ Few functions from `Dict` have been renamed for consistency: + - `from_list` -> `from_pairs` + - `from_ascending_list` -> `from_ascending_pairs` + - `to_list` -> `to_pairs` + +### Removed + +N/A + +## v1.8.0 - 2024-03-28 + +### Added + +- [`value.reduce`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#reduce) to efficiently fold over a value and its elements. + +- [`value.from_asset_list`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#from_asset_list) to turn an asset list into a Value while enforcing invariants expected of `Value`. + +- [`math.is_sqrt`](https://aiken-lang.github.io/stdlib/aiken/math.html#is_sqrt) as a more efficient alternative to `sqrt`. + +### Changed + +- Disclaimers in documentation to [`bytearray.to_string`](https://aiken-lang.github.io/stdlib/aiken/bytearray.html#to_string) and [`string.from_bytearray`](https://aiken-lang.github.io/stdlib/aiken/string.html#from_bytearray) regarding UTF-8 encoding. + +### Removed + +N/A + +## v1.7.0 - 2023-11-07 + +### Added + +- [`list.index_of`](https://aiken-lang.github.io/stdlib/aiken/list.html#index_of): For getting a values index in a list. +- [`transaction.placeholder`](https://aiken-lang.github.io/stdlib/aiken/transaction.html#placeholder): For constructing test transactions. +- [`transaction.value.is_zero`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#is_zero): For checking whether a value is null. + +### Changed + +- [`value.to_minted_value`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#to_minted_value) now correctly preserves the invariant of `MintedValue`: it always contain a null quantity of Ada. + +### Removed + +N/A + +## v1.6.0 - 2023-09-08 + +### Added + +- [`math.pow2`](https://aiken-lang.github.io/stdlib/aiken/math.html#pow2): For faster exponentions for powers of two. +- [`bytearray.test_bit`](https://aiken-lang.github.io/stdlib/aiken/bytearray.html#test_bit): For testing if a bit is set in a bytearray (MSB). + +## v1.5.0 - 2023-08-16 + +### Removed + +- retired `list.and` and `list.or` because of the new keywords for logical op chaining. + +## v1.4.0 - 2023-07-21 + +### Changed + +- Fixed missing null-check on `value.add`. Adding a null quantity of token is now correctly a no-op. + +## v1.3.0 - 2023-06-30 + +### Added + +- [`math.sqrt`](https://aiken-lang.github.io/stdlib/aiken/math.html#sqrt): For calculating integer square roots using a quadratically convergent method. +- [`math/rational.numerator`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#numerator) & [`math/rational.denominator`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#numerator): For accessing parts of a rational value. +- [`math/rational.arithmetic_mean`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#arithmetic_mean): For computing [arithmetic mean](https://en.wikipedia.org/wiki/Arithmetic_mean) of rational values. +- [`math/rational.geometric_mean`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html#geometric_mean): For computing [geometric mean](https://en.wikipedia.org/wiki/Geometric_mean) of two rational values. + +### Changed + +- Clear empty asset lists in [`Value`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#Value) on various operations. Before that fix, it could happen that removing all assets from a given policy would lead to an empty dictionnary of assets still be present in the `Value`. + +## v1.2.0 - 2023-06-17 + +### Added + +- [`transaction/value.MintedValue`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#MintedValue) +- [`transaction/value.from_minted_value`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#from_minted_value): Convert from `MintedValue` to `Value` +- [`transaction/value.to_minted_value`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#to_minted_value): Convert from `Value` to `MintedValue` +- [`transaction/bytearray.to_hex`](https://aiken-lang.github.io/stdlib/aiken/bytearray.html#to_hex): Convert a `ByteArray` to a hex encoded `String` +- [`math/rational`](https://aiken-lang.github.io/stdlib/aiken/math/rational.html): Working with rational numbers. + - [x] `abs` + - [x] `add` + - [x] `ceil` + - [x] `compare` + - [x] `compare_with` + - [x] `div` + - [x] `floor` + - [x] `from_int` + - [x] `mul` + - [x] `negate` + - [x] `new` + - [x] `proper_fraction` + - [x] `reciprocal` + - [x] `reduce` + - [x] `round` + - [x] `round_even` + - [x] `sub` + - [x] `truncate` + - [x] `zero` + +### Removed + +- module `MintedValue` was merged with `Value` + +## v1.1.0 - 2023-06-06 + +### Added + +- [`list.count`](https://aiken-lang.github.io/stdlib/aiken/list.html#count): Count how many items in the list satisfy the given predicate. + +- [`int.from_utf8`](https://aiken-lang.github.io/stdlib/aiken/int.html#from_utf8): Parse an integer from a utf-8 encoded `ByteArray`, when possible. + +- [`dict.foldl`](https://aiken-lang.github.io/stdlib/aiken/dict.html#foldl) & [`dict.foldr`](https://aiken-lang.github.io/stdlib/aiken/dict.html#foldr): for left and right folds over dictionnary elements in ascending key order. + +- [`dict.insert_with`](https://aiken-lang.github.io/stdlib/aiken/dict.html#insert_with): Insert a value in the dictionary at a given key. When the key already exist, the provided merge function is called. + +- [`transaction/value.add`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#add): Add a (positive or negative) quantity of a single token to a value. This is more efficient than `merge` for a single asset. + +- [`transaction/value.to_dict`](https://aiken-lang.github.io/stdlib/aiken/transaction/value.html#to_dict): Convert a `Value` into a dictionnary of dictionnaries. + +- A new module [`transaction/minted_value`](https://aiken-lang.github.io/stdlib/aiken/transaction/minted_value.html): This is used exclusively for representing values present in the `mint` field of transactions. This allows to simplify some of the implementation for `Value` which no longer needs to handle the special case where null-quantity tokens would be present. It isn't possible to construct `MintedValue` by hand, they come from the script context entirely and are 'read-only'. + +- More documentation for `dict` and `interval` modules. + +### Changed + +> **Warning** +> +> Most of those changes are breaking-changes. Though, given we're still in an +> alpha state, only the `minor` component is bumped from the version number. +> Please forgive us. + +- Rework `list.{foldl, foldr, reduce, indexed_foldr}`, `dict.{fold}`, `bytearray.{foldl, foldr, reduce}` to take the iterator as last argument. For example: + + ``` + fn foldl(self: List
, with: fn(a, b) -> b, zero: b) -> b + + ↓ becomes + + fn foldl(self: List, zero: b, with: fn(a, b) -> b) -> b + ``` + +- Fixed implementation of `bytearray.slice`; `slice` would otherwise behave as if the second argument were an offset. + +- Rename `transaction/value.add` into `transaction/value.merge`. + +- Swap arguments of the merge function in `dict.union_with`; the first value received now corresponds to the value already present in the dictionnary. + +- Fixed various examples from the documentation + +### Removed + +- Removed `dict.fold`; replaced with `dict.foldl` and `dict.foldr` to remove ambiguity. + +## v1.0.0 - 2023-04-13 + +### Added + +N/A + +### Changed + +N/A + +### Removed + +N/A diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/LICENSE b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/LICENSE new file mode 100644 index 00000000..4a1de273 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/LICENSE @@ -0,0 +1,201 @@ + Apache License + Version 2.0, January 2004 + http://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + + APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + + Copyright 2022 Lucas Rosa + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/README.md b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/README.md new file mode 100644 index 00000000..4cd6fef2 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/README.md @@ -0,0 +1,71 @@ +
+
+

Aiken Aiken Standard Library

+ +[![Licence](https://img.shields.io/github/license/aiken-lang/stdlib?style=for-the-badge)](https://github.com/aiken-lang/stdlib/blob/main/LICENSE) +[![Continuous Integration](https://img.shields.io/github/actions/workflow/status/aiken-lang/stdlib/continuous-integration.yml?style=for-the-badge)](https://github.com/aiken-lang/stdlib/actions/workflows/continuous-integration.yml) + +
+
+ +## Getting started + +``` +aiken add aiken-lang/stdlib --version v2 +``` + +## Compatibility + +aiken's version | stdlib's version(s) +--- | --- +`v1.1.3`
`v1.1.4`
`v1.1.5`
`v1.1.6`
`v1.1.7` | `>= 2.1.0` +`v1.1.1`
`v1.1.2` | `>= 2.0.0` && `< 2.1.0` +`v1.0.29-alpha`
`v1.0.28-alpha` | `>= 1.9.0` && `< 2.0.0` +`v1.0.26-alpha` | `<= 1.8.0` && `< 1.9.0` + +## Overview + +The official standard library for the [Aiken](https://aiken-lang.org) Cardano +smart-contract language. + +It extends the language builtins with useful data-types, functions, constants +and aliases that make using Aiken a bliss. + +```aiken +use aiken/collection/list +use aiken/crypto.{VerificationKeyHash} +use cardano/transaction.{OutputReference, Transaction} + +pub type Datum { + owner: VerificationKeyHash, +} + +pub type Redeemer { + msg: ByteArray, +} + +/// A simple validator which replicates a basic public/private signature lock. +/// +/// - The key (hash) is set as datum when the funds are sent to the script address. +/// - The spender is expected to provide a signature, and the string 'Hello, World!' as message +/// - The signature is implicitly verified by the ledger, and included as 'extra_signatories' +/// +validator hello_world { + spend(datum: Option, redeemer: Redeemer, _, self: Transaction) { + expect Some(Datum { owner }) = datum + + let must_say_hello = redeemer.msg == "Hello, World!" + + let must_be_signed = list.has(self.extra_signatories, owner) + + and { + must_say_hello, + must_be_signed, + } + } +} +``` + +## Stats + +![Alt](https://repobeats.axiom.co/api/embed/f0a17e7f6133630e165b9e56ec5447bef32fe831.svg "Repobeats analytics image") diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/aiken.lock b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/aiken.lock new file mode 100644 index 00000000..769ac20f --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/aiken.lock @@ -0,0 +1,16 @@ +# This file was generated by Aiken +# You typically do not need to edit this file + +[[requirements]] +name = "aiken-lang/fuzz" +version = "v2" +source = "github" + +[[packages]] +name = "aiken-lang/fuzz" +version = "v2" +requirements = [] +source = "github" + +[etags] +"aiken-lang/fuzz@v2" = [{ secs_since_epoch = 1734106349, nanos_since_epoch = 450591000 }, "64a32283418d58cade34059d3855b857e84505541158c541c460cafa0d355475"] diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/aiken.toml b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/aiken.toml new file mode 100644 index 00000000..cbc76a0b --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/aiken.toml @@ -0,0 +1,15 @@ +name = "aiken-lang/stdlib" +version = "2.2.0" +compiler = "v1.1.9" +plutus = "v3" +description = "The Aiken Standard Library" + +[repository] +user = "aiken-lang" +project = "stdlib" +platform = "github" + +[[dependencies]] +name = "aiken-lang/fuzz" +version = "v2" +source = "github" diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/cbor.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/cbor.ak new file mode 100644 index 00000000..f0c66d69 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/cbor.ak @@ -0,0 +1,293 @@ +use aiken +use aiken/builtin.{decode_utf8, serialise_data} +use aiken/primitive/bytearray + +/// Obtain a String representation of _anything_. This is particularly (and only) useful for tracing +/// and debugging. This function is expensive and should not be used in any production code as it +/// will very likely explodes the validator's budget. +/// +/// The output is a [CBOR diagnostic](https://www.rfc-editor.org/rfc/rfc8949#name-diagnostic-notation) +/// of the underlying on-chain binary representation of the data. It's not as +/// easy to read as plain Aiken code, but it is handy for troubleshooting values +/// _at runtime_. Incidentally, getting familiar with reading CBOR diagnostic is +/// a good idea in the Cardano world. +/// +/// ```aiken +/// cbor.diagnostic(42) == "42" +/// cbor.diagnostic(#"a1b2") == "h'A1B2'" +/// cbor.diagnostic([1, 2, 3]) == "[_ 1, 2, 3]" +/// cbor.diagnostic([]) == "[]" +/// cbor.diagnostic((1, 2)) == "[_ 1, 2]" +/// cbor.diagnostic((1, #"ff", 3)) == "[_ 1, h'FF', 3]" +/// cbor.diagnostic([(1, #"ff")]) == "{_ 1: h'FF' }" +/// cbor.diagnostic(Some(42)) == "121([_ 42])" +/// cbor.diagnostic(None) == "122([])" +/// ``` +pub fn diagnostic(self: Data) -> String { + aiken.diagnostic(self, #"") + |> decode_utf8 +} + +/// Deserialise a [CBOR](https://www.rfc-editor.org/rfc/rfc8949) Data. This is the reverse operation of [serialise](#serialise). +/// In particular, we have the following property: +/// +/// ```aiken +/// cbor.deserialise(cbor.serialise(any_data)) == Some(any_data) +/// ``` +/// +/// > [!CAUTION] +/// > Unfortunately, this function isn't derived from a builtin primitive. It +/// > is therefore an order of magnitude more expensive than its counterpart +/// > and shall be used with care. +/// > +/// > In general, one might prefer avoiding deserialisation unless truly necessary. +/// > Yet, it may come in handy for testing and in rare scenarios. +pub fn deserialise(bytes: ByteArray) -> Option { + let length = bytearray.length(bytes) + + let peek = + fn(offset: Int, callback: fn(Byte) -> Decoder) -> Decoder { + fn(cursor) { + if 0 >= cursor { + deserialise_failure + } else { + callback(bytearray.at(bytes, length - cursor))(cursor - offset) + } + } + } + + let take = + fn(n: Int, callback: fn(ByteArray) -> Decoder) -> Decoder { + fn(cursor) { + if 0 >= cursor { + deserialise_failure + } else { + callback(builtin.slice_bytearray(length - cursor, n, bytes))( + cursor - n, + ) + } + } + } + + if length == 0 { + None + } else { + let Pair(result, consumed) = decode_data(peek, take)(length) + if consumed != 0 { + None + } else { + Some(result) + } + } +} + +/// Serialise any value to binary, encoding using [CBOR](https://www.rfc-editor.org/rfc/rfc8949). +/// +/// This is particularly useful in combination with hashing functions, as a way +/// to obtain a byte representation that matches the serialised representation +/// used by the ledger in the context of on-chain code. +/// +/// Note that the output matches the output of [`diagnostic`](#diagnostic), +/// though with a different encoding. [`diagnostic`](#diagnostic) is merely a +/// textual representation of the CBOR encoding that is human friendly and +/// useful for debugging. +/// +/// ```aiken +/// cbor.serialise(42) == #"182a" +/// cbor.serialise(#"a1b2") == #"42a1b2" +/// cbor.serialise([]) == #"80" +/// cbor.serialise((1, 2)) == #"9f0102ff" +/// cbor.serialise((1, #"ff", 3)) == #"9f0141ff03ff" +/// cbor.serialise([(1, #"ff")]) == #"a10141ff" +/// cbor.serialise(Some(42)) == #"d8799f182aff" +/// cbor.serialise(None) == #"d87a80" +/// ``` +pub fn serialise(self: Data) -> ByteArray { + serialise_data(self) +} + +type Byte = + Int + +type Decoder
= + fn(Int) -> Pair + +type Peek = + fn(Int, fn(Byte) -> Decoder) -> Decoder + +type Take = + fn(Int, fn(ByteArray) -> Decoder) -> Decoder + +fn return(data: Data) -> Decoder { + fn(cursor) { Pair(data, cursor) } +} + +const deserialise_failure: Pair = { + let empty: Data = "" + Pair(empty, -1) + } + +const token_begin_bytes = 0x5f + +const token_begin_list = 0x9f + +const token_begin_map = 0xbf + +const token_break = 0xff + +fn decode_data(peek: Peek, take: Take) -> Decoder { + let next <- peek(1) + let major_type = next / 32 + if major_type <= 2 { + if major_type == 0 { + let i <- decode_uint(peek, take, next) + return(builtin.i_data(i)) + } else if major_type == 1 { + let i <- decode_uint(peek, take, next - 32) + return(builtin.i_data(-i - 1)) + } else { + if next == token_begin_bytes { + let b <- decode_chunks(peek, take) + return(builtin.b_data(b)) + } else { + let b <- decode_bytes(peek, take, next - 64) + return(builtin.b_data(b)) + } + } + } else if major_type == 6 { + let tag <- decode_uint(peek, take, next - 192) + let next <- peek(1) + if tag == 102 { + fn(_) { deserialise_failure } + } else { + let ix = + if tag >= 1280 { + tag - 1280 + 7 + } else { + tag - 121 + } + if next == token_begin_list { + let fields <- decode_indefinite(peek, take, decode_data) + return(builtin.constr_data(ix, fields)) + } else { + let size <- decode_uint(peek, take, next - 128) + let fields <- decode_definite(peek, take, decode_data, size) + return(builtin.constr_data(ix, fields)) + } + } + } else if major_type == 4 { + if next == token_begin_list { + let xs <- decode_indefinite(peek, take, decode_data) + return(builtin.list_data(xs)) + } else { + let size <- decode_uint(peek, take, next - 128) + let xs <- decode_definite(peek, take, decode_data, size) + return(builtin.list_data(xs)) + } + } else if major_type == 5 { + if next == token_begin_map { + let xs <- decode_indefinite(peek, take, decode_pair) + return(builtin.map_data(xs)) + } else { + let size <- decode_uint(peek, take, next - 160) + let xs <- decode_definite(peek, take, decode_pair, size) + return(builtin.map_data(xs)) + } + } else { + fn(_) { deserialise_failure } + } +} + +fn decode_pair(peek: Peek, take: Take) -> Decoder> { + fn(cursor) { + let Pair(k, cursor) = decode_data(peek, take)(cursor) + let Pair(v, cursor) = decode_data(peek, take)(cursor) + Pair(Pair(k, v), cursor) + } +} + +fn decode_uint( + peek: Peek, + take: Take, + header: Int, + and_then: fn(Int) -> Decoder, +) -> Decoder { + if header < 24 { + and_then(header) + } else if header == 24 { + let payload <- peek(1) + and_then(payload) + } else if header < 28 { + let width = bytearray.at(#[2, 4, 8], header - 25) + let payload <- take(width) + and_then(bytearray.to_int_big_endian(payload)) + } else { + fn(_) { deserialise_failure } + } +} + +fn decode_bytes( + peek: Peek, + take: Take, + header: Int, + and_then: fn(ByteArray) -> Decoder, +) -> Decoder { + let width <- decode_uint(peek, take, header) + let bytes <- take(width) + and_then(bytes) +} + +fn decode_chunks( + peek: Peek, + take: Take, + and_then: fn(ByteArray) -> Decoder, +) -> Decoder { + let next <- peek(1) + if next == token_break { + and_then("") + } else { + let chunk <- decode_bytes(peek, take, next - 64) + let chunks <- decode_chunks(peek, take) + and_then(builtin.append_bytearray(chunk, chunks)) + } +} + +fn decode_definite( + peek: Peek, + take: Take, + decode_one: fn(Peek, Take) -> Decoder, + size: Int, + and_then: fn(List) -> Decoder, +) -> Decoder { + if size <= 0 { + and_then([]) + } else { + fn(cursor) { + let Pair(elem, cursor) = decode_one(peek, take)(cursor) + { + let elems <- decode_definite(peek, take, decode_one, size - 1) + and_then([elem, ..elems]) + }(cursor) + } + } +} + +fn decode_indefinite( + peek: Peek, + take: Take, + decode_one: fn(Peek, Take) -> Decoder, + and_then: fn(List) -> Decoder, +) -> Decoder { + let next <- peek(1) + if next == token_break { + and_then([]) + } else { + fn(cursor) { + let Pair(elem, cursor) = decode_one(peek, take)(cursor + 1) + { + let elems <- decode_indefinite(peek, take, decode_one) + and_then([elem, ..elems]) + }(cursor) + } + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/cbor.test.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/cbor.test.ak new file mode 100644 index 00000000..28d9f5bb --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/cbor.test.ak @@ -0,0 +1,297 @@ +use aiken/cbor.{deserialise, diagnostic, serialise} +use aiken/fuzz + +// ------------------------------------------------------------------ diagnostic + +test diagnostic_1() { + diagnostic(42) == @"42" +} + +test diagnostic_2() { + diagnostic(#"a1b2") == @"h'A1B2'" +} + +test diagnostic_3() { + diagnostic([1, 2, 3]) == @"[_ 1, 2, 3]" +} + +test diagnostic_4() { + diagnostic([]) == @"[]" +} + +test diagnostic_5() { + diagnostic((1, 2)) == @"[_ 1, 2]" +} + +test diagnostic_6() { + diagnostic((1, #"ff", 3)) == @"[_ 1, h'FF', 3]" +} + +test diagnostic_7() { + diagnostic([(1, #"ff")]) == @"[_ [_ 1, h'FF']]" +} + +test diagnostic_7_alt() { + diagnostic([Pair(1, #"ff")]) == @"{_ 1: h'FF' }" +} + +test diagnostic_8() { + diagnostic(Some(42)) == @"121([_ 42])" +} + +test diagnostic_9() { + diagnostic(None) == @"122([])" +} + +test diagnostic_10() { + let xs: List<(Int, Int)> = [] + diagnostic(xs) == @"[]" +} + +test diagnostic_10_alt() { + let xs: Pairs = [] + diagnostic(xs) == @"{}" +} + +type Foo { + foo: Bar, +} + +type Bar { + A + B(Int) +} + +test diagnostic_11() { + diagnostic(Foo { foo: A }) == @"121([_ 121([])])" +} + +test diagnostic_12() { + diagnostic(Foo { foo: B(42) }) == @"121([_ 122([_ 42])])" +} + +type Baz { + a0: Int, + b0: ByteArray, +} + +test diagnostic_13() { + diagnostic(Baz { a0: 14, b0: #"ff" }) == @"121([_ 14, h'FF'])" +} + +test diagnostic_14() { + diagnostic([0]) == @"[_ 0]" +} + +test diagnostic_15() { + diagnostic(-42) == @"-42" +} + +test diagnostic_16() { + diagnostic([-1, 0, 1]) == @"[_ -1, 0, 1]" +} + +// ------------------------------------------------------------------ serialise + +test serialise_1() { + serialise(42) == #"182a" +} + +test serialise_2() { + serialise(#"a1b2") == #"42a1b2" +} + +test serialise_3() { + serialise([]) == #"80" +} + +test serialise_4() { + serialise((1, 2)) == #"9f0102ff" +} + +test serialise_5() { + serialise((1, #"ff", 3)) == #"9f0141ff03ff" +} + +test serialise_6() { + serialise([(1, #"ff")]) == #"9f9f0141ffffff" +} + +test serialise_7() { + serialise(Some(42)) == #"d8799f182aff" +} + +test serialise_8() { + serialise(None) == #"d87a80" +} + +test serialise_9() { + serialise([Pair(1, #"ff")]) == #"a10141ff" +} + +// ------------------------------------------------------------------ deserialise + +type AnyData { + AnyInt(Int) + AnyByteArray(ByteArray) + AnyList(List) + AnyPairs(Pairs) + AnyUnaryConstr0(UnaryConstr0) + AnyUnaryConstr1(UnaryConstr1) + AnyUnaryConstr2(UnaryConstr2) + AnyBinaryConstr0(BinaryConstr0) + AnyBinaryConstr1(BinaryConstr1) +} + +type UnaryConstr0 { + UnaryConstr0 +} + +type UnaryConstr1 { + field0: String, +} + +type UnaryConstr2 { + field0: Int, + field1: List>, +} + +type BinaryConstr0 = + Bool + +type BinaryConstr1 = + Option + +fn any_pair(any_key: Fuzzer, any_value: Fuzzer) -> Fuzzer> { + let k <- fuzz.and_then(any_key) + let v <- fuzz.map(any_value) + Pair(k, v) +} + +fn any_data() -> Fuzzer { + fuzz.either6( + { + let i <- fuzz.map(fuzz.int()) + AnyInt(i) + }, + { + let bs <- fuzz.map(fuzz.bytearray()) + AnyByteArray(bs) + }, + { + let xs <- fuzz.map(fuzz.list(fuzz.int())) + AnyList(xs) + }, + { + let ps <- fuzz.map(fuzz.list(any_pair(fuzz.bytearray(), fuzz.int()))) + AnyPairs(ps) + }, + fuzz.either3( + fuzz.constant(AnyUnaryConstr0(UnaryConstr0)), + fuzz.constant(AnyUnaryConstr1(UnaryConstr1(@"lorem ipsum"))), + { + let i <- fuzz.and_then(fuzz.int()) + let xs <- fuzz.map(fuzz.list(fuzz.list(fuzz.bytearray()))) + AnyUnaryConstr2(UnaryConstr2(i, xs)) + }, + ), + fuzz.either( + { + let b <- fuzz.map(fuzz.bool()) + AnyBinaryConstr0(b) + }, + { + let o <- fuzz.map(fuzz.option(fuzz.int())) + AnyBinaryConstr1(o) + }, + ), + ) +} + +test unit_deserialise_not_enough_bytes_1() { + expect None = deserialise(#"") +} + +test unit_deserialise_not_enough_bytes_2() { + expect None = deserialise(#"82") +} + +test unit_deserialise_non_empty_leftovers() { + expect None = deserialise(#"811442") +} + +test unit_deserialise_invalid_header() { + expect None = deserialise(#"f1") +} + +test unit_deserialise_invalid_uint() { + expect None = deserialise(#"1d0013bdae") +} + +/// A full script context with a minting policy and various assets. Meant to be +/// non-trivial and cover many things we might encounter in a transaction. +test bench_deserialise_script_context() { + expect Some(_) = + deserialise( + #"d8799fd8799f9fd8799fd8799f5820000000000000000000000000000000000000000000000000000000000000000000ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffd87a80ffa140a1401a000f4240d87980d87a80ffffff9fd8799fd8799f5820000000000000000000000000000000000000000000000000000000000000000000ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffd87a80ffa140a1401a000f4240d87980d87a80ffffff9fd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffd87a80ffa140a1401a000f4240d87a9f5820923918e403bf43c34b4ef6b48eb2ee04babed17320d8d1b9ff9ad086e86f44ecffd87a80ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffffffffa340a1401a000f4240581c0c8eaf490c53afbf27e3d84a3b57da51fbafe5aa78443fcec2dc262ea14561696b656e182a581c12593b4cbf7fdfd8636db99fe356437cd6af8539aadaa0a401964874a14474756e611b00005af3107a4000d87980d87a80ffd8799fd8799fd87a9f581c00000000000000000000000000000000000000000000000000000000ffd8799fd8799fd8799f581c00000000000000000000000000000000000000000000000000000000ffffffffa240a1401a000f4240581c0c8eaf490c53afbf27e3d84a3b57da51fbafe5aa78443fcec2dc262ea14763617264616e6f01d87980d8799f581c68ad54b3a8124d9fe5caaaf2011a85d72096e696a2fb3d7f86c41717ffffff182aa2581c0c8eaf490c53afbf27e3d84a3b57da51fbafe5aa78443fcec2dc262ea24561696b656e2d4763617264616e6f01581c12593b4cbf7fdfd8636db99fe356437cd6af8539aadaa0a401964874a14474756e611b00005af3107a400080a0d8799fd8799fd87980d87a80ffd8799fd87b80d87a80ffff80a2d8799f581c0c8eaf490c53afbf27e3d84a3b57da51fbafe5aa78443fcec2dc262effd87980d8799f581c12593b4cbf7fdfd8636db99fe356437cd6af8539aadaa0a401964874ff182aa15820923918e403bf43c34b4ef6b48eb2ee04babed17320d8d1b9ff9ad086e86f44ecd879805820e757985e48e43a95a185ddba08c814bc20f81cb68544ac937a9b992e4e6c38a0a080d87a80d87a80ff182ad8799f581c12593b4cbf7fdfd8636db99fe356437cd6af8539aadaa0a401964874ffff", + ) +} + +test prop_deserialise_any_data(any via any_data()) { + when any is { + AnyInt(i) -> { + fuzz.label(@"Int") + expect Some(data) = deserialise(serialise(i)) + expect i_decoded: Int = data + i_decoded == i + } + AnyByteArray(bs) -> { + fuzz.label(@"ByteArray") + expect Some(data) = deserialise(serialise(bs)) + expect bs_decoded: ByteArray = data + bs_decoded == bs + } + AnyList(xs) -> { + fuzz.label(@"List") + expect Some(data) = deserialise(serialise(xs)) + expect xs_decoded: List = data + xs_decoded == xs + } + AnyPairs(ps) -> { + fuzz.label(@"Pairs") + expect Some(data) = deserialise(serialise(ps)) + expect ps_decoded: Pairs = data + ps_decoded == ps + } + AnyUnaryConstr0(constr) -> { + fuzz.label(@"(unary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: UnaryConstr0 = data + constr_decoded == constr + } + AnyUnaryConstr1(constr) -> { + fuzz.label(@"(unary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: UnaryConstr1 = data + constr_decoded == constr + } + AnyUnaryConstr2(constr) -> { + fuzz.label(@"(unary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: UnaryConstr2 = data + constr_decoded == constr + } + AnyBinaryConstr0(constr) -> { + fuzz.label(@"(binary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: BinaryConstr0 = data + constr_decoded == constr + } + AnyBinaryConstr1(constr) -> { + fuzz.label(@"(binary) Constr") + expect Some(data) = deserialise(serialise(constr)) + expect constr_decoded: BinaryConstr1 = data + constr_decoded == constr + } + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection.ak new file mode 100644 index 00000000..3d4d332e --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection.ak @@ -0,0 +1,4 @@ +/// A non negative integer that materializes the position of an element in a +/// collection. +pub type Index = + Int diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection/dict.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection/dict.ak new file mode 100644 index 00000000..681d0bae --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection/dict.ak @@ -0,0 +1,1174 @@ +//// A module for working with bytearray dictionaries. +//// +//// +//// > [!IMPORTANT] +//// > +//// > Dictionaries are **ordered sets** of key-value pairs, which thus +//// > preserve some invariants. Specifically, each key is only present once in +//// > the dictionary and all keys are stored in ascending lexicographic order. +//// > +//// > These invariants allow for more optimized functions to operate on `Dict`, +//// > but as a trade-offs, prevent `Dict` from being serializable. To recover a `Dict` +//// > from an unknown `Data`, you must first recover an `Pairs` and use +//// > [`dict.from_ascending_list`](#from_ascending_list). + +use aiken/builtin + +/// An opaque `Dict`. The type is opaque because the module maintains some +/// invariant, namely: there's only one occurrence of a given key in the dictionary. +/// +/// Note that the `key` parameter is a phantom-type, and only present as a +/// means of documentation. Keys can be any type, yet will need to comparable +/// to use functions like `insert`. +/// +/// See for example: +/// +/// ```aiken +/// pub type Value = +/// Dict> +/// ``` +pub opaque type Dict { + inner: Pairs, +} + +// ## Constructing + +/// An empty dictionnary. +/// ```aiken +/// dict.to_pairs(dict.empty) == [] +/// ``` +pub const empty: Dict = Dict { inner: [] } + +const foo = #"666f6f" + +const bar = #"626172" + +const baz = #"62617a" + +const fixture_1 = + empty + |> insert(foo, 42) + |> insert(bar, 14) + +/// Like ['from_pairs'](#from_pairs), but from an already sorted list by ascending +/// keys. This function fails (i.e. halts the program execution) if the list isn't +/// sorted. +/// +/// ```aiken +/// let pairs = [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// +/// let result = +/// dict.from_ascending_pairs(pairs) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// ``` +/// +/// This is meant to be used to turn a list constructed off-chain into a `Dict` +/// which has taken care of maintaining interval invariants. This function still +/// performs a sanity check on all keys to avoid silly mistakes. It is, however, +/// considerably faster than ['from_pairs'](from_pairs) +pub fn from_ascending_pairs(xs: Pairs) -> Dict { + let Void = check_ascending_list(xs) + Dict { inner: xs } +} + +fn check_ascending_list(xs: Pairs) { + when xs is { + [] -> Void + [_] -> Void + [Pair(x0, _), Pair(x1, _) as e, ..rest] -> + if builtin.less_than_bytearray(x0, x1) { + check_ascending_list([e, ..rest]) + } else { + fail @"keys in associative list aren't in ascending order" + } + } +} + +/// Like [`from_ascending_pairs`](#from_ascending_pairs) but fails if **any** +/// value doesn't satisfy the predicate. +/// +/// ```aiken +/// let pairs = [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// +/// dict.from_ascending_pairs_with(pairs, fn(x) { x <= 250 }) // fail +/// ``` +pub fn from_ascending_pairs_with( + xs: Pairs, + predicate: fn(value) -> Bool, +) -> Dict { + let Void = check_ascending_pairs_with(xs, predicate) + Dict { inner: xs } +} + +fn check_ascending_pairs_with( + xs: Pairs, + predicate: fn(value) -> Bool, +) { + when xs is { + [] -> Void + [Pair(_, v)] -> + if predicate(v) { + Void + } else { + fail @"value doesn't satisfy predicate" + } + [Pair(x0, v0), Pair(x1, _) as e, ..rest] -> + if builtin.less_than_bytearray(x0, x1) { + if predicate(v0) { + check_ascending_pairs_with([e, ..rest], predicate) + } else { + fail @"value doesn't satisfy predicate" + } + } else { + fail @"keys in pairs aren't in ascending order" + } + } +} + +test bench_from_ascending_pairs() { + let dict = + from_ascending_pairs( + [ + Pair("aaaa", 1), Pair("aaab", 9), Pair("aaba", 5), Pair("aabb", 13), + Pair("abaa", 2), Pair("abab", 10), Pair("abba", 6), Pair("abbb", 14), + Pair("baaa", 3), Pair("baab", 11), Pair("baba", 7), Pair("babb", 15), + Pair("bbaa", 4), Pair("bbab", 12), Pair("bbba", 8), Pair("bbbb", 16), + ], + ) + + size(dict) == 16 +} + +/// Construct a dictionary from a list of key-value pairs. Note that when a key is present +/// multiple times, the first occurrence prevails. +/// +/// ```aiken +/// let pairs = [Pair("a", 100), Pair("c", 300), Pair("b", 200)] +/// +/// let result = +/// dict.from_pairs(pairs) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn from_pairs(self: Pairs) -> Dict { + Dict { inner: do_from_pairs(self) } +} + +fn do_from_pairs(xs: Pairs) -> Pairs { + when xs is { + [] -> [] + [Pair(k, v), ..rest] -> do_insert(do_from_pairs(rest), k, v) + } +} + +test from_list_1() { + from_pairs([]) == empty +} + +test from_list_2() { + from_pairs([Pair(foo, 42), Pair(bar, 14)]) == from_pairs( + [Pair(bar, 14), Pair(foo, 42)], + ) +} + +test from_list_3() { + from_pairs([Pair(foo, 42), Pair(bar, 14)]) == fixture_1 +} + +test from_list_4() { + from_pairs([Pair(foo, 42), Pair(bar, 14), Pair(foo, 1337)]) == fixture_1 +} + +test bench_from_pairs() { + let dict = + from_pairs( + [ + Pair("bbba", 8), Pair("bbab", 12), Pair("aabb", 13), Pair("aaab", 9), + Pair("bbbb", 16), Pair("aaaa", 1), Pair("aaba", 5), Pair("abab", 10), + Pair("baba", 7), Pair("baab", 11), Pair("abaa", 2), Pair("baaa", 3), + Pair("bbaa", 4), Pair("babb", 15), Pair("abbb", 14), Pair("abba", 6), + ], + ) + + size(dict) == 16 +} + +// ## Inspecting + +/// Finds a value in the dictionary, and returns the first key found to have that value. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 42) +/// |> dict.insert(key: "b", value: 14) +/// |> dict.insert(key: "c", value: 42) +/// |> dict.find(42) +/// +/// result == Some("a") +/// ``` +pub fn find(self: Dict, value v: value) -> Option { + do_find(self.inner, v) +} + +fn do_find(self: Pairs, value v: value) -> Option { + when self is { + [] -> None + [Pair(k2, v2), ..rest] -> + if v == v2 { + Some(k2) + } else { + do_find(rest, v) + } + } +} + +test find_1() { + find(empty, foo) == None +} + +test find_2() { + find( + empty + |> insert(foo, 14), + 14, + ) == Some(foo) +} + +test find_3() { + find( + empty + |> insert(foo, 14), + 42, + ) == None +} + +test find_4() { + find( + empty + |> insert(foo, 14) + |> insert(bar, 42) + |> insert(baz, 14), + 14, + ) == Some(baz) +} + +/// Get a value in the dict by its key. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: "Aiken") +/// |> dict.get(key: "a") +/// +/// result == Some("Aiken") +/// ``` +pub fn get(self: Dict, key: ByteArray) -> Option { + do_get(self.inner, key) +} + +fn do_get(self: Pairs, key k: ByteArray) -> Option { + when self is { + [] -> None + [Pair(k2, v), ..rest] -> + if builtin.less_than_equals_bytearray(k, k2) { + if k == k2 { + Some(v) + } else { + None + } + } else { + do_get(rest, k) + } + } +} + +test get_1() { + get(empty, foo) == None +} + +test get_2() { + let m = + empty + |> insert(foo, "Aiken") + |> insert(bar, "awesome") + get(m, key: foo) == Some("Aiken") +} + +test get_3() { + let m = + empty + |> insert(foo, "Aiken") + |> insert(bar, "awesome") + get(m, key: baz) == None +} + +test get_4() { + let m = + empty + |> insert("aaa", "1") + |> insert("bbb", "2") + |> insert("ccc", "3") + |> insert("ddd", "4") + |> insert("eee", "5") + |> insert("fff", "6") + |> insert("ggg", "7") + |> insert("hhh", "8") + |> insert("iii", "9") + |> insert("jjj", "10") + + get(m, "bcd") == None +} + +test get_5() { + let m = + empty + |> insert("aaa", "1") + |> insert("bbb", "2") + |> insert("ccc", "3") + |> insert("ddd", "4") + |> insert("eee", "5") + |> insert("fff", "6") + |> insert("ggg", "7") + |> insert("hhh", "8") + |> insert("iii", "9") + |> insert("jjj", "10") + + get(m, "kkk") == None +} + +/// Check if a key exists in the dictionary. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: "Aiken") +/// |> dict.has_key("a") +/// +/// result == True +/// ``` +pub fn has_key(self: Dict, key k: ByteArray) -> Bool { + do_has_key(self.inner, k) +} + +fn do_has_key(self: Pairs, key k: ByteArray) -> Bool { + when self is { + [] -> False + [Pair(k2, _), ..rest] -> + if builtin.less_than_equals_bytearray(k, k2) { + k == k2 + } else { + do_has_key(rest, k) + } + } +} + +test has_key_1() { + !has_key(empty, foo) +} + +test has_key_2() { + has_key( + empty + |> insert(foo, 14), + foo, + ) +} + +test has_key_3() { + !has_key( + empty + |> insert(foo, 14), + bar, + ) +} + +test has_key_4() { + has_key( + empty + |> insert(foo, 14) + |> insert(bar, 42), + bar, + ) +} + +/// Efficiently checks whether a dictionary is empty. +/// ```aiken +/// dict.is_empty(dict.empty) == True +/// ``` +pub fn is_empty(self: Dict) -> Bool { + when self.inner is { + [] -> True + _ -> False + } +} + +test is_empty_1() { + is_empty(empty) +} + +/// Extract all the keys present in a given `Dict`. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 14) +/// |> dict.insert("b", 42) +/// |> dict.insert("a", 1337) +/// |> dict.keys() +/// +/// result == ["a", "b"] +/// ``` +pub fn keys(self: Dict) -> List { + do_keys(self.inner) +} + +fn do_keys(self: Pairs) -> List { + when self is { + [] -> [] + [Pair(k, _), ..rest] -> [k, ..do_keys(rest)] + } +} + +test keys_1() { + keys(empty) == [] +} + +test keys_2() { + keys( + empty + |> insert(foo, 0) + |> insert(bar, 0), + ) == [bar, foo] +} + +/// Return the number of key-value pairs in the dictionary. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 100) +/// |> dict.insert("b", 200) +/// |> dict.insert("c", 300) +/// |> dict.size() +/// +/// result == 3 +/// ``` +pub fn size(self: Dict) -> Int { + do_size(self.inner) +} + +fn do_size(self: Pairs) -> Int { + when self is { + [] -> 0 + [_, ..rest] -> 1 + do_size(rest) + } +} + +test size_1() { + size(empty) == 0 +} + +test size_2() { + size( + empty + |> insert(foo, 14), + ) == 1 +} + +test size_3() { + size( + empty + |> insert(foo, 14) + |> insert(bar, 42), + ) == 2 +} + +/// Extract all the values present in a given `Dict`. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 14) +/// |> dict.insert("b", 42) +/// |> dict.insert("c", 1337) +/// |> dict.values() +/// +/// result == [14, 42, 1337] +/// ``` +pub fn values(self: Dict) -> List { + do_values(self.inner) +} + +fn do_values(self: Pairs) -> List { + when self is { + [] -> [] + [Pair(_, v), ..rest] -> [v, ..do_values(rest)] + } +} + +test values_1() { + values(empty) == [] +} + +test values_2() { + values( + empty + |> insert(foo, 3) + |> insert(bar, 4), + ) == [4, 3] +} + +// ## Modifying + +/// Remove a key-value pair from the dictionary. If the key is not found, no changes are made. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.delete(key: "a") +/// |> dict.to_pairs() +/// +/// result == [Pair("b", 200)] +/// ``` +pub fn delete(self: Dict, key: ByteArray) -> Dict { + Dict { inner: do_delete(self.inner, key) } +} + +fn do_delete( + self: Pairs, + key k: ByteArray, +) -> Pairs { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if builtin.less_than_equals_bytearray(k, k2) { + if k == k2 { + rest + } else { + self + } + } else { + [Pair(k2, v2), ..do_delete(rest, k)] + } + } +} + +test delete_1() { + delete(empty, foo) == empty +} + +test delete_2() { + let m = + empty + |> insert(foo, 14) + delete(m, foo) == empty +} + +test delete_3() { + let m = + empty + |> insert(foo, 14) + delete(m, bar) == m +} + +test delete_4() { + let m = + empty + |> insert(foo, 14) + |> insert(bar, 14) + !has_key(delete(m, foo), foo) +} + +test delete_5() { + let m = + empty + |> insert(foo, 14) + |> insert(bar, 14) + has_key(delete(m, bar), foo) +} + +test delete_6() { + let m = + empty + |> insert("aaa", 1) + |> insert("bbb", 2) + |> insert("ccc", 3) + |> insert("ddd", 4) + |> insert("eee", 5) + |> insert("fff", 6) + |> insert("ggg", 7) + |> insert("hhh", 8) + |> insert("iii", 9) + |> insert("jjj", 10) + + delete(m, "bcd") == m +} + +/// Keep only the key-value pairs that pass the given predicate. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.insert(key: "c", value: 300) +/// |> dict.filter(fn(k, _v) { k != "a" }) +/// |> dict.to_pairs() +/// +/// result == [Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn filter( + self: Dict, + with: fn(ByteArray, value) -> Bool, +) -> Dict { + Dict { inner: do_filter(self.inner, with) } +} + +fn do_filter( + self: Pairs, + with: fn(ByteArray, value) -> Bool, +) -> Pairs { + when self is { + [] -> [] + [Pair(k, v), ..rest] -> + if with(k, v) { + [Pair(k, v), ..do_filter(rest, with)] + } else { + do_filter(rest, with) + } + } +} + +test filter_1() { + filter(empty, fn(_, _) { True }) == empty +} + +test filter_2() { + let expected = + empty + |> insert(foo, 42) + filter(fixture_1, fn(_, v) { v > 14 }) == expected +} + +test filter_3() { + let expected = + empty + |> insert(bar, 14) + filter(fixture_1, fn(k, _) { k == bar }) == expected +} + +/// Insert a value in the dictionary at a given key. If the key already exists, its value is **overridden**. If you need ways to combine keys together, use (`insert_with`)[#insert_with]. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 1) +/// |> dict.insert(key: "b", value: 2) +/// |> dict.insert(key: "a", value: 3) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 3), Pair("b", 2)] +/// ``` +pub fn insert( + self: Dict, + key k: ByteArray, + value v: value, +) -> Dict { + Dict { inner: do_insert(self.inner, k, v) } +} + +fn do_insert( + self: Pairs, + key k: ByteArray, + value v: value, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if builtin.less_than_bytearray(k, k2) { + [Pair(k, v), ..self] + } else { + if k == k2 { + [Pair(k, v), ..rest] + } else { + [Pair(k2, v2), ..do_insert(rest, k, v)] + } + } + } +} + +test insert_1() { + let m1 = + empty + |> insert(foo, 42) + let m2 = + empty + |> insert(foo, 14) + insert(m1, foo, 14) == m2 +} + +test insert_2() { + let m1 = + empty + |> insert(foo, 42) + let m2 = + empty + |> insert(bar, 14) + insert(m1, bar, 14) == insert(m2, foo, 42) +} + +/// Insert a value in the dictionary at a given key. When the key already exist, the provided +/// merge function is called. The value existing in the dictionary is passed as the second argument +/// to the merge function, and the new value is passed as the third argument. +/// +/// ```aiken +/// let sum = +/// fn (_k, a, b) { Some(a + b) } +/// +/// let result = +/// dict.empty +/// |> dict.insert_with(key: "a", value: 1, with: sum) +/// |> dict.insert_with(key: "b", value: 2, with: sum) +/// |> dict.insert_with(key: "a", value: 3, with: sum) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 4), Pair("b", 2)] +/// ``` +pub fn insert_with( + self: Dict, + key k: ByteArray, + value v: value, + with: fn(ByteArray, value, value) -> Option, +) -> Dict { + Dict { + inner: do_insert_with(self.inner, k, v, fn(k, v1, v2) { with(k, v2, v1) }), + } +} + +test insert_with_1() { + let sum = + fn(_k, a, b) { Some(a + b) } + + let result = + empty + |> insert_with(key: "foo", value: 1, with: sum) + |> insert_with(key: "bar", value: 2, with: sum) + |> to_pairs() + + result == [Pair("bar", 2), Pair("foo", 1)] +} + +test insert_with_2() { + let sum = + fn(_k, a, b) { Some(a + b) } + + let result = + empty + |> insert_with(key: "foo", value: 1, with: sum) + |> insert_with(key: "bar", value: 2, with: sum) + |> insert_with(key: "foo", value: 3, with: sum) + |> to_pairs() + + result == [Pair("bar", 2), Pair("foo", 4)] +} + +test insert_with_3() { + let with = + fn(k, a, _b) { + if k == "foo" { + Some(a) + } else { + None + } + } + + let result = + empty + |> insert_with(key: "foo", value: 1, with: with) + |> insert_with(key: "bar", value: 2, with: with) + |> insert_with(key: "foo", value: 3, with: with) + |> insert_with(key: "bar", value: 4, with: with) + |> to_pairs() + + result == [Pair("foo", 1)] +} + +/// Apply a function to all key-value pairs in a Dict. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 100) +/// |> dict.insert("b", 200) +/// |> dict.insert("c", 300) +/// |> dict.map(fn(_k, v) { v * 2 }) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 200), Pair("b", 400), Pair("c", 600)] +/// ``` +pub fn map(self: Dict, with: fn(ByteArray, a) -> b) -> Dict { + Dict { inner: do_map(self.inner, with) } +} + +fn do_map( + self: Pairs, + with: fn(ByteArray, a) -> b, +) -> Pairs { + when self is { + [] -> [] + [Pair(k, v), ..rest] -> [Pair(k, with(k, v)), ..do_map(rest, with)] + } +} + +test map_1() { + let result = + fixture_1 + |> map(with: fn(k, _) { k }) + get(result, foo) == Some(foo) +} + +test map_2() { + let result = + fixture_1 + |> map(with: fn(_, v) { v + 1 }) + get(result, foo) == Some(43) && size(result) == size(fixture_1) +} + +/// Remove a key-value pair from the dictionary and return its value. If the key is not found, no changes are made. +/// +/// ```aiken +/// let (value, _) = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.pop(key: "a") +/// +/// result == 100 +/// ``` +pub fn pop( + self: Dict, + key: ByteArray, +) -> (Option, Dict) { + do_pop(self.inner, key, fn(value, inner) { (value, Dict { inner }) }) +} + +fn do_pop( + self: Pairs, + key k: ByteArray, + return: fn(Option, Pairs) -> result, +) -> result { + when self is { + [] -> return(None, []) + [Pair(k2, v2), ..rest] -> + if builtin.less_than_equals_bytearray(k, k2) { + if k == k2 { + return(Some(v2), rest) + } else { + return(None, self) + } + } else { + do_pop( + rest, + k, + fn(value, inner) { return(value, [Pair(k2, v2), ..inner]) }, + ) + } + } +} + +test pop_1() { + pop(empty, foo) == (None, empty) +} + +test pop_2() { + let m = + empty + |> insert(foo, 14) + pop(m, foo) == (Some(14), empty) +} + +test pop_3() { + let m = + empty + |> insert(foo, 14) + pop(m, bar) == (None, m) +} + +test pop_4() { + let m = + empty + |> insert(foo, 14) + |> insert(bar, 14) + pop(m, foo) == (Some(14), empty |> insert(bar, 14)) +} + +test pop_6() { + let m = + empty + |> insert("aaa", 1) + |> insert("bbb", 2) + |> insert("ccc", 3) + |> insert("ddd", 4) + |> insert("eee", 5) + |> insert("fff", 6) + |> insert("ggg", 7) + |> insert("hhh", 8) + |> insert("iii", 9) + |> insert("jjj", 10) + + pop(m, "bcd") == (None, m) +} + +// ## Combining + +/// Combine two dictionaries. If the same key exist in both the left and +/// right dictionary, values from the left are preferred (i.e. left-biaised). +/// +/// ```aiken +/// let left_dict = dict.from_pairs([Pair("a", 100), Pair("b", 200)]) +/// let right_dict = dict.from_pairs([Pair("a", 150), Pair("c", 300)]) +/// +/// let result = +/// dict.union(left_dict, right_dict) |> dict.to_pairs() +/// +/// result == [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn union( + left: Dict, + right: Dict, +) -> Dict { + Dict { inner: do_union(left.inner, right.inner) } +} + +fn do_union( + left: Pairs, + right: Pairs, +) -> Pairs { + when left is { + [] -> right + [Pair(k, v), ..rest] -> do_union(rest, do_insert(right, k, v)) + } +} + +test union_1() { + union(fixture_1, empty) == fixture_1 +} + +test union_2() { + union(empty, fixture_1) == fixture_1 +} + +test union_3() { + let left = + empty + |> insert(foo, 14) + let right = + empty + |> insert(bar, 42) + |> insert(baz, 1337) + union(left, right) == from_pairs( + [Pair(foo, 14), Pair(baz, 1337), Pair(bar, 42)], + ) +} + +test union_4() { + let left = + empty + |> insert(foo, 14) + let right = + empty + |> insert(bar, 42) + |> insert(foo, 1337) + union(left, right) == from_pairs([Pair(foo, 14), Pair(bar, 42)]) +} + +/// Like [`union`](#union) but allows specifying the behavior to adopt when a key is present +/// in both dictionaries. The first value received correspond to the value in the left +/// dictionnary, whereas the second argument corresponds to the value in the right dictionnary. +/// +/// When passing `None`, the value is removed and not present in the union. +/// +/// ```aiken +/// let left_dict = dict.from_pairs([Pair("a", 100), Pair("b", 200)]) +/// let right_dict = dict.from_pairs([Pair("a", 150), Pair("c", 300)]) +/// +/// let result = +/// dict.union_with( +/// left_dict, +/// right_dict, +/// fn(_k, v1, v2) { Some(v1 + v2) }, +/// ) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 250), Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn union_with( + left: Dict, + right: Dict, + with: fn(ByteArray, value, value) -> Option, +) -> Dict { + Dict { inner: do_union_with(left.inner, right.inner, with) } +} + +fn do_union_with( + left: Pairs, + right: Pairs, + with: fn(ByteArray, value, value) -> Option, +) -> Pairs { + when left is { + [] -> right + [Pair(k, v), ..rest] -> + do_union_with(rest, do_insert_with(right, k, v, with), with) + } +} + +fn do_insert_with( + self: Pairs, + key k: ByteArray, + value v: value, + with: fn(ByteArray, value, value) -> Option, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if builtin.less_than_bytearray(k, k2) { + [Pair(k, v), ..self] + } else { + if k == k2 { + when with(k, v, v2) is { + Some(combined) -> [Pair(k, combined), ..rest] + None -> rest + } + } else { + [Pair(k2, v2), ..do_insert_with(rest, k, v, with)] + } + } + } +} + +test union_with_1() { + let left = + empty + |> insert(foo, 14) + + let right = + empty + |> insert(bar, 42) + |> insert(foo, 1337) + + let result = union_with(left, right, with: fn(_, l, r) { Some(l + r) }) + + result == from_pairs([Pair(foo, 1351), Pair(bar, 42)]) +} + +// ## Transforming + +/// Fold over the key-value pairs in a dictionary. The fold direction follows keys +/// in ascending order and is done from left-to-right. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.insert(key: "c", value: 300) +/// |> dict.foldl(0, fn(_k, v, r) { v + r }) +/// +/// result == 600 +/// ``` +pub fn foldl( + self: Dict, + zero: result, + with: fn(ByteArray, value, result) -> result, +) -> result { + do_foldl(self.inner, zero, with) +} + +fn do_foldl( + self: Pairs, + zero: result, + with: fn(ByteArray, value, result) -> result, +) -> result { + when self is { + [] -> zero + [Pair(k, v), ..rest] -> do_foldl(rest, with(k, v, zero), with) + } +} + +test fold_1() { + foldl(empty, 14, fn(_, _, _) { 42 }) == 14 +} + +test fold_2() { + foldl(fixture_1, zero: 0, with: fn(_, v, total) { v + total }) == 56 +} + +/// Fold over the key-value pairs in a dictionary. The fold direction follows keys +/// in ascending order and is done from right-to-left. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert(key: "a", value: 100) +/// |> dict.insert(key: "b", value: 200) +/// |> dict.insert(key: "c", value: 300) +/// |> dict.foldr(0, fn(_k, v, r) { v + r }) +/// +/// result == 600 +/// ``` +pub fn foldr( + self: Dict, + zero: result, + with: fn(ByteArray, value, result) -> result, +) -> result { + do_foldr(self.inner, zero, with) +} + +fn do_foldr( + self: Pairs, + zero: result, + with: fn(ByteArray, value, result) -> result, +) -> result { + when self is { + [] -> zero + [Pair(k, v), ..rest] -> with(k, v, do_foldr(rest, zero, with)) + } +} + +test foldr_1() { + foldr(empty, 14, fn(_, _, _) { 42 }) == 14 +} + +test foldr_2() { + foldr(fixture_1, zero: 0, with: fn(_, v, total) { v + total }) == 56 +} + +/// Get the inner list holding the dictionary data. +/// +/// ```aiken +/// let result = +/// dict.empty +/// |> dict.insert("a", 100) +/// |> dict.insert("b", 200) +/// |> dict.insert("c", 300) +/// |> dict.to_pairs() +/// +/// result == [Pair("a", 100), Pair("b", 200), Pair("c", 300)] +/// ``` +pub fn to_pairs(self: Dict) -> Pairs { + self.inner +} + +test to_list_1() { + to_pairs(empty) == [] +} + +test to_list_2() { + to_pairs(fixture_1) == [Pair(bar, 14), Pair(foo, 42)] +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection/list.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection/list.ak new file mode 100644 index 00000000..b8e7f675 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection/list.ak @@ -0,0 +1,1411 @@ +use aiken/builtin +use aiken/primitive/bytearray +use aiken/primitive/int + +// ## Constructing + +/// Add an element in front of the list. Sometimes useful when combined with +/// other functions. +/// +/// ```aiken +/// list.push([2, 3], 1) == [1, ..[2, 3]] == [1, 2, 3] +/// ``` +pub fn push(self: List, elem: a) -> List { + [elem, ..self] +} + +test push_1() { + push([], 0) == [0] +} + +test push_2() { + push([2, 3], 1) == [1, 2, 3] +} + +/// Construct a list of a integer from a given range. +/// +/// ```aiken +/// list.range(0, 3) == [0, 1, 2, 3] +/// list.range(-1, 1) == [-1, 0, 1] +/// ``` +pub fn range(from: Int, to: Int) -> List { + if from > to { + [] + } else { + [from, ..range(from + 1, to)] + } +} + +test range_1() { + range(0, 3) == [0, 1, 2, 3] +} + +test range_2() { + range(-1, 1) == [-1, 0, 1] +} + +/// Construct a list filled with n copies of a value. +/// +/// ```aiken +/// list.repeat("na", 3) == ["na", "na", "na"] +/// ``` +pub fn repeat(elem: a, n_times: Int) -> List { + if n_times <= 0 { + [] + } else { + [elem, ..repeat(elem, n_times - 1)] + } +} + +test repeat_1() { + repeat(42, 0) == [] +} + +test repeat_2() { + repeat(14, 3) == [14, 14, 14] +} + +// ## Inspecting + +/// Determine if all elements of the list satisfy the given predicate. +/// +/// Note: an empty list always satisfies the predicate. +/// +/// ```aiken +/// list.all([], fn(n) { n > 0 }) == True +/// list.all([1, 2, 3], fn(n) { n > 0 }) == True +/// list.all([1, 2, 3], fn(n) { n == 2 }) == False +/// ``` +pub fn all(self: List, predicate: fn(a) -> Bool) -> Bool { + when self is { + [] -> True + [x, ..xs] -> predicate(x) && all(xs, predicate) + } +} + +test all_1() { + all([1, 2, 3], fn(n) { n > 0 }) == True +} + +test all_2() { + all([1, 2, 3], fn(n) { n > 42 }) == False +} + +test all_3() { + all([], fn(n) { n == 42 }) == True +} + +/// Determine if at least one element of the list satisfies the given predicate. +/// +/// Note: an empty list never satisfies the predicate. +/// +/// ```aiken +/// list.any([], fn(n) { n > 2 }) == False +/// list.any([1, 2, 3], fn(n) { n > 0 }) == True +/// list.any([1, 2, 3], fn(n) { n == 2 }) == True +/// list.any([1, 2, 3], fn(n) { n < 0 }) == False +/// ``` +pub fn any(self: List, predicate: fn(a) -> Bool) -> Bool { + when self is { + [] -> False + [x, ..xs] -> predicate(x) || any(xs, predicate) + } +} + +test any_1() { + any([1, 2, 3], fn(n) { n > 0 }) == True +} + +test any_2() { + any([1, 2, 3], fn(n) { n > 42 }) == False +} + +test any_3() { + any([], fn(n) { n == 42 }) == False +} + +/// Return Some(item) at the index or None if the index is out of range. The index is 0-based. +/// +/// ```aiken +/// list.at([1, 2, 3], 1) == Some(2) +/// list.at([1, 2, 3], 42) == None +/// ``` +pub fn at(self: List, index: Int) -> Option { + when self is { + [] -> None + [x, ..xs] -> + if index == 0 { + Some(x) + } else { + at(xs, index - 1) + } + } +} + +test at_1() { + at([1, 2, 3], -1) == None +} + +test at_2() { + at([], 0) == None +} + +test at_3() { + at([1, 2, 3], 3) == None +} + +test at_4() { + at([1], 0) == Some(1) +} + +test at_5() { + at([1, 2, 3], 2) == Some(3) +} + +/// Count how many items in the list satisfy the given predicate. +/// +/// ```aiken +/// list.count([], fn(a) { a > 2}) == 0 +/// list.count([1, 2, 3], fn(a) { n > 0 }) == 3 +/// list.count([1, 2, 3], fn(a) { n >= 2 }) == 2 +/// list.count([1, 2, 3], fn(a) { n > 5 }) == 0 +/// ``` +pub fn count(self: List, predicate: fn(a) -> Bool) -> Int { + foldr( + self, + 0, + fn(item, total) { + if predicate(item) { + total + 1 + } else { + total + } + }, + ) +} + +test count_empty() { + count([], fn(a) { a > 2 }) == 0 +} + +test count_all() { + count([1, 2, 3], fn(a) { a > 0 }) == 3 +} + +test count_some() { + count([1, 2, 3], fn(a) { a >= 2 }) == 2 +} + +test count_none() { + count([1, 2, 3], fn(a) { a > 5 }) == 0 +} + +/// Find the first element satisfying the given predicate, if any. +/// +/// ```aiken +/// list.find([1, 2, 3], fn(x) { x == 2 }) == Some(2) +/// list.find([4, 5, 6], fn(x) { x == 2 }) == None +/// ``` +pub fn find(self: List, predicate: fn(a) -> Bool) -> Option { + when self is { + [] -> None + [x, ..xs] -> + if predicate(x) { + Some(x) + } else { + find(xs, predicate) + } + } +} + +test find_1() { + find([1, 2, 3], fn(x) { x == 1 }) == Some(1) +} + +test find_2() { + find([1, 2, 3], fn(x) { x > 42 }) == None +} + +test find_3() { + find([], fn(_) { True }) == None +} + +/// Figures out whether a list contain the given element. +/// +/// ```aiken +/// list.has([1, 2, 3], 2) == True +/// list.has([1, 2, 3], 14) == False +/// list.has([], 14) == False +/// ``` +pub fn has(self: List, elem: a) -> Bool { + when self is { + [] -> False + [x, ..xs] -> + if x == elem { + True + } else { + has(xs, elem) + } + } +} + +test has_1() { + has([1, 2, 3], 1) == True +} + +test has_2() { + has([1, 2, 3], 14) == False +} + +test has_3() { + has([], 14) == False +} + +/// Get the first element of a list +/// +/// ```aiken +/// list.head([1, 2, 3]) == Some(1) +/// list.head([]) == None +/// ``` +pub fn head(self: List) -> Option { + when self is { + [] -> None + _ -> Some(builtin.head_list(self)) + } +} + +test head_1() { + head([1, 2, 3]) == Some(1) +} + +test head_2() { + head([]) == None +} + +/// Checks whether a list is empty. +/// +/// ```aiken +/// list.is_empty([]) == True +/// list.is_empty([1, 2, 3]) == False +/// ``` +pub fn is_empty(self: List) -> Bool { + when self is { + [] -> True + _ -> False + } +} + +test is_empty_1() { + is_empty([]) == True +} + +test is_empty_2() { + is_empty([1, 2, 3]) == False +} + +/// Gets the index of an element of a list, if any. Otherwise, returns None. +/// +/// ```aiken +/// list.index_of([1, 5, 2], 2) == Some(2) +/// list.index_of([1, 7, 3], 4) == None +/// list.index_of([1, 0, 9, 6], 6) == 3 +/// list.index_of([], 6) == None +/// ``` +pub fn index_of(self: List, elem: a) -> Option { + do_index_of(self, elem, 0) +} + +fn do_index_of(self: List, elem: a, i: Int) -> Option { + when self is { + [] -> None + [x, ..xs] -> + if x == elem { + Some(i) + } else { + do_index_of(xs, elem, i + 1) + } + } +} + +test index_of_1() { + index_of([1, 5, 2], 2) == Some(2) +} + +test index_of_2() { + index_of([1, 7, 3], 4) == None +} + +test index_of_3() { + index_of([1, 0, 9, 6], 6) == Some(3) +} + +test index_of_4() { + index_of([], 6) == None +} + +/// Get the last in the given list, if any. +/// +/// ```aiken +/// list.last([]) == None +/// list.last([1, 2, 3]) == Some(3) +/// ``` +pub fn last(self: List) -> Option { + when self is { + [] -> None + [x] -> Some(x) + [_, ..xs] -> last(xs) + } +} + +test last_1() { + last([]) == None +} + +test last_2() { + last([1]) == Some(1) +} + +test last_3() { + last([1, 2, 3, 4]) == Some(4) +} + +/// Get the number of elements in the given list. +/// +/// ```aiken +/// list.length([]) == 0 +/// list.length([1, 2, 3]) == 3 +/// ``` +pub fn length(self: List) -> Int { + when self is { + [] -> 0 + [_, ..xs] -> 1 + length(xs) + } +} + +test length_1() { + length([]) == 0 +} + +test length_2() { + length([1, 2, 3]) == 3 +} + +// ## Modifying + +// ### Extracting + +/// Remove the first occurrence of the given element from the list. +/// +/// ```aiken +/// list.delete([1, 2, 3, 1], 1) == [2, 3, 1] +/// list.delete([1, 2, 3], 14) == [1, 2, 3] +/// ``` +pub fn delete(self: List, elem: a) -> List { + when self is { + [] -> [] + [x, ..xs] -> + if x == elem { + xs + } else { + [x, ..delete(xs, elem)] + } + } +} + +test delete_1() { + delete([], 42) == [] +} + +test delete_2() { + delete([1, 2, 3, 1], 1) == [2, 3, 1] +} + +test delete_3() { + delete([1, 2, 3], 14) == [1, 2, 3] +} + +test delete_4() { + delete([2], 2) == [] +} + +/// Drop the first `n` elements of a list. +/// +/// ```aiken +/// list.drop([1, 2, 3], 2) == [3] +/// list.drop([], 42) == [] +/// list.drop([1, 2, 3], 42) == [] +/// ``` +pub fn drop(self: List, n: Int) -> List { + if n <= 0 { + self + } else { + when self is { + [] -> [] + [_x, ..xs] -> drop(xs, n - 1) + } + } +} + +test drop_1() { + drop([], 42) == [] +} + +test drop_2() { + drop([1, 2, 3], 2) == [3] +} + +/// Returns the suffix of the given list after removing all elements that satisfy the predicate. +/// +/// ```aiken +/// list.drop_while([1, 2, 3], fn(x) { x < 2 }) == [2, 3] +/// list.drop_while([], fn(x) { x > 2 }) == [] +/// list.drop_while([1, 2, 3], fn(x) { x == 3 }) == [1, 2, 3] +/// ``` +pub fn drop_while(self: List, predicate: fn(a) -> Bool) -> List { + when self is { + [] -> [] + [x, ..xs] -> + if predicate(x) { + drop_while(xs, predicate) + } else { + self + } + } +} + +test drop_while_1() { + drop_while([], fn(x) { x > 2 }) == [] +} + +test drop_while_2() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + drop_while(xs, fn(x) { x > 5 }) == [5, 4, 3, 2, 1] +} + +test drop_while_3() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + drop_while(xs, fn(x) { x == 42 }) == xs +} + +test drop_while_4() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + drop_while(xs, fn(x) { x < 42 }) == [] +} + +/// Produce a list of elements that satisfy a predicate. +/// +/// ```aiken +/// list.filter([1, 2, 3], fn(x) { x >= 2 }) == [2, 3] +/// list.filter([], fn(x) { x > 2 }) == [] +/// list.filter([1, 2, 3], fn(x) { x == 3 }) == [3] +/// ``` +pub fn filter(self: List, predicate: fn(a) -> Bool) -> List { + when self is { + [] -> [] + [x, ..xs] -> + if predicate(x) { + [x, ..filter(xs, predicate)] + } else { + filter(xs, predicate) + } + } +} + +test filter_1() { + filter([], fn(x) { x > 0 }) == [] +} + +test filter_2() { + let xs = [1, 2, 3, 4, 5, 6] + filter(xs, fn(x) { builtin.mod_integer(x, 2) == 0 }) == [2, 4, 6] +} + +test filter_3() { + let filter_foldr = + fn(xs, f) { + foldr( + xs, + [], + fn(x, ys) { + if f(x) { + [x, ..ys] + } else { + ys + } + }, + ) + } + + let is_odd = + fn(n) { builtin.mod_integer(n, 2) != 0 } + + filter_foldr([1, 2, 3], is_odd) == filter([1, 2, 3], is_odd) +} + +/// Produce a list of transformed elements that satisfy a predicate. +/// +/// ```aiken +/// let transform = fn(x) { if x % 2 == 0 { None } else { Some(3*x) } } +/// list.filter_map([1, 2, 3], transform) == [3, 9] +/// ``` +pub fn filter_map(self: List, predicate: fn(a) -> Option) -> List { + when self is { + [] -> [] + [x, ..xs] -> + when predicate(x) is { + None -> filter_map(xs, predicate) + Some(y) -> [y, ..filter_map(xs, predicate)] + } + } +} + +test filter_map_1() { + filter_map([], fn(_) { Some(42) }) == [] +} + +test filter_map_2() { + filter_map( + [1, 2, 3, 4, 5, 6], + fn(x) { + if builtin.mod_integer(x, 2) != 0 { + Some(3 * x) + } else { + None + } + }, + ) == [3, 9, 15] +} + +/// Return all elements except the last one. +/// +/// ```aiken +/// list.init([]) == None +/// list.init([1, 2, 3]) == Some([1, 2]) +/// ``` +pub fn init(self: List) -> Option> { + when self is { + [] -> None + _ -> Some(do_init(self)) + } +} + +fn do_init(self: List) -> List { + when self is { + [] -> fail @"unreachable" + [_] -> [] + [x, ..xs] -> [x, ..do_init(xs)] + } +} + +test init_1() { + init([]) == None +} + +test init_2() { + init([1]) == Some([]) +} + +test init_3() { + init([1, 2, 3, 4]) == Some([1, 2, 3]) +} + +/// Returns a tuple with all elements that satisfy the predicate at first +/// element, and the rest as second element. +/// +/// ```aiken +/// list.partition([1, 2, 3, 4], fn(x) { x % 2 == 0 }) == ([2, 4], [1, 3]) +/// ``` +pub fn partition(self: List, predicate: fn(a) -> Bool) -> (List, List) { + when self is { + [] -> ([], []) + [x, ..xs] -> { + let (left, right) = partition(xs, predicate) + if predicate(x) { + ([x, ..left], right) + } else { + (left, [x, ..right]) + } + } + } +} + +test partition_1() { + partition([], fn(x) { x > 2 }) == ([], []) +} + +test partition_2() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + partition(xs, fn(x) { x > 5 }) == ([10, 9, 8, 7, 6], [5, 4, 3, 2, 1]) +} + +test partition_3() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + partition(xs, fn(x) { x == 42 }) == ([], xs) +} + +test partition_4() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + partition(xs, fn(x) { x < 42 }) == (xs, []) +} + +test partition_5() { + partition([1, 2, 3, 4], fn(x) { x % 2 == 0 }) == ([2, 4], [1, 3]) +} + +/// Extract a sublist from the given list using 0-based indexes. Negative +/// indexes wrap over, so `-1` refers to the last element of the list. +/// +/// ```aiken +/// list.slice([1, 2, 3, 4, 5, 6], from: 2, to: 4) == [3, 4, 5] +/// list.slice([1, 2, 3, 4, 5, 6], from: -2, to: -1) == [5, 6] +/// list.slice([1, 2, 3, 4, 5, 6], from: 1, to: -1) == [2, 3, 4, 5, 6] +/// ``` +pub fn slice(self: List, from: Int, to: Int) -> List { + let (i, l) = + if from >= 0 { + (from, None) + } else { + let l = length(self) + (l + from, Some(l)) + } + + let j = + if to >= 0 { + to - i + 1 + } else { + when l is { + Some(l) -> l + to - i + 1 + None -> length(self) + to - i + 1 + } + } + + self + |> drop(i) + |> take(j) +} + +test slice_1() { + slice([1, 2, 3], 0, 2) == [1, 2, 3] +} + +test slice_2() { + slice([1, 2, 3, 4, 5, 6], from: 2, to: 4) == [3, 4, 5] +} + +test slice_3() { + slice([1, 2, 3, 4, 5, 6], from: -2, to: -1) == [5, 6] +} + +test slice_4() { + slice([1, 2, 3, 4, 5, 6], from: 1, to: -1) == [2, 3, 4, 5, 6] +} + +test slice_5() { + slice([1, 2, 3, 4, 5, 6], from: -4, to: -3) == [3, 4] +} + +test slice_6() { + slice([1, 2, 3, 4, 5, 6], from: -2, to: 1) == [] +} + +/// Cut a list in two, such that the first list contains the given number of / +/// elements and the second list contains the rest. +/// +/// Fundamentally equivalent to (but more efficient): +/// +/// ```aiken +/// // span(xs, n) == (take(xs, n), drop(xs, n)) +/// span([1, 2, 3, 4, 5], 3) == ([1, 2, 3], [4, 5]) +/// ``` +pub fn span(self: List, n: Int) -> (List, List) { + when self is { + [] -> ([], []) + [x, ..xs] -> + if n <= 0 { + ([], self) + } else { + let (left, right) = span(xs, n - 1) + ([x, ..left], right) + } + } +} + +test span_1() { + span([], 2) == ([], []) +} + +test span_2() { + span([1, 2, 3], 2) == ([1, 2], [3]) +} + +test span_3() { + span([1, 2, 3], -1) == ([], [1, 2, 3]) +} + +test span_4() { + span([1, 2, 3], 42) == ([1, 2, 3], []) +} + +/// Get elements of a list after the first one, if any. +/// +/// ```aiken +/// list.tail([]) == None +/// list.tail([1, 2, 3]) == Some([2, 3]) +/// ``` +pub fn tail(self: List) -> Option> { + when self is { + [] -> None + [_, ..xs] -> Some(xs) + } +} + +test tail_1() { + tail([1, 2, 3]) == Some([2, 3]) +} + +test tail_2() { + tail([]) == None +} + +/// Get the first `n` elements of a list. +/// +/// ```aiken +/// list.take([1, 2, 3], 2) == [1, 2] +/// list.take([1, 2, 3], 14) == [1, 2, 3] +/// ``` +pub fn take(self: List, n: Int) -> List { + if n <= 0 { + [] + } else { + when self is { + [] -> [] + [x, ..xs] -> [x, ..take(xs, n - 1)] + } + } +} + +test take_1() { + take([], 42) == [] +} + +test take_2() { + take([1, 2, 3], 2) == [1, 2] +} + +/// Returns the longest prefix of the given list where all elements satisfy the predicate. +/// +/// ```aiken +/// list.take_while([1, 2, 3], fn(x) { x > 2 }) == [] +/// list.take_while([1, 2, 3], fn(x) { x < 2 }) == [1] +/// ``` +pub fn take_while(self: List, predicate: fn(a) -> Bool) -> List { + when self is { + [] -> [] + [x, ..xs] -> + if predicate(x) { + [x, ..take_while(xs, predicate)] + } else { + [] + } + } +} + +test take_while_1() { + take_while([], fn(x) { x > 2 }) == [] +} + +test take_while_2() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + take_while(xs, fn(x) { x > 5 }) == [10, 9, 8, 7, 6] +} + +test take_while_3() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + take_while(xs, fn(x) { x == 42 }) == [] +} + +test take_while_4() { + let xs = [10, 9, 8, 7, 6, 5, 4, 3, 2, 1] + take_while(xs, fn(x) { x < 42 }) == xs +} + +/// Removes duplicate elements from a list. +/// +/// ```aiken +/// list.unique([1, 2, 3, 1]) == [1, 2, 3] +/// ``` +pub fn unique(self: List) -> List { + when self is { + [] -> [] + [x, ..xs] -> [x, ..unique(filter(xs, fn(y) { y != x }))] + } +} + +test unique_1() { + unique([]) == [] +} + +test unique_2() { + let xs = [1, 2, 3, 1, 1, 3, 4, 1, 2, 3, 2, 4, 5, 6, 7, 8, 9, 10, 9] + unique(xs) == [1, 2, 3, 4, 5, 6, 7, 8, 9, 10] +} + +// ### Mapping + +/// Map elements of a list into a new list and flatten the result. +/// +/// ```aiken +/// list.flat_map([1, 2, 3], fn(a) { [a, 2*a] }) == [1, 2, 2, 4, 3, 6] +/// ``` +pub fn flat_map(self: List, with: fn(a) -> List) -> List { + foldr(self, [], fn(x, xs) { concat(with(x), xs) }) +} + +test flat_map_1() { + flat_map([], fn(a) { [a] }) == [] +} + +test flat_map_2() { + flat_map([1, 2, 3], fn(a) { [a, a] }) == [1, 1, 2, 2, 3, 3] +} + +/// Perform an action for each element of a list. +/// +/// ```aiken +/// list.for_each(labels, do: fn(lbl) { trace lbl Void }) +/// ``` +pub fn for_each(self: List, do: fn(a) -> Void) -> Void { + foldr(self, Void, fn(x, _) { do(x) }) +} + +test for_each_1() { + for_each( + [@"hello", @"world"], + do: fn(lbl) { + trace lbl + Void + }, + ) +} + +/// List [`map`](#map) but provides the position (0-based) of the elements while iterating. +/// +/// ```aiken +/// list.indexed_map([1, 2, 3], fn(i, x) { i + x }) == [1, 3, 5] +/// ``` +pub fn indexed_map(self: List, with: fn(Int, a) -> result) -> List { + do_indexed_map(0, self, with) +} + +fn do_indexed_map( + n: Int, + self: List, + with: fn(Int, a) -> result, +) -> List { + when self is { + [] -> [] + [x, ..xs] -> [with(n, x), ..do_indexed_map(n + 1, xs, with)] + } +} + +test indexed_map_1() { + indexed_map([], fn(i, _n) { i }) == [] +} + +test indexed_map_2() { + indexed_map( + [4, 8, 13, 2], + fn(i, n) { + if n == 8 { + n + } else { + i + } + }, + ) == [0, 8, 2, 3] +} + +/// Apply a function to each element of a list. +/// +/// ```aiken +/// list.map([1, 2, 3, 4], fn(n) { n + 1 }) == [2, 3, 4, 5] +/// ``` +pub fn map(self: List, with: fn(a) -> result) -> List { + when self is { + [] -> [] + [x, ..xs] -> [with(x), ..map(xs, with)] + } +} + +test map_1() { + map([], fn(n) { n + 1 }) == [] +} + +test map_2() { + map([1, 2, 3, 4], fn(n) { n + 1 }) == [2, 3, 4, 5] +} + +/// Apply a function of two arguments, combining elements from two lists. +/// +/// Note: if one list is longer, the extra elements are dropped. +/// +/// ```aiken +/// list.map2([1, 2, 3], [1, 2], fn(a, b) { a + b }) == [2, 4] +/// ``` +pub fn map2( + self: List, + bs: List, + with: fn(a, b) -> result, +) -> List { + when self is { + [] -> [] + [x, ..xs] -> + when bs is { + [] -> [] + [y, ..ys] -> [with(x, y), ..map2(xs, ys, with)] + } + } +} + +test map2_1() { + map2([], [1, 2, 3], fn(a, b) { a + b }) == [] +} + +test map2_2() { + map2([1, 2, 3], [1, 2], fn(a, b) { a + b }) == [2, 4] +} + +test map2_3() { + map2([42], [1, 2, 3], fn(_a, b) { Some(b) }) == [Some(1)] +} + +/// Apply a function of three arguments, combining elements from three lists. +/// +/// Note: if one list is longer, the extra elements are dropped. +/// +/// ```aiken +/// list.map3([1, 2, 3], [1, 2], [1, 2, 3], fn(a, b, c) { a + b + c }) == [3, 6] +/// ``` +pub fn map3( + self: List, + bs: List, + cs: List, + with: fn(a, b, c) -> result, +) -> List { + when self is { + [] -> [] + [x, ..xs] -> + when bs is { + [] -> [] + [y, ..ys] -> + when cs is { + [] -> [] + [z, ..zs] -> [with(x, y, z), ..map3(xs, ys, zs, with)] + } + } + } +} + +test map3_1() { + map3([], [], [1, 2, 3], fn(a, b, c) { a + b + c }) == [] +} + +test map3_2() { + map3([1, 2, 3], [1, 2], [1, 2, 3], fn(a, b, c) { a + b + c }) == [3, 6] +} + +/// Return the list with its elements in the reserve order. +/// +/// ```aiken +/// list.reverse([1, 2, 3]) == [3, 2, 1] +/// ``` +pub fn reverse(self: List) -> List { + foldl(self, [], fn(x, xs) { [x, ..xs] }) +} + +test reverse_1() { + reverse([]) == [] +} + +test reverse_2() { + reverse([1, 2, 3]) == [3, 2, 1] +} + +/// Sort a list in ascending order using the given comparison function. +/// +/// ```aiken +/// use aiken/int +/// +/// sort([3, 1, 4, 0, 2], int.compare) == [0, 1, 2, 3, 4] +/// sort([1, 2, 3], int.compare) == [1, 2, 3] +/// ``` +pub fn sort(self: List, compare: fn(a, a) -> Ordering) -> List { + when self is { + [] -> [] + [x, ..xs] -> insert(sort(xs, compare), x, compare) + } +} + +fn insert(self: List, e: a, compare: fn(a, a) -> Ordering) -> List { + when self is { + [] -> [e] + [x, ..xs] -> + if compare(e, x) == Less { + [e, ..self] + } else { + [x, ..insert(xs, e, compare)] + } + } +} + +test sort_1() { + let xs = [6, 7, 5, 4, 1, 3, 9, 8, 0, 2] + sort(xs, int.compare) == [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] +} + +test sort_2() { + let xs = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] + sort(xs, int.compare) == [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] +} + +test sort_3() { + let xs = [9, 8, 7, 6, 5, 4, 3, 2, 1, 0] + sort(xs, int.compare) == [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] +} + +test sort_4() { + sort([], int.compare) == [] +} + +/// Decompose a list of tuples into a tuple of lists. +/// +/// ``` +/// list.unzip([(1, "a"), (2, "b")]) == ([1, 2], ["a", "b"]) +/// ``` +pub fn unzip(self: List<(a, b)>) -> (List, List) { + when self is { + [] -> ([], []) + [(a, b), ..xs] -> { + let (a_tail, b_tail) = unzip(xs) + ([a, ..a_tail], [b, ..b_tail]) + } + } +} + +test unzip_1() { + unzip([]) == ([], []) +} + +test unzip_2() { + unzip([(1, "a"), (2, "b")]) == ([1, 2], ["a", "b"]) +} + +// ## Combining + +/// Merge two lists together. +/// +/// ```aiken +/// list.concat([], []) == [] +/// list.concat([], [1, 2, 3]) == [1, 2, 3] +/// list.concat([1, 2, 3], [4, 5, 6]) == [1, 2, 3, 4, 5, 6] +/// ``` +pub fn concat(left: List, right: List) -> List { + when left is { + [] -> right + [x, ..xs] -> [x, ..concat(xs, right)] + } +} + +test concat_1() { + concat([1, 2, 3], [4, 5, 6]) == [1, 2, 3, 4, 5, 6] +} + +test concat_2() { + concat([1, 2, 3], []) == [1, 2, 3] +} + +test concat_3() { + concat([], [1, 2, 3]) == [1, 2, 3] +} + +/// Remove the first occurrence of each element of the second list from the first one. +/// +/// ``` +/// list.difference(["h", "e", "l", "l", "o"], ["l", "e", "l"]) == ["h", "o"] +/// list.difference([1, 2, 3, 4, 5], [1, 1, 2]) == [3, 4, 5] +/// list.difference([1, 2, 3], []) == [1, 2, 3] +/// ``` +pub fn difference(self: List, with: List) -> List { + when with is { + [] -> self + [x, ..xs] -> difference(delete(self, x), xs) + } +} + +test difference_1() { + difference(["h", "e", "l", "l", "o"], ["l", "e", "l"]) == ["h", "o"] +} + +test difference_2() { + difference([1, 2, 3, 4, 5], [1, 1, 2]) == [3, 4, 5] +} + +test difference_3() { + difference([1, 2, 3], []) == [1, 2, 3] +} + +test difference_4() { + difference([], [1, 2, 3]) == [] +} + +/// Combine two lists together. +/// +/// Note: if one list is longer, the extra elements are dropped. +/// +/// ```aiken +/// list.zip([1, 2], ["a", "b", "c"]) == [(1, "a"), (2, "b")] +/// ``` +pub fn zip(self: List, bs: List) -> List<(a, b)> { + when self is { + [] -> [] + [x, ..xs] -> + when bs is { + [] -> [] + [y, ..ys] -> [(x, y), ..zip(xs, ys)] + } + } +} + +test zip_1() { + zip([], [1, 2, 3]) == [] +} + +test zip_2() { + zip([1, 2, 3], []) == [] +} + +test zip_3() { + zip([1, 2], ["a", "b", "c"]) == [(1, "a"), (2, "b")] +} + +// ## Transforming + +/// Reduce a list from left to right. +/// +/// ```aiken +/// list.foldl([1, 2, 3], 0, fn(n, total) { n + total }) == 6 +/// list.foldl([1, 2, 3], [], fn(x, xs) { [x, ..xs] }) == [3, 2, 1] +/// ``` +pub fn foldl(self: List, zero: b, with: fn(a, b) -> b) -> b { + when self is { + [] -> zero + [x, ..xs] -> foldl(xs, with(x, zero), with) + } +} + +type Fold2 = + fn(a, b) -> result + +pub fn foldl2( + self: List, + zero_a: a, + zero_b: b, + with: fn(elem, a, b, Fold2) -> result, + return: Fold2, +) -> result { + do_foldl2(self, with, return)(zero_a, zero_b) +} + +fn do_foldl2( + self: List, + with: fn(elem, a, b, Fold2) -> result, + return: Fold2, +) -> Fold2 { + when self is { + [] -> return + [x, ..xs] -> do_foldl2(xs, with, fn(a, b) { with(x, a, b, return) }) + } +} + +test foldl2_optimized() { + let + len, + sum, + <- + foldl2( + [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], + 0, + 0, + fn(n, len, sum, return) { return(len + 1, sum + n) }, + ) + + and { + len == 10, + sum == 55, + } +} + +test foldl2_classic() { + let (len, sum) = + foldl( + [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], + (0, 0), + fn(n, (len, sum)) { (len + 1, sum + n) }, + ) + + and { + len == 10, + sum == 55, + } +} + +type Foo { + Foo(Int, Int) +} + +test foldl2_pair() { + let Pair(len, sum) = + foldl( + [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], + Pair(0, 0), + fn(n, Pair(len, sum)) { Pair(len + 1, sum + n) }, + ) + + and { + len == 10, + sum == 55, + } +} + +test foldl2_foo() { + let Foo(len, sum) = + foldl( + [1, 2, 3, 4, 5, 6, 7, 8, 9, 10], + Foo(0, 0), + fn(n, Foo(len, sum)) { Foo(len + 1, sum + n) }, + ) + + and { + len == 10, + sum == 55, + } +} + +test foldl_1() { + foldl([], 0, fn(_, _) { 1 }) == 0 +} + +test foldl_2() { + foldl([1, 2, 3, 4, 5], 0, fn(n, total) { n + total }) == 15 +} + +test foldl_3() { + foldl([1, 2, 3, 4], [], fn(x, xs) { [x, ..xs] }) == [4, 3, 2, 1] +} + +/// Reduce a list from right to left. +/// +/// ```aiken +/// list.foldr([1, 2, 3], 0, fn(n, total) { n + total }) == 6 +/// list.foldr([1, 2, 3], [], fn(x, xs) { [x, ..xs] }) == [1, 2, 3] +/// ``` +pub fn foldr(self: List, zero: b, with: fn(a, b) -> b) -> b { + when self is { + [] -> zero + [x, ..xs] -> with(x, foldr(xs, zero, with)) + } +} + +test foldr_1() { + foldr([1, 2, 3, 4, 5], 0, fn(n, total) { n + total }) == 15 +} + +test foldr_2() { + foldr( + [1, 2, 3], + "", + fn(n, _str) { + if builtin.mod_integer(n, 2) == 0 { + "foo" + } else { + "bar" + } + }, + ) == "bar" +} + +test foldr_3() { + foldr([1, 2, 3, 4], [], fn(x, xs) { [x, ..xs] }) == [1, 2, 3, 4] +} + +/// Like [`foldr`](#foldr), but also provides the position (0-based) of the elements when iterating. +/// +/// ```aiken +/// let group = fn(i, x, xs) { [(i, x), ..xs] } +/// list.indexed_foldr(["a", "b", "c"], [], group) == [ +/// (0, "a"), +/// (1, "b"), +/// (2, "c") +/// ] +/// ``` +pub fn indexed_foldr( + self: List, + zero: result, + with: fn(Int, a, result) -> result, +) -> result { + do_indexed_foldr(0, self, zero, with) +} + +fn do_indexed_foldr( + n: Int, + self: List, + zero: result, + with: fn(Int, a, result) -> result, +) -> result { + when self is { + [] -> zero + [x, ..xs] -> with(n, x, do_indexed_foldr(n + 1, xs, zero, with)) + } +} + +test indexed_foldr_1() { + indexed_foldr([], 0, fn(i, x, xs) { i + x + xs }) == 0 +} + +test indexed_foldr_2() { + let letters = ["a", "b", "c"] + indexed_foldr(letters, [], fn(i, x, xs) { [(i, x), ..xs] }) == [ + (0, "a"), (1, "b"), (2, "c"), + ] +} + +/// Reduce a list from left to right using the accumulator as left operand. +/// Said differently, this is [`foldl`](#foldl) with callback arguments swapped. +/// +/// ```aiken +/// list.reduce([#[1], #[2], #[3]], #[0], bytearray.concat) == #[0, 1, 2, 3] +/// list.reduce([True, False, True], False, fn(b, a) { or { b, a } }) == True +/// ``` +pub fn reduce(self: List, zero: b, with: fn(b, a) -> b) -> b { + foldl(self, zero, flip(with)) +} + +test reduce_1() { + reduce([], 0, fn(n, total) { n + total }) == 0 +} + +test reduce_2() { + reduce([1, 2, 3], 0, fn(n, total) { n + total }) == 6 +} + +test reduce_3() { + reduce([True, False, True], False, fn(left, right) { left || right }) == True +} + +test reduce_4() { + reduce( + [#[1], #[2], #[3]], + #[9], + fn(left, right) { bytearray.concat(left, right) }, + ) == #[9, 1, 2, 3] +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection/pairs.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection/pairs.ak new file mode 100644 index 00000000..01bfe763 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/collection/pairs.ak @@ -0,0 +1,833 @@ +//// A module for working with associative lists (a.k.a `Pairs`). +//// +//// While any function that works on `List` also work on `Pairs`, this module provides some extra helpers +//// that are specifically tailored to working with associative lists. Fundamentally, a `Pairs` is +//// a type-alias to `List>`. +//// +//// > [!CAUTION] +//// > +//// > Unlike dictionnaries (a.k.a. [`Dict`](./dict.html#Dict), associative lists make no assumption +//// > about the ordering of elements within the list. As a result, lookup +//// > functions do traverse the entire list when invoked. They are also not _sets_, +//// > and thus allow for duplicate keys. This is reflected in the functions used +//// > to interact with them. + +use aiken/builtin +use aiken/primitive/bytearray + +// ## Inspecting + +/// Get all values in the alist associated with a given key. +/// +/// ```aiken +/// pairs.get_all([], "a") == [] +/// pairs.get_all([Pair("a", 1)], "a") == [1] +/// pairs.get_all([Pair("a", 1), Pair("b", 2)], "a") == [1] +/// pairs.get_all([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [1, 3] +/// ``` +pub fn get_all(self: Pairs, key k: key) -> List { + when self is { + [] -> [] + [Pair(k2, v), ..rest] -> + if k == k2 { + [v, ..get_all(rest, k)] + } else { + get_all(rest, k) + } + } +} + +test get_all_1() { + get_all([], "a") == [] +} + +test get_all_2() { + get_all([Pair("a", 1)], "a") == [1] +} + +test get_all_3() { + get_all([Pair("a", 1), Pair("b", 2)], "a") == [1] +} + +test get_all_4() { + get_all([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [1, 3] +} + +test get_all_5() { + get_all([Pair("a", 1), Pair("b", 2), Pair("c", 3)], "d") == [] +} + +/// Get the value in the alist by its key. +/// If multiple values with the same key exist, only the first one is returned. +/// +/// ```aiken +/// pairs.get_first([], "a") == None +/// pairs.get_first([Pair("a", 1)], "a") == Some(1) +/// pairs.get_first([Pair("a", 1), Pair("b", 2)], "a") == Some(1) +/// pairs.get_first([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == Some(1) +/// ``` +pub fn get_first(self: Pairs, key k: key) -> Option { + when self is { + [] -> None + [Pair(k2, v), ..rest] -> + if k == k2 { + Some(v) + } else { + get_first(rest, k) + } + } +} + +test get_first_1() { + get_first([], "a") == None +} + +test get_first_2() { + get_first([Pair("a", 1)], "a") == Some(1) +} + +test get_first_3() { + get_first([Pair("a", 1), Pair("b", 2)], "a") == Some(1) +} + +test get_first_4() { + get_first([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == Some(1) +} + +test get_first_5() { + get_first([Pair("a", 1), Pair("b", 2), Pair("c", 3)], "d") == None +} + +/// Get the value in the alist by its key. +/// If multiple values with the same key exist, only the last one is returned. +/// +/// ```aiken +/// pairs.get_last([], "a") == None +/// pairs.get_last([Pair("a", 1)], "a") == Some(1) +/// pairs.get_last([Pair("a", 1), Pair("b", 2)], "a") == Some(1) +/// pairs.get_last([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == Some(3) +/// ``` +pub fn get_last(self: Pairs, key k: key) -> Option { + when self is { + [] -> None + [Pair(k2, v), ..rest] -> + if k == k2 { + when get_last(rest, k) is { + None -> Some(v) + some -> some + } + } else { + get_last(rest, k) + } + } +} + +test get_last_1() { + get_last([], "a") == None +} + +test get_last_2() { + get_last([Pair("a", 1)], "a") == Some(1) +} + +test get_last_3() { + get_last([Pair("a", 1), Pair("b", 2)], "a") == Some(1) +} + +test get_last_4() { + get_last([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == Some(3) +} + +test get_last_5() { + get_last([Pair("a", 1), Pair("b", 2), Pair("c", 3)], "d") == None +} + +/// Finds all keys in the alist associated with a given value. +/// +/// ```aiken +/// pairs.find_all([], 1) == [] +/// pairs.find_all([Pair("a", 1)], 1) == ["a"] +/// pairs.find_all([Pair("a", 1), Pair("b", 2)], 1) == ["a"] +/// pairs.find_all([Pair("a", 1), Pair("b", 2), Pair("c", 1)], 1) == ["a", "c"] +/// ``` +pub fn find_all(self: Pairs, v: value) -> List { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if v == v2 { + [k2, ..find_all(rest, v)] + } else { + find_all(rest, v) + } + } +} + +test find_all_1() { + find_all([], "a") == [] +} + +test find_all_2() { + find_all([Pair("a", 14)], 14) == ["a"] +} + +test find_all_3() { + find_all([Pair("a", 14)], 42) == [] +} + +test find_all_4() { + find_all([Pair("a", 14), Pair("b", 42), Pair("c", 14)], 14) == ["a", "c"] +} + +/// Finds the first key in the alist associated with a given value, if any. +/// +/// ```aiken +/// pairs.find_first([], 1) == None +/// pairs.find_first([Pair("a", 1)], 1) == Some("a") +/// pairs.find_first([Pair("a", 1), Pair("b", 2)], 1) == Some("a") +/// pairs.find_first([Pair("a", 1), Pair("b", 2), Pair("c", 1)], 1) == Some("a") +/// ``` +pub fn find_first(self: Pairs, v: value) -> Option { + when self is { + [] -> None + [Pair(k2, v2), ..rest] -> + if v == v2 { + Some(k2) + } else { + find_first(rest, v) + } + } +} + +test find_first_1() { + find_first([], "a") == None +} + +test find_first_2() { + find_first([Pair("a", 14)], 14) == Some("a") +} + +test find_first_3() { + find_first([Pair("a", 14)], 42) == None +} + +test find_first_4() { + find_first([Pair("a", 14), Pair("b", 42), Pair("c", 14)], 14) == Some("a") +} + +/// Finds the last key in the alist associated with a given value, if any. +/// +/// ```aiken +/// pairs.find_last([], 1) == None +/// pairs.find_last([Pair("a", 1)], 1) == Some("a") +/// pairs.find_last([Pair("a", 1), Pair("b", 2)], 1) == Some("a") +/// pairs.find_last([Pair("a", 1), Pair("b", 2), Pair("c", 1)], 1) == Some("c") +/// ``` +pub fn find_last(self: Pairs, v: value) -> Option { + when self is { + [] -> None + [Pair(k2, v2), ..rest] -> + if v == v2 { + when find_last(rest, v) is { + None -> Some(k2) + some -> some + } + } else { + find_last(rest, v) + } + } +} + +test find_last_1() { + find_last([], "a") == None +} + +test find_last_2() { + find_last([Pair("a", 14)], 14) == Some("a") +} + +test find_last_3() { + find_last([Pair("a", 14)], 42) == None +} + +test find_last_4() { + find_last([Pair("a", 14), Pair("b", 42), Pair("c", 14)], 14) == Some("c") +} + +/// Check if a key exists in the pairs. +/// +/// ```aiken +/// pairs.has_key([], "a") == False +/// pairs.has_key([Pair("a", 1)], "a") == True +/// pairs.has_key([Pair("a", 1), Pair("b", 2)], "a") == True +/// pairs.has_key([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == True +/// ``` +pub fn has_key(self: Pairs, k: key) -> Bool { + when self is { + [] -> False + // || is lazy so this is fine + [Pair(k2, _), ..rest] -> k == k2 || has_key(rest, k) + } +} + +test has_key_1() { + !has_key([], "a") +} + +test has_key_2() { + has_key([Pair("a", 14)], "a") +} + +test has_key_3() { + !has_key([Pair("a", 14)], "b") +} + +test has_key_4() { + has_key([Pair("a", 14), Pair("b", 42)], "b") +} + +test has_key_5() { + has_key([Pair("a", 14), Pair("b", 42), Pair("a", 42)], "a") +} + +/// Extract all the keys present in a given `Pairs`. +/// +/// ```aiken +/// pairs.keys([]) == [] +/// pairs.keys([Pair("a", 1)]) == ["a"] +/// pairs.keys([Pair("a", 1), Pair("b", 2)]) == ["a", "b"] +/// pairs.keys([Pair("a", 1), Pair("b", 2), Pair("a", 3)]) == ["a", "b", "a"] +/// ``` +pub fn keys(self: Pairs) -> List { + when self is { + [] -> [] + [Pair(k, _), ..rest] -> [k, ..keys(rest)] + } +} + +test keys_1() { + keys([]) == [] +} + +test keys_2() { + keys([Pair("a", 0)]) == ["a"] +} + +test keys_3() { + keys([Pair("a", 0), Pair("b", 0)]) == ["a", "b"] +} + +/// Extract all the values present in a given `Pairs`. +/// +/// ```aiken +/// pairs.values([]) == [] +/// pairs.values([Pair("a", 1)]) == [1] +/// pairs.values([Pair("a", 1), Pair("b", 2)]) == [1, 2] +/// pairs.values([Pair("a", 1), Pair("b", 2), Pair("a", 3)]) == [1, 2, 3] +/// ``` +pub fn values(self: Pairs) -> List { + when self is { + [] -> [] + [Pair(_, v), ..rest] -> [v, ..values(rest)] + } +} + +test values_1() { + values([]) == [] +} + +test values_2() { + values([Pair("a", 1)]) == [1] +} + +test values_3() { + values([Pair("a", 1), Pair("b", 2)]) == [1, 2] +} + +test values_4() { + values([Pair("a", 1), Pair("b", 2), Pair("a", 3)]) == [1, 2, 3] +} + +// ## Modifying + +/// Remove all key-value pairs matching the key from the Pairs. If the key is not found, no changes are made. +/// +/// ```aiken +/// pairs.delete_all([], "a") == [] +/// pairs.delete_all([Pair("a", 1)], "a") == [] +/// pairs.delete_all([Pair("a", 1), Pair("b", 2)], "a") == [Pair("b", 2)] +/// pairs.delete_all([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [Pair("b", 2)] +/// ``` +pub fn delete_all(self: Pairs, key k: key) -> Pairs { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if k == k2 { + delete_all(rest, k) + } else { + [Pair(k2, v2), ..delete_all(rest, k)] + } + } +} + +test delete_all_1() { + delete_all([], "a") == [] +} + +test delete_all_2() { + delete_all([Pair("a", 14)], "a") == [] +} + +test delete_all_3() { + let fixture = [Pair("a", 14)] + delete_all(fixture, "b") == fixture +} + +test delete_all_4() { + let fixture = [Pair("a", 1), Pair("b", 2), Pair("a", 3)] + delete_all(fixture, "a") == [Pair("b", 2)] +} + +/// Remove a single key-value pair from the `Pairs`. If the key is not found, no changes are made. +/// Duplicate keys are not deleted. Only the **first** key found is deleted. +/// +/// ```aiken +/// pairs.delete_first([], "a") == [] +/// pairs.delete_first([Pair("a", 1)], "a") == [] +/// pairs.delete_first([Pair("a", 1), Pair("b", 2)], "a") == [Pair("b", 2)] +/// pairs.delete_first([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [Pair("b", 2), Pair("a", 3)] +/// ``` +pub fn delete_first(self: Pairs, key k: key) -> Pairs { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if k == k2 { + rest + } else { + [Pair(k2, v2), ..delete_first(rest, k)] + } + } +} + +test delete_first_1() { + delete_first([], "a") == [] +} + +test delete_first_2() { + delete_first([Pair("a", 14)], "a") == [] +} + +test delete_first_3() { + let fixture = [Pair("a", 14)] + delete_first(fixture, "b") == fixture +} + +test delete_first_4() { + let fixture = [Pair("a", 1), Pair("b", 2), Pair("a", 3)] + delete_first(fixture, "a") == [Pair("b", 2), Pair("a", 3)] +} + +/// Remove a single key-value pair from the Pairs. If the key is not found, no changes are made. +/// Duplicate keys are not deleted. Only the **last** key found is deleted. +/// +/// ```aiken +/// pairs.delete_last([], "a") == [] +/// pairs.delete_last([Pair("a", 1)], "a") == [] +/// pairs.delete_last([Pair("a", 1), Pair("b", 2)], "a") == [Pair("b", 2)] +/// pairs.delete_last([Pair("a", 1), Pair("b", 2), Pair("a", 3)], "a") == [Pair("a", 1), Pair("b", 2)] +/// ``` +pub fn delete_last(self: Pairs, key k: key) -> Pairs { + when self is { + [] -> [] + [Pair(k2, v2), ..rest] -> + if k == k2 { + let tail = delete_last(rest, k) + if tail == rest { + rest + } else { + [Pair(k2, v2), ..tail] + } + } else { + [Pair(k2, v2), ..delete_last(rest, k)] + } + } +} + +test delete_last_1() { + delete_last([], "a") == [] +} + +test delete_last_2() { + delete_last([Pair("a", 14)], "a") == [] +} + +test delete_last_3() { + let fixture = [Pair("a", 14)] + delete_last(fixture, "b") == fixture +} + +test delete_last_4() { + let fixture = [Pair("a", 1), Pair("b", 2), Pair("a", 3)] + delete_last(fixture, "a") == [Pair("a", 1), Pair("b", 2)] +} + +/// Insert a value in the `Pairs` at a given key. If the key already exists, +/// the value is added in front. +/// +/// > [!CAUTION] +/// > The list is only traversed up to the given key and the traversal +/// > stops as soon as a higher key is encountered. Said differently, the list +/// > is assumed to **be ordered by ascending keys**! If it is not, expect the +/// > unexpected. +/// +/// ```aiken +/// use aiken/primitive/bytearray +/// +/// let result = +/// [] +/// |> pairs.insert_by_ascending_key(key: "foo", value: 1, compare: bytearray.compare) +/// |> pairs.insert_by_ascending_key(key: "bar", value: 2, compare: bytearray.compare) +/// |> pairs.insert_by_ascending_key(key: "foo", value: 3, compare: bytearray.compare) +/// +/// result == [Pair("bar", 2), Pair("foo", 3), Pair("foo", 1)] +/// ``` +pub fn insert_by_ascending_key( + self: Pairs, + key k: key, + value v: value, + compare: fn(key, key) -> Ordering, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if compare(k, k2) == Less { + [Pair(k, v), ..self] + } else { + if k == k2 { + [Pair(k, v), ..self] + } else { + [Pair(k2, v2), ..insert_by_ascending_key(rest, k, v, compare)] + } + } + } +} + +test insert_by_ascending_key_1() { + let m = + [] + |> insert_by_ascending_key("foo", 42, bytearray.compare) + |> insert_by_ascending_key("foo", 14, bytearray.compare) + + m == [Pair("foo", 14), Pair("foo", 42)] +} + +test insert_by_ascending_key_2() { + let m = + [] + |> insert_by_ascending_key("foo", 42, bytearray.compare) + |> insert_by_ascending_key("bar", 14, bytearray.compare) + |> insert_by_ascending_key("baz", 1337, bytearray.compare) + + m == [Pair("bar", 14), Pair("baz", 1337), Pair("foo", 42)] +} + +/// Like [`insert_by_ascending_key`](#insert_by_ascending_key) but specifies +/// how to combine two values on a key conflict. +/// +/// > [!CAUTION] +/// > The list is only traversed up to the given key and the traversal +/// > stops as soon as a higher key is encountered. Said differently, the list +/// > is assumed to **be ordered by ascending keys**! If it is not, expect the +/// > unexpected. +/// +/// ```aiken +/// use aiken/primitive/bytearray +/// +/// let add_integer = fn(x, y) { x + y } +/// +/// let result = +/// [] +/// |> pairs.insert_with_by_ascending_key(key: "foo", value: 1, compare: bytearray.compare, with: add_integer) +/// |> pairs.insert_with_by_ascending_key(key: "bar", value: 2, compare: bytearray.compare, with: add_integer) +/// |> pairs.insert_with_by_ascending_key(key: "foo", value: 3, compare: bytearray.compare, with: add_integer) +/// +/// result == [Pair("bar", 2), Pair("foo", 4)] +/// ``` +pub fn insert_with_by_ascending_key( + self: Pairs, + key k: key, + value v: value, + compare: fn(key, key) -> Ordering, + with: fn(value, value) -> value, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if compare(k, k2) == Less { + [Pair(k, v), ..self] + } else { + if k == k2 { + [Pair(k, with(v, v2)), ..rest] + } else { + [ + Pair(k2, v2), + ..insert_with_by_ascending_key(rest, k, v, compare, with) + ] + } + } + } +} + +test insert_with_by_ascending_key_1() { + let compare_un_b_data = + fn(l, r) { + bytearray.compare(l |> builtin.un_b_data, r |> builtin.un_b_data) + } + + let m = + [] + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 42, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 14, + compare_un_b_data, + builtin.add_integer, + ) + + m == [Pair("foo" |> builtin.b_data, 56)] +} + +test insert_with_by_ascending_key_2() { + let compare_un_b_data = + fn(l, r) { + bytearray.compare(l |> builtin.un_b_data, r |> builtin.un_b_data) + } + + let m = + [] + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 42, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "bar" |> builtin.b_data, + 14, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "baz" |> builtin.b_data, + 1337, + compare_un_b_data, + builtin.add_integer, + ) + + m == [ + Pair("bar" |> builtin.b_data, 14), + Pair("baz" |> builtin.b_data, 1337), + Pair("foo" |> builtin.b_data, 42), + ] +} + +test insert_with_by_ascending_key_3() { + let compare_un_b_data = + fn(l, r) { + bytearray.compare(l |> builtin.un_b_data, r |> builtin.un_b_data) + } + + let result = + [] + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 1, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "bar" |> builtin.b_data, + 2, + compare_un_b_data, + builtin.add_integer, + ) + |> insert_with_by_ascending_key( + "foo" |> builtin.b_data, + 3, + compare_un_b_data, + builtin.add_integer, + ) + + result == [Pair("bar" |> builtin.b_data, 2), Pair("foo" |> builtin.b_data, 4)] +} + +/// Apply a function to all key-value pairs in a alist, replacing the values. +/// +/// ```aiken +/// let fixture = [Pair("a", 100), Pair("b", 200)] +/// +/// pairs.map(fixture, fn(_k, v) { v * 2 }) == [Pair("a", 200), Pair("b", 400)] +/// ``` +pub fn map( + self: Pairs, + with: fn(key, value) -> result, +) -> Pairs { + when self is { + [] -> [] + [Pair(k, v), ..rest] -> [Pair(k, with(k, v)), ..map(rest, with)] + } +} + +test map_1() { + let fixture = [Pair("a", 1), Pair("b", 2)] + + map(fixture, with: fn(k, _) { k }) == [Pair("a", "a"), Pair("b", "b")] +} + +test map_2() { + let fixture = [Pair("a", 1), Pair("b", 2)] + + map(fixture, with: fn(_, v) { v + 1 }) == [Pair("a", 2), Pair("b", 3)] +} + +/// Insert a value in the `Pairs` at a given key. If the key already exists, +/// its value is replaced. +/// +/// > [!CAUTION] +/// > The list is only traversed up to the given key and the traversal +/// > stops as soon as a higher key is encountered. Said differently, the list +/// > is assumed to **be ordered by ascending keys**! If it is not, expect the +/// > unexpected. +/// +/// ```aiken +/// use aiken/primitive/bytearray +/// +/// let result = +/// [] +/// |> pairs.repsert_by_ascending_key(key: "foo", value: 1, compare: bytearray.compare) +/// |> pairs.repsert_by_ascending_key(key: "bar", value: 2, compare: bytearray.compare) +/// |> pairs.repsert_by_ascending_key(key: "foo", value: 3, compare: bytearray.compare) +/// +/// result == [Pair("bar", 2), Pair("foo", 3)] +/// ``` +pub fn repsert_by_ascending_key( + self: Pairs, + key k: key, + value v: value, + compare: fn(key, key) -> Ordering, +) -> Pairs { + when self is { + [] -> [Pair(k, v)] + [Pair(k2, v2), ..rest] -> + if compare(k, k2) == Less { + [Pair(k, v), ..self] + } else { + if k == k2 { + [Pair(k, v), ..rest] + } else { + [Pair(k2, v2), ..repsert_by_ascending_key(rest, k, v, compare)] + } + } + } +} + +test repsert_by_ascending_key_1() { + let m = + [] + |> repsert_by_ascending_key("foo", 42, bytearray.compare) + |> repsert_by_ascending_key("foo", 14, bytearray.compare) + + m == [Pair("foo", 14)] +} + +test repsert_by_ascending_key_2() { + let m = + [] + |> repsert_by_ascending_key("foo", 42, bytearray.compare) + |> repsert_by_ascending_key("bar", 14, bytearray.compare) + |> repsert_by_ascending_key("baz", 1337, bytearray.compare) + + m == [Pair("bar", 14), Pair("baz", 1337), Pair("foo", 42)] +} + +// ## Transforming + +/// Fold over the key-value pairs in a pairs. The fold direction follows keys +/// in ascending order and is done from left-to-right. +/// +/// ```aiken +/// let fixture = [ +/// Pair(1, 100), +/// Pair(2, 200), +/// Pair(3, 300), +/// ] +/// +/// pairs.foldl(fixture, 0, fn(k, v, result) { k * v + result }) == 1400 +/// ``` +pub fn foldl( + self: Pairs, + zero: result, + with: fn(key, value, result) -> result, +) -> result { + when self is { + [] -> zero + [Pair(k, v), ..rest] -> foldl(rest, with(k, v, zero), with) + } +} + +test foldl_1() { + foldl([], 14, fn(_, _, _) { 42 }) == 14 +} + +test foldl_2() { + foldl( + [Pair("a", 42), Pair("b", 14)], + zero: 0, + with: fn(_, v, total) { v + total }, + ) == 56 +} + +/// Fold over the key-value pairs in a Pairs. The fold direction follows the +/// order of elements in the Pairs and is done from right-to-left. +/// +/// ```aiken +/// let fixture = [ +/// Pair(1, 100), +/// Pair(2, 200), +/// Pair(3, 300), +/// ] +/// +/// pairs.foldr(fixture, 0, fn(k, v, result) { k * v + result }) == 1400 +/// ``` +pub fn foldr( + self: Pairs, + zero: result, + with: fn(key, value, result) -> result, +) -> result { + when self is { + [] -> zero + [Pair(k, v), ..rest] -> with(k, v, foldr(rest, zero, with)) + } +} + +test foldr_1() { + foldr([], 14, fn(_, _, _) { 42 }) == 14 +} + +test foldr_2() { + foldr( + [Pair("a", 42), Pair("b", 14)], + zero: 0, + with: fn(_, v, total) { v + total }, + ) == 56 +} + +test foldr_3() { + let fixture = [Pair(1, 100), Pair(2, 200), Pair(3, 300)] + + foldr(fixture, 0, fn(k, v, result) { k * v + result }) == 1400 +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto.ak new file mode 100644 index 00000000..46a7dda5 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto.ak @@ -0,0 +1,147 @@ +use aiken/builtin + +pub type VerificationKey = + ByteArray + +pub type VerificationKeyHash = + Hash + +pub type Script = + ByteArray + +pub type ScriptHash = + Hash + +pub type Signature = + ByteArray + +pub type DataHash = + Hash + +/// A `Hash` is nothing more than a `ByteArray`, but it carries extra +/// information for readability. +/// +/// On-chain, any hash digest value is represented as a plain 'ByteArray'. +/// Though in practice, hashes come from different sources and have +/// different semantics. +/// +/// Hence, while this type-alias doesn't provide any strong type-guarantees, +/// it helps writing functions signatures with more meaningful types than mere +/// 'ByteArray'. +/// +/// Compare for example: +/// +/// ```aiken +/// pub type Credential { +/// VerificationKey(ByteArray) +/// Script(ByteArray) +/// } +/// ``` +/// +/// with +/// +/// ```aiken +/// pub type Credential { +/// VerificationKey(Hash) +/// Script(Hash) +/// } +/// ``` +/// +/// Both are strictly equivalent, but the second reads much better. +pub type Hash = + ByteArray + +// ## Hashing + +/// A blake2b-224 hash algorithm. +/// +/// Typically used for: +/// +/// - [`Credential`](../cardano/address.html#Credential) +/// - [`PolicyId`](../cardano/assets.html#PolicyId) +/// +/// Note: there's no function to calculate blake2b-224 hash digests on-chain. +pub opaque type Blake2b_224 { + Blake2b_224 +} + +/// Compute the blake2b-224 hash digest (28 bytes) of some data. +pub fn blake2b_224(bytes: ByteArray) -> Hash { + builtin.blake2b_224(bytes) +} + +/// A blake2b-256 hash algorithm. +/// +/// Typically used for: +/// +/// - [`TransactionId`](../cardano/transaction.html#TransactionId) +pub opaque type Blake2b_256 { + Blake2b_256 +} + +/// Compute the blake2b-256 hash digest (32 bytes) of some data. +pub fn blake2b_256(bytes: ByteArray) -> Hash { + builtin.blake2b_256(bytes) +} + +/// A Keccak-256 hash algorithm. +pub opaque type Keccak_256 { + Keccak_256 +} + +/// Compute the keccak-256 hash digest (32 bytes) of some data. +pub fn keccak_256(bytes: ByteArray) -> Hash { + builtin.keccak_256(bytes) +} + +/// A SHA2-256 hash algorithm. +pub opaque type Sha2_256 { + Sha2_256 +} + +/// Compute the sha2-256 hash digest (32 bytes) of some data. +pub fn sha2_256(bytes: ByteArray) -> Hash { + builtin.sha2_256(bytes) +} + +/// A SHA3-256 hash algorithm. +pub opaque type Sha3_256 { + Sha3_256 +} + +/// Compute the sha3-256 hash digest (32 bytes) of some data. +pub fn sha3_256(bytes: ByteArray) -> Hash { + builtin.sha3_256(bytes) +} + +// ## Verifying signatures + +/// Verify an ECDCA signature (over secp256k1) using the given verification key. +/// Returns `True` when the signature is valid. +pub fn verify_ecdsa_signature( + key: VerificationKey, + msg: ByteArray, + sig: Signature, +) -> Bool { + builtin.verify_ecdsa_secp256k1_signature(key, msg, sig) +} + +/// Verify an Ed25519 signature using the given verification key. +/// Returns `True` when the signature is valid. +pub fn verify_ed25519_signature( + key: VerificationKey, + msg: ByteArray, + sig: Signature, +) -> Bool { + builtin.verify_ed25519_signature(key, msg, sig) +} + +/// Verify a Schnorr signature (over secp256k1) using the given verification key. +/// Returns `True` when the signature is valid. +pub fn verify_schnorr_signature( + key: VerificationKey, + msg: ByteArray, + sig: Signature, +) -> Bool { + builtin.verify_schnorr_secp256k1_signature(key, msg, sig) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g1.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g1.ak new file mode 100644 index 00000000..d7b4cc19 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g1.ak @@ -0,0 +1,115 @@ +//// This module is designed for cryptographic operations involving the BLS12-381 elliptic curve, particularly focusing on the G1 group of the curve. +//// +//// The key functionalities provided by this module include: +//// - Defining the generator of the G1 group, which is a fixed base point on the elliptic curve used for various cryptographic computations. +//// - Implementing the additive identity (zero) in the G1 group, which plays a crucial role in elliptic curve arithmetic. +//// - Providing functions to compress and decompress points in the G1 group. Compression reduces the size of the point representation, which is useful for efficient storage and transmission. Decompression restores the original point from its compressed form. +//// - Implementing basic arithmetic operations on the points in the G1 group, such as addition and subtraction. +//// - Enabling the exponentiation of a point in the G1 group with a scalar, which is a fundamental operation in elliptic curve cryptography. +//// - Offering a function to hash arbitrary data to a point in the G1 group, a process important in several cryptographic protocols. +//// +//// This module ensures that all operations respect the properties of the BLS12-381 curve and the mathematical structure of the G1 group. + +use aiken/builtin +use aiken/crypto/bls12_381/scalar.{Scalar} + +/// The compressed generator of the G1 group of the BLS12-381 curve. +/// This constant represents a fixed base point on the elliptic curve. +/// Note that flat encoded plutus does not allow for the direct usage of BLS12-381 points. +/// More explicit, any points in plutus data or scripts must be decompressed before usage onchain. +pub const generator: G1Element = + #"97f1d3a73197d7942695638c4fa9ac0fc3688c4f9774b905a14e3a3f171bac586c55e83ff97a1aeffb3af00adb22c6bb" + +test generator_1() { + builtin.bls12_381_g1_scalar_mul(scalar.field_prime, generator) == #"c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" +} + +/// Represents the additive identity (zero) in the G1 group. +/// Note that flat encoded plutus does not allow for the direct usage of BLS12-381 points. +/// More explicit, any points in plutus data or scripts must be decompressed before usage onchain. +pub const zero: G1Element = + #"c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" + +test zero_1() { + and { + zero == builtin.bls12_381_g1_scalar_mul(scalar.field_prime, generator), + zero == builtin.bls12_381_g1_scalar_mul( + scalar.field_prime, + #"88c7e388ee58f1db9a24d7098b01d13634298bebf2d159254975bd450cb0d287fcc622eb71edde8b469a8513551baf1f", + ), + zero == builtin.bls12_381_g1_scalar_mul( + scalar.field_prime, + #"a6ac32e625dc30b8d31bacf5f4c89c27b0388b15f57ae10de8d5cec02dd1f113c9a31077be05ab587ca57a88d34deb75", + ), + } +} + +/// Compresses a point in the G1 group into a more compact representation. +/// The compressed representation is a 48-byte string, corresponding to a modified `x` coordinate. +/// The leading most significant 3 bits of this string indicate how to reconstruct the `y` coordinate. +/// +/// > [!NOTE] +/// > More explicitly via [Zcash's spec](https://github.com/supranational/blst#serialization-format): +/// > +/// > The most-significant three bits of a G1 or G2 encoding should be masked away before the coordinate(s) are interpreted. These bits are used to unambiguously represent the underlying element: +/// > +/// > - The most significant bit, when set, indicates that the point is in compressed form. Otherwise, the point is in uncompressed form. +/// > - The second-most significant bit indicates that the point is at infinity. If this bit is set, the remaining bits of the group element's encoding should be set to zero. +/// > - The third-most significant bit is set if (and only if) this point is in compressed form and it is not the point at infinity and its y-coordinate is the lexicographically largest of the two associated with the encoded x-coordinate. +pub fn compress(point) { + builtin.bls12_381_g1_compress(point) +} + +test compress_1() { + compress( + #"97f1d3a73197d7942695638c4fa9ac0fc3688c4f9774b905a14e3a3f171bac586c55e83ff97a1aeffb3af00adb22c6bb", + ) == #"97f1d3a73197d7942695638c4fa9ac0fc3688c4f9774b905a14e3a3f171bac586c55e83ff97a1aeffb3af00adb22c6bb" +} + +/// Decompresses a point in the G1 group from its compressed form. +pub fn decompress(bytes) { + builtin.bls12_381_g1_uncompress(bytes) +} + +pub fn equal(left, right) { + builtin.bls12_381_g1_equal(left, right) +} + +test equal_1() { + equal(generator, generator) +} + +/// Adds two points in the G1 group. +pub fn add(left, right) { + builtin.bls12_381_g1_add(left, right) +} + +/// Subtracts one point in the G1 group from another. +pub fn sub(left, right) { + builtin.bls12_381_g1_add(left, builtin.bls12_381_g1_neg(right)) +} + +test sub_1() { + generator == sub(add(generator, generator), generator) +} + +/// Exponentiates a point in the G1 group with a `scalar`. +/// This operation is equivalent to the repeated addition of the point with itself `e` times. +pub fn scale(point, e: Scalar) { + builtin.bls12_381_g1_scalar_mul(scalar.to_int(e), point) +} + +test scale_1() { + expect Some(x) = scalar.new(2) + builtin.bls12_381_g1_add(generator, generator) == scale(generator, x) +} + +/// Hashes arbitrary data to a point in the G1 group. +/// You can use the `domain_separation_tag` parameter to cryptographically separate different uses of the hash function between applications. +pub fn hash_to_group(bytes: ByteArray, domain_separation_tag: ByteArray) { + builtin.bls12_381_g1_hash_to_group(bytes, domain_separation_tag) +} + +test hash_to_group_1() { + hash_to_group("hello", "world") == #"89223b03c629cc6bcbbdccbba46b6679bc6a79db82f2d3bd115899a45a5a38c391587b59d3d1e297f977d1c4ee9e3388" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g2.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g2.ak new file mode 100644 index 00000000..7a2013db --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/g2.ak @@ -0,0 +1,124 @@ +//// This module is designed for cryptographic operations involving the BLS12-381 elliptic curve, particularly focusing on the G2 group of the curve. +//// +//// The key functionalities provided by this module include: +//// - Defining the generator of the G2 group, which is a fixed base point on the elliptic curve used for various cryptographic computations. +//// - Implementing the additive identity (zero) in the G2 group, which plays a crucial role in elliptic curve arithmetic. +//// - Providing functions to compress and decompress points in the G2 group. Compression reduces the size of the point representation, which is useful for efficient storage and transmission. Decompression restores the original point from its compressed form. +//// - Implementing basic arithmetic operations on the points in the G2 group, such as addition and subtraction. +//// - Enabling the exponentiation of a point in the G2 group with a scalar, which is a fundamental operation in elliptic curve cryptography. +//// - Offering a function to hash arbitrary data to a point in the G2 group, a process important in several cryptographic protocols. +//// +//// This module ensures that all operations respect the properties of the BLS12-381 curve and the mathematical structure of the G2 group. + +use aiken/builtin +use aiken/crypto/bls12_381/scalar.{Scalar} + +/// The compressed generator of the G2 group of the BLS12-381 curve. +/// This constant represents a fixed base point on the elliptic curve. +/// Note that flat encoded plutus does not allow for the direct usage of BLS12-381 points. +/// More explicit, any points in plutus data or scripts must be decompressed before usage onchain. +pub const generator: G2Element = + #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8" + +test generator_1() { + builtin.bls12_381_g2_scalar_mul(scalar.field_prime, generator) == #"c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" +} + +/// Represents the additive identity (zero) in the G2 group. +/// Note that flat encoded plutus does not allow for the direct usage of BLS12-381 points. +/// More explicit, any points in plutus data or scripts must be decompressed before usage onchain. +pub const zero: G2Element = + #"c00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000" + +test zero_1() { + and { + zero == builtin.bls12_381_g2_scalar_mul(scalar.field_prime, generator), + zero == builtin.bls12_381_g2_scalar_mul( + scalar.field_prime, + #"9964a9ac2ee28a4dab595ff0970d446373bf46701c5d0b29ce8e1ba995d811a1c7b193c928269192c64ba1fbe4b1940207c251e086b452b920bc72e3cebab46ce672b9b088ca620a471d3b888d9737f6abd165319aa457dbf8835e3d34196051", + ), + zero == builtin.bls12_381_g2_scalar_mul( + scalar.field_prime, + #"a900e25cb53cf1eeb1a82c0c83292937c49c97966351273767a204256a7ef6e95aa391404387075d361e7b13ccd694db03aa73ee0e1bd2c3dd735582b99fdf71696de72e4eda18ae99ea45995f1c9605aa0057008ee9a4da604b5716fb4a345b", + ), + } +} + +/// Compresses a point in the G2 group into a more compact representation. +/// The compressed representation is the concatenation of two 48-byte strings, corresponding to a modified and complexified `x` coordinate. +/// The leading most significant 3 bits of this string indicate how to reconstruct the `y` coordinate. +/// +/// > [!NOTE] +/// > More explicitly via [Zcash's spec](https://github.com/supranational/blst#serialization-format): +/// > +/// > The most-significant three bits of a G1 or G2 encoding should be masked away before the coordinate(s) are interpreted. These bits are used to unambiguously represent the underlying element: +/// > +/// > - The most significant bit, when set, indicates that the point is in compressed form. Otherwise, the point is in uncompressed form. +/// > - The second-most significant bit indicates that the point is at infinity. If this bit is set, the remaining bits of the group element's encoding should be set to zero. +/// > - The third-most significant bit is set if (and only if) this point is in compressed form and it is not the point at infinity and its y-coordinate is the lexicographically largest of the two associated with the encoded x-coordinate. +pub fn compress(point) { + builtin.bls12_381_g2_compress(point) +} + +test compress_1() { + let g2 = + #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8" + compress(g2) == #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8" +} + +/// Decompresses a point in the G2 group from its compressed form. +pub fn decompress(bytes) { + builtin.bls12_381_g2_uncompress(bytes) +} + +test decompress_1() { + let g2 = + #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8" + generator == g2 +} + +pub fn equal(left, right) { + builtin.bls12_381_g2_equal(left, right) +} + +test equal_1() { + equal( + generator, + #"93e02b6052719f607dacd3a088274f65596bd0d09920b61ab5da61bbdc7f5049334cf11213945d57e5ac7d055d042b7e024aa2b2f08f0a91260805272dc51051c6e47ad4fa403b02b4510b647ae3d1770bac0326a805bbefd48056c8c121bdb8", + ) +} + +/// Adds two points in the G2 group. +pub fn add(left, right) { + builtin.bls12_381_g2_add(left, right) +} + +/// Subtracts one point in the G2 group from another. +pub fn sub(left, right) { + builtin.bls12_381_g2_add(left, builtin.bls12_381_g2_neg(right)) +} + +test sub_1() { + generator == sub(add(generator, generator), generator) +} + +/// Exponentiates a point in the G2 group with a `scalar`. +/// This operation is equivalent to the repeated addition of the point with itself `e` times. +pub fn scale(point, e: Scalar) { + builtin.bls12_381_g2_scalar_mul(scalar.to_int(e), point) +} + +test scale_1() { + expect Some(x) = scalar.new(2) + builtin.bls12_381_g2_add(generator, generator) == scale(generator, x) +} + +/// Hashes arbitrary data to a point in the G2 group. +/// You can use the `domain_separation_tag` parameter to cryptographically separate different uses of the hash function between applications. +pub fn hash_to_group(bytes, domain_separation_tag) { + builtin.bls12_381_g2_hash_to_group(bytes, domain_separation_tag) +} + +test hash_to_group_1() { + hash_to_group("hello", "world") == #"a18486bba1dc8321f4998ed4268c6df8dfa5618dd5c91595844059d517f8104bf8031d3e766f9c99db1d6f58b201ee9614de92fc08f9e5cc3a6cd814e871857cb6e3924e8a4fa48775116c5f158d58ceda63614d62f6b7bc47db798d656969a5" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/scalar.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/scalar.ak new file mode 100644 index 00000000..cf028ad7 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/crypto/bls12_381/scalar.ak @@ -0,0 +1,255 @@ +//// This module implements arithmetic operations in the scalar field associated with the BLS12-381 elliptic curve. +//// The scalar field, defined over a prime number `q`, is derived from the order of the subgroup G1. +//// +//// More explicitly, we have the identity: +//// +//// ```aiken +//// builtin.bls12_381_g1_scalar_mul(q, bls12_381_g1_generator) == 1 +//// ``` +//// +//// where, +//// +//// ```aiken +//// q = 52435875175126190479447740508185965837690552500527637822603658699938581184513 +//// ``` +//// +//// This module provides functionality for basic arithmetic operations (addition, subtraction, multiplication, division) within this scalar field. +//// Additionally, it includes advanced operations such as exponentiation and calculation of multiplicative inverses, tailored for cryptographic applications. + +use aiken/builtin + +/// The prime number defining the scalar field of the BLS12-381 curve. +pub const field_prime = + 52435875175126190479447740508185965837690552500527637822603658699938581184513 + +/// Represents the additive identity (zero) in the `Scalar` field. +pub const zero: Scalar = Scalar(0) + +/// Represents the multiplicative identity (one) in the `Scalar` field. +pub const one: Scalar = Scalar(1) + +/// Opaque type representing an element of the finite field `Scalar`. +pub opaque type Scalar { + integer: Int, +} + +// ## Constructing + +/// Constructs a new `Scalar` element from an integer, ensuring it's within the valid range of the field. +/// Returns `None` if the integer is negative or greater than the prime number defining the field. +pub fn new(n: Int) -> Option { + if n >= 0 && n < field_prime { + Some(Scalar(n)) + } else { + None + } +} + +test new_1() { + and { + new(-1) == None, + new(field_prime) == None, + new(834884848) == Some(Scalar(834884848)), + } +} + +/// Constructs a new `Scalar` element from a Big-Endian (most-significant bits first) `ByteArray`. +pub fn from_bytearray_big_endian(bytes: ByteArray) -> Option { + new(builtin.bytearray_to_integer(True, bytes)) +} + +test from_bytearray_big_endian_1() { + from_bytearray_big_endian(#"ffff00") == Some(Scalar(16776960)) +} + +/// Constructs a new `Scalar` element from a Little-Endian (least-significant bits first) `ByteArray`. +pub fn from_bytearray_little_endian(bytes: ByteArray) -> Option { + new(builtin.bytearray_to_integer(False, bytes)) +} + +test from_bytearray_little_endian_1() { + from_bytearray_little_endian(#"ffff00") == Some(Scalar(65535)) +} + +// ## Modifying + +/// Exponentiates an `Scalar` element by a non-negative integer exponent, using repeated squaring. +/// Note that this function returns `scalar.zero` for negative exponents. +/// A dedicated builtin function for this is in the making, see CIP 109. +pub fn scale(self: Scalar, e: Int) -> Scalar { + if e < 0 { + zero + } else if e == 0 { + one + } else if e % 2 == 0 { + scale(mul(self, self), e / 2) + } else { + mul(self, scale(mul(self, self), ( e - 1 ) / 2)) + } +} + +test scale_1() { + and { + scale(Scalar(834884848), -1) == zero, + scale(Scalar(834884848), 0) == one, + scale(Scalar(834884848), 1) == Scalar(834884848), + scale(Scalar(834884848), 2) == Scalar(697032709419983104), + scale(Scalar(834884848), 3) == Scalar(581942047655130761945608192), + scale(Scalar(field_prime - 4), 200) == Scalar( + 12843927705572658539565969578937286576443167978938369866871449552629978143484, + ), + } +} + +/// A faster version of `scale` for the case where the exponent is a power of two. +/// That is, the exponent `e = 2^k` for some non-negative integer `k`. Which is used alot in zk-SNARKs. +pub fn scale2(self: Scalar, k: Int) -> Scalar { + if k < 0 { + zero + } else { + do_scale2(self, k) + } +} + +fn do_scale2(self: Scalar, k: Int) -> Scalar { + if k == 0 { + self + } else { + do_scale2(mul(self, self), k - 1) + } +} + +test scale2_1() { + and { + scale2(Scalar(834884848), -1) == zero, + scale2(Scalar(834884848), 0) == scale(Scalar(834884848), 1), + scale2(Scalar(834884848), 1) == scale(Scalar(834884848), 2), + scale2(Scalar(834884848), 2) == scale(Scalar(834884848), 4), + scale2(Scalar(834884848), 3) == scale(Scalar(834884848), 8), + scale2(Scalar(834884848), 4) == scale(Scalar(834884848), 16), + } +} + +// ## Combining + +/// Adds two `Scalar` elements, ensuring the result stays within the finite field range. +pub fn add(left: Scalar, right: Scalar) -> Scalar { + Scalar(( left.integer + right.integer ) % field_prime) +} + +test add_1() { + and { + (add(Scalar(834884848), Scalar(834884848)) == Scalar(1669769696))?, + (add(Scalar(field_prime - 1), Scalar(1)) == Scalar(0))?, + (add(Scalar(3), Scalar(field_prime)) == Scalar(3))?, + } +} + +/// Divides one `Scalar` element by another, returning `None` if the divisor is zero. +pub fn div(left: Scalar, right: Scalar) -> Option { + if right == zero { + None + } else { + Some(mul(left, scale(right, field_prime - 2))) + } +} + +test div_1() { + and { + div(Scalar(834884848), Scalar(834884848)) == Some(Scalar(1)), + div(Scalar(834884848), zero) == None, + div(Scalar(field_prime - 1), Scalar(2)) == Some( + Scalar( + 26217937587563095239723870254092982918845276250263818911301829349969290592256, + ), + ), + } +} + +/// Multiplies two `Scalar` elements, with the result constrained within the finite field. +pub fn mul(left: Scalar, right: Scalar) -> Scalar { + Scalar(left.integer * right.integer % field_prime) +} + +test mul_1() { + and { + mul(Scalar(834884848), Scalar(834884848)) == Scalar(697032709419983104), + mul(zero, Scalar(834884848)) == zero, + mul(Scalar(field_prime - 1), Scalar(2)) == Scalar( + 52435875175126190479447740508185965837690552500527637822603658699938581184511, + ), + } +} + +/// Calculates the additive inverse of a `Scalar` element. +pub fn neg(self: Scalar) -> Scalar { + // this is basicly sub(zero, self), but more efficient as it saves one modulo operation + if self.integer == 0 { + self + } else { + Scalar(field_prime - self.integer) + } +} + +test neg_1() { + and { + neg(Scalar(834884848)) == Scalar( + 52435875175126190479447740508185965837690552500527637822603658699937746299665, + ), + neg(zero) == zero, + neg(one) == Scalar(field_prime - 1), + } +} + +/// Calculates the multiplicative inverse of an `Scalar` element, returning `None` if the element is zero. +pub fn recip(self: Scalar) -> Option { + div(one, self) +} + +test recip_1() { + and { + recip(Scalar(834884848)) == Some( + Scalar( + 35891248691642227249400403463796410930702563777316955162085759263735363466421, + ), + ), + recip(zero) == None, + } +} + +/// Subtracts one `Scalar` element from another, with the result wrapped within the finite field range. +pub fn sub(left: Scalar, right: Scalar) -> Scalar { + Scalar(( left.integer - right.integer ) % field_prime) +} + +test sub_1() { + and { + (sub(Scalar(834884848), Scalar(834884848)) == zero)?, + (sub(zero, Scalar(5)) == Scalar(field_prime - 5))?, + } +} + +// ## Transforming + +/// Converts a `Scalar` element back to its integer representation. +pub fn to_int(self: Scalar) -> Int { + self.integer +} + +test to_int_1() { + to_int(Scalar(834884848)) == 834884848 +} + +/// Converts a `Scalar` element to a Big-Endian (most-significant bits first) `ByteArray`. +pub fn to_bytearray_big_endian(self: Scalar, size: Int) -> ByteArray { + builtin.integer_to_bytearray(True, size, self.integer) +} + +/// Converts a `Scalar` element to a Little-Endian (least-significant bits first) `ByteArray`. +pub fn to_bytearray_little_endian(self: Scalar, size: Int) -> ByteArray { + builtin.integer_to_bytearray(False, size, self.integer) +} + +test to_bytearray_1() { + to_bytearray_big_endian(Scalar(16777215), 3) == #"ffffff" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/interval.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/interval.ak new file mode 100644 index 00000000..96179f9b --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/interval.ak @@ -0,0 +1,680 @@ +//// In a eUTxO-based blockchain like Cardano, the management of time can be +//// finicky. +//// +//// Indeed, in order to maintain a complete determinism in the execution of +//// scripts, it is impossible to introduce a notion of _"current time"_ since +//// the execution would then depend on factor that are external to the +//// transaction itself: the ineluctable stream of time flowing in our universe. +//// +//// Hence, to work around that, we typically define time intervals, which gives +//// window -- a.k.a intervals -- within which the transaction can be executed. +//// From within a script, it isn't possible to know when exactly the script is +//// executed, but we can reason about the interval bounds to validate pieces of +//// logic. + +// TODO: Replace 'Int' with a generic 'a' once we have comparable traits. + +/// A type to represent intervals of values. Interval are inhabited by a type +/// `a` which is useful for non-infinite intervals that have a finite +/// lower-bound and/or upper-bound. +/// +/// This allows to represent all kind of mathematical intervals: +/// +/// ```aiken +/// // [1; 10] +/// let i0: Interval = Interval +/// { lower_bound: +/// IntervalBound { bound_type: Finite(1), is_inclusive: True } +/// , upper_bound: +/// IntervalBound { bound_type: Finite(10), is_inclusive: True } +/// } +/// ``` +/// +/// ```aiken +/// // (20; infinity) +/// let i1: Interval = Interval +/// { lower_bound: +/// IntervalBound { bound_type: Finite(20), is_inclusive: False } +/// , upper_bound: +/// IntervalBound { bound_type: PositiveInfinity, is_inclusive: False } +/// } +/// ``` +pub type Interval { + lower_bound: IntervalBound, + upper_bound: IntervalBound, +} + +/// An interval bound, either inclusive or exclusive. +pub type IntervalBound { + bound_type: IntervalBoundType, + is_inclusive: Bool, +} + +/// A type of interval bound. Where finite, a value of type `a` must be +/// provided. `a` will typically be an `Int`, representing a number of seconds or +/// milliseconds. +pub type IntervalBoundType { + NegativeInfinity + Finite(a) + PositiveInfinity +} + +// ## Constructing + +/// Create an interval that includes all values greater than the given bound. i.e [lower_bound, +INF) +/// +/// ```aiken +/// interval.after(10) == Interval { +/// lower_bound: IntervalBound { bound_type: Finite(10), is_inclusive: True }, +/// upper_bound: IntervalBound { bound_type: PositiveInfinity, is_inclusive: True }, +/// } +/// ``` +pub fn after(lower_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: Finite(lower_bound), + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: PositiveInfinity, + is_inclusive: True, + }, + } +} + +/// Create an interval that includes all values after (and not including) the given bound. i.e (lower_bound, +INF) +/// +/// ```aiken +/// interval.entirely_after(10) == Interval { +/// lower_bound: IntervalBound { bound_type: Finite(10), is_inclusive: False }, +/// upper_bound: IntervalBound { bound_type: PositiveInfinity, is_inclusive: True }, +/// } +/// ``` +pub fn entirely_after(lower_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: Finite(lower_bound), + is_inclusive: False, + }, + upper_bound: IntervalBound { + bound_type: PositiveInfinity, + is_inclusive: True, + }, + } +} + +/// Create an interval that includes all values before (and including) the given bound. i.e (-INF, upper_bound] +/// +/// ```aiken +/// interval.before(100) == Interval { +/// lower_bound: IntervalBound { bound_type: NegativeInfinity, is_inclusive: True }, +/// upper_bound: IntervalBound { bound_type: Finite(100), is_inclusive: True }, +/// } +/// ``` +pub fn before(upper_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: NegativeInfinity, + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: Finite(upper_bound), + is_inclusive: True, + }, + } +} + +/// Create an interval that includes all values before (and not including) the given bound. i.e (-INF, upper_bound) +/// +/// ```aiken +/// interval.entirely_before(10) == Interval { +/// lower_bound: IntervalBound { bound_type: NegativeInfinity, is_inclusive: True }, +/// upper_bound: IntervalBound { bound_type: Finite(10), is_inclusive: False }, +/// } +/// ``` +pub fn entirely_before(upper_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: NegativeInfinity, + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: Finite(upper_bound), + is_inclusive: False, + }, + } +} + +/// Create an interval that includes all values between two bounds, including the bounds. i.e. [lower_bound, upper_bound] +/// +/// ```aiken +/// interval.between(10, 100) == Interval { +/// lower_bound: IntervalBound { bound_type: Finite(10), is_inclusive: True }, +/// upper_bound: IntervalBound { bound_type: Finite(100), is_inclusive: True }, +/// } +/// ``` +pub fn between(lower_bound: a, upper_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: Finite(lower_bound), + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: Finite(upper_bound), + is_inclusive: True, + }, + } +} + +/// Create an interval that includes all values between two bounds, excluding the bounds. i.e. (lower_bound, upper_bound) +/// +/// ```aiken +/// interval.entirely_between(10, 100) == Interval { +/// lower_bound: IntervalBound { bound_type: Finite(10), is_inclusive: False }, +/// upper_bound: IntervalBound { bound_type: Finite(100), is_inclusive: False }, +/// } +/// ``` +pub fn entirely_between(lower_bound: a, upper_bound: a) -> Interval { + Interval { + lower_bound: IntervalBound { + bound_type: Finite(lower_bound), + is_inclusive: False, + }, + upper_bound: IntervalBound { + bound_type: Finite(upper_bound), + is_inclusive: False, + }, + } +} + +/// Create an empty interval that contains no value. +/// +/// ```aiken +/// interval.contains(empty, 0) == False +/// interval.contains(empty, 1000) == False +/// ``` +pub const empty: Interval = + Interval { + lower_bound: IntervalBound { + bound_type: PositiveInfinity, + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: NegativeInfinity, + is_inclusive: True, + }, + } + +/// Create an interval that contains every possible values. i.e. (-INF, +INF) +/// +/// ```aiken +/// interval.contains(everything, 0) == True +/// interval.contains(everything, 1000) == True +/// ``` +pub const everything: Interval = + Interval { + lower_bound: IntervalBound { + bound_type: NegativeInfinity, + is_inclusive: True, + }, + upper_bound: IntervalBound { + bound_type: PositiveInfinity, + is_inclusive: True, + }, + } + +// ## Inspecting + +/// Checks whether an element is contained within the interval. +/// +/// ```aiken +/// let iv = +/// Interval { +/// lower_bound: IntervalBound { +/// bound_type: Finite(14), +/// is_inclusive: True +/// }, +/// upper_bound: IntervalBound { +/// bound_type: Finite(42), +/// is_inclusive: False +/// }, +/// } +/// +/// interval.contains(iv, 25) == True +/// interval.contains(iv, 0) == False +/// interval.contains(iv, 14) == True +/// interval.contains(iv, 42) == False +/// ``` +pub fn contains(self: Interval, elem: Int) -> Bool { + let is_greater_than_lower_bound = + when self.lower_bound.bound_type is { + NegativeInfinity -> True + Finite(lower_bound) -> + if self.lower_bound.is_inclusive { + elem >= lower_bound + } else { + elem > lower_bound + } + PositiveInfinity -> False + } + + let is_smaller_than_upper_bound = + when self.upper_bound.bound_type is { + NegativeInfinity -> False + Finite(upper_bound) -> + if self.upper_bound.is_inclusive { + elem <= upper_bound + } else { + elem < upper_bound + } + PositiveInfinity -> True + } + + is_greater_than_lower_bound && is_smaller_than_upper_bound +} + +test contains_1() { + let iv = everything + contains(iv, 14) +} + +test contains_2() { + let iv = entirely_before(15) + contains(iv, 14) +} + +test contains_3() { + let iv = before(14) + contains(iv, 14) +} + +test contains_4() { + let iv = entirely_before(14) + !contains(iv, 14) +} + +test contains_5() { + let iv = entirely_after(13) + contains(iv, 14) +} + +test contains_6() { + let iv = after(14) + contains(iv, 14) +} + +test contains_7() { + let iv = entirely_after(14) + !contains(iv, 14) +} + +test contains_8() { + let iv = between(42, 1337) + !contains(iv, 14) +} + +test contains_9() { + let iv = between(0, 42) + contains(iv, 14) +} + +test contains_10() { + let iv = between(0, 42) + contains(iv, 42) +} + +test contains_11() { + let iv = entirely_between(0, 42) + !contains(iv, 0) +} + +test contains_12() { + let iv = empty + !contains(iv, 14) +} + +/// Tells whether an interval is empty; i.e. that is contains no value. +/// +/// ```aiken +/// let iv1 = interval.empty +/// +/// let iv2 = Interval { +/// lower_bound: IntervalBound { bound_type: Finite(0), is_inclusive: False }, +/// upper_bound: IntervalBound { bound_type: Finite(0), is_inclusive: False }, +/// } +/// +/// let iv3 = Interval { +/// lower_bound: IntervalBound { bound_type: Finite(0), is_inclusive: False }, +/// upper_bound: IntervalBound { bound_type: Finite(100), is_inclusive: False }, +/// } +/// +/// interval.is_empty(iv1) == True +/// interval.is_empty(iv2) == True +/// interval.is_empty(iv3) == False +/// +/// // Note: Two empty intervals are not necessarily equal. +/// iv1 != iv2 +/// ``` +pub fn is_empty(self: Interval) -> Bool { + let ordering = + compare_bound_type(self.lower_bound.bound_type, self.upper_bound.bound_type) + + when ordering is { + Greater -> True + Equal -> !(self.lower_bound.is_inclusive && self.upper_bound.is_inclusive) + Less -> { + let is_open_interval = + !self.lower_bound.is_inclusive && !self.upper_bound.is_inclusive + if is_open_interval { + when (self.lower_bound.bound_type, self.upper_bound.bound_type) is { + (Finite(lower_bound), Finite(upper_bound)) -> + lower_bound + 1 == upper_bound + _ -> False + } + } else { + False + } + } + } +} + +/// Check whether the interval is entirely after the point "a" +/// +/// ```aiken +/// interval.is_entirely_after(interval.after(10), 5) == True +/// interval.is_entirely_after(interval.after(10), 10) == False +/// interval.is_entirely_after(interval.after(10), 15) == False +/// interval.is_entirely_after(interval.between(10, 20), 30) == False +/// interval.is_entirely_after(interval.between(10, 20), 5) == True +pub fn is_entirely_after(self: Interval, point: Int) -> Bool { + when self.lower_bound.bound_type is { + Finite(low) -> + if self.lower_bound.is_inclusive { + point < low + } else { + point <= low + } + _ -> False + } +} + +test is_entirely_after_1() { + is_entirely_after(after(10), 5) +} + +test is_entirely_after_2() { + !is_entirely_after(after(10), 10) +} + +test is_entirely_after_3() { + !is_entirely_after(after(10), 15) +} + +test is_entirely_after_4() { + !is_entirely_after(between(10, 20), 30) +} + +test is_entirely_after_5() { + is_entirely_after(between(10, 20), 5) +} + +test is_entirely_after_6() { + is_entirely_after(entirely_after(10), 10) +} + +test is_entirely_after_7() { + !is_entirely_after(before(10), 5) +} + +test is_entirely_after_8() { + !is_entirely_after(before(10), 15) +} + +test is_entirely_after_9() { + !is_entirely_after(entirely_before(10), 5) +} + +/// Check whether the interval is entirely before the point "a" +/// +/// ```aiken +/// interval.is_entirely_before(interval.before(10), 15) == True +/// interval.is_entirely_before(interval.before(10), 10) == False +/// interval.is_entirely_before(interval.before(10), 5) == False +/// interval.is_entirely_before(interval.between(10, 20), 30) == True +/// interval.is_entirely_before(interval.between(10, 20), 5) == False +pub fn is_entirely_before(self: Interval, point: Int) -> Bool { + when self.upper_bound.bound_type is { + Finite(hi) -> + if self.upper_bound.is_inclusive { + hi < point + } else { + hi <= point + } + _ -> False + } +} + +test is_entirely_before_1() { + is_entirely_before(before(10), 15) +} + +test is_entirely_before_2() { + !is_entirely_before(before(10), 10) +} + +test is_entirely_before_3() { + !is_entirely_before(before(10), 5) +} + +test is_entirely_before_4() { + is_entirely_before(between(10, 20), 30) +} + +test is_entirely_before_5() { + !is_entirely_before(between(10, 20), 5) +} + +test is_entirely_before_6() { + is_entirely_before(entirely_before(10), 10) +} + +test is_entirely_before_7() { + !is_entirely_before(after(10), 15) +} + +test is_entirely_before_8() { + !is_entirely_before(after(10), 5) +} + +test is_entirely_before_9() { + !is_entirely_before(entirely_after(10), 5) +} + +// ## Combining + +/// Computes the smallest interval containing the two given intervals, if any +/// +/// ```aiken +/// let iv1 = between(0, 10) +/// let iv2 = between(2, 14) +/// hull(iv1, iv2) == between(0, 14) +/// +/// let iv1 = between(5, 10) +/// let iv2 = before(0) +/// hull(iv1, iv2) == before(10) +/// +/// let iv1 = entirely_after(0) +/// let iv2 = between(10, 42) +/// hull(iv1, iv2) = entirely_after(0) +/// ``` +pub fn hull(iv1: Interval, iv2: Interval) -> Interval { + Interval { + lower_bound: min(iv1.lower_bound, iv2.lower_bound), + upper_bound: max(iv1.upper_bound, iv2.upper_bound), + } +} + +test hull_1() { + let iv1 = between(0, 10) + let iv2 = between(2, 14) + hull(iv1, iv2) == between(0, 14) +} + +test hull_2() { + let iv1 = between(5, 10) + let iv2 = before(0) + hull(iv1, iv2) == before(10) +} + +test hull_3() { + let iv1 = entirely_after(0) + let iv2 = between(10, 42) + hull(iv1, iv2) == entirely_after(0) +} + +/// Computes the largest interval contains in the two given intervals, if any. +/// +/// ```aiken +/// let iv1 = interval.between(0, 10) +/// let iv2 = interval.between(2, 14) +/// interval.intersection(iv1, iv2) == interval.between(2, 10) +/// +/// let iv1 = interval.entirely_before(10) +/// let iv2 = interval.entirely_after(0) +/// interval.intersection(iv1, iv2) == interval.entirely_between(0, 10) +/// +/// let iv1 = interval.between(0, 1) +/// let iv2 = interval.between(2, 3) +/// interval.intersection(iv1, iv2) |> interval.is_empty +/// ``` +pub fn intersection(iv1: Interval, iv2: Interval) -> Interval { + Interval { + lower_bound: max(iv1.lower_bound, iv2.lower_bound), + upper_bound: min(iv1.upper_bound, iv2.upper_bound), + } +} + +test intersection_1() { + let iv1 = between(0, 10) + let iv2 = between(2, 14) + intersection(iv1, iv2) == between(2, 10) +} + +test intersection_2() { + let iv1 = between(0, 1) + let iv2 = between(1, 2) + intersection(iv1, iv2) == between(1, 1) +} + +test intersection_3() { + let iv1 = between(0, 1) + let iv2 = entirely_between(1, 2) + intersection(iv1, iv2) + |> is_empty +} + +test intersection_4() { + let iv1 = entirely_between(0, 1) + let iv2 = entirely_between(1, 2) + intersection(iv1, iv2) + |> is_empty +} + +test intersection_5() { + let iv1 = between(0, 10) + let iv2 = before(4) + intersection(iv1, iv2) == between(0, 4) +} + +test intersection_6() { + let iv1 = entirely_before(10) + let iv2 = entirely_after(0) + intersection(iv1, iv2) == entirely_between(0, 10) +} + +/// Return the highest bound of the two. +/// +/// ```aiken +/// let ib1 = IntervalBound { bound_type: Finite(0), is_inclusive: False } +/// let ib2 = IntervalBound { bound_type: Finite(1), is_inclusive: False } +/// +/// interval.max(ib1, ib2) == ib2 +/// ``` +pub fn max( + left: IntervalBound, + right: IntervalBound, +) -> IntervalBound { + when compare_bound(left, right) is { + Less -> right + Equal -> left + Greater -> left + } +} + +/// Return the smallest bound of the two. +/// +/// ```aiken +/// let ib1 = IntervalBound { bound_type: Finite(0), is_inclusive: False } +/// let ib2 = IntervalBound { bound_type: Finite(1), is_inclusive: False } +/// +/// interval.min(ib1, ib2) == ib1 +/// ``` +pub fn min( + left: IntervalBound, + right: IntervalBound, +) -> IntervalBound { + when compare_bound(left, right) is { + Less -> left + Equal -> left + Greater -> right + } +} + +fn compare_bound( + left: IntervalBound, + right: IntervalBound, +) -> Ordering { + when compare_bound_type(left.bound_type, right.bound_type) is { + Less -> Less + Greater -> Greater + Equal -> + if left.is_inclusive == right.is_inclusive { + Equal + } else if left.is_inclusive { + Greater + } else { + Less + } + } +} + +fn compare_bound_type( + left: IntervalBoundType, + right: IntervalBoundType, +) -> Ordering { + when left is { + NegativeInfinity -> + when right is { + NegativeInfinity -> Equal + _ -> Less + } + PositiveInfinity -> + when right is { + PositiveInfinity -> Equal + _ -> Greater + } + Finite(left) -> + when right is { + NegativeInfinity -> Greater + PositiveInfinity -> Less + Finite(right) -> + if left < right { + Less + } else if left == right { + Equal + } else { + Greater + } + } + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/math.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/math.ak new file mode 100644 index 00000000..dd575e7a --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/math.ak @@ -0,0 +1,424 @@ +//// This module contains some basic Math utilities. Standard arithmetic +//// operations on integers are available through native operators: +//// +//// Operator | Description +//// --- | :--- +//// `+` | Arithmetic sum +//// `-` | Arithmetic difference +//// `/` | Whole division +//// `*` | Arithmetic multiplication +//// `%` | Remainder by whole division +//// +//// Here are a few examples: +//// +//// ```aiken +//// 1 + 1 // 2 +//// 10 - 2 // 8 +//// 40 / 14 // 2 +//// 3 * 4 // 12 +//// 10 % 3 // 1 + +use aiken/builtin + +/// Calculate the absolute value of an integer. +/// +/// ```aiken +/// math.abs(-42) == 42 +/// math.abs(14) == 14 +/// ``` +pub fn abs(self: Int) -> Int { + if self < 0 { + 0 - self + } else { + self + } +} + +test abs_1() { + abs(14) == 14 +} + +test abs_2() { + abs(-42) == 42 +} + +/// Restrict the value of an integer between two min and max bounds +/// +/// ```aiken +/// math.clamp(14, min: 0, max: 10) == 10 +/// ``` +pub fn clamp(self: Int, min: Int, max: Int) -> Int { + if self < min { + min + } else { + if self > max { + max + } else { + self + } + } +} + +test clamp_1() { + clamp(14, min: 0, max: 10) == 10 +} + +test clamp_2() { + clamp(7, min: 0, max: 10) == 7 +} + +test clamp_3() { + clamp(7, min: 10, max: 100) == 10 +} + +/// The greatest common divisor of two integers. +/// +/// ```aiken +/// math.gcd(42, 14) == 14 +/// math.gcd(14, 42) == 14 +/// math.gcd(0, 0) == 0 +/// ``` +pub fn gcd(x: Int, y: Int) -> Int { + abs(do_gcd(x, y)) +} + +fn do_gcd(x: Int, y: Int) -> Int { + when y is { + 0 -> x + _ -> do_gcd(y, x % y) + } +} + +test gcd_test1() { + gcd(10, 300) == 10 +} + +test gcd_test2() { + gcd(-10, 300) == 10 +} + +test gcd_test3() { + gcd(42, 14) == 14 +} + +/// Checks if an integer has a given integer square root x. +/// The check has constant time complexity $O(1)$. +/// +/// ```aiken +/// math.is_sqrt(0, 0) +/// math.is_sqrt(25, 5) +/// !math.is_sqrt(25, -5) +/// math.is_sqrt(44203, 210) +/// ``` +pub fn is_sqrt(self: Int, x: Int) -> Bool { + x * x <= self && ( x + 1 ) * ( x + 1 ) > self +} + +test is_sqrt1() { + is_sqrt(44203, 210) +} + +test is_sqrt2() { + is_sqrt(975461057789971041, 987654321) +} + +/// The logarithm in base `b` of an element using integer divisions. +/// +/// ```aiken +/// math.log(10, base: 2) == 3 +/// math.log(42, base: 2) == 5 +/// math.log(42, base: 3) == 3 +/// math.log(5, base: 0) == 0 +/// math.log(4, base: 4) == 1 +/// math.log(4, base: 42) == 0 +/// ``` +pub fn log(self: Int, base: Int) -> Int { + if base <= 0 { + 0 + } else if self == base { + 1 + } else if self < base { + 0 + } else { + 1 + log(self / base, base) + } +} + +test log_10_2() { + log(10, base: 2) == 3 +} + +test log_42_2() { + log(42, base: 2) == 5 +} + +test log_42_3() { + log(42, base: 3) == 3 +} + +test log_5_0() { + log(5, base: 0) == 0 +} + +test log_4_4() { + log(4, base: 4) == 1 +} + +test log_4_43() { + log(4, base: 43) == 0 +} + +/// The integer logarithm in base 2. Faster than [`log`](#log) in this particular case. +/// +/// ```aiken +/// math.log2(1) == 0 +/// math.log2(2) == 1 +/// math.log2(3) == 1 +/// math.log2(4) == 2 +/// math.log2(256) == 8 +/// math.log2(257) == 8 +/// math.log2(511) == 8 +/// math.log2(1025) == 10 +/// ``` +pub fn log2(x: Int) -> Int { + expect x > 0 + let s = builtin.integer_to_bytearray(True, 0, x) + let len = builtin.length_of_bytearray(s) + let b = builtin.index_bytearray(s, 0) + len * 8 - if b < 2 { + 8 + } else if b < 4 { + 7 + } else if b < 8 { + 6 + } else if b < 16 { + 5 + } else if b < 32 { + 4 + } else if b < 64 { + 3 + } else if b < 128 { + 2 + } else { + 1 + } +} + +test log2_matrix() { + and { + log2(1) == 0, + log2(2) == 1, + log2(3) == 1, + log2(4) == 2, + log2(256) == 8, + log2(257) == 8, + log2(511) == 8, + log2(1025) == 10, + } +} + +/// Return the maximum of two integers. +pub fn max(a: Int, b: Int) -> Int { + if a > b { + a + } else { + b + } +} + +test max_1() { + max(0, 0) == 0 +} + +test max_2() { + max(14, 42) == 42 +} + +test max_3() { + max(42, 14) == 42 +} + +/// Return the minimum of two integers. +pub fn min(a: Int, b: Int) -> Int { + if a > b { + b + } else { + a + } +} + +test min_1() { + min(0, 0) == 0 +} + +test min_2() { + min(14, 42) == 14 +} + +test min_3() { + min(42, 14) == 14 +} + +/// Calculates a number to the power of `e` using the exponentiation by +/// squaring method. +/// +/// ```aiken +/// math.pow(3, 5) == 243 +/// math.pow(7, 2) == 49 +/// math.pow(3, -4) == 0 +/// math.pow(0, 0) == 1 +/// math.pow(513, 3) == 135005697 +/// ``` +pub fn pow(self: Int, e: Int) -> Int { + if e < 0 { + 0 + } else if e == 0 { + 1 + } else if e % 2 == 0 { + pow(self * self, e / 2) + } else { + self * pow(self * self, ( e - 1 ) / 2) + } +} + +test pow_3_5() { + pow(3, 5) == 243 +} + +test pow_7_2() { + pow(7, 2) == 49 +} + +test pow_3__4() { + // negative powers round to zero + pow(3, -4) == 0 +} + +test pow_0_0() { + // sorry math + pow(0, 0) == 1 +} + +test pow_513_3() { + pow(513, 3) == 135005697 +} + +test pow_2_4() { + pow(2, 4) == 16 +} + +test pow_2_42() { + pow(2, 42) == 4398046511104 +} + +/// Calculates the power of 2 for a given exponent `e`. Much cheaper than +/// using `pow(2, _)` for small exponents $0 < e < 256$. +/// +/// ```aiken +/// math.pow2(-2) == 0 +/// math.pow2(0) == 1 +/// math.pow2(1) == 2 +/// math.pow2(4) == 16 +/// math.pow2(42) == 4398046511104 +/// ``` +pub fn pow2(e: Int) -> Int { + // do_pow2(e, 1) + if e < 8 { + if e < 0 { + 0 + } else { + builtin.index_bytearray(#[1, 2, 4, 8, 16, 32, 64, 128], e) + } + } else if e < 32 { + 256 * pow2(e - 8) + } else { + 4294967296 * pow2(e - 32) + } +} + +test pow2_neg() { + pow2(-2) == 0 +} + +test pow2_0() { + pow2(0) == 1 +} + +test pow2_1() { + pow2(1) == 2 +} + +test pow2_4() { + pow2(4) == 16 +} + +test pow2_42() { + pow2(42) == 4398046511104 +} + +test pow2_256() { + pow2(256) == 115792089237316195423570985008687907853269984665640564039457584007913129639936 +} + +/// Calculates the square root of an integer using the [Babylonian +/// method](https://en.wikipedia.org/wiki/Methods_of_computing_square_roots#Babylonian_method). This returns either the exact result or the smallest integer +/// nearest to the square root. +/// +/// Returns `None` for negative values. +/// +/// ```aiken +/// math.sqrt(0) == Some(0) +/// math.sqrt(25) == Some(5) +/// math.sqrt(44203) == Some(210) +/// math.sqrt(-42) == None +/// ``` +/// +/// > [!TIP] +/// > This function can be quite expensive to perform on-chain. Prefer using [`is_sqrt`](#is_sqrt) whenever possible. +pub fn sqrt(self: Int) -> Option { + if self < 0 { + None + } else if self <= 1 { + Some(self) + } else { + Some(sqrt_babylonian(self, self, ( self + 1 ) / 2)) + } +} + +// The basic idea is that if x is an overestimate to the square root of a +// non-negative real number S then S/x will be an underestimate, or vice versa, +// and so the average of these two numbers may reasonably be expected to provide a +// better approximation (though the formal proof of that assertion depends on the +// inequality of arithmetic and geometric means that shows this average is always +// an overestimate of the square root. +fn sqrt_babylonian(self: Int, x: Int, y: Int) -> Int { + if y >= x { + x + } else { + sqrt_babylonian(self, y, ( y + self / y ) / 2) + } +} + +test sqrt1() { + sqrt(0) == Some(0) +} + +test sqrt2() { + sqrt(1) == Some(1) +} + +test sqrt3() { + sqrt(25) == Some(5) +} + +test sqrt4() { + sqrt(44203) == Some(210) +} + +test sqrt5() { + sqrt(975461057789971041) == Some(987654321) +} + +test sqrt6() { + sqrt(-42) == None +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.ak new file mode 100644 index 00000000..88fe7ab7 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.ak @@ -0,0 +1,871 @@ +//// This module implements operations between rational numbers. +//// +//// > [!CAUTION] +//// > Internally, rational aren't automatically reduced as this is **only done on-demand**. +//// > +//// > Thus, for example: +//// > +//// > ```aiken +//// > rational.new(2, 3) != rational.new(4, 6) +//// > ``` +//// > +//// > Comparing rational values should, therefore, only happen after reduction (see [reduce](#reduce)) or via the [compare](#compare) method. + +use aiken/builtin +use aiken/collection/list +use aiken/math +use aiken/option + +/// Opaque type used to ensure the sign of the Rational is managed strictly in the numerator. +pub opaque type Rational { + numerator: Int, + denominator: Int, +} + +// ## Constructing + +/// Create a new `Rational` from an `Int`. +/// +/// ```aiken +/// Some(rational.from_int(14)) == rational.new(14, 1) +/// Some(rational.from_int(-5)) == rational.new(-5, 1) +/// Some(rational.from_int(0)) == rational.new(0, 1) +/// ``` +pub fn from_int(numerator: Int) -> Rational { + Rational { numerator, denominator: 1 } +} + +test from_int_1() { + and { + (from_int(14) == ratio(14, 1))?, + (from_int(-5) == ratio(-5, 1))?, + (from_int(0) == ratio(0, 1))?, + } +} + +/// An unsafe constructor for `Rational` values. Assumes that the following invariants are +/// enforced: +/// +/// - the denominator is positive (the sign is managed in the numerator); +/// - the denominator is not null. +/// +/// This function is mainly used as a quick way to construct rationals from literal values. +fn ratio(numerator: Int, denominator: Int) -> Rational { + Rational { numerator, denominator } +} + +/// Make a `Rational` number from the ratio of two integers. +/// +/// Returns `None` when the denominator is null. +/// +/// ```aiken +/// rational.new(14, 42) == Some(r) +/// rational.new(14, 0) == None +/// ``` +pub fn new(numerator: Int, denominator: Int) -> Option { + if denominator == 0 { + None + } else if denominator < 0 { + Some(Rational { numerator: -numerator, denominator: -denominator }) + } else { + Some(Rational { numerator, denominator }) + } +} + +test new_1() { + and { + (new(2, 0) == None)?, + (new(2, 3) == Some(ratio(2, 3)))?, + (new(-2, 3) == Some(ratio(-2, 3)))?, + (new(2, -3) == Some(ratio(-2, 3)))?, + (new(2, 4) == Some(ratio(2, 4)))?, + (new(-2, -3) == Some(ratio(2, 3)))?, + (new(-2, -4) == Some(ratio(2, 4)))?, + } +} + +/// A null `Rational`. +pub const zero: Rational = Rational { numerator: 0, denominator: 1 } + +test zero_1() { + zero == ratio(0, 1) +} + +// ## Inspecting + +/// Get the denominator of a rational value. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.denominator(x) == 3 +/// ``` +pub fn denominator(self: Rational) -> Int { + self.denominator +} + +test denominator_1() { + expect Some(x) = new(2, 3) + expect Some(y) = new(-2, 3) + expect Some(z) = new(2, -3) + expect Some(w) = new(-2, -3) + and { + (denominator(x) == 3)?, + (denominator(y) == 3)?, + (denominator(z) == 3)?, + (denominator(w) == 3)?, + } +} + +/// Get the numerator of a rational value. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.numerator(x) == 2 +/// ``` +pub fn numerator(self: Rational) -> Int { + self.numerator +} + +test numerator_1() { + expect Some(x) = new(2, 3) + expect Some(y) = new(-2, 3) + expect Some(z) = new(2, -3) + expect Some(w) = new(-2, -3) + + and { + (numerator(x) == 2)?, + (numerator(y) == -2)?, + (numerator(z) == -2)?, + (numerator(w) == 2)?, + } +} + +// ## Modifying + +/// Absolute value of a `Rational`. +/// +/// ```aiken +/// expect Some(x) = rational.new(3, 2) +/// expect Some(y) = rational.new(-3, 2) +/// +/// rational.abs(x) == x +/// rational.abs(y) == x +/// ``` +pub fn abs(self: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = self + Rational { numerator: math.abs(a_n), denominator: a_d } +} + +test abs_examples() { + and { + (abs(ratio(5, 2)) == ratio(5, 2))?, + (abs(ratio(-5, 2)) == ratio(5, 2))?, + (abs(ratio(5, 2)) == abs(ratio(-5, 2)))?, + } +} + +/// Change the sign of a `Rational`. +/// +/// ```aiken +/// expect Some(x) = rational.new(3, 2) +/// expect Some(y) = rational.new(-3, 2) +/// +/// rational.negate(x) == y +/// rational.negate(y) == x +/// ``` +pub fn negate(a: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = a + Rational { numerator: -a_n, denominator: a_d } +} + +test negate_1() { + and { + (negate(ratio(5, 2)) == ratio(-5, 2))?, + (negate(ratio(-5, 2)) == ratio(5, 2))?, + (negate(negate(ratio(5, 2))) == ratio(5, 2))?, + } +} + +/// Reciprocal of a `Rational` number. That is, a new `Rational` where the +/// numerator and denominator have been swapped. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 5) +/// rational.reciprocal(x) == rational.new(5, 2) +/// +/// let y = rational.zero +/// rational.reciprocal(y) == None +/// ``` +pub fn reciprocal(self: Rational) -> Option { + let Rational { numerator: a_n, denominator: a_d } = self + if a_n < 0 { + Some(Rational { numerator: -a_d, denominator: -a_n }) + } else if a_n > 0 { + Some(Rational { numerator: a_d, denominator: a_n }) + } else { + None + } +} + +test reciprocal_1() { + and { + (reciprocal(ratio(5, 2)) == new(2, 5))?, + (reciprocal(ratio(-5, 2)) == new(-2, 5))?, + (reciprocal(ratio(0, 2)) == None)?, + (reciprocal(ratio(2, 3)) == new(3, 2))?, + (reciprocal(ratio(-2, 3)) == new(-3, 2))?, + } +} + +/// Reduce a rational to its irreducible form. This operation makes the +/// numerator and denominator coprime. +/// +/// ```aiken +/// expect Some(x) = rational.new(80, 200) +/// Some(rational.reduce(x)) == rational.new(2, 5) +/// ``` +pub fn reduce(self: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = self + let d = math.gcd(a_n, a_d) + Rational { numerator: a_n / d, denominator: a_d / d } +} + +test reduce_1() { + and { + (reduce(ratio(80, 200)) == ratio(2, 5))?, + (reduce(ratio(-5, 1)) == ratio(-5, 1))?, + (reduce(ratio(0, 3)) == ratio(0, 1))?, + } +} + +// ## Combining + +// ### Arithmetic operations + +/// Addition: sum of two rational values +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// Some(rational.add(x, y)) == rational.new(17, 12) +/// ``` +pub fn add(left: Rational, right: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + Rational { numerator: a_n * b_d + b_n * a_d, denominator: a_d * b_d } +} + +test add_1() { + add(ratio(2, 3), ratio(3, 4)) == ratio(17, 12) +} + +test add_2() { + add(ratio(-2, 3), ratio(3, 4)) == ratio(1, 12) +} + +/// Division: quotient of two rational values. Returns `None` when the second +/// value is null. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// rational.div(x, y) == rational.new(8, 9) +/// ``` +pub fn div(left: Rational, right: Rational) -> Option { + reciprocal(right) |> option.map(mul(left, _)) +} + +test div_1() { + div(ratio(2, 3), ratio(3, 4)) == new(8, 9) +} + +test div_2() { + div(ratio(2, 3), ratio(-3, 4)) == new(-8, 9) +} + +/// Multiplication: the product of two rational values. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// Some(rational.mul(x, y)) == rational.new(6, 12) +/// ``` +pub fn mul(left: Rational, right: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + Rational { numerator: a_n * b_n, denominator: a_d * b_d } +} + +test mul_1() { + mul(ratio(2, 3), ratio(3, 4)) == ratio(6, 12) +} + +test mul_2() { + mul(ratio(-2, 3), ratio(-3, 4)) == ratio(6, 12) +} + +test mul_3() { + let result = + ratio(2, 5) + |> mul(ratio(1, 8)) + |> mul(ratio(3, 10)) + |> mul(ratio(21, 100)) + |> mul(ratio(3, 5)) + |> mul(ratio(2, 8)) + |> mul(ratio(4, 10)) + |> mul(ratio(22, 100)) + |> reduce + + result == ratio(2079, 50000000) +} + +/// Subtraction: difference of two rational values +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// Some(rational.sub(x, y)) == rational.new(-1, 12) +/// ``` +pub fn sub(left: Rational, right: Rational) -> Rational { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + Rational { numerator: a_n * b_d - b_n * a_d, denominator: a_d * b_d } +} + +test sub_1() { + sub(ratio(2, 3), ratio(3, 4)) == ratio(-1, 12) +} + +test sub_2() { + sub(ratio(2, 3), ratio(-3, 4)) == ratio(17, 12) +} + +test sub_3() { + sub(ratio(-2, 3), ratio(3, 4)) == ratio(-17, 12) +} + +// ### Ordering + +/// Compare two rationals for an ordering. This is safe to use even for +/// non-reduced rationals. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// expect Some(z) = rational.new(4, 6) +/// +/// compare(x, y) == Less +/// compare(y, x) == Greater +/// compare(x, x) == Equal +/// compare(x, z) == Equal +/// ``` +pub fn compare(left: Rational, right: Rational) -> Ordering { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + + let l = a_n * b_d + let r = b_n * a_d + + if l < r { + Less + } else if l > r { + Greater + } else { + Equal + } +} + +test compare_1() { + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + expect Some(z) = new(4, 6) + and { + compare(x, y) == Less, + compare(y, x) == Greater, + compare(x, x) == Equal, + compare(x, z) == Equal, + } +} + +/// Comparison of two rational values using a chosen heuristic. For example: +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// expect Some(y) = rational.new(3, 4) +/// +/// rational.compare_with(x, >, y) == False +/// rational.compare_with(y, >, x) == True +/// rational.compare_with(x, >, x) == False +/// rational.compare_with(x, >=, x) == True +/// rational.compare_with(x, ==, x) == True +/// rational.compare_with(x, ==, y) == False +/// ``` +pub fn compare_with( + left: Rational, + with: fn(Int, Int) -> Bool, + right: Rational, +) -> Bool { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + with(a_n * b_d, b_n * a_d) +} + +// TODO: Rewrite tests using binary-operator as first-class functions once aiken-lang/aiken#619 is merged. + +test compare_with_eq() { + let eq = + compare_with(_, fn(l, r) { l == r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + !eq(x, y)? && !eq(y, x)? && eq(x, x)? +} + +test compare_with_neq() { + let neq = + compare_with(_, fn(l, r) { l != r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + neq(x, y)? && neq(y, x)? && !neq(x, x)? +} + +test compare_with_gte() { + let gte = + compare_with(_, fn(l, r) { l >= r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + !gte(x, y)? && gte(y, x)? && gte(x, x)? +} + +test compare_with_gt() { + let gt = + compare_with(_, fn(l, r) { l > r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + !gt(x, y)? && gt(y, x)? && !gt(x, x)? +} + +test compare_with_lte() { + let lte = + compare_with(_, fn(l, r) { l <= r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + lte(x, y)? && !lte(y, x)? && lte(x, x)? +} + +test compare_with_lt() { + let lt = + compare_with(_, fn(l, r) { l < r }, _) + + expect Some(x) = new(2, 3) + expect Some(y) = new(3, 4) + + lt(x, y)? && !lt(y, x)? && !lt(x, x)? +} + +// ### Means + +/// Calculate the arithmetic mean between two `Rational` values. +/// +/// ```aiken +/// let x = rational.from_int(0) +/// let y = rational.from_int(1) +/// let z = rational.from_int(2) +/// +/// expect Some(result) = rational.arithmetic_mean([x, y, z]) +/// +/// rational.compare(result, y) == Equal +/// ``` +pub fn arithmetic_mean(self: List) -> Option { + div(list.foldr(self, zero, add), from_int(list.length(self))) +} + +test arithmetic_mean_1() { + let x = ratio(1, 2) + let y = ratio(1, 2) + expect Some(z) = arithmetic_mean([x, y]) + reduce(z) == ratio(1, 2) +} + +test arithmetic_mean_2() { + let x = ratio(1, 1) + let y = ratio(2, 1) + expect Some(z) = arithmetic_mean([x, y]) + reduce(z) == ratio(3, 2) +} + +test arithmetic_mean_3() { + let xs = + [ + ratio(1, 1), + ratio(2, 1), + ratio(3, 1), + ratio(4, 1), + ratio(5, 1), + ratio(6, 1), + ] + expect Some(z) = arithmetic_mean(xs) + reduce(z) == ratio(7, 2) +} + +/// Calculate the geometric mean between two `Rational` values. This returns +/// either the exact result or the smallest integer nearest to the square root +/// for the numerator and denominator. +/// +/// ```aiken +/// expect Some(x) = rational.new(1, 3) +/// expect Some(y) = rational.new(1, 6) +/// +/// rational.geometric_mean(x, y) == rational.new(1, 4) +/// ``` +pub fn geometric_mean(left: Rational, right: Rational) -> Option { + let Rational { numerator: a_n, denominator: a_d } = left + let Rational { numerator: b_n, denominator: b_d } = right + when math.sqrt(a_n * b_n) is { + Some(numerator) -> + when math.sqrt(a_d * b_d) is { + Some(denominator) -> Some(Rational { numerator, denominator }) + None -> None + } + None -> None + } +} + +test geometric_mean1() { + expect Some(x) = new(1, 2) + expect Some(y) = new(1, 2) + geometric_mean(x, y) == new(1, 2) +} + +test geometric_mean2() { + expect Some(x) = new(-1, 2) + expect Some(y) = new(1, 2) + geometric_mean(x, y) == None +} + +test geometric_mean3() { + expect Some(x) = new(1, 2) + expect Some(y) = new(-1, 2) + geometric_mean(x, y) == None +} + +test geometric_mean4() { + expect Some(x) = new(1, 3) + expect Some(y) = new(1, 6) + geometric_mean(x, y) == new(1, 4) +} + +test geometric_mean5() { + expect Some(x) = new(67, 2500) + expect Some(y) = new(35331, 1000) + expect Some(yi) = reciprocal(y) + geometric_mean(x, yi) == new(258, 9398) +} + +// ## Transforming + +/// Returns the smallest `Int` not less than a given `Rational` +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.ceil(x) == 1 +/// +/// expect Some(y) = rational.new(44, 14) +/// rational.ceil(y) == 4 +/// +/// expect Some(z) = rational.new(-14, 3) +/// rational.ceil(z) == -4 +/// ``` +pub fn ceil(self: Rational) -> Int { + let Rational { numerator, denominator } = self + if builtin.remainder_integer(numerator, denominator) > 0 { + builtin.quotient_integer(numerator, denominator) + 1 + } else { + builtin.quotient_integer(numerator, denominator) + } +} + +test ceil_1() { + and { + (ceil(ratio(13, 5)) == 3)?, + (ceil(ratio(15, 5)) == 3)?, + (ceil(ratio(16, 5)) == 4)?, + (ceil(ratio(-3, 5)) == 0)?, + (ceil(ratio(-5, 5)) == -1)?, + (ceil(ratio(-14, 3)) == -4)?, + (ceil(ratio(-14, 6)) == -2)?, + (ceil(ratio(44, 14)) == 4)?, + } +} + +/// Returns the greatest `Int` no greater than a given `Rational` +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.floor(x) == 0 +/// +/// expect Some(y) = rational.new(44, 14) +/// rational.floor(y) == 3 +/// +/// expect Some(z) = rational.new(-14, 3) +/// rational.floor(z) == -5 +/// ``` +pub fn floor(self: Rational) -> Int { + let Rational { numerator: a_n, denominator: a_d } = self + a_n / a_d +} + +test floor_1() { + and { + (floor(ratio(5, 2)) == 2)?, + (floor(ratio(5, 3)) == 1)?, + (floor(ratio(5, 4)) == 1)?, + (floor(ratio(5, 5)) == 1)?, + (floor(ratio(5, 6)) == 0)?, + (floor(ratio(8, 3)) == 2)?, + (floor(ratio(-14, 3)) == -5)?, + } +} + +/// Computes the rational number x raised to the power y. Returns `None` for +/// invalid exponentiation. +/// +/// ```aiken +/// expect Some(x) = rational.new(50, 2500) +/// rational.reduce(rational.pow(x, 3)) == rational.new(1, 125000) +/// +/// expect Some(x) = rational.new(50, 2500) +/// rational.reduce(rational.pow(x, -3)) == rational.new(125000, 1) +/// ``` +pub fn pow(x: Rational, y: Int) -> Option { + let Rational { numerator: a, denominator: b } = x + + if a == 0 && y <= 0 { + None + } else if y > 0 { + Some(Rational { numerator: math.pow(a, y), denominator: math.pow(b, y) }) + } else if y < 0 { + Some(Rational { numerator: math.pow(b, -y), denominator: math.pow(a, -y) }) + } else { + Some(Rational { numerator: 1, denominator: 1 }) + } +} + +test pow_negative_exponent_non_zero_fraction() { + expect Some(base) = new(50, 2500) + expect Some(calculated_result) = pow(base, -3) + expect Some(expected_result) = new(125000, 1) + reduce(calculated_result) == expected_result +} + +test pow_positive_exponent() { + expect Some(base) = new(50, 2500) + expect Some(calculated_result) = pow(base, 3) + expect Some(expected_result) = new(1, 125000) + reduce(calculated_result) == expected_result +} + +test pow_exponent_zero() { + expect Some(base) = new(50, 2500) + pow(base, 0) == new(1, 1) +} + +test pow_rational_zero_exponent_zero() { + expect Some(base) = new(0, 1) + pow(base, 0) == None +} + +/// Returns the proper fraction of a given `Rational` `r`. That is, a 2-tuple of +/// an `Int` and `Rational` (n, f) such that: +/// +/// - `r = n + f`; +/// - `n` and `f` have the same sign as `r`; +/// - `f` has an absolute value less than 1. +pub fn proper_fraction(self: Rational) -> (Int, Rational) { + let Rational { numerator, denominator } = self + ( + builtin.quotient_integer(numerator, denominator), + Rational { + numerator: builtin.remainder_integer(numerator, denominator), + denominator, + }, + ) +} + +test proper_fraction_1() { + let r = ratio(10, 7) + let (n, f) = proper_fraction(r) + and { + (n == 1)?, + (f == ratio(3, 7))?, + (r == add(from_int(n), f))?, + } +} + +test proper_fraction_2() { + let r = ratio(-10, 7) + let (n, f) = proper_fraction(r) + and { + (n == -1)?, + (f == ratio(-3, 7))?, + (r == add(from_int(n), f))?, + } +} + +test proper_fraction_3() { + let r = ratio(4, 2) + let (n, f) = proper_fraction(r) + and { + (n == 2)?, + (f == ratio(0, 2))?, + (r == add(from_int(n), f))?, + } +} + +/// Round the argument to the nearest whole number. If the argument is +/// equidistant between two values, the greater value is returned (it +/// rounds half towards positive infinity). +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.round(x) == 1 +/// +/// expect Some(y) = rational.new(3, 2) +/// rational.round(y) == 2 +/// +/// expect Some(z) = rational.new(-3, 2) +/// rational.round(z) == -1 +/// ``` +/// +/// > [!CAUTION] +/// > This behaves differently than _Haskell_. If you're coming from `PlutusTx`, beware that in Haskell, rounding on equidistant values depends on the whole number being odd or even. +/// > If you need this behaviour, use [`round_even`](#round_even). +pub fn round(self: Rational) -> Int { + let (n, f) = proper_fraction(self) + + let is_negative = f.numerator < 0 + + when compare(abs(f), ratio(1, 2)) is { + Less -> n + Equal -> + if is_negative { + n + } else { + n + 1 + } + Greater -> + if is_negative { + n - 1 + } else { + n + 1 + } + } +} + +test round_1() { + and { + (round(ratio(10, 7)) == 1)?, + (round(ratio(11, 7)) == 2)?, + (round(ratio(3, 2)) == 2)?, + (round(ratio(5, 2)) == 3)?, + (round(ratio(-3, 2)) == -1)?, + (round(ratio(-2, 3)) == -1)?, + (round(ratio(-10, 7)) == -1)?, + (round(ratio(4, 2)) == 2)?, + } +} + +/// Round the argument to the nearest whole number. If the argument is +/// equidistant between two values, it returns the value that is even (it +/// rounds half to even, also known as 'banker's rounding'). +/// +/// ```aiken +/// expect Some(w) = rational.new(2, 3) +/// rational.round_even(w) == 1 +/// +/// expect Some(x) = rational.new(3, 2) +/// rational.round_even(x) == 2 +/// +/// expect Some(y) = rational.new(5, 2) +/// rational.round_even(y) == 2 +/// +/// expect Some(y) = rational.new(-3, 2) +/// rational.round_even(y) == -2 +/// ``` +pub fn round_even(self: Rational) -> Int { + let (n, f) = proper_fraction(self) + + let m = + when compare(f, ratio(0, 1)) is { + Less -> -1 + _ -> 1 + } + + let is_even = n % 2 == 0 + + when compare(abs(f), ratio(1, 2)) is { + Less -> n + Equal -> + if is_even { + n + } else { + n + m + } + Greater -> n + m + } +} + +test round_even_1() { + and { + (round_even(ratio(10, 7)) == 1)?, + (round_even(ratio(11, 7)) == 2)?, + (round_even(ratio(3, 2)) == 2)?, + (round_even(ratio(5, 2)) == 2)?, + (round_even(ratio(-3, 2)) == -2)?, + (round_even(ratio(-2, 3)) == -1)?, + (round_even(ratio(-10, 7)) == -1)?, + (round_even(ratio(4, 2)) == 2)?, + } +} + +/// Returns the nearest `Int` between zero and a given `Rational`. +/// +/// ```aiken +/// expect Some(x) = rational.new(2, 3) +/// rational.truncate(x) == 0 +/// +/// expect Some(y) = rational.new(44, 14) +/// rational.truncate(y) == 3 +/// +/// expect Some(z) = rational.new(-14, 3) +/// rational.truncate(z) == -4 +/// ``` +pub fn truncate(self: Rational) -> Int { + let Rational { numerator: a_n, denominator: a_d } = self + builtin.quotient_integer(a_n, a_d) +} + +test truncate_1() { + and { + (truncate(ratio(5, 2)) == 2)?, + (truncate(ratio(5, 3)) == 1)?, + (truncate(ratio(5, 4)) == 1)?, + (truncate(ratio(5, 5)) == 1)?, + (truncate(ratio(5, 6)) == 0)?, + (truncate(ratio(8, 3)) == 2)?, + (truncate(ratio(-14, 3)) == -4)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.tests.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.tests.ak new file mode 100644 index 00000000..ab8cbc17 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/math/rational.tests.ak @@ -0,0 +1,65 @@ +use aiken/fuzz.{both, either, map} +use aiken/math/rational.{Rational, new, pow} + +const any_positive_rational: Fuzzer = + either( + map( + both(fuzz.int_at_least(1), fuzz.int_at_least(1)), + fn((num, den)) { + expect Some(new_fraction) = new(num, den) + new_fraction + }, + ), + map( + both(fuzz.int_at_most(-1), fuzz.int_at_most(-1)), + fn((num, den)) { + expect Some(new_fraction) = new(num, den) + new_fraction + }, + ), + ) + +const any_negative_rational: Fuzzer = + either( + map( + both(fuzz.int_at_most(-1), fuzz.int_at_least(1)), + fn((num, den)) { + expect Some(new_fraction) = new(num, den) + new_fraction + }, + ), + map( + both(fuzz.int_at_least(1), fuzz.int_at_most(-1)), + fn((num, den)) { + expect Some(new_fraction) = new(num, den) + new_fraction + }, + ), + ) + +const any_non_zero_rational: Fuzzer = + either(any_negative_rational, any_positive_rational) + +test prop_power_of_zero_returns_one(rational via any_non_zero_rational) { + expect Some(calculated_result) = pow(rational, 0) + expect Some(expected_result) = new(1, 1) + calculated_result == expected_result +} + +test prop_power_of_one_returns_same_fraction(rational via any_non_zero_rational) { + expect Some(calculated_result) = pow(rational, 1) + calculated_result == rational +} + +test prop_power_numerator_zero_exponent_negative_returns_none( + (denominator, exponent) via both(fuzz.int_at_least(1), fuzz.int_at_most(-1)), +) { + expect Some(fraction) = new(0, denominator) + expect None = pow(fraction, exponent) +} + +test prop_power_unit_fraction_is_immutable(exponent via fuzz.int()) { + expect Some(unit) = new(1, 1) + expect Some(calculated_result) = pow(unit, exponent) + calculated_result == unit +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/option.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/option.ak new file mode 100644 index 00000000..cf5ef7dc --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/option.ak @@ -0,0 +1,312 @@ +//// A type to capture optional results; useful for handling errors. +//// +//// Note that the `Option` type and its constructors are readily available in Aiken. They are part of the [Prelude](https://aiken-lang.github.io/prelude/aiken.html#Option) module imported by default in every module. + +// ## Inspecting + +/// Asserts whether an option is `None`. +pub fn is_none(self: Option) -> Bool { + when self is { + Some(_) -> False + _ -> True + } +} + +test is_none_1() { + is_none(Some(0)) == False +} + +test is_none_2() { + is_none(None) == True +} + +/// Asserts whether an option is `Some`, irrespective of the value it contains. +pub fn is_some(self: Option) -> Bool { + when self is { + Some(_) -> True + _ -> False + } +} + +test is_some_1() { + is_some(Some(0)) == True +} + +test is_some_2() { + is_some(None) == False +} + +// ## Combining + +/// Chain together many computations that may fail. +/// +/// ```aiken +/// self +/// |> dict.get(policy_id) +/// |> option.and_then(dict.get(_, asset_name)) +/// |> option.or_else(0) +/// ``` +pub fn and_then( + self: Option, + then: fn(a) -> Option, +) -> Option { + when self is { + None -> None + Some(a) -> then(a) + } +} + +fn try_decrement(n: Int) -> Option { + if n > 0 { + Some(n - 1) + } else { + None + } +} + +test and_then_1() { + let result = + None + |> and_then(try_decrement) + result == None +} + +test and_then_2() { + let result = + Some(14) + |> and_then(try_decrement) + result == Some(13) +} + +test and_then_3() { + let result = + Some(0) + |> and_then(try_decrement) + result == None +} + +/// Picks the first element which is not None. If there's no such element, return None. +/// +/// ```aiken +/// option.choice([]) == None +/// option.choice([Some(14), Some(42)]) == Some(14) +/// option.choice([None, Some(42)]) == Some(42) +/// option.choice([None, None]) == None +/// ``` +pub fn choice(self: List>) -> Option { + when self is { + [] -> None + [head, ..others] -> + when head is { + None -> choice(others) + _ -> head + } + } +} + +test choice_1() { + Some(1) == choice([Some(1), Some(2)]) +} + +test choice_2() { + None == choice([]) +} + +test choice_3() { + Some(1) == choice([None, Some(1)]) +} + +/// Converts from `Option>` to `Option`. +/// +/// ```aiken +/// option.flatten(Some(Some(42))) == Some(42) +/// option.flatten(Some(None)) == None +/// option.flatten(None) == None +/// ``` +/// +/// Flattening only removes one level of nesting at a time: +/// +/// ```aiken +/// flatten(Some(Some(Some(42)))) == Some(Some(42)) +/// Some(Some(Some(42))) |> flatten |> flatten == Some(42) +/// ``` +pub fn flatten(opt: Option>) -> Option { + when opt is { + Some(inner) -> inner + None -> None + } +} + +test flatten_1() { + let x: Option> = Some(Some(6)) + Some(6) == flatten(x) +} + +test flatten_2() { + let x: Option> = Some(None) + None == flatten(x) +} + +test flatten_3() { + let x: Option> = None + None == flatten(x) +} + +test flatten_4() { + let x: Option>> = Some(Some(Some(6))) + + let result = + x + |> flatten + |> flatten + + Some(6) == result +} + +/// Apply a function to the inner value of an [`Option`](#option) +/// +/// ```aiken +/// option.map(None, fn(n) { n * 2 }) == None +/// option.map(Some(14), fn(n) { n * 2 }) == Some(28) +/// ``` +pub fn map(self: Option, with: fn(a) -> result) -> Option { + when self is { + None -> None + Some(a) -> Some(with(a)) + } +} + +test map_1() { + map(None, fn(_) { Void }) == None +} + +test map_2() { + map(Some(14), fn(n) { n + 1 }) == Some(15) +} + +/// Combine two [`Option`](#option) together. +/// +/// ```aiken +/// type Foo { +/// Foo(Int, Int) +/// } +/// +/// option.map2(Some(14), Some(42), Foo) == Some(Foo(14, 42)) +/// option.map2(None, Some(42), Foo) == None +/// option.map2(Some(14), None, Foo) == None +/// ``` +pub fn map2( + opt_a: Option, + opt_b: Option, + with: fn(a, b) -> result, +) -> Option { + when opt_a is { + None -> None + Some(a) -> + when opt_b is { + None -> None + Some(b) -> Some(with(a, b)) + } + } +} + +test map2_1() { + map2(None, Some(42), fn(_, _) { 14 }) == None +} + +test map2_2() { + map2(Some(42), None, fn(_, _) { 14 }) == None +} + +test map2_3() { + map2(Some(14), Some(42), fn(a, b) { (a, b) }) == Some((14, 42)) +} + +/// Combine three [`Option`](#option) together. +/// +/// ```aiken +/// type Foo { +/// Foo(Int, Int, Int) +/// } +/// +/// option.map3(Some(14), Some(42), Some(1337), Foo) == Some(Foo(14, 42, 1337)) +/// option.map3(None, Some(42), Some(1337), Foo) == None +/// option.map3(Some(14), None, None, Foo) == None +/// ``` +pub fn map3( + opt_a: Option, + opt_b: Option, + opt_c: Option, + with: fn(a, b, c) -> result, +) -> Option { + when opt_a is { + None -> None + Some(a) -> + when opt_b is { + None -> None + Some(b) -> + when opt_c is { + None -> None + Some(c) -> Some(with(a, b, c)) + } + } + } +} + +test map3_1() { + map3(None, Some(42), None, fn(_, _, _) { 14 }) == None +} + +test map3_2() { + map3(Some(42), None, None, fn(_, _, _) { 14 }) == None +} + +test map3_3() { + map3(Some(14), Some(42), Some(1337), fn(a, b, c) { c - a + b }) == Some(1365) +} + +/// Like [`or_else`](#or_else) but allows returning an `Option`. +/// This is effectively mapping the error branch. +/// +/// ```aiken +/// option.or_try(None, fn(_) { Some("aiken") }) == Some("aiken") +/// option.or_try(Some(42), fn(_) { Some(14) }) == Some(42) +/// option.or_try(None, fn (_) { fail }) => 💥 +/// ``` +pub fn or_try(self: Option, compute_default: fn() -> Option) -> Option { + when self is { + None -> compute_default() + _ -> self + } +} + +test or_try_1() { + or_try(None, fn() { Some("aiken") }) == Some("aiken") +} + +test or_try_2() { + or_try(Some(42), fn() { fail }) == Some(42) +} + +// ## Transforming + +/// Provide a default value, turning an optional value into a normal value. +/// +/// ```aiken +/// option.or_else(None, "aiken") == "aiken" +/// option.or_else(Some(42), 14) == 42 +/// ``` +pub fn or_else(self: Option, default: a) -> a { + when self is { + None -> default + Some(a) -> a + } +} + +test or_else_1() { + or_else(None, "aiken") == "aiken" +} + +test or_else_2() { + or_else(Some(42), 14) == 42 +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/primitive/bytearray.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/primitive/bytearray.ak new file mode 100644 index 00000000..d2f125f5 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/primitive/bytearray.ak @@ -0,0 +1,668 @@ +use aiken/builtin +use aiken/math +use aiken/option + +pub type Byte = + Int + +// ## Constructing + +/// Encode an integer value as a Big-Endian (most-significant bytes first) `ByteArray`. +/// The size is the expected size in number of bytes. +/// +/// > [!IMPORTANT] +/// > This function fails (i.e. halts the program) if the value cannot fit in the given size. When the +/// > size is _too large_, the array is left-padded with zeroes. +/// +/// ```aiken +/// bytearray.from_int_big_endian(1_000_000, 3) == #"0f4240" +/// bytearray.from_int_big_endian(1_000_000, 5) == #"00000f4240" +/// bytearray.from_int_big_endian(0, 8) == #"0000000000000000" +/// bytearray.from_int_big_endian(1_000_000, 1) => 💥 +/// ``` +pub fn from_int_big_endian(self: Int, size: Int) -> ByteArray { + builtin.integer_to_bytearray(True, size, self) +} + +test from_int_big_endian_1() { + from_int_big_endian(1_000_000, 3) == #"0f4240" +} + +test from_int_big_endian_2() { + from_int_big_endian(1_000_000, 5) == #"00000f4240" +} + +test from_int_big_endian_3() { + from_int_big_endian(0, 8) == #"0000000000000000" +} + +test from_int_big_endian_4() fail { + from_int_big_endian(1_000_000, 1) == #"40" +} + +/// Encode an integer value as a Little-Endian (least-significant bytes first) `ByteArray`. +/// The size is the expected size in number of bytes. +/// +/// > [!IMPORTANT] +/// > This function fails (i.e. halts the program) if the value cannot fit in the given size. When the +/// > size is _too large_, the array is right-padded with zeroes. +/// +/// ```aiken +/// bytearray.from_int_little_endian(1_000_000, 3) == #"40420f" +/// bytearray.from_int_little_endian(1_000_000, 5) == #"40420f0000" +/// bytearray.from_int_little_endian(0, 8) == #"0000000000000000" +/// bytearray.from_int_little_endian(1_000_000, 1) => 💥 +/// ``` +pub fn from_int_little_endian(self: Int, size: Int) -> ByteArray { + builtin.integer_to_bytearray(False, size, self) +} + +test from_int_little_endian_1() { + from_int_little_endian(1_000_000, 3) == #"40420f" +} + +test from_int_little_endian_2() { + from_int_little_endian(1_000_000, 5) == #"40420f0000" +} + +test from_int_little_endian_3() { + from_int_little_endian(0, 8) == #"0000000000000000" +} + +test from_int_little_endian_4() fail { + from_int_little_endian(1_000_000, 1) == #"40" +} + +/// Convert a `String` into a `ByteArray`. +/// +/// ```aiken +/// bytearray.from_string(@"ABC") == #"414243" +/// ``` +pub fn from_string(str: String) -> ByteArray { + builtin.encode_utf8(str) +} + +test from_string_1() { + from_string(@"") == "" +} + +test from_string_2() { + from_string(@"ABC") == #"414243" +} + +/// Add a byte element in front of a `ByteArray`. When the given byte is +/// greater than 255, it wraps-around. **PlutusV2 behavior** So 256 is mapped to 0, 257 to 1, and so +/// forth. +/// In PlutusV3 this will error instead of wrapping around. +/// +/// ```aiken +/// bytearray.push(#"", 0) == #"00" +/// bytearray.push(#"0203", 1) == #"010203" +/// bytearray.push(#"0203", 257) == #"010203" +/// ``` +pub fn push(self: ByteArray, byte: Byte) -> ByteArray { + builtin.cons_bytearray(byte, self) +} + +test push_1() { + push(#[], 0) == #[0] +} + +test push_2() { + push(#[2, 3], 1) == #[1, 2, 3] +} + +test push_3() fail { + let x = 257 + push(#[2, 3], x) == #[1, 2, 3] +} + +// ## Inspecting + +/// Get the `Byte` at the given index, or crash. +/// +/// > [!WARNING] +/// > This functions fails (i.e. halts the program) if there's no byte at the given index. +pub fn at(self: ByteArray, index: Int) -> Byte { + builtin.index_bytearray(self, index) +} + +/// Search the start and end positions of a sub-array in a `ByteArray`. +/// +/// ```aiken +/// bytearray.index_of("Hello, World!", "World") == Some((7, 11)) +/// bytearray.index_of("Hello, World!", "foo") == None +/// bytearray.index_of("Hello, World!", "!") == Some((12, 12)) +/// bytearray.index_of("Hello, World!", "o") == Some((4, 4)) +/// bytearray.index_of("Hello, World!", "Hello, World!") == Some((0, 12)) +/// ``` +pub fn index_of(self: ByteArray, bytes: ByteArray) -> Option<(Int, Int)> { + let offset = length(bytes) + + do_index_of(self, bytes, 0, offset, length(self)) + |> option.map(fn(ix) { (ix, ix + offset - 1) }) +} + +fn do_index_of( + self: ByteArray, + bytes: ByteArray, + cursor: Int, + offset: Int, + size: Int, +) -> Option { + if cursor + offset > size { + None + } else { + if builtin.slice_bytearray(cursor, offset, self) == bytes { + Some(cursor) + } else { + do_index_of(self, bytes, cursor + 1, offset, size) + } + } +} + +test index_of_1() { + index_of("Hello, World!", "World") == Some((7, 11)) +} + +test index_of_2() { + index_of("Hello, World!", "foo") == None +} + +test index_of_3() { + index_of("Hello, World!", "!") == Some((12, 12)) +} + +test index_of_4() { + index_of("Hello, World!", "o") == Some((4, 4)) +} + +test index_of_5() { + index_of("Hello, World!", "Hello, World!") == Some((0, 12)) +} + +/// Returns `True` when the given `ByteArray` is empty. +/// +/// ```aiken +/// bytearray.is_empty(#"") == True +/// bytearray.is_empty(#"00ff") == False +/// ``` +pub fn is_empty(self: ByteArray) -> Bool { + builtin.length_of_bytearray(self) == 0 +} + +test is_empty_1() { + is_empty(#"") == True +} + +test is_empty_2() { + is_empty(#"01") == False +} + +/// Returns the number of bytes in a `ByteArray`. +/// +/// ```aiken +/// bytearray.length(#[1, 2, 3]) == 3 +/// ``` +pub fn length(self: ByteArray) -> Int { + builtin.length_of_bytearray(self) +} + +test length_1() { + length(#"") == 0 +} + +test length_2() { + length(#"010203") == 3 +} + +/// Checks whether a bit (Most-Significant-Bit first) is set in the given 'ByteArray'. +/// +/// For example, consider the following bytearray: `#"8b765f"`. It can also be written as the +/// following bits sequence: +/// +/// `8` | `b` | `7` | `6` | `5` | `f` +/// --- | --- | --- | --- | --- | --- +/// `1000` | `1011` | `0111` | `0110` | `0101` | `1111` +/// +/// And thus, we have: +/// +/// ```aiken +/// test_bit(#"8b765f", 0) == True +/// test_bit(#"8b765f", 1) == False +/// test_bit(#"8b765f", 2) == False +/// test_bit(#"8b765f", 3) == False +/// test_bit(#"8b765f", 7) == True +/// test_bit(#"8b765f", 8) == False +/// test_bit(#"8b765f", 20) == True +/// test_bit(#"8b765f", 21) == True +/// test_bit(#"8b765f", 22) == True +/// test_bit(#"8b765f", 23) == True +/// ``` +pub fn test_bit(self: ByteArray, ix: Int) -> Bool { + builtin.less_than_equals_bytearray( + #[128], + builtin.cons_bytearray( + builtin.index_bytearray(self, ix / 8) * math.pow2(ix % 8) % 256, + "", + ), + ) +} + +test test_bit_0() { + test_bit(#"8b765f", 0) +} + +test test_bit_1() { + !test_bit(#"8b765f", 1) +} + +test test_bit_2() { + !test_bit(#"8b765f", 2) +} + +test test_bit_3() { + !test_bit(#"8b765f", 3) +} + +test test_bit_7() { + test_bit(#"8b765f", 7) +} + +test test_bit_8() { + !test_bit(#"8b765f", 8) +} + +test test_bit_20_21_22_23() { + and { + test_bit(#"8b765f", 20), + test_bit(#"8b765f", 21), + test_bit(#"8b765f", 22), + test_bit(#"8b765f", 23), + } +} + +// ## Modifying + +/// Returns the suffix of a `ByteArray` after `n` elements. +/// +/// ```aiken +/// bytearray.drop(#[1, 2, 3], n: 2) == #[3] +/// ``` +pub fn drop(self: ByteArray, n: Int) -> ByteArray { + builtin.slice_bytearray(n, builtin.length_of_bytearray(self) - n, self) +} + +test drop_1() { + let x = #"01020304050607" + drop(x, 2) == #"0304050607" +} + +test drop_2() { + let x = #"01020304050607" + drop(x, 0) == x +} + +test drop_3() { + let x = #"01" + drop(x, 1) == #"" +} + +test drop_4() { + let x = #"" + drop(x, 2) == #"" +} + +/// Extract a `ByteArray` as a slice of another `ByteArray`. +/// +/// Indexes are 0-based and inclusive. +/// +/// ```aiken +/// bytearray.slice(#[0, 1, 2, 3, 4, 5, 6], start: 1, end: 3) == #[1, 2, 3] +/// ``` +pub fn slice(self: ByteArray, start: Int, end: Int) -> ByteArray { + builtin.slice_bytearray(start, end - start + 1, self) +} + +test slice_1() { + slice(#"", 1, 2) == #"" +} + +test slice_2() { + slice(#"010203", 1, 2) == #"0203" +} + +test slice_3() { + slice(#"010203", 0, 42) == #"010203" +} + +test slice_4() { + slice(#[0, 1, 2, 3, 4], 0, 3) == #[0, 1, 2, 3] +} + +test slice_5() { + slice(#[0, 1, 2, 3, 4], 1, 2) == #[1, 2] +} + +/// Returns the n-length prefix of a `ByteArray`. +/// +/// ```aiken +/// bytearray.take(#[1, 2, 3], n: 2) == #[1, 2] +/// ``` +pub fn take(self: ByteArray, n: Int) -> ByteArray { + builtin.slice_bytearray(0, n, self) +} + +test take_1() { + let x = #"01020304050607" + take(x, 2) == #"0102" +} + +test take_2() { + let x = #"01020304050607" + take(x, 0) == #"" +} + +test take_3() { + let x = #"01" + take(x, 1) == x +} + +test take_4() { + let x = #"010203" + take(x, 0) == #"" +} + +// ## Combining + +/// Combine two `ByteArray` together. +/// +/// ```aiken +/// bytearray.concat(left: #[1, 2, 3], right: #[4, 5, 6]) == #[1, 2, 3, 4, 5, 6] +/// ``` +pub fn concat(left: ByteArray, right: ByteArray) -> ByteArray { + builtin.append_bytearray(left, right) +} + +test concat_1() { + concat(#"", #"") == #"" +} + +test concat_2() { + concat(#"", #"01") == #"01" +} + +test concat_3() { + concat(#"0102", #"") == #"0102" +} + +test concat_4() { + concat(#"0102", #"0304") == #"01020304" +} + +/// Compare two bytearrays lexicographically. +/// +/// ```aiken +/// bytearray.compare(#"00", #"FF") == Less +/// bytearray.compare(#"42", #"42") == Equal +/// bytearray.compare(#"FF", #"00") == Greater +/// ``` +pub fn compare(left: ByteArray, right: ByteArray) -> Ordering { + if builtin.less_than_bytearray(left, right) { + Less + } else if builtin.equals_bytearray(left, right) { + Equal + } else { + Greater + } +} + +// ## Transforming + +/// Left-fold over bytes of a [`ByteArray`](https://aiken-lang.github.io/prelude/aiken.html#ByteArray). Note that every byte given to the callback function is comprised between 0 and 255. +/// +/// ```aiken +/// bytearray.foldl(#"acab", 0, fn(byte, acc) { acc * 256 + byte }) == 44203 +/// bytearray.foldl(#[1, 2, 3], #"", flip(bytearray.push)) == #[3, 2, 1] +/// ``` +pub fn foldl( + self: ByteArray, + zero: result, + with: fn(Int, result) -> result, +) -> result { + do_foldl(self, zero, builtin.length_of_bytearray(self), 0, with) +} + +fn do_foldl( + self: ByteArray, + zero: result, + len: Int, + cursor: Int, + with: fn(Int, result) -> result, +) -> result { + if cursor == len { + zero + } else { + do_foldl( + self, + with(builtin.index_bytearray(self, cursor), zero), + len, + cursor + 1, + with, + ) + } +} + +test foldl_1() { + foldl(#[], 42, fn(byte, acc) { byte + acc }) == 42 +} + +test foldl_2() { + foldl(#"acab", 0, fn(byte, acc) { acc * 256 + byte }) == 44203 +} + +test foldl_3() { + foldl( + #"356cf088720a169dae0ce0bb1df8588944389fa43322f0d6ef4ed8c069bfd405", + 0, + fn(byte, acc) { acc * 256 + byte }, + ) == 24165060555594911913195642527692216679757672038384202527929620681761931383813 +} + +test foldl_4() { + foldl(#[1, 2, 3, 4, 5], #"", flip(push)) == #[5, 4, 3, 2, 1] +} + +/// Right-fold over bytes of a [`ByteArray`](https://aiken-lang.github.io/prelude/aiken.html#ByteArray). Note that every byte given to the callback function is comprised between 0 and 255. +/// +/// ```aiken +/// bytearray.foldr(#"acab", 0, fn(byte, acc) { acc * 256 + byte }) == 43948 +/// bytearray.foldl(#[1, 2, 3], #"", flip(bytearray.push)) == #[1, 2, 3] +/// ``` +pub fn foldr( + self: ByteArray, + zero: result, + with: fn(Int, result) -> result, +) -> result { + do_foldr(self, zero, builtin.length_of_bytearray(self) - 1, with) +} + +fn do_foldr( + self: ByteArray, + zero: result, + cursor: Int, + with: fn(Int, result) -> result, +) -> result { + if cursor < 0 { + zero + } else { + do_foldr( + self, + with(builtin.index_bytearray(self, cursor), zero), + cursor - 1, + with, + ) + } +} + +test foldr_1() { + foldr(#[], 42, fn(byte, acc) { byte + acc }) == 42 +} + +test foldr_2() { + foldr(#"acab", 0, fn(byte, acc) { acc * 256 + byte }) == 43948 +} + +test foldr_3() { + foldr(#[1, 2, 3, 4, 5], #"", flip(push)) == #[1, 2, 3, 4, 5] +} + +/// Reduce bytes in a ByteArray from left to right using the accumulator as left operand. +/// Said differently, this is [`foldl`](#foldl) with callback arguments swapped. +/// +/// ```aiken +/// bytearray.reduce(#[1,2,3], #[], bytearray.push) == #[3, 2, 1] +/// ``` +pub fn reduce( + self: ByteArray, + zero: result, + with: fn(result, Int) -> result, +) -> result { + foldl(self, zero, flip(with)) +} + +test reduce_1() { + reduce(#[], #[], push) == #[] +} + +test reduce_2() { + reduce(#[1, 2, 3], #[], push) == #[3, 2, 1] +} + +/// Interpret a Big-Endian (most-significant bytes first) `ByteArray` as an `Int`. +/// +/// ```aiken +/// bytearray.to_int_big_endian(#"0f4240") == 1_000_000 +/// bytearray.to_int_big_endian(#"00000f4240") == 1_000_000 +/// bytearray.to_int_big_endian(#"0000000000000000") == 0 +/// ``` +pub fn to_int_big_endian(self: ByteArray) -> Int { + builtin.bytearray_to_integer(True, self) +} + +test to_int_big_endian_1() { + to_int_big_endian(#"0f4240") == 1_000_000 +} + +test to_int_big_endian_2() { + to_int_big_endian(#"00000f4240") == 1_000_000 +} + +test to_int_big_endian_3() { + to_int_big_endian(#"0000000000000000") == 0 +} + +/// Interpret a Little-Endian (least-significant bytes first) `ByteArray` as an `Int`. +/// +/// ```aiken +/// bytearray.to_int_big_endian(#"40420f") == 1_000_000 +/// bytearray.to_int_big_endian(#"40420f0000") == 1_000_000 +/// bytearray.to_int_big_endian(#"0000000000000000") == 0 +/// ``` +pub fn to_int_little_endian(self: ByteArray) -> Int { + builtin.bytearray_to_integer(False, self) +} + +test to_int_little_endian_1() { + to_int_little_endian(#"40420f") == 1_000_000 +} + +test to_int_little_endian_2() { + to_int_little_endian(#"40420f0000") == 1_000_000 +} + +test to_int_little_endian_3() { + to_int_little_endian(#"0000000000000000") == 0 +} + +/// Convert a `ByteArray` into a `String`. +/// +/// > [!WARNING] +/// > This functions fails (i.e. halts the program) if the underlying `ByteArray` isn't UTF-8-encoded. In particular, you cannot convert arbitrary hash digests using this function. +/// > +/// > For converting arbitrary `ByteArray`s, use [bytearray.to_hex](#to_hex). +/// +/// ```aiken +/// bytearray.to_string(#"414243") == "ABC" +/// bytearray.to_string(some_hash) => 💥 +/// ``` +pub fn to_string(self: ByteArray) -> String { + builtin.decode_utf8(self) +} + +test to_string_1() { + to_string("") == @"" +} + +test to_string_2() { + to_string("ABC") == @"ABC" +} + +/// Encode a `ByteArray` as a hexidecimal `String`. +/// +/// ```aiken +/// bytearray.to_hex("Hello world!") == @"48656c6c6f20776f726c6421" +/// ``` +pub fn to_hex(self: ByteArray) -> String { + self + |> encode_base16(builtin.length_of_bytearray(self) - 1, "") + |> builtin.decode_utf8 +} + +test to_hex_1() { + to_hex("Hello world!") == @"48656C6C6F20776F726C6421" +} + +test to_hex_2() { + to_hex("The quick brown fox jumps over the lazy dog") == @"54686520717569636B2062726F776E20666F78206A756D7073206F76657220746865206C617A7920646F67" +} + +/// Checks whether a `ByteArray` starts with a given prefix. +/// +/// ```aiken +/// bytearray.starts_with("Hello, World!", prefix: "Hello") == True +/// bytearray.starts_with("", prefix: "") == True +/// bytearray.starts_with("Hello", prefix: "Hello, World!") == False +/// ``` +pub fn starts_with(self: ByteArray, prefix: ByteArray) -> Bool { + let prefix_length = length(prefix) + if length(self) < prefix_length { + False + } else { + take(self, prefix_length) == prefix + } +} + +test starts_with_1() { + starts_with("", "") +} + +test starts_with_2() { + starts_with("Hello, World!", "Hello, World!") +} + +test starts_with_3() { + !starts_with("Hello, World!", "hello") +} + +test starts_with_4() { + !starts_with("", "World") +} + +test starts_with_5() { + starts_with("Hello, World", "Hello") +} + +test starts_with_6() { + !starts_with("foo", "foo_") +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/primitive/int.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/primitive/int.ak new file mode 100644 index 00000000..217749e9 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/primitive/int.ak @@ -0,0 +1,156 @@ +use aiken/builtin.{bytearray_to_integer, decode_utf8} +use aiken/math +use aiken/option +use aiken/primitive/bytearray + +// ## Combining + +/// Compare two integers. +/// +/// ```aiken +/// int.compare(14, 42) == Less +/// int.compare(14, 14) == Equal +/// int.compare(42, 14) == Greater +/// ``` +pub fn compare(left: Int, right: Int) -> Ordering { + if left < right { + Less + } else if left > right { + Greater + } else { + Equal + } +} + +// ## Transforming + +/// Interpret a Big-Endian (most-significant bytes first) `ByteArray` as an `Int`. +/// +/// ```aiken +/// int.from_bytearray_big_endian(#"0f4240") == 1_000_000 +/// int.from_bytearray_big_endian(#"00000f4240") == 1_000_000 +/// int.from_bytearray_big_endian(#"0000000000000000") == 0 +/// ``` +pub fn from_bytearray_big_endian(self: ByteArray) -> Int { + bytearray_to_integer(True, self) +} + +test from_bytearray_big_endian_1() { + from_bytearray_big_endian(#"0f4240") == 1_000_000 +} + +test from_bytearray_big_endian_2() { + from_bytearray_big_endian(#"00000f4240") == 1_000_000 +} + +test from_bytearray_big_endian_3() { + from_bytearray_big_endian(#"0000000000000000") == 0 +} + +/// Interpret a Little-Endian (least-significant bytes first) `ByteArray` as an `Int`. +/// +/// ```aiken +/// int.from_bytearray_big_endian(#"40420f") == 1_000_000 +/// int.from_bytearray_big_endian(#"40420f0000") == 1_000_000 +/// int.from_bytearray_big_endian(#"0000000000000000") == 0 +/// ``` +pub fn from_bytearray_little_endian(self: ByteArray) -> Int { + bytearray_to_integer(False, self) +} + +test from_bytearray_little_endian_1() { + from_bytearray_little_endian(#"40420f") == 1_000_000 +} + +test from_bytearray_little_endian_2() { + from_bytearray_little_endian(#"40420f0000") == 1_000_000 +} + +test from_bytearray_little_endian_3() { + from_bytearray_little_endian(#"0000000000000000") == 0 +} + +/// Parse an integer from a utf-8 encoded `ByteArray`, when possible. +/// +/// ```aiken +/// int.from_utf8("14") == Some(14) +/// int.from_utf8("-42") == Some(-42) +/// int.from_utf8("007") == Some(7) +/// int.from_utf8("foo") == None +/// int.from_utf8("1.0") == None +/// int.from_utf8("1-2") == None +/// ``` +pub fn from_utf8(bytes: ByteArray) -> Option { + bytes + |> bytearray.foldr( + Some((0, 0)), + fn(byte, st) { + when st is { + None -> None + Some((n, e)) -> + if byte < 48 || byte > 57 { + if byte == 45 { + Some((-n, 0)) + } else { + None + } + } else if n < 0 { + None + } else { + let digit = byte - 48 + Some((n + digit * math.pow(10, e), e + 1)) + } + } + }, + ) + |> option.map(fn(tuple) { tuple.1st }) +} + +test from_utf8_1() { + from_utf8("0017") == Some(17) +} + +test from_utf8_2() { + from_utf8("42") == Some(42) +} + +test from_utf8_3() { + from_utf8("1337") == Some(1337) +} + +test from_utf8_4() { + from_utf8("-14") == Some(-14) +} + +test from_utf8_5() { + from_utf8("foo") == None +} + +test from_utf8_6() { + from_utf8("1-2") == None +} + +/// Convert an `Int` to its `String` representation. +/// +/// ```aiken +/// int.to_string(42) == @"42" +/// ``` +pub fn to_string(n: Int) -> String { + diagnostic(n, "") |> decode_utf8 +} + +test to_string_1() { + to_string(0) == @"0" +} + +test to_string_2() { + to_string(5) == @"5" +} + +test to_string_3() { + to_string(42) == @"42" +} + +test to_string_4() { + to_string(200) == @"200" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/primitive/string.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/primitive/string.ak new file mode 100644 index 00000000..35fa5567 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/aiken/primitive/string.ak @@ -0,0 +1,139 @@ +use aiken/builtin.{ + append_bytearray, append_string, decode_utf8, encode_utf8, length_of_bytearray, +} + +// ## Constructing + +/// Convert a `ByteArray` into a `String` +/// +/// > [!WARNING] +/// > This functions fails if the underlying `ByteArray` isn't UTF-8-encoded. In particular, you cannot convert arbitrary hash digests using this function. +/// > +/// > For converting arbitrary `ByteArray`s, use [bytearray.to_hex](./bytearray.html#to_hex). +/// +/// ```aiken +/// string.from_bytearray("foo") == @"foo" +/// string.from_bytearray(#"666f6f") == @"foo" +/// string.from_bytearray(some_hash) -> fail +/// ``` +pub fn from_bytearray(bytes: ByteArray) -> String { + decode_utf8(bytes) +} + +test from_bytearray_1() { + from_bytearray(#[]) == @"" +} + +test from_bytearray_2() { + from_bytearray(#[65, 66, 67]) == @"ABC" +} + +test from_bytearray_3() { + from_bytearray("ABC") == @"ABC" +} + +/// Convert an `Int` to its `String` representation. +/// +/// ```aiken +/// string.from_int(42) == @"42" +/// ``` +pub fn from_int(n: Int) -> String { + diagnostic(n, "") |> decode_utf8 +} + +test from_int_1() { + from_int(0) == @"0" +} + +test from_int_2() { + from_int(5) == @"5" +} + +test from_int_3() { + from_int(42) == @"42" +} + +test from_int_4() { + from_int(200) == @"200" +} + +// ## Combining + +/// Combine two `String` together. +/// +/// ```aiken +/// string.concat(left: @"Hello", right: @", World!") == @"Hello, World!" +/// ``` +pub fn concat(left: String, right: String) -> String { + append_string(left, right) +} + +test concat_1() { + concat(@"", @"") == @"" +} + +test concat_2() { + concat(@"", @"foo") == concat(@"foo", @"") +} + +test concat_3() { + concat(left: @"Hello", right: @", World!") == @"Hello, World!" +} + +/// Join a list of strings, separated by a given _delimiter_. +/// +/// ```aiken +/// string.join([], @"+") == @"" +/// string.join([@"a", @"b", @"c"], @",") == @"a,b,c" +/// ``` +pub fn join(list: List, delimiter: String) -> String { + do_join(list, encode_utf8(delimiter), #"") + |> decode_utf8 +} + +fn do_join(xs, delimiter, bytes) { + when xs is { + [] -> bytes + [x, ..rest] -> + do_join( + rest, + delimiter, + if length_of_bytearray(bytes) == 0 { + encode_utf8(x) + } else { + append_bytearray(bytes, append_bytearray(delimiter, encode_utf8(x))) + }, + ) + } +} + +test join_1() { + join([], @",") == @"" +} + +test join_2() { + join([@"a", @"b", @"c"], @",") == @"a,b,c" +} + +// ## Transforming + +/// Convert a `String` into a `ByteArray` +/// +/// ```aiken +/// string.to_bytearray(@"foo") == "foo" +/// ``` +pub fn to_bytearray(self: String) -> ByteArray { + encode_utf8(self) +} + +test to_bytearray_1() { + to_bytearray(@"") == "" +} + +test to_bytearray_2() { + to_bytearray(@"ABC") == #[65, 66, 67] +} + +test to_bytearray_3() { + to_bytearray(@"ABC") == "ABC" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/address.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/address.ak new file mode 100644 index 00000000..0167b90f --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/address.ak @@ -0,0 +1,86 @@ +use aiken/crypto.{ + Blake2b_224, Hash, Script, ScriptHash, VerificationKey, VerificationKeyHash, +} + +/// A general structure for representing an on-chain `Credential`. +/// +/// Credentials are always one of two kinds: a direct public/private key +/// pair, or a script (native or Plutus). +pub type Credential { + VerificationKey(VerificationKeyHash) + Script(ScriptHash) +} + +// ## Constructing + +/// A Cardano `Address` typically holding one or two credential references. +/// +/// Note that legacy bootstrap addresses (a.k.a. 'Byron addresses') are +/// completely excluded from Plutus contexts. Thus, from an on-chain +/// perspective only exists addresses of type 00, 01, ..., 07 as detailed +/// in [CIP-0019 :: Shelley Addresses](https://github.com/cardano-foundation/CIPs/tree/master/CIP-0019/#shelley-addresses). +pub type Address { + payment_credential: PaymentCredential, + stake_credential: Option, +} + +/// Smart-constructor for an [Address](#Address) from a [script](#Script) hash. The address has no delegation rights whatsoever. +pub fn from_script(script: Hash) -> Address { + Address { payment_credential: Script(script), stake_credential: None } +} + +/// Smart-constructor for an [Address](#Address) from a [verification key](#VerificationKey) hash. The resulting address has no delegation rights whatsoever. +pub fn from_verification_key(vk: Hash) -> Address { + Address { payment_credential: VerificationKey(vk), stake_credential: None } +} + +/// Set (or reset) the delegation part of an [Address](#Address) using a [verification key](#VerificationKey) hash. This is useful when combined with [`from_verification_key`](#from_verification_key) and/or [`from_script`](#from_script). +pub fn with_delegation_key( + self: Address, + vk: Hash, +) -> Address { + Address { + payment_credential: self.payment_credential, + stake_credential: Some(Inline(VerificationKey(vk))), + } +} + +/// Set (or reset) the delegation part of an [Address](#Address) using a [script](#Script) hash. This is useful when combined with [`from_verification_key`](#from_verification_key) and/or [`from_script`](#from_script). +pub fn with_delegation_script( + self: Address, + script: Hash, +) -> Address { + Address { + payment_credential: self.payment_credential, + stake_credential: Some(Inline(Script(script))), + } +} + +/// Represent a type of object that can be represented either inline (by hash) +/// or via a reference (i.e. a pointer to an on-chain location). +/// +/// This is mainly use for capturing pointers to a stake credential +/// registration certificate in the case of so-called pointer addresses. +pub type Referenced { + Inline(a) + Pointer { slot_number: Int, transaction_index: Int, certificate_index: Int } +} + +/// A `StakeCredential` represents the delegation and rewards withdrawal conditions +/// associated with some stake address / account. +/// +/// A `StakeCredential` is either provided inline, or, by reference using an +/// on-chain pointer. +/// +/// Read more about pointers in [CIP-0019 :: Pointers](https://github.com/cardano-foundation/CIPs/tree/master/CIP-0019/#pointers). +pub type StakeCredential = + Referenced + +/// A 'PaymentCredential' represents the spending conditions associated with +/// some output. Hence, +/// +/// - a `VerificationKey` captures an output locked by a public/private key pair; +/// - and a `Script` captures an output locked by a native or Plutus script. +/// +pub type PaymentCredential = + Credential diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/address/credential.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/address/credential.ak new file mode 100644 index 00000000..2ebeaa91 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/address/credential.ak @@ -0,0 +1,30 @@ +use aiken/primitive/bytearray +use cardano/address.{Credential, Script, VerificationKey} + +pub fn compare(left: Credential, right: Credential) -> Ordering { + when left is { + Script(left) -> + when right is { + Script(right) -> bytearray.compare(left, right) + _ -> Less + } + VerificationKey(left) -> + when right is { + Script(_) -> Greater + VerificationKey(right) -> bytearray.compare(left, right) + } + } +} + +test compare_matrix() { + and { + (compare(Script(""), Script("")) == Equal)?, + (compare(VerificationKey(""), VerificationKey("")) == Equal)?, + (compare(Script(""), VerificationKey("")) == Less)?, + (compare(VerificationKey(""), Script("")) == Greater)?, + (compare(Script("01"), Script("02")) == Less)?, + (compare(Script("02"), Script("01")) == Greater)?, + (compare(VerificationKey("01"), VerificationKey("02")) == Less)?, + (compare(VerificationKey("02"), VerificationKey("01")) == Greater)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/assets.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/assets.ak new file mode 100644 index 00000000..664a3983 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/assets.ak @@ -0,0 +1,920 @@ +use aiken/builtin +use aiken/collection/dict.{Dict, from_ascending_pairs_with} +use aiken/collection/list +use aiken/crypto.{Blake2b_224, Hash, Script} +use aiken/option + +/// Lovelace is now a type wrapper for Int. +pub type Lovelace = + Int + +/// A type-alias for a `PolicyId`. A `PolicyId` is always 28-byte long +pub type PolicyId = + Hash + +/// Ada, the native currency, isn't associated with any `PolicyId` (it's not +/// possible to mint Ada!). +/// +/// By convention, it is an empty `ByteArray`. +pub const ada_policy_id = "" + +/// A type-alias for 'AssetName`, which are free-form byte-arrays between +/// 0 and 32 bytes. +pub type AssetName = + ByteArray + +/// Ada, the native currency, isn't associated with any `AssetName` (it's not +/// possible to mint Ada!). +/// +/// By convention, it is an empty `ByteArray`. +pub const ada_asset_name = "" + +/// A multi-asset output `Value`. Contains tokens indexed by [PolicyId](#PolicyId) and [AssetName](#AssetName). +/// +/// > [!IMPORTANT] +/// > This type maintain some invariants by construction; in particular, a `Value` will never contain a +/// zero quantity of a particular token. +pub opaque type Value { + inner: Dict>, +} + +// ## Constructing + +/// Construct a `Value` from an asset identifier (i.e. `PolicyId` + `AssetName`) +/// and a given quantity. +pub fn from_asset( + policy_id: PolicyId, + asset_name: AssetName, + quantity: Int, +) -> Value { + if quantity == 0 { + zero + } else { + let asset = + dict.empty + |> dict.insert(asset_name, quantity) + dict.empty + |> dict.insert(policy_id, asset) + |> Value + } +} + +/// Promote an arbitrary list of assets into a `Value`. This function fails +/// (i.e. halts the program execution) if: +/// +/// - there's any duplicate amongst `PolicyId`; +/// - there's any duplicate amongst `AssetName`; +/// - the `AssetName` aren't sorted in ascending lexicographic order; or +/// - any asset quantity is null. +/// +/// This function is meant to turn arbitrary user-defined `Data` into safe `Value`, +/// while checking for internal invariants. +pub fn from_asset_list(xs: Pairs>) -> Value { + xs + |> list.foldr( + dict.empty, + fn(inner, acc) { + expect Pair(p, [_, ..] as x) = inner + x + |> from_ascending_pairs_with(fn(v) { v != 0 }) + |> dict.insert_with( + acc, + p, + _, + fn(_, _, _) { + fail @"Duplicate policy in the asset list." + }, + ) + }, + ) + |> Value +} + +test from_asset_list_1() { + let v = from_asset_list([]) + v == zero +} + +test from_asset_list_2() fail { + let v = from_asset_list([Pair(#"33", [])]) + v == zero +} + +test from_asset_list_3() fail { + let v = from_asset_list([Pair(#"33", [Pair(#"", 0)])]) + v != zero +} + +test from_asset_list_4() { + let v = from_asset_list([Pair(#"33", [Pair(#"", 1)])]) + flatten(v) == [(#"33", #"", 1)] +} + +test from_asset_list_5() { + let v = from_asset_list([Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)])]) + flatten(v) == [(#"33", #"", 1), (#"33", #"33", 1)] +} + +test from_asset_list_6() fail { + let v = + from_asset_list( + [ + Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + ], + ) + v != zero +} + +test from_asset_list_7() fail { + let v = + from_asset_list( + [ + Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + Pair(#"34", [Pair(#"", 1), Pair(#"", 1)]), + ], + ) + v != zero +} + +test from_asset_list_8() { + let v = + from_asset_list( + [ + Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + Pair(#"34", [Pair(#"31", 1)]), Pair(#"35", [Pair(#"", 1)]), + ], + ) + flatten(v) == [ + (#"33", #"", 1), (#"33", #"33", 1), (#"34", #"31", 1), (#"35", #"", 1), + ] +} + +test from_asset_list_9() { + let v = + from_asset_list( + [ + Pair(#"35", [Pair(#"", 1)]), Pair(#"33", [Pair(#"", 1), Pair(#"33", 1)]), + Pair(#"34", [Pair(#"31", 1)]), + ], + ) + flatten(v) == [ + (#"33", #"", 1), (#"33", #"33", 1), (#"34", #"31", 1), (#"35", #"", 1), + ] +} + +/// Construct a `Value` from a lovelace quantity. +/// +/// Friendly reminder: 1 Ada = 1.000.000 Lovelace +pub fn from_lovelace(quantity: Int) -> Value { + from_asset(ada_policy_id, ada_asset_name, quantity) +} + +/// Construct an empty `Value` with nothing in it. +pub const zero: Value = Value { inner: dict.empty } + +// ## Inspecting + +/// Check is a `Value` is zero. That is, it has no assets and holds no Ada/Lovelace. +pub fn is_zero(self: Value) -> Bool { + self == zero +} + +/// Efficiently compare two values together, allowing a custom behaviour for Ada/Lovelace. +/// The second parameter is provided as `Data`, allowing to conveniently compare serialized +/// datums or similar structurually equivalent types (such as `Pairs>`). +/// +/// The third argument is a callback function to assert the left and right lovelace +/// quantities. Its first argument refers to the quantity of the first argument of +/// `match`, and the second argument of the callback to the quantity of the second +/// argument of `match`. In the absence of lovelace in any value, it defaults to `0`. +/// +/// ```aiken +/// const value: Value = +/// assets.from_lovelace(30) +/// |> assets.add("foo", "bar", 1) +/// |> assets.add("foo", "baz", 42) +/// +/// const datum: Data = +/// assets.from_lovelace(20) +/// |> assets.add("foo", "bar", 1) +/// |> assets.add("foo", "baz", 42) +/// +/// True == assets.match(value, datum, >=) +/// +/// False == assets.match(value, datum, ==) +/// +/// True == assets.match(value, datum, fn(value_lovelace, datum_lovelace) { +/// 2 * datum_lovelace >= value_lovelace +/// }) +/// ``` +pub fn match( + left: Value, + right: Data, + assert_lovelace: fn(Lovelace, Lovelace) -> Bool, +) -> Bool { + builtin.choose_data( + right, + False, + { + let (left_lovelace, left_assets) = dict.pop(left.inner, ada_policy_id) + let left_assets: Data = left_assets + let left_lovelace = + when left_lovelace is { + Some(tokens) -> builtin.head_list(dict.to_pairs(tokens)).2nd + None -> 0 + } + when builtin.un_map_data(right) is { + [] -> left_assets == right && assert_lovelace(left_lovelace, 0) + [first_asset, ..right_assets] -> + if first_asset.1st == builtin.b_data(ada_policy_id) { + and { + assert_lovelace( + left_lovelace, + builtin.un_i_data( + builtin.head_list(builtin.un_map_data(first_asset.2nd)).2nd, + ), + ), + left_assets == builtin.map_data(right_assets), + } + } else { + and { + assert_lovelace(left_lovelace, 0), + left_assets == right, + } + } + } + }, + False, + False, + False, + ) +} + +const fixture_match_value: Value = + zero + |> add(ada_policy_id, ada_asset_name, 42) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + |> add("bar", "01", 42) + +const fixture_match_data: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + |> add("bar", "01", 42) + +const fixture_match_data_missing_foo_02: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("bar", "01", 42) + +const fixture_match_data_altered_foo_01: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 14) + |> add("foo", "02", 1) + |> add("bar", "01", 42) + +const fixture_match_data_missing_bar: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + +const fixture_match_data_extra_policy: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + |> add("bar", "01", 42) + |> add("baz", "01", 1) + +const fixture_match_data_extra_asset: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + |> add("foo", "01", 1) + |> add("foo", "02", 1) + |> add("foo", "03", 1) + |> add("bar", "01", 42) + +const fixture_match_data_no_assets: Data = + zero + |> add(ada_policy_id, ada_asset_name, 14) + +test match_1() { + match(fixture_match_value, fixture_match_data, fn(_, _) { True }) +} + +test match_2() { + !match( + fixture_match_value, + fixture_match_data, + fn(source, target) { source == target }, + ) +} + +test match_3() { + !match( + fixture_match_value, + fixture_match_data_missing_foo_02, + fn(_, _) { True }, + ) +} + +test match_4() { + !match(fixture_match_value, fixture_match_data_missing_bar, fn(_, _) { True }) +} + +test match_5() { + !match( + fixture_match_value, + fixture_match_data_altered_foo_01, + fn(_, _) { True }, + ) +} + +test match_6() { + !match( + fixture_match_value, + fixture_match_data_extra_policy, + fn(_, _) { True }, + ) +} + +test match_7() { + !match(fixture_match_value, fixture_match_data_extra_asset, fn(_, _) { True }) +} + +test match_8() { + !match(fixture_match_value, fixture_match_data_no_assets, fn(_, _) { True }) +} + +test match_9() { + match(zero, zero, ==) +} + +test match_10() { + match( + without_lovelace(fixture_match_value), + without_lovelace(fixture_match_value), + fn(left, right) { left == 0 && right == 0 }, + ) +} + +test match_11() { + match( + without_lovelace(fixture_match_value), + fixture_match_value, + fn(left, right) { left == 0 && right > 0 }, + ) +} + +test match_12() { + match( + fixture_match_value, + without_lovelace(fixture_match_value), + fn(left, right) { left > 0 && right == 0 }, + ) +} + +test match_13() { + match( + zero |> add(ada_policy_id, ada_asset_name, 42), + zero, + fn(left, right) { left == 42 && right == 0 }, + ) +} + +test match_14() { + match( + zero, + zero |> add(ada_policy_id, ada_asset_name, 42), + fn(left, right) { left == 0 && right == 42 }, + ) +} + +const fixture_match_benchmark_left: Value = + zero + |> add(ada_policy_id, ada_asset_name, 1337) + |> add( + #"0246a14d04c3a0e9b65f6b90a3d1aa5faee5d56ab1e30ec7e8b02f29", + "MATTR", + 200, + ) + |> add( + #"0a9e126256cb38c4865cdac6eb2ada51c328ba0df2ebde22ae126c0d", + "ProphecyPoster076", + 1, + ) + |> add( + #"1774343241680e4daef7cbfe3536fc857ce23fb66cd0b66320b2e3dd", + "BISON", + 12_004_999_999, + ) + |> add( + #"279c909f348e533da5808898f87f9a14bb2c3dfbbacccd631d927a3f", + "SNEK", + 1486, + ) + |> add( + #"651dfc074202423585996ffa717cb45237d307e705e2cc3dab1ccabd", + "MAYZSilverFoundersEdition0035", + 1, + ) + |> add( + #"63df49056617dd14034986cf7c250bad6552fd2f0f9c71d797932008", + "CardanoSpaceSession", + 20, + ) + |> add( + #"5b01968867e13432afaa2f814e1d15e332d6cd0aa77e350972b0967d", + "ADAOGovernanceToken", + 1, + ) + |> add( + #"a0028f350aaabe0545fdcb56b039bfb08e4bb4d8c4d7c3c7d481c235", + "HOSKY", + 400_001_000, + ) + |> add( + #"da8c30857834c6ae7203935b89278c532b3995245295456f993e1d24", + "LQ", + 10_635_899, + ) + |> add( + #"95d9a98c2f7999a3d5e0f4d795cb1333837c09eb0f24835cd2ce954c", + "GrandmasterAdventurer659", + 1, + ) + |> add( + #"702cbdb06a81ef2fa4f85f9e32159c03f502539d762a71194fc11eb3", + "AdventurerOfThiolden8105", + 1, + ) + |> add( + #"d0112837f8f856b2ca14f69b375bc394e73d146fdadcc993bb993779", + "DiscoSolaris3725", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld535", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld1213", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld1518", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld1537", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld4199", + 1, + ) + |> add( + #"8dd5717e7d4d993019dbd788c19837910e3fcf647ab282f828c80a7a", + "CardaWorld3767", + 1, + ) + |> add( + #"7597444754551a8c17edbf7291cdaeca898ca02ee4e732b09a949396", + "Algae1", + 1, + ) + |> add( + #"7597444754551a8c17edbf7291cdaeca898ca02ee4e732b09a949396", + "Algae2", + 1, + ) + +const fixture_match_benchmark_right: Data = fixture_match_benchmark_left + +test match_benchmark() { + match(fixture_match_benchmark_left, fixture_match_benchmark_right, ==) +} + +test match_benchmark_vs() { + let data: Data = fixture_match_benchmark_right + expect pairs: Pairs> = data + fixture_match_benchmark_left == from_asset_list(pairs) +} + +/// A specialized version of `quantity_of` for the Ada currency. +pub fn lovelace_of(self: Value) -> Int { + quantity_of(self, ada_policy_id, ada_asset_name) +} + +/// A list of all token policies in that Value with non-zero tokens. +pub fn policies(self: Value) -> List { + dict.keys(self.inner) +} + +/// Extract the quantity of a given asset. +pub fn quantity_of( + self: Value, + policy_id: PolicyId, + asset_name: AssetName, +) -> Int { + self.inner + |> dict.get(policy_id) + |> option.and_then(dict.get(_, asset_name)) + |> option.or_else(0) +} + +/// Get all tokens associated with a given policy. +pub fn tokens(self: Value, policy_id: PolicyId) -> Dict { + self.inner + |> dict.get(policy_id) + |> option.or_else(dict.empty) +} + +// ## Combining + +/// Add a (positive or negative) quantity of a single token to a assets. +/// This is more efficient than [`merge`](#merge) for a single asset. +pub fn add( + self: Value, + policy_id: PolicyId, + asset_name: AssetName, + quantity: Int, +) -> Value { + if quantity == 0 { + self + } else { + let helper = + fn(_, left, _right) { + let inner_result = + dict.insert_with( + left, + asset_name, + quantity, + fn(_k, ql, qr) { + let q = ql + qr + if q == 0 { + None + } else { + Some(q) + } + }, + ) + if dict.is_empty(inner_result) { + None + } else { + Some(inner_result) + } + } + + Value( + dict.insert_with( + self.inner, + policy_id, + dict.from_ascending_pairs([Pair(asset_name, quantity)]), + helper, + ), + ) + } +} + +test add_1() { + let v = + zero + |> add(#"acab", #"beef", 321) + |> add(#"acab", #"beef", -321) + v == zero +} + +test add_2() { + let v = + from_lovelace(123) + |> add(#"acab", #"beef", 321) + |> add(#"acab", #"beef", -1 * 321) + v == from_lovelace(123) +} + +test add_3() { + let v = + from_lovelace(1) + |> add(ada_policy_id, ada_asset_name, 2) + |> add(ada_policy_id, ada_asset_name, 3) + v == from_lovelace(6) +} + +test add_4() { + let v = + zero + |> add(#"acab", #"beef", 0) + v == zero +} + +test add_5() { + let v = + zero + |> add(#"acab", #"beef", 0) + |> add(#"acab", #"beef", 0) + v == zero +} + +/// Combine two `Value` together. +pub fn merge(left v0: Value, right v1: Value) -> Value { + Value( + dict.union_with( + v0.inner, + v1.inner, + fn(_, a0, a1) { + let result = + dict.union_with( + a0, + a1, + fn(_, q0, q1) { + let q = q0 + q1 + if q == 0 { + None + } else { + Some(q) + } + }, + ) + if dict.is_empty(result) { + None + } else { + Some(result) + } + }, + ), + ) +} + +test merge_1() { + let v1 = from_lovelace(1) + let v2 = from_lovelace(-1) + merge(v1, v2) == zero +} + +test merge_2() { + let v1 = from_asset(#"00", #"", 1) + let v2 = from_asset(#"01", #"", 2) + let v3 = from_asset(#"02", #"", 3) + let v = + from_lovelace(42) + |> merge(v3) + |> merge(v1) + |> merge(v2) + + flatten(v) == [ + (#"", #"", 42), (#"00", #"", 1), (#"01", #"", 2), (#"02", #"", 3), + ] +} + +test merge_3() { + let v1 = from_asset(#"00", #"", 1) + let v2 = from_asset(#"00", #"", -1) + let v3 = from_asset(#"01", #"", 1) + + let v = + zero + |> merge(v1) + |> merge(v2) + |> merge(v3) + + flatten(v) == [(#"01", #"", 1)] +} + +test merge_4() { + let v1 = from_asset(#"00", #"", 1) + let v2 = from_asset(#"00", #"", -1) + + merge(v1, v2) == zero +} + +test merge_5() { + let v = + zero + |> add(#"acab", #"beef", 0) + + merge(zero, v) == zero +} + +/// Negates quantities of all tokens (including Ada) in that `Value`. +/// +/// ``` +/// v1 +/// |> assets.negate +/// |> assets.merge(v1) +/// |> assets.is_zero +/// // True +/// ``` +pub fn negate(self: Value) -> Value { + dict.map(self.inner, fn(_, a) { dict.map(a, fn(_, q) { 0 - q }) }) + |> Value +} + +/// Get a subset of the assets restricted to the given policies. +pub fn restricted_to(self: Value, mask: List) -> Value { + list.foldr( + policies(self), + zero, + fn(policy_id, value) { + if list.has(mask, policy_id) { + dict.foldr( + tokens(self, policy_id), + value, + fn(asset_name, quantity, value) { + add(value, policy_id, asset_name, quantity) + }, + ) + } else { + value + } + }, + ) +} + +test restricted_to_1() { + let self = from_lovelace(42) |> add("foo", "", 1) + restricted_to(self, []) == zero +} + +test restricted_to_2() { + let self = from_lovelace(42) |> add("foo", "", 1) + restricted_to(self, [ada_policy_id]) == from_lovelace(42) +} + +test restricted_to_3() { + let self = from_lovelace(42) |> add("foo", "", 1) |> add("bar", "", 1) + restricted_to(self, ["foo", "bar"]) == without_lovelace(self) +} + +test restricted_to_4() { + let self = from_lovelace(42) |> add("foo", "bar", 1) |> add("foo", "baz", 1) + restricted_to(self, ["foo"]) == without_lovelace(self) +} + +test restricted_to_5() { + let self = from_lovelace(42) |> add("foo", "bar", 1) |> add("foo", "baz", 1) + restricted_to(self, [ada_policy_id, "foo"]) == self +} + +/// Get a `Value` excluding Ada. +pub fn without_lovelace(self: Value) -> Value { + dict.delete(self.inner, ada_policy_id) + |> Value +} + +test without_lovelace_1() { + let v = from_lovelace(1000000) + without_lovelace(v) == zero +} + +test without_lovelace_2() { + let v = from_lovelace(1000000) + let v2 = from_lovelace(50000000) + without_lovelace(v) == without_lovelace(v2) +} + +test without_lovelace_3() { + let v = + from_asset(#"010203", #"040506", 100) + |> add(ada_policy_id, ada_asset_name, 100000000) + let v2 = from_asset(#"010203", #"040506", 100) + without_lovelace(v) == without_lovelace(v2) && without_lovelace(v) == v2 +} + +// ## Transforming + +/// Flatten a `Value` as list of 3-tuple `(PolicyId, AssetName, Quantity)`. +/// +/// Handy to manipulate values as uniform lists. +pub fn flatten(self: Value) -> List<(PolicyId, AssetName, Int)> { + dict.foldr( + self.inner, + [], + fn(policy_id, asset_list, value) { + dict.foldr( + asset_list, + value, + fn(asset_name, quantity, xs) { + [(policy_id, asset_name, quantity), ..xs] + }, + ) + }, + ) +} + +/// Flatten a `Value` as a list of results, possibly discarding some along the way. +/// +/// When the transform function returns `None`, the result is discarded altogether. +pub fn flatten_with( + self: Value, + with: fn(PolicyId, AssetName, Int) -> Option, +) -> List { + dict.foldr( + self.inner, + [], + fn(policy_id, asset_list, value) { + dict.foldr( + asset_list, + value, + fn(asset_name, quantity, xs) { + when with(policy_id, asset_name, quantity) is { + None -> xs + Some(x) -> [x, ..xs] + } + }, + ) + }, + ) +} + +test flatten_with_1() { + flatten_with(zero, fn(p, a, q) { Some((p, a, q)) }) == [] +} + +test flatten_with_2() { + let v = + zero + |> add("a", "1", 14) + |> add("b", "", 42) + |> add("a", "2", 42) + + flatten_with( + v, + fn(p, a, q) { + if q == 42 { + Some((p, a)) + } else { + None + } + }, + ) == [("a", "2"), ("b", "")] +} + +/// Reduce a value into a single result +/// +/// ``` +/// assets.zero +/// |> assets.add("a", "1", 10) +/// |> assets.add("b", "2", 20) +/// |> assets.reduce(v, 0, fn(_, _, quantity, acc) { acc + quantity }) +/// // 30 +/// ``` +pub fn reduce( + self: Value, + start: result, + with: fn(PolicyId, AssetName, Int, result) -> result, +) -> result { + dict.foldr( + self.inner, + start, + fn(policy_id, asset_list, result) { + dict.foldr(asset_list, result, with(policy_id, _, _, _)) + }, + ) +} + +test reduce_1() { + let v = + zero + |> add("a", "1", 10) + |> add("b", "2", 20) + let result = reduce(v, 0, fn(_, _, quantity, acc) { acc + quantity }) + result == 30 +} + +test reduce_2() { + let v = + zero + |> add("a", "1", 5) + |> add("a", "2", 15) + |> add("b", "", 10) + let result = + reduce( + v, + [], + fn(policy_id, asset_name, _, acc) { [(policy_id, asset_name), ..acc] }, + ) + result == [("a", "1"), ("a", "2"), ("b", "")] +} + +test reduce_3() { + let v = zero + let result = reduce(v, 1, fn(_, _, quantity, acc) { acc + quantity }) + result == 1 +} + +/// Convert the value into a dictionary of dictionaries. +pub fn to_dict(self: Value) -> Dict> { + self.inner +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/certificate.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/certificate.ak new file mode 100644 index 00000000..f0b6d258 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/certificate.ak @@ -0,0 +1,93 @@ +use aiken/crypto.{Blake2b_224, Hash, VerificationKey, VerificationKeyHash} +use cardano/address.{Credential} +use cardano/assets.{Lovelace} + +pub type StakePoolId = + Hash + +/// An on-chain certificate attesting of some operation. Publishing +/// certificates triggers different kind of rules; most of the time, +/// they require signatures from specific keys. +pub type Certificate { + /// Register a stake credential with an optional deposit amount. + /// The deposit is always present when using the new registration certificate + /// format available since the Conway era. + RegisterCredential { + credential: Credential, + /// > [!NOTE] + /// > The `deposit` ought to be an `Option`, but due to unfortunate + /// > circumstances it will always be instantiated to `None` even when set in + /// > the host transaction. This is what the `Never` type captures here. + deposit: Never, + } + /// Un-Register a stake credential with an optional refund amount + /// The deposit is always present when using the new de-registration certificate + /// format available since the Conway era. + UnregisterCredential { + credential: Credential, + /// > [!NOTE] + /// > The `refund` ought to be an `Option`, but due to unfortunate + /// > circumstances it will always be instantiated to `None` even when set in + /// > the host transaction. This is what the `Never` type captures here. + refund: Never, + } + /// Delegate stake to a [Delegate](#Delegate). + DelegateCredential { credential: Credential, delegate: Delegate } + /// Register and delegate staking credential to a Delegatee in one certificate. + RegisterAndDelegateCredential { + credential: Credential, + delegate: Delegate, + deposit: Lovelace, + } + /// Register a delegate representative (a.k.a DRep). The deposit is explicit and + /// is refunded when the delegate steps down (unregister). + RegisterDelegateRepresentative { + delegate_representative: Credential, + deposit: Lovelace, + } + /// Update a delegate representative (a.k.a DRep). The certificate also contains + /// metadata which aren't visible on-chain. + UpdateDelegateRepresentative { delegate_representative: Credential } + /// UnRegister a delegate representative, and refund back its past deposit. + UnregisterDelegateRepresentative { + delegate_representative: Credential, + refund: Lovelace, + } + /// Register a new stake pool + RegisterStakePool { + /// The hash digest of the stake pool's cold (public) key + stake_pool: StakePoolId, + /// The hash digest of the stake pool's VRF (public) key + vrf: VerificationKeyHash, + } + /// Retire a stake pool. 'at_epoch' indicates in which the retirement will take place + RetireStakePool { stake_pool: StakePoolId, at_epoch: Int } + /// Authorize a Hot credential for a specific Committee member's cold credential + AuthorizeConstitutionalCommitteeProxy { + constitutional_committee_member: Credential, + proxy: Credential, + } + /// Step down from the constitutional committee as a member. + RetireFromConstitutionalCommittee { + constitutional_committee_member: Credential, + } +} + +/// A type of stake delegation that can be either block-production, vote or +/// both. Note that delegation types aren't cancelling one another, so it is +/// possible to delegate block production in one transaction, and delegate vote +/// in another. This second delegation **does NOT** invalidate the first one. +pub type Delegate { + DelegateBlockProduction { stake_pool: StakePoolId } + DelegateVote { delegate_representative: DelegateRepresentative } + DelegateBoth { + stake_pool: StakePoolId, + delegate_representative: DelegateRepresentative, + } +} + +pub type DelegateRepresentative { + Registered(Credential) + AlwaysAbstain + AlwaysNoConfidence +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/governance.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/governance.ak new file mode 100644 index 00000000..3ec96800 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/governance.ak @@ -0,0 +1,109 @@ +use aiken/collection.{Index} +use aiken/crypto.{Blake2b_256, Hash, ScriptHash, VerificationKeyHash} +use aiken/math/rational.{Rational} +use cardano/address.{Credential} +use cardano/assets.{Lovelace} +use cardano/governance/protocol_parameters.{ProtocolParametersUpdate} + +pub type ProposalProcedure { + deposit: Lovelace, + return_address: Credential, + governance_action: GovernanceAction, +} + +pub type GovernanceAction { + ProtocolParameters { + /// The last governance action of type 'ProtocolParameters'. They must all + /// form a chain. + ancestor: Option, + /// The new proposed protocol parameters. Only values set to `Some` are relevant. + new_parameters: ProtocolParametersUpdate, + /// The optional guardrails script defined in the constitution. The script + /// is executed by the ledger in addition to the hard-coded ledger rules. + /// + /// It must pass for the new protocol parameters to be deemed valid. + guardrails: Option, + } + HardFork { + /// The last governance action of type `HardFork`. They must all + /// form a chain. + ancestor: Option, + /// The new proposed version. Few rules apply to proposing new versions: + /// + /// - The `major` component, if incremented, must be exactly one more than the current. + /// - The `minor` component, if incremented, must be exactly one more than the current. + /// - If the `major` component is incremented, `minor` must be set to `0`. + /// - Neither `minor` nor `major` can be decremented. + new_version: ProtocolVersion, + } + TreasuryWithdrawal { + /// A collection of beneficiaries, which can be plain verification key + /// hashes or script hashes (e.g. DAO). + beneficiaries: Pairs, + /// The optional guardrails script defined in the constitution. The script + /// is executed by the ledger in addition to the hard-coded ledger rules. + /// + /// It must pass for the withdrawals to be authorized. + guardrails: Option, + } + NoConfidence { + /// The last governance action of type `NoConfidence` or + /// `ConstitutionalCommittee`. They must all / form a chain. + ancestor: Option, + } + ConstitutionalCommittee { + /// The last governance action of type `NoConfidence` or + /// `ConstitutionalCommittee`. They must all / form a chain. + ancestor: Option, + /// Constitutional members to be removed. + evicted_members: List, + /// Constitutional members to be added. + added_members: Pairs, + /// The new quorum value, as a ratio of a numerator and a denominator. The + /// quorum specifies the threshold of 'Yes' votes necessary for the + /// constitutional committee to accept a proposal procedure. + quorum: Rational, + } + NewConstitution { + /// The last governance action of type `Constitution` or + /// `ConstitutionalCommittee`. They must all / form a chain. + ancestor: Option, + /// The new proposed constitution. + constitution: Constitution, + } + NicePoll +} + +pub type Vote { + No + Yes + Abstain +} + +pub type TransactionId = + Hash + +pub type GovernanceActionId { + transaction: TransactionId, + proposal_procedure: Index, +} + +pub type ProtocolVersion { + major: Int, + minor: Int, +} + +pub type Constitution { + guardrails: Option, +} + +/// An epoch number after which constitutional committee member +/// mandate expires. +pub type Mandate = + Int + +pub type Voter { + ConstitutionalCommitteeMember(Credential) + DelegateRepresentative(Credential) + StakePool(VerificationKeyHash) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/governance/protocol_parameters.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/governance/protocol_parameters.ak new file mode 100644 index 00000000..d9e7be95 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/governance/protocol_parameters.ak @@ -0,0 +1,360 @@ +use aiken/math/rational.{Rational} +use cardano/assets.{Lovelace} + +pub opaque type ProtocolParametersUpdate { + inner: Pairs, +} + +pub type ScriptExecutionPrices { + memory: Rational, + cpu: Rational, +} + +pub type ExecutionUnits { + memory: Int, + cpu: Int, +} + +pub type StakePoolOperatorVotingThresholds { + motion_of_no_confidence: Rational, + constitutional_committee: ConstitutionalCommitteeThresholds, + hard_fork: Rational, + protocol_parameters: ProtocolParametersThresholds< + Rational, + Void, + Void, + Void, + Void, + >, +} + +pub type DelegateRepresentativeVotingThresholds { + motion_of_no_confidence: Rational, + constitutional_committee: ConstitutionalCommitteeThresholds, + constitution: Rational, + hard_fork: Rational, + protocol_parameters: ProtocolParametersThresholds< + Void, + Rational, + Rational, + Rational, + Rational, + >, + treasury_withdrawal: Rational, +} + +pub type ProtocolParametersThresholds< + security, + network, + economic, + technical, + governance, +> { + security_group: security, + network_group: network, + economic_group: economic, + technical_group: technical, + governance_group: governance, +} + +pub type ConstitutionalCommitteeThresholds { + default: Rational, + under_no_confidence: Rational, +} + +/// The linear coefficient that intervenes in the transaction fee calculation. +/// It is multiplied by the size of the transaction in bytes to obtain a Lovelace value. +pub fn min_fee_coefficient(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 0, into_int) +} + +/// The constant factor that intervenes in the transaction fee calculation. It is +/// a flat cost of lovelace that is added to every fee calculation. +pub fn min_fee_constant(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 1, into_int) +} + +/// The maximum size of a serialized block body, expressed in bytes. +pub fn max_block_body_size(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 2, into_int) +} + +/// The maximum size of a serialized transaction (body + witnesses), expressed in bytes. +pub fn max_transaction_size(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 3, into_int) +} + +/// The maximum size of a serialized block header, expressed in bytes. +pub fn max_block_header_size(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 4, into_int) +} + +/// The required deposit amount when registering stake credentials, expressed in Lovelace. +pub fn stake_credential_deposit( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 5, into_int) +} + +/// The required deposit amount when registering a stake pool, expressed in Lovelace. +pub fn stake_pool_deposit(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 6, into_int) +} + +/// The maximum number of epoch in the future allowed for a stake pool retirement to be scheduled. +pub fn stake_pool_retirement_horizon( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 7, into_int) +} + +/// The desired/optimal number of fully saturated stake pools in the system. Also known as the _'k-parameter'_. +pub fn desired_number_of_stake_pools( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 8, into_int) +} + +/// A parameter controlling the influence of an pool owner's pledge on the rewards. Also known as _'a0'_. +pub fn stake_pool_pledge_influence( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 9, into_rational) +} + +/// The monetary expansion parameter, controlling the fraction of Ada put in circulation on every epoch through the incentivies model. Also known as _'ρ'_. +pub fn monetary_expansion(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 10, into_rational) +} + +/// The parameter controlling what fraction (%) of available rewards is sent to the treasury on every epoch. Also known as _'τ'_. +pub fn treasury_expansion(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 11, into_rational) +} + +/// Minimum authorized constant cost that stake pools can declare when registering, expressed in Lovelace. +pub fn min_stake_pool_cost(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 16, into_int) +} + +/// The linear coefficient that intervenes in the calculation of the minimum Ada value that any UTxO must hold. It is expressed in Lovelace per Byte, and is also known as the 'coins per utxo byte' parameter. +pub fn min_utxo_deposit_coefficient( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 17, into_int) +} + +/// The costs associated with the various operations of the Plutus Virtual Machine, which can be different for each Plutus version. +pub fn cost_models(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 18, identity) +} + +/// The price, in Lovelace per unit, of the execution units corresponding to cpu and memory usage of on-chain scripts. +pub fn script_execution_prices( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 19, into_script_execution_prices) +} + +/// The maximum execution units allowed for a single transaction. +pub fn max_transaction_execution_units( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 20, into_execution_units) +} + +/// The maximum execution units allowed for a single block. +pub fn max_block_execution_units( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 21, into_execution_units) +} + +/// The maximum size of a serialized value in a transaction output. This effectively limits +/// the maximum kinds of assets that can be sent in a single output. It is expressed in bytes. +pub fn max_value_size(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 22, into_int) +} + +/// The scaling factor applied to the transaction cost for defining the minimum collateral +/// amount. It is expressed in percent points (so 100 = 100%). +pub fn collateral_percentage(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 23, into_int) +} + +/// The maximum number of collateral inputs allowed in the transaction. +pub fn max_collateral_inputs(self: ProtocolParametersUpdate) -> Option { + get_protocol_param(self.inner, 24, into_int) +} + +/// The various governance voting thresholds pertaining to stake pool operators. +pub fn stake_pool_operator_voting_thresholds( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 25, into_spo_voting_thresholds) +} + +/// The various governance voting thresholds pertaining to delegate representatives +/// (a.k.a DReps). +pub fn delegate_representative_voting_thresholds( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 26, into_drep_voting_thresholds) +} + +/// The minimum number of members in the constitutional committee. Any updates of the committee +/// must leave at least this number of members. +pub fn min_constitutional_committee_size( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 27, into_int) +} + +/// The maximum length of a constitutional committee member, expressed in number of epochs. +pub fn max_constitutional_committee_mandate( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 28, into_int) +} + +/// The lifetime of any governance proposal. An action that hasn't been approved beyond that +/// period is considered inactive and discarded. It is expressed in number of epochs. +pub fn governance_proposal_lifetime( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 29, into_int) +} + +/// The required deposit amount for governance proposal procedures, expressed in Lovelace. +pub fn governance_proposal_deposit( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 30, into_int) +} + +/// The required deposit amount when registering as a delegate representative, expressed in +/// Lovelace. +pub fn delegate_representative_deposit( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 31, into_int) +} + +/// The maximum number of epochs that a delegate representative can stay inactive (i.e. no +/// voting) without becoming _inactive_ and removed from thresholds calculations. +pub fn delegate_representative_max_idle_time( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 32, into_int) +} + +/// The base tier fee coefficient for reference scripts. Reference scripts gets increasingly +/// more expensives every ~24KB, the base coefficient is a multiplicating factor which grows +/// exponentially with each tier. +pub fn reference_scripts_tier_fee_initial_factor( + self: ProtocolParametersUpdate, +) -> Option { + get_protocol_param(self.inner, 33, into_rational) +} + +// Internals ------------------------------------------------------------------- + +type ProtocolParametersIndex = + Int + +fn get_protocol_param( + self: Pairs, + ix: ProtocolParametersIndex, + into: fn(Data) -> a, +) -> Option { + when self is { + [] -> None + [Pair(jx, param), ..tail] -> + if ix == jx { + Some(into(param)) + } else { + get_protocol_param(tail, ix, into) + } + } +} + +fn into_int(param: Data) -> Int { + expect param: Int = param + param +} + +fn into_rational(param: Data) -> Rational { + expect [numerator, denominator]: List = param + expect Some(r) = rational.new(numerator, denominator) + r +} + +fn into_execution_units(param: Data) -> ExecutionUnits { + expect [memory, cpu]: List = param + ExecutionUnits { memory, cpu } +} + +fn into_script_execution_prices(param: Data) -> ScriptExecutionPrices { + expect [memory, cpu]: List = param + let memory = into_rational(memory) + let cpu = into_rational(cpu) + ScriptExecutionPrices { memory, cpu } +} + +fn into_spo_voting_thresholds(param: Data) -> StakePoolOperatorVotingThresholds { + expect [ + motion_of_no_confidence, constitutional_committee, + constitutional_committee_under_no_confidence, hard_fork, + protocol_parameters_security_group, + ]: List = param + + StakePoolOperatorVotingThresholds { + motion_of_no_confidence: into_rational(motion_of_no_confidence), + constitutional_committee: ConstitutionalCommitteeThresholds { + default: into_rational(constitutional_committee), + under_no_confidence: into_rational( + constitutional_committee_under_no_confidence, + ), + }, + hard_fork: into_rational(hard_fork), + protocol_parameters: ProtocolParametersThresholds { + security_group: into_rational(protocol_parameters_security_group), + network_group: Void, + economic_group: Void, + technical_group: Void, + governance_group: Void, + }, + } +} + +fn into_drep_voting_thresholds( + param: Data, +) -> DelegateRepresentativeVotingThresholds { + expect [ + motion_of_no_confidence, constitutional_committee, + constitutional_committee_under_no_confidence, constitution, hard_fork, + protocol_parameters_network_group, protocol_parameters_economic_group, + protocol_parameters_technical_group, protocol_parameters_governance_group, + treasury_withdrawal, + ]: List = param + + DelegateRepresentativeVotingThresholds { + motion_of_no_confidence: into_rational(motion_of_no_confidence), + constitutional_committee: ConstitutionalCommitteeThresholds { + default: into_rational(constitutional_committee), + under_no_confidence: into_rational( + constitutional_committee_under_no_confidence, + ), + }, + constitution: into_rational(constitution), + hard_fork: into_rational(hard_fork), + protocol_parameters: ProtocolParametersThresholds { + security_group: Void, + network_group: into_rational(protocol_parameters_network_group), + economic_group: into_rational(protocol_parameters_economic_group), + technical_group: into_rational(protocol_parameters_technical_group), + governance_group: into_rational(protocol_parameters_governance_group), + }, + treasury_withdrawal: into_rational(treasury_withdrawal), + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/governance/voter.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/governance/voter.ak new file mode 100644 index 00000000..e723e2d5 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/governance/voter.ak @@ -0,0 +1,62 @@ +use aiken/primitive/bytearray +use cardano/address.{Script} +use cardano/address/credential +use cardano/governance.{ + ConstitutionalCommitteeMember, DelegateRepresentative, StakePool, Voter, +} + +pub fn compare(left: Voter, right: Voter) -> Ordering { + when left is { + ConstitutionalCommitteeMember(left) -> + when right is { + ConstitutionalCommitteeMember(right) -> credential.compare(left, right) + _ -> Less + } + DelegateRepresentative(left) -> + when right is { + DelegateRepresentative(right) -> credential.compare(left, right) + ConstitutionalCommitteeMember(_) -> Greater + _ -> Less + } + StakePool(left) -> + when right is { + StakePool(right) -> bytearray.compare(left, right) + _ -> Greater + } + } +} + +test compare_matrix() { + let cc0 = ConstitutionalCommitteeMember(Script("0")) + let cc1 = ConstitutionalCommitteeMember(Script("1")) + + let drep0 = DelegateRepresentative(Script("0")) + let drep1 = DelegateRepresentative(Script("1")) + + let spo0 = StakePool("0") + let spo1 = StakePool("1") + + and { + (compare(cc0, cc0) == Equal)?, + (compare(cc0, cc1) == Less)?, + (compare(cc1, cc0) == Greater)?, + (compare(drep0, drep0) == Equal)?, + (compare(drep0, drep1) == Less)?, + (compare(drep1, drep0) == Greater)?, + (compare(spo0, spo0) == Equal)?, + (compare(spo0, spo1) == Less)?, + (compare(spo1, spo0) == Greater)?, + (compare(cc0, drep0) == Less)?, + (compare(cc0, drep1) == Less)?, + (compare(cc0, spo0) == Less)?, + (compare(cc0, spo1) == Less)?, + (compare(drep0, cc0) == Greater)?, + (compare(drep0, cc1) == Greater)?, + (compare(drep0, spo0) == Less)?, + (compare(drep0, spo1) == Less)?, + (compare(spo0, cc0) == Greater)?, + (compare(spo0, cc1) == Greater)?, + (compare(spo0, drep0) == Greater)?, + (compare(spo0, drep1) == Greater)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/script_context.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/script_context.ak new file mode 100644 index 00000000..ff73836a --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/script_context.ak @@ -0,0 +1,62 @@ +//// This module contains utilities for manually dealing with [`ScriptContext`](#ScriptContext). This is only ever useful for writing custom `else` handlers in validators. +//// +//// > [!NOTE] +//// > Unless you know what you're doing, you should prefer using named handlers: +//// > +//// > - `mint` +//// > - `spend` +//// > - `withdraw` +//// > - `publish` +//// > - `vote` +//// > - `propose` + +use aiken/collection.{Index} +use cardano/address.{Credential} +use cardano/assets.{PolicyId} +use cardano/certificate.{Certificate} +use cardano/governance.{ProposalProcedure, Voter} +use cardano/transaction.{OutputReference, Redeemer, Transaction} + +/// A context given to a script by the Cardano ledger when being executed. +/// +/// The context contains information about the entire transaction that contains +/// the script. The transaction may also contain other scripts; to distinguish +/// between multiple scripts, the [`ScriptContext`](#ScriptContext) contains a +/// [`ScriptInfo`](#ScriptInfo) which indicates which script (or, for what +/// purpose) the transaction is being executed. +pub type ScriptContext { + transaction: Transaction, + redeemer: Redeemer, + info: ScriptInfo, +} + +/// Characterizes the script information. The main (and only) difference with [`ScriptPurpose`](./transaction.html#ScriptPurpose) resides in the `Spending` variant which here contains a second field `datum: Option`. +pub type ScriptInfo { + /// For scripts executed as minting/burning policies, to insert + /// or remove assets from circulation. It's parameterized by the identifier + /// of the associated policy. + Minting(PolicyId) + /// For scripts that are used as payment credentials for addresses in + /// transaction outputs. They govern the rule by which the output they + /// reference can be spent. + Spending { output: OutputReference, datum: Option } + /// For scripts that validate reward withdrawals from a reward account. + /// + /// The argument identifies the target reward account. + Withdrawing(Credential) + /// Needed when delegating to a pool using stake credentials defined as a + /// custom script. This purpose is also triggered when de-registering such + /// stake credentials. + /// + /// The Int is a 0-based index of the given `Certificate` in `certificates`. + Publishing { at: Index, certificate: Certificate } + /// Voting for a type of voter using a governance action id to vote + /// yes / no / abstain inside a transaction. + /// + /// The voter is who is doing the governance action. + Voting(Voter) + /// Used to propose a governance action. + /// + /// A 0-based index of the given `ProposalProcedure` in `proposal_procedures`. + Proposing { at: Index, proposal_procedure: ProposalProcedure } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/transaction.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/transaction.ak new file mode 100644 index 00000000..6511a596 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/transaction.ak @@ -0,0 +1,225 @@ +use aiken/builtin +use aiken/collection.{Index} +use aiken/collection/dict.{Dict} +use aiken/collection/list +use aiken/crypto.{ + Blake2b_256, DataHash, Hash, ScriptHash, VerificationKeyHash, blake2b_256, +} +use aiken/interval.{Interval} +use aiken/option +use cardano/address.{Address, Credential, Script, VerificationKey} +use cardano/assets.{Lovelace, PolicyId, Value} +use cardano/certificate.{Certificate} +use cardano/governance.{GovernanceActionId, ProposalProcedure, Vote, Voter} + +pub type TransactionId = + Hash + +/// Characterizes the script purpose. +pub type ScriptPurpose { + /// For scripts executed as minting/burning policies, to insert + /// or remove assets from circulation. It's parameterized by the identifier + /// of the associated policy. + Mint(PolicyId) + /// For scripts that are used as payment credentials for addresses in + /// transaction outputs. They govern the rule by which the output they + /// reference can be spent. + Spend(OutputReference) + /// For scripts that validate reward withdrawals from a reward account. + /// + /// The argument identifies the target reward account. + Withdraw(Credential) + /// Needed when delegating to a pool using stake credentials defined as a + /// custom script. This purpose is also triggered when de-registering such + /// stake credentials. + /// + /// The Int is a 0-based index of the given `Certificate` in `certificates`. + Publish { at: Index, certificate: Certificate } + /// Voting for a type of voter using a governance action id to vote + /// yes / no / abstain inside a transaction. + /// + /// The voter is who is doing the governance action. + Vote(Voter) + /// Used to propose a governance action. + /// + /// A 0-based index of the given `ProposalProcedure` in `proposal_procedures`. + Propose { at: Index, proposal_procedure: ProposalProcedure } +} + +/// A Cardano `Transaction`, as seen by on-chain scripts. +/// +/// Note that this is a representation of a transaction, and not the 1:1 +/// translation of the transaction as seen by the ledger. In particular, +/// on-chain scripts can't see inputs locked by bootstrap addresses, outputs +/// to bootstrap addresses or just transaction metadata. +pub type Transaction { + inputs: List, + reference_inputs: List, + outputs: List, + fee: Lovelace, + mint: Value, + certificates: List, + /// > [!IMPORTANT] + /// > Withdrawals are ordered by ascending [Credential](./credential.html#Credential). Yet, note that [`Script`](./credential.html#Credential) credentials are treated as **lower values** than [`VerificationKey`](./credential.html#Credential) credentials. + withdrawals: Pairs, + validity_range: ValidityRange, + extra_signatories: List, + /// > [!IMPORTANT] + /// > Redeemers are ordered by ascending [ScriptPurpose](./transaction.html#ScriptPurpose). + redeemers: Pairs, + datums: Dict, + id: TransactionId, + /// > [!IMPORTANT] + /// > Votes are ordered by ascending [Voter](./governance.html#Voter) and [GovernanceActionId](./governance.html#GovernanceActionId).
First constructor variants in a type are treated as lower indices; except for [Credential](./credential.html#Credential) where [`Script`](./credential.html#Credential) credentials are treated as **lower values** than [`VerificationKey`](./credential.html#Credential) credentials. + votes: Pairs>, + proposal_procedures: List, + current_treasury_amount: Option, + treasury_donation: Option, +} + +/// An interval of POSIX time, measured in **number of milliseconds** since 1970-01-01T00:00:00Z. +pub type ValidityRange = + Interval + +/// An `Input` made of an output reference and, the resolved value associated with that output. +pub type Input { + output_reference: OutputReference, + output: Output, +} + +/// An `OutputReference` is a unique reference to an output on-chain. The `output_index` +/// corresponds to the position in the output list of the transaction (identified by its id) +/// that produced that output +pub type OutputReference { + transaction_id: Hash, + output_index: Int, +} + +/// A transaction `Output`, with an address, a value and optional datums and script references. +pub type Output { + address: Address, + value: Value, + datum: Datum, + reference_script: Option, +} + +/// An output `Datum`. +pub type Datum { + NoDatum + /// A datum referenced by its hash digest. + DatumHash(DataHash) + /// A datum completely inlined in the output. + InlineDatum(Data) +} + +/// A type-alias for Redeemers, passed to scripts for validation. The `Data` is +/// opaque because it is user-defined and it is the script's responsibility to +/// parse it into its expected form. +pub type Redeemer = + Data + +// ## Querying + +/// Find an input by its [`OutputReference`](#OutputReference). This is typically used in +/// combination with the `Spend` [`ScriptPurpose`](#ScriptPurpose) to find a script's own +/// input. +/// +/// ```aiken +/// validator { +/// spend(datum, redeemer, my_output_reference, self) { +/// expect Some(input) = +/// self.inputs +/// |> transaction.find_input(my_output_reference) +/// } +/// } +/// ``` +pub fn find_input( + inputs: List, + output_reference: OutputReference, +) -> Option { + inputs + |> list.find(fn(input) { input.output_reference == output_reference }) +} + +/// Find a [`Datum`](#Datum) by its hash, if present. The function looks first for +/// datums in the witness set, and then for inline datums if it doesn't find any in +/// witnesses. +pub fn find_datum( + outputs: List, + datums: Dict, + datum_hash: DataHash, +) -> Option { + datums + |> dict.get(datum_hash) + |> option.or_try( + fn() { + outputs + |> list.filter_map( + fn(output) { + when output.datum is { + InlineDatum(data) -> + if blake2b_256(builtin.serialise_data(data)) == datum_hash { + Some(data) + } else { + None + } + _ -> None + } + }, + ) + |> list.head + }, + ) +} + +/// Find all outputs that are paying into the given script hash, if any. This is useful for +/// contracts running over multiple transactions. +pub fn find_script_outputs( + outputs: List, + script_hash: ScriptHash, +) -> List { + outputs + |> list.filter( + fn(output) { + when output.address.payment_credential is { + Script(addr_script_hash) -> script_hash == addr_script_hash + VerificationKey(_) -> False + } + }, + ) +} + +// ## Testing + +/// A placeholder / empty `Transaction` to serve as a base in a transaction +/// builder. This is particularly useful for constructing test transactions. +/// +/// Every field is empty or null, and we have in particular: +/// +/// ```aiken +/// use aiken/interval +/// +/// transaction.placeholder.id == +/// #"0000000000000000000000000000000000000000000000000000000000000000" +/// +/// transaction.placeholder.validity_range == interval.everything +/// ``` +pub const placeholder: Transaction = + Transaction { + inputs: [], + reference_inputs: [], + outputs: [], + fee: 0, + mint: assets.zero, + certificates: [], + withdrawals: [], + validity_range: interval.everything, + extra_signatories: [], + redeemers: [], + datums: dict.empty, + id: #"0000000000000000000000000000000000000000000000000000000000000000", + votes: [], + proposal_procedures: [], + current_treasury_amount: None, + treasury_donation: None, + } diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/transaction/output_reference.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/transaction/output_reference.ak new file mode 100644 index 00000000..70b7550d --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/transaction/output_reference.ak @@ -0,0 +1,23 @@ +use aiken/primitive/bytearray +use aiken/primitive/int +use cardano/transaction.{OutputReference} + +pub fn compare(left: OutputReference, right: OutputReference) -> Ordering { + when bytearray.compare(left.transaction_id, right.transaction_id) is { + Equal -> int.compare(left.output_index, right.output_index) + ordering -> ordering + } +} + +test compare_matrix() { + and { + (compare(OutputReference("", 0), OutputReference("", 0)) == Equal)?, + (compare(OutputReference("00", 42), OutputReference("00", 42)) == Equal)?, + (compare(OutputReference("00", 0), OutputReference("01", 0)) == Less)?, + (compare(OutputReference("01", 0), OutputReference("00", 0)) == Greater)?, + (compare(OutputReference("00", 42), OutputReference("01", 14)) == Less)?, + (compare(OutputReference("01", 14), OutputReference("00", 42)) == Greater)?, + (compare(OutputReference("", 42), OutputReference("", 14)) == Greater)?, + (compare(OutputReference("", 14), OutputReference("", 42)) == Less)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/transaction/script_purpose.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/transaction/script_purpose.ak new file mode 100644 index 00000000..4fef2cbe --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/aiken-lang-stdlib/lib/cardano/transaction/script_purpose.ak @@ -0,0 +1,126 @@ +use aiken/primitive/bytearray +use aiken/primitive/int +use cardano/address.{Script, VerificationKey} +use cardano/address/credential +use cardano/certificate.{RegisterCredential} +use cardano/governance.{NicePoll, ProposalProcedure, StakePool} +use cardano/governance/voter +use cardano/transaction.{ + Mint, OutputReference, Propose, Publish, ScriptPurpose, Spend, Vote, Withdraw, +} +use cardano/transaction/output_reference + +pub fn compare(left: ScriptPurpose, right: ScriptPurpose) -> Ordering { + when left is { + Mint(left) -> + when right is { + Mint(right) -> bytearray.compare(left, right) + _ -> Less + } + + Spend(left) -> + when right is { + Spend(right) -> output_reference.compare(left, right) + Mint(_) -> Greater + _ -> Less + } + + Withdraw(left) -> + when right is { + Withdraw(right) -> credential.compare(left, right) + Spend(_) | Mint(_) -> Greater + _ -> Less + } + + Publish(left, _) -> + when right is { + Publish(right, _) -> int.compare(left, right) + Spend(_) | Mint(_) | Withdraw(_) -> Greater + _ -> Less + } + + Vote(left) -> + when right is { + Vote(right) -> voter.compare(left, right) + Propose(..) -> Less + _ -> Greater + } + + Propose(left, _) -> + when right is { + Propose(right, _) -> int.compare(left, right) + _ -> Greater + } + } +} + +test compare_matrix() { + let mint0 = Mint("0") + let mint1 = Mint("1") + + let spend0 = Spend(OutputReference("", 0)) + let spend1 = Spend(OutputReference("", 1)) + + let withdraw0 = Withdraw(VerificationKey("0")) + let withdraw1 = Withdraw(VerificationKey("1")) + + let publish0 = Publish(0, RegisterCredential(Script(""), Never)) + let publish1 = Publish(1, RegisterCredential(Script(""), Never)) + + let vote0 = Vote(StakePool("0")) + let vote1 = Vote(StakePool("1")) + + let propose0 = Propose(0, ProposalProcedure(0, Script(""), NicePoll)) + let propose1 = Propose(1, ProposalProcedure(0, Script(""), NicePoll)) + + and { + (compare(mint0, mint0) == Equal)?, + (compare(mint0, mint1) == Less)?, + (compare(mint1, mint0) == Greater)?, + (compare(mint0, spend0) == Less)?, + (compare(mint0, withdraw0) == Less)?, + (compare(mint0, publish0) == Less)?, + (compare(mint0, vote0) == Less)?, + (compare(mint0, propose0) == Less)?, + (compare(spend0, spend0) == Equal)?, + (compare(spend0, spend1) == Less)?, + (compare(spend1, spend0) == Greater)?, + (compare(spend0, mint0) == Greater)?, + (compare(spend0, withdraw0) == Less)?, + (compare(spend0, publish0) == Less)?, + (compare(spend0, vote0) == Less)?, + (compare(spend0, propose0) == Less)?, + (compare(withdraw0, withdraw0) == Equal)?, + (compare(withdraw0, withdraw1) == Less)?, + (compare(withdraw1, withdraw0) == Greater)?, + (compare(withdraw0, mint0) == Greater)?, + (compare(withdraw0, spend0) == Greater)?, + (compare(withdraw0, publish0) == Less)?, + (compare(withdraw0, vote0) == Less)?, + (compare(withdraw0, propose0) == Less)?, + (compare(publish0, publish0) == Equal)?, + (compare(publish0, publish1) == Less)?, + (compare(publish1, publish0) == Greater)?, + (compare(publish0, mint0) == Greater)?, + (compare(publish0, spend0) == Greater)?, + (compare(publish0, withdraw0) == Greater)?, + (compare(publish0, vote0) == Less)?, + (compare(publish0, propose0) == Less)?, + (compare(vote0, vote0) == Equal)?, + (compare(vote0, vote1) == Less)?, + (compare(vote1, vote0) == Greater)?, + (compare(vote0, mint0) == Greater)?, + (compare(vote0, spend0) == Greater)?, + (compare(vote0, withdraw0) == Greater)?, + (compare(vote0, publish0) == Greater)?, + (compare(vote0, propose0) == Less)?, + (compare(propose0, propose0) == Equal)?, + (compare(propose0, propose1) == Less)?, + (compare(propose1, propose0) == Greater)?, + (compare(propose0, mint0) == Greater)?, + (compare(propose0, spend0) == Greater)?, + (compare(propose0, withdraw0) == Greater)?, + (compare(propose0, publish0) == Greater)?, + (compare(propose0, vote0) == Greater)?, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/packages.toml b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/packages.toml new file mode 100644 index 00000000..f0c64bc6 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/build/packages/packages.toml @@ -0,0 +1,4 @@ +[[packages]] +name = "aiken-lang/stdlib" +version = "v2.2.0" +source = "github" diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cip.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cip.ak new file mode 100644 index 00000000..a4ca9d6f --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cip.ak @@ -0,0 +1,73 @@ +//// Vodka provides utility functions to build CIP onchain code +//// +//// ### Example usage +//// ```aiken +//// use cip +//// use cardano/assets.{AssetName} +//// +//// let cip68_100_asset_name = cip.cip68_100(asset_name) +//// let cip68_222_asset_name = cip.cip68_222(asset_name) +//// let cip68_333_asset_name = cip.cip68_333(asset_name) +//// let cip68_444_asset_name = cip.cip68_444(asset_name) + +use aiken/primitive/bytearray.{concat} +use cardano/assets.{AssetName} + +/// The byte prefix for CIP-68 asset - Reference Token +pub const cip68_100_prefix: ByteArray = #"000643b0" + +/// The byte prefix for CIP-68 asset - Non-Fungible Token +pub const cip68_222_prefix: ByteArray = #"000de140" + +/// The byte prefix for CIP-68 asset - Fungible Token +pub const cip68_333_prefix: ByteArray = #"0014df10" + +/// The byte prefix for CIP-68 asset - Rich-Fungible Token +pub const cip68_444_prefix: ByteArray = #"001bc280" + +pub fn drop_cip68_prefix(cip_68_asset_name: AssetName) -> AssetName { + cip_68_asset_name |> bytearray.drop(4) +} + +test test_drop_cip68_prefix() { + let cip68_100_asset_name = #"000643b012345678" + drop_cip68_prefix(cip68_100_asset_name) == #"12345678" +} + +/// Obtain the asset name for CIP-68 asset - Reference Token +/// ```aiken +/// let cip68_100_asset_name = cip68_100(asset_name) +/// ``` +pub fn cip68_100(asset_name: AssetName) -> AssetName { + concat(cip68_100_prefix, asset_name) +} + +/// Obtain the asset name for CIP-68 asset - Non-Fungible Token +/// ```aiken +/// let cip68_222_asset_name = cip68_222(asset_name) +/// ``` +pub fn cip68_222(asset_name: AssetName) -> AssetName { + concat(cip68_222_prefix, asset_name) +} + +/// Obtain the asset name for CIP-68 asset - Fungible Token +/// ```aiken +/// let cip68_333_asset_name = cip68_333(asset_name) +/// ``` +pub fn cip68_333(asset_name: AssetName) -> AssetName { + concat(cip68_333_prefix, asset_name) +} + +/// Obtain the asset name for CIP-68 asset - Rich-Fungible Token +/// ```aiken +/// let cip68_444_asset_name = cip68_444(asset_name) +/// ``` +pub fn cip68_444(asset_name: AssetName) -> AssetName { + concat(cip68_444_prefix, asset_name) +} + +/// The metadata attached with CIP-68 reference token (100) +pub type CIP68Metadata { + metadata: Pairs, + version: Int, +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail.ak new file mode 100644 index 00000000..f67cb2cc --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail.ak @@ -0,0 +1,161 @@ +//// Vodka cocktail provides utility functions to build Aiken onchain code +//// +//// All onchain utility functions are grouped with a naming convention of `vodka_`, +//// and all can be imported directly with `use cocktail` +//// +//// ### Cardano data types +//// - `Address` - [`use vodka_address`](./cocktail/vodka_address.html) +//// - `Value` - [`use vodka_value`](./cocktail/vodka_value.html) +//// +//// ### Transaction types +//// - `extra_signatories` - [Documentation](./cocktail/vodka_extra_signatories.html) +//// - `inputs` - [Documentation](./cocktail/vodka_inputs.html) +//// - `outputs` - [Documentation](./cocktail/vodka_outputs.html) +//// - `mints` - [Documentation](./cocktail/vodka_mints.html) +//// - `validity_range` - [Documentation](./cocktail/vodka_validity_range.html) +//// - `Redeemers` - [Documentation](./cocktail/vodka_redeemers.html) + +use cocktail/vodka_address +use cocktail/vodka_converter +use cocktail/vodka_extra_signatories +use cocktail/vodka_inputs +use cocktail/vodka_mints +use cocktail/vodka_outputs +use cocktail/vodka_redeemers +use cocktail/vodka_validity_range +use cocktail/vodka_value + +// Address + +/// Documentation please refer to [`vodka_address`](./cocktail/vodka_address.html) +pub const compare_script_address = vodka_address.compare_script_address + +/// Documentation please refer to [`vodka_address`](./cocktail/vodka_address.html) +pub const compare_address = vodka_address.compare_address + +/// Documentation please refer to [`vodka_address`](./cocktail/vodka_address.html) +pub const address_payment_key = vodka_address.address_payment_key + +/// Documentation please refer to [`vodka_address`](./cocktail/vodka_address.html) +pub const address_pub_key = vodka_address.address_pub_key + +/// Documentation please refer to [`vodka_address`](./cocktail/vodka_address.html) +pub const address_script_hash = vodka_address.address_script_hash + +// Converter + +/// Documentation please refer to [`vodka_converter`](./cocktail/vodka_converter.html) +pub const convert_int_to_bytes = vodka_converter.convert_int_to_bytes + +/// Documentation please refer to [`vodka_converter`](./cocktail/vodka_converter.html) +pub const get_number_digit = vodka_converter.get_number_digit + +// Extra Signatories + +/// Documentation please refer to [`vodka_extra_signatories`](./cocktail/vodka_extra_signatories.html) +pub const key_signed = vodka_extra_signatories.key_signed + +/// Documentation please refer to [`vodka_extra_signatories`](./cocktail/vodka_extra_signatories.html) +pub const one_of_keys_signed = vodka_extra_signatories.one_of_keys_signed + +/// Documentation please refer to [`vodka_extra_signatories`](./cocktail/vodka_extra_signatories.html) +pub const all_key_signed = vodka_extra_signatories.all_key_signed + +// Inputs + +/// Documentation please refer to [`vodka_inputs`](./cocktail/vodka_inputs.html) +pub const input_inline_datum = vodka_inputs.input_inline_datum + +/// Documentation please refer to [`vodka_inputs`](./cocktail/vodka_inputs.html) +pub const only_input_datum_with = vodka_inputs.only_input_datum_with + +/// Documentation please refer to [`vodka_inputs`](./cocktail/vodka_inputs.html) +pub const inputs_at = vodka_inputs.inputs_at + +/// Documentation please refer to [`vodka_inputs`](./cocktail/vodka_inputs.html) +pub const inputs_with = vodka_inputs.inputs_with + +/// Documentation please refer to [`vodka_inputs`](./cocktail/vodka_inputs.html) +pub const inputs_with_policy = vodka_inputs.inputs_with_policy + +/// Documentation please refer to [`vodka_inputs`](./cocktail/vodka_inputs.html) +pub const inputs_at_with = vodka_inputs.inputs_at_with + +/// Documentation please refer to [`vodka_inputs`](./cocktail/vodka_inputs.html) +pub const inputs_at_with_policy = vodka_inputs.inputs_at_with_policy + +/// Documentation please refer to [`vodka_inputs`](./cocktail/vodka_inputs.html) +pub const inputs_token_quantity = vodka_inputs.inputs_token_quantity + +// Mints + +/// Documentation please refer to [`vodka_mints`](./cocktail/vodka_mints.html) +pub const check_policy_only_burn = vodka_mints.check_policy_only_burn + +/// Documentation please refer to [`vodka_mints`](./cocktail/vodka_mints.html) +pub const only_minted_token = vodka_mints.only_minted_token + +/// Documentation please refer to [`vodka_mints`](./cocktail/vodka_mints.html) +pub const policy_only_minted_token = vodka_mints.policy_only_minted_token + +/// Documentation please refer to [`vodka_mints`](./cocktail/vodka_mints.html) +pub const token_minted = vodka_mints.token_minted + +// Outputs + +/// Documentation please refer to [`vodka_outputs`](./cocktail/vodka_outputs.html) +pub const output_inline_datum = vodka_outputs.output_inline_datum + +/// Documentation please refer to [`vodka_outputs`](./cocktail/vodka_outputs.html) +pub const outputs_at = vodka_outputs.outputs_at + +/// Documentation please refer to [`vodka_outputs`](./cocktail/vodka_outputs.html) +pub const outputs_with = vodka_outputs.outputs_with + +/// Documentation please refer to [`vodka_outputs`](./cocktail/vodka_outputs.html) +pub const outputs_with_policy = vodka_outputs.outputs_with_policy + +/// Documentation please refer to [`vodka_outputs`](./cocktail/vodka_outputs.html) +pub const outputs_at_with = vodka_outputs.outputs_at_with + +/// Documentation please refer to [`vodka_outputs`](./cocktail/vodka_outputs.html) +pub const outputs_at_with_policy = vodka_outputs.outputs_at_with_policy + +// Redeemers + +/// Documentation please refer to [`vodka_redeemers`](./cocktail/vodka_redeemers.html) +pub const redeemer_from = vodka_redeemers.redeemer_from + +/// Documentation please refer to [`vodka_redeemers`](./cocktail/vodka_redeemers.html) +pub const withdrawal_redeemer = vodka_redeemers.withdrawal_redeemer + +/// Documentation please refer to [`vodka_redeemers`](./cocktail/vodka_redeemers.html) +pub const compare_output_reference = vodka_redeemers.compare_output_reference + +// Validity Range + +/// Documentation please refer to [`vodka_validity_range`](./cocktail/vodka_validity_range.html) +pub const valid_after = vodka_validity_range.valid_after + +/// Documentation please refer to [`vodka_validity_range`](./cocktail/vodka_validity_range.html) +pub const valid_before = vodka_validity_range.valid_before + +// Value + +/// Documentation please refer to [`vodka_value`](./cocktail/vodka_value.html) +pub const value_length = vodka_value.value_length + +/// Documentation please refer to [`vodka_value`](./cocktail/vodka_value.html) +pub const get_all_value_to = vodka_value.get_all_value_to + +/// Documentation please refer to [`vodka_value`](./cocktail/vodka_value.html) +pub const get_all_value_from = vodka_value.get_all_value_from + +/// Documentation please refer to [`vodka_value`](./cocktail/vodka_value.html) +pub const value_geq = vodka_value.value_geq + +/// Documentation please refer to [`vodka_value`](./cocktail/vodka_value.html) +pub const value_policy_info = vodka_value.value_policy_info + +/// Documentation please refer to [`vodka_value`](./cocktail/vodka_value.html) +pub const value_tokens = vodka_value.value_tokens diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_address.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_address.ak new file mode 100644 index 00000000..5bbf8a3d --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_address.ak @@ -0,0 +1,56 @@ +use aiken/crypto.{Blake2b_224, Hash, ScriptHash, VerificationKeyHash} +use aiken/primitive/bytearray +use cardano/address.{Address, Script, VerificationKey} + +/// Compare two script addresses +pub fn compare_script_address(x: Address, y: Address) -> Ordering { + expect Script(x_hash) = x.payment_credential + expect Script(y_hash) = y.payment_credential + bytearray.compare(x_hash, y_hash) +} + +/// Compare two addresses +pub fn compare_address(x: Address, y: Address) -> Ordering { + let x_hash = x.payment_credential + let y_hash = y.payment_credential + when (x_hash, y_hash) is { + (Script(x_script_hash), Script(y_script_hash)) -> + bytearray.compare(x_script_hash, y_script_hash) + (VerificationKey(x_key_hash), VerificationKey(y_key_hash)) -> + bytearray.compare(x_key_hash, y_key_hash) + _ -> Equal + } +} + +/// Obtain the payment key of an address, it can be either a script hash or a verification key +/// ```aiken +/// let payment_key_hash = address_payment_key(address) +/// ``` +pub fn address_payment_key(address: Address) -> Hash { + when address.payment_credential is { + Script(hash) -> hash + VerificationKey(key_hash) -> key_hash + } +} + +/// Obtain the verification key of an address, None if it is a script address +/// ```aiken +/// expect Some(pub_key_hash) = address_pub_key(address) +/// ``` +pub fn address_pub_key(address: Address) -> Option { + when address.payment_credential is { + VerificationKey(key_hash) -> Some(key_hash) + _ -> None + } +} + +/// Obtain the script hash of an address, None if it is a verification key address +/// ```aiken +/// expect Some(script_hash) = address_pub_key(address) +/// ``` +pub fn address_script_hash(address: Address) -> Option { + when address.payment_credential is { + Script(script_hash) -> Some(script_hash) + _ -> None + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_converter.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_converter.ak new file mode 100644 index 00000000..f13c84aa --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_converter.ak @@ -0,0 +1,40 @@ +use aiken/primitive/bytearray + +/// Convert an integer to a "stringify" ByteArray value +/// ```aiken +/// let int_bytes = convert_int_to_bytes(123) +/// let this_is_true = int_bytes == "123" +/// ``` +pub fn convert_int_to_bytes(i: Int) -> ByteArray { + convert_int_to_bytes_go(i, get_number_digit(i)) +} + +fn convert_int_to_bytes_go(newInt: Int, digit: Int) -> ByteArray { + if digit == 1 { + bytearray.push("", newInt + 48) + } else { + bytearray.push( + convert_int_to_bytes_go(newInt % digit, digit / 10), + newInt / digit + 48, + ) + } +} + +/// Get the number of digits in an integer +pub fn get_number_digit(i: Int) -> Int { + go_get_number_digit(i, 1) +} + +fn go_get_number_digit(newInt: Int, digit: Int) -> Int { + if newInt < 10 { + digit + } else { + go_get_number_digit(newInt / 10, digit * 10) + } +} + +test byte_conversion() { + convert_int_to_bytes(1) == "1" && convert_int_to_bytes(123) == "123" && convert_int_to_bytes( + 672912, + ) == "672912" +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_extra_signatories.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_extra_signatories.ak new file mode 100644 index 00000000..17eb3b20 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_extra_signatories.ak @@ -0,0 +1,46 @@ +use aiken/collection/list + +/// Check if a key is signed by any of the extra_signatories +/// ```aiken +/// let extra_signatories = ["key1", "key2", "key3"] +/// +/// let key_to_test_1 = "key2" +/// let this_is_true = key_signed(extra_signatories, key_to_test_1) +/// +/// let key_to_test_2 = "key4" +/// let this_is_false = key_signed(extra_signatories, key_to_test_2) +/// ``` +pub fn key_signed(extra_signatories: List, key: ByteArray) { + list.has(extra_signatories, key) +} + +/// Check if any of the keys are signed by the extra_signatories +/// ```aiken +/// let extra_signatories = ["key1", "key2", "key3"] +/// +/// let keys_to_test_1 = ["key4", "key2", "key5"] +/// let this_is_true = one_of_keys_signed(extra_signatories, keys_to_test_1) +/// +/// let keys_to_test_2 = ["key4", "key5"] +/// let this_is_false = one_of_keys_signed(extra_signatories, keys_to_test_2) +/// ``` +pub fn one_of_keys_signed( + extra_signatories: List, + keys: List, +) { + list.any(keys, fn(key) { key_signed(extra_signatories, key) }) +} + +/// Check if all of the keys are signed by the extra_signatories +/// ```aiken +/// let extra_signatories = ["key1", "key2", "key3"] +/// +/// let keys_to_test_1 = ["key2", "key3"] +/// let this_is_true = all_keys_signed(extra_signatories, keys_to_test_1) +/// +/// let keys_to_test_2 = ["key2", "key4"] +/// let this_is_false = all_keys_signed(extra_signatories, keys_to_test_2) +/// ``` +pub fn all_key_signed(extra_signatories: List, keys: List) { + list.all(keys, fn(key) { key_signed(extra_signatories, key) }) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_inputs.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_inputs.ak new file mode 100644 index 00000000..5ddaaa7f --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_inputs.ak @@ -0,0 +1,123 @@ +use aiken/collection/list +use cardano/address.{Address} +use cardano/assets.{AssetName, PolicyId, flatten, quantity_of} +use cardano/transaction.{InlineDatum, Input} + +/// Extracts the inline datum from an input. +/// ```aiken +/// expect inline_datum: MyDatumType = input_inline_datum(input) +/// ``` +pub fn input_inline_datum(input: Input) { + expect InlineDatum(raw_datum) = input.output.datum + raw_datum +} + +/// Extract the inline datum by locating the first input in a list of inputs by Address and PolicyId. +/// ```aiken +/// expect inline_datum: MyDatumType = only_input_datum_with(inputs, policy, name) +/// ``` +pub fn only_input_datum_with( + inputs: List, + policy: PolicyId, + name: AssetName, +) { + expect Some(input) = + list.find( + inputs, + fn(input) { quantity_of(input.output.value, policy, name) == 1 }, + ) + input_inline_datum(input) +} + +/// Filters inputs by Address. +/// ```aiken +/// let filtered_inputs = inputs_at(inputs, address) +/// ``` +pub fn inputs_at(inputs: List, address: Address) -> List { + list.filter(inputs, fn(input) { input.output.address == address }) +} + +/// Filters inputs by PolicyId and AssetName. +/// ```aiken +/// let filtered_inputs = inputs_with(inputs, policy, name) +/// ``` +pub fn inputs_with( + inputs: List, + policy: PolicyId, + name: AssetName, +) -> List { + list.filter( + inputs, + fn(input) { quantity_of(input.output.value, policy, name) == 1 }, + ) +} + +/// Filters inputs by token policy. +/// ```aiken +/// let filtered_inputs = inputs_with_policy(inputs, policy) +/// ``` +pub fn inputs_with_policy(inputs: List, policy: PolicyId) -> List { + list.filter( + inputs, + fn(input) { + list.any(flatten(input.output.value), fn(token) { token.1st == policy }) + }, + ) +} + +/// Filters inputs by Address, PolicyId, and AssetName. +/// ```aiken +/// let filtered_inputs = inputs_at_with(inputs, address, policy, name) +/// ``` +pub fn inputs_at_with( + inputs: List, + address: Address, + policy: PolicyId, + name: AssetName, +) -> List { + list.filter( + inputs, + fn(input) { + input.output.address == address && quantity_of( + input.output.value, + policy, + name, + ) == 1 + }, + ) +} + +/// Filters inputs by Address and PolicyId. +/// ```aiken +/// let filtered_inputs = inputs_at_with_policy(inputs, address, policy) +/// ``` +pub fn inputs_at_with_policy( + inputs: List, + address: Address, + policy: PolicyId, +) -> List { + list.filter( + inputs, + fn(input) { + input.output.address == address && list.any( + flatten(input.output.value), + fn(token) { token.1st == policy }, + ) + }, + ) +} + +/// Calculate the total quantity of a token in a list of inputs. +/// ```aiken +/// let total_quantity = inputs_token_quantity(inputs, token) +/// ``` +pub fn inputs_token_quantity( + inputs: List, + token: (PolicyId, AssetName), +) -> Int { + list.map( + inputs, + fn(input) { quantity_of(input.output.value, token.1st, token.2nd) }, + ) + |> list.foldr(0, fn(n, total) { n + total }) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_mints.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_mints.ak new file mode 100644 index 00000000..aa7dfe9a --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_mints.ak @@ -0,0 +1,68 @@ +use aiken/collection/list +use cardano/assets.{AssetName, PolicyId, Value, flatten} + +/// Check if a certain PolicyId is burning only if exists in the minted value. +/// ```aiken +/// let is_policy_only_burn = check_policy_only_burn(minted_value, policy) +/// ``` +pub fn check_policy_only_burn(mint: Value, policy: PolicyId) -> Bool { + let mint_value = flatten(mint) + list.all( + mint_value, + fn(x) { + if x.1st == policy { + x.3rd < 0 + } else { + True + } + }, + ) +} + +/// Check if a certain policy has only minted this token. +/// ```aiken +/// let is_policy_only_minted = check_policy_only_minted(minted_value, policy, name, quantity) +/// ``` +pub fn policy_only_minted_token( + mint: Value, + policy: PolicyId, + name: AssetName, + quantity: Int, +) { + when flatten(mint) |> list.filter(fn(asset) { asset.1st == policy }) is { + [(_, minted_asset_name, minted_quantity)] -> + minted_asset_name == name && minted_quantity == quantity + _ -> False + } +} + +/// Check if the minted value contains only one distinct asset with particular PolicyId. +/// ```aiken +/// let is_only_minted_token = only_minted_token(minted_value, policy, name, quantity) +/// ``` +pub fn only_minted_token( + mint: Value, + policy: PolicyId, + name: AssetName, + quantity: Int, +) { + when flatten(mint) is { + [(minted_policy, minted_asset_name, minted_quantity)] -> + minted_policy == policy && minted_asset_name == name && minted_quantity == quantity + _ -> False + } +} + +/// Check if the minted value contains a token with particular PolicyId, AssetName, and quantity. +/// ```aiken +/// let is_token_minted = token_minted(minted_value, policy, name, quantity) +/// ``` +pub fn token_minted( + mint: Value, + policy: PolicyId, + name: AssetName, + quantity: Int, +) { + flatten(mint) + |> list.any(fn(x) { x.1st == policy && x.2nd == name && x.3rd == quantity }) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_outputs.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_outputs.ak new file mode 100644 index 00000000..d83ffaf5 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_outputs.ak @@ -0,0 +1,90 @@ +use aiken/collection/list +use cardano/address.{Address} +use cardano/assets.{AssetName, PolicyId, flatten, quantity_of} +use cardano/transaction.{InlineDatum, Output} + +/// Extracts the inline datum from an output. +/// ```aiken +/// expect inline_datum: MyDatumType = output_inline_datum(output) +/// ``` +pub fn output_inline_datum(output: Output) { + expect InlineDatum(raw_datum) = output.datum + raw_datum +} + +/// Filters outputs by Address. +/// ```aiken +/// let filtered_outputs = outputs_at(outputs, address) +/// ``` +pub fn outputs_at(outputs: List, address: Address) -> List { + list.filter(outputs, fn(output) { output.address == address }) +} + +/// Filters outputs by PolicyId and AssetName. +/// ```aiken +/// let filtered_outputs = outputs_with(outputs, policy, name) +/// ``` +pub fn outputs_with( + outputs: List, + policy: PolicyId, + name: AssetName, +) -> List { + list.filter( + outputs, + fn(output) { quantity_of(output.value, policy, name) == 1 }, + ) +} + +/// Filters outputs by token policy. +/// ```aiken +/// let filtered_outputs = outputs_with_policy(outputs, policy) +/// ``` +pub fn outputs_with_policy( + outputs: List, + policy: PolicyId, +) -> List { + list.filter( + outputs, + fn(output) { + list.any(flatten(output.value), fn(token) { token.1st == policy }) + }, + ) +} + +/// Filters outputs by Address, PolicyId, and AssetName. +/// ```aiken +/// let filtered_outputs = outputs_at_with(outputs, address, policy, name) +/// ``` +pub fn outputs_at_with( + outputs: List, + address: Address, + policy: PolicyId, + name: AssetName, +) -> List { + list.filter( + outputs, + fn(output) { + output.address == address && quantity_of(output.value, policy, name) == 1 + }, + ) +} + +/// Filters outputs by Address and PolicyId. +/// ```aiken +/// let filtered_outputs = outputs_at_with_policy(outputs, address, policy) +/// ``` +pub fn outputs_at_with_policy( + outputs: List, + address: Address, + policy: PolicyId, +) -> List { + list.filter( + outputs, + fn(output) { + output.address == address && list.any( + flatten(output.value), + fn(token) { token.1st == policy }, + ) + }, + ) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_redeemers.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_redeemers.ak new file mode 100644 index 00000000..df3d69e9 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_redeemers.ak @@ -0,0 +1,45 @@ +use aiken/collection/pairs +use aiken/primitive/bytearray +use cardano/address.{Address, Script} +use cardano/transaction.{ + Input, OutputReference, Redeemer, ScriptPurpose, Spend, Withdraw, find_input, +} + +/// Obtain the redeemer for a given output reference and address +/// ```aiken +/// expect Some(redeemer) = redeemer_from(redeemers, inputs, output_reference, input_address) +/// ``` +pub fn redeemer_from( + redeemers: Pairs, + inputs: List, + output_reference: OutputReference, + input_address: Address, +) -> Option { + expect Some(redeemer) = redeemers |> pairs.get_first(Spend(output_reference)) + expect Some(input) = find_input(inputs, output_reference) + if input.output.address == input_address { + Some(redeemer) + } else { + None + } +} + +/// Obtain the first redeemer for a given withdrawal script hash +/// ```aiken +/// expect Some(raw_redeemer) = withdrawal_redeemer(redeemers, withdrawal_script_hash) +/// expect my_redeemer: MyRedeemerType = raw_redeemer; +/// ``` +pub fn withdrawal_redeemer( + redeemers: Pairs, + withdrawal_script_hash: ByteArray, +) -> Option { + redeemers + |> pairs.get_first(Withdraw(Script(withdrawal_script_hash))) +} + +/// Compare the output reference of two spend transactions +pub fn compare_output_reference(x, y) { + expect Spend(out_ref_x) = x + expect Spend(out_ref_y) = y + bytearray.compare(out_ref_x.transaction_id, out_ref_y.transaction_id) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_validity_range.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_validity_range.ak new file mode 100644 index 00000000..498bc600 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_validity_range.ak @@ -0,0 +1,34 @@ +use aiken/interval.{Finite, IntervalBound} +use cardano/transaction.{ValidityRange} + +/// Check if the validity range is after the required timestamp. +/// ```aiken +/// let is_valid_after = valid_after(transaction.validity_range, required_timestamp) +/// ``` +pub fn valid_after( + validity_range: ValidityRange, + required_timestamp: Int, +) -> Bool { + let IntervalBound { bound_type, is_inclusive } = validity_range.lower_bound + when (bound_type, is_inclusive) is { + (Finite(lower_bound), True) -> lower_bound > required_timestamp + (Finite(lower_bound), False) -> lower_bound >= required_timestamp + _ -> False + } +} + +/// Check if the validity range is before the required timestamp. +/// ```aiken +/// let is_valid_before = valid_before(transaction.validity_range, required_timestamp) +/// ``` +pub fn valid_before( + validity_range: ValidityRange, + required_timestamp: Int, +) -> Bool { + let IntervalBound { bound_type, is_inclusive } = validity_range.upper_bound + when (bound_type, is_inclusive) is { + (Finite(upper_bound), True) -> upper_bound < required_timestamp + (Finite(upper_bound), False) -> upper_bound <= required_timestamp + _ -> False + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_value.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_value.ak new file mode 100644 index 00000000..770ddbcc --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/cocktail/vodka_value.ak @@ -0,0 +1,80 @@ +use aiken/collection/list +use cardano/address.{Address} +use cardano/assets.{ + AssetName, PolicyId, Value, flatten, merge, quantity_of, zero, +} +use cardano/transaction.{Input, Output} + +/// Calulate the length of a value +/// ```aiken +/// let value_length = value_length(value) +/// ``` +pub fn value_length(value: Value) -> Int { + list.length(flatten(value)) +} + +/// Get the value send to a particular address in a list of outputs +/// ```aiken +/// let value_to = get_all_value_to(outputs, address) +/// ``` +pub fn get_all_value_to(outputs: List, address: Address) -> Value { + list.foldr( + outputs, + zero, + fn(output, acc_value) { + if output.address == address { + merge(acc_value, output.value) + } else { + acc_value + } + }, + ) +} + +/// Get the value coming from a particular address in a list of inputs +/// ```aiken +/// let value_from = get_all_value_from(inputs, address) +/// ``` +pub fn get_all_value_from(inputs: List, address: Address) -> Value { + list.foldr( + inputs, + zero, + fn(input, acc_value) { + if input.output.address == address { + merge(acc_value, input.output.value) + } else { + acc_value + } + }, + ) +} + +/// Check if the first value provided is greater than or equal to the second value +/// ```aiken +/// let is_geq = value_geq(supposed_greater, supposed_smaller) +/// ``` +pub fn value_geq(greater: Value, smaller: Value) -> Bool { + list.all( + flatten(smaller), + fn(token) { quantity_of(greater, token.1st, token.2nd) >= token.3rd }, + ) +} + +/// Obtain the information (i.e. flattened value) of a policy in a value +/// ```aiken +/// expect Some((policyId, assetName, quantity)) = value_policy_info(value, policy) +/// ``` +pub fn value_policy_info( + value: Value, + policy: ByteArray, +) -> Option<(ByteArray, ByteArray, Int)> { + list.find(flatten(value), fn(t) { t.1st == policy }) +} + +/// Obtain the non-lovelace information (i.e. flattened value) of a policy in a value +/// ```aiken +/// let tokens = value_tokens(value) +/// ``` +pub fn value_tokens(value: Value) -> List<(PolicyId, AssetName, Int)> { + list.filter(flatten(value), fn(t) { t.1st != "" }) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail.ak new file mode 100644 index 00000000..79a8e7c7 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail.ak @@ -0,0 +1,776 @@ +//// Mocktail contains a set of functions to build transactions for testing purposes. +//// +//// To use Mocktail Tx, there are 4 steps +//// 1. Starts with [`mocktail_tx()`](./mocktail.html#mocktail_tx) to create a new transaction builder. +//// 2. Use tx building methods similar to MeshJS lower level APIs to build the transaction. +//// 3. Call [`complete`](./mocktail.html#complete) to complete building transaction. +//// 4. Finally, if there is any whole items to be added to the transaction, use the `add` functions. +//// +//// Mocktail is built with devex and multiple test cases compatibility in mind. +//// 1. It is pipable. +//// 2. For every tx building and adding methods, it takes first param as condition. that function will only run when this condition is `True`. +//// +//// ## Example +//// ```aiken +//// let tx: Transaction = +//// mocktail_tx() +//// |> required_signer_hash(is_signature_provided, mock_pub_key_hash(0)) +//// |> script_withdrawal(True, mock_script_hash(0), 0) +//// |> script_withdrawal(True, mock_script_hash(1), 0) +//// |> required_signer_hash(True, mock_pub_key_hash(1)) +//// |> complete() +//// |> add_reference_input(True, mock_oracle_ref_input_1()) +//// |> add_reference_input(True, mock_oracle_ref_input_2()) +//// |> add_output(True, mock_pub_key_output(mock_fee_collection_address, mock_fee)) +//// ``` + +use aiken/cbor +use aiken/collection/dict +use aiken/collection/list +use aiken/crypto.{VerificationKeyHash, blake2b_256} +use aiken/interval.{Finite, Interval} +use cardano/address.{Address, Credential, Script} +use cardano/assets.{Value, from_asset, merge, zero} +use cardano/certificate.{Certificate} +use cardano/transaction.{ + InlineDatum, Input, Output, OutputReference, Redeemer, ScriptPurpose, + Transaction, TransactionId, placeholder, +} +use mocktail/virgin_address +use mocktail/virgin_key_hash +use mocktail/virgin_output_reference +use mocktail/virgin_outputs +use mocktail/virgin_validity_range + +/// A mock transaction builder. It can be initialized with `mocktail_tx()`. +pub type MocktailTx { + tx: Transaction, + queue_input: Option, + queue_output: Option, + queue_ref_input: Option, +} + +/// Initialize a new mock transaction builder, and output a built transaction wiht [`.complete().`](./mocktail.html#complete) +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn mocktail_tx() -> MocktailTx { + MocktailTx { + tx: placeholder, + queue_input: None, + queue_output: None, + queue_ref_input: None, + } +} + +/// Tx building method - Add an input to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> tx_in(condition, tx_hash, tx_index, amount, address) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn tx_in( + mocktail_tx: MocktailTx, + condition: Bool, + tx_hash: ByteArray, + tx_index: Int, + amount: Value, + address: Address, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + let queue_input = + Some( + Input { + output_reference: OutputReference { + transaction_id: tx_hash, + output_index: tx_index, + }, + output: mock_pub_key_output(address, amount), + }, + ) + when mocktail_tx.queue_input is { + Some(input) -> + MocktailTx { + ..mocktail_tx, + queue_input: queue_input, + tx: mocktail_tx.tx |> add_input(True, input), + } + None -> MocktailTx { ..mocktail_tx, queue_input: queue_input } + } + } +} + +/// Tx building method - Add an input with inline datum to the transaction. +/// This can only be used right after [`tx_in`](./mocktail.html#tx_in). +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> tx_in(condition, tx_hash, tx_index, amount, address) +/// |> tx_in_inline_datum(condition, datum) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn tx_in_inline_datum( + mocktail_tx: MocktailTx, + condition: Bool, + datum: Data, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + let queue_input = + when mocktail_tx.queue_input is { + Some(input) -> { + let Input { output_reference, output } = input + Some( + Input { + output_reference, + output: Output { ..output, datum: InlineDatum(datum) }, + }, + ) + } + None -> + Some( + Input { + output_reference: mock_utxo_ref(0, 0), + output: mock_script_output( + mock_script_address(0, None), + zero, + InlineDatum(datum), + ), + }, + ) + } + MocktailTx { ..mocktail_tx, queue_input: queue_input } + } +} + +/// Tx building method - Add an output to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> tx_out(condition, address, amount) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn tx_out( + mocktail_tx: MocktailTx, + condition: Bool, + address: Address, + amount: Value, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + let queue_output = Some(mock_pub_key_output(address, amount)) + when mocktail_tx.queue_output is { + Some(output) -> + MocktailTx { + ..mocktail_tx, + queue_output: queue_output, + tx: mocktail_tx.tx |> add_output(True, output), + } + None -> MocktailTx { ..mocktail_tx, queue_output: queue_output } + } + } +} + +/// Tx building method - Add an output with inline datum to the transaction. +/// This can only be used right after [`tx_out`](./mocktail.html#tx_out). +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> tx_out(condition, address, amount) +/// |> tx_out_inline_datum(condition, datum) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn tx_out_inline_datum( + mocktail_tx: MocktailTx, + condition: Bool, + datum: Data, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + let queue_output = + when mocktail_tx.queue_output is { + Some(output) -> Some(Output { ..output, datum: InlineDatum(datum) }) + None -> + Some( + mock_script_output( + mock_script_address(0, None), + zero, + InlineDatum(datum), + ), + ) + } + MocktailTx { ..mocktail_tx, queue_output: queue_output } + } +} + +/// Tx building method - Add a mint to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> mint(condition, quantity, policy_id, token_name) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn mint( + mocktail_tx: MocktailTx, + condition: Bool, + quantity: Int, + policy_id: ByteArray, + token_name: ByteArray, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + MocktailTx { + ..mocktail_tx, + tx: mocktail_tx.tx + |> add_mint(True, from_asset(policy_id, token_name, quantity)), + } + } +} + +/// Tx building method - Add a reference input to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ref_tx_in(condition, tx_hash, tx_index, amount, address) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn ref_tx_in( + mocktail_tx: MocktailTx, + condition: Bool, + tx_hash: ByteArray, + tx_index: Int, + amount: Value, + address: Address, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + let queue_ref_input = + Some( + Input { + output_reference: OutputReference { + transaction_id: tx_hash, + output_index: tx_index, + }, + output: mock_pub_key_output(address, amount), + }, + ) + when mocktail_tx.queue_ref_input is { + Some(input) -> + MocktailTx { + ..mocktail_tx, + queue_ref_input: queue_ref_input, + tx: mocktail_tx.tx |> add_reference_input(True, input), + } + None -> MocktailTx { ..mocktail_tx, queue_ref_input: queue_ref_input } + } + } +} + +/// Tx building method - Add an inline datum to last reference input in the transaction. +/// This can only be used right after [`ref_tx_in`](./mocktail.html#ref_tx_in). +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ref_tx_in(condition, tx_hash, tx_index, amount, address) +/// |> ref_tx_in_inline_datum(condition, datum) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn ref_tx_in_inline_datum( + mocktail_tx: MocktailTx, + condition: Bool, + datum: Data, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + let queue_ref_input = + when mocktail_tx.queue_ref_input is { + Some(input) -> { + let Input { output_reference, output } = input + Some( + Input { + output_reference, + output: Output { ..output, datum: InlineDatum(datum) }, + }, + ) + } + None -> + Some( + Input { + output_reference: mock_utxo_ref(0, 0), + output: mock_script_output( + mock_script_address(0, None), + zero, + InlineDatum(datum), + ), + }, + ) + } + MocktailTx { ..mocktail_tx, queue_ref_input: queue_ref_input } + } +} + +/// Tx building method - Add a a lower bound validity range to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> valid_hereafter(condition, time) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn invalid_before( + mocktail_tx: MocktailTx, + condition: Bool, + time: Int, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + let tx = mocktail_tx.tx + let upper_bound = + when tx.validity_range.upper_bound.bound_type is { + Finite(x) -> Some(x) + _ -> None + } + MocktailTx { + ..mocktail_tx, + tx: Transaction { + ..tx, + validity_range: mock_interval(Some(time), upper_bound), + }, + } + } +} + +/// Tx building method - Add a a upper bound validity range to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> valid_hereafter(condition, time) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn invalid_hereafter( + mocktail_tx: MocktailTx, + condition: Bool, + time: Int, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + let tx = mocktail_tx.tx + let lower_bound = + when tx.validity_range.lower_bound.bound_type is { + Finite(x) -> Some(x) + _ -> None + } + MocktailTx { + ..mocktail_tx, + tx: Transaction { + ..tx, + validity_range: mock_interval(lower_bound, Some(time)), + }, + } + } +} + +/// Tx building method - Add a required signer hash to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> required_signer_hash(condition, key) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn required_signer_hash( + mocktail_tx: MocktailTx, + condition: Bool, + key: ByteArray, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + MocktailTx { + ..mocktail_tx, + tx: mocktail_tx.tx |> add_extra_signatory(True, key), + } + } +} + +/// Tx building method - Add a script withdrawal to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> script_withdrawal(condition, script_hash, withdrawal_amount) +/// |> ...other tx building methods +/// |> complete() +/// ``` +pub fn script_withdrawal( + mocktail_tx: MocktailTx, + condition: Bool, + script_hash: ByteArray, + withdrawal_amount: Int, +) -> MocktailTx { + if !condition { + mocktail_tx + } else { + MocktailTx { + ..mocktail_tx, + tx: mocktail_tx.tx + |> add_withdrawal(True, Pair(Script(script_hash), withdrawal_amount)), + } + } +} + +/// Tx building method - Conclude the transaction building process, and return the built transaction. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +pub fn complete(mocktail_tx: MocktailTx) -> Transaction { + let tx = mocktail_tx.tx + let tx = + when mocktail_tx.queue_input is { + Some(input) -> tx |> add_input(True, input) + None -> tx + } + let tx = + when mocktail_tx.queue_output is { + Some(output) -> tx |> add_output(True, output) + None -> tx + } + let tx = + when mocktail_tx.queue_ref_input is { + Some(input) -> tx |> add_reference_input(True, input) + None -> tx + } + tx +} + +/// Tx maniputlator - Add an input to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> add_input(condition, input) +/// |> ...other tx maniputlator methods +/// ``` +pub fn add_input(tx: Transaction, condition: Bool, input: Input) -> Transaction { + if !condition { + tx + } else { + Transaction { ..tx, inputs: tx.inputs |> list.concat([input]) } + } +} + +/// Tx maniputlator - Add a reference input to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> add_reference_input(condition, input) +/// |> ...other tx maniputlator methods +/// ``` +pub fn add_reference_input( + tx: Transaction, + condition: Bool, + input: Input, +) -> Transaction { + if !condition { + tx + } else { + Transaction { + ..tx, + reference_inputs: tx.reference_inputs |> list.concat([input]), + } + } +} + +/// Tx maniputlator - Add an output to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let t = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> add_output(condition, output) +/// |> ...other tx maniputlator methods +/// ``` +pub fn add_output( + tx: Transaction, + condition: Bool, + output: Output, +) -> Transaction { + if !condition { + tx + } else { + Transaction { ..tx, outputs: tx.outputs |> list.concat([output]) } + } +} + +/// Tx maniputlator - Set a fee to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> set_fee(condition, lovelace_fee) +/// |> ...other tx maniputlator methods +/// ``` +pub fn set_fee( + tx: Transaction, + condition: Bool, + lovelace_fee: Int, +) -> Transaction { + if !condition { + tx + } else { + Transaction { ..tx, fee: lovelace_fee } + } +} + +/// Tx maniputlator - Add a mint to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> add_mint(condition, mint) +/// |> ...other tx maniputlator methods +/// ``` +pub fn add_mint(tx: Transaction, condition: Bool, mint: Value) -> Transaction { + if !condition { + tx + } else { + Transaction { + ..tx, + mint: tx.mint + |> merge(mint), + } + } +} + +/// Tx maniputlator - Add a certificate to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> add_certificate(condition, certificate) +/// |> ...other tx maniputlator methods +/// ``` +pub fn add_certificate( + tx: Transaction, + condition: Bool, + certificate: Certificate, +) -> Transaction { + if !condition { + tx + } else { + Transaction { + ..tx, + certificates: tx.certificates |> list.concat([certificate]), + } + } +} + +/// Tx maniputlator - Add a withdrawal to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> add_withdrawal(condition, stake_credential, amount) +/// |> ...other tx maniputlator methods +/// ``` +pub fn add_withdrawal( + tx: Transaction, + condition: Bool, + withdrawal: Pair, +) -> Transaction { + if !condition { + tx + } else { + Transaction { + ..tx, + withdrawals: tx.withdrawals |> list.concat([withdrawal]), + } + } +} + +/// Tx maniputlator - Add an extra signatory to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> add_extra_signatory(condition, signatory) +/// |> ...other tx maniputlator methods +/// ``` +pub fn add_extra_signatory( + tx: Transaction, + condition: Bool, + signatory: VerificationKeyHash, +) -> Transaction { + if !condition { + tx + } else { + Transaction { + ..tx, + extra_signatories: tx.extra_signatories |> list.concat([signatory]), + } + } +} + +/// Tx maniputlator - Add a redeemer to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> add_redeemer(condition, redeemer) +/// |> ...other tx maniputlator methods +/// ``` +pub fn add_redeemer( + tx: Transaction, + condition: Bool, + redeemer: Pair, +) -> Transaction { + if !condition { + tx + } else { + Transaction { ..tx, redeemers: tx.redeemers |> list.concat([redeemer]) } + } +} + +/// Tx maniputlator - Add a datum to the transaction. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> add_datum(condition, datum) +/// |> ...other tx maniputlator methods +/// ``` +pub fn add_datum(tx: Transaction, condition: Bool, datum: Data) -> Transaction { + if !condition { + tx + } else { + let datum_hash = blake2b_256(cbor.serialise(datum)) + Transaction { ..tx, datums: tx.datums |> dict.insert(datum_hash, datum) } + } +} + +/// Tx maniputlator - Set the transaction id. +/// This function will only run when the condition is `True`. +/// ```aiken +/// let tx = mocktail_tx() +/// |> ...tx building methods +/// |> complete() +/// |> set_transaction_id(condition, transaction_id) +/// |> ...other tx maniputlator methods +/// ``` +pub fn set_transaction_id( + tx: Transaction, + condition: Bool, + transaction_id: TransactionId, +) -> Transaction { + if !condition { + tx + } else { + Transaction { ..tx, id: transaction_id } + } +} + +// Address + +/// Documentation please refer to [`virgin_address`](./mocktail/virgin_address.html) +pub const mock_verfication_key_credential = + virgin_address.mock_verfication_key_credential + +/// Documentation please refer to [`virgin_address`](./mocktail/virgin_address.html) +pub const mock_pub_key_address = virgin_address.mock_pub_key_address + +/// Documentation please refer to [`virgin_address`](./mocktail/virgin_address.html) +pub const mock_script_credential = virgin_address.mock_script_credential + +/// Documentation please refer to [`virgin_address`](./mocktail/virgin_address.html) +pub const mock_script_address = virgin_address.mock_script_address + +// Key hash + +/// Documentation please refer to [`virgin_key_hash`](./mocktail/virgin_key_hash.html) +pub const mock_key_hash = virgin_key_hash.mock_key_hash + +/// Documentation please refer to [`virgin_key_hash`](./mocktail/virgin_key_hash.html) +pub const mock_policy_id = virgin_key_hash.mock_policy_id + +/// Documentation please refer to [`virgin_key_hash`](./mocktail/virgin_key_hash.html) +pub const mock_pub_key_hash = virgin_key_hash.mock_pub_key_hash + +/// Documentation please refer to [`virgin_key_hash`](./mocktail/virgin_key_hash.html) +pub const mock_script_hash = virgin_key_hash.mock_script_hash + +/// Documentation please refer to [`virgin_key_hash`](./mocktail/virgin_key_hash.html) +pub const mock_stake_key_hash = virgin_key_hash.mock_stake_key_hash + +/// Documentation please refer to [`virgin_key_hash`](./mocktail/virgin_key_hash.html) +pub const mock_script_stake_key_hash = + virgin_key_hash.mock_script_stake_key_hash + +// Output reference + +/// Documentation please refer to [`virgin_output_reference`](./mocktail/virgin_output_reference.html) +pub const mock_tx_hash = virgin_output_reference.mock_tx_hash + +/// Documentation please refer to [`virgin_output_reference`](./mocktail/virgin_output_reference.html) +pub const mock_utxo_ref = virgin_output_reference.mock_utxo_ref + +// Outputs + +/// Documentation please refer to [`virgin_outputs`](./mocktail/virgin_outputs.html) +pub const mock_output = virgin_outputs.mock_output + +/// Documentation please refer to [`virgin_outputs`](./mocktail/virgin_outputs.html) +pub const mock_pub_key_output = virgin_outputs.mock_pub_key_output + +/// Documentation please refer to [`virgin_outputs`](./mocktail/virgin_outputs.html) +pub const mock_script_output = virgin_outputs.mock_script_output + +// Validity range + +/// Documentation please refer to [`virgin_validity_range`](./mocktail/virgin_validity_range.html) +pub const mock_interval = virgin_validity_range.mock_interval + +test preserve_tx_in_order() { + let tx: Transaction = + mocktail_tx() + |> tx_in(True, mock_tx_hash(0), 0, zero, mock_pub_key_address(0, None)) + |> tx_in(True, mock_tx_hash(1), 1, zero, mock_pub_key_address(1, None)) + |> complete() + expect [input1, input2] = tx.inputs + and { + input1.output_reference.transaction_id == mock_tx_hash(0), + input1.output_reference.output_index == 0, + input2.output_reference.transaction_id == mock_tx_hash(1), + input2.output_reference.output_index == 1, + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_address.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_address.ak new file mode 100644 index 00000000..30a6e40b --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_address.ak @@ -0,0 +1,57 @@ +use cardano/address.{ + Address, Credential, Inline, Script, StakeCredential, VerificationKey, +} +use mocktail/virgin_key_hash.{ + mock_pub_key_hash, mock_script_hash, mock_script_stake_key_hash, + mock_stake_key_hash, +} + +/// Mock a pub key credential +/// `variation` same the same index as `mock_pub_key_hash` +pub fn mock_verfication_key_credential(variation: Int) -> Credential { + VerificationKey(mock_pub_key_hash(variation)) +} + +/// Mock a pub key address +/// `variation` same the same index as `mock_pub_key_hash` +/// `stake_credential` is optional +pub fn mock_pub_key_address( + variation: Int, + stake_credential: Option, +) -> Address { + Address { + payment_credential: mock_verfication_key_credential(variation), + stake_credential, + } +} + +/// Mock a script credential +/// `variation` same the same index as `mock_script_hash` +pub fn mock_script_credential(variation: Int) -> Credential { + Script(mock_script_hash(variation)) +} + +/// Mock a script address +/// `variation` same the same index as `mock_script_hash` +/// `stake_credential` is optional +pub fn mock_script_address( + variation: Int, + stake_credential: Option, +) -> Address { + Address { + payment_credential: mock_script_credential(variation), + stake_credential, + } +} + +/// Mock a pub key stake credential +/// `variation` same the same index as `mock_stake_key_hash` +pub fn mock_pub_key_stake_cred(variation: Int) -> StakeCredential { + Inline(VerificationKey(mock_stake_key_hash(variation))) +} + +/// Mock a script stake credential +/// `variation` same the same index as `mock_script_stake_key_hash` +pub fn mock_script_stake_cred(variation: Int) -> StakeCredential { + Inline(Script(mock_script_stake_key_hash(variation))) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_key_hash.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_key_hash.ak new file mode 100644 index 00000000..9a32dd06 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_key_hash.ak @@ -0,0 +1,47 @@ +use aiken/cbor.{serialise} +use aiken/crypto.{ScriptHash, VerificationKeyHash, blake2b_224} +use aiken/primitive/bytearray.{concat} +use cardano/assets.{PolicyId} + +pub const root_hash = + #"a2c20c77887ace1cd986193e4e75babd8993cfd56995cd5cfce609c2" + +/// Mock a key in hexadecimal format +pub fn mock_key_hash(variation: Int) -> ByteArray { + serialise(variation) |> concat(root_hash) |> blake2b_224() +} + +/// Mock a PolicyID +/// The variation is used to distinguish between different PolicyIDs +/// Use this but not other `mock_key_hash` functions to avoid hash collision +pub fn mock_policy_id(variation: Int) -> PolicyId { + mock_key_hash(variation) +} + +/// Mock a public key hash +/// The variation is used to distinguish between different public keys +/// Use this but not other `mock_key_hash` functions to avoid hash collision +pub fn mock_pub_key_hash(variation: Int) -> VerificationKeyHash { + mock_key_hash(variation + 1000) +} + +/// Mock a script hash +/// The variation is used to distinguish between different scripts +/// Use this but not other `mock_key_hash` functions to avoid hash collision +pub fn mock_script_hash(variation: Int) -> ScriptHash { + mock_key_hash(variation + 2000) +} + +/// Mock a stake key hash +/// The variation is used to distinguish between different stake keys +/// Use this but not other `mock_key_hash` functions to avoid hash collision +pub fn mock_stake_key_hash(variation: Int) -> VerificationKeyHash { + mock_key_hash(variation + 3000) +} + +/// Mock a script stake key hash +/// The variation is used to distinguish between different scripts +/// Use this but not other `mock_key_hash` functions to avoid hash collision +pub fn mock_script_stake_key_hash(variation: Int) -> ScriptHash { + mock_key_hash(variation + 4000) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_output_reference.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_output_reference.ak new file mode 100644 index 00000000..03ec9c02 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_output_reference.ak @@ -0,0 +1,16 @@ +use aiken/cbor.{serialise} +use aiken/crypto.{Blake2b_256, Hash, blake2b_256} +use aiken/primitive/bytearray.{concat} +use cardano/transaction.{OutputReference, Transaction} + +const root_hash = + #"5a077cbcdffb88b104f292aacb9687ce93e2191e103a30a0cc5505c18b719f98" + +pub fn mock_tx_hash(variation: Int) -> Hash { + serialise(variation) |> concat(root_hash) |> blake2b_256() +} + +/// Mock an output reference +pub fn mock_utxo_ref(variation: Int, output_index: Int) -> OutputReference { + OutputReference { transaction_id: mock_tx_hash(variation), output_index } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_outputs.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_outputs.ak new file mode 100644 index 00000000..b75181ba --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_outputs.ak @@ -0,0 +1,30 @@ +use aiken/crypto.{ScriptHash} +use cardano/address.{Address} +use cardano/assets.{Value} +use cardano/transaction.{Datum, NoDatum, Output} + +/// Mock an output +pub fn mock_output( + address: Address, + value: Value, + datum: Datum, + reference_script: Option, +) -> Output { + Output { address, value, datum, reference_script } +} + +/// Mock an output with a public key address +/// `datum` and `reference_script` is omitted as it is seldom used in practice +pub fn mock_pub_key_output(address: Address, value: Value) -> Output { + mock_output(address, value, NoDatum, reference_script: None) +} + +/// Mock an output with a script address +/// `reference_script` is omitted as it is seldom used in practice +pub fn mock_script_output( + address: Address, + value: Value, + datum: Datum, +) -> Output { + mock_output(address, value, datum, reference_script: None) +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_validity_range.ak b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_validity_range.ak new file mode 100644 index 00000000..c11a249d --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/lib/mocktail/virgin_validity_range.ak @@ -0,0 +1,28 @@ +use aiken/interval.{ + Finite, Interval, IntervalBound, NegativeInfinity, PositiveInfinity, +} +use cardano/transaction.{ValidityRange} + +/// Mock a validity range with the given lower and upper bounds. +pub fn mock_interval(lower: Option, upper: Option) -> ValidityRange { + let lower_bound = + when lower is { + Some(lower_bound_number) -> + IntervalBound { + bound_type: Finite(lower_bound_number), + is_inclusive: True, + } + None -> IntervalBound { bound_type: NegativeInfinity, is_inclusive: True } + } + let upper_bound = + when upper is { + Some(upper_bound_number) -> + IntervalBound { + bound_type: Finite(upper_bound_number), + is_inclusive: True, + } + None -> IntervalBound { bound_type: PositiveInfinity, is_inclusive: True } + } + + Interval { lower_bound, upper_bound } +} diff --git a/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/plutus.json b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/plutus.json new file mode 100644 index 00000000..ebc0bcfa --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/build/packages/sidan-lab-vodka/plutus.json @@ -0,0 +1,14 @@ +{ + "preamble": { + "title": "sidan-lab/vodka", + "description": "Aiken utils for project 'sidan-lab/vodka", + "version": "0.1.13", + "plutusVersion": "v3", + "compiler": { + "name": "Aiken", + "version": "v1.1.9+2217206" + }, + "license": "Apache-2.0" + }, + "validators": [] +} \ No newline at end of file diff --git a/src/components/multisig/proxy/aiken-workspace/lib/types.ak b/src/components/multisig/proxy/aiken-workspace/lib/types.ak new file mode 100644 index 00000000..3084fe32 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/lib/types.ak @@ -0,0 +1,9 @@ +pub type MintPolarity { + RMint + RBurn +} + +pub type ProxyRedeemer { + SpendFunds + RemoveEmptyInstance +} diff --git a/src/components/multisig/proxy/aiken-workspace/plutus.json b/src/components/multisig/proxy/aiken-workspace/plutus.json new file mode 100644 index 00000000..a3e575f5 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/plutus.json @@ -0,0 +1,117 @@ +{ + "preamble": { + "title": "mesh/proxy", + "description": "Aiken contracts for project 'aiken-proxy'", + "version": "0.0.0", + "plutusVersion": "v3", + "compiler": { + "name": "Aiken", + "version": "v1.1.17+c3a7fba" + }, + "license": "Apache-2.0" + }, + "validators": [ + { + "title": "auth_token/mint.auth_token.mint", + "redeemer": { + "title": "redeemer", + "schema": { + "$ref": "#/definitions/types~1MintPolarity" + } + }, + "parameters": [ + { + "title": "utxo_ref", + "schema": { + "$ref": "#/definitions/cardano~1transaction~1OutputReference" + } + } + ], + "compiledCode": "59017b010100229800aba2aba1aba0aab9faab9eaab9dab9a488888896600264653001300800198041804800cdc3a400130080024888966002600460106ea800e2646644b300130050018acc004c030dd5003c00a2c806a2b30013370e9001000c56600260186ea801e00516403516402880504c966002601e00313259800980298059baa0078acc004c8cc004004dd6180818069baa0052259800800c528456600266ebcc044c038dd5180880080a4528c4cc008008c04800500c201e899b8700148052294100a44cdc3800a40268050dd698059807000c5900c192cc004cdc3a400460146ea8006297adef6c6089bab300e300b37540028048c8cc004004dd59807180798079807980798059baa0032259800800c5300103d87a8000899192cc004cdc8802800c56600266e3c014006266e95200033010300e0024bd7045300103d87a80004031133004004301200340306eb8c030004c03c00500d18049baa005375c601860126ea800e2c8038601000260066ea802229344d9590011", + "hash": "eaff18079b75649a8cfc35b99f8a145c4fabf5c02e239822316e9321" + }, + { + "title": "auth_token/mint.auth_token.else", + "redeemer": { + "schema": {} + }, + "parameters": [ + { + "title": "utxo_ref", + "schema": { + "$ref": "#/definitions/cardano~1transaction~1OutputReference" + } + } + ], + "compiledCode": "59017b010100229800aba2aba1aba0aab9faab9eaab9dab9a488888896600264653001300800198041804800cdc3a400130080024888966002600460106ea800e2646644b300130050018acc004c030dd5003c00a2c806a2b30013370e9001000c56600260186ea801e00516403516402880504c966002601e00313259800980298059baa0078acc004c8cc004004dd6180818069baa0052259800800c528456600266ebcc044c038dd5180880080a4528c4cc008008c04800500c201e899b8700148052294100a44cdc3800a40268050dd698059807000c5900c192cc004cdc3a400460146ea8006297adef6c6089bab300e300b37540028048c8cc004004dd59807180798079807980798059baa0032259800800c5300103d87a8000899192cc004cdc8802800c56600266e3c014006266e95200033010300e0024bd7045300103d87a80004031133004004301200340306eb8c030004c03c00500d18049baa005375c601860126ea800e2c8038601000260066ea802229344d9590011", + "hash": "eaff18079b75649a8cfc35b99f8a145c4fabf5c02e239822316e9321" + }, + { + "title": "proxy/spend.proxy.else", + "redeemer": { + "schema": {} + }, + "parameters": [ + { + "title": "auth_token", + "schema": { + "$ref": "#/definitions/cardano~1assets~1PolicyId" + } + } + ], + "compiledCode": "59011a010100229800aba2aba1aba0aab9faab9eaab9dab9a9bae0024888888896600266e212000323300100132330010013758601260146014600c6ea8c024c018dd5005912cc004006297ae0899912cc004c8cc004004c8cc004004dd59807180798059baa0042259800800c52f5c1132332232330010013756602000844b30010018801c4c8cc050dd39980a1ba90053301430110013301430120014bd7019801801980b001180a000a024375c6018002660060066022004601e0028068896600200314a115980099b8f375c601c6eb0c0380040222946266004004601e002804900c44cc02c008cc0100100062660080080028038c028004c02c005008112cc0040062900044cdc024004660040046014002803a29344d95900201", + "hash": "2baa0c6ed4aa555c15d53f6b85062d8661f380fb8d023d1b1535b035" + } + ], + "definitions": { + "ByteArray": { + "title": "ByteArray", + "dataType": "bytes" + }, + "Int": { + "dataType": "integer" + }, + "cardano/assets/PolicyId": { + "title": "PolicyId", + "dataType": "bytes" + }, + "cardano/transaction/OutputReference": { + "title": "OutputReference", + "description": "An `OutputReference` is a unique reference to an output on-chain. The `output_index`\n corresponds to the position in the output list of the transaction (identified by its id)\n that produced that output", + "anyOf": [ + { + "title": "OutputReference", + "dataType": "constructor", + "index": 0, + "fields": [ + { + "title": "transaction_id", + "$ref": "#/definitions/ByteArray" + }, + { + "title": "output_index", + "$ref": "#/definitions/Int" + } + ] + } + ] + }, + "types/MintPolarity": { + "title": "MintPolarity", + "anyOf": [ + { + "title": "RMint", + "dataType": "constructor", + "index": 0, + "fields": [] + }, + { + "title": "RBurn", + "dataType": "constructor", + "index": 1, + "fields": [] + } + ] + } + } +} \ No newline at end of file diff --git a/src/components/multisig/proxy/aiken-workspace/specs/1_auth_tokens.md b/src/components/multisig/proxy/aiken-workspace/specs/1_auth_tokens.md new file mode 100644 index 00000000..78afb6a1 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/specs/1_auth_tokens.md @@ -0,0 +1,15 @@ +# Auth Tokens - One Shot + +## Parameter + +- `utxo_ref`: UTxO to be spent at minting + +## User Action + +1. Mint - Redeemer `RMint` + + - Transaction hash as parameterized is included in input + +2. Burn - Redeemer `RBurn` + + - The current policy id only has negative minting value in transaction body. diff --git a/src/components/multisig/proxy/aiken-workspace/specs/2_proxy.md b/src/components/multisig/proxy/aiken-workspace/specs/2_proxy.md new file mode 100644 index 00000000..1f9abb9d --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/specs/2_proxy.md @@ -0,0 +1,19 @@ +# Specification - Crowdfund + +## Parameter + +- `auth_token`: The policy id of `AuthToken` + +## User Action + +1. SpendFunds + +2. RegisterDrep + +3. DeregisterDrep + +4. VoteasDrep + +5. RemoveEmptyInstance + + - `auth_token` from current input is burnt diff --git a/src/components/multisig/proxy/aiken-workspace/specs/_scripts.md b/src/components/multisig/proxy/aiken-workspace/specs/_scripts.md new file mode 100644 index 00000000..c44c42f3 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/specs/_scripts.md @@ -0,0 +1,20 @@ +# Aiken Crowdfunding + +## 1. Auth Tokens + +The tokens are held in a native script multisig wallet and have to be included in every transaction. + + +## 2. Proxy + +The validator that represents the actual treasury / drep + +## Param dependency tree + +1. First layer + + - `auth_tokens` - `utxo_ref` + +2. Second layer + + - `proxy` - param `auth_tokens` diff --git a/src/components/multisig/proxy/aiken-workspace/specs/application_setup_doc.md b/src/components/multisig/proxy/aiken-workspace/specs/application_setup_doc.md new file mode 100644 index 00000000..743db0a5 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/specs/application_setup_doc.md @@ -0,0 +1,13 @@ +# Application Setup Documentation + +## Setup + +The are 2 steps of setting up the applications: + +1. Minting `auth_token`, one time minting policy with empty token name with a quantity decided by the user. + + - Validation: 1.1 + +2. Sending the the `auth_token` to the owner multisig + + - Validation: N/A \ No newline at end of file diff --git a/src/components/multisig/proxy/aiken-workspace/specs/user_action_doc.md b/src/components/multisig/proxy/aiken-workspace/specs/user_action_doc.md new file mode 100644 index 00000000..dcb542e7 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/specs/user_action_doc.md @@ -0,0 +1,6 @@ +# User Actions Documentation + +## Multisig Users + + + diff --git a/src/components/multisig/proxy/aiken-workspace/validators/auth_token/mint.ak b/src/components/multisig/proxy/aiken-workspace/validators/auth_token/mint.ak new file mode 100644 index 00000000..11e14cf2 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/validators/auth_token/mint.ak @@ -0,0 +1,27 @@ +use aiken/collection/dict +use aiken/collection/list +use cardano/assets.{PolicyId} +use cardano/transaction.{OutputReference, Transaction} +use types.{MintPolarity, RBurn, RMint} + +validator auth_token(utxo_ref: OutputReference) { + mint(redeemer: MintPolarity, policy_id: PolicyId, self: Transaction) { + expect [Pair(_asset_name, quantity)] = + self.mint + |> assets.tokens(policy_id) + |> dict.to_pairs() + let Transaction { inputs, .. } = self + when redeemer is { + RMint -> { + let is_output_consumed = + list.any(inputs, fn(input) { input.output_reference == utxo_ref }) + is_output_consumed? && quantity == 10 + } + RBurn -> quantity == -10 + } + } + + else(_) { + fail + } +} diff --git a/src/components/multisig/proxy/aiken-workspace/validators/proxy/spend.ak b/src/components/multisig/proxy/aiken-workspace/validators/proxy/spend.ak new file mode 100644 index 00000000..f983ce93 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/validators/proxy/spend.ak @@ -0,0 +1,13 @@ +use aiken/collection/list +use cardano/assets.{PolicyId} +use cardano/transaction.{Transaction} +use cardano/script_context.{ScriptContext} +use cocktail.{outputs_with_policy} + +validator proxy(auth_token: PolicyId) { + else(ctx: ScriptContext) { + let Transaction { outputs, .. } = ctx.transaction + let auth_tokens_in_outputs = outputs_with_policy(outputs, auth_token) + list.length(auth_tokens_in_outputs) > 0 + } +} \ No newline at end of file diff --git a/src/components/multisig/proxy/aiken-workspace/validators/tests/auth_token/mint.ak b/src/components/multisig/proxy/aiken-workspace/validators/tests/auth_token/mint.ak new file mode 100644 index 00000000..c02a7111 --- /dev/null +++ b/src/components/multisig/proxy/aiken-workspace/validators/tests/auth_token/mint.ak @@ -0,0 +1,65 @@ +use auth_token/mint as auth_token_mint +use cardano/assets.{add, from_asset, zero} +use cardano/transaction.{Transaction, placeholder} +use mocktail.{ + complete, mint, mock_policy_id, mock_pub_key_address, mock_tx_hash, + mock_utxo_ref, mocktail_tx, tx_in, +} +use types.{RBurn, RMint} + + +const auth_token = mock_policy_id(0) + +test s1_mint_success_mint() { + let redeemer = RMint + let input_utxo = mock_utxo_ref(0, 1) + let policy_id = auth_token + + let tx = + mocktail_tx() + |> mint(True, 1, policy_id, "") + |> tx_in(True, mock_tx_hash(0), 1, zero, mock_pub_key_address(0, None)) + |> complete() + + auth_token_mint.auth_token.mint(input_utxo, redeemer, policy_id, tx) +} + +test s1_mint_fail_mint_no_utxo_ref_supply() { + let redeemer = RMint + let policy_id = auth_token + + let tx = + mocktail_tx() + |> mint(True, 1, policy_id, "") + |> tx_in(True, mock_tx_hash(0), 1, zero, mock_pub_key_address(0, None)) + |> complete() + !auth_token_mint.auth_token.mint(mock_utxo_ref(0, 0), redeemer, policy_id, tx) +} + +test s1_mint_success_burn() { + let redeemer = RBurn + let policy_id = auth_token + + let tx = Transaction { ..placeholder, mint: from_asset(policy_id, "", -1) } + auth_token_mint.auth_token.mint(mock_utxo_ref(0, 0), redeemer, policy_id, tx) +} + +test s1_mint_success_burn_with_other_minting() { + let redeemer = RBurn + let policy_id = auth_token + + let tx = + Transaction { + ..placeholder, + mint: from_asset(policy_id, "", -1) |> add(mock_policy_id(999), "", 1), + } + auth_token_mint.auth_token.mint(mock_utxo_ref(0, 0), redeemer, policy_id, tx) +} + +test s1_mint_fail_burn_with_mint() { + let redeemer = RBurn + let policy_id = auth_token + + let tx = Transaction { ..placeholder, mint: from_asset(policy_id, "", 1) } + !auth_token_mint.auth_token.mint(mock_utxo_ref(0, 0), redeemer, policy_id, tx) +} diff --git a/src/components/multisig/proxy/common.ts b/src/components/multisig/proxy/common.ts new file mode 100644 index 00000000..f620dafd --- /dev/null +++ b/src/components/multisig/proxy/common.ts @@ -0,0 +1,221 @@ +import { + serializePlutusScript, +} from "@meshsdk/core"; +import type { + IFetcher, + IWallet, + LanguageVersion, + MeshTxBuilder, + UTxO, +} from "@meshsdk/core"; + +export type MeshTxInitiatorInput = { + mesh: MeshTxBuilder; + fetcher?: IFetcher; + wallet?: IWallet; + networkId?: number; + stakeCredential?: string; + version?: number; +}; + +export class MeshTxInitiator { + mesh: MeshTxBuilder; + fetcher?: IFetcher; + wallet?: IWallet; + stakeCredential?: string; + networkId = 0; + version = 2; + languageVersion: LanguageVersion = "V2"; + + constructor({ + mesh, + fetcher, + wallet, + networkId = 0, + stakeCredential = "c08f0294ead5ab7ae0ce5471dd487007919297ba95230af22f25e575", + version = 2, + }: MeshTxInitiatorInput) { + this.mesh = mesh; + if (fetcher) { + this.fetcher = fetcher; + } + if (wallet) { + this.wallet = wallet; + } + + this.networkId = networkId; + switch (this.networkId) { + case 1: + this.mesh.setNetwork("mainnet"); + break; + default: + this.mesh.setNetwork("preprod"); + } + + this.version = version; + switch (this.version) { + case 1: + this.languageVersion = "V2"; + break; + default: + this.languageVersion = "V3"; + } + + if (stakeCredential) { + this.stakeCredential = stakeCredential; + } + } + + getScriptAddress = (scriptCbor: string) => { + const { address } = serializePlutusScript( + { code: scriptCbor, version: this.languageVersion }, + this.stakeCredential, + this.networkId, + ); + return address; + }; + + protected signSubmitReset = async () => { + const signedTx = this.mesh.completeSigning(); + const txHash = await this.mesh.submitTx(signedTx); + this.mesh.reset(); + return txHash; + }; + + protected queryUtxos = async (walletAddress: string): Promise => { + if (this.fetcher) { + const utxos = await this.fetcher.fetchAddressUTxOs(walletAddress); + return utxos; + } + return []; + }; + + protected getWalletDappAddress = async () => { + if (this.wallet) { + const usedAddresses = await this.wallet.getUsedAddresses(); + if (usedAddresses.length > 0) { + return usedAddresses[0]; + } + const unusedAddresses = await this.wallet.getUnusedAddresses(); + if (unusedAddresses.length > 0) { + return unusedAddresses[0]; + } + } + return ""; + }; + + protected getWalletCollateral = async (): Promise => { + if (this.wallet) { + const utxos = await this.wallet.getCollateral(); + return utxos[0]; + } + return undefined; + }; + + protected getWalletUtxosWithMinLovelace = async ( + lovelace: number, + providedUtxos: UTxO[] = [], + ) => { + let utxos: UTxO[] = providedUtxos; + if (this.wallet && (!providedUtxos || providedUtxos.length === 0)) { + utxos = await this.wallet.getUtxos(); + } + return utxos.filter((u) => { + const lovelaceAmount = u.output.amount.find( + (a: { unit: string; quantity: string }) => a.unit === "lovelace", + )?.quantity; + return Number(lovelaceAmount) > lovelace; + }); + }; + + protected getWalletUtxosWithToken = async ( + assetHex: string, + userUtxos: UTxO[] = [], + ) => { + let utxos: UTxO[] = userUtxos; + if (this.wallet && userUtxos.length === 0) { + utxos = await this.wallet.getUtxos(); + } + return utxos.filter((u) => { + const assetAmount = u.output.amount.find( + (a: { unit: string; quantity: string }) => a.unit === assetHex, + )?.quantity; + return Number(assetAmount) >= 1; + }); + }; + + protected getAddressUtxosWithMinLovelace = async ( + walletAddress: string, + lovelace: number, + providedUtxos: UTxO[] = [], + ) => { + let utxos: UTxO[] = providedUtxos; + if (this.fetcher && (!providedUtxos || providedUtxos.length === 0)) { + utxos = await this.fetcher.fetchAddressUTxOs(walletAddress); + } + return utxos.filter((u) => { + const lovelaceAmount = u.output.amount.find( + (a: { unit: string; quantity: string }) => a.unit === "lovelace", + )?.quantity; + return Number(lovelaceAmount) > lovelace; + }); + }; + + protected getAddressUtxosWithToken = async ( + walletAddress: string, + assetHex: string, + userUtxos: UTxO[] = [], + ) => { + let utxos: UTxO[] = userUtxos; + if (this.fetcher && userUtxos.length === 0) { + utxos = await this.fetcher.fetchAddressUTxOs(walletAddress); + } + return utxos.filter((u) => { + const assetAmount = u.output.amount.find( + (a: { unit: string; quantity: string }) => a.unit === assetHex, + )?.quantity; + return Number(assetAmount) >= 1; + }); + }; + + protected getWalletInfoForTx = async () => { + const utxos = await this.wallet?.getUtxos(); + const collateral = await this.getWalletCollateral(); + const walletAddress = await this.getWalletDappAddress(); + if (!utxos || utxos?.length === 0) { + throw new Error("No utxos found"); + } + if (!collateral) { + throw new Error("No collateral found"); + } + if (!walletAddress) { + throw new Error("No wallet address found"); + } + return { utxos, collateral, walletAddress }; + }; + + protected _getUtxoByTxHash = async ( + txHash: string, + scriptCbor?: string, + ): Promise => { + if (this.fetcher) { + const utxos = await this.fetcher?.fetchUTxOs(txHash); + let scriptUtxo = utxos[0]; + + if (scriptCbor) { + const scriptAddr = serializePlutusScript( + { code: scriptCbor, version: this.languageVersion }, + this.stakeCredential, + this.networkId, + ).address; + scriptUtxo = + utxos.find((utxo) => utxo.output.address === scriptAddr) ?? + utxos[0]; + } + + return scriptUtxo; + } + + return undefined; + }; +} diff --git a/src/components/multisig/proxy/index.ts b/src/components/multisig/proxy/index.ts new file mode 100644 index 00000000..e7c46daa --- /dev/null +++ b/src/components/multisig/proxy/index.ts @@ -0,0 +1,3 @@ +export { default as ProxyControl } from "./ProxyControl"; +export { default as ProxyControlExample } from "./ProxyControlExample"; +export { MeshProxyContract } from "./offchain"; \ No newline at end of file diff --git a/src/components/multisig/proxy/offchain.ts b/src/components/multisig/proxy/offchain.ts new file mode 100644 index 00000000..d0f5ebff --- /dev/null +++ b/src/components/multisig/proxy/offchain.ts @@ -0,0 +1,931 @@ +import { mConStr0, mOutputReference } from "@meshsdk/common"; +import { + resolveScriptHash, + serializePlutusScript, + applyParamsToScript, + resolveScriptHashDRepId, +} from "@meshsdk/core"; +import type { UTxO, MeshTxBuilder } from "@meshsdk/core"; +// import { parseDatumCbor } from "@meshsdk/core-cst"; + +import { MeshTxInitiator } from "./common"; +import type { MeshTxInitiatorInput } from "./common"; +import blueprint from "./aiken-workspace/plutus.json"; + +/** + * Mesh Plutus NFT contract class + * + * This NFT minting script enables users to mint NFTs with an automatically incremented index, which increases by one for each newly minted NFT. + * + * To facilitate this process, the first step is to set up a one-time minting policy by minting an oracle token. This oracle token is essential as it holds the current state and index of the NFTs, acting as a reference for the minting sequence. + * + * With each new NFT minted, the token index within the oracle is incremented by one, ensuring a consistent and orderly progression in the numbering of the NFTs. + */ +// Cache for DRep status to avoid multiple API calls +const drepStatusCache = new Map(); +const CACHE_DURATION = 5 * 60 * 1000; // 5 minutes + +export class MeshProxyContract extends MeshTxInitiator { + paramUtxo: UTxO["input"] = { outputIndex: 0, txHash: "" }; + proxyAddress?: string; + stakeCredential?: string | undefined; + networkId: number; + msCbor?: string; // Multisig script cbor + + // Reset method to clear state for retry + reset() { + this.paramUtxo = { outputIndex: 0, txHash: "" }; + this.proxyAddress = undefined; + this.stakeCredential = undefined; + } + + // Static method to clear DRep status cache + static clearDrepStatusCache(drepId?: string) { + if (drepId) { + drepStatusCache.delete(drepId); + } else { + drepStatusCache.clear(); + } + } + + getAuthTokenCbor = () => { + return applyParamsToScript(blueprint.validators[0]!.compiledCode, [ + mOutputReference(this.paramUtxo.txHash, this.paramUtxo.outputIndex), + ]); + }; + getAuthTokenPolicyId = () => { + return resolveScriptHash(this.getAuthTokenCbor(), "V3"); + }; + + getProxyCbor = () => { + const authTokenPolicyId = this.getAuthTokenPolicyId(); + return applyParamsToScript(blueprint.validators[2]!.compiledCode, [ + authTokenPolicyId, + ]); + }; + + setProxyAddress = () => { + const proxyAddress = serializePlutusScript( + { + code: this.getProxyCbor(), + version: "V3", + }, + this.stakeCredential, + this.networkId, + ).address; + this.proxyAddress = proxyAddress; + return proxyAddress; + }; + + constructor( + inputs: MeshTxInitiatorInput, + contract: { + paramUtxo?: UTxO["input"]; + }, + msCbor?: string, + ) { + super(inputs); + this.stakeCredential = inputs.stakeCredential; + this.networkId = inputs.networkId ?? 0; + this.msCbor = msCbor; + + // Set the proxyAddress if paramUtxo is provided + if (contract.paramUtxo) { + this.paramUtxo = contract.paramUtxo; + this.setProxyAddress(); + } + } + + /** + * Set up a proxy address with fixed amount of 10 auth tokens, that will be sent to the owner multisig + * Moving an auth token unlocks the proxy address. + * + * @returns - Transaction hex to be signed by the owner multisig + * + * @example + * ```typescript + * const { tx, paramUtxo } = await contract.setupProxy(); + * ``` + */ + setupProxy = async (msUtxos?: UTxO[], msWalletAddress?: string) => { + if (this.msCbor && !msUtxos && !msWalletAddress) { + throw new Error( + "No UTxOs and wallet address for multisig script cbor found", + ); + } + + const walletInfo = await this.getWalletInfoForTx(); + let { utxos, walletAddress } = walletInfo; + const { collateral } = walletInfo; + + if (this.msCbor && msUtxos && msWalletAddress) { + utxos = msUtxos; + walletAddress = msWalletAddress; + } + + //look for, get and set a paramUtxo for minting the AuthToken + if (!utxos || utxos.length <= 0) { + throw new Error("No UTxOs found"); + } + const paramUtxo = utxos?.find((utxo) => + utxo.output.amount.some( + (asset) => asset.unit === "lovelace" && Number(asset.quantity) >= 20000000, + ), + ); + if (!paramUtxo) { + throw new Error( + "Insufficicient balance. Create one utxo holding at Least 20 ADA.", + ); + } + this.paramUtxo = paramUtxo.input; + + //Set proxyAddress depending on the paramUtxo + const proxyAddress = this.setProxyAddress(); + if (!proxyAddress) { + throw new Error("Proxy address not set"); + } + + //prepare AuthToken mint + const policyId = this.getAuthTokenPolicyId(); + const tokenName = ""; + + // Try completing the transaction step by step + const tx = this.mesh.txIn( + paramUtxo.input.txHash, + paramUtxo.input.outputIndex, + paramUtxo.output.amount, + paramUtxo.output.address, + ); + // Add the multisig script cbor if it exists + if (this.msCbor) { + tx.txInScript(this.msCbor); + } + + tx.mintPlutusScriptV3() + .mint("10", policyId, tokenName) + .mintingScript(this.getAuthTokenCbor()) + .mintRedeemerValue(mConStr0([])) + .txOut(proxyAddress, [{ unit: "lovelace", quantity: "1000000" }]); + + for (let i = 0; i < 10; i++) { + tx.txOut(walletAddress, [{ unit: policyId, quantity: "1" }]); + } + + tx.txInCollateral( + collateral.input.txHash, + collateral.input.outputIndex, + collateral.output.amount, + collateral.output.address, + ).changeAddress(walletAddress); + + const txHex = tx; + + return { + tx: txHex, + paramUtxo: paramUtxo.input, + authTokenId: policyId, + proxyAddress: proxyAddress, + }; + }; + + spendProxySimple = async ( + outputs: { address: string; unit: string; amount: string }[], + msUtxos?: UTxO[], + msWalletAddress?: string, + ) => { + if (this.msCbor && !msUtxos && !msWalletAddress) { + throw new Error( + "No UTxOs and wallet address for multisig script cbor found", + ); + } + const walletInfo = await this.getWalletInfoForTx(); + let { utxos, walletAddress } = walletInfo; + const { collateral } = walletInfo; + // If multisig inputs are provided, use them instead of the wallet inputs + if (this.msCbor && msUtxos && msWalletAddress) { + utxos = msUtxos; + walletAddress = msWalletAddress; + } + if (!utxos || utxos.length <= 0) { + throw new Error("No UTxOs found"); + } + if (!walletAddress) { + throw new Error("No wallet address found"); + } + if (!collateral) { + throw new Error("No collateral found"); + } + if (this.proxyAddress === undefined) { + throw new Error("Proxy address not set. Please setupProxy first."); + } + const blockchainProvider = this.mesh.fetcher; + if (!blockchainProvider) { + throw new Error("Blockchain provider not found"); + } + + const proxyUtxos = await blockchainProvider.fetchAddressUTxOs( + this.proxyAddress, + ); + + // Calculate spend requirements and ensure coverage by proxy UTxOs + const REQUIRED_FEE_BUFFER = BigInt(500_000); // 0.5 ADA buffer in lovelace + + const requiredByUnit = new Map(); + for (const out of outputs) { + const prev = requiredByUnit.get(out.unit) ?? BigInt(0); + requiredByUnit.set(out.unit, prev + BigInt(out.amount)); + } + // Add buffer to lovelace + const lovelaceNeed = + (requiredByUnit.get("lovelace") ?? BigInt(0)) + REQUIRED_FEE_BUFFER; + requiredByUnit.set("lovelace", lovelaceNeed); + + const availableByUnit = new Map(); + for (const utxo of proxyUtxos) { + for (const asset of utxo.output.amount) { + const prev = availableByUnit.get(asset.unit) ?? BigInt(0); + availableByUnit.set(asset.unit, prev + BigInt(asset.quantity)); + } + } + + for (const [unit, needed] of requiredByUnit.entries()) { + const available = availableByUnit.get(unit) ?? BigInt(0); + if (available < needed) { + throw new Error( + `Insufficient proxy balance for ${unit}. Needed: ${needed.toString()}, Available: ${available.toString()}`, + ); + } + } + + // Select as few UTxOs as possible to cover required amounts + const remainingByUnit = new Map(requiredByUnit); + const candidateUtxos = [...proxyUtxos]; + const selectedUtxos: typeof proxyUtxos = []; + + const hasRemaining = () => { + for (const value of remainingByUnit.values()) { + if (value > BigInt(0)) return true; + } + return false; + }; + + const contributionScore = (utxo: (typeof proxyUtxos)[number]) => { + let score = BigInt(0); + for (const asset of utxo.output.amount) { + const remaining = remainingByUnit.get(asset.unit) ?? BigInt(0); + if (remaining > BigInt(0)) { + const qty = BigInt(asset.quantity); + score += qty < remaining ? qty : remaining; + } + } + return score; + }; + + while (hasRemaining()) { + let bestIdx = -1; + let bestScore = BigInt(0); + for (let i = 0; i < candidateUtxos.length; i++) { + const s = contributionScore(candidateUtxos[i]!); + if (s > bestScore) { + bestScore = s; + bestIdx = i; + } + } + if (bestIdx === -1 || bestScore === BigInt(0)) { + throw new Error( + "Unable to select proxy UTxOs to cover required amounts.", + ); + } + const chosen = candidateUtxos.splice(bestIdx, 1)[0]!; + selectedUtxos.push(chosen); + // Decrease remaining by chosen utxo's amounts + for (const asset of chosen.output.amount) { + const remaining = remainingByUnit.get(asset.unit) ?? BigInt(0); + if (remaining > BigInt(0)) { + const qty = BigInt(asset.quantity); + const newRemaining = remaining - (qty < remaining ? qty : remaining); + remainingByUnit.set(asset.unit, newRemaining); + } + } + } + + const freeProxyUtxos = selectedUtxos; + const paramScriptAT = this.getAuthTokenCbor(); + const policyIdAT = resolveScriptHash(paramScriptAT, "V3"); + const authTokenUtxos = utxos.filter((utxo) => + utxo.output.amount.some((asset) => asset.unit === policyIdAT), + ); + + if (!authTokenUtxos || authTokenUtxos.length === 0) { + throw new Error("No AuthToken found at control wallet address"); + } + //ToDo check if AuthToken utxo is used in a pending transaction and blocked then use a free AuthToken + const authTokenUtxo = authTokenUtxos[0]; + if (!authTokenUtxo) { + throw new Error("No AuthToken found"); + } + const authTokenUtxoAmt = authTokenUtxo.output.amount; + if (!authTokenUtxoAmt) { + throw new Error("No AuthToken amount found"); + } + + //prepare Proxy spend + //1 Get + const txHex = this.mesh; + + for (const input of freeProxyUtxos) { + txHex + .spendingPlutusScriptV3() + .txIn( + input.input.txHash, + input.input.outputIndex, + input.output.amount, + input.output.address, + ) + .txInScript(this.getProxyCbor()) + .txInInlineDatumPresent() + .txInRedeemerValue(mConStr0([])); + } + + txHex + .txIn( + authTokenUtxo.input.txHash, + authTokenUtxo.input.outputIndex, + authTokenUtxo.output.amount, + authTokenUtxo.output.address, + ) + .txInCollateral( + collateral.input.txHash, + collateral.input.outputIndex, + collateral.output.amount, + collateral.output.address, + ) + .txOut(walletAddress, [{ unit: policyIdAT, quantity: "1" }]); + + for (const output of outputs) { + txHex.txOut(output.address, [ + { unit: output.unit, quantity: output.amount }, + ]); + } + + txHex.changeAddress(this.proxyAddress); + + // Add the multisig script cbor if it exists (like in setupProxy) + if (this.msCbor) { + txHex.txInScript(this.msCbor); + } + + return txHex; + }; + + manageProxyDrep = async ( + action: "register" | "deregister" | "update", + anchorUrl?: string, + anchorHash?: string, + msUtxos?: UTxO[], + msWalletAddress?: string, + ) => { + if (this.proxyAddress === undefined) { + throw new Error("Proxy address not set. Please setupProxy first."); + } + if ( + (action === "register" || action === "update") && + (!anchorUrl || !anchorHash) + ) { + throw new Error( + "Anchor URL and hash are required for register and update actions", + ); + } + if (this.msCbor && !msUtxos && !msWalletAddress) { + throw new Error( + "No UTxOs and wallet address for multisig script cbor found", + ); + } + const walletInfo2 = await this.getWalletInfoForTx(); + let { utxos, walletAddress } = walletInfo2; + const { collateral } = walletInfo2; + // If multisig inputs are provided, use them instead of the wallet inputs + if (this.msCbor && msUtxos && msWalletAddress) { + utxos = msUtxos; + walletAddress = msWalletAddress; + } + if (!utxos || utxos.length <= 0) { + throw new Error("No UTxOs found"); + } + if (!walletAddress) { + throw new Error("No wallet address found"); + } + if (!collateral) { + throw new Error("No collateral found"); + } + if (this.proxyAddress === undefined) { + throw new Error("Proxy address not set. Please setupProxy first."); + } + + const blockchainProvider = this.mesh.fetcher; + if (!blockchainProvider) { + throw new Error("Blockchain provider not found"); + } + + const paramScriptAT = this.getAuthTokenCbor(); + const policyIdAT = resolveScriptHash(paramScriptAT, "V3"); + const authTokenUtxos = utxos.filter((utxo) => + utxo.output.amount.some((asset) => asset.unit === policyIdAT), + ); + + if (!authTokenUtxos || authTokenUtxos.length === 0) { + throw new Error("No AuthToken found at control wallet address"); + } + //ToDo check if AuthToken utxo is used in a pending transaction and blocked then use a free AuthToken + const authTokenUtxo = authTokenUtxos[0]; + if (!authTokenUtxo) { + throw new Error("No AuthToken found"); + } + const authTokenUtxoAmt = authTokenUtxo.output.amount; + if (!authTokenUtxoAmt) { + throw new Error("No AuthToken amount found"); + } + + const proxyCbor = this.getProxyCbor(); + const proxyScriptHash = resolveScriptHash(proxyCbor, "V3"); + const drepId = resolveScriptHashDRepId(proxyScriptHash); + + const txHex = this.mesh; + txHex.txIn( + authTokenUtxo.input.txHash, + authTokenUtxo.input.outputIndex, + authTokenUtxo.output.amount, + authTokenUtxo.output.address, + ); + + if (this.msCbor) { + txHex.txInScript(this.msCbor); + } + txHex.txInCollateral( + collateral.input.txHash, + collateral.input.outputIndex, + collateral.output.amount, + collateral.output.address, + ); + + // add more utxo inputs until the required amount is reached, use utxos list. + // Register requires 505 ADA, deregister and update only need 2 ADA + const requiredAmount = + action === "register" ? BigInt(505000000) : BigInt(2000000); + let totalAmount = BigInt(0); + for (const utxo of utxos) { + if (totalAmount >= requiredAmount) { + break; + } + txHex.txIn( + utxo.input.txHash, + utxo.input.outputIndex, + utxo.output.amount, + utxo.output.address, + ); + if (this.msCbor) { + txHex.txInScript(this.msCbor); + } + totalAmount += BigInt( + (utxo.output.amount.find((asset: { unit: string; quantity: string }) => asset.unit === "lovelace") + ?.quantity) ?? "0", + ); + } + + txHex.txOut(walletAddress, [{ unit: policyIdAT, quantity: "1" }]); + + // Add the appropriate certificate based on action + if (action === "register") { + txHex.drepRegistrationCertificate(drepId, { + anchorUrl: anchorUrl!, + anchorDataHash: anchorHash!, + }); + } else if (action === "deregister") { + txHex.drepDeregistrationCertificate(drepId, "500000000"); + } else if (action === "update") { + txHex.drepUpdateCertificate(drepId, { + anchorUrl: anchorUrl!, + anchorDataHash: anchorHash!, + }); + } + + txHex + .certificateScript(this.getProxyCbor(), "V3") + .certificateRedeemerValue(mConStr0([])) + .changeAddress(walletAddress); + + return txHex; + }; + + /** + * Register a proxy DRep + * + * @param anchorUrl - URL for the DRep metadata + * @param anchorHash - Hash of the DRep metadata + * @param msUtxos - Optional multisig UTxOs + * @param msWalletAddress - Optional multisig wallet address + * @returns - Transaction hex for signing + */ + registerProxyDrep = async ( + anchorUrl: string, + anchorHash: string, + msUtxos?: UTxO[], + msWalletAddress?: string, + ) => { + return this.manageProxyDrep( + "register", + anchorUrl, + anchorHash, + msUtxos, + msWalletAddress, + ); + }; + + /** + * Deregister a proxy DRep + * + * @param msUtxos - Optional multisig UTxOs + * @param msWalletAddress - Optional multisig wallet address + * @returns - Transaction hex for signing + */ + deregisterProxyDrep = async (msUtxos?: UTxO[], msWalletAddress?: string) => { + return this.manageProxyDrep( + "deregister", + undefined, + undefined, + msUtxos, + msWalletAddress, + ); + }; + + /** + * Update a proxy DRep + * + * @param anchorUrl - URL for the DRep metadata + * @param anchorHash - Hash of the DRep metadata + * @param msUtxos - Optional multisig UTxOs + * @param msWalletAddress - Optional multisig wallet address + * @returns - Transaction hex for signing + */ + updateProxyDrep = async ( + anchorUrl: string, + anchorHash: string, + msUtxos?: UTxO[], + msWalletAddress?: string, + ) => { + return this.manageProxyDrep( + "update", + anchorUrl, + anchorHash, + msUtxos, + msWalletAddress, + ); + }; + + /** + * Fetch the balance of the proxy address + * + * @returns - Array of assets with their quantities at the proxy address + * + * @example + * ```typescript + * const balance = await contract.getProxyBalance(); + * console.log(balance); // [{ unit: "lovelace", quantity: "1000000" }, ...] + * ``` + */ + getProxyBalance = async () => { + if (this.proxyAddress === undefined) { + throw new Error("Proxy address not set. Please setupProxy first."); + } + + const blockchainProvider = this.mesh.fetcher; + if (!blockchainProvider) { + throw new Error("Blockchain provider not found"); + } + + try { + const utxos = await blockchainProvider.fetchAddressUTxOs(this.proxyAddress); + + // Aggregate all assets from UTxOs + const balanceMap = new Map(); + + for (const utxo of utxos) { + for (const asset of utxo.output.amount) { + const currentAmount = balanceMap.get(asset.unit) ?? BigInt(0); + balanceMap.set(asset.unit, currentAmount + BigInt(asset.quantity)); + } + } + + // Convert back to string format for consistency + const balance = Array.from(balanceMap.entries()).map( + ([unit, quantity]) => ({ + unit, + quantity: quantity.toString(), + }), + ); + + return balance; + } catch (error: unknown) { + const errorMessage = error instanceof Error ? error.message : 'Unknown error'; + throw new Error(`Failed to fetch proxy balance: ${errorMessage}`); + } + }; + + getDrepId = () => { + const proxyCbor = this.getProxyCbor(); + const proxyScriptHash = resolveScriptHash(proxyCbor, "V3"); + return resolveScriptHashDRepId(proxyScriptHash); + }; + + getDrepStatus = async (forceRefresh = false) => { + const drepId = this.getDrepId(); + + // Check cache first + const cached = drepStatusCache.get(drepId); + if (!forceRefresh && cached && (Date.now() - cached.timestamp) < CACHE_DURATION) { + return cached.data; + } + + if (!this.mesh.fetcher) { + throw new Error("Blockchain provider not found"); + } + + try { + const drepStatus = await this.mesh.fetcher.get( + `/governance/dreps/${drepId}`, + ); + + // Cache the successful result + drepStatusCache.set(drepId, { + data: drepStatus, + timestamp: Date.now() + }); + + return drepStatus; + } catch (error: unknown) { + // Parse the error if it's a stringified JSON + let parsedError: unknown = error; + if (typeof error === 'string') { + try { + parsedError = JSON.parse(error); + } catch { + // If parsing fails, use the original error + } + } + + // Handle specific error cases - check multiple possible 404 indicators + const errorObj = error as Record; + const parsedObj = parsedError as Record; + const is404 = errorObj?.status === 404 || + (errorObj?.response as Record)?.status === 404 || + (errorObj?.data as Record)?.status_code === 404 || + parsedObj?.status === 404 || + (parsedObj?.data as Record)?.status_code === 404 || + (errorObj?.message as string)?.includes('404') || + (errorObj?.message as string)?.includes('Not Found') || + (errorObj?.message as string)?.includes('not found') || + (errorObj?.message as string)?.includes('NOT_FOUND') || + ((errorObj?.response as Record)?.data as Record)?.status_code === 404 || + ((errorObj?.data as Record)?.status_code === 404); + + if (is404) { + // DRep not registered yet - cache null result + drepStatusCache.set(drepId, { + data: null, + timestamp: Date.now() + }); + return null; + } + + // For other errors, don't cache and re-throw + const errorMessage = error instanceof Error ? error.message : 'Unknown error'; + console.log(`Failed to fetch DRep status: ${errorMessage}`); + } + }; + + /** + * Get DRep delegators and their delegation amounts + * @param forceRefresh Whether to bypass cache + * @returns Array of delegators with addresses and amounts, plus total delegation + */ + getDrepDelegators = async (forceRefresh = false) => { + const drepId = this.getDrepId(); + + // Check cache first + const cacheKey = `${drepId}_delegators`; + const cached = drepStatusCache.get(cacheKey); + if (!forceRefresh && cached && (Date.now() - cached.timestamp) < CACHE_DURATION) { + return cached.data; + } + + if (!this.mesh.fetcher) { + throw new Error("Blockchain provider not found"); + } + + try { + const delegators = await this.mesh.fetcher.get( + `/governance/dreps/${drepId}/delegators?count=100&page=1&order=asc`, + ); + + // Calculate total delegation amount + const totalDelegation = delegators.reduce((sum: bigint, delegator: { amount: string }) => { + return sum + BigInt(delegator.amount); + }, BigInt(0)); + + const result = { + delegators, + totalDelegation: totalDelegation.toString(), + totalDelegationADA: Number(totalDelegation) / 1000000, // Convert to ADA + count: delegators.length + }; + + // Cache the successful result + drepStatusCache.set(cacheKey, { + data: result, + timestamp: Date.now() + }); + + return result; + } catch (error: unknown) { + const errorMessage = error instanceof Error ? error.message : 'Unknown error'; + console.log(`Failed to fetch DRep delegators: ${errorMessage}`); + + // Return empty result for errors + return { + delegators: [], + totalDelegation: "0", + totalDelegationADA: 0, + count: 0 + }; + } + }; + + /** + * Vote on governance proposals using proxy DRep + * @param votes Array of vote objects with proposalId, voteKind, and optional metadata + * @param msUtxos Multisig UTxOs for transaction inputs (optional) + * @param msWalletAddress Multisig wallet address (optional) + * @returns Transaction builder + */ + voteProxyDrep = async ( + votes: Array<{ + proposalId: string; + voteKind: "Yes" | "No" | "Abstain"; + metadata?: unknown; + }>, + msUtxos?: UTxO[], + msWalletAddress?: string, + ): Promise => { + if (!votes || votes.length === 0) { + throw new Error("No votes provided"); + } + + // Get wallet info for transaction + const walletInfo = await this.getWalletInfoForTx(); + + // Use multisig inputs if provided, otherwise use regular wallet + const utxos = msUtxos ?? walletInfo.utxos; + const walletAddress = msWalletAddress ?? walletInfo.walletAddress; + + // Always get collateral from user's regular wallet + let collateral: UTxO; + try { + const collateralInfo = await this.getWalletInfoForTx(); + const foundCollateral = collateralInfo.utxos.find((utxo: UTxO) => + utxo.output.amount.some( + (amount: { unit: string; quantity: string }) => + amount.unit === "lovelace" && + BigInt(amount.quantity) >= BigInt(5000000), + ), + ); + if (!foundCollateral) { + throw new Error( + "No suitable collateral UTxO found in regular wallet. Please add at least 5 ADA to your regular wallet.", + ); + } + collateral = foundCollateral; + } catch { + throw new Error( + "Failed to get collateral from regular wallet. Please ensure you have at least 5 ADA in your regular wallet for transaction collateral.", + ); + } + + if (!walletAddress) { + throw new Error("No wallet address found"); + } + if (!collateral) { + throw new Error("No collateral found"); + } + if (this.proxyAddress === undefined) { + throw new Error("Proxy address not set. Please setupProxy first."); + } + + const blockchainProvider = this.mesh.fetcher; + if (!blockchainProvider) { + throw new Error("Blockchain provider not found"); + } + + const paramScriptAT = this.getAuthTokenCbor(); + const policyIdAT = resolveScriptHash(paramScriptAT, "V3"); + const authTokenUtxos = utxos.filter((utxo) => + utxo.output.amount.some((asset) => asset.unit === policyIdAT), + ); + + if (!authTokenUtxos || authTokenUtxos.length === 0) { + throw new Error("No AuthToken found at control wallet address"); + } + + const authTokenUtxo = authTokenUtxos[0]; + if (!authTokenUtxo) { + throw new Error("No AuthToken found"); + } + const authTokenUtxoAmt = authTokenUtxo.output.amount; + if (!authTokenUtxoAmt) { + throw new Error("No AuthToken amount found"); + } + + const proxyCbor = this.getProxyCbor(); + const proxyScriptHash = resolveScriptHash(proxyCbor, "V3"); + const drepId = resolveScriptHashDRepId(proxyScriptHash); + + const txHex = this.mesh; + + // 1. Add AuthToken UTxO first (following manageProxyDrep pattern) + txHex.txIn( + authTokenUtxo.input.txHash, + authTokenUtxo.input.outputIndex, + authTokenUtxo.output.amount, + authTokenUtxo.output.address, + ); + + if (this.msCbor) { + txHex.txInScript(this.msCbor); + } + + // 2. Add collateral + txHex.txInCollateral( + collateral.input.txHash, + collateral.input.outputIndex, + collateral.output.amount, + collateral.output.address, + ); + + // 3. Add additional UTxOs if needed (for voting fees) + const requiredAmount = BigInt(2000000); // 2 ADA for voting + let totalAmount = BigInt(0); + for (const utxo of utxos) { + if (totalAmount >= requiredAmount) { + break; + } + txHex.txIn( + utxo.input.txHash, + utxo.input.outputIndex, + utxo.output.amount, + utxo.output.address, + ); + if (this.msCbor) { + txHex.txInScript(this.msCbor); + } + totalAmount += BigInt( + (utxo.output.amount.find((asset: { unit: string; quantity: string }) => asset.unit === "lovelace") + ?.quantity) ?? "0", + ); + } + + // 4. Add output (return AuthToken) + txHex.txOut(walletAddress, [{ unit: policyIdAT, quantity: "1" }]); + + + // 5. Add votes for each proposal + for (const vote of votes) { + const [txHash, certIndex] = vote.proposalId.split("#"); + if (!txHash || certIndex === undefined) { + throw new Error(`Invalid proposal ID format: ${vote.proposalId}`); + } + + txHex + .votePlutusScriptV3() + .vote( + { + type: "DRep", + drepId: drepId, + }, + { + txHash: txHash, + txIndex: parseInt(certIndex), + }, + { + voteKind: vote.voteKind, + }, + ) + .voteScript(this.getProxyCbor()) + .voteRedeemerValue("") + } + + // 6. Add certificate script and redeemer (following manageProxyDrep pattern) + txHex + .changeAddress(walletAddress); + + return txHex; + }; +} diff --git a/src/components/pages/homepage/wallets/new-wallet-flow/create/ReviewNativeScript.tsx b/src/components/pages/homepage/wallets/new-wallet-flow/create/ReviewNativeScript.tsx index 8efc602a..002e6b92 100644 --- a/src/components/pages/homepage/wallets/new-wallet-flow/create/ReviewNativeScript.tsx +++ b/src/components/pages/homepage/wallets/new-wallet-flow/create/ReviewNativeScript.tsx @@ -84,7 +84,20 @@ export default function ReviewNativeScript({ }, [appWallet, walletsUtxos]); if (!mWallet) return null; - const dSAddr = deserializeAddress(mWallet.getScript().address); + + let dSAddr; + try { + dSAddr = deserializeAddress(mWallet.getScript().address); + } catch (error) { + console.error("Failed to get script address:", error); + return ( +
+

+ Unable to generate script address. Please check your wallet configuration. +

+
+ ); + } const menuItems = [ { id: "basics", label: "Basics" }, diff --git a/src/components/pages/wallet/dapps/index.tsx b/src/components/pages/wallet/dapps/index.tsx index 6c2ac479..2a003238 100644 --- a/src/components/pages/wallet/dapps/index.tsx +++ b/src/components/pages/wallet/dapps/index.tsx @@ -2,6 +2,7 @@ import { useEffect, useState } from "react"; import { Button } from "@/components/ui/button"; import { ExternalLink, Code, Database, ArrowLeft, CheckCircle, AlertTriangle, Info } from "lucide-react"; +import ProxyControl from "@/components/multisig/proxy/ProxyControl"; function DappCard({ title, description, url }: { title: string; description: string; url: string }) { const [ogImage, setOgImage] = useState(null); @@ -381,6 +382,11 @@ export default function PageDapps() {
+ {/* Proxy Control Section */} +
+ +
+ {/* dApps Grid */}
diff --git a/src/components/pages/wallet/governance/ballot/ballot.tsx b/src/components/pages/wallet/governance/ballot/ballot.tsx index d0b2b997..3a983d04 100644 --- a/src/components/pages/wallet/governance/ballot/ballot.tsx +++ b/src/components/pages/wallet/governance/ballot/ballot.tsx @@ -6,6 +6,8 @@ import type { Quantity, Unit, UTxO } from "@meshsdk/core"; import { useWalletsStore } from "@/lib/zustand/wallets"; import useMultisigWallet from "@/hooks/useMultisigWallet"; import { useToast } from "@/hooks/use-toast"; +import { useWallet } from "@meshsdk/react"; +import { useUserStore } from "@/lib/zustand/user"; import React, { useState } from "react"; import CardUI from "@/components/ui/card-content"; import { @@ -19,6 +21,8 @@ import { import { Button } from "@/components/ui/button"; import { api } from "@/utils/api"; import { ToastAction } from "@/components/ui/toast"; +import { useProxy } from "@/hooks/useProxy"; +import { MeshProxyContract } from "@/components/multisig/proxy/offchain"; const GovAction = 1; @@ -62,6 +66,20 @@ export default function BallotCard({ const { multisigWallet } = useMultisigWallet(); const [loading, setLoading] = useState(false); + // Proxy state + const { isProxyEnabled, selectedProxyId } = useProxy(); + const { wallet } = useWallet(); + const userAddress = useUserStore((state) => state.userAddress); + + // Get proxies for proxy mode + const { data: proxies } = api.proxy.getProxiesByUserOrWallet.useQuery( + { + walletId: appWallet?.id || undefined, + userAddress: userAddress || undefined, + }, + { enabled: !!(appWallet?.id || userAddress) } + ); + // CreateBallot mutation const createBallot = api.ballot.create.useMutation(); // Get ballots for wallet @@ -86,6 +104,124 @@ export default function BallotCard({ }, [getBallots.data]); + // Proxy ballot vote submission logic + async function handleSubmitProxyVote() { + if (!selectedBallot || !Array.isArray(selectedBallot.items) || selectedBallot.items.length === 0) { + toast({ + title: "No proposals in ballot", + description: "There are no proposals to vote on in this ballot.", + duration: 2000, + }); + return; + } + if (!utxos || utxos.length === 0) { + toast({ + title: "No UTxOs available", + description: "No UTxOs are available to build the transaction.", + duration: 2000, + }); + return; + } + if (!isProxyEnabled || !selectedProxyId) { + toast({ + title: "Proxy Error", + description: "Proxy mode not enabled or no proxy selected", + variant: "destructive", + }); + return; + } + + setLoading(true); + try { + // Get the selected proxy + const proxy = proxies?.find((p: any) => p.id === selectedProxyId); + if (!proxy) { + toast({ + title: "Proxy Error", + description: "Selected proxy not found", + variant: "destructive", + }); + return; + } + + // Create proxy contract instance + const meshTxBuilder = getTxBuilder(network); + const proxyContract = new MeshProxyContract( + { + mesh: meshTxBuilder, + wallet: wallet, + networkId: network, + }, + { + paramUtxo: JSON.parse(proxy.paramUtxo), + }, + appWallet.scriptCbor, + ); + proxyContract.proxyAddress = proxy.proxyAddress; + + // Prepare votes array + const votes = selectedBallot.items.map((proposalId: string, index: number) => ({ + proposalId, + voteKind: (selectedBallot.choices?.[index] ?? "Abstain") as "Yes" | "No" | "Abstain", + })); + + // Vote using proxy + const txBuilder = await proxyContract.voteProxyDrep(votes, utxos, multisigWallet?.getScript().address); + + await newTransaction({ + txBuilder: txBuilder, + description: `Proxy Ballot Vote: ${selectedBallot.description || ""}`, + toastMessage: "Proxy ballot vote transaction has been created", + }); + + toast({ + title: "Proxy Ballot Vote Successful", + description: `Your proxy ballot vote has been recorded.`, + duration: 5000, + }); + + setAlert("Proxy ballot vote transaction successfully created!"); + await getBallots.refetch(); + onBallotChanged?.(); + } catch (error: unknown) { + if ( + error instanceof Error && + error.message.includes("User rejected transaction") + ) { + toast({ + title: "Transaction Aborted", + description: "You canceled the proxy ballot vote transaction.", + duration: 1000, + }); + } else { + toast({ + title: "Proxy Ballot Vote Failed", + description: `Error: ${error instanceof Error ? error.message : String(error)}`, + duration: 10000, + action: ( + { + navigator.clipboard.writeText(JSON.stringify(error)); + toast({ + title: "Error Copied", + description: "Error details copied to clipboard.", + duration: 5000, + }); + }} + > + Copy Error + + ), + variant: "destructive", + }); + console.error("Proxy ballot vote transaction error:", error); + } + } finally { + setLoading(false); + } + } + // Ballot vote submission logic async function handleSubmitVote() { if (!selectedBallot || !Array.isArray(selectedBallot.items) || selectedBallot.items.length === 0) { @@ -350,12 +486,23 @@ export default function BallotCard({ )} {selectedBallot && ( <> + {isProxyEnabled && !selectedProxyId && ( +
+

+ Proxy Mode Active - Select a proxy to continue +

+

+ Go to the Proxy Control panel above and select a proxy to enable ballot voting. +

+
+ )} + {/* Global Proxy Toggle */} +
+ Proxy Mode: + +
+ + {proxies.length > 0 && ( +
+ + {selectedProxyId && ( + + )} +
+ )}
- {/* Status */} -
- -
-
-
- - {isDRepRegistered ? "Registered" : "Not registered"} - + {/* Content */} +
+ + + {/* DRep Information - Single Row */} +
+ {/* DRep ID */} +
+
+ + DRep ID +
+
+
+ + {loadingProxyDrep ? "..." : displayDrepId} + +
+ +
+
+ + {/* DRep Status */} +
+
+ + Status +
+
+ {loadingProxyDrep ? ( +
+
+ Loading... +
+ ) : ( + + + +
+
+ +

{displayDrepInfo?.active ? 'Active' : 'Inactive'}

+
+
+
+ )} + + {loadingProxyDrep ? "Loading..." : (displayDrepInfo?.active ? "Active" : "Inactive")} + +
-
-
- {/* Voting Power */} - {isDRepRegistered && ( -
- -
- - {Math.round(Number(drepInfo.amount) / 1000000) - .toString() - .replace(/\B(?=(\d{3})+(?!\d))/g, ' ')} ₳ - + {/* Voting Power */} +
+
+ + Voting Power +
+
+ {proxyDelegatorsInfo?.totalDelegationADA !== undefined + ? proxyDelegatorsInfo.totalDelegationADA.toLocaleString(undefined, { minimumFractionDigits: 2, maximumFractionDigits: 6 }) + : displayDrepInfo?.deposit + ? (parseInt(displayDrepInfo.deposit) / 1000000).toFixed(2) + : displayDrepInfo?.amount + ? (parseInt(displayDrepInfo.amount) / 1000000).toFixed(2) + : "0.00"} ADA +
+
+ {loadingProxyDrep + ? "Loading..." + : proxyDelegatorsInfo + ? `${proxyDelegatorsInfo.count} delegator${proxyDelegatorsInfo.count !== 1 ? 's' : ''}` + : "Deposit amount"} +
- )} +
{/* Actions */} @@ -153,7 +443,7 @@ export default function CardInfo({ appWallet }: { appWallet: Wallet }) { Update DRep - + + {isProxyMode && ( +

+ This will create a multisig transaction for proxy DRep registration +

+ )}
); diff --git a/src/components/pages/wallet/governance/drep/registerDrep.tsx b/src/components/pages/wallet/governance/drep/registerDrep.tsx index 44557189..03cd137b 100644 --- a/src/components/pages/wallet/governance/drep/registerDrep.tsx +++ b/src/components/pages/wallet/governance/drep/registerDrep.tsx @@ -1,5 +1,5 @@ import { Plus } from "lucide-react"; -import { useState } from "react"; +import { useState, useCallback } from "react"; import useAppWallet from "@/hooks/useAppWallet"; import { useWallet } from "@meshsdk/react"; import { useUserStore } from "@/lib/zustand/user"; @@ -13,6 +13,12 @@ import { getFile, hashDrepAnchor } from "@meshsdk/core"; import type { UTxO } from "@meshsdk/core"; import router from "next/router"; import useMultisigWallet from "@/hooks/useMultisigWallet"; +import { MeshProxyContract } from "@/components/multisig/proxy/offchain"; +import { getProvider } from "@/utils/get-provider"; +import { Label } from "@/components/ui/label"; +import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select"; +import { api } from "@/utils/api"; +import { useProxy } from "@/hooks/useProxy"; interface PutResponse { url: string; @@ -20,13 +26,23 @@ interface PutResponse { export default function RegisterDRep() { const { appWallet } = useAppWallet(); - const { connected } = useWallet(); + const { connected, wallet } = useWallet(); const userAddress = useUserStore((state) => state.userAddress); const network = useSiteStore((state) => state.network); const loading = useSiteStore((state) => state.loading); const setLoading = useSiteStore((state) => state.setLoading); const { newTransaction } = useTransaction(); const { multisigWallet } = useMultisigWallet(); + const { isProxyEnabled, selectedProxyId, setSelectedProxy } = useProxy(); + + // Get proxies for the current wallet + const { data: proxies, isLoading: proxiesLoading } = api.proxy.getProxiesByUserOrWallet.useQuery( + { + walletId: appWallet?.id || undefined, + userAddress: userAddress || undefined, + }, + { enabled: !!(appWallet?.id || userAddress) } + ); const [manualUtxos, setManualUtxos] = useState([]); const [formState, setFormState] = useState({ @@ -42,6 +58,17 @@ export default function RegisterDRep() { identities: [""], }); + // Helper to resolve inputs for multisig controlled txs + const getMsInputs = useCallback(async (): Promise<{ utxos: UTxO[]; walletAddress: string }> => { + if (!multisigWallet?.getScript().address) { + throw new Error("Multisig wallet address not available"); + } + if (!manualUtxos || manualUtxos.length === 0) { + throw new Error("No UTxOs selected. Please select UTxOs from the selector."); + } + return { utxos: manualUtxos, walletAddress: multisigWallet.getScript().address }; + }, [multisigWallet?.getScript().address, manualUtxos]); + async function createAnchor(): Promise<{ anchorUrl: string; anchorHash: string; @@ -139,6 +166,58 @@ export default function RegisterDRep() { setLoading(false); } + async function registerProxyDrep(): Promise { + if (!connected || !userAddress || !multisigWallet || !appWallet) { + throw new Error("Multisig wallet not connected"); + } + + if (!selectedProxyId) { + throw new Error("Please select a proxy for registration"); + } + + setLoading(true); + try { + const { anchorUrl, anchorHash } = await createAnchor(); + + // Get multisig inputs + const { utxos, walletAddress } = await getMsInputs(); + + // Get the selected proxy + const proxy = proxies?.find((p: any) => p.id === selectedProxyId); + if (!proxy) { + throw new Error("Selected proxy not found"); + } + + // Create proxy contract instance with the selected proxy + const txBuilder = getTxBuilder(network); + const proxyContract = new MeshProxyContract( + { + mesh: txBuilder, + wallet: wallet, + networkId: network, + }, + { + paramUtxo: JSON.parse(proxy.paramUtxo), + }, + appWallet.scriptCbor, + ); + proxyContract.proxyAddress = proxy.proxyAddress; + + // Register DRep using proxy + const txHex = await proxyContract.registerProxyDrep(anchorUrl, anchorHash, utxos, walletAddress); + + await newTransaction({ + txBuilder: txHex, + description: "Proxy DRep registration", + toastMessage: "Proxy DRep registration transaction has been created", + }); + } catch (e) { + console.error(e); + } + router.push(`/wallets/${appWallet.id}/governance`); + setLoading(false); + } + return (
@@ -146,6 +225,68 @@ export default function RegisterDRep() { Register DRep +
+ {/* Global Proxy Status */} +
+
+ + {isProxyEnabled ? 'Proxy Mode Enabled' : 'Standard Mode'} + + + {isProxyEnabled + ? 'DRep will be registered using a proxy contract' + : 'DRep will be registered directly' + } + +
+ + {/* Proxy Configuration */} + {isProxyEnabled && ( +
+

+ This will register the DRep using a proxy contract, allowing for more flexible governance control. +

+ {proxies && proxies.length > 0 ? ( +
+ + +
+ ) : ( +
+ {proxiesLoading ? "Loading proxies..." : "No proxies available. Please create a proxy first."} +
+ )} +
+ )} + + {/* Standard Mode Info */} + {!isProxyEnabled && ( +
+

+ DRep will be registered directly to your multisig wallet. + To use proxy registration, enable proxy mode in the Proxy Control panel. +

+
+ )} +
{appWallet && ( )}
diff --git a/src/components/pages/wallet/governance/drep/retire.tsx b/src/components/pages/wallet/governance/drep/retire.tsx index 88ed5679..bfe9ca29 100644 --- a/src/components/pages/wallet/governance/drep/retire.tsx +++ b/src/components/pages/wallet/governance/drep/retire.tsx @@ -3,85 +3,267 @@ import { Wallet } from "@/types/wallet"; import { useSiteStore } from "@/lib/zustand/site"; import { getProvider } from "@/utils/get-provider"; import { getTxBuilder } from "@/utils/get-tx-builder"; -import { keepRelevant, Quantity, Unit } from "@meshsdk/core"; +import { keepRelevant, Quantity, Unit, UTxO } from "@meshsdk/core"; import { useWallet } from "@meshsdk/react"; import { useUserStore } from "@/lib/zustand/user"; import { useWalletsStore } from "@/lib/zustand/wallets"; import useTransaction from "@/hooks/useTransaction"; import useMultisigWallet from "@/hooks/useMultisigWallet"; +import { useProxy } from "@/hooks/useProxy"; +import { MeshProxyContract } from "@/components/multisig/proxy/offchain"; +import { api } from "@/utils/api"; +import { useCallback } from "react"; +import { useToast } from "@/hooks/use-toast"; -export default function Retire({ appWallet }: { appWallet: Wallet }) { +export default function Retire({ appWallet, manualUtxos }: { appWallet: Wallet; manualUtxos: UTxO[] }) { const network = useSiteStore((state) => state.network); - const { connected } = useWallet(); + const { wallet, connected } = useWallet(); const userAddress = useUserStore((state) => state.userAddress); const drepInfo = useWalletsStore((state) => state.drepInfo); const { newTransaction } = useTransaction(); const loading = useSiteStore((state) => state.loading); const setLoading = useSiteStore((state) => state.setLoading); const { multisigWallet } = useMultisigWallet(); + const { isProxyEnabled, selectedProxyId } = useProxy(); + const { toast } = useToast(); - async function retireDrep() { - if (!connected) throw new Error("Not connected to wallet"); - if (!userAddress) throw new Error("No user address"); - if (!multisigWallet) throw new Error("Multisig Wallet could not be built."); - setLoading(true); + // Get proxies for proxy mode + const { data: proxies } = api.proxy.getProxiesByUserOrWallet.useQuery( + { + walletId: appWallet?.id || undefined, + userAddress: userAddress || undefined, + }, + { enabled: !!(appWallet?.id || userAddress) } + ); - const blockchainProvider = getProvider(network); - const utxos = await blockchainProvider.fetchAddressUTxOs(multisigWallet.getScript().address); - - const assetMap = new Map(); - assetMap.set("lovelace", "5000000"); - const selectedUtxos = keepRelevant(assetMap, utxos); - if (selectedUtxos.length === 0) throw new Error("No relevant UTxOs found"); - - const txBuilder = getTxBuilder(network); - const dRepId = multisigWallet?.getKeysByRole(3) ? multisigWallet?.getDRepId() : appWallet?.dRepId; - const scriptCbor = multisigWallet?.getKeysByRole(3) ? multisigWallet?.getScript().scriptCbor : appWallet.scriptCbor; - const drepCbor = multisigWallet?.getKeysByRole(3) ? multisigWallet?.getDRepScript() : appWallet.scriptCbor; - const changeAddress = multisigWallet?.getKeysByRole(3) ? multisigWallet?.getScript().address : appWallet.address; - if (!changeAddress) { - throw new Error("Change address not found"); + // Helper function to get multisig inputs (like in register component) + const getMsInputs = useCallback(async (): Promise<{ utxos: UTxO[]; walletAddress: string }> => { + if (!multisigWallet?.getScript().address) { + throw new Error("Multisig wallet address not available"); } - if (!scriptCbor) { - throw new Error("Script not found"); + if (!manualUtxos || manualUtxos.length === 0) { + throw new Error("No UTxOs selected. Please select UTxOs from the selector."); } - if (!drepCbor) { - throw new Error("DRep script not found"); + return { utxos: manualUtxos, walletAddress: multisigWallet.getScript().address }; + }, [multisigWallet?.getScript().address, manualUtxos]); + + async function retireProxyDrep(): Promise { + if (!connected || !userAddress || !multisigWallet || !appWallet) { + toast({ + title: "Connection Error", + description: "Multisig wallet not connected", + variant: "destructive", + }); + return; } - if (!dRepId) { - throw new Error("DRep not found"); + if (!isProxyEnabled || !selectedProxyId) { + toast({ + title: "Proxy Error", + description: "Proxy mode not enabled or no proxy selected", + variant: "destructive", + }); + return; } - for (const utxo of selectedUtxos) { - txBuilder.txIn( - utxo.input.txHash, - utxo.input.outputIndex, - utxo.output.amount, - utxo.output.address, + + setLoading(true); + + try { + // Get the selected proxy + const proxy = proxies?.find((p: any) => p.id === selectedProxyId); + if (!proxy) { + toast({ + title: "Proxy Error", + description: "Selected proxy not found", + variant: "destructive", + }); + return; + } + + // Get multisig inputs + let utxos, walletAddress; + try { + const inputs = await getMsInputs(); + utxos = inputs.utxos; + walletAddress = inputs.walletAddress; + } catch (error) { + toast({ + title: "UTxO Selection Error", + description: error instanceof Error ? error.message : "Failed to get multisig inputs", + variant: "destructive", + }); + return; + } + + // Create proxy contract instance + const txBuilder = getTxBuilder(network); + const proxyContract = new MeshProxyContract( + { + mesh: txBuilder, + wallet: wallet, + networkId: network, + }, + { + paramUtxo: JSON.parse(proxy.paramUtxo), + }, + appWallet.scriptCbor, ); + proxyContract.proxyAddress = proxy.proxyAddress; + + // Deregister DRep using proxy + const txHex = await proxyContract.deregisterProxyDrep(utxos, walletAddress); + + await newTransaction({ + txBuilder: txHex, + description: "Proxy DRep retirement", + toastMessage: "Proxy DRep retirement transaction has been created", + }); + } catch (error) { + console.error("Proxy DRep retirement error:", error); + toast({ + title: "Proxy DRep Retirement Failed", + description: error instanceof Error ? error.message : "An unexpected error occurred", + variant: "destructive", + }); + } finally { + setLoading(false); + } + } + + async function retireDrep() { + if (!connected) { + toast({ + title: "Connection Error", + description: "Not connected to wallet", + variant: "destructive", + }); + return; } + if (!userAddress) { + toast({ + title: "User Error", + description: "No user address", + variant: "destructive", + }); + return; + } + if (!multisigWallet) { + toast({ + title: "Wallet Error", + description: "Multisig Wallet could not be built", + variant: "destructive", + }); + return; + } + + setLoading(true); + + try { + const blockchainProvider = getProvider(network); + const utxos = await blockchainProvider.fetchAddressUTxOs(multisigWallet.getScript().address); + + const assetMap = new Map(); + assetMap.set("lovelace", "5000000"); + const selectedUtxos = keepRelevant(assetMap, utxos); + if (selectedUtxos.length === 0) { + toast({ + title: "UTxO Error", + description: "No relevant UTxOs found", + variant: "destructive", + }); + return; + } - txBuilder - .txInScript(scriptCbor) - .changeAddress(changeAddress) - .drepDeregistrationCertificate(dRepId, "500000000") - .certificateScript(drepCbor); - - await newTransaction({ - txBuilder, - description: "DRep retirement", - toastMessage: "DRep retirement transaction has been created", - }); + const txBuilder = getTxBuilder(network); + const dRepId = multisigWallet?.getKeysByRole(3) ? multisigWallet?.getDRepId() : appWallet?.dRepId; + const scriptCbor = multisigWallet?.getKeysByRole(3) ? multisigWallet?.getScript().scriptCbor : appWallet.scriptCbor; + const drepCbor = multisigWallet?.getKeysByRole(3) ? multisigWallet?.getDRepScript() : appWallet.scriptCbor; + const changeAddress = multisigWallet?.getKeysByRole(3) ? multisigWallet?.getScript().address : appWallet.address; + + if (!changeAddress) { + toast({ + title: "Address Error", + description: "Change address not found", + variant: "destructive", + }); + return; + } + if (!scriptCbor) { + toast({ + title: "Script Error", + description: "Script not found", + variant: "destructive", + }); + return; + } + if (!drepCbor) { + toast({ + title: "DRep Script Error", + description: "DRep script not found", + variant: "destructive", + }); + return; + } + if (!dRepId) { + toast({ + title: "DRep Error", + description: "DRep not found", + variant: "destructive", + }); + return; + } + + for (const utxo of selectedUtxos) { + txBuilder.txIn( + utxo.input.txHash, + utxo.input.outputIndex, + utxo.output.amount, + utxo.output.address, + ); + } + + txBuilder + .txInScript(scriptCbor) + .changeAddress(changeAddress) + .drepDeregistrationCertificate(dRepId, "500000000") + .certificateScript(drepCbor); + + await newTransaction({ + txBuilder, + description: "DRep retirement", + toastMessage: "DRep retirement transaction has been created", + }); + } catch (error) { + console.error("DRep retirement error:", error); + toast({ + title: "DRep Retirement Failed", + description: error instanceof Error ? error.message : "An unexpected error occurred", + variant: "destructive", + }); + } finally { + setLoading(false); + } } return (
+ + {isProxyEnabled && !selectedProxyId && ( +
+

+ Proxy Mode Active - Select a proxy to continue +

+

+ Go to the Proxy Control panel above and select a proxy to enable DRep retirement. +

+
+ )}
); } diff --git a/src/components/pages/wallet/governance/drep/updateDrep.tsx b/src/components/pages/wallet/governance/drep/updateDrep.tsx index c0145a43..2b117ef7 100644 --- a/src/components/pages/wallet/governance/drep/updateDrep.tsx +++ b/src/components/pages/wallet/governance/drep/updateDrep.tsx @@ -1,5 +1,5 @@ import { Minus } from "lucide-react"; -import { useState } from "react"; +import { useState, useCallback } from "react"; import useAppWallet from "@/hooks/useAppWallet"; import { useWallet } from "@meshsdk/react"; import { useUserStore } from "@/lib/zustand/user"; @@ -13,6 +13,10 @@ import { getFile, hashDrepAnchor } from "@meshsdk/core"; import type { UTxO } from "@meshsdk/core"; import router from "next/router"; import useMultisigWallet from "@/hooks/useMultisigWallet"; +import { useProxy } from "@/hooks/useProxy"; +import { MeshProxyContract } from "@/components/multisig/proxy/offchain"; +import { api } from "@/utils/api"; +import { getProvider } from "@/utils/get-provider"; interface PutResponse { url: string; @@ -20,15 +24,37 @@ interface PutResponse { export default function UpdateDRep() { const { appWallet } = useAppWallet(); - const { connected } = useWallet(); + const { wallet, connected } = useWallet(); const userAddress = useUserStore((state) => state.userAddress); const network = useSiteStore((state) => state.network); const loading = useSiteStore((state) => state.loading); const setLoading = useSiteStore((state) => state.setLoading); const { newTransaction } = useTransaction(); const { multisigWallet } = useMultisigWallet(); + const { isProxyEnabled, selectedProxyId } = useProxy(); + // UTxO selection state const [manualUtxos, setManualUtxos] = useState([]); + + // Get proxies for proxy mode + const { data: proxies } = api.proxy.getProxiesByUserOrWallet.useQuery( + { + walletId: appWallet?.id || undefined, + userAddress: userAddress || undefined, + }, + { enabled: !!(appWallet?.id || userAddress) } + ); + + // Helper function to get multisig inputs (like in register component) + const getMsInputs = useCallback(async (): Promise<{ utxos: UTxO[]; walletAddress: string }> => { + if (!multisigWallet?.getScript().address) { + throw new Error("Multisig wallet address not available"); + } + if (!manualUtxos || manualUtxos.length === 0) { + throw new Error("No UTxOs selected. Please select UTxOs from the selector."); + } + return { utxos: manualUtxos, walletAddress: multisigWallet.getScript().address }; + }, [multisigWallet?.getScript().address, manualUtxos]); const [formState, setFormState] = useState({ givenName: "", bio: "", @@ -78,6 +104,62 @@ export default function UpdateDRep() { return { anchorUrl, anchorHash }; } + async function updateProxyDrep(): Promise { + if (!connected || !userAddress || !multisigWallet || !appWallet) { + throw new Error("Multisig wallet not connected"); + } + if (!isProxyEnabled || !selectedProxyId) { + throw new Error("Proxy mode not enabled or no proxy selected"); + } + + setLoading(true); + + try { + // Get the selected proxy + const proxy = proxies?.find((p: any) => p.id === selectedProxyId); + if (!proxy) { + throw new Error("Selected proxy not found"); + } + + // Create anchor metadata + const { anchorUrl, anchorHash } = await createAnchor(); + + // Get multisig inputs + const { utxos, walletAddress } = await getMsInputs(); + + // Create proxy contract instance + const txBuilder = getTxBuilder(network); + const proxyContract = new MeshProxyContract( + { + mesh: txBuilder, + wallet: wallet, + networkId: network, + }, + { + paramUtxo: JSON.parse(proxy.paramUtxo), + }, + appWallet.scriptCbor, + ); + proxyContract.proxyAddress = proxy.proxyAddress; + + // Update DRep using proxy + const txHex = await proxyContract.updateProxyDrep(anchorUrl, anchorHash, utxos, walletAddress); + + await newTransaction({ + txBuilder: txHex, + description: "Proxy DRep update", + toastMessage: "Proxy DRep update transaction has been created", + }); + + router.push(`/wallets/${appWallet.id}/governance`); + } catch (error) { + console.error("Proxy DRep update error:", error); + throw error; + } finally { + setLoading(false); + } + } + async function updateDrep(): Promise { if (!connected || !userAddress || !multisigWallet || !appWallet) throw new Error("Multisig wallet not connected"); @@ -192,8 +274,9 @@ export default function UpdateDRep() { // This function is intentionally left empty. }} loading={loading} - onSubmit={updateDrep} + onSubmit={isProxyEnabled ? updateProxyDrep : updateDrep} mode="update" + isProxyMode={isProxyEnabled} /> )}
diff --git a/src/components/pages/wallet/governance/index.tsx b/src/components/pages/wallet/governance/index.tsx index 8322fb78..caac526b 100644 --- a/src/components/pages/wallet/governance/index.tsx +++ b/src/components/pages/wallet/governance/index.tsx @@ -28,7 +28,7 @@ export default function PageGovernance() { return (
{/* Info section */} - + {/* Proposals section right under info */} state.userAddress); + + // Get proxies for proxy mode + const { data: proxies } = api.proxy.getProxiesByUserOrWallet.useQuery( + { + walletId: appWallet?.id || undefined, + userAddress: userAddress || undefined, + }, + { enabled: !!(appWallet?.id || userAddress) } + ); + + async function voteProxy() { + if (!isProxyEnabled || !selectedProxyId) { + toast({ + title: "Proxy Error", + description: "Proxy mode not enabled or no proxy selected", + variant: "destructive", + }); + return; + } + + setLoading(true); + try { + // Get the selected proxy + const proxy = proxies?.find((p: any) => p.id === selectedProxyId); + if (!proxy) { + toast({ + title: "Proxy Error", + description: "Selected proxy not found", + variant: "destructive", + }); + return; + } + + // Create proxy contract instance + const txBuilder = getTxBuilder(network); + const proxyContract = new MeshProxyContract( + { + mesh: txBuilder, + wallet: wallet, + networkId: network, + }, + { + paramUtxo: JSON.parse(proxy.paramUtxo), + }, + appWallet.scriptCbor, + ); + proxyContract.proxyAddress = proxy.proxyAddress; + + // Prepare vote + const vote = { + proposalId, + voteKind: voteKind, + }; + + // Vote using proxy + const txBuilderResult = await proxyContract.voteProxyDrep([vote], utxos, multisigWallet?.getScript().address); + + await newTransaction({ + txBuilder: txBuilderResult, + description: `Proxy Vote: ${voteKind} - ${description}`, + metadataValue: metadata ? { label: "674", value: metadata } : undefined, + }); + + toast({ + title: "Proxy Vote Successful", + description: `Your proxy vote (${voteKind}) has been recorded.`, + duration: 5000, + }); + + setAlert("Proxy vote transaction successfully created!"); + } catch (error) { + if ( + error instanceof Error && + error.message.includes("User rejected transaction") + ) { + toast({ + title: "Transaction Aborted", + description: "You canceled the proxy vote transaction.", + duration: 1000, + }); + } else { + toast({ + title: "Proxy Vote Failed", + description: `Error: ${error instanceof Error ? error.message : String(error)}`, + duration: 10000, + action: ( + { + navigator.clipboard.writeText(JSON.stringify(error)); + toast({ + title: "Error Copied", + description: "Error details copied to clipboard.", + duration: 5000, + }); + }} + > + Copy Error + + ), + variant: "destructive", + }); + console.error("Proxy vote transaction error:", error); + } + } finally { + setLoading(false); + } + } + async function vote() { if (drepInfo === undefined) { setAlert("DRep not found"); @@ -269,12 +386,23 @@ export default function VoteButton({ + {isProxyEnabled && !selectedProxyId && ( +
+

+ Proxy Mode Active - Select a proxy to continue +

+

+ Go to the Proxy Control panel above and select a proxy to enable voting. +

+
+ )} + {selectedBallotId && ( diff --git a/src/components/pages/wallet/info/index.tsx b/src/components/pages/wallet/info/index.tsx index 5696fa3f..87624402 100644 --- a/src/components/pages/wallet/info/index.tsx +++ b/src/components/pages/wallet/info/index.tsx @@ -8,6 +8,7 @@ import { ArchiveWallet } from "./archive-wallet"; import InspectMultisigScript from "@/components/multisig/inspect-multisig-script"; import { UpgradeStakingWallet } from "./upgrade-staking-wallet"; import { RegisterWallet } from "./register-wallet"; +import ProxyControlCard from "./proxy-control"; import { UpgradeGovernanceWallet } from "./upgrade-governance-wallet"; export default function WalletInfo() { @@ -24,11 +25,12 @@ export default function WalletInfo() { {(!multisigWallet || !multisigWallet.stakingEnabled()) && } {multisigWallet && multisigWallet.stakingEnabled() && } + {multisigWallet && } + {multisigWallet && } {multisigWallet && } -
diff --git a/src/components/pages/wallet/info/migrate-wallet.tsx b/src/components/pages/wallet/info/migrate-wallet.tsx index 9ed36bd4..675723bc 100644 --- a/src/components/pages/wallet/info/migrate-wallet.tsx +++ b/src/components/pages/wallet/info/migrate-wallet.tsx @@ -1,14 +1,790 @@ +import React, { useState, useCallback } from "react"; import CardUI from "@/components/ui/card-content"; +import { Button } from "@/components/ui/button"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { ArrowRight, AlertCircle, Loader, CheckCircle, X } from "lucide-react"; import { Wallet } from "@/types/wallet"; +import { toast } from "@/hooks/use-toast"; +import { api } from "@/utils/api"; +import { useUserStore } from "@/lib/zustand/user"; +import MigrationPreChecks from "./migration/MigrationPreChecks"; +import NewWalletCreationStep from "./migration/NewWalletCreationStep"; +import ProxySetupStep from "./migration/ProxySetupStep"; +import FundTransferStep from "./migration/FundTransferStep"; +import ProxyTransferStep from "./migration/ProxyTransferStep"; +import MigrationCompleteStep from "./migration/MigrationCompleteStep"; + +// Progress indicator component +const MigrationProgress = ({ + currentStep, + totalSteps, + onAbortMigration, + isAbortingMigration +}: { + currentStep: number; + totalSteps: number; + onAbortMigration: () => void; + isAbortingMigration: boolean; +}) => { + const steps = [ + { id: 0, title: "Pre-checks", description: "Verify wallet status" }, + { id: 1, title: "Create Wallet", description: "Configure new wallet" }, + { id: 2, title: "Proxy Setup", description: "Setup proxy (optional)" }, + { id: 3, title: "Transfer Funds", description: "Move all assets" }, + { id: 4, title: "Transfer Proxies", description: "Move proxy registrations" }, + { id: 5, title: "Complete", description: "Finish migration" }, + ]; + + return ( +
+
+

Migration Progress

+
+ + Step {currentStep + 1} of {totalSteps} + + +
+
+ +
+ {/* Mobile Layout - Vertical Stack */} +
+ {steps.map((step, index) => ( +
+ {/* Circle */} +
+ {index < currentStep ? ( + + ) : ( + index + 1 + )} +
+ + {/* Text Content */} +
+

+ {step.title} +

+

+ {step.description} +

+
+ + {/* Progress indicator for mobile */} + {index < currentStep && ( +
+ )} +
+ ))} +
+ + {/* Desktop Layout - Horizontal with aligned circles and text */} +
+
+ {steps.map((step, index) => ( +
+ {/* Circle and Text Container */} +
+ {/* Circle */} +
+ {index < currentStep ? ( + + ) : ( + index + 1 + )} +
+ + {/* Text Content */} +
+

+ {step.title} +

+

+ {step.description} +

+
+
+ + {/* Connecting Line (except for last step) */} + {index < steps.length - 1 && ( +
+ )} +
+ ))} +
+
+
+
+ ); +}; + +// Migration step constants for better maintainability +const MIGRATION_STEPS = { + PRE_CHECKS: 0, + CREATE_WALLET: 1, + PROXY_SETUP: 2, + FUND_TRANSFER: 3, + PROXY_TRANSFER: 4, + COMPLETE: 5, +} as const; + +type MigrationStep = typeof MIGRATION_STEPS[keyof typeof MIGRATION_STEPS]; + +interface MigrationState { + step: MigrationStep | null; + newWalletId: string | null; + migrationId: string | null; + isStarting: boolean; + isAborting: boolean; + hasAborted: boolean; +} export function MigrateWallet({ appWallet }: { appWallet: Wallet }) { + // Consolidated migration state + const [migrationState, setMigrationState] = useState({ + step: null, + newWalletId: null, + migrationId: null, + isStarting: false, + isAborting: false, + hasAborted: false, + }); + + // API mutations + const { mutateAsync: abortMigration } = api.wallet.abortMigration.useMutation(); + const { mutate: createMigration } = api.migration.createMigration.useMutation(); + const { mutate: updateMigrationStep } = api.migration.updateMigrationStep.useMutation(); + const { mutate: completeMigration } = api.migration.completeMigration.useMutation(); + const { mutateAsync: cancelMigration } = api.migration.cancelMigration.useMutation(); + const { mutateAsync: deleteNewWallet } = api.wallet.deleteNewWallet.useMutation(); + const utils = api.useUtils(); + const { userAddress } = useUserStore(); + + // Helper functions for state management + const updateMigrationState = useCallback((updates: Partial) => { + setMigrationState(prev => ({ ...prev, ...updates })); + }, []); + + const resetMigrationState = useCallback(() => { + setMigrationState({ + step: null, + newWalletId: null, + migrationId: null, + isStarting: false, + isAborting: false, + hasAborted: false, + }); + }, []); + + const resetMigrationStateWithAbortFlag = useCallback(() => { + setMigrationState({ + step: null, + newWalletId: null, + migrationId: null, + isStarting: false, + isAborting: false, + hasAborted: true, + }); + }, []); + + // Check for existing pending migrations + const { data: pendingMigrations } = api.migration.getPendingMigrations.useQuery( + { ownerAddress: userAddress! }, + { enabled: !!userAddress } + ); + + // Check if current wallet has existing proxies + const { data: existingProxies } = api.proxy.getProxiesByUserOrWallet.useQuery( + { + walletId: appWallet.id, + userAddress: userAddress! + }, + { enabled: !!userAddress && !!appWallet.id } + ); + + + // Auto-resume migration if there's an existing pending migration for this wallet + React.useEffect(() => { + if (pendingMigrations && pendingMigrations.length > 0) { + const existingMigration = pendingMigrations.find( + (migration: any) => migration.originalWalletId === appWallet.id + ); + + if (existingMigration && migrationState.step === null && !migrationState.hasAborted) { + updateMigrationState({ + migrationId: existingMigration.id, + step: existingMigration.currentStep as MigrationStep, + newWalletId: existingMigration.newWalletId || null, + }); + } + } + }, [pendingMigrations, appWallet.id, migrationState.step, migrationState.hasAborted, updateMigrationState]); + + // Auto-start migration if there's already a migration target (legacy support) + React.useEffect(() => { + const migrationTargetId = (appWallet as any).migrationTargetWalletId; + + if (migrationTargetId && migrationState.step === null && !migrationState.hasAborted && !migrationState.migrationId) { + // Set the newWalletId but don't auto-start the migration steps + // Let the user explicitly click "Continue Migration" to proceed + updateMigrationState({ newWalletId: migrationTargetId }); + } + }, [(appWallet as any).migrationTargetWalletId, migrationState.step, migrationState.hasAborted, migrationState.migrationId, updateMigrationState]); + + // Reset abort flag when migration target is cleared (after successful abort) + React.useEffect(() => { + if (migrationState.hasAborted && !(appWallet as any).migrationTargetWalletId) { + updateMigrationState({ hasAborted: false }); + } + }, [migrationState.hasAborted, (appWallet as any).migrationTargetWalletId, updateMigrationState]); + + const handleStartMigration = () => { + // Reset any previous state before starting new migration + resetMigrationState(); + updateMigrationState({ isStarting: true }); + + // Create migration record + createMigration({ + originalWalletId: appWallet.id, + ownerAddress: userAddress!, + migrationData: { + walletName: appWallet.name, + walletDescription: appWallet.description, + startedAt: new Date().toISOString() + } + }, { + onSuccess: (migration) => { + // If there's already a migration target, start at step 1 (wallet creation) + // Otherwise start at step 0 (pre-checks) + const migrationTargetId = (appWallet as any).migrationTargetWalletId; + const startStep = migrationTargetId ? MIGRATION_STEPS.CREATE_WALLET : MIGRATION_STEPS.PRE_CHECKS; + + updateMigrationState({ + migrationId: migration.id, + step: startStep, + newWalletId: migrationTargetId || null, + isStarting: false, + hasAborted: false, + }); + + updateMigrationStep({ + migrationId: migration.id, + currentStep: startStep, + status: "in_progress", + newWalletId: migrationTargetId || undefined + }); + }, + onError: (error) => { + console.error("Failed to create migration:", error); + updateMigrationState({ isStarting: false }); + toast({ + title: "Error", + description: "Failed to start migration. Please try again.", + variant: "destructive", + }); + } + }); + }; + + const handlePreChecksContinue = () => { + updateMigrationState({ step: MIGRATION_STEPS.CREATE_WALLET }); + if (migrationState.migrationId) { + updateMigrationStep({ + migrationId: migrationState.migrationId, + currentStep: MIGRATION_STEPS.CREATE_WALLET, + status: "in_progress" + }); + } + }; + + const handlePreChecksCancel = () => { + resetMigrationState(); + }; + + const handleNewWalletCreated = (createdWalletId: string) => { + console.log("handleNewWalletCreated called with:", createdWalletId); + console.log("Current migration state:", migrationState); + console.log("App wallet migration target:", (appWallet as any).migrationTargetWalletId); + + // Check if wallet has existing proxies - if yes, skip to step 3 (fund transfer) + // If no proxies, go to step 2 (proxy setup) + const nextStep = existingProxies && existingProxies.length > 0 ? MIGRATION_STEPS.FUND_TRANSFER : MIGRATION_STEPS.PROXY_SETUP; + + updateMigrationState({ + newWalletId: createdWalletId, + step: nextStep + }); + + if (migrationState.migrationId) { + updateMigrationStep({ + migrationId: migrationState.migrationId, + currentStep: nextStep, + status: "in_progress", + newWalletId: createdWalletId + }); + } + }; + + const handleNewWalletBack = () => { + updateMigrationState({ step: MIGRATION_STEPS.PRE_CHECKS }); + }; + + const handleProxySetupContinue = () => { + updateMigrationState({ step: MIGRATION_STEPS.FUND_TRANSFER }); + if (migrationState.migrationId) { + updateMigrationStep({ + migrationId: migrationState.migrationId, + currentStep: MIGRATION_STEPS.FUND_TRANSFER, + status: "in_progress" + }); + } + }; + + const handleProxySetupSkip = () => { + updateMigrationState({ step: MIGRATION_STEPS.FUND_TRANSFER }); + if (migrationState.migrationId) { + updateMigrationStep({ + migrationId: migrationState.migrationId, + currentStep: MIGRATION_STEPS.FUND_TRANSFER, + status: "in_progress" + }); + } + }; + + const handleProxySetupBack = () => { + updateMigrationState({ step: MIGRATION_STEPS.CREATE_WALLET }); + }; + + const handleFundTransferContinue = () => { + updateMigrationState({ step: MIGRATION_STEPS.PROXY_TRANSFER }); + if (migrationState.migrationId) { + updateMigrationStep({ + migrationId: migrationState.migrationId, + currentStep: MIGRATION_STEPS.PROXY_TRANSFER, + status: "in_progress" + }); + } + }; + + const handleFundTransferBack = () => { + updateMigrationState({ step: MIGRATION_STEPS.PROXY_SETUP }); + }; + + const handleProxyTransferContinue = () => { + updateMigrationState({ step: MIGRATION_STEPS.COMPLETE }); + if (migrationState.migrationId) { + updateMigrationStep({ + migrationId: migrationState.migrationId, + currentStep: MIGRATION_STEPS.COMPLETE, + status: "in_progress" + }); + } + }; + + const handleProxyTransferBack = () => { + updateMigrationState({ step: MIGRATION_STEPS.FUND_TRANSFER }); + }; + + const handleArchiveOldWallet = () => { + // Complete migration + if (migrationState.migrationId) { + completeMigration({ migrationId: migrationState.migrationId }); + } + + // Reset migration state + resetMigrationState(); + + toast({ + title: "Migration Complete", + description: "Your wallet migration has been completed successfully.", + }); + }; + + const handleCancelMigration = () => { + resetMigrationState(); + }; + + const handleAbortMigration = async () => { + // Try multiple sources for the migration target ID + const migrationTargetId = migrationState.newWalletId || (appWallet as any).migrationTargetWalletId; + + // If we still don't have it, try to fetch the wallet data directly + let finalMigrationTargetId = migrationTargetId; + if (!finalMigrationTargetId && userAddress) { + try { + const freshWalletData = await utils.wallet.getWallet.fetch({ + address: userAddress, + walletId: appWallet.id, + }); + finalMigrationTargetId = (freshWalletData as any).migrationTargetWalletId; + } catch (error) { + console.error("Failed to fetch fresh wallet data:", error); + } + } + + if (!finalMigrationTargetId) { + toast({ + title: "Error", + description: "No migration to abort. No migration target wallet found.", + variant: "destructive", + }); + return; + } + + updateMigrationState({ isAborting: true }); + console.log("Starting migration abort process..."); + try { + console.log("Aborting migration with:", { + walletId: appWallet.id, + newWalletId: finalMigrationTargetId, + migrationState + }); + + // Delete the wallet (NewWallet or Wallet) + await abortMigration({ + walletId: appWallet.id, + newWalletId: finalMigrationTargetId || undefined, + }); + + // Delete the migration record + if (migrationState.migrationId) { + await cancelMigration({ migrationId: migrationState.migrationId }); + } + + // Also delete any NewWallet if it exists (in case the final wallet wasn't created yet) + if (migrationState.newWalletId && migrationState.newWalletId !== finalMigrationTargetId) { + try { + await deleteNewWallet({ walletId: migrationState.newWalletId }); + console.log("Deleted NewWallet:", migrationState.newWalletId); + } catch (error) { + console.log("NewWallet deletion failed (may not exist):", error); + } + } + + // Invalidate all relevant queries to refresh the UI + await Promise.all([ + utils.wallet.getWallet.invalidate({ + address: userAddress!, + walletId: appWallet.id, + }), + utils.wallet.getUserWallets.invalidate({ + address: userAddress!, + }), + utils.migration.getPendingMigrations.invalidate({ + ownerAddress: userAddress!, + }), + ]); + + // Show success message + toast({ + title: "Migration Aborted", + description: "The migration has been cancelled and all related data has been cleaned up.", + }); + + console.log("Migration abort completed successfully"); + + // Small delay to ensure UI updates are processed + setTimeout(() => { + // Reset migration state with abort flag to show success UI + resetMigrationStateWithAbortFlag(); + console.log("Migration state reset with abort flag"); + }, 100); + } catch (error) { + console.error("Failed to abort migration:", error); + toast({ + title: "Error", + description: "Failed to abort migration. Please try again.", + variant: "destructive", + }); + } finally { + updateMigrationState({ isAborting: false }); + } + }; + + // Show migration steps + if (migrationState.step !== null) { + return ( +
+ {/* Progress Indicator */} + + + + + {/* Connecting Line */} +
+
+
+ + {/* Step Content */} +
+ {migrationState.step === MIGRATION_STEPS.PRE_CHECKS && ( + + )} + + {migrationState.step === MIGRATION_STEPS.CREATE_WALLET && ( + + )} + + {migrationState.step === MIGRATION_STEPS.PROXY_SETUP && (!existingProxies || existingProxies.length === 0) && ( + + )} + + {/* Show message if wallet already has proxies */} + {migrationState.step === MIGRATION_STEPS.PROXY_SETUP && existingProxies && existingProxies.length > 0 && ( +
+
+
+ +
+

Proxies Already Configured

+

+ This wallet already has {existingProxies.length} proxy{existingProxies.length !== 1 ? 'ies' : ''} configured. + You can proceed directly to fund transfer. +

+
+
+ +
+
+ )} + + {migrationState.step === MIGRATION_STEPS.FUND_TRANSFER && ( + + )} + + {migrationState.step === MIGRATION_STEPS.PROXY_TRANSFER && ( + + )} + + {migrationState.step === MIGRATION_STEPS.COMPLETE && ( + + )} +
+
+ ); + } + + // Show abort success state + if (migrationState.hasAborted) { + console.log("Rendering abort success state with migration state:", migrationState); + return ( + +
+ + + + Migration successfully aborted. All wallets, migration records, and references have been removed. You can start a new migration when ready. + + + +
+ +
+
+
+ ); + } + + // Show initial migration card return ( - <>Coming soon. +
+ {(appWallet as any).migrationTargetWalletId || migrationState.newWalletId ? ( + + + + Migration In Progress: You have an ongoing migration. Click "Continue Migration" to resume where you left off. +
+ + Debug: Migration Target ID: {(appWallet as any).migrationTargetWalletId || migrationState.newWalletId} + +
+
+ ) : ( + + + + Migration Process: This will create a new wallet with updated signers and transfer all funds from your current wallet. + The process includes pre-checks, wallet creation, proxy setup, and fund transfer. + + + )} + +
+
+
+ 1 +
+ Pre-checks (DRep, staking, pending transactions) +
+ +
+
+ 2 +
+ Create new wallet with updated configuration +
+ +
+
+ 3 +
+ Setup proxy for the new wallet (optional) +
+ +
+
+ 4 +
+ Transfer all funds to the new wallet +
+ +
+
+ 5 +
+ Complete migration and archive old wallet +
+
+ +
+ {((appWallet as any).migrationTargetWalletId || migrationState.newWalletId || migrationState.step !== null) && ( + + )} + +
+
); } diff --git a/src/components/pages/wallet/info/migration/FundTransferStep.tsx b/src/components/pages/wallet/info/migration/FundTransferStep.tsx new file mode 100644 index 00000000..1fd983d9 --- /dev/null +++ b/src/components/pages/wallet/info/migration/FundTransferStep.tsx @@ -0,0 +1,518 @@ +import React, { useState, useEffect } from "react"; +import { Button } from "@/components/ui/button"; +import CardUI from "@/components/ui/card-content"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { + ArrowLeft, + ArrowRight, + Loader, + AlertCircle, + CheckCircle, + Send, +} from "lucide-react"; +import { Wallet } from "@/types/wallet"; +import { api } from "@/utils/api"; +import { useUserStore } from "@/lib/zustand/user"; +import { useSiteStore } from "@/lib/zustand/site"; +import { useWalletsStore } from "@/lib/zustand/wallets"; +import { toast } from "@/hooks/use-toast"; +import useTransaction from "@/hooks/useTransaction"; +import { getProvider } from "@/utils/get-provider"; +import { getTxBuilder } from "@/utils/get-tx-builder"; +import { getBalanceFromUtxos } from "@/utils/getBalance"; +import { numberWithCommas } from "@/utils/strings"; +import { + MultisigWallet, + paymentKeyHash, + stakeKeyHash, +} from "@/utils/multisigSDK"; + +interface FundTransferStepProps { + appWallet: Wallet; + newWalletId: string; + onBack: () => void; + onContinue: () => void; +} + +export default function FundTransferStep({ + appWallet, + newWalletId, + onBack, + onContinue, +}: FundTransferStepProps) { + const userAddress = useUserStore((state) => state.userAddress); + const network = useSiteStore((state) => state.network); + const walletsUtxos = useWalletsStore((state) => state.walletsUtxos); + const walletAssets = useWalletsStore((state) => state.walletAssets); + const { newTransaction } = useTransaction(); + + // State + const [newWallet, setNewWallet] = useState(null); + const [isTransferring, setIsTransferring] = useState(false); + const [transferComplete, setTransferComplete] = useState(false); + const [transferTxId, setTransferTxId] = useState(null); + + // Get current wallet data + const currentUtxos = walletsUtxos[appWallet.id] || []; + const currentBalance = getBalanceFromUtxos(currentUtxos); + const nonAdaAssets = + walletAssets?.filter((asset) => asset.unit !== "lovelace") || []; + + // Generate new wallet address using MultisigWallet SDK + const generateNewWalletAddress = (walletData: any): string | null => { + if ( + !walletData || + !walletData.signersAddresses || + walletData.signersAddresses.length === 0 + ) { + return null; + } + + try { + // Extract key hashes from addresses and stake keys + const keys: Array<{ keyHash: string; role: number; name: string }> = []; + + // Add payment keys (role 0) + walletData.signersAddresses.forEach((address: string, index: number) => { + const keyHash = paymentKeyHash(address); + keys.push({ + keyHash, + role: 0, // Payment key role + name: + walletData.signersDescriptions?.[index] || `Signer ${index + 1}`, + }); + }); + + // Add stake keys (role 2) if they exist + if ( + walletData.signersStakeKeys && + walletData.signersStakeKeys.length > 0 + ) { + walletData.signersStakeKeys.forEach( + (stakeKey: string, index: number) => { + if (stakeKey && stakeKey.trim() !== "") { + const keyHash = stakeKeyHash(stakeKey); + keys.push({ + keyHash, + role: 2, // Stake key role + name: `${walletData.signersDescriptions?.[index] || `Signer ${index + 1}`} Stake`, + }); + } + }, + ); + } + + // Create MultisigWallet instance with the new wallet data + const multisigWallet = new MultisigWallet( + walletData.name || "New Wallet", + keys, + walletData.description || "", + walletData.numRequiredSigners || 1, + network === 0 ? 0 : 1, // 0=testnet, 1=mainnet + walletData.stakeCredentialHash || undefined, + walletData.scriptType || "atLeast", + ); + + // Generate the script and get the address + const { address } = multisigWallet.getScript(); + return address; + } catch (error) { + console.error("Failed to generate new wallet address:", error); + return null; + } + }; + + // Load new wallet information - try both Wallet and NewWallet tables + const { + data: newWalletData, + isLoading: isLoadingNewWalletData, + error: newWalletError, + } = api.wallet.getWallet.useQuery( + { + address: userAddress!, + walletId: newWalletId, + }, + { + enabled: !!newWalletId && !!userAddress, + retry: false, // Don't retry if wallet doesn't exist + }, + ); + + // Fallback to NewWallet if Wallet query fails + const { + data: newWalletDataFallback, + isLoading: isLoadingNewWalletDataFallback, + error: newWalletErrorFallback, + } = api.wallet.getNewWallet.useQuery( + { + walletId: newWalletId, + }, + { + enabled: !!newWalletId && !!newWalletError && !isLoadingNewWalletData, + retry: false, + }, + ); + + useEffect(() => { + + if (newWalletData) { + setNewWallet(newWalletData); + } else if (newWalletDataFallback) { + // Convert NewWallet data to Wallet format for compatibility + const walletData = { + ...newWalletDataFallback, + address: newWalletDataFallback.signersAddresses?.[0] || "", // Use first signer address as wallet address + scriptCbor: "", // NewWallet doesn't have scriptCbor + type: newWalletDataFallback.scriptType || "atLeast", + verified: [], + isArchived: false, + clarityApiKey: null, + migrationTargetWalletId: null, + }; + setNewWallet(walletData); + } else if (newWalletError && newWalletErrorFallback) { + toast({ + title: "Error", + description: + "Failed to load new wallet information. The new wallet may not exist yet.", + variant: "destructive", + }); + } + }, [ + newWalletData, + newWalletError, + newWalletDataFallback, + newWalletErrorFallback, + newWalletId, + userAddress, + isLoadingNewWalletData, + isLoadingNewWalletDataFallback, + ]); + + const handleTransferAllFunds = async () => { + if (!newWallet || !userAddress) return; + + setIsTransferring(true); + try { + const blockchainProvider = getProvider(network); + const utxos = await blockchainProvider.fetchAddressUTxOs( + appWallet.address, + ); + + if (utxos.length === 0) { + toast({ + title: "No Funds to Transfer", + description: "There are no funds in the current wallet to transfer. You can continue to the next step.", + }); + // Automatically proceed to the next step when there are no funds + setTimeout(() => { + onContinue(); + }, 2000); // 2 second delay to show the message + return; + } + + const txBuilder = getTxBuilder(network); + + // Add all UTxOs as inputs + for (const utxo of utxos) { + txBuilder.txIn( + utxo.input.txHash, + utxo.input.outputIndex, + utxo.output.amount, + utxo.output.address, + ); + txBuilder.txInScript(appWallet.scriptCbor); + } + + // Generate new wallet address using MultisigWallet SDK + const newWalletAddress = generateNewWalletAddress(newWallet); + if (!newWalletAddress) { + throw new Error("Failed to generate new wallet address"); + } + //filter one utxo with just lovelace no other units and remove it from the utxos array to pay the fee + const lovelaceUtxo = utxos.find( + (utxo) => + utxo.output.amount.find( + (asset: { unit: string; quantity: string }) => + asset.unit === "lovelace", + ) && + utxo.output.amount.find( + (asset: { unit: string; quantity: string }) => + asset.unit !== "lovelace", + ) === undefined, + ); + if (lovelaceUtxo) { + utxos.splice(utxos.indexOf(lovelaceUtxo), 1); //remove the lovelace utxo from the utxos array to pay the fee + } + + for (const utxo of utxos) { + txBuilder.txOut(newWalletAddress, utxo.output.amount); + } + + txBuilder.changeAddress(newWalletAddress); + // Create the transaction with the lovelace utxo to pay the fee + await newTransaction({ + txBuilder, + description: "Migration: Transfer all funds to new wallet", + toastMessage: "Fund transfer transaction created successfully", + }); + + setTransferComplete(true); + toast({ + title: "Transfer Initiated", + description: + "Fund transfer transaction has been created and is pending signatures.", + }); + + // Automatically proceed to the next step after a short delay + setTimeout(() => { + onContinue(); + }, 2000); // 2 second delay to show the success message + } catch (error) { + console.error("Failed to transfer funds:", error); + toast({ + title: "Transfer Failed", + description: "Failed to create fund transfer transaction.", + variant: "destructive", + }); + } finally { + setIsTransferring(false); + } + }; + + if (isLoadingNewWalletData || isLoadingNewWalletDataFallback) { + return ( + +
+ + Loading new wallet information... +
+
+ ); + } + + if (newWalletError) { + return ( + + + + + The new wallet could not be loaded. This might happen if the wallet + hasn't been created yet or if there's a connection issue. + + +
+ +
+
+ ); + } + + if (!newWallet || !newWallet.id) { + return ( + + + + + Failed to load new wallet information. Please ensure the new wallet + was created successfully. + + +
+ +
+
+ ); + } + + return ( +
+ {/* Header */} + + + + + This will transfer all funds from your current wallet to the new + wallet. This action cannot be undone. + + + + + {/* Current Wallet Balance */} + +
+
+
+

ADA Balance

+

Native currency

+
+
+

+ {currentBalance + ? numberWithCommas(Number(currentBalance)) + " ₳" + : "0.00 ₳"} +

+
+
+ + {nonAdaAssets.length > 0 && ( +
+

Other Assets

+ {nonAdaAssets.map((asset, index) => ( +
+
+

{asset.unit}

+

+ Custom asset +

+
+
+

{asset.quantity}

+
+
+ ))} +
+ )} + + {currentUtxos.length === 0 && ( +
+ +
+

No Funds to Transfer

+

+ The current wallet has no funds to transfer. You can continue to the next step. +

+
+
+ )} +
+
+ + {/* New Wallet Information */} + +
+
+

Wallet Details

+
+
+ Name: + + {newWallet?.name || "Loading..."} + +
+
+ Address: + + {newWallet + ? (() => { + const address = generateNewWalletAddress(newWallet); + return address + ? `${address.slice(0, 20)}...` + : "Generating..."; + })() + : "Loading..."} + +
+
+ Signers: + + {newWallet?.signersAddresses?.length || 0} + +
+
+
+
+
+ + {/* Transfer Status */} + {transferComplete && ( + +
+ +
+

Transfer Initiated

+

+ The fund transfer transaction has been created and is pending + signatures. You can view it in the transactions section. +

+
+
+
+ )} + + {/* Action Buttons */} + +
+ + {!transferComplete ? ( + + ) : ( + + )} +
+
+
+ ); +} diff --git a/src/components/pages/wallet/info/migration/MigrationCompleteStep.tsx b/src/components/pages/wallet/info/migration/MigrationCompleteStep.tsx new file mode 100644 index 00000000..fc043358 --- /dev/null +++ b/src/components/pages/wallet/info/migration/MigrationCompleteStep.tsx @@ -0,0 +1,195 @@ +import React, { useState } from "react"; +import { Button } from "@/components/ui/button"; +import CardUI from "@/components/ui/card-content"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { CheckCircle, ExternalLink, Loader, AlertCircle } from "lucide-react"; +import { Wallet } from "@/types/wallet"; +import { api } from "@/utils/api"; +import { useUserStore } from "@/lib/zustand/user"; +import { toast } from "@/hooks/use-toast"; +import { useRouter } from "next/router"; + +interface MigrationCompleteStepProps { + appWallet: Wallet; + newWalletId: string; + onBack: () => void; +} + +export default function MigrationCompleteStep({ + appWallet, + newWalletId, + onBack +}: MigrationCompleteStepProps) { + const { userAddress } = useUserStore(); + const router = useRouter(); + const [isCompleting, setIsCompleting] = useState(false); + + // Define mutations + const { mutateAsync: clearMigrationTarget } = api.wallet.clearMigrationTarget.useMutation(); + const { mutateAsync: archiveWallet } = api.wallet.archiveWallet.useMutation(); + const utils = api.useUtils(); + + // Get new wallet data + const { data: newWalletData, isLoading: isLoadingNewWallet } = api.wallet.getWallet.useQuery( + { + address: userAddress!, + walletId: newWalletId, + }, + { + enabled: !!userAddress && !!newWalletId, + } + ); + + const handleCompleteMigration = async () => { + setIsCompleting(true); + try { + // Clear migration target from old wallet + await clearMigrationTarget({ + walletId: appWallet.id, + }); + + // Archive the old wallet + await archiveWallet({ + walletId: appWallet.id, + }); + + // Invalidate queries to refresh UI + await utils.wallet.getWallet.invalidate(); + await utils.wallet.getUserWallets.invalidate(); + + toast({ + title: "Migration Complete", + description: "Your wallet migration has been completed successfully! The old wallet has been archived.", + }); + + // Navigate to the new wallet + router.push(`/wallets/${newWalletId}/info`); + } catch (error) { + console.error("Failed to complete migration:", error); + toast({ + title: "Error", + description: "Failed to complete migration. Please try again.", + variant: "destructive", + }); + } finally { + setIsCompleting(false); + } + }; + + const handleViewNewWallet = () => { + router.push(`/wallets/${newWalletId}/info`); + }; + + if (isLoadingNewWallet) { + return ( + +
+ + Loading new wallet... +
+
+ ); + } + + return ( +
+ +
+
+ +

+ Migration Successful! +

+

+ Your wallet has been successfully migrated to a new configuration. +

+
+ +
+

What's Next?

+
    +
  • • Your new wallet is ready to use
  • +
  • • All funds have been transferred
  • +
  • • Proxy settings have been updated
  • +
  • • Old wallet will be archived
  • +
  • • You can now use your new wallet for transactions
  • +
+
+ + {newWalletData && ( +
+

New Wallet Details

+
+
+ Name: {newWalletData.name} +
+
+ Address: + + {newWalletData.signersAddresses?.[0] || "N/A"} + +
+
+ Signers: {newWalletData.signersAddresses?.length || 0} +
+
+ Required Signatures: {newWalletData.numRequiredSigners || 1} +
+
+
+ )} + + + + + Important: Your old wallet will be archived after migration completion. + You can continue using your new wallet for all future transactions. + + +
+ +
+ + + +
+
+
+ ); +} diff --git a/src/components/pages/wallet/info/migration/MigrationPreChecks.tsx b/src/components/pages/wallet/info/migration/MigrationPreChecks.tsx new file mode 100644 index 00000000..d794b6fc --- /dev/null +++ b/src/components/pages/wallet/info/migration/MigrationPreChecks.tsx @@ -0,0 +1,278 @@ +import React, { useState, useEffect } from "react"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { Button } from "@/components/ui/button"; +import CardUI from "@/components/ui/card-content"; +import { AlertCircle, CheckCircle, Loader, ArrowRight } from "lucide-react"; +import { Wallet } from "@/types/wallet"; +import { useWalletsStore } from "@/lib/zustand/wallets"; +import { useSiteStore } from "@/lib/zustand/site"; +import { getProvider } from "@/utils/get-provider"; +import usePendingTransactions from "@/hooks/usePendingTransactions"; +import { MultisigWallet } from "@/utils/multisigSDK"; + +interface PreCheckResult { + status: "loading" | "success" | "warning" | "error"; + message: string; + details?: string; +} + +interface MigrationPreChecksProps { + appWallet: Wallet; + onContinue: () => void; + onCancel: () => void; +} + +export default function MigrationPreChecks({ + appWallet, + onContinue, + onCancel +}: MigrationPreChecksProps) { + const network = useSiteStore((state) => state.network); + const drepInfo = useWalletsStore((state) => state.drepInfo); + const { transactions: pendingTransactions } = usePendingTransactions({ + walletId: appWallet.id, + }); + + const [drepCheck, setDrepCheck] = useState({ status: "loading", message: "Checking DRep registration..." }); + const [stakingCheck, setStakingCheck] = useState({ status: "loading", message: "Checking staking registration..." }); + const [pendingTxCheck, setPendingTxCheck] = useState({ status: "loading", message: "Checking pending transactions..." }); + + // Build multisig wallet to get stake address + const multisigWallet = React.useMemo(() => { + if (!appWallet) return null; + try { + return new MultisigWallet( + appWallet.name, + appWallet.signersAddresses.map((addr, i) => ({ + keyHash: addr, + role: 0, + name: appWallet.signersDescriptions[i] || "", + })), + appWallet.description || "", + appWallet.numRequiredSigners || 1, + network + ); + } catch (error) { + console.error("Failed to build multisig wallet:", error); + return null; + } + }, [appWallet, network]); + + // Check DRep registration + useEffect(() => { + async function checkDRepStatus() { + try { + if (drepInfo) { + setDrepCheck({ + status: drepInfo.active ? "warning" : "success", + message: drepInfo.active ? "DRep is registered" : "DRep is not registered", + details: drepInfo.active + ? "You have an active DRep registration. Consider updating your DRep registration after migration." + : "No DRep registration found." + }); + } else { + setDrepCheck({ + status: "success", + message: "DRep is not registered", + details: "No DRep registration found." + }); + } + } catch (error) { + setDrepCheck({ + status: "error", + message: "Failed to check DRep status", + details: "Could not verify DRep registration status." + }); + } + } + + checkDRepStatus(); + }, [drepInfo]); + + // Check staking registration + useEffect(() => { + async function checkStakingStatus() { + try { + if (!multisigWallet) { + setStakingCheck({ + status: "error", + message: "Could not determine stake address", + details: "Failed to build multisig wallet for staking check." + }); + return; + } + + const stakeAddress = multisigWallet.getStakeAddress(); + if (!stakeAddress) { + setStakingCheck({ + status: "success", + message: "No stake address configured", + details: "This wallet does not have staking capabilities." + }); + return; + } + + const blockchainProvider = getProvider(network); + const stakingInfo = await blockchainProvider.get(`/accounts/${stakeAddress}`); + + setStakingCheck({ + status: stakingInfo.active ? "warning" : "success", + message: stakingInfo.active ? "Stake is registered" : "Stake is not registered", + details: stakingInfo.active + ? `Stake is registered to pool: ${stakingInfo.pool_id || "Unknown"}. Consider updating delegation after migration.` + : "No staking registration found." + }); + } catch (error) { + setStakingCheck({ + status: "error", + message: "Failed to check staking status", + details: "Could not verify staking registration status." + }); + } + } + + checkStakingStatus(); + }, [multisigWallet, network]); + + // Check pending transactions + useEffect(() => { + if (pendingTransactions !== undefined) { + const count = pendingTransactions.length; + setPendingTxCheck({ + status: count > 0 ? "warning" : "success", + message: count > 0 ? `${count} pending transaction(s)` : "No pending transactions", + details: count > 0 + ? "You have pending transactions that may need to be completed before migration." + : "No pending transactions found." + }); + } + }, [pendingTransactions]); + + const allChecksComplete = drepCheck.status !== "loading" && + stakingCheck.status !== "loading" && + pendingTxCheck.status !== "loading"; + + const hasWarnings = drepCheck.status === "warning" || + stakingCheck.status === "warning" || + pendingTxCheck.status === "warning"; + + const hasErrors = drepCheck.status === "error" || + stakingCheck.status === "error" || + pendingTxCheck.status === "error"; + + const getStatusIcon = (status: PreCheckResult["status"]) => { + switch (status) { + case "loading": + return ; + case "success": + return ; + case "warning": + return ; + case "error": + return ; + } + }; + + const getStatusColor = (status: PreCheckResult["status"]) => { + switch (status) { + case "success": + return "border-green-200 bg-green-50 dark:border-green-800 dark:bg-green-900/20"; + case "warning": + return "border-yellow-200 bg-yellow-50 dark:border-yellow-800 dark:bg-yellow-900/20"; + case "error": + return "border-red-200 bg-red-50 dark:border-red-800 dark:bg-red-900/20"; + default: + return "border-gray-200 bg-gray-50 dark:border-gray-700 dark:bg-gray-800"; + } + }; + + return ( + +
+ {/* DRep Check */} +
+
+ {getStatusIcon(drepCheck.status)} +
+

DRep Registration

+

{drepCheck.message}

+ {drepCheck.details && ( +

{drepCheck.details}

+ )} +
+
+
+ + {/* Staking Check */} +
+
+ {getStatusIcon(stakingCheck.status)} +
+

Staking Registration

+

{stakingCheck.message}

+ {stakingCheck.details && ( +

{stakingCheck.details}

+ )} +
+
+
+ + {/* Pending Transactions Check */} +
+
+ {getStatusIcon(pendingTxCheck.status)} +
+

Pending Transactions

+

{pendingTxCheck.message}

+ {pendingTxCheck.details && ( +

{pendingTxCheck.details}

+ )} +
+
+
+ + {/* Summary Alert */} + {allChecksComplete && (hasWarnings || hasErrors) && ( + + + + {hasErrors + ? "Some checks failed. Please resolve these issues before proceeding with migration." + : "Some warnings were found. You can proceed with migration, but consider addressing these items after migration." + } + + + )} + + {/* Action Buttons */} +
+ + +
+
+
+ ); +} diff --git a/src/components/pages/wallet/info/migration/NewWalletCreationStep.tsx b/src/components/pages/wallet/info/migration/NewWalletCreationStep.tsx new file mode 100644 index 00000000..83149bff --- /dev/null +++ b/src/components/pages/wallet/info/migration/NewWalletCreationStep.tsx @@ -0,0 +1,219 @@ +import React from "react"; +import { Button } from "@/components/ui/button"; +import { ArrowLeft, ArrowRight, Loader } from "lucide-react"; +import { Wallet } from "@/types/wallet"; +import ReviewWalletInfoCard from "@/components/pages/homepage/wallets/new-wallet-flow/create/ReviewWalletInfoCard"; +import ReviewSignersCard from "@/components/pages/homepage/wallets/new-wallet-flow/create/ReviewSignersCard"; +import ReviewRequiredSignersCard from "@/components/pages/homepage/wallets/new-wallet-flow/create/ReviewRequiredSignersCard"; +import CollapsibleAdvancedSection from "@/components/pages/homepage/wallets/new-wallet-flow/create/CollapsibleAdvancedSection"; +import { useMigrationWalletFlowState } from "./useMigrationWalletFlowState"; + +interface NewWalletCreationStepProps { + appWallet: Wallet; + onBack: () => void; + onContinue: (newWalletId: string) => void; +} + +export default function NewWalletCreationStep({ + appWallet, + onBack, + onContinue +}: NewWalletCreationStepProps) { + const walletFlow = useMigrationWalletFlowState(appWallet); + const hasAttemptedTemporaryWallet = React.useRef(false); + + const handleCreateWallet = async () => { + const finalWalletId = await walletFlow.createMigrationWallet(); + + if (finalWalletId !== null) { + onContinue(finalWalletId); + } + }; + + // Create temporary wallet on mount to enable invite link + React.useEffect(() => { + if (!walletFlow.newWalletId && + walletFlow.name && + walletFlow.signersAddresses.length > 0 && + !walletFlow.loading && + !hasAttemptedTemporaryWallet.current) { + hasAttemptedTemporaryWallet.current = true; + walletFlow.createTemporaryWallet(); + } + }, [walletFlow.name, walletFlow.signersAddresses.length, walletFlow.newWalletId, walletFlow.loading, walletFlow.createTemporaryWallet]); + + // Don't automatically continue - let user decide when to proceed + // React.useEffect(() => { + // console.log("NewWalletCreationStep: newWalletId changed", walletFlow.newWalletId); + // if (walletFlow.newWalletId) { + // console.log("NewWalletCreationStep: calling onContinue with", walletFlow.newWalletId); + // onContinue(walletFlow.newWalletId); + // } + // }, [walletFlow.newWalletId, onContinue]); + + return ( +
+ {/* Wallet Info */} + + + {/* Signers */} + + + {/* Required Signatures */} + + + {/* Advanced Section */} + + + + {/* Action Section */} +
+ {/* Info Messages */} +
+ {!walletFlow.newWalletId && ( +
+ + + +

+ Step 1: Configure your wallet settings and generate an invite link to share with other signers. +

+
+ )} + +
+ + + +

+ Important: Final wallet creation is permanent - signers and rules cannot be changed afterwards. +

+
+ + {walletFlow.newWalletId && appWallet.migrationTargetWalletId && ( +
+ + + +

+ Final Wallet Already Created: The final wallet for this migration has already been created. You can only create one new wallet per migration. +

+
+ )} +
+ + {/* Action Buttons */} +
+ + + {!walletFlow.newWalletId ? ( + + ) : ( +
+ {/* Only show Create Final Wallet button if no final wallet has been created yet */} + {!appWallet.migrationTargetWalletId && ( + + )} + + {/* Show appropriate continue button based on whether final wallet exists */} + {appWallet.migrationTargetWalletId && ( + + )} +
+ )} +
+
+
+ ); +} diff --git a/src/components/pages/wallet/info/migration/ProxySetupStep.tsx b/src/components/pages/wallet/info/migration/ProxySetupStep.tsx new file mode 100644 index 00000000..06bcf0cf --- /dev/null +++ b/src/components/pages/wallet/info/migration/ProxySetupStep.tsx @@ -0,0 +1,180 @@ +import React, { useState } from "react"; +import { Button } from "@/components/ui/button"; +import CardUI from "@/components/ui/card-content"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { ArrowLeft, ArrowRight, Loader, AlertCircle, CheckCircle, SkipForward } from "lucide-react"; +import { Wallet } from "@/types/wallet"; +import { api } from "@/utils/api"; +import { useUserStore } from "@/lib/zustand/user"; +import { toast } from "@/hooks/use-toast"; +import ProxyControl from "@/components/multisig/proxy/ProxyControl"; + +interface ProxySetupStepProps { + appWallet: Wallet; + newWalletId: string; + onBack: () => void; + onContinue: () => void; +} + +export default function ProxySetupStep({ + appWallet, + newWalletId, + onBack, + onContinue +}: ProxySetupStepProps) { + const { userAddress } = useUserStore(); + const [isCheckingProxies, setIsCheckingProxies] = useState(true); + const [hasExistingProxy, setHasExistingProxy] = useState(false); + const [showProxySetup, setShowProxySetup] = useState(false); + + // Check for existing proxies + const { data: existingProxies, isLoading: isLoadingProxies } = api.proxy.getProxiesByWallet.useQuery( + { + walletId: appWallet.id, + }, + { + enabled: !!appWallet.id, + } + ); + + // Check for new wallet proxies + const { data: newWalletProxies, isLoading: isLoadingNewProxies } = api.proxy.getProxiesByWallet.useQuery( + { + walletId: newWalletId, + }, + { + enabled: !!newWalletId, + } + ); + + React.useEffect(() => { + if (!isLoadingProxies && !isLoadingNewProxies) { + setIsCheckingProxies(false); + setHasExistingProxy((existingProxies?.length || 0) > 0); + } + }, [isLoadingProxies, isLoadingNewProxies, existingProxies]); + + const handleSkipProxy = () => { + toast({ + title: "Skipped", + description: "Proxy setup skipped. You can set up a proxy later.", + }); + onContinue(); + }; + + const handleShowProxySetup = () => { + setShowProxySetup(true); + }; + + + if (isCheckingProxies) { + return ( + +
+ + Checking proxy status... +
+
+ ); + } + + if (showProxySetup) { + return ( +
+ + + +
+ ); + } + + return ( +
+ +
+ {hasExistingProxy ? ( + + + + Your current wallet has an existing proxy configuration. + You can create a new proxy for the migrated wallet or skip this step. + + + ) : ( + + + + No existing proxy found. You can optionally create a proxy for your new wallet + to enable advanced features like delegation and governance participation. + + + )} + +
+

What is a Proxy?

+

+ A proxy allows you to delegate certain operations to another address while maintaining + control over your funds. This is useful for: +

+
    +
  • • Staking delegation
  • +
  • • Governance participation (DRep voting)
  • +
  • • Advanced transaction management
  • +
+
+ + {hasExistingProxy && ( +
+

Existing Proxy

+

+ Your current wallet has {existingProxies?.length || 0} active proxy configuration(s). + The proxy will need to be updated to point to your new wallet after migration. +

+
+ )} +
+ +
+ + + +
+
+
+ ); +} diff --git a/src/components/pages/wallet/info/migration/ProxyTransferStep.tsx b/src/components/pages/wallet/info/migration/ProxyTransferStep.tsx new file mode 100644 index 00000000..6b04df8d --- /dev/null +++ b/src/components/pages/wallet/info/migration/ProxyTransferStep.tsx @@ -0,0 +1,233 @@ +import React, { useState } from "react"; +import { Button } from "@/components/ui/button"; +import CardUI from "@/components/ui/card-content"; +import { Alert, AlertDescription } from "@/components/ui/alert"; +import { ArrowLeft, ArrowRight, Loader, AlertCircle, CheckCircle, Users } from "lucide-react"; +import type { Wallet } from "@/types/wallet"; +import { api } from "@/utils/api"; +import { toast } from "@/hooks/use-toast"; + +interface ProxyTransferStepProps { + appWallet: Wallet; + newWalletId: string; + onBack: () => void; + onContinue: () => void; +} + +export default function ProxyTransferStep({ + appWallet, + newWalletId, + onBack, + onContinue +}: ProxyTransferStepProps) { + const [isTransferring, setIsTransferring] = useState(false); + const [transferComplete, setTransferComplete] = useState(false); + + // Get existing proxies for the current wallet + const { data: existingProxies, isLoading: isLoadingProxies } = api.proxy.getProxiesByUserOrWallet.useQuery({ + walletId: appWallet.id, + }); + + // Mutation to transfer proxies + const { mutateAsync: transferProxies } = api.proxy.transferProxies.useMutation({ + onSuccess: () => { + setTransferComplete(true); + toast({ + title: "Proxies Transferred", + description: "All proxy registrations have been transferred to the new wallet.", + }); + // Automatically proceed to the next step after a short delay + setTimeout(() => { + onContinue(); + }, 2000); + }, + onError: (error) => { + console.error("Failed to transfer proxies:", error); + toast({ + title: "Transfer Failed", + description: "Failed to transfer proxy registrations. Please try again.", + variant: "destructive", + }); + }, + }); + + const handleTransferProxies = async () => { + if (!existingProxies || existingProxies.length === 0) return; + + setIsTransferring(true); + try { + await transferProxies({ + fromWalletId: appWallet.id, + toWalletId: newWalletId, + }); + } catch (error) { + console.error("Failed to transfer proxies:", error); + } finally { + setIsTransferring(false); + } + }; + + if (isLoadingProxies) { + return ( + +
+ + Loading proxy information... +
+
+ ); + } + + const hasProxies = (existingProxies && existingProxies.length > 0) ?? false; + + return ( +
+ {/* Header */} + + + + + This will transfer all proxy registrations from your current wallet to the new wallet. + This ensures your governance participation continues seamlessly. + + + + + {/* Proxy Information */} + +
+ {hasProxies ? ( +
+ {(existingProxies ?? []).map((proxy, index) => ( +
+
+ +
+

Proxy {index + 1}

+

+ {proxy.description ?? `Proxy ${index + 1}`} +

+
+
+
+

Active

+

Will be transferred

+
+
+ ))} +
+ ) : ( +
+ +
+

No Proxies Found

+

+ There are no proxy registrations to transfer. You can continue to the next step. +

+
+
+ )} +
+
+ + {/* New Wallet Information */} + +
+
+

Transfer Details

+
+
+ From Wallet: + {appWallet.name} +
+
+ To Wallet: + New Migrated Wallet +
+
+ Proxies to Transfer: + {existingProxies?.length || 0} +
+
+
+
+
+ + {/* Transfer Status */} + {transferComplete && ( + +
+ +
+

Proxies Transferred

+

+ All proxy registrations have been successfully transferred to the new wallet. + You can now complete the migration. +

+
+
+
+ )} + + {/* Action Buttons */} + +
+ + {!transferComplete ? ( + + ) : ( + + )} +
+
+
+ ); +} diff --git a/src/components/pages/wallet/info/migration/useMigrationWalletFlowState.tsx b/src/components/pages/wallet/info/migration/useMigrationWalletFlowState.tsx new file mode 100644 index 00000000..5de653c4 --- /dev/null +++ b/src/components/pages/wallet/info/migration/useMigrationWalletFlowState.tsx @@ -0,0 +1,706 @@ +/** + * useMigrationWalletFlowState Hook + * Adapts the existing wallet flow state for migration purposes + * Pre-populates data from the current wallet and handles migration-specific logic + */ + +import { useState, useEffect, useMemo, useCallback } from "react"; +import { resolveStakeKeyHash } from "@meshsdk/core"; +import type { MultisigKey } from "@/utils/multisigSDK"; +import { MultisigWallet } from "@/utils/multisigSDK"; +import { paymentKeyHash } from "@/utils/multisigSDK"; + +import { api } from "@/utils/api"; +import { useUserStore } from "@/lib/zustand/user"; +import { useSiteStore } from "@/lib/zustand/site"; +import { useToast } from "@/hooks/use-toast"; +import type { Wallet } from "@/types/wallet"; + +export interface MigrationWalletFlowState { + // Core wallet data + name: string; + setName: React.Dispatch>; + description: string; + setDescription: React.Dispatch>; + + // Signers management + signersAddresses: string[]; + setSignerAddresses: React.Dispatch>; + signersDescriptions: string[]; + setSignerDescriptions: React.Dispatch>; + signersStakeKeys: string[]; + setSignerStakeKeys: React.Dispatch>; + signersDRepKeys: string[]; + setSignerDRepKeys: React.Dispatch>; + addSigner: () => void; + removeSigner: (index: number) => void; + + // Signature rules + numRequiredSigners: number; + setNumRequiredSigners: React.Dispatch>; + nativeScriptType: "all" | "any" | "atLeast"; + setNativeScriptType: React.Dispatch>; + + // Advanced options + stakeKey: string; + setStakeKey: React.Dispatch>; + removeExternalStakeAndBackfill: () => void; + + // UI state + loading: boolean; + setLoading: React.Dispatch>; + + // Computed values + multisigWallet?: MultisigWallet; + isValidForCreate: boolean; + + // Dependencies + userAddress?: string; + network: number; + toast: ReturnType['toast']; + + // Migration-specific + appWallet: Wallet; + newWalletId?: string; + + // Actions + createTemporaryWallet: () => Promise; + createMigrationWallet: () => Promise; + + // Save callbacks for create page + handleSaveWalletInfo: (newName: string, newDescription: string) => void; + handleSaveSigners: (newAddresses: string[], newDescriptions: string[], newStakeKeys: string[], newDRepKeys: string[]) => Promise; + handleSaveSignatureRules: (numRequired: number) => Promise; + handleSaveAdvanced: (newStakeKey: string, scriptType: "all" | "any" | "atLeast") => Promise; +} + +export function useMigrationWalletFlowState(appWallet: Wallet): MigrationWalletFlowState { + const [signersAddresses, setSignerAddresses] = useState([]); + const [signersDescriptions, setSignerDescriptions] = useState([]); + const [signersStakeKeys, setSignerStakeKeys] = useState([]); + const [signersDRepKeys, setSignerDRepKeys] = useState([]); + const [numRequiredSigners, setNumRequiredSigners] = useState(1); + const [name, setName] = useState(""); + const [description, setDescription] = useState(""); + const [loading, setLoading] = useState(false); + const [nativeScriptType, setNativeScriptType] = useState<"all" | "any" | "atLeast">("atLeast"); + const [stakeKey, setStakeKey] = useState(""); + const [newWalletId, setNewWalletId] = useState(); + + // Dependencies + const userAddress = useUserStore((state) => state.userAddress); + const network = useSiteStore((state) => state.network); + const { toast } = useToast(); + + // Get complete wallet data from database + const { data: walletData } = api.wallet.getWallet.useQuery( + { + address: userAddress!, + walletId: appWallet.id, + }, + { + enabled: !!userAddress && !!appWallet.id, + } + ); + + // Get existing new wallet data if migration is in progress + type WalletWithMigration = { migrationTargetWalletId?: string }; + const { data: existingNewWallet } = api.wallet.getNewWallet.useQuery( + { + walletId: ((appWallet as unknown as WalletWithMigration).migrationTargetWalletId) ?? "", + }, + { + enabled: Boolean((appWallet as unknown as WalletWithMigration).migrationTargetWalletId), + } + ); + + // Initialize data from current wallet + useEffect(() => { + if (walletData) { + setName(`${walletData.name} - Migrated`); + setDescription(walletData.description ?? ""); + setSignerAddresses(walletData.signersAddresses ?? []); + setSignerDescriptions(walletData.signersDescriptions ?? []); + setNumRequiredSigners(walletData.numRequiredSigners ?? 1); + setNativeScriptType((walletData.type as "atLeast" | "all" | "any") ?? "atLeast"); + setStakeKey(walletData.stakeCredentialHash ?? ""); + + // Filter and process stake keys + const validStakeKeys = (walletData.signersStakeKeys || []).filter((key: string) => { + // Check if it's a valid 28-byte or 32-byte hex hash + if (/^[0-9a-fA-F]{56}$/.test(key) || /^[0-9a-fA-F]{64}$/.test(key)) { + return true; + } + // Check if it's a full stake address + if (key.startsWith('stake1') || key.startsWith('stake_test1')) { + return true; + } + return false; + }); + + setSignerStakeKeys(validStakeKeys); + + // Initialize DRep keys (empty for now, can be added later) + setSignerDRepKeys( + Array.isArray((walletData as unknown as { signersDRepKeys?: string[] }).signersDRepKeys) + ? (walletData as unknown as { signersDRepKeys?: string[] }).signersDRepKeys! + : [], + ); + } + }, [walletData]); + + // Load existing new wallet data if available + useEffect(() => { + if (existingNewWallet) { + setNewWalletId(existingNewWallet.id); + setName(existingNewWallet.name); + setDescription(existingNewWallet.description ?? ""); + setSignerAddresses(existingNewWallet.signersAddresses ?? []); + setSignerDescriptions(existingNewWallet.signersDescriptions ?? []); + setSignerStakeKeys(existingNewWallet.signersStakeKeys ?? []); + setSignerDRepKeys( + Array.isArray((existingNewWallet as unknown as { signersDRepKeys?: string[] }).signersDRepKeys) + ? (existingNewWallet as unknown as { signersDRepKeys?: string[] }).signersDRepKeys! + : [], + ); + setNumRequiredSigners(existingNewWallet.numRequiredSigners ?? 1); + setStakeKey(existingNewWallet.stakeCredentialHash ?? ""); + setNativeScriptType((existingNewWallet.scriptType as "atLeast" | "all" | "any") ?? "atLeast"); + } + }, [existingNewWallet]); + + // MultisigWallet computation + const multisigWallet = useMemo(() => { + const keys: MultisigKey[] = []; + if (signersAddresses.length === 0) return; + + if (signersAddresses.length > 0) { + signersAddresses.forEach((addr, i) => { + if (addr) { + try { + const paymentHash = paymentKeyHash(addr); + keys.push({ + keyHash: paymentHash, + role: 0, + name: signersDescriptions[i] ?? "", + }); + } catch { + // Invalid payment address at index + } + } + }); + } + + // Only add individual signer stake keys if no external stake credential + if (!stakeKey && signersStakeKeys.length > 0) { + signersStakeKeys.forEach((stakeKey, i) => { + if (stakeKey) { + try { + const stakeKeyHash = resolveStakeKeyHash(stakeKey); + keys.push({ + keyHash: stakeKeyHash, + role: 2, + name: signersDescriptions[i] ?? "", + }); + } catch { + // Invalid stake address at index + } + } + }); + } + + if (keys.length === 0) return; + return new MultisigWallet( + name, + keys, + description, + numRequiredSigners, + network, + stakeKey || undefined, + nativeScriptType, + ); + }, [ + name, + description, + signersAddresses, + signersStakeKeys, + signersDescriptions, + numRequiredSigners, + network, + stakeKey, + nativeScriptType, + ]); + + // API Mutations + const { mutate: createNewWallet } = api.wallet.createNewWallet.useMutation({ + onSuccess: (data) => { + setNewWalletId(data.id); + setLoading(false); + toast({ + title: "Wallet Created", + description: "New wallet configuration created successfully", + duration: 3000, + }); + }, + onError: (_e) => { + setLoading(false); + toast({ + title: "Error", + description: "Failed to create new wallet configuration", + variant: "destructive", + duration: 3000, + }); + }, + }); + + const { mutateAsync: updateNewWallet } = api.wallet.updateNewWallet.useMutation({ + onSuccess: () => { + toast({ + title: "Saved", + description: "Changes saved successfully", + duration: 2000, + }); + }, + onError: (_e) => { + toast({ + title: "Error", + description: "Failed to save changes", + variant: "destructive", + duration: 3000, + }); + }, + }); + + const { mutate: createWallet } = api.wallet.createWallet.useMutation(); + const { mutateAsync: deleteNewWallet } = api.wallet.deleteNewWallet.useMutation(); + + const { mutate: setMigrationTarget } = api.wallet.setMigrationTarget.useMutation({ + onError: (e) => { + console.error("Failed to set migration target:", e); + toast({ + title: "Warning", + description: "Wallet created but migration target not set. Please try again.", + variant: "destructive", + duration: 3000, + }); + }, + }); + + // Utility functions + function addSigner() { + setSignerAddresses([...signersAddresses, ""]); + setSignerDescriptions([...signersDescriptions, ""]); + setSignerStakeKeys([...signersStakeKeys, ""]); + setSignerDRepKeys([...signersDRepKeys, ""]); + } + + function removeSigner(index: number) { + const updatedAddresses = [...signersAddresses]; + updatedAddresses.splice(index, 1); + setSignerAddresses(updatedAddresses); + + const updatedDescriptions = [...signersDescriptions]; + updatedDescriptions.splice(index, 1); + setSignerDescriptions(updatedDescriptions); + + const updatedStakeKeys = [...signersStakeKeys]; + updatedStakeKeys.splice(index, 1); + setSignerStakeKeys(updatedStakeKeys); + + const updatedDRepKeys = [...signersDRepKeys]; + updatedDRepKeys.splice(index, 1); + setSignerDRepKeys(updatedDRepKeys); + } + + // Adjust numRequiredSigners if it exceeds the number of signers + useEffect(() => { + if (numRequiredSigners > signersAddresses.length && signersAddresses.length > 0) { + setNumRequiredSigners(signersAddresses.length); + } + }, [signersAddresses.length, numRequiredSigners]); + + // Create temporary wallet for invite link (if not already created) + const createTemporaryWallet = useCallback(async () => { + if (newWalletId) { + return; // Already created + } + + + if (!name || signersAddresses.length === 0) { + toast({ + title: "Error", + description: "Please provide wallet name and at least one signer before creating invite link.", + variant: "destructive", + }); + return; + } + + setLoading(true); + try { + const walletData = { + name: name, + description: description, + signersAddresses: signersAddresses, + signersDescriptions: signersDescriptions, + signersStakeKeys: signersStakeKeys, + signersDRepKeys: signersDRepKeys, + numRequiredSigners: numRequiredSigners, + ownerAddress: userAddress ?? "", + stakeCredentialHash: stakeKey || undefined, + scriptType: nativeScriptType || undefined, + }; + + + // Create temporary wallet for invite link + createNewWallet(walletData); + } catch (error) { + console.error("Failed to create temporary wallet:", error); + setLoading(false); + toast({ + title: "Error", + description: "Failed to create temporary wallet. Please try again.", + variant: "destructive", + }); + } + }, [newWalletId, name, signersAddresses, description, signersDescriptions, signersStakeKeys, signersDRepKeys, numRequiredSigners, stakeKey, nativeScriptType, createNewWallet, toast, userAddress]); + + // Create final migration wallet + async function createMigrationWallet(): Promise { + + if (!multisigWallet) { + toast({ + title: "Error", + description: "Invalid wallet configuration. Please check your settings.", + variant: "destructive", + }); + return null; + } + + if (!newWalletId) { + toast({ + title: "Error", + description: "Please create the temporary wallet first to generate invite link.", + variant: "destructive", + }); + return null; + } + + // Check if final wallet has already been created + if ((appWallet as unknown as WalletWithMigration).migrationTargetWalletId) { + toast({ + title: "Error", + description: "Final wallet has already been created for this migration. You can only create one new wallet per migration.", + variant: "destructive", + }); + return null; + } + + setLoading(true); + try { + const { scriptCbor } = multisigWallet.getScript(); + if (!scriptCbor) { + throw new Error("Failed to generate script CBOR"); + } + + + // Create the final wallet using the mutation + return new Promise((resolve, reject) => { + createWallet({ + name: name, + description: description, + signersAddresses: signersAddresses, + signersDescriptions: signersDescriptions, + signersStakeKeys: signersStakeKeys, + signersDRepKeys: signersDRepKeys, + numRequiredSigners: numRequiredSigners, + scriptCbor: scriptCbor, + stakeCredentialHash: stakeKey || undefined, + type: nativeScriptType, + }, { + onSuccess: (data) => { + + // Set migration target after successful wallet creation + setMigrationTarget({ + walletId: appWallet.id, + migrationTargetWalletId: data.id, + }); + + // Clean up the temporary NewWallet + if (newWalletId && newWalletId !== data.id) { + void deleteNewWallet({ walletId: newWalletId }).catch((err) => { + console.warn("Failed to delete temporary new wallet:", err); + }); + } + + setNewWalletId(data.id); + setLoading(false); + toast({ + title: "Success", + description: "New wallet created successfully!", + duration: 3000, + }); + resolve(data.id); + }, + onError: (error) => { + console.error("Failed to create wallet:", error); + setLoading(false); + toast({ + title: "Error", + description: "Failed to create new wallet", + variant: "destructive", + duration: 3000, + }); + reject(error instanceof Error ? error : new Error(error?.message ?? 'Unknown error')); + } + }); + }); + + } catch (error) { + console.error("Failed to create wallet:", error); + setLoading(false); + toast({ + title: "Error", + description: "Failed to create new wallet. Please try again.", + variant: "destructive", + }); + return null; + } + } + + // Save callbacks for create page + const handleSaveWalletInfo = useCallback((newName: string, newDescription: string) => { + setName(newName); + setDescription(newDescription); + + if (newWalletId) { + void updateNewWallet({ + walletId: newWalletId, + name: newName, + description: newDescription, + signersAddresses: signersAddresses, + signersDescriptions: signersDescriptions, + signersStakeKeys: signersStakeKeys, + signersDRepKeys: signersDRepKeys, + numRequiredSigners: numRequiredSigners, + stakeCredentialHash: stakeKey || undefined, + scriptType: nativeScriptType || undefined, + }); + } + }, [newWalletId, signersAddresses, signersDescriptions, signersStakeKeys, signersDRepKeys, numRequiredSigners, stakeKey, nativeScriptType, updateNewWallet]); + + const handleSaveSigners = useCallback(async (newAddresses: string[], newDescriptions: string[], newStakeKeys: string[], newDRepKeys: string[]) => { + // Ensure all arrays are defined and filter out undefined values + const safeAddresses = (newAddresses || []).filter(addr => addr !== undefined); + const safeDescriptions = (newDescriptions || []).filter(desc => desc !== undefined); + const safeStakeKeys = (newStakeKeys || []).filter(key => key !== undefined); + const safeDRepKeys = (newDRepKeys || []).filter(key => key !== undefined); + + // Ensure all arrays have the same length + const maxLength = Math.max(safeAddresses.length, safeDescriptions.length, safeStakeKeys.length, safeDRepKeys.length); + + const paddedAddresses = [...safeAddresses]; + const paddedDescriptions = [...safeDescriptions]; + const paddedStakeKeys = [...safeStakeKeys]; + const paddedDRepKeys = [...safeDRepKeys]; + + // Pad arrays to same length with empty strings + while (paddedAddresses.length < maxLength) paddedAddresses.push(""); + while (paddedDescriptions.length < maxLength) paddedDescriptions.push(""); + while (paddedStakeKeys.length < maxLength) paddedStakeKeys.push(""); + while (paddedDRepKeys.length < maxLength) paddedDRepKeys.push(""); + + setSignerAddresses(paddedAddresses); + setSignerDescriptions(paddedDescriptions); + setSignerStakeKeys(paddedStakeKeys); + setSignerDRepKeys(paddedDRepKeys); + + if (newWalletId) { + const updateData = { + walletId: newWalletId, + name: name, + description: description, + signersAddresses: paddedAddresses, + signersDescriptions: paddedDescriptions, + signersStakeKeys: paddedStakeKeys, + signersDRepKeys: paddedDRepKeys, + numRequiredSigners: numRequiredSigners, + stakeCredentialHash: stakeKey || undefined, + scriptType: nativeScriptType || undefined, + }; + + // Validate data before sending + if (!updateData.walletId || !updateData.name) { + toast({ + title: "Error", + description: "Invalid wallet data. Please try again.", + variant: "destructive", + }); + return; + } + + // Ensure all arrays contain only strings + const validatedData = { + ...updateData, + signersAddresses: paddedAddresses.map(addr => String(addr || "")), + signersDescriptions: paddedDescriptions.map(desc => String(desc || "")), + signersStakeKeys: paddedStakeKeys.map(key => String(key || "")), + signersDRepKeys: paddedDRepKeys.map(key => String(key || "")), + }; + + + try { + await updateNewWallet(validatedData); + } catch (error) { + console.error("Failed to update new wallet:", error); + } + } + }, [newWalletId, name, description, numRequiredSigners, stakeKey, nativeScriptType, updateNewWallet, toast]); + + const handleSaveSignatureRules = useCallback(async (numRequired: number) => { + setNumRequiredSigners(numRequired); + + if (newWalletId) { + try { + await updateNewWallet({ + walletId: newWalletId, + name: name, + description: description, + signersAddresses: signersAddresses, + signersDescriptions: signersDescriptions, + signersStakeKeys: signersStakeKeys, + signersDRepKeys: signersDRepKeys, + numRequiredSigners: numRequired, + stakeCredentialHash: stakeKey || undefined, + scriptType: nativeScriptType || undefined, + }); + } catch (error) { + console.error("Failed to update signature rules:", error); + } + } + }, [newWalletId, name, description, signersAddresses, signersDescriptions, signersStakeKeys, signersDRepKeys, stakeKey, nativeScriptType, updateNewWallet]); + + const handleSaveAdvanced = useCallback(async (newStakeKey: string, scriptType: "all" | "any" | "atLeast") => { + setStakeKey(newStakeKey); + setNativeScriptType(scriptType); + + // If external stake credential is set, clear all signer stake keys + const updatedSignerStakeKeys = newStakeKey ? + signersStakeKeys.map(() => "") : + signersStakeKeys; + + if (newStakeKey) { + setSignerStakeKeys(updatedSignerStakeKeys); + } + + if (newWalletId) { + try { + await updateNewWallet({ + walletId: newWalletId, + name: name, + description: description, + signersAddresses: signersAddresses, + signersDescriptions: signersDescriptions, + signersStakeKeys: updatedSignerStakeKeys, + signersDRepKeys: signersDRepKeys, + numRequiredSigners: numRequiredSigners, + stakeCredentialHash: newStakeKey || null, + scriptType: scriptType, + }); + } catch (error) { + console.error("Failed to update advanced settings:", error); + } + } + }, [newWalletId, name, description, signersAddresses, signersDescriptions, signersStakeKeys, signersDRepKeys, numRequiredSigners, updateNewWallet]); + + // Remove external stake credential and try to backfill stake keys from addresses + const removeExternalStakeAndBackfill = useCallback(() => { + setStakeKey(""); + setSignerStakeKeys(signersStakeKeys); + + if (newWalletId) { + void updateNewWallet({ + walletId: newWalletId, + name: name, + description: description, + signersAddresses: signersAddresses, + signersDescriptions: signersDescriptions, + signersStakeKeys: signersStakeKeys, + signersDRepKeys: signersDRepKeys, + numRequiredSigners: numRequiredSigners, + stakeCredentialHash: null, + scriptType: nativeScriptType || undefined, + }); + } + + toast({ + title: "External stake removed", + description: "External stake credential has been removed.", + duration: 3000, + }); + }, [signersAddresses, signersStakeKeys, signersDRepKeys, newWalletId, name, description, signersDescriptions, numRequiredSigners, nativeScriptType, updateNewWallet, toast]); + + // Validation + const isValidForCreate = signersAddresses.length > 0 && + !signersAddresses.some((signer) => !signer || signer.length === 0) && + (nativeScriptType !== "atLeast" || numRequiredSigners > 0) && + name.length > 0 && + !loading; + + return { + // Core wallet data + name, + setName, + description, + setDescription, + + // Signers management + signersAddresses, + setSignerAddresses, + signersDescriptions, + setSignerDescriptions, + signersStakeKeys, + setSignerStakeKeys, + signersDRepKeys, + setSignerDRepKeys, + addSigner, + removeSigner, + + // Signature rules + numRequiredSigners, + setNumRequiredSigners, + nativeScriptType, + setNativeScriptType, + + // Advanced options + stakeKey, + setStakeKey, + removeExternalStakeAndBackfill, + + // UI state + loading, + setLoading, + + // Computed values + multisigWallet, + isValidForCreate, + + // Dependencies + userAddress, + network, + toast, + + // Migration-specific + appWallet, + newWalletId, + + // Actions + createTemporaryWallet, + createMigrationWallet, + + // Save callbacks + handleSaveWalletInfo, + handleSaveSigners, + handleSaveSignatureRules, + handleSaveAdvanced, + }; +} diff --git a/src/components/pages/wallet/info/proxy-control.tsx b/src/components/pages/wallet/info/proxy-control.tsx new file mode 100644 index 00000000..e1c0c240 --- /dev/null +++ b/src/components/pages/wallet/info/proxy-control.tsx @@ -0,0 +1,36 @@ +import React from "react"; +import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "@/components/ui/card"; +import { Badge } from "@/components/ui/badge"; +import { Settings, Wallet } from "lucide-react"; +import { ProxyControl } from "@/components/multisig/proxy"; + +/** + * ProxyControlCard component for the wallet info page + * + * This component wraps the ProxyControl component in a card format + * that matches the styling of other wallet info components. + */ +function ProxyControlCard() { + return ( + + + + + Proxy Control + + + Advanced + + + + Manage automated transactions through proxy contracts with auth token control + + + + + + + ); +} + +export default ProxyControlCard; diff --git a/src/hooks/useProxy.ts b/src/hooks/useProxy.ts new file mode 100644 index 00000000..5fb0eb4a --- /dev/null +++ b/src/hooks/useProxy.ts @@ -0,0 +1,56 @@ +import { create } from "zustand"; +import { persist, createJSONStorage } from "zustand/middleware"; +import { zustandStorage } from "@/lib/indexeddb"; + +// Simple proxy state interface +interface ProxyState { + selectedProxyId: string; + setSelectedProxy: (proxyId: string) => void; + clearSelectedProxy: () => void; +} + +// Create a simple proxy store +export const useProxyStore = create()( + persist( + (set) => ({ + selectedProxyId: "", + setSelectedProxy: (proxyId: string) => set({ selectedProxyId: proxyId }), + clearSelectedProxy: () => set({ selectedProxyId: "" }), + }), + { + name: "proxy-settings", + storage: createJSONStorage(() => zustandStorage), + } + ) +); + +// Re-export from the main proxy store +export { + useProxyData, + useSelectedProxy, + useProxyActions +} from "@/lib/zustand/proxy"; + +// Convenience hook for backward compatibility +export const useProxy = () => { + const selectedProxyId = useProxyStore((state) => state.selectedProxyId); + const setSelectedProxy = useProxyStore((state) => state.setSelectedProxy); + const clearSelectedProxy = useProxyStore((state) => state.clearSelectedProxy); + + // Proxy is enabled when a proxy is selected + const isProxyEnabled = !!selectedProxyId; + + // Enhanced clearSelectedProxy with debugging + const enhancedClearSelectedProxy = () => { + console.log("useProxy: Clearing selected proxy, current:", selectedProxyId); + clearSelectedProxy(); + console.log("useProxy: Proxy cleared"); + }; + + return { + isProxyEnabled, + selectedProxyId, + setSelectedProxy, + clearSelectedProxy: enhancedClearSelectedProxy, + }; +}; diff --git a/src/lib/zustand/proxy.ts b/src/lib/zustand/proxy.ts new file mode 100644 index 00000000..68c360e8 --- /dev/null +++ b/src/lib/zustand/proxy.ts @@ -0,0 +1,342 @@ +import { create } from "zustand"; +import { persist, createJSONStorage } from "zustand/middleware"; +import { zustandStorage } from "../indexeddb"; +import { MeshProxyContract } from "@/components/multisig/proxy/offchain"; +import { getTxBuilder } from "@/utils/get-tx-builder"; +import { useSiteStore } from "./site"; + +// Types for proxy data +export interface ProxyDrepInfo { + active: boolean; + amount: string; + deposit: string; + url?: string; + hash?: string; +} + +export interface DelegatorInfo { + address: string; + amount: string; +} + +export interface ProxyDelegatorsInfo { + delegators: DelegatorInfo[]; + totalDelegation: string; + totalDelegationADA: number; + count: number; +} + +export interface ProxyData { + id: string; + proxyAddress: string; + authTokenId: string; + paramUtxo: string; + description: string | null; + isActive: boolean; + createdAt: Date; + balance?: Array<{ unit: string; quantity: string }>; + drepId?: string; + drepInfo?: ProxyDrepInfo; + delegatorsInfo?: ProxyDelegatorsInfo; + lastUpdated?: number; +} + +interface ProxyState { + // Proxy data + proxies: { [walletId: string]: ProxyData[] }; + selectedProxyId: string; + isProxyEnabled: boolean; + + // Loading states + loading: { [walletId: string]: boolean }; + drepLoading: { [proxyId: string]: boolean }; + + // Error states + errors: { [walletId: string]: string | null }; + drepErrors: { [proxyId: string]: string | null }; + + // Actions + setProxies: (walletId: string, proxies: ProxyData[]) => void; + setSelectedProxy: (proxyId: string) => void; + setProxyEnabled: (enabled: boolean) => void; + toggleProxy: () => void; + clearSelectedProxy: () => void; + + // Loading actions + setLoading: (walletId: string, loading: boolean) => void; + setDrepLoading: (proxyId: string, loading: boolean) => void; + + // Error actions + setError: (walletId: string, error: string | null) => void; + setDrepError: (proxyId: string, error: string | null) => void; + + // Data fetching actions + fetchProxyBalance: (walletId: string, proxyId: string, proxyAddress: string, network: string) => Promise; + fetchProxyDrepInfo: (walletId: string, proxyId: string, proxyAddress: string, authTokenId: string, scriptCbor: string, network: string, paramUtxo: string, forceRefresh?: boolean) => Promise; + fetchProxyDelegatorsInfo: (walletId: string, proxyId: string, proxyAddress: string, authTokenId: string, scriptCbor: string, network: string, paramUtxo: string, forceRefresh?: boolean) => Promise; + + // Utility actions + updateProxyData: (walletId: string, proxyId: string, updates: Partial) => void; + clearProxyData: (walletId: string) => void; +} + +export const useProxyStore = create()( + persist( + (set, get) => ({ + // Initial state + proxies: {}, + selectedProxyId: "", + isProxyEnabled: false, + loading: {}, + drepLoading: {}, + errors: {}, + drepErrors: {}, + + // Basic actions + setProxies: (walletId, proxies) => + set((state) => ({ + proxies: { ...state.proxies, [walletId]: proxies }, + loading: { ...state.loading, [walletId]: false }, + errors: { ...state.errors, [walletId]: null }, + })), + + setSelectedProxy: (proxyId) => + set({ selectedProxyId: proxyId }), + + setProxyEnabled: (enabled) => + set({ isProxyEnabled: enabled }), + + toggleProxy: () => + set((state) => ({ isProxyEnabled: !state.isProxyEnabled })), + + clearSelectedProxy: () => + set({ selectedProxyId: "" }), + + // Loading actions + setLoading: (walletId, loading) => + set((state) => ({ + loading: { ...state.loading, [walletId]: loading }, + })), + + setDrepLoading: (proxyId, loading) => + set((state) => ({ + drepLoading: { ...state.drepLoading, [proxyId]: loading }, + })), + + // Error actions + setError: (walletId, error) => + set((state) => ({ + errors: { ...state.errors, [walletId]: error }, + })), + + setDrepError: (proxyId, error) => + set((state) => ({ + drepErrors: { ...state.drepErrors, [proxyId]: error }, + })), + + // Fetch proxy balance + fetchProxyBalance: async (walletId, proxyId, proxyAddress, network) => { + try { + const state = get(); + const blockchainProvider = (await import("@/utils/get-provider")).getProvider(parseInt(network)); + + const balance = await blockchainProvider.fetchAddressUTxOs(proxyAddress); + const balanceData = balance.map(utxo => ({ + unit: utxo.output.amount[0]?.unit || "lovelace", + quantity: utxo.output.amount[0]?.quantity || "0", + })); + + // Update the specific proxy's balance + const currentState = get(); + const updatedProxies = currentState.proxies[walletId]?.map(proxy => + proxy.id === proxyId + ? { ...proxy, balance: balanceData, lastUpdated: Date.now() } + : proxy + ) || []; + + set((state) => ({ + proxies: { ...state.proxies, [walletId]: updatedProxies }, + })); + } catch (error) { + get().setError(walletId, `Failed to fetch balance for proxy ${proxyId}`); + } + }, + + // Fetch proxy DRep information + fetchProxyDrepInfo: async (walletId, proxyId, proxyAddress, authTokenId, scriptCbor, network, paramUtxo, forceRefresh = false) => { + try { + get().setDrepLoading(proxyId, true); + get().setDrepError(proxyId, null); + + const txBuilder = getTxBuilder(parseInt(network)); + const proxyContract = new MeshProxyContract( + { + mesh: txBuilder, + wallet: undefined, + networkId: parseInt(network), + }, + { + paramUtxo: JSON.parse(paramUtxo || '{}'), + }, + scriptCbor, + ); + proxyContract.proxyAddress = proxyAddress; + + // Get DRep ID + const drepId = proxyContract.getDrepId(); + + // Get DRep status (now with caching and proper error handling) + const status = await proxyContract.getDrepStatus(forceRefresh); + const drepInfo: ProxyDrepInfo | undefined = status; + + // Update the specific proxy's DRep data + const currentState = get(); + const updatedProxies = currentState.proxies[walletId]?.map(proxy => + proxy.id === proxyId + ? { ...proxy, drepId, drepInfo, lastUpdated: Date.now() } + : proxy + ) || []; + + set((state) => ({ + proxies: { ...state.proxies, [walletId]: updatedProxies }, + drepLoading: { ...state.drepLoading, [proxyId]: false }, + drepErrors: { ...state.drepErrors, [proxyId]: null }, + })); + } catch (error) { + get().setDrepError(proxyId, `Failed to fetch DRep info for proxy ${proxyId}`); + get().setDrepLoading(proxyId, false); + } + }, + + // Fetch proxy delegators information + fetchProxyDelegatorsInfo: async (walletId, proxyId, proxyAddress, authTokenId, scriptCbor, network, paramUtxo, forceRefresh = false) => { + try { + get().setDrepLoading(proxyId, true); + get().setDrepError(proxyId, null); + + const txBuilder = getTxBuilder(parseInt(network)); + const proxyContract = new MeshProxyContract( + { + mesh: txBuilder, + wallet: undefined, + networkId: parseInt(network), + }, + { + paramUtxo: JSON.parse(paramUtxo || '{}'), + }, + scriptCbor, + ); + proxyContract.proxyAddress = proxyAddress; + + // Get delegators info + const delegatorsInfo = await proxyContract.getDrepDelegators(forceRefresh) as ProxyDelegatorsInfo; + + // Update the specific proxy's delegators data + const currentState = get(); + const updatedProxies = currentState.proxies[walletId]?.map(proxy => + proxy.id === proxyId + ? { ...proxy, delegatorsInfo, lastUpdated: Date.now() } + : proxy + ) || []; + + set((state) => ({ + proxies: { ...state.proxies, [walletId]: updatedProxies }, + drepLoading: { ...state.drepLoading, [proxyId]: false }, + drepErrors: { ...state.drepErrors, [proxyId]: null }, + })); + } catch (error) { + get().setDrepError(proxyId, `Failed to fetch delegators info for proxy ${proxyId}`); + get().setDrepLoading(proxyId, false); + } + }, + + // Update specific proxy data + updateProxyData: (walletId, proxyId, updates) => + set((state) => ({ + proxies: { + ...state.proxies, + [walletId]: state.proxies[walletId]?.map(proxy => + proxy.id === proxyId ? { ...proxy, ...updates } : proxy + ) || [], + }, + })), + + // Clear all proxy data for a wallet + clearProxyData: (walletId) => + set((state) => { + const newProxies = { ...state.proxies }; + delete newProxies[walletId]; + const newLoading = { ...state.loading }; + delete newLoading[walletId]; + const newErrors = { ...state.errors }; + delete newErrors[walletId]; + + return { + proxies: newProxies, + loading: newLoading, + errors: newErrors, + }; + }), + }), + { + name: "proxy-store", + storage: createJSONStorage(() => zustandStorage), + // Only persist essential state, not loading/error states + partialize: (state) => ({ + proxies: state.proxies, + selectedProxyId: state.selectedProxyId, + isProxyEnabled: state.isProxyEnabled, + }), + } + ) +); + +// Convenience hooks for easier access +export const useProxyData = (walletId?: string) => { + const proxies = useProxyStore((state) => walletId ? state.proxies[walletId] || [] : []); + const loading = useProxyStore((state) => walletId ? state.loading[walletId] || false : false); + const error = useProxyStore((state) => walletId ? state.errors[walletId] || null : null); + + return { proxies, loading, error }; +}; + +export const useSelectedProxy = () => { + const selectedProxyId = useProxyStore((state) => state.selectedProxyId); + const isProxyEnabled = useProxyStore((state) => state.isProxyEnabled); + const proxies = useProxyStore((state) => state.proxies); + + // Find the selected proxy across all wallets + let selectedProxy: ProxyData | undefined; + for (const walletProxies of Object.values(proxies)) { + selectedProxy = walletProxies.find(proxy => proxy.id === selectedProxyId); + if (selectedProxy) break; + } + + return { selectedProxy, selectedProxyId, isProxyEnabled }; +}; + +export const useProxyActions = () => { + const setProxies = useProxyStore((state) => state.setProxies); + const setSelectedProxy = useProxyStore((state) => state.setSelectedProxy); + const setProxyEnabled = useProxyStore((state) => state.setProxyEnabled); + const toggleProxy = useProxyStore((state) => state.toggleProxy); + const clearSelectedProxy = useProxyStore((state) => state.clearSelectedProxy); + const fetchProxyBalance = useProxyStore((state) => state.fetchProxyBalance); + const fetchProxyDrepInfo = useProxyStore((state) => state.fetchProxyDrepInfo); + const fetchProxyDelegatorsInfo = useProxyStore((state) => state.fetchProxyDelegatorsInfo); + const updateProxyData = useProxyStore((state) => state.updateProxyData); + const clearProxyData = useProxyStore((state) => state.clearProxyData); + + return { + setProxies, + setSelectedProxy, + setProxyEnabled, + toggleProxy, + clearSelectedProxy, + fetchProxyBalance, + fetchProxyDrepInfo, + fetchProxyDelegatorsInfo, + updateProxyData, + clearProxyData, + }; +}; diff --git a/src/server/api/root.ts b/src/server/api/root.ts index c8fa9a5d..3fba00d6 100644 --- a/src/server/api/root.ts +++ b/src/server/api/root.ts @@ -4,6 +4,8 @@ import { walletRouter } from "./routers/wallets"; import { transactionRouter } from "./routers/transactions"; import { signableRouter } from "./routers/signable"; import { ballotRouter } from "./routers/ballot"; +import { proxyRouter } from "./routers/proxy"; +import { migrationRouter } from "./routers/migrations"; /** @@ -17,6 +19,8 @@ export const appRouter = createTRPCRouter({ wallet: walletRouter, signable: signableRouter, ballot: ballotRouter, + proxy: proxyRouter, + migration: migrationRouter, }); // export type definition of API diff --git a/src/server/api/routers/migrations.ts b/src/server/api/routers/migrations.ts new file mode 100644 index 00000000..11b42971 --- /dev/null +++ b/src/server/api/routers/migrations.ts @@ -0,0 +1,152 @@ +import { z } from "zod"; +import { createTRPCRouter, publicProcedure } from "@/server/api/trpc"; + +export const migrationRouter = createTRPCRouter({ + // Get pending migrations for a user + getPendingMigrations: publicProcedure + .input(z.object({ ownerAddress: z.string() })) + .query(async ({ ctx, input }) => { + return ctx.db.migration.findMany({ + where: { + ownerAddress: input.ownerAddress, + status: { + in: ["pending", "in_progress"] + } + }, + orderBy: { + createdAt: "desc" + } + }); + }), + + // Get a specific migration by ID + getMigration: publicProcedure + .input(z.object({ migrationId: z.string() })) + .query(async ({ ctx, input }) => { + return ctx.db.migration.findUnique({ + where: { + id: input.migrationId + } + }); + }), + + // Create a new migration + createMigration: publicProcedure + .input(z.object({ + originalWalletId: z.string(), + ownerAddress: z.string(), + migrationData: z.any().optional() + })) + .mutation(async ({ ctx, input }) => { + return ctx.db.migration.create({ + data: { + originalWalletId: input.originalWalletId, + ownerAddress: input.ownerAddress, + migrationData: input.migrationData, + currentStep: 0, + status: "pending" + } + }); + }), + + // Update migration step + updateMigrationStep: publicProcedure + .input(z.object({ + migrationId: z.string(), + currentStep: z.number(), + status: z.enum(["pending", "in_progress", "completed", "failed", "cancelled"]).optional(), + newWalletId: z.string().optional(), + errorMessage: z.string().optional() + })) + .mutation(async ({ ctx, input }) => { + const updateData: any = { + currentStep: input.currentStep, + updatedAt: new Date() + }; + + if (input.status) { + updateData.status = input.status; + if (input.status === "completed") { + updateData.completedAt = new Date(); + } + } + + if (input.newWalletId) { + updateData.newWalletId = input.newWalletId; + } + + if (input.errorMessage) { + updateData.errorMessage = input.errorMessage; + } + + return ctx.db.migration.update({ + where: { + id: input.migrationId + }, + data: updateData + }); + }), + + // Update migration data + updateMigrationData: publicProcedure + .input(z.object({ + migrationId: z.string(), + migrationData: z.any() + })) + .mutation(async ({ ctx, input }) => { + return ctx.db.migration.update({ + where: { + id: input.migrationId + }, + data: { + migrationData: input.migrationData, + updatedAt: new Date() + } + }); + }), + + // Cancel a migration + cancelMigration: publicProcedure + .input(z.object({ migrationId: z.string() })) + .mutation(async ({ ctx, input }) => { + // Delete the migration record completely + return ctx.db.migration.delete({ + where: { + id: input.migrationId + } + }); + }), + + // Complete a migration + completeMigration: publicProcedure + .input(z.object({ migrationId: z.string() })) + .mutation(async ({ ctx, input }) => { + return ctx.db.migration.update({ + where: { + id: input.migrationId + }, + data: { + status: "completed", + completedAt: new Date(), + updatedAt: new Date() + } + }); + }), + + // Get migration by original wallet ID + getMigrationByOriginalWallet: publicProcedure + .input(z.object({ originalWalletId: z.string() })) + .query(async ({ ctx, input }) => { + return ctx.db.migration.findFirst({ + where: { + originalWalletId: input.originalWalletId, + status: { + in: ["pending", "in_progress"] + } + }, + orderBy: { + createdAt: "desc" + } + }); + }) +}); diff --git a/src/server/api/routers/proxy.ts b/src/server/api/routers/proxy.ts new file mode 100644 index 00000000..48b25ade --- /dev/null +++ b/src/server/api/routers/proxy.ts @@ -0,0 +1,208 @@ +import { z } from "zod"; +import { createTRPCRouter, publicProcedure } from "@/server/api/trpc"; + +export const proxyRouter = createTRPCRouter({ + getUserByAddress: publicProcedure + .input(z.object({ address: z.string() })) + .query(async ({ ctx, input }) => { + return ctx.db.user.findUnique({ + where: { + address: input.address, + }, + }); + }), + createProxy: publicProcedure + .input( + z.object({ + walletId: z.string().optional(), + userId: z.string().optional(), + proxyAddress: z.string(), + authTokenId: z.string(), + paramUtxo: z.string(), + description: z.string().optional(), + }).refine( + (data) => data.walletId || data.userId, + { + message: "Either walletId or userId must be provided", + } + ), + ) + .mutation(async ({ ctx, input }) => { + return ctx.db.proxy.create({ + data: { + walletId: input.walletId, + userId: input.userId, + proxyAddress: input.proxyAddress, + authTokenId: input.authTokenId, + paramUtxo: input.paramUtxo, + description: input.description, + }, + }); + }), + + getProxiesByWallet: publicProcedure + .input(z.object({ walletId: z.string() })) + .query(async ({ ctx, input }) => { + return ctx.db.proxy.findMany({ + where: { + walletId: input.walletId, + isActive: true, + }, + orderBy: { + createdAt: "desc", + }, + }); + }), + + getProxiesByUser: publicProcedure + .input(z.object({ userAddress: z.string() })) + .query(async ({ ctx, input }) => { + // First find the user by address + const user = await ctx.db.user.findUnique({ + where: { + address: input.userAddress, + }, + }); + + if (!user) { + return []; + } + + return ctx.db.proxy.findMany({ + where: { + userId: user.id, + isActive: true, + }, + orderBy: { + createdAt: "desc", + }, + }); + }), + + getProxiesByUserOrWallet: publicProcedure + .input(z.object({ + walletId: z.string().optional(), + userAddress: z.string().optional(), + })) + .query(async ({ ctx, input }) => { + // Prefer fetching by walletId when available + if (input.walletId) { + return ctx.db.proxy.findMany({ + where: { + walletId: input.walletId, + isActive: true, + }, + orderBy: { createdAt: "desc" }, + }); + } + + // Fallback: fetch by user address if provided + if (input.userAddress) { + const user = await ctx.db.user.findUnique({ + where: { address: input.userAddress }, + }); + if (!user) return []; + return ctx.db.proxy.findMany({ + where: { + userId: user.id, + isActive: true, + }, + orderBy: { createdAt: "desc" }, + }); + } + + // No criteria provided + return []; + }), + + getProxyById: publicProcedure + .input(z.object({ id: z.string() })) + .query(async ({ ctx, input }) => { + return ctx.db.proxy.findUnique({ + where: { + id: input.id, + }, + }); + }), + + updateProxy: publicProcedure + .input( + z.object({ + id: z.string(), + description: z.string().optional(), + isActive: z.boolean().optional(), + walletId: z.string().optional(), + userId: z.string().optional(), + }), + ) + .mutation(async ({ ctx, input }) => { + return ctx.db.proxy.update({ + where: { + id: input.id, + }, + data: { + description: input.description, + isActive: input.isActive, + walletId: input.walletId, + userId: input.userId, + }, + }); + }), + + deleteProxy: publicProcedure + .input(z.object({ id: z.string() })) + .mutation(async ({ ctx, input }) => { + return ctx.db.proxy.delete({ + where: { + id: input.id, + }, + }); + }), + + deactivateProxy: publicProcedure + .input(z.object({ id: z.string() })) + .mutation(async ({ ctx, input }) => { + return ctx.db.proxy.update({ + where: { + id: input.id, + }, + data: { + isActive: false, + }, + }); + }), + + transferProxies: publicProcedure + .input(z.object({ + fromWalletId: z.string(), + toWalletId: z.string(), + })) + .mutation(async ({ ctx, input }) => { + // Find all active proxies for the source wallet + const proxies = await ctx.db.proxy.findMany({ + where: { + walletId: input.fromWalletId, + isActive: true, + }, + }); + + if (proxies.length === 0) { + return { transferred: 0, message: "No proxies found to transfer" }; + } + + // Update all proxies to point to the new wallet + const updatePromises = proxies.map(proxy => + ctx.db.proxy.update({ + where: { id: proxy.id }, + data: { walletId: input.toWalletId }, + }) + ); + + await Promise.all(updatePromises); + + return { + transferred: proxies.length, + message: `Successfully transferred ${proxies.length} proxy${proxies.length !== 1 ? 'ies' : ''}` + }; + }), +}); \ No newline at end of file diff --git a/src/server/api/routers/wallets.ts b/src/server/api/routers/wallets.ts index 2503cd1e..9d5529c2 100644 --- a/src/server/api/routers/wallets.ts +++ b/src/server/api/routers/wallets.ts @@ -295,4 +295,97 @@ export const walletRouter = createTRPCRouter({ }, }); }), + + setMigrationTarget: publicProcedure + .input(z.object({ + walletId: z.string(), + migrationTargetWalletId: z.string() + })) + .mutation(async ({ ctx, input }) => { + return ctx.db.wallet.update({ + where: { + id: input.walletId, + }, + data: { + migrationTargetWalletId: input.migrationTargetWalletId, + }, + }); + }), + + clearMigrationTarget: publicProcedure + .input(z.object({ walletId: z.string() })) + .mutation(async ({ ctx, input }) => { + return ctx.db.wallet.update({ + where: { + id: input.walletId, + }, + data: { + migrationTargetWalletId: null, + }, + }); + }), + + abortMigration: publicProcedure + .input(z.object({ + walletId: z.string(), + newWalletId: z.string().optional() + })) + .mutation(async ({ ctx, input }) => { + // Try to delete the new wallet if it exists (it might be a NewWallet or Wallet) + if (input.newWalletId) { + try { + // First check if it exists in NewWallet table + const newWallet = await ctx.db.newWallet.findUnique({ + where: { id: input.newWalletId } + }); + + if (newWallet) { + await ctx.db.newWallet.delete({ + where: { id: input.newWalletId } + }); + console.log("Deleted NewWallet:", input.newWalletId); + } else { + // Check if it exists in Wallet table + const wallet = await ctx.db.wallet.findUnique({ + where: { id: input.newWalletId } + }); + + if (wallet) { + await ctx.db.wallet.delete({ + where: { id: input.newWalletId } + }); + console.log("Deleted Wallet:", input.newWalletId); + } else { + console.log("No wallet found with ID:", input.newWalletId, "- migration might be in a different state"); + } + } + } catch (error) { + console.error("Error deleting wallet during migration abort:", error); + // Continue with clearing migration target even if deletion fails + } + } + + // Clear the migration target reference from the original wallet + return ctx.db.wallet.update({ + where: { + id: input.walletId, + }, + data: { + migrationTargetWalletId: null, + }, + }); + }), + + archiveWallet: publicProcedure + .input(z.object({ walletId: z.string() })) + .mutation(async ({ ctx, input }) => { + return ctx.db.wallet.update({ + where: { + id: input.walletId, + }, + data: { + isArchived: true, + }, + }); + }), });