mirror of
https://github.com/stackblitz/bolt.new
synced 2024-11-27 14:32:46 +00:00
chore(eslint): enforce consistent import paths (#8)
This commit is contained in:
parent
d45b95dd11
commit
2a3d5f569e
@ -1,9 +1,10 @@
|
||||
import blitzPlugin from '@blitz/eslint-plugin';
|
||||
import { getNamingConventionRule } from '@blitz/eslint-plugin/dist/configs/typescript.js';
|
||||
import { jsFileExtensions } from '@blitz/eslint-plugin/dist/configs/javascript.js';
|
||||
import { getNamingConventionRule, tsFileExtensions } from '@blitz/eslint-plugin/dist/configs/typescript.js';
|
||||
|
||||
export default [
|
||||
{
|
||||
ignores: ['**/dist', '**/node_modules'],
|
||||
ignores: ['**/dist', '**/node_modules', '**/.wrangler', '**/bolt/build'],
|
||||
},
|
||||
...blitzPlugin.configs.recommended(),
|
||||
{
|
||||
@ -25,4 +26,20 @@ export default [
|
||||
'@typescript-eslint/no-empty-object-type': 'off',
|
||||
},
|
||||
},
|
||||
{
|
||||
files: [...tsFileExtensions, ...jsFileExtensions, '**/*.tsx'],
|
||||
rules: {
|
||||
'no-restricted-imports': [
|
||||
'error',
|
||||
{
|
||||
patterns: [
|
||||
{
|
||||
group: ['../'],
|
||||
message: `Relative imports are not allowed. Please use '~/' instead.`,
|
||||
},
|
||||
],
|
||||
},
|
||||
],
|
||||
},
|
||||
},
|
||||
];
|
||||
|
@ -3,11 +3,11 @@ import { AnimatePresence, motion } from 'framer-motion';
|
||||
import { computed } from 'nanostores';
|
||||
import { memo, useEffect, useRef, useState } from 'react';
|
||||
import { createHighlighter, type BundledLanguage, type BundledTheme, type HighlighterGeneric } from 'shiki';
|
||||
import type { ActionState } from '../../lib/runtime/action-runner';
|
||||
import { chatStore } from '../../lib/stores/chat';
|
||||
import { workbenchStore } from '../../lib/stores/workbench';
|
||||
import { classNames } from '../../utils/classNames';
|
||||
import { cubicEasingFn } from '../../utils/easings';
|
||||
import type { ActionState } from '~/lib/runtime/action-runner';
|
||||
import { chatStore } from '~/lib/stores/chat';
|
||||
import { workbenchStore } from '~/lib/stores/workbench';
|
||||
import { classNames } from '~/utils/classNames';
|
||||
import { cubicEasingFn } from '~/utils/easings';
|
||||
|
||||
const highlighterOptions = {
|
||||
langs: ['shell'],
|
||||
|
@ -1,9 +1,9 @@
|
||||
import type { Message } from 'ai';
|
||||
import React, { type LegacyRef, type RefCallback } from 'react';
|
||||
import { ClientOnly } from 'remix-utils/client-only';
|
||||
import { classNames } from '../../utils/classNames';
|
||||
import { IconButton } from '../ui/IconButton';
|
||||
import { Workbench } from '../workbench/Workbench.client';
|
||||
import { IconButton } from '~/components/ui/IconButton';
|
||||
import { Workbench } from '~/components/workbench/Workbench.client';
|
||||
import { classNames } from '~/utils/classNames';
|
||||
import { Messages } from './Messages.client';
|
||||
import { SendButton } from './SendButton.client';
|
||||
|
||||
|
@ -2,11 +2,11 @@ import { useChat } from 'ai/react';
|
||||
import { useAnimate } from 'framer-motion';
|
||||
import { useEffect, useRef, useState } from 'react';
|
||||
import { ToastContainer, cssTransition } from 'react-toastify';
|
||||
import { useMessageParser, usePromptEnhancer, useSnapScroll } from '../../lib/hooks';
|
||||
import { chatStore } from '../../lib/stores/chat';
|
||||
import { workbenchStore } from '../../lib/stores/workbench';
|
||||
import { cubicEasingFn } from '../../utils/easings';
|
||||
import { createScopedLogger } from '../../utils/logger';
|
||||
import { useMessageParser, usePromptEnhancer, useSnapScroll } from '~/lib/hooks';
|
||||
import { chatStore } from '~/lib/stores/chat';
|
||||
import { workbenchStore } from '~/lib/stores/workbench';
|
||||
import { cubicEasingFn } from '~/utils/easings';
|
||||
import { createScopedLogger } from '~/utils/logger';
|
||||
import { BaseChat } from './BaseChat';
|
||||
|
||||
const toastAnimation = cssTransition({
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { memo, useEffect, useState } from 'react';
|
||||
import { bundledLanguages, codeToHtml, isSpecialLang, type BundledLanguage, type SpecialLanguage } from 'shiki';
|
||||
import { classNames } from '../../utils/classNames';
|
||||
import { createScopedLogger } from '../../utils/logger';
|
||||
import { classNames } from '~/utils/classNames';
|
||||
import { createScopedLogger } from '~/utils/logger';
|
||||
import styles from './CodeBlock.module.scss';
|
||||
|
||||
const logger = createScopedLogger('CodeBlock');
|
||||
|
@ -1,8 +1,8 @@
|
||||
import { memo, useMemo } from 'react';
|
||||
import ReactMarkdown, { type Components } from 'react-markdown';
|
||||
import type { BundledLanguage } from 'shiki';
|
||||
import { createScopedLogger } from '../../utils/logger';
|
||||
import { rehypePlugins, remarkPlugins } from '../../utils/markdown';
|
||||
import { createScopedLogger } from '~/utils/logger';
|
||||
import { rehypePlugins, remarkPlugins } from '~/utils/markdown';
|
||||
import { Artifact } from './Artifact';
|
||||
import { CodeBlock } from './CodeBlock';
|
||||
|
||||
|
@ -1,8 +1,8 @@
|
||||
import type { Message } from 'ai';
|
||||
import { classNames } from '../../utils/classNames';
|
||||
import React from 'react';
|
||||
import { classNames } from '~/utils/classNames';
|
||||
import { AssistantMessage } from './AssistantMessage';
|
||||
import { UserMessage } from './UserMessage';
|
||||
import React from 'react';
|
||||
|
||||
interface MessagesProps {
|
||||
id?: string;
|
||||
|
@ -14,10 +14,10 @@ import {
|
||||
scrollPastEnd,
|
||||
} from '@codemirror/view';
|
||||
import { memo, useEffect, useRef, useState, type MutableRefObject } from 'react';
|
||||
import type { Theme } from '../../../types/theme';
|
||||
import { classNames } from '../../../utils/classNames';
|
||||
import { debounce } from '../../../utils/debounce';
|
||||
import { createScopedLogger, renderLogger } from '../../../utils/logger';
|
||||
import type { Theme } from '~/types/theme';
|
||||
import { classNames } from '~/utils/classNames';
|
||||
import { debounce } from '~/utils/debounce';
|
||||
import { createScopedLogger, renderLogger } from '~/utils/logger';
|
||||
import { BinaryContent } from './BinaryContent';
|
||||
import { getTheme, reconfigureTheme } from './cm-theme';
|
||||
import { indentKeyBinding } from './indent';
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { defaultHighlightStyle, syntaxHighlighting } from '@codemirror/language';
|
||||
import { Compartment, type Extension } from '@codemirror/state';
|
||||
import { EditorView } from '@codemirror/view';
|
||||
import type { Theme } from '../../../types/theme.js';
|
||||
import type { Theme } from '~/types/theme.js';
|
||||
import type { EditorSettings } from './CodeMirrorEditor.js';
|
||||
import { vscodeDarkTheme } from './themes/vscode-dark.js';
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { memo } from 'react';
|
||||
import { classNames } from '../../utils/classNames';
|
||||
import { classNames } from '~/utils/classNames';
|
||||
|
||||
type IconSize = 'sm' | 'md' | 'xl' | 'xxl';
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { memo } from 'react';
|
||||
import { classNames } from '../../utils/classNames';
|
||||
import { classNames } from '~/utils/classNames';
|
||||
|
||||
interface PanelHeaderButtonProps {
|
||||
className?: string;
|
||||
|
@ -1,10 +1,6 @@
|
||||
import { useStore } from '@nanostores/react';
|
||||
import { memo, useMemo } from 'react';
|
||||
import { Panel, PanelGroup, PanelResizeHandle } from 'react-resizable-panels';
|
||||
import type { FileMap } from '../../lib/stores/files';
|
||||
import { themeStore } from '../../lib/stores/theme';
|
||||
import { renderLogger } from '../../utils/logger';
|
||||
import { isMobile } from '../../utils/mobile';
|
||||
import {
|
||||
CodeMirrorEditor,
|
||||
type EditorDocument,
|
||||
@ -12,8 +8,12 @@ import {
|
||||
type OnChangeCallback as OnEditorChange,
|
||||
type OnSaveCallback as OnEditorSave,
|
||||
type OnScrollCallback as OnEditorScroll,
|
||||
} from '../editor/codemirror/CodeMirrorEditor';
|
||||
import { PanelHeaderButton } from '../ui/PanelHeaderButton';
|
||||
} from '~/components/editor/codemirror/CodeMirrorEditor';
|
||||
import { PanelHeaderButton } from '~/components/ui/PanelHeaderButton';
|
||||
import type { FileMap } from '~/lib/stores/files';
|
||||
import { themeStore } from '~/lib/stores/theme';
|
||||
import { renderLogger } from '~/utils/logger';
|
||||
import { isMobile } from '~/utils/mobile';
|
||||
import { FileTreePanel } from './FileTreePanel';
|
||||
|
||||
interface EditorPanelProps {
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { memo, useEffect, useMemo, useState, type ReactNode } from 'react';
|
||||
import type { FileMap } from '../../lib/stores/files';
|
||||
import { classNames } from '../../utils/classNames';
|
||||
import { renderLogger } from '../../utils/logger';
|
||||
import type { FileMap } from '~/lib/stores/files';
|
||||
import { classNames } from '~/utils/classNames';
|
||||
import { renderLogger } from '~/utils/logger';
|
||||
|
||||
const NODE_PADDING_LEFT = 12;
|
||||
const DEFAULT_HIDDEN_FILES = [/\/node_modules\//];
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { memo } from 'react';
|
||||
import type { FileMap } from '../../lib/stores/files';
|
||||
import { WORK_DIR } from '../../utils/constants';
|
||||
import { renderLogger } from '../../utils/logger';
|
||||
import type { FileMap } from '~/lib/stores/files';
|
||||
import { WORK_DIR } from '~/utils/constants';
|
||||
import { renderLogger } from '~/utils/logger';
|
||||
import { FileTree } from './FileTree';
|
||||
|
||||
interface FileTreePanelProps {
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { useStore } from '@nanostores/react';
|
||||
import { memo, useEffect, useRef, useState } from 'react';
|
||||
import { workbenchStore } from '../../lib/stores/workbench';
|
||||
import { IconButton } from '../ui/IconButton';
|
||||
import { IconButton } from '~/components/ui/IconButton';
|
||||
import { workbenchStore } from '~/lib/stores/workbench';
|
||||
|
||||
export const Preview = memo(() => {
|
||||
const iframeRef = useRef<HTMLIFrameElement>(null);
|
||||
|
@ -3,14 +3,14 @@ import { AnimatePresence, motion, type Variants } from 'framer-motion';
|
||||
import { memo, useCallback, useEffect } from 'react';
|
||||
import { Panel, PanelGroup, PanelResizeHandle } from 'react-resizable-panels';
|
||||
import { toast } from 'react-toastify';
|
||||
import { workbenchStore } from '../../lib/stores/workbench';
|
||||
import { cubicEasingFn } from '../../utils/easings';
|
||||
import { renderLogger } from '../../utils/logger';
|
||||
import {
|
||||
type OnChangeCallback as OnEditorChange,
|
||||
type OnScrollCallback as OnEditorScroll,
|
||||
} from '../editor/codemirror/CodeMirrorEditor';
|
||||
import { IconButton } from '../ui/IconButton';
|
||||
} from '~/components/editor/codemirror/CodeMirrorEditor';
|
||||
import { IconButton } from '~/components/ui/IconButton';
|
||||
import { workbenchStore } from '~/lib/stores/workbench';
|
||||
import { cubicEasingFn } from '~/utils/easings';
|
||||
import { renderLogger } from '~/utils/logger';
|
||||
import { EditorPanel } from './EditorPanel';
|
||||
import { Preview } from './Preview';
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { WORK_DIR } from '../../../utils/constants';
|
||||
import { stripIndents } from '../../../utils/stripIndent';
|
||||
import { WORK_DIR } from '~/utils/constants';
|
||||
import { stripIndents } from '~/utils/stripIndent';
|
||||
|
||||
export const getSystemPrompt = (cwd: string = WORK_DIR) => `
|
||||
You are Bolt, an expert AI assistant and exceptional senior software developer with vast knowledge across multiple programming languages, frameworks, and best practices.
|
||||
|
@ -1,6 +1,6 @@
|
||||
import { streamText as _streamText, convertToCoreMessages } from 'ai';
|
||||
import { getAPIKey } from '../llm/api-key';
|
||||
import { getAnthropicModel } from '../llm/model';
|
||||
import { getAPIKey } from '~/lib/.server/llm/api-key';
|
||||
import { getAnthropicModel } from '~/lib/.server/llm/model';
|
||||
import { MAX_TOKENS } from './constants';
|
||||
import { getSystemPrompt } from './prompts';
|
||||
|
||||
|
@ -1,8 +1,8 @@
|
||||
import type { Message } from 'ai';
|
||||
import { useCallback, useState } from 'react';
|
||||
import { createScopedLogger } from '../../utils/logger';
|
||||
import { StreamingMessageParser } from '../runtime/message-parser';
|
||||
import { workbenchStore } from '../stores/workbench';
|
||||
import { StreamingMessageParser } from '~/lib/runtime/message-parser';
|
||||
import { workbenchStore } from '~/lib/stores/workbench';
|
||||
import { createScopedLogger } from '~/utils/logger';
|
||||
|
||||
const logger = createScopedLogger('useMessageParser');
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { useState } from 'react';
|
||||
import { createScopedLogger } from '../../utils/logger';
|
||||
import { createScopedLogger } from '~/utils/logger';
|
||||
|
||||
const logger = createScopedLogger('usePromptEnhancement');
|
||||
|
||||
|
@ -1,9 +1,9 @@
|
||||
import { WebContainer } from '@webcontainer/api';
|
||||
import { map, type MapStore } from 'nanostores';
|
||||
import * as nodePath from 'node:path';
|
||||
import type { BoltAction } from '../../types/actions';
|
||||
import { createScopedLogger } from '../../utils/logger';
|
||||
import { unreachable } from '../../utils/unreachable';
|
||||
import type { BoltAction } from '~/types/actions';
|
||||
import { createScopedLogger } from '~/utils/logger';
|
||||
import { unreachable } from '~/utils/unreachable';
|
||||
import type { ActionCallbackData } from './message-parser';
|
||||
|
||||
const logger = createScopedLogger('ActionRunner');
|
||||
|
@ -1,7 +1,7 @@
|
||||
import type { ActionType, BoltAction, BoltActionData, FileAction, ShellAction } from '../../types/actions';
|
||||
import type { BoltArtifactData } from '../../types/artifact';
|
||||
import { createScopedLogger } from '../../utils/logger';
|
||||
import { unreachable } from '../../utils/unreachable';
|
||||
import type { ActionType, BoltAction, BoltActionData, FileAction, ShellAction } from '~/types/actions';
|
||||
import type { BoltArtifactData } from '~/types/artifact';
|
||||
import { createScopedLogger } from '~/utils/logger';
|
||||
import { unreachable } from '~/utils/unreachable';
|
||||
|
||||
const ARTIFACT_TAG_OPEN = '<boltArtifact';
|
||||
const ARTIFACT_TAG_CLOSE = '</boltArtifact>';
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { atom, computed, map, type MapStore, type WritableAtom } from 'nanostores';
|
||||
import type { EditorDocument, ScrollPosition } from '../../components/editor/codemirror/CodeMirrorEditor';
|
||||
import type { EditorDocument, ScrollPosition } from '~/components/editor/codemirror/CodeMirrorEditor';
|
||||
import type { FileMap, FilesStore } from './files';
|
||||
|
||||
export type EditorDocuments = Record<string, EditorDocument>;
|
||||
|
@ -1,9 +1,9 @@
|
||||
import type { PathWatcherEvent, WebContainer } from '@webcontainer/api';
|
||||
import { map, type MapStore } from 'nanostores';
|
||||
import * as nodePath from 'node:path';
|
||||
import { bufferWatchEvents } from '../../utils/buffer';
|
||||
import { WORK_DIR } from '../../utils/constants';
|
||||
import { createScopedLogger } from '../../utils/logger';
|
||||
import { bufferWatchEvents } from '~/utils/buffer';
|
||||
import { WORK_DIR } from '~/utils/constants';
|
||||
import { createScopedLogger } from '~/utils/logger';
|
||||
|
||||
const logger = createScopedLogger('FilesStore');
|
||||
|
||||
|
@ -1,9 +1,9 @@
|
||||
import { atom, map, type MapStore, type ReadableAtom, type WritableAtom } from 'nanostores';
|
||||
import type { EditorDocument, ScrollPosition } from '../../components/editor/codemirror/CodeMirrorEditor';
|
||||
import { unreachable } from '../../utils/unreachable';
|
||||
import { ActionRunner } from '../runtime/action-runner';
|
||||
import type { ActionCallbackData, ArtifactCallbackData } from '../runtime/message-parser';
|
||||
import { webcontainer } from '../webcontainer';
|
||||
import type { EditorDocument, ScrollPosition } from '~/components/editor/codemirror/CodeMirrorEditor';
|
||||
import { ActionRunner } from '~/lib/runtime/action-runner';
|
||||
import type { ActionCallbackData, ArtifactCallbackData } from '~/lib/runtime/message-parser';
|
||||
import { webcontainer } from '~/lib/webcontainer';
|
||||
import { unreachable } from '~/utils/unreachable';
|
||||
import { EditorStore } from './editor';
|
||||
import { FilesStore, type FileMap } from './files';
|
||||
import { PreviewsStore } from './previews';
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { WebContainer } from '@webcontainer/api';
|
||||
import { WORK_DIR_NAME } from '../../utils/constants';
|
||||
import { WORK_DIR_NAME } from '~/utils/constants';
|
||||
|
||||
interface WebContainerContext {
|
||||
loaded: boolean;
|
||||
|
@ -1,9 +1,9 @@
|
||||
import { json, redirect, type LoaderFunctionArgs, type MetaFunction } from '@remix-run/cloudflare';
|
||||
import { ClientOnly } from 'remix-utils/client-only';
|
||||
import { BaseChat } from '../components/chat/BaseChat';
|
||||
import { Chat } from '../components/chat/Chat.client';
|
||||
import { Header } from '../components/Header';
|
||||
import { isAuthenticated } from '../lib/.server/sessions';
|
||||
import { BaseChat } from '~/components/chat/BaseChat';
|
||||
import { Chat } from '~/components/chat/Chat.client';
|
||||
import { Header } from '~/components/Header';
|
||||
import { isAuthenticated } from '~/lib/.server/sessions';
|
||||
|
||||
export const meta: MetaFunction = () => {
|
||||
return [{ title: 'Bolt' }, { name: 'description', content: 'Talk with Bolt, an AI assistant from StackBlitz' }];
|
||||
|
@ -1,9 +1,9 @@
|
||||
import { type ActionFunctionArgs } from '@remix-run/cloudflare';
|
||||
import { StreamingTextResponse } from 'ai';
|
||||
import { MAX_RESPONSE_SEGMENTS, MAX_TOKENS } from '../lib/.server/llm/constants';
|
||||
import { CONTINUE_PROMPT } from '../lib/.server/llm/prompts';
|
||||
import { streamText, type Messages, type StreamingOptions } from '../lib/.server/llm/stream-text';
|
||||
import SwitchableStream from '../lib/.server/llm/switchable-stream';
|
||||
import { MAX_RESPONSE_SEGMENTS, MAX_TOKENS } from '~/lib/.server/llm/constants';
|
||||
import { CONTINUE_PROMPT } from '~/lib/.server/llm/prompts';
|
||||
import { streamText, type Messages, type StreamingOptions } from '~/lib/.server/llm/stream-text';
|
||||
import SwitchableStream from '~/lib/.server/llm/switchable-stream';
|
||||
|
||||
export async function action({ context, request }: ActionFunctionArgs) {
|
||||
const { messages } = await request.json<{ messages: Messages }>();
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { type ActionFunctionArgs } from '@remix-run/cloudflare';
|
||||
import { StreamingTextResponse, parseStreamPart } from 'ai';
|
||||
import { streamText } from '../lib/.server/llm/stream-text';
|
||||
import { stripIndents } from '../utils/stripIndent';
|
||||
import { streamText } from '~/lib/.server/llm/stream-text';
|
||||
import { stripIndents } from '~/utils/stripIndent';
|
||||
|
||||
const encoder = new TextEncoder();
|
||||
const decoder = new TextDecoder();
|
||||
|
@ -6,8 +6,8 @@ import {
|
||||
type TypedResponse,
|
||||
} from '@remix-run/cloudflare';
|
||||
import { Form, useActionData } from '@remix-run/react';
|
||||
import { verifyPassword } from '../lib/.server/login';
|
||||
import { createUserSession, isAuthenticated } from '../lib/.server/sessions';
|
||||
import { verifyPassword } from '~/lib/.server/login';
|
||||
import { createUserSession, isAuthenticated } from '~/lib/.server/sessions';
|
||||
|
||||
interface Errors {
|
||||
password?: string;
|
||||
|
@ -2,7 +2,7 @@ import type { ServerBuild } from '@remix-run/cloudflare';
|
||||
import { createPagesFunctionHandler } from '@remix-run/cloudflare-pages';
|
||||
|
||||
// @ts-ignore because the server build file is generated by `remix vite:build`
|
||||
import * as serverBuild from '../build/server';
|
||||
import * as serverBuild from '~/build/server';
|
||||
|
||||
export const onRequest = createPagesFunctionHandler({
|
||||
build: serverBuild as unknown as ServerBuild,
|
||||
|
Loading…
Reference in New Issue
Block a user