/**
 * SuperAssistant Content Script — Main Entry Point
 *
 * Injected into AI chat pages (ChatGPT, Gemini, etc.)
 * 1. Detects which AI platform is active
 * 2. Initializes MCP bridge (content ↔ background)
 * 3. Starts DOM observer to render function_call blocks
 * 4. ★ NEW: Fetches workflow context and injects into chat input
 */
import { logMessage, createLogger } from "./logger"
import { initializeBridge } from "./bridge"
import { detectAdapter } from "./adapters"
import { startObserver, stopObserver } from "./renderer"

const logger = createLogger("SuperAssistant")

async function initialize(): Promise<void> {
  logMessage("Content script loaded — initializing SuperAssistant")

  // 1. Detect platform
  const adapter = detectAdapter()
  if (!adapter) {
    logger.info("No supported AI platform detected on this page. SuperAssistant inactive.")
    return
  }

  logger.info(`Detected platform: ${adapter.name}`)

  // 2. Initialize adapter
  try {
    await adapter.initialize()
    await adapter.activate()
    // Expose adapter globally for renderer use
    ;(window as any).__n8nAdapter = adapter
    logger.info(`Adapter ${adapter.name} activated`)
  } catch (err) {
    logger.error(`Failed to initialize adapter ${adapter.name}:`, err)
  }

  // 3. Initialize MCP bridge
  try {
    initializeBridge()
    logger.info("MCP bridge ready")
  } catch (err) {
    logger.error("Failed to initialize MCP bridge:", err)
  }

  // 4. Start DOM observer (scans for function_call blocks in AI responses)
  try {
    startObserver()
    logger.info("DOM observer started — watching for function_call blocks")
  } catch (err) {
    logger.error("Failed to start DOM observer:", err)
  }

  // 5. ★ Context Injection — fetch workflow context and inject into chat
  try {
    await injectWorkflowContext(adapter)
  } catch (err) {
    logger.error("Context injection failed:", err)
  }

  logMessage(`SuperAssistant ready on ${adapter.name} ⚡`)
}

// ─── Context Injection ──────────────────────────────────────────────

/**
 * Fetch active workflow context from background and inject into AI chat input.
 * This is the "Context-First" UX — user must have opened n8n workflow first.
 */
async function injectWorkflowContext(adapter: any): Promise<void> {
  // Ask background for active workflow context
  const response = await sendMessage({ type: "n8n-context:get" })

  if (!response?.success || !response.context) {
    logger.info("No active workflow context — user hasn't selected a workflow yet")
    return
  }

  const ctx = response.context
  logger.info(`Found workflow context: ${ctx.workflowId} (${ctx.workflowName})`)

  // Store context globally for bridge to auto-attach to tool calls
  ;(window as any).__n8nWorkflowContext = ctx

  // Fetch system prompt from MCP proxy
  let systemPrompt = ""
  try {
    const mcpConfig = await sendMessage({ type: "n8n-mcp:get-config" })
    const proxyUrl = mcpConfig?.proxyUrl || "http://localhost:3006"
    const res = await fetch(`${proxyUrl}/system-prompt`)
    if (res.ok) {
      systemPrompt = await res.text()
      logger.info("✅ System prompt loaded from MCP proxy")
    }
  } catch (err) {
    logger.info("⚠️ Could not fetch system prompt — using inline fallback")
  }

  // Build the final prompt: system prompt + workflow context
  const prompt = buildContextPrompt(ctx, systemPrompt)

  // Wait a bit for the chat UI to fully render (especially on fresh page load)
  await sleep(2000)

  // Inject into chat input via adapter
  const inserted = await adapter.insertText(prompt)
  if (inserted) {
    logger.info("✅ Workflow context injected into chat input")
  } else {
    logger.info("⚠️ Could not inject context — chat input not found (user may type manually)")
  }
}

function buildContextPrompt(ctx: any, systemPrompt: string): string {
  const contextBlock = [
    `I'm working on an n8n workflow.`,
    ``,
    `**Workflow ID:** ${ctx.workflowId}`,
    `**Name:** ${ctx.workflowName}`,
    `**Instance:** ${ctx.n8nBaseUrl}`,
    ``,
    `**Current structure:**`,
    "```json",
    ctx.workflowSummary,
    "```",
    ``,
    `Please help me modify this workflow. Use the n8n MCP tools ` +
      `(n8n_get_workflow, n8n_update_workflow, etc.) targeting workflow ID \`${ctx.workflowId}\`.`,
  ].join("\n")

  // If system prompt available, prepend it (hidden in a system block)
  if (systemPrompt) {
    return [
      `<system>`,
      systemPrompt,
      `</system>`,
      ``,
      contextBlock,
    ].join("\n")
  }

  return contextBlock
}

// ─── Helpers ────────────────────────────────────────────────────────

function sendMessage(msg: any): Promise<any> {
  return new Promise((resolve) => {
    chrome.runtime.sendMessage(msg, (response) => {
      resolve(response || {})
    })
  })
}

function sleep(ms: number): Promise<void> {
  return new Promise((r) => setTimeout(r, ms))
}

// ─── Lifecycle ──────────────────────────────────────────────────────

// Initialize when DOM is ready
if (document.readyState === "loading") {
  document.addEventListener("DOMContentLoaded", initialize)
} else {
  initialize()
}

// Cleanup on page unload
window.addEventListener("beforeunload", () => {
  stopObserver()
  logMessage("SuperAssistant cleanup complete")
})

// Listen for messages from background/popup
chrome.runtime.onMessage.addListener((message, _sender, sendResponse) => {
  if (message.command === "superassistant:status") {
    const adapter = (window as any).__n8nAdapter
    const ctx = (window as any).__n8nWorkflowContext
    sendResponse({
      active: !!adapter,
      platform: adapter?.name || null,
      adapterStatus: adapter?.getStatus() || "inactive",
      workflowId: ctx?.workflowId || null,
      workflowName: ctx?.workflowName || null,
    })
    return true
  }

  if (message.command === "superassistant:rescan") {
    import("./renderer").then(({ scanAndRender }) => {
      scanAndRender()
      sendResponse({ success: true })
    })
    return true
  }
})
