T09 · Insecure Skill Coding Practices
- Location
scripts/query_valueset.py:46- Finding
Unrestricted terminology server allows sensitive query disclosure and unintended network access
- Content
View full analysis
- Remediation
View remediation
Security audit
Security checks for vulnerabilities and agentic risk
This healthcare questionnaire helper is mostly purpose-aligned, but it needs review because one lookup script can send clinical terms to arbitrary servers and the dependency install is not pinned.
Review and constrain network use before installing. Keep terminology lookups limited to trusted HTTPS FHIR terminology servers, avoid putting patient-identifying details in search terms, and consider pinning dependencies before running setup.sh. Generated questionnaire and CodeSystem files are user-directed local outputs, not hidden persistence.
scripts/query_valueset.py:46Unrestricted terminology server allows sensitive query disclosure and unintended network access
requirements.txt:1Unpinned dependency installation creates a supply-chain and reproducibility risk
The description emphasizes questionnaire-definition assistance and terminology lookup from official coding APIs for LOINC and SNOMED CT. The actual script serves a different purpose: generating reusable custom CodeSystem and ValueSet FHIR resources under a proprietary Welshare URL base. This is a materially different primary function from code lookup, and it introduces undeclared behavior of generating and saving local resource files. There is no evidence of API access, official terminology lookup, or processing of requirement ideation docs. Therefore the code chunk does not accurately match the declared description.
The description emphasizes generation of FHIR questionnaire definitions from plain-text requirement ideation documents and code lookup utilities for LOINC and SNOMED CT via official APIs. This code chunk instead serves a different purpose: post hoc inspection of an existing FHIR Questionnaire to extract and summarize LOINC codings. While optional validation may rely on a separate LOINC search helper, the core behavior is extraction/reporting, not questionnaire creation or broad terminology lookup. The mismatch is material because the primary function and supported terminologies differ from the declared description.
The description partially overlaps with the code because both concern FHIR terminology support and questionnaire construction. However, this code chunk specifically handles LOINC answer lists and ValueSet expansion/search, and can emit a Questionnaire item template. It does not process plain requirement ideation documents, and it does not implement SNOMED CT or broader clinical concept lookup for conditions, findings, observations, medications, or procedures. The external resource usage is a generic FHIR terminology server (tx.fhir.org), not obviously the 'official coding APIs' claimed. Therefore the supplied code does not fully and accurately match the declared description.
The description emphasizes questionnaire generation support from ideation documents and terminology lookup against LOINC/SNOMED CT APIs. The provided code does something materially different: it validates existing FHIR Questionnaire JSON files using a local schema and extra semantic rules. There is no code for parsing plain requirements, generating questionnaire definitions, calling external coding APIs, or looking up LOINC/SNOMED CT codes. While validation is related to FHIR questionnaires, it is an undeclared primary capability compared with the stated purpose, so this is a clear description-behavior mismatch.
Skill contains instructions that could directly expose system prompts, internal rules, or hidden instructions to users or external parties.
| prefix | 0..1 | string | Display prefix (e.g., "1.", "a)") |
| text | 0..1 | string | Primary text for the item |
| type | 1..1 | code | Type of item (see Item Types below) |
| enableWhen | 0..* | BackboneElement | Conditional display rules |
| enableBehavior | 0..1 | code | all \| any (default: all) |
| required | 0..1 | boolean | Whether item must be answered |
| repeats | 0..1 | boolean | Whether item can repeat |
The skill documentation advertises and instructs use of scripts that perform network access and local file reads/writes, but it does not declare any explicit tool scope such as permissions or allowed-tools. This creates an execution-governance gap where an agent may invoke broader capabilities than a reviewer or policy engine expects, increasing the risk of unintended file modification or outbound requests.
This markdown file provides example questionnaires that request personally identifiable information and health data, including name, date of birth, address, depression screening responses, medical history, allergies, surgeries, family history, tobacco use, and alcohol consumption. Under the markdown-specific warning rule, the description should disclose that these patterns involve sensitive personal and medical data and should be used with appropriate privacy and consent safeguards, but no such warning appears in the file.
Data from a source is assigned to a variable that is later passed to a sink, creating a variable-mediated taint flow.
codesystem_file = output_dir / f"CodeSystem-{id}.json"
valueset_file = output_dir / f"ValueSet-vs-{id}.json"
with open(codesystem_file, 'w') as f:
json.dump(codesystem, f, indent=2)
with open(valueset_file, 'w') as f:
Data from a source is assigned to a variable that is later passed to a sink, creating a variable-mediated taint flow.
with open(codesystem_file, 'w') as f:
json.dump(codesystem, f, indent=2)
with open(valueset_file, 'w') as f:
json.dump(valueset, f, indent=2)
# Success message
This is a JSON manifest-type file, so vague-trigger checks apply. The description and purpose describe a generic 'comprehensive questionnaire template' and 'starting point for complex clinical questionnaires' without any explicit scope, invocation conditions, or exclusion criteria, which could make the skill/template applicable in overly broad contexts.
This JSON schema includes a natural-language language property described as the base language of the resource, but it does not indicate that language selection should be user-driven or explicitly opted into. Because SQP-3 applies to all file types and covers language/locale policy concerns in natural-language text or config values, this is a mild policy concern in a schema that constrains locale-bearing content.
The dependency is specified as a lower-bounded range (jsonschema>=4.0.0) rather than being pinned to an exact version, which makes builds non-reproducible and can silently pull in newly released versions with breaking changes or supply-chain issues. In a skill that may run scripts and process healthcare-related questionnaire definitions, unexpected dependency updates could affect reliability and, in the worst case, introduce vulnerable transitive code into the environment.
jsonschema>=4.0.0
The script sends the user's search term directly to an external terminology server (tx.fhir.org) without any explicit notice or consent at runtime. In a healthcare context, free-text queries may contain sensitive clinical terms or even patient-related information, so this creates a real data exposure/privacy risk even though the transmission is over HTTPS and appears functionally intended.
No suspicious patterns detected.