11package main
22
33import (
4+ "fmt"
5+ "strconv"
6+ "strings"
7+
48 "github.com/urfave/cli/v2"
59
10+ "github.com/gitploy-io/gitploy/model/extent"
611 "github.com/gitploy-io/gitploy/pkg/api"
712)
813
@@ -26,6 +31,11 @@ var deploymentCreateCommand = &cli.Command{
2631 Usage : "The specific ref. It can be any named branch, tag, or SHA." ,
2732 Required : true ,
2833 },
34+ & cli.StringSliceFlag {
35+ Name : "field" ,
36+ Aliases : []string {"f" },
37+ Usage : "The pair of key and value to add to the payload. The format must be <key>=<value>." ,
38+ },
2939 },
3040 Action : func (cli * cli.Context ) error {
3141 ns , n , err := splitFullName (cli .Args ().First ())
@@ -34,10 +44,26 @@ var deploymentCreateCommand = &cli.Command{
3444 }
3545
3646 c := buildClient (cli )
47+
48+ config , err := c .Config .Get (cli .Context , ns , n )
49+ if err != nil {
50+ return err
51+ }
52+
53+ // If the 'dynamic_payload' field is enabled,
54+ // it creates a payload and pass it as a parameter.
55+ var payload map [string ]interface {}
56+ if env := config .GetEnv (cli .String ("env" )); env .IsDynamicPayloadEnabled () {
57+ if payload , err = buildDyanmicPayload (cli .StringSlice ("field" ), env ); err != nil {
58+ return err
59+ }
60+ }
61+
3762 d , err := c .Deployment .Create (cli .Context , ns , n , & api.DeploymentCreateRequest {
38- Type : cli .String ("type" ),
39- Ref : cli .String ("ref" ),
40- Env : cli .String ("env" ),
63+ Type : cli .String ("type" ),
64+ Ref : cli .String ("ref" ),
65+ Env : cli .String ("env" ),
66+ DynamicPayload : payload ,
4167 })
4268 if err != nil {
4369 return err
@@ -46,3 +72,78 @@ var deploymentCreateCommand = &cli.Command{
4672 return printJson (cli , d )
4773 },
4874}
75+
76+ func buildDyanmicPayload (fields []string , env * extent.Env ) (map [string ]interface {}, error ) {
77+ values := make (map [string ]string )
78+
79+ for _ , f := range fields {
80+ keyAndValue := strings .SplitN (f , "=" , 2 )
81+ if len (keyAndValue ) != 2 {
82+ return nil , fmt .Errorf ("The field must be <key>=<value> format" )
83+ }
84+
85+ values [keyAndValue [0 ]] = keyAndValue [1 ]
86+ }
87+
88+ payload := make (map [string ]interface {})
89+
90+ // Build the payload, and use the default value if there is no value.
91+ for key , input := range env .DynamicPayload .Inputs {
92+ val , ok := values [key ]
93+ // Set the default value if the value doesn't exist.
94+ if ! ok {
95+ if input .Default != nil {
96+ payload [key ] = * input .Default
97+ }
98+
99+ continue
100+ }
101+
102+ parsed , err := parseValue (input , val )
103+ if err != nil {
104+ return nil , fmt .Errorf ("The value of the '%s' field is not %s" , key , input .Type )
105+ }
106+
107+ payload [key ] = parsed
108+ }
109+
110+ // Check that the required values are present.
111+ for key , input := range env .DynamicPayload .Inputs {
112+ if ! (input .Required != nil && * input .Required ) {
113+ continue
114+ }
115+
116+ if _ , ok := payload [key ]; ! ok {
117+ return nil , fmt .Errorf ("The value of the '%s' field is required" , key )
118+ }
119+ }
120+
121+ return payload , nil
122+ }
123+
124+ func parseValue (input extent.Input , s string ) (interface {}, error ) {
125+ switch input .Type {
126+ case extent .InputTypeSelect :
127+ return s , nil
128+
129+ case extent .InputTypeString :
130+ return s , nil
131+
132+ case extent .InputTypeNumber :
133+ if val , err := strconv .ParseFloat (s , 64 ); err != nil {
134+ return nil , err
135+ } else {
136+ return val , nil
137+ }
138+
139+ case extent .InputTypeBoolean :
140+ if val , err := strconv .ParseBool (s ); err != nil {
141+ return nil , err
142+ } else {
143+ return val , nil
144+ }
145+
146+ default :
147+ return nil , fmt .Errorf ("%s is unsupported type." , input .Type )
148+ }
149+ }
0 commit comments