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

Reimplement getRequiredPlugins for go sdk #4297

Merged
merged 7 commits into from
Apr 6, 2020
Merged

Conversation

EvanBoyle
Copy link
Contributor

@EvanBoyle EvanBoyle commented Apr 3, 2020

This uses go list -m -json all. We must use -m module mode as this is the only way to get the version info as far as I can tell. This means that this approach only works for users using modules, not glide, dep, etc. This is the direction the community is going, and the direction we've moved our docs/examples so this should be fine. But as a result, I've made the implementation lenient. It doesn't fail if we run into errors along the way, just logs some messages saying we failed to acquire plugins. This is strictly better than what we have today, and we can always revisit this decision in the future as the ecosystem evolves.

Evans-MBP:aws-go-webserver evanboyle$ pulumi preview
Previewing update (dcgo):
[resource plugin aws-1.28.0] installing
Downloading plugin: 64.58 MiB / 64.58 MiB [=========================] 100.00% 7s
Moving plugin... done.
     Type                      Name               Plan       
 +   pulumi:pulumi:Stack       go-webserver-dcgo  create     
 +   ├─ aws:ec2:SecurityGroup  web-secgrp         create     
 +   └─ aws:ec2:Instance       web-server-www     create     
 
Resources:
    + 3 to create

Permalink: https://app.pulumi.com/EvanBoyle/go-webserver/dcgo/previews/a761b512-4136-4caa-b504-6843e72c0193

Fixes #1549
Fixes #4211

@EvanBoyle EvanBoyle requested review from pgavlin and lukehoban and removed request for pgavlin April 3, 2020 22:59
func getPluginName(modName string) string {
// github.com/pulumi/pulumi-aws/sdk/... => aws
pluginPart := strings.Split(modName, "/")[2]
return strings.SplitN(pluginPart, "-", 2)[1]
Copy link
Member

Choose a reason for hiding this comment

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

Both of these indexes could panic right? We should guard them and skip cleanly?

Copy link
Member

Choose a reason for hiding this comment

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

Oh - I see that the caller ensures they can't.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Correct. I refactored this to make the relationship clear in case we change this code in the future.

}

// don't wire up stderr so non-module users don't see error output from list
cmd := exec.Command(gobin, "list", "-m", "-json", "all")
Copy link
Member

Choose a reason for hiding this comment

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

I guess there is no built-in library that can be used to do this? Looks like the implementation of this command is all internal unfortunately.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Yup, tried this initially and learned about the internal restriction.

if strings.HasPrefix(m.Path, "github.com/pulumi/pulumi-") {
plugin := &pulumirpc.PluginDependency{
Name: getPluginName(m.Path),
Version: m.Version,
Copy link
Member

Choose a reason for hiding this comment

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

These versions can be things like "v0.0.0-20200317142112-1b76d66859c6". Do we need to do any filtering here to not return these back? Or do we rely on the other side of this interface being okay with weird versions it doesn't understand?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Good point. I updated this to handle non-tag commits (we normalize the patch to 0 to be compatible). The only way we can get something like v0.0.0 is when the module is new and has no associated tags, which should never happen now that we've upgraded to the new module structure. I suppose we could filter out 0.0.0 if we want to be extra careful. I'm open to suggestions here.

// GetRequiredPlugins computes the complete set of anticipated plugins required by a program.
// We're lenient here as this relies on the `go list` command and the use of modules.
// If the consumer insists on using some other form of dependency management tool like
// dep or glide, the list command fails with "go list -m: not using modules"
func (host *goLanguageHost) GetRequiredPlugins(ctx context.Context,
Copy link
Member

Choose a reason for hiding this comment

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

Can we add any test coverage of this?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I refactored to test the code to test the filtering and conversion of the module result from go list into a plugin description.

This seems sufficient to me. Any further validation would require an integration test with a dependency on pulumi-aws.

sdk/go/pulumi-language-go/main.go Outdated Show resolved Hide resolved
sdk/go/pulumi-language-go/main.go Show resolved Hide resolved
// downgrade to zero for the patch
// pinning to a specific commit can result in a minor version that doesn't exist
// v1.29.1-0.20200403140640-efb5e2a48a86 (first commit after 1.29.0 release)
version := fmt.Sprintf("v%v.%v.%v", v.Major, v.Minor, 0)
Copy link
Member

Choose a reason for hiding this comment

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

In the case that a precise version was specified - this seems wrong.

Also in general - I’m not positive this won’t work - for Kubernetes for example I think dev builds are prerelease for major version bumps? And is dependent on some very specific things about how we currently version dev tags. Anything more reliable we could do here?

Perhaps no and this is still the best we can do heuristically and is worth it?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Good point. I'll lift some of the pseduo version parsing code out of internal to make this more robust.

@EvanBoyle
Copy link
Contributor Author

@lukehoban Please take another look. I took some code out of internal that detects pseudo versions so we can special case their handling. This allows us to leave patch versions alone in the normal case where our version matches a tag. This also allows us to handle beta/dev tags. I added more unit test cases to document the behavior of more of these corner cases.

I manually tested the v2.0.0-beta.1 release of AWS:

Evans-MBP:aws-go-webserver evanboyle$ pulumi preview
Previewing update (dcgo):
[resource plugin aws-2.0.0-beta.1] installing
Downloading plugin: 64.56 MiB / 64.56 MiB [=========================] 100.00% 3s
Moving plugin... done.
     Type                      Name               Plan       Info
 +   pulumi:pulumi:Stack       go-webserver-dcgo  create     2 messages
 +   ├─ aws:ec2:SecurityGroup  web-secgrp         create     
 +   └─ aws:ec2:Instance       web-server-www     create     
 
Diagnostics:
  pulumi:pulumi:Stack (go-webserver-dcgo):
    go: downloading github.com/pulumi/pulumi-aws/sdk/v2 v2.0.0-beta.1
    go: extracting github.com/pulumi/pulumi-aws/sdk/v2 v2.0.0-beta.1
 

Permalink: https://app.pulumi.com/EvanBoyle/go-webserver/dcgo/previews/47722fda-8bc9-48d6-8776-ba2c3f4e7558

@EvanBoyle EvanBoyle requested a review from lukehoban April 4, 2020 21:47
sdk/go/common/util/buildutil/semver_test.go Outdated Show resolved Hide resolved
Copy link
Member

@pgavlin pgavlin left a comment

Choose a reason for hiding this comment

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

Looks good to me for now. We should consider revisiting the original approach in the future if we can figure out how to safely embed a version.

Co-Authored-By: Luke Hoban <luke@pulumi.com>
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 this pull request may close these issues.

Improve go plugin acquisition Pulumi Go programs have no natural way of acquiring plugins
3 participants