import 'package:flutter/foundation.dart';

import 'package:pshared/data/mapper/recipient/recipient.dart';
import 'package:pshared/models/describable.dart';
import 'package:pshared/models/payment/type.dart';
import 'package:pshared/models/recipient/payment_method_draft.dart';
import 'package:pshared/models/recipient/recipient.dart';
import 'package:pshared/provider/recipient/methods_cache.dart';
import 'package:pshared/provider/recipient/provider.dart';


class AddressBookRecipientFormProvider extends ChangeNotifier {
  RecipientMethodsCacheProvider? _methodsCache;
  RecipientsProvider? _recipientsProvider;
  final Recipient? _recipient;

  AddressBookRecipientFormProvider({
    Recipient? recipient,
  }) : _recipient = recipient;

  void updateProviders({
    required RecipientMethodsCacheProvider methodsCache,
    required RecipientsProvider recipientsProvider,
  }) {
    _recipientsProvider = recipientsProvider;
    _methodsCache = methodsCache;
  }

  Future<Recipient> save({
    required String name,
    required String email,
    required Map<PaymentType, String> methodNames,
    required List<RecipientMethodDraft> methodDrafts,
  }) async {
    final recipientsProvider = _recipientsProvider;
    final methodsCache = _methodsCache;
    if (recipientsProvider == null || methodsCache == null) {
      throw StateError('Form provider dependencies are not set');
    }

    final trimmedName = name.trim();
    final trimmedEmail = email.trim();

    if (_recipient == null) {
      final created = await recipientsProvider.create(
        name: trimmedName,
        email: trimmedEmail,
      );
      await methodsCache.syncRecipientMethods(
        recipientId: created.id,
        methods: methodDrafts,
        names: methodNames,
      );
      return created;
    }

    final updated = _recipient.copyWith(
      describable: newDescribable(
        name: trimmedName,
        description: _recipient.description,
      ),
      email: trimmedEmail,
    );
    await recipientsProvider.update(updated.toDTO().toJson());
    await methodsCache.syncRecipientMethods(
      recipientId: updated.id,
      methods: methodDrafts,
      names: methodNames,
    );
    return updated;
  }
}
