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

SHIP-0004: Build Environment Variables #10

Merged

Conversation

adambkaplan
Copy link
Member

This proposal introduces the concept of build strategy overrides,
whereby a developer can override the behavior declared in a build
strategy. Augmenting the environment variables in a build step is
presented as the first type of override that is made available.

The proposal includes rules and behavior for environment variables that
are declared in a build strategy. Specifically, builds cannot overwrite
declared environment variables unless said env var is exposed as a build
parameter.

@openshift-ci openshift-ci bot requested review from qu1queee and sbose78 June 3, 2021 21:47
Copy link
Member

@SaschaSchwarze0 SaschaSchwarze0 left a comment

Choose a reason for hiding this comment

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

Hm, certainly less complex. But, it forces the build user to know the names of the steps in the build strategy. Today ...

  • most of our sample build strategies (actually all beside s2i) today have only one real step (ignoring helper steps like prepare and results) where environment variable overrides make sense
  • as far as I can see it, no build strategy has any step combination where an environment variable needs to be overwritten for one of the steps but must not be set on the others because it would otherwise break them. (or is there any env variable that makes sense for s2i that would break kaniko or buildah; or vice versa?)

So, is it really necessary that our build users need to know the names of the strategy steps?

@adambkaplan
Copy link
Member Author

most of our sample build strategies (actually all beside s2i) today have only one real step (ignoring helper steps like prepare and results) where environment variable overrides make sense

I think establishing a community convention where "build" is the main step in any BuildStrategy would help here. Users wouldn't need to know this particularly detail offhand to inject environment variables in 80-90% of build strategies.

as far as I can see it, no build strategy has any step combination where an environment variable needs to be overwritten for one of the steps but must not be set on the others because it would otherwise break them. (or is there any env variable that makes sense for s2i that would break kaniko or buildah; or vice versa?)

Proxy environment variables could fall into this bucket. I'd rather err on the side of caution here, than have a case down the road where we need to twist our API to apply environment variables to only certain steps in a build strategy.

@adambkaplan adambkaplan changed the title SHIP-0004: Overrides for Environment Variables SHIP-0004: Build Environment Variables Jun 7, 2021
@SaschaSchwarze0
Copy link
Member

SaschaSchwarze0 commented Jun 7, 2021

Hm, I do understand your mindset of being prepared for future edge cases. But, we should take care to not let those pay the price that are on the 95 % path. Question now is: can we find an easy solution for those use cases without restricting those who need to go for the edge case:

  • A user wants to set the same environment variable for multiple steps in a strategy, like maybe for all buildah steps if somebody writes a strategy like we had until I recently consolidated that.
  • A user wants to set an environment variable for a build strategy that has only one step.
  • A user wants to set an environment variable for a build strategy step. The strategy also has other steps but they do not misbehave if they also have the envvar set. -> It does not matter if the envvar is applied globally.

I do not have the perfect suggestion for this, but some ideas:

  • Tekton makes it like this in a slightly different context.
  • One could allow the special value * as step name in your API.
  • We move the easy support for the common use cases to higher layers (CLI, other clients).

@adambkaplan
Copy link
Member Author

@SaschaSchwarze0 I've added a CLI enhancement to the proposal so that users can easily see the steps of a build strategy. I wish we could have surfaced this via kubectl get, but alas that didn't seem to work out in my experiments.

@adambkaplan
Copy link
Member Author

adambkaplan commented Jun 7, 2021

One could allow the special value * as step name in your API.

This makes a lot of sense.

We move the easy support for the common use cases to higher layers (CLI, other clients).

Another good idea - enhance the cli so developers can pass env vars into all build steps.

@gabemontero
Copy link
Member

One could allow the special value * as step name in your API.

This makes a lot of sense.

We move the easy support for the common use cases to higher layers (CLI, other clients).

Another good idea - enhance the cli so developers can pass env vars into all build steps.

fwiw the oc command has analogous function wrt env vars and openshift builds

still need to make a pass at this EP @adambkaplan @SaschaSchwarze0 before I can comment with some level of intelligence on the other points, but this specific point was "makeable now" :-)

Copy link
Member

@gabemontero gabemontero left a comment

Choose a reason for hiding this comment

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

Just a minor potential update suggestion (I want balk much if you disagree @adambkaplan ) and a question around the current non-goals and the initial discussions we had around the long term potential wrt other apects of the step/container field in the strategy.

