🧐 Add data exploration scripts
This commit is contained in:
80
packages/scripts/destroyUser.ts
Normal file
80
packages/scripts/destroyUser.ts
Normal file
@ -0,0 +1,80 @@
|
||||
import { PrismaClient } from '@typebot.io/prisma'
|
||||
import * as p from '@clack/prompts'
|
||||
import { promptAndSetEnvironment } from './utils'
|
||||
|
||||
const destroyUser = async () => {
|
||||
await promptAndSetEnvironment('production')
|
||||
|
||||
const prisma = new PrismaClient({
|
||||
log: [{ emit: 'event', level: 'query' }, 'info', 'warn', 'error'],
|
||||
})
|
||||
|
||||
prisma.$on('query', (e) => {
|
||||
console.log(e.query)
|
||||
console.log(e.params)
|
||||
console.log(e.duration, 'ms')
|
||||
})
|
||||
|
||||
const email = (await p.text({
|
||||
message: 'User email?',
|
||||
})) as string
|
||||
|
||||
if (!email || typeof email !== 'string') {
|
||||
console.log('No email provided')
|
||||
return
|
||||
}
|
||||
|
||||
const workspaces = await prisma.workspace.findMany({
|
||||
where: {
|
||||
members: { every: { user: { email } } },
|
||||
},
|
||||
include: {
|
||||
members: { select: { user: { select: { email: true } }, role: true } },
|
||||
typebots: {
|
||||
select: {
|
||||
results: {
|
||||
select: { id: true },
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
})
|
||||
|
||||
console.log(`Found ${workspaces.length} workspaces`)
|
||||
|
||||
const proceed = await p.confirm({ message: 'Proceed?' })
|
||||
if (!proceed || typeof proceed !== 'boolean') {
|
||||
console.log('Aborting')
|
||||
return
|
||||
}
|
||||
|
||||
for (const workspace of workspaces) {
|
||||
const hasResults = workspace.typebots.some((t) => t.results.length > 0)
|
||||
if (hasResults) {
|
||||
console.log(
|
||||
`Workspace ${workspace.name} has results. Deleting results first...`,
|
||||
workspace.typebots.filter((t) => t.results.length > 0)
|
||||
)
|
||||
console.log(JSON.stringify({ members: workspace.members }, null, 2))
|
||||
const proceed = await p.confirm({ message: 'Proceed?' })
|
||||
if (!proceed || typeof proceed !== 'boolean') {
|
||||
console.log('Aborting')
|
||||
return
|
||||
}
|
||||
}
|
||||
for (const typebot of workspace.typebots.filter(
|
||||
(t) => t.results.length > 0
|
||||
)) {
|
||||
for (const result of typebot.results) {
|
||||
await prisma.result.deleteMany({ where: { id: result.id } })
|
||||
}
|
||||
}
|
||||
await prisma.workspace.delete({ where: { id: workspace.id } })
|
||||
}
|
||||
|
||||
const user = await prisma.user.delete({ where: { email } })
|
||||
|
||||
console.log(`Deleted user ${JSON.stringify(user, null, 2)}`)
|
||||
}
|
||||
|
||||
destroyUser()
|
@ -32,6 +32,7 @@ const inspectUser = async () => {
|
||||
select: {
|
||||
workspace: {
|
||||
select: {
|
||||
id: true,
|
||||
name: true,
|
||||
plan: true,
|
||||
members: {
|
||||
@ -49,6 +50,7 @@ const inspectUser = async () => {
|
||||
name: true,
|
||||
createdAt: true,
|
||||
updatedAt: true,
|
||||
riskLevel: true,
|
||||
publishedTypebot: {
|
||||
select: {
|
||||
typebot: {
|
||||
@ -78,7 +80,8 @@ const inspectUser = async () => {
|
||||
console.log('Workspaces:')
|
||||
|
||||
for (const workspace of user.workspaces) {
|
||||
console.log(' - Name:', workspace.workspace.name)
|
||||
console.log(' - ID:', workspace.workspace.id)
|
||||
console.log(' Name:', workspace.workspace.name)
|
||||
console.log(' Plan:', workspace.workspace.plan)
|
||||
console.log(' Members:', workspace.workspace.members.length + 1)
|
||||
console.log(
|
||||
@ -94,6 +97,7 @@ const inspectUser = async () => {
|
||||
' Last updated:',
|
||||
typebot.updatedAt.toLocaleDateString()
|
||||
)
|
||||
console.log(' Risk level:', typebot.riskLevel)
|
||||
console.log(
|
||||
' Public ID:',
|
||||
typebot.publishedTypebot?.typebot.publicId
|
||||
|
@ -19,7 +19,10 @@
|
||||
"migrateSubscriptionsToUsageBased": "tsx migrateSubscriptionsToUsageBased.ts",
|
||||
"importContactToBrevo": "tsx importContactToBrevo.ts",
|
||||
"getUsage": "tsx getUsage.ts",
|
||||
"suspendWorkspace": "SKIP_ENV_CHECK=true dotenv -e ./.env.production -- tsx suspendWorkspace.ts"
|
||||
"suspendWorkspace": "tsx suspendWorkspace.ts",
|
||||
"destroyUser": "tsx destroyUser.ts",
|
||||
"updateTypebot": "tsx updateTypebot.ts",
|
||||
"updateWorkspace": "tsx updateWorkspace.ts"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@typebot.io/emails": "workspace:*",
|
||||
@ -37,6 +40,7 @@
|
||||
"zod": "3.22.4"
|
||||
},
|
||||
"dependencies": {
|
||||
"@clack/prompts": "^0.7.0",
|
||||
"@paralleldrive/cuid2": "2.2.1"
|
||||
}
|
||||
}
|
||||
|
@ -1,6 +1,10 @@
|
||||
import { PrismaClient } from '@typebot.io/prisma'
|
||||
import * as p from '@clack/prompts'
|
||||
import { isEmpty } from '@typebot.io/lib'
|
||||
import { promptAndSetEnvironment } from './utils'
|
||||
|
||||
const suspendWorkspace = async () => {
|
||||
await promptAndSetEnvironment('production')
|
||||
const prisma = new PrismaClient({
|
||||
log: [{ emit: 'event', level: 'query' }, 'info', 'warn', 'error'],
|
||||
})
|
||||
@ -11,9 +15,24 @@ const suspendWorkspace = async () => {
|
||||
console.log(e.duration, 'ms')
|
||||
})
|
||||
|
||||
const type = (await p.select({
|
||||
message: 'Select way',
|
||||
options: [
|
||||
{ label: 'Typebot public ID', value: 'typebotId' },
|
||||
{ label: 'Workspace ID', value: 'workspaceId' },
|
||||
],
|
||||
})) as 'typebotId' | 'workspaceId'
|
||||
|
||||
const val = (await p.text({
|
||||
message: 'Enter value',
|
||||
})) as string
|
||||
|
||||
let workspaceId = type === 'workspaceId' ? val : undefined
|
||||
|
||||
if (!workspaceId) {
|
||||
const typebot = await prisma.typebot.findUnique({
|
||||
where: {
|
||||
id: '',
|
||||
publicId: val,
|
||||
},
|
||||
select: {
|
||||
workspaceId: true,
|
||||
@ -25,9 +44,17 @@ const suspendWorkspace = async () => {
|
||||
return
|
||||
}
|
||||
|
||||
workspaceId = typebot.workspaceId
|
||||
}
|
||||
|
||||
if (isEmpty(workspaceId)) {
|
||||
console.log('Workspace not found')
|
||||
return
|
||||
}
|
||||
|
||||
const result = await prisma.workspace.update({
|
||||
where: {
|
||||
id: typebot.workspaceId,
|
||||
id: workspaceId,
|
||||
},
|
||||
data: {
|
||||
isSuspended: true,
|
||||
|
34
packages/scripts/updateTypebot.ts
Normal file
34
packages/scripts/updateTypebot.ts
Normal file
@ -0,0 +1,34 @@
|
||||
import { PrismaClient } from '@typebot.io/prisma'
|
||||
import { promptAndSetEnvironment } from './utils'
|
||||
import * as p from '@clack/prompts'
|
||||
|
||||
const updateTypebot = async () => {
|
||||
await promptAndSetEnvironment('production')
|
||||
|
||||
const prisma = new PrismaClient({
|
||||
log: [{ emit: 'event', level: 'query' }, 'info', 'warn', 'error'],
|
||||
})
|
||||
|
||||
prisma.$on('query', (e) => {
|
||||
console.log(e.query)
|
||||
console.log(e.params)
|
||||
console.log(e.duration, 'ms')
|
||||
})
|
||||
|
||||
const typebotId = (await p.text({
|
||||
message: 'Typebot ID?',
|
||||
})) as string
|
||||
|
||||
const typebot = await prisma.typebot.update({
|
||||
where: {
|
||||
id: typebotId,
|
||||
},
|
||||
data: {
|
||||
riskLevel: -1,
|
||||
},
|
||||
})
|
||||
|
||||
console.log(typebot)
|
||||
}
|
||||
|
||||
updateTypebot()
|
34
packages/scripts/updateWorkspace.ts
Normal file
34
packages/scripts/updateWorkspace.ts
Normal file
@ -0,0 +1,34 @@
|
||||
import { PrismaClient } from '@typebot.io/prisma'
|
||||
import { promptAndSetEnvironment } from './utils'
|
||||
import * as p from '@clack/prompts'
|
||||
|
||||
const updateTypebot = async () => {
|
||||
await promptAndSetEnvironment('production')
|
||||
|
||||
const prisma = new PrismaClient({
|
||||
log: [{ emit: 'event', level: 'query' }, 'info', 'warn', 'error'],
|
||||
})
|
||||
|
||||
prisma.$on('query', (e) => {
|
||||
console.log(e.query)
|
||||
console.log(e.params)
|
||||
console.log(e.duration, 'ms')
|
||||
})
|
||||
|
||||
const workspaceId = (await p.text({
|
||||
message: 'Workspace ID?',
|
||||
})) as string
|
||||
|
||||
const workspace = await prisma.workspace.update({
|
||||
where: {
|
||||
id: workspaceId,
|
||||
},
|
||||
data: {
|
||||
isVerified: true,
|
||||
},
|
||||
})
|
||||
|
||||
console.log(workspace)
|
||||
}
|
||||
|
||||
updateTypebot()
|
6
pnpm-lock.yaml
generated
6
pnpm-lock.yaml
generated
@ -1447,6 +1447,9 @@ importers:
|
||||
|
||||
packages/scripts:
|
||||
dependencies:
|
||||
'@clack/prompts':
|
||||
specifier: ^0.7.0
|
||||
version: 0.7.0
|
||||
'@paralleldrive/cuid2':
|
||||
specifier: 2.2.1
|
||||
version: 2.2.1
|
||||
@ -4277,7 +4280,6 @@ packages:
|
||||
dependencies:
|
||||
picocolors: 1.0.0
|
||||
sisteransi: 1.0.5
|
||||
dev: true
|
||||
|
||||
/@clack/prompts@0.7.0:
|
||||
resolution: {integrity: sha512-0MhX9/B4iL6Re04jPrttDm+BsP8y6mS7byuv0BvXgdXhbV5PdlsHt55dvNsuBCPZ7xq1oTAOOuotR9NFbQyMSA==}
|
||||
@ -4285,7 +4287,6 @@ packages:
|
||||
'@clack/core': 0.3.3
|
||||
picocolors: 1.0.0
|
||||
sisteransi: 1.0.5
|
||||
dev: true
|
||||
bundledDependencies:
|
||||
- is-unicode-supported
|
||||
|
||||
@ -19056,7 +19057,6 @@ packages:
|
||||
|
||||
/sisteransi@1.0.5:
|
||||
resolution: {integrity: sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg==}
|
||||
dev: true
|
||||
|
||||
/slash@2.0.0:
|
||||
resolution: {integrity: sha512-ZYKh3Wh2z1PpEXWr0MpSBZ0V6mZHAQfYevttO11c51CaWjGTaadiKZ+wVt1PbMlDV5qhMFslpZCemhwOK7C89A==}
|
||||
|
Reference in New Issue
Block a user