-
Notifications
You must be signed in to change notification settings - Fork 888
chore: color value_source
for deployment values
#9922
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
Conversation
value_source
for deployment valuesvalue_source
for deployment values
// If an option has no values, we have no idea how to unmarshal it. | ||
// So just discard the json data. | ||
if o.Value == nil { | ||
o.Value = &DiscardValue | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Since the values are behind an interface, if we do not know how to implement the .String()
method, then having the value in an unknown form is pointless.
We could add some logic to try and detect primitive options, but I do not see the value. We should always have the full set of Options when we unmarshal, so we should always get the correct types and values.
UpdateCheckOptions *updatecheck.Options // Set non-nil to enable update checking. | ||
// DeploymentOptions do contain the copy of DeploymentValues, but contain | ||
// contextual information about how the values were set. | ||
// Do not use DeploymentOptions to retrieve values, use DeploymentValues instead. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why not just strip all values from DeploymentOptions
then? Too many allocations?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I wanted to go this route, but the UI grabs the value from the option. Values are returned in the parsed form, and the option form:
Lines 34 to 37 in b1058a6
codersdk.DeploymentConfig{ | |
Values: values, | |
Options: api.DeploymentOptions, | |
}, |
There is no way to associate the values between the two, so the value needs to be present on the Option for the UI to know.
I feel like this could use a bit of a refactor, but it is working and not really that important.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
FE looks good.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Neat feature! While I understood the shortcoming, I didn't quite grasp why we had to work around it in UnmarhsalJSON
like we did. But I'm fine with it if you think that's the best approach. It would be ideal if we could just change our structures so that there's no need for it, though.
cli/clibase/option.go
Outdated
// | ||
// The value is discarded if it's type cannot be inferred. This behavior just | ||
// feels "safer", although it should never happen if the correct option set | ||
// is passed in. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure under what circumstances this Unmarshal is run? Is there a chance of conflicts between server versions (API response) and CLI version (decode)?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yup exactly. The new version can have more deployment options, so the old version has nothing to match it against.
Yea this was an annoying headache. Ideally we change the the data structure, but that would require us to change the slice into a struct, because you cannot have typed slices where each element is different. That change ripples aggressively through a lot of code on the FE and BE, and would be a much bigger change. I am taking a step back and trying to understand how https://goplay.tools/snippet/F5I4fFRB3au Essentially when you call If |
codersdk/deployment.go
Outdated
case "string-array": | ||
var empty clibase.StringArray | ||
cpyOpt.Value = &empty | ||
default: | ||
var empty clibase.String | ||
cpyOpt.Value = &empty | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oooh this is where I broke the json.Unmarshal()
. @johnstcn @mafredri
So json.Unmarshal
does unmarshal in place for arrays, so all the types were working correctly. When I was zeroing the secrets, I figured a string is fine, but it is not. I should have used a nil.
So this made a clibase.String
try to unmarshal into whatever the secret was, which did not work. If I instead just use a nil
, then it all works 🤦♂️.
So I can delete all the json unmarshal stuff I wrote, but my json unmarshal handles all the edge cases that would usually just fail (see https://goplay.tools/snippet/GPxfjtnfvys).
So I can delete my unmarshal code, and if your client and version have different option sets, the call will fail. 🤔
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
so if you have client version X, and we add an option in server version Y, then the unmarshal will fail when client tries to get DeploymentOptions?
Yes.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd rather have a custom UnmarshalJSON method than a potential regression between versions :-)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we should keep this complicated unmarshal logic. It is more complicated, but with testing, it is safe and only affects the codersdk.Client
. If we do not have this code, then we can unintentionally just break the client, and there is nothing the client can do to resolve this since the JSON from the server is the issue at hand.
closes #9760
Implementation of Optionset Unmarshal
Before this change, all
Value
fields of Options werenil
and so unmarshalling was ok. Now that I am passing a value, theUnmarshalJSON
function gets complicated because we cannot infer types easily.I got this to work, although we don't use these values anywhere in the Golang, so it didn't really matter on the golang side. On the Typescript side, we just use the
any
type and type case to the types we know they are. 🤷♂️It's a little janky. To move to a more statically typed struct, we would need to make
OptionSet
a struct with fields, rather than a slice? Or extend thepflag.Value
interface to include someType()
fields we can do some type interferences on. Or just make anany
type that implements the interface??For now, I think this solution is pretty good.
What this does
Indicates where the value is set. Should we add a tooltip or something? Or is this intuitive enough?
How it looks in green