1717 :icon =" Application20"
1818 @click =" showSoftwareCenterCoreApps()"
1919 class =" page-toolbar-item"
20- >{{
21- $t('applications_center.core_apps')
22- }}</NsButton
20+ >{{ $t("applications_center.core_apps") }}</NsButton
2321 >
2422 </div >
2523 </cv-column >
3432 />
3533 </cv-column >
3634 </cv-row >
37- {{ modules }}
35+ {{ modules }}
3836 <!-- <cv-row v-if="error.listCoreModules">
3937 <cv-column>
4038 <NsInlineNotification
122120 </cv-column>
123121 </cv-row> -->
124122
125-
123+ <cv-row >
124+ <cv-column >
125+ <cv-tile light >
126+ <cv-row >
127+ <cv-column >
128+ <NsDataTable
129+ :allRows =" modules"
130+ :columns =" i18nTableColumns"
131+ :rawColumns =" tableColumns"
132+ :sortable =" true"
133+ :pageSizes =" [10, 25, 50, 100]"
134+ isSearchable
135+ :searchPlaceholder =" $t('firewall.search_service_or_port')"
136+ :searchClearLabel =" $t('common.clear_search')"
137+ :noSearchResultsLabel =" $t('common.no_search_results')"
138+ :noSearchResultsDescription ="
139+ $t('common.no_search_results_description')
140+ "
141+ :isLoading =" loading.listModules"
142+ :skeletonRows =" 5"
143+ :isErrorShown =" !!error.listModules"
144+ :errorTitle =" $t('action.get-firewall-status')"
145+ :errorDescription =" error.listModules"
146+ :itemsPerPageLabel =" $t('pagination.items_per_page')"
147+ :rangeOfTotalItemsLabel ="
148+ $t('pagination.range_of_total_items')
149+ "
150+ :ofTotalPagesLabel =" $t('pagination.of_total_pages')"
151+ :backwardText =" $t('pagination.previous_page')"
152+ :forwardText =" $t('pagination.next_page')"
153+ :pageNumberLabel =" $t('pagination.page_number')"
154+ @updatePage =" tablePage = $event"
155+ >
156+ <template slot="empty-state">
157+ <NsEmptyState :title =" $t('firewall.no_service')" >
158+ <template #description >
159+ <div >
160+ {{ $t("firewall.no_service_description") }}
161+ </div >
162+ </template >
163+ </NsEmptyState >
164+ </template >
165+ <template slot="data">
166+ <cv-data-table-row
167+ v-for =" (row, rowIndex) in tablePage"
168+ :key =" `${rowIndex}`"
169+ :value =" `${rowIndex}`"
170+ >
171+ <cv-data-table-cell >
172+ <span >
173+ {{
174+ row.ui_name
175+ ? row.ui_name + " (" + row.id + ")"
176+ : row.id
177+ }}
178+ </span >
179+ </cv-data-table-cell >
180+ <cv-data-table-cell >
181+ <img :src =" getLogoSrc(row.logo)" :alt =" row.module" style =" height : 32px ; vertical-align : middle ; margin-right : 8px ;" />
182+ <span >{{ row.module }}</span >
183+ </cv-data-table-cell >
184+ <cv-data-table-cell >
185+ <span >{{ row.node_ui_name ? $t('common.node') + ' ' + row.node + ' (' + row.node_ui_name + ')' : $t('common.node') + ' ' + row.node }}</span >
186+ </cv-data-table-cell >
187+ <cv-data-table-cell >
188+ <span >{{ row.version }}</span >
189+ </cv-data-table-cell >
190+ <cv-data-table-cell class =" table-overflow-menu-cell" >
191+ <!-- <cv-overflow-menu
192+ flip-menu
193+ class="table-overflow-menu"
194+ :data-test-id="row.localuser + '-menu'"
195+ >
196+ <cv-overflow-menu-item
197+ @click="toggleEditTask(row)"
198+ :data-test-id="row.localuser + '-edit-task'"
199+ >
200+ <NsMenuItem
201+ :icon="Edit20"
202+ :label="$t('tasks.edit')"
203+ />
204+ </cv-overflow-menu-item>
205+ <cv-overflow-menu-item
206+ v-if="row.remoteusername !== ''"
207+ @click="toggleActionTask(row)"
208+ :data-test-id="row.localuser + '-action-task'"
209+ >
210+ <NsMenuItem
211+ :icon="row.service ? Stop20 : Play20"
212+ :label="
213+ row.service
214+ ? $t('tasks.stop')
215+ : $t('tasks.start')
216+ "
217+ />
218+ </cv-overflow-menu-item>
219+ <cv-overflow-menu-item
220+ v-if="row.remoteusername !== ''"
221+ @click="toggleDeleteTask(row)"
222+ :data-test-id="row.localuser + '-delete-task'"
223+ >
224+ <NsMenuItem
225+ :icon="TrashCan20"
226+ :label="$t('tasks.delete')"
227+ />
228+ </cv-overflow-menu-item>
229+ <cv-overflow-menu-item
230+ v-if="row.remoteusername !== ''"
231+ @click="toggleInformations(row)"
232+ :data-test-id="row.localuser + '-list-informations'"
233+ >
234+ <NsMenuItem
235+ :icon="Information20"
236+ :label="$t('tasks.informations')"
237+ />
238+ </cv-overflow-menu-item>
239+ </cv-overflow-menu>-->
240+ </cv-data-table-cell >
241+ </cv-data-table-row >
242+ </template >
243+ </NsDataTable >
244+ </cv-column >
245+ </cv-row >
246+ </cv-tile >
247+ </cv-column >
248+ </cv-row >
126249 </cv-grid >
127-
128250 </div >
129251</template >
130252
@@ -142,9 +264,7 @@ import { mapState, mapActions } from "vuex";
142264
143265export default {
144266 name: " SoftwareCenter" ,
145- components: {
146-
147- },
267+ components: {},
148268 mixins: [
149269 IconService,
150270 QueryParamService,
@@ -165,6 +285,8 @@ export default {
165285 view: " all" ,
166286 },
167287 modules: [],
288+ tableColumns: [" name" , " module" , " node" , " version" ],
289+ tablePage: [],
168290 loading: {
169291 listModules: true ,
170292 },
@@ -191,6 +313,11 @@ export default {
191313 return app .installed .length ;
192314 });
193315 },
316+ i18nTableColumns () {
317+ return this .tableColumns .map ((column ) => {
318+ return this .$t (" firewall." + column);
319+ });
320+ },
194321 // numInstancesToUpdate() {
195322 // let numInstancesToUpdate = 0;
196323
@@ -236,6 +363,13 @@ export default {
236363 },
237364 methods: {
238365 ... mapActions ([" setUpdateInProgressInStore" ]),
366+ getLogoSrc (logoPath ) {
367+ // Rewrite backend absolute path to public path
368+ if (logoPath && logoPath .startsWith (' /var/lib/nethserver/cluster/ui/apps/' )) {
369+ return logoPath .replace (' /var/lib/nethserver/cluster/ui/apps/' , ' /apps/' );
370+ }
371+ return logoPath;
372+ },
239373 async listModules () {
240374 this .loading .listModules = true ;
241375 this .error .listModules = " " ;
@@ -303,63 +437,64 @@ export default {
303437 // console.log("modules", this.modules);
304438 // console.log("appUpdates", this.appUpdates);
305439 // function extractModules(data) {
306- // if (!data || !Array.isArray(data.installed)) {
307- // return [];
308- // }
309-
310- function extractModulesWithUpdates (taskResult ) {
311- if (! taskResult || ! Array .isArray (taskResult .output )) return [];
312-
313- const modules = [];
314-
315- for (const obj of taskResult .output ) {
316- const disabledReason = obj .disabled_updates_reason || " " ;
317- const updates = Array .isArray (obj .updates ) ? obj .updates : [];
318-
319- if (Array .isArray (obj .installed )) {
320- for (const item of obj .installed ) {
321- // chercher update correspondant par id
322- const updateEntry = updates .find (u => u .id === item .id );
323- console .log (" item" , item);
324- console .log (" updateEntry" , updateEntry);
325- // if found, merge data from updateEntry into item
326- const source = updateEntry || item;
327-
328- modules .push ({
329- digest: source .digest || " " ,
330- rootfull: source .flags ? source .flags .includes (' rootfull' ) : false ,
331- id: source .id || " " ,
332- logo: source .logo || " " ,
333- module: source .module || " " ,
334- node: source .node || " " ,
335- node_ui_name: source .node_ui_name || " " ,
336- source: source .source || " " ,
337- ui_name: source .ui_name || " " ,
338- version: source .version || " " ,
339- disabled_updates_reason: disabledReason,
340- update: source .update || " "
341- });
342- }
343- }
344- }
345-
346- // sort by id
347- modules .sort ((a , b ) => a .id .localeCompare (b .id ));
440+ // if (!data || !Array.isArray(data.installed)) {
441+ // return [];
442+ // }
443+
444+ function extractModulesWithUpdates (taskResult ) {
445+ if (! taskResult || ! Array .isArray (taskResult .output )) return [];
446+
447+ const modules = [];
448+
449+ for (const obj of taskResult .output ) {
450+ const disabledReason = obj .disabled_updates_reason || " " ;
451+ const updates = Array .isArray (obj .updates ) ? obj .updates : [];
452+
453+ if (Array .isArray (obj .installed )) {
454+ for (const item of obj .installed ) {
455+ // chercher update correspondant par id
456+ const updateEntry = updates .find ((u ) => u .id === item .id );
457+ console .log (" item" , item);
458+ console .log (" updateEntry" , updateEntry);
459+ // if found, merge data from updateEntry into item
460+ const source = updateEntry || item;
461+
462+ modules .push ({
463+ digest: source .digest || " " ,
464+ rootfull: source .flags
465+ ? source .flags .includes (" rootfull" )
466+ : false ,
467+ id: source .id || " " ,
468+ logo: source .logo || " " ,
469+ module: source .module || " " ,
470+ node: source .node || " " ,
471+ node_ui_name: source .node_ui_name || " " ,
472+ source: source .source || " " ,
473+ ui_name: source .ui_name || " " ,
474+ version: source .version || " " ,
475+ disabled_updates_reason: disabledReason,
476+ update: source .update || " " ,
477+ });
478+ }
479+ }
480+ }
348481
349- return modules;
350- }
482+ // sort by id
483+ modules . sort (( a , b ) => a . id . localeCompare ( b . id ));
351484
352- this .modules = extractModulesWithUpdates (taskResult);
353- console .log (" extracted modules" , this .modules );
354- // return modules;
355- // }
356- // console.log("extracted modules", extractModules(taskResult));
357- // this.modules = extractModules(taskResult);
358- // // perform search on browser history navigation (e.g. going back to software center)
359- // if (this.q.search) {
360- // this.searchApp(this.q.search);
361- // }
485+ return modules;
486+ }
362487
488+ this .modules = extractModulesWithUpdates (taskResult);
489+ console .log (" extracted modules" , this .modules );
490+ // return modules;
491+ // }
492+ // console.log("extracted modules", extractModules(taskResult));
493+ // this.modules = extractModules(taskResult);
494+ // // perform search on browser history navigation (e.g. going back to software center)
495+ // if (this.q.search) {
496+ // this.searchApp(this.q.search);
497+ // }
363498 },
364499 // async listCoreModules() {
365500 // this.error.listCoreModules = "";
0 commit comments