GitHub Packages で プライベートリポジトリをgradleライブラリ化にする

# はじめに
社内で共通して利用するライブラリはGitHubのプライベートリポジトリとして管理したいですよね。サクッと作ろうとしたのですが、gradleではgithubのプライベートリポジトリをURL指定などで利用することができなかったので方法を調べました。
[Github Package](https://github.com/features/packages)という、GitHubが提供するパッケージ管理の仕組みを使うことで実現できました。

今回はgradle registoryとしての利用方法を紹介しますが、他にも以下の種類をサポートしているようです。

* Container registry
* Docker registry
* RubyGems registry
* npm registry
* Apache Maven registry
* Gradle registry
* NuGet registry



# ゴール
以下のように依存関係を指定して、GitHubのプライベートリポジトリのライブラリを利用する。
```
implementation 'app.beabuddy:gradlepackagesexample:1.0.4'
```

# 方法
## Androidライブラリの作成
新規にAndroidのプロジェクトを作成して、ライブラリ化したい部分をモジュールとして開発します。

今回はおおまかに以下のような構造になりました。
```
├── app // ライブラリ開発用にライブラリを利用するアプリ
│   ├── build.gradle // appレベルbuild.gradleと呼ぶ
│   └── src
├── mylibrary // ライブラリ自体
│   ├── build.gradle // ライブラリレベルbuild.gradleと呼ぶ
│   └── src
├── build.gradle // プロジェクトレベルbuild.gradleと呼ぶ
├── local.properties
└── settings.gradle
```

## ライブラリの公開設定
`ライブラリレベルbuild.gradle`のpluginsブロックの下に以下を追記します。

```
// local.propertiesからGitHub認証情報を取得
def localProperties = new Properties()
def localPropertiesFile = rootProject.file('local.properties')
if (localPropertiesFile.exists()) {
    localPropertiesFile.withReader('UTF-8') { reader ->
        localProperties.load(reader)
    }
}

publishing {
    repositories {
        maven {
            name = "GitHubPackages"
            url = uri("https://maven.pkg.github.com/ユーザー名や組織名/リポジトリ名")
            credentials { // 認証情報
                username = localProperties.getProperty("gpr.user") ?: System.getenv("USERNAME")
                password = localProperties.getProperty("gpr.key") ?: System.getenv("TOKEN")
            }
        }
    }
    publications {
        gpr(MavenPublication) {
            // groupId:artifactId:version というふうに利用側で依存関係を指定する
            // 自分の利用したい値に変更してください
            groupId = 'app.beabuddy' 
            artifactId = 'gradlepackagesexample' 
            version = '1.0.4'

            afterEvaluate {
                from(components.release)
            }
        }
    }
}
```

## 認証情報を設定
`local.properties`にGitHubのパーソナルアクセストークンを設定します。パーソナルアクセストークンはClassic形式である必要がありそうです。必要な権限は[こちら](https://docs.github.com/en/packages/learn-github-packages/about-permissions-for-github-packages#about-scopes-and-permissions-for-package-registries)

```:local.properties
gpr.user={GitHubのユーザー名}
gpr.key={GitHubのパーソナルアクセストークン(classic)}
```

## gradleライブラリとして公開(リポジトリへのアクセス権を持つ人にのみ)
「ライブラリの公開設定」で設定した値をもとに、gradleタスクが追加されるので実行します。
```
./gradlew publishGprPublicationToGitHubPackagesRepository
```

無事に公開されるとリポジトリのトップページの右下に以下のように `Packages` に公開されたライブラリが表示されます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/18273/1a9a651b-a3c6-7769-6698-6f11ae7384b5.png)

クリックすると以下のような情報が表示されます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/18273/31181df6-c228-f48c-60eb-5eaf57804a6a.png)


## 公開したライブラリを利用する
ここからは別のプロジェクトから公開したパッケージを利用する方法を紹介します。

### 認証情報の設定
`local.properties`にGitHubのパーソナルアクセストークンを設定します。パーソナルアクセストークンはClassic形式である必要がありそうです。 パッケージを利用するだけなら `read:packages` があればよいです。

```:local.properties
gpr.user={GitHubのユーザー名}
gpr.key={GitHubのパーソナルアクセストークン(classic)}
```

### リポジトリの追加
`settings.gradle`に以下のような設定を追加します。 プロジェクトの状況次第では `settings.gradle` でなく プロジェクトレベルの `build.gradle` かもしれません。 いずれにしても `repositories` のブロックに追記する形にすればよいと思います。

```gradle:settings.gradle
Properties localProperties = new Properties()
localProperties.load(file('local.properties').newDataInputStream())
dependencyResolutionManagement {
    repositoriesMode.set(RepositoriesMode.FAIL_ON_PROJECT_REPOS)
    repositories {
        google()
        mavenCentral()
        maven {
            name = "GitHubPackages"
            url = uri("https://maven.pkg.github.com/sekitaka/gradle-packages-example")
            credentials {
                username = localProperties.getProperty("gpr.user") ?: System.getenv("USERNAME")
                password = localProperties.getProperty("gpr.key") ?: System.getenv("TOKEN")
            }
        }
    }
}
```

### 依存関係の追加
ここまでくれば他のライブラリと同様にアプリレベルのbuild.gradleに依存関係を追加すれば、公開したパッケージを利用することができます。

```gradle:build.gradle
dependencies {
    implementation 'app.beabuddy:gradlepackagesexample:1.0.4'
}
```


# 参考
https://docs.github.com/en/packages/working-with-a-github-packages-registry/working-with-the-gradle-registry