forked from toolshed/abra
		
	Compare commits
	
		
			22 Commits
		
	
	
		
			0.1.4-alph
			...
			0.1.5-alph
		
	
	| Author | SHA1 | Date | |
|---|---|---|---|
| 09f49cdc76 | |||
| 22118b88e4 | |||
| e6db064149 | |||
| 3688ea9d69 | |||
| 7c4cdc530c | |||
| 49781c7e3f | |||
| 10b15d65b4 | |||
| 1c5d6d6357 | |||
| 75bdd59585 | |||
| 96bb145981 | |||
| c4c76f4848 | |||
| 2076c566bb | |||
| 62f6327b66 | |||
| 6f9120b59c | |||
| 8c617a9f12 | |||
| 857d12d23c | |||
| 22c4d0d864 | |||
| e700e44363 | |||
| 9faefd2592 | |||
| cd179175f5 | |||
| c0f92ca13d | |||
| 48d28c8dd1 | 
| @ -9,6 +9,7 @@ import ( | |||||||
| 	"coopcloud.tech/abra/cli/catalogue" | 	"coopcloud.tech/abra/cli/catalogue" | ||||||
| 	"coopcloud.tech/abra/cli/recipe" | 	"coopcloud.tech/abra/cli/recipe" | ||||||
| 	"coopcloud.tech/abra/cli/server" | 	"coopcloud.tech/abra/cli/server" | ||||||
|  | 	logrusStack "github.com/Gurpartap/logrus-stack" | ||||||
| 	"github.com/sirupsen/logrus" | 	"github.com/sirupsen/logrus" | ||||||
| 	"github.com/urfave/cli/v2" | 	"github.com/urfave/cli/v2" | ||||||
| ) | ) | ||||||
| @ -76,6 +77,9 @@ func RunApp(version, commit string) { | |||||||
| 	app.Before = func(c *cli.Context) error { | 	app.Before = func(c *cli.Context) error { | ||||||
| 		if Debug { | 		if Debug { | ||||||
| 			logrus.SetLevel(logrus.DebugLevel) | 			logrus.SetLevel(logrus.DebugLevel) | ||||||
|  | 			logrus.SetFormatter(&logrus.TextFormatter{}) | ||||||
|  | 			logrus.SetOutput(os.Stderr) | ||||||
|  | 			logrus.AddHook(logrusStack.StandardHook()) | ||||||
| 		} | 		} | ||||||
| 		return nil | 		return nil | ||||||
| 	} | 	} | ||||||
|  | |||||||
| @ -18,6 +18,7 @@ Cloud community and you can use Abra to read them and create apps for you. | |||||||
| 	Subcommands: []*cli.Command{ | 	Subcommands: []*cli.Command{ | ||||||
| 		recipeListCommand, | 		recipeListCommand, | ||||||
| 		recipeVersionCommand, | 		recipeVersionCommand, | ||||||
|  | 		recipeReleaseCommand, | ||||||
| 		recipeNewCommand, | 		recipeNewCommand, | ||||||
| 		recipeUpgradeCommand, | 		recipeUpgradeCommand, | ||||||
| 		recipeSyncCommand, | 		recipeSyncCommand, | ||||||
|  | |||||||
							
								
								
									
										302
									
								
								cli/recipe/release.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										302
									
								
								cli/recipe/release.go
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,302 @@ | |||||||
|  | package recipe | ||||||
|  |  | ||||||
|  | import ( | ||||||
|  | 	"fmt" | ||||||
|  | 	"path" | ||||||
|  | 	"strconv" | ||||||
|  | 	"strings" | ||||||
|  |  | ||||||
|  | 	"coopcloud.tech/abra/cli/internal" | ||||||
|  | 	"coopcloud.tech/abra/pkg/config" | ||||||
|  | 	"coopcloud.tech/abra/pkg/recipe" | ||||||
|  | 	"coopcloud.tech/tagcmp" | ||||||
|  | 	"github.com/AlecAivazis/survey/v2" | ||||||
|  | 	"github.com/go-git/go-git/v5" | ||||||
|  | 	"github.com/go-git/go-git/v5/plumbing" | ||||||
|  | 	"github.com/go-git/go-git/v5/plumbing/object" | ||||||
|  | 	"github.com/sirupsen/logrus" | ||||||
|  | 	"github.com/urfave/cli/v2" | ||||||
|  | ) | ||||||
|  |  | ||||||
|  | var Push bool | ||||||
|  | var PushFlag = &cli.BoolFlag{ | ||||||
|  | 	Name:        "push", | ||||||
|  | 	Value:       false, | ||||||
|  | 	Destination: &Push, | ||||||
|  | } | ||||||
|  |  | ||||||
|  | var Dry bool | ||||||
|  | var DryFlag = &cli.BoolFlag{ | ||||||
|  | 	Name:        "dry-run", | ||||||
|  | 	Value:       false, | ||||||
|  | 	Aliases:     []string{"d"}, | ||||||
|  | 	Destination: &Dry, | ||||||
|  | } | ||||||
|  |  | ||||||
|  | var Major bool | ||||||
|  | var MajorFlag = &cli.BoolFlag{ | ||||||
|  | 	Name:        "major", | ||||||
|  | 	Value:       false, | ||||||
|  | 	Aliases:     []string{"ma", "x"}, | ||||||
|  | 	Destination: &Major, | ||||||
|  | } | ||||||
|  |  | ||||||
|  | var Minor bool | ||||||
|  | var MinorFlag = &cli.BoolFlag{ | ||||||
|  | 	Name:        "minor", | ||||||
|  | 	Value:       false, | ||||||
|  | 	Aliases:     []string{"mi", "y"}, | ||||||
|  | 	Destination: &Minor, | ||||||
|  | } | ||||||
|  |  | ||||||
|  | var Patch bool | ||||||
|  | var PatchFlag = &cli.BoolFlag{ | ||||||
|  | 	Name:        "patch", | ||||||
|  | 	Value:       false, | ||||||
|  | 	Aliases:     []string{"p", "z"}, | ||||||
|  | 	Destination: &Patch, | ||||||
|  | } | ||||||
|  |  | ||||||
|  | var CommitMessage string | ||||||
|  | var CommitMessageFlag = &cli.StringFlag{ | ||||||
|  | 	Name:        "commit-message", | ||||||
|  | 	Usage:       "commit message", | ||||||
|  | 	Aliases:     []string{"cm"}, | ||||||
|  | 	Destination: &CommitMessage, | ||||||
|  | } | ||||||
|  |  | ||||||
|  | var Commit bool | ||||||
|  | var CommitFlag = &cli.BoolFlag{ | ||||||
|  | 	Name:        "commit", | ||||||
|  | 	Value:       false, | ||||||
|  | 	Aliases:     []string{"c"}, | ||||||
|  | 	Destination: &Commit, | ||||||
|  | } | ||||||
|  |  | ||||||
|  | var recipeReleaseCommand = &cli.Command{ | ||||||
|  | 	Name:      "release", | ||||||
|  | 	Usage:     "tag a recipe", | ||||||
|  | 	Aliases:   []string{"rl"}, | ||||||
|  | 	ArgsUsage: "<recipe> [<tag>]", | ||||||
|  | 	Description: ` | ||||||
|  | This command is used to specify a new tag for a recipe. These tags are used to | ||||||
|  | identify different versions of the recipe and are published on the Co-op Cloud | ||||||
|  | recipe catalogue. | ||||||
|  |  | ||||||
|  | These tags take the following form: | ||||||
|  |  | ||||||
|  |     a.b.c+x.y.z | ||||||
|  |  | ||||||
|  | Where the "a.b.c" part is maintained as a semantic version of the recipe by the | ||||||
|  | recipe maintainer. And the "x.y.z" part is the image tag of the recipe "app" | ||||||
|  | service (the main container which contains the software to be used). | ||||||
|  |  | ||||||
|  | We maintain a semantic versioning scheme ("a.b.c") alongside the libre app | ||||||
|  | versioning scheme in order to maximise the chances that the nature of recipe | ||||||
|  | updates are properly communicated. | ||||||
|  |  | ||||||
|  | Abra does its best to read the "a.b.c" version scheme and communicate what | ||||||
|  | action needs to be taken when performing different operations such as an update | ||||||
|  | or a rollback of an app. | ||||||
|  | `, | ||||||
|  | 	Flags: []cli.Flag{ | ||||||
|  | 		DryFlag, | ||||||
|  | 		PatchFlag, | ||||||
|  | 		MinorFlag, | ||||||
|  | 		MajorFlag, | ||||||
|  | 		PushFlag, | ||||||
|  | 		CommitFlag, | ||||||
|  | 		CommitMessageFlag, | ||||||
|  | 	}, | ||||||
|  | 	Action: func(c *cli.Context) error { | ||||||
|  | 		recipe := internal.ValidateRecipe(c) | ||||||
|  | 		directory := path.Join(config.APPS_DIR, recipe.Name) | ||||||
|  | 		tagstring := c.Args().Get(1) | ||||||
|  | 		imagesTmp := getImageVersions(recipe) | ||||||
|  | 		mainApp := getMainApp(recipe) | ||||||
|  | 		mainAppVersion := imagesTmp[mainApp] | ||||||
|  | 		if mainAppVersion == "" { | ||||||
|  | 			logrus.Fatal("main app version is empty?") | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		if tagstring != "" { | ||||||
|  | 			_, err := tagcmp.Parse(tagstring) | ||||||
|  | 			if err != nil { | ||||||
|  | 				logrus.Fatal("invalid tag specified") | ||||||
|  | 			} | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		if Commit || (CommitMessage != "") { | ||||||
|  | 			commitRepo, err := git.PlainOpen(directory) | ||||||
|  | 			if err != nil { | ||||||
|  | 				logrus.Fatal(err) | ||||||
|  | 			} | ||||||
|  | 			commitWorktree, err := commitRepo.Worktree() | ||||||
|  | 			if err != nil { | ||||||
|  | 				logrus.Fatal(err) | ||||||
|  | 			} | ||||||
|  |  | ||||||
|  | 			if CommitMessage == "" { | ||||||
|  | 				prompt := &survey.Input{ | ||||||
|  | 					Message: "commit message", | ||||||
|  | 				} | ||||||
|  | 				survey.AskOne(prompt, &CommitMessage) | ||||||
|  | 			} | ||||||
|  | 			_, err = commitWorktree.Commit(CommitMessage, &git.CommitOptions{}) | ||||||
|  | 			if err != nil { | ||||||
|  | 				logrus.Fatal(err) | ||||||
|  | 			} | ||||||
|  | 			logrus.Info("changes commited") | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		repo, err := git.PlainOpen(directory) | ||||||
|  | 		if err != nil { | ||||||
|  | 			logrus.Fatal(err) | ||||||
|  | 		} | ||||||
|  | 		head, err := repo.Head() | ||||||
|  | 		if err != nil { | ||||||
|  | 			logrus.Fatal(err) | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		// bumpType is used to decide what part of the tag should be incremented | ||||||
|  | 		bumpType := btoi(Major)*4 + btoi(Minor)*2 + btoi(Patch) | ||||||
|  | 		if bumpType != 0 { | ||||||
|  | 			// a bitwise check if the number is a power of 2 | ||||||
|  | 			if (bumpType & (bumpType - 1)) != 0 { | ||||||
|  | 				logrus.Fatal("you can only use one of: --major, --minor, --patch.") | ||||||
|  | 			} | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		if tagstring != "" { | ||||||
|  | 			if bumpType > 0 { | ||||||
|  | 				logrus.Warn("user specified a version number and --major/--minor/--patch at the same time! using version number...") | ||||||
|  | 			} | ||||||
|  | 			tag, err := tagcmp.Parse(tagstring) | ||||||
|  | 			if err != nil { | ||||||
|  | 				logrus.Fatal(err) | ||||||
|  | 			} | ||||||
|  | 			if tag.MissingMinor { | ||||||
|  | 				tag.Minor = "0" | ||||||
|  | 				tag.MissingMinor = false | ||||||
|  | 			} | ||||||
|  | 			if tag.MissingPatch { | ||||||
|  | 				tag.Patch = "0" | ||||||
|  | 				tag.MissingPatch = false | ||||||
|  | 			} | ||||||
|  | 			tagstring = fmt.Sprintf("%s+%s", tag.String(), mainAppVersion) | ||||||
|  | 			if Dry { | ||||||
|  | 				logrus.Info(fmt.Sprintf("dry run only: NOT creating tag %s at %s", tagstring, head.Hash())) | ||||||
|  | 				return nil | ||||||
|  | 			} | ||||||
|  |  | ||||||
|  | 			repo.CreateTag(tagstring, head.Hash(), nil) /* &git.CreateTagOptions{ | ||||||
|  | 				Message: tag, | ||||||
|  | 			})*/ | ||||||
|  | 			logrus.Info(fmt.Sprintf("created tag %s at %s", tagstring, head.Hash())) | ||||||
|  | 			if Push { | ||||||
|  | 				if err := repo.Push(&git.PushOptions{}); err != nil { | ||||||
|  | 					logrus.Fatal(err) | ||||||
|  | 				} | ||||||
|  | 				logrus.Info(fmt.Sprintf("pushed tag %s to remote", tagstring)) | ||||||
|  | 			} | ||||||
|  |  | ||||||
|  | 			return nil | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		// get the latest tag with its hash, name etc | ||||||
|  | 		var lastGitTag *object.Tag | ||||||
|  | 		iter, err := repo.Tags() | ||||||
|  | 		if err != nil { | ||||||
|  | 			logrus.Fatal(err) | ||||||
|  | 		} | ||||||
|  | 		if err := iter.ForEach(func(ref *plumbing.Reference) error { | ||||||
|  | 			obj, err := repo.TagObject(ref.Hash()) | ||||||
|  | 			if err == nil { | ||||||
|  | 				lastGitTag = obj | ||||||
|  | 				return nil | ||||||
|  | 			} | ||||||
|  | 			return err | ||||||
|  |  | ||||||
|  | 		}); err != nil { | ||||||
|  | 			logrus.Fatal(err) | ||||||
|  | 		} | ||||||
|  | 		newTag, err := tagcmp.Parse(lastGitTag.Name) | ||||||
|  | 		if err != nil { | ||||||
|  | 			logrus.Fatal(err) | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		var newTagString string | ||||||
|  | 		if bumpType > 0 { | ||||||
|  | 			if Patch { | ||||||
|  | 				now, err := strconv.Atoi(newTag.Patch) | ||||||
|  | 				if err != nil { | ||||||
|  | 					logrus.Fatal(err) | ||||||
|  | 				} | ||||||
|  | 				newTag.Patch = strconv.Itoa(now + 1) | ||||||
|  | 			} else if Minor { | ||||||
|  | 				now, err := strconv.Atoi(newTag.Minor) | ||||||
|  | 				if err != nil { | ||||||
|  | 					logrus.Fatal(err) | ||||||
|  | 				} | ||||||
|  | 				newTag.Minor = strconv.Itoa(now + 1) | ||||||
|  | 			} else if Major { | ||||||
|  | 				now, err := strconv.Atoi(newTag.Major) | ||||||
|  | 				if err != nil { | ||||||
|  | 					logrus.Fatal(err) | ||||||
|  | 				} | ||||||
|  | 				newTag.Major = strconv.Itoa(now + 1) | ||||||
|  | 			} | ||||||
|  | 			newTagString = newTag.String() | ||||||
|  | 		} else { | ||||||
|  | 			logrus.Fatal("we don't support automatic tag generation yet - specify a version or use one of: --major --minor --patch") | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		newTagString = fmt.Sprintf("%s+%s", newTagString, mainAppVersion) | ||||||
|  | 		if Dry { | ||||||
|  | 			logrus.Info(fmt.Sprintf("dry run only: NOT creating tag %s at %s", newTagString, head.Hash())) | ||||||
|  | 			return nil | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		repo.CreateTag(newTagString, head.Hash(), nil) /* &git.CreateTagOptions{ | ||||||
|  | 			Message: tag, | ||||||
|  | 		})*/ | ||||||
|  | 		logrus.Info(fmt.Sprintf("created tag %s at %s", newTagString, head.Hash())) | ||||||
|  | 		if Push { | ||||||
|  | 			if err := repo.Push(&git.PushOptions{}); err != nil { | ||||||
|  | 				logrus.Fatal(err) | ||||||
|  | 			} | ||||||
|  | 			logrus.Info(fmt.Sprintf("pushed tag %s to remote", newTagString)) | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		return nil | ||||||
|  |  | ||||||
|  | 	}, | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func getImageVersions(recipe recipe.Recipe) map[string]string { | ||||||
|  |  | ||||||
|  | 	var services = make(map[string]string) | ||||||
|  | 	for _, service := range recipe.Config.Services { | ||||||
|  | 		srv := strings.Split(service.Image, ":") | ||||||
|  | 		services[srv[0]] = srv[1] | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return services | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func getMainApp(recipe recipe.Recipe) string { | ||||||
|  | 	for _, service := range recipe.Config.Services { | ||||||
|  | 		name := service.Name | ||||||
|  | 		if name == "app" { | ||||||
|  | 			return strings.Split(service.Image, ":")[0] | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	return "" | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func btoi(b bool) int { | ||||||
|  | 	if b { | ||||||
|  | 		return 1 | ||||||
|  | 	} | ||||||
|  | 	return 0 | ||||||
|  | } | ||||||
| @ -40,7 +40,6 @@ This is step 1 of upgrading a recipe. Step 2 is running "abra recipe sync | |||||||
| 			if err != nil { | 			if err != nil { | ||||||
| 				logrus.Fatal(err) | 				logrus.Fatal(err) | ||||||
| 			} | 			} | ||||||
| 			logrus.Debugf("read '%s' from the recipe catalogue for '%s'", catlVersions, service.Name) |  | ||||||
|  |  | ||||||
| 			img, err := reference.ParseNormalizedNamed(service.Image) | 			img, err := reference.ParseNormalizedNamed(service.Image) | ||||||
| 			if err != nil { | 			if err != nil { | ||||||
|  | |||||||
| @ -2,15 +2,28 @@ package server | |||||||
|  |  | ||||||
| import ( | import ( | ||||||
| 	"context" | 	"context" | ||||||
|  | 	"errors" | ||||||
|  | 	"os" | ||||||
| 	"os/user" | 	"os/user" | ||||||
|  | 	"path" | ||||||
| 	"strings" | 	"strings" | ||||||
|  |  | ||||||
| 	"coopcloud.tech/abra/cli/internal" | 	"coopcloud.tech/abra/cli/internal" | ||||||
| 	"coopcloud.tech/abra/pkg/client" | 	"coopcloud.tech/abra/pkg/client" | ||||||
|  | 	"coopcloud.tech/abra/pkg/config" | ||||||
| 	"github.com/sirupsen/logrus" | 	"github.com/sirupsen/logrus" | ||||||
| 	"github.com/urfave/cli/v2" | 	"github.com/urfave/cli/v2" | ||||||
| ) | ) | ||||||
|  |  | ||||||
|  | var local bool | ||||||
|  | var localFlag = &cli.BoolFlag{ | ||||||
|  | 	Name:        "local", | ||||||
|  | 	Aliases:     []string{"L"}, | ||||||
|  | 	Value:       false, | ||||||
|  | 	Usage:       "Set up the local server", | ||||||
|  | 	Destination: &local, | ||||||
|  | } | ||||||
|  |  | ||||||
| var serverAddCommand = &cli.Command{ | var serverAddCommand = &cli.Command{ | ||||||
| 	Name:  "add", | 	Name:  "add", | ||||||
| 	Usage: "Add a new server", | 	Usage: "Add a new server", | ||||||
| @ -32,11 +45,33 @@ Abra will construct the following SSH connection string then: | |||||||
|  |  | ||||||
| All communication between Abra and the server will use this SSH connection. | All communication between Abra and the server will use this SSH connection. | ||||||
|  |  | ||||||
|  | NOTE: If you specify --local, none of the above applies 🙃 | ||||||
|  |  | ||||||
| `, | `, | ||||||
| 	Aliases: []string{"a"}, | 	Aliases: []string{"a"}, | ||||||
|  | 	Flags: []cli.Flag{ | ||||||
|  | 		localFlag, | ||||||
|  | 	}, | ||||||
| 	ArgsUsage: "<domain> [<user>] [<port>]", | 	ArgsUsage: "<domain> [<user>] [<port>]", | ||||||
| 	Action: func(c *cli.Context) error { | 	Action: func(c *cli.Context) error { | ||||||
| 		domainName := internal.ValidateDomain(c) | 		if c.Args().Len() == 1 && !local { | ||||||
|  | 			err := errors.New("missing arguments <domain> or '--local'") | ||||||
|  | 			internal.ShowSubcommandHelpAndError(c, err) | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		if c.Args().Get(1) != "" && local { | ||||||
|  | 			err := errors.New("cannot use '<domain>' and '--local' together") | ||||||
|  | 			internal.ShowSubcommandHelpAndError(c, err) | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		domainName := "default" | ||||||
|  |  | ||||||
|  | 		if local { | ||||||
|  | 			os.Mkdir(path.Join(config.ABRA_DIR, "servers", domainName), 0755) | ||||||
|  | 			return nil | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		domainName = internal.ValidateDomain(c) | ||||||
|  |  | ||||||
| 		var username string | 		var username string | ||||||
| 		var port string | 		var port string | ||||||
| @ -91,6 +126,8 @@ All communication between Abra and the server will use this SSH connection. | |||||||
| 		logrus.Debugf("remote connection to '%s' is definitely up", domainName) | 		logrus.Debugf("remote connection to '%s' is definitely up", domainName) | ||||||
| 		logrus.Infof("server at '%s' has been added", domainName) | 		logrus.Infof("server at '%s' has been added", domainName) | ||||||
|  |  | ||||||
|  | 		os.Mkdir(path.Join(config.ABRA_DIR, "servers", domainName), 0755) | ||||||
|  |  | ||||||
| 		return nil | 		return nil | ||||||
| 	}, | 	}, | ||||||
| } | } | ||||||
|  | |||||||
							
								
								
									
										2
									
								
								go.mod
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								go.mod
									
									
									
									
									
								
							| @ -6,6 +6,7 @@ require ( | |||||||
| 	coopcloud.tech/tagcmp v0.0.0-20210906102006-2a8edd82d75d | 	coopcloud.tech/tagcmp v0.0.0-20210906102006-2a8edd82d75d | ||||||
| 	github.com/AlecAivazis/survey/v2 v2.3.1 | 	github.com/AlecAivazis/survey/v2 v2.3.1 | ||||||
| 	github.com/Autonomic-Cooperative/godotenv v1.3.1-0.20210731170023-c37c0920d1a4 | 	github.com/Autonomic-Cooperative/godotenv v1.3.1-0.20210731170023-c37c0920d1a4 | ||||||
|  | 	github.com/Gurpartap/logrus-stack v0.0.0-20170710170904-89c00d8a28f4 | ||||||
| 	github.com/docker/cli v20.10.8+incompatible | 	github.com/docker/cli v20.10.8+incompatible | ||||||
| 	github.com/docker/distribution v2.7.1+incompatible | 	github.com/docker/distribution v2.7.1+incompatible | ||||||
| 	github.com/docker/docker v20.10.8+incompatible | 	github.com/docker/docker v20.10.8+incompatible | ||||||
| @ -39,6 +40,7 @@ require ( | |||||||
| 	github.com/docker/go-connections v0.4.0 // indirect | 	github.com/docker/go-connections v0.4.0 // indirect | ||||||
| 	github.com/docker/go-metrics v0.0.1 // indirect | 	github.com/docker/go-metrics v0.0.1 // indirect | ||||||
| 	github.com/emirpasic/gods v1.12.0 // indirect | 	github.com/emirpasic/gods v1.12.0 // indirect | ||||||
|  | 	github.com/facebookgo/stack v0.0.0-20160209184415-751773369052 // indirect | ||||||
| 	github.com/fvbommel/sortorder v1.0.2 // indirect | 	github.com/fvbommel/sortorder v1.0.2 // indirect | ||||||
| 	github.com/go-git/gcfg v1.5.0 // indirect | 	github.com/go-git/gcfg v1.5.0 // indirect | ||||||
| 	github.com/go-git/go-billy/v5 v5.3.1 // indirect | 	github.com/go-git/go-billy/v5 v5.3.1 // indirect | ||||||
|  | |||||||
							
								
								
									
										4
									
								
								go.sum
									
									
									
									
									
								
							
							
						
						
									
										4
									
								
								go.sum
									
									
									
									
									
								
							| @ -44,6 +44,8 @@ github.com/Azure/go-autorest/logger v0.2.0/go.mod h1:T9E3cAhj2VqvPOtCYAvby9aBXkZ | |||||||
| github.com/Azure/go-autorest/tracing v0.6.0/go.mod h1:+vhtPC754Xsa23ID7GlGsrdKBpUA79WCAKPPZVC2DeU= | github.com/Azure/go-autorest/tracing v0.6.0/go.mod h1:+vhtPC754Xsa23ID7GlGsrdKBpUA79WCAKPPZVC2DeU= | ||||||
| github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= | github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= | ||||||
| github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo= | github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo= | ||||||
|  | github.com/Gurpartap/logrus-stack v0.0.0-20170710170904-89c00d8a28f4 h1:vdT7QwBhJJEVNFMBNhRSFDRCB6O16T28VhvqRgqFyn8= | ||||||
|  | github.com/Gurpartap/logrus-stack v0.0.0-20170710170904-89c00d8a28f4/go.mod h1:SvXOG8ElV28oAiG9zv91SDe5+9PfIr7PPccpr8YyXNs= | ||||||
| github.com/Microsoft/go-winio v0.4.11/go.mod h1:VhR8bwka0BXejwEJY73c50VrPtXAaKcyvVC4A4RozmA= | github.com/Microsoft/go-winio v0.4.11/go.mod h1:VhR8bwka0BXejwEJY73c50VrPtXAaKcyvVC4A4RozmA= | ||||||
| github.com/Microsoft/go-winio v0.4.14/go.mod h1:qXqCSQ3Xa7+6tgxaGTIe4Kpcdsi+P8jBhyzoq1bpyYA= | github.com/Microsoft/go-winio v0.4.14/go.mod h1:qXqCSQ3Xa7+6tgxaGTIe4Kpcdsi+P8jBhyzoq1bpyYA= | ||||||
| github.com/Microsoft/go-winio v0.4.15-0.20190919025122-fc70bd9a86b5/go.mod h1:tTuCMEN+UleMWgg9dVx4Hu52b1bJo+59jBh3ajtinzw= | github.com/Microsoft/go-winio v0.4.15-0.20190919025122-fc70bd9a86b5/go.mod h1:tTuCMEN+UleMWgg9dVx4Hu52b1bJo+59jBh3ajtinzw= | ||||||
| @ -295,6 +297,8 @@ github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1m | |||||||
| github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= | github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= | ||||||
| github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5/go.mod h1:a2zkGnVExMxdzMo3M0Hi/3sEU+cWnZpSni0O6/Yb/P0= | github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5/go.mod h1:a2zkGnVExMxdzMo3M0Hi/3sEU+cWnZpSni0O6/Yb/P0= | ||||||
| github.com/evanphx/json-patch v4.9.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= | github.com/evanphx/json-patch v4.9.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= | ||||||
|  | github.com/facebookgo/stack v0.0.0-20160209184415-751773369052 h1:JWuenKqqX8nojtoVVWjGfOF9635RETekkoH6Cc9SX0A= | ||||||
|  | github.com/facebookgo/stack v0.0.0-20160209184415-751773369052/go.mod h1:UbMTZqLaRiH3MsBH8va0n7s1pQYcu3uTb8G4tygF4Zg= | ||||||
| github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= | github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= | ||||||
| github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc= | github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc= | ||||||
| github.com/form3tech-oss/jwt-go v3.2.2+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= | github.com/form3tech-oss/jwt-go v3.2.2+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= | ||||||
|  | |||||||
| @ -73,6 +73,11 @@ func getAllFilesInDirectory(directory string) ([]fs.FileInfo, error) { | |||||||
| 	for _, file := range files { | 	for _, file := range files { | ||||||
| 		// Follow any symlinks | 		// Follow any symlinks | ||||||
| 		filePath := path.Join(directory, file.Name()) | 		filePath := path.Join(directory, file.Name()) | ||||||
|  |  | ||||||
|  | 		if filepath.Ext(strings.TrimSpace(filePath)) != ".env" { | ||||||
|  | 			continue | ||||||
|  | 		} | ||||||
|  |  | ||||||
| 		realPath, err := filepath.EvalSymlinks(filePath) | 		realPath, err := filepath.EvalSymlinks(filePath) | ||||||
| 		if err != nil { | 		if err != nil { | ||||||
| 			logrus.Warningf("broken symlink in your abra config folders: '%s'", filePath) | 			logrus.Warningf("broken symlink in your abra config folders: '%s'", filePath) | ||||||
| @ -137,7 +142,7 @@ func ReadAbraShEnvVars(abraSh string) (map[string]string, error) { | |||||||
| 	file, err := os.Open(abraSh) | 	file, err := os.Open(abraSh) | ||||||
| 	if err != nil { | 	if err != nil { | ||||||
| 		if os.IsNotExist(err) { | 		if os.IsNotExist(err) { | ||||||
| 			return envVars, fmt.Errorf("'%s' does not exist?", abraSh) | 			return envVars, nil | ||||||
| 		} | 		} | ||||||
| 		return envVars, err | 		return envVars, err | ||||||
| 	} | 	} | ||||||
|  | |||||||
| @ -13,7 +13,7 @@ var validAbraConf = os.ExpandEnv("$PWD/../../tests/resources/valid_abra_config") | |||||||
|  |  | ||||||
| // make sure these are in alphabetical order | // make sure these are in alphabetical order | ||||||
| var tFolders = []string{"folder1", "folder2"} | var tFolders = []string{"folder1", "folder2"} | ||||||
| var tFiles = []string{"bar", "foo"} | var tFiles = []string{"bar.env", "foo.env"} | ||||||
|  |  | ||||||
| var appName = "ecloud" | var appName = "ecloud" | ||||||
| var serverName = "evil.corp" | var serverName = "evil.corp" | ||||||
|  | |||||||
| @ -1,6 +1,6 @@ | |||||||
| #!/usr/bin/env bash | #!/usr/bin/env bash | ||||||
|  |  | ||||||
| ABRA_VERSION="0.1.4-alpha" | ABRA_VERSION="0.1.5-alpha" | ||||||
| ABRA_RELEASE_URL="https://git.coopcloud.tech/api/v1/repos/coop-cloud/abra/releases/tags/$ABRA_VERSION" | ABRA_RELEASE_URL="https://git.coopcloud.tech/api/v1/repos/coop-cloud/abra/releases/tags/$ABRA_VERSION" | ||||||
|  |  | ||||||
| function show_banner { | function show_banner { | ||||||
|  | |||||||
		Reference in New Issue
	
	Block a user