/**
 * PR-A Baseline Test 12: Active Memory Plugin
 * Verifies: active-memory plugin exists, loads, has hook mechanism
 * Freezes: active-memory plugin contract
 */

import { describe, it } from "node:test";
import assert from "node:assert";
import { existsSync, readFileSync, readdirSync } from "node:fs";
import { homedir } from "node:os";
import { join } from "node:path";

const OPENCLAW_HOME = "/opt/homebrew/lib/node_modules/openclaw";
const ACTIVE_MEM_DIR = join(OPENCLAW_HOME, "dist", "extensions", "active-memory");
const MEMORY_CORE_DIR = join(OPENCLAW_HOME, "dist", "extensions", "memory-core");

describe("test-12: Active Memory Plugin Baseline", () => {
  it("12.01 - active-memory plugin directory exists", () => {
    const exists = existsSync(ACTIVE_MEM_DIR);
    console.log("[BASELINE] active-memory dir:", ACTIVE_MEM_DIR);
    console.log("[BASELINE] active-memory dir exists:", exists);
    if (exists) {
      const files = readdirSync(ACTIVE_MEM_DIR);
      console.log("[BASELINE] active-memory files:", files.join(", "));
    }
    assert.ok(exists, "active-memory plugin directory must exist");
  });

  it("12.02 - active-memory plugin.json has contracts", () => {
    const pluginPath = join(ACTIVE_MEM_DIR, "openclaw.plugin.json");
    if (existsSync(pluginPath)) {
      const plugin = JSON.parse(readFileSync(pluginPath, "utf8"));
      console.log("[BASELINE] active-memory plugin id:", plugin.id);
      console.log("[BASELINE] active-memory onStartup:", plugin.activation?.onStartup);
      console.log("[BASELINE] active-memory name:", plugin.name);
      
      // Check config schema keys
      if (plugin.configSchema?.properties) {
        const keys = Object.keys(plugin.configSchema.properties);
        console.log("[BASELINE] active-memory config keys:", keys.join(", "));
        console.log("[BASELINE] active-memory config key count:", keys.length);
        
        // Key config fields that must exist
        assert.ok(keys.includes("enabled"), "must have 'enabled' config");
        assert.ok(keys.includes("timeoutMs"), "must have 'timeoutMs' config");
        assert.ok(keys.includes("queryMode"), "must have 'queryMode' config");
      }
    } else {
      console.log("[BASELINE] active-memory plugin.json not found");
    }
    assert.ok(true, "baseline frozen: plugin contract");
  });

  it("12.03 - memory-core plugin also exists", () => {
    const exists = existsSync(MEMORY_CORE_DIR);
    console.log("[BASELINE] memory-core dir exists:", exists);
    if (exists) {
      const pluginPath = join(MEMORY_CORE_DIR, "openclaw.plugin.json");
      if (existsSync(pluginPath)) {
        const plugin = JSON.parse(readFileSync(pluginPath, "utf8"));
        console.log("[BASELINE] memory-core plugin id:", plugin.id);
        console.log("[BASELINE] memory-core kind:", plugin.kind);
        console.log("[BASELINE] memory-core contracts:", 
          JSON.stringify(plugin.contracts));
        console.log("[BASELINE] memory-core has dreaming:", 
          !!plugin.configSchema?.properties?.dreaming);
        
        // Tool contracts are critical
        const tools = plugin.contracts?.tools || [];
        console.log("[BASELINE] memory-core tools:", tools.join(", "));
        assert.ok(tools.includes("memory_search"), "must register memory_search");
        assert.ok(tools.includes("memory_get"), "must register memory_get");
        
        // Dreaming phases
        const phases = plugin.configSchema?.properties?.dreaming?.properties?.phases?.properties;
        if (phases) {
          const phaseNames = Object.keys(phases);
          console.log("[BASELINE] dreaming phases:", phaseNames.join(", "));
          // Freeze: current phase count (light, deep, rem = 3)
          console.log("[BASELINE] dreaming phase count:", phaseNames.length);
        }
      }
    }
    assert.ok(exists, "memory-core plugin directory must exist");
  });

  it("12.04 - active-memory hook mechanism verified", () => {
    // active-memory uses before_agent_reply hook
    const pluginPath = join(ACTIVE_MEM_DIR, "openclaw.plugin.json");
    if (existsSync(pluginPath)) {
      const plugin = JSON.parse(readFileSync(pluginPath, "utf8"));
      // Check if hook is declared in plugin metadata
      const hasHooks = plugin.hooks !== undefined || 
                       plugin.activation?.onStartup === true;
      console.log("[BASELINE] active-memory has hook declarations:", hasHooks);
      
      // Config reveals hook behavior
      const mode = plugin.configSchema?.properties?.queryMode;
      if (mode) {
        console.log("[BASELINE] queryMode options:", mode.enum?.join(", ") || "unknown");
      }
    }
    
    // Check that the actual code module loads
    const indexJs = join(ACTIVE_MEM_DIR, "index.js");
    if (existsSync(indexJs)) {
      const size = readFileSync(indexJs, "utf8").length;
      console.log("[BASELINE] active-memory index.js size:", size);
      assert.ok(size > 100, "active-memory code must be substantial");
    }
    
    assert.ok(true, "baseline frozen: active-memory hook mechanism");
  });

  it("12.05 - circuit breaker config exists", () => {
    const pluginPath = join(ACTIVE_MEM_DIR, "openclaw.plugin.json");
    if (existsSync(pluginPath)) {
      const plugin = JSON.parse(readFileSync(pluginPath, "utf8"));
      const props = plugin.configSchema?.properties || {};
      const hasCircuitBreaker = 
        props.circuitBreakerMaxTimeouts !== undefined &&
        props.circuitBreakerCooldownMs !== undefined;
      console.log("[BASELINE] circuit breaker config:", hasCircuitBreaker);
      
      if (hasCircuitBreaker) {
        console.log("[BASELINE] circuitBreakerMaxTimeouts min:", 
          props.circuitBreakerMaxTimeouts.minimum);
        console.log("[BASELINE] circuitBreakerCooldownMs min:", 
          props.circuitBreakerCooldownMs.minimum);
      }
    }
    assert.ok(true, "baseline frozen: circuit breaker config");
  });

  it("12.06 - block mode currently available (blocking path exists)", () => {
    // Active memory has a blocking mode that runs before agent reply
    // This test freezes the fact that it exists (not whether it's enabled)
    const pluginPath = join(ACTIVE_MEM_DIR, "openclaw.plugin.json");
    if (existsSync(pluginPath)) {
      const plugin = JSON.parse(readFileSync(pluginPath, "utf8"));
      const promptStyle = plugin.configSchema?.properties?.promptStyle;
      if (promptStyle) {
        console.log("[BASELINE] promptStyle options:", promptStyle.enum?.join(", "));
        assert.ok(promptStyle.enum.length >= 4, "must have multiple prompt styles");
      }
    }
    assert.ok(true, "baseline frozen: active memory blocking behavior exists");
  });
});
