@blockspark/chat-widget 1.0.1 → 1.0.3

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/README.md CHANGED
@@ -1,106 +1,145 @@
1
1
  # BlockSpark Chat Widget
2
2
 
3
- A reusable React chat widget component that connects directly with Dialogflow CX - no backend API required!
3
+ A reusable chat widget for **React**, **Next.js**, **Vue 3**, and **vanilla HTML (CDN)** that connects directly with Dialogflow CX no backend API required.
4
4
 
5
5
  ## Installation
6
6
 
7
- ### Option 1: Install from Local Path (Recommended for Development)
7
+ Install from npm (for React, Next.js, or Vue projects):
8
8
 
9
9
  ```bash
10
- # In your website project directory
11
- npm install /path/to/blockspark-chat-widget
12
- # or
13
- npm install ../blockspark-chat-widget
10
+ npm install @blockspark/chat-widget
14
11
  ```
15
12
 
16
- ### Option 2: Use npm link (For Development)
13
+ - **React / Next.js**: You also need `react` and `react-dom` (they are peer dependencies).
14
+ - **Vue 3**: You also need `vue`. The widget bundles React internally for the Vue build, so you do **not** need to install React.
17
15
 
18
16
  ```bash
19
- # In the blockspark-chat-widget directory
20
- npm link
17
+ # React or Next.js
18
+ npm install @blockspark/chat-widget react react-dom
21
19
 
22
- # In your website project directory
23
- npm link @blockspark/chat-widget
20
+ # Vue 3 only
21
+ npm install @blockspark/chat-widget vue
24
22
  ```
25
23
 
26
- ### Option 3: Publish to npm (For Production)
24
+ **Development / local testing:**
27
25
 
28
26
  ```bash
29
- # Build the library first
30
- npm run build
31
-
32
- # Publish to npm (make sure you're logged in)
33
- npm publish
27
+ # From your app directory
28
+ npm install /path/to/blockspark-chat-widget
29
+ # or use npm link in the widget repo, then npm link @blockspark/chat-widget in your app
34
30
  ```
35
31
 
36
- Then install in your project:
37
- ```bash
38
- npm install @blockspark/chat-widget
39
- ```
32
+ ---
40
33
 
41
34
  ## Usage
42
35
 
43
- ### Basic Usage
36
+ Use **camelCase** for all props in every environment (React, Next.js, Vue, and CDN). Examples: `dfProjectId`, `serviceAccountKey`, `languageCode`.
37
+
38
+ ---
39
+
40
+ ### React
41
+
42
+ Import the component and the default styles, then render with your config. Copy the props below and replace the placeholder values with yours.
44
43
 
45
44
  ```tsx
46
45
  import ChatWidget from '@blockspark/chat-widget';
47
46
  import '@blockspark/chat-widget/dist/styles.css';
48
47
 
49
- // Load your Google Cloud service account key
50
48
  import serviceAccountKey from './path/to/service-account-key.json';
51
49
 
52
50
  function App() {
53
51
  return (
54
- <div>
55
- <ChatWidget
56
- dfProjectId="your-project-id"
57
- dfLocation="us-central1"
58
- dfAgentId="your-agent-id"
59
- serviceAccountKey={serviceAccountKey}
60
- languageCode="en"
61
- />
62
- </div>
52
+ <ChatWidget
53
+ dfProjectId="your-project-id"
54
+ dfLocation="us-central1"
55
+ dfAgentId="your-agent-id"
56
+ serviceAccountKey={serviceAccountKey}
57
+ // accessToken="your-token" // use instead of serviceAccountKey if you have a token
58
+ languageCode="en"
59
+ title="💬 BlockSpark AI Assistant"
60
+ subtitle="We're here to help"
61
+ welcomeTitle="👋 Welcome to Blockspark"
62
+ welcomeMessage="My name is BlockSpark AI Assistant and I'll guide you."
63
+ welcomeCta="💬 Click here to start chatting!"
64
+ showWelcomePopup={true}
65
+ welcomePopupDelay={1500}
66
+ fallbackWelcomeMessage="Hello! I'm BlockSpark AI Assistant. How can I help you today?"
67
+ inputPlaceholder="Type your message..."
68
+ emptyStateMessage="Hi! I'm BlockSpark AI Assistant. How can I help you today?"
69
+ debug={false}
70
+ backendBaseUrl="http://localhost:8012"
71
+ backendWsUrl="ws://localhost:8012"
72
+ />
63
73
  );
64
74
  }
65
75
  ```
