From c4b375ffd91e8bc245f9fabd52bc5113afbb6c6c Mon Sep 17 00:00:00 2001
From: pkupczyk <piotr.kupczyk@id.ethz.ch>
Date: Wed, 10 Nov 2021 13:34:08 +0100
Subject: [PATCH] SSDM-11664 : NG UI & ELN : common table widget - add an
 option to export selected rows

---
 openbis_ng_ui/src/js/common/messages.js       | 12 +++++-
 .../src/js/components/common/grid/Grid.jsx    |  1 +
 .../components/common/grid/GridController.js  | 22 +++++++----
 .../common/grid/GridExportOptions.js          | 14 +++++--
 .../js/components/common/grid/GridExports.jsx | 39 ++++++++++++-------
 5 files changed, 59 insertions(+), 29 deletions(-)

diff --git a/openbis_ng_ui/src/js/common/messages.js b/openbis_ng_ui/src/js/common/messages.js
index 8e977d2148d..4bc9255bb1d 100644
--- a/openbis_ng_ui/src/js/common/messages.js
+++ b/openbis_ng_ui/src/js/common/messages.js
@@ -11,6 +11,8 @@ const keys = {
   ADD_TERM: 'ADD_TERM',
   ADD_USER: 'ADD_USER',
   ALL: 'ALL',
+  ALL_COLUMNS: 'ALL_COLUMNS',
+  ALL_PAGES: 'ALL_PAGES',
   AUTHENTICATION_SERVICE: 'AUTHENTICATION_SERVICE',
   AUTHENTICATION_SERVICE_OPENBIS: 'AUTHENTICATION_SERVICE_OPENBIS',
   AUTHENTICATION_SERVICE_SWITCH_AAI: 'AUTHENTICATION_SERVICE_SWITCH_AAI',
@@ -32,6 +34,7 @@ const keys = {
   CONTENT: 'CONTENT',
   CONVERTED: 'CONVERTED',
   CRASH: 'CRASH',
+  CURRENT_PAGE: 'CURRENT_PAGE',
   DATABASE: 'DATABASE',
   DATA_SET_TYPE: 'DATA_SET_TYPE',
   DATA_SET_TYPES: 'DATA_SET_TYPES',
@@ -163,6 +166,7 @@ const keys = {
   SECTION: 'SECTION',
   SECTION_IS_NOT_USED: 'SECTION_IS_NOT_USED',
   SECTION_IS_USED: 'SECTION_IS_USED',
+  SELECTED_ROWS: 'SELECTED_ROWS',
   SELECTED_ROWS_NOT_VISIBLE_DUE_TO_FILTERING_AND_PAGING: 'SELECTED_ROWS_NOT_VISIBLE_DUE_TO_FILTERING_AND_PAGING',
   SHOW: 'SHOW',
   SHOW_CONTAINER: 'SHOW_CONTAINER',
@@ -191,7 +195,7 @@ const keys = {
   VALIDATION_TERM_CODE_PATTERN: 'VALIDATION_TERM_CODE_PATTERN',
   VALIDATION_USER_CODE_PATTERN: 'VALIDATION_USER_CODE_PATTERN',
   VALUES: 'VALUES',
-  VISIBLE: 'VISIBLE',
+  VISIBLE_COLUMNS: 'VISIBLE_COLUMNS',
   VOCABULARY_TYPE: 'VOCABULARY_TYPE',
   VOCABULARY_TYPES: 'VOCABULARY_TYPES',
   VOCABULARY_TYPE_IS_INTERNAL: 'VOCABULARY_TYPE_IS_INTERNAL',
@@ -213,6 +217,8 @@ const messages_en = {
   [keys.ADD_TERM]: 'Add Term',
   [keys.ADD_USER]: 'Add User',
   [keys.ALL]: 'All',
+  [keys.ALL_COLUMNS]: 'All Columns',
+  [keys.ALL_PAGES]: 'All Pages',
   [keys.AUTHENTICATION_SERVICE]: 'Authentication Service',
   [keys.AUTHENTICATION_SERVICE_OPENBIS]: 'Default Login Service',
   [keys.AUTHENTICATION_SERVICE_SWITCH_AAI]: 'SWITCHaai Single Sign On Login Service',
@@ -234,6 +240,7 @@ const messages_en = {
   [keys.CONTENT]: 'Content',
   [keys.CONVERTED]: 'Converted',
   [keys.CRASH]: 'Something went wrong :(',
+  [keys.CURRENT_PAGE]: 'Current Page',
   [keys.DATABASE]: 'Database',
   [keys.DATA_SET_TYPES]: 'Data Set Types',
   [keys.DATA_SET_TYPE]: 'Data Set Type',
@@ -366,6 +373,7 @@ const messages_en = {
   [keys.SECTION]: 'Section',
   [keys.SECTION_IS_NOT_USED]: 'This section contains only property assignments which are not yet used by any entities of "${0}" type.',
   [keys.SECTION_IS_USED]: 'This section contains property assignments which are already used by existing entities of "${0}" type. Removing it is also going to remove ${1} existing property value(s) - data will be lost! Are you sure you want to proceed?',
+  [keys.SELECTED_ROWS]: 'Selected Rows',
   [keys.SELECTED_ROWS_NOT_VISIBLE_DUE_TO_FILTERING_AND_PAGING]: 'Some selected rows are not visible due to the chosen filtering and paging.',
   [keys.SHOW]: 'show',
   [keys.SHOW_CONTAINER]: 'Show Container',
@@ -394,7 +402,7 @@ const messages_en = {
   [keys.VALIDATION_TERM_CODE_PATTERN]: '${0} can only contain A-Z, a-z, 0-9 and _, -, ., :',
   [keys.VALIDATION_USER_CODE_PATTERN]: '${0} can only contain A-Z, a-z, 0-9 and _, -, ., @',
   [keys.VALUES]: 'Values',
-  [keys.VISIBLE]: 'Visible',
+  [keys.VISIBLE_COLUMNS]: 'Visible Columns',
   [keys.VOCABULARY_TYPES]: 'Vocabulary Types',
   [keys.VOCABULARY_TYPE]: 'Vocabulary Type',
   [keys.VOCABULARY_TYPE_IS_INTERNAL]: 'This is a system internal vocabulary.',
diff --git a/openbis_ng_ui/src/js/components/common/grid/Grid.jsx b/openbis_ng_ui/src/js/components/common/grid/Grid.jsx
index 40e708e1655..70578be9110 100644
--- a/openbis_ng_ui/src/js/components/common/grid/Grid.jsx
+++ b/openbis_ng_ui/src/js/components/common/grid/Grid.jsx
@@ -184,6 +184,7 @@ class Grid extends React.PureComponent {
                   <GridExports
                     disabled={rows.length === 0}
                     exportOptions={exportOptions}
+                    multiselectable={multiselectable}
                     onExport={this.controller.handleExport}
                     onExportOptionsChange={
                       this.controller.handleExportOptionsChange
diff --git a/openbis_ng_ui/src/js/components/common/grid/GridController.js b/openbis_ng_ui/src/js/components/common/grid/GridController.js
index 8845e0fd68d..fc53ba3bb84 100644
--- a/openbis_ng_ui/src/js/components/common/grid/GridController.js
+++ b/openbis_ng_ui/src/js/components/common/grid/GridController.js
@@ -31,8 +31,8 @@ export default class GridController {
       sortDirection: null,
       totalCount: 0,
       exportOptions: {
-        columns: GridExportOptions.VISIBLE,
-        rows: GridExportOptions.VISIBLE,
+        columns: GridExportOptions.VISIBLE_COLUMNS,
+        rows: GridExportOptions.CURRENT_PAGE,
         values: GridExportOptions.RICH_TEXT
       }
     })
@@ -780,10 +780,10 @@ export default class GridController {
     var columns = []
     var prefix = ''
 
-    if (exportOptions.columns === GridExportOptions.ALL) {
+    if (exportOptions.columns === GridExportOptions.ALL_COLUMNS) {
       columns = this.getAllColumns()
       prefix += 'AllColumns'
-    } else if (exportOptions.columns === GridExportOptions.VISIBLE) {
+    } else if (exportOptions.columns === GridExportOptions.VISIBLE_COLUMNS) {
       columns = this.getVisibleColumns()
       prefix += 'VisibleColumns'
     } else {
@@ -792,7 +792,7 @@ export default class GridController {
 
     columns = columns.filter(column => column.exportable)
 
-    if (exportOptions.rows === GridExportOptions.ALL) {
+    if (exportOptions.rows === GridExportOptions.ALL_PAGES) {
       if (props.rows) {
         data = state.filteredRows
       } else if (props.loadRows) {
@@ -810,11 +810,17 @@ export default class GridController {
         }
       }
 
-      prefix += 'AllRows'
+      prefix += 'AllPages'
       _exportColumnsFromData(prefix, data, columns)
-    } else if (exportOptions.rows === GridExportOptions.VISIBLE) {
+    } else if (exportOptions.rows === GridExportOptions.CURRENT_PAGE) {
       data = state.rows
-      prefix += 'VisibleRows'
+      prefix += 'CurrentPage'
+      _exportColumnsFromData(prefix, data, columns)
+    } else if (exportOptions.rows === GridExportOptions.SELECTED_ROWS) {
+      data = Object.values(state.multiselectedRows).map(
+        selectedRow => selectedRow.data
+      )
+      prefix += 'SelectedRows'
       _exportColumnsFromData(prefix, data, columns)
     } else {
       throw Error('Unsupported rows option: ' + exportOptions.columns)
diff --git a/openbis_ng_ui/src/js/components/common/grid/GridExportOptions.js b/openbis_ng_ui/src/js/components/common/grid/GridExportOptions.js
index 09e5bea82fe..1820a38d09c 100644
--- a/openbis_ng_ui/src/js/components/common/grid/GridExportOptions.js
+++ b/openbis_ng_ui/src/js/components/common/grid/GridExportOptions.js
@@ -1,11 +1,17 @@
-const ALL = 'ALL'
-const VISIBLE = 'VISIBLE'
+const ALL_COLUMNS = 'ALL_COLUMNS'
+const VISIBLE_COLUMNS = 'VISIBLE_COLUMNS'
+const ALL_PAGES = 'ALL_PAGES'
+const CURRENT_PAGE = 'CURRENT_PAGE'
+const SELECTED_ROWS = 'SELECTED_ROWS'
 const PLAIN_TEXT = 'PLAIN_TEXT'
 const RICH_TEXT = 'RICH_TEXT'
 
 export default {
-  ALL,
-  VISIBLE,
+  ALL_COLUMNS,
+  VISIBLE_COLUMNS,
+  ALL_PAGES,
+  CURRENT_PAGE,
+  SELECTED_ROWS,
   PLAIN_TEXT,
   RICH_TEXT
 }
diff --git a/openbis_ng_ui/src/js/components/common/grid/GridExports.jsx b/openbis_ng_ui/src/js/components/common/grid/GridExports.jsx
index 9017d19af75..38348480c07 100644
--- a/openbis_ng_ui/src/js/components/common/grid/GridExports.jsx
+++ b/openbis_ng_ui/src/js/components/common/grid/GridExports.jsx
@@ -70,9 +70,27 @@ class GridExports extends React.PureComponent {
   render() {
     logger.log(logger.DEBUG, 'GridExports.render')
 
-    const { exportOptions, disabled, classes } = this.props
+    const { exportOptions, disabled, multiselectable, classes } = this.props
     const { el } = this.state
 
+    const rowsOptions = [
+      {
+        label: messages.get(messages.ALL_PAGES),
+        value: GridExportOptions.ALL_PAGES
+      },
+      {
+        label: messages.get(messages.CURRENT_PAGE),
+        value: GridExportOptions.CURRENT_PAGE
+      }
+    ]
+
+    if (multiselectable) {
+      rowsOptions.push({
+        label: messages.get(messages.SELECTED_ROWS),
+        value: GridExportOptions.SELECTED_ROWS
+      })
+    }
+
     return (
       <div className={classes.container}>
         <Button
@@ -101,12 +119,12 @@ class GridExports extends React.PureComponent {
                 name='columns'
                 options={[
                   {
-                    label: messages.get(messages.ALL),
-                    value: GridExportOptions.ALL
+                    label: messages.get(messages.ALL_COLUMNS),
+                    value: GridExportOptions.ALL_COLUMNS
                   },
                   {
-                    label: messages.get(messages.VISIBLE),
-                    value: GridExportOptions.VISIBLE
+                    label: messages.get(messages.VISIBLE_COLUMNS),
+                    value: GridExportOptions.VISIBLE_COLUMNS
                   }
                 ]}
                 value={exportOptions.columns}
@@ -118,16 +136,7 @@ class GridExports extends React.PureComponent {
               <SelectField
                 label={messages.get(messages.ROWS)}
                 name='rows'
-                options={[
-                  {
-                    label: messages.get(messages.ALL),
-                    value: GridExportOptions.ALL
-                  },
-                  {
-                    label: messages.get(messages.VISIBLE),
-                    value: GridExportOptions.VISIBLE
-                  }
-                ]}
+                options={rowsOptions}
                 value={exportOptions.rows}
                 variant='standard'
                 onChange={this.handleChange}
-- 
GitLab