Proposal: Read release parameters from a JSON file
Current solution
The release-cli
currently supports taking all parameters to create a release using flags. These flags match exactly all the parameters defined in the create a release section of the Releases API.
./bin/release-cli create -h
NAME:
help create - Create a Release using GitLab's Releases API https://docs.gitlab.com/ee/api/releases/#create-a-release
USAGE:
help create [command options] [arguments...]
OPTIONS:
--name value The release name
--description value The description of the release, you can use Markdown
--tag-name value The tag the release will be created from [$CI_COMMIT_TAG]
--ref value If tag_name doesn’t exist, the release will be created from ref; it can be a commit SHA, another tag name, or a branch name [$CI_COMMIT_SHA]
--assets-links-name value [DEPRECATED use --assets-link instead] List of asset link names; must be used with --asset-links-url; ignored if --assets-link is defined (e.g. --assets-links-name "asset 1" --assets-links-url "https://example.com/url/1" --assets-links-name "asset 2" --assets-links-url "https://example.com/url/2")
--assets-links-url value [DEPRECATED use --assets-link instead] List of asset link URLs; must be used with --asset-links-name; ignored if --assets-link is defined (e.g. --assets-links-name "asset 1" --assets-links-url "https://example.com/url/1" --assets-links-name "asset 2" --assets-links-url "https://example.com/url/2")
--assets-link value JSON string representation of an asset link; takes precedence over --assets-links-name and --assets-links-url (e.g. --assets-link='{"name": "Asset1", "url":"https://<domain>/some/location/1", "type": "other", "filepath": "xzy" }'
--milestone value List of the titles of each milestone the release is associated with (e.g. --milestone "v1.0" --milestone "v1.0-rc)"; each milestone needs to exist
--released-at value The date when the release will be/was ready; defaults to the current time; expected in ISO 8601 format (2019-03-15T08:00:00Z)
--help, -h Show help (default: false)
Problem to solve
Defining all these variables while running the release-cli
becomes very verbose and it may be hard to follow, especially for flags that can be defined multiple times (e.g. --assets-link
or --milestone
).
Doing the validation of some of these flags is becoming more complex, as found in #48 (comment 398524715) and !33 (comment 365724553).
It is hard to validate all the repeated flags when some parameters are required and some are not, for example, adding a direct asset link to a release. Name and URL are required, but link_type
and filepath
are not.
Proposal
In #48 (closed) we decided to add an --assets-link
flag that takes a JSON string that can define the correct relationship between the assets. This can be further extended to the release-cli create
command to use a JSON file where all the parameters to create a release are defined in. For example,
// cat release.json
{
"name": "release name",
"description": "release description",
"tag_name": "v1.1.0",
"ref": "2a4b8138a035174d0db1b2a0c4fb985edab7884d",
"milestones": ["m1", "m2"],
"released_at": "2020-06-30T07:00:00Z",
"assets": {
"links": [
{
"name": "asset 1",
"url": "https://example.com/asset/1",
"filepath": "/permanent/path",
"link_type": "other"
},
{
"name": "asset 2",
"url": "https://example.com/asset/2"
},
{
"name": "asset 3",
"url": "https://example.com/asset/3",
"link_type": "image"
}
]
}
}
Adding a -file
flag to the release-cli create
command to load the release from the file. This would look like
release-cli create -file release.json
Advantages
- Related assets parameters are defined together, reducing the relationship/validation concern found in #48 (comment 398524715).
- Parsing a JSON file would reduce the complexity from the
release-cli
logic to validate flags and generate the correct request for the Releases API. - Generating this file directly from the CI YAML
release
node would be straightforward on the Rails side (YAML->JSON conversion is a well-known pattern).
Disadvantages
- The caller of the
release-cli
needs to generate the.json
file somehow. This is not a concern for GitLab CI (see point 3 above). - Moves the complexity out of the
release-cli
, giving the responsibility to standalone users.
Questions
- Should we support all the flags AND the
-file
option? - If we do, do we favor
-file
over individual flags? - Do we take the
-file
and other parameters together, overriding individual parameters. For example if-name
and-file
are passed together, do we load all the parameters from the file and only overridename
?