#!/usr/bin/python3

import argparse
import os
import sys
import shutil

from asemb import Asemb
from erimp import Erimp
from clarf import Clarf
from folda import Folda
from ishus import Ishus
from otria import Otria
from mocla import Mocla
from beric import Beric
from riffer import Riffer
from rixer import Rixer
from notip import Notip
from holis import Holis
from ursis import Ursis
from recon import Recon

import dater
import filer
import rifop
import shotiser

desc = 'unleash as issue'
parser = argparse.ArgumentParser(description=desc)
parser.add_argument('-v', action='store_true', help='raise verbosity')
parser.add_argument('-n', action='store_true', help='no notip')
parser.add_argument('-r', type=str, help='only repcode')
parser.add_argument('-i', type=str, help='only issuedate')
parser.add_argument('-p', action='store_true', help='peep only')
parser.add_argument('-b', action='store_true', help='use brown')
parser.add_argument('-B', action='store_true', help='ignore bremse')
parser.add_argument('-C', action='store_true', help='catch up')
parser.add_argument('-N', action='store_true', help='force notip')
parser.add_argument('-R', action='store_true', help='reissue')
parser.add_argument('-f', type=str, help='issue file')
parser.add_argument('bapis', metavar='bnp', type=str, nargs='*',
                    help='bits and pieces arguments')
args = parser.parse_args()

e = Erimp(args.bapis, do_verbose=args.v)

do_verbose = args.v
issues_fudi = e.dirs['issues']
notip = Notip(e, do_verbose=do_verbose)
otria = Otria(e)
ishus = Ishus(e)
rixer = Rixer(e)
ursis = Ursis(e)
folder = Folda(e)
riffer = Riffer(e, do_verbose=do_verbose)
mocla = Mocla(e, do_verbose=do_verbose)

# # issues take place at night
tonight = dater.tonight()
today = dater.today()

# # if a peep release, no source, no notify
if args.p:
    args.n = True
    repcode = e.given_repcode
    if repcode is None:
        print("I need a repcode with -p")
        sys.exit()
    issuedate = e.issuedates[0]
    out_fufi = mocla.run(repcode, issuedate, do_verbose=True,
                         do_redo=True)
    if repcode not in e.reports:
        print("I don't know about {repcode}")
        sys.exit()
    report = e.report[repcode]
    source_fudi = report.dirs['source']
    source_fufis = e.d.lasts(source_fudi)
    if len(list(source_fufis)) != 0:
        print('I see source files, no peep release')
        print(source_fufis)
    issuedate = e.given_issuedate
    if issuedate is None:
        issuedate = ishus.last_issuedate()
    out_fufi = mocla.run(repcode, issuedate, do_verbose=True)
    ursis.cache_selection_screen(out_fufi)
    sys.exit()

# quit()


# # ignore the bremse if called by Ernad/Final
do_ignore_bremse = args.B
#if 'bremse' not in e.conf:
#    do_ignore_bremse = True

bremsable = False
if 'bremse' in e.conf:
    bremsable = True

do_catch_up = args.C

# # redo if a specific issue and report is called for
do_redo = args.R
if args.i is not None and args.r is not None:
    do_redo = True
# # these should be only one way to give the issuedate
if e.given_issuedate is not None and args.r is not None:
    do_redo = True

issuedate = None
go_brown = args.b
fufi = args.f
if fufi is not None:
    if not os.path.isfile(fufi):
        print(f"I don't see {fufi}")
        sys.exit()
    issuedate = riffer.issuedate(fufi)
    if issuedate not in e.issuedates:
        msg = f"I don't have the issuedate {issuedate}"
        msg += " implicit in {fufi}"
        print(msg, file=sys.stderr)
        sys.exit()
elif args.i is not None:
    issuedate = args.i
    if issuedate not in e.issuedates:
        msg = f"I don't have the issuedate {issuedate}"
        print(msg, file=sys.stderr)
        sys.exit()
    fufi = ishus.fufi(issuedate)
elif e.given_issuedate is not None:
    issuedate = e.given_issuedate
    fufi = ishus.fufi(issuedate)

only_repcode = None
if e.given_repcode is not None:
    only_repcode = e.given_repcode
