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

all: Use Go module machinery to book-keep external tools #2430

Closed
wants to merge 1 commit into from

Conversation

2opremio
Copy link
Contributor

PR Checklist

PR Structure

  • This PR has reasonably narrow scope (if not, break it down into smaller PRs).
  • This PR avoids mixing refactoring changes with feature changes (split into two PRs
    otherwise).
  • This PR's title starts with name of package that is most changed in the PR, ex.
    services/friendbot, or all or doc if the changes are broad or impact many
    packages.

Thoroughness

  • This PR adds tests for the most critical parts of the new functionality or fixes.
  • I've updated any docs (developer docs, .md
    files, etc... affected by this change). Take a look in the docs folder for a given service,
    like this one.

Release planning

  • I've updated the relevant CHANGELOG (here for Horizon) if
    needed with deprecations, added features, breaking changes, and DB schema changes.
  • I've decided if this PR requires a new major/minor version according to
    semver, or if it's mainly a patch change. The PR is targeted at the next
    release branch if it's not a patch change.

What

Track and maintain external tooling through Go's module machinery.

For that, I am using a tools.go file, which seems to be an increasingly-adopted practice.

Why

  1. It centralizes version tracking of tooling instead of having versions spread around in shell-scripts
  2. Where possible (if performance allows it) it saves developers from installing external tools, by using go run, making things work transparently (e.g. it took me a while to find out that the specific version of go-bindata to use was buried in gogenerate.sh)

Known limitations

go run is slower than running a binary (at least until golang/go#33468 is resolved), so we need to be careful on where to use it (e.g. the shadow binary is installed because go run is too slow).

@cla-bot cla-bot bot added the cla: yes label Mar 31, 2020
@2opremio 2opremio force-pushed the dependencies-go-mod branch 3 times, most recently from 9f18c2c to 17c7729 Compare March 31, 2020 15:38
@2opremio 2opremio force-pushed the dependencies-go-mod branch from 17c7729 to d94b05f Compare March 31, 2020 15:47
Copy link
Contributor

@tamirms tamirms left a comment

Choose a reason for hiding this comment

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

this is a cool trick. TIL!

Copy link
Member

@leighmcculloch leighmcculloch left a comment

Choose a reason for hiding this comment

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

I think in regards to this becoming a common practice, I'd agree, but I don't think it's yet a general best practice. It comes with some tradeoffs, just like the approach we're currently using does too, so it just depends which tradeoffs are more valuable or less problematic for us.

An upside of this approach not mentioned above is it guarantees we're running the same versions of these tools locally. Our existing code doesn't guarantee this even though it installs specific versions of most of the tools.

The main tradeoff is stellar/go's module will expand it's dependency graph to include all the dependencies of these tools and will set minimum versions for those dependencies, which is unfortunate given none of our code is dependent on them. Anyone importing a stellar/go package will be constrained by those new minimum versions in their own dependency graph.

If this was a monorepo containing only applications I think the approach in this PR would have the least tradeoffs because it would impact only the applications inside the repo.

Because this monorepo also contains our Go SDK we should weigh if the benefits of this change are worth the continued expansion of the graph.

The dependencies we're adding are:

github.com/google/renameio                      +       v0.1.0          https://github.com/google/renameio
github.com/kevinburke/go-bindata                +       v3.18.0         https://github.com/kevinburke/go-bindata
github.com/kr/pty                               +       v1.1.1          https://github.com/kr/pty
github.com/rogpeppe/go-internal                 +       v1.3.0          https://github.com/rogpeppe/go-internal
golang.org/x/mod                                +       4bf6d317e70e    https://golang.org/x/mod
golang.org/x/xerrors                            +       a985d3407aa7    https://golang.org/x/xerrors
gopkg.in/errgo.v2                               +       v2.1.0          https://gopkg.in/errgo.v2

The dependencies being changed are:

github.com/kr/text              e373e137fafd    >       v0.1.0          https://github.com/kr/text/compare/e373e137fafd...v0.1.0
golang.org/x/tools              70d37148ca0c    >       6e064ea0cf2d    https://github.com/golang/tools/compare/70d37148ca0c...6e064ea0cf2d
github.com/kr/pretty            e6ac2fc51e89    >       v0.1.0          https://github.com/kr/pretty/compare/e6ac2fc51e89...v0.1.0
honnef.co/go/tools              c2f93a96b099    >       v0.0.1-2020.1.3

Another thing to consider is that when/if we move to multiple modules how we run the tools will need to change and it's not completely clear to me how we'd structure it since the simple go run ... won't work anymore. Would the plan be to have multiple tools.go, one for each project?

I don't think this adds enough benefits for the complications it adds to multiple modules, but if there's consensus that this approach is preferred I'm not opposed to it, we should just be aware of the trade-offs:

  • Dependencies in the graph that are never used by the code.
  • Something additional to unwind/figure out with multiple modules.

Copy link
Contributor

@abuiles abuiles left a comment

Choose a reason for hiding this comment

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

👍

leighmcculloch added a commit to stellar/golistcmp that referenced this pull request Mar 31, 2020
### What
When encountering a version that doesn't conform to the standard semver version format (vX.Y.Z) or the format that Go uses for tagless versions (v0.0.0-date-hash), fallback to just using the raw version name as the version.

### Why
While most developers use either semver tags for their versions, or no tags, some developers use non-standard formats for their tags and when we encounter these we should just use this as the version and not try to parse commit hashes out of them. The code is currently trying to parse a commit hash (the third component) out of `v0.0.1-2020.1.3` and raising an error because there is no third component.

This bug was discovered when using `golistcmp` on the `go list -m -json all` output for the dependencies in stellar/go#2430.
@2opremio
Copy link
Contributor Author

2opremio commented Apr 3, 2020

@leighmcculloch are we planning to break out the code base into different modules? If so, do you know when and where?

Also, regardless of this PR, the Go SDK should be its own module, so that it doesn't drag all the other dependencies.

Once that is done we can evaluate whether it makes sense to push this trick to the new modules or roll it back. Until then (based on the approvals in this PR) I think there is consensus on moving forward with this approach.

@leighmcculloch
Copy link
Member

There are plans to do it yup, see go modules part 1 and part 2 documents. We've done part 1, haven't done part 2 yet.

I think it is worth considering this after part 2 if the tools.go can live in its own module so that it doesn't pollute any other module. In fact you could probably introduce just that one module now independent of part 2.

@ire-and-curses
Copy link
Member

@2opremio Yeah this is a plan we've had for a while but haven't had bandwidth to execute. I'd love it if you took some time to read through the links @leighmcculloch shared and then we can discuss what we want to do about it, and when. For now I think we should pause this PR to keep the Go SDK deps frozen. Happy to discuss early next week.

@2opremio
Copy link
Contributor Author

I still need to look at this, but I think we can close it

@2opremio 2opremio closed this Sep 29, 2020
@tsachiherman tsachiherman deleted the dependencies-go-mod branch July 4, 2023 15:09
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.

5 participants