// (C) 2007-2021 GoodData Corporation import { flow, partial, get } from "lodash"; import { IMockProject, getAttributes, getDateAttributes } from "../../model/MockProject"; import { Application } from "express"; import { IElement } from "../../model/Element"; import { IError } from "../../model/Error"; import { objectUri } from "../../route/routes"; import * as HttpStatusCodes from "http-status-codes"; import { IOrder, orderByTitle } from "../helpers/ordering"; import { filterByTitle, filterByUri } from "../helpers/filtering"; import { getPage } from "../helpers/paging"; import { IAttribute } from "../../model/Attribute"; import { IDateAttribute } from "../../model/DateDataSet"; import { SortDirection } from "../../model/Visualization"; interface IValidElementsRequest { validElementsRequest: { uris?: string[]; complement?: boolean; includeTotalCountWithoutFilters?: boolean; restrictiveDefinition?: string; }; } interface IValidElementsResponse { validElements: { items: IElement[]; paging: { total: number; count: number; offset: number; }; totalCountWithoutFilters?: string; elementsMeta: { attribute: string; attributeDisplayForm: string; order: keyof IOrder; filter: string; }; }; } function getItems(project: IMockProject, attributeId: string): IElement[] { return project.elements.get(attributeId) || []; } function createError(attributeId: string): IError { return { error: { parameters: [attributeId], requestId: "PIeM4i3QEwcBhjvI:j7db5gbwtmwa3nac", component: "Resource::Elements::Service", errorClass: "GDC::Exception::User", message: "Object %s is not a display form", }, }; } function getPipeLine(items: IElement[], filter: string, order: string, uris: string[]): IElement[] { const getTitle = (item: IElement) => item.element.title; const getUri = (item: IElement) => item.element.uri; return flow( partial(filterByUri, uris, getUri), partial(filterByTitle, filter, getTitle), partial(orderByTitle, order, getTitle), )(items); } function getAttribute(project: IMockProject, identifier: string): IAttribute | IDateAttribute { const attributeHash = getAttributes(project).reduce((hash, attribute) => { return { ...hash, [attribute.content.displayForms[0].meta.identifier]: attribute, }; }, {}); const dateAttributeHash = getDateAttributes(project).reduce((hash, attribute) => { return { ...hash, [attribute.displayForms[0].meta.identifier]: attribute, }; }, {}); const hash = { ...attributeHash, ...dateAttributeHash, }; return hash[identifier]; } export const validElements = { register(app: Application, project: IMockProject) { app.post(`/gdc/md/${project.project.meta.identifier}/obj/:id/validElements`, (req, res) => { const attribute = getAttribute(project, req.params.id); if (attribute) { const requestBody: IValidElementsRequest = req.body; const projectId = project.project.meta.identifier; const uris = get(requestBody, "validElementsRequest.uris", []); const items: IElement[] = getPipeLine( getItems(project, attribute.meta.identifier), req.query.filter as string, req.query.order as string, uris, ); const { offset = 0, limit } = req.query; const sliced = getPage(items, Number(offset), Number(limit)); const body: IValidElementsResponse = { validElements: { items: sliced, paging: { total: items.length, count: sliced.length, offset: Number(offset), }, elementsMeta: { attribute: objectUri(projectId, attribute.meta.identifier), attributeDisplayForm: objectUri(projectId, req.params.id), order: (req.query.order || "asc") as SortDirection, filter: (req.query.filter || "") as string, }, }, }; res.status(HttpStatusCodes.OK).json(body); } else { res.status(HttpStatusCodes.BAD_REQUEST).json(createError(req.params.id)); } }); return app; }, };