@towns-protocol/contracts 0.0.302

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (396) hide show
  1. package/LICENSE.txt +21 -0
  2. package/README.md +206 -0
  3. package/docs/permitAndStake_integration_guide.md +266 -0
  4. package/docs/swap_integration_guide.md +591 -0
  5. package/package.json +57 -0
  6. package/scripts/common/DeployBase.s.sol +26 -0
  7. package/scripts/common/DeployFacet.s.sol +7 -0
  8. package/scripts/common/Deployer.s.sol +33 -0
  9. package/scripts/common/Interaction.s.sol +51 -0
  10. package/scripts/deployments/diamonds/DeployAppRegistry.s.sol +168 -0
  11. package/scripts/deployments/diamonds/DeployBaseRegistry.s.sol +263 -0
  12. package/scripts/deployments/diamonds/DeployRiverAirdrop.s.sol +203 -0
  13. package/scripts/deployments/diamonds/DeployRiverMigration.s.sol +129 -0
  14. package/scripts/deployments/diamonds/DeployRiverRegistry.s.sol +175 -0
  15. package/scripts/deployments/diamonds/DeploySpace.s.sol +285 -0
  16. package/scripts/deployments/diamonds/DeploySpaceFactory.s.sol +416 -0
  17. package/scripts/deployments/diamonds/DeploySpaceOwner.s.sol +183 -0
  18. package/scripts/deployments/diamonds/DeploySwapRouter.s.sol +176 -0
  19. package/scripts/deployments/diamonds/IDiamondInitHelper.sol +11 -0
  20. package/scripts/deployments/facets/DeployAppAccount.s.sol +51 -0
  21. package/scripts/deployments/facets/DeployAppRegistryFacet.s.sol +69 -0
  22. package/scripts/deployments/facets/DeployArchitect.s.sol +51 -0
  23. package/scripts/deployments/facets/DeployAttestationRegistry.s.sol +36 -0
  24. package/scripts/deployments/facets/DeployBanning.s.sol +30 -0
  25. package/scripts/deployments/facets/DeployChannels.s.sol +35 -0
  26. package/scripts/deployments/facets/DeployCreateSpace.s.sol +42 -0
  27. package/scripts/deployments/facets/DeployDropFacet.s.sol +49 -0
  28. package/scripts/deployments/facets/DeployERC721A.s.sol +48 -0
  29. package/scripts/deployments/facets/DeployERC721ANonTransferable.s.sol +49 -0
  30. package/scripts/deployments/facets/DeployERC721AQueryable.s.sol +30 -0
  31. package/scripts/deployments/facets/DeployEntitlementChecker.s.sol +49 -0
  32. package/scripts/deployments/facets/DeployEntitlementDataQueryable.s.sol +29 -0
  33. package/scripts/deployments/facets/DeployEntitlementsManager.s.sol +33 -0
  34. package/scripts/deployments/facets/DeployExecutorFacet.s.sol +60 -0
  35. package/scripts/deployments/facets/DeployFeatureManager.s.sol +38 -0
  36. package/scripts/deployments/facets/DeployGuardianFacet.s.sol +39 -0
  37. package/scripts/deployments/facets/DeployImplementationRegistry.s.sol +36 -0
  38. package/scripts/deployments/facets/DeployMainnetDelegation.s.sol +43 -0
  39. package/scripts/deployments/facets/DeployMembership.s.sol +77 -0
  40. package/scripts/deployments/facets/DeployMembershipMetadata.s.sol +30 -0
  41. package/scripts/deployments/facets/DeployMembershipToken.s.sol +47 -0
  42. package/scripts/deployments/facets/DeployMerkleAirdrop.s.sol +37 -0
  43. package/scripts/deployments/facets/DeployMetadata.s.sol +39 -0
  44. package/scripts/deployments/facets/DeployMockLegacyArchitect.s.sol +33 -0
  45. package/scripts/deployments/facets/DeployNodeOperator.s.sol +49 -0
  46. package/scripts/deployments/facets/DeployNodeRegistry.s.sol +37 -0
  47. package/scripts/deployments/facets/DeployOperatorRegistry.s.sol +36 -0
  48. package/scripts/deployments/facets/DeployPartnerRegistry.s.sol +41 -0
  49. package/scripts/deployments/facets/DeployPlatformRequirements.s.sol +75 -0
  50. package/scripts/deployments/facets/DeployPrepayFacet.s.sol +31 -0
  51. package/scripts/deployments/facets/DeployPricingModules.s.sol +36 -0
  52. package/scripts/deployments/facets/DeployReferrals.s.sol +34 -0
  53. package/scripts/deployments/facets/DeployReviewFacet.s.sol +31 -0
  54. package/scripts/deployments/facets/DeployRewardsDistributionV2.s.sol +76 -0
  55. package/scripts/deployments/facets/DeployRiverConfig.s.sol +41 -0
  56. package/scripts/deployments/facets/DeployRoles.s.sol +48 -0
  57. package/scripts/deployments/facets/DeploySchemaRegistry.s.sol +35 -0
  58. package/scripts/deployments/facets/DeploySignerFacet.s.sol +47 -0
  59. package/scripts/deployments/facets/DeploySimpleApp.s.sol +10 -0
  60. package/scripts/deployments/facets/DeploySpaceDelegation.s.sol +43 -0
  61. package/scripts/deployments/facets/DeploySpaceEntitlementGated.s.sol +31 -0
  62. package/scripts/deployments/facets/DeploySpaceFactoryInit.s.sol +33 -0
  63. package/scripts/deployments/facets/DeploySpaceOwnerFacet.s.sol +71 -0
  64. package/scripts/deployments/facets/DeployStreamRegistry.s.sol +50 -0
  65. package/scripts/deployments/facets/DeploySwapFacet.s.sol +33 -0
  66. package/scripts/deployments/facets/DeploySwapRouterFacet.s.sol +38 -0
  67. package/scripts/deployments/facets/DeployTipping.s.sol +31 -0
  68. package/scripts/deployments/facets/DeployTokenMigration.s.sol +40 -0
  69. package/scripts/deployments/facets/DeployTownsPoints.s.sol +53 -0
  70. package/scripts/deployments/facets/DeployTreasury.s.sol +30 -0
  71. package/scripts/deployments/facets/DeployUpgradeableBeacon.s.sol +34 -0
  72. package/scripts/deployments/facets/DeployWalletLink.s.sol +56 -0
  73. package/scripts/deployments/facets/DeployXChain.s.sol +35 -0
  74. package/scripts/deployments/utils/DeployAccountFactory.s.sol +40 -0
  75. package/scripts/deployments/utils/DeployEntitlementGatedExample.s.sol +23 -0
  76. package/scripts/deployments/utils/DeployEntrypoint.s.sol +28 -0
  77. package/scripts/deployments/utils/DeployMember.s.sol +95 -0
  78. package/scripts/deployments/utils/DeployMockDiamond.s.sol +7 -0
  79. package/scripts/deployments/utils/DeployMockERC20.s.sol +24 -0
  80. package/scripts/deployments/utils/DeployMockERC721A.s.sol +45 -0
  81. package/scripts/deployments/utils/DeployMockLegacyMembership.s.sol +29 -0
  82. package/scripts/deployments/utils/DeployMockMessenger.s.sol +42 -0
  83. package/scripts/deployments/utils/DeployMockNFT.s.sol +86 -0
  84. package/scripts/deployments/utils/DeployPoapEntitlement.s.sol +16 -0
  85. package/scripts/deployments/utils/DeployProxyBatchDelegation.s.sol +112 -0
  86. package/scripts/deployments/utils/DeploySpaceProxyInitializer.s.sol +28 -0
  87. package/scripts/deployments/utils/DeployTieredLogPricingV2.s.sol +23 -0
  88. package/scripts/deployments/utils/DeployTieredLogPricingV3.s.sol +23 -0
  89. package/scripts/deployments/utils/DeployTownsBase.s.sol +95 -0
  90. package/scripts/deployments/utils/DeployTownsMainnet.s.sol +66 -0
  91. package/scripts/deployments/utils/DeployTownsMulti.s.sol +53 -0
  92. package/scripts/deployments/utils/DeployWrappedTowns.s.sol +52 -0
  93. package/scripts/deployments/utils/LibLayerZeroValues.sol +34 -0
  94. package/scripts/deployments/utils/pricing/TieredLogPricing.s.sol +45 -0
  95. package/scripts/interactions/InteractAirdrop.s.sol +57 -0
  96. package/scripts/interactions/InteractAlphaPost.s.sol +32 -0
  97. package/scripts/interactions/InteractAlphaSparse.s.sol +173 -0
  98. package/scripts/interactions/InteractBaseAlpha.s.sol +84 -0
  99. package/scripts/interactions/InteractBaseBridge.s.sol +48 -0
  100. package/scripts/interactions/InteractBridgeLayerZero.s.sol +102 -0
  101. package/scripts/interactions/InteractClaimCondition.s.sol +56 -0
  102. package/scripts/interactions/InteractCreateSpace.s.sol +50 -0
  103. package/scripts/interactions/InteractDiamondCut.s.sol +47 -0
  104. package/scripts/interactions/InteractDropFacet.s.sol +32 -0
  105. package/scripts/interactions/InteractEnableNewSnapshotFormat.s.sol +27 -0
  106. package/scripts/interactions/InteractEnableNode2NodeAuth.s.sol +27 -0
  107. package/scripts/interactions/InteractMembership.s.sol +42 -0
  108. package/scripts/interactions/InteractMockERC721A.s.sol +20 -0
  109. package/scripts/interactions/InteractNodeOperators.s.sol +41 -0
  110. package/scripts/interactions/InteractPostDeploy.s.sol +59 -0
  111. package/scripts/interactions/InteractPrepay.s.sol +30 -0
  112. package/scripts/interactions/InteractRegisterApp.s.sol +61 -0
  113. package/scripts/interactions/InteractRiverAlpha.s.sol +30 -0
  114. package/scripts/interactions/InteractRiverAlphaSparse.s.sol +117 -0
  115. package/scripts/interactions/InteractRiverMainnet.s.sol +27 -0
  116. package/scripts/interactions/InteractRiverRegistry.s.sol +36 -0
  117. package/scripts/interactions/InteractRiverRegistrySetBlocklist.s.sol +30 -0
  118. package/scripts/interactions/InteractRiverRegistrySetFreq.s.sol +27 -0
  119. package/scripts/interactions/InteractRiverRegistrySetRepl.s.sol +30 -0
  120. package/scripts/interactions/InteractSetDefaultUri.s.sol +20 -0
  121. package/scripts/interactions/InteractSetDefaultUriLocalhost.s.sol +19 -0
  122. package/scripts/interactions/InteractTransferOwnership.s.sol +21 -0
  123. package/scripts/interactions/InteractUpdateMbRecencyCheck.s.sol +27 -0
  124. package/scripts/interactions/InteractUpdateMediaChunkCount.s.sol +27 -0
  125. package/scripts/interactions/InteractUpdateMediaChunkSize.s.sol +27 -0
  126. package/scripts/interactions/helpers/AlphaHelper.sol +149 -0
  127. package/scripts/interactions/helpers/RiverConfigValues.sol +22 -0
  128. package/scripts/interactions/interfaces/IL1StandardBridge.sol +35 -0
  129. package/scripts/interactions/interfaces/IL2StandardBridge.sol +69 -0
  130. package/src/airdrop/drop/DropBase.sol +210 -0
  131. package/src/airdrop/drop/DropClaim.sol +55 -0
  132. package/src/airdrop/drop/DropFacet.sol +176 -0
  133. package/src/airdrop/drop/DropGroup.sol +111 -0
  134. package/src/airdrop/drop/DropStorage.sol +23 -0
  135. package/src/airdrop/drop/IDropFacet.sol +136 -0
  136. package/src/airdrop/points/CheckIn.sol +71 -0
  137. package/src/airdrop/points/ITownsPoints.sol +64 -0
  138. package/src/airdrop/points/TownsPoints.sol +196 -0
  139. package/src/airdrop/points/TownsPointsStorage.sol +22 -0
  140. package/src/apps/BaseApp.sol +62 -0
  141. package/src/apps/ITownsApp.sol +28 -0
  142. package/src/apps/SchemaResolver.sol +170 -0
  143. package/src/apps/facets/attest/AttestationBase.sol +335 -0
  144. package/src/apps/facets/attest/AttestationLib.sol +64 -0
  145. package/src/apps/facets/attest/AttestationRegistry.sol +39 -0
  146. package/src/apps/facets/attest/AttestationStorage.sol +35 -0
  147. package/src/apps/facets/attest/IAttestationRegistry.sol +43 -0
  148. package/src/apps/facets/registry/AppRegistryBase.sol +403 -0
  149. package/src/apps/facets/registry/AppRegistryFacet.sol +173 -0
  150. package/src/apps/facets/registry/AppRegistryStorage.sol +53 -0
  151. package/src/apps/facets/registry/IAppRegistry.sol +159 -0
  152. package/src/apps/facets/schema/ISchema.sol +14 -0
  153. package/src/apps/facets/schema/SchemaBase.sol +88 -0
  154. package/src/apps/facets/schema/SchemaLib.sol +14 -0
  155. package/src/apps/facets/schema/SchemaRegistry.sol +51 -0
  156. package/src/apps/facets/schema/SchemaStorage.sol +34 -0
  157. package/src/apps/helpers/ISimpleApp.sol +51 -0
  158. package/src/apps/helpers/SimpleApp.sol +97 -0
  159. package/src/apps/helpers/SimpleAppStorage.sol +27 -0
  160. package/src/base/registry/facets/checker/EntitlementChecker.sol +237 -0
  161. package/src/base/registry/facets/checker/EntitlementCheckerStorage.sol +28 -0
  162. package/src/base/registry/facets/checker/IEntitlementChecker.sol +95 -0
  163. package/src/base/registry/facets/delegation/ISpaceDelegation.sol +69 -0
  164. package/src/base/registry/facets/delegation/SpaceDelegationFacet.sol +250 -0
  165. package/src/base/registry/facets/delegation/SpaceDelegationStorage.sol +35 -0
  166. package/src/base/registry/facets/distribution/v1/IRewardsDistribution.sol +51 -0
  167. package/src/base/registry/facets/distribution/v1/RewardsDistribution.sol +439 -0
  168. package/src/base/registry/facets/distribution/v1/RewardsDistributionStorage.sol +32 -0
  169. package/src/base/registry/facets/distribution/v2/DelegationProxy.sol +53 -0
  170. package/src/base/registry/facets/distribution/v2/IRewardsDistribution.sol +372 -0
  171. package/src/base/registry/facets/distribution/v2/RewardsDistributionBase.sol +299 -0
  172. package/src/base/registry/facets/distribution/v2/RewardsDistributionStorage.sol +37 -0
  173. package/src/base/registry/facets/distribution/v2/RewardsDistributionV2.sol +392 -0
  174. package/src/base/registry/facets/distribution/v2/StakingRewards.sol +466 -0
  175. package/src/base/registry/facets/mainnet/ICrossDomainMessenger.sol +58 -0
  176. package/src/base/registry/facets/mainnet/IMainnetDelegation.sol +127 -0
  177. package/src/base/registry/facets/mainnet/MainnetDelegation.sol +119 -0
  178. package/src/base/registry/facets/mainnet/MainnetDelegationBase.sol +274 -0
  179. package/src/base/registry/facets/mainnet/MainnetDelegationStorage.sol +36 -0
  180. package/src/base/registry/facets/operator/INodeOperator.sol +91 -0
  181. package/src/base/registry/facets/operator/NodeOperatorFacet.sol +189 -0
  182. package/src/base/registry/facets/operator/NodeOperatorStorage.sol +39 -0
  183. package/src/base/registry/facets/xchain/IXChain.sol +54 -0
  184. package/src/base/registry/facets/xchain/XChain.sol +158 -0
  185. package/src/base/registry/facets/xchain/XChainCheckLib.sol +105 -0
  186. package/src/base/registry/facets/xchain/XChainLib.sol +46 -0
  187. package/src/diamond/facets/beacon/UpgradeableBeacon.sol +38 -0
  188. package/src/diamond/facets/beacon/UpgradeableBeaconFacet.sol +34 -0
  189. package/src/diamond/facets/governance/votes/Checkpoints.sol +642 -0
  190. package/src/diamond/facets/governance/votes/Votes.sol +63 -0
  191. package/src/diamond/facets/governance/votes/VotesBase.sol +274 -0
  192. package/src/diamond/facets/governance/votes/VotesStorage.sol +21 -0
  193. package/src/diamond/facets/governance/votes/enumerable/IVotesEnumerable.sol +38 -0
  194. package/src/diamond/facets/governance/votes/enumerable/VotesEnumerable.sol +39 -0
  195. package/src/diamond/facets/governance/votes/enumerable/VotesEnumerableLib.sol +102 -0
  196. package/src/diamond/facets/metadata/IMetadata.sol +27 -0
  197. package/src/diamond/facets/metadata/MetadataFacet.sol +71 -0
  198. package/src/diamond/facets/token/ERC5643/ERC5643.sol +51 -0
  199. package/src/diamond/facets/token/ERC5643/ERC5643Base.sol +48 -0
  200. package/src/diamond/facets/token/ERC5643/ERC5643Storage.sol +26 -0
  201. package/src/diamond/facets/token/ERC5643/IERC5643.sol +44 -0
  202. package/src/diamond/facets/token/ERC721A/ERC721A.sol +270 -0
  203. package/src/diamond/facets/token/ERC721A/ERC721ABase.sol +829 -0
  204. package/src/diamond/facets/token/ERC721A/ERC721ANonTransferable.sol +21 -0
  205. package/src/diamond/facets/token/ERC721A/ERC721AStorage.sol +115 -0
  206. package/src/diamond/facets/token/ERC721A/IERC721A.sol +283 -0
  207. package/src/diamond/facets/token/ERC721A/extensions/ERC721AQueryable.sol +134 -0
  208. package/src/diamond/facets/token/ERC721A/extensions/IERC721AQueryable.sol +83 -0
  209. package/src/diamond/utils/Context.sol +19 -0
  210. package/src/factory/SpaceFactoryInit.sol +17 -0
  211. package/src/factory/facets/architect/Architect.sol +98 -0
  212. package/src/factory/facets/architect/ArchitectBase.sol +95 -0
  213. package/src/factory/facets/architect/ArchitectStorage.sol +28 -0
  214. package/src/factory/facets/architect/IArchitect.sol +155 -0
  215. package/src/factory/facets/architect/ImplementationStorage.sol +42 -0
  216. package/src/factory/facets/architect/pricing/IPricingModules.sol +41 -0
  217. package/src/factory/facets/architect/pricing/PricingModulesBase.sol +89 -0
  218. package/src/factory/facets/architect/pricing/PricingModulesFacet.sol +40 -0
  219. package/src/factory/facets/architect/pricing/PricingModulesStorage.sol +30 -0
  220. package/src/factory/facets/create/CreateSpace.sol +107 -0
  221. package/src/factory/facets/create/CreateSpaceLib.sol +335 -0
  222. package/src/factory/facets/create/ICreateSpace.sol +70 -0
  223. package/src/factory/facets/feature/FeatureConditionLib.sol +53 -0
  224. package/src/factory/facets/feature/FeatureManagerFacet.sol +66 -0
  225. package/src/factory/facets/feature/FeatureManagerLib.sol +168 -0
  226. package/src/factory/facets/feature/IFeatureManagerFacet.sol +73 -0
  227. package/src/factory/facets/partner/IPartnerRegistry.sol +56 -0
  228. package/src/factory/facets/partner/PartnerRegistry.sol +57 -0
  229. package/src/factory/facets/partner/PartnerRegistryBase.sol +132 -0
  230. package/src/factory/facets/partner/PartnerRegistryStorage.sol +40 -0
  231. package/src/factory/facets/platform/requirements/IPlatformRequirements.sol +143 -0
  232. package/src/factory/facets/platform/requirements/PlatformRequirementsBase.sol +124 -0
  233. package/src/factory/facets/platform/requirements/PlatformRequirementsFacet.sol +122 -0
  234. package/src/factory/facets/platform/requirements/PlatformRequirementsStorage.sol +41 -0
  235. package/src/factory/facets/registry/IImplementationRegistry.sol +46 -0
  236. package/src/factory/facets/registry/ImplementationRegistry.sol +64 -0
  237. package/src/factory/facets/registry/ImplementationRegistryStorage.sol +28 -0
  238. package/src/factory/facets/wallet-link/IWalletLink.sol +218 -0
  239. package/src/factory/facets/wallet-link/WalletLink.sol +108 -0
  240. package/src/factory/facets/wallet-link/WalletLinkBase.sol +492 -0
  241. package/src/factory/facets/wallet-link/interfaces/IDelegateRegistry.sol +63 -0
  242. package/src/factory/facets/wallet-link/interfaces/IDelegateRegistryV1.sol +35 -0
  243. package/src/factory/facets/wallet-link/interfaces/ISCL_EIP6565.sol +24 -0
  244. package/src/factory/facets/wallet-link/libraries/SolanaUtils.sol +161 -0
  245. package/src/factory/facets/wallet-link/libraries/WalletLib.sol +62 -0
  246. package/src/river/registry/facets/config/IRiverConfig.sol +117 -0
  247. package/src/river/registry/facets/config/RiverConfig.sol +174 -0
  248. package/src/river/registry/facets/node/INodeRegistry.sol +69 -0
  249. package/src/river/registry/facets/node/NodeRegistry.sol +143 -0
  250. package/src/river/registry/facets/operator/IOperatorRegistry.sol +28 -0
  251. package/src/river/registry/facets/operator/OperatorRegistry.sol +86 -0
  252. package/src/river/registry/facets/stream/IStreamRegistry.sol +184 -0
  253. package/src/river/registry/facets/stream/StreamRegistry.sol +396 -0
  254. package/src/river/registry/libraries/RegistryErrors.sol +24 -0
  255. package/src/river/registry/libraries/RegistryStorage.sol +181 -0
  256. package/src/router/ISwapRouter.sol +226 -0
  257. package/src/router/Permit2Hash.sol +92 -0
  258. package/src/router/SwapRouter.sol +463 -0
  259. package/src/router/SwapRouterStorage.sol +21 -0
  260. package/src/spaces/entitlements/ICrossChainEntitlement.sol +22 -0
  261. package/src/spaces/entitlements/IEntitlement.sol +61 -0
  262. package/src/spaces/entitlements/PolymarketEntitlement.sol +79 -0
  263. package/src/spaces/entitlements/poap/IPOAP.sol +26 -0
  264. package/src/spaces/entitlements/poap/PoapEntitlement.sol +56 -0
  265. package/src/spaces/entitlements/rule/IRuleEntitlement.sol +174 -0
  266. package/src/spaces/entitlements/rule/RuleEntitlement.sol +183 -0
  267. package/src/spaces/entitlements/rule/RuleEntitlementV2.sol +219 -0
  268. package/src/spaces/entitlements/user/IUserEntitlement.sol +24 -0
  269. package/src/spaces/entitlements/user/UserEntitlement.sol +273 -0
  270. package/src/spaces/facets/DependencyLib.sol +60 -0
  271. package/src/spaces/facets/Entitled.sol +172 -0
  272. package/src/spaces/facets/Permissions.sol +21 -0
  273. package/src/spaces/facets/account/AppAccount.sol +93 -0
  274. package/src/spaces/facets/account/AppAccountBase.sol +275 -0
  275. package/src/spaces/facets/account/AppAccountStorage.sol +63 -0
  276. package/src/spaces/facets/account/IAppAccount.sol +71 -0
  277. package/src/spaces/facets/account/SignerFacet.sol +26 -0
  278. package/src/spaces/facets/banning/Banning.sol +41 -0
  279. package/src/spaces/facets/banning/BanningBase.sol +33 -0
  280. package/src/spaces/facets/banning/BanningStorage.sol +23 -0
  281. package/src/spaces/facets/banning/IBanning.sol +35 -0
  282. package/src/spaces/facets/channels/ChannelBase.sol +87 -0
  283. package/src/spaces/facets/channels/ChannelService.sol +177 -0
  284. package/src/spaces/facets/channels/ChannelStorage.sol +34 -0
  285. package/src/spaces/facets/channels/Channels.sol +80 -0
  286. package/src/spaces/facets/channels/IChannel.sol +98 -0
  287. package/src/spaces/facets/dispatcher/DispatcherBase.sol +86 -0
  288. package/src/spaces/facets/dispatcher/DispatcherStorage.sol +21 -0
  289. package/src/spaces/facets/dispatcher/IDispatcher.sol +6 -0
  290. package/src/spaces/facets/entitlements/EntitlementsManager.sol +49 -0
  291. package/src/spaces/facets/entitlements/EntitlementsManagerBase.sol +87 -0
  292. package/src/spaces/facets/entitlements/EntitlementsManagerService.sol +142 -0
  293. package/src/spaces/facets/entitlements/EntitlementsManagerStorage.sol +34 -0
  294. package/src/spaces/facets/entitlements/IEntitlementsManager.sol +67 -0
  295. package/src/spaces/facets/entitlements/extensions/EntitlementDataQueryable.sol +153 -0
  296. package/src/spaces/facets/entitlements/extensions/IEntitlementDataQueryable.sol +32 -0
  297. package/src/spaces/facets/executor/ExecutorBase.sol +564 -0
  298. package/src/spaces/facets/executor/ExecutorFacet.sol +178 -0
  299. package/src/spaces/facets/executor/ExecutorStorage.sol +99 -0
  300. package/src/spaces/facets/executor/GroupLib.sol +128 -0
  301. package/src/spaces/facets/executor/IExecutor.sol +287 -0
  302. package/src/spaces/facets/executor/hooks/HookBase.sol +172 -0
  303. package/src/spaces/facets/executor/hooks/HookLib.sol +38 -0
  304. package/src/spaces/facets/executor/hooks/IHookBase.sol +48 -0
  305. package/src/spaces/facets/gated/EntitlementGated.sol +59 -0
  306. package/src/spaces/facets/gated/EntitlementGatedBase.sol +324 -0
  307. package/src/spaces/facets/gated/EntitlementGatedStorage.sol +29 -0
  308. package/src/spaces/facets/gated/IEntitlementGated.sol +55 -0
  309. package/src/spaces/facets/guardian/GuardianBase.sol +80 -0
  310. package/src/spaces/facets/guardian/GuardianFacet.sol +43 -0
  311. package/src/spaces/facets/guardian/GuardianStorage.sol +27 -0
  312. package/src/spaces/facets/guardian/IGuardian.sol +54 -0
  313. package/src/spaces/facets/membership/IMembership.sol +216 -0
  314. package/src/spaces/facets/membership/MembershipBase.sol +272 -0
  315. package/src/spaces/facets/membership/MembershipFacet.sol +191 -0
  316. package/src/spaces/facets/membership/MembershipStorage.sol +40 -0
  317. package/src/spaces/facets/membership/join/MembershipJoin.sol +547 -0
  318. package/src/spaces/facets/membership/metadata/IMembershipMetadata.sol +9 -0
  319. package/src/spaces/facets/membership/metadata/MembershipMetadata.sol +32 -0
  320. package/src/spaces/facets/membership/pricing/IMembershipPricing.sol +18 -0
  321. package/src/spaces/facets/membership/pricing/fixed/FixedPricing.sol +29 -0
  322. package/src/spaces/facets/membership/pricing/fixed/FixedPricingStorage.sol +27 -0
  323. package/src/spaces/facets/membership/pricing/tiered/TieredLogPricingOracleV2.sol +148 -0
  324. package/src/spaces/facets/membership/pricing/tiered/TieredLogPricingOracleV3.sol +137 -0
  325. package/src/spaces/facets/membership/token/MembershipToken.sol +25 -0
  326. package/src/spaces/facets/owner/ISpaceOwner.sol +85 -0
  327. package/src/spaces/facets/owner/SpaceOwner.sol +174 -0
  328. package/src/spaces/facets/owner/SpaceOwnerBase.sol +121 -0
  329. package/src/spaces/facets/owner/SpaceOwnerStorage.sol +41 -0
  330. package/src/spaces/facets/owner/SpaceOwnerUriBase.sol +54 -0
  331. package/src/spaces/facets/points/PointsBase.sol +35 -0
  332. package/src/spaces/facets/prepay/IPrepay.sol +43 -0
  333. package/src/spaces/facets/prepay/PrepayBase.sol +27 -0
  334. package/src/spaces/facets/prepay/PrepayFacet.sol +59 -0
  335. package/src/spaces/facets/prepay/PrepayStorage.sol +26 -0
  336. package/src/spaces/facets/proxy/ISpaceProxyInitializer.sol +21 -0
  337. package/src/spaces/facets/proxy/SpaceProxy.sol +15 -0
  338. package/src/spaces/facets/proxy/SpaceProxyInitializer.sol +55 -0
  339. package/src/spaces/facets/referrals/IReferrals.sol +98 -0
  340. package/src/spaces/facets/referrals/ReferralsBase.sol +81 -0
  341. package/src/spaces/facets/referrals/ReferralsFacet.sol +65 -0
  342. package/src/spaces/facets/referrals/ReferralsStorage.sol +36 -0
  343. package/src/spaces/facets/review/IReview.sol +50 -0
  344. package/src/spaces/facets/review/ReviewFacet.sol +105 -0
  345. package/src/spaces/facets/review/ReviewStorage.sol +29 -0
  346. package/src/spaces/facets/roles/IRoles.sol +197 -0
  347. package/src/spaces/facets/roles/Roles.sol +123 -0
  348. package/src/spaces/facets/roles/RolesBase.sol +420 -0
  349. package/src/spaces/facets/roles/RolesStorage.sol +132 -0
  350. package/src/spaces/facets/swap/ISwapFacet.sol +91 -0
  351. package/src/spaces/facets/swap/SwapFacet.sol +290 -0
  352. package/src/spaces/facets/swap/SwapFacetStorage.sol +24 -0
  353. package/src/spaces/facets/tipping/ITipping.sol +80 -0
  354. package/src/spaces/facets/tipping/TippingBase.sol +73 -0
  355. package/src/spaces/facets/tipping/TippingFacet.sol +123 -0
  356. package/src/spaces/facets/treasury/ITreasury.sol +64 -0
  357. package/src/spaces/facets/treasury/Treasury.sol +82 -0
  358. package/src/spaces/facets/xchain/SpaceEntitlementGated.sol +62 -0
  359. package/src/tokens/Member.sol +246 -0
  360. package/src/tokens/lock/ILock.sol +42 -0
  361. package/src/tokens/lock/LockBase.sol +64 -0
  362. package/src/tokens/lock/LockFacet.sol +44 -0
  363. package/src/tokens/lock/LockStorage.sol +26 -0
  364. package/src/tokens/mainnet/claimer/AuthorizedClaimerStorage.sol +26 -0
  365. package/src/tokens/mainnet/claimer/AuthorizedClaimers.sol +84 -0
  366. package/src/tokens/mainnet/claimer/IAuthorizedClaimers.sol +36 -0
  367. package/src/tokens/mainnet/delegation/ProxyBatchDelegation.sol +86 -0
  368. package/src/tokens/migration/ITokenMigration.sol +35 -0
  369. package/src/tokens/migration/TokenMigrationFacet.sol +86 -0
  370. package/src/tokens/migration/TokenMigrationStorage.sol +27 -0
  371. package/src/tokens/towns/base/IERC7802.sol +30 -0
  372. package/src/tokens/towns/base/IOptimismMintableERC20.sol +31 -0
  373. package/src/tokens/towns/base/ISemver.sol +13 -0
  374. package/src/tokens/towns/base/Towns.sol +283 -0
  375. package/src/tokens/towns/base/TownsDeployer.sol +32 -0
  376. package/src/tokens/towns/base/TownsLib.sol +31 -0
  377. package/src/tokens/towns/base/versions/TownsV2.sol +15 -0
  378. package/src/tokens/towns/mainnet/ITowns.sol +56 -0
  379. package/src/tokens/towns/mainnet/Towns.sol +220 -0
  380. package/src/tokens/towns/mainnet/libs/TokenInflationLib.sol +89 -0
  381. package/src/tokens/towns/multichain/Towns.sol +19 -0
  382. package/src/tokens/towns/multichain/wTowns.sol +18 -0
  383. package/src/utils/Airdrop.sol +156 -0
  384. package/src/utils/airdrop/merkle/IMerkleAirdrop.sol +55 -0
  385. package/src/utils/airdrop/merkle/MerkleAirdrop.sol +118 -0
  386. package/src/utils/airdrop/merkle/MerkleAirdropStorage.sol +29 -0
  387. package/src/utils/interfaces/AggregatorV3Interface.sol +37 -0
  388. package/src/utils/interfaces/IMulticall.sol +10 -0
  389. package/src/utils/interfaces/IWETH.sol +10 -0
  390. package/src/utils/libraries/BasisPoints.sol +24 -0
  391. package/src/utils/libraries/Create2Utils.sol +74 -0
  392. package/src/utils/libraries/CurrencyTransfer.sol +99 -0
  393. package/src/utils/libraries/CustomRevert.sol +49 -0
  394. package/src/utils/libraries/Factory.sol +66 -0
  395. package/src/utils/libraries/StringSet.sol +190 -0
  396. package/src/utils/libraries/Validator.sol +31 -0