66
76
 
67
- ### Using Access Token (Alternative)
77
+ ### Next.js
68
78
 
69
- If you prefer to manage authentication yourself:
79
+ The widget uses browser APIs (e.g. `localStorage`) and is intended to run on the client. Use **dynamic import with SSR disabled** so it only loads in the browser.
80
+
81
+ **App Router (Next.js 13+):**
70
82
 
71
83
  ```tsx
72
- import ChatWidget from '@blockspark/chat-widget';
84
+ 'use client';
85
+
86
+ import dynamic from 'next/dynamic';
73
87
  import '@blockspark/chat-widget/dist/styles.css';
74
88
 
75
- function App() {
76
- const [accessToken, setAccessToken] = useState<string>('');
89
+ const ChatWidget = dynamic(
90
+ () => import('@blockspark/chat-widget').then((mod) => mod.default),
91
+ { ssr: false }
92
+ );
77
93
 
78
- // Get access token from your backend or OAuth flow
79
- useEffect(() => {
80
- // Your token fetching logic here
81
- fetchAccessToken().then(setAccessToken);
82
- }, []);
94
+ export default function Page() {
95
+ const serviceAccountKey = {
96
+ /* your key object, or load from env/server */
97
+ };
83
98
 
84
99
  return (
85
- <ChatWidget
86
- dfProjectId="your-project-id"
87
- dfLocation="us-central1"
88
- dfAgentId="your-agent-id"
89
- accessToken={accessToken}
90
- languageCode="en"
91
- />
100
+ <div>
101
+ <h1>My Page</h1>
102
+ <ChatWidget
103
+ dfProjectId="your-project-id"
104
+ dfLocation="us-central1"
105
+ dfAgentId="your-agent-id"
106
+ serviceAccountKey={serviceAccountKey}
107
+ languageCode="en"
108
+ title="💬 BlockSpark AI Assistant"
109
+ subtitle="We're here to help"
110
+ welcomeTitle="👋 Welcome to Blockspark"
111
+ welcomeMessage="My name is BlockSpark AI Assistant and I'll guide you."
112
+ welcomeCta="💬 Click here to start chatting!"
113
+ showWelcomePopup={true}
114
+ welcomePopupDelay={1500}
115
+ fallbackWelcomeMessage="Hello! I'm BlockSpark AI Assistant. How can I help you today?"
116
+ inputPlaceholder="Type your message..."
117
+ emptyStateMessage="Hi! I'm BlockSpark AI Assistant. How can I help you today?"
118
+ debug={false}
119
+ backendBaseUrl="http://localhost:8012"
120
+ backendWsUrl="ws://localhost:8012"
121
+ />
122
+ </div>
92
123
  );
93
124
  }
94
125
  ```
95
126
 
96
- ### With Custom Configuration
127
+ **Pages Router:**
97
128
 
