Skip to content

Commit bb85784

Browse files
committed
Add docstrings
1 parent 6790295 commit bb85784

File tree

6 files changed

+112
-62
lines changed

6 files changed

+112
-62
lines changed

etc/firebase-admin.data-connect.api.md

Lines changed: 5 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -8,11 +8,9 @@
88

99
import { Agent } from 'http';
1010

11-
// @public (undocumented)
11+
// @public
1212
export interface ConnectorConfig {
13-
// (undocumented)
1413
location: string;
15-
// (undocumented)
1614
serviceId: string;
1715
}
1816

@@ -24,24 +22,23 @@ export class DataConnect {
2422
readonly app: App;
2523
// (undocumented)
2624
readonly connectorConfig: ConnectorConfig;
25+
// @beta
2726
executeGraphql<GraphqlResponse, Variables>(query: string, options?: GraphqlOptions<Variables>): Promise<ExecuteGraphqlResponse<GraphqlResponse>>;
27+
// @beta
2828
executeGraphqlRead<GraphqlResponse, Variables>(query: string, options?: GraphqlOptions<Variables>): Promise<ExecuteGraphqlResponse<GraphqlResponse>>;
2929
}
3030

31-
// @public (undocumented)
31+
// @public
3232
export interface ExecuteGraphqlResponse<GraphqlResponse> {
33-
// (undocumented)
3433
data: GraphqlResponse;
3534
}
3635

3736
// @public
3837
export function getDataConnect(connectorConfig: ConnectorConfig, app?: App): DataConnect;
3938

40-
// @public (undocumented)
39+
// @public
4140
export interface GraphqlOptions<Variables> {
42-
// (undocumented)
4341
operationName?: string;
44-
// (undocumented)
4542
variables?: Variables;
4643
}
4744

src/data-connect/data-connect-api-client-internal.ts

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,6 @@ import { ConnectorConfig, ExecuteGraphqlResponse, GraphqlOptions } from './data-
2727

2828
// Data Connect backend constants
2929
const DATA_CONNECT_HOST = 'https://firebasedataconnect.googleapis.com';
30-
//const DATA_CONNECT_EMULATOR_HOST = 'http://127.0.0.1:9399';
3130
const DATA_CONNECT_API_URL_FORMAT =
3231
'{host}/v1alpha/projects/{projectId}/locations/{locationId}/services/{serviceId}:{endpointId}';
3332

