From deeebaff79c0a2d8c03fdc09953f38c4acdffca0 Mon Sep 17 00:00:00 2001 From: Robert Axelsen Date: Thu, 13 Jul 2017 12:04:03 +0200 Subject: [PATCH] TT#17654 Csc destination grid reordering changes What has been done 1. Handle read and write rendering of all non-number destination types, parsing sip-uri values from API to human readable types 2. Implement ability to add new destinations, also non-number types 3. Move "first ring" section to grid 4. Implement persistent reordering of destinations in grid, handling both changes in termination status, priority order and destinationset 5. Implement color indication of what destinations are terminated (inactive/active) and not 6. Implement logic for handling Ajax PATCH request based on destinationset 7. Some cleanup/refactoring, including change names for CallForward store and models, clean up models, defaultValue added where needed 8. Render combinations of destination types and timeouts correctly 9. Implement cft/cfu rules. Currently you can't reposition it 10. Implement dynamic handling of labels in grid Change-Id: I9f9252412d5ae921b8a4160a51b0acec8e8ea179 --- app/model/CallForward.js | 42 --- app/model/CallForwardDestination.js | 53 ++++ app/model/CallForwardSourceset.js | 9 +- app/model/CallForwardTimeset.js | 18 +- ...lForward.js => CallForwardDestinations.js} | 6 +- .../view/pages/callforward/CallForward.scss | 9 + classic/src/view/login/LoginController.js | 14 - .../callforward/CallForwardController.js | 300 +++++++++++------- .../pages/callforward/CallForwardMainForm.js | 90 +----- .../pages/callforward/CallForwardMainGrid.js | 31 +- .../callforward/CallForwardTimesetGrid.js | 9 +- .../callforward/afterhours/AfterHours.js | 2 +- .../view/pages/callforward/always/Always.js | 2 +- .../callforward/companyhours/CompanyHours.js | 2 +- 14 files changed, 292 insertions(+), 295 deletions(-) delete mode 100644 app/model/CallForward.js create mode 100644 app/model/CallForwardDestination.js rename app/store/{CallForward.js => CallForwardDestinations.js} (71%) diff --git a/app/model/CallForward.js b/app/model/CallForward.js deleted file mode 100644 index b15e7760..00000000 --- a/app/model/CallForward.js +++ /dev/null @@ -1,42 +0,0 @@ -Ext.define('NgcpCsc.model.CallForward', { - extend: 'Ext.data.Model', - - fields: [{ - name: 'id', - type: 'string' - }, { - name: 'type', - type: 'auto' - }, { - name: 'destination_cleaned', - type: 'auto' - }, { - name: 'destination_announcement_id', - type: 'auto' - }, { - name: 'destination', - type: 'auto' - }, { - name: 'priority', - type: 'auto' - }, { - name: 'simple_destination', - type: 'auto' - }, { - name: 'ring_for', - type: 'auto' - }, { - name: 'sourceset', - type: 'auto' - }, { - name: 'timeset', - type: 'auto' - }, { - name: 'destinationset_id', - type: 'auto' - }, { - name: 'destinationset_name', - type: 'auto' - }] - -}); diff --git a/app/model/CallForwardDestination.js b/app/model/CallForwardDestination.js new file mode 100644 index 00000000..c50b3732 --- /dev/null +++ b/app/model/CallForwardDestination.js @@ -0,0 +1,53 @@ +Ext.define('NgcpCsc.model.CallForwardDestination', { + extend: 'Ext.data.Model', + + fields: [{ + name: 'id', + type: 'string' + }, + { + name: 'type' + }, + { + name: 'destination_displayed' + }, + { + name: 'destination' + }, + { + name: 'after_termination', + defaultValue: false + }, + { + name: 'destination_announcement_id', + defaultValue: null + }, + { + name: 'priority', + defaultValue: '1' + }, + { + name: 'timeout_displayed' + }, + { + name: 'timeout' + }, + { + name: 'sourceset' + }, + { + name: 'timeset' + }, + { + name: 'destinationset_id' + }, + { + name: 'destinationset_name' + }, + { + name: 'label', + defaultValue: '' + } + ] + +}); diff --git a/app/model/CallForwardSourceset.js b/app/model/CallForwardSourceset.js index ecc13f39..8f65f3c0 100644 --- a/app/model/CallForwardSourceset.js +++ b/app/model/CallForwardSourceset.js @@ -5,14 +5,11 @@ Ext.define('NgcpCsc.model.CallForwardSourceset', { name: 'id', type: 'string' }, { - name: 'sourceset_name', - type: 'auto' + name: 'sourceset_name' }, { - name: 'sourceset_id', - type: 'auto' + name: 'sourceset_id' }, { - name: 'source', - type: 'auto' + name: 'source' }, { name: 'edit', type: 'boolean' diff --git a/app/model/CallForwardTimeset.js b/app/model/CallForwardTimeset.js index 9c8a0773..0ed9203b 100644 --- a/app/model/CallForwardTimeset.js +++ b/app/model/CallForwardTimeset.js @@ -5,23 +5,17 @@ Ext.define('NgcpCsc.model.CallForwardTimeset', { name: 'id', type: 'string' }, { - name: 'timeset_name', - type: 'auto' + name: 'timeset_name' }, { - name: 'timeset_id', - type: 'auto' + name: 'timeset_id' }, { - name: 'time_from', - type: 'auto' + name: 'time_from' }, { - name: 'time_to', - type: 'auto' + name: 'time_to' }, { - name: 'day', - type: 'auto' + name: 'day' }, { - name: 'closed', - type: 'auto' + name: 'closed' }] }); diff --git a/app/store/CallForward.js b/app/store/CallForwardDestinations.js similarity index 71% rename from app/store/CallForward.js rename to app/store/CallForwardDestinations.js index f9eca466..e4e115ae 100644 --- a/app/store/CallForward.js +++ b/app/store/CallForwardDestinations.js @@ -1,9 +1,9 @@ -Ext.define('NgcpCsc.store.CallForward', { +Ext.define('NgcpCsc.store.CallForwardDestinations', { extend: 'Ext.data.Store', - storeId: 'CallForward', + storeId: 'CallForwardDestinations', - model: 'NgcpCsc.model.CallForward', + model: 'NgcpCsc.model.CallForwardDestination', proxy: { type: 'ngcp-api', diff --git a/classic/sass/src/view/pages/callforward/CallForward.scss b/classic/sass/src/view/pages/callforward/CallForward.scss index 5b57b235..93a55780 100644 --- a/classic/sass/src/view/pages/callforward/CallForward.scss +++ b/classic/sass/src/view/pages/callforward/CallForward.scss @@ -92,3 +92,12 @@ } } } + +.below-termination { + background: #FFB0C4; + color: grey; +} +.above-termination { + background: #B0FFC5; + color: black; +} diff --git a/classic/src/view/login/LoginController.js b/classic/src/view/login/LoginController.js index e5c71d12..97a190fa 100644 --- a/classic/src/view/login/LoginController.js +++ b/classic/src/view/login/LoginController.js @@ -50,20 +50,6 @@ Ext.define('NgcpCsc.view.login.LoginController', { } }, - loadSubscriberDomain: function () { - Ext.Ajax.request({ - url: window.location.origin + '/api/subscribers/' + localStorage.getItem('subscriber_id'), - success: function(response, opts) { - var decodedResponse = Ext.decode(response.responseText); - var domain = decodedResponse.domain; - localStorage.setItem('domain', domain); - }, - failure: function(response, opts) { - console.log('server-side failure with status code ' + response.status); - } - }); - }, - unsuccessLogin: function(response) { localStorage.removeItem('jwt'); Ext.Msg.alert('Error', 'Username or Password not valid!'); diff --git a/classic/src/view/pages/callforward/CallForwardController.js b/classic/src/view/pages/callforward/CallForwardController.js index d7ec2ba8..6db40286 100644 --- a/classic/src/view/pages/callforward/CallForwardController.js +++ b/classic/src/view/pages/callforward/CallForwardController.js @@ -21,12 +21,23 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { } }, - destinationDropped: function (node, data, overModel, dropPosition, eOpts) { - // TODO: Leaving uncommented code here for upcoming task #17654 - // var store = Ext.getStore('everybody-always-CallForwardBusy'); - // Ext.each(store.getRange(), function(record) { - // console.log(record.get('destination_cleaned')); - // }) + destinationDropped: function(node, data, overModel, dropPosition, eOpts) { + var dropRec = data.records[0]; + var store = overModel.store; + var recIndex = store.indexOf(dropRec); + var adjacentRec = dropPosition === 'before' ? store.getAt(recIndex+1) : store.getAt(recIndex-1); + var destinationsetId = adjacentRec.get('destinationset_id') === dropRec.get('destinationset_id') ? dropRec.get('destinationset_id') : adjacentRec.get('destinationset_id'); + var destinationsetName = adjacentRec.get('destinationset_name') === dropRec.get('destinationset_name') ? dropRec.get('destinationset_name') : adjacentRec.get('destinationset_name'); + var afterTermination = adjacentRec.get('after_termination') === dropRec.get('after_termination') ? dropRec.get('after_termination') : adjacentRec.get('after_termination'); + var priority = adjacentRec.get('priority') === dropRec.get('priority') ? dropRec.get('priority') : adjacentRec.get('priority'); + var type = adjacentRec.get('type') === dropRec.get('type') ? dropRec.get('type') : adjacentRec.get('type'); + dropRec.set('destinationset_id', destinationsetId); + dropRec.set('destinationset_name', destinationsetName); + dropRec.set('after_termination', afterTermination); + dropRec.set('priority', priority); + dropRec.set('type', type); + this.setLabelTerminationType(store); + store.sync(); }, cfTimesetStoreLoaded: function(store, data) { @@ -46,7 +57,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { if (/(After|Company)\s(Hours)/.test(timesetName)) { var times = me.getModelValuesFromTimesData(timeset.times[0]); Ext.each(times.days, function (weekday) { - var cfModel = Ext.create('NgcpCsc.model.CallForward', { + var cfModel = Ext.create('NgcpCsc.model.CallForwardDestination', { id: Ext.id(), timeset_name: timesetName, timeset_id: timesetId, @@ -95,7 +106,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { var sourcesetId = sourceset.id; me.setVmToTrue(sourcesetName); Ext.each(sourceset.sources, function (sourceEntry) { - var cfModel = Ext.create('NgcpCsc.model.CallForward', { + var cfModel = Ext.create('NgcpCsc.model.CallForwardDestination', { id: Ext.id(), sourceset_name: sourcesetName, sourceset_id: sourcesetId, @@ -125,6 +136,24 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { }; }, + sortDestinationsetByPriority: function (destinations) { + var sorted = destinations.sort(function(a, b) { + return parseFloat(a.priority) - parseFloat(b.priority); + }); + return sorted; + }, + + addCftOwnPhone: function (destinations) { + if (destinations.length > 0) { + destinations.unshift({ + "announcement_id": null, + "destination": "own phone", + "priority": 1, + "timeout": 15 + }) + } + }, + cfStoreLoaded: function(store, data) { var me = this; var cfTypeArrayOfObjects = [data.get('cfu'), data.get('cft'), data.get('cfb'), data.get('cfna')]; @@ -143,9 +172,11 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { var decodedResponse = Ext.decode(response.responseText); if (decodedResponse._embedded) { var destinationsets = decodedResponse._embedded['ngcp:cfdestinationsets']; + destinationsets[0].destinations = me.sortDestinationsetByPriority(destinationsets[0].destinations); me.getView()._preventReLoad = true; // assumes there is no need to reload the store Ext.each(cfTypeArrayOfObjects, function (cfTypeObjects, index) { var cfType = cfTypes[index]; + cfType !== 'cft' && me.addCftOwnPhone(destinationsets[0].destinations); // if 'cft' we invoke addCftOwnPhone() Ext.each(cfTypeObjects, function(cfTypeObject) { var destinationsetName = cfTypeObject.destinationset; var sourcesetName = cfTypeObject.sourceset; @@ -154,22 +185,23 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { Ext.each(destinationsets, function(destinationset) { if (destinationset.name == destinationsetName) { for (item in destinationset.destinations) { - var destinationToUse = me.getDestinationFromSipId(destinationset.destinations[item].destination); + var destinationToDisplayInGrid = me.getDestinationFromSipId(destinationset.destinations[item].destination); var destinationAnnouncementId = destinationset.announcement_id; var destination = destinationset.destinations[item].destination; var priority = destinationset.destinations[item].priority; - var simpleDestination = destinationset.destinations[item].simple_destination; + var timeout = destinationset.destinations[item].timeout; var destinationId = destinationset.id; var destinationName = destinationset.name; - var ringFor = destinationToUse == 'Voicemail' ? '' : destinationset.destinations[item].timeout; - var cbModel = Ext.create('NgcpCsc.model.CallForward', { + // Removes timeout if destination is not a number + var ringFor = !Ext.isNumber(parseInt(destinationToDisplayInGrid)) ? '' : destinationset.destinations[item].timeout; + var cbModel = Ext.create('NgcpCsc.model.CallForwardDestination', { type: cfType, - destination_cleaned: destinationToUse, - destination_announcement_id: destinationAnnouncementId, + destination_displayed: destinationToDisplayInGrid, destination: destination, + destination_announcement_id: destinationAnnouncementId, priority: priority, - simple_destination: simpleDestination, - ring_for: ringFor, + timeout_displayed: ringFor, + timeout: timeout, sourceset: sourcesetName, timeset: timesetName, destinationset_id: destinationId, @@ -202,24 +234,34 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { }, cfStoreBeforeSync: function(store, options) { - // TODO: #17654 Ensure we also have ability to display and write all - // required destination types, like voicemail, fax, conference, etc var me = this; var recordsToSend = []; delete options['destroy']; delete options['create']; + delete options['update']; Ext.each(store.getRange(), function(record) { var data = record.getData(); - switch (recordsToSend.length === 0 || !me.destinationIdExistsInArray(recordsToSend, data.destinationset_id)) { - case true: - recordsToSend.push({id: data.destinationset_id, records: [{ "announcement_id": null, "destination": data.simple_destination, "priority": data.priority, "timeout": data.ring_for }]}); - break; - case false: - recordsToSend.forEach(function (obj, index) { - if (obj.id == data.destinationset_id) { - recordsToSend[index].records.push({ "announcement_id": null, "destination": data.simple_destination, "priority": data.priority, "timeout": data.ring_for }); - } - }) + if (data.destination !== 'own phone') { + switch (recordsToSend.length === 0 || !me.destinationIdExistsInArray(recordsToSend, data.destinationset_id)) { + case true: + recordsToSend.push({id: data.destinationset_id, records: [{ + "announcement_id": null, + "destination": data.destination, + "priority": data.priority, + "timeout": data.timeout }]}); + break; + case false: + recordsToSend.forEach(function (obj, index) { + if (obj.id == data.destinationset_id) { + recordsToSend[index].records.push({ + "announcement_id": null, + "destination": data.destination, + "priority": data.priority, + "timeout": data.timeout }); + }; + }); + break; + }; }; }); Ext.each(recordsToSend, function (obj) { @@ -274,54 +316,36 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { return false; }, - timesBasedOnRecords: function (store) { - // TODO: Started this, but then discovered the issue leading to creation - // of #18401. Leaving the code in place for upcoming task #18401 - var recordsToSend = []; - Ext.each(store.getRange(), function(record) { - var data = record.getData(); - // console.log(data.time_from); - // console.log(data.time_to); - // For fields of data that have been changed in the grid, data is in - // this format: - // Tue Jan 01 2008 13:00:00 GMT+0100 (CET) - }); - return recordsToSend; - }, - cfTimesetBeforeSync: function (store, options) { delete options['destroy']; delete options['create']; delete options['update']; - var timesetId = store.last().get('timeset_id'); - // var recordsToSend = this.timesBasedOnRecords(store); - // TODO: Example ajax request for #18401 - // Ext.Ajax.request({ - // url: '/api/cftimesets/' + timesetId, - // method: 'PATCH', - // headers: { 'Content-Type': 'application/json-patch+json' }, - // jsonData: [{ - // "op": "add", - // "path": "/times", - // "value": recordsToSend - // }], - // success: function(response, opts) { - // console.log('server-side success with status code ' + response.status); - // }, - // failure: function(response, opts) { - // console.log('server-side failure with status code ' + response.status); - // } - // }); return false; }, getDestinationFromSipId: function (destination) { - var splitDestination = destination.split(/(:|@)/); - if (splitDestination[4] == 'voicebox.local') { - return 'Voicemail'; - } else { - return splitDestination[2]; - } + var splitDestination = destination === 'own phone' ? [null, null, 'own phone', null, null] : destination.split(/(:|@)/); + switch (splitDestination[4]) { + case 'voicebox.local': + return 'Voicemail'; + break; + case 'conference.local': + return 'Conference'; + break; + case 'fax2mail.local': + return 'Fax2Mail'; + break; + default: + // Returns parsed destination URI/Number types to make them + // human readable in grid, as well as for any app.local types + // that might exist (callingcard, callthrough, autoattendant, + // officehours, customhours, localuser) + if (!Ext.isNumber(parseInt(splitDestination[2]))) { + return Ext.util.Format.capitalize(splitDestination[2]); + } else { + return splitDestination[2]; + }; + }; }, getGridCategoryFromType: function (type) { @@ -336,7 +360,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { case 'cfna': return 'CallForwardOffline'; break; - } + }; }, getTypeFromTypeName: function (type) { @@ -350,7 +374,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { case 'Offline': return 'cfna'; break; - } + }; }, getSourceNameFromSourceSet: function (sourceset) { @@ -364,7 +388,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { case null: return 'everybody-'; break; - } + }; }, getSourceSetFromSourceName: function (sourceset) { @@ -378,7 +402,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { case null: return null; break; - } + }; }, getTimeNameFromTimeSet: function (timeset) { @@ -465,12 +489,60 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { }; }, + setLabelTerminationType: function (store) { + var terminationPositionRecord = store.findRecord('destination_displayed', /(Voicemail|Fax2Mail|Conference|Custom-hours|Office-hours|Auto-attendant|Callthrough|Callingcard)/); + var storeCount = store.getCount(); + // Sets after_termination value for all records after first non-number + if (terminationPositionRecord && terminationPositionRecord.get('destination_displayed')) { + var terminationPositionIndex = store.indexOf(terminationPositionRecord); + var terminationTrueIndexRange = []; + var terminationFalseIndexRange = []; + for (i = terminationPositionIndex+1; i < storeCount; i++) { + terminationTrueIndexRange.push(i); + }; + for (i = terminationPositionIndex; i >= 0; i--) { + terminationFalseIndexRange.push(i); + }; + terminationTrueIndexRange.map(function (index) { + store.getAt(index).set('after_termination', true); + }); + terminationFalseIndexRange.map(function (index) { + store.getAt(index).set('after_termination', false); + }); + }; + // Set all cft records to after_termination true if cfu records exist + if (store.findRecord('type', 'cfu') && store.findRecord('type', 'cft')) { + Ext.each(store.getRange(), function(record) { + if (!record.get('after_termination') && record.get('type') === 'cft') { + record.set('after_termination', true); + }; + }); + }; + // Sorts "own phone" to top plus prevents it from being reordered + Ext.each(store.getRange(), function(record) { + if (record.get('destination') === 'own phone') { + record.set('label', 'first ring'); + record.set('after_termination', false); + store.remove(record); + store.insert(0, record); + }; + }); + // Sets "first ring", "then forward to ..." and "" (empty) labels + Ext.each(store.getRange(), function(record, index) { + if (index === 0) { + record.set('label', 'first ring'); + } else if (index === 1) { + record.set('label', 'then forward to ...'); + } else { + record.set('label', ''); + } + }); + }, + populateDestinationStores: function (models) { var me = this; - var gridName = this.getGridCategoryFromType(models[0].get('type')); var store; - // TODO: #17654 New grid logic and styling with conditions for cft/cfu, - // and remove first ring section + var stores = []; Ext.each(models, function (model) { var sourcename = me.getSourceNameFromSourceSet(model.get('sourceset')); var timename = me.getTimeNameFromTimeSet(model.get('timeset')); @@ -479,10 +551,14 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { store = Ext.getStore(storeName); if (store) { store.add(model); + stores.push(store); } }); if (store) { - store.commitChanges(); + Ext.each(stores, function (store) { + store.commitChanges(); + me.setLabelTerminationType(store); + }); } }, @@ -661,7 +737,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { }, success: function(response, opts) { var sourcesetId = response.getResponseHeader('Location').split('/')[3]; - var cfSourcesetModel = Ext.create('NgcpCsc.model.CallForward', { + var cfSourcesetModel = Ext.create('NgcpCsc.model.CallForwardSourceset', { id: Ext.id(), source: " ", sourceset_name: sourcesetName, @@ -720,11 +796,13 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { }, confirmCFRemoval: function(record) { + var me = this; var store = record.store; if(store){ store.remove(record); store.sync(); - } + me.setLabelTerminationType(store); + }; }, getStoresArrayFromRoute: function(currentRoute, currentSourceset) { @@ -779,12 +857,14 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { }, renderDestinationColumn: function(value, metaData, record) { - if (record.get('ring_for') === '' && !Ext.isNumber(parseInt(value))) { + if (record.get('timeout_displayed') === '' && !Ext.isNumber(parseInt(value))) { return Ext.String.format('{0}', value); + } else if (record.get('destination') === 'own phone') { + return Ext.String.format('own phone and ring for {0} secs', record.get('timeout_displayed')); } else if (Ext.isNumber(parseInt(value))) { - return Ext.String.format('+{0} and ring for {1} secs', value, record.get('ring_for')); + return Ext.String.format('+{0} and ring for {1} secs', value, record.get('timeout_displayed')); } else { - return Ext.String.format('{0} and ring for {1} secs', value, record.get('ring_for')); + return Ext.String.format('{0} and ring for {1} secs', value, record.get('timeout_displayed')); }; }, @@ -942,8 +1022,8 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { var simpleDestination = destination; var priority = 1; var storeCount = store.getCount(); - var ringFor = destination == 'Voicemail' ? '' : timeout; - var destinationCleaned = destination; + // Removes timeout if destination is not a number + var ringFor = !Ext.isNumber(parseInt(destination)) ? '' : timeout; var storeIdSplit = store.storeId.split('-'); var newSourcesetName = storeIdSplit[0] == 'everybody' ? null : storeIdSplit[0]; var newTimesetName = storeIdSplit[1] == 'always' ? null : storeIdSplit[1]; @@ -951,39 +1031,36 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { var newSourceset = this.getSourceSetFromSourceName(newSourcesetName); var newTimeset = this.getTimeSetFromTimeSource(newTimesetName); var newType = this.getTypeFromTypeName(newTypeName); - var newDomain = localStorage.getItem('domain'); - // TODO: #17654 Consider the fact that one destinationset can be in - // several grids, so if you write one, update all other grids with - // that same destinationset id + var newDestination = destination === 'Voicemail' ? 'voicebox' : destination.toLowerCase(); + // TODO: Sets default timeout to 10 for non-number types, as can not be + // set to null. Not sure if this has any implication, so needs to be + // checked with Andreas + var newTimeout = !timeout ? '10' : timeout; if (!store.last()) { // if store empty we need to create new destset var newDestinationsetName = 'csc_defined_' + newType; var subscriberId = localStorage.getItem('subscriber_id'); Ext.Ajax.request({ url: '/api/cfdestinationsets/', method: 'POST', - defaultHeaders: 'Prefer: return=representation', jsonData: { name: newDestinationsetName, subscriber_id: subscriberId }, success: function(response, opts) { var destinationsetId = response.getResponseHeader('Location').split('/')[3]; - var cfModel = Ext.create('NgcpCsc.model.CallForward', { + var cfModel = Ext.create('NgcpCsc.model.CallForwardDestination', { type: newType, - destination_cleaned: destinationCleaned, - destination_announcement_id: null, - destination: 'sip:' + destination + '@' + newDomain, - // Keeping priority 1 as default for now, as we'll handle priotity - // with grid "drag-and-drop" widget plugin in upcoming task - priority: 1, - simple_destination: destination, - ring_for: ringFor, + destination_displayed: destination, + destination: newDestination, + timeout_displayed: ringFor, + timeout: newTimeout, sourceset: newSourceset, timeset: newTimeset, destinationset_id: destinationsetId, destinationset_name: newDestinationsetName }); store.add(cfModel); + me.setLabelTerminationType(store); store.sync(); // Creates new sourceset/timeset if variable is not set to null newSourceset && me.createNewStandardSet('/api/cfsourcesets/', newSourceset, subscriberId); @@ -996,20 +1073,30 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { }); } else { var lastRecordInStore = store.last(); - var cfModel = Ext.create('NgcpCsc.model.CallForward', { + var afterTermination = false; + switch (true) { + case (!lastRecordInStore.get('after_termination') && !Ext.isNumber(parseInt(lastRecordInStore.get('destination_displayed')))): + afterTermination = true; + break; + case (lastRecordInStore.get('after_termination')): + afterTermination = true; + break; + }; + var cfModel = Ext.create('NgcpCsc.model.CallForwardDestination', { type: lastRecordInStore.get('type'), - destination_cleaned: destinationCleaned, - destination_announcement_id: null, - destination: 'sip:' + destination + '@' + newDomain, - priority: 1, - simple_destination: destination, - ring_for: ringFor, + destination_displayed: destination, + destination: newDestination, + after_termination: afterTermination, + priority: lastRecordInStore.get('priority'), + timeout_displayed: ringFor, + timeout: newTimeout, sourceset: lastRecordInStore.get('sourceset'), timeset: lastRecordInStore.get('timeset'), destinationset_id: lastRecordInStore.get('destinationset_id'), destinationset_name: lastRecordInStore.get('destinationset_name') }); store.add(cfModel); + me.setLabelTerminationType(store); store.sync(); } }, @@ -1040,9 +1127,4 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardController', { store.sync(); } - // TODO #18401, maybe use a blur or change listener on editors in grid - // editingTimeDone: function () { - // - // } - }); diff --git a/classic/src/view/pages/callforward/CallForwardMainForm.js b/classic/src/view/pages/callforward/CallForwardMainForm.js index 5284ff9d..eab01896 100644 --- a/classic/src/view/pages/callforward/CallForwardMainForm.js +++ b/classic/src/view/pages/callforward/CallForwardMainForm.js @@ -37,17 +37,20 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardMainForm', { store: storeListB }); var busyGrid = Ext.create('NgcpCsc.view.pages.callforward.CallForwardMainGrid', { - store: Ext.create('NgcpCsc.store.CallForward', { + id: this._firstprefix + this._secondprefix + 'CallForwardBusy', + store: Ext.create('NgcpCsc.store.CallForwardDestinations', { storeId: this._firstprefix + this._secondprefix + 'CallForwardBusy' }) }); var onlineGrid = Ext.create('NgcpCsc.view.pages.callforward.CallForwardMainGrid', { - store: Ext.create('NgcpCsc.store.CallForward', { + id: this._firstprefix + this._secondprefix + 'CallForwardOnline', + store: Ext.create('NgcpCsc.store.CallForwardDestinations', { storeId: this._firstprefix + this._secondprefix + 'CallForwardOnline' }) }); var offlineGrid = Ext.create('NgcpCsc.view.pages.callforward.CallForwardMainGrid', { - store: Ext.create('NgcpCsc.store.CallForward', { + id: this._firstprefix + this._secondprefix + 'CallForwardOffline', + store: Ext.create('NgcpCsc.store.CallForwardDestinations', { storeId: this._firstprefix + this._secondprefix + 'CallForwardOffline' }) }); @@ -94,20 +97,11 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardMainForm', { layout: 'hbox', margin: '15 0 0 0', items: [ - // NOTE: Commenting out this now, and will tackle it as part of #17651 - // { - // xtype: 'button', - // html: Ngcp.csc.locales.callforward.change_title[localStorage.getItem('languageSelected')], - // id: this._firstprefix + this._secondprefix + 'lista_titleField-showButton', - // margin: '0 0 0 500', - // handler: 'toggleChangeTitle' - // }, { xtype: 'button', text: Ngcp.csc.locales.callforward.add_new_source[localStorage.getItem('languageSelected')], id: this._firstprefix + this._secondprefix + 'addListAButton', margin: '0 0 0 620', - // margin: '0 0 0 10', width: 135, listeners: { click: 'addEmptySourcesetRow' @@ -158,21 +152,12 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardMainForm', { hidden: '{list_b}' }, items: [ - // NOTE: Commenting out this now, and will tackle it as part of #17651 - // { - // xtype: 'button', - // html: Ngcp.csc.locales.callforward.change_title[localStorage.getItem('languageSelected')], - // id: this._firstprefix + this._secondprefix + 'listb_titleField-showButton', - // margin: '0 0 0 500', - // handler: 'toggleChangeTitle' - // }, { xtype: 'button', text: Ngcp.csc.locales.callforward.add_new_source[localStorage.getItem('languageSelected')], id: this._firstprefix + this._secondprefix + 'addListBButton', width: 135, margin: '0 0 0 620', - // margin: '0 0 0 10', listeners: { click: 'addEmptySourcesetRow' } @@ -182,60 +167,11 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardMainForm', { xtype: 'container', userCls: 'cf-text cf-subheader', html: Ngcp.csc.locales.callforward.when_phone_online[localStorage.getItem('languageSelected')] - }, { - xtype: 'panel', - layout: 'hbox', - id: this._firstprefix + this._secondprefix + 'onlineFirstRingFields', - padding: '0 11 0 0', - width: 500, - margin: '0 0 0 50', - items: [{ - xtype: 'combo', - store: 'FirstRingActions', - valueField: 'name', - displayField: 'name', - id: this._firstprefix + this._secondprefix + 'onlineFirstDest', - fieldLabel: Ngcp.csc.locales.callforward.first_ring[localStorage.getItem('languageSelected')], - value: 'Own phone', - allowBlank: false, - editable: false, - listeners: { - change: 'selectRing' - }, - flex: 5 - }, { - xtype: 'numberfield', - step: 10, - minValue:0, - maxValue: 300, - value: '10', - id: this._firstprefix + this._secondprefix + 'onlineFirstTimeout', - allowBlank: false, - editable: true, - flex: 4, - margin: '0 0 0 10', - bind: { - hidden: '{online_first_timeout_hidden}' - }, - fieldLabel: Ngcp.csc.locales.callforward.and_ring_for[localStorage.getItem('languageSelected')] - }, { - xtype: 'container', - html: Ngcp.csc.locales.callforward.secs[localStorage.getItem('languageSelected')], - padding: '7 0 0 20', - flex: 1, - bind: { - hidden: '{online_first_timeout_hidden}' - } - }] }, { xtype: 'container', layout: 'hbox', margin: '10 0 0 50', - items: [{ - xtype: 'container', - html: Ngcp.csc.locales.callforward.then_forward_to[localStorage.getItem('languageSelected')], - userCls: 'cf-thentext' - }, + items: [ onlineGrid ] }, { @@ -337,11 +273,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardMainForm', { xtype: 'container', layout: 'hbox', margin: '10 0 0 50', - items: [{ - xtype: 'container', - html: Ngcp.csc.locales.callforward.forward_to[localStorage.getItem('languageSelected')], - userCls: 'cf-thentext' - }, + items: [ busyGrid ] }, { @@ -443,11 +375,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardMainForm', { xtype: 'container', layout: 'hbox', margin: '10 0 0 50', - items: [{ - xtype: 'container', - html: Ngcp.csc.locales.callforward.forward_to[localStorage.getItem('languageSelected')], - userCls: 'cf-thentext' - }, + items: [ offlineGrid ] }, { diff --git a/classic/src/view/pages/callforward/CallForwardMainGrid.js b/classic/src/view/pages/callforward/CallForwardMainGrid.js index b61f90c9..b74d852d 100644 --- a/classic/src/view/pages/callforward/CallForwardMainGrid.js +++ b/classic/src/view/pages/callforward/CallForwardMainGrid.js @@ -14,30 +14,22 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardMainGrid', { dragText: Ngcp.csc.locales.callforward.drag_text[localStorage.getItem('languageSelected')] }, markDirty: false, - emptyText: Ngcp.csc.locales.callforward.nowhere[localStorage.getItem('languageSelected')], + emptyText: Ngcp.csc.locales.callforward.forward_to[localStorage.getItem('languageSelected')] + '' + Ngcp.csc.locales.callforward.nowhere[localStorage.getItem('languageSelected')] + '', deferEmptyText: false, stripeRows: false, listeners: { drop: 'destinationDropped' + }, + getRowClass: function(record, index) { + var afterTermination = record.get('after_termination'); + if (afterTermination) { + return 'below-termination'; + } else { + return 'above-termination'; + } } }, - // TODO: Leaving this for PUT/PATCH task, as it might make sense to use - // with unmask triggered in controller - // listeners: { - // render: function(grid) { - // grid.body.mask('Loading...'); - // var store = grid.getStore(); - // Ext.defer(function() { - // store.load; - // }, 100); - // Ext.defer(function() { - // grid.body.unmask(); - // }, 600); - // }, - // delay: 200 - // }, - plugins: { ptype: 'cellediting', clicksToEdit: 1 @@ -47,7 +39,10 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardMainGrid', { var me = this; me.columns = [{ - dataIndex: 'destination_cleaned', // Renderer also uses ring_for value + dataIndex: 'label', + width: 135 + }, { + dataIndex: 'destination_displayed', // Renderer also uses ring_for value width: 285, renderer: 'renderDestinationColumn' }, { diff --git a/classic/src/view/pages/callforward/CallForwardTimesetGrid.js b/classic/src/view/pages/callforward/CallForwardTimesetGrid.js index d2e6678c..5514c48d 100644 --- a/classic/src/view/pages/callforward/CallForwardTimesetGrid.js +++ b/classic/src/view/pages/callforward/CallForwardTimesetGrid.js @@ -7,11 +7,6 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardTimesetGrid', { markDirty: false }, - // TODO: #18401 - // listeners: { - // edit: 'editingTimeDone' - // }, - initComponent: function() { this.columns = { defaults: { @@ -25,7 +20,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardTimesetGrid', { flex: 1 }, { text: Ngcp.csc.locales.common.from[localStorage.getItem('languageSelected')], - dataIndex: 'time_from', // TODO: #18401 Add listener + dataIndex: 'time_from', xtype: 'widgetcolumn', editable: false, flex: 1, @@ -39,7 +34,7 @@ Ext.define('NgcpCsc.view.pages.callforward.CallForwardTimesetGrid', { } }, { text: Ngcp.csc.locales.common.to[localStorage.getItem('languageSelected')], - dataIndex: 'time_to', // TODO: #18401 Add listener + dataIndex: 'time_to', xtype: 'widgetcolumn', editable: false, flex: 1, diff --git a/classic/src/view/pages/callforward/afterhours/AfterHours.js b/classic/src/view/pages/callforward/afterhours/AfterHours.js index 4e5dacb2..42e46781 100644 --- a/classic/src/view/pages/callforward/afterhours/AfterHours.js +++ b/classic/src/view/pages/callforward/afterhours/AfterHours.js @@ -6,7 +6,7 @@ Ext.define('NgcpCsc.view.pages.callforward.afterhours.Afterhours', { ui: 'cf-mainform', initComponent: function() { - var cfInitialStore = Ext.create('NgcpCsc.store.CallForward', { + var cfInitialStore = Ext.create('NgcpCsc.store.CallForwardDestinations', { storeId: 'CallForwardAfterHours', _type: 'afterHours', autoLoad: true, diff --git a/classic/src/view/pages/callforward/always/Always.js b/classic/src/view/pages/callforward/always/Always.js index 4a270ffa..760488cb 100644 --- a/classic/src/view/pages/callforward/always/Always.js +++ b/classic/src/view/pages/callforward/always/Always.js @@ -8,7 +8,7 @@ Ext.define('NgcpCsc.view.pages.callforward.always.Always', { viewModel: 'callforward', initComponent: function() { - var cfInitialStore = Ext.create('NgcpCsc.store.CallForward',{ + var cfInitialStore = Ext.create('NgcpCsc.store.CallForwardDestinations',{ storeId: 'CallForwardAlways', _type: 'always', autoLoad: true, diff --git a/classic/src/view/pages/callforward/companyhours/CompanyHours.js b/classic/src/view/pages/callforward/companyhours/CompanyHours.js index 91d48fc5..41af35b1 100644 --- a/classic/src/view/pages/callforward/companyhours/CompanyHours.js +++ b/classic/src/view/pages/callforward/companyhours/CompanyHours.js @@ -6,7 +6,7 @@ Ext.define('NgcpCsc.view.pages.callforward.companyhours.Companyhours', { ui: 'cf-mainform', initComponent: function() { - var cfInitialStore = Ext.create('NgcpCsc.store.CallForward', { + var cfInitialStore = Ext.create('NgcpCsc.store.CallForwardDestinations', { storeId: 'CallForwardCompanyHours', _type: 'companyHours', autoLoad: true,