diff --git a/config/ci_test.yaml.example b/config/ci_test.yaml.example index 178999eab5bfbc82269149dc6b3e3b946e7b0489..135d40ef37ffa28711025b9ab4bb135381094664 100644 --- a/config/ci_test.yaml.example +++ b/config/ci_test.yaml.example @@ -211,3 +211,26 @@ dimensions: parent: "dim:0" relation: "year" description: "A dimension of Blendb. Has 1 possible value." +enumTypes: + - + name: "enum type:0" + values: + - "test:0" + - "test:1" + - "test:2" + - "test:3" + - + name: "enum type:1" + values: + - "test:4" + - "test:5" + - "test:6" + - + name: "enum type:2" + values: + - "test:7" + - "test:8" + - + name: "enum type:3" + values: + - "test:9" diff --git a/specs/blendb-api-v1.raml b/specs/blendb-api-v1.raml index 2693c9cae169ea0dbc0c6d65322bc9d88f869b71..a8ca0cba4b0f2bb688a46f2a2bf7cb52a5273d32 100644 --- a/specs/blendb-api-v1.raml +++ b/specs/blendb-api-v1.raml @@ -287,7 +287,13 @@ traits: the system and their descriptions. securedBy: [ null, oauth_2_0 ] get: - +/enumtypes: + description: | + A EnumType is short for enumerable type. This is a special data type that only accepts a few possible values. This + collection allows the user to list all the enumerable types available in the system, their descriptions and possible + values. + get: + securedBy: [ null, oauth_2_0 ] /data: description: | This is the main part of the API. You may query it for report diff --git a/src/api/controllers/engine.spec.ts b/src/api/controllers/engine.spec.ts index 0d1ea0804b331b7c11197cc826df18bb32687410..3151989c3277c95d289931edc66335e5e94f7f80 100644 --- a/src/api/controllers/engine.spec.ts +++ b/src/api/controllers/engine.spec.ts @@ -48,5 +48,15 @@ describe("API engine controller", () => { }) .end(done); }); + it("should respond 200 and the list of enumTypes", (done) => { + request(server) + .get("/v1/enumtypes") + .expect((res: any) => { + let result = res.body; + expect(result).to.be.an("array"); + expect(result).to.have.length(4); + }) + .end(done); + }); }); diff --git a/src/api/controllers/engine.ts b/src/api/controllers/engine.ts index 18de1e1a4252ecfed38bf340af6fe67a21b2f6fe..874e7513bd602449c21fdcdb87d84a3ecf7644d6 100644 --- a/src/api/controllers/engine.ts +++ b/src/api/controllers/engine.ts @@ -29,4 +29,8 @@ export class EngineCtrl { public static dimensions(req: Request, res: express.Response, next: express.NextFunction) { res.status(200).json(req.engine.getDimensionsDescription()); } + + public static enumTypes(req: Request, res: express.Response, next: express.NextFunction) { + res.status(200).json(req.engine.getEnumTypesDescription()); + } } diff --git a/src/api/middlewares/engine.ts b/src/api/middlewares/engine.ts index 8d1f764ea508530ce7f80e287add83de759bb97b..e01638997ca4898626ecc727886c2db3bda7388f 100644 --- a/src/api/middlewares/engine.ts +++ b/src/api/middlewares/engine.ts @@ -28,6 +28,7 @@ export function EngineMw (config: ParsedConfig): Middleware { config.metrics.forEach ((met) => engine.addMetric(met)); config.dimensions.forEach ((dim) => engine.addDimension(dim)); config.views.forEach ((view) => engine.addView(view)); + config.enumTypes.forEach ((enumt) => engine.addEnumType(enumt)); return function engineMiddleware(req, res, next) { req.engine = engine; diff --git a/src/api/router-v1.ts b/src/api/router-v1.ts index 53f3c05cf4998c2fa4fc90a30cee43fbef87b7b8..88073edc4292246914ab829a0f404099c5ecb1da 100644 --- a/src/api/router-v1.ts +++ b/src/api/router-v1.ts @@ -29,5 +29,6 @@ export const router = osprey.Router(); router.get("/metrics", EngineCtrl.metrics); router.get("/dimensions", EngineCtrl.dimensions); +router.get("/enumtypes", EngineCtrl.enumTypes); router.get("/data", DataCtrl.read); router.post("/collect/{class}", CollectCtrl.write); diff --git a/src/core/engine.ts b/src/core/engine.ts index c359596cb1d43892b96284ecfc0426391c76b878..c18c96b2ae2a66137586d9e53c67d8c750508c2f 100644 --- a/src/core/engine.ts +++ b/src/core/engine.ts @@ -25,14 +25,17 @@ import { Filter } from "./filter"; import { View } from "./view"; import { Query } from "../common/query"; import { Graph } from "../util/graph"; +import { EnumType, EnumTypeOptions} from "./enumType"; export class Engine { private views: View[] = []; private metrics: Metric[] = []; + private enumTypes: EnumType[] = []; private dimensions: Dimension[] = []; private graph: Graph; constructor () { + this.enumTypes = []; this.views = []; this.metrics = []; this.dimensions = []; @@ -47,6 +50,10 @@ export class Engine { return this.metrics.map((i) => i.strOptions()); } + public getEnumTypesDescription(): EnumTypeOptions[] { + return this.enumTypes.map((i) => i.strOptions()); + } + public getDimensionsDescription() { return this.dimensions.map((i) => i.strOptions()); } @@ -60,6 +67,11 @@ export class Engine { return null; } + public addEnumType(enumType: EnumType) { + this.enumTypes.push(enumType); + return enumType; + } + public addMetric(metric: Metric) { if (this.graph.addMetric(metric)) { this.metrics.push(metric); diff --git a/src/core/enumType.ts b/src/core/enumType.ts new file mode 100644 index 0000000000000000000000000000000000000000..039b8b4a07921c85b4bc2cefa042eb8484bd271e --- /dev/null +++ b/src/core/enumType.ts @@ -0,0 +1,39 @@ +/* + * Copyright (C) 2018 Centro de Computacao Cientifica e Software Livre + * Departamento de Informatica - Universidade Federal do Parana + * + * This file is part of blend. + * + * blend is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * blend is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with blend. If not, see <http://www.gnu.org/licenses/>. + */ + +export interface EnumTypeOptions { + name: string; + values: string[]; +} +export class EnumType { + public name: string; + public values: string[]; + + constructor(options: EnumTypeOptions) { + this.name = options.name; + this.values = options.values; + } + public strOptions(): EnumTypeOptions { + return{ + name: this.name, + values: this.values + }; + } +} diff --git a/src/util/configParser.ts b/src/util/configParser.ts index c4abac077eff6b79594ef40d19f723f9be037756..af4c0a9fb9d8fde92675ef0032ea805d7e9b2a3c 100644 --- a/src/util/configParser.ts +++ b/src/util/configParser.ts @@ -21,6 +21,7 @@ import { Metric, MetricOptions, MetricStrOptions } from "../core/metric"; import { Dimension, DimensionOptions, DimensionStrOptions } from "../core/dimension"; import { View, ViewOptions, LoadView } from "../core/view"; +import { EnumType, EnumTypeOptions } from "../core/enumType"; import { RelationType } from "../common/types"; import { Filter } from "../core/filter"; import { Clause } from "../core/clause"; @@ -42,6 +43,7 @@ interface ConfigSchema { views: ViewParsingOptions[]; metrics: MetricStrOptions[]; dimensions: DimensionStrOptions[]; + enumTypes: EnumTypeOptions[]; } interface BuildView { @@ -60,6 +62,7 @@ export interface ParsedConfig { connection: Connection; views: View[]; metrics: Metric[]; + enumTypes: EnumType[]; dimensions: Dimension[]; struct: LoadStruct; loadViews: LoadView[]; @@ -82,6 +85,10 @@ interface MetricMap { [key: string]: Metric; } +interface EnumTypeMap{ + [key: string]: EnumType; +} + export class ConfigParser { public static parse(configPath: string): ParsedConfig { let config: ConfigSchema = yaml.safeLoad(fs.readFileSync(configPath, { @@ -107,11 +114,13 @@ export class ConfigParser { let metricsOpts = config.metrics; let viewsOpts = config.views; let dimensionsOpts = config.dimensions; + let enumTypesOpts = config.enumTypes; let parsed: ParsedConfig = { adapter: process.env.BLENDB_ADAPTER || "postgres", connection: connection, views: [], metrics: [], + enumTypes: [], dimensions: [], struct: struct, loadViews: [], @@ -120,12 +129,18 @@ export class ConfigParser { let metMap: MetricMap = {}; let dimMap: DimensionMap = {}; + let enumMap: EnumTypeMap = {}; for (let i = 0; i < metricsOpts.length; ++i) { let met = new Metric(this.parseMetOpts(metricsOpts[i])); parsed.metrics.push(met); metMap[met.name] = met; } + for (let i = 0; i < enumTypesOpts.length; i++) { + let enumT = new EnumType((enumTypesOpts[i])); + parsed.enumTypes.push(enumT); + enumMap[enumT.name] = enumT; + } for (let i = 0; i < dimensionsOpts.length; ++i) { let dim = new Dimension(this.parseDimOpts(dimensionsOpts[i], parsed.dimensions)); diff --git a/tslint.json b/tslint.json index 5d8557a4c479d163bc46ebc9655a640887f6ffe2..9ff2666874a9cf86be918294959efa476481a69f 100644 --- a/tslint.json +++ b/tslint.json @@ -7,6 +7,6 @@ "trailing-comma": false, "interface-name": false, "max-line-length": false, - "member-ordering": false + "member-ordering": false } }