1// Copyright © 2015 Steve Francia <spf@spf13.com>. 2// 3// Licensed under the Apache License, Version 2.0 (the "License"); 4// you may not use this file except in compliance with the License. 5// You may obtain a copy of the License at 6// http://www.apache.org/licenses/LICENSE-2.0 7// 8// Unless required by applicable law or agreed to in writing, software 9// distributed under the License is distributed on an "AS IS" BASIS, 10// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 11// See the License for the specific language governing permissions and 12// limitations under the License. 13 14package cmd 15 16import ( 17 "fmt" 18 "os" 19 "unicode" 20 21 "github.com/spf13/cobra" 22) 23 24var ( 25 packageName string 26 parentName string 27 28 addCmd = &cobra.Command{ 29 Use: "add [command name]", 30 Aliases: []string{"command"}, 31 Short: "Add a command to a Cobra Application", 32 Long: `Add (cobra add) will create a new command, with a license and 33the appropriate structure for a Cobra-based CLI application, 34and register it to its parent (default rootCmd). 35 36If you want your command to be public, pass in the command name 37with an initial uppercase letter. 38 39Example: cobra add server -> resulting in a new cmd/server.go`, 40 41 Run: func(cmd *cobra.Command, args []string) { 42 if len(args) < 1 { 43 cobra.CheckErr(fmt.Errorf("add needs a name for the command")) 44 } 45 46 wd, err := os.Getwd() 47 cobra.CheckErr(err) 48 49 commandName := validateCmdName(args[0]) 50 command := &Command{ 51 CmdName: commandName, 52 CmdParent: parentName, 53 Project: &Project{ 54 AbsolutePath: wd, 55 Legal: getLicense(), 56 Copyright: copyrightLine(), 57 }, 58 } 59 60 cobra.CheckErr(command.Create()) 61 62 fmt.Printf("%s created at %s\n", command.CmdName, command.AbsolutePath) 63 }, 64 } 65) 66 67func init() { 68 addCmd.Flags().StringVarP(&packageName, "package", "t", "", "target package name (e.g. github.com/spf13/hugo)") 69 addCmd.Flags().StringVarP(&parentName, "parent", "p", "rootCmd", "variable name of parent command for this command") 70 cobra.CheckErr(addCmd.Flags().MarkDeprecated("package", "this operation has been removed.")) 71} 72 73// validateCmdName returns source without any dashes and underscore. 74// If there will be dash or underscore, next letter will be uppered. 75// It supports only ASCII (1-byte character) strings. 76// https://github.com/spf13/cobra/issues/269 77func validateCmdName(source string) string { 78 i := 0 79 l := len(source) 80 // The output is initialized on demand, then first dash or underscore 81 // occurs. 82 var output string 83 84 for i < l { 85 if source[i] == '-' || source[i] == '_' { 86 if output == "" { 87 output = source[:i] 88 } 89 90 // If it's last rune and it's dash or underscore, 91 // don't add it output and break the loop. 92 if i == l-1 { 93 break 94 } 95 96 // If next character is dash or underscore, 97 // just skip the current character. 98 if source[i+1] == '-' || source[i+1] == '_' { 99 i++ 100 continue 101 } 102 103 // If the current character is dash or underscore, 104 // upper next letter and add to output. 105 output += string(unicode.ToUpper(rune(source[i+1]))) 106 // We know, what source[i] is dash or underscore and source[i+1] is 107 // uppered character, so make i = i+2. 108 i += 2 109 continue 110 } 111 112 // If the current character isn't dash or underscore, 113 // just add it. 114 if output != "" { 115 output += string(source[i]) 116 } 117 i++ 118 } 119 120 if output == "" { 121 return source // source is initially valid name. 122 } 123 return output 124} 125