98
129
  ```tsx
99
- import ChatWidget from '@blockspark/chat-widget';
130
+ import dynamic from 'next/dynamic';
100
131
  import '@blockspark/chat-widget/dist/styles.css';
101
- import serviceAccountKey from './service-account-key.json';
102
132
 
103
- function App() {
133
+ const ChatWidget = dynamic(
134
+ () => import('@blockspark/chat-widget').then((mod) => mod.default),
135
+ { ssr: false }
136
+ );
137
+
138
+ export default function ChatPage() {
139
+ const serviceAccountKey = process.env.NEXT_PUBLIC_SERVICE_ACCOUNT_KEY_JSON
140
+ ? JSON.parse(process.env.NEXT_PUBLIC_SERVICE_ACCOUNT_KEY_JSON)
141
+ : undefined;
142
+
104
143
  return (
105
144
  <ChatWidget
106
145
  dfProjectId="your-project-id"
@@ -108,65 +147,200 @@ function App() {
108
147
  dfAgentId="your-agent-id"
109
148
  serviceAccountKey={serviceAccountKey}
110
149
  languageCode="en"
111
- title="💬 My Chat Assistant"
112
- subtitle="How can I help you?"
113
- welcomeTitle="👋 Welcome!"
114
- welcomeMessage="I'm here to help you with any questions."
115
- welcomeCta="Start chatting"
150
+ title="💬 BlockSpark AI Assistant"
151
+ subtitle="We're here to help"
152
+ welcomeTitle="👋 Welcome to Blockspark"
153
+ welcomeMessage="My name is BlockSpark AI Assistant and I'll guide you."
154
+ welcomeCta="💬 Click here to start chatting!"
116
155
  showWelcomePopup={true}
117
- welcomePopupDelay={2000}
156
+ welcomePopupDelay={1500}
157
+ fallbackWelcomeMessage="Hello! I'm BlockSpark AI Assistant. How can I help you today?"
118
158
  inputPlaceholder="Type your message..."
119
- emptyStateMessage="Hi! How can I help you today?"
159
+ emptyStateMessage="Hi! I'm BlockSpark AI Assistant. How can I help you today?"
120
160
  debug={false}
161
+ backendBaseUrl="http://localhost:8012"
162
+ backendWsUrl="ws://localhost:8012"
121
163
  />
122
164
  );
123
165
  }
124
166
  ```
125
167
 
126
- ### Using Environment Variables
168
+ **Important:** Do not expose raw service account keys in client-side code in production. Prefer a backend that returns short-lived tokens or use a proxy.
127
169
 
128
- You can configure the backend API URLs for Human Support Mode using environment variables. Create a `.env` file in the project root:
170
+ ### Vue 3
129
171
 
130
- ```bash
131
- # .env file
132
- REACT_APP_BACKEND_BASE_URL=http://localhost:8012
133
- REACT_APP_BACKEND_WS_URL=ws://localhost:8012
172
+ Use either the global plugin or the component directly.
173
+
174
+ **Option A — Global plugin (e.g. `main.js` / `main.ts`):**
175
+
176
+ ```js
177
+ import { createApp } from 'vue';
178
+ import App from './App.vue';
179
+ import BlockSparkChatWidget from '@blockspark/chat-widget/vue';
180
+ import '@blockspark/chat-widget/dist/styles.css';
181
+
182
+ const app = createApp(App);
183
+ app.use(BlockSparkChatWidget); // registers <BlockSparkChatWidget>
184
+ app.mount('#app');
134
185
  ```
135
186
 
136
- Or pass them as props:
187
+ Then in any template (copy and replace the placeholder values):
188
+
189
+ ```vue
190
+ <template>
191
+ <BlockSparkChatWidget
192
+ dfProjectId="your-project-id"
193
+ dfLocation="us-central1"
194
+ dfAgentId="your-agent-id"
195
+ :serviceAccountKey="serviceAccountKey"
196
+ languageCode="en"
197
+ title="💬 BlockSpark AI Assistant"
198
+ subtitle="We're here to help"
199
+ welcomeTitle="👋 Welcome to Blockspark"
200
+ welcomeMessage="My name is BlockSpark AI Assistant and I'll guide you."
201
+ welcomeCta="💬 Click here to start chatting!"
202
+ :showWelcomePopup="true"
203
+ :welcomePopupDelay="1500"
204
+ fallbackWelcomeMessage="Hello! I'm BlockSpark AI Assistant. How can I help you today?"
205
+ inputPlaceholder="Type your message..."
206
+ emptyStateMessage="Hi! I'm BlockSpark AI Assistant. How can I help you today?"
207
+ :debug="false"
208
+ backendBaseUrl="http://localhost:8012"
209
+ backendWsUrl="ws://localhost:8012"
210
+ />
211
+ </template>
212
+ ```
137
213
 
138
- ```tsx
139
- <ChatWidget
140
- dfProjectId="your-project-id"
141
- dfAgentId="your-agent-id"
142
- serviceAccountKey={serviceAccountKey}
143
- backendBaseUrl="http://your-backend-url:8012"
144
- backendWsUrl="ws://your-backend-url:8012"
145
- />
214
+ **Option B — Component only:**
215
+
216
+ ```vue
217
+ <script setup>
218
+ import { BlockSparkChatWidgetVue } from '@blockspark/chat-widget/vue';
219
+ import '@blockspark/chat-widget/dist/styles.css';
220
+
221
+ import serviceAccountKey from './path/to/service-account-key.json';
222
+ </script>
223
+
224
+ <template>
225
+ <BlockSparkChatWidgetVue
226
+ dfProjectId="your-project-id"
227
+ dfLocation="us-central1"
228
+ dfAgentId="your-agent-id"
229
+ :serviceAccountKey="serviceAccountKey"
230
+ languageCode="en"
231
+ title="💬 BlockSpark AI Assistant"
232
+ subtitle="We're here to help"
233
+ welcomeTitle="👋 Welcome to Blockspark"
234
+ welcomeMessage="My name is BlockSpark AI Assistant and I'll guide you."
235
+ welcomeCta="💬 Click here to start chatting!"
236
+ :showWelcomePopup="true"
237
+ :welcomePopupDelay="1500"
238
+ fallbackWelcomeMessage="Hello! I'm BlockSpark AI Assistant. How can I help you today?"
239
+ inputPlaceholder="Type your message..."
240
+ emptyStateMessage="Hi! I'm BlockSpark AI Assistant. How can I help you today?"
241
+ :debug="false"
242
+ backendBaseUrl="http://localhost:8012"
243
+ backendWsUrl="ws://localhost:8012"
244
+ />
245
+ </template>
146
246
  ```
