Skip to content

feature: functions can now declare lifecycle hooks#1915

Open
wandamora wants to merge 3 commits into
masterfrom
morawand-lifecycle-hook-api
Open

feature: functions can now declare lifecycle hooks#1915
wandamora wants to merge 3 commits into
masterfrom
morawand-lifecycle-hook-api

Conversation

@wandamora

Copy link
Copy Markdown
Contributor

Description

This PR adds support for declaring codebase lifecycle hooks in the Firebase Functions SDK. Developers can now register actions (afterInstall and afterUpdate) that are automatically executed post-deployment.

Summary of Changes

1. Hook Registrations (src/lifecycle/index.ts)

  • Added new top-level entrypoints and types under firebase-functions/lifecycle:
    • afterInstall(action: LifecycleAction): Registers a hook to run when resources in the codebase are deployed for the first time.
    • afterUpdate(action: LifecycleAction): Registers a hook to run when resources in the codebase are updated.
  • Supported action types:
    • task: Triggers a task queue function with an optional payload body.
    • call: Calls a function (callable trigger) with optional params.
    • http: Triggers a HTTP endpoint via request url/function, method, and body.
  • Ensures only one instance of afterInstall and afterUpdate can be registered per codebase at runtime.

2. Stack Manifest Parsing (src/runtime/loader.ts, src/runtime/manifest.ts)

  • Added ManifestLifecycleAction and updated ManifestStack types to include the lifecycleHooks field.
  • Updated loadStack inside loader.ts to capture any declared lifecycle hooks from global symbols during function discovery, mapping them into the compiled JSON/wire format returned to firebase-tools.
  • Updated stackToWire serialization helper to recursively resolve CEL expressions and reset values inside lifecycleHooks properties.

3. Tests

  • Created spec/lifecycle/lifecycle.spec.ts to test hook registration and duplicate hook prevention.
  • Added tests in spec/runtime/loader.spec.ts verifying that afterInstall and afterUpdate declarations are correctly discovered and serialized into the ManifestStack.

Code sample

export const runInitialSetup = onTaskDispatched(async (request) => {
  await performDatabaseSeeding(request.data);
});

// The CLI automatically discovers this call and queues the task after first-time deploy
afterInstall({
  task: {
    function: "runInitialSetup",
    body: { data: "default_catalog" }
  }
});

@gemini-code-assist gemini-code-assist Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request introduces support for post-deployment lifecycle hooks (afterInstall and afterUpdate) by adding a new lifecycle module, updating the manifest stack loader to capture these hooks, and exposing the module exports in package.json. The review feedback highlights a correctness issue in src/runtime/loader.ts where falsy but valid JSON values (such as 0 or false) are incorrectly omitted during serialization, and suggests using TypeScript union types in src/lifecycle/index.ts to enforce mutually exclusive properties at compile-time.

Comment thread src/runtime/loader.ts
Comment thread src/lifecycle/index.ts Outdated
@wandamora wandamora force-pushed the morawand-lifecycle-hook-api branch from 02d17b8 to 9489ef4 Compare June 25, 2026 20:06
@wandamora wandamora requested a review from inlined June 25, 2026 21:31
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants