import 'package:didvan/models/enums.dart';
import 'package:didvan/models/overview_data.dart';
import 'package:didvan/models/home_page_content/swot.dart';
import 'package:didvan/providers/core.dart';
import 'package:didvan/services/network/request.dart';
import 'package:didvan/services/network/request_helper.dart';
import 'package:didvan/views/home/bookmarks/bookmark_service.dart';
import 'package:didvan/services/swot_service.dart';

class BookmarksState extends CoreProvier {
  final List<OverviewData> bookmarks = [];
  List<SwotItem> bookmarkedSwotItems = [];

  String search = '';
  String lastSearch = '';
  int page = 1;
  int lastPage = 1;
  List<int> selectedTypes = [];
  DateTime? startDate;
  DateTime? endDate;
  bool get isFiltered =>
      selectedTypes.isNotEmpty || startDate != null || endDate != null;

  bool _swotItemsLoading = false;
  bool get searching => search.isNotEmpty;
  bool get swotItemsLoading => _swotItemsLoading;

  Future<void> loadInitialData() async {
    appState = AppState.busy;
    _swotItemsLoading = true;
    bookmarks.clear();
    bookmarkedSwotItems.clear();
    notifyListeners();

    await Future.wait([
      _fetchGeneralBookmarks(page: 1),
      _fetchSwotBookmarks(),
    ]);

    if (appState != AppState.failed && !searching) {
      appState = AppState.idle;
    } else if (appState != AppState.failed &&
        searching &&
        bookmarks.isEmpty &&
        bookmarkedSwotItems.isEmpty) {
      appState = AppState.idle;
    }
    _swotItemsLoading = false;
    notifyListeners();
  }

  Future<void> _fetchGeneralBookmarks({required int page}) async {
    if (page == 1) bookmarks.clear();
    this.page = page;
    if (!searching) lastSearch = search;

    final service = RequestService(
      RequestHelper.searchMarks(
        page: page,
        search: search.isNotEmpty ? search : null,
        types: selectedTypes.isNotEmpty ? selectedTypes : null,
        startDate: startDate?.toIso8601String().split('T').first,
        endDate: endDate?.toIso8601String().split('T').first,
      ),
    );
    await service.httpGet();
    if (service.isSuccess) {
      lastPage = service.result['lastPage'];
      final marks = service.result['contents'];
      for (var i = 0; i < marks.length; i++) {
        bookmarks.add(OverviewData.fromJson(marks[i]));
      }
    } else {
      appState = AppState.failed;
    }
  }

  Future<void> searchAndLoadData({required int page}) async {
    appState = AppState.busy;
    _swotItemsLoading = true;
    bookmarks.clear();
    notifyListeners();

    await Future.wait([
      _fetchGeneralBookmarks(page: page),
      _fetchSwotBookmarks(),
    ]);

    if (appState != AppState.failed) {
      appState = AppState.idle;
    }
    _swotItemsLoading = false;
    notifyListeners();
  }

  Future<void> _fetchSwotBookmarks() async {
    try {
      if (selectedTypes.isNotEmpty && !selectedTypes.contains(8)) {
        bookmarkedSwotItems = [];
        return;
      }

      final postIds = await BookmarkService.fetchBookmarks();
      if (postIds.isNotEmpty) {
        final allSwots = await SwotService.fetchSwotItems();

        bookmarkedSwotItems = allSwots.where((swot) {
          final isBookmarked = postIds.contains(swot.id);
          if (search.isEmpty) return isBookmarked;
          return isBookmarked &&
              swot.title.toLowerCase().contains(search.toLowerCase());
        }).toList();
      } else {
        bookmarkedSwotItems = [];
      }
    } catch (e) {
      bookmarkedSwotItems = [];
    }
  }

  void onMarkChanged(int id, bool value) {
    bookmarks.removeWhere((element) => element.id == id);
    notifyListeners();
  }

  void onSwotMarkChanged(int swotId) {
    bookmarkedSwotItems.removeWhere((element) => element.id == swotId);
    notifyListeners();
  }

  void resetFilters([bool notify = true]) {
    selectedTypes.clear();
    startDate = null;
    endDate = null;
    if (notify) {
      loadInitialData();
    }
  }

  void update() {
    notifyListeners();
  }
}
