github.com/fastly/cli@v1.7.2-0.20240304164155-9d0f1d77c3bf/pkg/commands/vcl/snippet/create.go (about) 1 package snippet 2 3 import ( 4 "io" 5 6 "github.com/fastly/go-fastly/v9/fastly" 7 8 "github.com/fastly/cli/pkg/argparser" 9 "github.com/fastly/cli/pkg/errors" 10 "github.com/fastly/cli/pkg/global" 11 "github.com/fastly/cli/pkg/text" 12 ) 13 14 // Locations is a list of VCL subroutines. 15 var Locations = []string{"init", "recv", "hash", "hit", "miss", "pass", "fetch", "error", "deliver", "log", "none"} 16 17 // NewCreateCommand returns a usable command registered under the parent. 18 func NewCreateCommand(parent argparser.Registerer, g *global.Data) *CreateCommand { 19 c := CreateCommand{ 20 Base: argparser.Base{ 21 Globals: g, 22 }, 23 } 24 c.CmdClause = parent.Command("create", "Create a snippet for a particular service and version").Alias("add") 25 26 // Required. 27 c.RegisterFlag(argparser.StringFlagOpts{ 28 Name: argparser.FlagVersionName, 29 Description: argparser.FlagVersionDesc, 30 Dst: &c.serviceVersion.Value, 31 Required: true, 32 }) 33 34 // Optional. 35 c.RegisterAutoCloneFlag(argparser.AutoCloneFlagOpts{ 36 Action: c.autoClone.Set, 37 Dst: &c.autoClone.Value, 38 }) 39 c.CmdClause.Flag("content", "VCL snippet passed as file path or content, e.g. $(< snippet.vcl)").Action(c.content.Set).StringVar(&c.content.Value) 40 c.CmdClause.Flag("dynamic", "Whether the VCL snippet is dynamic or versioned").Action(c.dynamic.Set).BoolVar(&c.dynamic.Value) 41 c.CmdClause.Flag("name", "The name of the VCL snippet").Action(c.name.Set).StringVar(&c.name.Value) 42 c.CmdClause.Flag("priority", "Priority determines execution order. Lower numbers execute first").Short('p').Action(c.priority.Set).IntVar(&c.priority.Value) 43 44 c.RegisterFlag(argparser.StringFlagOpts{ 45 Name: argparser.FlagServiceIDName, 46 Description: argparser.FlagServiceIDDesc, 47 Dst: &g.Manifest.Flag.ServiceID, 48 Short: 's', 49 }) 50 c.RegisterFlag(argparser.StringFlagOpts{ 51 Action: c.serviceName.Set, 52 Name: argparser.FlagServiceName, 53 Description: argparser.FlagServiceDesc, 54 Dst: &c.serviceName.Value, 55 }) 56 c.CmdClause.Flag("type", "The location in generated VCL where the snippet should be placed").Action(c.location.Set).HintOptions(Locations...).EnumVar(&c.location.Value, Locations...) 57 58 return &c 59 } 60 61 // CreateCommand calls the Fastly API to create an appropriate resource. 62 type CreateCommand struct { 63 argparser.Base 64 65 autoClone argparser.OptionalAutoClone 66 content argparser.OptionalString 67 dynamic argparser.OptionalBool 68 location argparser.OptionalString 69 name argparser.OptionalString 70 priority argparser.OptionalInt 71 serviceName argparser.OptionalServiceNameID 72 serviceVersion argparser.OptionalServiceVersion 73 } 74 75 // Exec invokes the application logic for the command. 76 func (c *CreateCommand) Exec(_ io.Reader, out io.Writer) error { 77 serviceID, serviceVersion, err := argparser.ServiceDetails(argparser.ServiceDetailsOpts{ 78 AutoCloneFlag: c.autoClone, 79 APIClient: c.Globals.APIClient, 80 Manifest: *c.Globals.Manifest, 81 Out: out, 82 ServiceNameFlag: c.serviceName, 83 ServiceVersionFlag: c.serviceVersion, 84 VerboseMode: c.Globals.Flags.Verbose, 85 }) 86 if err != nil { 87 c.Globals.ErrLog.AddWithContext(err, map[string]any{ 88 "Service ID": serviceID, 89 "Service Version": errors.ServiceVersion(serviceVersion), 90 }) 91 return err 92 } 93 94 input := c.constructInput(serviceID, fastly.ToValue(serviceVersion.Number)) 95 96 v, err := c.Globals.APIClient.CreateSnippet(input) 97 if err != nil { 98 c.Globals.ErrLog.AddWithContext(err, map[string]any{ 99 "Service ID": serviceID, 100 "Service Version": fastly.ToValue(serviceVersion.Number), 101 }) 102 return err 103 } 104 105 text.Success(out, 106 "Created VCL snippet '%s' (service: %s, version: %d, dynamic: %t, snippet id: %s, type: %s, priority: %d)", 107 fastly.ToValue(v.Name), 108 fastly.ToValue(v.ServiceID), 109 fastly.ToValue(v.ServiceVersion), 110 c.dynamic.WasSet, 111 fastly.ToValue(v.SnippetID), 112 c.location.Value, 113 fastly.ToValue(v.Priority), 114 ) 115 return nil 116 } 117 118 // constructInput transforms values parsed from CLI flags into an object to be used by the API client library. 119 func (c *CreateCommand) constructInput(serviceID string, serviceVersion int) *fastly.CreateSnippetInput { 120 input := fastly.CreateSnippetInput{ 121 Dynamic: fastly.ToPointer(0), 122 ServiceID: serviceID, 123 ServiceVersion: serviceVersion, 124 } 125 if c.name.WasSet { 126 input.Name = &c.name.Value 127 } 128 if c.content.WasSet { 129 input.Content = fastly.ToPointer(argparser.Content(c.content.Value)) 130 } 131 if c.location.WasSet { 132 sType := fastly.SnippetType(c.location.Value) 133 input.Type = &sType 134 } 135 if c.dynamic.WasSet { 136 input.Dynamic = fastly.ToPointer(1) 137 } 138 if c.priority.WasSet { 139 input.Priority = &c.priority.Value 140 } 141 142 return &input 143 }