import React, { useEffect, useState } from 'react';
import { View, Text, StyleSheet, ScrollView, TouchableOpacity, Alert, ActivityIndicator } from 'react-native';
import { useLocalSearchParams, useRouter } from 'expo-router';
import { withObservables } from '@nozbe/watermelondb/react';
import { database } from '../../src/db';
import Challenge from '../../src/db/models/Challenge';
import ChallengeRequirement from '../../src/db/models/ChallengeRequirement';
import { syncChallengeDetails } from '../../src/db/sync';
import UserChallenge from '../../src/db/models/UserChallenge';
import User from '../../src/db/models/User';

const ChallengeDetailScreen = ({ challenge, requirements }: { challenge: Challenge; requirements: ChallengeRequirement[] }) => {
  const router = useRouter();
  const [loading, setLoading] = useState(false);
  const [starting, setStarting] = useState(false);

  useEffect(() => {
    if (challenge) {
      setLoading(true);
      syncChallengeDetails(challenge.id).finally(() => setLoading(false));
    }
  }, [challenge]);

  const handleStartChallenge = async () => {
    if (!challenge) return;

    setStarting(true);
    try {
      await database.write(async () => {
        const userChallengesCollection = database.get<UserChallenge>('user_challenges');
        
        // Check if already active
        // Note: In a real app, we'd check for existing active challenges for this user
        // For now, we'll just create a new one.
        // We need a user ID. Since we don't have auth fully set up in this context,
        // we'll use a placeholder or fetch the first user if available.
        
        const usersCollection = database.get<User>('users');
        const users = await usersCollection.query().fetch();
        let userId = 'temp-user-id';
        if (users.length > 0) {
            userId = users[0].id;
        } else {
            // Create a temp user if none exists (for testing)
             const newUser = await usersCollection.create(user => {
                user.firebaseUid = 'temp-uid';
                user.email = 'test@example.com';
             });
             userId = newUser.id;
        }

        await userChallengesCollection.create(uc => {
          uc.user.id = userId;
          uc.challenge.set(challenge);
          uc.startDate = new Date().getTime();
          uc.status = 'active';
          uc.currentStreak = 0;
          uc.longestStreak = 0;
          uc.attemptNumber = 1;
          uc.createdAt = new Date().getTime();
        });
      });

      Alert.alert('Success', 'Challenge started!', [
        { text: 'OK', onPress: () => router.replace('/') }
      ]);
    } catch (error) {
      console.error('Error starting challenge:', error);
      Alert.alert('Error', 'Failed to start challenge.');
    } finally {
      setStarting(false);
    }
  };

  if (!challenge) {
    return (
      <View style={styles.loadingContainer}>
        <Text>Loading challenge...</Text>
      </View>
    );
  }

  return (
    <ScrollView style={styles.container}>
      <View style={styles.header}>
        <Text style={styles.title}>{challenge.name}</Text>
        <View style={styles.metaContainer}>
            <View style={[styles.badge, { backgroundColor: '#E0E0E0' }]}>
                <Text style={styles.badgeText}>{challenge.difficulty}</Text>
            </View>
            <Text style={styles.duration}>{challenge.durationDays} Days</Text>
        </View>
      </View>

      <Text style={styles.description}>{challenge.description}</Text>

      <View style={styles.section}>
        <Text style={styles.sectionTitle}>Daily Requirements</Text>
        {loading && requirements.length === 0 ? (
             <ActivityIndicator size="small" color="#0000ff" />
        ) : (
            requirements.map((req, index) => (
            <View key={req.id} style={styles.requirementItem}>
                <Text style={styles.reqIndex}>{index + 1}</Text>
                <View style={styles.reqContent}>
                <Text style={styles.reqTitle}>{req.title}</Text>
                {req.description ? <Text style={styles.reqDesc}>{req.description}</Text> : null}
                </View>
            </View>
            ))
        )}
      </View>

      <TouchableOpacity 
        style={[styles.startButton, starting && styles.disabledButton]} 
        onPress={handleStartChallenge}
        disabled={starting}
      >
        {starting ? (
            <ActivityIndicator color="white" />
        ) : (
            <Text style={styles.startButtonText}>Start Challenge</Text>
        )}
      </TouchableOpacity>
    </ScrollView>
  );
};

