Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: replace data table with UI data table #3015

Merged
merged 58 commits into from
Feb 12, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
58 commits
Select commit Hold shift + click to select a range
b6eb3f7
feat: switch to ui table with horizontal scrolling
jenniferarnesen Oct 18, 2023
7367aa3
feat: sorting on all but the index column
jenniferarnesen Oct 18, 2023
eb141d6
feat: sort by index as well
jenniferarnesen Oct 18, 2023
e77d7fd
chore: set bgcolor and font color for color cell
jenniferarnesen Oct 19, 2023
f47bc15
chore: lowercase color code
jenniferarnesen Oct 19, 2023
4c0cfcd
chore: filtering
jenniferarnesen Oct 19, 2023
21499dc
chore: event layer table
jenniferarnesen Oct 20, 2023
905a233
chore: localization
jenniferarnesen Jan 24, 2024
e0836fb
chore: update yarn.lock
HendrikThePendric Jan 25, 2024
b315e27
feat: add row hover and click behaviour
HendrikThePendric Jan 25, 2024
95794e3
feat: all supported layer types now showing in table
jenniferarnesen Jan 25, 2024
58f8247
feat: virtually scrolling table with dhis2 ui components
HendrikThePendric Jan 25, 2024
2c8ce4f
chore: remove redundant props
HendrikThePendric Jan 25, 2024
6a1b26a
Merge branch 'feat/new-data-table' of github.com:dhis2/maps-app into …
jenniferarnesen Jan 26, 2024
6dfabb2
chore: more table logic to hook
jenniferarnesen Jan 26, 2024
e4b749f
chore: use constants
jenniferarnesen Jan 26, 2024
db0e2f2
chore: add tests for useTableData hook
jenniferarnesen Jan 26, 2024
f9dbac8
chore: update cypress test
jenniferarnesen Jan 29, 2024
8b6809c
fix: align filter inputs at the bottom of the th
HendrikThePendric Jan 29, 2024
9ed22e9
chore: remove d2 from useTableData
jenniferarnesen Jan 29, 2024
5a4c4a7
chore: padding styling on table cells
jenniferarnesen Jan 29, 2024
a945239
fix: loading indicator for earthengine aggregations slow loading
jenniferarnesen Jan 29, 2024
4019f3c
fix: fetch extended data for event layers
jenniferarnesen Jan 29, 2024
3118943
chore: add cypress test for event layer data table
jenniferarnesen Jan 29, 2024
1e40397
chore: rename file to DataTable
jenniferarnesen Jan 29, 2024
1f75361
fix: show message when filter causes the array to be empty
HendrikThePendric Jan 29, 2024
3e1dc42
chore: use smaller text size in table
jenniferarnesen Jan 30, 2024
baeb4d6
fix: update snapshot
jenniferarnesen Jan 30, 2024
80770c1
fix: fix LayersLoader jest tests
jenniferarnesen Jan 30, 2024
caf8fb7
chore: snapshots
jenniferarnesen Jan 30, 2024
35544e3
chore: use renderHook to test useTableData
jenniferarnesen Jan 30, 2024
4364459
fix: dont show orgunitprofile for EVENT layers
jenniferarnesen Jan 31, 2024
21318ad
fix: dont use text select cursor in table rows
jenniferarnesen Jan 31, 2024
bd69a52
fix: make sure numeric data items are filterable and sortable
jenniferarnesen Jan 31, 2024
14a31de
chore: add additional assertions for filtering and sorting of event l…
jenniferarnesen Jan 31, 2024
9045cbc
fix: error feedback to user about unsuppored layer
jenniferarnesen Feb 1, 2024
41d3bd6
fix: no crash if EE layer doesnt have orgunits
jenniferarnesen Feb 7, 2024
62a74f0
fix: align number columns right
jenniferarnesen Feb 7, 2024
40972c8
fix: prevent column width changes while scrolling
HendrikThePendric Feb 7, 2024
93b88ea
fix: ensure width is a valid value in px
HendrikThePendric Feb 7, 2024
f4704ed
fix: allow the DOM to repaint before switching to fixed layout
HendrikThePendric Feb 7, 2024
1048506
fix: avoid rounding issue which can cause a scrollbar to appear
HendrikThePendric Feb 7, 2024
fc156fd
fix: switch back to automatic table layout when the headers change
HendrikThePendric Feb 7, 2024
e3c527e
fix: use DataTableRow instead of tr since it can also accept a ref
HendrikThePendric Feb 7, 2024
4c01a40
chore: fix spelling in a comment
HendrikThePendric Feb 7, 2024
4d9f558
fix: disable text selection in thead
HendrikThePendric Feb 7, 2024
6fdbe68
fix: switch to ui Input for column filters, handle serverCluster erro…
jenniferarnesen Feb 8, 2024
27471b6
fix: close button styling and position
jenniferarnesen Feb 8, 2024
090e9b3
fix: close icon additional positioning
jenniferarnesen Feb 8, 2024
e6a7d40
fix: destructure value
jenniferarnesen Feb 8, 2024
05afd5c
fix: cypress test fix
jenniferarnesen Feb 8, 2024
3ac7a66
fix: lint
jenniferarnesen Feb 8, 2024
db8b57e
fix: virtualization means you cant check last row if they arent shown
jenniferarnesen Feb 8, 2024
9fdf8aa
feat: data table control bar
jenniferarnesen Feb 9, 2024
73a6b6f
chore: final style touches on datatable control bar
jenniferarnesen Feb 9, 2024
999566d
fix: adjust cypress
jenniferarnesen Feb 9, 2024
0fed9be
fix: effect dependencies
jenniferarnesen Feb 9, 2024
6ed2551
chore: add ErrorBoundary around the datatable
jenniferarnesen Feb 12, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion cypress.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ module.exports = defineConfig({
// Enabled to reduce the risk of out-of-memory issues
experimentalMemoryManagement: true,
// Set to a low number to reduce the risk of out-of-memory issues
numTestsKeptInMemory: 5,
numTestsKeptInMemory: 4,
/* When allowing 1 retry on CI, the test suite will pass if
* it's flaky. And/but we also get to identify flaky tests on the
* Cypress Dashboard. */
Expand Down
8 changes: 8 additions & 0 deletions cypress/elements/event_layer.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { Layer } from './layer.js'
export class EventLayer extends Layer {
selectProgram(program) {
cy.get('[data-test="programselect"]').click()
cy.contains(program).scrollIntoView()
cy.contains(program).click()

return this
Expand All @@ -22,4 +23,11 @@ export class EventLayer extends Layer {

return this
}

selectPeriodType(periodType) {
cy.getByDataTest('relative-period-select-content').click()
cy.contains(periodType).click()

return this
}
}
240 changes: 229 additions & 11 deletions cypress/integration/dataTable.cy.js
HendrikThePendric marked this conversation as resolved.
Show resolved Hide resolved
Original file line number Diff line number Diff line change
@@ -1,4 +1,15 @@
import { EXTENDED_TIMEOUT } from '../support/util.js'
import { EventLayer } from '../elements/event_layer.js'
import { CURRENT_YEAR, EXTENDED_TIMEOUT } from '../support/util.js'

Cypress.on('uncaught:exception', (err) => {
if (
err.message.includes(
'ResizeObserver loop completed with undelivered notifications.'
)
) {
return false
}
})

const map = {
id: 'eDlFx0jTtV9',
Expand All @@ -8,7 +19,7 @@ const map = {
}

describe('data table', () => {
it('opens data table', () => {
it('opens data table and filters and sorts', () => {
cy.visit(`/#/${map.id}`, EXTENDED_TIMEOUT)
cy.get('canvas', EXTENDED_TIMEOUT).should('be.visible')

Expand All @@ -29,19 +40,226 @@ describe('data table', () => {

// check number of columns
cy.getByDataTest('bottom-panel')
.find('[role="columnheader"]')
.findByDataTest('dhis2-uicore-datatablecellhead')
.should('have.length', 10)

// try the filtering
// Filter by name
cy.getByDataTest('data-table-column-filter-input-Name')
.find('input')
.type('bar')

// check that the filter returned the correct number of rows
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.findByDataTest('dhis2-uicore-datatablerow')
.should('have.length', 7)

// confirm that the sort order is initially ascending by Name
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.first()
.find('td')
.eq(1)
.should('contain', 'Bargbe')

cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.last()
.find('td')
.eq(1)
.should('contain', 'Upper Bambara')

// Sort by name
cy.get('button[title="Sort by Name"]').click()

// confirm that the rows are sorted by Name descending
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.first()
.find('td')
.eq(1)
.should('contain', 'Upper Bambara')

cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.last()
.find('td')
.eq(1)
.should('contain', 'Bargbe')

// filter by Value (numeric)
cy.getByDataTest('data-table-column-filter-input-Value')
.find('input')
.type('>26')

// check that the (combined) filter returned the correct number of rows
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.findByDataTest('dhis2-uicore-datatablerow')
.should('have.length', 5)

// Sort by value
cy.get('button[title="Sort by Value"]').click()

// check that the rows are sorted by Value ascending
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.first()
.find('td')
.eq(3)
.should('contain', '35')

cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.last()
.find('td')
.eq(3)
.should('contain', '76')

// click on a row
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.findByDataTest('dhis2-uicore-datatablerow')
.first()
.click()

// check that the org unit profile drawer is opened
cy.getByDataTest('org-unit-profile').should('be.visible')
})

it('opens the data table for an Event layer', () => {
cy.visit('/', EXTENDED_TIMEOUT)

const Layer = new EventLayer()

Layer.openDialog('Events')
.selectProgram('Malaria case registration')
.validateStage('Malaria case registration')
.selectTab('Period')
.selectPeriodType('Start/end dates')
.typeStartDate(`${CURRENT_YEAR - 1}-01-01`)
.typeEndDate(`${CURRENT_YEAR - 1}-01-15`)
.selectTab('Org Units')
.selectOu('Bo')
.addToMap()

Layer.validateDialogClosed(true)

Layer.validateCardTitle('Malaria case registration')

cy.getByDataTest('moremenubutton').first().click()

cy.getByDataTest('more-menu')
.find('li')
.contains('Show data table')
.not('disabled')
.click()

cy.getByDataTest('bottom-panel').should('be.visible')

// check number of columns
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-datatablecellhead')
.should('have.length', 9)

cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-datatablecellhead')
.contains('Age in years', { matchCase: false })
.should('be.visible')

// filter by Org unit
const ouName = 'Benduma'
cy.getByDataTest('data-table-column-filter-input-Org unit')
.find('input')
.type(ouName)

// check that all the rows have Org unit Yakaji

cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.first()
.find('td')
.eq(1)
.should('contain', ouName)

cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.last()
.find('td')
.eq(1)
.should('contain', ouName)

cy.getByDataTest('bottom-panel')
.find('[role="columnheader"]')
.containsExact('Name')
.siblings('input')
.type('Kakua')
.findByDataTest('dhis2-uicore-tablebody')
.findByDataTest('dhis2-uicore-datatablerow')
.should('have.length', 5)

// filter by Gender
cy.getByDataTest('data-table-column-filter-input-Gender')
.find('input')
.type('Female')

cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.findByDataTest('dhis2-uicore-datatablerow')
.should('have.length', 4)

cy.getByDataTest('data-table-column-filter-input-Gender')
.find('input')
.clear()

// check that the filter worked
cy.getByDataTest('bottom-panel')
.find('.ReactVirtualized__Table__row')
.should('have.length', 1)
.findByDataTest('dhis2-uicore-tablebody')
.findByDataTest('dhis2-uicore-datatablerow')
.should('have.length', 5)

// filter by Age in years (numeric)
cy.getByDataTest('data-table-column-filter-input-Age in years')
.find('input')
.type('<51')

// check that the filter returned the correct number of rows
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.findByDataTest('dhis2-uicore-datatablerow')
.should('have.length', 3)

// Sort by Age in years
cy.get('button[title="Sort by Age in years"]').click()

// confirm that the rows are sorted by Age in years descending
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.first()
.find('td')
.eq(7)
.should('contain', '44')

cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.find('tr')
.last()
.find('td')
.eq(7)
.should('contain', '6')

// click on a row
cy.getByDataTest('bottom-panel')
.findByDataTest('dhis2-uicore-tablebody')
.findByDataTest('dhis2-uicore-datatablerow')
.first()
.click()

// check that the org unit profile drawer is NOT opened
cy.getByDataTest('org-unit-profile').should('not.exist')
})
})
2 changes: 1 addition & 1 deletion cypress/support/commands.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import '@dhis2/cypress-commands'
import 'cypress-wait-until'

Cypress.Commands.add('getByDataTest', (selector, ...args) =>
cy.get(`[data-test=${selector}]`, ...args)
cy.get(`[data-test="${selector}"]`, ...args)
)
Cypress.Commands.add(
'findByDataTest',
Expand Down
46 changes: 32 additions & 14 deletions i18n/en.pot
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@ msgstr ""
"Content-Type: text/plain; charset=utf-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=(n != 1)\n"
"POT-Creation-Date: 2024-01-11T09:20:59.829Z\n"
"PO-Revision-Date: 2024-01-11T09:20:59.829Z\n"
"POT-Creation-Date: 2024-02-12T09:30:18.362Z\n"
"PO-Revision-Date: 2024-02-12T09:30:18.362Z\n"

msgid "Untitled map, {{date}}"
msgstr "Untitled map, {{date}}"
Expand Down Expand Up @@ -131,23 +131,23 @@ msgstr "Date"
msgid "Data set"
msgstr "Data set"

msgid "Index"
msgstr "Index"
msgid "No results found"
msgstr "No results found"

msgid "Org unit"
msgstr "Org unit"
msgid "Sort by {{column}}"
msgstr "Sort by {{column}}"

msgid "Id"
msgstr "Id"
msgid "Something went wrong"
msgstr "Something went wrong"

msgid "Event time"
msgstr "Event time"
msgid "Search"
msgstr "Search"

msgid "Legend"
msgstr "Legend"
msgid "Index"
msgstr "Index"

msgid "Range"
msgstr "Range"
msgid "Id"
msgstr "Id"

msgid "Level"
msgstr "Level"
Expand All @@ -158,9 +158,27 @@ msgstr "Parent"
msgid "Type"
msgstr "Type"

msgid "Legend"
msgstr "Legend"

msgid "Range"
msgstr "Range"

msgid "Org unit"
msgstr "Org unit"

msgid "Event time"
msgstr "Event time"

msgid "Data table is not supported when events are grouped on the server."
msgstr "Data table is not supported when events are grouped on the server."

msgid "No valid data was found for the current layer configuration."
msgstr "No valid data was found for the current layer configuration."

msgid "Data table is not supported for this layer type."
msgstr "Data table is not supported for this layer type."

msgid "Items"
msgstr "Items"

Expand Down
2 changes: 2 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@
"@krakenjs/post-robot": "^11.0.0",
"@reportportal/agent-js-cypress": "git+https://github.com/dhis2/agent-js-cypress.git#develop",
"@reportportal/agent-js-jest": "^5.0.7",
"@testing-library/react-hooks": "^8.0.1",
"abortcontroller-polyfill": "^1.7.5",
"array-move": "^4.0.0",
"classnames": "^2.3.2",
Expand All @@ -75,6 +76,7 @@
"react-redux": "^8.1.2",
"react-sortable-hoc": "^1.11.0",
"react-virtualized": "^9.22.5",
"react-virtuoso": "^4.6.2",
"redux": "^4.2.1",
"redux-logger": "^3.0.6",
"redux-thunk": "^2.4.2",
Expand Down
Loading
Loading