Forms preview

This commit is contained in:
Tomas Bures 2018-12-15 20:09:07 +01:00
parent 97bbac8698
commit ba996d845d
23 changed files with 206 additions and 99 deletions

View file

@ -22,3 +22,5 @@ nameTag="username"
passwordresetlink="xxx"
[reports]
enabled=true
[redis]
enabled=true

View file

@ -9,9 +9,7 @@ const {convertToFake, getLang} = require('../../shared/langs');
const resourcesCommon = {};
function loadLanguage(longCode) {
resourcesCommon[longCode] = {
common: JSON.parse(fs.readFileSync(path.join(__dirname, '..', '..', 'locales', longCode, 'common.json')))
};
resourcesCommon[longCode] = JSON.parse(fs.readFileSync(path.join(__dirname, '..', '..', 'locales', longCode, 'common.json')));
}
loadLanguage('en-US');

View file

@ -316,7 +316,7 @@ async function sendPasswordReset(locale, usernameOrEmail) {
text: 'users/password-reset-text.hbs',
locale,
data: {
title: tUI('Mailtrain', locale),
title: tUI('mailtrain', locale),
username: user.username,
name: user.name,
confirmUrl: getTrustedUrl(`/account/reset/${encodeURIComponent(user.username)}/${encodeURIComponent(resetToken)}`)

View file

@ -11476,9 +11476,9 @@
}
},
"sprintf-js": {
"version": "1.1.1",
"resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.1.1.tgz",
"integrity": "sha1-Nr54Mgr+WAH2zqPueLblqrlA6gw=",
"version": "1.1.2",
"resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.1.2.tgz",
"integrity": "sha512-VE0SOVEHCk7Qc8ulkWw3ntAzXuqf7S2lvwQaDLRnUeIEaKNQJzV6BwmLKhOqT61aGhfUMrXeaBk+oDGCzvhcug==",
"dev": true
},
"sqlstring": {
@ -11899,9 +11899,9 @@
"integrity": "sha512-5/4etnCkd9c8gwgowi5/om/mYO5ajCaOgdzj/oW+0eQV9WxKBDZw5+ycmKmeaTXjInS/W0BzpGLo2xR2aBwZdg=="
},
"underscore.string": {
"version": "3.3.4",
"resolved": "https://registry.npmjs.org/underscore.string/-/underscore.string-3.3.4.tgz",
"integrity": "sha1-LCo/n4PmR2L9xF5s6sZRQoZCE9s=",
"version": "3.3.5",
"resolved": "https://registry.npmjs.org/underscore.string/-/underscore.string-3.3.5.tgz",
"integrity": "sha512-g+dpmgn+XBneLmXXo+sGlW5xQEt4ErkS3mgeN2GFbremYeMBSJKr9Wf2KJplQVaiPY/f7FN6atosWYNm9ovrYg==",
"dev": true,
"requires": {
"sprintf-js": "^1.0.3",

View file

@ -1,7 +1,12 @@
'use strict';
const passport = require('../../lib/passport');
const lists = require('../../models/lists');
const forms = require('../../models/forms');
const fields = require('../../models/fields');
const settings = require('../../models/settings');
const tools = require('../../lib/tools');
const contextHelpers = require('../../lib/context-helpers');
const router = require('../../lib/router-async').create();
const {castToInteger} = require('../../lib/helpers');
@ -38,5 +43,45 @@ router.postAsync('/forms-validate', passport.loggedIn, async (req, res) => {
return res.json(await forms.serverValidate(req.context, req.body));
});
router.postAsync('/forms-preview', passport.loggedIn, passport.csrfProtection, async (req, res) => {
function sortAndFilterCustomFieldsBy(key) {
data.customFields = data.customFields.filter(fld => fld[key] !== null);
data.customFields.sort((a, b) => a[key] - b[key]);
}
const formKey = req.body.formKey;
const listId = req.body.listId;
const data = {};
const list = await lists.getById(req.context, listId);
data.title = list.name;
data.cid = list.cid;
data.isWeb = true;
data.customFields = await fields.forHbs(req.context, listId, {});
const configItems = await settings.get(contextHelpers.getAdminContext(), ['pgpPrivateKey']);
data.hasPubkey = !!configItems.pgpPrivateKey;
data.formInputStyle = req.body.formInputStyle;
if (formKey === 'web_subscribe') {
sortAndFilterCustomFieldsBy('order_subscribe');
} else if (formKey === 'web_manage') {
sortAndFilterCustomFieldsBy('order_manage');
}
const tmpl = {
template: req.body.template,
layout: req.body.layout,
type: 'mjml'
};
const htmlRenderer = await tools.getTemplate(tmpl, req.locale);
return res.json({content: htmlRenderer(data)});
});
module.exports = router;

View file

@ -12,7 +12,7 @@ const settings = require('../models/settings');
const { tUI } = require('../lib/translate');
const contextHelpers = require('../lib/context-helpers');
const forms = require('../models/forms');
const {getTrustedUrl} = require('../lib/urls');
const {getTrustedUrl, getPublicUrl} = require('../lib/urls');
const bluebird = require('bluebird');
const { SubscriptionStatus, SubscriptionSource } = require('../../shared/lists');
@ -86,7 +86,7 @@ async function injectCustomFormData(customFormId, viewKey, data) {
data.template.template = form[viewKey] || data.template.template;
data.template.layout = form.layout || data.template.layout;
data.formInputStyle = form.formInputStyle || '@import url(/static/subscription/form-input-style.css);';
data.formInputStyle = form.formInputStyle || `@import url(${getPublicUrl('static/subscription/form-input-style.css')});`;
const configItems = await settings.get(contextHelpers.getAdminContext(), ['uaCode']);
@ -168,7 +168,6 @@ async function _renderSubscribe(req, res, list, subscription) {
data.csrfToken = req.csrfToken();
data.customFields = await fields.forHbs(contextHelpers.getAdminContext(), list.id, subscription);
data.useEditor = true;
const configItems = await settings.get(contextHelpers.getAdminContext(), ['pgpPrivateKey']);
data.hasPubkey = !!configItems.pgpPrivateKey;
@ -179,7 +178,7 @@ async function _renderSubscribe(req, res, list, subscription) {
type: 'mjml'
};
await injectCustomFormData(req.query.fid || list.default_form, 'subscription/web-subscribe', data);
await injectCustomFormData(req.query.fid || list.default_form, 'web_subscribe', data);
const htmlRenderer = await tools.getTemplate(data.template, req.locale);
@ -334,7 +333,7 @@ router.getAsync('/:cid/widget', cors(corsOptions), async (req, res) => {
layout: null,
};
await injectCustomFormData(req.query.fid || list.default_form, 'subscription/web-subscribe', data);
await injectCustomFormData(req.query.fid || list.default_form, 'web_subscribe', data);
const renderAsync = bluebird.promisify(res.render);
const html = await renderAsync('subscription/widget-subscribe', data);
@ -372,8 +371,6 @@ router.getAsync('/:lcid/manage/:ucid', passport.csrfProtection, async (req, res)
data.customFields = await fields.forHbs(contextHelpers.getAdminContext(), list.id, subscription);
data.useEditor = true;
const configItems = await settings.get(contextHelpers.getAdminContext(), ['pgpPrivateKey']);
data.hasPubkey = !!configItems.pgpPrivateKey;
@ -383,7 +380,7 @@ router.getAsync('/:lcid/manage/:ucid', passport.csrfProtection, async (req, res)
type: 'mjml'
};
await injectCustomFormData(req.query.fid || list.default_form, 'data/web-manage', data);
await injectCustomFormData(req.query.fid || list.default_form, 'web_manage', data);
const htmlRenderer = await tools.getTemplate(data.template, req.locale);
@ -433,7 +430,7 @@ router.getAsync('/:lcid/manage-address/:ucid', passport.csrfProtection, async (r
type: 'mjml'
};
await injectCustomFormData(req.query.fid || list.default_form, 'data/web-manage-address', data);
await injectCustomFormData(req.query.fid || list.default_form, 'web_manage_address', data);
const htmlRenderer = await tools.getTemplate(data.template, req.locale);
@ -533,7 +530,7 @@ router.getAsync('/:lcid/unsubscribe/:ucid', passport.csrfProtection, async (req,
type: 'mjml'
};
await injectCustomFormData(req.query.fid || list.default_form, 'subscription/web-unsubscribe', data);
await injectCustomFormData(req.query.fid || list.default_form, 'web_unsubscribe', data);
const htmlRenderer = await tools.getTemplate(data.template, req.locale);
@ -682,7 +679,7 @@ async function webNotice(type, req, res) {
}
};
await injectCustomFormData(req.query.fid || list.default_form, 'subscription/web-' + type + '-notice', data);
await injectCustomFormData(req.query.fid || list.default_form, 'web_' + type + '_notice', data);
const htmlRenderer = await tools.getTemplate(data.template, req.locale);

View file

@ -2,11 +2,11 @@
{{#if typeSubscriptionEmail}}
<div class="form-group email">
<label for="EMAIL">{{#translate}}Email Address{{/translate}}</label>
<label for="EMAIL">{{#translate}}emailAddress-2{{/translate}}</label>
{{#if ../isManagePreferences}}
<div class="input-group">
<input type="email" name="EMAIL" id="email" placeholder="" value="{{../email}}" readonly>
<div class="input-group-addon"><a href="/subscription/{{../lcid}}/manage-address/{{../cid}}">{{#translate}}want to change it?{{/translate}}</a></div>
<div class="input-group-addon"><a href="/subscription/{{../lcid}}/manage-address/{{../cid}}">{{#translate}}wantToChangeIt?{{/translate}}</a></div>
</div>
{{else}}
<input type="email" name="EMAIL" id="email" placeholder="" value="{{../email}}" required>
@ -53,11 +53,11 @@
<div class="form-group gpg {{key}}">
<label for="{{key}}">{{name}}</label>
{{#if ../hasPubkey}}
<button class="btn-download-pubkey" type="submit" form="download-pubkey">{{#translate}}Download signature verification key{{/translate}}</button>
<button class="btn-download-pubkey" type="submit" form="download-pubkey">{{#translate}}downloadSignatureVerificationKey{{/translate}}</button>
{{/if}}
<textarea class="form-control gpg-text" rows="4" name="{{key}}" placeholder="{{#translate}}Begins with &#39;-----BEGIN PGP PUBLIC KEY BLOCK-----&#39;{{/translate}}">{{value}}</textarea>
<textarea class="form-control gpg-text" rows="4" name="{{key}}" placeholder="{{#translate}}beginsWithAnd#39BeginPgpPublicKeyBloc{{/translate}}">{{value}}</textarea>
<span class="help-block">
{{#translate}}Insert your GPG public key here to encrypt messages sent to your address <em>(optional)</em>{{/translate}}
{{#translate}}insertYourGpgPublicKeyHereToEncrypt{{/translate}}
</span>
</div>
{{/if}}
@ -95,7 +95,7 @@
<label for="{{key}}">{{name}}</label>
<select name="{{key}}" class="form-control">
<option value="">
{{#translate}} Select {{/translate}}
{{#translate}}Select {{/translate}}
</option>
{{#each options}}
<option value="{{key}}" {{#if value}} selected {{/if}}>{{name}}</option>

View file

@ -2,7 +2,7 @@
{{#if needsJsWarning}}
<div class="alert alert-danger js-warning" role="alert">
<strong>{{#translate}}Warning!{{/translate}}</strong>
{{#translate}}JavaScript must be enabled in order for this form to work{{/translate}}
<strong>{{#translate}}warning!{{/translate}}</strong>
{{#translate}}javaScriptMustBeEnabledInOrderForThis{{/translate}}
</div>
{{/if}}

View file

@ -4,19 +4,19 @@
<input type="hidden" name="cid" value="{{cid}}">
<div class="form-group email">
<label for="EMAIL">{{#translate}}Existing Email Address{{/translate}}</label>
<label for="EMAIL">{{#translate}}existingEmailAddress{{/translate}}</label>
<input type="email" name="EMAIL" id="email" placeholder="" value="{{email}}" readonly>
</div>
<div class="form-group email">
<label for="EMAIL_NEW">{{#translate}}New Email Address{{/translate}}</label>
<label for="EMAIL_NEW">{{#translate}}newEmailAddress{{/translate}}</label>
<input type="email" name="EMAIL_NEW" id="email-new" placeholder="Your new email address" value="{{email}}">
</div>
<p>
{{#translate}}You will receive a confirmation request to your new email address that you need to accept before your email is actually changed{{/translate}}
{{#translate}}youWillReceiveAConfirmationRequestToYour{{/translate}}
</p>
<button type="submit" style="position: absolute; top: -9999px; left: -9999px;">{{#translate}}Update Email Address{{/translate}}</button>
<button type="submit" style="position: absolute; top: -9999px; left: -9999px;">{{#translate}}updateEmailAddress{{/translate}}</button>
</form>

View file

@ -12,7 +12,7 @@
{{> subscription_custom_fields}}
<button type="submit" style="position: absolute; top: -9999px; left: -9999px;">{{#translate}}Update Profile{{/translate}}</button>
<button type="submit" style="position: absolute; top: -9999px; left: -9999px;">{{#translate}}updateProfile{{/translate}}</button>
</form>
<script src="/moment/moment.min.js"></script>

View file

@ -14,7 +14,7 @@
{{> subscription_custom_fields}}
<button type="submit" style="position: absolute; top: -9999px; left: -9999px;">{{#translate}}Subscribe to list{{/translate}}</button>
<button type="submit" style="position: absolute; top: -9999px; left: -9999px;">{{#translate}}subscribeToList{{/translate}}</button>
</form>
<script>

View file

@ -4,10 +4,10 @@
<input type="hidden" name="ucid" value="{{ucid}}">
<div class="form-group">
<label for="email">{{#translate}}Email address{{/translate}}</label>
<label for="email">{{#translate}}emailAddress-1{{/translate}}</label>
<input type="email" name="email" id="email" placeholder="" value="{{email}}" readonly>
</div>
<button type="submit" style="position: absolute; top: -9999px; left: -9999px;">{{#translate}}Unsubscribe{{/translate}}</button>
<button type="submit" style="position: absolute; top: -9999px; left: -9999px;">{{#translate}}unsubscribe{{/translate}}</button>
</form>