215 lines
5.7 KiB
Dart
215 lines
5.7 KiB
Dart
import 'dart:convert';
|
|
import 'package:flutter/foundation.dart';
|
|
import 'package:shared_preferences/shared_preferences.dart';
|
|
|
|
import '../config/api_config.dart';
|
|
import '../models/club_model.dart';
|
|
import './api_service.dart';
|
|
import './event_bus.dart';
|
|
|
|
class ClubService with ChangeNotifier {
|
|
List<Club> _clubs = [];
|
|
Club? _currentClub;
|
|
bool _isLoading = false;
|
|
String? _token;
|
|
ApiService _apiService;
|
|
|
|
// 기본 생성자
|
|
ClubService() : _apiService = ApiService();
|
|
|
|
// 테스트용 생성자
|
|
ClubService.forTest(this._apiService);
|
|
|
|
List<Club> get clubs => [..._clubs];
|
|
Club? get currentClub => _currentClub;
|
|
bool get isLoading => _isLoading;
|
|
|
|
// 초기화 함수
|
|
Future<void> initialize(String token) async {
|
|
_token = token;
|
|
_apiService.setToken(token);
|
|
|
|
// 저장된 현재 클럽 ID 가져오기
|
|
final prefs = await SharedPreferences.getInstance();
|
|
final clubId = prefs.getString(ApiConfig.clubIdKey);
|
|
|
|
if (clubId != null) {
|
|
await fetchClubById(clubId);
|
|
}
|
|
}
|
|
|
|
// 사용자의 모든 클럽 가져오기
|
|
Future<void> fetchUserClubs() async {
|
|
if (_token == null) return;
|
|
|
|
_isLoading = true;
|
|
notifyListeners();
|
|
|
|
try {
|
|
final data = await _apiService.post('${ApiConfig.clubs}/user');
|
|
|
|
final List<dynamic> clubsData = data;
|
|
|
|
_clubs = clubsData.map((clubData) => Club.fromJson(clubData)).toList();
|
|
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
} catch (e) {
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
throw Exception('클럽 목록을 불러오는데 실패했습니다: $e');
|
|
}
|
|
}
|
|
|
|
// ID로 클럽 정보 가져오기
|
|
Future<void> fetchClubById(String clubId) async {
|
|
if (_token == null) return;
|
|
|
|
_isLoading = true;
|
|
notifyListeners();
|
|
|
|
try {
|
|
final data = await _apiService.post(
|
|
'${ApiConfig.clubs}',
|
|
data: {'clubId': clubId},
|
|
);
|
|
|
|
// 백엔드에서는 club 키로 감싸지 않고 직접 클럽 객체를 반환합니다
|
|
_currentClub = Club.fromJson(data);
|
|
|
|
// 현재 클럽 ID 저장
|
|
final prefs = await SharedPreferences.getInstance();
|
|
await prefs.setString(ApiConfig.clubIdKey, clubId);
|
|
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
} catch (e) {
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
throw Exception('클럽 정보를 불러오는데 실패했습니다: $e');
|
|
}
|
|
}
|
|
|
|
// 현재 클럽 설정
|
|
Future<void> setCurrentClub(String clubId) async {
|
|
await fetchClubById(clubId);
|
|
}
|
|
|
|
// 백엔드에 클럽 선택 요청 (세션에 clubId 저장)
|
|
Future<void> selectClub(String clubId) async {
|
|
if (_token == null) return;
|
|
|
|
_isLoading = true;
|
|
notifyListeners();
|
|
|
|
try {
|
|
await _apiService.post(
|
|
'${ApiConfig.clubs}/select-club',
|
|
data: {'clubId': clubId},
|
|
);
|
|
|
|
// 클럽 선택 성공 후 클럽 정보 가져오기
|
|
await fetchClubById(clubId);
|
|
|
|
// 클럽 ID를 로컬에 저장
|
|
final prefs = await SharedPreferences.getInstance();
|
|
await prefs.setString(ApiConfig.clubIdKey, clubId);
|
|
|
|
// 클럽 데이터도 함께 저장
|
|
if (_currentClub != null) {
|
|
await prefs.setString('${ApiConfig.clubIdKey}_data', jsonEncode(_currentClub!.toJson()));
|
|
}
|
|
|
|
// 클럽 변경 이벤트 발생 - 다른 서비스들에게 알림
|
|
EventBus().fire(ClubChangedEvent(clubId));
|
|
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
} catch (e) {
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
throw Exception('클럽 선택에 실패했습니다: $e');
|
|
}
|
|
}
|
|
|
|
// 클럽 생성
|
|
Future<Club> createClub(Club club) async {
|
|
if (_token == null) {
|
|
throw Exception('인증이 필요합니다');
|
|
}
|
|
|
|
_isLoading = true;
|
|
notifyListeners();
|
|
|
|
try {
|
|
final data = await _apiService.post(
|
|
'${ApiConfig.clubs}',
|
|
data: club.toJson(),
|
|
);
|
|
|
|
final newClub = Club.fromJson(data['club']);
|
|
|
|
_clubs.add(newClub);
|
|
_currentClub = newClub;
|
|
|
|
// 현재 클럽 ID 저장
|
|
final prefs = await SharedPreferences.getInstance();
|
|
await prefs.setString(ApiConfig.clubIdKey, newClub.id);
|
|
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
|
|
return newClub;
|
|
} catch (e) {
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
throw Exception('클럽 생성에 실패했습니다: $e');
|
|
}
|
|
}
|
|
|
|
// 클럽 정보 업데이트
|
|
Future<Club> updateClub(String clubId, Map<String, dynamic> updates) async {
|
|
if (_token == null) {
|
|
throw Exception('인증이 필요합니다');
|
|
}
|
|
|
|
_isLoading = true;
|
|
notifyListeners();
|
|
|
|
try {
|
|
final data = await _apiService.put(
|
|
ApiConfig.clubs,
|
|
data: {
|
|
'clubId': clubId,
|
|
...updates,
|
|
},
|
|
);
|
|
|
|
// 백엔드 응답 처리: 직접 클럽 객체가 반환되거나 {club: {...}} 형태로 반환될 수 있음
|
|
final updatedClub = data is Map && data.containsKey('club')
|
|
? Club.fromJson(data['club'])
|
|
: Club.fromJson(data);
|
|
|
|
// 클럽 목록 업데이트
|
|
final index = _clubs.indexWhere((club) => club.id == clubId);
|
|
if (index >= 0) {
|
|
_clubs[index] = updatedClub;
|
|
}
|
|
|
|
// 현재 클럽이 업데이트된 클럽인 경우 업데이트
|
|
if (_currentClub?.id == clubId) {
|
|
_currentClub = updatedClub;
|
|
}
|
|
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
|
|
return updatedClub;
|
|
} catch (e) {
|
|
_isLoading = false;
|
|
notifyListeners();
|
|
throw Exception('클럽 정보 업데이트에 실패했습니다: $e');
|
|
}
|
|
}
|
|
}
|