1
0
Fork 0
mirror of synced 2024-06-27 02:20:35 +12:00

work on app instances

This commit is contained in:
michael shanks 2019-07-07 09:03:37 +01:00
parent 60deb10b45
commit 1590b584d4
19 changed files with 375 additions and 894 deletions

@ -1 +1 @@
Subproject commit 804483d3a3210936743f3b57a032783296eab06c
Subproject commit ab14ab9db1698a82b1f98b692ecfa6b71c17752a

View file

@ -273,6 +273,18 @@
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "instanceVersion",
"type": "string",
"typeOptions": {
"maxLength": null,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Instance Version",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "username",
"type": "string",

View file

@ -23,13 +23,6 @@ module.exports = (config) => {
const application = await apis.recordApi.load(appKey);
const dbConfig = await createInstanceDb(
datastoreModule,
config.datastoreConfig,
application.id,
instance.id
);
const versionId = $(instance.version.key, [
splitKey,
last
@ -41,6 +34,15 @@ module.exports = (config) => {
if(!await exists(runtimeDir))
await downloadAppPackage(apis, instance, application.name, versionId);
const dbConfig = await createInstanceDb(
config,
datastoreModule,
config.datastoreConfig,
application,
instance
);
instance.datastoreconfig = JSON.stringify(dbConfig);
instance.isNew = false;

View file

@ -1 +1,75 @@
{"levels":[{"name":"owner","permissions":[{"type":"create record","nodeKey":"/applications/1-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}"},{"type":"create record","nodeKey":"/applications/1-{id}/users/8-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}/users/8-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}/users/8-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}/users/8-{id}"},{"type":"create record","nodeKey":"/applications/1-{id}/instances/2-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}/instances/2-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}/instances/2-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}/instances/2-{id}"},{"type":"create record","nodeKey":"/applications/1-{id}/versions/3-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}/versions/3-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}/versions/3-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}/versions/3-{id}"},{"type":"create record","nodeKey":"/applications/1-{id}/sessions/16-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}/sessions/16-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}/sessions/16-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}/sessions/16-{id}"},{"type":"create record","nodeKey":"/sessions/17-{id}"},{"type":"update record","nodeKey":"/sessions/17-{id}"},{"type":"delete record","nodeKey":"/sessions/17-{id}"},{"type":"read record","nodeKey":"/sessions/17-{id}"},{"type":"read index","nodeKey":"/mastersessions_by_user"},{"type":"read index","nodeKey":"/all_applications"},{"type":"read index","nodeKey":"/applications/1-{id}/allinstances"},{"type":"read index","nodeKey":"/applications/1-{id}/sessions_by_user"},{"type":"read index","nodeKey":"/applications/1-{id}/user_name_lookup"},{"type":"read index","nodeKey":"/applications/1-{id}/all_versions"},{"type":"read index","nodeKey":"/applications/1-{id}/instances/2-{id}/users_on_this_instance"},{"type":"read index","nodeKey":"/applications/1-{id}/versions/3-{id}/instances_for_this_version"},{"type":"read index","nodeKey":"/applications/1-{id}/versions/3-{id}/instances_on_this_version"},{"type":"write templates"},{"type":"create user"},{"type":"set password"},{"type":"create temporary access"},{"type":"enable or disable user"},{"type":"write access levels"},{"type":"list users"},{"type":"list access levels"},{"type":"manage index"},{"type":"manage collection"},{"type":"set user access levels"}]}],"version":0}
{
"levels": [
{
"name": "owner",
"permissions": [
{
"type": "create record",
"nodeKey": "/customers/1-{id}"
},
{
"type": "delete record",
"nodeKey": "/customers/1-{id}"
},
{
"type": "update record",
"nodeKey": "/customers/1-{id}"
},
{
"type": "read record",
"nodeKey": "/customers/1-{id}"
},
{
"type": "create record",
"nodeKey": "/customers/1-{id}/invoices/2-{id}"
},
{
"type": "update record",
"nodeKey": "/customers/1-{id}/invoices/2-{id}"
},
{
"type": "delete record",
"nodeKey": "/customers/1-{id}/invoices/2-{id}"
},
{
"type": "read record",
"nodeKey": "/customers/1-{id}/invoices/2-{id}"
},
{
"type": "write templates"
},
{
"type": "create user"
},
{
"type": "set password"
},
{
"type": "create temporary access"
},
{
"type": "enable or disable user"
},
{
"type": "write access levels"
},
{
"type": "list users"
},
{
"type": "list access levels"
},
{
"type": "manage index"
},
{
"type": "set user access levels"
},
{
"type": "manage collection"
}
]
}
],
"version": 0
}

View file

@ -4,148 +4,36 @@
"type": "root",
"children": [
{
"name": "application",
"name": "customer",
"type": "record",
"fields": [
{
"name": "name",
"type": "string",
"typeOptions": {
"maxLength": 500,
"maxLength": 1000,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Name",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "domain",
"type": "string",
"typeOptions": {
"maxLength": 500,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "domain",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "application_resolve_strategy",
"type": "string",
"typeOptions": {
"maxLength": 100,
"values": [
"domain",
"path"
],
"allowDeclaredValuesOnly": true
},
"label": "Resolve Application By",
"label": "name",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [
{
"name": "user",
"name": "invoice",
"type": "record",
"fields": [
{
"name": "unique_name",
"type": "string",
"name": "amount",
"type": "number",
"typeOptions": {
"maxLength": 200,
"values": null,
"allowDeclaredValuesOnly": false
"minValue": 99999999999,
"maxValue": 99999999999,
"decimalPlaces": 2
},
"label": "Name (unique)",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "active",
"type": "bool",
"typeOptions": {
"allowNulls": false
},
"label": "Is Active",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "instance",
"type": "reference",
"typeOptions": {
"indexNodeKey": "/applications/1-{id}/allinstances",
"reverseIndexNodeKeys": [
"/applications/1-{id}/instances/2-{id}/users_on_this_instance"
],
"displayValue": "name"
},
"label": "Instance",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 8,
"indexes": [],
"allidsShardFactor": "64",
"collectionName": "users",
"isSingle": false
},
{
"name": "instance",
"type": "record",
"fields": [
{
"name": "name",
"type": "string",
"typeOptions": {
"maxLength": 1000,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Name",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "active",
"type": "bool",
"typeOptions": {
"allowNulls": false
},
"label": "Is Active",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "version",
"type": "reference",
"typeOptions": {
"indexNodeKey": "/applications/1-{id}/all_versions",
"reverseIndexNodeKeys": [
"/applications/1-{id}/versions/3-{id}/instances_on_this_version"
],
"displayValue": "name"
},
"label": "Version",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "datastoreconfig",
"type": "string",
"typeOptions": {
"maxLength": 1000,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Datastore Config",
"label": "amount",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
@ -153,277 +41,22 @@
"children": [],
"validationRules": [],
"nodeId": 2,
"indexes": [
{
"name": "users_on_this_instance",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "reference",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [],
"nodeId": 15
}
],
"allidsShardFactor": 1,
"collectionName": "instances",
"isSingle": false
},
{
"name": "version",
"type": "record",
"fields": [
{
"name": "name",
"type": "string",
"typeOptions": {
"maxLength": 200,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Name",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "package",
"type": "file",
"typeOptions": {},
"label": "Package",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 3,
"indexes": [
{
"name": "instances_for_this_version",
"type": "index",
"map": "return {name:record.name};",
"filter": "",
"indexType": "ancestor",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [],
"nodeId": 9
},
{
"name": "instances_on_this_version",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "reference",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [],
"nodeId": 10
}
],
"allidsShardFactor": 1,
"collectionName": "versions",
"isSingle": false
},
{
"name": "session",
"type": "record",
"fields": [
{
"name": "created",
"type": "number",
"typeOptions": {
"minValue": 0,
"maxValue": 99999999999999,
"decimalPlaces": 0
},
"label": "Created",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "user_json",
"type": "string",
"typeOptions": {
"maxLength": null,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "User Json",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "instanceDatastoreConfig",
"type": "string",
"typeOptions": {
"maxLength": null,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Instance Datastore Config",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "username",
"type": "string",
"typeOptions": {
"maxLength": null,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "User",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 16,
"indexes": [],
"allidsShardFactor": 1,
"collectionName": "sessions",
"collectionName": "invoices",
"isSingle": false
}
],
"validationRules": [],
"nodeId": 1,
"indexes": [
{
"name": "allinstances",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "ancestor",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
2
],
"nodeId": 23
},
{
"name": "sessions_by_user",
"type": "index",
"map": "return {username:record.username};",
"filter": "",
"indexType": "ancestor",
"getShardName": "return record.username.substring(0,2)",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
16
],
"nodeId": 24
},
{
"name": "user_name_lookup",
"type": "index",
"map": "return {name:record.unique_name, instanceDatastoreConfig:instance.datastoreconfig};",
"filter": "",
"indexType": "ancestor",
"getShardName": "return record.unique_name.substring(0,2)",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
8
],
"nodeId": 25
},
{
"name": "all_versions",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "ancestor",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
3
],
"nodeId": 26
}
],
"allidsShardFactor": 64,
"collectionName": "applications",
"isSingle": false
},
{
"name": "mastersession",
"type": "record",
"fields": [
{
"name": "user_json",
"type": "string",
"typeOptions": {
"maxLength": 10000,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "User Json",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "username",
"type": "string",
"typeOptions": {
"maxLength": null,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "User",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 17,
"indexes": [],
"allidsShardFactor": 64,
"collectionName": "sessions",
"collectionName": "customers",
"isSingle": false
}
],
"pathMaps": [],
"indexes": [
{
"name": "all_applications",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "ancestor",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
1
],
"nodeId": 22
},
{
"name": "mastersessions_by_user",
"type": "index",
"map": "return {username:record.username};",
"filter": "",
"indexType": "ancestor",
"getShardName": "return record.username.substring(0,2)",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
17
],
"nodeId": 27
}
],
"indexes": [],
"nodeId": 0
},
"actions": {
@ -439,7 +72,7 @@
"actionName": "output_to_file",
"eventName": "authApi:createUser:onComplete",
"optionsCreator": "return { filename:'tempaccess' + context.user.name, content:context.result.tempCode };",
"condition": ""
"condition": "!context.password"
}
]
}

View file

@ -1,28 +1,44 @@
const {
initialiseData,
setupDatastore
setupDatastore,
common
} = require("budibase-core");
const constructHierarchy = require("../utilities/constructHierarchy");
const getDatabaseManager = require("../utilities/databaseManager");
const masterDbAppDefinition = require("../appPackages/master/appDefinition.json");
const { applictionVersionPackage } = require("../utilities/createAppPackage");
const { last } = require("lodash/fp");
const {$,splitKey} = common;
module.exports = async (datastoreModule, rootDatastoreConfig, appId, instanceId) => {
module.exports = async (config, datastoreModule, rootDatastoreConfig, app, instance) => {
try {
const databaseManager = getDatabaseManager(
datastoreModule, rootDatastoreConfig);
await databaseManager.createEmptyInstanceDb(
appId, instanceId);
app.id, instance.id);
const dbConfig = databaseManager.getInstanceDatastoreConfig(
appId, instanceId);
app.id, instance.id);
const datastore = setupDatastore(
datastoreModule.getDatastore(dbConfig));
datastoreModule.getDatastore(dbConfig));
const versionId = $(instance.version.key, [
splitKey,
last
]);
await initialiseData(datastore,
constructHierarchy(masterDbAppDefinition));
const appPackage = applictionVersionPackage(
config, app.name, versionId
);
await initialiseData(
datastore,
appPackage.appDefinition,
appPackage.accessLevels);
return dbConfig;

View file

@ -42,6 +42,11 @@ module.exports = (config, app) => {
ctx.request.body.username
);
if(!instanceApi) {
ctx.request.status = StatusCodes.OK;
return;
}
await instanceApi.authApi.setPasswordFromTemporaryCode(
ctx.request.body.tempCode,
ctx.request.body.newPassword);
@ -54,6 +59,11 @@ module.exports = (config, app) => {
ctx.request.body.username
);
if(!instanceApi) {
ctx.request.status = StatusCodes.OK;
return;
}
await instanceApi.authApi.createTemporaryAccess(
ctx.request.body.username);

View file

@ -1 +0,0 @@
{"levels":[{"name":"owner","permissions":[{"type":"create record","nodeKey":"/applications/1-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}"},{"type":"create record","nodeKey":"/applications/1-{id}/users/8-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}/users/8-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}/users/8-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}/users/8-{id}"},{"type":"create record","nodeKey":"/applications/1-{id}/instances/2-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}/instances/2-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}/instances/2-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}/instances/2-{id}"},{"type":"create record","nodeKey":"/applications/1-{id}/versions/3-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}/versions/3-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}/versions/3-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}/versions/3-{id}"},{"type":"create record","nodeKey":"/applications/1-{id}/sessions/16-{id}"},{"type":"update record","nodeKey":"/applications/1-{id}/sessions/16-{id}"},{"type":"delete record","nodeKey":"/applications/1-{id}/sessions/16-{id}"},{"type":"read record","nodeKey":"/applications/1-{id}/sessions/16-{id}"},{"type":"create record","nodeKey":"/sessions/17-{id}"},{"type":"update record","nodeKey":"/sessions/17-{id}"},{"type":"delete record","nodeKey":"/sessions/17-{id}"},{"type":"read record","nodeKey":"/sessions/17-{id}"},{"type":"read index","nodeKey":"/mastersessions_by_user"},{"type":"read index","nodeKey":"/all_applications"},{"type":"read index","nodeKey":"/applications/1-{id}/allinstances"},{"type":"read index","nodeKey":"/applications/1-{id}/sessions_by_user"},{"type":"read index","nodeKey":"/applications/1-{id}/user_name_lookup"},{"type":"read index","nodeKey":"/applications/1-{id}/all_versions"},{"type":"read index","nodeKey":"/applications/1-{id}/instances/2-{id}/users_on_this_instance"},{"type":"read index","nodeKey":"/applications/1-{id}/versions/3-{id}/instances_for_this_version"},{"type":"read index","nodeKey":"/applications/1-{id}/versions/3-{id}/instances_on_this_version"},{"type":"write templates"},{"type":"create user"},{"type":"set password"},{"type":"create temporary access"},{"type":"enable or disable user"},{"type":"write access levels"},{"type":"list users"},{"type":"list access levels"},{"type":"manage index"},{"type":"manage collection"},{"type":"set user access levels"}]}],"version":0}

View file

@ -1,445 +0,0 @@
{
"hierarchy": {
"name": "root",
"type": "root",
"children": [
{
"name": "application",
"type": "record",
"fields": [
{
"name": "name",
"type": "string",
"typeOptions": {
"maxLength": 500,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Name",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "domain",
"type": "string",
"typeOptions": {
"maxLength": 500,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "domain",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "application_resolve_strategy",
"type": "string",
"typeOptions": {
"maxLength": 100,
"values": [
"domain",
"path"
],
"allowDeclaredValuesOnly": true
},
"label": "Resolve Application By",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [
{
"name": "user",
"type": "record",
"fields": [
{
"name": "unique_name",
"type": "string",
"typeOptions": {
"maxLength": 200,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Name (unique)",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "active",
"type": "bool",
"typeOptions": {
"allowNulls": false
},
"label": "Is Active",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "instance",
"type": "reference",
"typeOptions": {
"indexNodeKey": "/applications/1-{id}/allinstances",
"reverseIndexNodeKeys": [
"/applications/1-{id}/instances/2-{id}/users_on_this_instance"
],
"displayValue": "name"
},
"label": "Instance",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 8,
"indexes": [],
"allidsShardFactor": "64",
"collectionName": "users",
"isSingle": false
},
{
"name": "instance",
"type": "record",
"fields": [
{
"name": "name",
"type": "string",
"typeOptions": {
"maxLength": 1000,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Name",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "active",
"type": "bool",
"typeOptions": {
"allowNulls": false
},
"label": "Is Active",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "version",
"type": "reference",
"typeOptions": {
"indexNodeKey": "/applications/1-{id}/all_versions",
"reverseIndexNodeKeys": [
"/applications/1-{id}/versions/3-{id}/instances_on_this_version"
],
"displayValue": "name"
},
"label": "Version",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "datastoreconfig",
"type": "string",
"typeOptions": {
"maxLength": 1000,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Datastore Config",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 2,
"indexes": [
{
"name": "users_on_this_instance",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "reference",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [],
"nodeId": 15
}
],
"allidsShardFactor": 1,
"collectionName": "instances",
"isSingle": false
},
{
"name": "version",
"type": "record",
"fields": [
{
"name": "name",
"type": "string",
"typeOptions": {
"maxLength": 200,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Name",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "package",
"type": "file",
"typeOptions": {},
"label": "Package",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 3,
"indexes": [
{
"name": "instances_for_this_version",
"type": "index",
"map": "return {name:record.name};",
"filter": "",
"indexType": "ancestor",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [],
"nodeId": 9
},
{
"name": "instances_on_this_version",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "reference",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [],
"nodeId": 10
}
],
"allidsShardFactor": 1,
"collectionName": "versions",
"isSingle": false
},
{
"name": "session",
"type": "record",
"fields": [
{
"name": "created",
"type": "number",
"typeOptions": {
"minValue": 0,
"maxValue": 99999999999999,
"decimalPlaces": 0
},
"label": "Created",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "user_json",
"type": "string",
"typeOptions": {
"maxLength": null,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "User Json",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "instanceDatastoreConfig",
"type": "string",
"typeOptions": {
"maxLength": null,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "Instance Datastore Config",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "username",
"type": "string",
"typeOptions": {
"maxLength": null,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "User",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 16,
"indexes": [],
"allidsShardFactor": 1,
"collectionName": "sessions",
"isSingle": false
}
],
"validationRules": [],
"nodeId": 1,
"indexes": [
{
"name": "allinstances",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "ancestor",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
2
],
"nodeId": 23
},
{
"name": "sessions_by_user",
"type": "index",
"map": "return {username:record.username};",
"filter": "",
"indexType": "ancestor",
"getShardName": "return record.username.substring(0,2)",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
16
],
"nodeId": 24
},
{
"name": "user_name_lookup",
"type": "index",
"map": "return {name:record.unique_name, instanceDatastoreConfig:instance.datastoreconfig};",
"filter": "",
"indexType": "ancestor",
"getShardName": "return record.unique_name.substring(0,2)",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
8
],
"nodeId": 25
},
{
"name": "all_versions",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "ancestor",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
3
],
"nodeId": 26
}
],
"allidsShardFactor": 64,
"collectionName": "applications",
"isSingle": false
},
{
"name": "mastersession",
"type": "record",
"fields": [
{
"name": "user_json",
"type": "string",
"typeOptions": {
"maxLength": 10000,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "User Json",
"getInitialValue": "default",
"getUndefinedValue": "default"
},
{
"name": "username",
"type": "string",
"typeOptions": {
"maxLength": null,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "User",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 17,
"indexes": [],
"allidsShardFactor": 64,
"collectionName": "sessions",
"isSingle": false
}
],
"pathMaps": [],
"indexes": [
{
"name": "all_applications",
"type": "index",
"map": "return {...record};",
"filter": "",
"indexType": "ancestor",
"getShardName": "",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
1
],
"nodeId": 22
},
{
"name": "mastersessions_by_user",
"type": "index",
"map": "return {username:record.username};",
"filter": "",
"indexType": "ancestor",
"getShardName": "return record.username.substring(0,2)",
"getSortKey": "record.id",
"aggregateGroups": [],
"allowedRecordNodeIds": [
17
],
"nodeId": 27
}
],
"nodeId": 0
},
"actions": {
"output_to_file": {
"name": "output_to_file",
"behaviourSource": "main",
"behaviourName": "outputToFile",
"initialOptions": {}
}
},
"triggers": [
{
"actionName": "output_to_file",
"eventName": "authApi:createUser:onComplete",
"optionsCreator": "return { filename:'tempaccess' + context.user.name, content:context.result.tempCode };",
"condition": ""
}
]
}

View file

@ -0,0 +1,75 @@
{
"levels": [
{
"name": "owner",
"permissions": [
{
"type": "create record",
"nodeKey": "/customers/1-{id}"
},
{
"type": "delete record",
"nodeKey": "/customers/1-{id}"
},
{
"type": "update record",
"nodeKey": "/customers/1-{id}"
},
{
"type": "read record",
"nodeKey": "/customers/1-{id}"
},
{
"type": "create record",
"nodeKey": "/customers/1-{id}/invoices/2-{id}"
},
{
"type": "update record",
"nodeKey": "/customers/1-{id}/invoices/2-{id}"
},
{
"type": "delete record",
"nodeKey": "/customers/1-{id}/invoices/2-{id}"
},
{
"type": "read record",
"nodeKey": "/customers/1-{id}/invoices/2-{id}"
},
{
"type": "write templates"
},
{
"type": "create user"
},
{
"type": "set password"
},
{
"type": "create temporary access"
},
{
"type": "enable or disable user"
},
{
"type": "write access levels"
},
{
"type": "list users"
},
{
"type": "list access levels"
},
{
"type": "manage index"
},
{
"type": "set user access levels"
},
{
"type": "manage collection"
}
]
}
],
"version": 0
}

View file

@ -0,0 +1,78 @@
{
"hierarchy": {
"name": "root",
"type": "root",
"children": [
{
"name": "customer",
"type": "record",
"fields": [
{
"name": "name",
"type": "string",
"typeOptions": {
"maxLength": 1000,
"values": null,
"allowDeclaredValuesOnly": false
},
"label": "name",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [
{
"name": "invoice",
"type": "record",
"fields": [
{
"name": "amount",
"type": "number",
"typeOptions": {
"minValue": 99999999999,
"maxValue": 99999999999,
"decimalPlaces": 2
},
"label": "amount",
"getInitialValue": "default",
"getUndefinedValue": "default"
}
],
"children": [],
"validationRules": [],
"nodeId": 2,
"indexes": [],
"allidsShardFactor": 1,
"collectionName": "invoices",
"isSingle": false
}
],
"validationRules": [],
"nodeId": 1,
"indexes": [],
"allidsShardFactor": 64,
"collectionName": "customers",
"isSingle": false
}
],
"pathMaps": [],
"indexes": [],
"nodeId": 0
},
"actions": {
"output_to_file": {
"name": "output_to_file",
"behaviourSource": "main",
"behaviourName": "outputToFile",
"initialOptions": {}
}
},
"triggers": [
{
"actionName": "output_to_file",
"eventName": "authApi:createUser:onComplete",
"optionsCreator": "return { filename:'tempaccess' + context.user.name, content:context.result.tempCode };",
"condition": "!context.password"
}
]
}

View file

@ -6,7 +6,8 @@ beforeAll(async () => await app.start())
afterAll(async () => await app.destroy())
describe("authenticateMaster", () => authenticateMaster(app));
describe("authenticateMaster", () => authenticateMaster(app, "_master", () => app.masterAuth));
describe("createNewApp", () => createNewApp(app));
describe("authenticateTestApp", () => authenticateMaster(app, "testApp", () => app.user1_instance1));

View file

@ -2,27 +2,29 @@ const statusCodes = require("../utilities/statusCodes");
const { readFile } = require("../utilities/fsawait");
const { timeout } = require("./helpers");
module.exports = (app) => {
module.exports = (app, appName) => {
const credentials = app.credentials[appName];
it("should return unauthorized if username is incorrect", async () => {
await app.post("/_master/api/authenticate", {
await app.post(`/${appName}/api/authenticate`, {
username: "unknownuser",
password: app.masterAuth.password
password: credentials.password
})
.expect(statusCodes.UNAUTHORIZED);
})
it("should return unauthorized if password is incorrect", async () => {
await app.post("/_master/api/authenticate", {
username: app.masterAuth.username,
await app.post(`/${appName}/api/authenticate`, {
username: credentials.username,
password: "incorrect_password"
})
.expect(statusCodes.UNAUTHORIZED);
})
it("should not get cookie when unauthorized", async () => {
const response = await app.post("/_master/api/authenticate", {
username: app.masterAuth.username,
const response = await app.post(`/${appName}/api/authenticate`, {
username: credentials.username,
password: "incorrect_password"
});
@ -32,20 +34,20 @@ module.exports = (app) => {
it("should return ok correct username and password supplied", async () => {
const response = await app.post("/_master/api/authenticate", {
username: app.masterAuth.username,
password: app.masterAuth.password
const response = await app.post(`/${appName}/api/authenticate`, {
username: credentials.username,
password: credentials.password
})
.expect(statusCodes.OK);
app.masterAuth.cookie = response.header['set-cookie'];
credentials.cookie = response.header['set-cookie'];
});
const testUserName = "test_user";
const testUserName = appName + "_test_user";
let testPassword = "test_user_password";
it("should be able to create new user with authenticated cookie", async () => {
await app.post("/_master/api/createUser", {
await app.post(`/${appName}/api/createUser`, {
user: {
name: testUserName,
accessLevels:["owner"],
@ -54,7 +56,7 @@ module.exports = (app) => {
},
password: testPassword
})
.set("cookie", app.masterAuth.cookie)
.set("cookie", credentials.cookie)
.expect(statusCodes.OK);
@ -63,7 +65,7 @@ module.exports = (app) => {
let newUserCookie;
it("should be able to authenticate with new user", async () => {
const responseNewUser = await app.post("/_master/api/authenticate", {
const responseNewUser = await app.post(`/${appName}/api/authenticate`, {
username: testUserName,
password: testPassword
})
@ -72,7 +74,7 @@ module.exports = (app) => {
newUserCookie = responseNewUser.header['set-cookie'];
expect(newUserCookie).toBeDefined();
expect(newUserCookie).not.toEqual(app.masterAuth.cookie);
expect(newUserCookie).not.toEqual(credentials.cookie);
app.get("/_master/api/users/")
.set("cookie", newUserCookie)
@ -81,17 +83,18 @@ module.exports = (app) => {
it("should not be able to perform requests when user is disabled", async () => {
await app.post("/_master/api/disableUser", {
//HERE
await app.post(`/${appName}/api/disableUser`, {
username: testUserName
})
.set("cookie", app.masterAuth.cookie)
.set("cookie", credentials.cookie)
.expect(statusCodes.OK);
await app.get("/_master/api/users/")
await app.get(`/${appName}/api/users`)
.set("cookie", newUserCookie)
.expect(statusCodes.UNAUTHORIZED);
await app.post("/_master/api/authenticate", {
await app.post(`/${appName}/api/authenticate`, {
username: testUserName,
password: testPassword
})
@ -100,7 +103,7 @@ module.exports = (app) => {
});
it("should not be able to re-authenticate when user is disabled", async () => {
await app.post("/_master/api/authenticate", {
await app.post(`/${appName}/api/authenticate`, {
username: testUserName,
password: testPassword
})
@ -109,13 +112,13 @@ module.exports = (app) => {
it("should be able with re-authenticate when user is enabled again", async () => {
await app.post("/_master/api/enableUser", {
await app.post(`/${appName}/api/enableUser`, {
username: testUserName
})
.set("cookie", app.masterAuth.cookie)
.set("cookie", credentials.cookie)
.expect(statusCodes.OK);
await app.post("/_master/api/authenticate", {
await app.post(`/${appName}/api/authenticate`, {
username: testUserName,
password: testPassword
})
@ -125,7 +128,7 @@ module.exports = (app) => {
let testUserTempCode;
it("should be able to reset password with temporary access", async () => {
await app.post("/_master/api/createTemporaryAccess", {
await app.post(`/${appName}/api/createTemporaryAccess`, {
username: testUserName
})
.expect(statusCodes.OK);
@ -138,14 +141,14 @@ module.exports = (app) => {
const testUserTempCode = await readFile(`./tests/.data/tempaccess${testUserName}`, "utf8");
await app.post("/_master/api/setPasswordFromTemporaryCode", {
await app.post(`/${appName}/api/setPasswordFromTemporaryCode`, {
username: testUserName,
tempCode:testUserTempCode,
newPassword:testPassword
})
.expect(statusCodes.OK);
await app.post("/_master/api/authenticate", {
await app.post(`/${appName}/api/authenticate`, {
username: testUserName,
password: testPassword
})
@ -157,20 +160,20 @@ module.exports = (app) => {
it("should not be able to set password with used temp code", async () => {
await app.post("/_master/api/setPasswordFromTemporaryCode", {
await app.post(`/${appName}/api/setPasswordFromTemporaryCode`, {
username: testUserName,
tempCode:testUserTempCode,
newPassword:"whatever"
})
.expect(statusCodes.OK);
await app.post("/_master/api/authenticate", {
await app.post(`/${appName}/api/authenticate`, {
username: testUserName,
password: "whatever"
})
.expect(statusCodes.UNAUTHORIZED);
await app.post("/_master/api/authenticate", {
await app.post(`/${appName}/api/authenticate`, {
username: testUserName,
password: testPassword
})

View file

@ -25,11 +25,11 @@ module.exports = (app) => {
newAppKey = newApp.key;
await app.post(`/_master/api/record/${newApp.key}`, newApp)
.set("cookie", app.masterAuth.cookie)
.set("cookie", app.credentials._master.cookie)
.expect(statusCodes.OK);
const response = await app.get(`/_master/api/record/${newApp.key}`)
.set("cookie", app.masterAuth.cookie)
.set("cookie", app.credentials._master.cookie)
.expect(statusCodes.OK);
expect(response.body.name).toBe(newApp.name);
@ -49,12 +49,12 @@ module.exports = (app) => {
version1.package = { relativePath: "package.tar.gz", size};
await app.post(`/_master/api/record/${version1.key}`, version1)
.set("cookie", app.masterAuth.cookie)
.set("cookie", app.credentials._master.cookie)
.expect(statusCodes.OK);
await app.post(`/_master/api/files/${version1.key}`)
.attach("file", path, "package.tar.gz")
.set("cookie", app.masterAuth.cookie)
.set("cookie", app.credentials._master.cookie)
.expect(statusCodes.OK);
});
@ -69,11 +69,11 @@ module.exports = (app) => {
instance1.version = {key:version1Key, name:"v1", defaultAccessLevel:"owner"};
await app.post(`/_master/api/record/${instance1.key}`, instance1)
.set("cookie", app.masterAuth.cookie)
.set("cookie", app.credentials._master.cookie)
.expect(statusCodes.OK);
const loadInstanceResponse = await app.get(`/_master/api/record/${instance1.key}`)
.set("cookie", app.masterAuth.cookie)
.set("cookie", app.credentials._master.cookie)
.expect(statusCodes.OK);
instance1 = loadInstanceResponse.body;
@ -85,36 +85,37 @@ module.exports = (app) => {
const master = await getmaster();
user1_instance1 = master.recordApi
.getNew(`${newAppKey}/users`, "user");
user1_instance1.name = "testAppUser1";
user1_instance1.name = app.credentials.testApp.username;
/*const lookupResponse = await app.get(`/_master/api/lookup_field/${user1_instance1.key}?fields=instance`)
.set("cookie", app.masterAuth.cookie)
.set("cookie", app.credentials._master.cookie)
.expect(statusCodes.OK);
*/
user1_instance1.instance = instance1;
user1_instance1.active = true;
//await timeout(100);
await app.post(`/_master/api/record/${user1_instance1.key}`, user1_instance1)
.set("cookie", app.masterAuth.cookie)
.set("cookie", app.credentials._master.cookie)
.expect(statusCodes.OK);
});
it("should be able to set password for new user using temporary code", async () => {
const testUserTempCode = await readFile(`./tests/.data/tempaccess${user1_instance1.name}`, "utf8");
user1_instance1.password = "user1_instance1_password";
user1_instance1.password = app.credentials.testApp.password;
await app.post("/testApp/api/setPasswordFromTemporaryCode", {
username: user1_instance1.name,
username: app.credentials.testApp.username,
tempCode:testUserTempCode,
newPassword:user1_instance1.password
newPassword:app.credentials.testApp.password
})
.expect(statusCodes.OK);
await app.post("/testApp/api/authenticate", {
username: user1_instance1.name,
password: user1_instance1.password
username: app.credentials.testApp.username,
password: app.credentials.testApp.password
})
.expect(statusCodes.OK);
})
}

View file

@ -68,11 +68,19 @@ module.exports = () => {
server:() => server,
post: (url, body) => postRequest(server,url,body),
get: (url) => getRequest(server, url),
masterAuth: {
username: masterOwnerName,
password: masterOwnerPassword,
cookie: ""
credentials: {
_master: {
username: masterOwnerName,
password: masterOwnerPassword,
cookie: ""
},
testApp: {
username: "testAppUser1",
password: "user1_instance1_password",
cookie: ""
}
},
testAppInfo: {
name: "testApp"
},

View file

@ -9,11 +9,16 @@ const createAppPackage = (config, appPath) => {
const pluginsModule = require(
join(appPath, "plugins.js"));
const accessLevels = require(
join(appPath, "access_levels.json")
);
return ({
appDefinition: appDefModule,
behaviourSources: pluginsModule(config),
appPath
appPath,
accessLevels
})
}

View file

@ -89,6 +89,7 @@ module.exports = async (config) => {
const app = await getApplication(appname);
const userInMaster = await getUser(bb, app.id, username);
if(!userInMaster) return null;
const instance = await bb.recordApi.load(
userInMaster.instanceKey);
@ -115,6 +116,7 @@ module.exports = async (config) => {
session.user_json = JSON.stringify(authUser);
session.instanceDatastoreConfig = instance.datastoreconfig;
session.username = username;
session.instanceVersion = instance.version.key;
await bb.recordApi.save(session);
return session;
};
@ -140,9 +142,14 @@ module.exports = async (config) => {
const session = await bb.recordApi.load(`/applications/${app.id}/sessions/${customId}`);
const dsConfig = JSON.parse(session.instanceDatastoreConfig);
const instanceDatastore = getInstanceDatastore(dsConfig)
const versionId = $(session.instanceVersion,[
splitKey,
last
]);
return await getApisForSession(
instanceDatastore,
applictionVersionPackage(config, appname, session.instanceVersion),
applictionVersionPackage(config, appname, versionId),
session);
} catch(_) {
return null;
@ -172,6 +179,8 @@ module.exports = async (config) => {
const app = await getApplication(appname);
const user = await getUser(bb, app.id, username);
if(!user) return null;
const dsConfig = JSON.parse(user.instanceDatastoreConfig);
const instanceDatastore = getInstanceDatastore(
dsConfig