[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M73FJS4XJ5J4GC1XFNDWAP0S":3,"skill-same:01M73FJS4XJ5J4GC1XFNDWAP0S":47},{"skillNo":4,"name":5,"nameZh":6,"description":6,"descriptionZh":6,"repositoryFullName":7,"ownerLogin":8,"ownerAvatarUrl":9,"ownerAccountNo":10,"ownerDisplayName":11,"repositoryNo":12,"starsCount":13,"licenseSpdxId":14,"licenseFileUrl":6,"sourceHtmlUrl":15,"categories":16,"keywords":17,"publishedAt":18,"linkOnly":19,"markdownContent":20,"markdownBody":21,"frontMatter":22,"refName":23,"commitSha":24,"skillDirectory":25,"forksCount":26,"repositoryHtmlUrl":27,"repositoryHomepageUrl":28,"ownerHtmlUrl":29,"ownerBlogUrl":30,"ownerDescription":31,"updatedAt":32,"install":33,"resources":46},"01M73FJS4XJ5J4GC1XFNDWAP0S","sanitize-html-cleanup",null,"Horonomos-laps\u002FYana-AI","Horonomos-laps","https:\u002F\u002Favatars.githubusercontent.com\u002Fu\u002F355299122?v=4","01M76B3QPXE88ET2SQPDPVATZT"," Horonomos-laps","01M72ZQRJPCYPSSWT4D00VJR2A",13,"Apache-2.0","https:\u002F\u002Fgithub.com\u002FHoronomos-laps\u002FYana-AI\u002Fblob\u002Fmain\u002Fcore\u002Fskills\u002Fsanitize-html-cleanup\u002FSKILL.md",[],[],"2026-11-11 15:11:14",false,"---\nname: sanitize-html-cleanup\ndescription: Strict HTML cleanup with self-closing tag repair, attribute allowlists, URL protocol validation, and CSS sanitization. apostrophecms\u002Fsanitize-html patterns for cleaning LLM-generated and web-scraped HTML. Sources: apostrophecms\u002Fsanitize-html.\norigin: yana-ai — synthesized from apostrophecms\u002Fsanitize-html (MIT)\nlicense: Apache-2.0\nversion: 1.0.0\ncompatibility: yana-ai >= 1.3.48\n---\n\n# \u002Fsanitize-html-cleanup\n\n## When to Use\n\n- Fix malformed HTML (unclosed tags, broken nesting) from LLM output\n- Sanitize HTML from web scraping before storing in agent knowledge base\n- Configure per-tag attribute rules more granularly than DOMPurify\n- Server-side Node.js HTML sanitization without JSDOM overhead\n\n## Do NOT use for\n\n- Pure XSS prevention in high-security contexts (use [[dompurify-xss-prevention]])\n- Plain text extraction (empty allowedTags list works but use regex instead)\n\n---\n\n## Strict config\n\n```javascript\nimport sanitizeHtml from 'sanitize-html'\n\nconst STRICT_OPTIONS: sanitizeHtml.IOptions = {\n  allowedTags: ['p', 'br', 'b', 'i', 'em', 'strong', 'ul', 'ol', 'li', 'code', 'pre',\n                'h1', 'h2', 'h3', 'blockquote', 'table', 'thead', 'tbody', 'tr', 'th', 'td'],\n\n  allowedAttributes: {\n    '*':    ['class'],\n    'a':    ['href', 'title'],\n    'code': ['class'],   \u002F\u002F for syntax highlighting classes\n    'pre':  ['class'],\n  },\n\n  allowedSchemes:       ['https', 'mailto'],\n  allowedSchemesByTag:  { 'a': ['https', 'mailto'] },\n\n  \u002F\u002F Auto-repair unclosed tags\n  selfClosing: ['br', 'hr', 'img', 'input'],\n\n  \u002F\u002F Transform: strip onclick but keep the element\n  transformTags: {\n    'a': sanitizeHtml.simpleTransform('a', { rel: 'noopener noreferrer' }),\n  },\n\n  disallowedTagsMode: 'discard',   \u002F\u002F 'discard' | 'escape' | 'recursiveEscape'\n}\n\nconst clean = sanitizeHtml(dirtyHtml, STRICT_OPTIONS)\n```\n\n---\n\n## Text-only extraction\n\n```javascript\nconst text = sanitizeHtml(html, {\n  allowedTags:       [],\n  allowedAttributes: {},\n})\n\u002F\u002F Preserves text content, strips all markup\n```\n\n---\n\n## LLM output pipeline\n\n```typescript\nfunction cleanLLMHtml(raw: string): string {\n  \u002F\u002F 1. sanitize-html fixes malformed structure + strips dangerous content\n  const sanitized = sanitizeHtml(raw, STRICT_OPTIONS)\n\n  \u002F\u002F 2. Strip empty paragraphs\n  return sanitized.replace(\u002F\u003Cp>\\s*\u003C\\\u002Fp>\u002Fg, '')\n}\n```\n\n---\n\n## Allow CSS with constraints\n\n```javascript\n{\n  allowedAttributes: { '*': ['style'] },\n  allowedStyles: {\n    '*': {\n      color:       [\u002F^#[0-9a-f]{3,6}$\u002Fi, \u002F^rgb\\(\\d{1,3},\\s*\\d{1,3},\\s*\\d{1,3}\\)$\u002F],\n      'font-size': [\u002F^\\d+(px|em|rem|%)$\u002F],\n      \u002F\u002F Block: expression(), url(), behavior: — these are not in the allowlist\n    },\n  },\n}\n```\n\n---\n\n## Anti-Fake-Pass Checklist\n\n```\n❌ allowedTags not set → sanitize-html uses its default list (may include script)\n❌ href allowed without allowedSchemes → javascript: and data: URIs pass through\n❌ disallowedTagsMode:'escape' → script tags rendered as visible text but NOT removed\n❌ Nested allowedAttributes { 'a': ['onclick'] } → XSS via event handler\n❌ CSS url() in style attribute not blocked by allowedStyles → SSRF via CSS\n❌ transformTags not a function but array → TypeError at runtime\n```\n","# \u002Fsanitize-html-cleanup\n\n## When to Use\n\n- Fix malformed HTML (unclosed tags, broken nesting) from LLM output\n- Sanitize HTML from web scraping before storing in agent knowledge base\n- Configure per-tag attribute rules more granularly than DOMPurify\n- Server-side Node.js HTML sanitization without JSDOM overhead\n\n## Do NOT use for\n\n- Pure XSS prevention in high-security contexts (use [[dompurify-xss-prevention]])\n- Plain text extraction (empty allowedTags list works but use regex instead)\n\n---\n\n## Strict config\n\n```javascript\nimport sanitizeHtml from 'sanitize-html'\n\nconst STRICT_OPTIONS: sanitizeHtml.IOptions = {\n  allowedTags: ['p', 'br', 'b', 'i', 'em', 'strong', 'ul', 'ol', 'li', 'code', 'pre',\n                'h1', 'h2', 'h3', 'blockquote', 'table', 'thead', 'tbody', 'tr', 'th', 'td'],\n\n  allowedAttributes: {\n    '*':    ['class'],\n    'a':    ['href', 'title'],\n    'code': ['class'],   \u002F\u002F for syntax highlighting classes\n    'pre':  ['class'],\n  },\n\n  allowedSchemes:       ['https', 'mailto'],\n  allowedSchemesByTag:  { 'a': ['https', 'mailto'] },\n\n  \u002F\u002F Auto-repair unclosed tags\n  selfClosing: ['br', 'hr', 'img', 'input'],\n\n  \u002F\u002F Transform: strip onclick but keep the element\n  transformTags: {\n    'a': sanitizeHtml.simpleTransform('a', { rel: 'noopener noreferrer' }),\n  },\n\n  disallowedTagsMode: 'discard',   \u002F\u002F 'discard' | 'escape' | 'recursiveEscape'\n}\n\nconst clean = sanitizeHtml(dirtyHtml, STRICT_OPTIONS)\n```\n\n---\n\n## Text-only extraction\n\n```javascript\nconst text = sanitizeHtml(html, {\n  allowedTags:       [],\n  allowedAttributes: {},\n})\n\u002F\u002F Preserves text content, strips all markup\n```\n\n---\n\n## LLM output pipeline\n\n```typescript\nfunction cleanLLMHtml(raw: string): string {\n  \u002F\u002F 1. sanitize-html fixes malformed structure + strips dangerous content\n  const sanitized = sanitizeHtml(raw, STRICT_OPTIONS)\n\n  \u002F\u002F 2. Strip empty paragraphs\n  return sanitized.replace(\u002F\u003Cp>\\s*\u003C\\\u002Fp>\u002Fg, '')\n}\n```\n\n---\n\n## Allow CSS with constraints\n\n```javascript\n{\n  allowedAttributes: { '*': ['style'] },\n  allowedStyles: {\n    '*': {\n      color:       [\u002F^#[0-9a-f]{3,6}$\u002Fi, \u002F^rgb\\(\\d{1,3},\\s*\\d{1,3},\\s*\\d{1,3}\\)$\u002F],\n      'font-size': [\u002F^\\d+(px|em|rem|%)$\u002F],\n      \u002F\u002F Block: expression(), url(), behavior: — these are not in the allowlist\n    },\n  },\n}\n```\n\n---\n\n## Anti-Fake-Pass Checklist\n\n```\n❌ allowedTags not set → sanitize-html uses its default list (may include script)\n❌ href allowed without allowedSchemes → javascript: and data: URIs pass through\n❌ disallowedTagsMode:'escape' → script tags rendered as visible text but NOT removed\n❌ Nested allowedAttributes { 'a': ['onclick'] } → XSS via event handler\n❌ CSS url() in style attribute not blocked by allowedStyles → SSRF via CSS\n❌ transformTags not a function but array → TypeError at runtime\n```\n",{},"main","481dcd7dd2e288b9d627a2bd017db70e64e6c6fa","core\u002Fskills\u002Fsanitize-html-cleanup",1,"https:\u002F\u002Fgithub.com\u002FHoronomos-laps\u002FYana-AI","https:\u002F\u002Fyana.vutam.link\u002F","https:\u002F\u002Fgithub.com\u002FHoronomos-laps","https:\u002F\u002Fyana.vutam.link","An open-source governed runtime & execution environment for multi-agent AI systems.","2026-11-11 23:56:26",{"source":7,"skillName":5,"commands":34,"prompt":44,"zipAvailable":45},[35,38,41],{"tool":36,"command":37},"npx","npx skills add Horonomos-laps\u002FYana-AI --skill sanitize-html-cleanup",{"tool":39,"command":40},"bunx","bunx skills add Horonomos-laps\u002FYana-AI --skill sanitize-html-cleanup",{"tool":42,"command":43},"pnpm","pnpm dlx skills add Horonomos-laps\u002FYana-AI --skill sanitize-html-cleanup","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002FHoronomos-laps\u002FYana-AI\u002Fblob\u002Fmain\u002Fcore\u002Fskills\u002Fsanitize-html-cleanup\u002FSKILL.md",true,[],[48,56,63,71,79,87],{"skillNo":49,"name":50,"nameZh":6,"description":51,"descriptionZh":6,"repositoryFullName":7,"ownerLogin":8,"ownerAvatarUrl":9,"ownerAccountNo":10,"ownerDisplayName":11,"repositoryNo":12,"starsCount":13,"licenseSpdxId":52,"licenseFileUrl":6,"sourceHtmlUrl":53,"categories":54,"keywords":55,"publishedAt":18},"01M735GKET5YVYKAY62W2P5YXB","openai--sentry--sentry","Use when the user asks to inspect Sentry issues or events, summarize recent production errors, or pull basic Sentry health data via the Sentry API; perform read-only queries with the bundled script and require `SENTRY_AUTH_TOKEN`.","MIT","https:\u002F\u002Fgithub.com\u002FHoronomos-laps\u002FYana-AI\u002Fblob\u002Fmain\u002F.claude\u002Fskills\u002Fopenai--sentry--sentry\u002FSKILL.md",[],[],{"skillNo":57,"name":58,"nameZh":6,"description":59,"descriptionZh":6,"repositoryFullName":7,"ownerLogin":8,"ownerAvatarUrl":9,"ownerAccountNo":10,"ownerDisplayName":11,"repositoryNo":12,"starsCount":13,"licenseSpdxId":14,"licenseFileUrl":6,"sourceHtmlUrl":60,"categories":61,"keywords":62,"publishedAt":18},"01M73DCAP83T17HY7SMGK7MGFE","ito-basket-compare","Compare Itô prediction-market baskets against a user's knowledge base, portfolio notes, financial context, watchlist, or research thesis. Use for read-only basket comparison and gap analysis without investment advice or live trading.","https:\u002F\u002Fgithub.com\u002FHoronomos-laps\u002FYana-AI\u002Fblob\u002Fmain\u002Fcore\u002Fskills\u002Fito-basket-compare\u002FSKILL.md",[],[],{"skillNo":64,"name":65,"nameZh":6,"description":66,"descriptionZh":6,"repositoryFullName":7,"ownerLogin":8,"ownerAvatarUrl":9,"ownerAccountNo":10,"ownerDisplayName":11,"repositoryNo":12,"starsCount":13,"licenseSpdxId":14,"licenseFileUrl":67,"sourceHtmlUrl":68,"categories":69,"keywords":70,"publishedAt":18},"01M734CYEMZFDR3KH6SW0JP8TD","implementing-network-traffic-baselining","Build network traffic baselines from NetFlow\u002FIPFIX data using Python pandas for statistical analysis, z-score anomaly detection, and hourly\u002Fdaily traffic pattern profiling","https:\u002F\u002Fgithub.com\u002Fyanacuti1121\u002FYana-AI\u002Fblob\u002Fmain\u002F.claude\u002Fskills\u002Fimplementing-network-traffic-baselining\u002FLICENSE","https:\u002F\u002Fgithub.com\u002FHoronomos-laps\u002FYana-AI\u002Fblob\u002Fmain\u002F.claude\u002Fskills\u002Fimplementing-network-traffic-baselining\u002FSKILL.md",[],[],{"skillNo":72,"name":73,"nameZh":6,"description":74,"descriptionZh":6,"repositoryFullName":7,"ownerLogin":8,"ownerAvatarUrl":9,"ownerAccountNo":10,"ownerDisplayName":11,"repositoryNo":12,"starsCount":13,"licenseSpdxId":14,"licenseFileUrl":75,"sourceHtmlUrl":76,"categories":77,"keywords":78,"publishedAt":18},"01M73ASZ6NJRJM44Z2P84NGQ3Q","detecting-evasion-techniques-in-endpoint-logs","Detects defense evasion techniques used by adversaries in endpoint logs including log tampering, timestomping, process injection, and security tool disabling. Use when investigating suspicious endpoint behavior, building detection rules for evasion tactics, or conducting threat hunting for stealthy adversary activity. Activates for requests involving evasion detection, defense evasion analysis, log tampering detection, or MITRE ATT&CK TA0005.","https:\u002F\u002Fgithub.com\u002Fyanacuti1121\u002FYana-AI\u002Fblob\u002Fmain\u002Fcore\u002Fskills\u002Fdetecting-evasion-techniques-in-endpoint-logs\u002FLICENSE","https:\u002F\u002Fgithub.com\u002FHoronomos-laps\u002FYana-AI\u002Fblob\u002Fmain\u002Fcore\u002Fskills\u002Fdetecting-evasion-techniques-in-endpoint-logs\u002FSKILL.md",[],[],{"skillNo":80,"name":81,"nameZh":6,"description":82,"descriptionZh":6,"repositoryFullName":7,"ownerLogin":8,"ownerAvatarUrl":9,"ownerAccountNo":10,"ownerDisplayName":11,"repositoryNo":12,"starsCount":13,"licenseSpdxId":14,"licenseFileUrl":83,"sourceHtmlUrl":84,"categories":85,"keywords":86,"publishedAt":18},"01M734AFNXD06Z78QRK0VKGT7Q","implementing-microsegmentation-with-guardicore","Implementing microsegmentation using Akamai Guardicore Segmentation to map application dependencies, create granular network policies, visualize east-west traffic flows, and enforce least-privilege communication between workloads across data centers and cloud.","https:\u002F\u002Fgithub.com\u002Fyanacuti1121\u002FYana-AI\u002Fblob\u002Fmain\u002F.claude\u002Fskills\u002Fimplementing-microsegmentation-with-guardicore\u002FLICENSE","https:\u002F\u002Fgithub.com\u002FHoronomos-laps\u002FYana-AI\u002Fblob\u002Fmain\u002F.claude\u002Fskills\u002Fimplementing-microsegmentation-with-guardicore\u002FSKILL.md",[],[],{"skillNo":88,"name":89,"nameZh":6,"description":6,"descriptionZh":6,"repositoryFullName":7,"ownerLogin":8,"ownerAvatarUrl":9,"ownerAccountNo":10,"ownerDisplayName":11,"repositoryNo":12,"starsCount":13,"licenseSpdxId":14,"licenseFileUrl":6,"sourceHtmlUrl":90,"categories":91,"keywords":92,"publishedAt":18},"01M736TK27QMCXK0DVCH25SJN5","ramdisk-tmpfs-patterns","https:\u002F\u002Fgithub.com\u002FHoronomos-laps\u002FYana-AI\u002Fblob\u002Fmain\u002F.claude\u002Fskills\u002Framdisk-tmpfs-patterns\u002FSKILL.md",[],[]]