From a27080fc34da70ddb559ffd668c23682ca360989 Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Mon, 26 Apr 2021 17:33:12 +1000 Subject: [PATCH 01/14] Use flex to keep the input box at the bottom --- web-chat/src/App.tsx | 21 ++++++++------------- web-chat/src/Room.tsx | 26 +++++++++++--------------- 2 files changed, 19 insertions(+), 28 deletions(-) diff --git a/web-chat/src/App.tsx b/web-chat/src/App.tsx index 0d77832c92..9c93e1c4c0 100644 --- a/web-chat/src/App.tsx +++ b/web-chat/src/App.tsx @@ -1,4 +1,3 @@ -import { Paper } from '@material-ui/core'; import { multiaddr } from 'multiaddr'; import PeerId from 'peer-id'; import React, { useEffect, useState } from 'react'; @@ -155,18 +154,14 @@ export default function App() { }; return ( -
-
- - - - - -
+
+ + +
); } diff --git a/web-chat/src/Room.tsx b/web-chat/src/Room.tsx index f62dc1613c..8c31c19f59 100644 --- a/web-chat/src/Room.tsx +++ b/web-chat/src/Room.tsx @@ -1,4 +1,4 @@ -import { Box, Grid, List, ListItem, ListItemText } from '@material-ui/core'; +import { List, ListItem, ListItemText } from '@material-ui/core'; import React, { useState } from 'react'; import { ChatMessage } from 'waku-chat/chat_message'; import { WakuMessage } from 'waku/waku_message'; @@ -38,24 +38,20 @@ export default function Room(props: Props) { }; return ( - - - - - - - - +
+
+ +
+
- - +
+
); } From b943a88affbfe23a3287ce6f4e215707290028d8 Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Tue, 27 Apr 2021 10:48:08 +1000 Subject: [PATCH 02/14] Split commandHandler in smaller pure functions --- web-chat/src/App.tsx | 96 +++++------------------------------ web-chat/src/command.ts | 109 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 122 insertions(+), 83 deletions(-) create mode 100644 web-chat/src/command.ts diff --git a/web-chat/src/App.tsx b/web-chat/src/App.tsx index 9c93e1c4c0..c27b4c93a9 100644 --- a/web-chat/src/App.tsx +++ b/web-chat/src/App.tsx @@ -5,6 +5,7 @@ import './App.css'; import { ChatMessage } from 'waku-chat/chat_message'; import { WakuMessage } from 'waku/waku_message'; import { RelayDefaultTopic } from 'waku/waku_relay'; +import handleCommand from './command'; import Room from './Room'; import Waku from 'waku/waku'; import { WakuContext } from './WakuContext'; @@ -71,95 +72,24 @@ export default function App() { } }); - const commandHandler = (input: string) => { - let commandResponses: string[] = []; - const args = input.split(' '); - const cmd = args.shift()!; - if (!stateWaku) { - commandResponses.push('Waku is not yet initialized'); - } else { - switch (cmd) { - case '/help': - commandResponses.push('/nick : set a new nickname'); - commandResponses.push('/info: some information about the node'); - commandResponses.push( - '/connect : connect to the given peer' - ); - commandResponses.push('/help: Display this help'); - break; - case '/nick': - const arg = args.shift(); - if (!arg) { - commandResponses.push('No nick provided'); - } else { - setNick(arg); - commandResponses.push(`New nick: ${arg}`); - } - break; - case '/info': - if (!stateWaku) { - commandResponses.push(`Waku node is starting`); - } else { - commandResponses.push( - `PeerId: ${stateWaku.libp2p.peerId.toB58String()}` - ); - } - break; - case '/connect': - const peer = args.shift(); - if (!peer) { - commandResponses.push('No peer provided'); - } else { - try { - const peerMultiaddr = multiaddr(peer); - const peerId = peerMultiaddr.getPeerId(); - if (!peerId) { - commandResponses.push('Peer Id needed to dial'); - } else { - stateWaku.libp2p.peerStore.addressBook.add( - PeerId.createFromB58String(peerId), - [peerMultiaddr] - ); - } - } catch (e) { - commandResponses.push('Invalid multiaddr: ' + e); - } - } - break; - case '/peers': - stateWaku.libp2p.peerStore.peers.forEach((peer, peerId) => { - commandResponses.push(peerId + ':'); - let addresses = ' addresses: ['; - peer.addresses.forEach(({ multiaddr }) => { - addresses += ' ' + multiaddr.toString() + ','; - }); - addresses = addresses.replace(/,$/, ''); - addresses += ']'; - commandResponses.push(addresses); - let protocols = ' protocols: ['; - protocols += peer.protocols; - protocols += ']'; - commandResponses.push(protocols); - }); - break; - default: - commandResponses.push('Unknown Command'); - } - } - const messages = stateMessages.slice(); - commandResponses.forEach((res) => { - messages.push(new ChatMessage(new Date(), cmd, res)); - }); - setMessages(messages); - }; - return (
{ + const { command, response } = handleCommand( + input, + stateWaku, + setNick + ); + const messages = stateMessages.slice(); + response.forEach((msg) => { + messages.push(new ChatMessage(new Date(), command, msg)); + }); + setMessages(messages); + }} />
diff --git a/web-chat/src/command.ts b/web-chat/src/command.ts new file mode 100644 index 0000000000..2741b124e2 --- /dev/null +++ b/web-chat/src/command.ts @@ -0,0 +1,109 @@ +import { multiaddr } from 'multiaddr'; +import PeerId from 'peer-id'; +import Waku from '../../build/main/lib/waku'; + +function help(): string[] { + return [ + '/nick : set a new nickname', + '/info: some information about the node', + '/connect : connect to the given peer', + '/help: Display this help', + ]; +} + +function nick( + nick: string | undefined, + setNick: (nick: string) => void +): string[] { + if (!nick) { + return ['No nick provided']; + } + setNick(nick); + return [`New nick: ${nick}`]; +} + +function info(waku: Waku | undefined): string[] { + if (!waku) { + return ['Waku node is starting']; + } + return [`PeerId: ${waku.libp2p.peerId.toB58String()}`]; +} + +function connect(peer: string | undefined, waku: Waku | undefined): string[] { + if (!waku) { + return ['Waku node is starting']; + } + if (!peer) { + return ['No peer provided']; + } + try { + const peerMultiaddr = multiaddr(peer); + const peerId = peerMultiaddr.getPeerId(); + if (!peerId) { + return ['Peer Id needed to dial']; + } + waku.libp2p.peerStore.addressBook.add(PeerId.createFromB58String(peerId), [ + peerMultiaddr, + ]); + return [ + `${peerId}: ${peerMultiaddr.toString()} added to address book, autodial in progress`, + ]; + } catch (e) { + return ['Invalid multiaddr: ' + e]; + } +} + +function peers(waku: Waku | undefined): string[] { + if (!waku) { + return ['Waku node is starting']; + } + let response: string[] = []; + waku.libp2p.peerStore.peers.forEach((peer, peerId) => { + response.push(peerId + ':'); + let addresses = ' addresses: ['; + peer.addresses.forEach(({ multiaddr }) => { + addresses += ' ' + multiaddr.toString() + ','; + }); + addresses = addresses.replace(/,$/, ''); + addresses += ']'; + response.push(addresses); + let protocols = ' protocols: ['; + protocols += peer.protocols; + protocols += ']'; + response.push(protocols); + }); + if (response.length === 0) { + response.push('Not connected to any peer.'); + } + return response; +} + +export default function handleCommand( + input: string, + waku: Waku | undefined, + setNick: (nick: string) => void +): { command: string; response: string[] } { + let response: string[] = []; + const args = input.split(' '); + const command = args.shift()!; + switch (command) { + case '/help': + help().map((str) => response.push(str)); + break; + case '/nick': + nick(args.shift(), setNick).map((str) => response.push(str)); + break; + case '/info': + info(waku).map((str) => response.push(str)); + break; + case '/connect': + connect(args.shift(), waku).map((str) => response.push(str)); + break; + case '/peers': + peers(waku).map((str) => response.push(str)); + break; + default: + response.push(`Unknown Command '${command}'`); + } + return { command, response }; +} From 5998eb1d5d01bc2b34ecccea00138a2fcf4bde8f Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Tue, 27 Apr 2021 11:00:09 +1000 Subject: [PATCH 03/14] Split handleNewMessages in smaller pure functions --- web-chat/src/App.tsx | 34 +++++++++++++++++++++++----------- 1 file changed, 23 insertions(+), 11 deletions(-) diff --git a/web-chat/src/App.tsx b/web-chat/src/App.tsx index c27b4c93a9..8bd3eaa575 100644 --- a/web-chat/src/App.tsx +++ b/web-chat/src/App.tsx @@ -45,13 +45,9 @@ export default function App() { } const handleNewMessages = (event: { data: Uint8Array }) => { - const wakuMsg = WakuMessage.decode(event.data); - if (wakuMsg.payload) { - const chatMsg = ChatMessage.decode(wakuMsg.payload); - const messages = stateMessages.slice(); - messages.push(chatMsg); - console.log('setState on ', messages); - setMessages(messages); + const chatMsg = decodeWakuMessage(event.data); + if (chatMsg) { + copyAndReplace([chatMsg], stateMessages, setMessages); } }; @@ -84,14 +80,30 @@ export default function App() { stateWaku, setNick ); - const messages = stateMessages.slice(); - response.forEach((msg) => { - messages.push(new ChatMessage(new Date(), command, msg)); + const commandMessages = response.map((msg) => { + return new ChatMessage(new Date(), command, msg); }); - setMessages(messages); + copyAndReplace(commandMessages, stateMessages, setMessages); }} />
); } + +function decodeWakuMessage(data: Uint8Array): null | ChatMessage { + const wakuMsg = WakuMessage.decode(data); + if (!wakuMsg.payload) { + return null; + } + return ChatMessage.decode(wakuMsg.payload); +} + +function copyAndReplace( + newValues: Array, + currentValues: Array, + setter: (val: Array) => void +) { + const copy = currentValues.slice(); + setter(copy.concat(newValues)); +} From f0c0adf226ae2ca1c3f8fc324f6fe1917252e217 Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Tue, 27 Apr 2021 11:05:35 +1000 Subject: [PATCH 04/14] Move `initWaku` out of `App` --- web-chat/src/App.tsx | 56 ++++++++++++++++++++++---------------------- 1 file changed, 28 insertions(+), 28 deletions(-) diff --git a/web-chat/src/App.tsx b/web-chat/src/App.tsx index 8bd3eaa575..6874133cc8 100644 --- a/web-chat/src/App.tsx +++ b/web-chat/src/App.tsx @@ -18,32 +18,6 @@ export default function App() { let [nick, setNick] = useState('web-chat'); useEffect(() => { - async function initWaku() { - try { - const waku = await Waku.create({ - config: { - pubsub: { - enabled: true, - emitSelf: true, - }, - }, - }); - - setWaku(waku); - - // FIXME: Connect to a go-waku instance by default, temporary hack until - // we have a go-waku instance in the fleet - waku.libp2p.peerStore.addressBook.add( - PeerId.createFromB58String( - '16Uiu2HAmVVi6Q4j7MAKVibquW8aA27UNrA4Q8Wkz9EetGViu8ZF1' - ), - [multiaddr('/ip4/134.209.113.86/tcp/9001/ws')] - ); - } catch (e) { - console.log('Issue starting waku ', e); - } - } - const handleNewMessages = (event: { data: Uint8Array }) => { const chatMsg = decodeWakuMessage(event.data); if (chatMsg) { @@ -52,7 +26,7 @@ export default function App() { }; if (!stateWaku) { - initWaku() + initWaku(setWaku) .then(() => console.log('Waku init done')) .catch((e) => console.log('Waku init failed ', e)); } else { @@ -66,7 +40,7 @@ export default function App() { ); }; } - }); + }, [stateWaku, stateMessages]); return (
@@ -91,6 +65,32 @@ export default function App() { ); } +async function initWaku(setter: (waku: Waku) => void) { + try { + const waku = await Waku.create({ + config: { + pubsub: { + enabled: true, + emitSelf: true, + }, + }, + }); + + setter(waku); + + // FIXME: Connect to a go-waku instance by default, temporary hack until + // we have a go-waku instance in the fleet + waku.libp2p.peerStore.addressBook.add( + PeerId.createFromB58String( + '16Uiu2HAmVVi6Q4j7MAKVibquW8aA27UNrA4Q8Wkz9EetGViu8ZF1' + ), + [multiaddr('/ip4/134.209.113.86/tcp/9001/ws')] + ); + } catch (e) { + console.log('Issue starting waku ', e); + } +} + function decodeWakuMessage(data: Uint8Array): null | ChatMessage { const wakuMsg = WakuMessage.decode(data); if (!wakuMsg.payload) { From 5635ca028bf688263c5fa76a79ea8213268c4cb5 Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Tue, 27 Apr 2021 13:36:25 +1000 Subject: [PATCH 05/14] Make functions in Room component pure --- web-chat/src/MessageInput.tsx | 14 +++++---- web-chat/src/Room.tsx | 54 ++++++++++++++++++++--------------- 2 files changed, 39 insertions(+), 29 deletions(-) diff --git a/web-chat/src/MessageInput.tsx b/web-chat/src/MessageInput.tsx index f3fc69d688..fda34fc022 100644 --- a/web-chat/src/MessageInput.tsx +++ b/web-chat/src/MessageInput.tsx @@ -4,16 +4,18 @@ import { useWaku } from './WakuContext'; interface Props { messageHandler: (msg: string) => void; - sendMessage: () => void; + sendMessage: (() => Promise) | undefined; } export default function MessageInput(props: Props) { const [inputText, setInputText] = useState(''); const { waku } = useWaku(); - const sendMessage = () => { - props.sendMessage(); - setInputText(''); + const sendMessage = async () => { + if (props.sendMessage) { + await props.sendMessage(); + setInputText(''); + } }; const messageHandler = (event: ChangeEvent) => { @@ -21,9 +23,9 @@ export default function MessageInput(props: Props) { props.messageHandler(event.target.value); }; - const keyPressHandler = (event: KeyboardEvent) => { + const keyPressHandler = async (event: KeyboardEvent) => { if (event.key === 'Enter') { - sendMessage(); + await sendMessage(); } }; diff --git a/web-chat/src/Room.tsx b/web-chat/src/Room.tsx index 8c31c19f59..8f09914224 100644 --- a/web-chat/src/Room.tsx +++ b/web-chat/src/Room.tsx @@ -16,27 +16,6 @@ export default function Room(props: Props) { let [messageToSend, setMessageToSend] = useState(''); const { waku } = useWaku(); - const messageHandler = (msg: string) => { - setMessageToSend(msg); - }; - - const sendMessage = async () => { - if (messageToSend.startsWith('/')) { - props.commandHandler(messageToSend); - } else { - const chatMessage = new ChatMessage( - new Date(), - props.nick, - messageToSend - ); - const wakuMsg = WakuMessage.fromBytes( - chatMessage.encode(), - ChatContentTopic - ); - await waku!.relay.send(wakuMsg); - } - }; - return (
{ + return handleMessage( + messageToSend, + props.nick, + props.commandHandler, + waku.relay.send.bind(waku.relay) + ); + } + : undefined + } />
); } +async function handleMessage( + message: string, + nick: string, + commandHandler: (cmd: string) => void, + messageSender: (msg: WakuMessage) => Promise +) { + if (message.startsWith('/')) { + commandHandler(message); + } else { + const chatMessage = new ChatMessage(new Date(), nick, message); + const wakuMsg = WakuMessage.fromBytes( + chatMessage.encode(), + ChatContentTopic + ); + return messageSender(wakuMsg); + } +} + interface LinesProps { messages: ChatMessage[]; } From 243a9aba77b958a25fd588a120578654a569fb07 Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Tue, 27 Apr 2021 13:57:53 +1000 Subject: [PATCH 06/14] Make message a component --- web-chat/src/Room.tsx | 41 ++++++++++++++++++++++------------------- 1 file changed, 22 insertions(+), 19 deletions(-) diff --git a/web-chat/src/Room.tsx b/web-chat/src/Room.tsx index 8f09914224..c3a1efe623 100644 --- a/web-chat/src/Room.tsx +++ b/web-chat/src/Room.tsx @@ -22,7 +22,7 @@ export default function Room(props: Props) { style={{ height: '100vh', display: 'flex', flexDirection: 'column' }} >
- +
{ - const renderedLines = []; +function ChatList(props: ChatListProps) { + const messages = props.messages; - for (const i in props.messages) { - renderedLines.push( - - - - ); - } + const listItems = messages.map((message) => ( + + } /> + + )); - return {renderedLines}; -}; + return {listItems}; +} -// TODO: Make it a proper component -function printMessage(chatMsg: ChatMessage) { +interface MessageProps { + message: ChatMessage; +} + +function Message(props: MessageProps) { + const chatMsg = props.message; const timestamp = chatMsg.timestamp.toLocaleString([], { month: 'short', day: 'numeric', @@ -93,5 +92,9 @@ function printMessage(chatMsg: ChatMessage) { minute: '2-digit', hour12: false, }); - return `<${timestamp}> ${chatMsg.nick}: ${chatMsg.message}`; + return ( +
+ {`<${timestamp}> ${chatMsg.nick}: ${chatMsg.message}`} +
+ ); } From 14ccfdf2ddc0c6ef7dad5f420ed52c05c46d343a Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Tue, 27 Apr 2021 13:59:25 +1000 Subject: [PATCH 07/14] Move ChatList component to dedicated file --- web-chat/src/ChatList.tsx | 39 +++++++++++++++++++++++++++++++++++++++ web-chat/src/Room.tsx | 38 +------------------------------------- 2 files changed, 40 insertions(+), 37 deletions(-) create mode 100644 web-chat/src/ChatList.tsx diff --git a/web-chat/src/ChatList.tsx b/web-chat/src/ChatList.tsx new file mode 100644 index 0000000000..90e2238437 --- /dev/null +++ b/web-chat/src/ChatList.tsx @@ -0,0 +1,39 @@ +import { List, ListItem, ListItemText } from '@material-ui/core'; +import React from 'react'; +import { ChatMessage } from '../../build/main/chat/chat_message'; + +interface Props { + messages: ChatMessage[]; +} + +export default function ChatList(props: Props) { + const messages = props.messages; + + const listItems = messages.map((message) => ( + + } /> + + )); + + return {listItems}; +} + +interface MessageProps { + message: ChatMessage; +} + +function Message(props: MessageProps) { + const chatMsg = props.message; + const timestamp = chatMsg.timestamp.toLocaleString([], { + month: 'short', + day: 'numeric', + hour: 'numeric', + minute: '2-digit', + hour12: false, + }); + return ( +
+ {`<${timestamp}> ${chatMsg.nick}: ${chatMsg.message}`} +
+ ); +} diff --git a/web-chat/src/Room.tsx b/web-chat/src/Room.tsx index c3a1efe623..4b8f105010 100644 --- a/web-chat/src/Room.tsx +++ b/web-chat/src/Room.tsx @@ -1,8 +1,8 @@ -import { List, ListItem, ListItemText } from '@material-ui/core'; import React, { useState } from 'react'; import { ChatMessage } from 'waku-chat/chat_message'; import { WakuMessage } from 'waku/waku_message'; import { ChatContentTopic } from './App'; +import ChatList from './ChatList'; import MessageInput from './MessageInput'; import { useWaku } from './WakuContext'; @@ -62,39 +62,3 @@ async function handleMessage( return messageSender(wakuMsg); } } - -interface ChatListProps { - messages: ChatMessage[]; -} - -function ChatList(props: ChatListProps) { - const messages = props.messages; - - const listItems = messages.map((message) => ( - - } /> - - )); - - return {listItems}; -} - -interface MessageProps { - message: ChatMessage; -} - -function Message(props: MessageProps) { - const chatMsg = props.message; - const timestamp = chatMsg.timestamp.toLocaleString([], { - month: 'short', - day: 'numeric', - hour: 'numeric', - minute: '2-digit', - hour12: false, - }); - return ( -
- {`<${timestamp}> ${chatMsg.nick}: ${chatMsg.message}`} -
- ); -} From 973fd95df9c06ed1eadb214a8f2366f5daef6e17 Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Tue, 27 Apr 2021 14:26:52 +1000 Subject: [PATCH 08/14] Make chat lines slightly prettier --- web-chat/src/ChatList.tsx | 36 ++++++++++++++++++++++++++++++++---- 1 file changed, 32 insertions(+), 4 deletions(-) diff --git a/web-chat/src/ChatList.tsx b/web-chat/src/ChatList.tsx index 90e2238437..615c3992b2 100644 --- a/web-chat/src/ChatList.tsx +++ b/web-chat/src/ChatList.tsx @@ -1,4 +1,11 @@ -import { List, ListItem, ListItemText } from '@material-ui/core'; +import { + Card, + CardContent, + List, + ListItem, + ListItemText, + Typography, +} from '@material-ui/core'; import React from 'react'; import { ChatMessage } from '../../build/main/chat/chat_message'; @@ -31,9 +38,30 @@ function Message(props: MessageProps) { minute: '2-digit', hour12: false, }); + + // {`<${timestamp}> ${chatMsg.nick}: ${chatMsg.message}`} return ( -
- {`<${timestamp}> ${chatMsg.nick}: ${chatMsg.message}`} -
+ + + + {chatMsg.nick} + + {timestamp} + + + + {chatMsg.message} + + + ); } From 2d037c3e46d944f77890698bc015f104dc53b33e Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Tue, 27 Apr 2021 14:39:34 +1000 Subject: [PATCH 09/14] Attempt to fix double scrollbar issue --- web-chat/src/App.tsx | 5 ++++- web-chat/src/index.css | 2 ++ 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/web-chat/src/App.tsx b/web-chat/src/App.tsx index 6874133cc8..1907d2d819 100644 --- a/web-chat/src/App.tsx +++ b/web-chat/src/App.tsx @@ -43,7 +43,10 @@ export default function App() { }, [stateWaku, stateMessages]); return ( -
+
Date: Tue, 27 Apr 2021 14:55:30 +1000 Subject: [PATCH 10/14] Implement auto-scroll of the chat list --- web-chat/src/ChatList.tsx | 21 +++++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) diff --git a/web-chat/src/ChatList.tsx b/web-chat/src/ChatList.tsx index 615c3992b2..e74c48f235 100644 --- a/web-chat/src/ChatList.tsx +++ b/web-chat/src/ChatList.tsx @@ -6,7 +6,7 @@ import { ListItemText, Typography, } from '@material-ui/core'; -import React from 'react'; +import React, { useEffect, useRef } from 'react'; import { ChatMessage } from '../../build/main/chat/chat_message'; interface Props { @@ -22,7 +22,12 @@ export default function ChatList(props: Props) { )); - return {listItems}; + return ( + + {listItems} + + + ); } interface MessageProps { @@ -65,3 +70,15 @@ function Message(props: MessageProps) { ); } + +const AlwaysScrollToBottom = (props: Props) => { + const elementRef = useRef(); + + useEffect(() => { + // @ts-ignore + elementRef.current.scrollIntoView(); + }, [props.messages]); + + // @ts-ignore + return
; +}; From 462569583f2f8c7e116ca971aa02fa0133247f40 Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Tue, 27 Apr 2021 16:26:32 +1000 Subject: [PATCH 11/14] Make command handling more robust --- web-chat/src/command.ts | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/web-chat/src/command.ts b/web-chat/src/command.ts index 2741b124e2..3034c686ec 100644 --- a/web-chat/src/command.ts +++ b/web-chat/src/command.ts @@ -84,7 +84,7 @@ export default function handleCommand( setNick: (nick: string) => void ): { command: string; response: string[] } { let response: string[] = []; - const args = input.split(' '); + const args = parseInput(input); const command = args.shift()!; switch (command) { case '/help': @@ -107,3 +107,8 @@ export default function handleCommand( } return { command, response }; } + +export function parseInput(input: string): string[] { + const clean = input.trim().replaceAll(/\s\s+/g, ' '); + return clean.split(' '); +} From cf732829942cd82ed4a6257cdc3988242cb0d82e Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Wed, 28 Apr 2021 09:53:33 +1000 Subject: [PATCH 12/14] Add instructions on how to run web app --- README.md | 24 +++++++++++++++++++++++- 1 file changed, 23 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index c76c48551d..ba0ad9019b 100644 --- a/README.md +++ b/README.md @@ -34,7 +34,29 @@ For support, questions & more general topics, please join the discussion on the ## Examples -## Chat app +## Web Chat App (ReactJS) + +A ReactJS web app is provided as an a show case of the library used in the browser. + +A deployed version is available at https://status-im.github.io/js-waku/ +Do note that due to some technical restrictions, it does not currently work out-of-the-box. +If you wish to try it out, follow the instructions on the [Vac forum](status-im.github.io/js-waku/). +It is currently unstable and likely to break. + +To run a development version locally, do: + +```shell +git clone https://github.com/status-im/js-waku/ ; cd js-waku +npm install +npm run build +cd web-chat +npm install +npm run start +``` + +Then, you can use `/help` to change your nick and connect to a server. + +## CLI Chat App (NodeJS) A node chat app is provided as a working example of the library. It is interoperable with the [nim-waku chat app example](https://github.com/status-im/nim-waku/blob/master/examples/v2/chat2.nim). From 8b87e50b5162391ebe3ba0d3092f7dc65a1a7dc8 Mon Sep 17 00:00:00 2001 From: Franck Royer Date: Wed, 28 Apr 2021 10:46:44 +1000 Subject: [PATCH 13/14] Fix all scrolling issues --- web-chat/src/MessageInput.tsx | 6 ++---- web-chat/src/Room.tsx | 9 ++++++--- 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/web-chat/src/MessageInput.tsx b/web-chat/src/MessageInput.tsx index fda34fc022..e8ba597ef4 100644 --- a/web-chat/src/MessageInput.tsx +++ b/web-chat/src/MessageInput.tsx @@ -30,15 +30,13 @@ export default function MessageInput(props: Props) { }; return ( - + -
+
-
+
Date: Mon, 26 Apr 2021 20:34:11 +1000 Subject: [PATCH 14/14] Automatically add new issues to board --- .github/workflows/add-action-project.yml | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) create mode 100644 .github/workflows/add-action-project.yml diff --git a/.github/workflows/add-action-project.yml b/.github/workflows/add-action-project.yml new file mode 100644 index 0000000000..a33e8d954b --- /dev/null +++ b/.github/workflows/add-action-project.yml @@ -0,0 +1,16 @@ +on: + issues: + types: opened + +jobs: + assign_issue_to_project: + runs-on: ubuntu-latest + name: Assign new issue to project + steps: + - name: Create new project card with issue + id: list + uses: qmacro/action-add-issue-to-project-column@v1 + with: + token: ${{ secrets.GITHUB_TOKEN }} + project: 'js-waku' + column: 'New'