Add file uploading support
Co-Authored-By: Max Leiter <hello@maxleiter.com> Co-Authored-By: Jérémie Astori <astorije@users.noreply.github.com>
This commit is contained in:
parent
7c12883dc1
commit
ce212e001c
@ -242,6 +242,7 @@ kbd {
|
|||||||
#settings .extra-experimental,
|
#settings .extra-experimental,
|
||||||
#settings .extra-help,
|
#settings .extra-help,
|
||||||
#settings #play::before,
|
#settings #play::before,
|
||||||
|
#form #upload::before,
|
||||||
#form #submit::before,
|
#form #submit::before,
|
||||||
#chat .away .from::before,
|
#chat .away .from::before,
|
||||||
#chat .back .from::before,
|
#chat .back .from::before,
|
||||||
@ -315,6 +316,7 @@ kbd {
|
|||||||
#footer .settings::before { content: "\f013"; /* http://fontawesome.io/icon/cog/ */ }
|
#footer .settings::before { content: "\f013"; /* http://fontawesome.io/icon/cog/ */ }
|
||||||
#footer .help::before { content: "\f059"; /* http://fontawesome.io/icon/question/ */ }
|
#footer .help::before { content: "\f059"; /* http://fontawesome.io/icon/question/ */ }
|
||||||
|
|
||||||
|
#form #upload::before { content: "\f0c6"; /* https://fontawesome.com/icons/paperclip?style=solid */ }
|
||||||
#form #submit::before { content: "\f1d8"; /* http://fontawesome.io/icon/paper-plane/ */ }
|
#form #submit::before { content: "\f1d8"; /* http://fontawesome.io/icon/paper-plane/ */ }
|
||||||
|
|
||||||
#chat .away .from::before,
|
#chat .away .from::before,
|
||||||
@ -1930,6 +1932,12 @@ part/quit messages where we don't load previews (adds a blank line otherwise) */
|
|||||||
content: "\f00c"; /* http://fontawesome.io/icon/check/ */
|
content: "\f00c"; /* http://fontawesome.io/icon/check/ */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#upload-progressbar {
|
||||||
|
background: blue;
|
||||||
|
width: 0%;
|
||||||
|
height: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
#form {
|
#form {
|
||||||
flex: 0 0 auto;
|
flex: 0 0 auto;
|
||||||
border: 0;
|
border: 0;
|
||||||
@ -1957,6 +1965,7 @@ part/quit messages where we don't load previews (adds a blank line otherwise) */
|
|||||||
|
|
||||||
#connection-error.shown {
|
#connection-error.shown {
|
||||||
display: block;
|
display: block;
|
||||||
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
|
||||||
#form #nick {
|
#form #nick {
|
||||||
@ -1991,6 +2000,11 @@ part/quit messages where we don't load previews (adds a blank line otherwise) */
|
|||||||
touch-action: pan-y;
|
touch-action: pan-y;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#form #upload-input {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
#form #upload,
|
||||||
#form #submit {
|
#form #submit {
|
||||||
color: #607992;
|
color: #607992;
|
||||||
font-size: 14px;
|
font-size: 14px;
|
||||||
@ -2519,8 +2533,9 @@ part/quit messages where we don't load previews (adds a blank line otherwise) */
|
|||||||
background: rgba(0, 0, 0, 0.6);
|
background: rgba(0, 0, 0, 0.6);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Image viewer */
|
/* Image viewer and drag-and-drop overlay */
|
||||||
|
|
||||||
|
#upload-overlay,
|
||||||
#image-viewer,
|
#image-viewer,
|
||||||
#image-viewer .close-btn {
|
#image-viewer .close-btn {
|
||||||
/* Vertically and horizontally center stuff */
|
/* Vertically and horizontally center stuff */
|
||||||
@ -2530,6 +2545,7 @@ part/quit messages where we don't load previews (adds a blank line otherwise) */
|
|||||||
justify-content: center;
|
justify-content: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#upload-overlay,
|
||||||
#image-viewer {
|
#image-viewer {
|
||||||
position: fixed;
|
position: fixed;
|
||||||
top: 0;
|
top: 0;
|
||||||
@ -2548,6 +2564,11 @@ part/quit messages where we don't load previews (adds a blank line otherwise) */
|
|||||||
opacity: 1;
|
opacity: 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#upload-overlay.is-dragover {
|
||||||
|
visibility: visible;
|
||||||
|
opacity: 0.3;
|
||||||
|
}
|
||||||
|
|
||||||
#image-viewer .close-btn,
|
#image-viewer .close-btn,
|
||||||
#image-viewer .previous-image-btn,
|
#image-viewer .previous-image-btn,
|
||||||
#image-viewer .next-image-btn {
|
#image-viewer .next-image-btn {
|
||||||
|
@ -84,9 +84,14 @@
|
|||||||
<div id="chat-container" class="window">
|
<div id="chat-container" class="window">
|
||||||
<div id="chat"></div>
|
<div id="chat"></div>
|
||||||
<div id="connection-error"></div>
|
<div id="connection-error"></div>
|
||||||
|
<span id="upload-progressbar"></span>
|
||||||
<form id="form" method="post" action="">
|
<form id="form" method="post" action="">
|
||||||
<span id="nick"></span>
|
<span id="nick"></span>
|
||||||
<textarea id="input" class="mousetrap"></textarea>
|
<textarea id="input" class="mousetrap"></textarea>
|
||||||
|
<span id="upload-tooltip" class="tooltipped tooltipped-w tooltipped-no-touch" aria-label="Upload File">
|
||||||
|
<input id="upload-input" type="file" multiple></button>
|
||||||
|
<button id="upload" type="button" aria-label="Upload file"></button>
|
||||||
|
</span>
|
||||||
<span id="submit-tooltip" class="tooltipped tooltipped-w tooltipped-no-touch" aria-label="Send message">
|
<span id="submit-tooltip" class="tooltipped tooltipped-w tooltipped-no-touch" aria-label="Send message">
|
||||||
<button id="submit" type="submit" aria-label="Send message"></button>
|
<button id="submit" type="submit" aria-label="Send message"></button>
|
||||||
</span>
|
</span>
|
||||||
@ -102,6 +107,7 @@
|
|||||||
|
|
||||||
<div id="context-menu-container"></div>
|
<div id="context-menu-container"></div>
|
||||||
<div id="image-viewer"></div>
|
<div id="image-viewer"></div>
|
||||||
|
<div id="upload-overlay"></div>
|
||||||
|
|
||||||
<script src="js/bundle.vendor.js"></script>
|
<script src="js/bundle.vendor.js"></script>
|
||||||
<script src="js/bundle.js"></script>
|
<script src="js/bundle.js"></script>
|
||||||
|
@ -7,6 +7,7 @@ const options = require("../options");
|
|||||||
const webpush = require("../webpush");
|
const webpush = require("../webpush");
|
||||||
const connect = $("#connect");
|
const connect = $("#connect");
|
||||||
const utils = require("../utils");
|
const utils = require("../utils");
|
||||||
|
const upload = require("../upload");
|
||||||
|
|
||||||
window.addEventListener("beforeinstallprompt", (installPromptEvent) => {
|
window.addEventListener("beforeinstallprompt", (installPromptEvent) => {
|
||||||
$("#webapp-install-button")
|
$("#webapp-install-button")
|
||||||
@ -23,6 +24,12 @@ window.addEventListener("beforeinstallprompt", (installPromptEvent) => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
socket.on("configuration", function(data) {
|
socket.on("configuration", function(data) {
|
||||||
|
if (data.fileUpload) {
|
||||||
|
$("#upload").show();
|
||||||
|
} else {
|
||||||
|
$("#upload").hide();
|
||||||
|
}
|
||||||
|
|
||||||
if (options.initialized) {
|
if (options.initialized) {
|
||||||
// Likely a reconnect, request sync for possibly missed settings.
|
// Likely a reconnect, request sync for possibly missed settings.
|
||||||
socket.emit("setting:get");
|
socket.emit("setting:get");
|
||||||
@ -44,6 +51,11 @@ socket.on("configuration", function(data) {
|
|||||||
pop.play();
|
pop.play();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
if (data.fileUpload) {
|
||||||
|
upload.initialize();
|
||||||
|
upload.setMaxFileSize(data.fileUploadMaxFileSize);
|
||||||
|
}
|
||||||
|
|
||||||
utils.togglePasswordField("#change-password .reveal-password");
|
utils.togglePasswordField("#change-password .reveal-password");
|
||||||
|
|
||||||
options.initialize();
|
options.initialize();
|
||||||
|
@ -15,6 +15,7 @@ require("./part");
|
|||||||
require("./quit");
|
require("./quit");
|
||||||
require("./sync_sort");
|
require("./sync_sort");
|
||||||
require("./topic");
|
require("./topic");
|
||||||
|
require("./uploads");
|
||||||
require("./users");
|
require("./users");
|
||||||
require("./sign_out");
|
require("./sign_out");
|
||||||
require("./sessions_list");
|
require("./sessions_list");
|
||||||
|
10
client/js/socket-events/uploads.js
Normal file
10
client/js/socket-events/uploads.js
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
"use strict";
|
||||||
|
|
||||||
|
const socket = require("../socket");
|
||||||
|
const wrapCursor = require("undate").wrapCursor;
|
||||||
|
|
||||||
|
socket.on("upload:success", (url) => {
|
||||||
|
const fullURL = new URL(url, location);
|
||||||
|
const textbox = document.getElementById("input");
|
||||||
|
wrapCursor(textbox, fullURL, " ");
|
||||||
|
});
|
@ -11,6 +11,10 @@ const socket = io({
|
|||||||
reconnection: !$(document.body).hasClass("public"),
|
reconnection: !$(document.body).hasClass("public"),
|
||||||
});
|
});
|
||||||
|
|
||||||
|
$("#connection-error").on("click", function() {
|
||||||
|
$(this).removeClass("shown");
|
||||||
|
});
|
||||||
|
|
||||||
socket.on("disconnect", handleDisconnect);
|
socket.on("disconnect", handleDisconnect);
|
||||||
socket.on("connect_error", handleDisconnect);
|
socket.on("connect_error", handleDisconnect);
|
||||||
socket.on("error", handleDisconnect);
|
socket.on("error", handleDisconnect);
|
||||||
@ -42,6 +46,7 @@ function handleDisconnect(data) {
|
|||||||
$("#loading-page-message, #connection-error").text(`Waiting to reconnect… (${message})`).addClass("shown");
|
$("#loading-page-message, #connection-error").text(`Waiting to reconnect… (${message})`).addClass("shown");
|
||||||
$(".show-more button, #input").prop("disabled", true);
|
$(".show-more button, #input").prop("disabled", true);
|
||||||
$("#submit").hide();
|
$("#submit").hide();
|
||||||
|
$("#upload").hide();
|
||||||
|
|
||||||
// If the server shuts down, socket.io skips reconnection
|
// If the server shuts down, socket.io skips reconnection
|
||||||
// and we have to manually call connect to start the process
|
// and we have to manually call connect to start the process
|
||||||
|
54
client/js/upload.js
Normal file
54
client/js/upload.js
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
"use strict";
|
||||||
|
|
||||||
|
const $ = require("jquery");
|
||||||
|
const socket = require("./socket");
|
||||||
|
const SocketIOFileUpload = require("socketio-file-upload/client");
|
||||||
|
const instance = new SocketIOFileUpload(socket);
|
||||||
|
|
||||||
|
function initialize() {
|
||||||
|
instance.listenOnInput(document.getElementById("upload-input"));
|
||||||
|
instance.listenOnDrop(document);
|
||||||
|
|
||||||
|
$("#upload").on("click", () => {
|
||||||
|
$("#upload-input").trigger("click");
|
||||||
|
});
|
||||||
|
|
||||||
|
instance.addEventListener("complete", () => {
|
||||||
|
// Reset progressbar
|
||||||
|
$("#upload-progressbar").width(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
instance.addEventListener("progress", (event) => {
|
||||||
|
const percent = `${((event.bytesLoaded / event.file.size) * 100)}%`;
|
||||||
|
$("#upload-progressbar").width(percent);
|
||||||
|
});
|
||||||
|
|
||||||
|
instance.addEventListener("error", (event) => {
|
||||||
|
// Reset progressbar
|
||||||
|
$("#upload-progressbar").width(0);
|
||||||
|
$("#connection-error").addClass("shown").text(event.message);
|
||||||
|
});
|
||||||
|
|
||||||
|
const $form = $(document);
|
||||||
|
const $overlay = $("#upload-overlay");
|
||||||
|
|
||||||
|
$form.on("dragover", () => {
|
||||||
|
$overlay.addClass("is-dragover");
|
||||||
|
return false;
|
||||||
|
});
|
||||||
|
|
||||||
|
$form.on("dragend dragleave drop", () => {
|
||||||
|
$overlay.removeClass("is-dragover");
|
||||||
|
return false;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called in the `configuration` socket event.
|
||||||
|
* Makes it so the user can be notified if a file is too large without waiting for the upload to finish server-side.
|
||||||
|
**/
|
||||||
|
function setMaxFileSize(kb) {
|
||||||
|
instance.maxFileSize = kb;
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = {initialize, setMaxFileSize};
|
@ -139,6 +139,27 @@ module.exports = {
|
|||||||
// This value is set to `2048` kilobytes by default.
|
// This value is set to `2048` kilobytes by default.
|
||||||
prefetchMaxImageSize: 2048,
|
prefetchMaxImageSize: 2048,
|
||||||
|
|
||||||
|
// ### `fileUpload`
|
||||||
|
//
|
||||||
|
// Allow uploading files to the server hosting The Lounge.
|
||||||
|
//
|
||||||
|
// Files are stored in the `${THELOUNGE_HOME}/uploads` folder, do not expire,
|
||||||
|
// and are not removed by The Lounge. This may cause issues depending on your
|
||||||
|
// hardware, for example in terms of disk usage.
|
||||||
|
//
|
||||||
|
// The available keys for the `fileUpload` object are:
|
||||||
|
//
|
||||||
|
// - `enable`: When set to `true`, files can be uploaded on the client with a
|
||||||
|
// drag-and-drop or using the upload dialog.
|
||||||
|
// - `maxFileSize`: When file upload is enabled, users sending files above
|
||||||
|
// this limit will be prompted an error message in their browser. A value of
|
||||||
|
// `-1` disables the file size limit and allows files of any size. **Use at
|
||||||
|
// your own risk.** This value is set to `10240` kilobytes by default.
|
||||||
|
fileUpload: {
|
||||||
|
enable: true,
|
||||||
|
maxFileSize: 10240,
|
||||||
|
},
|
||||||
|
|
||||||
// ### `transports`
|
// ### `transports`
|
||||||
//
|
//
|
||||||
// Set `socket.io` transports.
|
// Set `socket.io` transports.
|
||||||
|
@ -44,9 +44,11 @@
|
|||||||
"cheerio": "0.22.0",
|
"cheerio": "0.22.0",
|
||||||
"commander": "2.17.1",
|
"commander": "2.17.1",
|
||||||
"express": "4.16.3",
|
"express": "4.16.3",
|
||||||
|
"file-type": "9.0.0",
|
||||||
"filenamify": "2.1.0",
|
"filenamify": "2.1.0",
|
||||||
"fs-extra": "7.0.0",
|
"fs-extra": "7.0.0",
|
||||||
"irc-framework": "3.1.0",
|
"irc-framework": "3.1.0",
|
||||||
|
"is-utf8": "0.2.1",
|
||||||
"linkify-it": "2.0.3",
|
"linkify-it": "2.0.3",
|
||||||
"lodash": "4.17.10",
|
"lodash": "4.17.10",
|
||||||
"mime-types": "2.1.20",
|
"mime-types": "2.1.20",
|
||||||
@ -54,9 +56,11 @@
|
|||||||
"package-json": "5.0.0",
|
"package-json": "5.0.0",
|
||||||
"primer-tooltips": "1.5.7",
|
"primer-tooltips": "1.5.7",
|
||||||
"read": "1.0.7",
|
"read": "1.0.7",
|
||||||
|
"read-chunk": "3.0.0",
|
||||||
"request": "2.88.0",
|
"request": "2.88.0",
|
||||||
"semver": "5.5.1",
|
"semver": "5.5.1",
|
||||||
"socket.io": "2.1.1",
|
"socket.io": "2.1.1",
|
||||||
|
"socketio-file-upload": "0.6.2",
|
||||||
"thelounge-ldapjs-non-maintained-fork": "1.0.2",
|
"thelounge-ldapjs-non-maintained-fork": "1.0.2",
|
||||||
"tlds": "1.203.1",
|
"tlds": "1.203.1",
|
||||||
"ua-parser-js": "0.7.18",
|
"ua-parser-js": "0.7.18",
|
||||||
|
@ -15,6 +15,7 @@ let configPath;
|
|||||||
let usersPath;
|
let usersPath;
|
||||||
let storagePath;
|
let storagePath;
|
||||||
let packagesPath;
|
let packagesPath;
|
||||||
|
let fileUploadPath;
|
||||||
let userLogsPath;
|
let userLogsPath;
|
||||||
|
|
||||||
const Helper = {
|
const Helper = {
|
||||||
@ -25,6 +26,7 @@ const Helper = {
|
|||||||
getPackageModulePath,
|
getPackageModulePath,
|
||||||
getStoragePath,
|
getStoragePath,
|
||||||
getConfigPath,
|
getConfigPath,
|
||||||
|
getFileUploadPath,
|
||||||
getUsersPath,
|
getUsersPath,
|
||||||
getUserConfigPath,
|
getUserConfigPath,
|
||||||
getUserLogsPath,
|
getUserLogsPath,
|
||||||
@ -92,6 +94,7 @@ function setHome(newPath) {
|
|||||||
configPath = path.join(homePath, "config.js");
|
configPath = path.join(homePath, "config.js");
|
||||||
usersPath = path.join(homePath, "users");
|
usersPath = path.join(homePath, "users");
|
||||||
storagePath = path.join(homePath, "storage");
|
storagePath = path.join(homePath, "storage");
|
||||||
|
fileUploadPath = path.join(homePath, "uploads");
|
||||||
packagesPath = path.join(homePath, "packages");
|
packagesPath = path.join(homePath, "packages");
|
||||||
userLogsPath = path.join(homePath, "logs");
|
userLogsPath = path.join(homePath, "logs");
|
||||||
|
|
||||||
@ -142,6 +145,10 @@ function getConfigPath() {
|
|||||||
return configPath;
|
return configPath;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getFileUploadPath() {
|
||||||
|
return fileUploadPath;
|
||||||
|
}
|
||||||
|
|
||||||
function getUsersPath() {
|
function getUsersPath() {
|
||||||
return usersPath;
|
return usersPath;
|
||||||
}
|
}
|
||||||
|
152
src/plugins/uploader.js
Normal file
152
src/plugins/uploader.js
Normal file
@ -0,0 +1,152 @@
|
|||||||
|
"use strict";
|
||||||
|
|
||||||
|
const SocketIOFileUploadServer = require("socketio-file-upload/server");
|
||||||
|
const Helper = require("../helper");
|
||||||
|
const path = require("path");
|
||||||
|
const fsextra = require("fs-extra");
|
||||||
|
const fs = require("fs");
|
||||||
|
const fileType = require("file-type");
|
||||||
|
const readChunk = require("read-chunk");
|
||||||
|
const crypto = require("crypto");
|
||||||
|
const isUtf8 = require("is-utf8");
|
||||||
|
const log = require("../log");
|
||||||
|
|
||||||
|
const whitelist = [
|
||||||
|
"application/ogg",
|
||||||
|
"audio/midi",
|
||||||
|
"audio/mpeg",
|
||||||
|
"audio/ogg",
|
||||||
|
"audio/x-wav",
|
||||||
|
"image/bmp",
|
||||||
|
"image/gif",
|
||||||
|
"image/jpeg",
|
||||||
|
"image/png",
|
||||||
|
"image/webp",
|
||||||
|
"text/plain",
|
||||||
|
"video/mp4",
|
||||||
|
"video/ogg",
|
||||||
|
"video/webm",
|
||||||
|
];
|
||||||
|
|
||||||
|
class Uploader {
|
||||||
|
constructor(client, socket) {
|
||||||
|
const uploader = new SocketIOFileUploadServer();
|
||||||
|
const folder = path.join(Helper.getFileUploadPath(), ".tmp");
|
||||||
|
|
||||||
|
fsextra.ensureDir(folder, (err) => {
|
||||||
|
if (err) {
|
||||||
|
log.err(`Error ensuring ${folder} exists for uploads.`);
|
||||||
|
} else {
|
||||||
|
uploader.dir = folder;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
uploader.on("complete", (data) => {
|
||||||
|
handleSaving(data).then((randomName) => {
|
||||||
|
const randomFileName = randomName;
|
||||||
|
const slug = data.file.base;
|
||||||
|
const url = `uploads/${randomFileName}/${slug}`;
|
||||||
|
client.emit("upload:success", url);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
uploader.on("error", (data) => {
|
||||||
|
log.error(`Error uploading ${data.error.name}`);
|
||||||
|
log.error(data.error);
|
||||||
|
});
|
||||||
|
|
||||||
|
// maxFileSize is in bytes, but config option is passed in as KB
|
||||||
|
uploader.maxFileSize = Uploader.getMaxFileSize();
|
||||||
|
uploader.listen(socket);
|
||||||
|
|
||||||
|
// Returns Promise
|
||||||
|
function handleSaving(data) {
|
||||||
|
const tempPath = path.join(Helper.getFileUploadPath(), ".tmp", data.file.name);
|
||||||
|
let randomName, destPath;
|
||||||
|
|
||||||
|
// If file conflicts
|
||||||
|
do {
|
||||||
|
randomName = crypto.randomBytes(8).toString("hex");
|
||||||
|
destPath = path.join(Helper.getFileUploadPath(), randomName.substring(0, 2), randomName);
|
||||||
|
} while (fs.stat(destPath, (err) => (err ? true : false)));
|
||||||
|
|
||||||
|
return fsextra.move(tempPath, destPath)
|
||||||
|
.then(() => randomName).catch(() => {
|
||||||
|
log.warn(`Unable to move file ${tempPath} to ${destPath}`);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static isValidType(mimeType) {
|
||||||
|
return whitelist.includes(mimeType);
|
||||||
|
}
|
||||||
|
|
||||||
|
static router(express) {
|
||||||
|
express.get("/uploads/:name/:slug*?", (req, res) => {
|
||||||
|
const name = req.params.name;
|
||||||
|
|
||||||
|
const nameRegex = /^[0-9a-f]{16}$/;
|
||||||
|
|
||||||
|
if (!nameRegex.test(name)) {
|
||||||
|
return res.status(404).send("Not found");
|
||||||
|
}
|
||||||
|
|
||||||
|
const folder = name.substring(0, 2);
|
||||||
|
const uploadPath = Helper.getFileUploadPath();
|
||||||
|
const filePath = path.join(uploadPath, folder, name);
|
||||||
|
const type = Uploader.getFileType(filePath);
|
||||||
|
const mimeType = type || "application/octet-stream";
|
||||||
|
const contentDisposition = Uploader.isValidType(type) ? "inline" : "attachment";
|
||||||
|
|
||||||
|
// doesn't exist
|
||||||
|
if (type === undefined) {
|
||||||
|
return res.status(404).send("Not found");
|
||||||
|
}
|
||||||
|
|
||||||
|
res.setHeader("Content-Disposition", contentDisposition);
|
||||||
|
res.setHeader("Cache-Control", "max-age=86400");
|
||||||
|
res.contentType(mimeType);
|
||||||
|
|
||||||
|
return res.sendFile(filePath);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
static getMaxFileSize() {
|
||||||
|
const configOption = Helper.config.fileUpload.maxFileSize;
|
||||||
|
|
||||||
|
if (configOption === -1) { // no file size limit
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
return configOption * 1024;
|
||||||
|
}
|
||||||
|
|
||||||
|
static getFileType(filePath) {
|
||||||
|
let buffer;
|
||||||
|
let type;
|
||||||
|
|
||||||
|
try {
|
||||||
|
buffer = readChunk.sync(filePath, 0, 4100);
|
||||||
|
} catch (e) {
|
||||||
|
if (e.code === "ENOENT") { // doesn't exist
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
log.warn(`Failed to read ${filePath}`);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// returns {ext, mime} if found, null if not.
|
||||||
|
const file = fileType(buffer);
|
||||||
|
|
||||||
|
if (file) {
|
||||||
|
type = file.mime;
|
||||||
|
} else if (isUtf8(buffer)) {
|
||||||
|
type = "text/plain";
|
||||||
|
}
|
||||||
|
|
||||||
|
return type;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = Uploader;
|
@ -10,6 +10,7 @@ const fs = require("fs");
|
|||||||
const path = require("path");
|
const path = require("path");
|
||||||
const io = require("socket.io");
|
const io = require("socket.io");
|
||||||
const dns = require("dns");
|
const dns = require("dns");
|
||||||
|
const Uploader = require("./plugins/uploader");
|
||||||
const Helper = require("./helper");
|
const Helper = require("./helper");
|
||||||
const colors = require("chalk");
|
const colors = require("chalk");
|
||||||
const net = require("net");
|
const net = require("net");
|
||||||
@ -51,9 +52,13 @@ module.exports = function() {
|
|||||||
.use(express.static(path.join(__dirname, "..", "public"), staticOptions))
|
.use(express.static(path.join(__dirname, "..", "public"), staticOptions))
|
||||||
.use("/storage/", express.static(Helper.getStoragePath(), staticOptions));
|
.use("/storage/", express.static(Helper.getStoragePath(), staticOptions));
|
||||||
|
|
||||||
|
if (Helper.config.fileUpload.enable) {
|
||||||
|
Uploader.router(app);
|
||||||
|
}
|
||||||
|
|
||||||
// This route serves *installed themes only*. Local themes are served directly
|
// This route serves *installed themes only*. Local themes are served directly
|
||||||
// from the `public/themes/` folder as static assets, without entering this
|
// from the `public/themes/` folder as static assets, without entering this
|
||||||
// handler. Remember this is you make changes to this function, serving of
|
// handler. Remember this if you make changes to this function, serving of
|
||||||
// local themes will not get those changes.
|
// local themes will not get those changes.
|
||||||
app.get("/themes/:theme.css", (req, res) => {
|
app.get("/themes/:theme.css", (req, res) => {
|
||||||
const themeName = req.params.theme;
|
const themeName = req.params.theme;
|
||||||
@ -284,6 +289,10 @@ function initializeClient(socket, client, token, lastMessage) {
|
|||||||
|
|
||||||
client.clientAttach(socket.id, token);
|
client.clientAttach(socket.id, token);
|
||||||
|
|
||||||
|
if (Helper.config.fileUpload.enable) {
|
||||||
|
new Uploader(client, socket);
|
||||||
|
}
|
||||||
|
|
||||||
socket.on("disconnect", function() {
|
socket.on("disconnect", function() {
|
||||||
client.clientDetach(socket.id);
|
client.clientDetach(socket.id);
|
||||||
});
|
});
|
||||||
@ -583,6 +592,7 @@ function getClientConfiguration(network) {
|
|||||||
"prefetch",
|
"prefetch",
|
||||||
]);
|
]);
|
||||||
|
|
||||||
|
config.fileUpload = Helper.config.fileUpload.enable;
|
||||||
config.ldapEnabled = Helper.config.ldap.enable;
|
config.ldapEnabled = Helper.config.ldap.enable;
|
||||||
|
|
||||||
if (config.displayNetwork) {
|
if (config.displayNetwork) {
|
||||||
@ -607,6 +617,10 @@ function getClientConfiguration(network) {
|
|||||||
config.defaults.nick = Helper.getDefaultNick();
|
config.defaults.nick = Helper.getDefaultNick();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (Uploader) {
|
||||||
|
config.fileUploadMaxFileSize = Uploader.getMaxFileSize();
|
||||||
|
}
|
||||||
|
|
||||||
return config;
|
return config;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
97
yarn.lock
97
yarn.lock
@ -1528,12 +1528,12 @@ caniuse-api@^1.5.2:
|
|||||||
lodash.uniq "^4.5.0"
|
lodash.uniq "^4.5.0"
|
||||||
|
|
||||||
caniuse-db@^1.0.30000529, caniuse-db@^1.0.30000634, caniuse-db@^1.0.30000639:
|
caniuse-db@^1.0.30000529, caniuse-db@^1.0.30000634, caniuse-db@^1.0.30000639:
|
||||||
version "1.0.30000882"
|
version "1.0.30000883"
|
||||||
resolved "https://registry.yarnpkg.com/caniuse-db/-/caniuse-db-1.0.30000882.tgz#d9d50e5189be253ffb31d347cd7f3c615b602f7f"
|
resolved "https://registry.yarnpkg.com/caniuse-db/-/caniuse-db-1.0.30000883.tgz#976f22d6a9be119b342d5ce6c7ee98fc6e0bc94a"
|
||||||
|
|
||||||
caniuse-lite@^1.0.30000878:
|
caniuse-lite@^1.0.30000878:
|
||||||
version "1.0.30000882"
|
version "1.0.30000883"
|
||||||
resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30000882.tgz#0d5066847a11a5af0e50ffce6c062ef0665f68ea"
|
resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30000883.tgz#597c1eabfb379bd9fbeaa778632762eb574706ac"
|
||||||
|
|
||||||
caseless@~0.12.0:
|
caseless@~0.12.0:
|
||||||
version "0.12.0"
|
version "0.12.0"
|
||||||
@ -1571,7 +1571,7 @@ chalk@2.4.1, chalk@^2.0.0, chalk@^2.0.1, chalk@^2.1.0, chalk@^2.3.0, chalk@^2.4.
|
|||||||
|
|
||||||
chalk@^1.1.3:
|
chalk@^1.1.3:
|
||||||
version "1.1.3"
|
version "1.1.3"
|
||||||
resolved "http://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz#a8115c55e4a702fe4d150abd3872822a7e09fc98"
|
resolved "https://registry.yarnpkg.com/chalk/-/chalk-1.1.3.tgz#a8115c55e4a702fe4d150abd3872822a7e09fc98"
|
||||||
dependencies:
|
dependencies:
|
||||||
ansi-styles "^2.2.1"
|
ansi-styles "^2.2.1"
|
||||||
escape-string-regexp "^1.0.2"
|
escape-string-regexp "^1.0.2"
|
||||||
@ -1595,9 +1595,9 @@ character-reference-invalid@^1.0.0:
|
|||||||
version "1.1.2"
|
version "1.1.2"
|
||||||
resolved "https://registry.yarnpkg.com/character-reference-invalid/-/character-reference-invalid-1.1.2.tgz#21e421ad3d84055952dab4a43a04e73cd425d3ed"
|
resolved "https://registry.yarnpkg.com/character-reference-invalid/-/character-reference-invalid-1.1.2.tgz#21e421ad3d84055952dab4a43a04e73cd425d3ed"
|
||||||
|
|
||||||
chardet@^0.5.0:
|
chardet@^0.7.0:
|
||||||
version "0.5.0"
|
version "0.7.0"
|
||||||
resolved "https://registry.yarnpkg.com/chardet/-/chardet-0.5.0.tgz#fe3ac73c00c3d865ffcc02a0682e2c20b6a06029"
|
resolved "https://registry.yarnpkg.com/chardet/-/chardet-0.7.0.tgz#90094849f0937f2eedc2425d0d28a9e5f0cbad9e"
|
||||||
|
|
||||||
check-error@^1.0.1:
|
check-error@^1.0.1:
|
||||||
version "1.0.2"
|
version "1.0.2"
|
||||||
@ -2309,8 +2309,8 @@ detect-libc@^1.0.2:
|
|||||||
resolved "https://registry.yarnpkg.com/detect-libc/-/detect-libc-1.0.3.tgz#fa137c4bd698edf55cd5cd02ac559f91a4c4ba9b"
|
resolved "https://registry.yarnpkg.com/detect-libc/-/detect-libc-1.0.3.tgz#fa137c4bd698edf55cd5cd02ac559f91a4c4ba9b"
|
||||||
|
|
||||||
detect-node@^2.0.3:
|
detect-node@^2.0.3:
|
||||||
version "2.0.3"
|
version "2.0.4"
|
||||||
resolved "https://registry.yarnpkg.com/detect-node/-/detect-node-2.0.3.tgz#a2033c09cc8e158d37748fbde7507832bd6ce127"
|
resolved "https://registry.yarnpkg.com/detect-node/-/detect-node-2.0.4.tgz#014ee8f8f669c5c58023da64b8179c083a28c46c"
|
||||||
|
|
||||||
diff@3.5.0, diff@^3.5.0:
|
diff@3.5.0, diff@^3.5.0:
|
||||||
version "3.5.0"
|
version "3.5.0"
|
||||||
@ -2434,8 +2434,8 @@ ee-first@1.1.1:
|
|||||||
resolved "https://registry.yarnpkg.com/ee-first/-/ee-first-1.1.1.tgz#590c61156b0ae2f4f0255732a158b266bc56b21d"
|
resolved "https://registry.yarnpkg.com/ee-first/-/ee-first-1.1.1.tgz#590c61156b0ae2f4f0255732a158b266bc56b21d"
|
||||||
|
|
||||||
electron-to-chromium@^1.2.7, electron-to-chromium@^1.3.61:
|
electron-to-chromium@^1.2.7, electron-to-chromium@^1.3.61:
|
||||||
version "1.3.61"
|
version "1.3.62"
|
||||||
resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.3.61.tgz#a8ac295b28d0f03d85e37326fd16b6b6b17a1795"
|
resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.3.62.tgz#2e8e2dc070c800ec8ce23ff9dfcceb585d6f9ed8"
|
||||||
|
|
||||||
elliptic@^6.0.0:
|
elliptic@^6.0.0:
|
||||||
version "6.4.1"
|
version "6.4.1"
|
||||||
@ -2667,7 +2667,7 @@ etag@~1.8.1:
|
|||||||
|
|
||||||
event-stream@~3.3.0:
|
event-stream@~3.3.0:
|
||||||
version "3.3.4"
|
version "3.3.4"
|
||||||
resolved "http://registry.npmjs.org/event-stream/-/event-stream-3.3.4.tgz#4ab4c9a0f5a54db9338b4c34d86bfce8f4b35571"
|
resolved "https://registry.yarnpkg.com/event-stream/-/event-stream-3.3.4.tgz#4ab4c9a0f5a54db9338b4c34d86bfce8f4b35571"
|
||||||
dependencies:
|
dependencies:
|
||||||
duplexer "~0.1.1"
|
duplexer "~0.1.1"
|
||||||
from "~0"
|
from "~0"
|
||||||
@ -2809,11 +2809,11 @@ extend@^3.0.0, extend@~3.0.2:
|
|||||||
resolved "https://registry.yarnpkg.com/extend/-/extend-3.0.2.tgz#f8b1136b4071fbd8eb140aff858b1019ec2915fa"
|
resolved "https://registry.yarnpkg.com/extend/-/extend-3.0.2.tgz#f8b1136b4071fbd8eb140aff858b1019ec2915fa"
|
||||||
|
|
||||||
external-editor@^3.0.0:
|
external-editor@^3.0.0:
|
||||||
version "3.0.1"
|
version "3.0.3"
|
||||||
resolved "https://registry.yarnpkg.com/external-editor/-/external-editor-3.0.1.tgz#fc9638c4d7cde4f0bb82b12307a1a23912c492e3"
|
resolved "https://registry.yarnpkg.com/external-editor/-/external-editor-3.0.3.tgz#5866db29a97826dbe4bf3afd24070ead9ea43a27"
|
||||||
dependencies:
|
dependencies:
|
||||||
chardet "^0.5.0"
|
chardet "^0.7.0"
|
||||||
iconv-lite "^0.4.22"
|
iconv-lite "^0.4.24"
|
||||||
tmp "^0.0.33"
|
tmp "^0.0.33"
|
||||||
|
|
||||||
extglob@^0.3.1:
|
extglob@^0.3.1:
|
||||||
@ -2903,6 +2903,10 @@ file-entry-cache@^2.0.0:
|
|||||||
flat-cache "^1.2.1"
|
flat-cache "^1.2.1"
|
||||||
object-assign "^4.0.1"
|
object-assign "^4.0.1"
|
||||||
|
|
||||||
|
file-type@9.0.0:
|
||||||
|
version "9.0.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/file-type/-/file-type-9.0.0.tgz#a68d5ad07f486414dfb2c8866f73161946714a18"
|
||||||
|
|
||||||
filename-regex@^2.0.0:
|
filename-regex@^2.0.0:
|
||||||
version "2.0.1"
|
version "2.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/filename-regex/-/filename-regex-2.0.1.tgz#c1c4b9bee3e09725ddb106b75c1e301fe2f18b26"
|
resolved "https://registry.yarnpkg.com/filename-regex/-/filename-regex-2.0.1.tgz#c1c4b9bee3e09725ddb106b75c1e301fe2f18b26"
|
||||||
@ -3249,7 +3253,7 @@ globjoin@^0.1.4:
|
|||||||
version "0.1.4"
|
version "0.1.4"
|
||||||
resolved "https://registry.yarnpkg.com/globjoin/-/globjoin-0.1.4.tgz#2f4494ac8919e3767c5cbb691e9f463324285d43"
|
resolved "https://registry.yarnpkg.com/globjoin/-/globjoin-0.1.4.tgz#2f4494ac8919e3767c5cbb691e9f463324285d43"
|
||||||
|
|
||||||
gonzales-pe@4.2.3:
|
gonzales-pe@^4.2.3:
|
||||||
version "4.2.3"
|
version "4.2.3"
|
||||||
resolved "https://registry.yarnpkg.com/gonzales-pe/-/gonzales-pe-4.2.3.tgz#41091703625433285e0aee3aa47829fc1fbeb6f2"
|
resolved "https://registry.yarnpkg.com/gonzales-pe/-/gonzales-pe-4.2.3.tgz#41091703625433285e0aee3aa47829fc1fbeb6f2"
|
||||||
dependencies:
|
dependencies:
|
||||||
@ -3552,7 +3556,7 @@ iconv-lite@0.4.19:
|
|||||||
version "0.4.19"
|
version "0.4.19"
|
||||||
resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.19.tgz#f7468f60135f5e5dad3399c0a81be9a1603a082b"
|
resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.19.tgz#f7468f60135f5e5dad3399c0a81be9a1603a082b"
|
||||||
|
|
||||||
iconv-lite@^0.4.11, iconv-lite@^0.4.22, iconv-lite@^0.4.4:
|
iconv-lite@^0.4.11, iconv-lite@^0.4.24, iconv-lite@^0.4.4:
|
||||||
version "0.4.24"
|
version "0.4.24"
|
||||||
resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b"
|
resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b"
|
||||||
dependencies:
|
dependencies:
|
||||||
@ -3980,6 +3984,10 @@ is-typedarray@~1.0.0:
|
|||||||
version "1.0.0"
|
version "1.0.0"
|
||||||
resolved "https://registry.yarnpkg.com/is-typedarray/-/is-typedarray-1.0.0.tgz#e479c80858df0c1b11ddda6940f96011fcda4a9a"
|
resolved "https://registry.yarnpkg.com/is-typedarray/-/is-typedarray-1.0.0.tgz#e479c80858df0c1b11ddda6940f96011fcda4a9a"
|
||||||
|
|
||||||
|
is-utf8@0.2.1:
|
||||||
|
version "0.2.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-utf8/-/is-utf8-0.2.1.tgz#4b0da1442104d1b336340e80797e865cf39f7d72"
|
||||||
|
|
||||||
is-whitespace-character@^1.0.0:
|
is-whitespace-character@^1.0.0:
|
||||||
version "1.0.2"
|
version "1.0.2"
|
||||||
resolved "https://registry.yarnpkg.com/is-whitespace-character/-/is-whitespace-character-1.0.2.tgz#ede53b4c6f6fb3874533751ec9280d01928d03ed"
|
resolved "https://registry.yarnpkg.com/is-whitespace-character/-/is-whitespace-character-1.0.2.tgz#ede53b4c6f6fb3874533751ec9280d01928d03ed"
|
||||||
@ -4759,7 +4767,7 @@ mixin-deep@^1.2.0:
|
|||||||
|
|
||||||
mkdirp@0.5.1, mkdirp@0.5.x, mkdirp@^0.5.0, mkdirp@^0.5.1, mkdirp@~0.5.0, mkdirp@~0.5.1:
|
mkdirp@0.5.1, mkdirp@0.5.x, mkdirp@^0.5.0, mkdirp@^0.5.1, mkdirp@~0.5.0, mkdirp@~0.5.1:
|
||||||
version "0.5.1"
|
version "0.5.1"
|
||||||
resolved "http://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz#30057438eac6cf7f8c4767f38648d6697d75c903"
|
resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.1.tgz#30057438eac6cf7f8c4767f38648d6697d75c903"
|
||||||
dependencies:
|
dependencies:
|
||||||
minimist "0.0.8"
|
minimist "0.0.8"
|
||||||
|
|
||||||
@ -5744,11 +5752,11 @@ postcss-safe-parser@^4.0.0:
|
|||||||
postcss "^7.0.0"
|
postcss "^7.0.0"
|
||||||
|
|
||||||
postcss-sass@^0.3.0:
|
postcss-sass@^0.3.0:
|
||||||
version "0.3.2"
|
version "0.3.3"
|
||||||
resolved "https://registry.yarnpkg.com/postcss-sass/-/postcss-sass-0.3.2.tgz#17f3074cecb28128b156f1a4407c6ad075d7e00c"
|
resolved "https://registry.yarnpkg.com/postcss-sass/-/postcss-sass-0.3.3.tgz#bec188ac285d21ac8feba194c2f327fdda31e671"
|
||||||
dependencies:
|
dependencies:
|
||||||
gonzales-pe "4.2.3"
|
gonzales-pe "^4.2.3"
|
||||||
postcss "6.0.22"
|
postcss "^7.0.1"
|
||||||
|
|
||||||
postcss-scss@^2.0.0:
|
postcss-scss@^2.0.0:
|
||||||
version "2.0.0"
|
version "2.0.0"
|
||||||
@ -5809,14 +5817,6 @@ postcss-zindex@^2.0.1:
|
|||||||
postcss "^5.0.4"
|
postcss "^5.0.4"
|
||||||
uniqs "^2.0.0"
|
uniqs "^2.0.0"
|
||||||
|
|
||||||
postcss@6.0.22:
|
|
||||||
version "6.0.22"
|
|
||||||
resolved "https://registry.yarnpkg.com/postcss/-/postcss-6.0.22.tgz#e23b78314905c3b90cbd61702121e7a78848f2a3"
|
|
||||||
dependencies:
|
|
||||||
chalk "^2.4.1"
|
|
||||||
source-map "^0.6.1"
|
|
||||||
supports-color "^5.4.0"
|
|
||||||
|
|
||||||
postcss@^5.0.10, postcss@^5.0.11, postcss@^5.0.12, postcss@^5.0.13, postcss@^5.0.14, postcss@^5.0.16, postcss@^5.0.2, postcss@^5.0.4, postcss@^5.0.5, postcss@^5.0.6, postcss@^5.0.8, postcss@^5.2.16:
|
postcss@^5.0.10, postcss@^5.0.11, postcss@^5.0.12, postcss@^5.0.13, postcss@^5.0.14, postcss@^5.0.16, postcss@^5.0.2, postcss@^5.0.4, postcss@^5.0.5, postcss@^5.0.6, postcss@^5.0.8, postcss@^5.2.16:
|
||||||
version "5.2.18"
|
version "5.2.18"
|
||||||
resolved "https://registry.yarnpkg.com/postcss/-/postcss-5.2.18.tgz#badfa1497d46244f6390f58b319830d9107853c5"
|
resolved "https://registry.yarnpkg.com/postcss/-/postcss-5.2.18.tgz#badfa1497d46244f6390f58b319830d9107853c5"
|
||||||
@ -5834,7 +5834,7 @@ postcss@^6.0.1, postcss@^6.0.23, postcss@^6.0.8:
|
|||||||
source-map "^0.6.1"
|
source-map "^0.6.1"
|
||||||
supports-color "^5.4.0"
|
supports-color "^5.4.0"
|
||||||
|
|
||||||
postcss@^7.0.0, postcss@^7.0.2:
|
postcss@^7.0.0, postcss@^7.0.1, postcss@^7.0.2:
|
||||||
version "7.0.2"
|
version "7.0.2"
|
||||||
resolved "https://registry.yarnpkg.com/postcss/-/postcss-7.0.2.tgz#7b5a109de356804e27f95a960bef0e4d5bc9bb18"
|
resolved "https://registry.yarnpkg.com/postcss/-/postcss-7.0.2.tgz#7b5a109de356804e27f95a960bef0e4d5bc9bb18"
|
||||||
dependencies:
|
dependencies:
|
||||||
@ -6044,6 +6044,13 @@ rc@^1.0.1, rc@^1.1.6, rc@^1.2.7:
|
|||||||
minimist "^1.2.0"
|
minimist "^1.2.0"
|
||||||
strip-json-comments "~2.0.1"
|
strip-json-comments "~2.0.1"
|
||||||
|
|
||||||
|
read-chunk@3.0.0:
|
||||||
|
version "3.0.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/read-chunk/-/read-chunk-3.0.0.tgz#086cd198406104355626afacd2d21084afc367ec"
|
||||||
|
dependencies:
|
||||||
|
pify "^4.0.0"
|
||||||
|
with-open-file "^0.1.3"
|
||||||
|
|
||||||
read-pkg-up@^3.0.0:
|
read-pkg-up@^3.0.0:
|
||||||
version "3.0.0"
|
version "3.0.0"
|
||||||
resolved "https://registry.yarnpkg.com/read-pkg-up/-/read-pkg-up-3.0.0.tgz#3ed496685dba0f8fe118d0691dc51f4a1ff96f07"
|
resolved "https://registry.yarnpkg.com/read-pkg-up/-/read-pkg-up-3.0.0.tgz#3ed496685dba0f8fe118d0691dc51f4a1ff96f07"
|
||||||
@ -6407,8 +6414,8 @@ runes@^0.4.3:
|
|||||||
resolved "https://registry.yarnpkg.com/runes/-/runes-0.4.3.tgz#32f7738844bc767b65cc68171528e3373c7bb355"
|
resolved "https://registry.yarnpkg.com/runes/-/runes-0.4.3.tgz#32f7738844bc767b65cc68171528e3373c7bb355"
|
||||||
|
|
||||||
rxjs@^6.1.0:
|
rxjs@^6.1.0:
|
||||||
version "6.2.2"
|
version "6.3.1"
|
||||||
resolved "https://registry.yarnpkg.com/rxjs/-/rxjs-6.2.2.tgz#eb75fa3c186ff5289907d06483a77884586e1cf9"
|
resolved "https://registry.yarnpkg.com/rxjs/-/rxjs-6.3.1.tgz#878a1a8c64b8a5da11dcf74b5033fe944cdafb84"
|
||||||
dependencies:
|
dependencies:
|
||||||
tslib "^1.9.0"
|
tslib "^1.9.0"
|
||||||
|
|
||||||
@ -6683,6 +6690,10 @@ socket.io@2.1.1:
|
|||||||
socket.io-client "2.1.1"
|
socket.io-client "2.1.1"
|
||||||
socket.io-parser "~3.2.0"
|
socket.io-parser "~3.2.0"
|
||||||
|
|
||||||
|
socketio-file-upload@0.6.2:
|
||||||
|
version "0.6.2"
|
||||||
|
resolved "https://registry.yarnpkg.com/socketio-file-upload/-/socketio-file-upload-0.6.2.tgz#0e13c5e2b2a6798f0754d2bdcf2b404f8707e192"
|
||||||
|
|
||||||
sockjs-client@1.1.5:
|
sockjs-client@1.1.5:
|
||||||
version "1.1.5"
|
version "1.1.5"
|
||||||
resolved "https://registry.yarnpkg.com/sockjs-client/-/sockjs-client-1.1.5.tgz#1bb7c0f7222c40f42adf14f4442cbd1269771a83"
|
resolved "https://registry.yarnpkg.com/sockjs-client/-/sockjs-client-1.1.5.tgz#1bb7c0f7222c40f42adf14f4442cbd1269771a83"
|
||||||
@ -7342,8 +7353,8 @@ uglify-es@^3.3.4:
|
|||||||
source-map "~0.6.1"
|
source-map "~0.6.1"
|
||||||
|
|
||||||
uglify-js@3.4.x:
|
uglify-js@3.4.x:
|
||||||
version "3.4.8"
|
version "3.4.9"
|
||||||
resolved "https://registry.yarnpkg.com/uglify-js/-/uglify-js-3.4.8.tgz#d590777b208258b54131b1ae45bc9d3f68033a3e"
|
resolved "https://registry.yarnpkg.com/uglify-js/-/uglify-js-3.4.9.tgz#af02f180c1207d76432e473ed24a28f4a782bae3"
|
||||||
dependencies:
|
dependencies:
|
||||||
commander "~2.17.1"
|
commander "~2.17.1"
|
||||||
source-map "~0.6.1"
|
source-map "~0.6.1"
|
||||||
@ -7742,8 +7753,8 @@ webpack-log@^2.0.0:
|
|||||||
uuid "^3.3.2"
|
uuid "^3.3.2"
|
||||||
|
|
||||||
webpack-sources@^1.0.1, webpack-sources@^1.1.0:
|
webpack-sources@^1.0.1, webpack-sources@^1.1.0:
|
||||||
version "1.1.0"
|
version "1.2.0"
|
||||||
resolved "https://registry.yarnpkg.com/webpack-sources/-/webpack-sources-1.1.0.tgz#a101ebae59d6507354d71d8013950a3a8b7a5a54"
|
resolved "https://registry.yarnpkg.com/webpack-sources/-/webpack-sources-1.2.0.tgz#18181e0d013fce096faf6f8e6d41eeffffdceac2"
|
||||||
dependencies:
|
dependencies:
|
||||||
source-list-map "^2.0.0"
|
source-list-map "^2.0.0"
|
||||||
source-map "~0.6.1"
|
source-map "~0.6.1"
|
||||||
@ -7817,6 +7828,14 @@ window-size@0.1.0:
|
|||||||
version "0.1.0"
|
version "0.1.0"
|
||||||
resolved "https://registry.yarnpkg.com/window-size/-/window-size-0.1.0.tgz#5438cd2ea93b202efa3a19fe8887aee7c94f9c9d"
|
resolved "https://registry.yarnpkg.com/window-size/-/window-size-0.1.0.tgz#5438cd2ea93b202efa3a19fe8887aee7c94f9c9d"
|
||||||
|
|
||||||
|
with-open-file@^0.1.3:
|
||||||
|
version "0.1.3"
|
||||||
|
resolved "https://registry.yarnpkg.com/with-open-file/-/with-open-file-0.1.3.tgz#9d8ed7a993cd15c55b3f7b815930a94c430885a1"
|
||||||
|
dependencies:
|
||||||
|
p-finally "^1.0.0"
|
||||||
|
p-try "^2.0.0"
|
||||||
|
pify "^3.0.0"
|
||||||
|
|
||||||
wordwrap@0.0.2:
|
wordwrap@0.0.2:
|
||||||
version "0.0.2"
|
version "0.0.2"
|
||||||
resolved "https://registry.yarnpkg.com/wordwrap/-/wordwrap-0.0.2.tgz#b79669bb42ecb409f83d583cad52ca17eaa1643f"
|
resolved "https://registry.yarnpkg.com/wordwrap/-/wordwrap-0.0.2.tgz#b79669bb42ecb409f83d583cad52ca17eaa1643f"
|
||||||
|
Loading…
Reference in New Issue
Block a user