Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Internal implementation of multiDb #1949

Merged
merged 3 commits into from Oct 26, 2022
Merged

Internal implementation of multiDb #1949

merged 3 commits into from Oct 26, 2022

Conversation

tom-andersen
Copy link
Contributor

@tom-andersen tom-andersen commented Oct 21, 2022

No description provided.

@tom-andersen tom-andersen force-pushed the tomandersen/multiDb branch 4 times, most recently from e65059b to 93c8c4f Compare October 21, 2022 16:59
@tom-andersen tom-andersen marked this pull request as ready for review October 21, 2022 17:06
@wu-hui
Copy link

wu-hui commented Oct 21, 2022

please take package-lock.json out of this PR. Otherwise LGTM.

@tom-andersen
Copy link
Contributor Author

please take package-lock.json out of this PR. Otherwise LGTM.

Done

Copy link
Member

@lahirumaramba lahirumaramba left a comment

Choose a reason for hiding this comment

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

Thank you @tom-andersen ! Overall LGTM!
I left a few comments and questions.

this.appInternal = app;
}

getDatabase(databaseId: string): Firestore {
let database = this.databases.get(databaseId);
if (database === undefined) {
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
if (database === undefined) {
if (typeof database === undefined) {

Copy link
Member

Choose a reason for hiding this comment

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

Or we could also do if (!this.databases.has(databaseId)) { just a suggestion really. I will leave it up to you. :)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Any of these solutions are valid. But I have a preference towards existing for a couple of reasons.

  • conciseness
  • performance (though only a small difference, calling has followed by get does consume more resources)
  • correctness (even if map has value, it could be 'undefined')

Just a note, using typeof will require putting quotes around undefined.

src/firestore/firestore-internal.ts Outdated Show resolved Hide resolved
src/firestore/index.ts Show resolved Hide resolved
src/firestore/index.ts Show resolved Hide resolved
appOrDatabaseId?: App | string,
optionalDatabaseId?: string
): Firestore {
const app: App = typeof appOrDatabaseId === 'object' ? appOrDatabaseId : getApp();
Copy link
Member

Choose a reason for hiding this comment

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

I think type of null is also object... we might want to check if app !== null as well. Alternatively, you can also move the implementations into the respective functions separately.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

They would need to bypass Typescript type checking for this to happen, since appOrDatabaseId?: App | string.

According to this doc, we should not guard against invalid types.
https://g3doc.corp.google.com/firebase/g3doc/aip/3270.md?cl=head#input-validation

const databaseId =
typeof appOrDatabaseId === 'string'
? appOrDatabaseId
: optionalDatabaseId || '(default)';
Copy link
Member

Choose a reason for hiding this comment

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

Is '(default)' a const?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Yes. I have imported it from Server SDK (though it is not part of public API).

): Firestore {
const app: App = typeof appOrDatabaseId === 'object' ? appOrDatabaseId : getApp();
const databaseId =
typeof appOrDatabaseId === 'string'
Copy link
Member

Choose a reason for hiding this comment

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

Do we want to check if appOrDatabaseId is a non-empty string? We a validator util if this is needed validator.isNonEmptyString().

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Good point. I think we should consider an empty string equivalent to the default database id.

@@ -98,23 +98,25 @@ describe('Firestore', () => {
it(`should throw given invalid app: ${ JSON.stringify(invalidApp) }`, () => {
expect(() => {
const firestoreAny: any = FirestoreService;
return new firestoreAny(invalidApp);
const firestoreService: FirestoreService = new firestoreAny(invalidApp);
return firestoreService.getDatabase('(default)')
Copy link
Member

Choose a reason for hiding this comment

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

Should we make this '(default)' a constant?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Imported from Server SDK

@@ -158,19 +160,6 @@ describe('Firestore', () => {
});
});

describe('client', () => {
Copy link
Member

Choose a reason for hiding this comment

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

Could this be a potential breaking change in the public API?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

It's a private variable of an internal class. No one should rely on this externally.

/**
* @param app
* @param databaseId
* @internal
Copy link
Member

Choose a reason for hiding this comment

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

@internal will hide this from both reference docs and autocomplete (it will remove the typescript annotation). Is that what we expect here? If we only want to hide from reference docs and would like to keep autocomplete we can use @alpha instead.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I feel safer to keep this completely hidden for the moment. We have a follow up task to expose API.

Copy link
Member

@lahirumaramba lahirumaramba left a comment

Choose a reason for hiding this comment

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

LGTM. Thanks!

@tom-andersen tom-andersen merged commit 4d6b79e into master Oct 26, 2022
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.

None yet

4 participants