Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
Signed-off-by: Salim Afiune Maya <[email protected]>
  • Loading branch information
afiune committed Oct 23, 2024
1 parent 8f55ac3 commit 44d752d
Showing 1 changed file with 200 additions and 0 deletions.
200 changes: 200 additions & 0 deletions apps/cnspec/cmd/integrate.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,200 @@
// Copyright (c) Mondoo, Inc.
// SPDX-License-Identifier: BUSL-1.1

package cmd

import (
"dario.cat/mergo"
"github.com/AlecAivazis/survey/v2"

Check failure on line 8 in apps/cnspec/cmd/integrate.go

View workflow job for this annotation

GitHub Actions / go-test

no required module provides package github.com/AlecAivazis/survey/v2; to add it:

Check failure on line 8 in apps/cnspec/cmd/integrate.go

View workflow job for this annotation

GitHub Actions / go-test

no required module provides package github.com/AlecAivazis/survey/v2; to add it:

Check failure on line 8 in apps/cnspec/cmd/integrate.go

View workflow job for this annotation

GitHub Actions / go-test

no required module provides package github.com/AlecAivazis/survey/v2; to add it:
"github.com/cockroachdb/errors"
"github.com/spf13/cobra"
)

func init() {
// cnspec integrate
rootCmd.AddCommand(integrateCmd)
// cnspec integrate azure
integrateCmd.AddCommand(integrateAzureCmd)
}

