import { describe, test } from 'node:test';
import assert from 'node:assert/strict';
import { isLinkedInContent } from '../linkedin-content-filter.mjs';

// The short-form de-AI / differentiation gate (Step 14) is scoped by the same
// content/non-content boundary the content-gatekeeper hook uses. These tests
// pin that boundary so the gate fires on the short-form draft paths the five
// creation commands (post/quick/react/carousel/video) actually write to, and
// stays silent on plugin infrastructure (commands, hooks, references, config).

describe('isLinkedInContent — short-form gate scope (positive)', () => {
  test('fires on a draft post under assets/drafts/', () => {
    assert.equal(isLinkedInContent('assets/drafts/2026-05-30-ai-governance.md'), true);
  });

  test('fires on a carousel slide image under assets/drafts/', () => {
    assert.equal(isLinkedInContent('assets/drafts/carousel-20260530-ai/slide-1.png'), true);
  });

  test('fires on a nested absolute assets/drafts path', () => {
    assert.equal(
      isLinkedInContent('/Users/ktg/work/assets/drafts/video-script.md'),
      true
    );
  });

  test('fires on a linkedin-posts content path', () => {
    assert.equal(isLinkedInContent('/Users/ktg/linkedin-posts/quick-take.md'), true);
  });

  test('fires on a linkedin-studio/assets content path', () => {
    assert.equal(
      isLinkedInContent('/repo/plugins/linkedin-studio/assets/examples/post.md'),
      true
    );
  });
});

describe('isLinkedInContent — gate stays silent on infrastructure (negative)', () => {
  test('does not fire on a command file', () => {
    assert.equal(isLinkedInContent('commands/post.md'), false);
  });

  test('does not fire on a hook prompt', () => {
    assert.equal(isLinkedInContent('hooks/prompts/voice-guardian.md'), false);
  });

  test('does not fire on a reference doc', () => {
    assert.equal(isLinkedInContent('references/linkedin-formats.md'), false);
  });

  test('does not fire on an agent definition', () => {
    assert.equal(isLinkedInContent('agents/differentiation-checker.md'), false);
  });

  test('does not fire on a script or its tests', () => {
    assert.equal(isLinkedInContent('hooks/scripts/state-updater.mjs'), false);
    assert.equal(
      isLinkedInContent('hooks/scripts/__tests__/linkedin-content-filter.test.mjs'),
      false
    );
  });
});

describe('isLinkedInContent — code/config/template/meta files (negative)', () => {
  test('does not fire on code/config extensions', () => {
    for (const p of ['x.json', 'x.mjs', 'x.ts', 'x.yaml', 'x.css', 'x.html']) {
      assert.equal(isLinkedInContent(p), false, `${p} should be non-content`);
    }
  });

  test('does not fire on template files', () => {
    assert.equal(isLinkedInContent('config/state-file.template.md'), false);
  });

  test('does not fire on known meta filenames', () => {
    for (const p of ['CLAUDE.md', 'README.md', 'CHANGELOG.md', 'notes.local.md']) {
      assert.equal(isLinkedInContent(p), false, `${p} should be non-content`);
    }
  });

  test('returns false for empty or missing path', () => {
    assert.equal(isLinkedInContent(''), false);
    assert.equal(isLinkedInContent(null), false);
    assert.equal(isLinkedInContent(undefined), false);
  });
});

// M0-10: after drafts relocate to the external data root, the gate must still
// fire on them. `.claude` is an infraDir, so a naive check rejects any /.claude/
// path — the external-drafts positive must short-circuit BEFORE that negative,
// while the state file (.local.md) and REMEMBER.md stay excluded.
describe('isLinkedInContent — external data-root drafts (M0-10)', () => {
  const H = '/Users/test';

  test('fires on a relocated draft under ~/.claude/linkedin-studio/drafts/', () => {
    assert.equal(isLinkedInContent(`${H}/.claude/linkedin-studio/drafts/2026-06-20-post.md`), true);
  });

  test('fires on a relocated carousel slide under the external drafts dir', () => {
    assert.equal(isLinkedInContent(`${H}/.claude/linkedin-studio/drafts/carousel-x/slide-1.png`), true);
  });

  test('does NOT fire on the external state file (.local.md)', () => {
    assert.equal(isLinkedInContent(`${H}/.claude/linkedin-studio.local.md`), false);
  });

  test('does NOT fire on the external REMEMBER.md', () => {
    assert.equal(isLinkedInContent(`${H}/.claude/linkedin-studio/REMEMBER.md`), false);
  });

  test('does NOT fire on ~/.claude/settings.json', () => {
    assert.equal(isLinkedInContent(`${H}/.claude/settings.json`), false);
  });

  test('still fires on in-plugin assets/drafts/ (migration-window back-compat)', () => {
    assert.equal(isLinkedInContent('assets/drafts/2026-06-20-post.md'), true);
  });
});
