← Files KataARCHIVED FILE
tests/test_plugin_skill_layout.py
3.6 KB · Oct 3, 2026 · 06:31 UTC
"""Plugin skill layout: Codex/OpenAI do not follow symlinks into skills/kata/."""
from __future__ import annotations
import filecmp
import json
import unittest
from pathlib import Path
ROOT = Path(__file__).resolve().parents[1]
PLUGIN_SKILL = ROOT / "skills" / "kata"
class PluginSkillLayoutTest(unittest.TestCase):
def test_plugin_skill_files_are_real_copies(self) -> None:
pairs = [
(ROOT / "SKILL.md", PLUGIN_SKILL / "SKILL.md"),
(ROOT / "scripts" / "runner.py", PLUGIN_SKILL / "scripts" / "runner.py"),
(ROOT / "scripts" / "progress.py", PLUGIN_SKILL / "scripts" / "progress.py"),
(ROOT / "assets" / "icon.svg", PLUGIN_SKILL / "assets" / "icon.svg"),
(ROOT / "assets" / "icon.png", PLUGIN_SKILL / "assets" / "icon.png"),
(ROOT / "assets" / "logo.png", PLUGIN_SKILL / "assets" / "logo.png"),
(ROOT / "agents" / "openai.yaml", PLUGIN_SKILL / "agents" / "openai.yaml"),
(
ROOT / "references" / "session-protocol.md",
PLUGIN_SKILL / "references" / "session-protocol.md",
),
]
for canonical, packed in pairs:
with self.subTest(packed=str(packed.relative_to(ROOT))):
self.assertTrue(packed.is_file(), f"missing {packed}")
self.assertFalse(packed.is_symlink(), f"symlink would be dropped: {packed}")
self.assertTrue(
filecmp.cmp(canonical, packed, shallow=False),
f"{packed} drifted from {canonical}; run scripts/sync-plugin-skill.sh",
)
class PluginListingLimitsTest(unittest.TestCase):
def test_codex_interface_fits_openai_directory_limits(self) -> None:
manifest = json.loads((ROOT / ".codex-plugin" / "plugin.json").read_text(encoding="utf-8"))
interface = manifest["interface"]
self.assertLessEqual(len(interface["displayName"]), 30)
self.assertLessEqual(len(interface["shortDescription"]), 30)
self.assertEqual(interface["shortDescription"].count("\n"), 0)
self.assertLessEqual(len(interface["longDescription"]), 4000)
self.assertEqual(manifest["author"]["name"], interface["developerName"])
self.assertLessEqual(len(interface["defaultPrompt"]), 3)
for prompt in interface["defaultPrompt"]:
self.assertLessEqual(len(prompt), 128)
self.assertNotIn("@", prompt)
def test_openai_yaml_short_description_fits_limit(self) -> None:
text = (ROOT / "agents" / "openai.yaml").read_text(encoding="utf-8")
lines = [line for line in text.splitlines() if line.startswith(" short_description:")]
self.assertEqual(len(lines), 1)
value = lines[0].split(":", 1)[1].strip()
self.assertLessEqual(len(value), 30)
def test_openai_yaml_policy_only_allows_implicit_invocation(self) -> None:
"""Directory scanner: policy may contain only allow_implicit_invocation."""
text = (ROOT / "agents" / "openai.yaml").read_text(encoding="utf-8")
policy_lines = []
in_policy = False
for line in text.splitlines():
if line.startswith("policy:"):
in_policy = True
continue
if in_policy and line and not line.startswith(" "):
break
if in_policy:
policy_lines.append(line)
keys = [line.split(":", 1)[0].strip() for line in policy_lines if line.strip()]
self.assertEqual(keys, ["allow_implicit_invocation"])
self.assertIn("allow_implicit_invocation: false", text)
if __name__ == "__main__":
unittest.main()
SHA-256: 0ae87a55b265babc33381bc1bec3adb3ab4b30297925db6019f05bb6b73c53f2