forked from Github/ocrcc-chatbox
trying ot get the images to load
This commit is contained in:
parent
47d546a8d4
commit
d8e482a689
@ -116,6 +116,8 @@
|
||||
"webpack-serve": "3.2.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"browser-encrypt-attachment": "^0.3.0",
|
||||
"isomorphic-fetch": "^2.2.1",
|
||||
"linkifyjs": "^2.1.9",
|
||||
"matrix-js-sdk": "^4.0.0",
|
||||
"node-localstorage": "^2.1.5",
|
||||
|
@ -341,8 +341,11 @@ class ChatBox extends React.Component {
|
||||
sender: event.getSender(),
|
||||
roomId: event.getRoomId(),
|
||||
content: event.getContent(),
|
||||
|
||||
}
|
||||
|
||||
console.log('message ===========>', message)
|
||||
|
||||
const messages = [...this.state.messages]
|
||||
messages.push(message)
|
||||
this.setState({ messages })
|
||||
@ -479,7 +482,7 @@ class ChatBox extends React.Component {
|
||||
{
|
||||
messages.map((message, index) => {
|
||||
return(
|
||||
<Message key={message.id} message={message} userId={userId} botId={this.props.botUsername} />
|
||||
<Message key={message.id} message={message} userId={userId} botId={this.props.botUsername} client={this.state.client} />
|
||||
)
|
||||
})
|
||||
}
|
||||
|
@ -1,44 +1,113 @@
|
||||
import React from "react"
|
||||
import PropTypes from "prop-types"
|
||||
import Linkify from 'linkifyjs/react';
|
||||
import decryptFile from '../utils/decryptFile'
|
||||
|
||||
const Message = ({ message, userId, botId }) => {
|
||||
|
||||
const senderClass = () => {
|
||||
switch (message.sender) {
|
||||
class Message extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.state = {
|
||||
decryptedUrl: null,
|
||||
decryptedFile: null,
|
||||
}
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
const needsDecryption = ['m.file', 'm.image'];
|
||||
if (needsDecryption.includes(this.props.message.content.msgtype)) {
|
||||
decryptFile(this.props.message.content.file, this.props.client)
|
||||
.then((decryptedBlob) => {
|
||||
const decryptedUrl = URL.createObjectURL(decryptedBlob)
|
||||
this.setState({
|
||||
decryptedUrl: decryptedUrl,
|
||||
decryptedBlob: decryptedBlob
|
||||
})
|
||||
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
componentWillUnmount() {
|
||||
if (this.state.decryptedUrl) {
|
||||
URL.revokeObjectURL(this.state.decryptedUrl);
|
||||
}
|
||||
}
|
||||
|
||||
senderClass = () => {
|
||||
switch (this.props.message.sender) {
|
||||
case 'from-me':
|
||||
return 'from-me'
|
||||
case userId:
|
||||
case this.props.userId:
|
||||
return 'from-me'
|
||||
case botId:
|
||||
case this.props.botId:
|
||||
return 'from-bot'
|
||||
default:
|
||||
return 'from-support'
|
||||
}
|
||||
}
|
||||
|
||||
renderTextMessage = () => {
|
||||
const linkifyOpts = {
|
||||
linkAttributes: {
|
||||
rel: 'noreferrer noopener',
|
||||
},
|
||||
}
|
||||
|
||||
if (message.content.formatted_body) {
|
||||
return (
|
||||
<div className={`message ${senderClass()}`}>
|
||||
<div className="text" dangerouslySetInnerHTML={{__html: message.content.formatted_body}} />
|
||||
<div className={`message ${this.senderClass()}`}>
|
||||
<div className="text">
|
||||
<Linkify options={linkifyOpts}>{ this.props.message.content.body }</Linkify>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
const linkifyOpts = {
|
||||
linkAttributes: {
|
||||
rel: 'noreferrer noopener',
|
||||
},
|
||||
renderHtmlMessage = () => {
|
||||
return (
|
||||
<div className={`message ${this.senderClass()}`}>
|
||||
<div className="text" dangerouslySetInnerHTML={{__html: this.props.message.content.formatted_body}} />
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
return (
|
||||
<div className={`message ${senderClass()}`}>
|
||||
<div className="text">
|
||||
<Linkify options={linkifyOpts}>{ message.content.body }</Linkify>
|
||||
renderImageMessage = () => {
|
||||
return (
|
||||
<div className={`message ${this.senderClass()}`}>
|
||||
<div className="text">
|
||||
<a href={this.state.decryptedUrl} target='_blank' rel='noopener noreferrer'>{ this.props.message.content.body }</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
renderFileMessage = () => {
|
||||
return (
|
||||
<div className={`message ${this.senderClass()}`}>
|
||||
<div className="text">
|
||||
<a href={this.state.decryptedUrl} target='_blank' rel='noopener noreferrer'>{ this.props.message.content.body }</a>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
render() {
|
||||
console.log(this.props.message)
|
||||
console.log(this.state)
|
||||
const { message } = this.props;
|
||||
|
||||
switch(message.content.msgtype) {
|
||||
case 'm.file':
|
||||
return this.renderFileMessage()
|
||||
case 'm.image':
|
||||
return this.renderImageMessage()
|
||||
default:
|
||||
if (message.content.formatted_body) {
|
||||
return this.renderHtmlMessage()
|
||||
}
|
||||
return this.renderTextMessage()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export default Message;
|
@ -1,30 +0,0 @@
|
||||
function checkFunc(dom, selector) {
|
||||
if (typeof dom.update === 'function') {
|
||||
const el = dom.update().find(selector);
|
||||
if (el.exists()) {
|
||||
return el;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
const els = dom.querySelectorAll(selector);
|
||||
if (els.length !== 0) {
|
||||
return els;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
export async function waitForSelection(dom, selector) {
|
||||
let numSleep = 0;
|
||||
for (;;) {
|
||||
const el = checkFunc(dom, selector);
|
||||
if (el) {
|
||||
return el;
|
||||
}
|
||||
if (numSleep > 2) {
|
||||
throw new Error(`could not find ${selector}`);
|
||||
}
|
||||
await new Promise(resolve => setTimeout(resolve, 250));
|
||||
numSleep += 1;
|
||||
}
|
||||
}
|
46
src/utils/decryptFile.js
Normal file
46
src/utils/decryptFile.js
Normal file
@ -0,0 +1,46 @@
|
||||
import encrypt from 'browser-encrypt-attachment';
|
||||
import 'isomorphic-fetch';
|
||||
|
||||
const ALLOWED_BLOB_MIMETYPES = {
|
||||
'image/jpeg': true,
|
||||
'image/gif': true,
|
||||
'image/png': true,
|
||||
|
||||
'video/mp4': true,
|
||||
'video/webm': true,
|
||||
'video/ogg': true,
|
||||
|
||||
'audio/mp4': true,
|
||||
'audio/webm': true,
|
||||
'audio/aac': true,
|
||||
'audio/mpeg': true,
|
||||
'audio/ogg': true,
|
||||
'audio/wave': true,
|
||||
'audio/wav': true,
|
||||
'audio/x-wav': true,
|
||||
'audio/x-pn-wav': true,
|
||||
'audio/flac': true,
|
||||
'audio/x-flac': true,
|
||||
};
|
||||
|
||||
const decryptFile = (file, client) => {
|
||||
const url = client.mxcUrlToHttp(file.url);
|
||||
// Download the encrypted file as an array buffer.
|
||||
return Promise.resolve(fetch(url))
|
||||
.then((response) => response.arrayBuffer())
|
||||
.then((responseData) => encrypt.decryptAttachment(responseData, file))
|
||||
.then((dataArray) => {
|
||||
// IMPORTANT: we must not allow scriptable mime-types into Blobs otherwise
|
||||
// they introduce XSS attacks if the Blob URI is viewed directly in the
|
||||
// browser (e.g. by copying the URI into a new tab or window.)
|
||||
let mimetype = file.mimetype ? file.mimetype.split(';')[0].trim() : '';
|
||||
if (!ALLOWED_BLOB_MIMETYPES[mimetype]) {
|
||||
mimetype = 'application/octet-stream';
|
||||
}
|
||||
|
||||
const blob = new Blob([dataArray], { type: mimetype });
|
||||
return blob;
|
||||
});
|
||||
};
|
||||
|
||||
export default decryptFile;
|
37
yarn.lock
37
yarn.lock
@ -3237,6 +3237,11 @@ brorand@^1.0.1:
|
||||
resolved "https://registry.yarnpkg.com/brorand/-/brorand-1.1.0.tgz#12c25efe40a45e3c323eb8675a0a0ce57b22371f"
|
||||
integrity sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=
|
||||
|
||||
browser-encrypt-attachment@^0.3.0:
|
||||
version "0.3.0"
|
||||
resolved "https://registry.yarnpkg.com/browser-encrypt-attachment/-/browser-encrypt-attachment-0.3.0.tgz#205a94caadf0dc7e81413941812f655bd190ff1c"
|
||||
integrity sha1-IFqUyq3w3H6BQTlBgS9lW9GQ/xw=
|
||||
|
||||
browser-process-hrtime@^0.1.2:
|
||||
version "0.1.3"
|
||||
resolved "https://registry.yarnpkg.com/browser-process-hrtime/-/browser-process-hrtime-0.1.3.tgz#616f00faef1df7ec1b5bf9cfe2bdc3170f26c7b4"
|
||||
@ -4789,6 +4794,13 @@ encodeurl@^1.0.2, encodeurl@~1.0.2:
|
||||
resolved "https://registry.yarnpkg.com/encodeurl/-/encodeurl-1.0.2.tgz#ad3ff4c86ec2d029322f5a02c3a9a606c95b3f59"
|
||||
integrity sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=
|
||||
|
||||
encoding@^0.1.11:
|
||||
version "0.1.12"
|
||||
resolved "https://registry.yarnpkg.com/encoding/-/encoding-0.1.12.tgz#538b66f3ee62cd1ab51ec323829d1f9480c74beb"
|
||||
integrity sha1-U4tm8+5izRq1HsMjgp0flIDHS+s=
|
||||
dependencies:
|
||||
iconv-lite "~0.4.13"
|
||||
|
||||
end-of-stream@^1.0.0, end-of-stream@^1.1.0:
|
||||
version "1.4.4"
|
||||
resolved "https://registry.yarnpkg.com/end-of-stream/-/end-of-stream-1.4.4.tgz#5ae64a5f45057baf3626ec14da0ca5e4b2431eb0"
|
||||
@ -6492,7 +6504,7 @@ humanize-url@^1.0.0:
|
||||
normalize-url "^1.0.0"
|
||||
strip-url-auth "^1.0.0"
|
||||
|
||||
iconv-lite@0.4.24, iconv-lite@^0.4.24:
|
||||
iconv-lite@0.4.24, iconv-lite@^0.4.24, iconv-lite@~0.4.13:
|
||||
version "0.4.24"
|
||||
resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b"
|
||||
integrity sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==
|
||||
@ -7051,7 +7063,7 @@ is-set@^2.0.1:
|
||||
resolved "https://registry.yarnpkg.com/is-set/-/is-set-2.0.1.tgz#d1604afdab1724986d30091575f54945da7e5f43"
|
||||
integrity sha512-eJEzOtVyenDs1TMzSQ3kU3K+E0GUS9sno+F0OBT97xsgcJsF9nXMBtkT9/kut5JEpM7oL7X/0qxR17K3mcwIAA==
|
||||
|
||||
is-stream@^1.1.0:
|
||||
is-stream@^1.0.1, is-stream@^1.1.0:
|
||||
version "1.1.0"
|
||||
resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-1.1.0.tgz#12d4a3dd4e68e0b79ceb8dbc84173ae80d91ca44"
|
||||
integrity sha1-EtSj3U5o4Lec6428hBc66A2RykQ=
|
||||
@ -7140,6 +7152,14 @@ isobject@^4.0.0:
|
||||
resolved "https://registry.yarnpkg.com/isobject/-/isobject-4.0.0.tgz#3f1c9155e73b192022a80819bacd0343711697b0"
|
||||
integrity sha512-S/2fF5wH8SJA/kmwr6HYhK/RI/OkhD84k8ntalo0iJjZikgq1XFvR5M8NPT1x5F7fBwCG3qHfnzeP/Vh/ZxCUA==
|
||||
|
||||
isomorphic-fetch@^2.2.1:
|
||||
version "2.2.1"
|
||||
resolved "https://registry.yarnpkg.com/isomorphic-fetch/-/isomorphic-fetch-2.2.1.tgz#611ae1acf14f5e81f729507472819fe9733558a9"
|
||||
integrity sha1-YRrhrPFPXoH3KVB0coGf6XM1WKk=
|
||||
dependencies:
|
||||
node-fetch "^1.0.1"
|
||||
whatwg-fetch ">=0.10.0"
|
||||
|
||||
isstream@~0.1.2:
|
||||
version "0.1.2"
|
||||
resolved "https://registry.yarnpkg.com/isstream/-/isstream-0.1.2.tgz#47e63f7af55afa6f92e1500e690eb8b8529c099a"
|
||||
@ -8653,6 +8673,14 @@ node-dir@^0.1.10:
|
||||
dependencies:
|
||||
minimatch "^3.0.2"
|
||||
|
||||
node-fetch@^1.0.1:
|
||||
version "1.7.3"
|
||||
resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-1.7.3.tgz#980f6f72d85211a5347c6b2bc18c5b84c3eb47ef"
|
||||
integrity sha512-NhZ4CsKx7cYm2vSrBAr2PvFOe6sWDf0UYLRqA6svUYg7+/TSfVAu49jYC4BvQ4Sms9SZgdqGBgroqfDhJdTyKQ==
|
||||
dependencies:
|
||||
encoding "^0.1.11"
|
||||
is-stream "^1.0.1"
|
||||
|
||||
node-fetch@^2.3.0, node-fetch@^2.6.0:
|
||||
version "2.6.0"
|
||||
resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.0.tgz#e633456386d4aa55863f676a7ab0daa8fdecb0fd"
|
||||
@ -12408,6 +12436,11 @@ whatwg-encoding@^1.0.1, whatwg-encoding@^1.0.3:
|
||||
dependencies:
|
||||
iconv-lite "0.4.24"
|
||||
|
||||
whatwg-fetch@>=0.10.0:
|
||||
version "3.0.0"
|
||||
resolved "https://registry.yarnpkg.com/whatwg-fetch/-/whatwg-fetch-3.0.0.tgz#fc804e458cc460009b1a2b966bc8817d2578aefb"
|
||||
integrity sha512-9GSJUgz1D4MfyKU7KRqwOjXCXTqWdFNvEr7eUBYchQiVc744mqK/MzXPNR2WsPkmkOa4ywfg8C2n8h+13Bey1Q==
|
||||
|
||||
whatwg-mimetype@^2.1.0, whatwg-mimetype@^2.2.0:
|
||||
version "2.3.0"
|
||||
resolved "https://registry.yarnpkg.com/whatwg-mimetype/-/whatwg-mimetype-2.3.0.tgz#3d4b1e0312d2079879f826aff18dbeeca5960fbf"
|
||||
|
Loading…
Reference in New Issue
Block a user