diff --git a/CHANGES.md b/CHANGES.md index ae7422d2c..4e7b30229 100644 --- a/CHANGES.md +++ b/CHANGES.md @@ -13,6 +13,8 @@ - MP4 and MP3 files when sent as XEP-0066 Out of Band Data, are now playable directly in chat - Support for rendering URLs sent according to XEP-0066 Out of Band Data. - Geo-URIs (e.g. from Conversations) are now replaced by links to openstreetmap (works in reverse also) +- Add a checkbox to indicate whether a trusted device is being used or not. + If the device is not trusted, then all user data is deleted from the cache upon logout. ### Bugfixes diff --git a/css/converse.css b/css/converse.css index 2ad875ada..6cf664754 100644 --- a/css/converse.css +++ b/css/converse.css @@ -7203,7 +7203,7 @@ body.reset { #conversejs form .form-group { margin-bottom: 2em; } #conversejs form .form-check-label { - margin-top: 0.3rem; } + margin-top: 0.1rem; } #conversejs form .form-control::-webkit-input-placeholder { /* Chrome/Opera/Safari */ color: #A8ABA1; } @@ -7240,7 +7240,7 @@ body.reset { margin: 1em 0; } #conversejs form.converse-form { background: white; - padding: 1em; } + padding: 1.5em; } #conversejs form.converse-form legend { color: #666; font-size: 125%; @@ -7276,6 +7276,9 @@ body.reset { #conversejs form.converse-centered-form { text-align: center; } +#conversejs.fullscreen form .form-check-label { + margin-top: 0.3rem; } + #conversejs #user-profile-modal label { font-weight: bold; } diff --git a/css/inverse.css b/css/inverse.css index d53ccce4e..fdb990680 100644 --- a/css/inverse.css +++ b/css/inverse.css @@ -7245,7 +7245,7 @@ body { #conversejs form .form-group { margin-bottom: 2em; } #conversejs form .form-check-label { - margin-top: 0.3rem; } + margin-top: 0.1rem; } #conversejs form .form-control::-webkit-input-placeholder { /* Chrome/Opera/Safari */ color: #A8ABA1; } @@ -7282,7 +7282,7 @@ body { margin: 1em 0; } #conversejs form.converse-form { background: white; - padding: 1em; } + padding: 1.5em; } #conversejs form.converse-form legend { color: #666; font-size: 125%; @@ -7318,6 +7318,9 @@ body { #conversejs form.converse-centered-form { text-align: center; } +#conversejs.fullscreen form .form-check-label { + margin-top: 0.3rem; } + #conversejs #user-profile-modal label { font-weight: bold; } diff --git a/sass/_forms.scss b/sass/_forms.scss index 0873fedd0..55fcd4917 100644 --- a/sass/_forms.scss +++ b/sass/_forms.scss @@ -5,7 +5,7 @@ } .form-check-label { - margin-top: $form-check-input-margin-y; + margin-top: 0.1rem; } .form-control { @@ -61,7 +61,7 @@ &.converse-form { background: white; - padding: 1em; + padding: 1.5em; legend { color: $text-color; font-size: 125%; @@ -108,3 +108,12 @@ } } } + +#conversejs.fullscreen { + form { + .form-check-label { + margin-top: $form-check-input-margin-y; + } + } +} + diff --git a/spec/login.js b/spec/login.js new file mode 100644 index 000000000..ea833bc15 --- /dev/null +++ b/spec/login.js @@ -0,0 +1,45 @@ +(function (root, factory) { + define(["jasmine", "mock", "converse-core", "test-utils"], factory); +} (this, function (jasmine, mock, converse, test_utils) { + + describe("The Login Form", function () { + + it("contains a checkbox to indicate whether the computer is trusted or not", + mock.initConverseWithPromises( + null, ['connectionInitialized', 'chatBoxesInitialized'], + { auto_login: false, + allow_registration: false }, + function (done, _converse) { + + test_utils.waitUntil(() => _converse.chatboxviews.get('controlbox')) + .then(function () { + var cbview = _converse.chatboxviews.get('controlbox'); + test_utils.openControlBox(); + const checkboxes = cbview.el.querySelectorAll('input[type="checkbox"]'); + expect(checkboxes.length).toBe(1); + + const checkbox = checkboxes[0]; + const label = cbview.el.querySelector(`label[for="${checkbox.getAttribute('id')}"]`); + expect(label.textContent).toBe('This is a trusted device'); + expect(checkbox.checked).toBe(true); + + cbview.el.querySelector('input[name="jid"]').value = 'dummy@localhost'; + cbview.el.querySelector('input[name="password"]').value = 'secret'; + + spyOn(cbview.loginpanel, 'connect'); + cbview.delegateEvents(); + + expect(_converse.storage).toBe('session'); + cbview.el.querySelector('input[type="submit"]').click(); + expect(_converse.storage).toBe('local'); + expect(cbview.loginpanel.connect).toHaveBeenCalled(); + + + checkbox.click(); + cbview.el.querySelector('input[type="submit"]').click(); + expect(_converse.storage).toBe('session'); + done(); + }); + })); + }); +})); diff --git a/spec/register.js b/spec/register.js index 0d912aa08..1403259dd 100644 --- a/spec/register.js +++ b/spec/register.js @@ -14,15 +14,12 @@ allow_registration: false }, function (done, _converse) { - test_utils.waitUntil(function () { - return _converse.chatboxviews.get('controlbox'); - }, 300) + test_utils.waitUntil(() => _converse.chatboxviews.get('controlbox')) .then(function () { - - test_utils.openControlBox(); - var cbview = _converse.chatboxviews.get('controlbox'); - expect($(cbview.el.querySelector('a.register-account')).length).toBe(0); - done(); + test_utils.openControlBox(); + var cbview = _converse.chatboxviews.get('controlbox'); + expect($(cbview.el.querySelector('a.register-account')).length).toBe(0); + done(); }); })); diff --git a/src/converse-controlbox.js b/src/converse-controlbox.js index 562ab86ee..a76f04698 100644 --- a/src/converse-controlbox.js +++ b/src/converse-controlbox.js @@ -8,6 +8,7 @@ (function (root, factory) { define(["converse-core", + "bootstrap", "lodash.fp", "tpl!converse_brand_heading", "tpl!controlbox", @@ -19,6 +20,7 @@ ], factory); }(this, function ( converse, + bootstrap, fp, tpl_brand_heading, tpl_controlbox, @@ -414,6 +416,14 @@ initialize (cfg) { this.model.on('change', this.render, this); this.listenTo(_converse.connfeedback, 'change', this.render); + this.render(); + _.forEach(this.el.querySelectorAll('[data-title]'), (el) => { + const popover = new bootstrap.Popover(el, { + 'trigger': _converse.view_mode === 'mobile' && 'click' || 'hover', + 'dismissible': _converse.view_mode === 'mobile' && true || false, + 'container': _converse.chatboxviews.el + }) + }); }, toHTML () { @@ -465,18 +475,18 @@ this.connect(_converse.jid, null); return; } - if (!this.validate()) { - return; - } - let jid = ev.target.querySelector('input[name=jid]').value; + if (!this.validate()) { return; } + + const form_data = new FormData(ev.target); + _converse.storage = form_data.get('trusted') ? 'local' : 'session'; + + let jid = form_data.get('jid'); if (_converse.locked_domain) { jid = Strophe.escapeNode(jid) + '@' + _converse.locked_domain; } else if (_converse.default_domain && !_.includes(jid, '@')) { jid = jid + '@' + _converse.default_domain; } - this.connect( - jid, _.get(ev.target.querySelector('input[name=password]'), 'value') - ); + this.connect(jid, form_data.get('password')); }, connect (jid, password) { diff --git a/src/templates/login_panel.html b/src/templates/login_panel.html index 958c921df..4f32a688f 100644 --- a/src/templates/login_panel.html +++ b/src/templates/login_panel.html @@ -9,17 +9,25 @@ {[ } else { ]} {[ if (o.authentication == o.LOGIN || o.authentication == o.EXTERNAL) { ]}
- - + +
{[ if (o.authentication !== o.EXTERNAL) { ]}
- - + +
{[ } ]} +
+ + + +
+
- +
{[ } ]} {[ if (o.authentication == o.ANONYMOUS) { ]} diff --git a/tests/runner.js b/tests/runner.js index ed176bb95..335e2d1de 100644 --- a/tests/runner.js +++ b/tests/runner.js @@ -56,6 +56,7 @@ var specs = [ "spec/chatroom", "spec/minchats", "spec/notification", + "spec/login", "spec/register", "spec/http-file-upload" ];