| name | saas-orchestrator |
| description | Use when wraps the existing 23 security skills into a sellable security-as-a-Service offering — automated pentest reports, compliance checking, client management |
| domain | cybersecurity |
| author | oyi77 |
| license | Apache-2.0 |
| subdomain | general-cybersecurity |
| tags | ["compliance","cybersecurity","orchestrator","penetration-testing","saas","security","threat-defense"] |
| version | 1.0.0 |
Overview
Orchestration layer that packages the existing 23 security skills (bug-hunting, vulnerability-scanner, recon-automation, api-destroyer, auth-killer, cloud-hunter, etc.) into a sellable Security-as-a-Service business. Handles the full client lifecycle: onboarding, scope definition, scan orchestration, report generation, delivery, and billing. Transforms security skills from ad-hoc hunting into a repeatable revenue stream.
Required Tools
- Client Management: Supabase/Firebase for client database, or simple JSON/YAML files
- Scheduling: cron jobs or Temporal/Prefect for scan orchestration
- Reporting: Markdown → PDF (pandoc or md-to-pdf), email delivery (SendGrid)
- Billing: Stripe Subscriptions API or Lemon Squeezy
- Notifications: Slack webhooks, email alerts
- Storage: S3/R2 for scan results, reports, and evidence
- CLI: All existing security skills are invoked via their SKILL.md patterns
Capabilities
- Onboard clients with automated scope definition
- Schedule and orchestrate scans across multiple security skills
- Aggregate findings from multiple skills into unified reports
- Generate professional PDF reports with severity ratings, PoCs, and remediation
- Manage client tiers (basic scan, full pentest, continuous monitoring)
- Handle billing and subscription management
- Track client scan history and trend analysis
- Compliance mapping (OWASP Top 10, CIS Benchmarks, SOC2)
When to Use
Trigger phrases:
-
"saas orchestrator"
-
"Wraps the existing 23 security skills into a sellable security-as-a-Service offe"
-
You want to monetize the existing security skills as a recurring service
-
Clients request security assessments or pentests
-
You need to run the same security checks across multiple targets regularly
-
You want to offer tiered security packages (basic, standard, premium)
-
Building a security consulting or audit business
When NOT to Use
- Task is outside your authorization scope
- You need to implement controls (use implementing-* skills)
- Task is about analysis, not action (use analyzing-* skills)
- You don't have access to target systems
- Task requires compliance expertise (consult professionals)
- Task is about defense, not offense (use defensive skills)
Pseudo Code
This section covers pseudo code for saas orchestrator.
- Ensure all prerequisites are met before proceeding
- Follow the documented workflow steps in sequence
- Record results and any anomalies encountered during this phase
Phase 1: Client Onboarding
client:
name: "Acme Corp"
slug: "acme-corp"
tier: "premium"
contact:
email: "security@acme.com"
name: "John Doe"
billing:
stripe_customer_id: "cus_xxx"
subscription_id: "sub_xxx"
plan: "monthly_premium"
scope:
domains:
- "acme.com"
- "*.acme.com"
- "api.acme.com"
exclude:
- "legacy.acme.com"
- "*.staging.acme.com"
ips:
- "203.0.113.0/24"
apis:
- base_url: "https://api.acme.com/v2"
auth_type: "bearer"
endpoints_file: "endpoints.json"
compliance:
frameworks: ["owasp-top10", "cis-benchmark"]
report_format: "pdf"
delivery: "email"
def onboard_client(client_data):
client_dir = f"clients/{client_data['slug']}"
os.makedirs(client_dir, exist_ok=True)
config = {
'client': client_data,
'scope': define_scope(client_data),
'compliance': get_compliance_requirements(client_data['tier'])
}
write_yaml(f"{client_dir}/config.yaml", config)
subscription = create_stripe_subscription(
customer_email=client_data['contact']['email'],
plan=client_data['tier']
)
schedule_scans(client_data['slug'], client_data['tier'])
send_welcome_email(client_data)
return client_dir
Phase 2: Scan Orchestration by Tier
TIER_SCANS = {
"basic": {
"skills": ["recon-automation", "vulnerability-scanner"],
"frequency": "monthly",
"max_targets": 3
},
"standard": {
"skills": [
"recon-automation", "vulnerability-scanner",
"api-destroyer", "auth-killer"
],
"frequency": "bi-weekly",
"max_targets": 10
},
"premium": {
"skills": [
"recon-automation", "vulnerability-scanner",
"api-destroyer", "auth-killer", "bug-hunting",
"cloud-hunter", "supply-chain-attacker"
],
"frequency": "weekly",
"max_targets": -1
},
"pentest": {
"skills": [
"recon-automation", "vulnerability-scanner",
"api-destroyer", "auth-killer", "bug-hunting",
"cloud-hunter", "fuzz-master", "bug-chain-builder",
"mobile-hacking", "supply-chain-attacker"
],
"frequency": "one-time",
: -
}
}
():
config = load_client_config(client_slug)
tier = config[][]
scan_config = TIER_SCANS[tier]
results = {
: client_slug,
: tier,
: datetime.utcnow().isoformat(),
: [],
: {}
}
recon_result = invoke_skill(
skill=,
targets=config[][],
output_dir=
)
results[][] = recon_result
skill_name scan_config[]:
skill_name == :
skill_result = invoke_skill(
skill=skill_name,
targets=recon_result.get(, config[]),
output_dir=
)
results[][skill_name] = skill_result
finding skill_result.get(, []):
results[].append({
: skill_name,
: finding[],
: finding[],
: finding[],
: finding.get(),
: finding.get()
})
results[] = deduplicate_findings(results[])
results[].sort(key= f: severity_order(f[]))
results[] = datetime.utcnow().isoformat()
results[] = generate_summary(results)
save_results(client_slug, results)
results
():
os.makedirs(output_dir, exist_ok=)
skill_def = load_skill(skill)
skill_def.execute(targets=targets, output_dir=output_dir)
Phase 3: Report Generation
def generate_report(client_slug, results):
"""Generate professional security assessment report."""
config = load_client_config(client_slug)
report = f"""---
title: "Security Assessment Report"
client: "{config['client']['name']}"
date: "{datetime.now().strftime('%Y-%m-%d')}"
tier: "{config['client']['tier']}"
---
# Security Assessment Report
**Client:** {config['client']['name']}
**Date:** {datetime.now().strftime('%B %d, %Y')}
**Assessment Type:** {config['client']['tier'].title()}
**Scope:** {', '.join(config['scope']['domains'])}
## Executive Summary
{generate_executive_summary(results)}
## Risk Overview
| Severity | Count |
|----------|-------|
| Critical | {count_by_severity(results, 'critical')} |
| High | {count_by_severity(results, 'high')} |
| Medium | {count_by_severity(results, 'medium')} |
| Low | {count_by_severity(results, 'low')} |
| Info | {count_by_severity(results, 'info')} |
## Findings
"""
for i, finding in enumerate(results['findings'], 1):
report += f"""### {i}. {finding['title']}
**Severity:** {finding['severity'].upper()}
**Category:** {finding['skill']}
**CVSS Score:** {finding.get('cvss', 'N/A')}
**Description:**
{finding['description']}
**Evidence:**
{finding.get('evidence', 'No direct evidence captured')}
**Remediation:**
{finding.get('remediation', 'Contact security team for remediation guidance')}
---
"""
# Compliance mapping section
if config['compliance']['frameworks']:
report += generate_compliance_section(results, config['compliance']['frameworks'])
# Save as markdown and convert to PDF
report_path = f"clients/{client_slug}/reports/{datetime.now().strftime('%Y-%m-%d')}-assessment.md"
write_file(report_path, report)
# Convert to PDF
pdf_path = report_path.replace('.md', '.pdf')
subprocess.run(['pandoc', report_path, '-o', pdf_path,
'--pdf-engine=wkhtmltopdf',
'-V', 'margin-top=20mm'])
return pdf_path
Phase 4: Delivery & Billing
def deliver_report(client_slug, report_path):
"""Deliver report to client and handle billing."""
config = load_client_config(client_slug)
send_email(
to=config['client']['contact']['email'],
subject=f"Security Assessment Report - {datetime.now().strftime('%B %Y')}",
body=f"Your {config['client']['tier']} security assessment is complete. See attached report.",
attachments=[report_path]
)
s3_key = f"reports/{client_slug}/{os.path.basename(report_path)}"
upload_to_s3(report_path, s3_key)
if config['client']['tier'] == 'pentest':
stripe.InvoiceItem.create(
customer=config['billing']['stripe_customer_id'],
amount=get_tier_price(config['client']['tier']),
currency='usd',
description=f"Security Assessment - {datetime.now().strftime('%B %Y')}"
)
notify_slack(
f"Report delivered to {config['client']['name']} "
f"({count_findings(results)} findings, "
f"{count_critical(results)} critical)"
)
():
frequency = TIER_SCANS[tier][]
frequency == :
cron =
frequency == :
cron =
frequency == :
cron =
:
add_cron_job(
cron=cron,
command=,
job_id=
)
Phase 5: Client Dashboard Data
def get_client_dashboard(client_slug):
"""Generate dashboard data for client portal."""
config = load_client_config(client_slug)
history = load_scan_history(client_slug)
return {
"client": config['client']['name'],
"tier": config['client']['tier'],
"last_scan": history[-1]['completed_at'] if history else None,
"next_scan": get_next_scan_time(client_slug),
"trend": {
"total_findings": [h['summary']['total'] for h in history[-6:]],
"critical_findings": [h['summary']['critical'] for h in history[-6:]],
"months": [h['completed_at'][:7] for h in history[-6:]]
},
"current_risk_score": calculate_risk_score(history[-1] if history else None),
"compliance_status": get_compliance_status(client_slug)
}
Error Handling
| Error | Cause | Fix |
|---|
| Skill invocation timeout | Target too large or skill hung | Set per-skill timeout (30min default), retry once |
| No findings from skill | Wrong targets or skill misconfigured | Validate target format, check skill dependencies |
| PDF generation fails | pandoc not installed or template error | brew install pandoc wkhtmltopdf, verify markdown |
| Stripe billing fails | Invalid customer ID | Verify Stripe customer exists, check API key |
| Report delivery fails | Email bounce or S3 permissions | Check email validity, verify S3 bucket policy |
| Duplicate findings | Same vuln found by multiple skills | Deduplicate by title+target+port before reporting |
| Client scope exceeds tier | Too many targets for plan | Enforce target limits, suggest tier upgrade |
Common Patterns
- Follow the principle of least privilege — use the minimum permissions needed for each task
- Document everything — maintain logs of all actions, configurations, and findings
- Verify before acting — confirm assumptions about the environment before making changes
- Automate repetitive steps — script common workflows to reduce human error
Tiered Pricing Structure
plans:
basic:
price_id: "price_basic_monthly"
amount: 49900
features: ["monthly_scan", "basic_report", "email_support"]
standard:
price_id: "price_standard_monthly"
amount: 149900
features: ["biweekly_scan", "full_report", "api_testing", "slack_support"]
premium:
price_id: "price_premium_monthly"
amount: 499900
features: ["weekly_scan", "full_report", "all_skills", "priority_support", "compliance"]
pentest:
price_id: "price_pentest_onetime"
amount: 999900
features: ["full_pentest", "all_skills", "manual_review", "executive_report"]
Finding Severity Mapping
SEVERITY_CVSS = {
"critical": (9.0, 10.0),
"high": (7.0, 8.9),
"medium": (4.0, 6.9),
"low": (0.1, 3.9),
"info": (0.0, 0.0)
}
def map_severity(cvss_score):
for severity, (low, high) in SEVERITY_CVSS.items():
if low <= cvss_score <= high:
return severity
return "info"
Compliance Report Template
def generate_compliance_section(results, frameworks):
section = "## Compliance Mapping\n\n"
for framework in frameworks:
controls = load_framework_controls(framework)
section += f"### {framework.upper()}\n\n"
section += "| Control | Status | Findings |\n|---------|--------|----------|\n"
for control in controls:
related = find_related_findings(results, control)
status = "PASS" if not related else "FAIL"
section += f"| {control['id']} | {status} | {len(related)} |\n"
return section
Red Flags
- Performing actions without explicit written authorization from the asset owner
- Testing against production systems without a defined scope and rules of engagement
- Exceeding the authorized scope of the engagement
- Leaving persistent access mechanisms without explicit approval
- Causing denial-of-service on production systems during testing
Verification
- All steps executed successfully against a test environment before production use
- Output documented with screenshots or logs demonstrating expected behavior
- All exploited vulnerabilities documented with reproduction steps
- Scope boundaries confirmed — only authorized targets were tested
- Remediation recommendations included for every finding
Process
- Analyze the task requirements
- Apply domain expertise
- Verify output quality
Anti-Rationalization Table
| Rationalization | Reality |
|---|
| "We are too small to be targeted" | Automated attacks target everyone. Size does not matter. |
| "Security slows us down" | A breach slows you down 100x more. Build security in from the start. |
| "We will fix it after launch" | Vulnerabilities in production are exploited within hours. Fix before deploy. |