Skip to content

Commit

Permalink
[IMP] web: Kanban: allow to archive/restore column records
Browse files Browse the repository at this point in the history
This feature has been removed in rev. e533085 but this commit
reintroduces it. It was considered as "too dangerous" for new users.

Instead of removing the feature, a confirmation request has been added to warn
the user about his potentially harmful action.

The same warning has also been added in List view when archiving records.

Task 60393

Co-authored-by: Mohammed Shekha <msh@openerp.com>
  • Loading branch information
2 people authored and mgeubelle committed Apr 25, 2018
1 parent b192431 commit 5c651a0
Show file tree
Hide file tree
Showing 6 changed files with 117 additions and 4 deletions.
24 changes: 24 additions & 0 deletions addons/web/static/src/js/views/kanban/kanban_column.js
Expand Up @@ -27,6 +27,8 @@ var KanbanColumn = Widget.extend({
'click .o_kanban_quick_add': '_onAddQuickCreate',
'click .o_kanban_load_more': '_onLoadMore',
'click .o_kanban_toggle_fold': '_onToggleFold',
'click .o_column_archive_records': '_onArchiveRecords',
'click .o_column_unarchive_records': '_onUnarchiveRecords'
},
/**
* @override
Expand Down Expand Up @@ -355,6 +357,28 @@ var KanbanColumn = Widget.extend({
ev.data.callback(record.$el, record.state.data);
});
},
/**
* @private
* @param {MouseEvent} event
*/
_onArchiveRecords: function (event) {
event.preventDefault();
Dialog.confirm(this, _t("Are you sure that you want to archive all the records from this column?"), {
confirm_callback: this.trigger_up.bind(this, 'kanban_column_records_toggle_active', {
archive: true,
}),
});
},
/**
* @private
* @param {MouseEvent} event
*/
_onUnarchiveRecords: function (event) {
event.preventDefault();
this.trigger_up('kanban_column_records_toggle_active', {
archive: false,
});
}
});

return KanbanColumn;
Expand Down
22 changes: 22 additions & 0 deletions addons/web/static/src/js/views/kanban/kanban_controller.js
Expand Up @@ -30,6 +30,7 @@ var KanbanController = BasicController.extend({
kanban_load_more: '_onLoadMore',
kanban_load_records: '_onLoadColumnRecords',
column_toggle_fold: '_onToggleColumn',
kanban_column_records_toggle_active: '_onToggleActiveRecords',
}),
/**
* @override
Expand Down Expand Up @@ -443,6 +444,27 @@ var KanbanController = BasicController.extend({
ev.data.force_save = true;
this._applyChanges(ev.target.db_id, changes, ev);
},
/**
* Allow the user to archive/restore all the records of a column.
*
* @private
* @param {OdooEvent} event
*/
_onToggleActiveRecords: function (event) {
var self = this;
var active = !event.data.archive;
var column = event.target;
var recordIds = _.pluck(column.records, 'db_id');
if (recordIds.length) {
this.model
.toggleActive(recordIds, active, column.db_id)
.then(function (dbID) {
var data = self.model.get(dbID);
self.renderer.updateColumn(dbID, data);
self._updateEnv();
});
}
},
});

