import { execFile } from 'child_process'
import { rmSync } from 'fs'
import type { Platform } from '../index.js'
import { createClawstrTempHome } from '../index.js'
import { parseClawstrReplyResult } from './clawstr.js'
import type { ReplierApiKeys, ReplyPostResult } from './types.js'

async function replyOnMoltx(parentExternalId: string, content: string, apiKey: string): Promise<ReplyPostResult> {
  const res = await fetch('https://moltx.io/v1/posts', {
    method: 'POST',
    headers: { 'Authorization': `Bearer ${apiKey}`, 'Content-Type': 'application/json' },
    body: JSON.stringify({ type: 'reply', parent_id: parentExternalId, content }),
  })
  if (!res.ok) throw new Error(`Moltx reply API ${res.status}: ${await res.text()}`)
  const raw = await res.json()
  const wrapper = raw as { data?: { post?: { id?: string }; id?: string }; id?: string }
  const externalId = wrapper?.data?.post?.id || wrapper?.data?.id || wrapper?.id || ''
  if (!externalId) {
    throw new Error(`Moltx reply API returned no reply id: ${JSON.stringify(raw).slice(0, 200)}`)
  }
  return { externalId, url: externalId ? `https://moltx.io/post/${externalId}` : undefined }
}

async function replyOnMoltbook(postExternalId: string, commentExternalId: string, content: string, apiKey: string): Promise<ReplyPostResult> {
  const res = await fetch(`https://www.moltbook.com/api/v1/posts/${postExternalId}/comments`, {
    method: 'POST',
    headers: { 'Authorization': `Bearer ${apiKey}`, 'Content-Type': 'application/json' },
    body: JSON.stringify({ content, parent_id: commentExternalId }),
  })
  if (!res.ok) throw new Error(`Moltbook reply API ${res.status}: ${await res.text()}`)
  const raw = await res.json()
  const wrapper = raw as { comment?: { id?: string }; id?: string }
  const externalId = wrapper?.comment?.id || wrapper?.id || ''
  if (!externalId) {
    throw new Error(`Moltbook reply API returned no reply id: ${JSON.stringify(raw).slice(0, 200)}`)
  }
  return { externalId, url: externalId ? `https://www.moltbook.com/comment/${externalId}` : undefined }
}

async function replyOnClawstr(noteExternalId: string, content: string, secretKey: string): Promise<ReplyPostResult> {
  const tmpHome = createClawstrTempHome(secretKey)
  return new Promise((resolve, reject) => {
    execFile('npx', ['-y', '@clawstr/cli@latest', 'reply', noteExternalId, content], { timeout: 60_000, env: { ...process.env, HOME: tmpHome } }, (error, stdout, stderr) => {
      try { rmSync(tmpHome, { recursive: true, force: true }) } catch { /* ignore */ }
      if (error) {
        reject(new Error(`Clawstr reply CLI failed: ${error.message}${stderr ? ` stderr: ${stderr}` : ''}`))
        return
      }
      try {
        resolve(parseClawstrReplyResult(stdout, stderr))
      } catch (parseError) {
        reject(parseError instanceof Error ? parseError : new Error(String(parseError)))
      }
    })
  })
}

export async function postReplyOnPlatform(
  platform: Platform,
  parentPostExternalId: string,
  parentReplyExternalId: string,
  content: string,
  keys: ReplierApiKeys,
): Promise<ReplyPostResult> {
  switch (platform) {
    case 'moltx': {
      if (!keys.moltxApiKey) throw new Error('Moltx API key not configured')
      return replyOnMoltx(parentReplyExternalId, content, keys.moltxApiKey)
    }
    case 'moltbook': {
      if (!keys.moltbookApiKey) throw new Error('Moltbook API key not configured')
      return replyOnMoltbook(parentPostExternalId, parentReplyExternalId, content, keys.moltbookApiKey)
    }
    case 'clawstr': {
      if (!keys.clawstrSecretKey) throw new Error('Clawstr secret key not configured')
      return replyOnClawstr(parentReplyExternalId, content, keys.clawstrSecretKey)
    }
  }
}
