#!/usr/bin/env python
import signal
signal.signal(signal.SIGPIPE, signal.SIG_DFL)

import sys
import argparse
import bisect
from lib_alu_detect import *

delta = 50


def load_deletions(s):
    f = gzopen(s)
    d = dict()
    for l in f:
        l = l.strip().split('\t')
        chr = l[0]
        if chr not in d:
            d[chr] = [None] * 2
            d[chr][0] = list()
            d[chr][1] = list()
        st = int(l[5] == '-')
        d[chr][st].append([int(l[1]), int(l[6])])
        d[chr][st].append([int(l[2]) - 1, int(l[7])])
    gzclose(f)
    for chr in d:
        d[chr][0].sort()
        d[chr][1].sort()
    return d


parser = argparse.ArgumentParser(description=sys.argv[0])
parser.add_argument('-v', '--verbose', action='append_const', const=1, default=[], dest='verbose')
parser.add_argument('-d', '--delta', action='store', type=int, default=delta, dest='delta')
#parser.add_argument('-o', '--original-coordinates', action='store_true', default=False, dest='orig_coord')
parser.add_argument('alus_file', action='store')
parser.add_argument('input_file', action='store')
args = parser.parse_args()
set_log_level(len(args.verbose))

delta = args.delta
note('using delta=' + str(delta), 1)


refAlus = load_deletions(args.alus_file)

def check_not_overlap(refAlus, curLine, st):
    left_end = int(curLine[1])
    right_end = int(curLine[2]) - 1
    alu_left_end = int(curLine[6])
    alu_right_end = int(curLine[7])
    left_end_support = int(curLine[9])
    right_end_support = int(curLine[10])

    if left_end_support == 0 and right_end_support == 0:
        # must not overlap a reference Alu on same strand

        i = bisect.bisect_left(refAlus, [left_end - delta])
        if i < len(refAlus) and refAlus[i][0] < right_end + delta:
            note('\t'.join(curLine) + '\t0bp and intersecting reference Alu', 1)
            return False

        # this will allow calls with 0bp that do not intersect ref Alus
        return True

    if int(curLine[11]) < 0:
        # call made with 2 breakpoints & TSLoss: swap for consistent treatment below
        tmp = left_end
        left_end = right_end
        right_end = tmp

    # now left and right support are reversed
    if left_end_support > 0:
        i = bisect.bisect_left(refAlus, [right_end - delta - 300])
        while i < len(refAlus) and refAlus[i][0] < right_end + delta + 300:
            if abs( (refAlus[i][1] - alu_left_end) + [-1, 1][st] * (refAlus[i][0] - right_end) ) < delta:
                note('\t'.join(curLine) + '\tremoving left end support:\t' + '\t'.join(map(str, refAlus[i])), 1)
                left_end_support = 0
                break
            i += 1

    if right_end_support > 0:
        i = bisect.bisect_left(refAlus, [left_end - delta - 300])
        while i < len(refAlus) and refAlus[i][0] < left_end + delta + 300:
            if abs( (refAlus[i][1] - alu_right_end) + [-1, 1][st] * (refAlus[i][0] - left_end) ) < delta:
                note('i=' + str(i) + ' refAlus[i]=' + str(refAlus[i]), 1)
                note('\t'.join(curLine) + '\tremoving right end support\t' + '\t'.join(map(str, refAlus[i])), 1)
                right_end_support = 0
                break
            i += 1

    if left_end_support == 0 and right_end_support == 0:
        note('\t'.join(curLine) + '\tno bp support left', 1)
        return False

    return True


g = gzopen(args.input_file)
for line in g:
    line = line.strip().split('\t')
    chr = line[0]
    st = int(line[5] == '-')
    if chr not in refAlus.keys() or check_not_overlap(refAlus[chr][st], line, st):
        print '\t'.join(line)
gzclose(g)
