@budibase/worker 1.2.6 → 1.2.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@budibase/worker",
3
3
  "email": "hi@budibase.com",
4
- "version": "1.2.6",
4
+ "version": "1.2.9",
5
5
  "description": "Budibase background service",
6
6
  "main": "src/index.ts",
7
7
  "repository": {
@@ -35,10 +35,10 @@
35
35
  "author": "Budibase",
36
36
  "license": "GPL-3.0",
37
37
  "dependencies": {
38
- "@budibase/backend-core": "^1.2.6",
39
- "@budibase/pro": "1.2.5",
40
- "@budibase/string-templates": "^1.2.6",
41
- "@budibase/types": "^1.2.6",
38
+ "@budibase/backend-core": "^1.2.9",
39
+ "@budibase/pro": "1.2.8",
40
+ "@budibase/string-templates": "^1.2.9",
41
+ "@budibase/types": "^1.2.9",
42
42
  "@koa/router": "8.0.8",
43
43
  "@sentry/node": "6.17.7",
44
44
  "@techpass/passport-openidconnect": "0.3.2",
@@ -101,5 +101,5 @@
101
101
  "./scripts/jestSetup.js"
102
102
  ]
103
103
  },
104
- "gitHead": "7aa3a20ecc0f6d0f4617c6e703bf4f6f1998071e"
104
+ "gitHead": "c6e737e509e3e9651e726dbb4569252b8b355a17"
105
105
  }
@@ -0,0 +1,13 @@
1
+ const { migrate, MIGRATIONS } = require("../../../migrations")
2
+
3
+ export const runMigrations = async (ctx: any) => {
4
+ const options = ctx.request.body
5
+ // don't await as can take a while, just return
6
+ migrate(options)
7
+ ctx.status = 200
8
+ }
9
+
10
+ export const fetchDefinitions = async (ctx: any) => {
11
+ ctx.body = MIGRATIONS
12
+ ctx.status = 200
13
+ }
package/src/api/index.js CHANGED
@@ -106,7 +106,10 @@ router
106
106
  if (ctx.publicEndpoint) {
107
107
  return next()
108
108
  }
