import 'package:flutter_test/flutter_test.dart';
import 'package:travel_mate/models/group.dart';

void main() {
  group('Group Model Tests', () {
    const id = 'group1';
    const name = 'Paris Trip Group';
    const tripId = 'trip1';
    const createdBy = 'user1';
    final createdAt = DateTime(2023, 1, 1);
    final updatedAt = DateTime(2023, 1, 2);
    const memberIds = ['user1', 'user2'];

    final groupInstance = Group(
      id: id,
      name: name,
      tripId: tripId,
      createdBy: createdBy,
      createdAt: createdAt,
      updatedAt: updatedAt,
      memberIds: memberIds,
    );

    test('props correct', () {
      expect(groupInstance.id, id);
      expect(groupInstance.name, name);
      expect(groupInstance.tripId, tripId);
      expect(groupInstance.createdBy, createdBy);
      expect(groupInstance.createdAt, createdAt);
      expect(groupInstance.updatedAt, updatedAt);
      expect(groupInstance.memberIds, memberIds);
      expect(groupInstance.members, isEmpty);
    });

    group('fromMap', () {
      test('returns correct group from valid map', () {
        final map = {
          'name': name,
          'tripId': tripId,
          'createdBy': createdBy,
          'createdAt': createdAt.millisecondsSinceEpoch,
          'updatedAt': updatedAt.millisecondsSinceEpoch,
          'memberIds': memberIds,
        };
        final fromMapGroup = Group.fromMap(map, id);

        expect(fromMapGroup.id, id);
        expect(fromMapGroup.name, name);
        expect(fromMapGroup.tripId, tripId);
        expect(fromMapGroup.createdBy, createdBy);
        expect(fromMapGroup.createdAt, createdAt);
        expect(fromMapGroup.updatedAt, updatedAt);
        expect(fromMapGroup.memberIds, memberIds);
      });

      test('handles missing values gracefully', () {
        final map = <String, dynamic>{};
        final fromMapGroup = Group.fromMap(map, id);

        expect(fromMapGroup.id, id);
        expect(fromMapGroup.name, '');
        expect(fromMapGroup.tripId, '');
        expect(fromMapGroup.createdBy, '');
        expect(fromMapGroup.memberIds, isEmpty);
      });
    });

    group('toMap', () {
      test('returns correct map', () {
        final map = groupInstance.toMap();

        expect(map['name'], name);
        expect(map['tripId'], tripId);
        expect(map['createdBy'], createdBy);
        expect(map['createdAt'], createdAt.millisecondsSinceEpoch);
        expect(map['updatedAt'], updatedAt.millisecondsSinceEpoch);
        expect(map['memberIds'], memberIds);
      });
    });

    group('copyWith', () {
      test('returns object with updated values', () {
        const newName = 'London Trip Group';
        final updatedGroup = groupInstance.copyWith(name: newName);

        expect(updatedGroup.name, newName);
        expect(updatedGroup.id, id);
        expect(updatedGroup.tripId, tripId);
      });

      test('returns distinct object but same values if no args', () {
        final copy = groupInstance.copyWith();
        expect(copy.id, groupInstance.id);
        expect(copy.name, groupInstance.name);
        // Note: Group does not implement == so we check reference inequality but value equality manually or trust fields are copied
        expect(identical(copy, groupInstance), isFalse);
      });
    });
  });
}
