A modern, intuitive visual flow builder for creating chatbot conversations. Built with React, TypeScript, and React Flow.
π Live Demo: Live Demo
- Features
- Screenshots
- Tech Stack
- Project Structure
- Getting Started
- Usage Guide
- Validation Rules
- Extensibility
- Deployment
- Assignment Completion
- Drag and Drop Interface: Intuitive node placement on canvas
- Visual Connection System: Connect nodes with visual edges to define conversation flow
- Real-time Editing: Edit message content with instant visual feedback
- Flow Validation: Smart validation ensures proper chatbot flow structure
- Auto-Save to localStorage: Flow automatically persists and restores on page refresh
- Responsive Design: Works seamlessly across different screen sizes
- TypeScript: Full type safety across the application
- Custom React Hooks: Reusable logic with
useFlowValidation,useNodeOperations,useFlowPersistence - Clean Architecture: Well-organized, maintainable codebase
- Extensible Design: Easy to add new node types
- Commented Code: Comprehensive documentation for future developers
- Production Ready: Optimized build with proper error handling
- Canvas area with draggable nodes
- Right panel showing available node types
- Save button with validation
- Appears when a node is selected
- Real-time text editing
- Easy navigation back to nodes panel
- Success notification when flow is valid
- Error notification with descriptive message when flow is invalid
- React 18 - UI Framework
- TypeScript - Type Safety
- React Flow - Flow visualization and management
- Vite - Build tool and dev server
- CSS3 - Styling with modern features
src/
βββ components/
β βββ FlowBuilder.tsx # Main orchestrator component
β βββ TextNode.tsx # Custom message node component
β βββ NodesPanel.tsx # Panel with draggable node types
β βββ SettingsPanel.tsx # Node editing interface
β βββ SaveButton.tsx # Validation and save functionality
βββ hooks/
β βββ index.ts # Hooks barrel export
β βββ useFlowValidation.ts # Validation & notification logic
β βββ useNodeOperations.ts # Node CRUD operations
β βββ useFlowPersistence.ts # localStorage save/load logic
βββ types/
β βββ index.ts # TypeScript type definitions
βββ utils/
β βββ validation.ts # Flow validation logic
βββ styles/
β βββ FlowBuilder.css # Main canvas styles
β βββ TextNode.css # Node styling
β βββ NodesPanel.css # Nodes panel styling
β βββ SettingsPanel.css # Settings panel styling
β βββ SaveButton.css # Button and notification styles
βββ App.tsx # Root component
βββ main.tsx # Application entry point
βββ index.css # Global styles
- Node.js (v18 or higher recommended)
- npm or yarn
- Clone the repository
git clone <your-repo-url>
cd chatbot-flow-builder- Install dependencies
npm install- Start development server
npm run dev- Open browser and navigate to
http://localhost:5173
npm run buildThe production-ready files will be in the dist/ directory.
- Look at the Nodes Panel on the right side
- Find the Message node type
- Drag it onto the canvas
- Drop it where you want it placed
- Click and drag from a node's source handle (right side)
- Connect to another node's target handle (left side)
- The edge (connection) will be created
- Note: Each source handle can only have ONE outgoing connection
- Click on a node to select it
- The Settings Panel appears on the right
- Edit the text in the textarea
- Changes are saved automatically
- Click the back button to return to the Nodes Panel
- Click the Save Changes button (top right)
- The flow will be validated
- You'll see either:
- β Success message if flow is valid (automatically saved to localStorage)
- β Error message if flow has issues
Your flow is automatically saved and restored:
- On Save: When you click "Save Changes" and validation passes, the flow is saved to browser localStorage
- On Load: When you refresh the page or return later, your flow is automatically restored
- No Setup: Everything works out of the box - no configuration needed
Note: localStorage is browser-specific and domain-specific. Your flow persists across sessions but is stored locally in your browser.
The flow builder enforces one key rule:
If there are more than one nodes, then more than one node cannot have empty target handles.
- Empty Target Handle: A node with no incoming connections
- Valid Flow: At most ONE node can have an empty target (the start node)
- Invalid Flow: Multiple nodes with empty targets means a disconnected flow
β Valid Flows:
- Single node (no connections needed)
- Multiple nodes where only ONE has no incoming connection
- All nodes connected in a sequence
β Invalid Flows:
- Two or more disconnected nodes
- Multiple "start" nodes with no incoming connections
The codebase is designed for easy extension with custom React hooks and modular architecture.
The application uses three custom hooks for clean separation of concerns:
Handles flow validation and notification state management:
const { notification, validateAndSave } = useFlowValidation();
const isValid = validateAndSave(nodes, edges);Provides methods for node CRUD operations:
const { updateNodeData, deleteNode, duplicateNode, getNodeById } =
useNodeOperations({ nodes, setNodes });Manages localStorage save/load operations:
const { saveFlow, loadFlow, clearFlow, hasStoredFlow } =
useFlowPersistence({ nodes, edges, setNodes, setEdges });Here's how to add a new node type:
// src/types/index.ts
export const NodeType = {
TEXT_MESSAGE: 'textMessage',
IMAGE_MESSAGE: 'imageMessage', // New type
} as const;// src/types/index.ts
export interface ImageMessageData {
imageUrl: string;
caption: string;
}// src/components/ImageNode.tsx
import { memo } from 'react';
import { Handle, Position, type NodeProps } from 'reactflow';
import type { ImageMessageData } from '../types';
const ImageNode = ({ data }: NodeProps<ImageMessageData>) => {
return (
<div className="image-node">
<Handle type="target" position={Position.Left} />
<img src={data.imageUrl} alt={data.caption} />
<Handle type="source" position={Position.Right} />
</div>
);
};
export default memo(ImageNode);// src/components/FlowBuilder.tsx
const nodeTypes = {
[NodeType.TEXT_MESSAGE]: TextNode,
[NodeType.IMAGE_MESSAGE]: ImageNode, // Register new type
};// src/components/NodesPanel.tsx
const availableNodes: DraggableNodeType[] = [
{
type: NodeType.TEXT_MESSAGE,
label: 'Message',
icon: 'π¬',
description: 'Send a text message'
},
{
type: NodeType.IMAGE_MESSAGE,
label: 'Image',
icon: 'πΌοΈ',
description: 'Send an image'
},
];- Install Vercel CLI
npm install -g vercel- Build the project
npm run build- Deploy
vercel --prod- Build the project
npm run build- Drag and drop the
distfolder to Netlify Drop
Or use Netlify CLI:
npm install -g netlify-cli
netlify deploy --prod --dir=dist- Install gh-pages
npm install --save-dev gh-pages- Add to package.json
{
"homepage": "https://yourusername.github.io/chatbot-flow-builder",
"scripts": {
"predeploy": "npm run build",
"deploy": "gh-pages -d dist"
}
}- Deploy
npm run deployThis project was built as a submission for the BiteSpeed Frontend Task. Here's how it meets all requirements:
- Text Node - Custom node component with message display
- Nodes Panel - Draggable panel with available node types
- Edge - Visual connections between nodes
- Source Handle - Only one edge originating from source (enforced)
- Target Handle - Multiple edges can connect to target
- Settings Panel - Replaces nodes panel when node is selected
- Save Button - Validates flow and shows notifications
- β Built with React and TypeScript
- β Uses React Flow library
- β Code is well-commented
- β Extensible architecture for adding new node types
- β Proper validation logic implemented
- β Production build works correctly
Beyond the basic requirements, this submission includes:
- Custom React Hooks - Three reusable hooks (
useFlowValidation,useNodeOperations,useFlowPersistence) - Auto-Persistence - Flow automatically saves to localStorage and restores on refresh
- Advanced TypeScript - Full type safety with no
anytypes - Clean Architecture - Separation of concerns (components, hooks, utils, types)
- Professional UI/UX - Smooth animations, hover states, and visual feedback
- Comprehensive Documentation - Detailed README, FEATURES.md, and SUBMISSION_GUIDE.md
- β Code hosted on GitHub
- β Application deployed and accessible
- β README with deployment link
- β All features working as specified
- β Clean, commented code
- β TypeScript for better code quality
This is a submission project, but suggestions are welcome! Feel free to open an issue or reach out.
MIT License - feel free to use this code for learning and development.
Built with β€οΈ for the BiteSpeed Frontend Task