Skip to content

Commit 556824e

Browse files
committed
add remote mode
1 parent f4fb20c commit 556824e

File tree

4 files changed

+160
-42
lines changed

4 files changed

+160
-42
lines changed

src/components/NewTicket.vue

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -166,6 +166,22 @@ export default {
166166
formData.CustomCreated = true;
167167
formData.ticket = this.ticketsLength + 1;
168168
169+
// Save the ticket in localStorage
170+
let localTickets = [];
171+
if (localStorage.getItem('local-tickets')) {
172+
try {
173+
localTickets = JSON.parse(localStorage.getItem('local-tickets'));
174+
}
175+
catch (e) {
176+
localStorage.removeItem('local-tickets');
177+
}
178+
}
179+
localTickets.unshift(formData);
180+
// save it in localstorage
181+
let jsonString = JSON.stringify(localTickets);
182+
localStorage.removeItem('local-tickets');
183+
localStorage.setItem('local-tickets', jsonString);
184+
169185
this.$emit('new-ticket-data', formData);
170186
this.form = {
171187
"Requestor": null,

src/components/TicketsTable/ColumnOptions.js

Lines changed: 14 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@ export default {
1313
field: 'RequestorSeniority',
1414
globalSearchDisabled: true,
1515
sortable: true,
16-
sortFn: this.sortValueAfterHyphen,
1716
formatFn: this.showValueAfterHyphen,
1817
filterOptions: {
1918
enabled: true,
@@ -35,19 +34,30 @@ export default {
3534
{
3635
label: 'Filed Against',
3736
field: 'FiledAgainst',
38-
sortable: true
37+
globalSearchDisabled: true,
38+
sortable: true,
39+
filterOptions: {
40+
enabled: true,
41+
placeholder: "Filter",
42+
filterDropdownItems: ["Access/Login", "Hardware", "Software", "Systems"]
43+
}
3944
},
4045
{
4146
label: 'Ticket Type',
4247
field: 'TicketType',
43-
sortable: true
48+
globalSearchDisabled: true,
49+
sortable: true,
50+
filterOptions: {
51+
enabled: true,
52+
placeholder: "Filter",
53+
filterDropdownItems: ["Issue", "Request"]
54+
}
4455
},
4556
{
4657
label: 'Severity',
4758
field: 'Severity',
4859
globalSearchDisabled: true,
4960
sortable: true,
50-
sortFn: this.sortValueAfterHyphen,
5161
formatFn: this.showValueAfterHyphen,
5262
filterOptions: {
5363
enabled: true,
@@ -65,7 +75,6 @@ export default {
6575
field: 'Priority',
6676
globalSearchDisabled: true,
6777
sortable: true,
68-
sortFn: this.sortValueAfterHyphen,
6978
formatFn: this.showValueAfterHyphen,
7079
filterOptions: {
7180
enabled: true,
@@ -89,7 +98,6 @@ export default {
8998
field: 'Satisfaction',
9099
globalSearchDisabled: true,
91100
sortable: true,
92-
sortFn: this.sortValueAfterHyphen,
93101
formatFn: this.showValueAfterHyphen,
94102
filterOptions: {
95103
enabled: true,
@@ -111,13 +119,6 @@ export default {
111119
}
112120
},
113121
methods: {
114-
sortValueAfterHyphen(x, y) {
115-
// x - row1 value for column
116-
// y - row2 value for column
117-
x = x.split("-").pop().trim();
118-
y = y.split("-").pop().trim();
119-
return (x < y ? -1 : (x > y ? 1 : 0));
120-
},
121122
showValueAfterHyphen(inputString) {
122123
return inputString.split("-").pop().trim();
123124
}

src/components/TicketsTable/SortFilterSearch.js

Lines changed: 92 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,10 @@
11
export default {
22
methods: {
3-
onColumnFilter(params) {
4-
let filters = params.columnFilters;
3+
performFilter: function () {
4+
let filters = this.serverParams.columnFilters;
55
let keys = Object.keys(filters);
6-
// If some filter is removed, delete the key from the params
7-
keys.forEach(function(key) {
8-
if (filters[key] === "") {
9-
delete filters[key];
10-
}
11-
});
12-
keys = Object.keys(filters);
136
if (keys.length === 0) { // meaning no filters applied
147
this.filteredTickets = this.completeTickets;
15-
this.getChartsData();
168
return;
179
}
1810
this.filteredTickets = this.completeTickets.filter(function(entry) {
@@ -26,7 +18,26 @@ export default {
2618
}
2719
return match;
2820
});
29-
this.getChartsData();
21+
},
22+
performSearch: function() {
23+
let searchInput = this.userSearchInput;
24+
let keysToSearch = [
25+
"Requestor",
26+
"ITOwner",
27+
"daysOpen",
28+
"Ticket Creation Date"
29+
];
30+
this.filteredTickets = this.filteredTickets.filter(function(entry) {
31+
let match = false;
32+
for (let i = 0; i < keysToSearch.length; i++) {
33+
let key = keysToSearch[i];
34+
if (entry[key] == searchInput) {
35+
match = true;
36+
break;
37+
}
38+
}
39+
return match;
40+
})
3041
},
3142
getChartsData: function () {
3243
let priority = {
@@ -68,5 +79,75 @@ export default {
6879
};
6980

7081
},
82+
performFilterSearch: function () {
83+
84+
// Whenever search or filter is applied, sort and page number are reset
85+
this.serverParams.sort = {
86+
field: '', // example: 'name'
87+
type: '' // 'asc' or 'desc'
88+
};
89+
this.serverParams.page = 1;
90+
91+
this.performFilter();
92+
this.performSearch();
93+
this.getChartsData();
94+
95+
this.ticketsToShow = this.filteredTickets.slice(0, this.serverParams.perPage);
96+
},
97+
/**
98+
*
99+
* Vue-Good-Table event handlers
100+
*/
101+
onColumnFilter: function(params) { // event from vue-good-table
102+
let filters = params.columnFilters;
103+
let keys = Object.keys(filters);
104+
// If some filter is removed, delete the key from the params
105+
keys.forEach(function(key) {
106+
if (filters[key] === "") {
107+
delete filters[key];
108+
}
109+
});
110+
this.serverParams.columnFilters = filters;
111+
this.performFilterSearch();
112+
},
113+
onSortChange: function(params) { // event from vue-good-table
114+
params.forEach(function(entry){
115+
console.log(entry.type);
116+
});
117+
params = params.pop();
118+
let field = params.field;
119+
let type = params.type;
120+
this.serverParams.sort = {
121+
field: field,
122+
type: type
123+
};
124+
let columnFieldType = this.columns.filter(function(entry) {
125+
return entry.field === field;
126+
})[0].type;
127+
this.filteredTickets.sort(function(a, b) {
128+
a = a[field];
129+
b = b[field];
130+
if (columnFieldType !== 'number') {
131+
a = a.split("-").pop().trim();
132+
b = b.split("-").pop().trim();
133+
}
134+
if (type === "asc") {
135+
return (a < b ? -1 : (a > b ? 1 : 0));
136+
}
137+
else { // type = "dsc"
138+
return (a > b ? -1 : (a < b ? 1 : 0));
139+
}
140+
});
141+
// reset page number on sort
142+
this.serverParams.page = 1;
143+
this.ticketsToShow = this.filteredTickets.slice(0, this.serverParams.perPage);
144+
},
145+
onPageChange: function(params) { // event from vue-good-table
146+
this.serverParams.page = params.currentPage;
147+
// change page
148+
let start = (this.serverParams.page - 1) * this.serverParams.perPage;
149+
let end = this.serverParams.page * this.serverParams.perPage;
150+
this.ticketsToShow = this.filteredTickets.slice(start, end);
151+
},
71152
}
72153
}

src/components/TicketsTable/TicketsTable.vue

Lines changed: 38 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -18,29 +18,30 @@
1818
<pie-chart attr-class="priority-chart" :chart-data="chartsData.priority"></pie-chart>
1919
<bar-chart attr-class="overall-bar-chart" :chart-data="chartsData"></bar-chart>
2020
<vue-good-table
21-
:columns="columns"
22-
:rows="completeTickets"
23-
@on-column-filter="onColumnFilter"
24-
styleClass="vgt-table striped bordered condensed"
25-
:search-options="{
26-
enabled: true,
27-
skipDiacritics: true,
28-
externalQuery: debouncedSearchInput
29-
}"
21+
mode="remote"
3022
:pagination-options="{
3123
enabled: true,
3224
mode: 'pages',
3325
position: 'top',
26+
perPage: 10,
27+
perPageDropdown: [10],
3428
dropdownAllowAll: false
3529
}"
30+
:totalRows="filteredTickets.length"
31+
:columns="columns"
32+
:rows="ticketsToShow"
33+
@on-column-filter="onColumnFilter"
34+
@on-sort-change="onSortChange"
35+
@on-page-change="onPageChange"
36+
styleClass="vgt-table striped bordered condensed"
3637
/>
3738
</div>
3839
</template>
3940

4041
<script>
4142
/* eslint-disable */
4243
import debounce from 'lodash.debounce';
43-
import ticketsFromJSONFile from "@/data/sample-data.json";
44+
import ticketsFromJSONFile from "@/data/sample-data-2.json";
4445
import PieChart from '../PieChart.vue';
4546
import BarChart from '../BarChart.vue';
4647
import NewTicket from '../NewTicket.vue';
@@ -67,23 +68,41 @@ export default {
6768
seniority: {},
6869
satisfaction: {}
6970
},
70-
debouncedSearchInput: "",
71-
userSearchInput: ""
71+
userSearchInput: "",
72+
serverParams: {
73+
// a map of column filters example: {name: 'john', age: '20'}
74+
columnFilters: {},
75+
sort: {
76+
field: '', // example: 'name'
77+
type: '' // 'asc' or 'desc'
78+
},
79+
80+
page: 1, // what page I want to show
81+
perPage: 10 // how many items I'm showing per page
82+
}
7283
}
7384
},
7485
methods: {
75-
setDebounceUserInput: debounce(function() {
76-
this.debouncedSearchInput = this.userSearchInput;
77-
}, 500),
7886
saveNewTicket: function(formData) {
7987
this.$refs.myModalRef.hide();
8088
this.ticketsLength += 1;
8189
this.completeTickets.unshift(formData);
82-
// once the new ticket is saved => apply filterSortSearchPaginate etc
90+
91+
// reset server params
92+
this.serverParams.columnFilters = {};
93+
this.serverParams.sort = {
94+
field: '', // example: 'name'
95+
type: '' // 'asc' or 'desc'
96+
};
97+
this.serverParams.page = 1;
98+
this.userSearchInput = "";
8399
},
84100
closeModal: function() {
85101
this.$refs.myModalRef.hide();
86-
}
102+
},
103+
debounceSearch: debounce(function() {
104+
this.performFilterSearch();
105+
}, 500)
87106
},
88107
mounted: function() {
89108
// Fetch tickets form localStorage
@@ -101,12 +120,13 @@ export default {
101120
102121
// On first render, filteredTickets and completeTickets are same
103122
this.filteredTickets = this.completeTickets;
123+
this.ticketsToShow = this.filteredTickets.slice(0, 10); // default pagination
104124
this.ticketsLength = this.completeTickets.length;
105125
setTimeout(this.getChartsData);
106126
},
107127
watch: {
108128
userSearchInput: function() {
109-
this.setDebounceUserInput();
129+
this.debounceSearch();
110130
}
111131
}
112132
};

0 commit comments

Comments
 (0)