正文
获取原文件SKILL.md
Purpose
Produce a WeChat-pasteable HTML article from a Liu Haonan Obsidian Markdown note without modifying the original. Prefer this skill for 医疗 AI 情报精读 and similar posts that should use the black/yellow 刘浩南丨医疗AI实战派 visual language, with publisher-friendly ordered image assets. This skill formats content; it must not perform editorial deletion or silently remove evidence and viewpoints.
Default Inputs
- Source Markdown: user-provided
.mdpath. - Component library:
/Users/liuhaoxian/Downloads/我的/AI项目/00 刘浩南/刘浩南公众号排版组件库 - Base converter:
/Users/liuhaoxian/.agents/skills/wechat-article-formatter/convert.py - Output files next to the source:
{stem}_公众号排版副本.md{stem}_公众号排版.html
Fast Path
Use the bundled script whenever possible:
python3 /Users/liuhaoxian/.codex/skills/haonan-wechat-article/scripts/format_article.py \
--input "/path/to/article.md" \
--wechat-body-only \
--recompute-reading-time
Useful options:
--component-library "/path/to/刘浩南公众号排版组件库"
--converter "/path/to/wechat-article-formatter/convert.py"
--output-html "/path/to/output.html"
--output-md "/path/to/output_copy.md"
--author "刘浩南"
--wechat-body-only # recommended for final WeChat publishing; avoids duplicate in-body title/byline
--recompute-reading-time # recompute after editorial trimming instead of keeping a stale source estimate
--no-ordered-image-names # optional fallback; default keeps ordered image names
The script:
- Reads the original Markdown and does not edit it.
- Removes YAML frontmatter from the layout copy.
- Preserves the source article H1 in normal preview mode; with
--wechat-body-only, omits the duplicate in-body H1 because the WeChat title field already displays it. - Adds
作者|刘浩南in normal preview mode; with--wechat-body-only, omits the duplicate byline because the account identity and final brand block already identify the author. - Combines the estimated reading time and opening hint near the top. With
--recompute-reading-time, calculates the value from final visible source content at roughly 420 Chinese characters or 220 Latin words per minute, rounded up. - Converts Obsidian
[!summary]callout into a normal Markdown blockquote so it stays copyable as quote-style content in the WeChat editor. - Keeps the opening quote such as
本期一句话as a single-layer quote, without nested quote/card styling. - Splits source English quotes and
译文:into separate blockquote modules, then validates the final HTML so every single blockquote is no more than 300 characters. - Copies required article and component images into the output location when output is not next to the source.
- By default, copies every local image used by the prepared article into
figures/ordered/and rewrites Markdown/HTML refs to ordered filenames such as01-cover-handdrawn.png,02-divider-01.png, and03-overview-tech.png, matching visual appearance order in the article. For publishing packages outside the source directory, onlyfigures/ordered/is kept so the WeChat backend file picker is not cluttered with duplicate originals. Use--no-ordered-image-namesonly when preserving original image paths is required. - Inserts divider PNGs before each actual major Markdown section (
## ...) and keeps that text heading. H2 headings are stripped of leading numbers in the WeChat output, centered, and shown as black bold text on a yellow background. - Styles
原文引用:quote contents like captions: left-aligned, small, and visually quiet. - Removes standalone Markdown horizontal rules between small modules.
- Appends a final brand block as a native
haonan-brand-cardHTML block, not a Markdown blockquote, so the only final blockquote can remain本期一句话:
刘浩南丨医疗AI实战派关注医疗 AI 从 demo 到真实落地,聚焦产品化、商业化与院内工作流效率提升,让医生把更多时间留给诊疗本身。12年医疗产研经验大湾区头部医疗AI公司前产品总监独立开发者感谢关注,我在大湾区,下期见
- Fails fast if a divider image or article image is missing, instead of silently producing an incomplete publishing package.
- Runs the WeChat formatter and post-processes the HTML with inline black/yellow brand styling.
- Preserves Markdown emphasis (
**重点句**) through the Markdown and HTML outputs. For polished publishing packages, the final HTML should normally contain 5-10 meaningfulstrong/bhighlights for core judgments, engineering takeaways, risk boundaries, or closing thesis. Do not strip emphasis during cleanup. - Preserves explicit image-caption paragraphs after key source images. Treat a paragraph as a caption only when it starts with an explicit caption marker:
图注:,图片说明:,图片来源:, or图源:(ASCII colons are also accepted). Captions are required for project website/README first images, GitHub repository metric screenshots, and important Release/official documentation screenshots. Generated whiteboard images and reused cover images only need captions when they clarify a specific argument. Captions should render at 12px, centered, visually quiet, and should not be converted into section headings or blockquotes. Never infer a caption merely because a short paragraph follows an image; ordinary explanation or narrative after an image keeps the normal body style.
Manual Rules
If editing manually, follow these rules:
- Never modify the original Markdown.
- Keep the source H1 in the Obsidian original. For the final WeChat body, do not repeat the H1 or
作者|刘浩南; use--wechat-body-only. Keep them only in local preview mode when explicitly needed. - Put
预计阅读at the very beginning of the rendered article, combined with关注不迷路,加星标更聚焦in one compact opening element. Recompute it after content trimming. - Convert
本期速览into a normal quote-style block, not an Obsidian-only callout card. - Keep source article images and overview images. For 医疗 AI 情报精读, do not accept placeholder-like SVG/canvas/PIL/script diagrams as final source images; the publishing package should preserve image2/imagegen raster assets prepared by the writer.
- The in-article cover image must match the current title/main line, not a generic column cover; if the source cover is generic, stop and return to writing/image generation rather than silently publishing it.
- Preserve Markdown bold emphasis for important judgment sentences. A publish-ready article should usually retain 5-10 highlighted sentences, not only bold terms. Prioritize core judgment, counterintuitive point, engineering mechanism, adoption boundary, and closing thesis.
- Add or preserve a short
图注:line after key source screenshots: project website/README first image, GitHub repository metric page, and important Release/official documentation pages. For generated explanation images and reused cover images, add captions only when they help the reader understand the argument. Keep captions factual and concise, normally no more than 60 Chinese characters. - For publishing packages, prefer ordered image filenames in
figures/ordered/so the WeChat backend file picker matches article reading order. - Use divider images (
divider-01.png, etc.) as module boundaries for whatever H2 sections the article actually has. - Keep text H2 titles in the complete long article, remove leading numbering in the WeChat output, center them, and style them as black bold text on a yellow background; do not hard-code section names or counts.
- Keep H3 story/item titles unless the user explicitly removes them.
- Keep
本期一句话or similar opening quotes as one quote block only. - Split long source quote modules that contain both English content and
译文:into separate blockquotes, and ensure every final HTML blockquote is no more than 300 characters. - Make only explicitly marked image captions 12px, centered, and visually quieter than body text. Recognize
图注:,图片说明:,图片来源:, and图源:(including ASCII-colon variants). Do not use image proximity, paragraph length, italics, or visual position alone to classify a paragraph as a caption. - Keep explicit caption prefixes and style those paragraphs like captions. Do not remove them as boilerplate. Do not force captions onto every decorative or self-explanatory image. A normal paragraph immediately below an image remains normal body text.
- Make
原文引用:quote contents match caption text size and color. - In tables, preserve selective bold emphasis for key recommendations or risk labels, but do not bold entire tables.
- After formatting, check that emphasis, key image captions, ordered image names, dynamic dividers, and the one-blockquote rule all survive together.
- For workflows that require only one body quote, keep
本期一句话as the only blockquote. The final brand tail may appear as an image plus normal paragraph-style brand text, but it must not create a second blockquote. - Remove small standalone gray dividers between modules; rely on whitespace and numbered section divider images instead.
- Remove decorative ending component images unless the user asks to keep them.
- End with one brand image plus a native
haonan-brand-cardintro block; do not render the brand intro as a Markdown blockquote. - Keep all styles inline for WeChat paste compatibility.
- Local images will still need to be uploaded or pasted into the WeChat editor as WeChat requires.
Validation
After generation, check:
python3 - <<'PY'
from bs4 import BeautifulSoup
from pathlib import Path
p = Path("/path/to/output.html")
s = BeautifulSoup(p.read_text(encoding="utf-8"), "html.parser")
print("h2_count", len(s.find_all("h2")))
print("h1_count", len(s.find_all("h1")))
print("images", len(s.find_all("img")))
print("ordered_images", len(list(p.parent.joinpath("figures", "ordered").glob("*"))))
print("hr_count", len(s.find_all("hr")))
print("has_author", "作者|刘浩南" in s.get_text())
print("has_opening_hint", "关注不迷路,加星标更聚焦" in s.get_text())
print("has_brand", "刘浩南丨医疗AI实战派" in s.get_text())
quotes = [len(q.get_text("", strip=True)) for q in s.find_all("blockquote")]
print("blockquote_count", len(quotes))
print("max_quote_chars", max(quotes) if quotes else 0)
print("brand_card_count", len(s.find_all("div", class_="haonan-brand-card")))
print("brand_in_blockquote", any("刘浩南丨医疗AI实战派" in q.get_text() for q in s.find_all("blockquote")))
print("h2_texts", [h.get_text(strip=True) for h in s.find_all("h2")])
print("strong_count", len(s.find_all(["strong", "b"])))
caption_prefixes = ("图注:", "图注:", "图片说明:", "图片说明:", "图片来源:", "图片来源:", "图源:", "图源:")
print("caption_count", sum(1 for t in s.get_text("\n").splitlines() if t.strip().startswith(caption_prefixes)))
PY
Expected for the current style: normal preview mode has h1_count=1 and an author line; final --wechat-body-only mode has h1_count=0 and no in-body author line. In both modes, hr_count=0, max_quote_chars<=300, brand_card_count=1, brand_in_blockquote=False, complete long articles retain centered H2 headings without leading numbers, and all local image references resolve under figures/ordered/. The final body must include the recomputed reading-time/opening hint, dynamic dividers, overview/source images, references, and the final native brand intro.
For polished publishing packages, also expect strong_count to be at least 5 when the source contains editorial emphasis, and caption_count to cover key source images rather than every image. If emphasis drops unexpectedly after formatting, or key source captions disappear, fix the Markdown or formatter output before publishing.
医院科室 AI 现状发布版排版校准(2026-07)
已发表样稿表明,“医院科室 AI 现状”存在两种发布形态:
- 平台化长稿可能达到约 1.1 万可见字符、30+ 图片、4 张宽表、19 分钟阅读;不要在排版阶段删减内容,只需保证阅读提示、ordered 图片、宽表提示、H1=0、blockquote=1、hr=0、missing=0。
- 产品评测稿可能约 6900 可见字符、3 张宽表、多个 H3 产品标题;必须保留 H3,因为它承担手机端扫读功能。
排版验收时,宽表数量不再固定为最多 3 张:平台化稿允许 4 张,但每张表前必须有电脑端阅读提示或同等短提示,表后必须有采购判断。最终品牌块必须是普通品牌卡,不得转换成 blockquote,确保全文只有“本期一句话”一个 blockquote。
开篇演进图后的说明可以是自然叙述段,不强制以“图注:”开头,并保持正常正文样式;但官网截图、监管证据图、未来架构图仍应有带显式图注标记的短图注,说明来源/访问时间或解释用途。