/* /obj/toostels/fehlerteufel.c
   Fehlerteufel - Magiertool zur Abfrage des Fehler-Daemons der Mudlib
   Autor: Zesstra
   Changelog:
*/

#pragma strict_types
//#pragma pedantic
#pragma range_check
#pragma no_shadow
#pragma no_inherit

inherit "/std/secure_thing";
inherit "/secure/errord-structs";

#include <defines.h>
#include <wizlevels.h>
#include <properties.h>
#include <moving.h>
#include <errord.h>
#include <config.h>
#include <debug_info.h>
#include <input_to.h>
#include <strings.h>

#define TI this_interactive()

#define DEBUG(x)  if (funcall(symbol_function('find_player),"zesstra"))\
        tell_object(funcall(symbol_function('find_player),"zesstra"),\
        "EDBG: "+x+"\n")

// variables
private string owner;  // UID vom Eigentuemer
private string *uids=({}); // UIDs, auf die man schreibrechte hat
private string *filteruids=({}); // wenn nicht-leer, nur diese UIDs zeigen
private string *monitoruids=({}); // diese UIDs in die Liste einschliessen
private int filterstatus=0;       // Filter an oder aus?
private mapping issuelist = ([]);
/* ([ type1: ([uid1: <issuelist>, uid2: <issuelist> ]),
      type2: ... ])
   <issuelist> ist ein < <int|string>* >* vom ErrorD */

//Welche Art von Fehler anzeigen?
private int modus=T_RTERROR | T_RTWARN | T_REPORTED_ERR;
private string *xmonitoruids = ({}); // expanded Monitor-UIDs
private int lfehler;              // letzter 'benutzter' Fehler.
private int fehlerzahl;       // fehlerzahl im letzten Reset.
private mapping feingabe;         // gerade eingegebener Fehler

// ************** private functions  **************
private varargs int update_issuelist(int lmodus);
private void get_uids();
private struct fullissue_s get_issue(string arg);
private struct fullissue_s|struct fullissue_s* get_issues(string arg, int parsed = 0);

// irgendeinen Fehler oder Warnung anzeigen.
private int show_entry(struct fullissue_s issue)
{
  if (!issue) return 0;

  string txt=({string})ERRORD->format_error(issue, 0);

  if (!stringp(txt) || !sizeof(txt))
      return 0;

  tell_object(PL,txt+"\n");
  return 1;
}

protected int _feingabe_fertig(string arg) {

  if (arg == "j")
  {
    if (!feingabe[F_MSG])
    {
      tell_object(PL,
        "Also, eine Fehlerbeschreibung solltest Du schon eingeben! Abgebrochen.\n");
    }
    else
    {
      string hashkey = ({string})ERRORD->LogReportedError(feingabe);
      tell_object(PL, sprintf(
         "Vielen Dank! Die ID des eingegebenen Fehlers lautet: %s\n",
         hashkey || "N/A"));
    }
  }
  else
  {
    tell_object(PL, "Fehlereingabe abgebrochen.\n");
  }

  feingabe = 0;

  return 1;
}

public int CmdFehlerEingabe(string arg) {
  object|string target;

  if (feingabe)
  {
    tell_object(PL, "Du gibst doch bereits einen Fehler ein!\n");
    return 1;
  }
  feingabe = ([]);

  if (arg)
  {
    target = present(arg);
    if (!target)
      target = find_object(arg); // vielleicht direkt angegeben?
    // Vielleicht gibt es ja eine Datei, die so heisst?
    if (!target && file_size(arg) >= 0)
      target = arg;
  }
  // wenn nix gefunden, Environment des Magiers nehmen.
  if (!target)
  {
    tell_object(PL, break_string("Kein Objekt und keine Datei "
      "angegeben, Fehler wird fuer den Raum eingetragen.",78));
    target = environment(environment());
  }

  feingabe[F_OBJ] = target;

  tell_object(PL, break_string(sprintf(
          "Du beginnst einen Fehlereintrag fuer das Objekt: %O\n", target),78));

  input_to(function void (string str)
      {
        if (sizeof(str)) feingabe[F_MSG] = str;
      }, INPUT_PROMPT, "Fehlerbeschreibung eingeben:\n");

  input_to(function void (string str)
      {
        if (sizeof(str)) feingabe[F_PROG] = str;
        else feingabe[F_PROG] = "unbekannt";
      }, INPUT_PROMPT|INPUT_APPEND, 
     "Programm eingeben, in dem der Fehler auftritt (falls bekannt):\n");

  input_to(function void (string str)
      {
        if (sizeof(str)) feingabe[F_LINE] = to_int(str);
        tell_object(PL,break_string(sprintf(
          "Du hast die folgenden Daten eingegeben:\n"
          "Objekt: %O\n"
          "Fehlerbeschreibung: %s\n"
          "Programm: %s\n"
          "Zeilennr.: %d\n",
          feingabe[F_OBJ], feingabe[F_MSG] || "", feingabe[F_PROG],
          feingabe[F_LINE]), 78, "", BS_LEAVE_MY_LFS));
      }, INPUT_PROMPT|INPUT_APPEND,
      "Zeilennr. eingeben, in der der Fehler auftritt (falls bekannt):\n");

  input_to(#'_feingabe_fertig,
      INPUT_PROMPT|INPUT_APPEND, "Eingaben korrekt? (j/n)\n");

  return 1;
}

public int CmdFehlerZeigen(string arg)
{
  struct fullissue_s|struct fullissue_s* issues=get_issues(arg);
  notify_fail("Einen Eintrag mit dieser ID gibt es nicht!\n");

  if (structp(issues))
  {
    show_entry(issues);
    // letzten Fehler merken.
    lfehler = issues->id;
    return 1;
  }
  else if (pointerp(issues))
  {
    foreach(struct fullissue_s issue : issues)
    {
      show_entry(issue);
    }
    return 1;
  }

  notify_fail("Keine Eintraege fuer diesen Dateinamen/diese ID gefunden.\n");
  return 0;
}

public int CmdFehlerLoeschen(string arg)
{
  int issueid;
  string note;
  struct fullissue_s|struct fullissue_s* issues;
  arg = ({string})this_player()->_unparsed_args(0);

  if (stringp(arg) && sizeof(arg))
  {
    // Fuehrende Leerzeichen entfernen, um ID und Notiz zuverlaessig trennen zu
    // koennen.
    arg = trim(arg, TRIM_LEFT);
    // Alles ab dem zweiten Wort sollte eine Notiz sein.
    int spacepos = strstr(arg, " ");
    if(spacepos != -1)
    {
      note = arg[spacepos + 1 ..];
      arg = arg[.. spacepos - 1];
    }
    issues = get_issues(arg, 1);
    if(structp(issues))
    {
      issueid = issues->id;
    }
  }
  else
    issueid = lfehler;

  notify_fail("Einen Eintrag mit dieser ID/diesem Loadname gibt es nicht!\n");

  if(issueid > 0)
  {
    int res = ({int})ERRORD->ToggleDeleteError(issueid, note);
    if (res == 1)
    {
      tell_object(PL,
        "Fehler/Warnung wurde zum Loeschen markiert und wird in Kuerze "
        "geloescht.\n");
      lfehler = issueid;
      return 1;
    }
    else if (res==0)
    {
      tell_object(PL,"Loeschmarkierung wurde entfernt.\n");
      lfehler = issueid;
      return 1;
    }
    else if (res < -1)
    {
      tell_object(PL, "Irgendwas ist beim Loeschen schiefgegangen. "
                      "Keine Schreibrechte?\n");
      lfehler = issueid;
      return 1;
    }
  }
  else if(pointerp(issues))
  {
    int sum_deleted = 0;
    string res = "";
    foreach(struct fullissue_s issue : issues)
    {
      issueid = issue->id;
      if(({int})ERRORD->ToggleDeleteError(issueid, note) == 1)
      {
        res += issueid + " als geloescht markiert.\n";
        ++sum_deleted;
      }
    }
    PL->ReceiveMsg(res, MT_NOTIFICATION | MSG_DONT_WRAP);
    return sum_deleted;
  }
  // Offenbar kein Fehler gefunden
  return 0;
}

public int CmdRefresh(string arg) {
    reset();
    tell_object(PL,"Fehlerdaten wurden neu eingelesen.\n");
    return 1;
}

#define NO_FALLBACK 1
#define NO_COMBINED_TYPES 2
private int select_modus(string arg, int flags = 0) {
    int lmodus;
    switch(arg) {
    case "alles":
    case "alle":
      if(flags & NO_COMBINED_TYPES)
      {
        lmodus = 0;
      }
      else
      {
        lmodus = T_RTERROR | T_RTWARN | T_CTERROR | T_CTWARN | T_REPORTED_ERR
                 | T_REPORTED_IDEA | T_REPORTED_TYPO | T_REPORTED_MD | 
                 T_REPORTED_SYNTAX;
      }
      break;
    case "fehler":
    case "error":
    case "errors":
      if(flags & NO_COMBINED_TYPES)
      {
        lmodus = 0;
      }
      else
      {
        lmodus=T_RTERROR | T_CTERROR | T_REPORTED_ERR;
      }
      break;
    case "warnungen":
    case "warnung":
    case "warning":
    case "warnings":
      if(flags & NO_COMBINED_TYPES)
      {
        lmodus = 0;
      }
      else
      {
        lmodus=T_RTWARN | T_CTWARN;
      }
      break;
    case "laufzeitfehler":
      lmodus=T_RTERROR;
      break;
    case "ladezeitfehler":
      lmodus=T_CTERROR;
      break;
    case "fehlerhinweis":
    case "fehlerhinweise":
    case "hinweise":
      lmodus=T_REPORTED_ERR;
      break;
    case "ideen":
    case "idee":
      lmodus=T_REPORTED_IDEA;
      break;
    case "md":
      lmodus=T_REPORTED_MD;
      break;
    case "typo":
    case "typos":
      lmodus=T_REPORTED_TYPO;
      break;
    case "syntax":
    case "syntaxhinweis":
    case "syntaxhinweise":
      lmodus=T_REPORTED_SYNTAX;
      break;
    case "laufzeitwarnungen":
    case "runtimewarnings":
      lmodus=T_RTWARN;
      break;
    case "ladezeitwarnungen":
    case "compiletimewarnings":
      lmodus=T_CTWARN;
      break;
    default:
      if(flags & NO_FALLBACK)
      {
        lmodus = 0;
      }
      else
      {
        lmodus=modus;
      }
    }
    return lmodus;
}

private string  * errorlabel(int t)
{
  switch(t) {
    case T_RTERROR:
      return ({"Laufzeitfehler","Laufzeitfehler","Dieser Laufzeitfehler"});
    case T_REPORTED_ERR:
      return ({"Fehlerhinweis","Fehlerhinweise","Dieser Fehlerhinweis"});
    case T_REPORTED_IDEA:
      return ({"Idee","Ideen","Diese Idee"});
    case T_REPORTED_MD:
      return ({"fehlende Detail","fehlende Details","Dieses fehlende Detail"});
    case T_REPORTED_TYPO:
      return ({"Typo","Typos","Dieser Typo"});
    case T_REPORTED_SYNTAX:
      return ({"Syntaxhinweis","Syntaxhinweise","Dieser Syntaxhinweis"});
    case T_RTWARN:
      return ({"Laufzeitwarnung","Laufzeitwarnungen","Diese Laufzeitwarnung"});
    case T_CTWARN:
      return ({"Ladezeitwarnung", "Ladezeitwarnungen","Diese Ladezeitwarnung"});
    case T_CTERROR:
      return ({"Ladezeitfehler","Ladezeitfehler","Dieser Ladezeitfehler"});
  }
  raise_error("Unkannter Fehlertyp: "+t+"\n");
}

public int CmdFehlerListe(string arg) {
  string txt;
  //string *luids;
  int lmodus; // modus fuer diese Liste
  mapping fehlerbackup;

  if (stringp(arg) && sizeof(arg))
  {
    lmodus=select_modus(arg);
    if (lmodus != modus)
    {
      fehlerbackup=issuelist; // Fehlerliste von 'modus' aufheben
      update_issuelist(lmodus);  // neue Fehlerliste holen
    }
  }
  else
    lmodus=modus;
/*
  if (!fehlerzahl)
  {
    txt="Fuer Deine UIDs sind keine Fehler/Warnungen bekannt. :-)\n";
    tell_object(PL,txt);
    return 1;
  }
*/
  foreach(int typ, mapping typemap : issuelist)
  {
    if (!(typ & lmodus))
      continue; // Type nicht gewaehlt.
    txt="";
    if (!sizeof(typemap)) {
      tell_object(PL,
        "Es sind keine " + errorlabel(typ)[1] + "Deiner UIDs bekannt. :-)");
      continue;
    }
    foreach(string uid, < <int|string>* >* list : typemap)
    {
      if (!sizeof(list)) continue;
      if (filterstatus && member(filteruids, uid) > -1) continue;
      //txt+=sprintf("%s:\n", uid);
      foreach(<int|string>* row : list)
      {
        txt+=sprintf("%:6d | %:40-s | %:26-s\n",
              row[0], row[1], row[2]);
      }
    }
    if (txt && sizeof(txt))
    {
      txt = sprintf("\nFuer Deine UIDs sind folgende %s bekannt (Filter: %s):\n"
                    "%:6|s | %:40|s |   %s\n",
                 errorlabel(typ)[1], (filterstatus ? "an" : "aus"),
                 "ID", "Loadname", "UID")
          + txt;
      tell_object(PL, txt);
    }
    else
    {
      tell_object(PL, sprintf(
            "\nFuer Deine UIDs sind keine %s bekannt (Filter: %s):\n",
            errorlabel(typ)[1], (filterstatus ? "an" : "aus")));
    }
  }

  if (mappingp(fehlerbackup) && modus!=lmodus)
    issuelist=fehlerbackup; // fehlerliste fuer 'modus' restaurieren
  return 1;
}

public int CmdFilter(string arg) {

  arg=({string})PL->_unparsed_args(0);  

  if (!stringp(arg) || !sizeof(arg)) {
    tell_object(PL,break_string(
          "Momentan interessieren Dich folgende UIDs nicht"
          +(filterstatus ? " (Filter an):\n" : " (Filter aus):\n")
          +CountUp(filteruids)+"\n", 78,"",BS_LEAVE_MY_LFS));
    return 1;
  }

  if (arg=="keine") {
    filteruids=({});
    filterstatus=1;
    tell_object(PL,break_string(
        "Dein Fehlerteufel wird Dir nun nur noch ausgewaehlte "
        "Fehler berichten. Momentan hast Du keine UIDs ausgeblendet. "
        "(Filter an)",78));
  }
  else if (arg=="alle") {
    filterstatus=1;
    filteruids=uids;
    tell_object(PL,break_string(
        "Dein Fehlerteufel wird Dir nun nur noch ausgewaehlte "
        "Fehler berichten. Du blendest momentan alle UIDs aus. "
        "(Filter an)",78));
  }
  else if (arg=="aus") {
    filterstatus=0;
    tell_object(PL,break_string(
        "Dein Fehlerteufel wird Dir nun wieder alle Fehler berichten. ",
        78));
  }
  else if (arg=="an" || arg=="ein") {
    filterstatus=1;
    tell_object(PL,break_string(
        "Dein Fehlerteufel wird Dir nun nur noch ausgewaehlte "
        "Fehler berichten.",78));
  }
  else {
    foreach(string uid: explode(arg," ")-({""})) {
      if (sizeof(uid)>1 && uid[0]=='+') {
        if (member(filteruids,uid[1..])==-1)
          filteruids+=({uid[1..]});
      }
      else if (sizeof(uid)>1 && uid[0]=='-') {
          filteruids-=({uid[1..]});
      }
      else {
        if (member(filteruids,uid)==-1)
          filteruids+=({uid});
        else
          filteruids-=({uid});
      }
    }
  }

  tell_object(PL,break_string(
          "Momentan interessieren Dich folgende UIDs nicht"
          +(filterstatus ? " (Filter an):\n" : " (Filter aus):\n")
          +CountUp(filteruids)+"\n", 78,"",BS_LEAVE_MY_LFS));

  return 1;
}

public int CmdMonitor(string arg) {

  arg=({string})PL->_unparsed_args(0);  

  if (!stringp(arg) || !sizeof(arg)) {
    tell_object(PL,break_string(
          "Momentan interessieren Dich folgende UIDs zusaetzlich zu Deinen: \n"
          +(sizeof(monitoruids) ? CountUp(monitoruids) : "")
          +"\n", 78,"",BS_LEAVE_MY_LFS));
    return 1;
  }

  if (arg=="keine") {
    monitoruids=({});
    xmonitoruids=({});
    tell_object(PL,break_string(
        "Dein Fehlerteufel wird Dir nun nur noch "
        "Fehler Deiner eigenen UIDs berichten.",78));
    return 1;
  }
  else {
    foreach(string uid: explode(arg," ")-({""})) {
      if (sizeof(uid)>1 && uid[0]=='+') {
        if (member(monitoruids,uid[1..])==-1)
          monitoruids+=({uid[1..]});
      }
      else if (sizeof(uid)>1 && uid[0]=='-') {
          monitoruids-=({uid[1..]});
      }
      else {
        if (member(monitoruids,uid)==-1)
          monitoruids+=({uid});
        else
          monitoruids-=({uid});
      }
    }
  }
  get_uids();
  tell_object(PL,break_string(
        "Momentan interessieren Dich folgende UIDs zusaetzlich zu Deinen: \n"
        +(sizeof(monitoruids) ? CountUp(monitoruids) : "")
        +"\n", 78,"",BS_LEAVE_MY_LFS));

  return 1;
}

public int CmdModus(string arg) {
  // Argument verwursten
  if (stringp(arg) && sizeof(arg)) {
    modus = select_modus(arg);
    reset();  // neue Fehlerliste holen
  }
  // aktuelle Einstellung ausgeben.
  string *modstr=({});
  if (modus & T_RTERROR)
      modstr+=({"Fehler (Laufzeit)"});
  if (modus & T_RTWARN)
      modstr+=({"Warnungen (Laufzeit)"});
  if (modus & T_CTERROR)
      modstr+=({"Fehler (Ladezeit)"});
  if (modus & T_CTWARN)
      modstr+=({"Warnungen (Ladezeit)"});
  if (modus & T_REPORTED_ERR)
      modstr+=({"Fehlerhinweise"});
  if (modus & T_REPORTED_IDEA)
      modstr+=({"Idee"});
  if (modus & T_REPORTED_MD)
      modstr+=({"fehlende Details"});
  if (modus & T_REPORTED_TYPO)
      modstr+=({"Typo"});
  if(modus&T_REPORTED_SYNTAX)
    modstr+=({"Syntaxhinweise"});

  tell_object(PL, break_string(
      "Dein Fehlerteufel wird Dir nun ueber aufgetretene "
      +CountUp(modstr)+" Bericht erstatten.",78));
  return(1);
}

int CmdAddNote(string str) {
  string *arr;

  notify_fail("Bitte eine ID und einen Text angeben!\n");
  if(!objectp(TI))
    return 0;

  str=({string})PL->_unparsed_args(0);
  if (!stringp(str) || !sizeof(str))
    return 0;

  arr=explode(str," ")-({""});
  if (sizeof(arr)<2)
    return 0;
  int issueid = to_int(arr[0]);

  str=implode(arr[1..]," ");  //text wiederherstellen, aber ohne ID

  switch(({int})ERRORD->AddNote(issueid,str))
  {
    case -1:
      tell_object(PL,
          sprintf("Es gibt keinen Fehler mit der ID: %d\n",issueid));
      return 1;
    case -3:
      return 0; //offenbar keine Notiz angegeben.
  }
  // letzten Fehler merken.
  lfehler = issueid;

  tell_object(PL,
      sprintf("Deine Notiz wurde zu %d hinzugefuegt.\n",
        issueid));
  return 1;
}

int CmdFix(string str)
{
  string *arr;
  int fixing, res;

  notify_fail("Bitte eine ID und optional eine Notiz angeben!\n");
  if(!objectp(TI))
    return 0;

  str=({string})PL->_unparsed_args(0);
  if (!stringp(str) || !sizeof(str))
    return 0;

  arr=explode(str," ")-({""});
  if (!sizeof(arr))
    return 0;

  int issueid=to_int(arr[0]);
  if (sizeof(arr)>1)
    str=implode(arr[1..]," ");  //text wiederherstellen, aber ohne Key
  else str=0;

  if (query_verb()=="ffix" || query_verb()=="fehlerfix")
  {
      fixing=1;
      res = ({int})ERRORD->ResolveIssue(issueid, str);
  }
  else
  {
      res = ({int})ERRORD->ReOpenIssue(issueid, str);
  }

  if (res==-1)
  {
      tell_object(PL,
          sprintf("Es gibt keinen Fehler mit der ID: %d\n",issueid));
  }
  else if (res==-10)
  {
      tell_object(PL,
        "Du hast leider keinen Schreibzugriff diesen Fehler.\n"
        "Aber vielleicht moechtest Du mit fnotiz eine Notiz anhaengen?\n");
  }
  else if (res==-3)
  {
    if (fixing)
      tell_object(PL,"Dieser Fehler ist bereits gefixt.\n");
    else
      tell_object(PL,"Dieser Fehler ist noch nicht gefixt.\n");
  }
  else if (res==1)
  {
      tell_object(PL,
          sprintf("Fehler %d als gefixt markiert.\n",issueid));
  }
  else if (res==0)
  {
      tell_object(PL,
          sprintf("Fehler %d als nicht gefixt markiert.\n",issueid));
  }
  // letzten Fehler merken.
  lfehler = issueid;

  return 1;
}

int CmdLock(string str) {
  string *arr;
  int locking;
  int res;

  notify_fail("Bitte eine ID und optional eine Notiz angeben!\n");
  if(!objectp(TI))
    return 0;

  str=({string})PL->_unparsed_args(0);
  if (!stringp(str) || !sizeof(str))
    return 0;

  arr=explode(str," ")-({""});
  if (!sizeof(arr))
    return 0;

  int issueid=to_int(arr[0]);
  if (sizeof(arr)>1)
    str=implode(arr[1..]," ");  //text wiederherstellen, aber ohne Key
  else str=0;

  if (query_verb()=="flock" || query_verb()=="fehlerlock")
  {
      locking=1;
      res=({int})ERRORD->LockIssue(issueid,str);
  }
  else
  {
      res=({int})ERRORD->UnlockIssue(issueid,str);
  }

  if (res==-1)
  {
      tell_object(PL,
          sprintf("Es gibt keinen Fehler mit der ID: %d\n",issueid));
  }
  else if (res==-10)
  {
       tell_object(PL,
           "Du hast leider keinen Schreibzugriff diesen Fehler.\n");
  }
  else if (res==-3)
  {
      if (locking)
          tell_object(PL,
              "Dieser Fehler ist bereits vor autom. Loeschen geschuetzt.\n");
      else
          tell_object(PL,
              "Dieser Fehler ist bereits zum autom. Loeschen freigegeben.\n");
  }
  else if (res==-2)
  {
       tell_object(PL,
           "Dieser Fehler ist bereits gefixt und wird bald geloescht.\n");
  }
  else if (res==1)
  {
    tell_object(PL,
        sprintf("Fehler %d vor autom. Loeschen geschuetzt.\n",issueid));
  }
  else if (res==0)
  {
    tell_object(PL,
        sprintf("Fehler %d zum autom. Loeschen freigegeben.\n",issueid));
  }
  // letzten Fehler merken.
  lfehler = issueid;

  return 1;
}

int CmdReassign(string str) {

  notify_fail("Bitte eine ID, die neue UID und ggf. eine Notiz angeben!\n");
  if(!objectp(TI))
    return 0;

  str=({string})PL->_unparsed_args(0);
  if (!stringp(str) || !sizeof(str))
    return 0;

  string *arr=explode(str," ")-({""});
  if (sizeof(arr)<2)
    return 0;
  int issueid=to_int(arr[0]);
  string newuid=arr[1];

  //text wiederherstellen, aber ohne Key und UID
  if (sizeof(arr) > 2)
    str = implode(arr[2..]," ");
  else
    str = 0;

  switch(({int})ERRORD->ReassignIssue(issueid, newuid, str))
  {
    case -1:
      tell_object(PL,
          sprintf("Es gibt keinen Fehler mit der ID: %d\n",issueid));
      return(1);
    case -10:
      tell_object(PL,
          sprintf("Du hast keine Schreibrechte auf Fehler %d\n",issueid));
      return 1;
    case -2:
      return(0); //offenbar keine neue uid angegeben. (kann nicht)
    case -3:
      tell_object(PL,break_string(
          "Alte == Neue UID ist irgendwie unsinnig...",78));
      return 1;
  }
  // letzten Fehler merken.
  lfehler = issueid;

  tell_object(PL,break_string(
      sprintf("Der Fehler der ID %d wurde an die UID %s "
        "uebertragen.\n", issueid, newuid),78));
  return 1;
}

int CmdFehlerDirectory(string arg)
{
  struct fullissue_s issue=get_issue(arg);
  if(!structp(issue))
  {
    PL->ReceiveMsg(
      "Kein Eintrag mit dieser ID gefunden.",
      MT_NOTIFICATION);
  }
  else
  {
    string path=issue->loadname||issue->obj;
    if(!stringp(path) || !sizeof(path))
    {
      PL->ReceiveMsg(
        "Kein Pfad zu dieser ID verfuegbar.",
        MT_NOTIFICATION);
    }
    else
    {
      path=implode(explode(path,"/")[..<2],"/");
      PL->SetProp(P_LASTDIR, PL->QueryProp(P_CURRENTDIR));
      PL->SetProp(P_CURRENTDIR,path);
      PL->ReceiveMsg(
        "Aktuelles Verzeichnis ist jetzt: "+path,
        MT_NOTIFICATION);
    }
  }
  return 1;
  }

public int CmdFehlerAendere(string arg)
{
  string note;
  arg = ({string})PL->_unparsed_args(0);
  
  notify_fail("Bitte ID, Typ und optional einen Kommentar angeben.\n");

  if(!sizeof(arg)) return 0;
  // Fuehrende Leerzeichen entfernen, um ID, Typ und Notiz zuverlaessig
  // trennen zu koennen.
  arg = trim(arg, TRIM_LEFT);
  string* words = explode(arg, " ");
  if(sizeof(words) < 2) return 0;
  arg = words[0];
  // Alles ab dem dritten Wort sollte eine Notiz sein.
  if(sizeof(words) > 2)
  {
    note = implode(words[2..], " ");
  }

  struct fullissue_s issue = get_issue(arg);

  if(!structp(issue))
  {
    notify_fail("Kein Fehler mit dieser ID gefunden.\n");
    return 0;
  }

  int type = select_modus(words[1], NO_FALLBACK | NO_COMBINED_TYPES);
  if(!type)
  {
    notify_fail("Fehlertyp nicht bekannt.\n");
    return 0;
  }

  if(!(type in CHANGEABLE_TYPES) || !(issue->type in CHANGEABLE_TYPES))
  {
    ({int})PL->ReceiveMsg(
      "Fehlertyp nicht aenderbar.\n",
      MT_NOTIFICATION);
    return 1;
  }

  if(({int})ERRORD->ChangeType(issue->id, type, issue->type, note) == 1)
  {
    string* type_name = ({string*})ERRORD->print_type(type);
    ({int})PL->ReceiveMsg(
      "Fehlertyp von " + issue->id + " auf " + type_name[0] + " geaendert.",
      MT_NOTIFICATION);
  }
  else
  {
    ({int})PL->ReceiveMsg(
      "Aendern nicht moeglich. Keine Schreibrechte?",
      MT_NOTIFICATION);
  }
  return 1;
}

// ************** public 'internal' functions **************
public string QueryOwner() {return owner;}
public mixed QueryIssueList() {return issuelist;}

protected void create() {
    if (!clonep(ME))
        return;
    ::create(); 

    SetProp(P_SHORT,"Der Fehlerteufel");
    SetProp(P_LONG,break_string(
          "Dein Fehlerteufel soll Dir helfen, Informationen "
          "ueber aufgetretene Fehler zu erhalten. Hierzu fragt er die "
          "in \"Deinen\" UIDs aufgetretenen Fehler und deren Details vom "
          "Fehlerspeicher der Mudlib ab. Folgende Kommandos kennt er:",78)
    +"fehlerabfrage <id>  - Fragt Details ueber Fehler mit der ID ab.\n"
    "fehlerloeschen <id> - Fehler zum Loeschen markieren.\n"
    "fehlerliste         - Fehlerliste der eigenen UIDs anzeigen\n"
    "fehlerrefresh       - Fehlerdaten und UIDs neu einlesen\n"
    "fehlerfilter        - UIDs fuer den Filter angeben (s. manpage!)\n"
    "fehlermodus         - Fehler oder Warnungen ausgeben? (s. manpage)\n"
    "fehlermonitor       - zus. UIDs beobachten (s. manpage)\n"
    "fnotiz <id> <note>  - eine Notiz anhaengen\n"
    "flock <id>  <note>  - Fehler vor autom. Loeschen schuetzen\n"
    "funlock <id> <note> - Fehler zum autom. Loeschen freigeben\n"
    "ffix <id> <note>    - Fehler als gefixt kennzeichnen\n"
    "funfix <id> <note>  - gefixten Fehler als nicht-gefixt markieren\n"
    "fdir <id>           - in das Verzeichnis des fehlerhaften Objekts "
    "wechseln\n"
    "fuebertrage <id> <newuid> <note>\n"
    "                    - Fehler an die UID uebertragen\n"
    "faendere <id> <newtype> <note>\n"
    "                    - Fehlertyp aendern\n"
    );
    SetProp(P_NAME,"Fehlerteufel");
    SetProp(P_GENDER,MALE);
    SetProp(P_WEIGHT,0);
    SetProp(P_VALUE,0);
    SetProp(P_SIZE,10);
    SetProp(P_NODROP,"Den Fehlerteufel behaelst Du lieber bei Dir.\n");
    SetProp(P_NEVERDROP,1);

    AddId( ({"fehlerteufel","teufel"}) );

    AddCmd(({"fehlerabfrage","fabfrage"}), "CmdFehlerZeigen" );
    AddCmd(({"fehlerloeschen","floeschen"}), "CmdFehlerLoeschen");
    AddCmd(({"fehlerliste","fliste", "fehleruebersicht","fuebersicht"}), 
        "CmdFehlerListe");
    AddCmd(({"fehlerrefresh","frefresh"}),"CmdRefresh");
    AddCmd(({"fehlerfilter","ffilter"}),"CmdFilter");
    AddCmd(({"fehlermodus","fmodus"}),"CmdModus");
    AddCmd(({"fehlermonitor","fmonitor"}),"CmdMonitor");
    AddCmd(({"fehlernotiz","fnotiz"}),"CmdAddNote");
    AddCmd(({"fehlerlock","flock","fehlerunlock","funlock"}),
        "CmdLock");
    AddCmd(({"fehlerfix","ffix","fehlerunfix","funfix"}),
        "CmdFix");
    AddCmd(({"fehleruebertrage","fuebertrage"}),"CmdReassign");
    AddCmd(({"fehlereingabe", "feingabe"}), "CmdFehlerEingabe");
    AddCmd(({"fehlerdir","fdir"}),"CmdFehlerDirectory");
    AddCmd(({"fehleraendere", "faendere"}), "CmdFehlerAendere");
}

public varargs void init(object origin)
{
    if (find_call_out("remove") != -1) return;

    // pruefung auf env nicht noetig, move geht nur in ein env und ohne env
    // auch kein init().
    if ( !query_once_interactive(environment()) || 
        !IS_LEARNER(environment())) {
        // in interactive, aber kein magier -> direkt weg.
        call_out("remove",0,1);
        return;
    }
    else if (!sizeof(owner))
        // Env ist Interactiv und Magier (sonst waer man oben rausgeflogen)
        owner=getuid(environment());
    else if (owner!=getuid(environment())) {
       //ok, nicht der Eigentuemer, direkt weg.
       call_out("remove",0);
       return;
   }
   SetProp(P_EXTRA_LOOK,break_string(
         "Auf "+({string})environment()->Name(WESSEN)
         +" Schulter sitzt ein kleiner "
         "Fehlerteufel, der "
         +({string})environment()->QueryPronoun(WEM)
         +" immer wieder etwas ins Ohr fluestert.",78));

   call_out("reset",1);

   ::init();
}

public mixed Configure(mixed data)
{
  if (!data)
  {
    return (["filteruids":filteruids,
             "filterstatus":filterstatus,
             "modus":modus,
             "monitoruids":monitoruids,
             "fehlerzahl": fehlerzahl]);
  }
  else if (mappingp(data))
  {
    if (member(data,"filteruids") && pointerp(data["filteruids"]))
      filteruids=data["filteruids"];
    if (member(data,"filterstatus") && intp(data["filterstatus"]))
      filterstatus=data["filterstatus"];
    if (member(data,"modus") && intp(data["modus"]))
      modus=data["modus"];
    if (member(data,"monitoruids") && pointerp(data["monitoruids"]))
      monitoruids=data["monitoruids"];
    if (member(data,"fehlerzahl") && intp(data["fehlerzahl"]))
      fehlerzahl=data["fehlerzahl"];
    return 1;
  }
  return 0;
}

mapping _query_autoloadobj()
{
  return Configure(0);
}

mapping _set_autoloadobj(mixed data)
{
  Configure(data);
  return _query_autoloadobj();
}


void reset()
{
    get_uids();
    int neuefehlerzahl=update_issuelist();

    if (fehlerzahl < neuefehlerzahl)
      tell_object(environment(ME), break_string(
        "Deine Fehlerliste ist soeben laenger geworden.",78,
        "Dein Fehlerteufel teilt Dir mit: "));
    else if (fehlerzahl > neuefehlerzahl)
      tell_object(environment(ME), break_string(
        "Deine Fehlerliste ist soeben kuerzer geworden.",78,
        "Dein Fehlerteufel teilt Dir mit: "));
    fehlerzahl = neuefehlerzahl;
}

// ******** private functions *********************
private void get_uids()
{
    uids=({string *})master()->QueryUIDsForWizard(owner);
    xmonitoruids=({});
    if (sizeof(monitoruids))
    {
      closure cl=symbol_function("QueryUIDAlias", master());
      foreach(string uid: monitoruids) {
        xmonitoruids += ({string*})funcall(cl, uid);
      }
    }
}

/* Holt sich aus dem ErrorD die Liste ungeloeschter und ungefixter Fehler fuer
 * fuer die UIDs des Magier fuer alle Typen
 */
private varargs int update_issuelist(int lmodus)
{
    int count;

    if (!lmodus)
      lmodus=modus;

    issuelist=m_allocate(sizeof(ALL_ERR_TYPES),1);

    foreach(int type: ALL_ERR_TYPES)
    {
      if (type & lmodus)
      {
          //DEBUG(sprintf("Type: %d\n",type));
          foreach(string uid : uids + xmonitoruids)
          {
            //DEBUG(sprintf("Type: %d, UID: %s\n",type,uid));
            < <int|string>* >* list =
                  ({< <int|string>* >*})ERRORD->QueryIssueList(type,uid);
            count += sizeof(list);

            if (!member(issuelist, type))
              issuelist += ([ type: ([ uid: list ]) ]);
            else if (!member(issuelist[type], uid))
              issuelist[type] += ([uid: list ]);
        }
      }
    }

    return count;
}

private struct fullissue_s get_issue(string arg)
{
  int issueid;
  struct fullissue_s issue;

  if (stringp(arg) && sizeof(arg))
  {
    arg = trim(arg, TRIM_BOTH);
    issueid = to_int(arg);
  }
  else
  {
    issueid = lfehler;
    arg = to_string(issueid);
  }

  // Wurde ein Hash uebergeben, ist issueid 0 und arg der Hash.
  // Wurde eine ID oder nichts uebergeben, ist issueid die ID als int und 
  // arg die ID als string.
  if (to_string(issueid) == arg)
    issue = ({struct fullissue_s})ERRORD->QueryIssueByID(issueid);
  else
    issue = ({struct fullissue_s})ERRORD->QueryIssueByHash(arg);
  return issue;
}

private struct fullissue_s|struct fullissue_s* get_issues(string arg, int parsed)
{
  // Manche Funktionen kuemmern sich selbst um _unparsed_args((), da z.B.
  // noch eine Notiz abgeschnitten werden muss.
  if(!parsed)
    arg=({string})PL->_unparsed_args();
  struct fullissue_s|struct fullissue_s* issues;

  // Erstmal schauen, ob arg eine ID ist.
  issues=get_issue(arg);
  // Wenn nicht, dann ist es wohl ein Pfad.
  if(!structp(issues))
  {
    // Mit einem / am Anfang ist der Pfad vermutlich komplett, ansonsten
    // wird im aktuellen Verzeichnis gesucht.
    if(sizeof(arg) && arg[0] != '/')
    {
      arg=({string})PL->QueryProp(P_CURRENTDIR)+"/"+arg;
    }
    issues=({});
    foreach(int m: ALL_ERR_TYPES)
    {
      if (!(m & modus))
        continue;
      struct fullissue_s *tmp = 
                       ({struct fullissue_s *})ERRORD->QueryIssuesByFile(arg, m);
      if (tmp)
        issues+=tmp;
    }
    if (!sizeof(issues))
      issues=0;
  }

  return issues;
}
