import 'package:flutter/material.dart'; import 'package:invoiceninja_flutter/data/models/models.dart'; import 'package:invoiceninja_flutter/redux/app/app_actions.dart'; import 'package:invoiceninja_flutter/redux/project/project_actions.dart'; import 'package:invoiceninja_flutter/redux/credit/credit_actions.dart'; import 'package:invoiceninja_flutter/redux/ui/ui_actions.dart'; import 'package:invoiceninja_flutter/ui/credit/credit_pdf_vm.dart'; import 'package:invoiceninja_flutter/ui/credit/edit/credit_edit_vm.dart'; import 'package:invoiceninja_flutter/ui/credit/credit_email_vm.dart'; import 'package:invoiceninja_flutter/ui/credit/credit_screen.dart'; import 'package:invoiceninja_flutter/ui/credit/view/credit_view_vm.dart'; import 'package:redux/redux.dart'; import 'package:invoiceninja_flutter/redux/app/app_state.dart'; import 'package:invoiceninja_flutter/data/repositories/credit_repository.dart'; import 'package:invoiceninja_flutter/main_app.dart'; List> createStoreCreditsMiddleware([ CreditRepository repository = const CreditRepository(), ]) { final viewCreditList = _viewCreditList(); final viewCredit = _viewCredit(); final editCredit = _editCredit(); final showEmailCredit = _showEmailCredit(); final showPdfCredit = _showPdfCredit(); final loadCredits = _loadCredits(repository); final loadCredit = _loadCredit(repository); final saveCredit = _saveCredit(repository); final archiveCredit = _archiveCredit(repository); final deleteCredit = _deleteCredit(repository); final restoreCredit = _restoreCredit(repository); final emailCredit = _emailCredit(repository); final bulkEmailCredits = _bulkEmailCredits(repository); final markSentCredit = _markSentCredit(repository); final downloadCredits = _downloadCredits(repository); final saveDocument = _saveDocument(repository); return [ TypedMiddleware(viewCreditList), TypedMiddleware(viewCredit), TypedMiddleware(editCredit), TypedMiddleware(showEmailCredit), TypedMiddleware(showPdfCredit), TypedMiddleware(loadCredits), TypedMiddleware(loadCredit), TypedMiddleware(saveCredit), TypedMiddleware(archiveCredit), TypedMiddleware(deleteCredit), TypedMiddleware(restoreCredit), TypedMiddleware(emailCredit), TypedMiddleware(bulkEmailCredits), TypedMiddleware(markSentCredit), TypedMiddleware(downloadCredits), TypedMiddleware(saveDocument), ]; } Middleware _viewCredit() { return (Store store, dynamic dynamicAction, NextDispatcher next) async { final action = dynamicAction as ViewCredit; next(action); store.dispatch(UpdateCurrentRoute(CreditViewScreen.route)); if (store.state.prefState.isMobile) { await navigatorKey.currentState.pushNamed(CreditViewScreen.route); } }; } Middleware _viewCreditList() { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as ViewCreditList; next(action); if (store.state.isStale) { store.dispatch(RefreshData()); } store.dispatch(UpdateCurrentRoute(CreditScreen.route)); if (store.state.prefState.isMobile) { navigatorKey.currentState.pushNamedAndRemoveUntil( CreditScreen.route, (Route route) => false); } }; } Middleware _editCredit() { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as EditCredit; next(action); store.dispatch(UpdateCurrentRoute(CreditEditScreen.route)); if (store.state.prefState.isMobile) { navigatorKey.currentState.pushNamed(CreditEditScreen.route); } }; } Middleware _showEmailCredit() { return (Store store, dynamic dynamicAction, NextDispatcher next) async { final action = dynamicAction as ShowEmailCredit; next(action); store.dispatch(UpdateCurrentRoute(CreditEmailScreen.route)); if (store.state.prefState.isMobile) { final emailWasSent = await navigatorKey.currentState.pushNamed(CreditEmailScreen.route); if (action.completer != null && emailWasSent != null && emailWasSent) { action.completer.complete(null); } } }; } Middleware _showPdfCredit() { return (Store store, dynamic dynamicAction, NextDispatcher next) async { final action = dynamicAction as ShowPdfCredit; next(action); store.dispatch(UpdateCurrentRoute(CreditPdfScreen.route)); if (store.state.prefState.isMobile) { navigatorKey.currentState.pushNamed(CreditPdfScreen.route); } }; } Middleware _archiveCredit(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as ArchiveCreditsRequest; final prevCredits = action.creditIds.map((id) => store.state.creditState.map[id]).toList(); repository .bulkAction( store.state.credentials, action.creditIds, EntityAction.archive) .then((List credits) { store.dispatch(ArchiveCreditsSuccess(credits)); if (action.completer != null) { action.completer.complete(null); } }).catchError((Object error) { print(error); store.dispatch(ArchiveCreditsFailure(prevCredits)); if (action.completer != null) { action.completer.completeError(error); } }); next(action); }; } Middleware _deleteCredit(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as DeleteCreditsRequest; final prevCredits = action.creditIds.map((id) => store.state.creditState.map[id]).toList(); repository .bulkAction( store.state.credentials, action.creditIds, EntityAction.delete) .then((List credits) { store.dispatch(DeleteCreditsSuccess(credits)); if (action.completer != null) { action.completer.complete(null); } }).catchError((Object error) { print(error); store.dispatch(DeleteCreditsFailure(prevCredits)); if (action.completer != null) { action.completer.completeError(error); } }); next(action); }; } Middleware _restoreCredit(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as RestoreCreditsRequest; final prevCredits = action.creditIds.map((id) => store.state.creditState.map[id]).toList(); repository .bulkAction( store.state.credentials, action.creditIds, EntityAction.restore) .then((List credits) { store.dispatch(RestoreCreditsSuccess(credits)); if (action.completer != null) { action.completer.complete(null); } }).catchError((Object error) { print(error); store.dispatch(RestoreCreditsFailure(prevCredits)); if (action.completer != null) { action.completer.completeError(error); } }); next(action); }; } Middleware _markSentCredit(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as MarkSentCreditRequest; repository .bulkAction( store.state.credentials, action.creditIds, EntityAction.markSent) .then((credits) { store.dispatch(MarkSentCreditSuccess(credits)); if (action.completer != null) { action.completer.complete(null); } }).catchError((Object error) { print(error); store.dispatch(MarkSentCreditFailure(error)); if (action.completer != null) { action.completer.completeError(error); } }); next(action); }; } Middleware _emailCredit(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as EmailCreditRequest; final origCredit = store.state.creditState.map[action.creditId]; repository .emailCredit(store.state.credentials, origCredit, action.template, action.subject, action.body) .then((void _) { store.dispatch(EmailCreditSuccess()); if (action.completer != null) { action.completer.complete(null); } }).catchError((Object error) { print(error); store.dispatch(EmailCreditFailure(error)); if (action.completer != null) { action.completer.completeError(error); } }); next(action); }; } Middleware _saveCredit(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as SaveCreditRequest; // remove any empty line items final updatedCredit = action.credit.rebuild((b) => b ..lineItems .replace(action.credit.lineItems.where((item) => !item.isEmpty))); repository .saveData(store.state.credentials, updatedCredit) .then((InvoiceEntity credit) { if (action.credit.isNew) { store.dispatch(AddCreditSuccess(credit)); } else { store.dispatch(SaveCreditSuccess(credit)); } action.completer.complete(credit); }).catchError((Object error) { print(error); store.dispatch(SaveCreditFailure(error)); action.completer.completeError(error); }); next(action); }; } Middleware _loadCredit(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as LoadCredit; store.dispatch(LoadCreditRequest()); repository .loadItem(store.state.credentials, action.creditId) .then((credit) { store.dispatch(LoadCreditSuccess(credit)); if (action.completer != null) { action.completer.complete(null); } }).catchError((Object error) { print(error); store.dispatch(LoadCreditFailure(error)); if (action.completer != null) { action.completer.completeError(error); } }); next(action); }; } Middleware _loadCredits(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as LoadCredits; final state = store.state; store.dispatch(LoadCreditsRequest()); repository .loadList( state.credentials, state.createdAtLimit, state.filterDeletedClients) .then((data) { store.dispatch(LoadCreditsSuccess(data)); if (action.completer != null) { action.completer.complete(null); } store.dispatch(LoadProjects()); }).catchError((Object error) { print(error); store.dispatch(LoadCreditsFailure(error)); if (action.completer != null) { action.completer.completeError(error); } }); next(action); }; } Middleware _downloadCredits(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as DownloadCreditsRequest; repository .bulkAction( store.state.credentials, action.creditIds, EntityAction.download) .then((invoices) { store.dispatch(DownloadCreditsSuccess()); if (action.completer != null) { action.completer.complete(null); } }).catchError((Object error) { print(error); store.dispatch(DownloadCreditsFailure(error)); if (action.completer != null) { action.completer.completeError(error); } }); next(action); }; } Middleware _bulkEmailCredits(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as BulkEmailCreditsRequest; repository .bulkAction( store.state.credentials, action.creditIds, EntityAction.emailCredit) .then((List credits) { store.dispatch(BulkEmailCreditsSuccess(credits)); if (action.completer != null) { action.completer.complete(null); } }).catchError((Object error) { print(error); store.dispatch(BulkEmailCreditsFailure(error)); if (action.completer != null) { action.completer.completeError(error); } }); next(action); }; } Middleware _saveDocument(CreditRepository repository) { return (Store store, dynamic dynamicAction, NextDispatcher next) { final action = dynamicAction as SaveCreditDocumentRequest; if (store.state.isEnterprisePlan) { repository .uploadDocument( store.state.credentials, action.credit, action.multipartFile) .then((credit) { store.dispatch(SaveCreditSuccess(credit)); action.completer.complete(null); }).catchError((Object error) { print(error); store.dispatch(SaveCreditDocumentFailure(error)); action.completer.completeError(error); }); } else { const error = 'Uploading documents requires an enterprise plan'; store.dispatch(SaveCreditDocumentFailure(error)); action.completer.completeError(error); } next(action); }; }