import 'package:dartz/dartz.dart';
import 'package:supabase_flutter/supabase_flutter.dart';
import 'package:tugas_akhir_supabase/core/errors/failures.dart';
import 'package:tugas_akhir_supabase/data/models/field_model.dart';
import 'package:tugas_akhir_supabase/domain/entities/field.dart';
import 'package:tugas_akhir_supabase/domain/repositories/field_repository.dart';

class FieldRepositoryImpl implements FieldRepository {
  final SupabaseClient supabaseClient;

  FieldRepositoryImpl({required this.supabaseClient});

  @override
  Future<Either<Failure, List<Field>>> getFields(String userId) async {
    try {
      final response = await supabaseClient
          .from('fields')
          .select()
          .eq('user_id', userId);

      final fields =
          (response as List)
              .map((e) => FieldModel.fromJson(e).toEntity())
              .toList();

      return Right(fields);
    } on PostgrestException catch (e) {
      return Left(DatabaseFailure(message: e.message));
    } catch (e) {
      return Left(ServerFailure(message: e.toString()));
    }
  }

  @override
  Future<Either<Failure, Field>> createField(Field field) async {
    try {
      final fieldModel =
          field is FieldModel
              ? field as FieldModel
              : FieldModel.fromEntity(field);

      final data = fieldModel.toJson();

      final response =
          await supabaseClient.from('fields').insert(data).select().single();

      return Right(FieldModel.fromJson(response).toEntity());
    } on PostgrestException catch (e) {
      return Left(DatabaseFailure(message: e.message));
    } catch (e) {
      return Left(ServerFailure(message: e.toString()));
    }
  }

  @override
  Future<Either<Failure, Field>> updateField(Field field) async {
    try {
      final fieldModel =
          field is FieldModel
              ? field as FieldModel
              : FieldModel.fromEntity(field);

      final data = fieldModel.toJson();

      final response =
          await supabaseClient
              .from('fields')
              .update(data)
              .eq('id', field.id)
              .select()
              .single();

      return Right(FieldModel.fromJson(response).toEntity());
    } on PostgrestException catch (e) {
      return Left(DatabaseFailure(message: e.message));
    } catch (e) {
      return Left(ServerFailure(message: e.toString()));
    }
  }

  @override
  Future<Either<Failure, bool>> deleteField(String fieldId) async {
    try {
      await supabaseClient.from('fields').delete().eq('id', fieldId);

      return const Right(true);
    } on PostgrestException catch (e) {
      return Left(DatabaseFailure(message: e.message));
    } catch (e) {
      return Left(ServerFailure(message: e.toString()));
    }
  }
}
