Back to skill

Security audit

Zillow Property Data API - For Sale, Rent, Sold, Price History

Security checks for vulnerabilities and agentic risk

Overview

This skill is a disclosed Zillow data API helper that sends user-directed property queries to Scavio and does not show hidden persistence, privilege escalation, or unrelated data handling.

Use a revocable Scavio API key with spending limits if possible. Prefer the direct HTTPS examples if you do not want to install third-party SDK packages, and remember that property and agent queries are sent to Scavio's API service.

Vulnerability Patterns
  • Insecure DependenciesIntroduces malicious components through unsafe dependency sources
  • 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)

T08 · Insecure Dependencies

Warning
Location
SKILL.md:220
Finding

Unaudited Third-Party SDKs Can Access the API Credential

Content
View full analysis

Vulnerability Details

File Location: SKILL.md:220-240
Vulnerability Type: Third-party dependency and supply-chain exposure
Risk Level: Medium

The Skill recommends installing and executing Scavio SDK packages from both the Python Package Index and the npm registry:

bash
pip install scavio==0.15.0
python
from scavio import ScavioClient

client = ScavioClient()  # reads SCAVIO_API_KEY

listings = client.zillow.search("Austin, TX", listing_status="for_sale", beds_min=3)
prop = client.zillow.property(listings["data"]["properties"][0]["zpid"])
agent = client.zillow.agent_reviews("jane-smith")
bash
npm install scavio@0.15.0
javascript
import { Scavio } from "scavio";

const client = new Scavio(); // reads SCAVIO_API_KEY
const listings = await client.zillow.search({ location: "Austin, TX", listing_status: "for_rent", max_price: 2500 });
const agent = await client.zillow.agentReviews({ screen_name: "jane-smith" });

Technical Analysis

The package contents are not included in the audited project, so their installation hooks and runtime behavior cannot be verified from the Skill package. Both SDKs are explicitly allowed to read SCAVIO_API_KEY. Consequently, any malicious or compromised code in the selected package versions would execute within the user's process and could access that credential.

Pinning the packages to version 0.15.0 reduces unintended version drift but does not provide cryptographic integrity verification. The instructions do not specify package hashes, npm integrity values, provenance verification, install-script restrictions, or sandboxing.

The direct HTTPS examples elsewhere in SKILL.md send the bearer credential only to the declared https://api.scavio.dev service. That network flow is disclosed and necessary for the Skill's functionality; no unrelated credential-exfiltration destination was identified in the audited file. The risk ide ...[truncated 1545 chars]

Remediation
View remediation

Remediation Suggestions

  1. Prefer the documented direct HTTPS API calls, which avoid executing additional SDK code.
  2. If the SDKs are retained, verify package ownership, release provenance, and source repositories before recommending installation.
  3. Provide lockfiles with cryptographic hashes or integrity metadata and require hash-verified installation.
  4. Audit the exact package versions and all transitive dependencies before deployment.
  5. Disable package installation scripts where practical, such as with npm's --ignore-scripts, after confirming that the package does not legitimately require them.
  6. Install and execute dependencies in an isolated, unprivileged environment with access only to the required API credential and network destination.
  7. Use a narrowly scoped, revocable API key with spending or usage limits, and rotate it immediately if dependency compromise is suspected.
  8. Restrict outbound traffic so the runtime can communicate only with the documented Scavio API endpoint.
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
Findings (5)

External Transmission

Medium
Category
Data Exfiltration
Confidence
70% 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 · SKILL.md (reported line 134)May include surrounding context.

md
HEADERS = {"Authorization": f"Bearer {API_KEY}"}

# 1. Homes for sale - use the CITY name, not a ZIP, when filtering
listings = requests.post(f"{BASE}/api/v1/zillow/search", headers=HEADERS,
    json={"location": "Austin, TX", "listing_status": "for_sale",
          "min_price": 400000, "max_price": 750000,
          "beds_min": 3, "baths_min": 2, "sort": "newest"}).json()

External Transmission

Medium
Category
Data Exfiltration
Confidence
70% 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 · SKILL.md (reported line 146)May include surrounding context.

md
HEADERS = {"Authorization": f"Bearer {API_KEY}"}

# 1. Homes for sale - use the CITY name, not a ZIP, when filtering
listings = requests.post(f"{BASE}/api/v1/zillow/search", headers=HEADERS,
    json={"location": "Austin, TX", "listing_status": "for_sale",
          "min_price": 400000, "max_price": 750000,
          "beds_min": 3, "baths_min": 2, "sort": "newest"}).json()

External Transmission

Medium
Category
Data Exfiltration
Confidence
70% 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 · SKILL.md (reported line 142)May include surrounding context.

md
zpid = listings["data"]["properties"][0]["zpid"]

# 2. Full property record
prop = requests.post(f"{BASE}/api/v1/zillow/property", headers=HEADERS,
    json={"zpid": zpid}).json()

# 3. Rentals: min_price / max_price are MONTHLY RENT here

External Transmission

Medium
Category
Data Exfiltration
Confidence
70% 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 · SKILL.md (reported line 151)May include surrounding context.

md
zpid = listings["data"]["properties"][0]["zpid"]

# 2. Full property record
prop = requests.post(f"{BASE}/api/v1/zillow/property", headers=HEADERS,
    json={"zpid": zpid}).json()

# 3. Rentals: min_price / max_price are MONTHLY RENT here

External Transmission

Medium
Category
Data Exfiltration
Confidence
70% 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 · SKILL.md (reported line 155)May include surrounding context.

json={"zpid": "https://www.zillow.com/apartments/austin-tx/the-quincy/5XjKpQ/"}).json()

5. An AGENT's profile and reviews (not a property)

agent = requests.post(f"{BASE}/api/v1/zillow/reviews", headers=HEADERS, json={"screen_name": "jane-smith"}).json()

text