Syncing user metadata when builder opened as well as including all global user props for filtering/searching.
This commit is contained in:
parent
80789824b8
commit
311fe5f2eb
|
@ -44,6 +44,7 @@ const {
|
||||||
revertClientLibrary,
|
revertClientLibrary,
|
||||||
} = require("../../utilities/fileSystem/clientLibrary")
|
} = require("../../utilities/fileSystem/clientLibrary")
|
||||||
const { getTenantId, isMultiTenant } = require("@budibase/auth/tenancy")
|
const { getTenantId, isMultiTenant } = require("@budibase/auth/tenancy")
|
||||||
|
const { syncGlobalUsers } = require("./user")
|
||||||
|
|
||||||
const URL_REGEX_SLASH = /\/|\\/g
|
const URL_REGEX_SLASH = /\/|\\/g
|
||||||
|
|
||||||
|
@ -328,6 +329,8 @@ exports.sync = async ctx => {
|
||||||
if (!isDevAppID(appId)) {
|
if (!isDevAppID(appId)) {
|
||||||
ctx.throw(400, "This action cannot be performed for production apps")
|
ctx.throw(400, "This action cannot be performed for production apps")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// replicate prod to dev
|
||||||
const prodAppId = getDeployedAppID(appId)
|
const prodAppId = getDeployedAppID(appId)
|
||||||
const replication = new Replication({
|
const replication = new Replication({
|
||||||
source: prodAppId,
|
source: prodAppId,
|
||||||
|
@ -343,6 +346,10 @@ exports.sync = async ctx => {
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
error = err
|
error = err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// sync the users
|
||||||
|
await syncGlobalUsers(appId)
|
||||||
|
|
||||||
if (error) {
|
if (error) {
|
||||||
ctx.throw(400, error)
|
ctx.throw(400, error)
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -14,6 +14,8 @@ exports.fetchSelf = async ctx => {
|
||||||
}
|
}
|
||||||
|
|
||||||
const user = await getFullUser(ctx, userId)
|
const user = await getFullUser(ctx, userId)
|
||||||
|
// this shouldn't be returned by the app self
|
||||||
|
delete user.roles
|
||||||
|
|
||||||
if (appId) {
|
if (appId) {
|
||||||
const db = new CouchDB(appId)
|
const db = new CouchDB(appId)
|
||||||
|
@ -36,6 +38,7 @@ exports.fetchSelf = async ctx => {
|
||||||
// user has a role of some sort, return them
|
// user has a role of some sort, return them
|
||||||
else if (err.status === 404) {
|
else if (err.status === 404) {
|
||||||
const metadata = {
|
const metadata = {
|
||||||
|
...user,
|
||||||
_id: userId,
|
_id: userId,
|
||||||
}
|
}
|
||||||
const dbResp = await db.put(metadata)
|
const dbResp = await db.put(metadata)
|
||||||
|
|
|
@ -6,25 +6,58 @@ const {
|
||||||
const { InternalTables } = require("../../db/utils")
|
const { InternalTables } = require("../../db/utils")
|
||||||
const { getGlobalUsers } = require("../../utilities/global")
|
const { getGlobalUsers } = require("../../utilities/global")
|
||||||
const { getFullUser } = require("../../utilities/users")
|
const { getFullUser } = require("../../utilities/users")
|
||||||
|
const { isEqual } = require("lodash")
|
||||||
|
const { BUILTIN_ROLE_IDS } = require("@budibase/auth/roles")
|
||||||
|
|
||||||
function removeGlobalProps(user) {
|
exports.rawMetadata = async db => {
|
||||||
// make sure to always remove some of the global user props
|
return (
|
||||||
delete user.password
|
await db.allDocs(
|
||||||
delete user.roles
|
|
||||||
delete user.builder
|
|
||||||
return user
|
|
||||||
}
|
|
||||||
|
|
||||||
exports.fetchMetadata = async function (ctx) {
|
|
||||||
const database = new CouchDB(ctx.appId)
|
|
||||||
const global = await getGlobalUsers(ctx.appId)
|
|
||||||
const metadata = (
|
|
||||||
await database.allDocs(
|
|
||||||
getUserMetadataParams(null, {
|
getUserMetadataParams(null, {
|
||||||
include_docs: true,
|
include_docs: true,
|
||||||
})
|
})
|
||||||
)
|
)
|
||||||
).rows.map(row => row.doc)
|
).rows.map(row => row.doc)
|
||||||
|
}
|
||||||
|
|
||||||
|
exports.syncGlobalUsers = async appId => {
|
||||||
|
// sync user metadata
|
||||||
|
const db = new CouchDB(appId)
|
||||||
|
const [users, metadata] = await Promise.all([
|
||||||
|
getGlobalUsers(appId),
|
||||||
|
exports.rawMetadata(db),
|
||||||
|
])
|
||||||
|
const toWrite = []
|
||||||
|
for (let user of users) {
|
||||||
|
// skip users with no access
|
||||||
|
if (user.roleId === BUILTIN_ROLE_IDS.PUBLIC) {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
delete user._rev
|
||||||
|
const metadataId = generateUserMetadataID(user._id)
|
||||||
|
const newDoc = {
|
||||||
|
...user,
|
||||||
|
_id: metadataId,
|
||||||
|
tableId: InternalTables.USER_METADATA,
|
||||||
|
}
|
||||||
|
const found = metadata.find(doc => doc._id === metadataId)
|
||||||
|
// copy rev over for the purposes of equality check
|
||||||
|
if (found) {
|
||||||
|
newDoc._rev = found._rev
|
||||||
|
}
|
||||||
|
if (found == null || !isEqual(newDoc, found)) {
|
||||||
|
toWrite.push({
|
||||||
|
...found,
|
||||||
|
...newDoc,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
await db.bulkDocs(toWrite)
|
||||||
|
}
|
||||||
|
|
||||||
|
exports.fetchMetadata = async function (ctx) {
|
||||||
|
const database = new CouchDB(ctx.appId)
|
||||||
|
const global = await getGlobalUsers(ctx.appId)
|
||||||
|
const metadata = await exports.rawMetadata(database)
|
||||||
const users = []
|
const users = []
|
||||||
for (let user of global) {
|
for (let user of global) {
|
||||||
// find the metadata that matches up to the global ID
|
// find the metadata that matches up to the global ID
|
||||||
|
@ -52,7 +85,9 @@ exports.updateSelfMetadata = async function (ctx) {
|
||||||
exports.updateMetadata = async function (ctx) {
|
exports.updateMetadata = async function (ctx) {
|
||||||
const appId = ctx.appId
|
const appId = ctx.appId
|
||||||
const db = new CouchDB(appId)
|
const db = new CouchDB(appId)
|
||||||
const user = removeGlobalProps(ctx.request.body)
|
const user = ctx.request.body
|
||||||
|
// this isn't applicable to the user
|
||||||
|
delete user.roles
|
||||||
const metadata = {
|
const metadata = {
|
||||||
tableId: InternalTables.USER_METADATA,
|
tableId: InternalTables.USER_METADATA,
|
||||||
...user,
|
...user,
|
||||||
|
|
Loading…
Reference in New Issue