Merge branch 'staging' into u

pull/1/head
yflory 5 years ago
commit f98ffee07a

@ -62,7 +62,7 @@ define([
var imprintUrl = AppConfig.imprint && (typeof(AppConfig.imprint) === "boolean" ?
'/imprint.html' : AppConfig.imprint);
Pages.versionString = "CryptPad v3.19.0 (Thylacine)";
Pages.versionString = "CryptPad v3.19.1 (Thylacine's revenge)";
// used for the about menu
Pages.imprintLink = AppConfig.imprint ? footLink(imprintUrl, 'imprint') : undefined;

@ -2,9 +2,11 @@
@import (reference) "../include/colortheme-all.less";
@import (reference) "../include/alertify.less";
@import (reference) "../include/checkmark.less";
@import (reference) "../include/forms.less";
&.cp-page-register {
.infopages_main();
.forms_main();
.alertify_main();
.checkmark_main(20px);

2
package-lock.json generated

@ -1,6 +1,6 @@
{
"name": "cryptpad",
"version": "3.19.0",
"version": "3.19.1",
"lockfileVersion": 1,
"requires": true,
"dependencies": {

@ -1,7 +1,7 @@
{
"name": "cryptpad",
"description": "realtime collaborative visual editor with zero knowlege server",
"version": "3.19.0",
"version": "3.19.1",
"license": "AGPL-3.0+",
"repository": {
"type": "git",

@ -647,9 +647,6 @@ define([
var $ok = $(ok).click(function (ev) { close(true, ev); });
var $cancel = $(cancel).click(function (ev) { close(false, ev); });
if (opt.cancelClass) { $cancel.addClass(opt.cancelClass); }
if (opt.okClass) { $ok.addClass(opt.okClass); }
listener = listenForKeys(function () {
$ok.click();
}, function () {

@ -2155,6 +2155,11 @@ define([
'class': 'fa fa-caret-down',
}).prependTo($button);
}
if (config.angleDown) {
$('<span>', {
'class': 'fa fa-angle-down',
}).prependTo($button);
}
// Menu
var $innerblock = $('<div>', {'class': 'cp-dropdown-content'});

@ -500,7 +500,7 @@ define([
}, 500);
progress(0, 0);*/
}).nThen(function () {
Realtime.whenRealtimeSyncs(store.realtime, Util.bake(cb));
Realtime.whenRealtimeSyncs(store.realtime, Util.mkAsync(Util.bake(cb)));
});
};
});

@ -798,7 +798,6 @@ var factory = function (Util, Hash, CPNetflux, Sortify, nThen, Crypto) {
return void console.error(err);
}
metadata = ref.internal.metadata = (data && data[0]) || undefined;
console.log("TEAM_METADATA", metadata);
});
}).nThen(function (w) {
if (!config.keys.teamEdPublic && metadata && metadata.validateKey) {

@ -175,6 +175,23 @@ define([
Pinpad.create(ctx.store.network, data, function (e, call) {
if (e) { return void cb(e); }
team.rpc = call;
team.pin = function (data, cb) {
if (!team.rpc) { return void cb({error: 'TEAM_RPC_NOT_READY'}); }
if (typeof(cb) !== 'function') { console.error('expected a callback'); }
team.rpc.pin(data, function (e, hash) {
if (e) { return void cb({error: e}); }
cb({hash: hash});
});
};
team.unpin = function (data, cb) {
if (!team.rpc) { return void cb({error: 'TEAM_RPC_NOT_READY'}); }
if (typeof(cb) !== 'function') { console.error('expected a callback'); }
team.rpc.unpin(data, function (e, hash) {
if (e) { return void cb({error: e}); }
cb({hash: hash});
});
};
cb();
});
});
@ -245,27 +262,7 @@ define([
nThen(function (waitFor) {
// Init Team RPC
if (!keys.drive.edPrivate) { return; }
initRpc(ctx, team, keys.drive, waitFor(function (err) {
if (err) { return; }
team.pin = function (data, cb) {
if (!team.rpc) { return void cb({error: 'TEAM_RPC_NOT_READY'}); }
if (typeof(cb) !== 'function') { console.error('expected a callback'); }
team.rpc.pin(data, function (e, hash) {
if (e) { return void cb({error: e}); }
cb({hash: hash});
});
};
team.unpin = function (data, cb) {
if (!team.rpc) { return void cb({error: 'TEAM_RPC_NOT_READY'}); }
if (typeof(cb) !== 'function') { console.error('expected a callback'); }
team.rpc.unpin(data, function (e, hash) {
if (e) { return void cb({error: e}); }
cb({hash: hash});
});
};
}));
initRpc(ctx, team, keys.drive, waitFor(function () {}));
}).nThen(function () {
// Create the proxy manager
var loadSharedFolder = function (id, data, cb, isNew) {
@ -474,6 +471,16 @@ define([
// Make sure we have not been kicked from the roster
var state = roster.getState();
var me = Util.find(ctx, ['store', 'proxy', 'curvePublic']);
// XXX FIXME roster history temporarily corrupted, don't leave the team
if (!state.members || !Object.keys(state.members).length) {
lm.stop();
roster.stop();
lm.proxy = {};
cb({error: 'EINVAL'});
waitFor.abort();
console.error(JSON.stringify(state));
return;
}
if (!state.members[me]) {
lm.stop();
roster.stop();
@ -1122,6 +1129,7 @@ define([
teamData.hash = data.hash;
teamData.keys.drive.edPrivate = data.keys.drive.edPrivate;
teamData.keys.chat.edit = data.keys.chat.edit;
initRpc(ctx, team, teamData.keys.drive, function () {});
var secret = Hash.getSecrets('team', data.hash, teamData.password);
team.secondaryKey = secret && secret.keys.secondaryKey;
@ -1130,6 +1138,9 @@ define([
delete teamData.keys.drive.edPrivate;
delete teamData.keys.chat.edit;
delete team.secondaryKey;
if (team.rpc && team.rpc.destroy) {
team.rpc.destroy();
}
}
updateMyRights(ctx, teamId, data.hash);
@ -1660,6 +1671,7 @@ define([
var safe = false;
if (['drive', 'teams', 'settings'].indexOf(app) !== -1) { safe = true; }
Object.keys(teams).forEach(function (id) {
if (!ctx.teams[id]) { return; }
t[id] = {
owner: teams[id].owner,
name: teams[id].metadata.name,
@ -1716,6 +1728,15 @@ define([
team.removeClient = function (clientId) {
removeClient(ctx, clientId);
};
var listTeams = function (cb) {
var t = Util.clone(teams);
Object.keys(t).forEach(function (id) {
// If failure to load the team, don't send it
if (ctx.teams[id]) { return; }
t[id].error = true;
});
cb(t);
};
team.execCommand = function (clientId, obj, cb) {
if (ctx.store.offline) {
return void cb({ error: 'OFFLINE' });
@ -1728,7 +1749,7 @@ define([
return void subscribe(ctx, data, clientId, cb);
}
if (cmd === 'LIST_TEAMS') {
return void cb(store.proxy.teams);
return void listTeams(cb);
}
if (cmd === 'OPEN_TEAM_CHAT') {
return void openTeamChat(ctx, data, clientId, cb);

@ -144,7 +144,6 @@ define([
var onMessage = function (data, cb) {
// data = { type: 'type', content: {msg: 'msg', hash: 'hash'} }
console.debug(data.type, data.content);
pushMessage(data);
if (data.content && typeof (data.content.getFormatText) === "function") {
var text = $('<div>').html(data.content.getFormatText()).text();
@ -188,7 +187,6 @@ define([
onMessageHandlers.push(function (data, el) {
var type = data.type;
if (types.indexOf(type) === -1 && !(teams && /^team-/.test(type))) { return; }
console.log('okokok');
cfg.onMessage(data, el);
});
}

@ -1027,7 +1027,6 @@ MessengerUI, Messages) {
Common.mailbox.subscribe(['notifications', 'team'], {
onMessage: function (data, el) {
console.log(data, el, div);
if (el) {
$(div).prepend(el);
}

@ -1087,7 +1087,7 @@
"support_disabledTitle": "Support ist nicht aktiviert",
"support_disabledHint": "Diese CryptPad-Instanz wurde noch nicht für die Verwendung eines Support-Formulars konfiguriert.",
"support_cat_new": "Neues Ticket",
"support_formTitle": "Titel des Tickets",
"support_formTitle": "Neues Ticket",
"support_formHint": "Mit diesem Formular kann ein neues Support-Ticket eröffnet werden. Es erlaubt die sichere Kontaktaufnahme mit den Administratoren zur Lösung von Problemen oder Beantwortung von Fragen. Bitte eröffne kein neues Ticket, wenn du bereits ein offenes Ticket bezüglich des gleichen Problems hast. Verwende stattdessen die Antworten-Schaltfläche, um weitere Informationen hinzuzufügen.",
"support_formButton": "Absenden",
"support_formTitleError": "Fehler: Titel ist leer",

@ -1086,7 +1086,7 @@
"support_disabledTitle": "Le support n'est pas activé",
"support_disabledHint": "Cette instance de CryptPad n'est pas encore configurée pour utiliser le formulaire de support.",
"support_cat_new": "Nouveau ticket",
"support_formTitle": "Titre du ticket",
"support_formTitle": "Nouveau Ticket",
"support_formButton": "Envoyer",
"support_formTitleError": "Erreur : le titre est vide",
"support_formContentError": "Erreur : le contenu est vide",

@ -1108,7 +1108,7 @@
"support_disabledTitle": "Support is not enabled",
"support_disabledHint": "This CryptPad instance is not yet configured to use a support form.",
"support_cat_new": "New ticket",
"support_formTitle": "Ticket title",
"support_formTitle": "New Ticket",
"support_formHint": "This form can be used to create a new support ticket. Use it to contact the administrators to solve issues or ask any question in a secure way. Please don't create a new ticket if you already have an open ticket about the same issue, but use the reply button to provide more information.",
"support_formButton": "Send",
"support_formTitleError": "Error: title is empty",

@ -115,8 +115,11 @@ define([
}, {
ok: Messages.register_writtenPassword,
cancel: Messages.register_cancel,
cancelClass: 'safe',
okClass: 'danger',
/* If we're certain that we aren't using these "*Class" APIs
anywhere else then we can deprecate them and make this a
custom modal in common-interface (or here). */
cancelClass: 'btn.btn-safe',
okClass: 'btn.btn-danger',
reverseOrder: true,
done: function ($dialog) {
$dialog.find('> div').addClass('half');

@ -66,11 +66,20 @@ define([
var $cat = $form.find('.cp-support-form-category');
var $title = $form.find('.cp-support-form-title');
var $content = $form.find('.cp-support-form-msg');
// XXX block submission until pending uploads are complete?
// TODO block submission until pending uploads are complete?
var $attachments = $form.find('.cp-support-attachments');
var category = $cat.val().trim();
/*
// || ($form.closest('.cp-support-list-ticket').data('cat') || "").trim();
// Messages.support_formCategoryError = "Error: category is empty"; // TODO ensure this is translated before use
if (!category) {
console.log($cat);
return void UI.alert(Messages.support_formCategoryError);
}
*/
var category = $cat.val().trim(); // XXX make category a required field?
var title = $title.val().trim();
if (!title) {
return void UI.alert(Messages.support_formTitleError);
@ -117,6 +126,7 @@ define([
});
var dropdownCfg = {
text: Messages.support_category,
angleDown: 1,
options: categories,
container: $(container),
isSelect: true
@ -178,8 +188,6 @@ define([
}).on('change', function (e) {
var files = Util.slice(e.target.files);
files.forEach(function (file) {
// XXX validate that the href is hosted on the same instance
// use relative URLs or compare it against a list or allowed domains?
var ev = {};
ev.callback = function (data) {
var x, a;
@ -320,10 +328,11 @@ define([
var attachments = (content.attachments || []).map(function (obj) {
if (!obj || !obj.name || !obj.href) { return; }
// only support files explicitly beginning with /file/ so that users can't link outside of the instance
if (!/^\/file\//.test(obj.href)) { return; }
var a = h('a', {
href: '#'
}, obj.name);
// XXX disallow remote URLs
$(a).click(function (e) {
e.preventDefault();
ctx.common.openURL(obj.href);

@ -418,6 +418,10 @@ define([
]));
common.displayAvatar($(avatar), team.metadata.avatar, team.metadata.name);
$(btn).click(function () {
if (team.error) {
UI.warn(Messages.error); // XXX better error message - roster bug, can't load the team for now
return;
}
openTeam(common, id, team);
});
});

Loading…
Cancel
Save