147
247
 
148
- **Note**: Props take precedence over environment variables.
248
+ ### CDN (script tag, no build step)
249
+
250
+ You can load the widget from a CDN and mount it with React (the widget is a React component). Load React, ReactDOM, the widget CSS, and the widget script, then render into a container.
251
+
252
+ Replace `1.0.1` with the version you want (or use `latest` for the latest release).
253
+
254
+ **Using unpkg:**
255
+
256
+ ```html
257
+ <!DOCTYPE html>
258
+ <html lang="en">
259
+ <head>
260
+ <meta charset="UTF-8" />
261
+ <title>BlockSpark Chat Widget</title>
262
+ <!-- 1. React (required by the widget) -->
263
+ <script crossorigin src="https://unpkg.com/react@18/umd/react.production.min.js"></script>
264
+ <script crossorigin src="https://unpkg.com/react-dom@18/umd/react-dom.production.min.js"></script>
265
+ <!-- 2. Widget CSS -->
266
+ <link rel="stylesheet" href="https://unpkg.com/@blockspark/chat-widget@1.0.1/dist/styles.css" />
267
+ </head>
268
+ <body>
269
+ <div id="chat-root"></div>
270
+
271
+ <!-- 3. Widget script (UMD: exposes BlockSparkChatWidget) -->
272
+ <script src="https://unpkg.com/@blockspark/chat-widget@1.0.1/dist/index.js"></script>
273
+
274
+ <script>
275
+ (function () {
276
+ var container = document.getElementById('chat-root');
277
+ var React = window.React;
278
+ var ReactDOM = window.ReactDOM;
279
+ var ChatWidget = window.BlockSparkChatWidget;
280
+
281
+ var config = {
282
+ dfProjectId: 'your-project-id',
283
+ dfLocation: 'us-central1',
284
+ dfAgentId: 'your-agent-id',
285
+ serviceAccountKey: { /* your service account key object */ },
286
+ // accessToken: 'your-token', // use instead of serviceAccountKey if you have a token
287
+ languageCode: 'en',
288
+ title: '💬 BlockSpark AI Assistant',
289
+ subtitle: "We're here to help",
290
+ welcomeTitle: '👋 Welcome to Blockspark',
291
+ welcomeMessage: "My name is BlockSpark AI Assistant and I'll guide you.",
292
+ welcomeCta: '💬 Click here to start chatting!',
293
+ showWelcomePopup: true,
294
+ welcomePopupDelay: 1500,
295
+ fallbackWelcomeMessage: "Hello! I'm BlockSpark AI Assistant. How can I help you today?",
296
+ inputPlaceholder: 'Type your message...',
297
+ emptyStateMessage: "Hi! I'm BlockSpark AI Assistant. How can I help you today?",
298
+ debug: false,
299
+ backendBaseUrl: 'http://localhost:8012',
300
+ backendWsUrl: 'ws://localhost:8012'
301
+ };
302
+
303
+ if (ReactDOM.createRoot) {
304
+ ReactDOM.createRoot(container).render(React.createElement(ChatWidget, config));
305
+ } else {
306
+ ReactDOM.render(React.createElement(ChatWidget, config), container);
307
+ }
308
+ })();
309
+ </script>
310
+ </body>
311
+ </html>
312
+ ```
149
313
 
