import React from 'react';
import { Dimensions, Text, View, FlatList, TouchableOpacity } from 'react-native';
import { Button } from 'react-native-elements';

import { strings } from '../../locales/i18n';
import { fetchAuth } from '../../utils/fetch';
import { showFlashErrorMessage } from '../../utils/errorHandler';

import UserListItem from '../../components/new/UserListItem';
import ListActivityIndicator from '../../components/new/ListActivityIndicator';
import colors from '../../config/colors.json';
import errors from '../../config/errors';
import endpoints from '../../config/apiEndpoints';
import { loadSignupState, saveAuthState } from '../../realm/actions/AuthActions';

export default class SignupScreenSix extends React.Component {
  static navigationOptions = {
    title: strings('contact.suggestedContacts_title'),
    headerStyle: { borderBottomWidth: 0, backgroundColor: colors.offWhite },
    headerTintColor: '#0D497E',
    headerRight: <Text style={{ color: colors.middleGrey, marginRight: 5 }}>6/6</Text>
  };

  constructor(props) {
    super(props);
    this.state = {
      users: [],
      selectedUsers: new Map(),
      loading: true
    };

    this.onLoad();
    this.onSignup = this.onSignup.bind(this);
  }

  // Load suggested contacts
  async onLoad() {
    const resp = await fetchAuth(endpoints.suggestProfiles);
    this.setState({ loading: false, users: resp.profiles });

    if (resp.error) {
      showFlashErrorMessage(errors.APP_NETWORK_ERROR);
    }
  }

  // Add user to selected map 
  onSelectUser(index) {
    this.setState((state) => {
      const selectedUsers = new Map(state.selectedUsers);
      if (selectedUsers.has(index)) {
        selectedUsers.delete(index);
      } else {
        selectedUsers.set(index, state.users[index].tagferId);
      }

      return { selectedUsers };
    });
  }

  async onSignup() {
    this.setState({ loading: true });
    const { prevState } = await loadSignupState(6);
    const { user, profile, invites } = prevState;
    const invitesObject = this.createInvitesObject(invites, this.state.selectedUsers.values());
    const requestBody = this.createSignupRequest(user, profile, invitesObject);
    console.log(requestBody);
    const resp = await fetchAuth(endpoints.signup, requestBody);
    this.setState({ loading: false });

    if (resp.error) {
      showFlashErrorMessage(resp.error);
    } else {
      saveAuthState(resp.sessionId);
      this.props.navigation.navigate('App');
    } 
  }

  createSignupRequest(user, profile, invites) {
    const { email, password, firstName, lastName, tagferId, formattedPhoneNumber } = user;
    const { jobTitle, companyName, companyEmail, companyPhoneNumber, photoBytes } = profile;
    return {
      user: {
        email,
        password,
        tagferId,
        phoneNumber: formattedPhoneNumber
      },
      profile: {
        fullName: `${firstName} ${lastName}`,
        jobTitle,
        companyName,
        companyEmail,
        companyPhoneNumber,
        photoBytes
      },
      invites: {
        phoneNumbers: invites.phoneNumbers,
        requests: invites.tagferIds
      }
    };
  }

  createInvitesObject(invites, suggested) {
    const { tagferIds, phoneNumbers } = invites;
    const set = new Set();

    // Avoids sending duplicate tagferIds
    for (const tagferId of suggested) { set.add(tagferId); }
    for (let i = 0; i < tagferIds.length; i++) { set.add(tagferIds[i]); }

    return {
      tagferIds: [...set.values()],
      phoneNumbers: [...phoneNumbers.values()]
    };
  }

  // Render a single entry in the list
  renderItem(profile, index) {
    const selected = this.state.selectedUsers.has(index);
    return <UserListItem profile={profile} selected={selected} onPress={() => this.onSelectUser(index)} />;
  }

  render() {
    return (
      <View style={styles.container}>
        {/* INSTRUCTIONS + SKIP BUTTON */}
        <InstructionsSection onSkip={this.onSignup} />

        {/* SUGGESTED CONTACTS */}
        <FlatList 
          data={this.state.users}
          extraData={this.state}
          renderItem={({ item, index }) => this.renderItem(item, index)}
          keyExtractor={(item) => item.tagferId}
          style={{ flex: 1, marginHorizontal: 10 }}
          ListEmptyComponent={<ListActivityIndicator />}
        />

        {/* SIGNUP BUTTON */}
        <Button
          onPress={this.onSignup}
          title={strings('userCreateFlow.signUp.title')}
          buttonStyle={styles.buttonStyle}
          loading={this.state.loading}
          disabled={this.state.loading}
          fontSize={20}
        />
      </View>
    );
  }
}

const InstructionsSection = ({ onSkip }) => (
  <View style={styles.instructionsContainer}>
    <Text style={styles.instructionsText}>{strings('contact.suggestedContacts_description')}</Text>
    <TouchableOpacity style={{ marginRight: 5 }} onPress={onSkip}>
      <Text style={styles.skipButton}>SKIP</Text>
    </TouchableOpacity>
  </View>
);

const SCREEN_WIDTH = Dimensions.get('window').width;
const styles = {
  container: {
    flex: 1,
    backgroundColor: colors.offWhite
  },
  instructionsContainer: {
    flexDirection: 'row',
    justifyContent: 'space-between',
    marginTop: 10,
    marginBottom: 15
  },
  instructionsText: {
    fontSize: 14,
    color: colors.darkGrey,
    marginLeft: 20
  },
  skipButton: {
    fontSize: 12,
    color: colors.darkGrey 
  },
  buttonStyle: {
    width: SCREEN_WIDTH * 0.9,
    marginTop: 15,
    marginBottom: 30,
    borderRadius: 5,
    backgroundColor: colors.buttonBlue
  }
};
