@@ -5,29 +5,36 @@ import {
5
5
PostConditionPrincipalId ,
6
6
PostConditionType ,
7
7
} from './constants' ;
8
- import { PostCondition , PostConditionModeName } from './postcondition-types' ;
9
8
import {
9
+ FungibleComparator ,
10
+ NonFungibleComparator ,
11
+ PostCondition ,
12
+ PostConditionModeName ,
13
+ } from './postcondition-types' ;
14
+ import { AssetString } from './types' ;
15
+ import {
16
+ AssetWire ,
17
+ PostConditionPrincipalWire ,
10
18
PostConditionWire ,
11
19
StacksWireType ,
20
+ addressToString ,
12
21
parseAssetString ,
13
22
parsePrincipalString ,
14
23
serializePostConditionWire ,
15
24
} from './wire' ;
16
25
17
- const FUNGIBLE_COMPARATOR_MAPPING = {
18
- eq : FungibleConditionCode . Equal ,
19
- gt : FungibleConditionCode . Greater ,
20
- lt : FungibleConditionCode . Less ,
21
- gte : FungibleConditionCode . GreaterEqual ,
22
- lte : FungibleConditionCode . LessEqual ,
23
- } ;
26
+ /** @internal */
27
+ enum PostConditionCodeWireType {
28
+ eq = FungibleConditionCode . Equal ,
29
+ gt = FungibleConditionCode . Greater ,
30
+ lt = FungibleConditionCode . Less ,
31
+ gte = FungibleConditionCode . GreaterEqual ,
32
+ lte = FungibleConditionCode . LessEqual ,
24
33
25
- const NON_FUNGIBLE_COMPARATOR_MAPPING = {
26
- sent : NonFungibleConditionCode . Sends ,
27
- 'not-sent' : NonFungibleConditionCode . DoesNotSend ,
28
- } ;
34
+ sent = NonFungibleConditionCode . Sends ,
35
+ 'not-sent' = NonFungibleConditionCode . DoesNotSend ,
36
+ }
29
37
30
- /** @ignore */
31
38
export function postConditionToWire ( postcondition : PostCondition ) : PostConditionWire {
32
39
switch ( postcondition . type ) {
33
40
case 'stx-postcondition' :
@@ -38,7 +45,7 @@ export function postConditionToWire(postcondition: PostCondition): PostCondition
38
45
postcondition . address === 'origin'
39
46
? { type : StacksWireType . Principal , prefix : PostConditionPrincipalId . Origin }
40
47
: parsePrincipalString ( postcondition . address ) ,
41
- conditionCode : FUNGIBLE_COMPARATOR_MAPPING [ postcondition . condition ] ,
48
+ conditionCode : conditionTypeToByte ( postcondition . condition ) as FungibleConditionCode ,
42
49
amount : BigInt ( postcondition . amount ) ,
43
50
} ;
44
51
case 'ft-postcondition' :
@@ -49,7 +56,7 @@ export function postConditionToWire(postcondition: PostCondition): PostCondition
49
56
postcondition . address === 'origin'
50
57
? { type : StacksWireType . Principal , prefix : PostConditionPrincipalId . Origin }
51
58
: parsePrincipalString ( postcondition . address ) ,
52
- conditionCode : FUNGIBLE_COMPARATOR_MAPPING [ postcondition . condition ] ,
59
+ conditionCode : conditionTypeToByte ( postcondition . condition ) as FungibleConditionCode ,
53
60
amount : BigInt ( postcondition . amount ) ,
54
61
asset : parseAssetString ( postcondition . asset ) ,
55
62
} ;
@@ -61,7 +68,7 @@ export function postConditionToWire(postcondition: PostCondition): PostCondition
61
68
postcondition . address === 'origin'
62
69
? { type : StacksWireType . Principal , prefix : PostConditionPrincipalId . Origin }
63
70
: parsePrincipalString ( postcondition . address ) ,
64
- conditionCode : NON_FUNGIBLE_COMPARATOR_MAPPING [ postcondition . condition ] ,
71
+ conditionCode : conditionTypeToByte ( postcondition . condition ) ,
65
72
asset : parseAssetString ( postcondition . asset ) ,
66
73
assetName : postcondition . assetId ,
67
74
} ;
@@ -70,6 +77,63 @@ export function postConditionToWire(postcondition: PostCondition): PostCondition
70
77
}
71
78
}
72
79
80
+ export function wireToPostCondition ( wire : PostConditionWire ) : PostCondition {
81
+ switch ( wire . conditionType ) {
82
+ case PostConditionType . STX :
83
+ return {
84
+ type : 'stx-postcondition' ,
85
+ address : principalWireToString ( wire . principal ) ,
86
+ condition : conditionByteToType ( wire . conditionCode ) ,
87
+ amount : wire . amount . toString ( ) ,
88
+ } ;
89
+ case PostConditionType . Fungible :
90
+ return {
91
+ type : 'ft-postcondition' ,
92
+ address : principalWireToString ( wire . principal ) ,
93
+ condition : conditionByteToType ( wire . conditionCode ) ,
94
+ amount : wire . amount . toString ( ) ,
95
+ asset : assetWireToString ( wire . asset ) ,
96
+ } ;
97
+ case PostConditionType . NonFungible :
98
+ return {
99
+ type : 'nft-postcondition' ,
100
+ address : principalWireToString ( wire . principal ) ,
101
+ condition : conditionByteToType ( wire . conditionCode ) ,
102
+ asset : assetWireToString ( wire . asset ) ,
103
+ assetId : wire . assetName ,
104
+ } ;
105
+ default : {
106
+ const _exhaustiveCheck : never = wire ;
107
+ throw new Error ( `Invalid post condition type: ${ _exhaustiveCheck } ` ) ;
108
+ }
109
+ }
110
+ }
111
+
112
+ /** @internal */
113
+ export function conditionTypeToByte < T extends FungibleComparator | NonFungibleComparator > (
114
+ condition : T
115
+ ) : T extends FungibleComparator ? FungibleConditionCode : NonFungibleConditionCode {
116
+ return (
117
+ PostConditionCodeWireType as unknown as Record <
118
+ T ,
119
+ T extends FungibleComparator ? FungibleConditionCode : NonFungibleConditionCode
120
+ >
121
+ ) [ condition ] ;
122
+ }
123
+
124
+ /** @internal */
125
+ export function conditionByteToType < T extends FungibleConditionCode | NonFungibleConditionCode > (
126
+ wireType : T
127
+ ) : T extends FungibleConditionCode ? FungibleComparator : NonFungibleComparator {
128
+ return (
129
+ PostConditionCodeWireType as unknown as Record <
130
+ // numerical enums are bidirectional in TypeScript
131
+ T ,
132
+ T extends FungibleConditionCode ? FungibleComparator : NonFungibleComparator
133
+ >
134
+ ) [ wireType ] ;
135
+ }
136
+
73
137
/**
74
138
* Convert a post condition to a hex string
75
139
* @param postcondition - The post condition object to convert
@@ -102,3 +166,26 @@ export function postConditionModeFrom(
102
166
if ( mode === 'deny' ) return PostConditionMode . Deny ;
103
167
throw new Error ( `Invalid post condition mode: ${ mode } ` ) ;
104
168
}
169
+
170
+ /** @internal */
171
+ function assetWireToString ( asset : AssetWire ) : AssetString {
172
+ const address = addressToString ( asset . address ) ;
173
+ const contractId = `${ address } .${ asset . contractName . content } ` as const ;
174
+ return `${ contractId } ::${ asset . assetName . content } ` ;
175
+ }
176
+
177
+ /** @internal */
178
+ function principalWireToString ( principal : PostConditionPrincipalWire ) : string {
179
+ switch ( principal . prefix ) {
180
+ case PostConditionPrincipalId . Origin :
181
+ return 'origin' ;
182
+ case PostConditionPrincipalId . Standard :
183
+ return addressToString ( principal . address ) ;
184
+ case PostConditionPrincipalId . Contract :
185
+ const address = addressToString ( principal . address ) ;
186
+ return `${ address } .${ principal . contractName . content } ` ;
187
+ default :
188
+ const _exhaustiveCheck : never = principal ;
189
+ throw new Error ( `Invalid principal type: ${ _exhaustiveCheck } ` ) ;
190
+ }
191
+ }
0 commit comments