-- args structure id
DROP FUNCTION calculate_status(INT);
CREATE OR REPLACE FUNCTION calculate_status(INT) RETURNS TEXT
AS $$
  oid = args[0]

  # loading all events from this object
  load_events = plpy.prepare("SELECT value, time_start, time_anchor, time_end, time_entry FROM data WHERE visible AND objectid = $1 AND datatypeid = 'event' ORDER BY value ASC NULLS LAST", ["int"])
  events = plpy.execute(load_events, [oid])

  if not (events.nrows() > 0):
    return None

  from PartialDate import PartialDate

  status = None
  known_status = None
  time = PartialDate(-100000000)
  status_time = PartialDate(-200000000)
  known_status_time = PartialDate(-200000000)
  nowdate = PartialDate(None)
  for event in events:
    if event['time_entry']:
      entrytime = PartialDate(event['time_entry'])
    else:
      entrytime = nowdate

    if event['time_end']:
      time = PartialDate(int(event['time_end']))
    elif event['time_anchor']:
      time = PartialDate(int(event['time_anchor']))
    elif event['time_start']:
      time = PartialDate(int(event['time_start']))
    elif event['time_entry']:
      time = PartialDate(event['time_entry'])

    if (entrytime >= time and nowdate > time):
      prediction = False
    else:
      prediction = True

    predictiontime = float(time) - float(entrytime)

    if event['value'][0:9] > known_status and event['value'][0:9] > 'event.1' and not prediction:
      known_status = event['value'][0:9]
      known_status_time = time

    if known_status:
      ev_dist = int(event['value'][6]) - int(known_status[6])
    else:
      ev_dist = 0

    if ((time >= status_time) and (time < nowdate) and event['value'][0:9] > 'event.1' and (not prediction or (predictiontime < 40000 and ev_dist < 2 and event['value'][0:9] >= 'event.4' ))):
      status = event['value'][0:9]
      status_time = time

  return status
$$ LANGUAGE plpythonu;