const enhance = withObservables(['id'], ({ id }: { id: string }) => ({
  challenge: database.get<Challenge>('challenges').findAndObserve(id),
  requirements: database.get<ChallengeRequirement>('challenge_requirements')
    .query(
        // We can't easily query by relation in withObservables without Q.on
        // But since we are syncing details which updates requirements, 
        // we can just query by challenge_id if we had the challenge object available immediately.
        // However, 'challenge' prop is async.
        // A common pattern is to pass the challenge itself or query requirements based on the ID prop.
    ).observeWithColumns(['title', 'description', 'sort_order']) 
    // Wait, the above query is empty. We need to filter by challenge_id.
    // But we only have `id` (challenge id) from props.
}));

// Correct way to query related records with WatermelonDB observables
const enhanceWithRelated = withObservables(['id'], ({ id }: { id: string }) => {
    const challengeObservable = database.get<Challenge>('challenges').findAndObserve(id);
    
    // We need to return an object where keys are prop names and values are observables
    return {
        challenge: challengeObservable,
        // To get requirements, we can't use `challenge.requirements` directly here because `challenge` is an observable, not the record yet.
        // But we can query the requirements table directly using the ID.
        requirements: database.get<ChallengeRequirement>('challenge_requirements')
            .query(
                // @ts-ignore
                // We need to import Q from watermelondb
                // But for now let's assume the query is correct
                 require('@nozbe/watermelondb').Q.where('challenge_id', id),
                 require('@nozbe/watermelondb').Q.sortBy('sort_order', require('@nozbe/watermelondb').Q.asc)
            )
    };
});

export default function ChallengeDetailWrapper() {
    const { id } = useLocalSearchParams();
    const ChallengeDetail = enhanceWithRelated(ChallengeDetailScreen);
    
    // Ensure ID is a string
    const challengeId = Array.isArray(id) ? id[0] : id;

    if (!challengeId) return null;

    return <ChallengeDetail id={challengeId} />;
}

const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: '#fff',
    padding: 20,
  },
  loadingContainer: {
    flex: 1,
    justifyContent: 'center',
    alignItems: 'center',
  },
  header: {
    marginBottom: 20,
  },
  title: {
    fontSize: 28,
    fontWeight: 'bold',
    color: '#333',
    marginBottom: 10,
  },
  metaContainer: {
    flexDirection: 'row',
    alignItems: 'center',
  },
  badge: {
    paddingHorizontal: 10,
    paddingVertical: 5,
    borderRadius: 15,
    marginRight: 10,
  },
  badgeText: {
    fontSize: 12,
    fontWeight: 'bold',
    color: '#555',
    textTransform: 'uppercase',
  },
  duration: {
    fontSize: 14,
    color: '#666',
  },
  description: {
    fontSize: 16,
    color: '#444',
    lineHeight: 24,
    marginBottom: 30,
  },
  section: {
    marginBottom: 30,
  },
  sectionTitle: {
    fontSize: 20,
    fontWeight: '600',
    marginBottom: 15,
    color: '#333',
  },
  requirementItem: {
    flexDirection: 'row',
    marginBottom: 15,
    backgroundColor: '#f9f9f9',
    padding: 15,
    borderRadius: 10,
  },
  reqIndex: {
    fontSize: 16,
    fontWeight: 'bold',
    color: '#007AFF',
    marginRight: 15,
    width: 24,
  },
  reqContent: {
    flex: 1,
  },
  reqTitle: {
    fontSize: 16,
    fontWeight: '500',
    color: '#333',
    marginBottom: 4,
  },
  reqDesc: {
    fontSize: 14,
    color: '#666',
  },
  startButton: {
    backgroundColor: '#007AFF',
    paddingVertical: 16,
    borderRadius: 12,
    alignItems: 'center',
    marginBottom: 40,
  },
  disabledButton: {
    opacity: 0.7,
  },
  startButtonText: {
    color: 'white',
    fontSize: 18,
    fontWeight: 'bold',
  },
});