@flowtyio/flow-contracts 0.1.0-beta.3 → 0.1.0-beta.30
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.
- package/README.md +1 -1
- package/contracts/Burner.cdc +44 -0
- package/contracts/FlowStorageFees.cdc +15 -15
- package/contracts/FlowToken.cdc +29 -78
- package/contracts/FungibleToken.cdc +80 -53
- package/contracts/FungibleTokenMetadataViews.cdc +13 -25
- package/contracts/FungibleTokenSwitchboard.cdc +360 -0
- package/contracts/MetadataViews.cdc +107 -50
- package/contracts/NonFungibleToken.cdc +110 -60
- package/contracts/TokenForwarding.cdc +19 -11
- package/contracts/ViewResolver.cdc +20 -16
- package/contracts/capability-cache/CapabilityCache.cdc +97 -0
- package/contracts/dapper/DapperUtilityCoin.cdc +106 -39
- package/contracts/dapper/FlowUtilityToken.cdc +107 -40
- package/contracts/dapper/TopShot.cdc +323 -259
- package/contracts/dapper/TopShotLocking.cdc +41 -15
- package/contracts/dapper/offers/DapperOffersV2.cdc +46 -43
- package/contracts/dapper/offers/OffersV2.cdc +40 -56
- package/contracts/dapper/offers/Resolver.cdc +20 -13
- package/contracts/emerald-city/FLOAT.cdc +259 -254
- package/contracts/example/ExampleNFT.cdc +18 -21
- package/contracts/example/ExampleToken.cdc +68 -1
- package/contracts/find/FindViews.cdc +357 -353
- package/contracts/flow-utils/AddressUtils.cdc +20 -23
- package/contracts/flow-utils/ArrayUtils.cdc +10 -11
- package/contracts/flow-utils/ScopedFTProviders.cdc +27 -19
- package/contracts/flow-utils/ScopedNFTProviders.cdc +31 -26
- package/contracts/flow-utils/StringUtils.cdc +24 -37
- package/contracts/flowty-drops/ContractManager.cdc +47 -0
- package/contracts/flowty-drops/DropFactory.cdc +75 -0
- package/contracts/flowty-drops/DropTypes.cdc +278 -0
- package/contracts/flowty-drops/FlowtyAddressVerifiers.cdc +64 -0
- package/contracts/flowty-drops/FlowtyDrops.cdc +431 -0
- package/contracts/flowty-drops/FlowtyPricers.cdc +48 -0
- package/contracts/flowty-drops/FlowtySwitchers.cdc +113 -0
- package/contracts/flowty-drops/initializers/ContractBorrower.cdc +14 -0
- package/contracts/flowty-drops/initializers/ContractInitializer.cdc +7 -0
- package/contracts/flowty-drops/initializers/OpenEditionInitializer.cdc +58 -0
- package/contracts/flowty-drops/nft/BaseCollection.cdc +97 -0
- package/contracts/flowty-drops/nft/BaseNFT.cdc +107 -0
- package/contracts/flowty-drops/nft/ContractFactory.cdc +13 -0
- package/contracts/flowty-drops/nft/ContractFactoryTemplate.cdc +48 -0
- package/contracts/flowty-drops/nft/NFTMetadata.cdc +119 -0
- package/contracts/flowty-drops/nft/OpenEditionNFT.cdc +41 -0
- package/contracts/flowty-drops/nft/OpenEditionTemplate.cdc +52 -0
- package/contracts/flowty-drops/nft/UniversalCollection.cdc +23 -0
- package/contracts/fungible-token-router/FungibleTokenRouter.cdc +105 -0
- package/contracts/hybrid-custody/CapabilityDelegator.cdc +28 -26
- package/contracts/hybrid-custody/CapabilityFactory.cdc +20 -18
- package/contracts/hybrid-custody/CapabilityFilter.cdc +41 -24
- package/contracts/hybrid-custody/HybridCustody.cdc +303 -242
- package/contracts/hybrid-custody/factories/FTAllFactory.cdc +16 -4
- package/contracts/hybrid-custody/factories/FTBalanceFactory.cdc +16 -4
- package/contracts/hybrid-custody/factories/FTProviderFactory.cdc +17 -5
- package/contracts/hybrid-custody/factories/FTReceiverBalanceFactory.cdc +16 -4
- package/contracts/hybrid-custody/factories/FTReceiverFactory.cdc +16 -4
- package/contracts/hybrid-custody/factories/FTVaultFactory.cdc +46 -0
- package/contracts/hybrid-custody/factories/NFTCollectionFactory.cdc +45 -0
- package/contracts/hybrid-custody/factories/NFTCollectionPublicFactory.cdc +16 -4
- package/contracts/hybrid-custody/factories/NFTProviderAndCollectionFactory.cdc +22 -0
- package/contracts/hybrid-custody/factories/NFTProviderFactory.cdc +16 -4
- package/contracts/lost-and-found/LostAndFound.cdc +29 -25
- package/contracts/nft-catalog/NFTCatalog.cdc +60 -64
- package/contracts/nft-catalog/NFTCatalogAdmin.cdc +28 -27
- package/flow.json +189 -5
- package/package.json +1 -1
- package/contracts/hybrid-custody/factories/NFTProviderAndCollectionPublicFactory.cdc +0 -10
|
@@ -1,8 +1,5 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
pub contract AddressUtils {
|
|
4
|
-
|
|
5
|
-
pub fun withoutPrefix(_ input: String): String {
|
|
1
|
+
access(all) contract AddressUtils {
|
|
2
|
+
access(all) fun withoutPrefix(_ input: String): String {
|
|
6
3
|
var address = input
|
|
7
4
|
|
|
8
5
|
// get rid of 0x
|
|
@@ -17,7 +14,7 @@ pub contract AddressUtils {
|
|
|
17
14
|
return address
|
|
18
15
|
}
|
|
19
16
|
|
|
20
|
-
|
|
17
|
+
access(all) fun parseUInt64(_ input: AnyStruct): UInt64? {
|
|
21
18
|
var stringValue = ""
|
|
22
19
|
|
|
23
20
|
if let string = input as? String {
|
|
@@ -25,7 +22,7 @@ pub contract AddressUtils {
|
|
|
25
22
|
} else if let address = input as? Address {
|
|
26
23
|
stringValue = address.toString()
|
|
27
24
|
} else if let type = input as? Type {
|
|
28
|
-
let parts =
|
|
25
|
+
let parts = type.identifier.split(separator: ".")
|
|
29
26
|
if parts.length == 1 {
|
|
30
27
|
return nil
|
|
31
28
|
}
|
|
@@ -45,14 +42,14 @@ pub contract AddressUtils {
|
|
|
45
42
|
return r
|
|
46
43
|
}
|
|
47
44
|
|
|
48
|
-
|
|
45
|
+
access(all) fun parseAddress(_ input: AnyStruct): Address? {
|
|
49
46
|
if let parsed = self.parseUInt64(input) {
|
|
50
47
|
return Address(parsed)
|
|
51
48
|
}
|
|
52
49
|
return nil
|
|
53
50
|
}
|
|
54
51
|
|
|
55
|
-
|
|
52
|
+
access(all) fun isValidAddress(_ input: AnyStruct, forNetwork: String): Bool {
|
|
56
53
|
let address = self.parseUInt64(input)
|
|
57
54
|
if address == nil {
|
|
58
55
|
return false
|
|
@@ -61,18 +58,19 @@ pub contract AddressUtils {
|
|
|
61
58
|
let codeWords: {String: UInt64} = {
|
|
62
59
|
"MAINNET" : 0,
|
|
63
60
|
"TESTNET" : 0x6834ba37b3980209,
|
|
61
|
+
"CRESCENDO" : 0x6834ba37b3980209,
|
|
64
62
|
"EMULATOR": 0x1cb159857af02018
|
|
65
63
|
}
|
|
66
64
|
|
|
67
65
|
let parityCheckMatrixColumns: [UInt64] = [
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
66
|
+
0x00001, 0x00002, 0x00004, 0x00008, 0x00010, 0x00020, 0x00040, 0x00080,
|
|
67
|
+
0x00100, 0x00200, 0x00400, 0x00800, 0x01000, 0x02000, 0x04000, 0x08000,
|
|
68
|
+
0x10000, 0x20000, 0x40000, 0x7328d, 0x6689a, 0x6112f, 0x6084b, 0x433fd,
|
|
69
|
+
0x42aab, 0x41951, 0x233ce, 0x22a81, 0x21948, 0x1ef60, 0x1deca, 0x1c639,
|
|
70
|
+
0x1bdd8, 0x1a535, 0x194ac, 0x18c46, 0x1632b, 0x1529b, 0x14a43, 0x13184,
|
|
71
|
+
0x12942, 0x118c1, 0x0f812, 0x0e027, 0x0d00e, 0x0c83c, 0x0b01d, 0x0a831,
|
|
72
|
+
0x0982b, 0x07034, 0x0682a, 0x05819, 0x03807, 0x007d2, 0x00727, 0x0068e,
|
|
73
|
+
0x0067c, 0x0059d, 0x004eb, 0x003b4, 0x0036a, 0x002d9, 0x001c7, 0x0003f
|
|
76
74
|
]
|
|
77
75
|
|
|
78
76
|
var parity: UInt64 = 0
|
|
@@ -93,8 +91,8 @@ pub contract AddressUtils {
|
|
|
93
91
|
return parity == 0 && codeWord == 0
|
|
94
92
|
}
|
|
95
93
|
|
|
96
|
-
|
|
97
|
-
for network in ["MAINNET", "TESTNET", "EMULATOR"]{
|
|
94
|
+
access(all) fun getNetworkFromAddress(_ input: AnyStruct): String? {
|
|
95
|
+
for network in ["MAINNET", "TESTNET", "EMULATOR"] {
|
|
98
96
|
if self.isValidAddress(input, forNetwork: network){
|
|
99
97
|
return network
|
|
100
98
|
}
|
|
@@ -102,8 +100,7 @@ pub contract AddressUtils {
|
|
|
102
100
|
return nil
|
|
103
101
|
}
|
|
104
102
|
|
|
105
|
-
|
|
106
|
-
return
|
|
103
|
+
access(all) fun currentNetwork(): String {
|
|
104
|
+
return self.getNetworkFromAddress(self.account.address) ?? panic("unknown network!")
|
|
107
105
|
}
|
|
108
|
-
|
|
109
|
-
}
|
|
106
|
+
}
|
|
@@ -1,8 +1,7 @@
|
|
|
1
1
|
// Copied from https://github.com/bluesign/flow-utils/blob/dnz/cadence/contracts/ArrayUtils.cdc with minor adjustments
|
|
2
2
|
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
pub fun rangeFunc(_ start: Int, _ end: Int, _ f: ((Int): Void)) {
|
|
3
|
+
access(all) contract ArrayUtils {
|
|
4
|
+
access(all) fun rangeFunc(_ start: Int, _ end: Int, _ f: fun (Int): Void) {
|
|
6
5
|
var current = start
|
|
7
6
|
while current < end {
|
|
8
7
|
f(current)
|
|
@@ -10,7 +9,7 @@ pub contract ArrayUtils {
|
|
|
10
9
|
}
|
|
11
10
|
}
|
|
12
11
|
|
|
13
|
-
|
|
12
|
+
access(all) fun range(_ start: Int, _ end: Int): [Int] {
|
|
14
13
|
var res: [Int] = []
|
|
15
14
|
self.rangeFunc(start, end, fun (i: Int) {
|
|
16
15
|
res.append(i)
|
|
@@ -18,7 +17,7 @@ pub contract ArrayUtils {
|
|
|
18
17
|
return res
|
|
19
18
|
}
|
|
20
19
|
|
|
21
|
-
|
|
20
|
+
access(all) fun reverse(_ array: [Int]): [Int] {
|
|
22
21
|
var res: [Int] = []
|
|
23
22
|
var i: Int = array.length - 1
|
|
24
23
|
while i >= 0 {
|
|
@@ -28,13 +27,13 @@ pub contract ArrayUtils {
|
|
|
28
27
|
return res
|
|
29
28
|
}
|
|
30
29
|
|
|
31
|
-
|
|
30
|
+
access(all) fun transform(_ array: auth(Mutate) &[AnyStruct], _ f : fun (&AnyStruct, auth(Mutate) &[AnyStruct], Int)){
|
|
32
31
|
for i in self.range(0, array.length){
|
|
33
|
-
array[i]
|
|
32
|
+
f(array[i], array, i)
|
|
34
33
|
}
|
|
35
34
|
}
|
|
36
35
|
|
|
37
|
-
|
|
36
|
+
access(all) fun iterate(_ array: [AnyStruct], _ f : fun (AnyStruct): Bool) {
|
|
38
37
|
for item in array{
|
|
39
38
|
if !f(item){
|
|
40
39
|
break
|
|
@@ -42,7 +41,7 @@ pub contract ArrayUtils {
|
|
|
42
41
|
}
|
|
43
42
|
}
|
|
44
43
|
|
|
45
|
-
|
|
44
|
+
access(all) fun map(_ array: [AnyStruct], _ f : fun (AnyStruct): AnyStruct) : [AnyStruct] {
|
|
46
45
|
var res : [AnyStruct] = []
|
|
47
46
|
for item in array{
|
|
48
47
|
res.append(f(item))
|
|
@@ -50,7 +49,7 @@ pub contract ArrayUtils {
|
|
|
50
49
|
return res
|
|
51
50
|
}
|
|
52
51
|
|
|
53
|
-
|
|
52
|
+
access(all) fun mapStrings(_ array: [String], _ f: fun (String) : String) : [String] {
|
|
54
53
|
var res : [String] = []
|
|
55
54
|
for item in array{
|
|
56
55
|
res.append(f(item))
|
|
@@ -58,7 +57,7 @@ pub contract ArrayUtils {
|
|
|
58
57
|
return res
|
|
59
58
|
}
|
|
60
59
|
|
|
61
|
-
|
|
60
|
+
access(all) fun reduce(_ array: [AnyStruct], _ initial: AnyStruct, _ f : fun (AnyStruct, AnyStruct): AnyStruct) : AnyStruct{
|
|
62
61
|
var res: AnyStruct = f(initial, array[0])
|
|
63
62
|
for i in self.range(1, array.length){
|
|
64
63
|
res = f(res, array[i])
|
|
@@ -8,14 +8,14 @@ import "StringUtils"
|
|
|
8
8
|
//
|
|
9
9
|
// ScopedProviders are meant to solve the issue of unbounded access FungibleToken vaults
|
|
10
10
|
// when a provider is called for.
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
11
|
+
access(all) contract ScopedFTProviders {
|
|
12
|
+
access(all) struct interface FTFilter {
|
|
13
|
+
access(all) view fun canWithdrawAmount(_ amount: UFix64): Bool
|
|
14
|
+
access(FungibleToken.Withdraw) fun markAmountWithdrawn(_ amount: UFix64)
|
|
15
|
+
access(all) fun getDetails(): {String: AnyStruct}
|
|
16
16
|
}
|
|
17
17
|
|
|
18
|
-
|
|
18
|
+
access(all) struct AllowanceFilter: FTFilter {
|
|
19
19
|
access(self) let allowance: UFix64
|
|
20
20
|
access(self) var allowanceUsed: UFix64
|
|
21
21
|
|
|
@@ -24,15 +24,15 @@ pub contract ScopedFTProviders {
|
|
|
24
24
|
self.allowanceUsed = 0.0
|
|
25
25
|
}
|
|
26
26
|
|
|
27
|
-
|
|
27
|
+
access(all) view fun canWithdrawAmount(_ amount: UFix64): Bool {
|
|
28
28
|
return amount + self.allowanceUsed <= self.allowance
|
|
29
29
|
}
|
|
30
30
|
|
|
31
|
-
|
|
31
|
+
access(FungibleToken.Withdraw) fun markAmountWithdrawn(_ amount: UFix64) {
|
|
32
32
|
self.allowanceUsed = self.allowanceUsed + amount
|
|
33
33
|
}
|
|
34
34
|
|
|
35
|
-
|
|
35
|
+
access(all) fun getDetails(): {String: AnyStruct} {
|
|
36
36
|
return {
|
|
37
37
|
"allowance": self.allowance,
|
|
38
38
|
"allowanceUsed": self.allowanceUsed
|
|
@@ -44,31 +44,35 @@ pub contract ScopedFTProviders {
|
|
|
44
44
|
//
|
|
45
45
|
// A ScopedFTProvider is a wrapped FungibleTokenProvider with
|
|
46
46
|
// filters that can be defined by anyone using the ScopedFTProvider.
|
|
47
|
-
|
|
48
|
-
access(self) let provider: Capability
|
|
47
|
+
access(all) resource ScopedFTProvider: FungibleToken.Provider {
|
|
48
|
+
access(self) let provider: Capability<auth(FungibleToken.Withdraw) &{FungibleToken.Provider}>
|
|
49
49
|
access(self) var filters: [{FTFilter}]
|
|
50
50
|
|
|
51
51
|
// block timestamp that this provider can no longer be used after
|
|
52
52
|
access(self) let expiration: UFix64?
|
|
53
53
|
|
|
54
|
-
|
|
54
|
+
access(all) init(provider: Capability<auth(FungibleToken.Withdraw) &{FungibleToken.Provider}>, filters: [{FTFilter}], expiration: UFix64?) {
|
|
55
55
|
self.provider = provider
|
|
56
56
|
self.filters = filters
|
|
57
57
|
self.expiration = expiration
|
|
58
58
|
}
|
|
59
59
|
|
|
60
|
-
|
|
60
|
+
access(all) fun getProviderType(): Type {
|
|
61
|
+
return self.provider.borrow()!.getType()
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
access(all) fun check(): Bool {
|
|
61
65
|
return self.provider.check()
|
|
62
66
|
}
|
|
63
67
|
|
|
64
|
-
|
|
68
|
+
access(all) view fun isExpired(): Bool {
|
|
65
69
|
if let expiration = self.expiration {
|
|
66
70
|
return getCurrentBlock().timestamp >= expiration
|
|
67
71
|
}
|
|
68
72
|
return false
|
|
69
73
|
}
|
|
70
74
|
|
|
71
|
-
|
|
75
|
+
access(all) view fun canWithdraw(_ amount: UFix64): Bool {
|
|
72
76
|
if self.isExpired() {
|
|
73
77
|
return false
|
|
74
78
|
}
|
|
@@ -82,7 +86,11 @@ pub contract ScopedFTProviders {
|
|
|
82
86
|
return true
|
|
83
87
|
}
|
|
84
88
|
|
|
85
|
-
|
|
89
|
+
access(all) view fun isAvailableToWithdraw(amount: UFix64): Bool {
|
|
90
|
+
return self.canWithdraw(amount)
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
access(FungibleToken.Withdraw) fun withdraw(amount: UFix64): @{FungibleToken.Vault} {
|
|
86
94
|
pre {
|
|
87
95
|
!self.isExpired(): "provider has expired"
|
|
88
96
|
}
|
|
@@ -100,7 +108,7 @@ pub contract ScopedFTProviders {
|
|
|
100
108
|
return <-self.provider.borrow()!.withdraw(amount: amount)
|
|
101
109
|
}
|
|
102
110
|
|
|
103
|
-
|
|
111
|
+
access(all) fun getDetails(): [{String: AnyStruct}] {
|
|
104
112
|
let details: [{String: AnyStruct}] = []
|
|
105
113
|
for filter in self.filters {
|
|
106
114
|
details.append(filter.getDetails())
|
|
@@ -110,8 +118,8 @@ pub contract ScopedFTProviders {
|
|
|
110
118
|
}
|
|
111
119
|
}
|
|
112
120
|
|
|
113
|
-
|
|
114
|
-
provider: Capability
|
|
121
|
+
access(all) fun createScopedFTProvider(
|
|
122
|
+
provider: Capability<auth(FungibleToken.Withdraw) &{FungibleToken.Provider}>,
|
|
115
123
|
filters: [{FTFilter}],
|
|
116
124
|
expiration: UFix64?
|
|
117
125
|
): @ScopedFTProvider {
|
|
@@ -11,14 +11,14 @@ import "StringUtils"
|
|
|
11
11
|
//
|
|
12
12
|
// By using a scoped provider, only a subset of assets can be taken if the provider leaks
|
|
13
13
|
// instead of the entire nft collection.
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
14
|
+
access(all) contract ScopedNFTProviders {
|
|
15
|
+
access(all) struct interface NFTFilter {
|
|
16
|
+
access(all) fun canWithdraw(_ nft: &{NonFungibleToken.NFT}): Bool
|
|
17
|
+
access(NonFungibleToken.Withdraw) fun markWithdrawn(_ nft: &{NonFungibleToken.NFT})
|
|
18
|
+
access(all) fun getDetails(): {String: AnyStruct}
|
|
19
19
|
}
|
|
20
20
|
|
|
21
|
-
|
|
21
|
+
access(all) struct NFTIDFilter: NFTFilter {
|
|
22
22
|
// the ids that are allowed to be withdrawn.
|
|
23
23
|
// If ids[num] is false, the id cannot be withdrawn anymore
|
|
24
24
|
access(self) let ids: {UInt64: Bool}
|
|
@@ -31,22 +31,22 @@ pub contract ScopedNFTProviders {
|
|
|
31
31
|
self.ids = d
|
|
32
32
|
}
|
|
33
33
|
|
|
34
|
-
|
|
34
|
+
access(all) fun canWithdraw(_ nft: &{NonFungibleToken.NFT}): Bool {
|
|
35
35
|
return self.ids[nft.id] != nil && self.ids[nft.id] == true
|
|
36
36
|
}
|
|
37
37
|
|
|
38
|
-
|
|
38
|
+
access(NonFungibleToken.Withdraw) fun markWithdrawn(_ nft: &{NonFungibleToken.NFT}) {
|
|
39
39
|
self.ids[nft.id] = false
|
|
40
40
|
}
|
|
41
41
|
|
|
42
|
-
|
|
42
|
+
access(all) fun getDetails(): {String: AnyStruct} {
|
|
43
43
|
return {
|
|
44
44
|
"ids": self.ids
|
|
45
45
|
}
|
|
46
46
|
}
|
|
47
47
|
}
|
|
48
48
|
|
|
49
|
-
|
|
49
|
+
access(all) struct UUIDFilter: NFTFilter {
|
|
50
50
|
// the ids that are allowed to be withdrawn.
|
|
51
51
|
// If ids[num] is false, the id cannot be withdrawn anymore
|
|
52
52
|
access(self) let uuids: {UInt64: Bool}
|
|
@@ -59,15 +59,15 @@ pub contract ScopedNFTProviders {
|
|
|
59
59
|
self.uuids = d
|
|
60
60
|
}
|
|
61
61
|
|
|
62
|
-
|
|
62
|
+
access(all) fun canWithdraw(_ nft: &{NonFungibleToken.NFT}): Bool {
|
|
63
63
|
return self.uuids[nft.uuid] != nil && self.uuids[nft.uuid]! == true
|
|
64
64
|
}
|
|
65
65
|
|
|
66
|
-
|
|
66
|
+
access(NonFungibleToken.Withdraw) fun markWithdrawn(_ nft: &{NonFungibleToken.NFT}) {
|
|
67
67
|
self.uuids[nft.uuid] = false
|
|
68
68
|
}
|
|
69
69
|
|
|
70
|
-
|
|
70
|
+
access(all) fun getDetails(): {String: AnyStruct} {
|
|
71
71
|
return {
|
|
72
72
|
"uuids": self.uuids
|
|
73
73
|
}
|
|
@@ -77,39 +77,43 @@ pub contract ScopedNFTProviders {
|
|
|
77
77
|
// ScopedNFTProvider
|
|
78
78
|
//
|
|
79
79
|
// Wrapper around an NFT Provider that is restricted to specific ids.
|
|
80
|
-
|
|
81
|
-
access(self) let provider: Capability
|
|
80
|
+
access(all) resource ScopedNFTProvider: NonFungibleToken.Provider {
|
|
81
|
+
access(self) let provider: Capability<auth(NonFungibleToken.Withdraw) &{NonFungibleToken.Collection}>
|
|
82
82
|
access(self) let filters: [{NFTFilter}]
|
|
83
83
|
|
|
84
84
|
// block timestamp that this provider can no longer be used after
|
|
85
85
|
access(self) let expiration: UFix64?
|
|
86
86
|
|
|
87
|
-
|
|
87
|
+
access(all) view fun isExpired(): Bool {
|
|
88
88
|
if let expiration = self.expiration {
|
|
89
89
|
return getCurrentBlock().timestamp >= expiration
|
|
90
90
|
}
|
|
91
91
|
return false
|
|
92
92
|
}
|
|
93
93
|
|
|
94
|
-
|
|
94
|
+
access(all) init(provider: Capability<auth(NonFungibleToken.Withdraw) &{NonFungibleToken.Collection}>, filters: [{NFTFilter}], expiration: UFix64?) {
|
|
95
95
|
self.provider = provider
|
|
96
96
|
self.expiration = expiration
|
|
97
97
|
self.filters = filters
|
|
98
98
|
}
|
|
99
99
|
|
|
100
|
-
|
|
100
|
+
access(all) fun canWithdraw(_ id: UInt64): Bool {
|
|
101
101
|
if self.isExpired() {
|
|
102
102
|
return false
|
|
103
103
|
}
|
|
104
104
|
|
|
105
|
-
|
|
105
|
+
if !self.provider.check() {
|
|
106
|
+
return false
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
let nft: &{NonFungibleToken.NFT}? = self.provider.borrow()!.borrowNFT(id)
|
|
106
110
|
if nft == nil {
|
|
107
111
|
return false
|
|
108
112
|
}
|
|
109
113
|
|
|
110
114
|
var i = 0
|
|
111
115
|
while i < self.filters.length {
|
|
112
|
-
if !self.filters[i].canWithdraw(nft) {
|
|
116
|
+
if !self.filters[i].canWithdraw(nft!) {
|
|
113
117
|
return false
|
|
114
118
|
}
|
|
115
119
|
i = i + 1
|
|
@@ -117,17 +121,17 @@ pub contract ScopedNFTProviders {
|
|
|
117
121
|
return true
|
|
118
122
|
}
|
|
119
123
|
|
|
120
|
-
|
|
124
|
+
access(all) fun check(): Bool {
|
|
121
125
|
return self.provider.check()
|
|
122
126
|
}
|
|
123
127
|
|
|
124
|
-
|
|
128
|
+
access(NonFungibleToken.Withdraw) fun withdraw(withdrawID: UInt64): @{NonFungibleToken.NFT} {
|
|
125
129
|
pre {
|
|
126
130
|
!self.isExpired(): "provider has expired"
|
|
127
131
|
}
|
|
128
132
|
|
|
129
133
|
let nft <- self.provider.borrow()!.withdraw(withdrawID: withdrawID)
|
|
130
|
-
let ref = &nft as &NonFungibleToken.NFT
|
|
134
|
+
let ref = &nft as &{NonFungibleToken.NFT}
|
|
131
135
|
|
|
132
136
|
var i = 0
|
|
133
137
|
while i < self.filters.length {
|
|
@@ -142,7 +146,7 @@ pub contract ScopedNFTProviders {
|
|
|
142
146
|
return <-nft
|
|
143
147
|
}
|
|
144
148
|
|
|
145
|
-
|
|
149
|
+
access(all) fun getDetails(): [{String: AnyStruct}] {
|
|
146
150
|
let details: [{String: AnyStruct}] = []
|
|
147
151
|
for f in self.filters {
|
|
148
152
|
details.append(f.getDetails())
|
|
@@ -152,11 +156,12 @@ pub contract ScopedNFTProviders {
|
|
|
152
156
|
}
|
|
153
157
|
}
|
|
154
158
|
|
|
155
|
-
|
|
156
|
-
provider: Capability
|
|
159
|
+
access(all) fun createScopedNFTProvider(
|
|
160
|
+
provider: Capability<auth(NonFungibleToken.Withdraw) &{NonFungibleToken.Collection}>,
|
|
157
161
|
filters: [{NFTFilter}],
|
|
158
162
|
expiration: UFix64?
|
|
159
163
|
): @ScopedNFTProvider {
|
|
160
164
|
return <- create ScopedNFTProvider(provider: provider, filters: filters, expiration: expiration)
|
|
161
165
|
}
|
|
162
166
|
}
|
|
167
|
+
|
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
import "ArrayUtils"
|
|
2
2
|
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
3
|
+
access(all) contract StringUtils {
|
|
4
|
+
|
|
5
|
+
access(all) fun format(_ s: String, _ args: {String:String}): String{
|
|
6
|
+
var formatted = s
|
|
7
|
+
for key in args.keys{
|
|
8
|
+
formatted = StringUtils.replaceAll(formatted, "{".concat(key).concat("}"), args[key]!)
|
|
9
|
+
}
|
|
10
|
+
return formatted
|
|
11
11
|
}
|
|
12
12
|
|
|
13
|
-
|
|
13
|
+
access(all) fun explode(_ s: String): [String]{
|
|
14
14
|
var chars : [String] = []
|
|
15
15
|
for i in ArrayUtils.range(0, s.length){
|
|
16
16
|
chars.append(s[i].toString())
|
|
@@ -18,7 +18,7 @@ pub contract StringUtils {
|
|
|
18
18
|
return chars
|
|
19
19
|
}
|
|
20
20
|
|
|
21
|
-
|
|
21
|
+
access(all) fun trimLeft(_ s: String): String{
|
|
22
22
|
for i in ArrayUtils.range(0, s.length){
|
|
23
23
|
if s[i] != " "{
|
|
24
24
|
return s.slice(from: i, upTo: s.length)
|
|
@@ -27,23 +27,23 @@ pub contract StringUtils {
|
|
|
27
27
|
return ""
|
|
28
28
|
}
|
|
29
29
|
|
|
30
|
-
|
|
30
|
+
access(all) fun trim(_ s: String): String{
|
|
31
31
|
return self.trimLeft(s)
|
|
32
32
|
}
|
|
33
33
|
|
|
34
|
-
|
|
35
|
-
return
|
|
34
|
+
access(all) fun replaceAll(_ s: String, _ search: String, _ replace: String): String{
|
|
35
|
+
return s.replaceAll(of: search, with: replace)
|
|
36
36
|
}
|
|
37
37
|
|
|
38
|
-
|
|
38
|
+
access(all) fun hasPrefix(_ s: String, _ prefix: String) : Bool{
|
|
39
39
|
return s.length >= prefix.length && s.slice(from:0, upTo: prefix.length)==prefix
|
|
40
40
|
}
|
|
41
41
|
|
|
42
|
-
|
|
42
|
+
access(all) fun hasSuffix(_ s: String, _ suffix: String) : Bool{
|
|
43
43
|
return s.length >= suffix.length && s.slice(from:s.length-suffix.length, upTo: s.length)==suffix
|
|
44
44
|
}
|
|
45
45
|
|
|
46
|
-
|
|
46
|
+
access(all) fun index(_ s : String, _ substr : String, _ startIndex: Int): Int?{
|
|
47
47
|
for i in ArrayUtils.range(startIndex,s.length-substr.length+1){
|
|
48
48
|
if s[i]==substr[0] && s.slice(from:i, upTo:i+substr.length) == substr{
|
|
49
49
|
return i
|
|
@@ -52,7 +52,7 @@ pub contract StringUtils {
|
|
|
52
52
|
return nil
|
|
53
53
|
}
|
|
54
54
|
|
|
55
|
-
|
|
55
|
+
access(all) fun count(_ s: String, _ substr: String): Int{
|
|
56
56
|
var pos = [self.index(s, substr, 0)]
|
|
57
57
|
while pos[0]!=nil {
|
|
58
58
|
pos.insert(at:0, self.index(s, substr, pos[0]!+pos.length*substr.length+1))
|
|
@@ -60,38 +60,25 @@ pub contract StringUtils {
|
|
|
60
60
|
return pos.length-1
|
|
61
61
|
}
|
|
62
62
|
|
|
63
|
-
|
|
63
|
+
access(all) fun contains(_ s: String, _ substr: String): Bool {
|
|
64
64
|
if let index = self.index(s, substr, 0) {
|
|
65
65
|
return true
|
|
66
66
|
}
|
|
67
67
|
return false
|
|
68
68
|
}
|
|
69
69
|
|
|
70
|
-
|
|
70
|
+
access(all) fun substringUntil(_ s: String, _ until: String, _ startIndex: Int): String{
|
|
71
71
|
if let index = self.index( s, until, startIndex){
|
|
72
72
|
return s.slice(from:startIndex, upTo: index)
|
|
73
73
|
}
|
|
74
74
|
return s.slice(from:startIndex, upTo:s.length)
|
|
75
75
|
}
|
|
76
76
|
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
var p = 0
|
|
80
|
-
while p<=s.length{
|
|
81
|
-
var preDelimiter = self.substringUntil(s, delimiter, p)
|
|
82
|
-
segments.append(preDelimiter)
|
|
83
|
-
p = p + preDelimiter.length + delimiter.length
|
|
84
|
-
}
|
|
85
|
-
return segments
|
|
77
|
+
access(all) fun split(_ s: String, _ delimiter: String): [String] {
|
|
78
|
+
return s.split(separator: delimiter)
|
|
86
79
|
}
|
|
87
80
|
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
for s in strs {
|
|
91
|
-
joinedStr = joinedStr.concat(s).concat(separator)
|
|
92
|
-
}
|
|
93
|
-
return joinedStr.slice(from: 0, upTo: joinedStr.length - separator.length)
|
|
81
|
+
access(all) fun join(_ strs: [String], _ separator: String): String {
|
|
82
|
+
return String.join(strs, separator: separator)
|
|
94
83
|
}
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
}
|
|
84
|
+
}
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import "FlowToken"
|
|
2
|
+
import "FungibleToken"
|
|
3
|
+
|
|
4
|
+
access(all) contract ContractManager {
|
|
5
|
+
access(all) let StoragePath: StoragePath
|
|
6
|
+
access(all) let PublicPath: PublicPath
|
|
7
|
+
|
|
8
|
+
access(all) entitlement Manage
|
|
9
|
+
|
|
10
|
+
access(all) resource Manager {
|
|
11
|
+
access(self) let acct: Capability<auth(Storage, Contracts, Keys, Inbox, Capabilities) &Account>
|
|
12
|
+
|
|
13
|
+
access(Manage) fun borrowContractAccount(): auth(Contracts) &Account {
|
|
14
|
+
return self.acct.borrow()!
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
access(all) fun addFlowTokensToAccount(_ tokens: @FlowToken.Vault) {
|
|
18
|
+
self.acct.borrow()!.storage.borrow<&{FungibleToken.Receiver}>(from: /storage/flowTokenVault)!.deposit(from: <-tokens)
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
access(all) fun getAccount(): &Account {
|
|
22
|
+
return getAccount(self.acct.address)
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
init(tokens: @FlowToken.Vault) {
|
|
26
|
+
pre {
|
|
27
|
+
tokens.balance >= 0.001: "minimum balance of 0.001 required for initialization"
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
let acct = Account(payer: ContractManager.account)
|
|
31
|
+
self.acct = acct.capabilities.account.issue<auth(Storage, Contracts, Keys, Inbox, Capabilities) &Account>()
|
|
32
|
+
assert(self.acct.check(), message: "failed to setup account capability")
|
|
33
|
+
|
|
34
|
+
acct.storage.borrow<&{FungibleToken.Receiver}>(from: /storage/flowTokenVault)!.deposit(from: <-tokens)
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
access(all) fun createManager(tokens: @FlowToken.Vault): @Manager {
|
|
39
|
+
return <- create Manager(tokens: <- tokens)
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
init() {
|
|
43
|
+
let identifier = "ContractManager_".concat(self.account.address.toString())
|
|
44
|
+
self.StoragePath = StoragePath(identifier: identifier)!
|
|
45
|
+
self.PublicPath = PublicPath(identifier: identifier)!
|
|
46
|
+
}
|
|
47
|
+
}
|