{"uid":"cap__6mJ7vLC5vuoJjuhVsFcg","slug":"lineagelint-github-actions-workflow-risk-analyzer-760070ac","name":"LineageLint GitHub Actions Workflow Risk Analyzer","description":"An autonomous paid API accepting USDC on Base mainnet.","url":"https://47-85-47-24.sslip.io/v1/github-actions-workflow-risk","method":"GET","headers":{},"bodySchema":{"type":"object","$schema":"https://json-schema.org/draft/2020-12/schema","required":["input"],"properties":{"input":{"type":"object","required":["type","method"],"properties":{"type":{"type":"string","const":"http"},"method":{"enum":["GET","HEAD","DELETE"],"type":"string"},"queryParams":{"type":"object","properties":{"scenario":{"enum":["privileged-pr-publisher"],"type":"string","description":"Built-in paid GitHub Actions security-review scenario"}}}},"additionalProperties":false},"output":{"type":"object","required":["type"],"properties":{"type":{"type":"string"},"example":{"type":"object","required":["analysis_id","analyzer_version","label","profile","verdict","risk_score","summary","stats","events","untrusted_event_classes","jobs","findings","approval_gates","coverage"],"properties":{"jobs":{"type":"array","items":{"type":"object"}},"label":{"type":"string"},"stats":{"type":"object"},"events":{"type":"array","items":{"type":"string"}},"profile":{"enum":["public","private"],"type":"string"},"summary":{"type":"string"},"verdict":{"enum":["BLOCK","WARN","PASS"],"type":"string"},"coverage":{"type":"object"},"findings":{"type":"array","items":{"type":"object"}},"risk_score":{"type":"integer","maximum":100,"minimum":0},"analysis_id":{"type":"string"},"approval_gates":{"type":"array","items":{"type":"string"}},"analyzer_version":{"type":"string"},"untrusted_event_classes":{"type":"array","items":{"type":"string"}}}}}}}},"responseSchema":{"type":"json","example":{"jobs":[{"index":1,"job_id":"publish","step_count":3,"runner_class":"self-hosted-or-dynamic","has_environment":false,"permission_mode":"write-all","write_scope_count":16,"untrusted_checkout":true,"action_reference_count":2}],"label":"paid-demo:privileged-pr-publisher","stats":{"job_count":1,"line_count":18,"step_count":3,"shell_step_count":1,"findings_by_severity":{"low":0,"high":5,"medium":4,"critical":4},"unpinned_action_count":2,"action_reference_count":2,"write_capable_job_count":1},"events":["pull_request_target"],"profile":"public","summary":"BLOCK: 13 finding(s) across 1 job(s); 9 require resolution or explicit approval.","verdict":"BLOCK","coverage":{"mode":"static-github-actions-workflow-yaml","checks":["GITHUB_TOKEN least privilege","pull_request_target and workflow_run trust boundaries","untrusted-context script injection","action and reusable-workflow immutable pinning","self-hosted runner exposure","secret handling and delegation","OIDC environment protection","workflow artifact trust"],"limitations":["Does not inspect referenced action source, repository settings, environment protection rules, or cloud OIDC trust policies.","Cannot prove whether a commit SHA belongs to the expected upstream action repository.","Static findings do not replace CodeQL workflow scanning, policy enforcement, or a review of every third-party action."],"workflow_executed":false,"github_api_contacted":false,"repository_checked_out":false,"secret_values_returned":false},"findings":[{"code":"job_write_all_permissions","path":"jobs.publish.permissions","message":"The job grants write access to every supported GITHUB_TOKEN scope.","severity":"critical","standard":"github-actions-workflow-syntax","remediation":"Grant only the exact scopes this job needs and separate untrusted processing from privileged work."},{"code":"pull_request_target_untrusted_checkout","path":"jobs.publish.steps[0].with.ref","message":"A privileged pull_request_target job checks out attacker-controlled pull-request code.","severity":"critical","standard":"github-actions-untrusted-checkout","remediation":"Do not check out or execute pull-request head code in pull_request_target; use an unprivileged pull_request workflow."},{"code":"privileged_secret_to_unpinned_action","path":"jobs.publish.steps[2]","message":"A privileged pull_request_target job exposes a secret-bearing input to a non-immutable action.","severity":"critical","standard":"github-actions-supply-chain","remediation":"Remove the secret from this event path and pin any trusted action to a reviewed full commit SHA."},{"code":"write_all_permissions","path":"permissions","message":"The workflow grants write access to every supported GITHUB_TOKEN scope.","severity":"critical","standard":"github-actions-workflow-syntax","remediation":"Replace write-all with explicit least-privilege scopes and isolate privileged jobs."},{"code":"literal_secret_like_workflow_env","path":"env","message":"Workflow-level env contains 1 literal secret-like value(s); names and values are omitted.","severity":"high","standard":"github-actions-secrets","remediation":"Store credentials in GitHub secrets or use OIDC for short-lived cloud access."},{"code":"self_hosted_runner_on_untrusted_trigger","path":"jobs.publish.runs-on","message":"A self-hosted or dynamically selected runner can process attacker-controlled public-repository events.","severity":"high","standard":"github-actions-runner-security","remediation":"Use a GitHub-hosted ephemeral runner, or gate self-hosted execution behind trusted approval and isolated infrastructure."},{"code":"checkout_persists_token_with_untrusted_code","path":"jobs.publish.steps[0].with.persist-credentials","message":"Checkout keeps repository credentials available while untrusted code is present.","severity":"high","standard":"github-actions-untrusted-checkout","remediation":"Set persist-credentials: false and separate privileged operations into a trusted job."},{"code":"untrusted_context_in_inline_script","path":"jobs.publish.steps[1].run","message":"Attacker-controlled GitHub context is interpolated directly into an inline script.","severity":"high","standard":"github-actions-script-injection","remediation":"Assign the expression to an environment variable and consume it as quoted data, or use a purpose-built action."},{"code":"literal_secret_like_step_input","path":"jobs.publish.steps[2]","message":"The step contains 1 literal secret-like input or env value(s); names and values are omitted.","severity":"high","standard":"github-actions-secrets","remediation":"Reference GitHub secrets through a narrowly scoped env/input or use OIDC instead of embedding credentials."},{"code":"oidc_write_without_environment","path":"jobs.publish.permissions.id-token","message":"The job can mint an OIDC token without declaring a protected GitHub environment.","severity":"medium","standard":"github-actions-oidc","remediation":"Bind cloud trust to immutable claims and use an environment with protection rules for deployments."},{"code":"action_not_immutable_pinned","path":"jobs.publish.steps[0].uses","message":"An action or container image is not pinned to an immutable commit SHA or image digest.","severity":"medium","standard":"github-actions-supply-chain","remediation":"Pin repository actions to a reviewed 40-character commit SHA and container actions to sha256 digests."},{"code":"action_not_immutable_pinned","path":"jobs.publish.steps[2].uses","message":"An action or container image is not pinned to an immutable commit SHA or image digest.","severity":"medium","standard":"github-actions-supply-chain","remediation":"Pin repository actions to a reviewed 40-character commit SHA and container actions to sha256 digests."},{"code":"privileged_pull_request_target_trigger","path":"on.pull_request_target","message":"pull_request_target runs in the base repository's privileged context.","severity":"medium","standard":"github-actions-secure-use","remediation":"Use pull_request when possible; otherwise keep the workflow metadata-only and never execute untrusted pull-request code."}],"risk_score":100,"analysis_id":"workflow-a127c053ca9bb4db0bdc","approval_gates":["Resolve or explicitly approve 9 critical/high finding(s) before enabling the workflow.","Demonstrate that attacker-controlled code and data cannot cross into a privileged token, secret, cache, artifact, or runner boundary.","Confirm that every credential is short-lived or narrowly scoped and cannot be emitted to logs or delegated to untrusted code.","Review and immutable-pin 2 external action or reusable-workflow reference(s)."],"analyzer_version":"workflowguard-github-actions/1.0","untrusted_event_classes":["pull_request_target"]}},"example":null,"exampleRequest":null,"tags":["x402"],"displayCostAmount":"0.001","displayCostAsset":"USDC","priceDynamic":false,"priceHint":null,"priceStatus":"priced","priceSource":"probe","requiresHandshake":false,"reviewCount":0,"rating":{"score":"0.00","successRate":"0.00","reviews":0,"stars":null,"state":"unrated"},"availabilityStatus":"unknown","priceObserved":null,"sessionDeposit":null,"pricing":{"kind":"static","summary":"$0.001/call","primary":{"kind":"static","protocol":"x402","network":"base","amountUsd":"0.001","per":"call","confidence":"exact"},"accepted":[{"kind":"static","protocol":"x402","network":"base","amountUsd":"0.001","per":"call","confidence":"exact"}]},"paymentMethods":[{"uid":"pm_h4JIydTlJLtnlsR9kPLiw","protocol":"x402","methodType":"crypto","chain":"base","mode":"charge","costAmount":"0.001","costPer":"request","priority":0,"asset":"0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913","unit":"request","depositMicros":null,"planRef":null}],"brandName":null,"brandSlug":null,"brandBaseUrl":null,"brandDocsUrl":null,"whatItDoes":"Statically analyzes a GitHub Actions workflow for security risks including privilege escalation, untrusted checkouts, and GITHUB_TOKEN misuse, returning a scored verdict (BLOCK/WARN/PASS).","exampleAgentPrompt":"Run a security risk analysis on the privileged-pr-publisher GitHub Actions scenario and tell me if it should be blocked, what the risk score is, and what the most critical findings are.","exampleUseCases":[{"title":"CI/CD pipeline approval gate automation","prompt":"Before we merge this new workflow file, can you analyze it for security risks and let me know if there are any privilege escalation or token misuse issues I should fix first?"},{"title":"Automated security scanning for team onboarding","prompt":"Our team just added a bunch of new GitHub Actions workflows. Run security checks on all of them and flag anything risky so we can remediate before they go live."},{"title":"Incident response for compromised runner","prompt":"We think one of our self-hosted runners might have been compromised. Analyze our workflows to see if any of them are exposed to privilege escalation or untrusted checkout vulnerabilities that an attacker could exploit."}],"resultDescription":"Returns a JSON object with a verdict (BLOCK/WARN/PASS), integer risk score (0-100), human-readable summary, per-job analysis including permission modes and untrusted checkout flags, a findings array with severity/code/remediation for each issue, approval gates, and a coverage report describing what checks were and were not performed.","failureModes":["Invalid or unsupported scenario enum value returns a 400 or validation error","Payment not included or insufficient USDC results in a 402 Payment Required response","Network timeout if the analysis backend is unavailable","Missing required 'input' body property returns schema validation error","Unsupported HTTP method returns 405"],"whenToPreferThis":"Use this endpoint when you need a fast, static security audit of a GitHub Actions workflow — specifically for risks like pull_request_target privilege escalation, write-all GITHUB_TOKEN permissions, unpinned actions, and untrusted checkouts — and want a machine-readable verdict with severity-graded findings. Prefer this over general SAST tools when the focus is GitHub Actions-specific workflow security posture rather than application code vulnerabilities.","instructions":null,"reviewSummary":null,"reviewSummaryHighlights":null,"reviewSummaryConcerns":null,"reviewSummaryGeneratedAt":null,"activationCount":0,"lastUsedAt":null,"lastSuccessfullyRanAt":null,"lastHealthCheckAt":"2026-09-13T18:49:15.340Z","isFirstParty":false}