/*
  interface
  ao_interface.d
*/
mixin template Interfaces() {
  interface AssertOCN {
    int ocn_emitter(int ocn_status_flag)
      in { assert(ocn_status_flag <= 2); }
      out(ocn) { assert(ocn >= 0); }
  }
  interface AssertObjInlineMarkup {
    string obj_inline_markup(string obj_raw, string obj_type_)
      in {
      }
      out(inline_markup) {
      }
  }
  interface AssertObjAttrib {
    string obj_attributes(string obj_raw, string node, string obj_type_)
      in {
      }
      out(obj_attrib_json) {
      }
  }
  interface AssertBookIndexNuggetHash {
    string[][string][string] bookindex_nugget_hash(string bookindex, int ocn)
      in {
        debug(bookindexraw) {
          mixin ScreenTxtColors;
          if (!bookindex.empty) {
            writeln(
              scr_txt_color["blue"], "* [bookindex] ", scr_txt_color["off"],
              "[", to!string(ocn), "] ", bookindex
            );
          }
        }
      }
      out(hash_nugget) {
      }
  }
  interface AssertBookIndexReport {
    string[][string][][string][] bookindex_nugget_hash(string[][string][string] bookindex_unordered_hashes)
      in {
      }
  }
  interface AssertNodeJSON {
    string node_emitter(
      string lvn,
      int ocn_,
      int counter_,
      int pointer_,
      string is_
    )
    in {
      auto rgx = new Rgx();
      assert(is_ != "heading");
      assert(to!int(ocn_) >= 0);
    }
    out(node) {
      debug(node) {
        mixin ScreenTxtColors;
        if (match(lvn, rgx.levels_numbered_headings)) {
          writeln(scr_txt_marker["yellow"], to!string(node));
        } else {
          writeln(scr_txt_marker["white"], to!string(node));
        }
      }
      JSONValue j = parseJSON(node);
      assert(j["parent_lvn"].integer >= 4);
      assert(j["parent_lvn"].integer <= 7);
      assert(j["parent_ocn"].integer >= 0);
    }
    string node_emitter_heading(
      string lvn,
      string lcn,
      int ocn_,
      int counter_,
      int pointer_,
      string is_
    )
    in {
      auto rgx = new Rgx();
      assert(is_ == "heading");
      assert(to!uint(ocn_) >= 0);
      assert(
        match(lvn, rgx.levels_numbered),
        ("not a valid heading level: " ~ lvn ~ " at " ~ to!string(ocn_))
      );
      if (match(lvn, rgx.levels_numbered)) {
        if (to!uint(lvn) == 0) {
          assert(to!uint(ocn_) == 1);
        }
      }
    }
    out(node) {
      auto rgx = new Rgx();
      debug(heading) {
        mixin ScreenTxtColors;
        if (match(lvn, rgx.levels_numbered_headings)) {
          writeln(scr_txt_marker["yellow"], to!string(node));
        }
      }
      debug(node) {
        mixin ScreenTxtColors;
        if (match(lvn, rgx.levels_numbered_headings)) {
          writeln(scr_txt_marker["yellow"], to!string(node));
        } else {
          writeln(scr_txt_marker["white"], to!string(node));
        }
      }
      JSONValue j = parseJSON(node);
      assert(j["parent_lvn"].integer <= 7);
      assert(j["parent_ocn"].integer >= 0);
      if (match(lvn, rgx.levels_numbered_headings)) {
        assert(j["lvn"].integer <= 7);
        assert(j["ocn"].integer >= 0);
        if (j["parent_lvn"].integer > 0) {
          assert(j["parent_lvn"].integer < j["lvn"].integer);
          if (j["ocn"].integer != 0) {
            assert(j["parent_ocn"].integer < j["ocn"].integer);
          }
        }
        if (j["lvn"].integer == 0) {
          assert(j["parent_lvn"].integer == 0);
        } else if  (j["lvn"].integer == 1) {
          assert(j["parent_lvn"].integer == 0);
        } else if  (j["lvn"].integer == 2) {
          assert(j["parent_lvn"].integer == 1);
        } else if  (j["lvn"].integer == 3) {
          assert(j["parent_lvn"].integer == 2);
        } else if  (j["lvn"].integer == 4) {
          assert(j["parent_lvn"].integer <= 3);
        } else if  (j["lvn"].integer == 5) {
          assert(j["parent_lvn"].integer == 4);
        } else if  (j["lvn"].integer == 6) {
          assert(j["parent_lvn"].integer == 5);
        } else if  (j["lvn"].integer == 7) {
          assert(j["parent_lvn"].integer == 6);
        } else if  (j["lvn"].integer == 8) {
        }
      }
    }
  }
}