@@ -0,0 +1,136 @@
1
+ // SPDX-License-Identifier: MIT
2
+ pragma solidity ^0.8.23;
3
+
4
+ // interfaces
5
+ import {DropClaim} from "./DropClaim.sol";
6
+ import {DropGroup} from "./DropGroup.sol";
7
+
8
+ // libraries
9
+
10
+ // contracts
11
+
12
+ interface IDropFacetBase {
13
+ // =============================================================
14
+ // Events
15
+ // =============================================================
16
+ event DropFacet_Claimed_WithPenalty(
17
+ uint256 indexed conditionId,
18
+ address indexed claimer,
19
+ address indexed account,
20
+ uint256 amount
21
+ );
22
+
23
+ event DropFacet_Claimed_And_Staked(
24
+ uint256 indexed conditionId,
25
+ address indexed claimer,
26
+ address indexed account,
27
+ uint256 amount
28
+ );
29
+
30
+ event DropFacet_ClaimConditionsUpdated(
31
+ uint256 indexed conditionId,
32
+ DropGroup.ClaimCondition[] conditions
33
+ );
34
+
35
+ event DropFacet_ClaimConditionAdded(
36
+ uint256 indexed conditionId,
37
+ DropGroup.ClaimCondition condition
38
+ );
39
+
40
+ // =============================================================
41
+ // Errors
42
+ // =============================================================
43
+ error DropFacet__NoActiveClaimCondition();
44
+ error DropFacet__MerkleRootNotSet();
45
+ error DropFacet__QuantityMustBeGreaterThanZero();
46
+ error DropFacet__ExceedsMaxClaimableSupply();
47
+ error DropFacet__ClaimHasNotStarted();
48
+ error DropFacet__AlreadyClaimed();
49
+ error DropFacet__InvalidProof();
50
+ error DropFacet__ClaimConditionsNotInAscendingOrder();
51
+ error DropFacet__CannotSetClaimConditions();
52
+ error DropFacet__ClaimHasEnded();
53
+ error DropFacet__UnexpectedPenaltyBps();
54
+ error DropFacet__CurrencyNotSet();
55
+ error DropFacet__RewardsDistributionNotSet();
56
+ error DropFacet__InsufficientBalance();
57
+ error DropFacet__NotClaimingAccount();
58
+ error DropFacet__InvalidRecipient();
59
+ }
60
+
61
+ interface IDropFacet is IDropFacetBase {
62
+ /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
63
+ /* ADMIN FUNCTIONS */
64
+ /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/
65
+
66
+ /// @notice Adds a new claim condition
67
+ /// @param condition The ClaimCondition struct defining the condition
68
+ function addClaimCondition(DropGroup.ClaimCondition calldata condition) external;
69
+
70
+ /// @notice Sets the claim conditions for the drop
71
+ /// @param conditions An array of ClaimCondition structs defining the conditions
72
+ function setClaimConditions(DropGroup.ClaimCondition[] calldata conditions) external;
73
+
74
+ /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
75
+ /* CLAIMING */
76
+ /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/
77
+
78
+ /// @notice Claims tokens with a penalty
79
+ /// @param req The claim request
80
+ /// @param expectedPenaltyBps The expected penalty in basis points
81
+ /// @return The amount of tokens claimed
82
+ function claimWithPenalty(
83
+ DropClaim.Claim calldata req,
84
+ uint16 expectedPenaltyBps
85
+ ) external returns (uint256);
86
+
87
+ /// @notice Claims tokens and stakes them in the staking contract
88
+ /// @param req The claim request
89
+ /// @param delegatee The address of the delegatee
90
+ /// @param deadline The deadline for the transaction
91
+ /// @param signature The signature of the delegatee
92
+ /// @return The amount of tokens claimed
93
+ function claimAndStake(
94
+ DropClaim.Claim calldata req,
95
+ address delegatee,
96
+ uint256 deadline,
97
+ bytes calldata signature
98
+ ) external returns (uint256);
99
+
100
+ /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
101
+ /* GETTERS */
102
+ /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/
103
+
104
+ /// @notice Gets the ID of the currently active claim condition
105
+ /// @return The ID of the active claim condition
106
+ function getActiveClaimConditionId() external view returns (uint256);
107
+
108
+ /// @notice Gets all claim conditions
109
+ /// @return An array of ClaimCondition structs
110
+ function getClaimConditions() external view returns (DropGroup.ClaimCondition[] memory);
111
+
112
+ /// @notice Retrieves a specific claim condition by its ID
113
+ /// @param conditionId The ID of the claim condition to retrieve
114
+ /// @return The ClaimCondition struct for the specified ID
115
+ function getClaimConditionById(
116
+ uint256 conditionId
117
+ ) external view returns (DropGroup.ClaimCondition memory);
118
+
119
+ /// @notice Gets the amount of tokens claimed by a specific wallet for a given condition
120
+ /// @param account The address of the wallet to check
121
+ /// @param conditionId The ID of the claim condition
122
+ /// @return The number of tokens claimed by the wallet for the specified condition
123
+ function getSupplyClaimedByWallet(
124
+ address account,
125
+ uint256 conditionId
126
+ ) external view returns (uint256);
127
+
128
+ /// @notice Gets the deposit ID of a specific wallet for a given condition
129
+ /// @param account The address of the wallet to check
130
+ /// @param conditionId The ID of the claim condition
131
+ /// @return The deposit ID of the wallet for the specified condition
132
+ function getDepositIdByWallet(
133
+ address account,
134
+ uint256 conditionId
135
+ ) external view returns (uint256);
136
+ }
@@ -0,0 +1,71 @@
1
+ // SPDX-License-Identifier: MIT
2
+ pragma solidity ^0.8.24;
3
+
4
+ // interfaces
5
+
6
+ // libraries
7
+
8
+ // contracts
9
+
10
+ library CheckIn {
11
+ // keccak256(abi.encode(uint256(keccak256("river.tokens.checkin.storage")) - 1)) &
12
+ // ~bytes32(uint256(0xff))
13
+ bytes32 internal constant STORAGE_SLOT =
14
+ 0x62755009e737dbac2f30b2876987ec999edfaa30486a87d0930a58dbf1ec6800;
15
+
16
+ uint256 internal constant MAX_STREAK_PER_CHECKIN = 30; // Maximum streak per check-in
17
+ uint256 internal constant MAX_POINTS_PER_CHECKIN = 30 ether; // Maximum points per check-in
18
+ uint256 internal constant CHECK_IN_FORGIVENESS_PERIOD = 2 days; // Time window to continue
19
+ // streak
20
+ uint256 internal constant CHECK_IN_WAIT_PERIOD = 1 days; // Time between check-ins
21
+
22
+ struct CheckInData {
23
+ uint256 streak;
24
+ uint256 lastCheckIn;
25
+ }
26
+
27
+ struct Layout {
28
+ mapping(address => CheckInData) checkInsByAddress;
29
+ }
30
+
31
+ function layout() internal pure returns (Layout storage l) {
32
+ assembly {
33
+ l.slot := STORAGE_SLOT
34
+ }
35
+ }
36
+
37
+ function getPointsAndStreak(
38
+ uint256 lastCheckIn,
39
+ uint256 currentStreak,
40
+ uint256 currentTime
41
+ ) internal pure returns (uint256 pointsToAward, uint256 streak) {
42
+ // First time checking in
43
+ if (lastCheckIn == 0) {
44
+ return (1 ether, 1); // equivalent to 1 point
45
+ }
46
+
47
+ // Must wait at least 24 hours between check-ins
48
+ if (currentTime <= lastCheckIn + CHECK_IN_WAIT_PERIOD) {
49
+ return (0, 0);
50
+ }
51
+
52
+ // Update streak based on timing
53
+ bool isWithinForgiveness = currentTime <= lastCheckIn + CHECK_IN_FORGIVENESS_PERIOD;
54
+ uint256 newStreak = isWithinForgiveness ? currentStreak + 1 : 1;
55
+
56
+ // Calculate points based on new streak
57
+ pointsToAward = newStreak > MAX_STREAK_PER_CHECKIN
58
+ ? MAX_POINTS_PER_CHECKIN
59
+ : newStreak * 1 ether;
60
+
61
+ return (pointsToAward, newStreak);
62
+ }
63
+
64
+ function getCurrentStreak(address user) internal view returns (uint256) {
65
+ return layout().checkInsByAddress[user].streak;
66
+ }
67
+
68
+ function getLastCheckIn(address user) internal view returns (uint256) {
69
+ return layout().checkInsByAddress[user].lastCheckIn;
70
+ }
71
+ }
@@ -0,0 +1,64 @@
1
+ // SPDX-License-Identifier: MIT
2
+ pragma solidity ^0.8.23;
3
+
4
+ interface ITownsPointsBase {
5
+ enum Action {
6
+ JoinSpace,
7
+ CheckIn,
8
+ Tip,
9
+ Swap
10
+ }
11
+
12
+ /// @notice Emitted when a user successfully checks in and receives points
13
+ /// @param user The address of the user who checked in
14
+ /// @param points The number of points awarded for this check-in
15
+ /// @param streak The user's current check-in streak after this check-in
16
+ /// @param lastCheckIn The timestamp when this check-in occurred
17
+ event CheckedIn(address indexed user, uint256 points, uint256 streak, uint256 lastCheckIn);
18
+
19
+ /// @notice Error thrown when the space is invalid
20
+ error TownsPoints__InvalidSpace();
21
+
22
+ /// @notice Error thrown when the call data is invalid
23
+ error TownsPoints__InvalidCallData();
24
+
25
+ /// @notice Error thrown when the array length is invalid
26
+ error TownsPoints__InvalidArrayLength();
27
+
28
+ /// @notice Error thrown when a user attempts to check in too soon after their last check-in
29
+ error TownsPoints__CheckInPeriodNotPassed();
30
+ }
31
+
32
+ interface ITownsPoints is ITownsPointsBase {
33
+ /// @notice Batch mint points to multiple users
34
+ /// @dev Only callable by the owner
35
+ /// @param data The abi-encoded array of addresses and values to mint
36
+ function batchMintPoints(bytes calldata data) external;
37
+
38
+ /// @notice Mint points to a user
39
+ /// @dev Only spaces can mint points
40
+ /// @param to The address to mint the points to
41
+ /// @param value The amount of points to mint
42
+ function mint(address to, uint256 value) external;
43
+
44
+ /// @notice Get the points from an eligible action
45
+ /// @param action The action to get the points from
46
+ /// @param data The data of the action
47
+ function getPoints(Action action, bytes calldata data) external view returns (uint256);
48
+
49
+ /// @notice Allows a user to check in and earn points based on their streak
50
+ /// @dev Users must wait at least 24 hours between check-ins
51
+ /// @dev If a user checks in within 48 hours of their last check-in, their streak continues
52
+ /// @dev Otherwise, their streak resets to 1
53
+ function checkIn() external;
54
+
55
+ /// @notice Gets the current check-in streak for a user
56
+ /// @param user The address of the user to query
57
+ /// @return The current streak count for the user
58
+ function getCurrentStreak(address user) external view returns (uint256);
59
+
60
+ /// @notice Gets the timestamp of the user's last check-in
61
+ /// @param user The address of the user to query
62
+ /// @return The timestamp of the user's last check-in, 0 if never checked in
63
+ function getLastCheckIn(address user) external view returns (uint256);
64
+ }
@@ -0,0 +1,196 @@
1
+ // SPDX-License-Identifier: MIT
2
+ pragma solidity ^0.8.23;
3
+
4
+ // interfaces
5
+
6
+ import {ITownsPoints} from "./ITownsPoints.sol";
7
+ import {IERC20} from "@openzeppelin/contracts/token/ERC20/IERC20.sol";
8
+ import {IERC20Metadata} from "@openzeppelin/contracts/token/ERC20/extensions/IERC20Metadata.sol";
9
+ import {IArchitect} from "src/factory/facets/architect/IArchitect.sol";
10
+
11
+ // libraries
12
+
13
+ import {CheckIn} from "./CheckIn.sol";
14
+ import {TownsPointsStorage} from "./TownsPointsStorage.sol";
15
+ import {CustomRevert} from "src/utils/libraries/CustomRevert.sol";
16
+
17
+ // contracts
18
+ import {Facet} from "@towns-protocol/diamond/src/facets/Facet.sol";
19
+ import {OwnableBase} from "@towns-protocol/diamond/src/facets/ownable/OwnableBase.sol";
20
+
21
+ contract TownsPoints is IERC20Metadata, ITownsPoints, OwnableBase, Facet {
22
+ function __TownsPoints_init(address spaceFactory) external onlyInitializing {
23
+ TownsPointsStorage.Layout storage ds = TownsPointsStorage.layout();
24
+ ds.spaceFactory = spaceFactory;
25
+ _addInterface(type(IERC20).interfaceId);
26
+ _addInterface(type(IERC20Metadata).interfaceId);
27
+ }
28
+
29
+ /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
30
+ /* POINTS */
31
+ /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/
32
+
33
+ modifier onlySpace() {
34
+ address spaceFactory = TownsPointsStorage.layout().spaceFactory;
35
+ if (IArchitect(spaceFactory).getTokenIdBySpace(msg.sender) == 0) {
36
+ CustomRevert.revertWith(TownsPoints__InvalidSpace.selector);
37
+ }
38
+ _;
39
+ }
40
+
41
+ /// @inheritdoc ITownsPoints
42
+ function batchMintPoints(bytes calldata data) external onlyOwner {
43
+ address[] calldata accounts;
44
+ uint256[] calldata values;
45
+ uint256 relativeOffset;
46
+ assembly {
47
+ // call data layout:
48
+ // address | value
49
+ // data.offset | 0x40 (accounts relative offset)
50
+ // + 0x20 | values relative offset
51
+ // + 0x40 | accounts.length
52
+ // + 0x60 (accounts.offset) | accounts[0]
53
+ let accountsLengthPtr := add(data.offset, calldataload(data.offset))
54
+ accounts.length := calldataload(accountsLengthPtr)
55
+ accounts.offset := add(accountsLengthPtr, 0x20)
56
+ let valuesLengthPtr := add(data.offset, calldataload(add(data.offset, 0x20)))
57
+ values.length := calldataload(valuesLengthPtr)
58
+ values.offset := add(valuesLengthPtr, 0x20)
59
+ relativeOffset := sub(values.offset, data.offset)
60
+ }
61
+ if (data.length < relativeOffset + (values.length << 5)) {
62
+ CustomRevert.revertWith(TownsPoints__InvalidCallData.selector);
63
+ }
64
+
65
+ if (accounts.length != values.length) {
66
+ CustomRevert.revertWith(TownsPoints__InvalidArrayLength.selector);
67
+ }
68
+
69
+ TownsPointsStorage.Layout storage self = TownsPointsStorage.layout();
70
+ for (uint256 i; i < accounts.length; ++i) {
71
+ self.inner.mint(accounts[i], values[i]);
72
+ emit Transfer(address(0), accounts[i], values[i]);
73
+ }
74
+ }
75
+
76
+ /// @inheritdoc ITownsPoints
77
+ function getPoints(Action action, bytes calldata data) external pure returns (uint256 points) {
78
+ if (action == Action.JoinSpace) {
79
+ uint256 membershipPrice = abi.decode(data, (uint256));
80
+ points = membershipPrice * 200_000;
81
+ }
82
+
83
+ if (action == Action.CheckIn) {
84
+ (uint256 lastCheckIn, uint256 streak, uint256 currentTime) = abi.decode(
85
+ data,
86
+ (uint256, uint256, uint256)
87
+ );
88
+ (points, ) = CheckIn.getPointsAndStreak(lastCheckIn, streak, currentTime);
89
+ }
90
+
91
+ if (action == Action.Tip || action == Action.Swap) {
92
+ uint256 protocolFee = abi.decode(data, (uint256));
93
+ points = (protocolFee * 2_000_000) / 3;
94
+ }
95
+ }
96
+
97
+ /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
98
+ /* CHECKIN */
99
+ /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/
100
+
101
+ /// @inheritdoc ITownsPoints
102
+ function checkIn() external {
103
+ CheckIn.CheckInData storage userCheckIn = CheckIn.layout().checkInsByAddress[msg.sender];
104
+
105
+ (uint256 pointsToAward, uint256 newStreak) = CheckIn.getPointsAndStreak(
106
+ userCheckIn.lastCheckIn,
107
+ userCheckIn.streak,
108
+ block.timestamp
109
+ );
110
+
111
+ // Must wait at least 24 hours between check-ins
112
+ if (pointsToAward == 0 && newStreak == 0) {
113
+ CustomRevert.revertWith(TownsPoints__CheckInPeriodNotPassed.selector);
114
+ }
115
+
116
+ (userCheckIn.streak, userCheckIn.lastCheckIn) = (newStreak, block.timestamp);
117
+ TownsPointsStorage.layout().inner.mint(msg.sender, pointsToAward);
118
+ emit Transfer(address(0), msg.sender, pointsToAward);
119
+ emit CheckedIn(msg.sender, pointsToAward, newStreak, block.timestamp);
120
+ }
121
+
122
+ /// @inheritdoc ITownsPoints
123
+ function getCurrentStreak(address user) external view returns (uint256) {
124
+ return CheckIn.getCurrentStreak(user);
125
+ }
126
+
127
+ /// @inheritdoc ITownsPoints
128
+ function getLastCheckIn(address user) external view returns (uint256) {
129
+ return CheckIn.getLastCheckIn(user);
130
+ }
131
+
132
+ /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
133
+ /* ERC20 */
134
+ /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/
135
+
136
+ /// @inheritdoc IERC20
137
+ function approve(address spender, uint256 value) external returns (bool) {
138
+ TownsPointsStorage.layout().inner.approve(spender, value);
139
+ emit Approval(msg.sender, spender, value);
140
+ return true;
141
+ }
142
+
143
+ /// @inheritdoc ITownsPoints
144
+ function mint(address to, uint256 value) external onlySpace {
145
+ TownsPointsStorage.layout().inner.mint(to, value);
146
+ emit Transfer(address(0), to, value);
147
+ }
148
+
149
+ /// @inheritdoc IERC20
150
+ function transfer(address to, uint256 value) external returns (bool) {
151
+ TownsPointsStorage.layout().inner.transfer(to, value);
152
+ emit Transfer(msg.sender, to, value);
153
+ return true;
154
+ }
155
+
156
+ /// @inheritdoc IERC20
157
+ function transferFrom(address from, address to, uint256 value) external returns (bool) {
158
+ TownsPointsStorage.layout().inner.transferFrom(from, to, value);
159
+ emit Transfer(from, to, value);
160
+ return true;
161
+ }
162
+
163
+ /// @inheritdoc IERC20
164
+ function allowance(address owner, address spender) external view returns (uint256) {
165
+ return TownsPointsStorage.layout().inner.allowance(owner, spender);
166
+ }
167
+
168
+ /// @inheritdoc IERC20
169
+ function balanceOf(address account) external view returns (uint256) {
170
+ return TownsPointsStorage.layout().inner.balanceOf(account);
171
+ }
172
+
173
+ /// @inheritdoc IERC20
174
+ function totalSupply() external view returns (uint256) {
175
+ return TownsPointsStorage.layout().inner.totalSupply;
176
+ }
177
+
178
+ /*´:°•.°+.*•´.*:˚.°*.˚•´.°:°•.°•.*•´.*:˚.°*.˚•´.°:°•.°+.*•´.*:*/
179
+ /* ERC20 METADATA */
180
+ /*.•°:°.´+˚.*°.˚:*.´•*.+°.•°:´*.´•*.•°.•°:°.´:•˚°.*°.˚:*.´+°.•*/
181
+
182
+ /// @inheritdoc IERC20Metadata
183
+ function name() external pure returns (string memory) {
184
+ return "Towns Points";
185
+ }
186
+
187
+ /// @inheritdoc IERC20Metadata
188
+ function symbol() external pure returns (string memory) {
189
+ return "TWP";
190
+ }
191
+
192
+ /// @inheritdoc IERC20Metadata
193
+ function decimals() public pure virtual returns (uint8) {
194
+ return 18;
195
+ }
196
+ }
@@ -0,0 +1,22 @@
1
+ // SPDX-License-Identifier: MIT
2
+ pragma solidity ^0.8.23;
3
+
4
+ import {MinimalERC20Storage} from "@towns-protocol/diamond/src/primitive/ERC20.sol";
5
+
6
+ library TownsPointsStorage {
7
+ // keccak256(abi.encode(uint256(keccak256("tokens.points.storage")) - 1)) &
8
+ // ~bytes32(uint256(0xff))
9
+ bytes32 internal constant STORAGE_SLOT =
10
+ 0x25a22d57af6f735dc617e9781981413da3bc5a71376b4237270a04c144aaf700;
11
+
12
+ struct Layout {
13
+ MinimalERC20Storage inner;
14
+ address spaceFactory;
15
+ }
16
+
17
+ function layout() internal pure returns (Layout storage l) {
18
+ assembly {
19
+ l.slot := STORAGE_SLOT
20
+ }
21
+ }
22
+ }
@@ -0,0 +1,62 @@
1
+ // SPDX-License-Identifier: MIT
2
+ pragma solidity ^0.8.23;
3
+
4
+ // interfaces
5
+ import {IERC6900ExecutionModule} from "@erc6900/reference-implementation/interfaces/IERC6900ExecutionModule.sol";
6
+ import {IERC6900Module} from "@erc6900/reference-implementation/interfaces/IERC6900Module.sol";
7
+ import {ITownsApp} from "./ITownsApp.sol";
8
+
9
+ /// @title BaseApp
10
+ /// @notice Base contract for Towns apps implementing core ERC-6900 module functionality
11
+ /// @dev Provides base implementation for module installation/uninstallation and interface support
12
+ /// @dev Inheriting contracts should override _onInstall and _onUninstall as needed
13
+ /// @dev Implements IERC6900Module, IERC6900ExecutionModule, and ITownsApp interfaces
14
+
15
+ abstract contract BaseApp is ITownsApp {
16
+ receive() external payable {
17
+ _onPayment(msg.sender, msg.value);
18
+ }
19
+
20
+ // External functions
21
+ function supportsInterface(bytes4 interfaceId) external pure returns (bool) {
22
+ return
23
+ interfaceId == type(IERC6900ExecutionModule).interfaceId ||
24
+ interfaceId == type(IERC6900Module).interfaceId ||
25
+ interfaceId == type(ITownsApp).interfaceId;
26
+ }
27
+
28
+ /// @notice Required by IERC6900Module - called when module is installed
29
+ function onInstall(bytes calldata postInstallData) external {
30
+ _onInstall(postInstallData);
31
+ }
32
+
33
+ /// @notice Required by IERC6900Module - called when module is uninstalled
34
+ function onUninstall(bytes calldata postUninstallData) external {
35
+ _onUninstall(postUninstallData);
36
+ }
37
+
38
+ function moduleOwner() external view returns (address) {
39
+ return _moduleOwner();
40
+ }
41
+
42
+ function installPrice() external view returns (uint256) {
43
+ return _installPrice();
44
+ }
45
+
46
+ function accessDuration() external view returns (uint48) {
47
+ return _accessDuration();
48
+ }
49
+
50
+ // Internal functions
51
+ function _onInstall(bytes calldata postInstallData) internal virtual {}
52
+
53
+ function _onUninstall(bytes calldata postUninstallData) internal virtual {}
54
+
55
+ function _moduleOwner() internal view virtual returns (address) {}
56
+
57
+ function _installPrice() internal view virtual returns (uint256) {}
58
+
59
+ function _accessDuration() internal view virtual returns (uint48) {}
60
+
61
+ function _onPayment(address payer, uint256 amount) internal virtual {}
62
+ }
@@ -0,0 +1,28 @@
1
+ // SPDX-License-Identifier: MIT
2
+ pragma solidity ^0.8.23;
3
+
4
+ // interfaces
5
+ import {IERC6900ExecutionModule} from "@erc6900/reference-implementation/interfaces/IERC6900ExecutionModule.sol";
6
+ import {IERC6900Module} from "@erc6900/reference-implementation/interfaces/IERC6900Module.sol";
7
+
8
+ /// @title ITownsApp Interface
9
+ /// @notice Base interface for Towns apps implementing core module functionality
10
+ /// @dev Combines IERC6900Module (module lifecycle), and IERC6900ExecutionModule (execution)
11
+ /// @dev Apps must implement required permissions and support these interfaces
12
+ interface ITownsApp is IERC6900Module, IERC6900ExecutionModule {
13
+ /// @notice Returns the required permissions for the app
14
+ /// @return permissions The required permissions for the app
15
+ function requiredPermissions() external view returns (bytes32[] memory);
16
+
17
+ /// @notice Returns the owner of the app
18
+ /// @return owner The owner of the app
19
+ function moduleOwner() external view returns (address);
20
+
21
+ /// @notice Returns the install price of the app
22
+ /// @return installPrice The install price of the app
23
+ function installPrice() external view returns (uint256);
24
+
25
+ /// @notice Returns the access duration of the app
26
+ /// @return accessDuration The access duration of the app
27
+ function accessDuration() external view returns (uint48);
28
+ }