2
0

⚗️ Implement bot v2 MVP (#194)

Closes #190
This commit is contained in:
Baptiste Arnaud
2022-12-22 17:02:34 +01:00
committed by GitHub
parent e55823e011
commit 1a3869ae6d
202 changed files with 8060 additions and 1152 deletions

View File

@ -38,6 +38,7 @@ export const SearchableDropdown = ({
const { onOpen, onClose, isOpen } = useDisclosure()
const [inputValue, setInputValue] = useState(selectedItem ?? '')
const debounced = useDebouncedCallback(
// eslint-disable-next-line @typescript-eslint/no-empty-function
onValueChange ? onValueChange : () => {},
env('E2E_TEST') === 'true' ? 0 : debounceTimeout
)

View File

@ -2,7 +2,6 @@ import {
useDisclosure,
Flex,
Popover,
PopoverTrigger,
Input,
PopoverContent,
Button,

View File

@ -24,6 +24,7 @@ const userContext = createContext<{
currentWorkspaceId?: string
updateUser: (newUser: Partial<User>) => void
saveUser: (newUser?: Partial<User>) => Promise<void>
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore
}>({})

View File

@ -11,7 +11,7 @@ import {
Text,
} from '@chakra-ui/react'
import { UploadIcon } from '@/components/icons'
import React, { ChangeEvent, useState } from 'react'
import React, { ChangeEvent } from 'react'
import { isDefined } from 'utils'
import { ApiTokensList } from './ApiTokensList'
import { UploadButton } from '@/components/ImageUploadContent/UploadButton'

View File

@ -46,10 +46,14 @@ export const AnalyticsGraphContainer = ({ stats }: { stats?: Stats }) => {
flex="1"
typebot={publishedTypebot}
onUnlockProPlanClick={onOpen}
answersCounts={[
{ ...answersCounts[0], totalAnswers: stats?.totalStarts },
...answersCounts?.slice(1),
]}
answersCounts={
answersCounts
? [
{ ...answersCounts[0], totalAnswers: stats?.totalStarts },
...answersCounts.slice(1),
]
: []
}
/>
</GroupsCoordinatesProvider>
</GraphProvider>

View File

@ -115,7 +115,7 @@ export const SendEmailSettings = ({ options, onOptionsChange }: Props) => {
onCredentialsSelect={handleCredentialsSelect}
onCreateNewClick={onOpen}
defaultCredentialLabel={env('SMTP_FROM')
?.match(/\<(.*)\>/)
?.match(/<(.*)>/)
?.pop()}
refreshDropdownKey={refreshCredentialsKey}
/>

View File

@ -1,3 +1,4 @@
// eslint-disable-next-line @typescript-eslint/no-explicit-any
export const getDeepKeys = (obj: any): string[] => {
let keys: string[] = []
for (const key in obj) {

View File

@ -8,7 +8,6 @@ import {
MenuItem,
MenuList,
SkeletonCircle,
SkeletonText,
Text,
Tag,
Flex,

View File

@ -11,7 +11,7 @@ export const useTypebots = ({
}) => {
const { data, isLoading, refetch } = trpc.typebot.listTypebots.useQuery(
{
workspaceId: workspaceId!,
workspaceId: workspaceId as string,
folderId,
},
{

View File

@ -1,10 +1,4 @@
import {
Flex,
HStack,
Text,
Tooltip,
useColorModeValue,
} from '@chakra-ui/react'
import { Flex, HStack, Tooltip, useColorModeValue } from '@chakra-ui/react'
import { DraggableBlockType } from 'models'
import { useBlockDnd } from '@/features/graph'
import React, { useEffect, useState } from 'react'

View File

@ -16,6 +16,7 @@ const editorContext = createContext<{
setRightPanel: Dispatch<SetStateAction<RightPanel | undefined>>
startPreviewAtGroup: string | undefined
setStartPreviewAtGroup: Dispatch<SetStateAction<string | undefined>>
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore
}>({})

View File

@ -88,6 +88,7 @@ const typebotContext = createContext<
ItemsActions &
VariablesActions &
EdgesActions
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore
>({})

View File

@ -14,6 +14,7 @@ const typebotDndContext = createContext<{
setDraggedTypebot: Dispatch<SetStateAction<TypebotInDashboard | undefined>>
mouseOverFolderId?: string | null
setMouseOverFolderId: Dispatch<SetStateAction<string | undefined | null>>
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
}>({})

View File

@ -103,7 +103,7 @@ export const FolderContent = ({ folder }: Props) => {
if (newFolder) mutateFolders({ folders: [...folders, newFolder] })
}
const handleTypebotDeleted = (deletedId: string) => {
const handleTypebotDeleted = () => {
if (!typebots) return
refetchTypebots()
}
@ -206,7 +206,7 @@ export const FolderContent = ({ folder }: Props) => {
<TypebotButton
key={typebot.id.toString()}
typebot={typebot}
onTypebotDeleted={() => handleTypebotDeleted(typebot.id)}
onTypebotDeleted={handleTypebotDeleted}
onMouseDown={handleMouseDown(typebot)}
/>
))}

View File

@ -6,7 +6,6 @@ import {
useColorModeValue,
VStack,
} from '@chakra-ui/react'
import { GlobeIcon, ToolIcon } from '@/components/icons'
import { TypebotInDashboard } from '@/features/dashboard'
import { EmojiOrImageIcon } from '@/components/EmojiOrImageIcon'

View File

@ -1,7 +1,7 @@
import { Coordinates, useGraph, useGroupsCoordinates } from '../../providers'
import React, { useEffect, useLayoutEffect, useMemo, useState } from 'react'
import { Edge as EdgeProps } from 'models'
import { color, Portal, useColorMode, useDisclosure } from '@chakra-ui/react'
import { Portal, useColorMode, useDisclosure } from '@chakra-ui/react'
import { useTypebot } from '@/features/editor'
import { EdgeMenu } from './EdgeMenu'
import { colors } from '@/lib/theme'

View File

@ -1,4 +1,4 @@
import { useEventListener, Stack, Flex, Portal } from '@chakra-ui/react'
import { useEventListener, Stack, Portal } from '@chakra-ui/react'
import { DraggableBlock, DraggableBlockType, Block } from 'models'
import {
computeNearestPlaceholderIndex,

View File

@ -27,6 +27,7 @@ const graphDndContext = createContext<{
setMouseOverGroup: Dispatch<SetStateAction<NodeInfo | undefined>>
mouseOverBlock?: NodeInfo
setMouseOverBlock: Dispatch<SetStateAction<NodeInfo | undefined>>
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore
}>({})

View File

@ -80,6 +80,7 @@ const graphContext = createContext<{
isReadOnly: boolean
focusedGroupId?: string
setFocusedGroupId: Dispatch<SetStateAction<string | undefined>>
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore
}>({
graphPosition: graphPositionDefaultValue({ x: 0, y: 0 }),

View File

@ -12,6 +12,7 @@ import { GroupsCoordinates, Coordinates } from './GraphProvider'
const groupsCoordinatesContext = createContext<{
groupsCoordinates: GroupsCoordinates
updateGroupCoordinates: (groupId: string, newCoord: Coordinates) => void
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore
}>({})

View File

@ -17,6 +17,7 @@ const resultsContext = createContext<{
onDeleteResults: (totalResultsDeleted: number) => void
fetchNextPage: () => void
refetchResults: () => void
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore
}>({})

View File

@ -2,10 +2,12 @@ import { Checkbox, Flex } from '@chakra-ui/react'
import React from 'react'
const TableCheckBox = (
// eslint-disable-next-line @typescript-eslint/no-explicit-any
{ indeterminate, checked, ...rest }: any,
ref: React.LegacyRef<HTMLInputElement>
) => {
const defaultRef = React.useRef()
// eslint-disable-next-line @typescript-eslint/no-explicit-any
const resolvedRef: any = ref || defaultRef
return (

View File

@ -3,7 +3,6 @@ import {
Checkbox,
Flex,
Skeleton,
useColorMode,
useColorModeValue,
} from '@chakra-ui/react'
import React from 'react'

View File

@ -14,7 +14,7 @@ test.describe.parallel('Templates page', () => {
test('From file should import correctly', async ({ page }) => {
await page.goto('/typebots/create')
await page.waitForTimeout(1000)
await page.waitForTimeout(2000)
await page.setInputFiles(
'input[type="file"]',
getTestAsset('typebots/singleChoiceTarget.json')

View File

@ -50,7 +50,9 @@ test.describe.parallel('Theme page', () => {
await importTypebotInDatabase(getTestAsset('typebots/theme.json'), {
id: typebotId,
})
} catch {}
} catch {
/* empty */
}
await page.goto(`/typebots/${typebotId}/theme`)
await expect(

View File

@ -1,7 +1,6 @@
import {
createContext,
ReactNode,
useCallback,
useContext,
useEffect,
useMemo,
@ -26,6 +25,7 @@ const workspaceContext = createContext<{
updateWorkspace: (updates: { icon?: string; name?: string }) => void
deleteCurrentWorkspace: () => Promise<void>
refreshWorkspace: () => void
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore
}>({})
@ -59,12 +59,12 @@ export const WorkspaceProvider = ({
)
const { data: workspaceData } = trpc.workspace.getWorkspace.useQuery(
{ workspaceId: workspaceId! },
{ workspaceId: workspaceId as string },
{ enabled: !!workspaceId }
)
const { data: membersData } = trpc.workspace.listMembersInWorkspace.useQuery(
{ workspaceId: workspaceId! },
{ workspaceId: workspaceId as string },
{ enabled: !!workspaceId }
)

View File

@ -15,7 +15,7 @@ import {
UsersIcon,
} from '@/components/icons'
import { EmojiOrImageIcon } from '@/components/EmojiOrImageIcon'
import { GraphNavigation, User, Workspace, WorkspaceRole } from 'db'
import { User, Workspace, WorkspaceRole } from 'db'
import { useState } from 'react'
import { MembersList } from './MembersList'
import { WorkspaceSettingsForm } from './WorkspaceSettingsForm'
@ -149,13 +149,7 @@ export const WorkspaceSettingsModal = ({
{isOpen && (
<Flex flex="1" p="10">
<SettingsContent
tab={selectedTab}
onClose={onClose}
defaultGraphNavigation={
user.graphNavigation ?? GraphNavigation.TRACKPAD
}
/>
<SettingsContent tab={selectedTab} onClose={onClose} />
</Flex>
)}
</ModalContent>
@ -165,11 +159,9 @@ export const WorkspaceSettingsModal = ({
const SettingsContent = ({
tab,
defaultGraphNavigation,
onClose,
}: {
tab: SettingsTab
defaultGraphNavigation: GraphNavigation
onClose: () => void
}) => {
switch (tab) {

View File

@ -17,6 +17,7 @@
*/
import * as Sentry from '@sentry/nextjs'
import { NextPageContext } from 'next'
import NextErrorComponent from 'next/error'
const CustomErrorComponent = (props: {
@ -31,7 +32,7 @@ const CustomErrorComponent = (props: {
return <NextErrorComponent statusCode={props.statusCode} />
}
CustomErrorComponent.getInitialProps = async (contextData: any) => {
CustomErrorComponent.getInitialProps = async (contextData: NextPageContext) => {
// In case this is running in a serverless function, await this in order to give Sentry
// time to send the error before the lambda exits
await Sentry.captureUnderscoreErrorException(contextData)

View File

@ -13,7 +13,9 @@ const handler = async (req: NextApiRequest, res: NextApiResponse) => {
const domain = req.query.domain as string
try {
await deleteDomainOnVercel(domain)
} catch {}
} catch {
/* empty */
}
const customDomains = await prisma.customDomain.delete({
where: { name: domain },
})

View File

@ -1,4 +1,4 @@
import { captureException, withSentry } from '@sentry/nextjs'
import { captureException } from '@sentry/nextjs'
import { SmtpCredentialsData } from 'models'
import { NextApiRequest, NextApiResponse } from 'next'
import { createTransport } from 'nodemailer'

View File

@ -2,7 +2,7 @@ import { NextApiRequest, NextApiResponse } from 'next'
import { drive } from '@googleapis/drive'
import { getAuthenticatedGoogleClient } from '@/lib/googleSheets'
import { badRequest, methodNotAllowed, notAuthenticated } from 'utils/api'
import { setUser, withSentry } from '@sentry/nextjs'
import { setUser } from '@sentry/nextjs'
import { getAuthenticatedUser } from '@/features/auth/api'
const handler = async (req: NextApiRequest, res: NextApiResponse) => {

View File

@ -3,7 +3,7 @@ import { GoogleSpreadsheet } from 'google-spreadsheet'
import { getAuthenticatedGoogleClient } from '@/lib/googleSheets'
import { isDefined } from 'utils'
import { badRequest, methodNotAllowed, notAuthenticated } from 'utils/api'
import { withSentry, setUser } from '@sentry/nextjs'
import { setUser } from '@sentry/nextjs'
import { getAuthenticatedUser } from '@/features/auth/api'
const handler = async (req: NextApiRequest, res: NextApiResponse) => {

View File

@ -5,6 +5,7 @@ import Cors from 'micro-cors'
import { buffer } from 'micro'
import prisma from '@/lib/prisma'
import { Plan } from 'db'
import { RequestHandler } from 'next/dist/server/next'
if (!process.env.STRIPE_SECRET_KEY || !process.env.STRIPE_WEBHOOK_SECRET)
throw new Error('STRIPE_SECRET_KEY or STRIPE_WEBHOOK_SECRET missing')
@ -127,4 +128,4 @@ const webhookHandler = async (req: NextApiRequest, res: NextApiResponse) => {
return methodNotAllowed(res)
}
export default cors(webhookHandler as any)
export default cors(webhookHandler as RequestHandler)