mirror of
https://github.com/OneUptime/oneuptime.git
synced 2026-04-06 00:32:12 +02:00
type -> modeltype
This commit is contained in:
@@ -11,7 +11,6 @@ import { JSONObject } from 'Common/Types/JSON';
|
||||
import LoginUtil from '../Utils/Login';
|
||||
|
||||
const LoginPage: FunctionComponent = () => {
|
||||
const user: User = new User();
|
||||
const apiUrl: URL = LOGIN_API_URL;
|
||||
|
||||
return (
|
||||
@@ -46,8 +45,7 @@ const LoginPage: FunctionComponent = () => {
|
||||
</div>
|
||||
|
||||
<ModelForm<User>
|
||||
type={User}
|
||||
model={user}
|
||||
modelType={User}
|
||||
id="login-form"
|
||||
fields={[
|
||||
{
|
||||
|
||||
@@ -12,7 +12,6 @@ import URL from 'Common/Types/API/URL';
|
||||
import { SIGNUP_API_URL } from '../Utils/ApiPaths';
|
||||
|
||||
const RegisterPage: FunctionComponent = () => {
|
||||
const user: User = new User();
|
||||
const apiUrl: URL = SIGNUP_API_URL;
|
||||
|
||||
return (
|
||||
@@ -47,8 +46,7 @@ const RegisterPage: FunctionComponent = () => {
|
||||
</div>
|
||||
|
||||
<ModelForm<User>
|
||||
model={user}
|
||||
type={User}
|
||||
modelType={User}
|
||||
id="register-form"
|
||||
showAsColumns={2}
|
||||
maxPrimaryButtonWidth={true}
|
||||
|
||||
@@ -69,6 +69,23 @@ export default class BaseAPI<
|
||||
}
|
||||
);
|
||||
|
||||
// count
|
||||
router.post(
|
||||
`/${new this.entityType().getCrudApiPath()?.toString()}/count`,
|
||||
UserMiddleware.getUserMiddleware,
|
||||
async (
|
||||
req: ExpressRequest,
|
||||
res: ExpressResponse,
|
||||
next: NextFunction
|
||||
) => {
|
||||
try {
|
||||
await this.count(req, res);
|
||||
} catch (err) {
|
||||
next(err);
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
// Get Item
|
||||
router.post(
|
||||
`/${new this.entityType()
|
||||
@@ -225,6 +242,31 @@ export default class BaseAPI<
|
||||
return Response.sendListResponse(req, res, list, count);
|
||||
}
|
||||
|
||||
public async count(
|
||||
req: ExpressRequest,
|
||||
res: ExpressResponse
|
||||
): Promise<void> {
|
||||
|
||||
|
||||
let query: Query<BaseModel> = {};
|
||||
|
||||
if (req.body) {
|
||||
query = JSONFunctions.deserialize(
|
||||
req.body['query']
|
||||
) as Query<BaseModel>;
|
||||
}
|
||||
|
||||
const databaseProps: DatabaseCommonInteractionProps =
|
||||
this.getDatabaseCommonInteractionProps(req);
|
||||
|
||||
const count: PositiveNumber = await this.service.countBy({
|
||||
query,
|
||||
props: databaseProps,
|
||||
});
|
||||
|
||||
return Response.sendItemResponse(req, res, { count: count.toNumber() });
|
||||
}
|
||||
|
||||
public async getItem(
|
||||
req: ExpressRequest,
|
||||
res: ExpressResponse
|
||||
|
||||
@@ -63,11 +63,11 @@ class DatabaseService<TBaseModel extends BaseModel> {
|
||||
private model!: TBaseModel;
|
||||
|
||||
public constructor(
|
||||
type: { new (): TBaseModel },
|
||||
modelType: { new (): TBaseModel },
|
||||
postgresDatabase?: PostgresDatabase
|
||||
) {
|
||||
this.entityType = type;
|
||||
this.model = new type();
|
||||
this.entityType = modelType;
|
||||
this.model = new modelType();
|
||||
|
||||
if (postgresDatabase) {
|
||||
this.postgresDatabase = postgresDatabase;
|
||||
|
||||
@@ -13,6 +13,7 @@ export interface ComponentProps {
|
||||
title?: undefined | string;
|
||||
onClose?: undefined | (() => void);
|
||||
type?: undefined | AlertType;
|
||||
onClick?:(() => void) | undefined;
|
||||
}
|
||||
|
||||
const Alert: FunctionComponent<ComponentProps> = (
|
||||
@@ -48,6 +49,9 @@ const Alert: FunctionComponent<ComponentProps> = (
|
||||
<div
|
||||
className={`alert-label-icon flex label-arrow alert ${cssClass} alert-dismissible fade show`}
|
||||
role="alert"
|
||||
onClick={() => {
|
||||
props.onClick && props.onClick();
|
||||
}}
|
||||
>
|
||||
{props.onClose && (
|
||||
<button
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
import React, { ReactElement, useEffect, useState } from 'react';
|
||||
import Alert, { AlertType } from '../Alerts/Alert';
|
||||
import BaseModel from 'Common/Models/BaseModel';
|
||||
import Query from '../../Utils/ModelAPI/Query';
|
||||
import ModelAPI from '../../Utils/ModelAPI/ModelAPI';
|
||||
import HTTPErrorResponse from 'Common/Types/API/HTTPErrorResponse';
|
||||
import { JSONObject } from 'Common/Types/JSON';
|
||||
|
||||
export interface ComponentProps<TBaseModel extends BaseModel> {
|
||||
alertType: AlertType,
|
||||
modelType: { new(): TBaseModel },
|
||||
singularName: string;
|
||||
pluralName: string;
|
||||
query: Query<TBaseModel>;
|
||||
onCountFetchInit?: (() => void) | undefined;
|
||||
onClick?:(() => void) | undefined;
|
||||
}
|
||||
|
||||
const CounterModelAlert: Function = <TBaseModel extends BaseModel>(
|
||||
props: ComponentProps<TBaseModel>
|
||||
): ReactElement => {
|
||||
|
||||
const [isLoading, setIsLoading] = useState<boolean>(true);
|
||||
const [error, setError] = useState<string>('');
|
||||
const [count, setCount] = useState<number>(0);
|
||||
|
||||
const fetchCount: Function = async () => {
|
||||
setError('');
|
||||
setIsLoading(true);
|
||||
|
||||
if (props.onCountFetchInit) {
|
||||
props.onCountFetchInit();
|
||||
}
|
||||
|
||||
try {
|
||||
const count: number =
|
||||
await ModelAPI.count<TBaseModel>(
|
||||
props.modelType,
|
||||
props.query,
|
||||
);
|
||||
|
||||
setCount(count);
|
||||
} catch (err) {
|
||||
try {
|
||||
setError(
|
||||
((err as HTTPErrorResponse).data as JSONObject)[
|
||||
'error'
|
||||
] as string
|
||||
);
|
||||
} catch (e) {
|
||||
setError('Server Error. Please try again');
|
||||
}
|
||||
}
|
||||
|
||||
setIsLoading(false);
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
setIsLoading(true);
|
||||
fetchCount();
|
||||
setIsLoading(false);
|
||||
}, [])
|
||||
|
||||
if (error) {
|
||||
return <></>
|
||||
}
|
||||
|
||||
if (isLoading) {
|
||||
return <></>
|
||||
}
|
||||
|
||||
if (count === 0) {
|
||||
return <></>
|
||||
}
|
||||
|
||||
return (
|
||||
<Alert
|
||||
onClick={props.onClick}
|
||||
type={props.alertType}
|
||||
title={`${count} ${count > 1 ? props.pluralName : props.singularName}`}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
||||
export default CounterModelAlert;
|
||||
@@ -36,8 +36,7 @@ export enum FormType {
|
||||
}
|
||||
|
||||
export interface ComponentProps<TBaseModel extends BaseModel> {
|
||||
type: { new (): TBaseModel };
|
||||
model: TBaseModel;
|
||||
modelType: { new (): TBaseModel };
|
||||
id: string;
|
||||
onValidate?:
|
||||
| undefined
|
||||
@@ -77,6 +76,7 @@ const ModelForm: Function = <TBaseModel extends BaseModel>(
|
||||
useState<boolean>(false);
|
||||
const [error, setError] = useState<string>('');
|
||||
const [itemToEdit, setItemToEdit] = useState<TBaseModel | null>(null);
|
||||
const model = new props.modelType();
|
||||
|
||||
const getSelectFields: Function = (): Select<TBaseModel> => {
|
||||
const select: Select<TBaseModel> = {};
|
||||
@@ -101,7 +101,7 @@ const ModelForm: Function = <TBaseModel extends BaseModel>(
|
||||
? (Object.keys(field.field)[0] as string)
|
||||
: null;
|
||||
|
||||
if (key && props.model.isEntityColumn(key)) {
|
||||
if (key && model.isEntityColumn(key)) {
|
||||
(populate as JSONObject)[key] = true;
|
||||
}
|
||||
}
|
||||
@@ -129,7 +129,7 @@ const ModelForm: Function = <TBaseModel extends BaseModel>(
|
||||
userPermissions.push(Permission.Public);
|
||||
|
||||
const accessControl: Dictionary<ColumnAccessControl> =
|
||||
props.model.getColumnAccessControlForAllColumns();
|
||||
model.getColumnAccessControlForAllColumns();
|
||||
|
||||
let fieldsToSet: Fields<TBaseModel> = [];
|
||||
|
||||
@@ -175,7 +175,7 @@ const ModelForm: Function = <TBaseModel extends BaseModel>(
|
||||
}
|
||||
|
||||
const item: TBaseModel | null = await ModelAPI.getItem(
|
||||
props.type,
|
||||
props.modelType,
|
||||
props.modelIdToEdit,
|
||||
getSelectFields(),
|
||||
getPopulate()
|
||||
@@ -184,9 +184,9 @@ const ModelForm: Function = <TBaseModel extends BaseModel>(
|
||||
if (!item) {
|
||||
setError(
|
||||
`Cannot edit ${(
|
||||
props.model.singularName || 'item'
|
||||
model.singularName || 'item'
|
||||
).toLowerCase()}. It could be because you don't have enough permissions to read or edit this ${(
|
||||
props.model.singularName || 'item'
|
||||
model.singularName || 'item'
|
||||
).toLowerCase()}.`
|
||||
);
|
||||
}
|
||||
@@ -360,9 +360,9 @@ const ModelForm: Function = <TBaseModel extends BaseModel>(
|
||||
delete valuesToSend[key];
|
||||
}
|
||||
|
||||
let tBaseModel: TBaseModel = props.model.fromJSON(
|
||||
let tBaseModel: TBaseModel = model.fromJSON(
|
||||
valuesToSend,
|
||||
props.type
|
||||
props.modelType
|
||||
);
|
||||
|
||||
if (props.onBeforeCreate && props.formType === FormType.Create) {
|
||||
@@ -416,7 +416,7 @@ const ModelForm: Function = <TBaseModel extends BaseModel>(
|
||||
<BasicModelForm<TBaseModel>
|
||||
title={props.title}
|
||||
description={props.description}
|
||||
model={props.model}
|
||||
model={model}
|
||||
id={props.id}
|
||||
fields={fields}
|
||||
showAsColumns={props.showAsColumns}
|
||||
|
||||
@@ -10,7 +10,7 @@ import { IconProp } from '../Icon/Icon';
|
||||
import ConfirmModal from '../Modal/ConfirmModal';
|
||||
|
||||
export interface ComponentProps<TBaseModel extends BaseModel> {
|
||||
type: { new (): TBaseModel };
|
||||
modelType: { new (): TBaseModel };
|
||||
modelId: ObjectID;
|
||||
onDeleteSuccess: () => void;
|
||||
}
|
||||
@@ -18,7 +18,7 @@ export interface ComponentProps<TBaseModel extends BaseModel> {
|
||||
const ModelDelete: Function = <TBaseModel extends BaseModel>(
|
||||
props: ComponentProps<TBaseModel>
|
||||
): ReactElement => {
|
||||
const model: TBaseModel = new props.type();
|
||||
const model: TBaseModel = new props.modelType();
|
||||
const [showModal, setShowModal] = useState<boolean>(false);
|
||||
const [isLoading, setIsLoading] = useState<boolean>(false);
|
||||
const [error, setError] = useState<string>('');
|
||||
@@ -27,7 +27,7 @@ const ModelDelete: Function = <TBaseModel extends BaseModel>(
|
||||
const deleteItem: Function = async () => {
|
||||
setIsLoading(true);
|
||||
try {
|
||||
await ModelAPI.deleteItem<TBaseModel>(props.type, props.modelId);
|
||||
await ModelAPI.deleteItem<TBaseModel>(props.modelType, props.modelId);
|
||||
props.onDeleteSuccess && props.onDeleteSuccess();
|
||||
} catch (err) {
|
||||
try {
|
||||
|
||||
@@ -31,6 +31,7 @@ const CardModelDetail: Function = <TBaseModel extends BaseModel>(
|
||||
const [showModel, setShowModal] = useState<boolean>(false);
|
||||
const [item, setItem] = useState<TBaseModel | null>(null);
|
||||
const [refresher, setRefresher] = useState<boolean>(false);
|
||||
const model = new props.modelDetailProps.modelType();
|
||||
|
||||
useEffect(() => {
|
||||
const userProjectPermissions: UserProjectAccessPermission | null =
|
||||
@@ -40,7 +41,7 @@ const CardModelDetail: Function = <TBaseModel extends BaseModel>(
|
||||
userProjectPermissions &&
|
||||
userProjectPermissions.permissions &&
|
||||
PermissionHelper.doesPermissionsIntersect(
|
||||
props.modelDetailProps.model.updateRecordPermissions,
|
||||
model.updateRecordPermissions,
|
||||
userProjectPermissions.permissions.map(
|
||||
(item: UserPermission) => {
|
||||
return item.permission;
|
||||
@@ -52,7 +53,7 @@ const CardModelDetail: Function = <TBaseModel extends BaseModel>(
|
||||
if (props.isEditable && hasPermissionToEdit) {
|
||||
setCardButtons([
|
||||
{
|
||||
title: `Edit ${props.modelDetailProps.model.singularName}`,
|
||||
title: `Edit ${model.singularName}`,
|
||||
buttonStyle: ButtonStyleType.OUTLINE,
|
||||
onClick: () => {
|
||||
setShowModal(true);
|
||||
@@ -77,7 +78,7 @@ const CardModelDetail: Function = <TBaseModel extends BaseModel>(
|
||||
|
||||
{showModel ? (
|
||||
<ModelFromModal<TBaseModel>
|
||||
title={`Edit ${props.modelDetailProps.model.singularName}`}
|
||||
title={`Edit ${model.singularName}`}
|
||||
onClose={() => {
|
||||
setShowModal(false);
|
||||
}}
|
||||
@@ -86,13 +87,12 @@ const CardModelDetail: Function = <TBaseModel extends BaseModel>(
|
||||
setShowModal(false);
|
||||
setRefresher(!refresher);
|
||||
}}
|
||||
type={props.modelDetailProps.type}
|
||||
modelType={props.modelDetailProps.modelType}
|
||||
formProps={{
|
||||
model: props.modelDetailProps.model,
|
||||
id: `edit-${props.modelDetailProps.model.singularName?.toLowerCase()}-from`,
|
||||
id: `edit-${model.singularName?.toLowerCase()}-from`,
|
||||
fields: props.formFields || [],
|
||||
formType: FormType.Update,
|
||||
type: props.modelDetailProps.type,
|
||||
modelType: props.modelDetailProps.modelType,
|
||||
}}
|
||||
modelIdToEdit={item?._id}
|
||||
/>
|
||||
|
||||
@@ -22,8 +22,7 @@ import FieldType from './FieldType';
|
||||
import HiddenText from '../HiddenText/HiddenText';
|
||||
|
||||
export interface ComponentProps<TBaseModel extends BaseModel> {
|
||||
type: { new (): TBaseModel };
|
||||
model: TBaseModel;
|
||||
modelType: { new (): TBaseModel };
|
||||
id: string;
|
||||
fields: Array<Field<TBaseModel>>;
|
||||
onLoadingChange?: undefined | ((isLoading: boolean) => void);
|
||||
@@ -41,6 +40,8 @@ const ModelDetail: Function = <TBaseModel extends BaseModel>(
|
||||
const [error, setError] = useState<string>('');
|
||||
const [item, setItem] = useState<TBaseModel | null>(null);
|
||||
|
||||
const model = new props.modelType();
|
||||
|
||||
useEffect(() => {
|
||||
fetchItem();
|
||||
}, [props.refresher]);
|
||||
@@ -82,7 +83,7 @@ const ModelDetail: Function = <TBaseModel extends BaseModel>(
|
||||
userPermissions.push(Permission.Public);
|
||||
|
||||
const accessControl: Dictionary<ColumnAccessControl> =
|
||||
props.model.getColumnAccessControlForAllColumns();
|
||||
model.getColumnAccessControlForAllColumns();
|
||||
|
||||
const fieldsToSet: Array<Field<TBaseModel>> = [];
|
||||
|
||||
@@ -118,7 +119,7 @@ const ModelDetail: Function = <TBaseModel extends BaseModel>(
|
||||
setError('');
|
||||
try {
|
||||
const item: TBaseModel | null = await ModelAPI.getItem(
|
||||
props.type,
|
||||
props.modelType,
|
||||
props.modelId,
|
||||
getSelectFields()
|
||||
);
|
||||
@@ -126,9 +127,9 @@ const ModelDetail: Function = <TBaseModel extends BaseModel>(
|
||||
if (!item) {
|
||||
setError(
|
||||
`Cannot load ${(
|
||||
props.model.singularName || 'item'
|
||||
model.singularName || 'item'
|
||||
).toLowerCase()}. It could be because you don't have enough permissions to read this ${(
|
||||
props.model.singularName || 'item'
|
||||
model.singularName || 'item'
|
||||
).toLowerCase()}.`
|
||||
);
|
||||
}
|
||||
|
||||
@@ -13,7 +13,7 @@ import Alert, { AlertType } from '../Alerts/Alert';
|
||||
|
||||
export interface ComponentProps<TBaseModel extends BaseModel> {
|
||||
title: string;
|
||||
type: { new (): TBaseModel };
|
||||
modelType: { new (): TBaseModel };
|
||||
onClose?: undefined | (() => void);
|
||||
submitButtonText?: undefined | string;
|
||||
onSuccess?:
|
||||
@@ -47,7 +47,7 @@ const ModelFromModal: Function = <TBaseModel extends BaseModel>(
|
||||
{!error ? (
|
||||
<ModelForm<TBaseModel>
|
||||
{...props.formProps}
|
||||
type={props.type}
|
||||
modelType={props.modelType}
|
||||
modelIdToEdit={props.modelIdToEdit}
|
||||
hideSubmitButton={true}
|
||||
onLoadingChange={(isFormLoading: boolean) => {
|
||||
|
||||
@@ -40,8 +40,7 @@ import BadDataException from 'Common/Types/Exception/BadDataException';
|
||||
import Populate from '../../Utils/ModelAPI/Populate';
|
||||
|
||||
export interface ComponentProps<TBaseModel extends BaseModel> {
|
||||
model: TBaseModel;
|
||||
type: { new (): TBaseModel };
|
||||
modelType: { new (): TBaseModel };
|
||||
id: string;
|
||||
onFetchInit?:
|
||||
| undefined
|
||||
@@ -77,7 +76,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
): ReactElement => {
|
||||
const [tableColumns, setColumns] = useState<Array<TableColumn>>([]);
|
||||
const [cardButtons, setCardButtons] = useState<Array<CardButtonSchema>>([]);
|
||||
const model: TBaseModel = new props.type();
|
||||
const model: TBaseModel = new props.modelType();
|
||||
const [actionButtonSchema, setActionButtonSchema] = useState<
|
||||
Array<ActionButtonSchema>
|
||||
>([]);
|
||||
@@ -107,7 +106,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
const deleteItem: Function = async (id: ObjectID) => {
|
||||
setIsLoading(true);
|
||||
try {
|
||||
await ModelAPI.deleteItem<TBaseModel>(props.type, id);
|
||||
await ModelAPI.deleteItem<TBaseModel>(props.modelType, id);
|
||||
if (data.length === 1 && currentPageNumber > 1) {
|
||||
setCurrentPageNumber(currentPageNumber - 1);
|
||||
}
|
||||
@@ -138,7 +137,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
try {
|
||||
const listResult: ListResult<TBaseModel> =
|
||||
await ModelAPI.getList<TBaseModel>(
|
||||
props.type,
|
||||
props.modelType,
|
||||
{
|
||||
...query,
|
||||
...props.query,
|
||||
@@ -205,7 +204,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
? (Object.keys(column.field)[0] as string)
|
||||
: null;
|
||||
|
||||
if (key && props.model.isEntityColumn(key)) {
|
||||
if (key && model.isEntityColumn(key)) {
|
||||
(populate as JSONObject)[key] = true;
|
||||
}
|
||||
}
|
||||
@@ -222,7 +221,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
userProjectPermissions &&
|
||||
userProjectPermissions.permissions &&
|
||||
PermissionHelper.doesPermissionsIntersect(
|
||||
props.model.createRecordPermissions,
|
||||
model.createRecordPermissions,
|
||||
userProjectPermissions.permissions.map(
|
||||
(item: UserPermission) => {
|
||||
return item.permission;
|
||||
@@ -283,7 +282,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
}, [showTableFilter]);
|
||||
|
||||
const shouldDisableSort: Function = (columnName: string): boolean => {
|
||||
return props.model.isEntityColumn(columnName);
|
||||
return model.isEntityColumn(columnName);
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
@@ -295,7 +294,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
_id: true,
|
||||
};
|
||||
|
||||
const slugifyColumn: string | null = props.model.getSlugifyColumn();
|
||||
const slugifyColumn: string | null = model.getSlugifyColumn();
|
||||
|
||||
if (slugifyColumn) {
|
||||
(selectFields as Dictionary<boolean>)[slugifyColumn] = true;
|
||||
@@ -320,7 +319,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
userPermissions.push(Permission.Public);
|
||||
|
||||
const accessControl: Dictionary<ColumnAccessControl> =
|
||||
props.model.getColumnAccessControlForAllColumns();
|
||||
model.getColumnAccessControlForAllColumns();
|
||||
|
||||
for (const column of props.columns) {
|
||||
const key: string | null = column.field
|
||||
@@ -391,7 +390,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
userProjectPermissions &&
|
||||
userProjectPermissions.permissions &&
|
||||
PermissionHelper.doesPermissionsIntersect(
|
||||
props.model.deleteRecordPermissions,
|
||||
model.deleteRecordPermissions,
|
||||
userProjectPermissions.permissions.map(
|
||||
(item: UserPermission) => {
|
||||
return item.permission;
|
||||
@@ -404,7 +403,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
userProjectPermissions &&
|
||||
userProjectPermissions.permissions &&
|
||||
PermissionHelper.doesPermissionsIntersect(
|
||||
props.model.updateRecordPermissions,
|
||||
model.updateRecordPermissions,
|
||||
userProjectPermissions.permissions.map(
|
||||
(item: UserPermission) => {
|
||||
return item.permission;
|
||||
@@ -417,7 +416,7 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
userProjectPermissions &&
|
||||
userProjectPermissions.permissions &&
|
||||
PermissionHelper.doesPermissionsIntersect(
|
||||
props.model.readRecordPermissions,
|
||||
model.readRecordPermissions,
|
||||
userProjectPermissions.permissions.map(
|
||||
(item: UserPermission) => {
|
||||
return item.permission;
|
||||
@@ -592,16 +591,16 @@ const ModelTable: Function = <TBaseModel extends BaseModel>(
|
||||
fetchItems();
|
||||
}}
|
||||
onBeforeCreate={props.onBeforeCreate}
|
||||
type={props.type}
|
||||
type={props.modelType}
|
||||
formProps={{
|
||||
model: model,
|
||||
id: `create-${props.type.name}-from`,
|
||||
id: `create-${props.modelType.name}-from`,
|
||||
fields: props.formFields || [],
|
||||
formType:
|
||||
modalType === ModalType.Create
|
||||
? FormType.Create
|
||||
: FormType.Update,
|
||||
type: props.type,
|
||||
type: props.modelType,
|
||||
}}
|
||||
modelIdToEdit={
|
||||
currentEditableItem
|
||||
|
||||
@@ -101,7 +101,7 @@ export default class ModelAPI {
|
||||
}
|
||||
|
||||
public static async getList<TBaseModel extends BaseModel>(
|
||||
type: { new (): TBaseModel },
|
||||
modelType: { new (): TBaseModel },
|
||||
query: Query<TBaseModel>,
|
||||
limit: number,
|
||||
skip: number,
|
||||
@@ -109,7 +109,7 @@ export default class ModelAPI {
|
||||
sort: Sort<TBaseModel>,
|
||||
populate?: Populate<TBaseModel>
|
||||
): Promise<ListResult<TBaseModel>> {
|
||||
const model: TBaseModel = new type();
|
||||
const model: TBaseModel = new modelType();
|
||||
const apiPath: Route | null = model.getCrudApiPath();
|
||||
if (!apiPath) {
|
||||
throw new BadDataException(
|
||||
@@ -149,7 +149,7 @@ export default class ModelAPI {
|
||||
if (result.isSuccess()) {
|
||||
const list: Array<TBaseModel> = model.fromJSONArray(
|
||||
result.data as JSONArray,
|
||||
type
|
||||
modelType
|
||||
);
|
||||
|
||||
return {
|
||||
@@ -162,6 +162,49 @@ export default class ModelAPI {
|
||||
throw result;
|
||||
}
|
||||
|
||||
|
||||
|
||||
public static async count<TBaseModel extends BaseModel>(
|
||||
modelType: { new (): TBaseModel },
|
||||
query: Query<TBaseModel>
|
||||
): Promise<number> {
|
||||
const model: TBaseModel = new modelType();
|
||||
const apiPath: Route | null = model.getCrudApiPath();
|
||||
if (!apiPath) {
|
||||
throw new BadDataException(
|
||||
'This model does not support list operations.'
|
||||
);
|
||||
}
|
||||
|
||||
const apiUrl: URL = URL.fromURL(DASHBOARD_API_URL)
|
||||
.addRoute(apiPath)
|
||||
.addRoute('/count');
|
||||
|
||||
if (!apiUrl) {
|
||||
throw new BadDataException(
|
||||
'This model does not support count operations.'
|
||||
);
|
||||
}
|
||||
|
||||
const result: HTTPResponse<JSONArray> | HTTPErrorResponse =
|
||||
await API.fetch<JSONArray>(
|
||||
HTTPMethod.POST,
|
||||
apiUrl,
|
||||
{
|
||||
query: JSONFunctions.serialize(query as JSONObject)
|
||||
},
|
||||
this.getCommonHeaders()
|
||||
);
|
||||
|
||||
if (result.isSuccess()) {
|
||||
const count: number = result.count;
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
throw result;
|
||||
}
|
||||
|
||||
public static getCommonHeaders(): Dictionary<string> {
|
||||
const headers: Dictionary<string> = {};
|
||||
|
||||
@@ -175,12 +218,12 @@ export default class ModelAPI {
|
||||
}
|
||||
|
||||
public static async getItem<TBaseModel extends BaseModel>(
|
||||
type: { new (): TBaseModel },
|
||||
modelType: { new (): TBaseModel },
|
||||
id: ObjectID,
|
||||
select: Select<TBaseModel>,
|
||||
populate?: Populate<TBaseModel>
|
||||
): Promise<TBaseModel | null> {
|
||||
const apiPath: Route | null = new type().getCrudApiPath();
|
||||
const apiPath: Route | null = new modelType().getCrudApiPath();
|
||||
if (!apiPath) {
|
||||
throw new BadDataException(
|
||||
'This model does not support get operations.'
|
||||
@@ -218,10 +261,10 @@ export default class ModelAPI {
|
||||
}
|
||||
|
||||
public static async deleteItem<TBaseModel extends BaseModel>(
|
||||
type: { new (): TBaseModel },
|
||||
modelType: { new (): TBaseModel },
|
||||
id: ObjectID
|
||||
): Promise<void> {
|
||||
const apiPath: Route | null = new type().getCrudApiPath();
|
||||
const apiPath: Route | null = new modelType().getCrudApiPath();
|
||||
if (!apiPath) {
|
||||
throw new BadDataException(
|
||||
'This model does not support delete operations.'
|
||||
|
||||
@@ -28,8 +28,7 @@ const MonitorPage: FunctionComponent<PageComponentProps> = (
|
||||
]}
|
||||
>
|
||||
<ModelTable<Monitor>
|
||||
type={Monitor}
|
||||
model={new Monitor()}
|
||||
modelType={Monitor}
|
||||
id="Monitors-table"
|
||||
isDeleteable={false}
|
||||
isEditable={true}
|
||||
|
||||
@@ -28,8 +28,7 @@ const OnCallDutyPage: FunctionComponent<PageComponentProps> = (
|
||||
]}
|
||||
>
|
||||
<ModelTable<OnCallDuty>
|
||||
type={OnCallDuty}
|
||||
model={new OnCallDuty()}
|
||||
modelType={OnCallDuty}
|
||||
id="on-call-duty-table"
|
||||
isDeleteable={false}
|
||||
isEditable={true}
|
||||
|
||||
@@ -138,8 +138,7 @@ const APIKeyView: FunctionComponent<PageComponentProps> = (
|
||||
{/* API Key Permisison Table */}
|
||||
|
||||
<ModelTable<ApiKeyPermission>
|
||||
type={ApiKeyPermission}
|
||||
model={new ApiKeyPermission()}
|
||||
modelType={ApiKeyPermission}
|
||||
id="api-key-permission-table"
|
||||
isDeleteable={true}
|
||||
query={{
|
||||
@@ -254,7 +253,7 @@ const APIKeyView: FunctionComponent<PageComponentProps> = (
|
||||
/>
|
||||
|
||||
<ModelDelete
|
||||
type={ApiKey}
|
||||
modelType={ApiKey}
|
||||
modelId={modelId}
|
||||
onDeleteSuccess={() => {
|
||||
Navigation.navigate(
|
||||
|
||||
@@ -34,8 +34,7 @@ const APIKeys: FunctionComponent<PageComponentProps> = (
|
||||
sideMenu={<DashboardSideMenu />}
|
||||
>
|
||||
<ModelTable<ApiKey>
|
||||
type={ApiKey}
|
||||
model={new ApiKey()}
|
||||
modelType={ApiKey}
|
||||
id="api-keys-table"
|
||||
isDeleteable={false}
|
||||
isEditable={true}
|
||||
|
||||
@@ -34,8 +34,7 @@ const CustomSMTP: FunctionComponent<PageComponentProps> = (
|
||||
sideMenu={<DashboardSideMenu />}
|
||||
>
|
||||
<ModelTable<ProjectSmtpConfig>
|
||||
type={ProjectSmtpConfig}
|
||||
model={new ProjectSmtpConfig()}
|
||||
modelType={ProjectSmtpConfig}
|
||||
id="smtp-table"
|
||||
isDeleteable={true}
|
||||
isEditable={true}
|
||||
|
||||
@@ -39,7 +39,7 @@ const Settings: FunctionComponent<PageComponentProps> = (
|
||||
/>
|
||||
|
||||
<ModelDelete
|
||||
type={Project}
|
||||
modelType={Project}
|
||||
modelId={new ObjectID(props.currentProject?._id || '')}
|
||||
/>
|
||||
</Page>
|
||||
|
||||
@@ -37,8 +37,7 @@ const APIKeys: FunctionComponent<PageComponentProps> = (
|
||||
sideMenu={<DashboardSideMenu />}
|
||||
>
|
||||
<ModelTable<Label>
|
||||
type={Label}
|
||||
model={new Label()}
|
||||
modelType={Label}
|
||||
id="labels-table"
|
||||
isDeleteable={true}
|
||||
isEditable={true}
|
||||
|
||||
@@ -117,8 +117,7 @@ const TeamView: FunctionComponent<PageComponentProps> = (
|
||||
{/* Team Members Table */}
|
||||
|
||||
<ModelTable<TeamMember>
|
||||
type={TeamMember}
|
||||
model={new TeamMember()}
|
||||
modelType={TeamMember}
|
||||
id="table-team-member"
|
||||
isDeleteable={true}
|
||||
createVerb={'Invite'}
|
||||
@@ -190,8 +189,7 @@ const TeamView: FunctionComponent<PageComponentProps> = (
|
||||
{/* Team Permisison Table */}
|
||||
|
||||
<ModelTable<TeamPermission>
|
||||
type={TeamPermission}
|
||||
model={new TeamPermission()}
|
||||
modelType={TeamPermission}
|
||||
id="table-team-permission"
|
||||
isDeleteable={true}
|
||||
isEditable={true}
|
||||
@@ -298,7 +296,7 @@ const TeamView: FunctionComponent<PageComponentProps> = (
|
||||
/>
|
||||
|
||||
<ModelDelete
|
||||
type={Team}
|
||||
modelType={Team}
|
||||
modelId={
|
||||
new ObjectID(Navigation.getLastParam()?.toString() || '')
|
||||
}
|
||||
|
||||
@@ -34,8 +34,7 @@ const Teams: FunctionComponent<PageComponentProps> = (
|
||||
sideMenu={<DashboardSideMenu />}
|
||||
>
|
||||
<ModelTable<Team>
|
||||
type={Team}
|
||||
model={new Team()}
|
||||
modelType={Team}
|
||||
id="teams-table"
|
||||
isDeleteable={false}
|
||||
isEditable={true}
|
||||
|
||||
@@ -28,8 +28,7 @@ const StatusPages: FunctionComponent<PageComponentProps> = (
|
||||
]}
|
||||
>
|
||||
<ModelTable<StatusPage>
|
||||
type={StatusPage}
|
||||
model={new StatusPage()}
|
||||
modelType={StatusPage}
|
||||
id="status-page-table"
|
||||
isDeleteable={false}
|
||||
isEditable={true}
|
||||
|
||||
Reference in New Issue
Block a user