@ethora/chat-component 25.12.2 → 26.1.2

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.
Files changed (49) hide show
  1. package/README.md +557 -149
  2. package/dist/components/MainComponents/MessageContainer.d.ts +1 -0
  3. package/dist/components/MessageBubble/MessageReply.d.ts +2 -2
  4. package/dist/components/MessageNotification/MessageNotificationToast.d.ts +17 -0
  5. package/dist/components/MessageNotification/index.d.ts +2 -0
  6. package/dist/components/Modals/SettingsModals/SharedStyledComponents.d.ts +22 -0
  7. package/dist/components/Modals/styledModalComponents.d.ts +28 -0
  8. package/dist/components/styled/Button.d.ts +2 -2
  9. package/dist/components/styled/DateLabel.d.ts +2 -2
  10. package/dist/components/styled/StyledComponents.d.ts +10 -10
  11. package/dist/components/styled/StyledInputComponents/StyledInputComponents.d.ts +6 -6
  12. package/dist/context/MessageNotificationContext.d.ts +12 -0
  13. package/dist/firebase-config.d.ts +6 -2
  14. package/dist/firebase-messaging-sw.js +351 -0
  15. package/dist/helpers/getDataFromXml.d.ts +1 -0
  16. package/dist/helpers/initRoomsPresence.d.ts +1 -1
  17. package/dist/helpers/storeConsole.d.ts +6 -0
  18. package/dist/hooks/useInAppNotifications.d.ts +18 -0
  19. package/dist/hooks/usePushNotifications.d.ts +45 -0
  20. package/dist/hooks/useTabVisibility.d.ts +1 -0
  21. package/dist/main.css +1 -1
  22. package/dist/main.d.ts +5 -0
  23. package/dist/main.js +14686 -11893
  24. package/dist/main.js.map +1 -1
  25. package/dist/networking/api-requests/push.api.d.ts +18 -0
  26. package/dist/networking/stanzaHandlers.d.ts +4 -2
  27. package/dist/networking/xmpp/allRoomPresences.xmpp.d.ts +11 -1
  28. package/dist/networking/xmpp/presenceInRoom.xmpp.d.ts +1 -1
  29. package/dist/networking/xmpp/sendTextMessage.xmpp.d.ts +1 -1
  30. package/dist/networking/xmpp/sendTextMessageWithTranslateTag.xmpp.d.ts +1 -1
  31. package/dist/networking/xmpp/subscribeToRoomMessages.xmpp.d.ts +9 -0
  32. package/dist/networking/xmppClient.d.ts +13 -3
  33. package/dist/roomStore/chatSettingsSlice.d.ts +1 -0
  34. package/dist/roomStore/index.d.ts +28 -0
  35. package/dist/roomStore/roomHeapSlice.d.ts +1 -1
  36. package/dist/roomStore/roomsSlice.d.ts +11 -1
  37. package/dist/types/models/config.model.d.ts +35 -1
  38. package/dist/types/models/room.model.d.ts +4 -1
  39. package/dist/types/models/xmpp.model.d.ts +3 -1
  40. package/dist/utils/firebasePushNotifications.d.ts +34 -0
  41. package/dist/utils/formatError.d.ts +1 -0
  42. package/dist/utils/messageNotificationManager.d.ts +16 -0
  43. package/dist/utils/notificationPolicy.d.ts +45 -0
  44. package/dist/utils/notificationUtils.d.ts +22 -0
  45. package/dist/utils/pushSubscriptionService.d.ts +12 -0
  46. package/dist/version.d.ts +1 -1
  47. package/package.json +7 -4
  48. package/public/firebase-messaging-sw.js +351 -0
  49. package/scripts/init-push.js +48 -0
package/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # Ethora Chat Component: a single npm for your React chat
1
+ # Ethora Chat Component (`@ethora/chat-component`)
2
2
 
