Skip to content

Commit 4cb0945

Browse files
Add GMPID Header to Firestore (#3888)
1 parent 7b585e8 commit 4cb0945

File tree

11 files changed

+42
-7
lines changed

11 files changed

+42
-7
lines changed

.changeset/honest-hounds-sin.md

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
"@firebase/firestore": patch
3+
---
4+
5+
Added new internal HTTP header to all network requests.

packages/firestore/src/core/database_info.ts

+2
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ export class DatabaseInfo {
2121
* persistenceKey.
2222
*
2323
* @param databaseId - The database to use.
24+
* @param appId - The Firebase App Id.
2425
* @param persistenceKey - A unique identifier for this Firestore's local
2526
* storage (used in conjunction with the databaseId).
2627
* @param host - The Firestore backend host to connect to.
@@ -32,6 +33,7 @@ export class DatabaseInfo {
3233
*/
3334
constructor(
3435
readonly databaseId: DatabaseId,
36+
readonly appId: string,
3537
readonly persistenceKey: string,
3638
readonly host: string,
3739
readonly ssl: boolean,

packages/firestore/src/exp/database.ts

+1
Original file line numberDiff line numberDiff line change
@@ -178,6 +178,7 @@ export function configureFirestore(firestore: FirebaseFirestore): void {
178178

179179
const databaseInfo = makeDatabaseInfo(
180180
firestore._databaseId,
181+
firestore._app?.options.appId || '',
181182
firestore._persistenceKey,
182183
settings
183184
);

packages/firestore/src/lite/components.ts

+3
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,7 @@ export function getDatastore(firestore: FirestoreService): Datastore {
7070
logDebug(LOG_TAG, 'Initializing Datastore');
7171
const databaseInfo = makeDatabaseInfo(
7272
firestore._databaseId,
73+
firestore.app.options.appId || '',
7374
firestore._persistenceKey,
7475
firestore._freezeSettings()
7576
);
@@ -101,11 +102,13 @@ export function removeComponents(firestore: FirestoreService): void {
101102

102103
export function makeDatabaseInfo(
103104
databaseId: DatabaseId,
105+
appId: string,
104106
persistenceKey: string,
105107
settings: FirestoreSettings
106108
): DatabaseInfo {
107109
return new DatabaseInfo(
108110
databaseId,
111+
appId,
109112
persistenceKey,
110113
settings.host,
111114
settings.ssl,

packages/firestore/src/lite/database.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,7 @@ export class FirebaseFirestore implements FirestoreService {
6666
// all components have shut down.
6767
private _terminateTask?: Promise<void>;
6868

69-
private _app?: FirebaseApp;
69+
_app?: FirebaseApp;
7070

7171
/** @hideconstructor */
7272
constructor(

packages/firestore/src/platform/node/grpc_connection.ts

+23-6
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,11 @@ import { Deferred } from '../../util/promise';
3838
const LOG_TAG = 'Connection';
3939
const X_GOOG_API_CLIENT_VALUE = `gl-node/${process.versions.node} fire/${SDK_VERSION} grpc/${grpcVersion}`;
4040

41-
function createMetadata(databasePath: string, token: Token | null): Metadata {
41+
function createMetadata(
42+
databasePath: string,
43+
token: Token | null,
44+
appId: string
45+
): Metadata {
4246
hardAssert(
4347
token === null || token.type === 'OAuth',
4448
'If provided, token must be OAuth'
@@ -52,10 +56,11 @@ function createMetadata(databasePath: string, token: Token | null): Metadata {
5256
}
5357
}
5458
}
55-
metadata.set('x-goog-api-client', X_GOOG_API_CLIENT_VALUE);
59+
metadata.set('X-Firebase-GMPID', appId);
60+
metadata.set('X-Goog-Api-Client', X_GOOG_API_CLIENT_VALUE);
5661
// This header is used to improve routing and project isolation by the
5762
// backend.
58-
metadata.set('google-cloud-resource-prefix', databasePath);
63+
metadata.set('Google-Cloud-Resource-Prefix', databasePath);
5964
return metadata;
6065
}
6166

@@ -102,7 +107,11 @@ export class GrpcConnection implements Connection {
102107
token: Token | null
103108
): Promise<Resp> {
104109
const stub = this.ensureActiveStub();
105-
const metadata = createMetadata(this.databasePath, token);
110+
const metadata = createMetadata(
111+
this.databasePath,
112+
token,
113+
this.databaseInfo.appId
114+
);
106115
const jsonRequest = { database: this.databasePath, ...request };
107116

108117
return nodePromise((callback: NodeCallback<Resp>) => {
@@ -147,7 +156,11 @@ export class GrpcConnection implements Connection {
147156
request
148157
);
149158
const stub = this.ensureActiveStub();
150-
const metadata = createMetadata(this.databasePath, token);
159+
const metadata = createMetadata(
160+
this.databasePath,
161+
token,
162+
this.databaseInfo.appId
163+
);
151164
const jsonRequest = { ...request, database: this.databasePath };
152165
const stream = stub[rpcName](jsonRequest, metadata);
153166
stream.on('data', (response: Resp) => {
@@ -173,7 +186,11 @@ export class GrpcConnection implements Connection {
173186
token: Token | null
174187
): Stream<Req, Resp> {
175188
const stub = this.ensureActiveStub();
176-
const metadata = createMetadata(this.databasePath, token);
189+
const metadata = createMetadata(
190+
this.databasePath,
191+
token,
192+
this.databaseInfo.appId
193+
);
177194
const grpcStream = stub[rpcName](metadata);
178195

179196
let closed = false;

packages/firestore/src/remote/rest_connection.ts

+1
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,7 @@ export abstract class RestConnection implements Connection {
119119
token: Token | null
120120
): void {
121121
headers['X-Goog-Api-Client'] = X_GOOG_API_CLIENT_VALUE;
122+
headers['X-Firebase-GMPID'] = this.databaseInfo.appId;
122123

123124
// Content-Type: text/plain will avoid preflight requests which might
124125
// mess with CORS and redirects by proxies. If we add custom headers

packages/firestore/test/integration/util/internal_helpers.ts

+1
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ export function asyncQueue(db: firestore.FirebaseFirestore): AsyncQueueImpl {
4343
export function getDefaultDatabaseInfo(): DatabaseInfo {
4444
return new DatabaseInfo(
4545
new DatabaseId(DEFAULT_PROJECT_ID),
46+
'test-app-id',
4647
'persistenceKey',
4748
DEFAULT_SETTINGS.host!,
4849
!!DEFAULT_SETTINGS.ssl,

packages/firestore/test/unit/local/persistence_test_helpers.ts

+1
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,7 @@ export const MOCK_SEQUENCE_NUMBER_SYNCER: SequenceNumberSyncer = {
5656
export const TEST_PROJECT = 'test-project';
5757
export const TEST_DATABASE_ID = new DatabaseId(TEST_PROJECT);
5858
export const TEST_PERSISTENCE_KEY = '[PersistenceTestHelpers]';
59+
export const TEST_APP_ID = 'test-app-id';
5960

6061
/** The persistence prefix used for testing in IndexedBD and LocalStorage. */
6162
export const TEST_PERSISTENCE_PREFIX = indexedDbStoragePrefix(

packages/firestore/test/unit/remote/rest_connection.test.ts

+2
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,7 @@ export class TestRestConnection extends RestConnection {
5858
describe('RestConnection', () => {
5959
const testDatabaseInfo = new DatabaseInfo(
6060
new DatabaseId('testproject'),
61+
'test-app-id',
6162
'persistenceKey',
6263
'example.com',
6364
/*ssl=*/ false,
@@ -92,6 +93,7 @@ describe('RestConnection', () => {
9293
expect(connection.lastHeaders).to.deep.equal({
9394
'Authorization': 'Bearer owner',
9495
'Content-Type': 'text/plain',
96+
'X-Firebase-GMPID': 'test-app-id',
9597
'X-Goog-Api-Client': `gl-js/ fire/${SDK_VERSION}`
9698
});
9799
});

packages/firestore/test/unit/specs/spec_test_runner.ts

+2
Original file line numberDiff line numberDiff line change
@@ -142,6 +142,7 @@ import {
142142
import {
143143
clearTestPersistence,
144144
INDEXEDDB_TEST_DATABASE_NAME,
145+
TEST_APP_ID,
145146
TEST_DATABASE_ID,
146147
TEST_PERSISTENCE_KEY,
147148
TEST_SERIALIZER
@@ -250,6 +251,7 @@ abstract class TestRunner {
250251
this.clientId = `client${clientIndex}`;
251252
this.databaseInfo = new DatabaseInfo(
252253
TEST_DATABASE_ID,
254+
TEST_APP_ID,
253255
TEST_PERSISTENCE_KEY,
254256
'host',
255257
/*ssl=*/ false,

0 commit comments

Comments
 (0)