if args.r is not None:
    only_repcode = args.r
if only_repcode is not None:
    if only_repcode not in e.report:
        print(f"I don't know your report {only_repcode}")
        sys.exit()
    repcode = only_repcode
    report = e.report[repcode]
    # is_active = report.is_active()
    if issuedate is None:
        issuedate = report.next_missing_issuedate()
        if issuedate is None:
            issuedate = ishus.last_issuedate()
            print(f"I use {issuedate} for {repcode}")
        if do_verbose:
            print(f"I have the {repcode} issuedate {issuedate}")
        firsts = folder.firsts(e.dirs['issues'])
        if issuedate in firsts:
            fufi = firsts[issuedate]
        else:
            print(issuedate + '???')
if go_brown:
    if fufi is not None:
        print("I can't have a fufi if I go brown.")
        sys.exit()
    if 'brown_dir' not in e.conf:
        print("I can't go brown without a brown_dir config.",
              file=sys.stderr)
        sys.exit()
    #if tonight in e.issuedates:
    #    print(f"I already have an issuefile for {tonight}")
    #    sys.exit()
    if do_ignore_bremse:
        print("I can't do brown -b and ignore bremse -B",
              file=sys.stderr)
        sys.exit()
    if do_verbose:
        print("I go brown.")
    brown_fudi = e.conf['brown_dir']
    if not os.path.isdir(brown_fudi):
        print("I can't see {brown_fudi}",
              file=sys.stderr)
        sys.exit()
    issuedate = tonight
    # tonight = dater.tonight()
    amf_ext = e.abovo.constants['ext_amf']
    brown_fufi = brown_fudi + '/' + tonight + amf_ext + '.gz'
    if not os.path.isfile(brown_fufi):
        print(f"I can't see {brown_fufi}",
              file=sys.stderr)
        sys.exit()
    if tonight != dater.today():
        print("I can't do a brown release in the evening.",
              file=sys.stderr)
        sys.exit()
    shoti = shotiser.now()
    target_fufi = e.dirs['issues'] + '/' + tonight + '_'
    target_fufi += shoti + amf_ext + '.gz'
    # # This needs a check whether the file is there
    if issuedate not in e.issuedates:
        if do_verbose:
            print(f"I install {brown_fufi} as {target_fufi}")
        shutil.copy(brown_fufi, target_fufi)
        # # insert the issudate to avoid problem of 2024-08-11
        e.issuedates.insert(0, issuedate)
        fufi = target_fufi
    else:
        if do_verbose:
            print(f"I already have an issue for {issuedate}")
        fufi = ishus.fufi(issuedate)
    ## here we use that bims is going brown and nep has no
    ## holis yet. Run the poish of holis. the new issuedate
    ## was added just a few lines above
    holis = Holis(e)
    holis.poish(today)

## check the date is tonight
# if (issuedate is None and args.i is None and args.f is None) \
if (only_repcode is None and issuedate is None and args.f is None) \
   and (not do_ignore_bremse or not bremsable):
    # # neither issudate nor fufi are given, look at last issuedate
    last_issuedate = ishus.last_issuedate()
    if ishus.last_issuedate() != tonight and only_repcode is None:
        ## ishus.last_issuedate() does not see the new issue create
        ## from the brown_fufi. insert above may not work, caution
        ## to avoid problem of 2024-08-11
        print(f"last issuedate {last_issuedate} is not tonight {tonight}.")
        ## test removing this condition on bims
        if not args.b:
            sys.exit()
    ## set for last fufi
    last_fufi = ishus.last_fufi()
    if tonight in last_fufi:
        if do_verbose:
            print(f"I use tonight's {last_fufi}")
        fufi = last_fufi
    else:
        print(f"I do not use {last_fufi}.")
    issuedate = last_issuedate

if args.r is None and fufi is None:
    print("I need a fufi here, not None",
          file=sys.stderr)
    sys.exit()

issue_doc = filer.parse_lax(fufi)
if issue_doc is None:
    print(f"I can't use {fufi}.")
    sys.exit()
docs = rixer.docs(issue_doc)
if len(docs) == 0:
    print(f"No papers in {fufi}.")
    sys.exit()

