{"_id":"@daisypayments/subscription-contracts","_rev":"9-2353b8454b5552b9122b3a276829ac3c","name":"@daisypayments/subscription-contracts","dist-tags":{"latest":"4.2.1","beta":"5.0.1-beta"},"versions":{"4.2.1":{"name":"@daisypayments/subscription-contracts","version":"4.2.1","repository":{"type":"git","url":"git+https://github.com/consensys/subscription-contracts.git"},"author":{"name":"vdrg","email":"vicente.dragicevic@consensys.net"},"license":"MIT","main":"index.js","scripts":{"compile":"truffle compile","coverage":"./scripts/coverage.sh","exec":"truffle exec","ganache":"ganache-cli","docgen":"./scripts/docgen.sh","publish-docs":"./scripts/publish-docs.sh","prepublish":"yarn compile","lint":"solhint \"contracts/**/*.sol\"","migrate":"truffle migrate","test":"./scripts/test.sh"},"devDependencies":{"@daisypayments/eslint-config":"^1.5.1","bip39":"^2.5.0","bn.js":"^4.11.8","chai":"^4.2.0","codecov":"^3.2.0","dotenv":"^6.2.0","eslint":"^5.13.0","eslint-config-prettier":"^4.0.0","eslint-plugin-mocha":"^5.2.1","eslint-plugin-prettier":"^3.0.1","eth-gas-reporter":"0.1.10","eth-sig-util":"^2.1.1","ethereumjs-util":"^6.1.0","ethereumjs-wallet":"^0.6.3","ganache-cli":"^6.4.4","lodash":"^4.17.11","moment":"^2.24.0","openzeppelin-solidity":"2.2.0","openzeppelin-test-helpers":"^0.1.2","prettier":"^1.16.3","solhint":"^2.0.0","solidity-coverage":"^0.6.0-beta.3","solidity-docgen":"^0.1.1","truffle":"^5.0.22","truffle-hdwallet-provider":"^1.0.4"},"gitHead":"31413d94e0277f8b0c024a181b1ea1cad55fc7a4","description":"[![CircleCI](https://circleci.com/gh/consensys/subscription-contracts.svg?style=shield&circle-token=fa80cef2024b3f1042ec1d3113f163c70e59354a)](https://circleci.com/gh/consensys/subscription-contracts) [![codecov](https://codecov.io/gh/consensys/subscripti","bugs":{"url":"https://github.com/consensys/subscription-contracts/issues"},"homepage":"https://github.com/consensys/subscription-contracts#readme","_id":"@daisypayments/subscription-contracts@4.2.1","_npmVersion":"6.4.1","_nodeVersion":"10.13.0","_npmUser":{"name":"jmoreira","email":"jmoreiras@gmail.com"},"dist":{"integrity":"sha512-nveGmgRZ6TWtEXkUe7nd10egBhsSFKDj+TYUUjekB6Y76X21ld+ylfZ7JNaFBpUhbOlzoriM4DsGiwJ1LgrYLA==","shasum":"57f7ee39daaec926a9be351a82a5b162251d6215","tarball":"https://registry.npmjs.org/@daisypayments/subscription-contracts/-/subscription-contracts-4.2.1.tgz","fileCount":7,"unpackedSize":2985435,"npm-signature":"-----BEGIN PGP SIGNATURE-----\r\nVersion: OpenPGP.js v3.0.4\r\nComment: https://openpgpjs.org\r\n\r\nwsFcBAEBCAAQBQJdG+zBCRA9TVsSAnZWagAArucQAIfayVPUcYRIbAddkaLl\n16jLQGHtY+fYPYf2+4JgwQa1YIBqxado+aNxHlYqT+EdipDBDWlhVIYoBNBq\nYrLmg5+MzA4UcasAT+HjPQUelG32h9cgxpfIvQOszqFZ7TdyUs3FknHIlm4Y\nvyQeV3ipfen9cmnUlrMFqlkKWqkJ4Xbj0THgfB3UfoYNstIbd2ZceH8b+TAK\nxR/F6msZgl5lLM5pw2G0GFXIG2kMK+sOqvOE4u3sMa0Nchbct5x5+APyZfDh\n2JAX6OSpBZYaqMUXoj2HjesBzHeWtsGP8nZbNGyvqNEkjAXMyoT2EGXyVt94\nFfwfZDwmL06Uc4xVPGUQOHYrbEWeJY361y5bzEDFCgFuGApO+uIimOj4hNy0\nGOz26n+4P/edqAVkVZdR9HeF1NLG6+jRtcBCXCqf/ivxV09DbmME5RHv0qAd\npYp5MQw6bP//x6D9WGx2nJ7srd62lGeXmUBGT3Pvw6eGeGPNhCHA9u4vI+g7\n5vGx/bm1aoMfD0KcZ30krNHnB6ffCTQqTF3+mE5raiDLv5ZZ5PUJv1OppWWj\nI1OjlptHePu7cRAjh8dcvNmkKD9kmp601Z2YHn/phBXh4FWrycdz9jJkLKef\nG29foEEi7AG+ExnSNu8gdVTKJR8/1f+lX4rq8OFkatkMkdCa9SYpoi0zWpTr\nu86T\r\n=rgWE\r\n-----END PGP SIGNATURE-----\r\n","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEQCIFxOGkWc907fwXzsqFFDO/vhUnIuIRPqfqRMeSjb2B2hAiAzFJ6h+WSYhbNjBvIMI50NnvzCrmd810H61em4FTD1Ow=="}]},"maintainers":[{"name":"daisy-duck","email":"hello@daisypayments.com"},{"name":"jmoreira","email":"jmoreiras@gmail.com"}],"directories":{},"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/subscription-contracts_4.2.1_1562111168859_0.1240835022044513"},"_hasShrinkwrap":false},"5.0.0-beta":{"name":"@daisypayments/subscription-contracts","version":"5.0.0-beta","repository":{"type":"git","url":"https://github.com/consensys/daisy-subscription-contracts"},"author":{"name":"vdrg","email":"vicente.dragicevic@consensys.net"},"license":"MIT","main":"index.js","scripts":{"compile":"truffle compile","coverage":"./scripts/coverage.sh","exec":"truffle exec","ganache":"ganache-cli","docgen":"./scripts/docgen.sh","publish-docs":"./scripts/publish-docs.sh","prepublish":"yarn compile","lint":"solhint \"contracts/**/*.sol\"","migrate":"truffle migrate","test":"./scripts/test.sh"},"devDependencies":{"@tokenfoundry/eslint-config":"^1.5.1","bip39":"^2.5.0","bn.js":"^4.11.8","chai":"^4.2.0","codecov":"^3.2.0","dotenv":"^6.2.0","eslint":"^5.13.0","eslint-config-prettier":"^4.0.0","eslint-plugin-mocha":"^5.2.1","eslint-plugin-prettier":"^3.0.1","eth-gas-reporter":"0.1.10","eth-sig-util":"^2.2.0","ethereumjs-util":"^6.1.0","ethereumjs-wallet":"^0.6.3","ganache-cli":"^6.4.4","lodash":"^4.17.11","moment":"^2.24.0","openzeppelin-solidity":"^2.3.0","openzeppelin-test-helpers":"^0.4.0","prettier":"^1.16.3","solhint":"^2.0.0","solidity-coverage":"^0.6.0-beta.3","solidity-docgen":"^0.1.1","truffle":"^5.0.25","truffle-hdwallet-provider":"^1.0.4"},"readmeFilename":"README.md","readme":"# Daisy Contracts\n[![CircleCI](https://circleci.com/gh/tokenfoundry/subscription-contracts.svg?style=shield&circle-token=fa80cef2024b3f1042ec1d3113f163c70e59354a)](https://circleci.com/gh/tokenfoundry/subscription-contracts) [![codecov](https://codecov.io/gh/tokenfoundry/subscription-contracts/branch/master/graph/badge.svg?token=6Wl1hPg27M)](https://codecov.io/gh/tokenfoundry/subscription-contracts)\n\n(DOCGEN NOT WORKING IN CURRENT VERSION) NatSpec docs are available [here](https://tokenfoundry.github.io/subscription-contracts/) (generated with [solidity-codegen](https://github.com/OpenZeppelin/solidity-docgen))\n\n## Overview\n\n### Subscriptions\n\nA subscription is composed of:\n\n* subscriber: address from which tokens will be transferred from.\n* token: address of the ERC 20 token that the subscription is denominated in.\n* amount: number of tokens to transfer in each payment.\n* periodUnit: \"Day\", \"Month\", or \"Year\".\n* periods: number of period units between payments.\n* maxExecutions: max number of payments that can be made before the subscriber must manually renew their subscription. If this value is 0, there is no execution limit.\n* credits: amount of tokens to substract from future payments. On each payment, these credits get consumed until they get to 0.\n\nA subscription can be in one of four states:\n1. Created: after it is created but has yet to be executed.\n2. Active: Once it has been executed and the next payment is in the future.\n3. Active and Cancelled: When it is cancelled before reaching the next payment timestamp. It will remain active until the end of the period.\n4. Cancelled: when it has been cancelled and the last billed period has ended.\n5. Deleted: the subscription data will be deleted upon execution if the subscription can't be executed anymore.\n\n### Plans\n\nA plan is just a way to group multiple subscriptions, and allows the publisher to invalidate a group of subscriptions at once. A plan is identified by a bytes32 identifier. When a plan based subscription is created, it is necessary to specify the plan's identifier, and the creation only goes through if a valid authorization signature is provided.\n\nThe contract provides a function to delete a plan by providing the plan id. All subscriptions with that plan get invalidated (they get deleted upon the next execution).\n\n## Core Contracts\n\n### `SubscriptionManager.sol`\n\nThis is the base implementation. It handles creation, execution, and cancellation, and provides internal methods that can be used or overriden by child contracts.\n\nIt also provides helpers like `getActionHash`, `_getPeriodUnitHash` and `_replayGuard` for delegated execution (optional extension for delegated execution).\n\nFinally, it provides methods for enumerating subscriptions and subscription by subscriber (optional extension for enumeration). This implementation was adapted from OpenZeppelin's `EIP721Enumerable` [implementation](https://github.com/OpenZeppelin/openzeppelin-solidity/blob/master/contracts/token/ERC721/ERC721Enumerable.sol).\n\n## Specific Use Cases\n\n### `PlanSubscriptionManager.sol`\n\nThis contract inherits from the base contract and implements plan based subscriptions.\n\n## Time\n\nTo support different time units (days, months and years) we use [BokkyPooBah's Date Time Library](https://github.com/bokkypoobah/BokkyPooBahsDateTimeLibrary).\n\n## Subscription Flow with Delegated Execution (for Plan based usecase)\n\n1. Subscriber calls the `approve` function in the token in which the subscription is denominated in to allow the manager contract to manipulate her funds.\n2. Using EIP 712, subscriber signs the creation of a subscription.\n3. A relayer executes the creation by calling the method `create()` and passing the parameters and signature.\n4. At the beggining of each payment period, a relayer can execute the subscription and bill the subscriber.\n\nFor subscription services created using Daisy the platform, Daisy will serve as the relayer in this flow.\n\n## Off-chain service flow\n\n#### Checking if the publisher needs to provide the service\n\n1. Receive request from subscriber.\n2. Call `subscriptionManager.nextPaymentTimestamp(subscriptionId)`.\n3. If `now < nextPaymentTimestamp`, answer the request.\n\n#### Executing subscriptions\n\nTo retrieve all subscription ids from the contract (Note: if count is too large, it could be better to obtain the ids in batches):\n1. Call `subscriptionManager.subscriptionCount()`.\n2. Call `subscriptionManager.subscriptionRange(0, count)`.\n\nTo execute a batch of subscriptions:\n1. Call `subscriptionManager.executeBatch(ids)`.\n2. In the logs, there may be one event present that can be used by the service to update its state:\n    * `SubscriptionNotFound(subscriptionId)`\n    * `SubscriptionNotReady(subscriptionId, nextPayment)`\n    * `SubscriptionExecuted(subscriptionId, nextPayment) `\n    * `SubscriptionDeleted(subscriptionId, reason)`\n\nThe `reason` parameter in the SubscriptionDeleted event can correspond to:\n* 0 (CANCELLED): The subscription was cancelled before the execution.\n* 1 (EXPIRED): The subscription reached its maxExecutions in the previous execution.\n* 2 (INVALID_STATE): The state was invalid during the execution. In the plan based usecase, this can happen if the subscription's plan was deleted.\n* 3 (NOT_ENOUGH_FUNDS): The subscriber address doesn't have enough funds to perform the execution.\n\n## Key Differences Between Daisy and the Current EIP 1337 Proposal\n\n#### Subscriptions creation is not standardized\n\nBy not defining how the subscription must be created, we can support multiple different use cases (e.g. plan or tier based subscriptions, or subscriptions whose prices are determined by what feautures are turned on/off).\n\n#### Subscription data is stored in the contract\n\nThis makes interoperability with other contracts/services easier, without needing to rely on a centralized data source. Subscription data is removed from the contract if it can't be executed anymore or if the user doesn't have enough funds.\n\n#### Execution of a payment only requires specifying the subscription id\n\nThis allows for easier batching of executions and makes it easier for off-chain services to execute subscriptions.\n\n#### Delegated execution and enumeration are OPTIONAL\n\nThere are three interfaces used by the base implementation: `ISubscriptionManager`, `IDelegatedSubscriptionManager` and `IEnumerableSubscriptionManager`. In this implementation, all of these interfaces are implemented in the base contract as most of the time they will be used together. However, we propose that the delegated execution and enumerable functionality should be optional (similar to the ideas present in ERC721).\n\n#### `isValidSubscription()` split into `isCancelled(subscriptionId)` and `nextPaymentTimestamp(subscriptionId)`\n\nInstead of having an `isValidSubscription()` function that returns a boolean, this implementation provides a `nextPaymentTimestamp()` function that returns the unix timestamp at which the next payment can be executed. This returned value is more usable than a boolean. On the other hand, with `isCancelled` one can get more granular information about a subscription, improving interoperability.\n\n# Testing\n\nTo run the tests, clone this repo and run `yarn install` to install dependencies.\n\nRun `yarn test` to run all tests.\n\nRun `yarn coverage` to run tests and get code coverage.\n\n","description":"[![CircleCI](https://circleci.com/gh/tokenfoundry/subscription-contracts.svg?style=shield&circle-token=fa80cef2024b3f1042ec1d3113f163c70e59354a)](https://circleci.com/gh/tokenfoundry/subscription-contracts) [![codecov](https://codecov.io/gh/tokenfoundry/s","licenseText":"MIT License\n\nCopyright (c) 2019 Token Foundry\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\nof this software and associated documentation files (the \"Software\"), to deal\nin the Software without restriction, including without limitation the rights\nto use, copy, modify, merge, publish, distribute, sublicense, and/or sell\ncopies of the Software, and to permit persons to whom the Software is\nfurnished to do so, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in all\ncopies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\nSOFTWARE.\n","_id":"@daisypayments/subscription-contracts@5.0.0-beta","dist":{"shasum":"360aa5990a3f810023f81e8aaf6435dd2cf14e6b","integrity":"sha512-SYNW8qRWNio6p6XcLXOOWzSHhoEKgMNBw521A76EzjBM7fn6rGXzJctgDVxJhnYdSRaoFex4uWxhBzg4qPITVA==","tarball":"https://registry.npmjs.org/@daisypayments/subscription-contracts/-/subscription-contracts-5.0.0-beta.tgz","fileCount":10,"unpackedSize":2541908,"npm-signature":"-----BEGIN PGP SIGNATURE-----\r\nVersion: OpenPGP.js v3.0.4\r\nComment: https://openpgpjs.org\r\n\r\nwsFcBAEBCAAQBQJdI32/CRA9TVsSAnZWagAAA6wP/inao0FzH0V7ugRLTPlc\nLTt6RFDSH1NLbvnK6BWrSLD8ceDZKr6WpXq/V7G6xb75l/Upq733fuKtzvSg\nd7lNXSQn7ug/ENhSw6/mleGaxIVX0IlaMCThdDGotQTczM5l8JBZ8IOIW+zq\nemEhxX1sxT2wAqzt9F1g4R9wyAQhKLlCkqpPpcmx/BqUVvQy7BZIpiIfyvMe\nEVTYw/lF343kJHO7tT1l981ffQIfbeCx/fa5inROJ2R7ZUr0y1rb0/ZxRh4l\nNcRNlH0d512gxaQ7o84FBrjy/cXk50n8bGMNP+77CsL5xgbKtJRTdup3/x23\narBCriFb9sC3jl7C8I/GrXMPXBkjROjITe99Hxv/fkN+8+QG+Rtk/LEcVJ8b\n+e1RNGBxaljkEVabEEJnHDlkB83ufhhqMXO6NA+TOG88wf/LxSNgzulsFupR\nWVLdmbqyGechQG4VjtyFv9dw0b9jIT9BOzYs85vm8qeYHfQeLz1fnuqStB9L\nKmgM7Z1TUePInFsrQkabOseaWQbGRaOjUrazZjqLSk8+JB/jfU3AGu/ZZZfX\nyzEdsDvEEFDiytCpjGx1jLs+XBII3W3ynND/KJ2HE5/77TD2TJmJmRgXA35m\nXW+c7anLE/uQJyDXp24o4ZFGB7+TDmieLtnzx66VIKy+Pjqp1jJAm3fL/IZC\nqPAd\r\n=uyVR\r\n-----END PGP SIGNATURE-----\r\n","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEUCIQCbCjjlBzpLmnjMzsJHUHmaVc1GL1qsaWsePShznl1ETwIgFUPZk6WuJbXhMJwTuHvyAGi8xTzwxXmFrC93YngL3/k="}]},"maintainers":[{"email":"jmoreiras@gmail.com","name":"jmoreira"},{"email":"lopezjuripatricio@gmail.com","name":"lopezjurip"},{"email":"lhloreti@gmail.com","name":"sloreti"},{"email":"vdrg@protonmail.ch","name":"vdrg"}],"_npmUser":{"name":"vdrg","email":"vdrg@protonmail.ch"},"directories":{},"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/subscription-contracts_5.0.0-beta_1562607038246_0.2924048111225177"},"_hasShrinkwrap":false},"5.0.1-beta":{"name":"@daisypayments/subscription-contracts","version":"5.0.1-beta","repository":{"type":"git","url":"https://github.com/consensys/daisy-subscription-contracts"},"author":{"name":"vdrg","email":"vicente.dragicevic@consensys.net"},"license":"MIT","main":"index.js","scripts":{"compile":"truffle compile","coverage":"./scripts/coverage.sh","exec":"truffle exec","ganache":"ganache-cli","docgen":"./scripts/docgen.sh","publish-docs":"./scripts/publish-docs.sh","prepublish":"yarn compile","lint":"solhint \"contracts/**/*.sol\"","migrate":"truffle migrate","test":"./scripts/test.sh"},"devDependencies":{"@tokenfoundry/eslint-config":"^1.5.1","bip39":"^2.5.0","bn.js":"^4.11.8","chai":"^4.2.0","codecov":"^3.2.0","dotenv":"^6.2.0","eslint":"^5.13.0","eslint-config-prettier":"^4.0.0","eslint-plugin-mocha":"^5.2.1","eslint-plugin-prettier":"^3.0.1","eth-gas-reporter":"0.1.10","eth-sig-util":"^2.2.0","ethereumjs-util":"^6.1.0","ethereumjs-wallet":"^0.6.3","ganache-cli":"^6.4.4","lodash":"^4.17.11","moment":"^2.24.0","openzeppelin-solidity":"^2.3.0","openzeppelin-test-helpers":"^0.4.0","prettier":"^1.16.3","solhint":"^2.0.0","solidity-coverage":"^0.6.0","solidity-docgen":"^0.1.1","truffle":"^5.0.25","truffle-hdwallet-provider":"^1.0.4"},"readmeFilename":"README.md","readme":"# Daisy Contracts\n[![CircleCI](https://circleci.com/gh/tokenfoundry/subscription-contracts.svg?style=shield&circle-token=fa80cef2024b3f1042ec1d3113f163c70e59354a)](https://circleci.com/gh/tokenfoundry/subscription-contracts) [![codecov](https://codecov.io/gh/tokenfoundry/subscription-contracts/branch/master/graph/badge.svg?token=6Wl1hPg27M)](https://codecov.io/gh/tokenfoundry/subscription-contracts)\n\n(DOCGEN NOT WORKING IN CURRENT VERSION) NatSpec docs are available [here](https://tokenfoundry.github.io/subscription-contracts/) (generated with [solidity-codegen](https://github.com/OpenZeppelin/solidity-docgen))\n\n## Overview\n\n### Subscriptions\n\nA subscription is composed of:\n\n* subscriber: address from which tokens will be transferred from.\n* token: address of the ERC 20 token that the subscription is denominated in.\n* amount: number of tokens to transfer in each payment.\n* periodUnit: \"Day\", \"Month\", or \"Year\".\n* periods: number of period units between payments.\n* maxExecutions: max number of payments that can be made before the subscriber must manually renew their subscription. If this value is 0, there is no execution limit.\n* credits: amount of tokens to substract from future payments. On each payment, these credits get consumed until they get to 0.\n\nA subscription can be in one of four states:\n1. Created: after it is created but has yet to be executed.\n2. Active: Once it has been executed and the next payment is in the future.\n3. Active and Cancelled: When it is cancelled before reaching the next payment timestamp. It will remain active until the end of the period.\n4. Cancelled: when it has been cancelled and the last billed period has ended.\n5. Deleted: the subscription data will be deleted upon execution if the subscription can't be executed anymore.\n\n### Plans\n\nA plan is just a way to group multiple subscriptions, and allows the publisher to invalidate a group of subscriptions at once. A plan is identified by a bytes32 identifier. When a plan based subscription is created, it is necessary to specify the plan's identifier, and the creation only goes through if a valid authorization signature is provided.\n\nThe contract provides a function to delete a plan by providing the plan id. All subscriptions with that plan get invalidated (they get deleted upon the next execution).\n\n## Core Contracts\n\n### `SubscriptionManager.sol`\n\nThis is the base implementation. It handles creation, execution, and cancellation, and provides internal methods that can be used or overriden by child contracts.\n\nIt also provides helpers like `getActionHash`, `_getPeriodUnitHash` and `_replayGuard` for delegated execution (optional extension for delegated execution).\n\nFinally, it provides methods for enumerating subscriptions and subscription by subscriber (optional extension for enumeration). This implementation was adapted from OpenZeppelin's `EIP721Enumerable` [implementation](https://github.com/OpenZeppelin/openzeppelin-solidity/blob/master/contracts/token/ERC721/ERC721Enumerable.sol).\n\n## Specific Use Cases\n\n### `PlanSubscriptionManager.sol`\n\nThis contract inherits from the base contract and implements plan based subscriptions.\n\n## Time\n\nTo support different time units (days, months and years) we use [BokkyPooBah's Date Time Library](https://github.com/bokkypoobah/BokkyPooBahsDateTimeLibrary).\n\n## Subscription Flow with Delegated Execution (for Plan based usecase)\n\n1. Subscriber calls the `approve` function in the token in which the subscription is denominated in to allow the manager contract to manipulate her funds.\n2. Using EIP 712, subscriber signs the creation of a subscription.\n3. A relayer executes the creation by calling the method `create()` and passing the parameters and signature.\n4. At the beggining of each payment period, a relayer can execute the subscription and bill the subscriber.\n\nFor subscription services created using Daisy the platform, Daisy will serve as the relayer in this flow.\n\n## Off-chain service flow\n\n#### Checking if the publisher needs to provide the service\n\n1. Receive request from subscriber.\n2. Call `subscriptionManager.nextPaymentTimestamp(subscriptionId)`.\n3. If `now < nextPaymentTimestamp`, answer the request.\n\n#### Executing subscriptions\n\nTo retrieve all subscription ids from the contract (Note: if count is too large, it could be better to obtain the ids in batches):\n1. Call `subscriptionManager.subscriptionCount()`.\n2. Call `subscriptionManager.subscriptionRange(0, count)`.\n\nTo execute a batch of subscriptions:\n1. Call `subscriptionManager.executeBatch(ids)`.\n2. In the logs, there may be one event present that can be used by the service to update its state:\n    * `SubscriptionNotFound(subscriptionId)`\n    * `SubscriptionNotReady(subscriptionId, nextPayment)`\n    * `SubscriptionExecuted(subscriptionId, nextPayment) `\n    * `SubscriptionDeleted(subscriptionId, reason)`\n\nThe `reason` parameter in the SubscriptionDeleted event can correspond to:\n* 0 (CANCELLED): The subscription was cancelled before the execution.\n* 1 (EXPIRED): The subscription reached its maxExecutions in the previous execution.\n* 2 (INVALID_STATE): The state was invalid during the execution. In the plan based usecase, this can happen if the subscription's plan was deleted.\n* 3 (NOT_ENOUGH_FUNDS): The subscriber address doesn't have enough funds to perform the execution.\n\n## Key Differences Between Daisy and the Current EIP 1337 Proposal\n\n#### Subscriptions creation is not standardized\n\nBy not defining how the subscription must be created, we can support multiple different use cases (e.g. plan or tier based subscriptions, or subscriptions whose prices are determined by what feautures are turned on/off).\n\n#### Subscription data is stored in the contract\n\nThis makes interoperability with other contracts/services easier, without needing to rely on a centralized data source. Subscription data is removed from the contract if it can't be executed anymore or if the user doesn't have enough funds.\n\n#### Execution of a payment only requires specifying the subscription id\n\nThis allows for easier batching of executions and makes it easier for off-chain services to execute subscriptions.\n\n#### Delegated execution and enumeration are OPTIONAL\n\nThere are three interfaces used by the base implementation: `ISubscriptionManager`, `IDelegatedSubscriptionManager` and `IEnumerableSubscriptionManager`. In this implementation, all of these interfaces are implemented in the base contract as most of the time they will be used together. However, we propose that the delegated execution and enumerable functionality should be optional (similar to the ideas present in ERC721).\n\n#### `isValidSubscription()` split into `isCancelled(subscriptionId)` and `nextPaymentTimestamp(subscriptionId)`\n\nInstead of having an `isValidSubscription()` function that returns a boolean, this implementation provides a `nextPaymentTimestamp()` function that returns the unix timestamp at which the next payment can be executed. This returned value is more usable than a boolean. On the other hand, with `isCancelled` one can get more granular information about a subscription, improving interoperability.\n\n# Testing\n\nTo run the tests, clone this repo and run `yarn install` to install dependencies.\n\nRun `yarn test` to run all tests.\n\nRun `yarn coverage` to run tests and get code coverage.\n\n","description":"[![CircleCI](https://circleci.com/gh/tokenfoundry/subscription-contracts.svg?style=shield&circle-token=fa80cef2024b3f1042ec1d3113f163c70e59354a)](https://circleci.com/gh/tokenfoundry/subscription-contracts) [![codecov](https://codecov.io/gh/tokenfoundry/s","licenseText":"MIT License\n\nCopyright (c) 2019 Token Foundry\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\nof this software and associated documentation files (the \"Software\"), to deal\nin the Software without restriction, including without limitation the rights\nto use, copy, modify, merge, publish, distribute, sublicense, and/or sell\ncopies of the Software, and to permit persons to whom the Software is\nfurnished to do so, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in all\ncopies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\nSOFTWARE.\n","_id":"@daisypayments/subscription-contracts@5.0.1-beta","dist":{"shasum":"59592f23e568e7106adb703ee02e0bcb8fb48dde","integrity":"sha512-J+MmZOu1aBS7tbe8CSwzhgszi8FkursHz+a+/aI16fGv91qbcd2BcT713QNTOgz9kgPIFR1wvBWyEgz7gQAFaw==","tarball":"https://registry.npmjs.org/@daisypayments/subscription-contracts/-/subscription-contracts-5.0.1-beta.tgz","fileCount":10,"unpackedSize":2705385,"npm-signature":"-----BEGIN PGP SIGNATURE-----\r\nVersion: OpenPGP.js v3.0.4\r\nComment: https://openpgpjs.org\r\n\r\nwsFcBAEBCAAQBQJdL0tMCRA9TVsSAnZWagAAONAP/AovvabQ94fchmM6Hwlv\neAMYHb5vtE57qiSwLIBIDv/gWtdMxMDXdYZtL7vGzsCcr3c4CGAyBLcqUJcM\n4KJJyfcF3gTC1xw/Hy6XP3jdE23Ogs+XveNf3fx0ICKrrw74HlLxc+B7Gcbb\nL43aCP96YuwEN+XesLdedeGAyWn3Q9BvktTthE1CU/PG3OhuorBAjG0j4C1k\nHPjhxZM/9MIx7CfvJJi8Bct7xJu5f6shp7o8bbNlSIa96Eubaiu0Y9zODGcH\nqVloxg69nroly2pln7u03AFZsPXp2imzjvhzyMTcu9AmPrjBhjwAZrBnPjoE\nP6nua93r4TSR99OotdAVZyGNc40LQhvDhS7y1pLB1Xi/YgF5TaWiNRIdnoFs\nop3+SEt1IPiVdIWIhic2iLD0IGjr8v5WYnuFMy5ZGsJBsex9LTh8uzb3ukw3\nP4cfiIsUiwyhkPk8oJ9YANqiRv+y/jEeuibZ0cJ54/YONSSX4NJWa/21viP0\nYsH8wIyMycWqPewoVP/El8G0rP3YSbiyYVI8rGIuh92R9jC8+JKpMeTswHWd\nDJWqWNqRqtYibSebiRiAn0F3oQouxB+I7jm74JzoYdmfQ9nmsBVhids19I3H\n1m20xXNIbEip2RIOXPKKyrxaFLFeOtZxM62U/nhLiPmviZa5lWvtZl7Cv/61\nzpzt\r\n=wNKz\r\n-----END PGP SIGNATURE-----\r\n","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEQCIHsPHbtWlxQlr5XAVJPs95Cg9hEG1gfaMzT/PBRy7FvuAiA5oIjSKI/vvGUVvUHgvGzfUrv03DbARn/vIt0yIlg2RA=="}]},"maintainers":[{"email":"jmoreiras@gmail.com","name":"jmoreira"},{"email":"lopezjuripatricio@gmail.com","name":"lopezjurip"},{"email":"lhloreti@gmail.com","name":"sloreti"},{"email":"vdrg@protonmail.ch","name":"vdrg"}],"_npmUser":{"name":"vdrg","email":"vdrg@protonmail.ch"},"directories":{},"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/subscription-contracts_5.0.1-beta_1563380556010_0.4753077930311085"},"_hasShrinkwrap":false}},"time":{"created":"2019-07-02T23:46:08.639Z","4.2.1":"2019-07-02T23:46:09.029Z","modified":"2022-04-05T02:36:47.592Z","5.0.0-beta":"2019-07-08T17:30:38.478Z","5.0.1-beta":"2019-07-17T16:22:36.122Z"},"maintainers":[{"email":"nate.chastain@consensys.net","name":"nchastain"},{"email":"wachunei@gmail.com","name":"wachunei"},{"email":"lopezjuripatricio@gmail.com","name":"lopezjurip"},{"email":"vdrg@protonmail.ch","name":"vdrg"},{"email":"lhloreti@gmail.com","name":"sloreti"},{"email":"jmoreiras@gmail.com","name":"jmoreira"}],"description":"[![CircleCI](https://circleci.com/gh/consensys/subscription-contracts.svg?style=shield&circle-token=fa80cef2024b3f1042ec1d3113f163c70e59354a)](https://circleci.com/gh/consensys/subscription-contracts) [![codecov](https://codecov.io/gh/consensys/subscripti","homepage":"https://github.com/consensys/subscription-contracts#readme","repository":{"type":"git","url":"git+https://github.com/consensys/subscription-contracts.git"},"author":{"name":"vdrg","email":"vicente.dragicevic@consensys.net"},"bugs":{"url":"https://github.com/consensys/subscription-contracts/issues"},"license":"MIT","readme":"","readmeFilename":""}