From 87980d8194884ba5eb40507f9ac9ce5e25b1e13b Mon Sep 17 00:00:00 2001 From: Max Fierke Date: Sun, 10 Nov 2019 10:00:44 -0600 Subject: [PATCH] Fallback to environment if values not specified for AppleId If any values are not specified in the config file for `AppleId` we can fallback to pulling them from `AC_USERNAME`, `AC_PASSWORD`, and `AC_PROVIDER`. `AC_PASSWORD` will still be passed into `altool` using the `@env:` prefix as supported by `altool` to avoid printing sensitive information but all others will be read from the environment and passed by value to `altool`. --- cmd/gon/main.go | 40 +++++++++++++++++++ internal/config/config.go | 12 +++--- internal/config/testdata/basic.hcl.golden | 7 ++-- internal/config/testdata/entitle.hcl.golden | 18 +++++++++ internal/config/testdata/env_appleid.hcl | 6 +++ .../config/testdata/env_appleid.hcl.golden | 14 +++++++ internal/config/testdata/notarize.hcl.golden | 4 +- .../testdata/notarize_multiple.hcl.golden | 4 +- 8 files changed, 93 insertions(+), 12 deletions(-) create mode 100644 internal/config/testdata/entitle.hcl.golden create mode 100644 internal/config/testdata/env_appleid.hcl create mode 100644 internal/config/testdata/env_appleid.hcl.golden diff --git a/cmd/gon/main.go b/cmd/gon/main.go index 2fd91f0..f2f34a6 100644 --- a/cmd/gon/main.go +++ b/cmd/gon/main.go @@ -140,6 +140,46 @@ func realMain() int { } } + // If not specified in the configuration, we initialize a new struct that we'll + // load with values from the environment. + if cfg.AppleId == nil { + cfg.AppleId = &config.AppleId{} + } + + if cfg.AppleId.Username == "" { + appleIdUsername, ok := os.LookupEnv("AC_USERNAME") + + if ok { + cfg.AppleId.Username = appleIdUsername + } else { + color.New(color.Bold, color.FgRed).Fprintf(os.Stdout, "❗️ No apple_id username provided\n") + color.New(color.FgRed).Fprintf(os.Stdout, + "An Apple ID username must be specified in the `apple_id` block or\n"+ + "it must exist in the environment as AC_USERNAME,\n"+ + "otherwise we won't be able to authenticate with Apple to notarize.\n") + return 1 + } + } + + if cfg.AppleId.Password == "" { + _, ok := os.LookupEnv("AC_PASSWORD") + + if ok { + cfg.AppleId.Password = "@env:AC_PASSWORD" + } else { + color.New(color.Bold, color.FgRed).Fprintf(os.Stdout, "❗️ No apple_id password provided\n") + color.New(color.FgRed).Fprintf(os.Stdout, + "An Apple ID password (or lookup directive) must be specified in the\n"+ + "`apple_id` block or it must exist in the environment as AC_PASSWORD,\n"+ + "otherwise we won't be able to authenticate with Apple to notarize.\n") + return 1 + } + } + + if cfg.AppleId.Provider == "" { + cfg.AppleId.Provider = os.Getenv("AC_PROVIDER") + } + // If we're in source mode, then sign & package as configured if len(cfg.Source) > 0 { if cfg.Sign != nil { diff --git a/internal/config/config.go b/internal/config/config.go index a0bc3d5..8c8706e 100644 --- a/internal/config/config.go +++ b/internal/config/config.go @@ -18,7 +18,7 @@ type Config struct { Sign *Sign `hcl:"sign,block"` // AppleId are the credentials to use to talk to Apple. - AppleId AppleId `hcl:"apple_id,block"` + AppleId *AppleId `hcl:"apple_id,block"` // Zip, if present, creates a notarized zip file as the output. Note // that zip files do not support stapling, so the final result will @@ -32,14 +32,16 @@ type Config struct { // AppleId are the authentication settings for Apple systems. type AppleId struct { - // Username is your AC username, typically an email. - Username string `hcl:"username"` + // Username is your AC username, typically an email. This is required, but will + // be read from the environment via AC_USERNAME if not specified via config. + Username string `hcl:"username,optional"` // Password is the password for your AC account. This also accepts // two additional forms: '@keychain:' which reads the password from // the keychain and '@env:' which reads the password from an - // an environmental variable named . - Password string `hcl:"password"` + // an environmental variable named . If omitted, it has the same effect + // as passing '@env:AC_PASSWORD'. + Password string `hcl:"password,optional"` // Provider is the AC provider. This is optional and only needs to be // specified if you're using an Apple ID account that has multiple diff --git a/internal/config/testdata/basic.hcl.golden b/internal/config/testdata/basic.hcl.golden index 3000dc6..e31f737 100644 --- a/internal/config/testdata/basic.hcl.golden +++ b/internal/config/testdata/basic.hcl.golden @@ -5,13 +5,14 @@ BundleId: (string) (len=28) "com.mitchellh.test.terraform", Notarize: ([]config.Notarize) , Sign: (*config.Sign)({ - ApplicationIdentity: (string) (len=3) "foo" + ApplicationIdentity: (string) (len=3) "foo", + EntitlementsFile: (string) "" }), - AppleId: (config.AppleId) { + AppleId: (*config.AppleId)({ Username: (string) (len=21) "mitchellh@example.com", Password: (string) (len=5) "hello", Provider: (string) "" - }, + }), Zip: (*config.Zip)(), Dmg: (*config.Dmg)() }) diff --git a/internal/config/testdata/entitle.hcl.golden b/internal/config/testdata/entitle.hcl.golden new file mode 100644 index 0000000..1f10236 --- /dev/null +++ b/internal/config/testdata/entitle.hcl.golden @@ -0,0 +1,18 @@ +(*config.Config)({ + Source: ([]string) (len=1 cap=1) { + (string) (len=11) "./terraform" + }, + BundleId: (string) (len=28) "com.mitchellh.test.terraform", + Notarize: ([]config.Notarize) , + Sign: (*config.Sign)({ + ApplicationIdentity: (string) (len=3) "foo", + EntitlementsFile: (string) (len=29) "/path/to/example.entitlements" + }), + AppleId: (*config.AppleId)({ + Username: (string) (len=21) "mitchellh@example.com", + Password: (string) (len=5) "hello", + Provider: (string) "" + }), + Zip: (*config.Zip)(), + Dmg: (*config.Dmg)() +}) diff --git a/internal/config/testdata/env_appleid.hcl b/internal/config/testdata/env_appleid.hcl new file mode 100644 index 0000000..e78e407 --- /dev/null +++ b/internal/config/testdata/env_appleid.hcl @@ -0,0 +1,6 @@ +source = ["./terraform"] +bundle_id = "com.mitchellh.test.terraform" + +sign { + application_identity = "foo" +} diff --git a/internal/config/testdata/env_appleid.hcl.golden b/internal/config/testdata/env_appleid.hcl.golden new file mode 100644 index 0000000..70382c1 --- /dev/null +++ b/internal/config/testdata/env_appleid.hcl.golden @@ -0,0 +1,14 @@ +(*config.Config)({ + Source: ([]string) (len=1 cap=1) { + (string) (len=11) "./terraform" + }, + BundleId: (string) (len=28) "com.mitchellh.test.terraform", + Notarize: ([]config.Notarize) , + Sign: (*config.Sign)({ + ApplicationIdentity: (string) (len=3) "foo", + EntitlementsFile: (string) "" + }), + AppleId: (*config.AppleId)(), + Zip: (*config.Zip)(), + Dmg: (*config.Dmg)() +}) diff --git a/internal/config/testdata/notarize.hcl.golden b/internal/config/testdata/notarize.hcl.golden index 42acecf..8566ee1 100644 --- a/internal/config/testdata/notarize.hcl.golden +++ b/internal/config/testdata/notarize.hcl.golden @@ -10,11 +10,11 @@ } }, Sign: (*config.Sign)(), - AppleId: (config.AppleId) { + AppleId: (*config.AppleId)({ Username: (string) (len=21) "mitchellh@example.com", Password: (string) (len=5) "hello", Provider: (string) "" - }, + }), Zip: (*config.Zip)(), Dmg: (*config.Dmg)() }) diff --git a/internal/config/testdata/notarize_multiple.hcl.golden b/internal/config/testdata/notarize_multiple.hcl.golden index 2f0f568..b667f6d 100644 --- a/internal/config/testdata/notarize_multiple.hcl.golden +++ b/internal/config/testdata/notarize_multiple.hcl.golden @@ -15,11 +15,11 @@ } }, Sign: (*config.Sign)(), - AppleId: (config.AppleId) { + AppleId: (*config.AppleId)({ Username: (string) (len=21) "mitchellh@example.com", Password: (string) (len=5) "hello", Provider: (string) "" - }, + }), Zip: (*config.Zip)(), Dmg: (*config.Dmg)() })