Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement Exception Handling #159

Open
atomic111 opened this issue Nov 28, 2024 · 4 comments · May be fixed by #165
Open

Implement Exception Handling #159

atomic111 opened this issue Nov 28, 2024 · 4 comments · May be fixed by #165
Labels
enhancement New feature or request

Comments

@atomic111
Copy link
Member

atomic111 commented Nov 28, 2024

Works similar to the https://github.com/mondoohq/terraform-provider-mondoo/blob/main/internal/provider/policy_assignment_resource.go where the API defines mutations but tf defines the state.

The implementation is a combination of ListExceptionGroup and ApplyException. Terraform only needs to apply the exception if it is not listed already.

resource "mondoo_exception" "exception_1" {
  scopeMrn        = "" # either asset mrn or space mrn
  valid_until     = # timestamp
  justification   = "description why the exception is required" # Optional
  action          = "SNOOZE" # Snooze is default, does not need to be provided 
  
  checkMrns = [] # list of check mrns, mapped to queryMrns, we adjust the API later
  vulnerabilityMrns = [] # list of advisory mrns, mapped to advisoryMrns in the Graphql call, we adjust that later in the API
}

GraphQL call:

"""
The input to apply an exception
"""
input ExceptionMutationInput {
  """
  The scope of the exception. Can be a space or an asset mrn
  """
  scopeMrn: String!
  """
  RFC3339 timestamp
  The date, from which on the exception is no longer valid.
  Only applies to action SNOZZE, empty is interpreted as forever
  """
  validUntil: String
  """
  The justification for the exception
  """
  justification: String
  """
  How this exception should be handled
  Snooze the controls or disable them
  "enable" will delete the supplied control mrn from any exception
  """
  action: ExceptionMutationAction!
  """
  List of control mrns that are excepted. Applies only for compliance exceptions
  """
  controlMrns: [String!]
  """
  List of query mrns that are excepted. Applies only for security exceptions
  """
  queryMrns: [String!]
  """
  List of cve mrns that are excepted. Applies only for cve exceptions
  """
  cveMrns: [String!]
  """
  List of advisory mrns that are excepted. Applies only for cve exceptions
  """
  advisoryMrns: [String!]
  """
  Apply the exception to the CVEs that are part of the advisories. Applies only for advisory exceptions
  """
  applyToCves: Boolean
}

Space-wide exception GraphQL call

{
  "operationName": "ApplyException",
  "variables": {
    "input": {
      "scopeMrn": "//captain.api.mondoo.app/spaces/beautiful-wiles-231755",
      "queryMrns": [
        "//policy.api.mondoo.app/queries/mondoo-gcp-security-cloud-storage-bucket-not-anonymously-publicly-accessible"
      ],
      "action": "SNOOZE",
      "justification": "",
      "applyToCves": false
    }
  },
  "query": "mutation ApplyException($input: ExceptionMutationInput!) {\n  applyException(input: $input)\n}"
}

Asset-level exception GraphQL call

{
  "operationName": "ApplyException",
  "variables": {
    "input": {
      "scopeMrn": "//assets.api.mondoo.app/spaces/beautiful-wiles-231755/assets/2otSfjoOJ83VyUK35xVgMwAKr4G",
      "queryMrns": [
        "//policy.api.mondoo.app/queries/mondoo-kubernetes-security-deployment-runasnonroot"
      ],
      "action": "SNOOZE",
      "justification": "",
      "applyToCves": false
    }
  },
  "query": "mutation ApplyException($input: ExceptionMutationInput!) {\n  applyException(input: $input)\n}"
}
@atomic111 atomic111 added the enhancement New feature or request label Nov 28, 2024
@atomic111 atomic111 changed the title Exception Handling Implement Exception Handling Nov 28, 2024
@mati007thm
Copy link
Contributor

mati007thm commented Dec 2, 2024

@atomic111 I ran into an unexpected error:
client: user not found
Image
Image

The same can be seen in the browser after I applied the tf changes:
Image
Image

Where can I find this action IGNORE?

RFC3339 timestamp
The date, from which on the exception is no longer valid.
Only applies to action IGNORE, empty is interpreted as forever

I could only find:

// ExceptionMutationAction represents the action to apply to the exception.
type ExceptionMutationAction string

// The action to apply to the exception.
const (
	ExceptionMutationActionEnable     ExceptionMutationAction = "ENABLE"
	ExceptionMutationActionDisable    ExceptionMutationAction = "DISABLE"
	ExceptionMutationActionSnooze     ExceptionMutationAction = "SNOOZE"
	ExceptionMutationActionOutOfScope ExceptionMutationAction = "OUT_OF_SCOPE" // Applicable only for compliance.
)

@atomic111
Copy link
Member Author

@mati007thm can you please provide the steps to reproduce it via the UI.

@chris-rock
Copy link
Member

chris-rock commented Dec 2, 2024

Ignore was renamed to "SNOOZE"

@mati007thm
Copy link
Contributor

@atomic111 I could not replicate it using the UI. I only get the error when using the tf provider. But I simply can not find out where I went wrong...
I am using the following GraphQL function:

func (c *ExtendedGqlClient) ApplyException(
	ctx context.Context,
	scopeMrn string,
	action mondoov1.ExceptionMutationAction,
	checkMrns, controlMrns, cveMrns, vulnerabilityMrns []string,
	justification *string,
	validUntil *string,
	applyToCves *bool,
) error {
	var applyException struct {
		ApplyException bool `graphql:"applyException(input: $input)"`
	}

	// Helper function to convert string slices to *[]mondoov1.String
	convertToGraphQLList := func(mrns []string) *[]mondoov1.String {
		if len(mrns) == 0 {
			return nil
		}
		entries := []mondoov1.String{}
		for _, mrn := range mrns {
			entries = append(entries, mondoov1.String(mrn))
		}
		return &entries
	}

	// Prepare input fields
	input := mondoov1.ExceptionMutationInput{
		ScopeMrn:      mondoov1.String(scopeMrn),
		Action:        action,
		QueryMrns:     convertToGraphQLList(checkMrns),
		ControlMrns:   convertToGraphQLList(controlMrns),
		CveMrns:       convertToGraphQLList(cveMrns),
		AdvisoryMrns:  convertToGraphQLList(vulnerabilityMrns),
		Justification: (*mondoov1.String)(justification),
		ValidUntil:    (*mondoov1.String)(validUntil),
		ApplyToCves:   mondoov1.NewBooleanPtr(mondoov1.Boolean(*applyToCves)),
	}

	return c.Mutate(ctx, &applyException, input, nil)
}

and call it with:

err := r.client.ApplyException(ctx, data.ScopeMrn.ValueString(), mondoov1.ExceptionMutationAction(data.Action.ValueString()), checks, []string{}, []string{}, vulnerabilities, data.Justification.ValueStringPointer(), &validUntilStr, (*bool)(mondoov1.NewBooleanPtr(false)))

The code is at #165

@chris-rock chris-rock linked a pull request Dec 4, 2024 that will close this issue
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants