factored out progress into progress.js
This commit is contained in:
parent
5ac013ca40
commit
c91d24cd86
|
@ -1,96 +1,49 @@
|
||||||
const { Raven } = require('./common');
|
const { Raven } = require('./common');
|
||||||
const FileReceiver = require('./fileReceiver');
|
const FileReceiver = require('./fileReceiver');
|
||||||
const { notify, gcmCompliant } = require('./utils');
|
const { bytes, notify, gcmCompliant } = require('./utils');
|
||||||
const bytes = require('bytes');
|
|
||||||
const Storage = require('./storage');
|
const Storage = require('./storage');
|
||||||
const storage = new Storage(localStorage);
|
const storage = new Storage(localStorage);
|
||||||
const links = require('./links');
|
const links = require('./links');
|
||||||
const metrics = require('./metrics');
|
const metrics = require('./metrics');
|
||||||
|
const progress = require('./progress');
|
||||||
const $ = require('jquery');
|
const $ = require('jquery');
|
||||||
require('jquery-circle-progress');
|
|
||||||
|
|
||||||
$(() => {
|
function onUnload(size) {
|
||||||
gcmCompliant()
|
metrics.cancelledDownload({ size });
|
||||||
.then(() => {
|
}
|
||||||
|
|
||||||
|
function download() {
|
||||||
const $downloadBtn = $('#download-btn');
|
const $downloadBtn = $('#download-btn');
|
||||||
const $dlProgress = $('#dl-progress');
|
|
||||||
const $progressText = $('.progress-text');
|
|
||||||
const $title = $('.title');
|
const $title = $('.title');
|
||||||
|
const $file = $('#dl-file');
|
||||||
const filename = $('#dl-filename').text();
|
const size = Number($file.attr('data-size'));
|
||||||
const size = Number($('#dl-size').text());
|
const ttl = Number($file.attr('data-ttl'));
|
||||||
const ttl = Number($('#dl-ttl').text());
|
const unloadHandler = onUnload.bind(null, size);
|
||||||
|
const startTime = Date.now();
|
||||||
//initiate progress bar
|
|
||||||
$dlProgress.circleProgress({
|
|
||||||
value: 0.0,
|
|
||||||
startAngle: -Math.PI / 2,
|
|
||||||
fill: '#3B9DFF',
|
|
||||||
size: 158,
|
|
||||||
animation: { duration: 300 }
|
|
||||||
});
|
|
||||||
|
|
||||||
const download = () => {
|
|
||||||
// Disable the download button to avoid accidental double clicks.
|
|
||||||
$downloadBtn.attr('disabled', 'disabled');
|
|
||||||
links.setOpenInNewTab(true);
|
|
||||||
|
|
||||||
const fileReceiver = new FileReceiver();
|
const fileReceiver = new FileReceiver();
|
||||||
|
|
||||||
fileReceiver.on('progress', progress => {
|
$downloadBtn.attr('disabled', 'disabled');
|
||||||
window.onunload = function() {
|
|
||||||
metrics.cancelledDownload({ size });
|
|
||||||
};
|
|
||||||
|
|
||||||
$('#download-page-one').attr('hidden', true);
|
$('#download-page-one').attr('hidden', true);
|
||||||
$('#download-progress').removeAttr('hidden');
|
$('#download-progress').removeAttr('hidden');
|
||||||
const percent = progress[0] / progress[1];
|
metrics.startedDownload({ size, ttl });
|
||||||
// update progress bar
|
links.setOpenInNewTab(true);
|
||||||
$dlProgress.circleProgress('value', percent);
|
window.addEventListener('unload', unloadHandler);
|
||||||
$('.percent-number').text(`${Math.floor(percent * 100)}`);
|
|
||||||
$progressText.text(
|
fileReceiver.on('progress', data => {
|
||||||
`${filename} (${bytes(progress[0], {
|
progress.setProgress({ complete: data[0], total: data[1] });
|
||||||
decimalPlaces: 1,
|
|
||||||
fixedDecimals: true
|
|
||||||
})} of ${bytes(progress[1], { decimalPlaces: 1 })})`
|
|
||||||
);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
let downloadEnd;
|
let downloadEnd;
|
||||||
fileReceiver.on('decrypting', isStillDecrypting => {
|
fileReceiver.on('decrypting', () => {
|
||||||
// The file is being decrypted
|
|
||||||
if (isStillDecrypting) {
|
|
||||||
fileReceiver.removeAllListeners('progress');
|
|
||||||
window.onunload = null;
|
|
||||||
document.l10n.formatValue('decryptingFile').then(decryptingFile => {
|
|
||||||
$progressText.text(decryptingFile);
|
|
||||||
});
|
|
||||||
} else {
|
|
||||||
downloadEnd = Date.now();
|
downloadEnd = Date.now();
|
||||||
}
|
window.removeEventListener('unload', unloadHandler);
|
||||||
|
fileReceiver.removeAllListeners('progress');
|
||||||
|
document.l10n.formatValue('decryptingFile').then(progress.setText);
|
||||||
});
|
});
|
||||||
|
|
||||||
fileReceiver.on('hashing', isStillHashing => {
|
fileReceiver.on('hashing', () => {
|
||||||
// The file is being hashed to make sure a malicious user hasn't tampered with it
|
document.l10n.formatValue('verifyingFile').then(progress.setText);
|
||||||
if (isStillHashing) {
|
|
||||||
document.l10n.formatValue('verifyingFile').then(verifyingFile => {
|
|
||||||
$progressText.text(verifyingFile);
|
|
||||||
});
|
});
|
||||||
} else {
|
|
||||||
$progressText.text(' ');
|
|
||||||
document.l10n
|
|
||||||
.formatValues('downloadNotification', 'downloadFinish')
|
|
||||||
.then(translated => {
|
|
||||||
notify(translated[0]);
|
|
||||||
$title.text(translated[1]);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
const startTime = Date.now();
|
|
||||||
|
|
||||||
metrics.startedDownload({ size, ttl });
|
|
||||||
|
|
||||||
fileReceiver
|
fileReceiver
|
||||||
.download()
|
.download()
|
||||||
|
@ -115,6 +68,13 @@ $(() => {
|
||||||
const speed = size / (downloadTime / 1000);
|
const speed = size / (downloadTime / 1000);
|
||||||
storage.totalDownloads += 1;
|
storage.totalDownloads += 1;
|
||||||
metrics.completedDownload({ size, time, speed });
|
metrics.completedDownload({ size, time, speed });
|
||||||
|
progress.setText(' ');
|
||||||
|
document.l10n
|
||||||
|
.formatValues('downloadNotification', 'downloadFinish')
|
||||||
|
.then(translated => {
|
||||||
|
notify(translated[0]);
|
||||||
|
$title.text(translated[1]);
|
||||||
|
});
|
||||||
|
|
||||||
const dataView = new DataView(decrypted);
|
const dataView = new DataView(decrypted);
|
||||||
const blob = new Blob([dataView]);
|
const blob = new Blob([dataView]);
|
||||||
|
@ -136,9 +96,23 @@ $(() => {
|
||||||
return Promise.reject(err);
|
return Promise.reject(err);
|
||||||
})
|
})
|
||||||
.then(() => links.setOpenInNewTab(false));
|
.then(() => links.setOpenInNewTab(false));
|
||||||
};
|
}
|
||||||
|
|
||||||
$downloadBtn.on('click', download);
|
$(() => {
|
||||||
|
const $file = $('#dl-file');
|
||||||
|
const filename = $file.attr('data-filename');
|
||||||
|
const b = Number($file.attr('data-size'));
|
||||||
|
const size = bytes(b);
|
||||||
|
document.l10n
|
||||||
|
.formatValue('downloadFileSize', { size })
|
||||||
|
.then(str => $('#dl-filesize').text(str));
|
||||||
|
document.l10n
|
||||||
|
.formatValue('downloadingPageProgress', { filename, size })
|
||||||
|
.then(str => $('#dl-title').text(str));
|
||||||
|
|
||||||
|
gcmCompliant()
|
||||||
|
.then(() => {
|
||||||
|
$('#download-btn').on('click', download);
|
||||||
})
|
})
|
||||||
.catch(err => {
|
.catch(err => {
|
||||||
metrics.unsupported({ err }).then(() => {
|
metrics.unsupported({ err }).then(() => {
|
||||||
|
|
|
@ -62,7 +62,7 @@ class FileReceiver extends EventEmitter {
|
||||||
});
|
});
|
||||||
})
|
})
|
||||||
.then(([fdata, key]) => {
|
.then(([fdata, key]) => {
|
||||||
this.emit('decrypting', true);
|
this.emit('decrypting');
|
||||||
return Promise.all([
|
return Promise.all([
|
||||||
window.crypto.subtle
|
window.crypto.subtle
|
||||||
.decrypt(
|
.decrypt(
|
||||||
|
@ -76,7 +76,6 @@ class FileReceiver extends EventEmitter {
|
||||||
fdata.data
|
fdata.data
|
||||||
)
|
)
|
||||||
.then(decrypted => {
|
.then(decrypted => {
|
||||||
this.emit('decrypting', false);
|
|
||||||
return Promise.resolve(decrypted);
|
return Promise.resolve(decrypted);
|
||||||
}),
|
}),
|
||||||
fdata.filename,
|
fdata.filename,
|
||||||
|
@ -84,11 +83,10 @@ class FileReceiver extends EventEmitter {
|
||||||
]);
|
]);
|
||||||
})
|
})
|
||||||
.then(([decrypted, fname, proposedHash]) => {
|
.then(([decrypted, fname, proposedHash]) => {
|
||||||
this.emit('hashing', true);
|
this.emit('hashing');
|
||||||
return window.crypto.subtle
|
return window.crypto.subtle
|
||||||
.digest('SHA-256', decrypted)
|
.digest('SHA-256', decrypted)
|
||||||
.then(calculatedHash => {
|
.then(calculatedHash => {
|
||||||
this.emit('hashing', false);
|
|
||||||
const integrity =
|
const integrity =
|
||||||
new Uint8Array(calculatedHash).toString() ===
|
new Uint8Array(calculatedHash).toString() ===
|
||||||
proposedHash.toString();
|
proposedHash.toString();
|
||||||
|
|
|
@ -34,7 +34,7 @@ class FileSender extends EventEmitter {
|
||||||
|
|
||||||
upload() {
|
upload() {
|
||||||
const self = this;
|
const self = this;
|
||||||
self.emit('loading', true);
|
self.emit('loading');
|
||||||
return Promise.all([
|
return Promise.all([
|
||||||
window.crypto.subtle.generateKey(
|
window.crypto.subtle.generateKey(
|
||||||
{
|
{
|
||||||
|
@ -48,12 +48,10 @@ class FileSender extends EventEmitter {
|
||||||
const reader = new FileReader();
|
const reader = new FileReader();
|
||||||
reader.readAsArrayBuffer(this.file);
|
reader.readAsArrayBuffer(this.file);
|
||||||
reader.onload = function(event) {
|
reader.onload = function(event) {
|
||||||
self.emit('loading', false);
|
self.emit('hashing');
|
||||||
self.emit('hashing', true);
|
|
||||||
const plaintext = new Uint8Array(this.result);
|
const plaintext = new Uint8Array(this.result);
|
||||||
window.crypto.subtle.digest('SHA-256', plaintext).then(hash => {
|
window.crypto.subtle.digest('SHA-256', plaintext).then(hash => {
|
||||||
self.emit('hashing', false);
|
self.emit('encrypting');
|
||||||
self.emit('encrypting', true);
|
|
||||||
resolve({ plaintext: plaintext, hash: new Uint8Array(hash) });
|
resolve({ plaintext: plaintext, hash: new Uint8Array(hash) });
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
@ -64,8 +62,7 @@ class FileSender extends EventEmitter {
|
||||||
])
|
])
|
||||||
.then(([secretKey, file]) => {
|
.then(([secretKey, file]) => {
|
||||||
return Promise.all([
|
return Promise.all([
|
||||||
window.crypto.subtle
|
window.crypto.subtle.encrypt(
|
||||||
.encrypt(
|
|
||||||
{
|
{
|
||||||
name: 'AES-GCM',
|
name: 'AES-GCM',
|
||||||
iv: this.iv,
|
iv: this.iv,
|
||||||
|
@ -74,13 +71,7 @@ class FileSender extends EventEmitter {
|
||||||
},
|
},
|
||||||
secretKey,
|
secretKey,
|
||||||
file.plaintext
|
file.plaintext
|
||||||
)
|
),
|
||||||
.then(encrypted => {
|
|
||||||
self.emit('encrypting', false);
|
|
||||||
return new Promise((resolve, reject) => {
|
|
||||||
resolve(encrypted);
|
|
||||||
});
|
|
||||||
}),
|
|
||||||
window.crypto.subtle.exportKey('jwk', secretKey),
|
window.crypto.subtle.exportKey('jwk', secretKey),
|
||||||
new Promise((resolve, reject) => {
|
new Promise((resolve, reject) => {
|
||||||
resolve(file.hash);
|
resolve(file.hash);
|
||||||
|
|
|
@ -0,0 +1,41 @@
|
||||||
|
const { bytes } = require('./utils');
|
||||||
|
const $ = require('jquery');
|
||||||
|
require('jquery-circle-progress');
|
||||||
|
|
||||||
|
let $progress = null;
|
||||||
|
let $percent = null;
|
||||||
|
let $text = null;
|
||||||
|
|
||||||
|
document.addEventListener('DOMContentLoaded', function() {
|
||||||
|
$percent = $('.percent-number');
|
||||||
|
$text = $('.progress-text');
|
||||||
|
$progress = $('.progress-bar');
|
||||||
|
$progress.circleProgress({
|
||||||
|
value: 0.0,
|
||||||
|
startAngle: -Math.PI / 2,
|
||||||
|
fill: '#3B9DFF',
|
||||||
|
size: 158,
|
||||||
|
animation: { duration: 300 }
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
function setProgress(params) {
|
||||||
|
const percent = params.complete / params.total;
|
||||||
|
$progress.circleProgress('value', percent);
|
||||||
|
$percent.text(`${Math.floor(percent * 100)}`);
|
||||||
|
document.l10n
|
||||||
|
.formatValue('fileSizeProgress', {
|
||||||
|
partialSize: bytes(params.complete),
|
||||||
|
totalSize: bytes(params.total)
|
||||||
|
})
|
||||||
|
.then(setText);
|
||||||
|
}
|
||||||
|
|
||||||
|
function setText(str) {
|
||||||
|
$text.text(str);
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = {
|
||||||
|
setProgress,
|
||||||
|
setText
|
||||||
|
};
|
|
@ -2,18 +2,18 @@
|
||||||
const { Raven } = require('./common');
|
const { Raven } = require('./common');
|
||||||
const FileSender = require('./fileSender');
|
const FileSender = require('./fileSender');
|
||||||
const {
|
const {
|
||||||
|
bytes,
|
||||||
copyToClipboard,
|
copyToClipboard,
|
||||||
notify,
|
notify,
|
||||||
gcmCompliant,
|
gcmCompliant,
|
||||||
ONE_DAY_IN_MS
|
ONE_DAY_IN_MS
|
||||||
} = require('./utils');
|
} = require('./utils');
|
||||||
const bytes = require('bytes');
|
|
||||||
const Storage = require('./storage');
|
const Storage = require('./storage');
|
||||||
const storage = new Storage(localStorage);
|
const storage = new Storage(localStorage);
|
||||||
const metrics = require('./metrics');
|
const metrics = require('./metrics');
|
||||||
|
const progress = require('./progress');
|
||||||
|
|
||||||
const $ = require('jquery');
|
const $ = require('jquery');
|
||||||
require('jquery-circle-progress');
|
|
||||||
|
|
||||||
const allowedCopy = () => {
|
const allowedCopy = () => {
|
||||||
const support = !!document.queryCommandSupported;
|
const support = !!document.queryCommandSupported;
|
||||||
|
@ -27,10 +27,8 @@ $(() => {
|
||||||
const $copyBtn = $('#copy-btn');
|
const $copyBtn = $('#copy-btn');
|
||||||
const $link = $('#link');
|
const $link = $('#link');
|
||||||
const $uploadWindow = $('.upload-window');
|
const $uploadWindow = $('.upload-window');
|
||||||
const $ulProgress = $('#ul-progress');
|
|
||||||
const $uploadError = $('#upload-error');
|
const $uploadError = $('#upload-error');
|
||||||
const $uploadProgress = $('#upload-progress');
|
const $uploadProgress = $('#upload-progress');
|
||||||
const $progressText = $('.progress-text');
|
|
||||||
const $fileList = $('#file-list');
|
const $fileList = $('#file-list');
|
||||||
|
|
||||||
$pageOne.removeAttr('hidden');
|
$pageOne.removeAttr('hidden');
|
||||||
|
@ -96,15 +94,6 @@ $(() => {
|
||||||
$uploadWindow.removeClass('ondrag');
|
$uploadWindow.removeClass('ondrag');
|
||||||
});
|
});
|
||||||
|
|
||||||
//initiate progress bar
|
|
||||||
$ulProgress.circleProgress({
|
|
||||||
value: 0.0,
|
|
||||||
startAngle: -Math.PI / 2,
|
|
||||||
fill: '#3B9DFF',
|
|
||||||
size: 158,
|
|
||||||
animation: { duration: 300 }
|
|
||||||
});
|
|
||||||
|
|
||||||
//link back to homepage
|
//link back to homepage
|
||||||
$('.send-new').attr('href', window.location);
|
$('.send-new').attr('href', window.location);
|
||||||
|
|
||||||
|
@ -152,9 +141,15 @@ $(() => {
|
||||||
$pageOne.attr('hidden', true);
|
$pageOne.attr('hidden', true);
|
||||||
$uploadError.attr('hidden', true);
|
$uploadError.attr('hidden', true);
|
||||||
$uploadProgress.removeAttr('hidden');
|
$uploadProgress.removeAttr('hidden');
|
||||||
document.l10n.formatValue('importingFile').then(importingFile => {
|
document.l10n
|
||||||
$progressText.text(importingFile);
|
.formatValue('uploadingPageProgress', {
|
||||||
|
size: bytes(file.size),
|
||||||
|
filename: file.name
|
||||||
|
})
|
||||||
|
.then(str => {
|
||||||
|
$('#upload-filename').text(str);
|
||||||
});
|
});
|
||||||
|
document.l10n.formatValue('importingFile').then(progress.setText);
|
||||||
//don't allow drag and drop when not on page-one
|
//don't allow drag and drop when not on page-one
|
||||||
$(document.body).off('drop', onUpload);
|
$(document.body).off('drop', onUpload);
|
||||||
|
|
||||||
|
@ -168,40 +163,21 @@ $(() => {
|
||||||
location.reload();
|
location.reload();
|
||||||
});
|
});
|
||||||
|
|
||||||
fileSender.on('progress', progress => {
|
|
||||||
const percent = progress[0] / progress[1];
|
|
||||||
// update progress bar
|
|
||||||
$ulProgress.circleProgress('value', percent);
|
|
||||||
$ulProgress.circleProgress().on('circle-animation-end', function() {
|
|
||||||
$('.percent-number').text(`${Math.floor(percent * 100)}`);
|
|
||||||
});
|
|
||||||
$progressText.text(
|
|
||||||
`${file.name} (${bytes(progress[0], {
|
|
||||||
decimalPlaces: 1,
|
|
||||||
fixedDecimals: true
|
|
||||||
})} of ${bytes(progress[1], { decimalPlaces: 1 })})`
|
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
fileSender.on('hashing', isStillHashing => {
|
|
||||||
// The file is being hashed
|
|
||||||
if (isStillHashing) {
|
|
||||||
document.l10n.formatValue('verifyingFile').then(verifyingFile => {
|
|
||||||
$progressText.text(verifyingFile);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
let uploadStart;
|
let uploadStart;
|
||||||
fileSender.on('encrypting', isStillEncrypting => {
|
fileSender.on('progress', data => {
|
||||||
// The file is being encrypted
|
uploadStart = uploadStart || Date.now();
|
||||||
if (isStillEncrypting) {
|
progress.setProgress({
|
||||||
document.l10n.formatValue('encryptingFile').then(encryptingFile => {
|
complete: data[0],
|
||||||
$progressText.text(encryptingFile);
|
total: data[1]
|
||||||
});
|
});
|
||||||
} else {
|
});
|
||||||
uploadStart = Date.now();
|
|
||||||
}
|
fileSender.on('hashing', () => {
|
||||||
|
document.l10n.formatValue('verifyingFile').then(progress.setText);
|
||||||
|
});
|
||||||
|
|
||||||
|
fileSender.on('encrypting', () => {
|
||||||
|
document.l10n.formatValue('encryptingFile').then(progress.setText);
|
||||||
});
|
});
|
||||||
|
|
||||||
let t;
|
let t;
|
||||||
|
@ -244,16 +220,11 @@ $(() => {
|
||||||
};
|
};
|
||||||
|
|
||||||
storage.addFile(info.fileId, fileData);
|
storage.addFile(info.fileId, fileData);
|
||||||
$('#upload-filename').attr(
|
|
||||||
'data-l10n-id',
|
|
||||||
'uploadSuccessConfirmHeader'
|
|
||||||
);
|
|
||||||
t = window.setTimeout(() => {
|
|
||||||
$pageOne.attr('hidden', true);
|
$pageOne.attr('hidden', true);
|
||||||
$uploadProgress.attr('hidden', true);
|
$uploadProgress.attr('hidden', true);
|
||||||
$uploadError.attr('hidden', true);
|
$uploadError.attr('hidden', true);
|
||||||
$('#share-link').removeAttr('hidden');
|
$('#share-link').removeAttr('hidden');
|
||||||
}, 1000);
|
|
||||||
|
|
||||||
populateFileList(fileData);
|
populateFileList(fileData);
|
||||||
document.l10n.formatValue('notifyUploadDone').then(str => {
|
document.l10n.formatValue('notifyUploadDone').then(str => {
|
||||||
|
@ -331,7 +302,7 @@ $(() => {
|
||||||
|
|
||||||
$link.attr('value', url);
|
$link.attr('value', url);
|
||||||
$('#copy-text')
|
$('#copy-text')
|
||||||
.attr('data-l10n-args', `{"filename": "${file.name}"}`)
|
.attr('data-l10n-args', JSON.stringify({ filename: file.name }))
|
||||||
.attr('data-l10n-id', 'copyUrlFormLabelWithName');
|
.attr('data-l10n-id', 'copyUrlFormLabelWithName');
|
||||||
|
|
||||||
$popupText.attr('tabindex', '-1');
|
$popupText.attr('tabindex', '-1');
|
||||||
|
|
|
@ -104,9 +104,29 @@ function copyToClipboard(str) {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const LOCALIZE_NUMBERS = !!(
|
||||||
|
typeof Intl === 'object' &&
|
||||||
|
Intl &&
|
||||||
|
typeof Intl.NumberFormat === 'function'
|
||||||
|
);
|
||||||
|
|
||||||
|
const UNITS = ['B', 'kB', 'MB', 'GB'];
|
||||||
|
function bytes(num) {
|
||||||
|
const exponent = Math.min(Math.floor(Math.log10(num) / 3), UNITS.length - 1);
|
||||||
|
const n = Number(num / Math.pow(1000, exponent));
|
||||||
|
const nStr = LOCALIZE_NUMBERS
|
||||||
|
? n.toLocaleString(navigator.languages, {
|
||||||
|
minimumFractionDigits: 1,
|
||||||
|
maximumFractionDigits: 1
|
||||||
|
})
|
||||||
|
: n.toFixed(1);
|
||||||
|
return `${nStr}${UNITS[exponent]}`;
|
||||||
|
}
|
||||||
|
|
||||||
const ONE_DAY_IN_MS = 86400000;
|
const ONE_DAY_IN_MS = 86400000;
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
|
bytes,
|
||||||
copyToClipboard,
|
copyToClipboard,
|
||||||
arrayToHex,
|
arrayToHex,
|
||||||
hexToArray,
|
hexToArray,
|
||||||
|
|
|
@ -663,11 +663,6 @@
|
||||||
"readable-stream": "1.1.14"
|
"readable-stream": "1.1.14"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"bytes": {
|
|
||||||
"version": "2.5.0",
|
|
||||||
"resolved": "https://registry.npmjs.org/bytes/-/bytes-2.5.0.tgz",
|
|
||||||
"integrity": "sha1-TJQj6i0lLCcMQbK97+/5u2tiwGo="
|
|
||||||
},
|
|
||||||
"cached-path-relative": {
|
"cached-path-relative": {
|
||||||
"version": "1.0.1",
|
"version": "1.0.1",
|
||||||
"resolved": "https://registry.npmjs.org/cached-path-relative/-/cached-path-relative-1.0.1.tgz",
|
"resolved": "https://registry.npmjs.org/cached-path-relative/-/cached-path-relative-1.0.1.tgz",
|
||||||
|
|
|
@ -6,7 +6,6 @@
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"aws-sdk": "^2.89.0",
|
"aws-sdk": "^2.89.0",
|
||||||
"body-parser": "^1.17.2",
|
"body-parser": "^1.17.2",
|
||||||
"bytes": "^2.5.0",
|
|
||||||
"connect-busboy": "0.0.2",
|
"connect-busboy": "0.0.2",
|
||||||
"convict": "^3.0.0",
|
"convict": "^3.0.0",
|
||||||
"express": "^4.15.3",
|
"express": "^4.15.3",
|
||||||
|
|
|
@ -11,7 +11,7 @@ uploadPageBrowseButton = Select a file on your computer
|
||||||
.title = Select a file on your computer
|
.title = Select a file on your computer
|
||||||
uploadPageMultipleFilesAlert = Uploading multiple files or a folder is currently not supported.
|
uploadPageMultipleFilesAlert = Uploading multiple files or a folder is currently not supported.
|
||||||
uploadPageBrowseButtonTitle = Upload file
|
uploadPageBrowseButtonTitle = Upload file
|
||||||
uploadingPageHeader = Uploading Your File
|
uploadingPageProgress = Uploading { $filename } ({ $size })
|
||||||
importingFile = Importing…
|
importingFile = Importing…
|
||||||
verifyingFile = Verifying…
|
verifyingFile = Verifying…
|
||||||
encryptingFile = Encrypting…
|
encryptingFile = Encrypting…
|
||||||
|
@ -50,6 +50,8 @@ downloadButtonLabel = Download
|
||||||
.title = Download
|
.title = Download
|
||||||
downloadNotification = Your download has completed.
|
downloadNotification = Your download has completed.
|
||||||
downloadFinish = Download Complete
|
downloadFinish = Download Complete
|
||||||
|
// This message is displayed when uploading or downloading a file, e.g. "(1,3 MB of 10 MB)".
|
||||||
|
fileSizeProgress = ({ $partialSize } of { $totalSize })
|
||||||
// Firefox Send is a brand name and should not be localized. Title text for button should be the same.
|
// Firefox Send is a brand name and should not be localized. Title text for button should be the same.
|
||||||
sendYourFilesLink = Try Firefox Send
|
sendYourFilesLink = Try Firefox Send
|
||||||
.title = Try Firefox Send
|
.title = Try Firefox Send
|
||||||
|
|
|
@ -4,7 +4,6 @@ const busboy = require('connect-busboy');
|
||||||
const path = require('path');
|
const path = require('path');
|
||||||
const bodyParser = require('body-parser');
|
const bodyParser = require('body-parser');
|
||||||
const helmet = require('helmet');
|
const helmet = require('helmet');
|
||||||
const bytes = require('bytes');
|
|
||||||
const conf = require('./config.js');
|
const conf = require('./config.js');
|
||||||
const storage = require('./storage.js');
|
const storage = require('./storage.js');
|
||||||
const Raven = require('raven');
|
const Raven = require('raven');
|
||||||
|
@ -141,13 +140,15 @@ app.get('/download/:id', async (req, res) => {
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const filename = await storage.filename(id);
|
const efilename = await storage.filename(id);
|
||||||
const contentLength = await storage.length(id);
|
const filename = decodeURIComponent(efilename);
|
||||||
|
const filenameJson = JSON.stringify({ filename });
|
||||||
|
const sizeInBytes = await storage.length(id);
|
||||||
const ttl = await storage.ttl(id);
|
const ttl = await storage.ttl(id);
|
||||||
res.render('download', {
|
res.render('download', {
|
||||||
filename: decodeURIComponent(filename),
|
filename,
|
||||||
filesize: bytes(contentLength),
|
filenameJson,
|
||||||
sizeInBytes: contentLength,
|
sizeInBytes,
|
||||||
ttl
|
ttl
|
||||||
});
|
});
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
|
|
|
@ -2,13 +2,13 @@
|
||||||
<script src="/download.js"></script>
|
<script src="/download.js"></script>
|
||||||
<div id="download-page-one">
|
<div id="download-page-one">
|
||||||
<div class="title">
|
<div class="title">
|
||||||
<span id="dl-filename"
|
<span id="dl-file"
|
||||||
|
data-filename="{{filename}}"
|
||||||
|
data-size="{{sizeInBytes}}"
|
||||||
|
data-ttl="{{ttl}}"
|
||||||
data-l10n-id="downloadFileName"
|
data-l10n-id="downloadFileName"
|
||||||
data-l10n-args='{"filename": "{{filename}}"}'></span>
|
data-l10n-args='{{filenameJson}}'></span>
|
||||||
<span data-l10n-id="downloadFileSize"
|
<span id="dl-filesize"></span>
|
||||||
data-l10n-args='{"size": "{{filesize}}"}'></span>
|
|
||||||
<span id="dl-size" hidden="true">{{sizeInBytes}}</span>
|
|
||||||
<span id="dl-ttl" hidden="true">{{ttl}}</span>
|
|
||||||
</div>
|
</div>
|
||||||
<div class="description" data-l10n-id="downloadMessage"></div>
|
<div class="description" data-l10n-id="downloadMessage"></div>
|
||||||
<img src="/resources/illustration_download.svg" id="download-img" data-l10n-id="downloadAltText"/>
|
<img src="/resources/illustration_download.svg" id="download-img" data-l10n-id="downloadAltText"/>
|
||||||
|
@ -18,10 +18,7 @@
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="download-progress" hidden="true">
|
<div id="download-progress" hidden="true">
|
||||||
<div class="title"
|
<div id="dl-title" class="title"></div>
|
||||||
data-l10n-id="downloadingPageProgress"
|
|
||||||
data-l10n-args='{"filename": "{{filename}}", "size": "{{filesize}}"}'>
|
|
||||||
</div>
|
|
||||||
<div class="description" data-l10n-id="downloadingPageMessage"></div>
|
<div class="description" data-l10n-id="downloadingPageMessage"></div>
|
||||||
<!-- progress bar here -->
|
<!-- progress bar here -->
|
||||||
<div class="progress-bar" id="dl-progress">
|
<div class="progress-bar" id="dl-progress">
|
||||||
|
|
|
@ -35,7 +35,7 @@
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="upload-progress" hidden="true">
|
<div id="upload-progress" hidden="true">
|
||||||
<div class="title" id="upload-filename" data-l10n-id="uploadingPageHeader"></div>
|
<div class="title" id="upload-filename"></div>
|
||||||
<div class="description"></div>
|
<div class="description"></div>
|
||||||
<!-- progress bar here -->
|
<!-- progress bar here -->
|
||||||
<div class="progress-bar" id="ul-progress">
|
<div class="progress-bar" id="ul-progress">
|
||||||
|
|
Loading…
Reference in New Issue