#!/usr/bin/python
#encoding: utf8

'''
Aplikacja dokonuje rzutowania synsetow Slowosieci na SUMO. Wynikiem dzialania aplikacji
sa informacje, ktore synsety Slowosieci, polaczone sa z ktorymi synsetami PWN oraz ktore 
synsety PWN polaczone sa z pojeciami SUMO wraz z informacjami o typie reacji pomiedzy 
Slowosiecia a PWN oraz PWN a SUMO oraz opcjonalnie relacja wynikowa pomiedzy Slowosiecia 
a SUMO - jezeli ustalono przelacznik odpowiadajacy za wykonanie rzutowania. 
Synsety, ktore maja zostac zrzutowane podawane sa z dwoch zrodel:
	- oznaczony za pomoca WSD (np. za pomoca narzedzia NP-UKB-WSD z pakietu npsemrel) korpus
	- polaczenie do bazy Slowosieci i rzutowanie wszystkich synsetow znajdujacych sie w Slowosieci
Wybor zrodla rzutowania wybiera uzytkownik przy uruchamianiu aplikacji.


Przyklady uruchomienia:
- Pobranie na podstawie korpusu
	PYTHONIOENCODING=utf8 python wn_pwn2sumo.py -i /home/pkedzia/work/corps/kpwr-1.0-ukbwsd-plwn/index_wsd.txt -d ../../cfg/spock.db

- Pobranie z bazy
	PYTHONIOENCODING=utf8 python wn_pwn2sumo.py -d ../../cfg/spock.db


Wynik uruchomienia, zarowno z bazy jak i korpusu wypisywany jest do pliku podanego na wejsciu 
programu i ma postac:
	mowa.2;6;18106;syn_pa;language.5;6;158791;capability;subsumed;+;subsumed
lub, jezeli rzutowanie ma nie byc wykonane:
	mowa.2;6;18106;syn_pa;language.5;6;158791;capability;subsumed;+
'''

import argparse
import os
import sys

import corpus2
from npsemrel.carrot.db import db
from plumper.wn import plwnhandler
from plumper.sumo import mapper


def make_parser():
    desc = 'Krok pierwszy rzutowania plWN -> SUMO'
    parser = argparse.ArgumentParser(description=desc)
    parser.add_argument('-d', '--db-cfg-file', dest='dbcfgfile', required=True)
    parser.add_argument('-i', '--indexcorp-file', dest='indexcorp_file',
                        required=False)
    parser.add_argument('-t', '--tagset', dest='tagset', required=False,
                        default='nkjp')
    parser.add_argument('-r', '--resolve-plwn-sumo', dest='resolve_plwn_sumo',
                        action='store_true')
    parser.add_argument('-o', '--output-file', dest='output_file',
                        required=True)
    return parser


def read_corpus_get_wsd(corpus_index_file, tagset):
    synids = []
    with open(corpus_index_file, 'rt') as corpidx:
        for corpfile in corpidx:
            corpfile = os.path.join(os.path.dirname(corpus_index_file),
                                    corpfile).strip()
            try:
                cclreader = corpus2.CclRelReader(tagset, corpfile, corpfile)
                document = cclreader.read()
                for paragraph in document.paragraphs():
                    for sentence in paragraph.sentences():
                        for token in sentence.tokens():
                            md = token.get_metadata()
                            if md:
                                ukb_syn_id = md.get_attribute(
                                    'sense:ukb:syns_id')
                                if ukb_syn_id:
                                    synids.append(ukb_syn_id)
            except Exception, e:
                pass
            # print >> sys.stderr, e
    return set(synids)

def show_p2s_map_list(p2s_map_list):
    for p2s in p2s_map_list:
        sense_idx = p2s.pwn_sense_index
        print '%s.%d' % (sense_idx.lemma, sense_idx.sensenum)

def main(argv=None):
    parser = make_parser()
    args = parser.parse_args(argv)

    tagset = corpus2.get_named_tagset(args.tagset)

    dbcon = db.DB()
    print >> sys.stderr, 'Connecting to database...'
    dbconnection = dbcon.connect(args.dbcfgfile)
    if not dbconnection:
        print >> sys.stderr, 'Cannot connect to DB!'
        return 1
    print >> sys.stderr, ' connected!'

    dbplwn = plwnhandler.DbPlwnHandler(dbconnection)

    '''
    +-----+----------------+
    | ID  | shortcut       |
    +-----+----------------+
    | 201 | mero:cz_pa     |
    | 202 | mero:el_pa     |
    | 203 | mero:mat_pa    |
    | 205 | holo:cz_pa     |
    | 206 | holo:el_pa     |
    | 207 | holo:mat_pa    |
    | 208 | syn_pa         |
    | 210 | hipo_pa        |
    | 212 | hiper_pa       |
    | 222 | po_pa          |
    | 225 | syncz_pa       |
    | 228 | synmr_pa       |
    +-----+----------------+
    '''
    #	bez 222
    relations_id = [201, 202, 203, 205, 206, 207, 208, 210, 212, 225, 228]

    synids = []
    # czytam albo korpus
    if args.indexcorp_file != None:
        print >> sys.stderr, 'Reading %s' % args.indexcorp_file,
        synids = read_corpus_get_wsd(args.indexcorp_file, tagset)
        print >> sys.stderr, 'done'
    else:
        # albo wszystko ze slowosieci
        print >> sys.stderr, 'Mapping whole plWordNet...'
        synids = dbplwn.get_all_synset_ids()

    # sense p2s
    pwn_map_dir = '../../resources/pwn_sumo_map'
    senseindexfile = '../../resources/wn30-dict/index.sense'
    senseindexfiles = [
        os.path.join(pwn_map_dir, 'WordNetMappings30-adj.txt'),
        os.path.join(pwn_map_dir, 'WordNetMappings30-adv.txt'),
        os.path.join(pwn_map_dir, 'WordNetMappings30-noun.txt'),
        os.path.join(pwn_map_dir, 'WordNetMappings30-verb.txt'),
        os.path.join(pwn_map_dir, 'MWEmapping-noun.txt')
    ]
    mapper_obj = mapper.Mapper()
    mapper_obj.basic_sumo_mapping(args.output_file, args.resolve_plwn_sumo,
                                  dbplwn, relations_id, senseindexfile,
                                  senseindexfiles, synids)

if __name__ == '__main__':
    main()

