import * as React from 'react';
import { Dimmer, Loader } from 'semantic-ui-react';
import * as XML from 'xml2js';
import * as _ from 'lodash';
import { LexEditor } from './LexComponents';

const fieldMetaMap = {
  label: { lens: 'label[0]', type: 'text' },
  unl: { lens: 'unl[0]', type: 'text' },
  synset: { lens: 'lexprops[0].wnsynset[0]', type: 'text' },
  guid: { lens: 'guid[0]', type: 'text' },
  pos: { lens: 'pos[0]', type: 'select' },
  image: { lens: 'image[0]', type: 'preview' },
  relations: { lens: 'relations[0]', type: 'text' },
  frame: { lens: 'syntacticprops[0].property[0]._', type: 'select' },
  morphclass: {
    lens: 'lexprops[0].morphology[0].morph[0]._',
    type: 'select'
  },
  stats: { lens: 'stats[0].property[0]._', type: 'text' },
  lang: { lens: '$.id', type: 'select', options: ['en', 'es'] },
};

export class LexSetup extends React.Component<any, any> {
  public componentDidMount() {
    fetch(this.props.fileName)
      .then((response) => response.text())
      .then((xmlString) => {
        XML.parseString(xmlString, (err, lexData) => {
          let allEntries = _.chain(lexData)
            .get<any>('document.lexicon[0].item')
            .flatMap((o: any) => _.chain(o)
              .get<any>('entry')
              .map((p: any) => _.chain(p)
                .get<any>('lang[0]')
                .set('guid[0]', o.$.guid)
                .value())
              .value()
            )
            .value();

          let langReducer = ((result: any, q: any) => {
            let lang = _.get<any>(q, fieldMetaMap.lang.lens, 'en');
            (result[lang] || (result[lang] = [])).push(q);
            return result;
          });
          let langEntries = _.reduce(allEntries, langReducer, {});
          let langs = _.keys(langEntries);
          let selectFields = _.fromPairs(langs.map((lang) => {
            let langOpts = _.fromPairs(_.keys(fieldMetaMap).filter((s) => {
              return fieldMetaMap[s].type === 'select';
            }).map((s) => {
              let lens = fieldMetaMap[s].lens;
              let entries = _.get<any>(langEntries, lang, 'en');
              let selectOptions = _.uniq(entries.map((q: any) => {
                return _.get<any>(q, lens, '');
              }));
              return [s, selectOptions];
            }));
            return [lang, langOpts];
          }));
          this.props.addXmlData(lexData);
          this.setState({
            allEntries, selectFields, fieldMetaMap
          });
        });
      })
      .catch((e) => {
        console.log('errored :', e);
      });
  }

  render() {
    return this.state ? (
      <LexEditor {...this.state} {...this.props} />
    ) : (
        <Dimmer active={true} inverted={true}>
          <Loader inverted={true}>Loading</Loader>
        </Dimmer>
      );
  }
}
