2026-04-23 01:23:18 +00:00
|
|
|
|
import 'dart:async';
|
2026-04-10 15:05:53 +00:00
|
|
|
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
|
|
|
|
|
import '../services/license_service.dart';
|
|
|
|
|
|
|
2026-04-23 01:23:18 +00:00
|
|
|
|
/// 起動時にキャッシュから事前ロードした値を保持するプロバイダー
|
2026-04-10 15:05:53 +00:00
|
|
|
|
///
|
2026-04-23 01:23:18 +00:00
|
|
|
|
/// main() で override して初期値を渡すことで、
|
|
|
|
|
|
/// licenseStatusProvider が loading 状態を経由せず即座に AsyncData になる。
|
|
|
|
|
|
final licenseInitialStatusProvider = Provider<LicenseStatus?>((ref) => null);
|
|
|
|
|
|
|
|
|
|
|
|
/// ライセンス状態プロバイダー
|
|
|
|
|
|
///
|
|
|
|
|
|
/// - build() は licenseInitialStatusProvider に値がある場合は同期で返す(ちらつきなし)
|
|
|
|
|
|
/// - 同時にバックグラウンドでサーバー検証を実行し、差異があれば状態を更新する
|
|
|
|
|
|
final licenseStatusProvider =
|
|
|
|
|
|
AsyncNotifierProvider<LicenseStatusNotifier, LicenseStatus>(
|
|
|
|
|
|
LicenseStatusNotifier.new,
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
class LicenseStatusNotifier extends AsyncNotifier<LicenseStatus> {
|
|
|
|
|
|
@override
|
|
|
|
|
|
FutureOr<LicenseStatus> build() {
|
|
|
|
|
|
final initial = ref.read(licenseInitialStatusProvider);
|
|
|
|
|
|
if (initial != null) {
|
|
|
|
|
|
// キャッシュ値を同期で返すことで loading 状態をスキップ
|
|
|
|
|
|
_refreshFromServer();
|
|
|
|
|
|
return initial;
|
|
|
|
|
|
}
|
|
|
|
|
|
// override なし(テスト等): 通常フロー
|
|
|
|
|
|
return LicenseService.checkStatus();
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/// バックグラウンドでサーバー検証を実行し、変化があれば状態を更新する
|
|
|
|
|
|
Future<void> _refreshFromServer() async {
|
|
|
|
|
|
try {
|
|
|
|
|
|
final fresh = await LicenseService.checkStatus();
|
|
|
|
|
|
if (state.hasValue && state.value != fresh) {
|
|
|
|
|
|
state = AsyncData(fresh);
|
|
|
|
|
|
}
|
|
|
|
|
|
} catch (_) {
|
|
|
|
|
|
// ネットワークエラーはキャッシュ値を維持
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
2026-04-10 15:05:53 +00:00
|
|
|
|
|
|
|
|
|
|
/// Pro版かどうか(ナビゲーション・機能解放の分岐に使う)
|
2026-04-23 01:23:18 +00:00
|
|
|
|
///
|
|
|
|
|
|
/// licenseStatusProvider が同期で AsyncData を返すため、
|
|
|
|
|
|
/// アプリ起動時に false をちらつかせることなく正しい値を返す。
|
2026-04-10 15:05:53 +00:00
|
|
|
|
final isProProvider = Provider<bool>((ref) {
|
|
|
|
|
|
final statusAsync = ref.watch(licenseStatusProvider);
|
|
|
|
|
|
return statusAsync.maybeWhen(
|
|
|
|
|
|
data: (status) => status == LicenseStatus.pro,
|
|
|
|
|
|
orElse: () => false,
|
|
|
|
|
|
);
|
|
|
|
|
|
});
|