はじめに
この記事は、OpenAIのChatGPTを用いて、以下のようなやり取りを行った際の内容をまとめたものです。
モダンなアーキテクトでAndroidアプリを開発してみたくなったので、chatGPTに色々質問しながら開発してみました。
Androidアプリ開発に関する質問と回答
Androidはアーキテクチャーは何が推奨されていますか?
Android開発において、推奨されるアーキテクチャは、Googleが提唱するAndroidアーキテクチャコンポーネントと一般的なソフトウェアアーキテクチャパターンを組み合わせたものです。
一般的なアーキテクチャパターンには、
MVVM(Model-View-ViewModel)やMVP(Model-View-Presenter)
があります。
Androidアーキテクチャコンポーネントは、アプリのライフサイクル管理、データ永続化、バックグラウンドタスクの実行などの問題に対処するために設計されたライブラリで、以下の主要なコンポーネントが含まれています。
Lifecycle: ライフサイクルイベントの処理を容易にします。
LiveData: ライフサイクルに関連するデータの更新を効率的に行います。
ViewModel: UIに関連するデータを保持し、ライフサイクルの変更に耐えるようにします。
Room: SQLiteデータベースに対する抽象化レイヤーを提供し、データ永続化を容易にします。
WorkManager: バックグラウンドタスクのスケジューリングと実行を管理します。
これらのコンポーネントを使用して、アプリの機能や構造を整理し、効率的で保守性の高いアプリケーションを開発することが推奨されています。最終的に選択されるアーキテクチャは、アプリケーションの要件や開発チームのスキルセットによって異なりますが、GoogleはMVVMパターンとAndroidアーキテクチャコンポーネントの組み合わせを推奨しています。
MVVMのパッケージ構成を教えてください
MVVM (Model-View-ViewModel) アーキテクチャを使用する場合、パッケージ構成は一般的に以下のようになります。
├───com
│ └───yourdomain
│ └───yourappname
│ ├───data
│ │ ├───local
│ │ ├───remote
│ │ └───repository
│ ├───model
│ ├───ui
│ │ ├───activities
│ │ ├───fragments
│ │ └───adapters
│ └───viewmodel
各パッケージの役割:
- data: データソースに関連するコードが含まれます。
- local: データのローカルストレージ(SQLite、Room、Shared Preferencesなど)を扱うコードが含まれます。
- remote: データのリモートストレージ(API やクラウドサービスなど)を扱うコードが含まれます。
- repository: データの取得と更新を担当するリポジトリクラスが含まれます。これは、ローカルおよびリモートデータソースからデータを取得し、ViewModel にデータを提供する役割を果たします。
- model: アプリケーションのデータモデルが含まれます。これらは、データソースや ViewModel で使用されるエンティティやデータオブジェクトを定義します。
- ui: アプリケーションのユーザーインターフェースに関連するコードが含まれます。
- activities: Activity クラスが含まれます。
- fragments: Fragment クラスが含まれます。
- adapters: RecyclerView のアダプターや他のアダプターが含まれます。
- viewmodel: ViewModel クラスが含まれます。これらは、UI コンポーネントに表示するデータを提供し、ユーザー操作に応じてモデルを更新します。
このパッケージ構成は、MVVM アーキテクチャに適した構成の一例です。プロジェクトの要件や規模によっては、異なる構成を採用することがあります。重要なのは、パッケージ構成が整理されており、各コンポーネントの役割が明確であることです。
MVVMで新しいプロジェクトを作成する方法を教えてください
MVVM (Model-View-ViewModel) パターンを使って新しい Android プロジェクトを作成する方法を説明します。
MVVM パターンは、アプリのデータロジックと UI を分離するために使用されます。まず、新しいプロジェクトを作成して、以下の手順に従ってください。
1.Android Studio を開き、「Start a new Android Studio project」をクリックします。
2.プロジェクトを作成する際に、Kotlin を選択し、最低限の SDK バージョンを設定します。
3.作成したプロジェクトの build.gradle(Module)ファイルに、必要な依存関係を追加します。主に Android アーキテクチャコンポーネント(ViewModel と LiveData)が必要です。
dependencies {
def lifecycle_version = "2.4.1" // このバージョンは変更される可能性があるため、最新バージョンを確認してください
// ViewModel
implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:$lifecycle_version"
// LiveData
implementation "androidx.lifecycle:lifecycle-livedata-ktx:$lifecycle_version"
}
4.各層のフォルダ構造を作成します。例えば、次のようになります。
model: データモデルやリポジトリが含まれます。
view: アクティビティやフラグメントが含まれます。
viewmodel: ViewModel クラスが含まれます。
5.model ディレクトリにデータモデルを作成します。例えば、User.kt という名前のデータクラスを作成できます。
data class User(
val id: Int,
val name: String,
val email: String
)
6.viewmodel ディレクトリに ViewModel を作成します。例えば、UserViewModel.kt という名前のクラスを作成できます。このクラスでは、ViewModel() を継承し、LiveData を使用してデータを保持します。
class UserViewModel : ViewModel() {
private val _user = MutableLiveData<User>()
val user: LiveData<User>
get() = _user
fun setUser(newUser: User) {
_user.value = newUser
}
}
- MainActivity クラスで、ViewModel のインスタンスを取得し、LiveData にオブザーバーを追加して UI にデータをバインドします。
class MainActivity : AppCompatActivity() {
private val userViewModel: UserViewModel by viewModels()
private lateinit var binding: ActivityMainBinding
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = ActivityMainBinding.inflate(layoutInflater)
setContentView(binding.root)
// オブザーバーを追加して、LiveData が更新されたときに UI を更新します
userViewModel.user.observe(this, { user ->
// ここで UI を更新します。例: TextView にユーザー名を表示
binding.textViewUserName.text = user.name
})
// 任意のタイミングで、ViewModel のデータを更新します(例:ボタンクリック時)
binding.buttonUpdate.setOnClickListener {
val newUser = User(id = 1, name = "New User", email = "newuser@example.com")
userViewModel.setUser(newUser)
}
}
}
ここでは、MainActivity で UserViewModel のインスタンスを取得し、user プロパティの LiveData にオブザーバーを追加しています。LiveData のデータが変更されるたびに、オブザーバーが通知され、UI を更新することができます。
また、buttonUpdate のクリックリスナー内で、ViewModel のデータを更新しています。これにより、UI が自動的に更新されます。
8.MainActivity クラスで、データバインディングを使用して UI と ViewModel を接続します。まず、プロジェクトの build.gradle(Module)ファイルでデータバインディングを有効にします。
android {
...
buildFeatures {
dataBinding true
}
}
9.アクティビティのレイアウトファイル(例:activity_main.xml)を編集し、 タグで囲み、データバインディング用の変数を追加します。
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<data>
<variable
name="viewModel"
type="com.example.yourappname.viewmodel.UserViewModel" />
</data>
<!-- ここにレイアウトのコンテンツを追加します。例えば、TextView など -->
</layout>
10.MainActivity クラスで、データバインディングを初期化し、ViewModel をバインドします。
class MainActivity : AppCompatActivity() {
private val userViewModel: UserViewModel by viewModels()
private lateinit var binding: ActivityMainBinding
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = DataBindingUtil.setContentView(this, R.layout.activity_main)
binding.lifecycleOwner = this
binding.viewModel = userViewModel
}
}
以上で、MVVM パターンを使用した新しいプロジェクトの作成が完了しました。これで、アプリの UI とデータロジックが分離されており、コードの再利用性やテストの容易性が向上します。
今回の総括
何も考えずに、chatGPTの指示に従ってコードを入力しました。
build.gradleの設定が足りていないかったり、OSSのバージョンなどが古かったりでビルドがなかなか通らない時間はありましたが、ほぼ指示通りにコーディングしたら、MVVMでサンプルを動かすことができました。
およそ2時間くらいかな?
GPT-4は、4時間ごとに100メッセージまでの回数制限が設けられているので、途中でオーバーになってしまいました。
初心者から綺麗なコードを書けるので、エンジニア時代にあったら便利だったんだろうなと思いました。
今後、少しずつですが難しいことをchatGPTなどのAIを活用しながらやって行ってみようと思います。