TL;DR
- 外部ライブラリは
build.gradle
に書いたライブラリ以外にも存在することがある -
dependencies
タスクを実行することで使用しているライブラリの一覧を調べることができる - Mave Repositoryを見ればそのライブラリの情報がわかる
- ライブラリがApache License 2.0の場合、jarの中を覗いてNOTICEファイルの有無をチェックしないといけない
はじめに
作成したアプリをGoogle Playで配布する場合、使用した外部ライブラリのライセンス条件には適切に従わなければなりません。
よって、アプリ開発者は自分のアプリがどんな外部ライブラリを使用しているかを把握しておく必要があります。
Androidでは外部ライブラリの導入にGradleを使うのが標準的なやり方です。
Gradleは、使いたい外部ライブラリが参照(依存)するライブラリも含めてローカル環境にダウンロードしてくれます。
Gradleが煩雑な作業を隠蔽してくれる反面、実は思いも寄らぬライブラリを使用していることがあります。
//...
dependencies {
implementation 'com.android.support:appcompat-v7:28.0.0'
}
//...
appcompat-v7
はモダンなAndroidアプリを作るうえでほぼ必須のライブラリで、使用している方は多いと思います。
appcompat-v7
を取り込むアプリは、同時に以下に挙げるライブラリも取り込んでいることをご存知でしたか?
- android.arch.core:common:1.1.1@jar
- android.arch.core:runtime-1.1.1
- android.arch.lifecycle:common:1.1.1@jar
- android.arch.lifecycle:livedata-1.1.1
- android.arch.lifecycle:livedata-core-1.1.1
- android.arch.lifecycle:runtime-1.1.1
- android.arch.lifecycle:viewmodel-1.1.1
- com.android.support:animated-vector-drawable-28.0.0
- com.android.support:asynclayoutinflater-28.0.0
- com.android.support:collections:28.0.0@jar
- com.android.support:coordinatorlayout-28.0.0
- com.android.support:cursoradapter-28.0.0
- com.android.support:customview-28.0.0
- com.android.support:documentfile-28.0.0
- com.android.support:drawerlayout-28.0.0
- com.android.support:interpolator-28.0.0
- com.android.support:loader-28.0.0
- com.android.support:localbroadcastmanager-28.0.0
- com.android.support:print-28.0.0
- com.android.support:slidingpanelayout-28.0.0
- com.android.support:support-annotations:28.0.0@jar
- com.android.support:support-compat-28.0.0
- com.android.support:support-core-ui-28.0.0
- com.android.support:support-core-utils-28.0.0
- com.android.support:support-fragment-28.0.0
- com.android.support:support-vector-drawable-28.0.0
- com.android.support:swiperefreshlayout-28.0.0
- com.android.support:versionedparcelable-28.0.0
- com.android.support:viewpager-28.0.0
appcompat-v7
も含めて計30のライブラリです。
念を押しておきますが、これらのライブラリはユーザーがimplementation
を書いたわけではなく、appcompat-v7
をimplementation
する文を1行書いただけでくっついてくるライブラリです。
本記事ではAndroidアプリ制作において、使用されている外部ライブラリをどのように調べればいいかを説明します。
また、Androidライブラリによく適用されているApache License 2.0の帰属告知の調べ方も合わせて説明します。
自分が使用しているライブラリを知る
今回は下記の依存関係を例に説明します。
Android Studioのプロジェクト作成ウィザードをデフォルト設定で進めた結果作成される依存関係にプラスしてApache Commons Codecを追加しています。
//...
dependencies {
// Android Studioが初期状態で追加済み
implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation 'com.android.support:appcompat-v7:28.0.0'
implementation 'com.android.support.constraint:constraint-layout:1.1.3'
testImplementation 'junit:junit:4.12'
androidTestImplementation 'com.android.support.test:runner:1.0.2'
androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.2'
// 追加
implementation 'commons-codec:commons-codec:1.11'
}
//...
さて、自分が使用しているライブラリを知る方法を説明します。
実はこれはGraldeタスクを1発実行するだけでわかってしまいます。
GradleウィンドウからandroidDependencies
タスクを実行しましょう。
すると、Runウィンドウにわらわらと結果が出てきたと思います。
その中のreleaseRuntimeClassPath
から始まるブロックを見てみましょう。
...
releaseRuntimeClasspath - Dependencies for runtime/packaging
+--- com.android.support:appcompat-v7:28.0.0@aar
+--- com.android.support.constraint:constraint-layout:1.1.3@aar
+--- commons-codec:commons-codec:1.11@jar
+--- com.android.support:support-fragment:28.0.0@aar
+--- com.android.support:animated-vector-drawable:28.0.0@aar
+--- com.android.support:support-core-ui:28.0.0@aar
+--- com.android.support:support-core-utils:28.0.0@aar
+--- com.android.support:support-vector-drawable:28.0.0@aar
+--- com.android.support:loader:28.0.0@aar
+--- com.android.support:viewpager:28.0.0@aar
+--- com.android.support:coordinatorlayout:28.0.0@aar
+--- com.android.support:drawerlayout:28.0.0@aar
+--- com.android.support:slidingpanelayout:28.0.0@aar
+--- com.android.support:customview:28.0.0@aar
+--- com.android.support:swiperefreshlayout:28.0.0@aar
+--- com.android.support:asynclayoutinflater:28.0.0@aar
+--- com.android.support:support-compat:28.0.0@aar
+--- com.android.support:versionedparcelable:28.0.0@aar
+--- com.android.support:collections:28.0.0@jar
+--- com.android.support:cursoradapter:28.0.0@aar
+--- android.arch.lifecycle:runtime:1.1.1@aar
+--- com.android.support:documentfile:28.0.0@aar
+--- com.android.support:localbroadcastmanager:28.0.0@aar
+--- com.android.support:print:28.0.0@aar
+--- android.arch.lifecycle:viewmodel:1.1.1@aar
+--- android.arch.lifecycle:livedata:1.1.1@aar
+--- android.arch.lifecycle:livedata-core:1.1.1@aar
+--- android.arch.lifecycle:common:1.1.1@jar
+--- android.arch.core:runtime:1.1.1@aar
+--- android.arch.core:common:1.1.1@jar
+--- com.android.support:interpolator:28.0.0@aar
+--- com.android.support:support-annotations:28.0.0@jar
\--- com.android.support.constraint:constraint-layout-solver:1.1.3@jar
...
androidDependencies
タスクは、アプリの依存関係を提示してくれるタスクです。
通常、releaseタスクの実行時クラスパスと実際に取り込んでいるライブラリは一致します。
したがって、アプリが使用しているライブラリの一覧を知るためにはreleaseRuntimeClasspath
を見ればよい、ということになります。
なお、より詳細な依存関係が知りたい、という人はdependencies
タスクを実行しましょう。
...
releaseCompileClasspath - Resolved configuration for compilation for variant: release
+--- com.android.support:appcompat-v7:28.0.0
| +--- com.android.support:support-annotations:28.0.0
| +--- com.android.support:support-compat:28.0.0
| | +--- com.android.support:support-annotations:28.0.0
| | +--- com.android.support:collections:28.0.0
| | | \--- com.android.support:support-annotations:28.0.0
| | +--- android.arch.lifecycle:runtime:1.1.1
| | | +--- android.arch.lifecycle:common:1.1.1
| | | | \--- com.android.support:support-annotations:26.1.0 -> 28.0.0
| | | +--- android.arch.core:common:1.1.1
| | | | \--- com.android.support:support-annotations:26.1.0 -> 28.0.0
| | | \--- com.android.support:support-annotations:26.1.0 -> 28.0.0
| | \--- com.android.support:versionedparcelable:28.0.0
| | +--- com.android.support:support-annotations:28.0.0
| | \--- com.android.support:collections:28.0.0 (*)
| +--- com.android.support:collections:28.0.0 (*)
| +--- com.android.support:cursoradapter:28.0.0
| | \--- com.android.support:support-annotations:28.0.0
| +--- com.android.support:support-core-utils:28.0.0
| | +--- com.android.support:support-annotations:28.0.0
| | +--- com.android.support:support-compat:28.0.0 (*)
| | +--- com.android.support:documentfile:28.0.0
| | | \--- com.android.support:support-annotations:28.0.0
| | +--- com.android.support:loader:28.0.0
| | | +--- com.android.support:support-annotations:28.0.0
| | | +--- com.android.support:support-compat:28.0.0 (*)
| | | +--- android.arch.lifecycle:livedata:1.1.1
| | | | +--- android.arch.core:runtime:1.1.1
| | | | | +--- com.android.support:support-annotations:26.1.0 -> 28.0.0
| | | | | \--- android.arch.core:common:1.1.1 (*)
| | | | +--- android.arch.lifecycle:livedata-core:1.1.1
| | | | | +--- android.arch.lifecycle:common:1.1.1 (*)
| | | | | +--- android.arch.core:common:1.1.1 (*)
| | | | | \--- android.arch.core:runtime:1.1.1 (*)
| | | | \--- android.arch.core:common:1.1.1 (*)
| | | \--- android.arch.lifecycle:viewmodel:1.1.1
| | | \--- com.android.support:support-annotations:26.1.0 -> 28.0.0
| | +--- com.android.support:localbroadcastmanager:28.0.0
| | | \--- com.android.support:support-annotations:28.0.0
| | \--- com.android.support:print:28.0.0
| | \--- com.android.support:support-annotations:28.0.0
| +--- com.android.support:support-fragment:28.0.0
| | +--- com.android.support:support-compat:28.0.0 (*)
| | +--- com.android.support:support-core-ui:28.0.0
| | | +--- com.android.support:support-annotations:28.0.0
| | | +--- com.android.support:support-compat:28.0.0 (*)
| | | +--- com.android.support:support-core-utils:28.0.0 (*)
| | | +--- com.android.support:customview:28.0.0
| | | | +--- com.android.support:support-annotations:28.0.0
| | | | \--- com.android.support:support-compat:28.0.0 (*)
| | | +--- com.android.support:viewpager:28.0.0
| | | | +--- com.android.support:support-annotations:28.0.0
| | | | +--- com.android.support:support-compat:28.0.0 (*)
| | | | \--- com.android.support:customview:28.0.0 (*)
| | | +--- com.android.support:coordinatorlayout:28.0.0
| | | | +--- com.android.support:support-annotations:28.0.0
| | | | +--- com.android.support:support-compat:28.0.0 (*)
| | | | \--- com.android.support:customview:28.0.0 (*)
| | | +--- com.android.support:drawerlayout:28.0.0
| | | | +--- com.android.support:support-annotations:28.0.0
| | | | +--- com.android.support:support-compat:28.0.0 (*)
| | | | \--- com.android.support:customview:28.0.0 (*)
| | | +--- com.android.support:slidingpanelayout:28.0.0
| | | | +--- com.android.support:support-annotations:28.0.0
| | | | +--- com.android.support:support-compat:28.0.0 (*)
| | | | \--- com.android.support:customview:28.0.0 (*)
| | | +--- com.android.support:interpolator:28.0.0
| | | | \--- com.android.support:support-annotations:28.0.0
| | | +--- com.android.support:swiperefreshlayout:28.0.0
| | | | +--- com.android.support:support-annotations:28.0.0
| | | | +--- com.android.support:support-compat:28.0.0 (*)
| | | | \--- com.android.support:interpolator:28.0.0 (*)
| | | +--- com.android.support:asynclayoutinflater:28.0.0
| | | | +--- com.android.support:support-annotations:28.0.0
| | | | \--- com.android.support:support-compat:28.0.0 (*)
| | | \--- com.android.support:cursoradapter:28.0.0 (*)
| | +--- com.android.support:support-core-utils:28.0.0 (*)
| | +--- com.android.support:support-annotations:28.0.0
| | +--- com.android.support:loader:28.0.0 (*)
| | \--- android.arch.lifecycle:viewmodel:1.1.1 (*)
| +--- com.android.support:support-vector-drawable:28.0.0
| | +--- com.android.support:support-annotations:28.0.0
| | \--- com.android.support:support-compat:28.0.0 (*)
| \--- com.android.support:animated-vector-drawable:28.0.0
| +--- com.android.support:support-vector-drawable:28.0.0 (*)
| \--- com.android.support:support-core-ui:28.0.0 (*)
+--- com.android.support.constraint:constraint-layout:1.1.3
| \--- com.android.support.constraint:constraint-layout-solver:1.1.3
\--- commons-codec:commons-codec:1.11
...
androidDependencies
は最終的に使用されるライブラリを箇条書き形式で教えてくれますが、dependencies
は依存関係をツリー形式で教えてくれます。
あるライブラリが本当に必要かどうかを調査するときはこちらを使いましょう。
何のライブラリかを調べる
androidDependencies
で一覧を出力してみると知らないライブラリがたくさん出てきます。
そのようなライブラリはMaven Repositoryで調べてみましょう。
例えばandroid.arch.lifecycle:viewmodel
を調べてみると、以下のページが出てきます。
このページから、android.arch.lifecycle:viewmodel
はどうやらAndroid Lifecycle ViewModelという名称のAndroidパッケージの一部で、Apache License 2.0で配布されていることがわかります。
よって、android.arch.lifecycle:viewmodel
はApache License 2.0の頒布条件にしたがえばよいことがわかります。
実は自動でやってくれる
ここまで長々と説明しましたが、実は以上の手順を自動的に出力してくれる(しかも物によってはライセンス表示のアクティビティまで作ってくれる)Android Studioプラグインは多数存在します。
@tyoroさんの記事にまとまっていますのでそちらを参照してください。
Androidアプリにライセンス表示を埋め込むライブラリいくつか
おまけ:[Apache License 2.0]NOTICEファイルを知る
「自動でやってくれるんだったらもうやることないだろ?」と思われるかもしれません。
が、Apache License 2.0でライセンスされたライブラリを使うためにライセンス表示をする場合、自動化できない作業があります。
それは帰属の内容の告知です。
Apache License 2.0では、使用するライブラリが帰属を有している場合、ドキュメントにその内容を見えるところに表示しなければならいという条件があります。
この帰属の内容を含むファイルはNOTICEファイルなどと呼ばれます。
厄介なことにAndroid(Java)の世界ではNOTICEファイルはjarやaarの中に埋め込んで配布されるのが一般的です。また、NOTICEファイルはファイル名や書式に決まりはありません。
つまり、使用するjarやaarがNOTICEファイルに相当するファイルを含んでいるか、1つ1つ見て回る作業が必要なのです。
以下にAndroid Studioを使って効率的に(?)確認していく手順を説明します。
- Projectウィンドウの
Android
と表示されているコンボボックスをクリックする
- コンボボックスの一覧から
Project
を選び表示を切り替える -
External Libraries
から中身を見たいライブラリを選択する
Android Studioでは依存関係にあるライブラリがすべて見えるようになっているのですね。
さて、ここで先ほどのAndroid Lifecycle ViewModelにNOTICEファイルがあるか調べてみましょう。
Gradle:android.arch.lifecycle:viewmodel-1.1.1
を掘り下げていくと……
META-INF
の中にandroid.arch.lifecycle_viewmodel.version
という見慣れないファイルがありましたが、中身を覗いてみると、ファイル名どおり本当にバージョン情報だけしか記述されていません。
ほかにファイルもないので、どうやらAndroid Lifecycle ViewModelにはNOTICEファイルはなさそうです。
つぎに、ApacheのCommons-CodecにNOTICEファイルがあるか調べてみましょう。
Gradle:commons-codec:commons-codec:1.11@jar
を掘り下げていくと……
commons-codec-1.11.jar
のMETA-INF
の中にNOTICE.txt
があるのを見つけました。
NOTICE.txt
を開いてみると確かに帰属の内容(クレジットの情報)が書いてありますね。
ライセンス表示にはこの記述を引用すればよさそうです。
今回はNOTICEファイルはMETA-INF/NOTICE.txt
というパスで存在していましたが、ライブラリによっては全く異なるファイル名・ファイルパスに存在していることも珍しくありません。
根気よく探していきましょう。
おわりに
ライセンス条件に従わないソフトウェアを頒布すると、最悪の場合著作者から訴えられ裁判に発展することもあります。
ライセンスされたソフトウェアは適切に取り扱いましょう。