diff --git a/languageserver/src/context-providers/secrets.ts b/languageserver/src/context-providers/secrets.ts index c2cb8f2..16bf2d3 100644 --- a/languageserver/src/context-providers/secrets.ts +++ b/languageserver/src/context-providers/secrets.ts @@ -16,13 +16,24 @@ export async function getSecrets( defaultContext: DescriptionDictionary | undefined, mode: Mode ): Promise { + const secretsContext = defaultContext || new DescriptionDictionary(); + const permission = await getRepoPermission(octokit, cache, repo); if (permission === "none") { - const secretsContext = defaultContext || new DescriptionDictionary(); secretsContext.complete = false; return secretsContext; } + const eventsConfig = workflowContext?.template?.events; + if (eventsConfig?.workflow_call) { + // Unpredictible secrets may be pased in via a workflow_call trigger + secretsContext.complete = false; + // Exit early for validation mode or if workflow_call is the only trigger + if (mode === Mode.Validation || Object.keys(eventsConfig).length == 1) { + return secretsContext; + } + } + let environmentName: string | undefined; if (workflowContext?.job?.environment) { if (isString(workflowContext.job.environment)) { @@ -39,16 +50,6 @@ export async function getSecrets( } } - const secretsContext = defaultContext || new DescriptionDictionary(); - - // Exit early if workflow_call is the only trigger - if (mode === Mode.Completion) { - const eventsConfig = workflowContext?.template?.events; - if (eventsConfig?.workflow_call && Object.keys(eventsConfig).length == 1) { - return secretsContext; - } - } - const secrets = await getRemoteSecrets(octokit, cache, repo, environmentName); // Build combined map of secrets diff --git a/languageservice/src/context-providers/secrets.ts b/languageservice/src/context-providers/secrets.ts index af80858..56b5485 100644 --- a/languageservice/src/context-providers/secrets.ts +++ b/languageservice/src/context-providers/secrets.ts @@ -11,10 +11,12 @@ export function getSecretsContext(workflowContext: WorkflowContext, mode: Mode): description: getDescription("secrets", "GITHUB_TOKEN") }); - if (mode === Mode.Completion) { - const eventsConfig = workflowContext?.template?.events; - if (eventsConfig?.workflow_call?.secrets) { - for (const [name, value] of Object.entries(eventsConfig.workflow_call.secrets)) { + const eventsConfig = workflowContext?.template?.events; + if (eventsConfig?.workflow_call) { + // Unpredictible secrets may be pased in via a workflow_call trigger + d.complete = false; + if (mode === Mode.Completion) { + for (const [name, value] of Object.entries(eventsConfig.workflow_call.secrets || {})) { d.add(name, new StringData(""), value.description); } } diff --git a/languageservice/src/validate.expressions.test.ts b/languageservice/src/validate.expressions.test.ts index 29b2f6f..747bb58 100644 --- a/languageservice/src/validate.expressions.test.ts +++ b/languageservice/src/validate.expressions.test.ts @@ -98,6 +98,25 @@ jobs: ]); }); + it("no secret validation with workflow_call", async () => { + const input = ` +on: + workflow_call: + secrets: + my_secret: +env: + my_secret: \${{ secrets.my_secret }} + secret: \${{ secrets.secret-not-exist }} +jobs: + build: + runs-on: ubuntu-latest + steps: + - run: echo`; + + const result = await validate(createDocument("wf.yaml", input)); + expect(result).toEqual([]); + }); + it("access invalid nested context field", async () => { const result = await validate( createDocument(