var (
integrateCmd = &cobra.Command{
Use: "integrate",
Aliases: []string{"onboard"},
Hidden: true,
Short: "Onboard integrations for continuous scanning into the Mondoo platform",
Long: "Run automation code to onboard your account and deploy Mondoo into various environments.",
}
integrateAzureCmd = &cobra.Command{
Use: "azure",
Aliases: []string{"az"},
Short: "Onboard Microsoft Azure",
Long: `Use this command to connect your Azure environment into the Mondoo platform.`,
RunE: func(cmd *cobra.Command, args []string) error {
// Generate TF Code
cli.StartProgress("Generating Azure Terraform Code...")

if cli.Profile != "default" {
GenerateAzureCommandState.LaceworkProfile = cli.Profile
}

// Setup modifiers for NewTerraform constructor
mods := []azure.AzureTerraformModifier{
azure.WithLaceworkProfile(GenerateAzureCommandState.LaceworkProfile),
azure.WithSubscriptionID(GenerateAzureCommandState.SubscriptionID),
azure.WithAllSubscriptions(GenerateAzureCommandState.AllSubscriptions),
azure.WithManagementGroup(GenerateAzureCommandState.ManagementGroup),
azure.WithExistingStorageAccount(GenerateAzureCommandState.ExistingStorageAccount),
azure.WithStorageAccountName(GenerateAzureCommandState.StorageAccountName),
azure.WithStorageLocation(GenerateAzureCommandState.StorageLocation),
azure.WithActivityLogIntegrationName(GenerateAzureCommandState.ActivityLogIntegrationName),
azure.WithConfigIntegrationName(GenerateAzureCommandState.ConfigIntegrationName),
azure.WithEntraIdActivityLogIntegrationName(GenerateAzureCommandState.EntraIdIntegrationName),
azure.WithEventHubLocation(GenerateAzureCommandState.EventHubLocation),
azure.WithEventHubPartitionCount(GenerateAzureCommandState.EventHubPartitionCount),
}

// Check if AD Creation is required, need to set values for current integration
if !GenerateAzureCommandState.CreateAdIntegration {
mods = append(mods, azure.WithAdApplicationId(GenerateAzureCommandState.AdApplicationId))
mods = append(mods, azure.WithAdApplicationPassword(GenerateAzureCommandState.AdApplicationPassword))
mods = append(mods, azure.WithAdServicePrincipalId(GenerateAzureCommandState.AdServicePrincipalId))
}

// Check subscriptions
if !GenerateAzureCommandState.AllSubscriptions {
if len(GenerateAzureCommandState.SubscriptionIds) > 0 {
mods = append(mods, azure.WithSubscriptionIds(GenerateAzureCommandState.SubscriptionIds))
}
}

// Check management groups
if GenerateAzureCommandState.ManagementGroup {
mods = append(mods, azure.WithManagementGroupId(GenerateAzureCommandState.ManagementGroupId))
}

// Check storage account
if GenerateAzureCommandState.ExistingStorageAccount {
mods = append(mods,
azure.WithStorageAccountResourceGroup(GenerateAzureCommandState.StorageAccountResourceGroup))
}

// Create new struct
data := azure.NewTerraform(
GenerateAzureCommandState.Config,
GenerateAzureCommandState.ActivityLog,
GenerateAzureCommandState.EntraIdActivityLog,
GenerateAzureCommandState.CreateAdIntegration,
mods...)

// Generate HCL for azure deployment
hcl, err := data.Generate()
cli.StopProgress()

if err != nil {
return errors.Wrap(err, "failed to generate terraform code")
}

// Write-out generated code to location specified
dirname, _, err := writeGeneratedCodeToLocation(cmd, hcl, "azure")
if err != nil {
return err
}

// Prompt to execute, if the command line flag has not been set
if !GenerateAzureCommandExtraState.TerraformApply {
err = SurveyQuestionInteractiveOnly(SurveyQuestionWithValidationArgs{
Prompt: &survey.Confirm{Default: GenerateAzureCommandExtraState.TerraformApply, Message: QuestionRunTfPlan},
Response: &GenerateAzureCommandExtraState.TerraformApply,
})

if err != nil {
return errors.Wrap(err, "failed to prompt for terraform execution")
}
}

locationDir, _ := determineOutputDirPath(dirname, "azure")
if GenerateAzureCommandExtraState.TerraformApply {
// Execution pre-run check
err := executionPreRunChecks(dirname, locationDir, "azure")
if err != nil {
return err
}
}

// Output where code was generated
if !GenerateAzureCommandExtraState.TerraformApply {
cli.OutputHuman(provideGuidanceAfterExit(false, false, locationDir, "terraform"))
}

return nil
},
PreRunE: func(cmd *cobra.Command, _ []string) error {

// Validate output location is OK if supplied
dirname, err := cmd.Flags().GetString("output")
if err != nil {
return errors.Wrap(err, "failed to load command flags")
}
if err := validateOutputLocation(dirname); err != nil {
return err
}

// Validate Storage Location
storageLocation, err := cmd.Flags().GetString("location")
if err != nil {
return errors.Wrap(err, "failed to load command flags")
}
if err := validateAzureLocation(storageLocation); storageLocation != "" && err != nil {
return err
}

// Load any cached inputs if interactive
if cli.InteractiveMode() {
cachedOptions := &azure.GenerateAzureTfConfigurationArgs{}
iacParamsExpired := cli.ReadCachedAsset(CachedAzureAssetIacParams, &cachedOptions)
if iacParamsExpired {
cli.Log.Debug("loaded previously set values for Azure iac generation")
}

extraState := &AzureGenerateCommandExtraState{}
extraStateParamsExpired := cli.ReadCachedAsset(CachedAzureAssetExtraState, &extraState)
if extraStateParamsExpired {
cli.Log.Debug("loaded previously set values for Azure iac generation (extra state)")
}

// Determine if previously cached options exists; prompt user if they'd like to continue
answer := false
if !iacParamsExpired || !extraStateParamsExpired {
if err := SurveyQuestionInteractiveOnly(SurveyQuestionWithValidationArgs{
Prompt: &survey.Confirm{Message: QuestionUsePreviousCache, Default: false},
Response: &answer,
}); err != nil {
return errors.Wrap(err, "failed to load saved options")
}
}

// If the user decides NOT to use the previous values; we won't load them. However, every time the command runs
// we are going to write out new cached values, so if they run it - bail out - and run it again they'll get
// re-prompted.
if answer {
// Merge cached inputs to current options (current options win)
if err := mergo.Merge(GenerateAzureCommandState, cachedOptions); err != nil {
return errors.Wrap(err, "failed to load saved options")
}
if err := mergo.Merge(GenerateAzureCommandExtraState, extraState); err != nil {
return errors.Wrap(err, "failed to load saved options")
}
}
}

// Collect and/or confirm parameters
err = promptAzureGenerate(GenerateAzureCommandState, GenerateAzureCommandExtraState)
if err != nil {
return errors.Wrap(err, "collecting/confirming parameters")
}

return nil
},
}
)

0 comments on commit 44d752d

Please sign in to comment.