@budibase/backend-core 3.2.4 → 3.2.6
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/dist/index.js.map +1 -1
- package/dist/index.js.meta.json +1 -1
- package/dist/package.json +11 -4
- package/dist/plugins.js.meta.json +1 -1
- package/package.json +11 -4
- package/src/accounts/accounts.ts +0 -82
- package/src/accounts/api.ts +0 -59
- package/src/accounts/index.ts +0 -1
- package/src/auth/auth.ts +0 -210
- package/src/auth/index.ts +0 -1
- package/src/auth/tests/auth.spec.ts +0 -14
- package/src/blacklist/blacklist.ts +0 -54
- package/src/blacklist/index.ts +0 -1
- package/src/blacklist/tests/blacklist.spec.ts +0 -46
- package/src/cache/appMetadata.ts +0 -88
- package/src/cache/base/index.ts +0 -150
- package/src/cache/docWritethrough.ts +0 -105
- package/src/cache/generic.ts +0 -33
- package/src/cache/index.ts +0 -8
- package/src/cache/invite.ts +0 -86
- package/src/cache/passwordReset.ts +0 -49
- package/src/cache/tests/docWritethrough.spec.ts +0 -296
- package/src/cache/tests/user.spec.ts +0 -145
- package/src/cache/tests/writethrough.spec.ts +0 -139
- package/src/cache/user.ts +0 -154
- package/src/cache/writethrough.ts +0 -133
- package/src/configs/configs.ts +0 -263
- package/src/configs/index.ts +0 -1
- package/src/configs/tests/configs.spec.ts +0 -184
- package/src/constants/db.ts +0 -75
- package/src/constants/index.ts +0 -2
- package/src/constants/misc.ts +0 -36
- package/src/context/Context.ts +0 -14
- package/src/context/identity.ts +0 -58
- package/src/context/index.ts +0 -3
- package/src/context/mainContext.ts +0 -422
- package/src/context/tests/index.spec.ts +0 -255
- package/src/context/types.ts +0 -26
- package/src/db/Replication.ts +0 -94
- package/src/db/couch/DatabaseImpl.ts +0 -511
- package/src/db/couch/connections.ts +0 -89
- package/src/db/couch/index.ts +0 -4
- package/src/db/couch/pouchDB.ts +0 -97
- package/src/db/couch/pouchDump.ts +0 -0
- package/src/db/couch/tests/DatabaseImpl.spec.ts +0 -118
- package/src/db/couch/utils.ts +0 -55
- package/src/db/db.ts +0 -34
- package/src/db/errors.ts +0 -14
- package/src/db/index.ts +0 -12
- package/src/db/instrumentation.ts +0 -199
- package/src/db/lucene.ts +0 -721
- package/src/db/searchIndexes/index.ts +0 -1
- package/src/db/searchIndexes/searchIndexes.ts +0 -62
- package/src/db/tests/DatabaseImpl.spec.ts +0 -55
- package/src/db/tests/connections.spec.ts +0 -22
- package/src/db/tests/index.spec.ts +0 -32
- package/src/db/tests/lucene.spec.ts +0 -400
- package/src/db/tests/pouch.spec.js +0 -62
- package/src/db/tests/utils.spec.ts +0 -63
- package/src/db/utils.ts +0 -208
- package/src/db/views.ts +0 -245
- package/src/docIds/conversions.ts +0 -60
- package/src/docIds/ids.ts +0 -126
- package/src/docIds/index.ts +0 -2
- package/src/docIds/newid.ts +0 -5
- package/src/docIds/params.ts +0 -189
- package/src/docUpdates/index.ts +0 -24
- package/src/environment.ts +0 -293
- package/src/errors/errors.ts +0 -119
- package/src/errors/index.ts +0 -1
- package/src/events/analytics.ts +0 -6
- package/src/events/asyncEvents/index.ts +0 -2
- package/src/events/asyncEvents/publisher.ts +0 -12
- package/src/events/asyncEvents/queue.ts +0 -22
- package/src/events/backfill.ts +0 -183
- package/src/events/documentId.ts +0 -56
- package/src/events/events.ts +0 -47
- package/src/events/identification.ts +0 -311
- package/src/events/index.ts +0 -15
- package/src/events/processors/AnalyticsProcessor.ts +0 -64
- package/src/events/processors/AuditLogsProcessor.ts +0 -92
- package/src/events/processors/LoggingProcessor.ts +0 -36
- package/src/events/processors/Processors.ts +0 -52
- package/src/events/processors/async/DocumentUpdateProcessor.ts +0 -38
- package/src/events/processors/index.ts +0 -19
- package/src/events/processors/posthog/PosthogProcessor.ts +0 -118
- package/src/events/processors/posthog/index.ts +0 -3
- package/src/events/processors/posthog/rateLimiting.ts +0 -106
- package/src/events/processors/posthog/tests/PosthogProcessor.spec.ts +0 -164
- package/src/events/processors/types.ts +0 -1
- package/src/events/publishers/account.ts +0 -41
- package/src/events/publishers/ai.ts +0 -21
- package/src/events/publishers/app.ts +0 -168
- package/src/events/publishers/auditLog.ts +0 -26
- package/src/events/publishers/auth.ts +0 -73
- package/src/events/publishers/automation.ts +0 -110
- package/src/events/publishers/backfill.ts +0 -74
- package/src/events/publishers/backup.ts +0 -42
- package/src/events/publishers/datasource.ts +0 -48
- package/src/events/publishers/email.ts +0 -17
- package/src/events/publishers/environmentVariable.ts +0 -38
- package/src/events/publishers/group.ts +0 -99
- package/src/events/publishers/index.ts +0 -25
- package/src/events/publishers/installation.ts +0 -38
- package/src/events/publishers/layout.ts +0 -26
- package/src/events/publishers/license.ts +0 -84
- package/src/events/publishers/org.ts +0 -37
- package/src/events/publishers/plugin.ts +0 -47
- package/src/events/publishers/query.ts +0 -89
- package/src/events/publishers/role.ts +0 -62
- package/src/events/publishers/rows.ts +0 -29
- package/src/events/publishers/screen.ts +0 -36
- package/src/events/publishers/serve.ts +0 -43
- package/src/events/publishers/table.ts +0 -70
- package/src/events/publishers/user.ts +0 -202
- package/src/events/publishers/view.ts +0 -107
- package/src/features/features.ts +0 -277
- package/src/features/index.ts +0 -2
- package/src/features/tests/features.spec.ts +0 -267
- package/src/features/tests/utils.ts +0 -64
- package/src/helpers.ts +0 -9
- package/src/index.ts +0 -59
- package/src/installation.ts +0 -115
- package/src/logging/alerts.ts +0 -26
- package/src/logging/correlation/correlation.ts +0 -15
- package/src/logging/correlation/index.ts +0 -1
- package/src/logging/correlation/middleware.ts +0 -18
- package/src/logging/index.ts +0 -4
- package/src/logging/pino/logger.ts +0 -239
- package/src/logging/pino/middleware.ts +0 -48
- package/src/logging/system.ts +0 -81
- package/src/logging/tests/system.spec.ts +0 -61
- package/src/middleware/adminOnly.ts +0 -9
- package/src/middleware/auditLog.ts +0 -6
- package/src/middleware/authenticated.ts +0 -247
- package/src/middleware/builderOnly.ts +0 -21
- package/src/middleware/builderOrAdmin.ts +0 -21
- package/src/middleware/contentSecurityPolicy.ts +0 -113
- package/src/middleware/csrf.ts +0 -81
- package/src/middleware/errorHandling.ts +0 -43
- package/src/middleware/index.ts +0 -24
- package/src/middleware/internalApi.ts +0 -23
- package/src/middleware/ip.ts +0 -12
- package/src/middleware/joi-validator.ts +0 -58
- package/src/middleware/matchers.ts +0 -39
- package/src/middleware/passport/datasource/google.ts +0 -102
- package/src/middleware/passport/local.ts +0 -54
- package/src/middleware/passport/sso/google.ts +0 -77
- package/src/middleware/passport/sso/oidc.ts +0 -152
- package/src/middleware/passport/sso/sso.ts +0 -138
- package/src/middleware/passport/sso/tests/google.spec.ts +0 -68
- package/src/middleware/passport/sso/tests/oidc.spec.ts +0 -144
- package/src/middleware/passport/sso/tests/sso.spec.ts +0 -197
- package/src/middleware/passport/utils.ts +0 -38
- package/src/middleware/querystringToBody.ts +0 -28
- package/src/middleware/tenancy.ts +0 -36
- package/src/middleware/tests/builder.spec.ts +0 -181
- package/src/middleware/tests/contentSecurityPolicy.spec.ts +0 -75
- package/src/middleware/tests/matchers.spec.ts +0 -100
- package/src/migrations/definitions.ts +0 -40
- package/src/migrations/index.ts +0 -2
- package/src/migrations/migrations.ts +0 -186
- package/src/migrations/tests/__snapshots__/migrations.spec.ts.snap +0 -11
- package/src/migrations/tests/migrations.spec.ts +0 -64
- package/src/objectStore/buckets/app.ts +0 -53
- package/src/objectStore/buckets/global.ts +0 -29
- package/src/objectStore/buckets/index.ts +0 -3
- package/src/objectStore/buckets/plugins.ts +0 -71
- package/src/objectStore/buckets/tests/app.spec.ts +0 -161
- package/src/objectStore/buckets/tests/global.spec.ts +0 -74
- package/src/objectStore/buckets/tests/plugins.spec.ts +0 -111
- package/src/objectStore/cloudfront.ts +0 -41
- package/src/objectStore/index.ts +0 -3
- package/src/objectStore/objectStore.ts +0 -585
- package/src/objectStore/utils.ts +0 -113
- package/src/platform/index.ts +0 -3
- package/src/platform/platformDb.ts +0 -6
- package/src/platform/tenants.ts +0 -101
- package/src/platform/tests/tenants.spec.ts +0 -26
- package/src/platform/users.ts +0 -129
- package/src/plugin/index.ts +0 -1
- package/src/plugin/tests/validation.spec.ts +0 -209
- package/src/plugin/utils.ts +0 -175
- package/src/queue/constants.ts +0 -8
- package/src/queue/inMemoryQueue.ts +0 -189
- package/src/queue/index.ts +0 -2
- package/src/queue/listeners.ts +0 -199
- package/src/queue/queue.ts +0 -84
- package/src/redis/index.ts +0 -6
- package/src/redis/init.ts +0 -118
- package/src/redis/redis.ts +0 -358
- package/src/redis/redlockImpl.ts +0 -155
- package/src/redis/tests/redis.spec.ts +0 -207
- package/src/redis/tests/redlockImpl.spec.ts +0 -105
- package/src/redis/utils.ts +0 -128
- package/src/security/auth.ts +0 -24
- package/src/security/encryption.ts +0 -185
- package/src/security/index.ts +0 -1
- package/src/security/permissions.ts +0 -166
- package/src/security/roles.ts +0 -655
- package/src/security/secrets.ts +0 -20
- package/src/security/sessions.ts +0 -123
- package/src/security/tests/auth.spec.ts +0 -45
- package/src/security/tests/encryption.spec.ts +0 -31
- package/src/security/tests/permissions.spec.ts +0 -146
- package/src/security/tests/secrets.spec.ts +0 -35
- package/src/security/tests/sessions.spec.ts +0 -12
- package/src/sql/designDoc.ts +0 -17
- package/src/sql/index.ts +0 -5
- package/src/sql/sql.ts +0 -1854
- package/src/sql/sqlTable.ts +0 -319
- package/src/sql/utils.ts +0 -193
- package/src/tenancy/db.ts +0 -6
- package/src/tenancy/index.ts +0 -2
- package/src/tenancy/tenancy.ts +0 -148
- package/src/tenancy/tests/tenancy.spec.ts +0 -184
- package/src/timers/index.ts +0 -1
- package/src/timers/timers.ts +0 -22
- package/src/users/db.ts +0 -582
- package/src/users/events.ts +0 -176
- package/src/users/index.ts +0 -4
- package/src/users/lookup.ts +0 -99
- package/src/users/test/db.spec.ts +0 -188
- package/src/users/test/utils.spec.ts +0 -67
- package/src/users/users.ts +0 -353
- package/src/users/utils.ts +0 -81
- package/src/utils/Duration.ts +0 -56
- package/src/utils/hashing.ts +0 -15
- package/src/utils/index.ts +0 -4
- package/src/utils/stringUtils.ts +0 -8
- package/src/utils/tests/Duration.spec.ts +0 -19
- package/src/utils/tests/utils.spec.ts +0 -204
- package/src/utils/utils.ts +0 -249
- package/tests/core/logging.ts +0 -34
- package/tests/core/users/users.spec.js +0 -53
- package/tests/core/utilities/index.ts +0 -7
- package/tests/core/utilities/jestUtils.ts +0 -33
- package/tests/core/utilities/mocks/alerts.ts +0 -4
- package/tests/core/utilities/mocks/date.ts +0 -3
- package/tests/core/utilities/mocks/events.ts +0 -132
- package/tests/core/utilities/mocks/index.ts +0 -9
- package/tests/core/utilities/mocks/licenses.ts +0 -119
- package/tests/core/utilities/queue.ts +0 -9
- package/tests/core/utilities/structures/Chance.ts +0 -20
- package/tests/core/utilities/structures/accounts.ts +0 -80
- package/tests/core/utilities/structures/apps.ts +0 -21
- package/tests/core/utilities/structures/common.ts +0 -7
- package/tests/core/utilities/structures/db.ts +0 -12
- package/tests/core/utilities/structures/documents/index.ts +0 -1
- package/tests/core/utilities/structures/documents/platform/index.ts +0 -1
- package/tests/core/utilities/structures/documents/platform/installation.ts +0 -12
- package/tests/core/utilities/structures/generator.ts +0 -3
- package/tests/core/utilities/structures/index.ts +0 -15
- package/tests/core/utilities/structures/koa.ts +0 -16
- package/tests/core/utilities/structures/licenses.ts +0 -190
- package/tests/core/utilities/structures/plugins.ts +0 -19
- package/tests/core/utilities/structures/quotas.ts +0 -72
- package/tests/core/utilities/structures/scim.ts +0 -80
- package/tests/core/utilities/structures/sso.ts +0 -118
- package/tests/core/utilities/structures/tenants.ts +0 -5
- package/tests/core/utilities/structures/userGroups.ts +0 -10
- package/tests/core/utilities/structures/users.ts +0 -89
- package/tests/core/utilities/testContainerUtils.ts +0 -165
- package/tests/core/utilities/utils/index.ts +0 -2
- package/tests/core/utilities/utils/queue.ts +0 -27
- package/tests/core/utilities/utils/time.ts +0 -3
- package/tests/extra/DBTestConfiguration.ts +0 -36
- package/tests/extra/index.ts +0 -2
- package/tests/extra/testEnv.ts +0 -95
- package/tests/index.ts +0 -2
- package/tests/jestEnv.ts +0 -10
- package/tests/jestSetup.ts +0 -36
|
@@ -1,92 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
Event,
|
|
3
|
-
Identity,
|
|
4
|
-
IdentityType,
|
|
5
|
-
AuditLogQueueEvent,
|
|
6
|
-
AuditLogFn,
|
|
7
|
-
HostInfo,
|
|
8
|
-
} from "@budibase/types"
|
|
9
|
-
import { EventProcessor } from "./types"
|
|
10
|
-
import { getAppId, doInTenant, getTenantId } from "../../context"
|
|
11
|
-
import BullQueue from "bull"
|
|
12
|
-
import { createQueue, JobQueue } from "../../queue"
|
|
13
|
-
import { isAudited } from "../../utils"
|
|
14
|
-
import env from "../../environment"
|
|
15
|
-
|
|
16
|
-
export default class AuditLogsProcessor implements EventProcessor {
|
|
17
|
-
static auditLogsEnabled = false
|
|
18
|
-
static auditLogQueue: BullQueue.Queue<AuditLogQueueEvent>
|
|
19
|
-
|
|
20
|
-
// can't use constructor as need to return promise
|
|
21
|
-
static init(fn: AuditLogFn) {
|
|
22
|
-
AuditLogsProcessor.auditLogsEnabled = true
|
|
23
|
-
const writeAuditLogs = fn
|
|
24
|
-
AuditLogsProcessor.auditLogQueue = createQueue<AuditLogQueueEvent>(
|
|
25
|
-
JobQueue.AUDIT_LOG
|
|
26
|
-
)
|
|
27
|
-
return AuditLogsProcessor.auditLogQueue.process(async job => {
|
|
28
|
-
return doInTenant(job.data.tenantId, async () => {
|
|
29
|
-
let properties = job.data.properties
|
|
30
|
-
if (properties.audited) {
|
|
31
|
-
properties = {
|
|
32
|
-
...properties,
|
|
33
|
-
...properties.audited,
|
|
34
|
-
}
|
|
35
|
-
delete properties.audited
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
// this feature is disabled by default due to privacy requirements
|
|
39
|
-
// in some countries - available as env var in-case it is desired
|
|
40
|
-
// in self host deployments
|
|
41
|
-
let hostInfo: HostInfo | undefined = {}
|
|
42
|
-
if (env.ENABLE_AUDIT_LOG_IP_ADDR) {
|
|
43
|
-
hostInfo = job.data.opts.hostInfo
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
await writeAuditLogs(job.data.event, properties, {
|
|
47
|
-
userId: job.data.opts.userId,
|
|
48
|
-
timestamp: job.data.opts.timestamp,
|
|
49
|
-
appId: job.data.opts.appId,
|
|
50
|
-
hostInfo,
|
|
51
|
-
})
|
|
52
|
-
})
|
|
53
|
-
})
|
|
54
|
-
}
|
|
55
|
-
|
|
56
|
-
async processEvent(
|
|
57
|
-
event: Event,
|
|
58
|
-
identity: Identity,
|
|
59
|
-
properties: any,
|
|
60
|
-
timestamp?: string
|
|
61
|
-
): Promise<void> {
|
|
62
|
-
if (AuditLogsProcessor.auditLogsEnabled && isAudited(event)) {
|
|
63
|
-
// only audit log actual events, don't include backfills
|
|
64
|
-
const userId =
|
|
65
|
-
identity.type === IdentityType.USER ? identity.id : undefined
|
|
66
|
-
// add to the event queue, rather than just writing immediately
|
|
67
|
-
await AuditLogsProcessor.auditLogQueue.add({
|
|
68
|
-
event,
|
|
69
|
-
properties,
|
|
70
|
-
opts: {
|
|
71
|
-
userId,
|
|
72
|
-
timestamp,
|
|
73
|
-
appId: getAppId(),
|
|
74
|
-
hostInfo: identity.hostInfo,
|
|
75
|
-
},
|
|
76
|
-
tenantId: getTenantId(),
|
|
77
|
-
})
|
|
78
|
-
}
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
async identify() {
|
|
82
|
-
// no-op
|
|
83
|
-
}
|
|
84
|
-
|
|
85
|
-
async identifyGroup() {
|
|
86
|
-
// no-op
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
shutdown(): void {
|
|
90
|
-
AuditLogsProcessor.auditLogQueue?.close()
|
|
91
|
-
}
|
|
92
|
-
}
|
|
@@ -1,36 +0,0 @@
|
|
|
1
|
-
import { Event, Identity, Group } from "@budibase/types"
|
|
2
|
-
import { EventProcessor } from "./types"
|
|
3
|
-
import env from "../../environment"
|
|
4
|
-
|
|
5
|
-
const skipLogging = env.SELF_HOSTED && !env.isDev()
|
|
6
|
-
|
|
7
|
-
export default class LoggingProcessor implements EventProcessor {
|
|
8
|
-
async processEvent(
|
|
9
|
-
event: Event,
|
|
10
|
-
identity: Identity,
|
|
11
|
-
properties: any
|
|
12
|
-
): Promise<void> {
|
|
13
|
-
if (skipLogging) {
|
|
14
|
-
return
|
|
15
|
-
}
|
|
16
|
-
console.log(`[audit] [identityType=${identity.type}] ${event}`, properties)
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
async identify(identity: Identity) {
|
|
20
|
-
if (skipLogging) {
|
|
21
|
-
return
|
|
22
|
-
}
|
|
23
|
-
console.log(`[audit] identified`, identity)
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
async identifyGroup(group: Group) {
|
|
27
|
-
if (skipLogging) {
|
|
28
|
-
return
|
|
29
|
-
}
|
|
30
|
-
console.log(`[audit] group identified`, group)
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
shutdown(): void {
|
|
34
|
-
// no-op
|
|
35
|
-
}
|
|
36
|
-
}
|
|
@@ -1,52 +0,0 @@
|
|
|
1
|
-
import { Event, Identity, Group } from "@budibase/types"
|
|
2
|
-
import { EventProcessor } from "./types"
|
|
3
|
-
|
|
4
|
-
export default class Processor implements EventProcessor {
|
|
5
|
-
initialised: boolean = false
|
|
6
|
-
processors: EventProcessor[] = []
|
|
7
|
-
|
|
8
|
-
constructor(processors: EventProcessor[]) {
|
|
9
|
-
this.processors = processors
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
async processEvent(
|
|
13
|
-
event: Event,
|
|
14
|
-
identity: Identity,
|
|
15
|
-
properties: any,
|
|
16
|
-
timestamp?: string | number
|
|
17
|
-
): Promise<void> {
|
|
18
|
-
for (const eventProcessor of this.processors) {
|
|
19
|
-
await eventProcessor.processEvent(event, identity, properties, timestamp)
|
|
20
|
-
}
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
async identify(
|
|
24
|
-
identity: Identity,
|
|
25
|
-
timestamp?: string | number
|
|
26
|
-
): Promise<void> {
|
|
27
|
-
for (const eventProcessor of this.processors) {
|
|
28
|
-
if (eventProcessor.identify) {
|
|
29
|
-
await eventProcessor.identify(identity, timestamp)
|
|
30
|
-
}
|
|
31
|
-
}
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
async identifyGroup(
|
|
35
|
-
identity: Group,
|
|
36
|
-
timestamp?: string | number
|
|
37
|
-
): Promise<void> {
|
|
38
|
-
for (const eventProcessor of this.processors) {
|
|
39
|
-
if (eventProcessor.identifyGroup) {
|
|
40
|
-
await eventProcessor.identifyGroup(identity, timestamp)
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
shutdown() {
|
|
46
|
-
for (const eventProcessor of this.processors) {
|
|
47
|
-
if (eventProcessor.shutdown) {
|
|
48
|
-
eventProcessor.shutdown()
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
}
|
|
52
|
-
}
|
|
@@ -1,38 +0,0 @@
|
|
|
1
|
-
import { EventProcessor } from "../types"
|
|
2
|
-
import { Event, Identity, DocUpdateEvent } from "@budibase/types"
|
|
3
|
-
import { doInTenant } from "../../../context"
|
|
4
|
-
import { getDocumentId } from "../../documentId"
|
|
5
|
-
import { shutdown } from "../../asyncEvents"
|
|
6
|
-
|
|
7
|
-
export type Processor = (update: DocUpdateEvent) => Promise<void>
|
|
8
|
-
export type ProcessorMap = { events: Event[]; processor: Processor }[]
|
|
9
|
-
|
|
10
|
-
export default class DocumentUpdateProcessor implements EventProcessor {
|
|
11
|
-
processors: ProcessorMap = []
|
|
12
|
-
|
|
13
|
-
constructor(processors: ProcessorMap) {
|
|
14
|
-
this.processors = processors
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
async processEvent(event: Event, identity: Identity, properties: any) {
|
|
18
|
-
const tenantId = identity.realTenantId
|
|
19
|
-
const docId = getDocumentId(event, properties)
|
|
20
|
-
if (!tenantId || !docId) {
|
|
21
|
-
return
|
|
22
|
-
}
|
|
23
|
-
for (let { events, processor } of this.processors) {
|
|
24
|
-
if (events.includes(event)) {
|
|
25
|
-
await doInTenant(tenantId, async () => {
|
|
26
|
-
await processor({
|
|
27
|
-
id: docId,
|
|
28
|
-
tenantId,
|
|
29
|
-
})
|
|
30
|
-
})
|
|
31
|
-
}
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
shutdown() {
|
|
36
|
-
return shutdown()
|
|
37
|
-
}
|
|
38
|
-
}
|
|
@@ -1,19 +0,0 @@
|
|
|
1
|
-
import AnalyticsProcessor from "./AnalyticsProcessor"
|
|
2
|
-
import LoggingProcessor from "./LoggingProcessor"
|
|
3
|
-
import AuditLogsProcessor from "./AuditLogsProcessor"
|
|
4
|
-
import Processors from "./Processors"
|
|
5
|
-
import { AuditLogFn } from "@budibase/types"
|
|
6
|
-
|
|
7
|
-
export const analyticsProcessor = new AnalyticsProcessor()
|
|
8
|
-
const loggingProcessor = new LoggingProcessor()
|
|
9
|
-
const auditLogsProcessor = new AuditLogsProcessor()
|
|
10
|
-
|
|
11
|
-
export function init(auditingFn: AuditLogFn) {
|
|
12
|
-
return AuditLogsProcessor.init(auditingFn)
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
export const processors = new Processors([
|
|
16
|
-
analyticsProcessor,
|
|
17
|
-
loggingProcessor,
|
|
18
|
-
auditLogsProcessor,
|
|
19
|
-
])
|
|
@@ -1,118 +0,0 @@
|
|
|
1
|
-
import { PostHog } from "posthog-node"
|
|
2
|
-
import { Event, Identity, Group, BaseEvent } from "@budibase/types"
|
|
3
|
-
import { EventProcessor } from "../types"
|
|
4
|
-
import env from "../../../environment"
|
|
5
|
-
import * as context from "../../../context"
|
|
6
|
-
import * as rateLimiting from "./rateLimiting"
|
|
7
|
-
|
|
8
|
-
const EXCLUDED_EVENTS: Event[] = [
|
|
9
|
-
Event.USER_UPDATED,
|
|
10
|
-
Event.EMAIL_SMTP_UPDATED,
|
|
11
|
-
Event.AUTH_SSO_UPDATED,
|
|
12
|
-
Event.APP_UPDATED,
|
|
13
|
-
Event.ROLE_UPDATED,
|
|
14
|
-
Event.DATASOURCE_UPDATED,
|
|
15
|
-
Event.QUERY_UPDATED,
|
|
16
|
-
Event.TABLE_UPDATED,
|
|
17
|
-
Event.VIEW_UPDATED,
|
|
18
|
-
Event.VIEW_FILTER_UPDATED,
|
|
19
|
-
Event.VIEW_CALCULATION_UPDATED,
|
|
20
|
-
Event.AUTOMATION_TRIGGER_UPDATED,
|
|
21
|
-
Event.USER_GROUP_UPDATED,
|
|
22
|
-
]
|
|
23
|
-
|
|
24
|
-
export default class PosthogProcessor implements EventProcessor {
|
|
25
|
-
posthog: PostHog
|
|
26
|
-
|
|
27
|
-
constructor(token: string | undefined) {
|
|
28
|
-
if (!token) {
|
|
29
|
-
throw new Error("Posthog token is not defined")
|
|
30
|
-
}
|
|
31
|
-
this.posthog = new PostHog(token)
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
async processEvent(
|
|
35
|
-
event: Event,
|
|
36
|
-
identity: Identity,
|
|
37
|
-
properties: BaseEvent,
|
|
38
|
-
timestamp?: string | number
|
|
39
|
-
): Promise<void> {
|
|
40
|
-
// don't send excluded events
|
|
41
|
-
if (EXCLUDED_EVENTS.includes(event)) {
|
|
42
|
-
return
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
if (await rateLimiting.limited(event)) {
|
|
46
|
-
return
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
properties = this.clearPIIProperties(properties)
|
|
50
|
-
|
|
51
|
-
properties.version = env.VERSION
|
|
52
|
-
properties.service = env.SERVICE
|
|
53
|
-
properties.environment = identity.environment
|
|
54
|
-
properties.hosting = identity.hosting
|
|
55
|
-
|
|
56
|
-
const appId = context.getAppId()
|
|
57
|
-
if (appId) {
|
|
58
|
-
properties.appId = appId
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
const payload: any = { distinctId: identity.id, event, properties }
|
|
62
|
-
|
|
63
|
-
if (timestamp) {
|
|
64
|
-
payload.timestamp = new Date(timestamp)
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
// add groups to the event
|
|
68
|
-
if (identity.installationId || identity.tenantId) {
|
|
69
|
-
payload.groups = {}
|
|
70
|
-
if (identity.installationId) {
|
|
71
|
-
payload.groups.installation = identity.installationId
|
|
72
|
-
payload.properties.installationId = identity.installationId
|
|
73
|
-
}
|
|
74
|
-
if (identity.tenantId) {
|
|
75
|
-
payload.groups.tenant = identity.tenantId
|
|
76
|
-
payload.properties.tenantId = identity.tenantId
|
|
77
|
-
}
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
this.posthog.capture(payload)
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
clearPIIProperties(properties: any) {
|
|
84
|
-
if (properties.email) {
|
|
85
|
-
delete properties.email
|
|
86
|
-
}
|
|
87
|
-
if (properties.audited) {
|
|
88
|
-
delete properties.audited
|
|
89
|
-
}
|
|
90
|
-
return properties
|
|
91
|
-
}
|
|
92
|
-
|
|
93
|
-
async identify(identity: Identity, timestamp?: string | number) {
|
|
94
|
-
const payload: any = { distinctId: identity.id, properties: identity }
|
|
95
|
-
if (timestamp) {
|
|
96
|
-
payload.timestamp = new Date(timestamp)
|
|
97
|
-
}
|
|
98
|
-
this.posthog.identify(payload)
|
|
99
|
-
}
|
|
100
|
-
|
|
101
|
-
async identifyGroup(group: Group, timestamp?: string | number) {
|
|
102
|
-
const payload: any = {
|
|
103
|
-
distinctId: group.id,
|
|
104
|
-
groupType: group.type,
|
|
105
|
-
groupKey: group.id,
|
|
106
|
-
properties: group,
|
|
107
|
-
}
|
|
108
|
-
|
|
109
|
-
if (timestamp) {
|
|
110
|
-
payload.timestamp = new Date(timestamp)
|
|
111
|
-
}
|
|
112
|
-
this.posthog.groupIdentify(payload)
|
|
113
|
-
}
|
|
114
|
-
|
|
115
|
-
shutdown() {
|
|
116
|
-
this.posthog.shutdown()
|
|
117
|
-
}
|
|
118
|
-
}
|
|
@@ -1,106 +0,0 @@
|
|
|
1
|
-
import { Event } from "@budibase/types"
|
|
2
|
-
import { CacheKey, TTL } from "../../../cache/generic"
|
|
3
|
-
import * as cache from "../../../cache/generic"
|
|
4
|
-
import * as context from "../../../context"
|
|
5
|
-
|
|
6
|
-
type RateLimitedEvent =
|
|
7
|
-
| Event.SERVED_BUILDER
|
|
8
|
-
| Event.SERVED_APP_PREVIEW
|
|
9
|
-
| Event.SERVED_APP
|
|
10
|
-
|
|
11
|
-
const isRateLimited = (event: Event): event is RateLimitedEvent => {
|
|
12
|
-
return (
|
|
13
|
-
event === Event.SERVED_BUILDER ||
|
|
14
|
-
event === Event.SERVED_APP_PREVIEW ||
|
|
15
|
-
event === Event.SERVED_APP
|
|
16
|
-
)
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
const isPerApp = (event: RateLimitedEvent) => {
|
|
20
|
-
return event === Event.SERVED_APP_PREVIEW || event === Event.SERVED_APP
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
interface EventProperties {
|
|
24
|
-
timestamp: number
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
enum RateLimit {
|
|
28
|
-
CALENDAR_DAY = "calendarDay",
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
const RATE_LIMITS = {
|
|
32
|
-
[Event.SERVED_APP]: RateLimit.CALENDAR_DAY,
|
|
33
|
-
[Event.SERVED_APP_PREVIEW]: RateLimit.CALENDAR_DAY,
|
|
34
|
-
[Event.SERVED_BUILDER]: RateLimit.CALENDAR_DAY,
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
/**
|
|
38
|
-
* Check if this event should be sent right now
|
|
39
|
-
* Return false to signal the event SHOULD be sent
|
|
40
|
-
* Return true to signal the event should NOT be sent
|
|
41
|
-
*/
|
|
42
|
-
export const limited = async (event: Event): Promise<boolean> => {
|
|
43
|
-
// not a rate limited event -- send
|
|
44
|
-
if (!isRateLimited(event)) {
|
|
45
|
-
return false
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
const cachedEvent = await readEvent(event)
|
|
49
|
-
if (cachedEvent) {
|
|
50
|
-
const timestamp = new Date(cachedEvent.timestamp)
|
|
51
|
-
const limit = RATE_LIMITS[event]
|
|
52
|
-
switch (limit) {
|
|
53
|
-
case RateLimit.CALENDAR_DAY: {
|
|
54
|
-
// get midnight at the start of the next day for the timestamp
|
|
55
|
-
timestamp.setDate(timestamp.getDate() + 1)
|
|
56
|
-
timestamp.setHours(0, 0, 0, 0)
|
|
57
|
-
|
|
58
|
-
// if we have passed the threshold into the next day
|
|
59
|
-
if (Date.now() > timestamp.getTime()) {
|
|
60
|
-
// update the timestamp in the event -- send
|
|
61
|
-
await recordEvent(event, { timestamp: Date.now() })
|
|
62
|
-
return false
|
|
63
|
-
} else {
|
|
64
|
-
// still within the limited period -- don't send
|
|
65
|
-
return true
|
|
66
|
-
}
|
|
67
|
-
}
|
|
68
|
-
}
|
|
69
|
-
} else {
|
|
70
|
-
// no event present i.e. expired -- send
|
|
71
|
-
await recordEvent(event, { timestamp: Date.now() })
|
|
72
|
-
return false
|
|
73
|
-
}
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
const eventKey = (event: RateLimitedEvent) => {
|
|
77
|
-
let key = `${CacheKey.EVENTS_RATE_LIMIT}:${event}`
|
|
78
|
-
if (isPerApp(event)) {
|
|
79
|
-
key = key + ":" + context.getAppId()
|
|
80
|
-
}
|
|
81
|
-
return key
|
|
82
|
-
}
|
|
83
|
-
|
|
84
|
-
const readEvent = async (
|
|
85
|
-
event: RateLimitedEvent
|
|
86
|
-
): Promise<EventProperties | undefined> => {
|
|
87
|
-
const key = eventKey(event)
|
|
88
|
-
const result = await cache.get(key)
|
|
89
|
-
return result as EventProperties
|
|
90
|
-
}
|
|
91
|
-
|
|
92
|
-
const recordEvent = async (
|
|
93
|
-
event: RateLimitedEvent,
|
|
94
|
-
properties: EventProperties
|
|
95
|
-
) => {
|
|
96
|
-
const key = eventKey(event)
|
|
97
|
-
const limit = RATE_LIMITS[event]
|
|
98
|
-
let ttl
|
|
99
|
-
switch (limit) {
|
|
100
|
-
case RateLimit.CALENDAR_DAY: {
|
|
101
|
-
ttl = TTL.ONE_DAY
|
|
102
|
-
}
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
await cache.store(key, properties, ttl)
|
|
106
|
-
}
|
|
@@ -1,164 +0,0 @@
|
|
|
1
|
-
import { testEnv } from "../../../../../tests/extra"
|
|
2
|
-
import PosthogProcessor from "../PosthogProcessor"
|
|
3
|
-
import { Event, IdentityType, Hosting } from "@budibase/types"
|
|
4
|
-
import tk from "timekeeper"
|
|
5
|
-
import * as cache from "../../../../cache/generic"
|
|
6
|
-
import { CacheKey } from "../../../../cache/generic"
|
|
7
|
-
import * as context from "../../../../context"
|
|
8
|
-
|
|
9
|
-
const newIdentity = () => {
|
|
10
|
-
return {
|
|
11
|
-
id: "test",
|
|
12
|
-
type: IdentityType.USER,
|
|
13
|
-
hosting: Hosting.SELF,
|
|
14
|
-
environment: "test",
|
|
15
|
-
}
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
describe("PosthogProcessor", () => {
|
|
19
|
-
let processor: PosthogProcessor
|
|
20
|
-
let spy: jest.SpyInstance
|
|
21
|
-
|
|
22
|
-
beforeAll(() => {
|
|
23
|
-
testEnv.singleTenant()
|
|
24
|
-
})
|
|
25
|
-
|
|
26
|
-
beforeEach(async () => {
|
|
27
|
-
jest.clearAllMocks()
|
|
28
|
-
await cache.bustCache(
|
|
29
|
-
`${CacheKey.EVENTS_RATE_LIMIT}:${Event.SERVED_BUILDER}`
|
|
30
|
-
)
|
|
31
|
-
|
|
32
|
-
processor = new PosthogProcessor("test")
|
|
33
|
-
spy = jest.spyOn(processor.posthog, "capture")
|
|
34
|
-
})
|
|
35
|
-
|
|
36
|
-
describe("processEvent", () => {
|
|
37
|
-
it("processes event", async () => {
|
|
38
|
-
const identity = newIdentity()
|
|
39
|
-
const properties = {}
|
|
40
|
-
|
|
41
|
-
await processor.processEvent(Event.APP_CREATED, identity, properties)
|
|
42
|
-
expect(spy).toHaveBeenCalledTimes(1)
|
|
43
|
-
})
|
|
44
|
-
|
|
45
|
-
it("honours exclusions", async () => {
|
|
46
|
-
const identity = newIdentity()
|
|
47
|
-
const properties = {}
|
|
48
|
-
|
|
49
|
-
await processor.processEvent(Event.AUTH_SSO_UPDATED, identity, properties)
|
|
50
|
-
expect(spy).toHaveBeenCalledTimes(0)
|
|
51
|
-
})
|
|
52
|
-
|
|
53
|
-
it("removes audited information", async () => {
|
|
54
|
-
const identity = newIdentity()
|
|
55
|
-
const properties = {
|
|
56
|
-
email: "test",
|
|
57
|
-
audited: {
|
|
58
|
-
name: "test",
|
|
59
|
-
},
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
await processor.processEvent(Event.USER_CREATED, identity, properties)
|
|
63
|
-
expect(spy).toHaveBeenCalled()
|
|
64
|
-
|
|
65
|
-
// @ts-ignore
|
|
66
|
-
const call = processor.posthog.capture.mock.calls[0][0]
|
|
67
|
-
expect(call.properties.audited).toBeUndefined()
|
|
68
|
-
expect(call.properties.email).toBeUndefined()
|
|
69
|
-
})
|
|
70
|
-
|
|
71
|
-
describe("rate limiting", () => {
|
|
72
|
-
it("sends daily event once in same day", async () => {
|
|
73
|
-
const identity = newIdentity()
|
|
74
|
-
const properties = {}
|
|
75
|
-
|
|
76
|
-
tk.freeze(new Date(2022, 0, 1, 14, 0))
|
|
77
|
-
await processor.processEvent(Event.SERVED_BUILDER, identity, properties)
|
|
78
|
-
// go forward one hour
|
|
79
|
-
tk.freeze(new Date(2022, 0, 1, 15, 0))
|
|
80
|
-
await processor.processEvent(Event.SERVED_BUILDER, identity, properties)
|
|
81
|
-
|
|
82
|
-
expect(spy).toHaveBeenCalledTimes(1)
|
|
83
|
-
})
|
|
84
|
-
|
|
85
|
-
it("sends daily event once per unique day", async () => {
|
|
86
|
-
const identity = newIdentity()
|
|
87
|
-
const properties = {}
|
|
88
|
-
|
|
89
|
-
tk.freeze(new Date(2022, 0, 1, 14, 0))
|
|
90
|
-
await processor.processEvent(Event.SERVED_BUILDER, identity, properties)
|
|
91
|
-
// go forward into next day
|
|
92
|
-
tk.freeze(new Date(2022, 0, 2, 9, 0))
|
|
93
|
-
await processor.processEvent(Event.SERVED_BUILDER, identity, properties)
|
|
94
|
-
// go forward into next day
|
|
95
|
-
tk.freeze(new Date(2022, 0, 3, 5, 0))
|
|
96
|
-
await processor.processEvent(Event.SERVED_BUILDER, identity, properties)
|
|
97
|
-
// go forward one hour
|
|
98
|
-
tk.freeze(new Date(2022, 0, 3, 6, 0))
|
|
99
|
-
await processor.processEvent(Event.SERVED_BUILDER, identity, properties)
|
|
100
|
-
|
|
101
|
-
expect(spy).toHaveBeenCalledTimes(3)
|
|
102
|
-
})
|
|
103
|
-
|
|
104
|
-
it("sends event again after cache expires", async () => {
|
|
105
|
-
const identity = newIdentity()
|
|
106
|
-
const properties = {}
|
|
107
|
-
|
|
108
|
-
tk.freeze(new Date(2022, 0, 1, 14, 0))
|
|
109
|
-
await processor.processEvent(Event.SERVED_BUILDER, identity, properties)
|
|
110
|
-
|
|
111
|
-
await cache.bustCache(
|
|
112
|
-
`${CacheKey.EVENTS_RATE_LIMIT}:${Event.SERVED_BUILDER}`
|
|
113
|
-
)
|
|
114
|
-
|
|
115
|
-
tk.freeze(new Date(2022, 0, 1, 14, 0))
|
|
116
|
-
await processor.processEvent(Event.SERVED_BUILDER, identity, properties)
|
|
117
|
-
|
|
118
|
-
expect(spy).toHaveBeenCalledTimes(2)
|
|
119
|
-
})
|
|
120
|
-
|
|
121
|
-
it("sends per app events once per day per app", async () => {
|
|
122
|
-
const identity = newIdentity()
|
|
123
|
-
const properties = {}
|
|
124
|
-
|
|
125
|
-
const runAppEvents = async (appId: string) => {
|
|
126
|
-
await context.doInAppContext(appId, async () => {
|
|
127
|
-
tk.freeze(new Date(2022, 0, 1, 14, 0))
|
|
128
|
-
await processor.processEvent(Event.SERVED_APP, identity, properties)
|
|
129
|
-
await processor.processEvent(
|
|
130
|
-
Event.SERVED_APP_PREVIEW,
|
|
131
|
-
identity,
|
|
132
|
-
properties
|
|
133
|
-
)
|
|
134
|
-
|
|
135
|
-
// go forward one hour - should be ignored
|
|
136
|
-
tk.freeze(new Date(2022, 0, 1, 15, 0))
|
|
137
|
-
await processor.processEvent(Event.SERVED_APP, identity, properties)
|
|
138
|
-
await processor.processEvent(
|
|
139
|
-
Event.SERVED_APP_PREVIEW,
|
|
140
|
-
identity,
|
|
141
|
-
properties
|
|
142
|
-
)
|
|
143
|
-
|
|
144
|
-
// go forward into next day
|
|
145
|
-
tk.freeze(new Date(2022, 0, 2, 9, 0))
|
|
146
|
-
|
|
147
|
-
await processor.processEvent(Event.SERVED_APP, identity, properties)
|
|
148
|
-
await processor.processEvent(
|
|
149
|
-
Event.SERVED_APP_PREVIEW,
|
|
150
|
-
identity,
|
|
151
|
-
properties
|
|
152
|
-
)
|
|
153
|
-
})
|
|
154
|
-
}
|
|
155
|
-
|
|
156
|
-
await runAppEvents("app_1")
|
|
157
|
-
expect(spy).toHaveBeenCalledTimes(4)
|
|
158
|
-
|
|
159
|
-
await runAppEvents("app_2")
|
|
160
|
-
expect(spy).toHaveBeenCalledTimes(8)
|
|
161
|
-
})
|
|
162
|
-
})
|
|
163
|
-
})
|
|
164
|
-
})
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export { EventProcessor } from "@budibase/types"
|
|
@@ -1,41 +0,0 @@
|
|
|
1
|
-
import { publishEvent } from "../events"
|
|
2
|
-
import {
|
|
3
|
-
Event,
|
|
4
|
-
Account,
|
|
5
|
-
AccountCreatedEvent,
|
|
6
|
-
AccountDeletedEvent,
|
|
7
|
-
AccountVerifiedEvent,
|
|
8
|
-
Identity,
|
|
9
|
-
} from "@budibase/types"
|
|
10
|
-
|
|
11
|
-
async function created(account: Account, identityOverride?: Identity) {
|
|
12
|
-
const properties: AccountCreatedEvent = {
|
|
13
|
-
tenantId: account.tenantId,
|
|
14
|
-
}
|
|
15
|
-
await publishEvent(
|
|
16
|
-
Event.ACCOUNT_CREATED,
|
|
17
|
-
properties,
|
|
18
|
-
undefined,
|
|
19
|
-
identityOverride
|
|
20
|
-
)
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
async function deleted(account: Account) {
|
|
24
|
-
const properties: AccountDeletedEvent = {
|
|
25
|
-
tenantId: account.tenantId,
|
|
26
|
-
}
|
|
27
|
-
await publishEvent(Event.ACCOUNT_DELETED, properties)
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
async function verified(account: Account) {
|
|
31
|
-
const properties: AccountVerifiedEvent = {
|
|
32
|
-
tenantId: account.tenantId,
|
|
33
|
-
}
|
|
34
|
-
await publishEvent(Event.ACCOUNT_VERIFIED, properties)
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
export default {
|
|
38
|
-
created,
|
|
39
|
-
deleted,
|
|
40
|
-
verified,
|
|
41
|
-
}
|
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
import { publishEvent } from "../events"
|
|
2
|
-
import {
|
|
3
|
-
Event,
|
|
4
|
-
AIConfigCreatedEvent,
|
|
5
|
-
AIConfigUpdatedEvent,
|
|
6
|
-
} from "@budibase/types"
|
|
7
|
-
|
|
8
|
-
async function AIConfigCreated(timestamp?: string | number) {
|
|
9
|
-
const properties: AIConfigCreatedEvent = {}
|
|
10
|
-
await publishEvent(Event.AI_CONFIG_CREATED, properties, timestamp)
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
async function AIConfigUpdated() {
|
|
14
|
-
const properties: AIConfigUpdatedEvent = {}
|
|
15
|
-
await publishEvent(Event.AI_CONFIG_UPDATED, properties)
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
export default {
|
|
19
|
-
AIConfigCreated,
|
|
20
|
-
AIConfigUpdated,
|
|
21
|
-
}
|