Skip to content

cub unit set-protection

cub unit set-protection

Protect paths or resources of a unit from being overwritten by a merge

Synopsis

Set the Protected flags stored on a unit's MutationSources.

A protected path is a local override a merge must not overwrite. An unprotected path holds a value that came from somewhere else -- a clone, an upgrade, a merge -- and is the merge's to update. Merges consult these stored values by default, and they are then the only mechanism preserving local overrides; a WhereMutation filter protects further paths on top of them. Turning the merge's subtraction step on (via --merge-enable-subtraction or a link's MergeEnableSubtraction) preserves them by a second mechanism, and the stored values are not consulted.

Each --protect and --unprotect takes RESOURCE_TYPE:RESOURCE_NAME:PATH, where RESOURCE_TYPE and RESOURCE_NAME identify the resource (e.g. apps/v1/Deployment and default/myapp) and PATH is a path within that resource. RESOURCE_TYPE may be left empty, as :default/myapp:PATH, when the name alone picks out the resource, and it matches in any API version. RESOURCE_NAME is the whole name, or a name the resource had before a rename; a name without a namespace (myapp) matches that name in any namespace, and has to match only one resource. PATH names a list element by merge key (containers.?name=app.image) or by position (containers.0.image), and * stands for every element or key there is (containers.*.image). Repeat either flag to set several paths or resources at once, and combine them to protect some paths and re-open others in one revision; a path named on its own decides over a * that also names it.

Leave out PATH, as RESOURCE_TYPE:RESOURCE_NAME, to protect or re-open the resource as a whole. A merge withholds every change to a resource protected as a whole -- deleting it and replacing it included -- whatever its paths say, and its paths' own protection takes effect again once it is re-opened. That is how to protect a resource a change added whole, such as a ServiceAccount a variant added, since such a resource has no paths of its own to protect. A resource the unit deleted can be protected as a whole too, which keeps a merge from adding it back. A path that is not already present inherits the closest ancestor mutation's provenance. Protecting a path does not protect a path beneath it that a change of its own wrote, such as an env entry's value set after the entry was added: name that path too, and check the result with 'cub unit blame', which marks a protected field P, and a resource protected as a whole P on its (resource) row, deleted resources included.

--unprotect-all clears every protected path and resource of the unit, so a future merge may overwrite all of them. Combined with --protect, it clears the rest first, and the paths named are the only ones protected afterwards.

Setting protection creates a new revision only if it changes; pass --change-desc to record why on it.

It prints the unit's MutationSources with -o json, yaml, jq or yq, or after its confirmation with --verbose.

Examples:

  # Protect the downstream replica count from being overwritten by upgrades
  cub unit set-protection my-unit \
    --protect "apps/v1/Deployment:default/myapp:spec.replicas" \
    --change-desc "Prod runs more replicas than the base"

  # Re-open a path so a future merge may overwrite it again
  cub unit set-protection my-unit \
    --unprotect "apps/v1/Deployment:default/myapp:spec.replicas"

  # Keep a ServiceAccount the variant added from being replaced by upgrades
  cub unit set-protection my-unit \
    --protect "v1/ServiceAccount:default/myapp"

  # Protect every container's image, naming the resource without its type or namespace
  cub unit set-protection my-unit \
    --protect ":myapp:spec.template.spec.containers.*.image"

  # Re-open every protected path of the unit
  cub unit set-protection my-unit --unprotect-all

  # Make the replica count the only protected path
  cub unit set-protection my-unit --unprotect-all \
    --protect "apps/v1/Deployment:default/myapp:spec.replicas"
cub unit set-protection <unit-slug> [--unprotect-all] [--protect <spec> ...] [--unprotect <spec> ...] [flags]

Options

      --change-desc string      change description recorded on the revision the edit creates
  -h, --help                    help for set-protection
  -o, --output string           Output format. One of: json, yaml, name, wide, mutations, jq=<expr>, yq=<expr>, custom-columns=<spec>
      --protect stringArray     path to protect from merges, as RESOURCE_TYPE:RESOURCE_NAME:PATH, or a whole resource as RESOURCE_TYPE:RESOURCE_NAME; RESOURCE_TYPE may be empty (repeatable)
      --quiet                   No default output.
      --unprotect stringArray   path to re-open to merges, as RESOURCE_TYPE:RESOURCE_NAME:PATH, or a whole resource as RESOURCE_TYPE:RESOURCE_NAME; RESOURCE_TYPE may be empty (repeatable)
      --unprotect-all           re-open every protected path of the unit to merges, before applying --protect and --unprotect
      --verbose                 Detailed output, additive with default output

Options inherited from parent commands

      --component string   the Component of --variant, when that names the variant alone; --variant <component>/<variant> says the same in one flag
      --context string     The context to use for this command
      --debug              Debug output
      --space string       space to operate in, by slug or UUID. Omitted, a list or bulk operation spans the organization and a single entity is named as <space>/<slug>; "*" means the same as omitting it
      --variant string     variant to operate in, as <component>/<variant>, or as <variant> with --component: the space naming that Component whose Variant label is <variant>. The same scope as --space, named by what it is rather than by the space's slug; the two cannot be combined

SEE ALSO