150
- ### Human Support Mode
314
+ **Using jsDelivr:**
151
315
 
152
- The widget supports automatic handoff from bot to human agents. When Dialogflow returns `{"handoff": true}`, the widget will:
316
+ Use the same structure and swap the CDN base URL:
153
317
 
154
- 1. Switch from Bot Mode to Human Support Mode
155
- 2. Create a support chat session
156
- 3. Connect via WebSocket for real-time messaging
157
- 4. Load message history
158
- 5. Route messages to the backend API instead of Dialogflow
318
+ - CSS: `https://cdn.jsdelivr.net/npm/@blockspark/chat-widget@1.0.1/dist/styles.css`
319
+ - JS: `https://cdn.jsdelivr.net/npm/@blockspark/chat-widget@1.0.1/dist/index.js`
159
320
 
160
- The widget displays mode indicators and connection status in the chat header.
321
+ **Notes for CDN:**
161
322
 
162
- ### Import Types (TypeScript)
323
+ - You must provide `serviceAccountKey` (or `accessToken`) in the config object. Do not hardcode real keys in production; use a backend or token endpoint.
324
+ - Pin the version in the URL (e.g. `@1.0.1`) instead of `@latest` for stable behavior.
163
325
 
164
- ```tsx
165
- import ChatWidget, { ChatWidgetProps, DialogflowConfig } from '@blockspark/chat-widget';
166
- ```
326
+ ---
327
+
328
+ ## Human Support Mode
329
+
330
+ The widget supports automatic handoff from bot to human agents. When Dialogflow returns `{"handoff": true}`, the widget will:
331
+
332
+ 1. Switch from Bot Mode to Human Support Mode
333
+ 2. Create a support chat session
334
+ 3. Connect via WebSocket for real-time messaging
335
+ 4. Load message history
336
+ 5. Route messages to the backend API instead of Dialogflow
337
+
338
+ The widget shows mode and connection status in the chat header.
167
339
 
168
340
  ## Props
169
341
 
342
+ All props use **camelCase** in every framework (React, Next.js, Vue, CDN).
343
+
170
344
  | Prop | Type | Required | Default | Description |
171
345
  |------|------|----------|---------|-------------|
172
346
  | `dfProjectId` | `string` | Yes | - | Dialogflow project ID |
@@ -186,62 +360,57 @@ import ChatWidget, { ChatWidgetProps, DialogflowConfig } from '@blockspark/chat-
186
360
  | `inputPlaceholder` | `string` | No | `"Type your message..."` | Input field placeholder |
187
361
  | `emptyStateMessage` | `string` | No | `"Hi! I'm BlockSpark..."` | Empty state message |
188
362
  | `debug` | `boolean` | No | `false` | Enable debug logging |
189
- | `backendBaseUrl` | `string` | No | `process.env.REACT_APP_BACKEND_BASE_URL` or `"http://localhost:8012"` | Backend REST API base URL for Human Support Mode |
190
- | `backendWsUrl` | `string` | No | `process.env.REACT_APP_BACKEND_WS_URL` or `"ws://localhost:8012"` | Backend WebSocket URL for Human Support Mode |
363
+ | `backendBaseUrl` | `string` | No | env or `"http://localhost:8012"` | Backend REST API base URL for Human Support Mode |
364
+ | `backendWsUrl` | `string` | No | env or `"ws://localhost:8012"` | Backend WebSocket URL for Human Support Mode |
191
365
 
