T09 · Insecure Skill Coding Practices
- Location
scripts/fill_from_simplified.py:306- Finding
Default Workflow Silently Removes Tables and Contract Content
- Content
View full analysis
Vulnerability Details
File Location:
scripts/fill_from_simplified.py, lines 306–314, 425–426, and 434–440
Vulnerability Type: Destructive document processing caused by an unsafe default
Risk Level: MediumEvidence
python def remove_contract_and_tables(doc): for t in list(doc.tables): tbl = t._tbl tbl.getparent().remove(tbl) idx = find_anchor_index(doc.paragraphs, ['接待标准', '行程包含', '旅游合同', '补充协议', '合同']) if idx is not None: for p in list(doc.paragraphs[idx:]): e = p._element e.getparent().remove(e)python if itinerary_only: remove_contract_and_tables(doc) doc.save(str(output))python if __name__ == '__main__': ap = argparse.ArgumentParser() ap.add_argument('--template', required=True) ap.add_argument('--content', required=True) ap.add_argument('--output', required=True) ap.add_argument('--keep-contract', action='store_true') args = ap.parse_args() fill_template(args.template, args.content, args.output, itinerary_only=(not args.keep_contract)) print(args.output)Technical Analysis
The default command-line behavior sets
itinerary_onlyto true unless the caller supplies--keep-contract. This invokesremove_contract_and_tables, which performs two broad destructive operations:- It removes every table in the document without checking whether the table contains itinerary information.
- It finds the first paragraph containing any broad contract-related keyword and removes that paragraph and every subsequent paragraph.
This behavior conflicts with the documented requirement in
SKILL.mdto preserve template clauses and terms while replacing only itinerary-related paragraphs. A keyword match can therefore cause unrelated notices, pricing data, signatures, legal provisions, or appendices to disappear from the generated document.Th ...[truncated 1604 chars]
- Remediation
View remediation
Remediation Suggestions
- Preserve all non-itinerary content by default. Make destructive removal an explicit opt-in operation.
- Replace
--keep-contractwith a clearly named flag such as--remove-contract-sections, defaulting to false. - Do not remove every table. Identify itinerary tables through precise structural markers, bookmarks, content controls, or validated section identifiers.
- Define both the start and end boundary of any removable section rather than deleting every paragraph after the first keyword match.
- Require a unique anchor match and abort with a clear error if anchors are missing, duplicated, or ambiguous.
- Emit a summary of removed elements and require confirmation before destructive processing in interactive workflows.
- Save to a new output path and never overwrite the source template.
- Add regression tests using templates that contain unrelated tables, contract clauses, appendices, and repeated keywords.
- Update
SKILL.mdso the documented behavior accurately describes every modification made to the source document.
