Merge branch 'plus-datasources' of github.com:Budibase/budibase into feature/opinionated-sql
This commit is contained in:
commit
01fabba959
4 changed files with 91 additions and 3 deletions
|
@ -5,6 +5,8 @@ const {
|
||||||
getQueryParams,
|
getQueryParams,
|
||||||
} = require("../../db/utils")
|
} = require("../../db/utils")
|
||||||
const { integrations } = require("../../integrations")
|
const { integrations } = require("../../integrations")
|
||||||
|
const plusIntegrations = require("../../integrations/plus")
|
||||||
|
const PostgresConnector = require("../../integrations/plus/Postgres")
|
||||||
|
|
||||||
exports.fetch = async function (ctx) {
|
exports.fetch = async function (ctx) {
|
||||||
const database = new CouchDB(ctx.appId)
|
const database = new CouchDB(ctx.appId)
|
||||||
|
@ -30,10 +32,12 @@ exports.save = async function (ctx) {
|
||||||
datasource._rev = response.rev
|
datasource._rev = response.rev
|
||||||
|
|
||||||
// Drain connection pools when configuration is changed
|
// Drain connection pools when configuration is changed
|
||||||
|
if (datasource.source) {
|
||||||
const source = integrations[datasource.source]
|
const source = integrations[datasource.source]
|
||||||
if (source && source.pool) {
|
if (source && source.pool) {
|
||||||
await source.pool.end()
|
await source.pool.end()
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ctx.status = 200
|
ctx.status = 200
|
||||||
ctx.message = "Datasource saved successfully."
|
ctx.message = "Datasource saved successfully."
|
||||||
|
@ -58,3 +62,26 @@ exports.find = async function (ctx) {
|
||||||
const database = new CouchDB(ctx.appId)
|
const database = new CouchDB(ctx.appId)
|
||||||
ctx.body = await database.get(ctx.params.datasourceId)
|
ctx.body = await database.get(ctx.params.datasourceId)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: merge endpoint with main datasource endpoint
|
||||||
|
exports.plus = async function (ctx) {
|
||||||
|
const db = new CouchDB(ctx.appId)
|
||||||
|
|
||||||
|
const PlusConnector = plusIntegrations[ctx.request.body.source]
|
||||||
|
|
||||||
|
const connector = new PlusConnector(ctx.request.body)
|
||||||
|
await connector.init()
|
||||||
|
|
||||||
|
const datasource = {
|
||||||
|
_id: generateDatasourceID(),
|
||||||
|
type: "datasource:plus",
|
||||||
|
...ctx.request.body,
|
||||||
|
entities: connector.tables,
|
||||||
|
relationships: {},
|
||||||
|
}
|
||||||
|
|
||||||
|
const response = await db.post(datasource)
|
||||||
|
datasource._rev = response.rev
|
||||||
|
|
||||||
|
ctx.body = datasource
|
||||||
|
}
|
||||||
|
|
|
@ -16,6 +16,7 @@ router
|
||||||
authorized(PermissionTypes.TABLE, PermissionLevels.READ),
|
authorized(PermissionTypes.TABLE, PermissionLevels.READ),
|
||||||
datasourceController.find
|
datasourceController.find
|
||||||
)
|
)
|
||||||
|
.post("/api/datasources/plus", datasourceController.plus)
|
||||||
.post("/api/datasources", authorized(BUILDER), datasourceController.save)
|
.post("/api/datasources", authorized(BUILDER), datasourceController.save)
|
||||||
.delete(
|
.delete(
|
||||||
"/api/datasources/:datasourceId/:revId",
|
"/api/datasources/:datasourceId/:revId",
|
||||||
|
|
5
packages/server/src/integrations/plus/index.js
Normal file
5
packages/server/src/integrations/plus/index.js
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
const postgres = require("./postgres")
|
||||||
|
|
||||||
|
module.exports = {
|
||||||
|
postgres,
|
||||||
|
}
|
55
packages/server/src/integrations/plus/postgres.js
Normal file
55
packages/server/src/integrations/plus/postgres.js
Normal file
|
@ -0,0 +1,55 @@
|
||||||
|
const { Pool } = require("pg")
|
||||||
|
const { FieldTypes } = require("../../constants")
|
||||||
|
|
||||||
|
const TYPE_MAP = {
|
||||||
|
text: FieldTypes.LONGFORM,
|
||||||
|
varchar: FieldTypes.STRING,
|
||||||
|
integer: FieldTypes.NUMBER,
|
||||||
|
bigint: FieldTypes.NUMBER,
|
||||||
|
decimal: FieldTypes.NUMBER,
|
||||||
|
smallint: FieldTypes.NUMBER,
|
||||||
|
timestamp: FieldTypes.DATETIME,
|
||||||
|
time: FieldTypes.DATETIME,
|
||||||
|
boolean: FieldTypes.BOOLEAN,
|
||||||
|
}
|
||||||
|
|
||||||
|
class PostgresPlus {
|
||||||
|
static pool
|
||||||
|
COLUMNS_SQL =
|
||||||
|
"select * from information_schema.columns where table_schema = 'public'"
|
||||||
|
|
||||||
|
constructor(config) {
|
||||||
|
this.config = config
|
||||||
|
if (!this.pool) {
|
||||||
|
this.pool = new Pool(this.config)
|
||||||
|
}
|
||||||
|
|
||||||
|
this.client = this.pool
|
||||||
|
}
|
||||||
|
|
||||||
|
async init() {
|
||||||
|
const response = await this.client.query(this.COLUMNS_SQL)
|
||||||
|
|
||||||
|
const tables = {}
|
||||||
|
for (let column of response.rows) {
|
||||||
|
// table key doesn't exist yet
|
||||||
|
if (!tables[column.table_name]) {
|
||||||
|
tables[column.table_name] = []
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add the new column
|
||||||
|
const columnData = {
|
||||||
|
type: TYPE_MAP[column.data_type] || "unknown",
|
||||||
|
table: column.table_name,
|
||||||
|
name: column.column_name,
|
||||||
|
updateable: column.is_updatable,
|
||||||
|
precision: column.numeric_precision,
|
||||||
|
nullable: column.is_nullable === "YES",
|
||||||
|
}
|
||||||
|
tables[column.table_name].push(columnData)
|
||||||
|
}
|
||||||
|
this.tables = tables
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = PostgresPlus
|
Loading…
Reference in a new issue