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

StackId should support the "any" stack ("*") #104

Closed
edmorley opened this issue Oct 12, 2021 · 1 comment · Fixed by #109
Closed

StackId should support the "any" stack ("*") #104

edmorley opened this issue Oct 12, 2021 · 1 comment · Fixed by #109
Assignees

Comments

@edmorley
Copy link
Member

edmorley commented Oct 12, 2021

As of Buildpack API 0.5, a buildpack can declare support for any stack using a stack ID of "*":
https://github.com/buildpacks/rfcs/blob/main/text/0056-any-stack-buildpacks.md
https://github.com/buildpacks/spec/blob/main/buildpack.md#buildpack-implementations
https://github.com/buildpacks/spec/blob/main/platform.md#stack-id

However this isn't currently supported:

use std::str::FromStr;
use libcnb::data::buildpack::BuildpackId;

let valid = BuildpackId::from_str("*");
assert_eq!(valid.unwrap().as_str(), "*");

Gives:

thread 'main' panicked at 'called `Result::unwrap()` on an `Err` value: InvalidBuildpackId("*")', src/data/buildpack.rs:8:18

Due to:
https://github.com/Malax/libcnb.rs/blob/f46bdda85838c9cc21cd1de3243d4160b85afc12/src/data/buildpack.rs#L209-L224

In addition, there is no validation that mixins is not set when the any stack is used (which is forbidden by the spec).

GUS-W-10055742

@schneems
Copy link
Contributor

schneems commented Oct 19, 2021

In this example:

use std::str::FromStr;
use libcnb::data::buildpack::BuildpackId;

let valid = BuildpackId::from_str("*");
assert_eq!(valid.unwrap().as_str(), "*");

I think you mean:

use std::str::FromStr;
use libcnb::data::buildpack::StackId;

let valid = StackId::from_str("*");
assert_eq!(valid.unwrap().as_str(), "*");

Regarding:

In addition, there is no validation that mixins is not set when the any stack is used (which is forbidden by the spec).

I think that's the harder piece. StackId is used by Stack which is used by BuildpackToml and they're mostly there for serializing/deserializing.

I found:

It looks like this is the most promising way to get the functionality today (shadow struct with a try_from):

@schneems schneems reopened this Oct 19, 2021
schneems added a commit that referenced this issue Oct 20, 2021
When a `Stack` struct has a `StackId` of `*` then it should have no mixins.

This is validated by a "shadow" struct deserializing working from https://dev.to/equalma/validate-fields-and-types-in-serde-with-tryfrom-c2n.

Based on the comment from serde-rs/serde#939 (comment)

In my own words it works like this: We create a duplicate struct and use serde's normal `derive(Deserialize)` on it. Then we specify that the `Stack` struct should be converted using the duplicate struct with `#[serde(try_from = "StackUnchecked")]. Finally we implement `try_from` and include our special logic that checks to see we don't have a `*` stack id AND any mixins.

I also hard wrapped a few comments and put backpacks around special characters in the error output to make them clearer

Close #104
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants