aerie icon indicating copy to clipboard operation
aerie copied to clipboard

Procedural Build Plugin

Open skovati opened this issue 1 year ago • 11 comments

closes https://github.com/NASA-AMMOS/aerie/issues/1470

Description

Extract the build logic used to generate procedural scheduling (and soon to be constraint) jars into a separate gradle plugin, which can be applied to new projects. This drastically simplifies the new user experience (they don't have to copy paste some build logic) and allows us to "remotely" update build logic with bug fixes or new features, i.e., users can just update to v0.0.2 of our plugin to get e.g. new dynamic linking support.

[!CAUTION] The current implementation of this plugin requires anyone who wants to run gradle commands in the aerie repo to have a GITHUB_TOKEN env var populated with an API key. This is so that gradle can consume this plugin before "configuring" the project.

Summary of changes

  • Refactor procedural build logic into procedural/plugin/src/main/groovy/gov.nasa.ammos.aerie.procedural.plugin.gradle
  • Set up publishing to Github packages for this plugin
  • Configure base Aerie project to look for plugins in Github packages
  • Refactor e2e test procedure assets to use this new plugin

Verification

I've published many times to my aerie fork to test this plugin works as expected when published. Additionally, I've already published to aerie packages, so our e2e tests for this PR.

Documentation

We can update the new user guides for procedural scheduling / constraints with this plugin. Additionally we can streamline the build.gradle in the aerie mission model template repo.

Future work

It could also be useful to create an extension for this plugin, which would allow us to configure procedural builds something like the following, i.e. we can write our own configuration DSL.

plugins {
  id "gov.nasa.ammos.aerie.procedural.plugin"
}

procedures {
  sharedDependencies {
    implementation("some-big-jar-we-want-dynamically-linked")
  }
  schedulers = [
    "PlaceDSNEvents"
    "XbandWindows"
  ]
  constraints = [
    "XbandKeepOut"
  ]
}

It might also be fruitful to extend this plugin idea to mission models.

We can also drastically simplify our existing... 🤔

 ~ fd build.gradle --exec cat | wc -l
 2093

...two thousand lines of gradle build script by deduplicating shared logic (e.g. a convention script for all our java libraries that gets published and tested in the same way)

skovati avatar Sep 24 '24 23:09 skovati

Question for @dandelany, should this plugin version track the Aerie version?

skovati avatar Oct 09 '24 17:10 skovati

@dandelany another thought, we might need to expose ${{ github.actor }} and ${{ secrets.GITHUB_TOKEN }} as environment variables (for gradle to use) in our e2e tests workflows if these aren't already exposed as deployment level environment variables

skovati avatar Oct 09 '24 18:10 skovati

Can we add the procedural library dependencies in this plugin?

JoelCourtney avatar Oct 09 '24 21:10 JoelCourtney

Hmm good question @JoelCourtney . We'd want to make sure end users can define which version of Aerie deps they want to grab. One option would be pinning this Gradle plugin to Aerie versions, so that applying version e.g. v2.22.0 of this gradle plugin would pull in v2.22.0 Aerie procedural deps 🤔

skovati avatar Oct 09 '24 21:10 skovati

I like that idea

JoelCourtney avatar Oct 09 '24 21:10 JoelCourtney

Sounds reasonable to me - we'd just need to make sure we include the plugin in our release process. Would that be relatively straightforward?

mattdailis avatar Oct 09 '24 22:10 mattdailis

I've taken a slightly different approach implementing this @JoelCourtney @mattdailis. The procedural plugin's version won't directly track Aerie version, since I wasn't able to propagate specific dependency versions to plugin consumers. Instead, the plugin will read the dependency version from properties.aerieVersion, which can be populated by our mission model template build script. See https://github.com/NASA-AMMOS/aerie-mission-model-template/blob/3cf4d104ba12caf4380341866f38abd94f63cea6/build.gradle#L27-L34

skovati avatar Oct 14 '24 22:10 skovati

I'm fine with using properties.aerieVersion for now, but in a future release I'd rather do it through a configuration in the procedures {} extension you mentioned in the description. Since we don't have that yet, I'm OK using a variable.

JoelCourtney avatar Oct 17 '24 23:10 JoelCourtney

I am totally baffled how the tests are passing... the plugin hasn't been published, yet both the e2e package and the procedural/examples package are fetching and applying them as if they are. It doesn't work on my machine, but it seems to work in gh workflows... ???

JoelCourtney avatar Oct 22 '24 23:10 JoelCourtney

They actually are published already @JoelCourtney!

https://github.com/NASA-AMMOS/aerie/packages/2282306

I sort of accidentally did this, I didn't realize my test API token had write permissions to the aerie packages 🫣. As stated in the caution block, you'll need to expose GITHUB_TOKEN and GITHUB_ACTOR environment variables (populated correctly) to consume these plugins on your machine.

skovati avatar Oct 22 '24 23:10 skovati

Placing this on hold for now while we revisit the GITHUB_TOKEN requirement; ideally we could consume this plugin locally instead of requiring a build to already be published, but gradle requires that plugins are resolved at configuration time, and the plugin is built at build time in the gradle life cycle. Publishing and consuming in two steps was the only way I could "break" this cycle

skovati avatar Nov 05 '24 21:11 skovati