Skip to content

Commit 515289b

Browse files
committed
launchpad callback
1 parent 8d33d0b commit 515289b

File tree

2 files changed

+132
-6
lines changed

2 files changed

+132
-6
lines changed

contract/p/gnoswap/launchpad/info_type.gno

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,8 @@ func (r *RefundInfo) JSON(b *json.NodeBuilder) *json.NodeBuilder {
6262

6363
// region: Condition
6464

65+
type tokenConditionMap map[string]Condition
66+
6567
type Condition struct {
6668
tokenPath string
6769
minAmount uint64

contract/p/gnoswap/launchpad/launchpad.gno

Lines changed: 130 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,10 +3,18 @@ package launchpad
33
import (
44
"errors"
55
"std"
6+
"strconv"
7+
"strings"
68

79
"gno.land/p/demo/ufmt"
810
)
911

12+
var (
13+
errEmptyTokenPath = errors.New("token path cannot be empty")
14+
errInvalidAddress = errors.New("invalid address")
15+
errZeroDepositAmount = errors.New("deposit amount cannot be 0")
16+
)
17+
1018
// region: projectInput
1119

1220
// ProjectInput defines the input parameters required to create a project.
@@ -87,8 +95,37 @@ func NewProjectInput(
8795
}
8896
}
8997

90-
// CheckName checks if the project name is valid.
91-
func (p *projectInput) CheckName() error {
98+
// CheckAll checks all the project input fields.
99+
// need to pass `IsRegistered` function as a callback parameter to check if the token is registered.
100+
func (p *projectInput) CheckAll(now uint64, f func(string) error) (tokenConditionMap, error) {
101+
if err := p.checkName(); err != nil {
102+
return nil, err
103+
}
104+
if err := p.checkTokenPath(f); err != nil {
105+
return nil, err
106+
}
107+
if err := p.checkRecipient(); err != nil {
108+
return nil, err
109+
}
110+
if err := p.checkDepositAmount(); err != nil {
111+
return nil, err
112+
}
113+
if err := p.checkRatio(); err != nil {
114+
return nil, err
115+
}
116+
if err := p.checkStartTime(now); err != nil {
117+
return nil, err
118+
}
119+
120+
conds, err := p.parseConditions(f)
121+
if err != nil {
122+
return nil, err
123+
}
124+
return conds, nil
125+
}
126+
127+
// checkName checks if the project name is valid.
128+
func (p *projectInput) checkName() error {
92129
if p.name == "" {
93130
return errors.New("project name cannot be empty")
94131
}
@@ -98,8 +135,8 @@ func (p *projectInput) CheckName() error {
98135
return nil
99136
}
100137

101-
// VerifyRatio checks if the sum of the tier ratios equals 100.
102-
func (p *projectInput) VerifyRatio() error {
138+
// checkRatio checks if the sum of the tier ratios equals 100.
139+
func (p *projectInput) checkRatio() error {
103140
if p.tierSum() != 100 {
104141
return ufmt.Errorf(
105142
"invalid ratio, sum of all tiers(30:%d, 90:%d, 180:%d) should be 100",
@@ -113,14 +150,101 @@ func (p *projectInput) tierSum() uint64 {
113150
return p.Tier30Ratio() + p.Tier90Ratio() + p.Tier180Ratio()
114151
}
115152

116-
// ValidateStartTime checks if the start time is in the future.
117-
func (p *projectInput) ValidateStartTime(now uint64) error {
153+
// checkStartTime checks if the start time is in the future.
154+
func (p *projectInput) checkStartTime(now uint64) error {
118155
if p.startTime <= now {
119156
return errors.New("start time must be greater than now")
120157
}
121158
return nil
122159
}
123160

161+
func (p *projectInput) checkTokenPath(f func(string) error) error {
162+
path := p.TokenPath()
163+
if path == "" {
164+
return errEmptyTokenPath
165+
}
166+
if err := f(path); err != nil {
167+
return err
168+
}
169+
return nil
170+
}
171+
172+
func (p *projectInput) checkRecipient() error {
173+
if !p.Recipient().IsValid() {
174+
return errInvalidAddress
175+
}
176+
return nil
177+
}
178+
179+
func (p *projectInput) checkDepositAmount() error {
180+
if p.DepositAmount() == 0 {
181+
return errZeroDepositAmount
182+
}
183+
return nil
184+
}
185+
186+
// ParseConditions parses the conditions from `ConditionsToken` and `ConditionsAmount`.
187+
//
188+
// Splits the token and amount strings using `*PAD*`, validates each token path, and converts
189+
// the amounts to integers. Returns a map of token paths to their corresponding conditions.
190+
func (p *projectInput) parseConditions(f func(string) error) (tokenConditionMap, error) {
191+
if p.ConditionsToken() == "" || p.ConditionsAmount() == "" {
192+
return nil, nil
193+
}
194+
195+
return parseConditions(p.ConditionsToken(), p.ConditionsAmount(), f)
196+
}
197+
198+
func parseConditions(condToken, condAmount string, f func(string) error) (tokenConditionMap, error) {
199+
tokens, amounts, err := trySplitConditions(condToken, condAmount)
200+
if err != nil {
201+
return nil, err
202+
}
203+
204+
return buildTokenConditions(tokens, amounts, f)
205+
}
206+
207+
func trySplitConditions(tokenStr, amountStr string) (tokens, amounts []string, err error) {
208+
if tokenStr == "" || amountStr == "" {
209+
return nil, nil, errors.New("conditionsToken or conditionsAmount cannot be empty")
210+
}
211+
212+
tokens = strings.Split(tokenStr, PAD_SEP)
213+
amounts = strings.Split(amountStr, PAD_SEP)
214+
if len(tokens) != len(amounts) {
215+
return nil, nil, ufmt.Errorf("length of tokens(%d) and amounts(%d) are not same", len(tokens), len(amounts))
216+
}
217+
218+
return tokens, amounts, nil
219+
}
220+
221+
func buildTokenConditions(tokens, amounts []string, f func(string) error) (tokenConditionMap, error) {
222+
condition := make(tokenConditionMap)
223+
224+
for i, tok := range tokens {
225+
if tok == "" {
226+
return nil, ufmt.Errorf("invalid token(%s)", tok)
227+
}
228+
if err := f(tok); err != nil {
229+
return nil, ufmt.Errorf("token(%s) not registered", tok)
230+
}
231+
if _, exists := condition[tok]; exists {
232+
return nil, ufmt.Errorf("duplicated condition token(%s)", tok)
233+
}
234+
235+
amtv, err := strconv.ParseUint(amounts[i], 10, 64)
236+
if err != nil {
237+
return nil, ufmt.Errorf("invalid amount(%s)", amounts[i])
238+
}
239+
240+
condition[tok] = Condition{
241+
tokenPath: tok,
242+
minAmount: amtv,
243+
}
244+
}
245+
return condition, nil
246+
}
247+
124248
// region: ProjectCalculationResult
125249

126250
// ProjectCalculationResult middle result of project params calculation

0 commit comments

Comments
 (0)