return KanbanController;
Expand Down
8 changes: 7 additions & 1 deletion addons/web/static/src/js/views/list/list_controller.js
Expand Up @@ -10,6 +10,7 @@ odoo.define('web.ListController', function (require) {
var core = require('web.core');
var BasicController = require('web.BasicController');
var DataExport = require('web.DataExport');
var Dialog = require('web.Dialog');
var pyeval = require('web.pyeval');
var Sidebar = require('web.Sidebar');

Expand Down Expand Up @@ -136,6 +137,7 @@ var ListController = BasicController.extend({
* @param {jQuery Node} $node
*/
renderSidebar: function ($node) {
var self = this;
if (this.hasSidebar) {
var other = [{
label: _t("Export"),
Expand All @@ -144,7 +146,11 @@ var ListController = BasicController.extend({
if (this.archiveEnabled) {
other.push({
label: _t("Archive"),
callback: this._onToggleArchiveState.bind(this, true)
callback: function () {
Dialog.confirm(self, _t("Are you sure that you want to archive all the selected records?"), {
confirm_callback: self._onToggleArchiveState.bind(self, true),
});
}
});
other.push({
label: _t("Unarchive"),
Expand Down
4 changes: 4 additions & 0 deletions addons/web/static/src/xml/kanban.xml
Expand Up @@ -22,6 +22,10 @@
<li t-if="widget.editable and widget.id"><a class="o_column_edit" href="#">Edit Stage</a></li>
<li t-if="widget.deletable and widget.id"><a class="o_column_delete" href="#">Delete</a></li>
</t>
<t t-if="widget.has_active_field">
<li><a class="o_column_archive_records" href="#">Archive All</a></li>
<li><a class="o_column_unarchive_records" href="#">Restore All</a></li>
</t>
</ul>
</span>
<span t-if="widget.quick_create" class="o_kanban_quick_add"><i class="fa fa-plus"/></span>
Expand Down
55 changes: 53 additions & 2 deletions addons/web/static/tests/views/kanban_tests.js
Expand Up @@ -97,7 +97,7 @@ QUnit.module('Views', {
});

QUnit.test('basic grouped rendering', function (assert) {
assert.expect(11);
assert.expect(13);

var kanban = createView({
View: KanbanView,
Expand Down Expand Up @@ -135,6 +135,8 @@ QUnit.module('Views', {
"should not be able to edit the column");
assert.ok(!kanban.$('.o_kanban_header:first .o_kanban_config .o_column_delete').length,
"should not be able to delete the column");
assert.ok(!kanban.$('.o_kanban_header:first .o_kanban_config .o_column_archive_records').length, "should not be able to archive all the records");
assert.ok(!kanban.$('.o_kanban_header:first .o_kanban_config .o_column_unarchive_records').length, "should not be able to restore all the records");

// the next line makes sure that reload works properly. It looks useless,
// but it actually test that a grouped local record can be reloaded without
Expand All @@ -145,6 +147,51 @@ QUnit.module('Views', {
kanban.destroy();
});

QUnit.test('basic grouped rendering with active field', function (assert) {
assert.expect(9);

// add active field on partner model and make all records active
this.data.partner.fields.active = {string: 'Active', type: 'char', default: true};

var envIDs = [1, 2, 3, 4]; // the ids that should be in the environment during this test
var kanban = createView({
View: KanbanView,
model: 'partner',
data: this.data,
arch: '<kanban class="o_kanban_test">' +
'<field name="active"/>' +
'<field name="bar"/>' +
'<templates><t t-name="kanban-box">' +
'<div><field name="foo"/></div>' +
'</t></templates></kanban>',
groupBy: ['bar'],
intercepts: {
env_updated: function (event) {
assert.deepEqual(event.data.env.ids, envIDs,
"should notify the environment with the correct ids");
},
},
});

// check archive/restore all actions in kanban header's config dropdown
assert.ok(kanban.$('.o_kanban_header:first .o_kanban_config .o_column_archive_records').length, "should be able to archive all the records");
assert.ok(kanban.$('.o_kanban_header:first .o_kanban_config .o_column_unarchive_records').length, "should be able to restore all the records");

// archive the records of the first column
assert.strictEqual(kanban.$('.o_kanban_group:last .o_kanban_record').length, 3,
"last column should contain 3 records");
envIDs = [4];
kanban.$('.o_kanban_group:last .o_column_archive_records').click(); // Click on 'Archive All'
assert.ok($('.modal').length, 'a confirm modal should be displayed');
$('.modal .modal-footer .btn-default').click(); // Click on 'Cancel'
assert.strictEqual(kanban.$('.o_kanban_group:last .o_kanban_record').length, 3, "still last column should contain 3 records");
kanban.$('.o_kanban_group:last .o_column_archive_records').click();
assert.ok($('.modal').length, 'a confirm modal should be displayed');
$('.modal .modal-footer .btn-primary').click(); // Click on 'Ok'
assert.strictEqual(kanban.$('.o_kanban_group:last .o_kanban_record').length, 0, "last column should not contain any records");
kanban.destroy();
});

QUnit.test('pager should be hidden in grouped mode', function (assert) {
assert.expect(1);

Expand Down Expand Up @@ -1684,7 +1731,7 @@ QUnit.module('Views', {
});

QUnit.test('delete a column in grouped on m2o', function (assert) {
assert.expect(29);
assert.expect(33);

testUtils.patch(KanbanRenderer, {
_renderGrouped: function () {
Expand Down Expand Up @@ -1741,6 +1788,8 @@ QUnit.module('Views', {
"should be able to edit the column");
assert.ok(kanban.$('.o_kanban_group:first .o_column_delete').length,
"should be able to delete the column");
assert.ok(!kanban.$('.o_kanban_group:first .o_column_archive_records').length, "should not be able to archive all the records");
assert.ok(!kanban.$('.o_kanban_group:first .o_column_unarchive_records').length, "should not be able to restore all the records");

// delete second column (first cancel the confirm request, then confirm)
kanban.$('.o_kanban_group:last .o_column_delete').click(); // click on delete
Expand All @@ -1763,6 +1812,8 @@ QUnit.module('Views', {
'Undefined column could not be deleted');
assert.ok(!kanban.$('.o_kanban_group:first .o_column_edit').length,
'Undefined column could not be edited');
assert.ok(!kanban.$('.o_kanban_group:first .o_column_archive_records').length, "Records of undefined column could not be archived");
assert.ok(!kanban.$('.o_kanban_group:first .o_column_unarchive_records').length, "Records of undefined column could not be restored");
assert.verifySteps(['read_group', 'unlink', 'read_group']);
assert.strictEqual(kanban.renderer.widgets.length, 2,
"the old widgets should have been correctly deleted");
Expand Down
8 changes: 7 additions & 1 deletion addons/web/static/tests/views/list_tests.js
Expand Up @@ -843,7 +843,7 @@ QUnit.module('Views', {
});

QUnit.test('archiving one record', function (assert) {
assert.expect(9);
assert.expect(12);

// add active field on foo model and make all records active
this.data.foo.fields.active = {string: 'Active', type: 'boolean', default: true};
Expand Down Expand Up @@ -872,7 +872,13 @@ QUnit.module('Views', {

assert.verifySteps(['/web/dataset/search_read']);
list.sidebar.$('a:contains(Archive)').click();
assert.strictEqual($('.modal').length, 1, 'a confirm modal should be displayed');
$('.modal .modal-footer .btn-default').click(); // Click on 'Cancel'
assert.strictEqual(list.$('tbody td.o_list_record_selector').length, 4, "still should have 4 records");

list.sidebar.$('a:contains(Archive)').click();
assert.strictEqual($('.modal').length, 1, 'a confirm modal should be displayed');
$('.modal .modal-footer .btn-primary').click(); // Click on 'Ok'
assert.strictEqual(list.$('tbody td.o_list_record_selector').length, 3, "should have 3 records");
assert.verifySteps(['/web/dataset/search_read', '/web/dataset/call_kw/foo/write', '/web/dataset/search_read']);
list.destroy();
Expand Down

0 comments on commit 5c651a0

Please sign in to comment.