109
- if ((!ctx.isAuthenticated || !ctx.user.budibaseAccess) && !ctx.internal) {
109
+ if (
110
+ (!ctx.isAuthenticated || (ctx.user && !ctx.user.budibaseAccess)) &&
111
+ !ctx.internal
112
+ ) {
110
113
  ctx.throw(403, "Unauthorized - no public worker access")
111
114
  }
112
115
  return next()
@@ -12,6 +12,7 @@ const tenantsRoutes = require("./system/tenants")
12
12
  const statusRoutes = require("./system/status")
13
13
  const selfRoutes = require("./global/self")
14
14
  const licenseRoutes = require("./global/license")
15
+ const migrationRoutes = require("./system/migrations")
15
16
 
16
17
  let userGroupRoutes = api.groups
17
18
  exports.routes = [
@@ -29,4 +30,5 @@ exports.routes = [
29
30
  selfRoutes,
30
31
  licenseRoutes,
31
32
  userGroupRoutes,
33
+ migrationRoutes,
32
34
  ]
@@ -0,0 +1,19 @@
1
+ import Router from "@koa/router"
2
+ import * as migrationsController from "../../controllers/system/migrations"
3
+ import { auth } from "@budibase/backend-core"
4
+
5
+ const router = new Router()
6
+
7
+ router
8
+ .post(
9
+ "/api/system/migrations/run",
10
+ auth.internalApi,
11
+ migrationsController.runMigrations
12
+ )
13
+ .get(
14
+ "/api/system/migrations/definitions",
15
+ auth.internalApi,
16
+ migrationsController.fetchDefinitions
17
+ )
18
+
19
+ export = router
@@ -0,0 +1,20 @@
1
+ import { User } from "@budibase/types"
2
+ import * as sdk from "../../sdk"
3
+
4
+ /**
5
+ * Date:
6
+ * Aug 2022
7
+ *
8
+ * Description:
9
+ * Re-sync the global-db users to the global-info db users
10
+ */
11
+ export const run = async (globalDb: any) => {
12
+ const users = (await sdk.users.allUsers()) as User[]
13
+ const promises = []
14
+ for (let user of users) {
15
+ promises.push(
16
+ sdk.users.addTenant(user.tenantId, user._id as string, user.email)
17
+ )
18
+ }
19
+ await Promise.all(promises)
20
+ }
@@ -0,0 +1,74 @@
1
+ import { migrations, redis } from "@budibase/backend-core"
2
+ import { Migration, MigrationOptions, MigrationName } from "@budibase/types"
3
+ import env from "../environment"
4
+
5
+ // migration functions
6
+ import * as syncUserInfo from "./functions/globalInfoSyncUsers"
7
+
8
+ /**
9
+ * Populate the migration function and additional configuration from
10
+ * the static migration definitions.
11
+ */
12
+ export const buildMigrations = () => {
13
+ const definitions = migrations.DEFINITIONS
14
+ const workerMigrations: Migration[] = []
15
+
16
+ for (const definition of definitions) {
17
+ switch (definition.name) {
18
+ case MigrationName.GLOBAL_INFO_SYNC_USERS: {
19
+ // only needed in cloud
20
+ if (!env.SELF_HOSTED) {
21
+ workerMigrations.push({
22
+ ...definition,
23
+ fn: syncUserInfo.run,
24
+ })
25
+ }
26
+ break
27
+ }
28
+ }
29
+ }
30
+
31
+ return workerMigrations
32
+ }
33
+
34
+ export const MIGRATIONS = buildMigrations()
35
+
36
+ export const migrate = async (options?: MigrationOptions) => {
37
+ if (env.SELF_HOSTED) {
38
+ await migrateWithLock(options)
39
+ } else {
40
+ await migrations.runMigrations(MIGRATIONS, options)
41
+ }
42
+ }
43
+
44
+ const migrateWithLock = async (options?: MigrationOptions) => {
45
+ // get a new lock client
46
+ const redlock = await redis.clients.getMigrationsRedlock()
47
+ // lock for 15 minutes
48
+ const ttl = 1000 * 60 * 15
49
+
50
+ let migrationLock
51
+
52
+ // acquire lock
53
+ try {
54
+ migrationLock = await redlock.lock("migrations", ttl)
55
+ } catch (e: any) {
56
+ if (e.name === "LockError") {
57
+ return
58
+ } else {
59
+ throw e
60
+ }
61
+ }
62
+
63
+ // run migrations
64
+ try {
65
+ await migrations.runMigrations(MIGRATIONS, options)
66
+ } finally {
67
+ // release lock
68
+ try {
69
+ await migrationLock.unlock()
70
+ } catch (e) {
71
+ console.error("unable to release migration lock")
72
+ }
73
+ }
74
+ }
@@ -101,12 +101,11 @@ interface SaveUserOpts {
101
101
  bulkCreate?: boolean
102
102
  }
103
103
 
104
- export const buildUser = async (
104
+ const buildUser = async (
105
105
  user: any,
106
106
  opts: SaveUserOpts = {
107
107
  hashPassword: true,
108
108
  requirePassword: true,
109
- bulkCreate: false,
110
109
  },
111
110
  tenantId: string,
112
111
  dbUser?: any
@@ -185,15 +184,12 @@ export const save = async (
185
184
  dbUser = await db.get(_id)
186
185
  }
187
186
 
188
- let builtUser = await buildUser(
189
- user,
190
- {
191
- hashPassword: true,
192
- requirePassword: user.requirePassword,
193
- },
194
- tenantId,
195
- dbUser
196
- )
187
+ let builtUser = await buildUser(user, opts, tenantId, dbUser)
188
+
189
+ // make sure we set the _id field for a new user
190
+ if (!_id) {
191
+ _id = builtUser._id
192
+ }
197
193
 
198
194
  try {
199
195
  const putOpts = {
@@ -220,7 +216,7 @@ export const save = async (
220
216
  await addTenant(tenantId, _id, email)
221
217
  await cache.user.invalidateUser(response.id)
222
218
  // let server know to sync user
223
- await apps.syncUserInApps(builtUser._id)
219
+ await apps.syncUserInApps(_id)
224
220
 
225
221
  return {
226
222
  _id: response.id,
@@ -293,7 +289,6 @@ export const bulkCreate = async (
293
289
  {
294
290
  hashPassword: true,
295
291
  requirePassword: user.requirePassword,
296
- bulkCreate: false,
297
292
  },
298
293
  tenantId
299
294
  )
@@ -305,6 +300,9 @@ export const bulkCreate = async (
305
300
 
306
301
  // Post processing of bulk added users, i.e events and cache operations
307
302
  for (const user of usersToBulkSave) {
303
+ // TODO: Refactor to bulk insert users into the info db
304
+ // instead of relying on looping tenant creation
305
+ await addTenant(tenantId, user._id, user.email)
308
306
  await eventHelpers.handleSaveEvents(user, null)
309
307
  await apps.syncUserInApps(user._id)
310
308
  }