+1 on the its simpler, more conservative (which is admittedly safer at this point wrt user input into the project)

Otherwise, from the reviewers of my PR, aside from @SaschaSchwarze0 and whether he and his users can at least progress with the needing to know the build step element, I'm curious what @sbose78 thinks, as he was the one who prompted me about "allow" list type functionality. Among other things, I don't recall if his input stemmed from any early customer discussion or not.

Certainly you have a explicit way of declaring a finite set of what is allowed with this approach. An an implicit way of declaring what is not allowed (i.e. if it ain't in a step already, it is not allowed).

But sure, let's see what feedback we get once we implement this, and how much of a call for decoupling from strategy build step knowledge, and as a result, potential need for explicit not allowed / deny lists, and then add that later on if need be.

ships/0004-build-env-vars.md Outdated Show resolved Hide resolved
ships/0004-build-env-vars.md Show resolved Hide resolved
@gabemontero
Copy link
Member

/approve

Copy link
Contributor

@qu1queee qu1queee left a comment

Choose a reason for hiding this comment

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

I´m late to the party. Adding minor and major request for changes. I know you folks have been very diligent on this particular topic, so kudos for that. I read @gabemontero proposal in advance, to get the right rational for this one.

ships/0004-build-env-vars.md Outdated Show resolved Hide resolved
ships/0004-build-env-vars.md Show resolved Hide resolved
ships/0004-build-env-vars.md Outdated Show resolved Hide resolved

## Proposal

### User Stories
Copy link
Contributor

Choose a reason for hiding this comment

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

It would be good if we can layout more elaborated user stories. For example, I took a look on the Tekton/Catalog, as this should provide real examples on how people uses env support there. The majority of the use cases are a combination of:

  • [1] env vars + the script field per step
  • [2] env vars defined because someone knows in advance that the image in the step will read it ( very specific knowledge )

Because today we dont support the script field, our use case today for envs vars is merely related to [2]. That does not mean that we cannot support [1] in the future, so some ideas for more user stories:

Copy link
Member Author

Choose a reason for hiding this comment

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

Interesting to note that your example with the Tekton catalog entry for buildpacks, they expose build time environment variables as a Tekton parameter: https://github.com/tektoncd/catalog/blob/main/task/buildpacks/0.3/buildpacks.yaml#L32-L34

This IMO validates the problem statement (developers need to be able to manipulate arbitrary environment variables) and our solution (provide an API to append environment variables)

ships/0004-build-env-vars.md Show resolved Hide resolved
ships/0004-build-env-vars.md Outdated Show resolved Hide resolved
@adambkaplan
Copy link
Member Author

@gabemontero @SaschaSchwarze0 @qu1queee @sbose78 this is ready for final review as an Implementable proposal.

Copy link
Contributor

@qu1queee qu1queee left a comment

Choose a reason for hiding this comment

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

@adambkaplan nice work! I'm requesting two minor things from my side, I'm happy to approve after that!

ships/0004-build-env-vars.md Outdated Show resolved Hide resolved
ships/0004-build-env-vars.md Outdated Show resolved Hide resolved
@gabemontero
Copy link
Member

tell you what @qu1queee I'll

/approve

and let you lgtm once @adambkaplan updates basaed on you comments yesterday

@gabemontero
Copy link
Member

[APPROVALNOTIFIER] This PR is NOT APPROVED

This pull-request has been approved by: gabemontero
To complete the pull request process, please ask for approval from adambkaplan after the PR has been reviewed.

The full list of commands accepted by this bot can be found here.
Needs approval from an approver in each of these files:

* **[OWNERS](https://github.com/shipwright-io/community/blob/main/OWNERS)**

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

ah never mind :-)

I'll lgtm if need be after your comments are addressed @qu1queee

This proposal provides a mechanism for developers to append environment
variables to a Build or BuildRun. Many programming languages and
frameworks use environment variables to tune the behavior of their
tooling. For image building tools that aggregate dev frameworks like
Cloud Native Buildpacks, this capaiblity is important because the
number of environment variables that can be tuned is unbounded. Other
developer tools like maven use environment variables to inject
private repository credentials.

This proposal defines the behavior of how environment variables are
defined at the BuildStrategy, Build, and BuildRun levels. It also
proposes enhancements to the shp CLI that make it easier for developers
to set environment variables at build time.
@adambkaplan
Copy link
Member Author

@qu1queee @gabemontero updated

@gabemontero
Copy link
Member

/lgtm

@openshift-ci openshift-ci bot added the lgtm Indicates that a PR is ready to be merged. label Jun 30, 2021
@qu1queee qu1queee self-requested a review July 2, 2021 06:41
Copy link
Contributor

@qu1queee qu1queee left a comment

Choose a reason for hiding this comment

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

great, approving.

@qu1queee
Copy link
Contributor

qu1queee commented Jul 2, 2021

/lgtm

@sbose78 you are marked as an approver on this EP. Do you mind giving your final thoughts pls.

#### Story: Alter build behavior via environment variables

As a nodejs developer using buildpacks
I want to set the `NPM_INCLUDE` environment variable in my Build and BuildRuns
Copy link
Member

Choose a reason for hiding this comment

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

👍


As a build strategy author
I want to keep fixed values for some environment variables in my build strategy
So that I don't allow end users to enable insecure or potentially harmful features.
Copy link
Member

Choose a reason for hiding this comment

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

👍


As a Java developer using maven to build my application (via buildpacks or source-to-image)
I want to use environment variables to pass usernames and passwords to values defined in my `pom.xml` file
So that I don't store sensitive information in source control.
Copy link
Member

Choose a reason for hiding this comment

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

👍

### Risks and Mitigations

There is a risk that developers will want an environment variable to be set in one build step, but unset or restored to a default value in a different build step.
This could be addressed in a future enhancemenent via separate API field (ex: `excludeFromSteps`).
Copy link
Member

Choose a reason for hiding this comment

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

👍

## Drawbacks

The primary drawback is that build strategy authors need to provide fixed or default values for environment variables they want to control.
A strategy author cannot simply declare that an environment variable is "off limits" - they must declare when a controlled env var is used and what value it should have.
Copy link
Member

Choose a reason for hiding this comment

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

👍 This is a concern I've had, but we can start with what we have in this proposal.

Also, when should we really care about off-limit environment variables ? When a user uses an environment variable to break out of the sandbox of a container. However, a secure container platform wouldn't let you do that if the pod isn't being run with elevated privileges/capabilities.

Copy link
Member Author

Choose a reason for hiding this comment

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

CVE-2021-20182 is a truly compelling case for a build author to declare an environment variable off limits. Setting the BUILDAH_ISOLATION env var to chroot AND running with the privileged: true security context exposes devices on the node (storage, network, etc.).


This proposal won't allow developers to set environment variables in some build strategy steps, but not others.
This capability implies that the developer knows some information about the build strategy, which the community consideres an advanced skill.
The Shipwright community does not expect developers to know the names of the steps declared in build strategies.
Copy link
Member

Choose a reason for hiding this comment

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

👍

A strategy author cannot simply declare that an environment variable is "off limits" - they must declare when a controlled env var is used and what value it should have.
This is a fair compromise to establish a clear contract between a build strategy author and the developer augmenting the build strategy's behavior.

This proposal won't allow developers to set environment variables in some build strategy steps, but not others.
Copy link
Member

Choose a reason for hiding this comment

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

This is fine. The likelihood of an environment variable being useful in more than one step is extremely low since the steps would ideally accomplish pretty distinct tasks.

In that proposal, it was incumbent on the build strategy authors to declare which environment variables could be overrode, and which environment variables could not be set.
This was accomplished through allow/block lists, as well as a separate list of environment variables that could be declared with default values (and which were not declared in build steps).
The downside of this proposal was that it severed the relationship of an environment variable from the place where the environment variable is used.
Its complexity also led to competing paths to implement similar capabilites.
Copy link
Member

Choose a reason for hiding this comment

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

Fair enough. I did see a value in that. However, it did add complexities, agreed.

@sbose78
Copy link
Member

sbose78 commented Jul 12, 2021

/lgtm
/approve

@openshift-ci
Copy link

openshift-ci bot commented Jul 12, 2021

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: gabemontero, sbose78

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@openshift-ci openshift-ci bot added the approved Indicates a PR has been approved by an approver from all required OWNERS files. label Jul 12, 2021
@openshift-merge-robot openshift-merge-robot merged commit 63188bf into shipwright-io:main Jul 12, 2021
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
approved Indicates a PR has been approved by an approver from all required OWNERS files. lgtm Indicates that a PR is ready to be merged.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

6 participants