firstdarkdev / modpublisher

A dual publishing Gradle Plugin to publish mods to Modrinth, Curseforge and GitHub in one go
MIT License
19 stars 3 forks source link

Check if tag exists without getting all tags #12

Closed MattSturgeon closed 7 months ago

MattSturgeon commented 8 months ago

Since the GitHub Java API doesn't have a getTagByName method, I iterated over listTags in #8 to implement !createTag.

Looking into things further, while the REST API has no endpoint for getting a specific tag, the GraphQL API is capable of handling these kinda requests.

In fact, that is exactly how GitHub CLI's --verify-tag option is implemented.

We can use this query to determine if a tag exists, by checking whether data.repository.ref.id is null:

query($owner:String!, $repo:String!, $tag:String!) {
  repository(owner: $owner, name: $repo) {
    ref(qualifiedName: $tag) {
      id
    }
  }
}
Valid request

#### Variables ```json { "owner": "MinecraftFreecam", "repo": "Freecam", "tag": "refs/tags/v1.2.3" } ``` #### Response ```json { "data": { "repository": { "ref": { "id": "REF_kwDOGh1Gq7ByZWZzL3RhZ3MvdjEuMi4z" } } } } ```

Missing request

#### Variables ```json { "owner": "MinecraftFreecam", "repo": "Freecam", "tag": "refs/tags/invalid-tag-name" } ``` #### Response ```json { "data": { "repository": { "ref": { "id": null } } } } ```

I believe the GitHub Java API has a way to run GraphQL queries, so this should be fairly simple. Maybe they'd be interested in having GHRepository.containsTag(String name) upstream :thinking:

MattSturgeon commented 8 months ago

I'm dumb. We can use the /repos/{owner}/{repo}/git/ref/{ref} endpoint, exposed as GHRepository.getRef(String).

This function takes a ref string such as tags/v1.2.3 or heads/main and returns a GHRef object. It throws GHFileNotFoundException if the ref doesn't exist.