diff --git a/pkg/prompts/prompts.go b/pkg/prompts/prompts.go index 8b4d3bf8..57018331 100644 --- a/pkg/prompts/prompts.go +++ b/pkg/prompts/prompts.go @@ -11,6 +11,7 @@ import ( "github.com/manifoldco/promptui" log "github.com/sirupsen/logrus" + "k8s.io/apimachinery/pkg/util/validation" "github.com/Azure/draft/pkg/config" ) @@ -141,28 +142,10 @@ func NoBlankStringValidator(s string) error { // Validator for App name func appNameValidator(name string) error { - if name == "" { - return fmt.Errorf("application name cannot be empty") + errors := validation.IsDNS1123Label(name) + if errors != nil { + return fmt.Errorf("invalid app name: %s", strings.Join(errors, ", ")) } - - if !unicode.IsLetter(rune(name[0])) && !unicode.IsDigit(rune(name[0])) { - return fmt.Errorf("application name must start with a letter or digit") - } - - if name[len(name)-1] == '-' || name[len(name)-1] == '_' || name[len(name)-1] == '.' { - return fmt.Errorf("application name must end with a letter or digit") - } - - for _, r := range name { - if !unicode.IsLetter(r) && !unicode.IsDigit(r) && r != '-' && r != '_' && r != '.' { - return fmt.Errorf("application name can only contain letters, digits, '-', '_', and '.'") - } - } - - if len(name) > 63 { - return fmt.Errorf("application name cannot be longer than 63 characters") - } - return nil } @@ -312,9 +295,9 @@ func getCurrentDirName() (string, error) { func sanitizeAppName(name string) string { var builder strings.Builder - // Remove all characters except alphanumeric, '-', '_', '.' + // Remove all characters except alphanumeric, '-', '.' for _, r := range name { - if unicode.IsLetter(r) || unicode.IsDigit(r) || r == '-' || r == '_' || r == '.' { + if unicode.IsLetter(r) || unicode.IsDigit(r) || r == '-' || r == '.' { builder.WriteRune(r) } } diff --git a/pkg/providers/az-client.go b/pkg/providers/az-client.go index bad4a310..56eabc14 100644 --- a/pkg/providers/az-client.go +++ b/pkg/providers/az-client.go @@ -19,21 +19,21 @@ type AzClientInterface interface { AzAcrExists(acrName string) bool AzAksExists(aksName string, resourceGroup string) bool AzAppExists(appName string) bool - CreateAzApp(appName string) error - CreateServicePrincipal(appId string) error + CreateAzApp(appName string) (string, error) + CreateServicePrincipal(appId string) (string, error) EnsureAzCli() EnsureAzCliLoggedIn() GetAzCliVersion() (string, error) GetAzSubscriptionLabels() ([]SubLabel, error) GetAzUpgrade() string GetCurrentAzSubscriptionLabel() (SubLabel, error) + GetServicePrincipal(appId string) (string, error) IsLoggedInToAz() bool IsSubscriptionIdValid(subscriptionId string) error IsValidResourceGroup(subscriptionId string, resourceGroup string) error ListResourceGroups(ctx context.Context, subscriptionID string) ([]armresources.ResourceGroup, error) ListTenants(ctx context.Context) ([]armsubscription.TenantIDDescription, error) LogInToAz() error - ServicePrincipalExists(appId string) bool UpgradeAzCli() ValidateAzCliInstalled() error } diff --git a/pkg/providers/azcli.go b/pkg/providers/azcli.go index 3eecea18..4fda5491 100644 --- a/pkg/providers/azcli.go +++ b/pkg/providers/azcli.go @@ -88,7 +88,7 @@ func (az *AzClient) ValidateAzCliInstalled() error { func (az *AzClient) IsLoggedInToAz() bool { log.Debug("Checking that user is logged in to Azure CLI...") _, err := az.CommandRunner.RunCommand("az", "ad", "signed-in-user", "show", "--only-show-errors", "--query", "objectId") - return err != nil + return err != nil } func (az *AzClient) EnsureAzCliLoggedIn() { @@ -173,17 +173,17 @@ func (az *AzClient) AzAppExists(appName string) bool { return len(azApp) >= 1 } -func (az *AzClient) ServicePrincipalExists(appId string) bool { +func (az *AzClient) GetServicePrincipal(appId string) (string, error) { out, err := az.CommandRunner.RunCommand("az", "ad", "sp", "show", "--only-show-errors", "--id", appId, "--query", "id") if err != nil { - return false + return "", err } var objectId string json.Unmarshal([]byte(out), &objectId) log.Debugf("Service principal with appId '%s' exists", appId) - return true + return objectId, nil } func (az *AzClient) AzAcrExists(acrName string) bool { diff --git a/pkg/providers/azure.go b/pkg/providers/azure.go index c7688ba6..3217cff2 100644 --- a/pkg/providers/azure.go +++ b/pkg/providers/azure.go @@ -42,15 +42,18 @@ func InitiateAzureOIDCFlow(ctx context.Context, sc *SetUpCmd, s spinner.Spinner, } if !az.AzAppExists(sc.AppName) { - err := az.CreateAzApp(sc.AppName) + appId, err := az.CreateAzApp(sc.AppName) if err != nil { return err } + sc.appId = appId } - if err := az.CreateServicePrincipal(sc.appId); err != nil { + spObjId, err := az.CreateServicePrincipal(sc.appId) + if err != nil { return err } + sc.spObjectId = spObjId if err := sc.getAppObjectId(); err != nil { return err @@ -80,10 +83,13 @@ func InitiateAzureOIDCFlow(ctx context.Context, sc *SetUpCmd, s spinner.Spinner, return nil } -func (az *AzClient) CreateAzApp(appName string) error { +// CreateAzApp creates an Azure app with the given name +// Returns the appId of the created app +func (az *AzClient) CreateAzApp(appName string) (string, error) { log.Debug("Commencing Azure app creation...") start := time.Now() log.Debug(start) + createdAppId := "" createApp := func() error { out, err := az.CommandRunner.RunCommand("az", "ad", "app", "create", "--only-show-errors", "--display-name", appName) @@ -97,7 +103,7 @@ func (az *AzClient) CreateAzApp(appName string) error { if err := json.Unmarshal([]byte(out), &azApp); err != nil { return err } - createdAppId := fmt.Sprint(azApp["appId"]) + createdAppId = fmt.Sprint(azApp["appId"]) end := time.Since(start) log.Debugf("App with appId '%s' created successfully!", createdAppId) @@ -114,17 +120,24 @@ func (az *AzClient) CreateAzApp(appName string) error { err := bo.Retry(createApp, backoff) if err != nil { log.Debug(err) - return err + return "", err } - return nil + return createdAppId, nil } -func (az *AzClient) CreateServicePrincipal(appId string) error { +// CreateServicePrincipal creates a service principal with the given appId +// Returns the objectId of the created service principal +func (az *AzClient) CreateServicePrincipal(appId string) (string, error) { log.Debug("creating Azure service principal...") start := time.Now() log.Debug(start) + if appId == "" { + return "", errors.New("appId cannot be empty") + } + createdObjectId := "" + createServicePrincipal := func() error { out, err := az.CommandRunner.RunCommand("az", "ad", "sp", "create", "--id", appId, "--only-show-errors") if err != nil { @@ -133,14 +146,16 @@ func (az *AzClient) CreateServicePrincipal(appId string) error { } log.Debug("checking sp was created...") - if az.ServicePrincipalExists(appId) { - log.Debug("Service principal created successfully!") - end := time.Since(start) - log.Debug(end) - return nil + spObjId, err := az.GetServicePrincipal(appId) + if err != nil { + return errors.New("service principal not found") } + log.Debug("Service principal created successfully!") + end := time.Since(start) + log.Debug(end) + createdObjectId = spObjId + return nil - return errors.New("service principal not found") } backoff := bo.NewExponentialBackOff() @@ -149,10 +164,10 @@ func (az *AzClient) CreateServicePrincipal(appId string) error { err := bo.Retry(createServicePrincipal, backoff) if err != nil { log.Debug(err) - return err + return "", err } - return nil + return createdObjectId, nil } // Prompt the user to select a tenant ID if there are multiple tenants, or return the only tenant ID if there is only one diff --git a/test/integration/clojure/helm.yaml b/test/integration/clojure/helm.yaml index b4570ad0..c7b57b21 100644 --- a/test/integration/clojure/helm.yaml +++ b/test/integration/clojure/helm.yaml @@ -10,8 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "8-jdk-alpine" diff --git a/test/integration/clojure/kustomize.yaml b/test/integration/clojure/kustomize.yaml index fa0f4f73..5cfee3cd 100644 --- a/test/integration/clojure/kustomize.yaml +++ b/test/integration/clojure/kustomize.yaml @@ -10,8 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "8-jdk-alpine" diff --git a/test/integration/clojure/manifest.yaml b/test/integration/clojure/manifest.yaml index f0a27248..f9ac4edf 100644 --- a/test/integration/clojure/manifest.yaml +++ b/test/integration/clojure/manifest.yaml @@ -10,8 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "8-jdk-alpine" diff --git a/test/integration/gradle/helm.yaml b/test/integration/gradle/helm.yaml index 9fbcd1ac..4c85a036 100644 --- a/test/integration/gradle/helm.yaml +++ b/test/integration/gradle/helm.yaml @@ -10,8 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "11-jre" diff --git a/test/integration/gradle/kustomize.yaml b/test/integration/gradle/kustomize.yaml index 9f4da724..c351a773 100644 --- a/test/integration/gradle/kustomize.yaml +++ b/test/integration/gradle/kustomize.yaml @@ -10,8 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "11-jre" diff --git a/test/integration/gradle/manifest.yaml b/test/integration/gradle/manifest.yaml index dee9ef7e..a3781268 100644 --- a/test/integration/gradle/manifest.yaml +++ b/test/integration/gradle/manifest.yaml @@ -10,8 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "11-jre" diff --git a/test/integration/java/helm.yaml b/test/integration/java/helm.yaml index 8ac5b16f..8c338a80 100644 --- a/test/integration/java/helm.yaml +++ b/test/integration/java/helm.yaml @@ -10,8 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "11-jre" diff --git a/test/integration/java/kustomize.yaml b/test/integration/java/kustomize.yaml index db0a432f..3aca136f 100644 --- a/test/integration/java/kustomize.yaml +++ b/test/integration/java/kustomize.yaml @@ -10,8 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "11-jre" diff --git a/test/integration/java/manifest.yaml b/test/integration/java/manifest.yaml index d31b63d5..1aa1cfbc 100644 --- a/test/integration/java/manifest.yaml +++ b/test/integration/java/manifest.yaml @@ -10,8 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "11-jre" diff --git a/test/integration/swift/helm.yaml b/test/integration/swift/helm.yaml index 843ce49d..eecb1c58 100644 --- a/test/integration/swift/helm.yaml +++ b/test/integration/swift/helm.yaml @@ -10,12 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "CPULIMIT" - value: "3" - - name: "MEMLIMIT" - value: "2Gi" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "5.5" diff --git a/test/integration/swift/kustomize.yaml b/test/integration/swift/kustomize.yaml index 45985c01..254bbb98 100644 --- a/test/integration/swift/kustomize.yaml +++ b/test/integration/swift/kustomize.yaml @@ -10,12 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "CPULIMIT" - value: "3" - - name: "MEMLIMIT" - value: "2Gi" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "5.5" diff --git a/test/integration/swift/manifest.yaml b/test/integration/swift/manifest.yaml index 300b59ba..91b7fbdb 100644 --- a/test/integration/swift/manifest.yaml +++ b/test/integration/swift/manifest.yaml @@ -10,12 +10,6 @@ deployVariables: value: "testapp" - name: "IMAGENAME" value: "host.minikube.internal:5001/testapp" - - name: "CPULIMIT" - value: "3" - - name: "MEMLIMIT" - value: "2Gi" - - name: "STARTUPINITIALDELAY" - value: 30 languageVariables: - name: "VERSION" value: "5.5"