## no need to take account of holidays, yanabino does
## that for us
## no need to take account of bremse, not working in NEP
##

repcodes = otria.by_timely()

# # active reports
repcodes = otria.by_timely()
if only_repcode is not None and only_repcode not in repcodes:
    print(f"I don't see {only_repcode}")
    sys.exit()

if issuedate is None:
    print("I set the issuedate to today.")
    issuedate = today

## test if the issuedate is ahead of its time
if dater.now_tist() < dater.issuedate_tist(issuedate):
    print(f"I can't issue ahead of {issuedate}")
    sys.exit()

for repcode in repcodes:
    if only_repcode is not None and repcode != only_repcode:
        continue
    report = e.report[repcode]
    if not report.audit_issuedate(issuedate):
        ## this should be added to a list of non-released reports
        if do_verbose:
            previous_issuedate = ishus.shift(issuedate, 1)
            print(f"{repcode} misses {previous_issuedate}")
        continue
    # # should be e.report[repcode]
    # report = Report(e, repcode)
    report = e.report[repcode]
    if not report.is_active() and not do_ignore_bremse:
        if do_verbose:
            print(f"{repcode} is not active")
        if do_catch_up:
            print("I catchup via -C")
        else:
            continue
    source_fudi = report.dirs['source']
    # # this is gziped
    if rifop.count_by_issuedate(source_fudi, issuedate) == 0:
        if do_verbose:
            print(f"I call mocla {repcode} {issuedate}")
        out_fufi = mocla.run(repcode, issuedate, do_verbose=True,
                             do_redo=do_redo)
        if out_fufi is None:
            if not report.is_it_pregnant():
                print(f"I can't mocla {repcode} for {issuedate}")
                continue
            else:
                recon = Recon(e)
                mother_reports = recon.get_mothers(repcode)
                if mother_reports is None:
                    print(f"I can't mocla {repcode} for {issuedate}")
                    continue
                mother_report = list(recon.get_mothers(repcode).keys())[0]
                asemb = Asemb(e)
                out_fufi = asemb.build(repcode=repcode,
                                       issuedate=issuedate,
                                       parent=mother_report)
        ## now verbiaage in ursis.make_source
        txt = filer.sread(out_fufi)
        # # should use
        bana = riffer.bana(issuedate)
        source_fufi = report.dirs['source'] + '/' + bana
        filer.prepare(source_fufi)
        filer.srite(source_fufi, txt, do_change_check=False)
    elif do_redo:
        out_fufi = mocla.run(repcode, issuedate, do_verbose=True,
                             do_redo=do_redo)
        source_fufis = rifop.list_by_issuedate(source_fudi, issuedate)
        source_fufi = source_fufis[0]
    else:
        source_fufis = rifop.list_by_issuedate(source_fudi, issuedate)
        source_fufi = source_fufis[0]
    ursis.cache_selection_screen(source_fufi)
    if not os.path.isfile(source_fufi):
        print("I don't have {source_fufi}", file=sys.stderr)
        continue
    result = notip.new_issue(source_fufi, repcode, dont_send=args.n,
                             date=issuedate, force_send=args.N)
    if result is None:
        print(f"I can't notip {repcode} for {issuedate}",
              file=sys.stderr)
        continue

    # # call clarf for single
    if only_repcode is not None:
        clarf = Clarf(e)
        clarf.single(only_repcode, issuedate)


if 'bremse' not in e.conf:
    print("no work on inactive reports")
    sys.exit()

if args.n:
    sys.exit()

# # if the repcode is given, stop here
if only_repcode is not None:
    sys.exit()

# # inactive reports
print("start release for inactive reports")
for repcode in repcodes:
    if only_repcode is not None and repcode != only_repcode:
        # print("skip for report")
        continue
    if do_ignore_bremse:
        print("skip for bremse")
        continue
    report = Beric(e, repcode)
    if report.is_active() and do_verbose:
        print(f"{repcode} is active")
        continue
    result = notip.bremsed(repcode, issuedate, dont_send=args.N,
                           date=issuedate)
    if result is None:
        print(f"I can't notip {repcode} for {issuedate}")
        continue
