diff --git a/cobra/cmd/helpers.go b/cobra/cmd/helpers.go index e5b37ec7..cd94b3e3 100644 --- a/cobra/cmd/helpers.go +++ b/cobra/cmd/helpers.go @@ -24,7 +24,6 @@ import ( "text/template" ) -var cmdDirs = [...]string{"cmd", "cmds", "command", "commands"} var srcPaths []string func init() { @@ -128,8 +127,6 @@ func writeStringToFile(path string, s string) error { // writeToFile writes r to file with path only // if file/directory on given path doesn't exist. -// If file/directory exists on given path, then -// it terminates app and prints an appropriate error. func writeToFile(path string, r io.Reader) error { if exists(path) { return fmt.Errorf("%v already exists", path) diff --git a/cobra/cmd/project.go b/cobra/cmd/project.go index de1168a1..7ddb8258 100644 --- a/cobra/cmd/project.go +++ b/cobra/cmd/project.go @@ -17,10 +17,9 @@ type Project struct { } // NewProject returns Project with specified project name. -// If projectName is blank string, it returns nil. func NewProject(projectName string) *Project { if projectName == "" { - return nil + er("can't create project with blank name") } p := new(Project) @@ -54,8 +53,6 @@ func NewProject(projectName string) *Project { } // findPackage returns full path to existing go package in GOPATHs. -// findPackage returns "", if it can't find path. -// If packageName is "", findPackage returns "". func findPackage(packageName string) string { if packageName == "" { return "" @@ -73,16 +70,29 @@ func findPackage(packageName string) string { // NewProjectFromPath returns Project with specified absolute path to // package. -// If absPath is blank string or if absPath is not actually absolute, -// it returns nil. func NewProjectFromPath(absPath string) *Project { - if absPath == "" || !filepath.IsAbs(absPath) { - return nil + if absPath == "" { + er("can't create project: absPath can't be blank") + } + if !filepath.IsAbs(absPath) { + er("can't create project: absPath is not absolute") + } + + // If absPath is symlink, use its destination. + fi, err := os.Lstat(absPath) + if err != nil { + er("can't read path info: " + err.Error()) + } + if fi.Mode()&os.ModeSymlink != 0 { + path, err := os.Readlink(absPath) + if err != nil { + er("can't read the destination of symlink: " + err.Error()) + } + absPath = path } p := new(Project) - p.absPath = absPath - p.absPath = strings.TrimSuffix(p.absPath, findCmdDir(p.absPath)) + p.absPath = strings.TrimSuffix(absPath, findCmdDir(absPath)) p.name = filepath.ToSlash(trimSrcPath(p.absPath, p.SrcPath())) return p } @@ -91,7 +101,7 @@ func NewProjectFromPath(absPath string) *Project { func trimSrcPath(absPath, srcPath string) string { relPath, err := filepath.Rel(srcPath, absPath) if err != nil { - er("Cobra supports project only within $GOPATH: " + err.Error()) + er(err) } return relPath } @@ -101,7 +111,6 @@ func (p *Project) License() License { if p.license.Text == "" && p.license.Name != "None" { p.license = getLicense() } - return p.license } @@ -111,8 +120,6 @@ func (p Project) Name() string { } // CmdPath returns absolute path to directory, where all commands are located. -// -// CmdPath returns blank string, only if p.AbsPath() is a blank string. func (p *Project) CmdPath() string { if p.absPath == "" { return "" @@ -125,8 +132,6 @@ func (p *Project) CmdPath() string { // findCmdDir checks if base of absPath is cmd dir and returns it or // looks for existing cmd dir in absPath. -// If the cmd dir doesn't exist, empty, or cannot be found, -// it returns "cmd". func findCmdDir(absPath string) string { if !exists(absPath) || isEmpty(absPath) { return "cmd" @@ -149,7 +154,7 @@ func findCmdDir(absPath string) string { // isCmdDir checks if base of name is one of cmdDir. func isCmdDir(name string) bool { name = filepath.Base(name) - for _, cmdDir := range cmdDirs { + for _, cmdDir := range []string{"cmd", "cmds", "command", "commands"} { if name == cmdDir { return true }