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

Update the doc link and add the example link to the cutom policy guide #378

Merged
merged 2 commits into from
Feb 13, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
140 changes: 138 additions & 2 deletions docs/guides/tanzu-mission-control_policy.md
Original file line number Diff line number Diff line change
Expand Up @@ -211,7 +211,7 @@ resource "tanzu-mission-control_iam_policy" "namespace_scoped_iam_policy" {
}
```

## Custom Policy on a CLuster Group
## Custom Policy on a Cluster Group

```terraform
/*
Expand Down Expand Up @@ -278,5 +278,141 @@ resource "tanzu-mission-control_custom_policy" "cluster_group_scoped_tmc-block-r
## Custom Template and Custom Policy

Template provides a declarative definition of a policy, which can be used to apply custom constraints on managed kubernetes resources.
Custom policy consumes these declared custom templates to enforce specific policies. One must create the custom template before consuming it the custom policy.
Custom policy consumes these declared custom templates to enforce specific policies. One must create the [custom template][custom-policy-template] before consuming it in the custom policy.
Please refer to custom policy template and custom policy terraform scripts within examples.

[custom-policy-template]: https://docs.vmware.com/en/VMware-Tanzu-Mission-Control/services/tanzumc-using/GUID-F147492B-04FD-4CFD-8D1F-66E36D40D49C.html

## Refer the following example for creating custom policy template and assign it to custom policy

```terraform
/*
NOTE: Creation of custom policy depends on cluster group and custom policy template.
*/

terraform {
required_providers {
tanzu-mission-control = {
source = "vmware/tanzu-mission-control"
}
}
}

# Create cluster group.
resource "tanzu-mission-control_cluster_group" "create_cluster_group" {
name = "tf-demo-cluster-group"
}

# Create custom policy template.
resource "tanzu-mission-control_custom_policy_template" "sample_template" {
name = "tf-custom-template-test"

spec {
object_type = "ConstraintTemplate"
template_type = "OPAGatekeeper"

data_inventory {
kind = "ConfigMap"
group = "admissionregistration.k8s.io"
version = "v1"
}

data_inventory {
kind = "Deployment"
group = "extensions"
version = "v1"
}

template_manifest = <<YAML
apiVersion: templates.gatekeeper.sh/v1beta1
kind: ConstraintTemplate
metadata:
name: tf-custom-template-test
annotations:
description: Requires Pods to have readiness and/or liveness probes.
spec:
crd:
spec:
names:
kind: tf-custom-template-test
validation:
openAPIV3Schema:
properties:
probes:
type: array
items:
type: string
probeTypes:
type: array
items:
type: string
targets:
- target: admission.k8s.gatekeeper.sh
rego: |
package k8srequiredprobes
probe_type_set = probe_types {
probe_types := {type | type := input.parameters.probeTypes[_]}
}
violation[{"msg": msg}] {
container := input.review.object.spec.containers[_]
probe := input.parameters.probes[_]
probe_is_missing(container, probe)
msg := get_violation_message(container, input.review, probe)
}
probe_is_missing(ctr, probe) = true {
not ctr[probe]
}
probe_is_missing(ctr, probe) = true {
probe_field_empty(ctr, probe)
}
probe_field_empty(ctr, probe) = true {
probe_fields := {field | ctr[probe][field]}
diff_fields := probe_type_set - probe_fields
count(diff_fields) == count(probe_type_set)
}
get_violation_message(container, review, probe) = msg {
msg := sprintf("Container <%v> in your <%v> <%v> has no <%v>", [container.name, review.kind.kind, review.object.metadata.name, probe])
}
YAML
}
}


# Cluster group scoped custom template assigned Custom Policy
resource "tanzu-mission-control_custom_policy" "cluster_group_scoped_custom_template_assigned_custom_policy" {
name = "tf-custom-template-policy-test"

scope {
cluster_group {
cluster_group = tanzu-mission-control_cluster_group.create_cluster_group.name
}
}

spec {
input {
custom {
template_name = tanzu-mission-control_custom_policy_template.sample_template.name
audit = false

target_kubernetes_resources {
api_groups = [
"apps",
]
kinds = [
"Deployment"
]
}

target_kubernetes_resources {
api_groups = [
"apps",
]
kinds = [
"StatefulSet",
]
}
}
}
}
}
```
129 changes: 129 additions & 0 deletions examples/usecases/custom_policy_with_custom_template_usecase.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,129 @@
/*
NOTE: Creation of custom policy depends on cluster group and custom policy template.
*/

terraform {
required_providers {
tanzu-mission-control = {
source = "vmware/tanzu-mission-control"
}
}
}

# Create cluster group.
resource "tanzu-mission-control_cluster_group" "create_cluster_group" {
name = "tf-demo-cluster-group"
}

# Create custom policy template.
resource "tanzu-mission-control_custom_policy_template" "sample_template" {
name = "tf-custom-template-test"

spec {
object_type = "ConstraintTemplate"
template_type = "OPAGatekeeper"

data_inventory {
kind = "ConfigMap"
group = "admissionregistration.k8s.io"
version = "v1"
}

data_inventory {
kind = "Deployment"
group = "extensions"
version = "v1"
}

template_manifest = <<YAML
apiVersion: templates.gatekeeper.sh/v1beta1
kind: ConstraintTemplate
metadata:
name: tf-custom-template-test
annotations:
description: Requires Pods to have readiness and/or liveness probes.
spec:
crd:
spec:
names:
kind: tf-custom-template-test
validation:
openAPIV3Schema:
properties:
probes:
type: array
items:
type: string
probeTypes:
type: array
items:
type: string
targets:
- target: admission.k8s.gatekeeper.sh
rego: |
package k8srequiredprobes
probe_type_set = probe_types {
probe_types := {type | type := input.parameters.probeTypes[_]}
}
violation[{"msg": msg}] {
container := input.review.object.spec.containers[_]
probe := input.parameters.probes[_]
probe_is_missing(container, probe)
msg := get_violation_message(container, input.review, probe)
}
probe_is_missing(ctr, probe) = true {
not ctr[probe]
}
probe_is_missing(ctr, probe) = true {
probe_field_empty(ctr, probe)
}
probe_field_empty(ctr, probe) = true {
probe_fields := {field | ctr[probe][field]}
diff_fields := probe_type_set - probe_fields
count(diff_fields) == count(probe_type_set)
}
get_violation_message(container, review, probe) = msg {
msg := sprintf("Container <%v> in your <%v> <%v> has no <%v>", [container.name, review.kind.kind, review.object.metadata.name, probe])
}
YAML
}
}


# Cluster group scoped custom template assigned Custom Policy
resource "tanzu-mission-control_custom_policy" "cluster_group_scoped_custom_template_assigned_custom_policy" {
name = "tf-custom-template-policy-test"

scope {
cluster_group {
cluster_group = tanzu-mission-control_cluster_group.create_cluster_group.name
}
}

spec {
input {
custom {
template_name = tanzu-mission-control_custom_policy_template.sample_template.name
audit = false

target_kubernetes_resources {
api_groups = [
"apps",
]
kinds = [
"Deployment"
]
}

target_kubernetes_resources {
api_groups = [
"apps",
]
kinds = [
"StatefulSet",
]
}
}
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import (
"github.com/pkg/errors"

"github.com/vmware/terraform-provider-tanzu-mission-control/internal/authctx"
clienterrors "github.com/vmware/terraform-provider-tanzu-mission-control/internal/client/errors"
"github.com/vmware/terraform-provider-tanzu-mission-control/internal/helper"
openapiv3 "github.com/vmware/terraform-provider-tanzu-mission-control/internal/helper/openapi_v3_schema_validator"
policyrecipecustommodel "github.com/vmware/terraform-provider-tanzu-mission-control/internal/models/policy/recipe/custom"
Expand Down Expand Up @@ -117,7 +118,11 @@ func ValidateCustomRecipe(config authctx.TanzuContext, customRecipe map[string]i
recipeData, err := config.TMCConnection.RecipeResourceService.RecipeResourceServiceGet(recipeModel)

if err != nil {
errMessages = append(errMessages, err.Error())
// NOTE: If error is 404 not found then do not fail the planning. This fix ensures that if user tries to create the new custom template
// and assign the same template to the custom policy in a single terraform apply operation will be able to proceed, instead of failing in the planning phase.
if !clienterrors.IsNotFoundError(err) {
errMessages = append(errMessages, err.Error())
}
} else {
errs := ValidateRecipeParameters(recipeData.Recipe.Spec.InputSchema, customRecipe[ParametersKey].(string))

Expand Down
10 changes: 8 additions & 2 deletions templates/guides/tanzu-mission-control_policy.md.tmpl
Original file line number Diff line number Diff line change
Expand Up @@ -37,12 +37,18 @@ In the following example, there are multiple dependencies shown.

{{ tffile "examples/usecases/access_policy_usecase.tf" }}

## Custom Policy on a CLuster Group
## Custom Policy on a Cluster Group

{{ tffile "examples/usecases/custom_policy_usecase.tf" }}

## Custom Template and Custom Policy

Template provides a declarative definition of a policy, which can be used to apply custom constraints on managed kubernetes resources.
Custom policy consumes these declared custom templates to enforce specific policies. One must create the custom template before consuming it the custom policy.
Custom policy consumes these declared custom templates to enforce specific policies. One must create the [custom template][custom-policy-template] before consuming it in the custom policy.
Please refer to custom policy template and custom policy terraform scripts within examples.

[custom-policy-template]: https://docs.vmware.com/en/VMware-Tanzu-Mission-Control/services/tanzumc-using/GUID-F147492B-04FD-4CFD-8D1F-66E36D40D49C.html

## Refer the following example for creating custom policy template and assign it to custom policy

{{ tffile "examples/usecases/custom_policy_with_custom_template_usecase.tf" }}
Loading