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

ENG-14702: Update documentation for repo level policies #602

Merged
merged 5 commits into from
Jan 2, 2025
Merged
Show file tree
Hide file tree
Changes from 1 commit
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
12 changes: 6 additions & 6 deletions cyral/internal/regopolicy/resource_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -68,20 +68,20 @@ var (
regoPolicyInstanceOnlyRequiredArguments = RegoPolicyInstanceTestParameters{
policy: regopolicy.RegoPolicyInstancePayload{
RegoPolicyInstance: regopolicy.RegoPolicyInstance{
Name: "some-rate-limit-policy",
TemplateID: "rate-limit",
Parameters: "{\"rateLimit\":7,\"labels\":[\"EMAIL\"],\"alertSeverity\":\"high\",\"block\":false}",
Name: "some-object-protection-policy",
TemplateID: "object-protection",
Parameters: "{\"block\":false,\"objectType\":\"role/user\",\"alertSeverity\":\"high\",\"monitorCreates\":true,\"monitorDrops\":false,\"monitorAlters\":false}",
},
},
policyCategory: "SECURITY",
}
regoPolicyInstanceAllArguments = RegoPolicyInstanceTestParameters{
policy: regopolicy.RegoPolicyInstancePayload{
RegoPolicyInstance: regopolicy.RegoPolicyInstance{
Name: "some-rate-limit-policy",
Name: "some-object-protection-policy",
TemplateID: "object-protection",
Parameters: "{\"block\":false,\"objectType\":\"role/user\",\"alertSeverity\":\"high\",\"monitorCreates\":true,\"monitorDrops\":false,\"monitorAlters\":false}",
Description: "Some description.",
TemplateID: "rate-limit",
Parameters: "{\"rateLimit\":7,\"labels\":[\"EMAIL\"],\"alertSeverity\":\"high\",\"block\":false}",
Enabled: true,
Scope: &regopolicy.RegoPolicyInstanceScope{
RepoIDs: []string{"2U4prk5o6yi1rTvvXyImz8lgbgG"},
Expand Down
166 changes: 9 additions & 157 deletions docs/resources/rego_policy_instance.md
Original file line number Diff line number Diff line change
Expand Up @@ -71,167 +71,19 @@ All templates use parameters defined as JSON, below is a list of all the corresp

-> You can also use the Cyral API `GET` `/v1/regopolicies/templates` to retrieve all existing templates and their corresponding parameters schema.

### Data Firewall (data-firewall)
yoursnerdly marked this conversation as resolved.
Show resolved Hide resolved

- `dataSet` (String) Data Set.
- `dataFilter` (String) Data filter that will be applied when anyone tries to read the specified data labels from the data set.
- `tags` (Array) Tags.
- `labels` (Array) Data Labels.
- `excludedIdentities` (Object) Identities that will be excluded from this policy. See [identityList](#objects--identityList).

### Data Masking (data-masking)

- `maskType` (String) Mask Type (E.g.: `NULL_MASK`, `CONSTANT_MASK`, `MASK`).
- `maskArguments` (Array) Mask Argument associated to the given Mask Type (E.g.: Replacement Value).
- `tags` (Array) Tags.
- `labels` (Array) Data Labels.
- `identities` (Object) Identities associated to the policy. If empty, the policy will be associated to all identities. See [identities](#objects--identities).
- `dbAccounts` (Object) Database Accounts associated to the policy. If empty, the policy will be associated to any database account. See [dbAccounts](#objects--dbAccounts).

### Data Protection (data-protection)

- `block` (Boolean) Policy action to block.
- `monitorReads` (Boolean) Monitor read operations.
- `monitorUpdates` (Boolean) Monitor update operations.
- `monitorDeletes` (Boolean) Monitor delete operations.
- `tags` (Array) Tags.
- `labels` (Array) Data Labels.
- `identities` (Object) Identities associated to the policy. If empty, the policy will be associated to all identities. See [identities](#objects--identities).
- `dbAccounts` (Object) Database Accounts associated to the policy. If empty, the policy will be associated to any database account. See [dbAccounts](#objects--dbAccounts).
- `alertSeverity` (String) Policy action to alert, using the respective severity. Allowed values are: `low`, `medium`, `high`.

### Ephemeral Grant (EphemeralGrantPolicy)

- `repoAccount` (String) Repository Account Name.
- `repo` (String) Repository Name.
- `allowedSensitiveAttributes` (Array) Allowed Sensitive Attributes.

### Rate Limit (rate-limit)

- `rateLimit` (Integer) Maximum number of rows that can be returned per hour. Note: the value must be an integer greater than zero.
- `block` (Boolean) Policy action to enforce.
- `tags` (Array) Tags.
- `labels` (Array) Data Labels.
- `identities` (Object) Identities associated to the policy. If empty, the policy will be associated to all identities. See [identities](#objects--identities).
- `dbAccounts` (Object) Database Accounts associated to the policy. If empty, the policy will be associated to any database account. See [dbAccounts](#objects--dbAccounts).
- `alertSeverity` (String) Policy action to alert, using the respective severity. Allowed values are: `low`, `medium`, `high`.

### Read Limit (read-limit)

- `rowLimit` (Integer) Maximum number of rows that can be read per query. Note: the value must be an integer greater than zero.
- `block` (Boolean) Policy action to enforce.
- `appliesToAllData` (Boolean) Whether the policy should apply to the entire repository data.
- `tags` (Array) Tags.
- `labels` (Array) Data Labels.
- `identities` (Object) Identities associated to the policy. If empty, the policy will be associated to all identities. See [identities](#objects--identities).
- `dbAccounts` (Object) Database Accounts associated to the policy. If empty, the policy will be associated to any database account. See [dbAccounts](#objects--dbAccounts).
- `alertSeverity` (String) Policy action to alert, using the respective severity. Allowed values are: `low`, `medium`, `high`.

### Repository Protection (repository-protection)
### Object Protection (object-protection)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since we're updating this, maybe add information about the two new templates (ungoverned-statements and fail-closed) should be added as well.


- `rowLimit` (Integer) Maximum number of rows that can be modified per query. Note: the value must be an integer greater than zero.
- `monitorUpdates` (Boolean) Monitor update operations.
- `monitorDeletes` (Boolean) Monitor delete operations.
- `identities` (Object) Identities associated to the policy. If empty, the policy will be associated to all identities. See [identities](#objects--identities).
- `dbAccounts` (Object) Database Accounts associated to the policy. If empty, the policy will be associated to any database account. See [dbAccounts](#objects--dbAccounts).
yoursnerdly marked this conversation as resolved.
Show resolved Hide resolved
- `alertSeverity` (String) Policy action to alert, using the respective severity. Allowed values are: `low`, `medium`, `high`.
- `objectType` (String) The type of object to monitor or protect. Supported types include tables, views, roles/users, and schemas. Specific actions depend on the object type.
- `block` (Boolean) Indicates whether unauthorized operations should be blocked. If true, operations violating the policy are prevented..
- `monitorCreates` (Boolean) Specifies whether to monitor 'CREATE' operations for the defined object type. Applies only to relevant object types.
- `monitorDrops` (Boolean) Specifies whether to monitor 'DROP' operations for the defined object type. Applies only to relevant object types.
- `monitorAlters` (Boolean) Specifies whether to monitor 'ALTER' operations for the defined object type. Applies only to relevant object types.
- `objects` (Array) A list of specific objects (e.g., tables or views) to monitor or protect. Required for 'table' or 'view' object types. Not applicable to 'role/user' or 'schema'.
- `identities` (Object) Defines users, groups, or emails that are included or excluded from the policy. If included identities are defined, only those users are exempt from policy enforcement. Excluded identities are always subject to the policy.
- `dbAccounts` (Object) Defines database accounts to include or exclude from the policy. Excluded accounts are not subject to the policy, while included accounts must adhere to it.

### Service Account Abuse (service-account-abuse)

- `block` (Boolean) Policy action to enforce.
- `serviceAccounts` (Array) Service accounts for which end user attribution is always required.
- `alertSeverity` (String) Policy action to alert, using the respective severity. Allowed values are: `low`, `medium`, `high`.

### User Segmentation (user-segmentation)

- `dataSet` (String) Data Set.
- `dataFilter` (String) Data filter that will be applied when anyone tries to read the specified data labels from the data set.
- `tags` (Array) Tags.
- `labels` (Array) Data Labels.
- `includedIdentities` (Object) Identities that cannot see restricted records. See [identityList](#objects--identityList).
- `includedDbAccounts` (Array) Database accounts cannot see restricted records.

<a id="parameter-objects"></a>

### Objects

<a id="objects--identities"></a>

- `identities` (Object) Identities. See properties below:
- `included` (Object) Included Identities. See [identityList](#objects--identityList).
- `excluded` (Object) Excluded Identities. See [identityList](#objects--identityList).
<a id="objects--dbAccounts"></a>
- `dbAccounts` (Object) Database Accounts. See properties below:
- `included` (Array) Included Database Accounts.
- `excluded` (Array) Excluded Database Accounts.
<a id="objects--identityList"></a>
- `identityList` (Object) Identity List. See properties below:
- `userNames` (Array) Identity Emails.
- `emails` (Array) Identity Usernames.
- `groups` (Array) Identity Groups.

<!-- schema generated by tfplugindocs -->

## Schema

### Required

- `category` (String) Policy category. List of supported categories:
- `SECURITY`
- `GRANT`
- `USER_DEFINED`
- `name` (String) Policy name.
- `template_id` (String) Policy template identifier. Predefined templates are:
- `data-firewall`
- `data-masking`
- `data-protection`
- `EphemeralGrantPolicy`
- `rate-limit`
- `read-limit`
- `repository-protection`
- `service-account-abuse`
- `user-segmentation`

### Optional

- `description` (String) Policy description.
- `duration` (String) Policy duration. The policy expires after the duration specified. Should follow the protobuf duration string format, which corresponds to a sequence of decimal numbers suffixed by a 's' at the end, representing the duration in seconds. For example: `300s`, `60s`, `10.50s`, etc.
- `enabled` (Boolean) Enable/disable the policy. Defaults to `false` (Disabled).
- `parameters` (String) Policy parameters. The parameters vary based on the policy template schema.
- `scope` (Block Set, Max: 1) Determines the scope that the policy applies to. It can be used to create a repo-level policy by specifying the corresponding `repo_ids` that this policy should be applied. (see [below for nested schema](#nestedblock--scope))
- `tags` (List of String) Tags that can be used to categorize the policy.

### Read-Only

- `created` (Set of Object) Information regarding the policy creation. (see [below for nested schema](#nestedatt--created))
- `id` (String) The resource identifier. It is a composed ID that follows the format `{category}/{policy_id}`.
- `last_updated` (Set of Object) Information regarding the policy last update. (see [below for nested schema](#nestedatt--last_updated))
- `policy_id` (String) ID of this rego policy instance in Cyral environment.

<a id="nestedblock--scope"></a>

### Nested Schema for `scope`

Required:

- `repo_ids` (List of String) A list of repository identifiers that belongs to the policy scope. The policy will be applied at repo-level for every repository ID included in this list. This is equivalent of creating a repo-level policy in the UI for a given repository.

<a id="nestedatt--created"></a>

### Nested Schema for `created`

Read-Only:

- `actor` (String)
- `actor_type` (String)
- `timestamp` (String)

<a id="nestedatt--last_updated"></a>

### Nested Schema for `last_updated`

Read-Only:

- `actor` (String)
- `actor_type` (String)
- `timestamp` (String)
16 changes: 8 additions & 8 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@ go 1.22.7
toolchain go1.23.3

require (
buf.build/gen/go/cyral/policy/grpc/go v1.5.1-20241204234652-6dee75984790.1
buf.build/gen/go/cyral/policy/protocolbuffers/go v1.36.0-20241204234652-6dee75984790.1
buf.build/gen/go/cyral/policy/grpc/go v1.5.1-20241204234652-6dee75984790.2
buf.build/gen/go/cyral/policy/protocolbuffers/go v1.36.1-20241204234652-6dee75984790.1
github.com/aws/aws-sdk-go v1.55.5
github.com/google/uuid v1.6.0
github.com/hashicorp/terraform-plugin-docs v0.19.4
Expand All @@ -16,13 +16,13 @@ require (
golang.org/x/exp v0.0.0-20241217172543-b2144cdd0a67
golang.org/x/oauth2 v0.24.0
google.golang.org/grpc v1.69.2
google.golang.org/protobuf v1.36.0
google.golang.org/protobuf v1.36.1
)

require (
buf.build/gen/go/cyral/utils/protocolbuffers/go v1.36.0-20241202152456-363249a7515c.1 // indirect
buf.build/gen/go/envoyproxy/protoc-gen-validate/protocolbuffers/go v1.36.0-20240617172848-daf171c6cdb5.1 // indirect
buf.build/gen/go/grpc-ecosystem/grpc-gateway/protocolbuffers/go v1.36.0-20240617172850-a48fcebcf8f1.1 // indirect
buf.build/gen/go/cyral/utils/protocolbuffers/go v1.36.1-20241202152456-363249a7515c.1 // indirect
buf.build/gen/go/envoyproxy/protoc-gen-validate/protocolbuffers/go v1.36.1-20240617172848-daf171c6cdb5.1 // indirect
buf.build/gen/go/grpc-ecosystem/grpc-gateway/protocolbuffers/go v1.36.1-20241220201140-4c5ba75caaf8.1 // indirect
cloud.google.com/go/compute/metadata v0.6.0 // indirect
github.com/BurntSushi/toml v1.2.1 // indirect
github.com/Kunde21/markdownfmt/v3 v3.1.0 // indirect
Expand Down Expand Up @@ -90,8 +90,8 @@ require (
golang.org/x/text v0.21.0 // indirect
golang.org/x/tools v0.28.0 // indirect
google.golang.org/appengine v1.6.8 // indirect
google.golang.org/genproto/googleapis/api v0.0.0-20241219192143-6b3ec007d9bb // indirect
google.golang.org/genproto/googleapis/rpc v0.0.0-20241219192143-6b3ec007d9bb // indirect
google.golang.org/genproto/googleapis/api v0.0.0-20241223144023-3abc09e42ca8 // indirect
google.golang.org/genproto/googleapis/rpc v0.0.0-20241223144023-3abc09e42ca8 // indirect
gopkg.in/yaml.v2 v2.3.0 // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect
)
32 changes: 16 additions & 16 deletions go.sum
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
buf.build/gen/go/cyral/policy/grpc/go v1.5.1-20241204234652-6dee75984790.1 h1:tl6pcZSURzy71NYelbi7ZARClsFxsOy3Zz97lfgraU8=
buf.build/gen/go/cyral/policy/grpc/go v1.5.1-20241204234652-6dee75984790.1/go.mod h1:nnv6Imx5xapOLV612Q4oJ2z7hQDz1FyO0bJGImPJKEU=
buf.build/gen/go/cyral/policy/protocolbuffers/go v1.36.0-20241204234652-6dee75984790.1 h1:ULg02uNwg6d5ACf3d/svhmWQxI3XOUa+zsT9PcqGE7U=
buf.build/gen/go/cyral/policy/protocolbuffers/go v1.36.0-20241204234652-6dee75984790.1/go.mod h1:2MVlkoQXXNnCCegVZo/PrM697vKjMdtIZKZpsMjq06E=
buf.build/gen/go/cyral/utils/protocolbuffers/go v1.36.0-20241202152456-363249a7515c.1 h1:AEZ/C4Xb3Q5flHtGWznh60EWLz83mMhqviRVDHzEXMc=
buf.build/gen/go/cyral/utils/protocolbuffers/go v1.36.0-20241202152456-363249a7515c.1/go.mod h1:L7zSeN1DerTkeWs9ZtNPOvFBz4v2rKSCks5OOCh5W0Y=
buf.build/gen/go/envoyproxy/protoc-gen-validate/protocolbuffers/go v1.36.0-20240617172848-daf171c6cdb5.1 h1:lVToKI30NYvd2m/n9oHlbctPyL1z7qOl3J2kTIVLqbQ=
buf.build/gen/go/envoyproxy/protoc-gen-validate/protocolbuffers/go v1.36.0-20240617172848-daf171c6cdb5.1/go.mod h1:z6TXPjhMrkUwpR6h+lbyDMJ9sJ/eGltAclrTUW9gbE0=
buf.build/gen/go/grpc-ecosystem/grpc-gateway/protocolbuffers/go v1.36.0-20240617172850-a48fcebcf8f1.1 h1:nAE4HLCyHRljGiUA1PQ0jsl2VvuHfRg/AvAsIP280qA=
buf.build/gen/go/grpc-ecosystem/grpc-gateway/protocolbuffers/go v1.36.0-20240617172850-a48fcebcf8f1.1/go.mod h1:9kAozfForX2SS4gDDl/P+ImNbDypB9unxBZQqsyahYA=
buf.build/gen/go/cyral/policy/grpc/go v1.5.1-20241204234652-6dee75984790.2 h1:Nb/a7uA1oABwVaNLaNpZ4wHaF2ruUWYqX47RF7mp1mc=
buf.build/gen/go/cyral/policy/grpc/go v1.5.1-20241204234652-6dee75984790.2/go.mod h1:XTNaF/nhX6bf6V7wQOHqHF0VoVYh9iQSMIhzKxV7luo=
buf.build/gen/go/cyral/policy/protocolbuffers/go v1.36.1-20241204234652-6dee75984790.1 h1:Znp6P4KIpZu0y+pwJfEJKK7OQX/tHAwueAvl5SZNJvA=
buf.build/gen/go/cyral/policy/protocolbuffers/go v1.36.1-20241204234652-6dee75984790.1/go.mod h1:jObqyFs4Fbkj5YhlRelQM8Q93QTIFGws4cBAh8TMA/Q=
buf.build/gen/go/cyral/utils/protocolbuffers/go v1.36.1-20241202152456-363249a7515c.1 h1:HVBV6zROo/gV3oMuCHqONvzN/qGHe80FlvoU1LP7SSs=
buf.build/gen/go/cyral/utils/protocolbuffers/go v1.36.1-20241202152456-363249a7515c.1/go.mod h1:8Oifv1n03AaERmI2kDvZ0Sxr5NyXxG/v+9QLakIqn4M=
buf.build/gen/go/envoyproxy/protoc-gen-validate/protocolbuffers/go v1.36.1-20240617172848-daf171c6cdb5.1 h1:3NW/OKYVUjacnT14MdeSrRwrv20SU4hfbDl+Cqspaf0=
buf.build/gen/go/envoyproxy/protoc-gen-validate/protocolbuffers/go v1.36.1-20240617172848-daf171c6cdb5.1/go.mod h1:L3a8fJ4WVDtMqrivTUIK2pmaOZ/GF7qFq9xcSbeyA2M=
buf.build/gen/go/grpc-ecosystem/grpc-gateway/protocolbuffers/go v1.36.1-20241220201140-4c5ba75caaf8.1 h1:LuhF0tLV6LajBr3N1uHRWt2VtgdNB9qzhSwJwsD4nNk=
buf.build/gen/go/grpc-ecosystem/grpc-gateway/protocolbuffers/go v1.36.1-20241220201140-4c5ba75caaf8.1/go.mod h1:B0L3Am51xJ+EaDE1BkvpJEYvc22m404djbLMTWy3me0=
cloud.google.com/go/compute/metadata v0.6.0 h1:A6hENjEsCDtC1k8byVsgwvVcioamEHvZ4j01OwKxG9I=
cloud.google.com/go/compute/metadata v0.6.0/go.mod h1:FjyFAW1MW0C203CEOMDTu3Dk1FlqW3Rga40jzHL4hfg=
dario.cat/mergo v1.0.0 h1:AGCNq9Evsj31mOgNPcLyXc+4PNABt905YmuqPYYpBWk=
Expand Down Expand Up @@ -291,16 +291,16 @@ golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8T
google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
google.golang.org/appengine v1.6.8 h1:IhEN5q69dyKagZPYMSdIjS2HqprW324FRQZJcGqPAsM=
google.golang.org/appengine v1.6.8/go.mod h1:1jJ3jBArFh5pcgW8gCtRJnepW8FzD1V44FJffLiz/Ds=
google.golang.org/genproto/googleapis/api v0.0.0-20241219192143-6b3ec007d9bb h1:B7GIB7sr443wZ/EAEl7VZjmh1V6qzkt5V+RYcUYtS1U=
google.golang.org/genproto/googleapis/api v0.0.0-20241219192143-6b3ec007d9bb/go.mod h1:E5//3O5ZIG2l71Xnt+P/CYUY8Bxs8E7WMoZ9tlcMbAY=
google.golang.org/genproto/googleapis/rpc v0.0.0-20241219192143-6b3ec007d9bb h1:3oy2tynMOP1QbTC0MsNNAV+Se8M2Bd0A5+x1QHyw+pI=
google.golang.org/genproto/googleapis/rpc v0.0.0-20241219192143-6b3ec007d9bb/go.mod h1:lcTa1sDdWEIHMWlITnIczmw5w60CF9ffkb8Z+DVmmjA=
google.golang.org/genproto/googleapis/api v0.0.0-20241223144023-3abc09e42ca8 h1:st3LcW/BPi75W4q1jJTEor/QWwbNlPlDG0JTn6XhZu0=
google.golang.org/genproto/googleapis/api v0.0.0-20241223144023-3abc09e42ca8/go.mod h1:klhJGKFyG8Tn50enBn7gizg4nXGXJ+jqEREdCWaPcV4=
google.golang.org/genproto/googleapis/rpc v0.0.0-20241223144023-3abc09e42ca8 h1:TqExAhdPaB60Ux47Cn0oLV07rGnxZzIsaRhQaqS666A=
google.golang.org/genproto/googleapis/rpc v0.0.0-20241223144023-3abc09e42ca8/go.mod h1:lcTa1sDdWEIHMWlITnIczmw5w60CF9ffkb8Z+DVmmjA=
google.golang.org/grpc v1.69.2 h1:U3S9QEtbXC0bYNvRtcoklF3xGtLViumSYxWykJS+7AU=
google.golang.org/grpc v1.69.2/go.mod h1:vyjdE6jLBI76dgpDojsFGNaHlxdjXN9ghpnd2o7JGZ4=
google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw=
google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc=
google.golang.org/protobuf v1.36.0 h1:mjIs9gYtt56AzC4ZaffQuh88TZurBGhIJMBZGSxNerQ=
google.golang.org/protobuf v1.36.0/go.mod h1:9fA7Ob0pmnwhb644+1+CVWFRbNajQ6iRojtC/QF5bRE=
google.golang.org/protobuf v1.36.1 h1:yBPeRvTftaleIgM3PZ/WBIZ7XM/eEYAaEyCwvyjq/gk=
google.golang.org/protobuf v1.36.1/go.mod h1:9fA7Ob0pmnwhb644+1+CVWFRbNajQ6iRojtC/QF5bRE=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY=
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
Expand Down
Loading
Loading