diff --git a/app/lib/components/Chat/FileChatEntry.jsx b/app/lib/components/Chat/FileChatEntry.jsx index a0890ba..b36cf72 100644 --- a/app/lib/components/Chat/FileChatEntry.jsx +++ b/app/lib/components/Chat/FileChatEntry.jsx @@ -28,36 +28,63 @@ class FileChatEntry extends Component }); }; + handleTorrent = (torrent) => + { + // Torrent already done, this can happen if the + // same file was sent multiple times. + if (torrent.progress === 1) + { + this.setState({ + files: torrent.files, + numPeers: torrent.numPeers, + progress: 1, + active: false + }); + + return; + } + + const onProgress = () => + { + this.setState({ + numPeers : torrent.numPeers, + progress : torrent.progress + }); + }; + + onProgress(); + + setInterval(onProgress, 500); + + torrent.on('done', () => + { + onProgress(); + clearInterval(onProgress); + + this.setState({ + files : torrent.files, + active: false + }); + }); + }; + download = () => { this.setState({ active : true }); + + const magnet = this.props.message.file.magnet; - client.add(this.props.message.file.magnet, (torrent) => + const existingTorrent = client.get(magnet); + + if (existingTorrent) { - const onProgress = () => - { - this.setState({ - numPeers : torrent.numPeers, - progress : torrent.progress - }); - }; + // Never add duplicate torrents, use the existing one instead. + return this.handleTorrent(existingTorrent); + } - setInterval(onProgress, 500); - onProgress(); - - torrent.on('done', () => - { - onProgress(); - clearInterval(onProgress); - - this.setState({ - files : torrent.files, - active: false - }); - }); - }); + client.add(magnet, this.handleTorrent); } render() diff --git a/app/lib/components/Chat/FileSharing.jsx b/app/lib/components/Chat/FileSharing.jsx index 60bd479..f2b248a 100644 --- a/app/lib/components/Chat/FileSharing.jsx +++ b/app/lib/components/Chat/FileSharing.jsx @@ -1,9 +1,11 @@ import React, { Component } from 'react'; import WebTorrent from 'webtorrent'; +import createTorrent from 'create-torrent'; import dragDrop from 'drag-drop'; import * as stateActions from '../../redux/stateActions'; import * as requestActions from '../../redux/requestActions'; import { store } from '../../store'; +import { promisify } from 'util'; export const client = new WebTorrent(); @@ -15,17 +17,35 @@ const notifyPeers = (file) => store.dispatch(requestActions.sendChatFile(file, displayName, picture)); }; -const shareFiles = (files) => +const shareFiles = async (files) => { - client.seed(files, (torrent) => + createTorrent(files, (err, torrent) => { - notifyPeers({ - magnet : torrent.magnetURI + if (err) + { + console.error('Error creating torrent', err); + return; + } + + const existingTorrent = client.get(torrent); + + if (existingTorrent) + { + return notifyPeers({ + magnet: existingTorrent.magnetURI + }); + } + + client.seed(files, (newTorrent) => + { + notifyPeers({ + magnet : newTorrent.magnetURI + }); }); }); }; -dragDrop('body', shareFiles); +dragDrop('body', async (files) => await shareFiles(files)); class FileSharing extends Component { @@ -36,11 +56,11 @@ class FileSharing extends Component this.fileInput = React.createRef(); } - handleFileChange = (event) => + handleFileChange = async (event) => { if (event.target.files.length > 0) { - shareFiles(event.target.files); + await shareFiles(event.target.files); } }; diff --git a/app/package-lock.json b/app/package-lock.json index 73e9b4b..f40b840 100644 --- a/app/package-lock.json +++ b/app/package-lock.json @@ -3109,9 +3109,9 @@ } }, "create-torrent": { - "version": "3.32.0", - "resolved": "https://registry.npmjs.org/create-torrent/-/create-torrent-3.32.0.tgz", - "integrity": "sha512-l9chXj5LLyVFfPF6nFCWlm5/Wt+04d+mXUpG5LJAogeyRruWfjnUozfmQspAi6iW91ibp7qKBuFMPJViz5lp1Q==", + "version": "3.32.1", + "resolved": "https://registry.npmjs.org/create-torrent/-/create-torrent-3.32.1.tgz", + "integrity": "sha512-8spZUeFyVc+2mGnWBRTuLOhuHmHrmUomFWf7QvxztCEvTpn5SIrvF8F+HKdkzBPM9B7v/2w+f/65jqLWBXSndg==", "requires": { "bencode": "^2.0.0", "block-stream2": "^1.0.0", diff --git a/app/package.json b/app/package.json index 2a2dda2..45fb090 100644 --- a/app/package.json +++ b/app/package.json @@ -9,6 +9,7 @@ "dependencies": { "babel-runtime": "^6.26.0", "classnames": "^2.2.6", + "create-torrent": "^3.32.1", "debug": "^3.1.0", "domready": "^1.0.8", "drag-drop": "^4.2.0",