Skip to content

Commit c6f102f

Browse files
joehanfredzqmjrothfederJamie Rothfederyuchenshi
authored
v15 (#9604)
* Update next to match master (#9313) * Remove overrides that diverge the test configuration from the build configuration. (#9300) Co-authored-by: Jamie Rothfeder <rothbutter@google.com> * Fix misleading typing for options.json. (#9275) * feat(dataconnect): Add confirmation for Gemini schema generation (#9282) * feat(dataconnect): add confirmation for Gemini schema generation Instead of directly asking for an app description to generate a schema with Gemini, this change first asks the user to confirm if they want to use Gemini. If the user confirms, it then prompts for the app description with a default value of "an app for ${setup.projectId}". * prompts * changelog * m * feedback * typo * metrics * Update index.ts --------- Co-authored-by: google-labs-jules[bot] <161369871+google-labs-jules[bot]@users.noreply.github.com> --------- Co-authored-by: Jamie Rothfeder <jamie.rothfeder@gmail.com> Co-authored-by: Jamie Rothfeder <rothbutter@google.com> Co-authored-by: Yuchen Shi <yuchenshi@google.com> Co-authored-by: google-labs-jules[bot] <161369871+google-labs-jules[bot]@users.noreply.github.com> * BREAKING: clean up monkey patching in functions emulator runtime (#9402) 1. Removed `functions.config()` Polyfill Removed initializeRuntimeConfig() from `src/emulator/functionsEmulatorRuntime.ts`. This function manually read `.runtimeconfig.json` and set `CLOUD_RUNTIME_CONFIG` env var to polyfill the logic for old clients of the Functions SDK. Functions SDK has included this feature for more than 5+ years now. 2. Removed Callable Auth Monkey Patches Removed wrapCallableHandler from src/emulator/functionsEmulatorRuntime.ts. that handled manual auth header swapping logic in src/emulator/functionsEmulator.ts. We now rely on the SDK's built-in skipTokenVerification feature shipped since 3.16.0. 3. Bumped Minimum SDK Version Increased minimum required firebase-functions version from 3.15.1 to 3.16.0 (launched 4+ years ago) in `src/emulator/functionsEmulatorRuntime.ts`. This ensures users have an SDK that supports skipTokenVerification and likely handles .runtimeconfig.json loading correctly in emulation. * BREAKING: hide functions:config:* commands by default (#9340) We'll gate all mutating functions:config:* commands behind the new `legacyRuntimeConfigCommands` experiment. We'll keep functions:config:{get,export} available for inspection. Includes some minor refactoring to align deprecation message across all surfaces. ```shell $ firebase functions:config:set FOO=bar Error: DEPRECATION NOTICE: Action required before March 2026 The functions.config() API and the Cloud Runtime Config service are deprecated. Deploys that rely on functions.config() will fail once Runtime Config shuts down in March 2026. The legacy functions:config:* CLI commands are deprecated and will be removed before March 2026. Migrate configuration to the Firebase Functions params APIs: import { defineJsonSecret } from "firebase-functions/params"; const config = defineJsonSecret("RUNTIME_CONFIG"); exports.myFunction = functions .runWith({ secrets: [config] }) .https.onRequest((req, res) => { const apiKey = config.value().service.key; // ... }); To convert existing runtime config values, try the interactive migration command: firebase functions:config:export Learn more: https://firebase.google.com/docs/functions/config-env#migrate-config To run this legacy command temporarily, run the following command and try again: firebase experiments:enable legacyRuntimeConfigCommands ``` * BREAKING: Rewrite functions:config:export command (#9341) Target the new defineJsonSecret API as migration target for functions.config() usage. The new API is a simpler migration target for existing functions.config() use cases. Example flow: ```shell $ firebase functions:config:export i This command retrieves your Runtime Config values (accessed via functions.config()) and exports them as a Secret Manager secret. i Fetching your existing functions.config() from danielylee-90... ✔ Fetched your existing functions.config(). i Configuration to be exported: ⚠ This may contain sensitive data. Do not share this output. { <CONFIG> } ✔ What would you like to name the new secret for your configuration? RUNTIME_CONFIG ✔ Created new secret version projects/XXX/secrets/RUNTIME_CONFIG/versions/1 i To complete the migration, update your code: // Before: const functions = require('firebase-functions'); exports.myFunction = functions.https.onRequest((req, res) => { const apiKey = functions.config().service.key; // ... }); // After: const functions = require('firebase-functions'); const { defineJsonSecret } = require('firebase-functions/params'); const config = defineJsonSecret("RUNTIME_CONFIG"); exports.myFunction = functions .runWith({ secrets: [config] }) // Bind secret here .https.onRequest((req, res) => { const apiKey = config.value().service.key; // ... }); i Note: defineJsonSecret requires firebase-functions v6.6.0 or later. Update your package.json if needed. i Then deploy your functions: firebase deploy --only functions ``` * feat(firestore): return listBackupsResponse from firestore:backups:list --json (#9392) The `firestore:backups:list --json` command now returns the full `listBackupsResponse` object instead of just the `backups` array. This provides more information to the user, including a list of unreachable locations. * Break java (#9451) * error out java version below 21 * error out java version below 21 * error out java version below 21 * update formatting * Remove duplicate error message * Update CHANGELOG.md to include breaking change * update CI to java 21 * Add setup-java action to integration --------- Co-authored-by: Joe Hanley <joehanley@google.com> * Removing support for .bolt rules (#9339) * Removing support for .bolt rules * Changelog * Merging in master * Stop following symlinks when archiving directories (#9284) * Stop following symlinks when archiving directories * Update exfil PR (#9289) * Fix filter for symlinks * Fine. Preserve ordering at the cost of readability * Format * Progress on new approach * Remove unused tar path, fix up zip path to ignore symlinks, add test * More tests * Actually good for real this time ; --------- Co-authored-by: Thomas Bouldin <inlined@users.noreply.github.com> * Remove --open-sesame and --close-sesame (#9532) * Lazy load commands (#9519) * Refactor command loading to be lazy - Updated `src/commands/index.ts` to make `loadCommand` return a lazy runner that only `require`s and registers the command when executed or explicitly loaded. - Updated `src/index.ts` to handle lazy loading in the catch-all command handler by traversing the `client` object and loading the matching command before re-parsing arguments. - Updated `src/bin/cli.ts` to load all commands when no arguments are provided (global help), ensuring the help text is fully populated. - Added cycle detection to the `loadAll` logic to handle circular references in the `client` object. * Refactor command loading to be lazy - Updated `src/commands/index.ts` to make `loadCommand` return a lazy runner that only `require`s and registers the command when executed or explicitly loaded. - Updated `src/index.ts` to handle lazy loading in the catch-all command handler by traversing the `client` object and loading the matching command before re-parsing arguments. - Updated `src/bin/cli.ts` to load all commands when no arguments are provided (global help), ensuring the help text is fully populated. - Added cycle detection to the `loadAll` logic to handle circular references in the `client` object. - Added `scripts/benchmark_load.ts` to measure command load time. * Fix help command as well * Get rid of flawed benchmark test; * Clean up unused vars * Typeguards for style points * Move typeguard * Better types * CHANGELOG * More type cleanup * No anys * Fixing getCommand * Bump timeout? * 20s is better * Removing extra timing code * format --------- Co-authored-by: google-labs-jules[bot] <161369871+google-labs-jules[bot]@users.noreply.github.com> * BREAKING: Enforce strict timeout validation for functions (#9540) * feat: enforce strict timeout validation for functions * nit: run formatter * docs: add changelog entry for timeout validation * refactor: optimize timeout validation logic * nit: add "breaking" prefix in changelog. * bug: remove redundant timeout validation. * feat: remove obsolete parseTriggers fallback (#9521) * feat: remove obsolete parseTriggers fallback * nit: clean up conditional paths * feat(dataconnect): Update dataconnect:* commands to use flags for --service & --location (#9312) * Update Firestore Emulator to v1.20.2 (#9565) * Bump FS emulator version to 1.20.2 * Update CHANGELOG.md Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com> --------- Co-authored-by: Joe Hanley <joehanley@google.com> Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com> * Fix test broken by merge conflict * format * Update version in server.json * Implement a `firebase init dataconnect:resolver` command. (#9493) * Implement a `firebase init dataconnect:schema` command. * Gate behind experiment flag and a few other fixes. * Add unit tests. * Fix unit tests. * Rename command to `firebase init dataconnect:resolver`. * Commit missed file. * Fix default location in Cloud Run URL. * Don't prompt for Cloud Run URL. * Remove no-op line. * Gate command at init level. * [VS Code] Fix rendering of generate query code lens (#9588) * Fix package-lock.json * Fix missing auth:import and appdistribution:testers:remove commands (#9590) * Fix missing auth:import and appdistribution:testers:remove commands * Update CHANGELOG.md Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com> --------- Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com> * Dont pass undefined to getCommand (#9596) * Fix --help (#9597) * Fix --help * handle firebase --help * bump fdc emulator to v3 (#9602) * FDC V3 * FDC V3 * merging --------- Co-authored-by: oleina <oleina@google.com> Co-authored-by: Joe Hanley <joehanley@google.com> * lint --------- Co-authored-by: Fred Zhang <fredzqm@google.com> Co-authored-by: Jamie Rothfeder <jamie.rothfeder@gmail.com> Co-authored-by: Jamie Rothfeder <rothbutter@google.com> Co-authored-by: Yuchen Shi <yuchenshi@google.com> Co-authored-by: google-labs-jules[bot] <161369871+google-labs-jules[bot]@users.noreply.github.com> Co-authored-by: Daniel Lee <danielylee@google.com> Co-authored-by: harshyyy21 <harshoza24@gmail.com> Co-authored-by: Thomas Bouldin <inlined@users.noreply.github.com> Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com> Co-authored-by: Rosalyn Tan <rosalyntan@google.com> Co-authored-by: Anthony Oleinik <48811365+antholeole@users.noreply.github.com> Co-authored-by: oleina <oleina@google.com>
1 parent b847191 commit c6f102f

File tree

77 files changed

+1597
-2975
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

77 files changed

+1597
-2975
lines changed

.github/workflows/node-test.yml

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@ jobs:
8585
# - name: Setup Java JDK
8686
# uses: actions/setup-java@v3.3.0
8787
# with:
88-
# java-version: 17
88+
# java-version: 21
8989
# distribution: temurin
9090

9191
# - uses: actions/checkout@v4
@@ -211,6 +211,11 @@ jobs:
211211
node-version: ${{ matrix.node-version }}
212212
cache: npm
213213
cache-dependency-path: npm-shrinkwrap.json
214+
- name: Setup Java JDK
215+
uses: actions/setup-java@v3.3.0
216+
with:
217+
java-version: 21
218+
distribution: temurin
214219
- name: Setup Chrome
215220
uses: browser-actions/setup-chrome@v1.7.2
216221
with:
@@ -270,7 +275,7 @@ jobs:
270275
- name: Setup Java JDK
271276
uses: actions/setup-java@v3.3.0
272277
with:
273-
java-version: 17
278+
java-version: 21
274279
distribution: temurin
275280

276281
- uses: actions/checkout@v4

CHANGELOG.md

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
- [BREAKING] Changed `firestore:backups:list --json` to return a `listBackupsResponse` object instead of a raw array of backups.
2+
- [BREAKING] Removed support for '.bolt' rules files.
3+
- [BREAKING] Removed support for running emulators with Java versions prior to 21.
4+
- [BREAKING] Removed deprecated `firebase --open-sesame` and `firebase --close-sesame` commands. Use `firebase experiments:enable` and `firebase experiments:disable` instead.
5+
- [BREAKING] Enforce strict timeout validation for functions. (#9540)
6+
- [BREAKING] Update `dataconnect:\*` commands to use flags instead of positional arguments for `--service` & `--location`. Changed output type of `dataconnect:sql:migrate --json` (#9312)
7+
- [BREAKING] When using 'firebase-tools' as a Node module, `cli.auth.upload` has been renamed to `cli.auth.import` and `cli.appdistribution.testers.delete` has been renamed to `cli.appdistribution.testers.remove`.
8+
- [BREAKING] Updated Firebase Data Connect emulator version to v3.0.0
9+
- [BREAKING] Fixed generated code character case when letters follow numbers (https://github.com/firebase/firebase-tools/issues/9567).
10+
- [BREAKING] Dart codegen: Int64 types are now serialized and deserialized using BigInt.
11+
- [BREAKING] Kotlin codegen: Removed magic "convenience renames" of keys and counts in selection sets (https://github.com/firebase/firebase-tools/issues/9571).
12+
- Eagerly load config upon any requests from VS Code Extensions or Firebase CLI. This ensures the emulator always serve the latest local configs.
13+
- Kotlin codegen: Removed vestigial FIREBASE_DATA_CONNECT_GENERATED_FILE section at the bottom of each generated file.
14+
- Updated Firestore Emulator to v1.20.2, which includes minor bug fixes for Datastore Mode.
15+
- Improved command loading performance by implementing lazy loading.
16+
- Add a confirmation in `firebase init dataconnect` before asking for app idea description. (#9282)

firebase-vscode/CHANGELOG.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,11 @@
11
## NEXT
22

3+
- Fixed common code lens rendering issue.
4+
- Don't show "Generate query" in schema file.
5+
- Don't show "Generate query" for comments within an operation.
6+
- Show "Add Data" for @table type only.
7+
- Show "View Data" for @table and @view type.
8+
39
## 1.10.2
410

511
- Update internal `firebase-tools` dependency to 14.27.0

firebase-vscode/package-lock.json

Lines changed: 9 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

firebase-vscode/src/data-connect/code-lens-provider.ts

Lines changed: 89 additions & 71 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import * as vscode from "vscode";
2-
import { Kind, parse } from "graphql";
2+
import { ExecutableDefinitionNode, Kind, parse } from "graphql";
33
import { Disposable } from "vscode";
44

55
import { Signal } from "@preact/signals-core";
@@ -72,84 +72,94 @@ export class OperationCodeLensProvider extends ComputedCodeLensProvider {
7272
): vscode.CodeLens[] {
7373
// Wait for configs to be loaded and emulator to be running
7474
const fdcConfigs = this.watch(dataConnectConfigs)?.tryReadValue;
75-
const projectId = this.watch(firebaseRC)?.tryReadValue?.projects.default;
7675
if (!fdcConfigs) {
7776
return [];
7877
}
79-
80-
const codeLenses: vscode.CodeLens[] = [];
78+
const projectId = this.watch(firebaseRC)?.tryReadValue?.projects.default;
8179

8280
const documentText = document.getText();
8381
// TODO: replace w/ online-parser to work with malformed documents
8482
const documentNode = parse(documentText);
83+
const definitions: ExecutableDefinitionNode[] = [];
84+
for (const def of documentNode.definitions) {
85+
switch (def.kind) {
86+
case Kind.OPERATION_DEFINITION:
87+
case Kind.FRAGMENT_DEFINITION:
88+
definitions.push(def);
89+
break;
90+
default:
91+
// No code lenses for schema files
92+
return [];
93+
}
94+
}
8595

86-
for (let i = 0; i < documentNode.definitions.length; i++) {
87-
const x = documentNode.definitions[i];
88-
if (x.kind === Kind.OPERATION_DEFINITION && x.loc) {
89-
// startToken.line is 1-indexed, range is 0-indexed
90-
const line = x.loc.startToken.line - 1;
91-
const range = new vscode.Range(line, 0, line, 0);
92-
const position = new vscode.Position(line, 0);
93-
const service = fdcConfigs.findEnclosingServiceForPath(document.fileName);
94-
if (service) {
95-
{
96-
const arg: ExecutionInput = {
97-
operationAst: x,
98-
document: documentText,
99-
documentPath: document.fileName,
100-
position: position,
101-
instance: InstanceType.LOCAL,
102-
};
103-
codeLenses.push(
104-
new vscode.CodeLens(range, {
105-
title: `$(play) Run (local)`,
106-
command: "firebase.dataConnect.executeOperation",
107-
tooltip: "Execute the operation (⌘+enter or Ctrl+Enter)",
108-
arguments: [arg],
109-
}),
110-
);
111-
}
96+
const codeLenses: vscode.CodeLens[] = [];
97+
for (let i = 0; i < definitions.length; i++) {
98+
const x = definitions[i];
99+
if (!x.loc) {
100+
throw new Error("Definition has no location");
101+
}
102+
if (x.kind !== Kind.OPERATION_DEFINITION) {
103+
continue;
104+
}
105+
// startToken.line is 1-indexed, range is 0-indexed
106+
const line = x.loc.startToken.line - 1;
107+
const range = new vscode.Range(line, 0, line, 0);
108+
const position = new vscode.Position(line, 0);
109+
const service = fdcConfigs.findEnclosingServiceForPath(document.fileName);
110+
if (service) {
111+
{
112+
const arg: ExecutionInput = {
113+
operationAst: x,
114+
document: documentText,
115+
documentPath: document.fileName,
116+
position: position,
117+
instance: InstanceType.LOCAL,
118+
};
119+
codeLenses.push(
120+
new vscode.CodeLens(range, {
121+
title: `$(play) Run (local)`,
122+
command: "firebase.dataConnect.executeOperation",
123+
tooltip: "Execute the operation (⌘+enter or Ctrl+Enter)",
124+
arguments: [arg],
125+
}),
126+
);
127+
}
112128

113-
if (projectId) {
114-
const arg: ExecutionInput = {
115-
operationAst: x,
116-
document: documentText,
117-
documentPath: document.fileName,
118-
position: position,
119-
instance: InstanceType.PRODUCTION,
120-
};
121-
codeLenses.push(
122-
new vscode.CodeLens(range, {
123-
title: `$(play) Run (Production – Project: ${projectId})`,
124-
command: "firebase.dataConnect.executeOperation",
125-
tooltip: "Execute the operation (⌘+enter or Ctrl+Enter)",
126-
arguments: [arg],
127-
}),
128-
);
129-
}
129+
if (projectId) {
130+
const arg: ExecutionInput = {
131+
operationAst: x,
132+
document: documentText,
133+
documentPath: document.fileName,
134+
position: position,
135+
instance: InstanceType.PRODUCTION,
136+
};
137+
codeLenses.push(
138+
new vscode.CodeLens(range, {
139+
title: `$(play) Run (Production – Project: ${projectId})`,
140+
command: "firebase.dataConnect.executeOperation",
141+
tooltip: "Execute the operation (⌘+enter or Ctrl+Enter)",
142+
arguments: [arg],
143+
}),
144+
);
130145
}
131146
}
132147
}
133148

134-
const comments = findCommentsBlocks(documentText);
149+
const comments = findCommentsBlocks(documentText, definitions);
135150
for (let i = 0; i < comments.length; i++) {
136151
const c = comments[i];
137152
const range = new vscode.Range(c.startLine, 0, c.startLine, 0);
138-
const queryDoc = documentNode.definitions.find((d) =>
139-
d.kind === Kind.OPERATION_DEFINITION &&
140-
// startToken.line is 1-indexed, endLine is 0-indexed
141-
d.loc?.startToken.line === c.endLine + 2
142-
);
143153
const arg: GenerateOperationInput = {
144154
projectId,
145155
document: document,
146156
description: c.text,
147157
insertPosition: c.endIndex + 1,
148-
existingQuery: queryDoc?.loc ? documentText.substring(c.endIndex + 1, queryDoc.loc.endToken.end) : '',
158+
existingQuery: c.queryDoc?.loc ? documentText.substring(c.endIndex + 1, c.queryDoc.loc.endToken.end) : '',
149159
};
150160
codeLenses.push(
151161
new vscode.CodeLens(range, {
152-
title: queryDoc ? `$(sparkle) Refine Operation` : `$(sparkle) Generate Operation`,
162+
title: c.queryDoc ? `$(sparkle) Refine Operation` : `$(sparkle) Generate Operation`,
153163
command: "firebase.dataConnect.generateOperation",
154164
tooltip: "Generate the operation (⌘+enter or Ctrl+Enter)",
155165
arguments: [arg],
@@ -195,29 +205,37 @@ export class SchemaCodeLensProvider extends ComputedCodeLensProvider {
195205
// );
196206
// }
197207

198-
codeLenses.push(
199-
new vscode.CodeLens(range, {
200-
title: `$(database) Add data`,
201-
command: "firebase.dataConnect.schemaAddData",
202-
tooltip: "Generate a mutation to add data of this type",
203-
arguments: [x, documentPath],
204-
}),
205-
);
208+
const isTable = x.directives?.some((d) => d.name.value === "table");
209+
const isView = x.directives?.some((d) => d.name.value === "view");
206210

207-
codeLenses.push(
208-
new vscode.CodeLens(range, {
209-
title: `$(database) Read data`,
210-
command: "firebase.dataConnect.schemaReadData",
211-
tooltip: "Generate a query to read data of this type",
212-
arguments: [documentNode, x, documentPath],
213-
}),
214-
);
211+
if (isTable) {
212+
codeLenses.push(
213+
new vscode.CodeLens(range, {
214+
title: `$(database) Add data`,
215+
command: "firebase.dataConnect.schemaAddData",
216+
tooltip: "Generate a mutation to add data of this type",
217+
arguments: [x, documentPath],
218+
}),
219+
);
220+
}
221+
222+
if (isTable || isView) {
223+
codeLenses.push(
224+
new vscode.CodeLens(range, {
225+
title: `$(database) Read data`,
226+
command: "firebase.dataConnect.schemaReadData",
227+
tooltip: "Generate a query to read data of this type",
228+
arguments: [documentNode, x, documentPath],
229+
}),
230+
);
231+
}
215232
}
216233
}
217234

218235
return codeLenses;
219236
}
220237
}
238+
221239
/**
222240
* CodeLensProvider for Configure SDK in Connector.yaml
223241
*/

firebase-vscode/src/data-connect/execution/execution.ts

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -20,17 +20,13 @@ import {
2020
OperationDefinitionNode,
2121
OperationTypeNode,
2222
print,
23-
buildClientSchema,
24-
validate,
25-
parse,
2623
} from "graphql";
2724
import { DataConnectService } from "../service";
2825
import { DataConnectError, toSerializedError } from "../../../common/error";
2926
import { InstanceType } from "../code-lens-provider";
3027
import { DATA_CONNECT_EVENT_NAME, AnalyticsLogger } from "../../analytics";
3128
import { EmulatorsController } from "../../core/emulators";
3229
import { getConnectorGQLText, insertQueryAt } from "../file-utils";
33-
import { pluginLogger } from "../../logger-wrapper";
3430
import * as gif from "../../../../src/gemini/fdcExperience";
3531
import { ensureGIFApiTos } from "../../../../src/dataconnect/ensureApis";
3632
import { configstore } from "../../../../src/configstore";

0 commit comments

Comments
 (0)