@@ -117,8 +116,7 @@ export class DataConnectApiClient {
117116
data,
118117
};
119118
const resp = await this.httpClient.send(request);
120-
//console.dir(resp, { depth: null });
121-
if (resp.data.errors && validator.isArray(resp.data.errors)) {
119+
if (resp.data.errors && validator.isNonEmptyArray(resp.data.errors)) {
122120
const allMessages = resp.data.errors.map((error: { message: any; }) => error.message).join(' ');
123121
throw new FirebaseDataConnectError(
124122
DATA_CONNECT_ERROR_CODE_MAPPING.QUERY_ERROR, allMessages);

src/data-connect/data-connect-api.ts

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,16 +15,42 @@
1515
* limitations under the License.
1616
*/
1717

18+
/**
19+
* Interface representing a Data Connect connector configuration.
20+
*/
1821
export interface ConnectorConfig {
22+
/**
23+
* Location ID of the Data Connect service.
24+
*/
1925
location: string;
26+
27+
/**
28+
* Service ID of the Data Connect service.
29+
*/
2030
serviceId: string;
2131
}
2232

33+
/**
34+
* Interface representing GraphQL response.
35+
*/
2336
export interface ExecuteGraphqlResponse<GraphqlResponse> {
37+
/**
38+
* Data payload of the GraphQL response.
39+
*/
2440
data: GraphqlResponse;
2541
}
2642

43+
/**
44+
* Interface representing GraphQL options.
45+
*/
2746
export interface GraphqlOptions<Variables> {
47+
/**
48+
* Values for GraphQL variables provided in this query or mutation.
49+
*/
2850
variables?: Variables;
51+
52+
/**
53+
* The name of the GraphQL operation. Required only if `query` contains multiple operations.
54+
*/
2955
operationName?: string;
3056
}

src/data-connect/data-connect.ts

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -17,13 +17,11 @@
1717

1818
import { App } from '../app';
1919
import { DataConnectApiClient } from './data-connect-api-client-internal';
20-
//import * as validator from '../utils/validator';
2120

2221
import {
2322
ConnectorConfig,
2423
ExecuteGraphqlResponse,
2524
GraphqlOptions,
26-
//GraphqlReadOptions,
2725
} from './data-connect-api';
2826

2927
export class DataConnectService {
@@ -48,9 +46,9 @@ export class DataConnectService {
4846
}
4947

5048
/**
51-
* Returns the app associated with this `DataConnect` instance.
49+
* Returns the app associated with this `DataConnectService` instance.
5250
*
53-
* @returns The app associated with this `DataConnect` instance.
51+
* @returns The app associated with this `DataConnectService` instance.
5452
*/
5553
get app(): App {
5654
return this.appInternal;
@@ -65,7 +63,7 @@ export class DataConnect {
6563
private readonly client: DataConnectApiClient;
6664

6765
/**
68-
* @param connectorConfig - Connector Config
66+
* @param connectorConfig - The connector configuration.
6967
* @param app - The app for this `DataConnect` service.
7068
* @constructor
7169
* @internal
@@ -78,9 +76,10 @@ export class DataConnect {
7876
* Execute an arbitrary GraphQL query or mutation
7977
*
8078
* @param query - The GraphQL query or mutation.
81-
* @param options - Optional options object when creating a new App Check Token.
79+
* @param options - Optional {@link GraphqlOptions} when executing a GraphQL query or mutation.
8280
*
83-
* @returns A promise that fulfills with a `Something`.
81+
* @returns A promise that fulfills with a `ExecuteGraphqlResponse`.
82+
* @beta
8483
*/
8584
public executeGraphql<GraphqlResponse, Variables>(
8685
query: string,
@@ -93,9 +92,10 @@ export class DataConnect {
9392
* Execute an arbitrary read-only GraphQL query
9493
*
9594
* @param query - The GraphQL read-only query.
96-
* @param options - Optional options object when creating a new App Check Token.
95+
* @param options - Optional {@link GraphqlOptions} when executing a read-only GraphQL query.
9796
*
98-
* @returns A promise that fulfills with a `Something`.
97+
* @returns A promise that fulfills with a `ExecuteGraphqlResponse`.
98+
* @beta
9999
*/
100100
public executeGraphqlRead<GraphqlResponse, Variables>(
101101
query: string,

src/data-connect/index.ts

Lines changed: 14 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -36,32 +36,37 @@ export {
3636
} from './data-connect'
3737

3838
/**
39-
* Gets the {@link DataConnect} service for the default app
40-
* or a given app.
39+
* Gets the {@link DataConnect} service with the provided connector configuration
40+
* for the default app or a given app.
4141
*
42-
* `getDataConnect()` can be called with no arguments to access the default
43-
* app's `DataConnect` service or as `getDataConnect(app)` to access the
42+
* `getDataConnect(connectorConfig)` can be called with no app argument to access the default
43+
* app's `DataConnect` service or as `getDataConnect(connectorConfig, app)` to access the
4444
* `DataConnect` service associated with a specific app.
4545
*
4646
* @example
4747
* ```javascript
48+
* const connectorConfig: ConnectorConfig = {
49+
* location: 'us-west2',
50+
* serviceId: 'my-service',
51+
* };
52+
*
4853
* // Get the `DataConnect` service for the default app
49-
* const defaultDataConnect = getDataConnect();
54+
* const defaultDataConnect = getDataConnect(connectorConfig);
5055
* ```
5156
*
5257
* @example
5358
* ```javascript
5459
* // Get the `DataConnect` service for a given app
55-
* const otherDataConnect = getDataConnect(otherApp);
60+
* const otherDataConnect = getDataConnect(connectorConfig, otherApp);
5661
* ```
5762
*
58-
* @param connectorConfig - Connector Config
63+
* @param connectorConfig - Connector configuration for the `DataConnect` service.
5964
*
6065
* @param app - Optional app for which to return the `DataConnect` service.
6166
* If not provided, the default `DataConnect` service is returned.
6267
*
63-
* @returns The default `DataConnect` service if no app is provided, or the `DataConnect`
64-
* service associated with the provided app.
68+
* @returns The default `DataConnect` service with the provided connector configuration
69+
* if no app is provided, or the `DataConnect` service associated with the provided app.
6570
*/
6671
export function getDataConnect(connectorConfig: ConnectorConfig, app?: App): DataConnect {
6772
if (typeof app === 'undefined') {

test/integration/data-connect.spec.ts

Lines changed: 57 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,13 @@ chai.use(chaiAsPromised);
2424
const expect = chai.expect;
2525

2626
interface UserResponse {
27+
user: {
28+
name: string;
29+
uid: string;
30+
}
31+
}
32+
33+
interface UsersResponse {
2734
users: [
2835
user: {
2936
id: string;
@@ -33,6 +40,24 @@ interface UserResponse {
3340
];
3441
}
3542

43+
interface UserUpdateResponse {
44+
user_upsert: { uid: string }
45+
}
46+
47+
interface EmailsResponse {
48+
emails: [
49+
email: {
50+
text: string;
51+
subject: string;
52+
id: string;
53+
date: string;
54+
from: {
55+
name: string;
56+
}
57+
}
58+
];
59+
}
60+
3661
interface UserVariables {
3762
id: string;
3863
}
@@ -42,76 +67,75 @@ const connectorConfig: ConnectorConfig = {
4267
serviceId: 'my-service',
4368
};
4469

70+
const userId = 'QVBJcy5ndXJ3';
71+
4572
describe('getDataConnect()', () => {
4673

47-
const query1 = 'query ListUsers @auth(level: PUBLIC) { users { uid, name, address } }';
48-
const query2 = 'query ListEmails @auth(level: NO_ACCESS) { emails { id subject text date from { name } } }';
49-
const getUserQuery = 'query GetUser($id: User_Key!) { user(key: $id) { uid name } }';
74+
const queryListUsers = 'query ListUsers @auth(level: PUBLIC) { users { uid, name, address } }';
75+
const queryListEmails = 'query ListEmails @auth(level: NO_ACCESS) { emails { id subject text date from { name } } }';
76+
const queryGetUserById = 'query GetUser($id: User_Key!) { user(key: $id) { uid name } }';
5077
const multipleQueries = `
51-
${query1}
52-
${query2}
78+
${queryListUsers}
79+
${queryListEmails}
5380
`;
54-
const mutation = 'mutation user { user_insert(data: {uid: "QVBJcy5ndXJ3", address: "Address", name: "Name"}) }'
55-
const mutationUpdate = 'mutation UpdateUser($id: User_Key!) { user_update(key: $id, data: { name: "Name" }) }';
81+
const mutation = `mutation user { user_insert(data: {uid: "${userId}", address: "32 St", name: "Fred Car"}) }`;
82+
const upsertUser = `mutation UpsertUser($id: String) {
83+
user_upsert(data: { uid: $id, address: "32 St.", name: "Fred" }) }`;
5684

5785
describe('executeGraphql()', () => {
86+
it('executeGraphql() successfully executes a GraphQL mutation', async () => {
87+
const resp = await getDataConnect(connectorConfig).executeGraphql<UserUpdateResponse, unknown>(
88+
upsertUser, { variables: { id: userId } }
89+
);
90+
//{ data: { user_insert: { uid: 'QVBJcy5ndXJ3' } } }
91+
expect(resp.data.user_upsert.uid).to.be.not.empty;
92+
expect(resp.data.user_upsert.uid).equals(userId);
93+
});
94+
5895
it('executeGraphql() successfully executes a GraphQL', async () => {
59-
const resp = await getDataConnect(connectorConfig).executeGraphql<UserResponse, UserVariables>(query1);
60-
//console.dir(resp.data.users);
96+
const resp = await getDataConnect(connectorConfig).executeGraphql<UsersResponse, UserVariables>(queryListUsers);
6197
expect(resp.data.users).to.be.not.empty;
6298
expect(resp.data.users[0].name).to.be.not.undefined;
6399
expect(resp.data.users[0].address).to.be.not.undefined;
64100
});
65101

66102
it('executeGraphql() use the operationName when multiple queries are provided', async () => {
67-
const resp = await getDataConnect(connectorConfig).executeGraphql(
103+
const resp = await getDataConnect(connectorConfig).executeGraphql<EmailsResponse, unknown>(
68104
multipleQueries,
69105
{ operationName: 'ListEmails' }
70106
);
71-
console.dir(resp.data);
72-
// expect(resp.data.users).to.be.not.empty;
73-
// expect(resp.data.users[0].name).to.be.not.undefined;
74-
// expect(resp.data.users[0].address).to.be.not.undefined;
75-
});
76-
77-
it('executeGraphql() successfully executes a GraphQL mutation', async () => {
78-
const resp = await getDataConnect(connectorConfig).executeGraphql(
79-
mutationUpdate, { variables: { id: 'QVBJcy5ndXJ3' } }
80-
);
81-
console.dir(resp); //{ data: { user_insert: { uid: 'QVBJcy5ndXJ3' } } }
82-
//expect(resp.data.users).to.be.not.empty;
83-
// expect(resp.data.users[0].name).to.be.not.undefined;
84-
// expect(resp.data.users[0].address).to.be.not.undefined;
107+
expect(resp.data.emails).to.be.not.empty;
108+
expect(resp.data.emails[0].id).to.be.not.undefined;
109+
expect(resp.data.emails[0].from.name).to.be.not.undefined;
85110
});
86111

87-
it('executeGraphql() should throw for a duplicate key GraphQL mutation', async () => {
112+
it('executeGraphql() should throw for a query error', async () => {
88113
return getDataConnect(connectorConfig).executeGraphql(mutation)
89114
.should.eventually.be.rejected.and.have.property('code', 'data-connect/query-error');
90115
});
91116

92117
it('executeGraphql() successfully executes a GraphQL query with variables', async () => {
93118
const resp = await getDataConnect(connectorConfig).executeGraphql<UserResponse, UserVariables>(
94-
getUserQuery,
95-
{ variables: { id: 'QVBJcy5ndXJ3' } }
119+
queryGetUserById,
120+
{ variables: { id: userId } }
96121
);
97-
console.dir(resp);
98-
// expect(resp.data.users).to.be.not.empty;
99-
// expect(resp.data.users[0].name).to.be.not.undefined;
100-
// expect(resp.data.users[0].address).to.be.not.undefined;
122+
expect(resp.data.user.name).to.be.not.undefined;
123+
expect(resp.data.user.uid).equals(userId);
101124
});
102125
});
103126

104127
describe('executeGraphqlRead()', () => {
105128
it('executeGraphqlRead() successfully executes a read-only GraphQL', async () => {
106-
const resp = await getDataConnect(connectorConfig).executeGraphqlRead<UserResponse, UserVariables>(query1);
129+
const resp =
130+
await getDataConnect(connectorConfig).executeGraphqlRead<UsersResponse, UserVariables>(queryListUsers);
107131
expect(resp.data.users).to.be.not.empty;
108132
expect(resp.data.users[0].name).to.be.not.undefined;
109133
expect(resp.data.users[0].address).to.be.not.undefined;
110134
});
111135

112136
it('executeGraphqlRead() should throw for a GraphQL mutation', async () => {
113137
return getDataConnect(connectorConfig).executeGraphqlRead(mutation)
114-
.should.eventually.be.rejected.and.have.property('code', 'data-connect/permission-denied');
138+
.should.eventually.be.rejected;
115139
});
116140
});
117141
});

0 commit comments

Comments
 (0)