Back to skill

Security audit

LegiScan Bill Search

Security checks for vulnerabilities and agentic risk

Overview

This skill is a straightforward LegiScan bill-search helper, with a real but limited API-key handling risk.

Before installing, use a dedicated revocable LegiScan API key, avoid logging request URLs, and be aware that your configured key, state, and search keywords are sent to LegiScan. Scheduling it with cron is a user choice and should be done only at a frequency compatible with your API quota.

Vulnerability Patterns
  • Insecure Skill Coding PracticesFinds exploitable flaws such as hardcoded secrets or command injection
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • Embedded Malicious CodeShips malicious scripts inside the skill and executes them locally
Findings (1)

T09 · Insecure Skill Coding Practices

Warning
Location
search.py:12
Finding

API Credential Exposed in Request URLs

Content
View full analysis
Remediation
View remediation
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Taint TrackingDirect Taint Flow, Variable-Mediated Taint Flow, Credential Exfiltration Chain
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
Findings (4)

Tainted flow: 'url' from os.environ.get (line 62, credential/environment) → requests.get (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Content

Scanner excerpt · search.py (reported line 15)May include surrounding context.

python
query_param = f'"{q}"' if ' ' in q and not q.startswith('"') else q
        url = f"https://api.legiscan.com/?key={api_key}&op=getSearch&state={state}&query={query_param}"
        try:
            response = requests.get(url).json()
            if response.get('status') == 'OK':
                search_results = response.get('searchresult', {})
                for key, bill in search_results.items():

Tainted flow: 'url' from os.environ.get (line 62, credential/environment) → requests.get (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Content

Scanner excerpt · search.py (reported line 35)May include surrounding context.

python
def get_bill_details(api_key, bill_id):
    url = f"https://api.legiscan.com/?key={api_key}&op=getBill&id={bill_id}"
    try:
        res = requests.get(url).json()
        if res.get('status') == 'OK':
            return res.get('bill')
    except Exception as e:

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · search.py (reported line 13)May include surrounding context.

python
for q in queries:
        # Ensure query is properly quoted if it contains spaces
        query_param = f'"{q}"' if ' ' in q and not q.startswith('"') else q
        url = f"https://api.legiscan.com/?key={api_key}&op=getSearch&state={state}&query={query_param}"
        try:
            response = requests.get(url).json()
            if response.get('status') == 'OK':

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · search.py (reported line 33)May include surrounding context.

python
for q in queries:
        # Ensure query is properly quoted if it contains spaces
        query_param = f'"{q}"' if ' ' in q and not q.startswith('"') else q
        url = f"https://api.legiscan.com/?key={api_key}&op=getSearch&state={state}&query={query_param}"
        try:
            response = requests.get(url).json()
            if response.get('status') == 'OK':

Static analysis

No suspicious patterns detected.