Skip to content

team-musashi/stamp-rally

Repository files navigation

BURALLY

ぶらりとスタンプラリー

ログイン画面 ホーム画面 参加中画面
Screenshot_1671762522 Screenshot_1671762494 Screenshot_1671762510

開発環境をセットアップしよう

開発マシンの OS は Mac、IDE は VSCode の利用を前提としています。

fvm をインストールして Flutter SDK のインストールをする

次の記事を参考にして、fvm をインストールして、fvm コマンドが使える状態にしましょう。

FVMでFlutter SDKのバージョンをプロジェクト毎に管理する

次のコマンドを実行して本プロジェクト指定の Flutter SDK をインスト−ルをしましょう。

fvm install

環境変数を設定する

本アプリで使用する Google マップ用の API キーを取得して、カレントディレクトリで次のコマンドを実行してください。このコマンドを実行しないとアプリは起動しません。

# 引数で与えられた環境変数を基にビルドに必要な `lib/util/env/env.dart` を作成してくれます。
# 作成された `lib/util/env/env.dart` を直接編集しても大丈夫です。

bin/flutter_env -g [Google マップ用の API キー]
パラメータ 説明
-g Must Google マップ用の API キーの値
-h ヘルプを表示します。

Git コミット簡単ツールのインストール

次の記事を参考にして、Git コミット時に Prefix や絵文字を簡単に追加できるツールである commitizengit-cz をインスト−ルしましょう。

Commitizenを使ってgitのコミットメッセージをしっかり書こう

適当なファイルを修正・ステージングにあげて git cz というコマンドを打って次のような表示が出れば OK です。

アプリを実行しよう

開発環境のセットアップが終わったら、VSCode 右下から実行するデバイスを選択し、実行したい Configuration を選択して実行してみましょう。

Configuration 名 プラットフォーム 接続先の Firebase
app-dev iOS / Android flutteruniv-stamp-rally-dev
app-prod iOS / Android flutteruniv-stamp-rally-prod

実装時の Tips

コードの自動生成

go_router_builderfreezed を使った自動生成ファイルを変更した場合は次のコマンドを実行してください。

make build-runner

システム構成

ポイントは Cloud Functions は裏で動くこと。

システム構成図

アーキテクチャ / パッケージ

アーキテクチャ図

Presentation 層

ユーザーとの I/F を担う層。Application 層と Domain 層に依存する。Infrastructure 層に依存してはいけない。

Widget

ページや UI 部品の Widget クラス群。State を監視( watch / listen )して UI に表現する。ユーザーイベントを検知して Service のメソッドを呼び出す。キャッシュが効かなくなるので直接 Repository Interface を呼び出してはいけない。画面遷移の実装は Widget のイベントハンドラー内で行ってよい。

Application 層

アプリケーションのロジックや状態を定義する層。Domain 層に依存する。Presentation 層と Infrastructure 層に依存してはいけない。

State

アプリのあらゆる状態。Domain 層の Entity そのものでもよいし、複数の Repository をまたいだ Entity を統合するクラスでもよい。State は StateProvider 等でラップされ Widget や他の State から参照される。

Service

ユーザーイベントを受け付けて、複数の Repository Interface を呼び出して Entity を受け取って State を更新するサービスクラス。Widget からのメソッド呼び出しや、依存する State の更新を契機に発火する。

Domain 層

ドメインロジックやドメインオブジェクト(エンティティ)を定義する層。どの層にも依存してはいけない。

Entity

Repository Interface で扱うドメインオブジェクト(データの構造体)。入力値のバリデーションは Entity のコンストラクタで実装する。Infrastructure 層が投げる例外はドメイン層で定義する。

Repository Interface

データの永続化や外部サービス連携を担う Repository のインターフェース。集約毎に定義する。

Infrastructure 層

データの永続化や外部サービス連携を担う層。Domain 層に依存する。Presentation 層と Application 層に依存してはいけない。

Repository Implements

Repository Interface の実装。Data Source を利用してデータの永続化を行う。

Data Source

様々なデータソース。Firebase だったり、API だったり、Hive だったり、SharedPreferences だったり、Isar だったりする。

フォルダ構成

├── application                              アプリケーション層
│   └── <関心事>
│       ├── <state>                          状態クラス群
│       └── <関心事>_service.dart             サービスクラス
├── domain                                   ドメイン層
│   ├── exceptions.dart                      例外クラス
│   └── repository
│       └── <集約>
│           ├── <集約>_repository.dart        リポジトリのインターフェースクラス
│           └── entity                       集約単位のエンティティ
├── infrastructure                           インフラストラクチャ層
│   └── <データソース>
│       └── <集約>
│           └── <集約>_repository.dart       リポジトリの実装
├── presentation
│   ├── app.dart                             アプリケーション
│   ├── router.dart                          ルーティング
│   ├── theme.dart                           テーマ
│   ├── component                            プレゼンテーション層で共通の Widget
│   └── page
│       └── <関心事>
│           ├── component                    画面単位の Widget
│           └── <関心事>_<CURD>page.dart      画面Widget
└── util                                     どの層からもアクセス可能な便利クラス(ロガー、拡張メソッドなど)

処理の流れの例

ユーザー操作を契機とした処理の流れの例を図にしました。Riverpod の ref.listen() を使ってローディング表示や SnackBar の表示を制御しています。図には示していませんがエラー時のエラーダイアログの表示も制御できます。

手続き的に処理をするよりも、コードが簡素になりますしコードの再利用もしやすくなりますが、少し理解しづらいので図にしてみました。

処理の流れ

ファイル分割の方針

基本的に 関心事 毎にファイルを分割しています。1つのファイルに複数のクラスがあっても問題ありません。ファイル名は「ファイル名 = クラス名」とはせず 関心事.dart とします。

ブランチモデル

git-flow を採用しています。

実装するときは?

上のブランチモデルに従います。具体的には次のとおりです。

  1. develop ブランチに移動(checkout)して最新の状態にする(pull
  2. feature/0-hoge ブランチを作成して移動する
  • ブランチ名の 0 は Issue 番号、hoge は実装する内容を端的に表した言葉です
  • すべてハイフン区切りでお願いします
  1. Feature ブランチ上で実装をする
  2. 実装が完了したら GitHub サイト上で develop ブランチ向けにプルリクエストを作成する
  • 原則レビュー不要、必要に応じて誰かにレビュー依頼を出して下さい
  1. GitHub サイト上でマージを実行
  2. Issue を Close する

Firebase 関連のタスクが発生したときは?

発生した時点で stamp-rally-firebase に Issue を起票して修正をしてください。

CI (継続的インテグレーション)

GitHub Actions を利用して CI を構築しています。

発火タイミング 実行内容
developにマージ
PR作成・更新
コードフォーマット
静的解析(flutter analyze)
テスト(flutter test)
Androidリリースビルド
結果を共同開発用のSlackに通知

CD (継続的デリバリー)

対応していません。