@botuyo/chat-widget-standalone 1.0.0

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.
@@ -0,0 +1,168 @@
1
+ "use strict";
2
+ // @ts-nocheck
3
+ /**
4
+ * Ejemplo de uso del Chat Widget en una aplicación React con TypeScript
5
+ * Usando el ChatWidgetProvider para acceso global al estado del chat
6
+ *
7
+ * NOTA: Este es código de ejemplo y no se incluye en el build de producción.
8
+ */
9
+ Object.defineProperty(exports, "__esModule", { value: true });
10
+ exports.default = App;
11
+ var react_1 = require("react");
12
+ var chat_widget_standalone_1 = require("@botuyo/chat-widget-standalone");
13
+ // ========== Configuración del Tema ==========
14
+ var chatTheme = {
15
+ primaryColor: '#10b981',
16
+ botName: 'Asistente BotUyo',
17
+ logoUrl: '/logo.png',
18
+ position: 'bottom-right',
19
+ welcomeMessage: '¡Hola! 👋 ¿En qué puedo ayudarte hoy?',
20
+ inputPlaceholder: 'Escribe tu mensaje aquí...',
21
+ borderRadius: '1rem',
22
+ launcherBorderRadius: '50%',
23
+ starterPrompt: '¿Necesitas ayuda? 💬',
24
+ bubbleStyles: {
25
+ radius: {
26
+ bubble: 'rounded-2xl',
27
+ image: 'rounded-xl',
28
+ button: 'rounded-full',
29
+ card: 'rounded-2xl'
30
+ },
31
+ bot: {
32
+ bg: 'bg-gray-100',
33
+ text: 'text-gray-900',
34
+ border: 'border-gray-200'
35
+ },
36
+ launcher: {
37
+ pulse: true
38
+ }
39
+ }
40
+ };
41
+ // ========== Componente con botones de control ==========
42
+ function ChatControls() {
43
+ var chat = (0, chat_widget_standalone_1.useChatWidget)();
44
+ return (<div className="p-6 bg-white rounded-lg shadow-lg">
45
+ <h2 className="text-2xl font-bold mb-4">Control del Chat</h2>
46
+
47
+ <div className="space-y-3">
48
+ <button onClick={chat.open} className="w-full bg-green-500 hover:bg-green-600 text-white px-4 py-2 rounded-lg transition">
49
+ 🚀 Abrir Chat
50
+ </button>
51
+
52
+ <button onClick={chat.close} className="w-full bg-red-500 hover:bg-red-600 text-white px-4 py-2 rounded-lg transition">
53
+ ❌ Cerrar Chat
54
+ </button>
55
+
56
+ <button onClick={chat.toggle} className="w-full bg-blue-500 hover:bg-blue-600 text-white px-4 py-2 rounded-lg transition">
57
+ 🔄 Toggle Chat
58
+ </button>
59
+
60
+ <button onClick={function () { return chat.sendMessage('Hola, necesito ayuda con mi reserva'); }} className="w-full bg-purple-500 hover:bg-purple-600 text-white px-4 py-2 rounded-lg transition">
61
+ 💬 Mensaje Rápido
62
+ </button>
63
+
64
+ <button onClick={chat.clearMessages} className="w-full bg-gray-500 hover:bg-gray-600 text-white px-4 py-2 rounded-lg transition">
65
+ 🗑️ Limpiar Historial
66
+ </button>
67
+ </div>
68
+
69
+ <div className="mt-6 p-4 bg-gray-100 rounded-lg">
70
+ <h3 className="font-semibold mb-2">Estado:</h3>
71
+ <ul className="space-y-1 text-sm">
72
+ <li>
73
+ Estado: <strong>{chat.isOpen ? '✅ Abierto' : '❌ Cerrado'}</strong>
74
+ </li>
75
+ <li>
76
+ Mensajes sin leer: <strong className="text-green-600">{chat.unreadCount}</strong>
77
+ </li>
78
+ </ul>
79
+ </div>
80
+ </div>);
81
+ }
82
+ // ========== Botón flotante personalizado (opcional) ==========
83
+ function _CustomFloatingButton() {
84
+ var chat = (0, chat_widget_standalone_1.useChatWidget)();
85
+ return (<button onClick={chat.toggle} className="fixed bottom-4 left-4 bg-blue-600 hover:bg-blue-700 text-white p-4 rounded-full shadow-lg transition transform hover:scale-110" aria-label="Toggle Chat">
86
+ 💬
87
+ {chat.unreadCount > 0 && (<span className="absolute -top-1 -right-1 bg-red-500 text-white text-xs rounded-full h-6 w-6 flex items-center justify-center">
88
+ {chat.unreadCount}
89
+ </span>)}
90
+ </button>);
91
+ }
92
+ // ========== Layout Principal ==========
93
+ function AppContent() {
94
+ return (<div className="min-h-screen bg-gradient-to-br from-blue-50 to-green-50">
95
+ <div className="container mx-auto px-4 py-12">
96
+ <header className="text-center mb-12">
97
+ <h1 className="text-4xl font-bold text-gray-800 mb-4">
98
+ 🎉 Ejemplo React + TypeScript
99
+ </h1>
100
+ <p className="text-gray-600 max-w-2xl mx-auto">
101
+ Este ejemplo muestra cómo integrar el Chat Widget en una aplicación React
102
+ usando el <code className="bg-gray-200 px-2 py-1 rounded">ChatWidgetProvider</code> y
103
+ el hook <code className="bg-gray-200 px-2 py-1 rounded">useChatWidget()</code>.
104
+ </p>
105
+ </header>
106
+
107
+ <div className="max-w-md mx-auto">
108
+ <ChatControls />
109
+ </div>
110
+
111
+ {/* Botón flotante personalizado (opcional, el widget ya tiene uno) */}
112
+ {/* <CustomFloatingButton /> */}
113
+ </div>
114
+ </div>);
115
+ }
116
+ // ========== App Root con Provider ==========
117
+ function App() {
118
+ return (<chat_widget_standalone_1.ChatWidgetProvider
119
+ // Configuración requerida
120
+ apiKey={process.env.REACT_APP_CHAT_API_KEY || 'demo-api-key'} apiBaseUrl={process.env.REACT_APP_CHAT_API_URL || 'https://api.botuyo.com'}
121
+ // Tema personalizado
122
+ theme={chatTheme}
123
+ // Contexto de página
124
+ pageContext={{
125
+ page: 'React Example',
126
+ url: window.location.href,
127
+ title: 'React TypeScript Example'
128
+ }}
129
+ // Metadata SEO automática
130
+ includeSEOMetadata={true}
131
+ // Estado inicial (opcional)
132
+ initialState={{
133
+ isOpen: false
134
+ }}
135
+ // Callbacks
136
+ onStateChange={function (isOpen) {
137
+ console.log('Chat widget:', isOpen ? 'opened' : 'closed');
138
+ }} onNavigate={function (url) {
139
+ console.log('Navigate to:', url);
140
+ // Usar React Router aquí si lo necesitas
141
+ window.location.href = url;
142
+ }} onLogin={function (userData) {
143
+ console.log('User logged in:', userData);
144
+ // Guardar token, actualizar estado global, etc.
145
+ }} onEvent={function (eventName, data) {
146
+ console.log('Event:', eventName, data);
147
+ }}>
148
+ <AppContent />
149
+ </chat_widget_standalone_1.ChatWidgetProvider>);
150
+ }
151
+ // ========== Tipos disponibles para importar ==========
152
+ /*
153
+ import type {
154
+ ChatWidgetProps,
155
+ ChatWidgetProviderProps,
156
+ ChatWidgetContextValue,
157
+ ChatTheme,
158
+ BubbleStyles,
159
+ UserContext,
160
+ PageContext,
161
+ ChatMessage,
162
+ TextMessage,
163
+ ImageMessage,
164
+ AudioMessage,
165
+ LocationMessage,
166
+ AuthenticatedUser
167
+ } from '@botuyo/chat-widget-standalone';
168
+ */
@@ -0,0 +1,221 @@
1
+ // @ts-nocheck
2
+ /**
3
+ * Ejemplo de uso del Chat Widget en una aplicación React con TypeScript
4
+ * Usando el ChatWidgetProvider para acceso global al estado del chat
5
+ *
6
+ * NOTA: Este es código de ejemplo y no se incluye en el build de producción.
7
+ */
8
+
9
+ import React from 'react';
10
+ import {
11
+ ChatWidgetProvider,
12
+ useChatWidget,
13
+ type ChatWidgetProviderProps as _ChatWidgetProviderProps,
14
+ type ChatTheme
15
+ } from '@botuyo/chat-widget-standalone';
16
+
17
+ // ========== Configuración del Tema ==========
18
+ const chatTheme: ChatTheme = {
19
+ primaryColor: '#10b981',
20
+ botName: 'Asistente BotUyo',
21
+ logoUrl: '/logo.png',
22
+ position: 'bottom-right',
23
+ welcomeMessage: '¡Hola! 👋 ¿En qué puedo ayudarte hoy?',
24
+ inputPlaceholder: 'Escribe tu mensaje aquí...',
25
+ borderRadius: '1rem',
26
+ launcherBorderRadius: '50%',
27
+ starterPrompt: '¿Necesitas ayuda? 💬',
28
+ bubbleStyles: {
29
+ radius: {
30
+ bubble: 'rounded-2xl',
31
+ image: 'rounded-xl',
32
+ button: 'rounded-full',
33
+ card: 'rounded-2xl'
34
+ },
35
+ bot: {
36
+ bg: 'bg-gray-100',
37
+ text: 'text-gray-900',
38
+ border: 'border-gray-200'
39
+ },
40
+ launcher: {
41
+ pulse: true
42
+ }
43
+ }
44
+ };
45
+
46
+ // ========== Componente con botones de control ==========
47
+ function ChatControls() {
48
+ const chat = useChatWidget();
49
+
50
+ return (
51
+ <div className="p-6 bg-white rounded-lg shadow-lg">
52
+ <h2 className="text-2xl font-bold mb-4">Control del Chat</h2>
53
+
54
+ <div className="space-y-3">
55
+ <button
56
+ onClick={chat.open}
57
+ className="w-full bg-green-500 hover:bg-green-600 text-white px-4 py-2 rounded-lg transition"
58
+ >
59
+ 🚀 Abrir Chat
60
+ </button>
61
+
62
+ <button
63
+ onClick={chat.close}
64
+ className="w-full bg-red-500 hover:bg-red-600 text-white px-4 py-2 rounded-lg transition"
65
+ >
66
+ ❌ Cerrar Chat
67
+ </button>
68
+
69
+ <button
70
+ onClick={chat.toggle}
71
+ className="w-full bg-blue-500 hover:bg-blue-600 text-white px-4 py-2 rounded-lg transition"
72
+ >
73
+ 🔄 Toggle Chat
74
+ </button>
75
+
76
+ <button
77
+ onClick={() => chat.sendMessage('Hola, necesito ayuda con mi reserva')}
78
+ className="w-full bg-purple-500 hover:bg-purple-600 text-white px-4 py-2 rounded-lg transition"
79
+ >
80
+ 💬 Mensaje Rápido
81
+ </button>
82
+
83
+ <button
84
+ onClick={chat.clearMessages}
85
+ className="w-full bg-gray-500 hover:bg-gray-600 text-white px-4 py-2 rounded-lg transition"
86
+ >
87
+ 🗑️ Limpiar Historial
88
+ </button>
89
+ </div>
90
+
91
+ <div className="mt-6 p-4 bg-gray-100 rounded-lg">
92
+ <h3 className="font-semibold mb-2">Estado:</h3>
93
+ <ul className="space-y-1 text-sm">
94
+ <li>
95
+ Estado: <strong>{chat.isOpen ? '✅ Abierto' : '❌ Cerrado'}</strong>
96
+ </li>
97
+ <li>
98
+ Mensajes sin leer: <strong className="text-green-600">{chat.unreadCount}</strong>
99
+ </li>
100
+ </ul>
101
+ </div>
102
+ </div>
103
+ );
104
+ }
105
+
106
+ // ========== Botón flotante personalizado (opcional) ==========
107
+ function _CustomFloatingButton() {
108
+ const chat = useChatWidget();
109
+
110
+ return (
111
+ <button
112
+ onClick={chat.toggle}
113
+ className="fixed bottom-4 left-4 bg-blue-600 hover:bg-blue-700 text-white p-4 rounded-full shadow-lg transition transform hover:scale-110"
114
+ aria-label="Toggle Chat"
115
+ >
116
+ 💬
117
+ {chat.unreadCount > 0 && (
118
+ <span className="absolute -top-1 -right-1 bg-red-500 text-white text-xs rounded-full h-6 w-6 flex items-center justify-center">
119
+ {chat.unreadCount}
120
+ </span>
121
+ )}
122
+ </button>
123
+ );
124
+ }
125
+
126
+ // ========== Layout Principal ==========
127
+ function AppContent() {
128
+ return (
129
+ <div className="min-h-screen bg-gradient-to-br from-blue-50 to-green-50">
130
+ <div className="container mx-auto px-4 py-12">
131
+ <header className="text-center mb-12">
132
+ <h1 className="text-4xl font-bold text-gray-800 mb-4">
133
+ 🎉 Ejemplo React + TypeScript
134
+ </h1>
135
+ <p className="text-gray-600 max-w-2xl mx-auto">
136
+ Este ejemplo muestra cómo integrar el Chat Widget en una aplicación React
137
+ usando el <code className="bg-gray-200 px-2 py-1 rounded">ChatWidgetProvider</code> y
138
+ el hook <code className="bg-gray-200 px-2 py-1 rounded">useChatWidget()</code>.
139
+ </p>
140
+ </header>
141
+
142
+ <div className="max-w-md mx-auto">
143
+ <ChatControls />
144
+ </div>
145
+
146
+ {/* Botón flotante personalizado (opcional, el widget ya tiene uno) */}
147
+ {/* <CustomFloatingButton /> */}
148
+ </div>
149
+ </div>
150
+ );
151
+ }
152
+
153
+ // ========== App Root con Provider ==========
154
+ export default function App() {
155
+ return (
156
+ <ChatWidgetProvider
157
+ // Configuración requerida
158
+ apiKey={process.env.REACT_APP_CHAT_API_KEY || 'demo-api-key'}
159
+ apiBaseUrl={process.env.REACT_APP_CHAT_API_URL || 'https://api.botuyo.com'}
160
+
161
+ // Tema personalizado
162
+ theme={chatTheme}
163
+
164
+ // Contexto de página
165
+ pageContext={{
166
+ page: 'React Example',
167
+ url: window.location.href,
168
+ title: 'React TypeScript Example'
169
+ }}
170
+
171
+ // Metadata SEO automática
172
+ includeSEOMetadata={true}
173
+
174
+ // Estado inicial (opcional)
175
+ initialState={{
176
+ isOpen: false
177
+ }}
178
+
179
+ // Callbacks
180
+ onStateChange={(isOpen) => {
181
+ console.log('Chat widget:', isOpen ? 'opened' : 'closed');
182
+ }}
183
+
184
+ onNavigate={(url) => {
185
+ console.log('Navigate to:', url);
186
+ // Usar React Router aquí si lo necesitas
187
+ window.location.href = url;
188
+ }}
189
+
190
+ onLogin={(userData) => {
191
+ console.log('User logged in:', userData);
192
+ // Guardar token, actualizar estado global, etc.
193
+ }}
194
+
195
+ onEvent={(eventName, data) => {
196
+ console.log('Event:', eventName, data);
197
+ }}
198
+ >
199
+ <AppContent />
200
+ </ChatWidgetProvider>
201
+ );
202
+ }
203
+
204
+ // ========== Tipos disponibles para importar ==========
205
+ /*
206
+ import type {
207
+ ChatWidgetProps,
208
+ ChatWidgetProviderProps,
209
+ ChatWidgetContextValue,
210
+ ChatTheme,
211
+ BubbleStyles,
212
+ UserContext,
213
+ PageContext,
214
+ ChatMessage,
215
+ TextMessage,
216
+ ImageMessage,
217
+ AudioMessage,
218
+ LocationMessage,
219
+ AuthenticatedUser
220
+ } from '@botuyo/chat-widget-standalone';
221
+ */
package/package.json ADDED
@@ -0,0 +1,147 @@
1
+ {
2
+ "name": "@botuyo/chat-widget-standalone",
3
+ "version": "1.0.0",
4
+ "type": "module",
5
+ "description": "BotUyo Chat Widget - Standalone CDN version with React/TypeScript support",
6
+ "main": "dist/botuyo-chat.js",
7
+ "module": "dist/index.esm.js",
8
+ "types": "dist/standalone.d.ts",
9
+ "exports": {
10
+ ".": {
11
+ "types": "./dist/standalone.d.ts",
12
+ "import": "./dist/index.esm.js",
13
+ "require": "./dist/botuyo-chat.js"
14
+ },
15
+ "./react": {
16
+ "types": "./dist/chat-widget/index.d.ts",
17
+ "import": "./dist/index.esm.js"
18
+ }
19
+ },
20
+ "scripts": {
21
+ "dev": "vite",
22
+ "build": "npm run clean && vite build && npm run build:types",
23
+ "build:types": "tsc --project tsconfig.build.json",
24
+ "preview": "vite preview",
25
+ "clean": "npx rimraf dist",
26
+ "lint": "eslint .",
27
+ "lint:fix": "eslint . --fix",
28
+ "typecheck": "tsc --noEmit",
29
+ "test": "vitest",
30
+ "test:ui": "vitest --ui",
31
+ "test:run": "vitest run",
32
+ "test:coverage": "vitest run --coverage",
33
+ "test:e2e": "playwright test",
34
+ "test:e2e:ui": "playwright test --ui",
35
+ "test:e2e:debug": "playwright test --debug",
36
+ "test:e2e:report": "playwright show-report",
37
+ "storybook": "storybook dev -p 6006",
38
+ "build-storybook": "storybook build",
39
+ "format": "prettier --write \"src/**/*.{ts,tsx,css}\"",
40
+ "format:check": "prettier --check \"src/**/*.{ts,tsx,css}\""
41
+ },
42
+ "lint-staged": {
43
+ "*.{ts,tsx}": [
44
+ "eslint --fix",
45
+ "prettier --write"
46
+ ],
47
+ "*.{css,md,json}": [
48
+ "prettier --write"
49
+ ]
50
+ },
51
+ "keywords": [
52
+ "chat",
53
+ "widget",
54
+ "chatbot",
55
+ "customer-support",
56
+ "botuyo",
57
+ "standalone",
58
+ "cdn",
59
+ "react",
60
+ "typescript",
61
+ "nextjs",
62
+ "socket.io"
63
+ ],
64
+ "author": "BotUyo",
65
+ "license": "MIT",
66
+ "repository": {
67
+ "type": "git",
68
+ "url": "https://github.com/botuyo/chat-widget.git"
69
+ },
70
+ "bugs": {
71
+ "url": "https://github.com/botuyo/chat-widget/issues"
72
+ },
73
+ "homepage": "https://github.com/botuyo/chat-widget#readme",
74
+ "devDependencies": {
75
+ "@axe-core/playwright": "^4.11.0",
76
+ "@chromatic-com/storybook": "^5.0.0",
77
+ "@eslint/js": "^9.39.2",
78
+ "@playwright/test": "^1.58.0",
79
+ "@storybook/addon-a11y": "^10.2.0",
80
+ "@storybook/addon-docs": "^10.2.0",
81
+ "@storybook/addon-onboarding": "^10.2.0",
82
+ "@storybook/addon-vitest": "^10.2.0",
83
+ "@storybook/react-vite": "^10.2.0",
84
+ "@tailwindcss/postcss": "^4.1.18",
85
+ "@tanstack/react-virtual": "^3.13.18",
86
+ "@testing-library/jest-dom": "^6.9.1",
87
+ "@testing-library/react": "^16.3.2",
88
+ "@testing-library/user-event": "^14.6.1",
89
+ "@types/node": "^25.0.10",
90
+ "@types/react": "^19.2.9",
91
+ "@types/react-dom": "^19.2.3",
92
+ "@typescript-eslint/eslint-plugin": "^8.53.1",
93
+ "@typescript-eslint/parser": "^8.53.1",
94
+ "@vitejs/plugin-react": "^5.1.2",
95
+ "@vitest/browser-playwright": "^4.0.18",
96
+ "@vitest/coverage-v8": "^4.0.18",
97
+ "@vitest/ui": "^4.0.18",
98
+ "autoprefixer": "^10.4.23",
99
+ "axe-core": "^4.11.1",
100
+ "cssnano": "^7.1.2",
101
+ "cssnano-preset-advanced": "^7.0.10",
102
+ "eslint": "^9.39.2",
103
+ "eslint-plugin-react-hooks": "^7.0.1",
104
+ "eslint-plugin-react-refresh": "^0.4.5",
105
+ "eslint-plugin-storybook": "^10.2.0",
106
+ "globals": "^17.1.0",
107
+ "happy-dom": "^20.3.7",
108
+ "husky": "^9.1.7",
109
+ "lint-staged": "^16.2.7",
110
+ "playwright": "^1.58.0",
111
+ "postcss": "^8.5.6",
112
+ "prettier": "^3.8.1",
113
+ "rehype-sanitize": "^6.0.0",
114
+ "rollup-plugin-visualizer": "^6.0.5",
115
+ "storybook": "^10.2.0",
116
+ "tailwindcss": "^4.1.18",
117
+ "terser": "^5.46.0",
118
+ "typescript": "^5.3.3",
119
+ "typescript-eslint": "^8.53.1",
120
+ "vite": "^7.3.1",
121
+ "vitest": "^4.0.18",
122
+ "zod": "^4.3.6"
123
+ },
124
+ "peerDependencies": {
125
+ "react": "^19.0.0",
126
+ "react-dom": "^19.0.0"
127
+ },
128
+ "dependencies": {
129
+ "browser-image-compression": "^2.0.2",
130
+ "clsx": "^2.1.1",
131
+ "idb": "^8.0.3",
132
+ "lucide-react": "^0.563.0",
133
+ "react": "^19.0.0",
134
+ "react-dom": "^19.0.0",
135
+ "react-markdown": "^10.1.0",
136
+ "remark-gfm": "^4.0.1",
137
+ "socket.io-client": "^4.7.4",
138
+ "tailwind-merge": "^3.4.0"
139
+ },
140
+ "files": [
141
+ "dist",
142
+ "README.md",
143
+ "INSTALLATION_GUIDE.md",
144
+ "LICENSE",
145
+ "examples"
146
+ ]
147
+ }