fix: Do not rely on class names in production bundle (#6212)
This commit is contained in:
@@ -351,6 +351,6 @@ export default class AuthStore extends Store<Team> {
|
||||
|
||||
// Tell the host application we logged out, if any – allows window cleanup.
|
||||
void Desktop.bridge?.onLogout?.();
|
||||
this.rootStore.logout();
|
||||
this.rootStore.clear();
|
||||
};
|
||||
}
|
||||
|
||||
@@ -10,8 +10,6 @@ import RootStore from "./RootStore";
|
||||
import Store from "./base/Store";
|
||||
|
||||
export default class CommentsStore extends Store<Comment> {
|
||||
apiEndpoint = "comments";
|
||||
|
||||
constructor(rootStore: RootStore) {
|
||||
super(rootStore, Comment);
|
||||
}
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
import invariant from "invariant";
|
||||
import pluralize from "pluralize";
|
||||
import ApiKeysStore from "./ApiKeysStore";
|
||||
import AuthStore from "./AuthStore";
|
||||
import AuthenticationProvidersStore from "./AuthenticationProvidersStore";
|
||||
@@ -25,6 +27,7 @@ import UiStore from "./UiStore";
|
||||
import UsersStore from "./UsersStore";
|
||||
import ViewsStore from "./ViewsStore";
|
||||
import WebhookSubscriptionsStore from "./WebhookSubscriptionStore";
|
||||
import Store from "./base/Store";
|
||||
|
||||
export default class RootStore {
|
||||
apiKeys: ApiKeysStore;
|
||||
@@ -56,42 +59,79 @@ export default class RootStore {
|
||||
webhookSubscriptions: WebhookSubscriptionsStore;
|
||||
|
||||
constructor() {
|
||||
this.apiKeys = new ApiKeysStore(this);
|
||||
this.authenticationProviders = new AuthenticationProvidersStore(this);
|
||||
this.collections = new CollectionsStore(this);
|
||||
this.collectionGroupMemberships = new CollectionGroupMembershipsStore(this);
|
||||
this.comments = new CommentsStore(this);
|
||||
this.dialogs = new DialogsStore();
|
||||
this.documents = new DocumentsStore(this);
|
||||
this.events = new EventsStore(this);
|
||||
this.groups = new GroupsStore(this);
|
||||
this.groupMemberships = new GroupMembershipsStore(this);
|
||||
this.integrations = new IntegrationsStore(this);
|
||||
this.memberships = new MembershipsStore(this);
|
||||
this.notifications = new NotificationsStore(this);
|
||||
this.pins = new PinsStore(this);
|
||||
this.policies = new PoliciesStore(this);
|
||||
this.presence = new DocumentPresenceStore();
|
||||
this.revisions = new RevisionsStore(this);
|
||||
this.searches = new SearchesStore(this);
|
||||
this.shares = new SharesStore(this);
|
||||
this.stars = new StarsStore(this);
|
||||
this.subscriptions = new SubscriptionsStore(this);
|
||||
this.ui = new UiStore();
|
||||
this.users = new UsersStore(this);
|
||||
this.views = new ViewsStore(this);
|
||||
this.fileOperations = new FileOperationsStore(this);
|
||||
this.webhookSubscriptions = new WebhookSubscriptionsStore(this);
|
||||
// Models
|
||||
this.registerStore(ApiKeysStore);
|
||||
this.registerStore(AuthenticationProvidersStore);
|
||||
this.registerStore(CollectionsStore);
|
||||
this.registerStore(CollectionGroupMembershipsStore);
|
||||
this.registerStore(CommentsStore);
|
||||
this.registerStore(DocumentsStore);
|
||||
this.registerStore(EventsStore);
|
||||
this.registerStore(GroupsStore);
|
||||
this.registerStore(GroupMembershipsStore);
|
||||
this.registerStore(IntegrationsStore);
|
||||
this.registerStore(MembershipsStore);
|
||||
this.registerStore(NotificationsStore);
|
||||
this.registerStore(PinsStore);
|
||||
this.registerStore(PoliciesStore);
|
||||
this.registerStore(RevisionsStore);
|
||||
this.registerStore(SearchesStore);
|
||||
this.registerStore(SharesStore);
|
||||
this.registerStore(StarsStore);
|
||||
this.registerStore(SubscriptionsStore);
|
||||
this.registerStore(UsersStore);
|
||||
this.registerStore(ViewsStore);
|
||||
this.registerStore(FileOperationsStore);
|
||||
this.registerStore(WebhookSubscriptionsStore);
|
||||
|
||||
// Non-models
|
||||
this.registerStore(DocumentPresenceStore, "presence");
|
||||
this.registerStore(DialogsStore, "dialogs");
|
||||
this.registerStore(UiStore, "ui");
|
||||
|
||||
// AuthStore must be initialized last as it makes use of the other stores.
|
||||
this.auth = new AuthStore(this);
|
||||
this.registerStore(AuthStore, "auth");
|
||||
}
|
||||
|
||||
logout() {
|
||||
/**
|
||||
* Get a store by model name.
|
||||
*
|
||||
* @param modelName
|
||||
*/
|
||||
public getStoreForModelName<K extends keyof RootStore>(
|
||||
modelName: string
|
||||
): RootStore[K] {
|
||||
const storeName = this.getStoreNameForModelName(modelName);
|
||||
const store = this[storeName];
|
||||
invariant(store, `No store found for model name "${modelName}"`);
|
||||
|
||||
return store;
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear all data from the stores except for auth and ui.
|
||||
*/
|
||||
public clear() {
|
||||
Object.getOwnPropertyNames(this)
|
||||
.filter((key) => ["auth", "ui"].includes(key) === false)
|
||||
.forEach((key) => {
|
||||
this[key]?.clear?.();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Register a store with the root store.
|
||||
*
|
||||
* @param StoreClass
|
||||
*/
|
||||
private registerStore<T = typeof Store>(StoreClass: T, name?: string) {
|
||||
// @ts-expect-error TS thinks we are instantiating an abstract class.
|
||||
const store = new StoreClass(this);
|
||||
const storeName = name ?? this.getStoreNameForModelName(store.modelName);
|
||||
this[storeName] = store;
|
||||
}
|
||||
|
||||
private getStoreNameForModelName(modelName: string) {
|
||||
return pluralize(modelName.toLowerCase());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,8 +7,6 @@ import Store, { RPCAction } from "./base/Store";
|
||||
export default class SearchesStore extends Store<SearchQuery> {
|
||||
actions = [RPCAction.List, RPCAction.Delete];
|
||||
|
||||
apiEndpoint = "searches";
|
||||
|
||||
constructor(rootStore: RootStore) {
|
||||
super(rootStore, SearchQuery);
|
||||
}
|
||||
|
||||
@@ -2,7 +2,7 @@ import invariant from "invariant";
|
||||
import lowerFirst from "lodash/lowerFirst";
|
||||
import orderBy from "lodash/orderBy";
|
||||
import { observable, action, computed, runInAction } from "mobx";
|
||||
import { Class } from "utility-types";
|
||||
import pluralize from "pluralize";
|
||||
import RootStore from "~/stores/RootStore";
|
||||
import Policy from "~/models/Policy";
|
||||
import Model from "~/models/base/Model";
|
||||
@@ -22,8 +22,6 @@ export enum RPCAction {
|
||||
|
||||
type FetchPageParams = PaginationParams & Record<string, any>;
|
||||
|
||||
export const DEFAULT_PAGINATION_LIMIT = 25;
|
||||
|
||||
export const PAGINATION_SYMBOL = Symbol.for("pagination");
|
||||
|
||||
export default abstract class Store<T extends Model> {
|
||||
@@ -39,7 +37,7 @@ export default abstract class Store<T extends Model> {
|
||||
@observable
|
||||
isLoaded = false;
|
||||
|
||||
model: Class<T>;
|
||||
model: typeof Model;
|
||||
|
||||
modelName: string;
|
||||
|
||||
@@ -56,13 +54,13 @@ export default abstract class Store<T extends Model> {
|
||||
RPCAction.Count,
|
||||
];
|
||||
|
||||
constructor(rootStore: RootStore, model: Class<T>) {
|
||||
constructor(rootStore: RootStore, model: typeof Model) {
|
||||
this.rootStore = rootStore;
|
||||
this.model = model;
|
||||
this.modelName = lowerFirst(model.name).replace(/\d$/, "");
|
||||
this.modelName = model.modelName;
|
||||
|
||||
if (!this.apiEndpoint) {
|
||||
this.apiEndpoint = `${this.modelName}s`;
|
||||
this.apiEndpoint = pluralize(lowerFirst(model.modelName));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -89,6 +87,7 @@ export default abstract class Store<T extends Model> {
|
||||
return existingModel;
|
||||
}
|
||||
|
||||
// @ts-expect-error TS thinks that we're instantiating an abstract class here
|
||||
const newModel = new ModelClass(item, this);
|
||||
this.data.set(newModel.id, newModel);
|
||||
return newModel;
|
||||
@@ -103,20 +102,21 @@ export default abstract class Store<T extends Model> {
|
||||
const inverseRelations = getInverseRelationsForModelClass(this.model);
|
||||
|
||||
inverseRelations.forEach((relation) => {
|
||||
// TODO: Need a better way to get the store for a given model name.
|
||||
const store = this.rootStore[`${relation.modelName.toLowerCase()}s`];
|
||||
const items = store.orderedData.filter(
|
||||
(item: Model) => item[relation.idKey] === id
|
||||
);
|
||||
const store = this.rootStore.getStoreForModelName(relation.modelName);
|
||||
if ("orderedData" in store) {
|
||||
const items = (store.orderedData as Model[]).filter(
|
||||
(item) => item[relation.idKey] === id
|
||||
);
|
||||
|
||||
if (relation.options.onDelete === "cascade") {
|
||||
items.forEach((item: Model) => store.remove(item.id));
|
||||
}
|
||||
if (relation.options.onDelete === "cascade") {
|
||||
items.forEach((item) => store.remove(item.id));
|
||||
}
|
||||
|
||||
if (relation.options.onDelete === "null") {
|
||||
items.forEach((item: Model) => {
|
||||
item[relation.idKey] = null;
|
||||
});
|
||||
if (relation.options.onDelete === "null") {
|
||||
items.forEach((item) => {
|
||||
item[relation.idKey] = null;
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
Reference in New Issue
Block a user