3
3
  ![GitHub watchers](https://img.shields.io/github/watchers/dappros/ethora-chat-component) ![GitHub forks](https://img.shields.io/github/forks/dappros/ethora-chat-component) ![GitHub Repo stars](https://img.shields.io/github/stars/dappros/ethora-chat-component) ![GitHub repo size](https://img.shields.io/github/repo-size/dappros/ethora-chat-component) ![GitHub language count](https://img.shields.io/github/languages/count/dappros/ethora-chat-component) ![GitHub top language](https://img.shields.io/github/languages/top/dappros/ethora-chat-component) <a href="https://codeclimate.com/github/dappros/ethora-chat-component/maintainability"><img src="https://api.codeclimate.com/v1/badges/715c6f3ffb08de5ca621/maintainability" /></a> ![GitHub commit activity (branch)](https://img.shields.io/github/commit-activity/m/dappros/ethora-chat-component/main) ![GitHub issues](https://img.shields.io/github/issues/dappros/ethora-chat-component) ![GitHub closed issues](https://img.shields.io/github/issues-closed-raw/dappros/ethora-chat-component) ![GitHub](https://img.shields.io/github/license/dappros/ethora-chat-component) ![GitHub contributors](https://img.shields.io/github/contributors/dappros/ethora-chat-component)
4
4
 
@@ -7,221 +7,629 @@
7
7
 
8
8
  [![Discord](https://img.shields.io/badge/%3Cethora%3E-%237289DA.svg?style=flat&logo=discord&logoColor=white)](https://discord.gg/Sm6bAHA3ZC) [![Twitter URL](https://img.shields.io/twitter/url?url=https%3A%2F%2Fgithub.com%2Fdappros%2Fethora)](https://twitter.com/intent/tweet?url=https%3A%2F%2Fgithub.com%2Fdappros%2Fethora%2F&via=tarasfilatov&text=check%20out%20Ethora%20%23web3%20%23social%20app%20engine&hashtags=lowcode%2Creactnative%2Copensource%2Cnocode) [![Website](https://img.shields.io/website?url=https%3A%2F%2Fethora.com%2F)](https://ethora.com/) [![YouTube Channel Subscribers](https://img.shields.io/youtube/channel/subscribers/UCRvrXwMOU0WBkRZyFlU7V_g)](https://www.youtube.com/channel/UCRvrXwMOU0WBkRZyFlU7V_g)
9
9
 
10
- ## About Chat Component
10
+ React + TypeScript chat UI component powered by Ethora backend APIs and XMPP.
11
+ Use it as a standalone chat page, as an embedded widget in your existing app, or as a customizable chat foundation with your own auth and UI.
12
+
13
+ ## Table of Contents
14
+
15
+ - [Overview](#overview)
16
+ - [Why Ethora](#why-ethora)
17
+ - [Quick Start](#quick-start)
18
+ - [Integration Modes](#integration-modes)
19
+ - [Behavior Notes and Legacy Quirks](#behavior-notes-and-legacy-quirks)
20
+ - [Chat Props Reference](#chat-props-reference)
21
+ - [Full Config Reference (`IConfig`)](#full-config-reference-iconfig)
22
+ - [Custom Widgets and Overrides](#custom-widgets-and-overrides)
23
+ - [Push Notifications](#push-notifications)
24
+ - [Auth Strategies](#auth-strategies)
25
+ - [Hooks and API Exports](#hooks-and-api-exports)
26
+ - [Use Cases and Feature Coverage](#use-cases-and-feature-coverage)
27
+ - [Hosted vs Self-Host Guidance](#hosted-vs-self-host-guidance)
28
+ - [Security Notes](#security-notes)
29
+ - [Reference Architectures](#reference-architectures)
30
+ - [Use-Case Templates](#use-case-templates)
31
+ - [Feature Roadmap Snapshot](#feature-roadmap-snapshot)
32
+ - [Troubleshooting](#troubleshooting)
33
+ - [Ethora Links and Support](#ethora-links-and-support)
34
+
35
+ ## Overview
36
+
37
+ `@ethora/chat-component` gives you a production-oriented chat interface with:
38
+
39
+ - Room list and room chat UI
40
+ - Message history, replies, reactions, edits, deletes
41
+ - Typing indicators
42
+ - In-app notifications + Web Push integration
43
+ - Configurable auth modes (default/login form/google/jwt/custom user)
44
+ - Custom render components for message/input/scroll/day separator/new-message label
45
+
46
+ The package exports:
47
+
48
+ - `Chat` (main component)
49
+ - `XmppProvider`
50
+ - `useUnread`
51
+ - `logoutService`
52
+ - `useQRCodeChat`, `handleQRChatId`
53
+ - `useInAppNotifications`
54
+ - `usePushNotifications`
55
+ - `resendMessage`
56
+
57
+ ## Why Ethora
58
+
59
+ Ethora provides hosted and customizable messaging infrastructure plus a wider product ecosystem.
60
+
61
+ | Dimension | Ethora Chat Component | Full Ethora Platform |
62
+ | --- | --- | --- |
63
+ | Primary goal | Embed chat quickly in a React app | End-to-end product stack (chat, profiles, wallets, AI, admin) |
64
+ | Time to first chat | Minutes | Higher initial setup, broader capabilities |
65
+ | Frontend scope | Focused web chat UI package | Multi-product ecosystem and broader SDK/tooling |
66
+ | Custom UI control | High via props + custom components | High, with additional platform-specific tooling |
67
+ | Best fit | Support chat, portal messaging, embedded chat widget | Full social/messaging app platforms with extended modules |
68
+
69
+ ## Quick Start
70
+
71
+ ### 1. Install
72
+
73
+ | Tool | Command |
74
+ | --- | --- |
75
+ | npm | `npm i @ethora/chat-component` |
76
+ | yarn | `yarn add @ethora/chat-component` |
77
+ | pnpm | `pnpm add @ethora/chat-component` |
78
+ | bun | `bun add @ethora/chat-component` |
79
+
80
+ ### 2. Render the chat
81
+
82
+ ```tsx
83
+ import { Chat, XmppProvider } from '@ethora/chat-component';
84
+ import './App.css';
85
+
86
+ export default function App() {
87
+ return (
88
+ <XmppProvider>
89
+ <Chat />
90
+ </XmppProvider>
91
+ );
92
+ }
93
+ ```
11
94
 
12
- Ethora Chat Component allows you to build a functioning chat room super quickly.
13
- Sounds simple and is easy to build your app with.
14
- Uses XMPP chat protocol and ejabberd chat server to provide your users with a seamless instant messaging experience.
95
+ ### Required wrapper (`XmppProvider`)
15
96
 
16
- Once you need more functionality however you will be pleasantly surprised. Our Ethora platform behind the chat component offers a plethora of functionalities around chat/social, user profiles, digital wallets, business documents exchange, digital collectables, web3 and AI bots. The history behind Chat Component is following. First, we have built a low-code “super app” engine called Ethora: https://github.com/dappros/ethora/ which we used to drastically speed up app development for our clients. Afterwards, we have open-sourced it for the benefit of other developers. Later on, we realized that whilst developers love what Ethora can do, many of them don’t need such a complex engine with all bells and whistles but a steep learning curver. In most cases you’re after a certain functionality (like a simple chat room) and you need it quick.
97
+ `Chat` relies on internals that use `useXmppClient()`. In real integrations, wrap `Chat` (or your entire app shell) with `XmppProvider`:
17
98
 
18
- Enter Ethora Chat Component which allows you to quickly implement your chat room experience!
99
+ ```tsx
100
+ import { Chat, XmppProvider } from '@ethora/chat-component';
19
101
 
20
- If / once you need additional functionalities you will have options like: (a) build them yourself on top of chat component; (b) peek into or use code from Ethora open-source monorepo https://github.com/dappros/ethora/ or (c) seek help from Ethora team or other developers at our forum: https://forum.ethora.com/ or Discord server: https://discord.gg/Sm6bAHA3ZC
102
+ export default function App() {
103
+ return (
104
+ <XmppProvider>
105
+ <Chat config={{ baseUrl: 'https://api.ethoradev.com/v1' }} />
106
+ </XmppProvider>
107
+ );
108
+ }
109
+ ```
21
110
 
22
- Note: scroll below for use cases and functionality break down of this Chat Component.
111
+ ### 3. Run
23
112
 
24
- ## How to build your chat room in 5 minutes
113
+ ```bash
114
+ npm run dev
115
+ ```
25
116
 
26
- 1. npm create vite@latest
27
- 2. specify a name for your project (e.g. "vite-project")
28
- 3. select framework and variant (for example, React -> Typescript but may be different depending on your project requirements, it will work with plain Javascript too)
117
+ Open `http://localhost:5173`.
29
118
 
30
- <img src="https://github.com/dappros/ethora-chat-component/blob/main/img/readme01.png" width="500" />
119
+ ## Integration Modes
31
120
 
32
- <img src="https://github.com/dappros/ethora-chat-component/blob/main/img/readme02.png" width="500" />
121
+ All modes below assume `XmppProvider` wraps `Chat`.
33
122
 
34
- 4. cd vite-project _(use your name instead of "vite-project")_
35
- 5. npm i
36
- 6. npm i @ethora/chat-component
37
- 7. go to file src/App.tsx and replace it with the below code
123
+ ### A) Minimal demo mode (provider + chat)
38
124
 
125
+ ```tsx
126
+ <XmppProvider>
127
+ <Chat />
128
+ </XmppProvider>
39
129
  ```
40
- import { Chat } from "@ethora/chat-component";
41
- import "./App.css";
42
130
 
43
- function App() {
44
- return (
45
- <Chat />
46
- );
47
- }
131
+ Useful for local proof-of-concept and quick UI validation.
48
132
 
49
- export default App;
50
- ```
133
+ ### B) Auto default credential fallback (legacy behavior)
51
134
 
52
- 7. run like this
135
+ If no `googleLogin`, no `jwtLogin`, no `userLogin`, and no `defaultLogin`, `LoginWrapper` currently triggers internal email/password fallback logic.
53
136
 
54
- ```
55
- npm run dev
137
+ ```tsx
138
+ <XmppProvider>
139
+ <Chat config={{ colors: { primary: '#2563eb', secondary: '#dbeafe' } }} />
140
+ </XmppProvider>
56
141
  ```
57
142
 
58
- you should see something like this:
59
- <br /><img src="https://github.com/dappros/ethora-chat-component/blob/main/img/readme03.png" width="350" />
143
+ ### C) Explicit email/password via `user` prop
60
144
 
61
- 8. Open http://localhost:5173/ in your browser
62
-
63
- Voilà - your chat app should work like so:
145
+ ```tsx
146
+ <XmppProvider>
147
+ <Chat
148
+ user={{
149
+ email: 'user@example.com',
150
+ password: 'PLACEHOLDER_PASSWORD',
151
+ }}
152
+ />
153
+ </XmppProvider>
154
+ ```
64
155
 
65
- <img src="https://github.com/dappros/ethora-chat-component/blob/main/img/readme_animation.gif" width="860" />
156
+ ### D) Injected logged-in user (`userLogin`)
66
157
 
67
- ℹ️ Note: your Ethora App, User and Chat credentials are hard-coded and login screen is bypassed. This is done so that you can scaffold and test the functionality quickly.
68
- Leave this as is if you only need to demo or validate the chat functionality as part of your project.
69
- If you need to have your own private chats, be able to login multiple users etc then go to https://www.ethora.com/, sign up in the top right which gives you a free account with Ethora backend where you can create your own App, manage your Users and Chats, view stats etc. Copy App ID & App Secret to your chat component code which will then switch to your own App context on the server side. The free tier is generous but should you need extra you can later build your own backend, upgrade to a paid tier from Ethora or use a self-hosted AWS marketplace image from Ethora.
158
+ ```tsx
159
+ <XmppProvider>
160
+ <Chat
161
+ config={{
162
+ userLogin: {
163
+ enabled: true,
164
+ user: {
165
+ _id: 'PLACEHOLDER_USER_ID',
166
+ appId: 'PLACEHOLDER_APP_ID',
167
+ walletAddress: 'PLACEHOLDER_WALLET_ADDRESS',
168
+ defaultWallet: { walletAddress: 'PLACEHOLDER_WALLET_ADDRESS' },
169
+ firstName: 'Jane',
170
+ lastName: 'Doe',
171
+ xmppPassword: 'PLACEHOLDER_XMPP_PASSWORD',
172
+ token: 'PLACEHOLDER_ACCESS_TOKEN',
173
+ refreshToken: 'PLACEHOLDER_REFRESH_TOKEN',
174
+ username: 'PLACEHOLDER_USERNAME',
175
+ },
176
+ },
177
+ }}
178
+ />
179
+ </XmppProvider>
180
+ ```
70
181
 
71
- ## Extra options (styling etc)
182
+ ### E) JWT login
72
183
 
73
- To create custom chat room styles in **App.tsx**:
184
+ ```tsx
185
+ <XmppProvider>
186
+ <Chat
187
+ config={{
188
+ jwtLogin: {
189
+ enabled: true,
190
+ token: 'PLACEHOLDER_JWT_TOKEN',
191
+ },
192
+ }}
193
+ />
194
+ </XmppProvider>
195
+ ```
74
196
 
75
- replace
197
+ ### F) Google login
76
198
 
77
- ```
78
- <Chat />
199
+ ```tsx
200
+ <XmppProvider>
201
+ <Chat
202
+ config={{
203
+ googleLogin: {
204
+ enabled: true,
205
+ firebaseConfig: {
206
+ apiKey: 'PLACEHOLDER_API_KEY',
207
+ authDomain: 'PLACEHOLDER_AUTH_DOMAIN',
208
+ projectId: 'PLACEHOLDER_PROJECT_ID',
209
+ storageBucket: 'PLACEHOLDER_STORAGE_BUCKET',
210
+ messagingSenderId: 'PLACEHOLDER_MESSAGING_SENDER_ID',
211
+ appId: 'PLACEHOLDER_APP_ID',
212
+ },
213
+ },
214
+ }}
215
+ />
216
+ </XmppProvider>
79
217
  ```
80
218
 
81
- with:
219
+ ### G) Single-room entry + URL/QR behavior
82
220
 
83
- ```
84
- <Chat
221
+ ```tsx
222
+ <XmppProvider>
223
+ <Chat
224
+ roomJID="ROOM_JID@conference.xmpp.ethoradev.com"
85
225
  config={{
86
- disableHeader: true,
87
- disableMedia: true,
88
- colors: { primary: "#4287f5", secondary: "#42f5e9" },
89
- defaultLogin=true
90
- googleLogin: {
91
- firebaseConfig: config, //Ethora app config
92
- enabled: true,
93
- },
94
- }}
95
- MainComponentStyles={{
96
- width: "100%",
97
- height: "500px",
98
- borderRadius: "16px",
99
- border: "1px solid #42f5e9",
226
+ setRoomJidInPath: true,
227
+ qrUrl: 'https://your-app.example/chat/?qrChatId=',
100
228
  }}
101
- roomJID=""
102
- user={{ email: "", password: "" }}
103
- disableHeader?: boolean;
104
-
105
- disableRooms: boolean;
106
- defaultLogin: boolean;
107
- disableInteractions: boolean; //disable interactions
108
- chatHeaderBurgerMenu: boolean; // disable burger menu in room header
109
- roomListStyles: React.CSSProperties; // used to change room List styles (left)
110
- chatRoomStyles: React.CSSProperties; // used to change room styles (right)
111
- setRoomJidInPath: boolean; // used to set RoomId to url
112
229
  />
230
+ </XmppProvider>
113
231
  ```
114
232
 
115
- ℹ️ Note: Add room and user which are registered at Ethora. After these changes - the pre-written user & room will be changed to yours.
233
+ `roomJID` forces entry room.
234
+ `setRoomJidInPath` syncs room identity to URL path.
235
+ `useQRCodeChat` / `handleQRChatId` support QR/deep-link room opening.
236
+
237
+ ## Behavior Notes and Legacy Quirks
238
+
239
+ - `newArch` is now default-on. If omitted, runtime uses new architecture paths.
240
+ - Old architecture is used only when you explicitly set `config.newArch = false`.
241
+ - `defaultLogin` currently has legacy inverted behavior in `LoginWrapper`:
242
+ - internal fallback login runs when login modes are not configured and `defaultLogin` is not set.
243
+ - keep this in mind when migrating; prefer explicit `userLogin` / `jwtLogin` / `googleLogin`.
244
+
245
+ ## Chat Props Reference
246
+
247
+ These are the top-level props accepted by `Chat` (exported from `ReduxWrapper`).
248
+
249
+ | Prop | Type | Required | Notes |
250
+ | --- | --- | --- | --- |
251
+ | `config` | `IConfig` | No | Main behavior/configuration object. |
252
+ | `roomJID` | `string` | No | Force specific room JID on load. |
253
+ | `user` | `{ email: string; password: string }` | No | Credentials for email/password login helper path. |
254
+ | `loginData` | `{ email: string; password: string }` | No | Optional login payload. |
255
+ | `MainComponentStyles` | `React.CSSProperties` | No | Outer container style override. |
256
+ | `token` | `string` | No | Optional token input (legacy/integration-specific usage). |
257
+ | `CustomMessageComponent` | `React.ComponentType<MessageProps>` | No | Replace message bubble rendering. |
258
+ | `CustomInputComponent` | `React.ComponentType<SendInputProps & { onSendMessage?; onSendMedia?; placeholderText?; }>` | No | Replace chat input area. |
259
+ | `CustomScrollableArea` | `React.ComponentType<CustomScrollableAreaProps>` | No | Replace list/scroll wrapper behavior. |
260
+ | `CustomDaySeparator` | `React.ComponentType<DaySeparatorProps>` | No | Replace day separator node. |
261
+ | `CustomNewMessageLabel` | `React.ComponentType<NewMessageLabelProps>` | No | Replace "new message" marker. |
262
+
263
+ ## Full Config Reference (`IConfig`)
264
+
265
+ Below is a grouped reference for all `config` options.
266
+
267
+ ### Core
268
+
269
+ | Option | Type | Description |
270
+ | --- | --- | --- |
271
+ | `appId` | `string` | App identifier for backend context. |
272
+ | `baseUrl` | `string` | API base URL (default project uses `https://api.ethoradev.com/v1`). |
273
+ | `customAppToken` | `string` | Custom app token for API initialization. |
274
+ | `xmppSettings` | `{ devServer; host; conference?; xmppPingOnSendEnabled? }` | XMPP connectivity settings. |
275
+ | `initBeforeLoad` | `boolean` | Initialize XMPP before normal chat load flow. |
276
+ | `clearStoreBeforeInit` | `boolean` | Clear local store before initialization. |
277
+ | `newArch` | `boolean` | Defaults to `true`; set `false` to explicitly force legacy/old architecture paths. |
278
+ | `useStoreConsoleEnabled` | `boolean` | Enable verbose internal logging in console. |
279
+
280
+ ### UI and Layout
281
+
282
+ | Option | Type | Description |
283
+ | --- | --- | --- |
284
+ | `disableHeader` | `boolean` | Hide chat header. |
285
+ | `disableMedia` | `boolean` | Disable media sending/processing paths. |
286
+ | `disableRooms` | `boolean` | Hide/disable room list area. |
287
+ | `disableRoomMenu` | `boolean` | Disable room menu controls. |
288
+ | `disableRoomConfig` | `boolean` | Disable room configuration actions. |
289
+ | `disableNewChatButton` | `boolean` | Hide new chat/create room action. |
290
+ | `disableUserCount` | `boolean` | Hide user count in header/UI. |
291
+ | `disableChatInfo` | `{ disableHeader?; disableDescription?; disableType?; disableMembers?; hideMembers?; disableChatHeaderMenu? }` | Fine-grained chat info panel toggles. |
292
+ | `chatHeaderBurgerMenu` | `boolean` | Toggle burger menu in chat header. |
293
+ | `chatHeaderSettings` | `{ hide?; disableCreate?; disableMenu?; hideSearch? }` | Additional header-level controls. |
294
+ | `chatHeaderAdditional` | `{ enabled: boolean; element: any }` | Inject custom element into header area. |
295
+ | `headerLogo` | `string \| React.ReactElement` | Custom logo in header. |
296
+ | `headerMenu` | `() => void` | Custom menu handler. |
297
+ | `headerChatMenu` | `() => void` | Custom room header menu handler. |
298
+ | `colors` | `{ primary: string; secondary: string }` | Theme colors for component UI. |
299
+ | `roomListStyles` | `React.CSSProperties` | Styles for room list pane. |
300
+ | `chatRoomStyles` | `React.CSSProperties` | Styles for chat pane. |
301
+ | `backgroundChat` | `{ color?: string; image?: string \| File }` | Chat background customization. |
302
+ | `bubleMessage` | `MessageBubble` | Bubble-level style overrides (as defined in types). |
303
+ | `setRoomJidInPath` | `boolean` | Sync room JID to URL path. |
304
+ | `qrUrl` | `string` | Base URL for QR deep link behavior. |
305
+
306
+ ### Auth and Identity
307
+
308
+ | Option | Type | Description |
309
+ | --- | --- | --- |
310
+ | `defaultLogin` | `boolean` | Legacy quirk: current runtime fallback behavior is inverted; see Behavior Notes section. |
311
+ | `googleLogin` | `{ enabled: boolean; firebaseConfig: FBConfig }` | Google login support via Firebase config. |
312
+ | `jwtLogin` | `{ token: string; enabled: boolean; handleBadlogin?: React.ReactElement }` | Log user in using JWT exchange flow. |
313
+ | `userLogin` | `{ enabled: boolean; user: User \| null }` | Inject already-authenticated user directly. |
314
+ | `customLogin` | `{ enabled: boolean; loginFunction: () => Promise<User \| null> }` | Provide your custom async login function. |
315
+ | `refreshTokens` | `{ enabled: boolean; refreshFunction?: () => Promise<{ accessToken: string; refreshToken?: string } \| null> }` | Token refresh strategy. |
316
+
317
+ ### Rooms and Data
318
+
319
+ | Option | Type | Description |
320
+ | --- | --- | --- |
321
+ | `defaultRooms` | `ConfigRoom[]` | Seed/default rooms. |
322
+ | `customRooms` | `{ rooms: PartialRoomWithMandatoryKeys[]; disableGetRooms?: boolean; singleRoom: boolean }` | Fully controlled room source. |
323
+ | `forceSetRoom` | `boolean` | Force room setup path in init flow. |
324
+ | `enableRoomsRetry` | `{ enabled: boolean; helperText: string }` | Enable retry UX when rooms fail to load. |
325
+
326
+ ### Messaging and Interactions
327
+
328
+ | Option | Type | Description |
329
+ | --- | --- | --- |
330
+ | `disableInteractions` | `boolean` | Disable message interaction menu/actions. |
331
+ | `disableProfilesInteractions` | `boolean` | Disable profile interactions from chat UI. |
332
+ | `disableSentLogic` | `boolean` | Disable default sent-state logic when needed. |
333
+ | `secondarySendButton` | `{ enabled: boolean; messageEdit: string; label?: React.ReactNode; buttonStyles?: React.CSSProperties; hideInputSendButton?: boolean; overwriteEnterClick?: true }` | Extra send action/button config. |
334
+ | `botMessageAutoScroll` | `boolean` | Force auto-scroll behavior on bot messages. |
335
+ | `messageTextFilter` | `{ enabled: boolean; filterFunction: (text: string) => string }` | Transform/filter outgoing message text. |
336
+ | `eventHandlers` | `{ onMessageSent?; onMessageFailed?; onMessageEdited? }` | Lifecycle callbacks for message operations. |
337
+ | `translates` | `{ enabled: boolean; translations?: Iso639_1Codes }` | Message translation-related options. |
338
+ | `whitelistSystemMessage` | `string[]` | Restrict/render only selected system message types. |
339
+ | `customSystemMessage` | `React.ComponentType<MessageProps>` | Replace system message component renderer. |
340
+
341
+ ### Typing and Sending Control
342
+
343
+ | Option | Type | Description |
344
+ | --- | --- | --- |
345
+ | `disableTypingIndicator` | `boolean` | Disable typing indicator UI logic. |
346
+ | `customTypingIndicator` | `{ enabled: boolean; text?: string \| ((usersTyping: string[]) => string); position?: 'bottom' \| 'top' \| 'overlay' \| 'floating'; styles?: React.CSSProperties; customComponent?: React.ComponentType<{ usersTyping: string[]; text: string; isVisible: boolean; }> }` | Customize typing indicator content and rendering. |
347
+ | `blockMessageSendingWhenProcessing` | `boolean \| { enabled: boolean; timeout?: number; onTimeout?: (roomJID: string) => void }` | Gate sends while processing in-flight state. |
348
+
349
+ ### Notifications
350
+
351
+ | Option | Type | Description |
352
+ | --- | --- | --- |
353
+ | `inAppNotifications` | `{ enabled?; showInContext?; position?; maxNotifications?; duration?; onClick?; customComponent? }` | In-app toast notification behavior and custom rendering. |
354
+
355
+ ### Push
356
+
357
+ | Option | Type | Description |
358
+ | --- | --- | --- |
359
+ | `pushNotifications.enabled` | `boolean` | Enable browser push subscription flow. |
360
+ | `pushNotifications.vapidPublicKey` | `string` | VAPID public key for push registration. |
361
+ | `pushNotifications.firebaseConfig` | `FBConfig` | Firebase app config for push messaging. |
362
+ | `pushNotifications.serviceWorkerPath` | `string` | Service worker path, default `/firebase-messaging-sw.js`. |
363
+ | `pushNotifications.serviceWorkerScope` | `string` | Service worker scope, default `/`. |
364
+ | `pushNotifications.softAsk` | `boolean` | Do not immediately trigger browser permission prompt. |
365
+
366
+ ## Custom Widgets and Overrides
367
+
368
+ You can replace key UI parts without forking the package.
369
+
370
+ | Override prop | Purpose |
371
+ | --- | --- |
372
+ | `CustomMessageComponent` | Fully custom message bubble/row rendering. |
373
+ | `CustomInputComponent` | Custom composer and send controls. |
374
+ | `CustomScrollableArea` | Custom scroll/list container (virtualized or custom behavior). |
375
+ | `CustomDaySeparator` | Custom date separator component. |
376
+ | `CustomNewMessageLabel` | Custom "new message" divider label. |
377
+
378
+ Example:
379
+
380
+ ```tsx
381
+ import { Chat } from '@ethora/chat-component';
382
+ import CustomMessageBubble from './CustomMessageBubble';
383
+ import CustomChatInput from './CustomChatInput';
384
+ import CustomScrollableArea from './CustomScrollableArea';
385
+ import CustomDaySeparator from './CustomDaySeparator';
386
+ import CustomNewMessageLabel from './CustomNewMessageLabel';
387
+
388
+ export default function App() {
389
+ return (
390
+ <Chat
391
+ CustomMessageComponent={CustomMessageBubble}
392
+ CustomInputComponent={CustomChatInput}
393
+ CustomScrollableArea={CustomScrollableArea}
394
+ CustomDaySeparator={CustomDaySeparator}
395
+ CustomNewMessageLabel={CustomNewMessageLabel}
396
+ config={{
397
+ colors: { primary: '#1d4ed8', secondary: '#dbeafe' },
398
+ }}
399
+ />
400
+ );
401
+ }
402
+ ```
116
403
 
117
- ℹ️ Note:
118
- There is also a prop CustomMessageComponent: React.ComponentType<MessageProps>
119
- This prop is used to fully change styles of messageBubble.
120
- You can find an example here: https://github.com/dappros/ethora-chat-component/blob/main/src/components/ExampleComponents/CustomMessage.tsx
404
+ Reference example components in repository:
121
405
 
122
- For styling you can alter **App.css**:
406
+ - `src/examples/customComponents/CustomMessageBubble.tsx`
407
+ - `src/examples/customComponents/CustomChatInput.tsx`
408
+ - `src/examples/customComponents/CustomScrollableArea.tsx`
409
+ - `src/examples/customComponents/CustomDaySeparator.tsx`
410
+ - `src/examples/customComponents/CustomNewMessageLabel.tsx`
123
411
 
124
- ```
125
- #root {
126
- width: 100%;
127
- margin: 0 auto;
128
- text-align: center;
129
- }
130
- ```
412
+ ## Push Notifications
413
+
414
+ ### Prerequisites
415
+
416
+ | Requirement | Why |
417
+ | --- | --- |
418
+ | HTTPS origin (or localhost) | Browser push APIs require secure contexts. |
419
+ | Firebase project | FCM token + push transport setup. |
420
+ | VAPID public key | Required for web push subscription. |
421
+ | Service worker file | Required for background notification handling. |
422
+
423
+ ### Setup steps
131
424
 
132
- and **index.css**:
425
+ 1. Copy service worker into your app's public assets:
133
426
 
427
+ ```bash
428
+ npx @ethora/chat-component ethora-chat
134
429
  ```
135
- body {
136
- margin: 0;
137
- display: flex;
138
- place-items: center;
139
- min-width: 320px;
140
- min-height: 100vh;
141
- width: 100%;
142
- }
430
+
431
+ 2. Configure push in `config`:
432
+
433
+ ```tsx
434
+ <Chat
435
+ config={{
436
+ pushNotifications: {
437
+ enabled: true,
438
+ vapidPublicKey: 'PLACEHOLDER_VAPID_PUBLIC_KEY',
439
+ firebaseConfig: {
440
+ apiKey: 'PLACEHOLDER_API_KEY',
441
+ authDomain: 'PLACEHOLDER_AUTH_DOMAIN',
442
+ projectId: 'PLACEHOLDER_PROJECT_ID',
443
+ storageBucket: 'PLACEHOLDER_STORAGE_BUCKET',
444
+ messagingSenderId: 'PLACEHOLDER_MESSAGING_SENDER_ID',
445
+ appId: 'PLACEHOLDER_APP_ID',
446
+ },
447
+ serviceWorkerPath: '/firebase-messaging-sw.js',
448
+ serviceWorkerScope: '/',
449
+ softAsk: false,
450
+ },
451
+ }}
452
+ />
143
453
  ```
144
454
 
145
- After these changes you can modify **MainComponentStyles** for your chat.
455
+ 3. Optional: use hook directly for controlled permission flow:
146
456
 
147
- ## Architecture Diagram
457
+ ```tsx
458
+ import { usePushNotifications } from '@ethora/chat-component';
148
459
 
149
- ![CleanShot 2025-01-09 at 13 14 37@2x](https://github.com/user-attachments/assets/4d187bbb-6697-4e96-97d3-3a4a4b7e8adf)
460
+ function PushPermissionButton() {
461
+ const { requestPermission } = usePushNotifications({
462
+ enabled: true,
463
+ softAsk: true,
464
+ vapidPublicKey: 'PLACEHOLDER_VAPID_PUBLIC_KEY',
465
+ });
150
466
 
151
- ## Use cases and functionalities details
467
+ return <button onClick={() => requestPermission()}>Enable Push</button>;
468
+ }
469
+ ```
152
470
 
153
- ### LOGIN FUNCTIONALITY
471
+ ## Auth Strategies
154
472
 
155
- Chat component includes an optional Login / Sign-on screen that allows you to login existing users or sign up new users.
156
- In cases where chat component is embedded into your existing web or app experience, you would likely want to disable and bypass the login screen.
473
+ | Strategy | Config shape | Best for |
474
+ | --- | --- | --- |
475
+ | Default fallback (legacy quirk) | no auth block / `defaultLogin` | Legacy/demo flows; prefer explicit auth modes in production |
476
+ | Injected user | `userLogin: { enabled: true, user }` | App already has authenticated user/session |
477
+ | JWT login | `jwtLogin: { enabled: true, token }` | Token-based backend auth flow |
478
+ | Google login | `googleLogin: { enabled: true, firebaseConfig }` | Google SSO using Firebase |
479
+ | Custom login function | `customLogin: { enabled: true, loginFunction }` | Fully custom identity provider |
157
480
 
158
- Supported out of the box:
481
+ ### Example: injected user (bypass login screen)
159
482
 
160
- - **Login bypass** (user credentials are passed from your existing backend) ✅
161
- - **E-mail + password** ✅
162
- - **Google SSO** ✅
483
+ ```tsx
484
+ <Chat
485
+ config={{
486
+ userLogin: {
487
+ enabled: true,
488
+ user: {
489
+ _id: 'PLACEHOLDER_USER_ID',
490
+ appId: 'PLACEHOLDER_APP_ID',
491
+ walletAddress: 'PLACEHOLDER_WALLET_ADDRESS',
492
+ defaultWallet: { walletAddress: 'PLACEHOLDER_WALLET_ADDRESS' },
493
+ firstName: 'Jane',
494
+ lastName: 'Doe',
495
+ xmppPassword: 'PLACEHOLDER_XMPP_PASSWORD',
496
+ token: 'PLACEHOLDER_ACCESS_TOKEN',
497
+ refreshToken: 'PLACEHOLDER_REFRESH_TOKEN',
498
+ username: 'PLACEHOLDER_USERNAME',
499
+ },
500
+ },
501
+ }}
502
+ />
503
+ ```
163
504
 
164
- Supported by Ethora platform but not implemented into Chat Component yet:
505
+ ### Example: JWT login
165
506
 
166
- - **Custom set of credentials** ✅
167
- - **Apple SSO** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub>
168
- - **Facebook SSO** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub>
169
- - **Metamask SSO** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub>
507
+ ```tsx
508
+ <Chat
509
+ config={{
510
+ jwtLogin: {
511
+ enabled: true,
512
+ token: 'PLACEHOLDER_JWT_TOKEN',
513
+ },
514
+ refreshTokens: {
515
+ enabled: true,
516
+ refreshFunction: async () => {
517
+ return {
518
+ accessToken: 'PLACEHOLDER_NEW_ACCESS_TOKEN',
519
+ refreshToken: 'PLACEHOLDER_NEW_REFRESH_TOKEN',
520
+ };
521
+ },
522
+ },
523
+ }}
524
+ />
525
+ ```
170
526
 
171
- ### CHAT FUNCTIONALITY
527
+ ## Hooks and API Exports
528
+
529
+ | Export | Type | Purpose |
530
+ | --- | --- | --- |
531
+ | `Chat` | React component | Main chat component. |
532
+ | `XmppProvider` | React provider | Provides XMPP client context for internal hooks/state. |
533
+ | `useUnread` | hook | Returns unread counters. |
534
+ | `logoutService` | service | Programmatic logout utility. |
535
+ | `useQRCodeChat` | hook | Handle QR-based room links. |
536
+ | `handleQRChatId` | function | Parse/process QR chat ID from URL. |
537
+ | `useInAppNotifications` | hook | Enables and handles in-app notifications. |
538
+ | `usePushNotifications` | hook | Push subscription + foreground handling workflow. |
539
+ | `resendMessage` | function | Retry sending failed/pending messages. |
540
+
541
+ Basic hook usage:
542
+
543
+ ```tsx
544
+ import { useUnread, logoutService } from '@ethora/chat-component';
545
+
546
+ function HeaderActions() {
547
+ const { totalCount } = useUnread();
548
+
549
+ return (
550
+ <div>
551
+ <span>Unread: {totalCount}</span>
552
+ <button onClick={() => logoutService.performLogout()}>Logout</button>
553
+ </div>
554
+ );
555
+ }
556
+ ```
172
557
 
173
- #### "One room at a time - chat session"
558
+ `logoutService.performLogout()` behavior:
174
559
 
175
- - Use Case 1: **One global chat room for all users** ✅ - (e.g. chat lobby for all of your website / app users). Simply create a chat room manually and hardcode the UUID into your chat component code.
176
- - Use Case 2: **One chat room per case** ✅ - (e.g. customer support session, AI bot, a chat room for each location or department, web page specific chat etc). You have to create rooms as required by your business logic via Ethora API and then pass the corresponding chat UUID into chat component. Your end User will see the corresponding room.
560
+ - Dispatches `chatSettingStore/logout`
561
+ - Dispatches `rooms/setLogoutState`
562
+ - Dispatches `roomHeap/clearHeap`
563
+ - Triggers logout middleware, which emits `ethora-xmpp-logout`
564
+ - `XmppProvider` listens to that event and disconnects active XMPP client
177
565
 
178
- #### "Multiple rooms - messenger / social app”
566
+ ## Use Cases and Feature Coverage
179
567
 
180
- - Use Case 3: **Users can switch between Chats** ✅
181
- Similar to Use Case 2, but also allows your User to switch to the **List of Chats** where they can see chat rooms, the count of new messages and a last message for -each room etc. Users can create new Chats and invite others into Chats (depending on your App settings). This functionality is available in full Ethora app but is currently "work in progress" for Chat Component.
568
+ | Area | Status in this package |
569
+ | --- | --- |
570
+ | One-room embedded chat | Available |
571
+ | Multi-room chat UI | Available |
572
+ | Message interactions (reply/copy/edit/delete/report/reactions) | Available |
573
+ | Typing indicator | Available |
574
+ | Profile interactions in chat | Available (can be disabled) |
575
+ | File/media attachments | Available with ongoing enhancements |
576
+ | In-app notifications | Available |
577
+ | Web push notifications | Available |
578
+ | Wallet/assets and extended social modules | Primarily in full Ethora platform |
182
579
 
183
- #### Misc core chat functionalities
580
+ ## Hosted vs Self-Host Guidance
184
581
 
185
- - **Chat header** ✅ - Header with chat title and Users counter (this is optional and you can disable the header)
186
- - **Message bubbles** ✅ - Message bubbles next to user avatars with message content and timestamp
187
- - **Chat history caching and scrolling** ✅
188
- - **Chat history date divider** ✅
189
- - **Now typing** ✅ - when someone is typing, other room Users will see indication of who is typing
582
+ | Model | Best for | Pros | Tradeoffs |
583
+ | --- | --- | --- | --- |
584
+ | Hosted Ethora backend | Fast time-to-market, smaller teams, MVPs | Fast setup, managed backend operations, easier push/auth onboarding | Less infrastructure-level control |
585
+ | Self-hosted Ethora stack | Regulated environments, deep infra control | Full control over infrastructure, compliance customization, internal network deployment options | Higher DevOps/maintenance overhead |
586
+ | Hybrid | Gradual migration or split workloads | Can start fast and migrate critical paths later | More architecture complexity |
190
587
 
191
- #### Message interactions
192
588
 
193
- - **Message menu** ✅ - Long tap or right click opens message menu with "Reply", "Copy", "Edit", "Delete", "Report" options available as well as send Coin / Item options
194
- - **Emoji Reactions** ✅ - Users are able to long tap / click on the message and send Emoji reactions to the message. Reactions are displayed in the corner of the message bubble.
589
+ ## Feature Roadmap
195
590
 
196
- #### Avatars (profile photos)
591
+ This is a practical planning snapshot for cross-platform consumers. It is not a release commitment.
197
592
 
198
- - **Basic avatars** ✅ - in chat screen, users can see basic avatars next to chat bubbles. Simply default avatar icon for everyone.
199
- - **"Initials" avatars** ✅ - in Chat scree, users who don't have photos uploaded will show as "initials" avatars generated by taking the first letter of User's first name and last name
200
- - **Google SSO avatars** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub> - when using Google SSO, their Google profile photo will be automatically displayed as chat avatar
201
- - **Custom profile photos** ✅ - users are able to upload their custom photos when managing their Profile and the mini-photo will be displayed as a chat avatar
593
+ | Surface | Current state | Notes |
594
+ | --- | --- | --- |
595
+ | Web React (`@ethora/chat-component`) | Available now | This repository. |
596
+ | React Native | Via broader Ethora stack | Track platform-specific implementation in Ethora repos/docs. |
597
+ | Swift (iOS native) | Planned / ecosystem-level | Confirm status with Ethora team for production timelines. |
598
+ | Kotlin (Android native) | Planned / ecosystem-level | Confirm status with Ethora team for production timelines. |
599
+ | Flutter | Planned / ecosystem-level | Confirm status with Ethora team for production timelines. |
600
+ | Additional roadmap items | Ongoing | Media improvements, richer profile/wallet experiences, broader integration guides. |
202
601
 
203
- #### Notifications
602
+ ## Troubleshooting
204
603
 
205
- - **Browser and mobile push notifications** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub> - push notifications are useful to alert the User about new messages or transactions related to them when they are not actively using your app / chat in the browser.
604
+ | Issue | Likely cause | Fix |
605
+ | --- | --- | --- |
606
+ | `useXmppClient must be used within an XmppProvider` | Using internal XMPP-dependent logic without provider context | Wrap the app tree with `XmppProvider` where needed. |
607
+ | Chat loads but no rooms appear | Auth/app context mismatch or room fetching restrictions | Verify `appId`, user credentials/tokens, `baseUrl`, and `customRooms` settings. |
608
+ | Push permission never appears | `softAsk: true` without manual trigger, insecure origin, or missing VAPID key | Trigger `requestPermission()`, use HTTPS/localhost, set valid VAPID key. |
609
+ | Service worker not found | `firebase-messaging-sw.js` missing in public dir | Run `npx @ethora/chat-component ethora-chat` or copy file manually. |
610
+ | Login loop / auth failure | Wrong token/user object shape | Validate `jwtLogin`, `userLogin.user`, and refresh token flow. |
206
611
 
207
- ### FILE ATTACHMENTS
612
+ ## Ethora Links and Support
613
+ ### Product
208
614
 
209
- - **File attachments** ✅ - file attachments, previews, media attachments, audio/video player etc currently are work in progress for chat component
615
+ - Website: https://ethora.com/
616
+ - Try Ethora: https://app.ethora.com/register
210
617
 
211
- ### USER PROFILES AND DIGITAL WALLET FUNCTIONALITY
618
+ ### Developer Docs
212
619
 
213
- - **Profile screen** ✅ - users can see their own and other Users Profile screens by tapping their avatar in Chat. Profile includes Photo, name, description, direct message button and profile share link
214
- - **Profile Assets (Digital Wallet)** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub> - Users can view assets (Documents, art/collectables, Coins) within their own profile or profiles of other Users, depending on App-wide and User-specific visibility settings
215
- - **Profile Asset: Coins** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub> - Coins, Points, Stars (you can call this anything in your project) are a rewards system where Users and Bots can reward individual messages of other Users
216
- - **Profile Asset: Documents** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub> - Documents in Profiles support use cases where certain User (or bot / business page) need to display certain documents and their provenance history. E.g. business / educational / medical certificates, case-related documents, contracts etc.
217
- - **Profile Asset: Media (audio, video) files** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub> - Media files playable right from Profiles.
218
- - **Profile Asset: Digital Art (collectables / NFT)** 🚧 <sub><sup>(available in [Ethora git repo](https://github.com/dappros/ethora))</sup></sub> - For projects which support rewarding Users with unique digital collectables and/or allowing Users to upload/mint, distribute or trade digital art or collectables.
620
+ - Chat component docs: https://docs.ethora.com/
621
+ - Ethora GitHub hub: https://github.com/dappros/ethora
622
+ - This package repo: https://github.com/dappros/ethora-chat-component
623
+ - Ethora GitHub organization: https://github.com/dappros
624
+ - API docs (public): https://app.dappros.com/api-docs/
625
+ - API docs (environment used in this repo): https://api.ethoradev.com/api-docs
219
626
 
220
- ## Contacts, Documentation and Technical Support
627
+ ### Community and Support
221
628
 
222
- - Community support forum: https://forum.ethora.com/
629
+ - Forum: https://forum.ethora.com/
223
630
  - Discord: https://discord.gg/Sm6bAHA3ZC
224
- - Contact Ethora team: https://www.ethora.com/#contact
225
- - Documentation main: https://docs.ethora.com/
226
- - Documentation for Ethora API (Swagger): https://api.ethoradev.com/api-docs
227
- - Documentation on github including chat protocol and bots: https://github.com/dappros/ethora/tree/main/api
631
+ - Contact: https://ethora.com/#contact
632
+
633
+ ## License
634
+
635
+ AGPL. See [LICENSE.txt](./LICENSE.txt).