192
366
  \* Either `serviceAccountKey` or `accessToken` must be provided.
193
367
 
368
+ ## TypeScript
369
+
370
+ ```tsx
371
+ import ChatWidget, { ChatWidgetProps, DialogflowConfig } from '@blockspark/chat-widget';
372
+ ```
373
+
194
374
  ## How It Works
195
375
 
196
- The widget connects **directly** to Dialogflow CX using the REST API - no backend required!
376
+ The widget talks **directly** to Dialogflow CX via the REST API (no custom backend required for basic use):
197
377
 
198
- 1. **Authentication**: Uses Google Cloud service account key to generate OAuth2 access tokens
199
- 2. **Session Management**: Creates and manages Dialogflow sessions automatically
200
- 3. **Message Handling**: Sends messages directly to Dialogflow and displays responses
201
- 4. **Rich Content**: Supports Dialogflow rich content (chips, cards, etc.)
378
+ 1. **Authentication** Uses a Google Cloud service account key to obtain OAuth2 access tokens
379
+ 2. **Sessions** Creates and manages Dialogflow sessions
380
+ 3. **Messages** Sends user messages to Dialogflow and displays responses
381
+ 4. **Rich content** Supports Dialogflow rich content (chips, cards, etc.)
202
382
 
203
383
  ## Requirements
204
384
 
205
- - React 16.8.0 or higher
206
- - React DOM 16.8.0 or higher
207
- - Google Cloud service account with Dialogflow API enabled
208
- - Dialogflow CX agent
385
+ - **React / Next.js**: React 16.8+ and React DOM
386
+ - **Vue**: Vue 3.x
387
+ - **CDN**: React 17 or 18 and React DOM loaded via script tags
388
+ - Google Cloud project with Dialogflow API enabled and a Dialogflow CX agent
209
389
 
210
390
  ## Getting Your Service Account Key
211
391
 
212
- 1. Go to [Google Cloud Console](https://console.cloud.google.com/)
213
- 2. Select your project
214
- 3. Navigate to **IAM & Admin** > **Service Accounts**
215
- 4. Create a new service account or select an existing one
216
- 5. Create a JSON key and download it
217
- 6. Enable **Dialogflow API** for your project
218
- 7. Grant the service account **Dialogflow API User** role
219
-
220
- ## Security Warning ⚠️
392
+ 1. Open [Google Cloud Console](https://console.cloud.google.com/) and select your project
393
+ 2. Go to **IAM & Admin** → **Service Accounts**
394
+ 3. Create or select a service account and create a JSON key
395
+ 4. Enable **Dialogflow API** for the project
396
+ 5. Grant the service account the **Dialogflow API User** role
221
397
 
222
- **Important**: Service account keys contain sensitive credentials.
398
+ ## Security
223
399
 
224
- - **For Development**: You can import the key directly (as shown in examples)
225
- - **For Production**:
226
- - **DO NOT** expose service account keys in client-side code
227
- - Use a backend proxy to handle authentication
228
- - Or use OAuth2 flow to get access tokens securely
229
- - Consider using restricted service account keys with minimal permissions
400
+ - **Development**: You can import or pass the service account key in code for local testing
401
+ - **Production**:
402
+ - **Do not** ship service account keys in client-side code or public HTML
403
+ - Prefer a backend that issues short-lived tokens or proxies Dialogflow calls
404
+ - Use restricted keys and minimal permissions where possible
230
405
 
231
406
  ## Development
232
407
 
233
408
  ```bash
234
- # Install dependencies
235
409
  npm install
236
-
237
- # Build for production
238
- npm run build
239
-
240
- # Watch mode for development
241
- npm run dev
410
+ npm run build # production build
411
+ npm run dev # watch mode
242
412
  ```
243
413
 
244
414
  ## License
245
415
 
246
416
  MIT
247
- export NPM_TOKEN=your_token_here