@genspectrum/dashboard-components 0.3.2 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/custom-elements.json +45 -26
- package/dist/dashboard-components.js +340 -186
- package/dist/dashboard-components.js.map +1 -1
- package/dist/genspectrum-components.d.ts +17 -8
- package/dist/style.css +58 -50
- package/package.json +2 -1
- package/src/preact/aggregatedData/aggregate.tsx +1 -1
- package/src/preact/components/info.stories.tsx +8 -8
- package/src/preact/components/info.tsx +113 -20
- package/src/preact/dateRangeSelector/computeInitialValues.spec.ts +99 -0
- package/src/preact/dateRangeSelector/computeInitialValues.ts +73 -0
- package/src/preact/dateRangeSelector/date-range-selector.stories.tsx +93 -4
- package/src/preact/dateRangeSelector/date-range-selector.tsx +27 -88
- package/src/preact/dateRangeSelector/selectableOptions.ts +79 -0
- package/src/preact/locationFilter/location-filter.tsx +1 -1
- package/src/preact/mutationComparison/mutation-comparison.tsx +1 -1
- package/src/preact/mutationFilter/mutation-filter.stories.tsx +3 -6
- package/src/preact/mutationFilter/mutation-filter.tsx +48 -54
- package/src/preact/mutations/mutations.tsx +1 -1
- package/src/preact/prevalenceOverTime/prevalence-over-time.tsx +2 -2
- package/src/preact/relativeGrowthAdvantage/relative-growth-advantage.tsx +1 -1
- package/src/web-components/input/gs-date-range-selector.stories.ts +11 -5
- package/src/web-components/input/gs-date-range-selector.tsx +22 -5
- package/src/web-components/input/gs-location-filter.stories.ts +6 -7
- package/src/web-components/input/gs-location-filter.tsx +3 -2
- package/src/web-components/input/gs-mutation-filter.stories.ts +1 -8
- package/src/web-components/input/gs-mutation-filter.tsx +1 -9
package/custom-elements.json
CHANGED
|
@@ -268,7 +268,7 @@
|
|
|
268
268
|
"type": {
|
|
269
269
|
"text": "Meta<Required<DateRangeSelectorProps<'CustomDateRange'>>>"
|
|
270
270
|
},
|
|
271
|
-
"default": "{ title: 'Input/DateRangeSelector', component: 'gs-date-range-selector', parameters: withComponentDocs({ actions: { handles: ['gs-date-range-changed'], }, fetchMock: {}, componentDocs: { opensShadowDom: true, expectsChildren: false, codeExample, }, }), argTypes: { initialValue: { control: { type: 'select', }, options: [ PRESET_VALUE_CUSTOM, PRESET_VALUE_ALL_TIMES, PRESET_VALUE_LAST_2_WEEKS, PRESET_VALUE_LAST_MONTH, PRESET_VALUE_LAST_2_MONTHS, PRESET_VALUE_LAST_3_MONTHS, PRESET_VALUE_LAST_6_MONTHS, 'CustomDateRange', ], }, dateColumn: { control: { type: 'text' } }, customSelectOptions: { control: { type: 'object', }, }, earliestDate: { control: { type: 'text', }, }, width: { control: { type: 'text', }, }, }, args: { customSelectOptions: [{ label: 'CustomDateRange', dateFrom: '2021-01-01', dateTo: '2021-12-31' }], earliestDate: '1970-01-01', initialValue: PRESET_VALUE_LAST_6_MONTHS, dateColumn: 'aDateColumn', width: '100%', }, decorators: [withActions], tags: ['autodocs'], }"
|
|
271
|
+
"default": "{ title: 'Input/DateRangeSelector', component: 'gs-date-range-selector', parameters: withComponentDocs({ actions: { handles: ['gs-date-range-changed'], }, fetchMock: {}, componentDocs: { opensShadowDom: true, expectsChildren: false, codeExample, }, }), argTypes: { initialValue: { control: { type: 'select', }, options: [ PRESET_VALUE_CUSTOM, PRESET_VALUE_ALL_TIMES, PRESET_VALUE_LAST_2_WEEKS, PRESET_VALUE_LAST_MONTH, PRESET_VALUE_LAST_2_MONTHS, PRESET_VALUE_LAST_3_MONTHS, PRESET_VALUE_LAST_6_MONTHS, 'CustomDateRange', ], }, dateColumn: { control: { type: 'text' } }, customSelectOptions: { control: { type: 'object', }, }, earliestDate: { control: { type: 'text', }, }, width: { control: { type: 'text', }, }, }, args: { customSelectOptions: [{ label: 'CustomDateRange', dateFrom: '2021-01-01', dateTo: '2021-12-31' }], earliestDate: '1970-01-01', initialValue: PRESET_VALUE_LAST_6_MONTHS, dateColumn: 'aDateColumn', width: '100%', initialDateFrom: '', initialDateTo: '', }, decorators: [withActions], tags: ['autodocs'], }"
|
|
272
272
|
},
|
|
273
273
|
{
|
|
274
274
|
"kind": "variable",
|
|
@@ -276,7 +276,7 @@
|
|
|
276
276
|
"type": {
|
|
277
277
|
"text": "StoryObj<Required<DateRangeSelectorProps<'CustomDateRange'>>>"
|
|
278
278
|
},
|
|
279
|
-
"default": "{ render: (args) => html` <gs-app lapis=\"${LAPIS_URL}\"> <div class=\"max-w-screen-lg\"> <gs-date-range-selector .customSelectOptions=${args.customSelectOptions} .earliestDate=${args.earliestDate} .initialValue=${args.initialValue} .width=${args.width} .dateColumn=${args.dateColumn} ></gs-date-range-selector> </div> </gs-app>`, play: async ({ canvasElement, step }) => { const canvas = await withinShadowRoot(canvasElement, 'gs-date-range-selector'); const dateTo = () => canvas.getByPlaceholderText('Date to'); await step('Expect last 6 months to be selected', async () => { await expect(canvas.getByRole('combobox')).toHaveValue('last6Months'); await waitFor(() => { expect(dateTo()).toHaveValue(toYYYYMMDD(new Date())); }); }); // Due to the limitations of storybook testing which does not fire an event, // when selecting a value from the dropdown we can't test the fired event here. // An e2e test (using playwright) for that can be found in tests/dateRangeSelector.spec.ts }, }"
|
|
279
|
+
"default": "{ render: (args) => html` <gs-app lapis=\"${LAPIS_URL}\"> <div class=\"max-w-screen-lg\"> <gs-date-range-selector .customSelectOptions=${args.customSelectOptions} .earliestDate=${args.earliestDate} .initialValue=${args.initialValue} .initialDateFrom=${args.initialDateFrom} .initialDateTo=${args.initialDateTo} .width=${args.width} .dateColumn=${args.dateColumn} ></gs-date-range-selector> </div> </gs-app>`, play: async ({ canvasElement, step }) => { const canvas = await withinShadowRoot(canvasElement, 'gs-date-range-selector'); const dateTo = () => canvas.getByPlaceholderText('Date to'); await step('Expect last 6 months to be selected', async () => { await expect(canvas.getByRole('combobox')).toHaveValue('last6Months'); await waitFor(() => { expect(dateTo()).toHaveValue(toYYYYMMDD(new Date())); }); }); // Due to the limitations of storybook testing which does not fire an event, // when selecting a value from the dropdown we can't test the fired event here. // An e2e test (using playwright) for that can be found in tests/dateRangeSelector.spec.ts }, }"
|
|
280
280
|
}
|
|
281
281
|
],
|
|
282
282
|
"exports": [
|
|
@@ -334,9 +334,29 @@
|
|
|
334
334
|
"text": "'custom'\n | 'allTimes'\n | 'last2Weeks'\n | 'lastMonth'\n | 'last2Months'\n | 'last3Months'\n | 'last6Months'\n | string"
|
|
335
335
|
},
|
|
336
336
|
"default": "'last6Months'",
|
|
337
|
-
"description": "The initial value to use for this date range selector.\nMust be a valid label from the preset labels or a `label` given in the `customSelectOptions`.\n\nIf the value is invalid, the component will default to `'last6Months'
|
|
337
|
+
"description": "The initial value to use for this date range selector.\nMust be a valid label from the preset labels or a `label` given in the `customSelectOptions`.\n\nIf the value is invalid, the component will default to `'last6Months'`.\n\nIt will be overwritten if `initialDateFrom` or `initialDateTo` is set.",
|
|
338
338
|
"attribute": "initialValue"
|
|
339
339
|
},
|
|
340
|
+
{
|
|
341
|
+
"kind": "field",
|
|
342
|
+
"name": "initialDateFrom",
|
|
343
|
+
"type": {
|
|
344
|
+
"text": "string"
|
|
345
|
+
},
|
|
346
|
+
"default": "''",
|
|
347
|
+
"description": "A date string in the format `YYYY-MM-DD`.\nIf set, the date range selector will be initialized with the given date (overwriting `initialValue` to `custom`).\nIf `initialDateTo` is set, but this is unset, it will default to `earliestDate`.",
|
|
348
|
+
"attribute": "initialDateFrom"
|
|
349
|
+
},
|
|
350
|
+
{
|
|
351
|
+
"kind": "field",
|
|
352
|
+
"name": "initialDateTo",
|
|
353
|
+
"type": {
|
|
354
|
+
"text": "string"
|
|
355
|
+
},
|
|
356
|
+
"default": "''",
|
|
357
|
+
"description": "A date string in the format `YYYY-MM-DD`.\nIf set, the date range selector will be initialized with the given date (overwriting `initialValue` to `custom`).\nIf `initialDateFrom` is set, but this is unset, it will default to the current date.",
|
|
358
|
+
"attribute": "initialDateTo"
|
|
359
|
+
},
|
|
340
360
|
{
|
|
341
361
|
"kind": "field",
|
|
342
362
|
"name": "width",
|
|
@@ -392,9 +412,27 @@
|
|
|
392
412
|
"text": "'custom'\n | 'allTimes'\n | 'last2Weeks'\n | 'lastMonth'\n | 'last2Months'\n | 'last3Months'\n | 'last6Months'\n | string"
|
|
393
413
|
},
|
|
394
414
|
"default": "'last6Months'",
|
|
395
|
-
"description": "The initial value to use for this date range selector.\nMust be a valid label from the preset labels or a `label` given in the `customSelectOptions`.\n\nIf the value is invalid, the component will default to `'last6Months'
|
|
415
|
+
"description": "The initial value to use for this date range selector.\nMust be a valid label from the preset labels or a `label` given in the `customSelectOptions`.\n\nIf the value is invalid, the component will default to `'last6Months'`.\n\nIt will be overwritten if `initialDateFrom` or `initialDateTo` is set.",
|
|
396
416
|
"fieldName": "initialValue"
|
|
397
417
|
},
|
|
418
|
+
{
|
|
419
|
+
"name": "initialDateFrom",
|
|
420
|
+
"type": {
|
|
421
|
+
"text": "string"
|
|
422
|
+
},
|
|
423
|
+
"default": "''",
|
|
424
|
+
"description": "A date string in the format `YYYY-MM-DD`.\nIf set, the date range selector will be initialized with the given date (overwriting `initialValue` to `custom`).\nIf `initialDateTo` is set, but this is unset, it will default to `earliestDate`.",
|
|
425
|
+
"fieldName": "initialDateFrom"
|
|
426
|
+
},
|
|
427
|
+
{
|
|
428
|
+
"name": "initialDateTo",
|
|
429
|
+
"type": {
|
|
430
|
+
"text": "string"
|
|
431
|
+
},
|
|
432
|
+
"default": "''",
|
|
433
|
+
"description": "A date string in the format `YYYY-MM-DD`.\nIf set, the date range selector will be initialized with the given date (overwriting `initialValue` to `custom`).\nIf `initialDateFrom` is set, but this is unset, it will default to the current date.",
|
|
434
|
+
"fieldName": "initialDateTo"
|
|
435
|
+
},
|
|
398
436
|
{
|
|
399
437
|
"name": "width",
|
|
400
438
|
"type": {
|
|
@@ -483,7 +521,7 @@
|
|
|
483
521
|
"type": {
|
|
484
522
|
"text": "StoryObj<LocationFilterProps>"
|
|
485
523
|
},
|
|
486
|
-
"default": "{ ...Template, parameters: { fetchMock: { mocks: [ { matcher: aggregatedEndpointMatcher, response: { status: 200, body: data, }, }, ], }, }, play: async ({ canvasElement, step }) => { const canvas = await withinShadowRoot(canvasElement, 'gs-location-filter'); const inputField = () => canvas.getByRole('combobox'); const listenerMock = fn(); await step('Setup event listener mock', async () => { canvasElement.addEventListener('gs-location-changed', listenerMock); }); await step('wait until data is loaded', async () => { await waitFor(() => { return expect(inputField()).toBeEnabled(); }); }); await step('Input invalid location', async () => { await userEvent.type(inputField(), 'Not / A / Location'); await expect(listenerMock).not.toHaveBeenCalled(); await userEvent.type(inputField(), '{backspace>18/}'); }); await step('Select Asia', async () => { await userEvent.type(inputField(), 'Asia'); await expect(listenerMock
|
|
524
|
+
"default": "{ ...Template, parameters: { fetchMock: { mocks: [ { matcher: aggregatedEndpointMatcher, response: { status: 200, body: data, }, }, ], }, }, play: async ({ canvasElement, step }) => { const canvas = await withinShadowRoot(canvasElement, 'gs-location-filter'); const inputField = () => canvas.getByRole('combobox'); const listenerMock = fn(); await step('Setup event listener mock', async () => { canvasElement.addEventListener('gs-location-changed', listenerMock); }); await step('wait until data is loaded', async () => { await waitFor(() => { return expect(inputField()).toBeEnabled(); }); }); await step('Input invalid location', async () => { await userEvent.type(inputField(), 'Not / A / Location'); await expect(listenerMock).not.toHaveBeenCalled(); await userEvent.type(inputField(), '{backspace>18/}'); }); await step('Select Asia', async () => { await userEvent.type(inputField(), 'Asia'); await expect(listenerMock.mock.calls.at(-1)[0].detail).toStrictEqual({ region: 'Asia', country: undefined, division: undefined, location: undefined, }); }); await step('Select Asia / Bangladesh / Rajshahi / Chapainawabgonj', async () => { await userEvent.type(inputField(), ' / Bangladesh / Rajshahi / Chapainawabgonj'); await expect(listenerMock).toHaveBeenCalledWith( expect.objectContaining({ detail: { region: 'Asia', country: 'Bangladesh', division: 'Rajshahi', location: 'Chapainawabgonj', }, }), ); }); }, }"
|
|
487
525
|
}
|
|
488
526
|
],
|
|
489
527
|
"exports": [
|
|
@@ -574,7 +612,7 @@
|
|
|
574
612
|
"type": {
|
|
575
613
|
"text": "CustomEvent<Record<string, string>>"
|
|
576
614
|
},
|
|
577
|
-
"description": "Fired when a value from the datalist is selected or when a valid value is typed into the field. The `details` of this event contain an object with all `fields` as keys and the corresponding values as values, if they are
|
|
615
|
+
"description": "Fired when a value from the datalist is selected or when a valid value is typed into the field. The `details` of this event contain an object with all `fields` as keys and the corresponding values as values, even if they are `undefined`. Example: ``` { continent: \"Asia\", country: \"China\", city: \"Beijing\", district: undefined, } ```",
|
|
578
616
|
"name": "gs-location-changed"
|
|
579
617
|
}
|
|
580
618
|
],
|
|
@@ -644,7 +682,7 @@
|
|
|
644
682
|
"type": {
|
|
645
683
|
"text": "Meta<MutationFilterProps>"
|
|
646
684
|
},
|
|
647
|
-
"default": "{ title: 'Input/Mutation filter', component: 'gs-mutation-filter', parameters: withComponentDocs({ actions: { handles: ['gs-mutation-filter-changed', 'gs-mutation-filter-on-blur'], }, fetchMock: {}, componentDocs: { opensShadowDom: true, expectsChildren: false, codeExample, }, }), argTypes: { initialValue: { control: { type: 'object', }, }, width: { control: 'text' },
|
|
685
|
+
"default": "{ title: 'Input/Mutation filter', component: 'gs-mutation-filter', parameters: withComponentDocs({ actions: { handles: ['gs-mutation-filter-changed', 'gs-mutation-filter-on-blur'], }, fetchMock: {}, componentDocs: { opensShadowDom: true, expectsChildren: false, codeExample, }, }), argTypes: { initialValue: { control: { type: 'object', }, }, width: { control: 'text' }, }, decorators: [withActions], tags: ['autodocs'], }"
|
|
648
686
|
},
|
|
649
687
|
{
|
|
650
688
|
"kind": "variable",
|
|
@@ -734,16 +772,6 @@
|
|
|
734
772
|
"default": "'100%'",
|
|
735
773
|
"description": "The width of the component.\n\nVisit https://genspectrum.github.io/dashboards/?path=/docs/components-size-of-components--docs for more information.",
|
|
736
774
|
"attribute": "width"
|
|
737
|
-
},
|
|
738
|
-
{
|
|
739
|
-
"kind": "field",
|
|
740
|
-
"name": "height",
|
|
741
|
-
"type": {
|
|
742
|
-
"text": "string"
|
|
743
|
-
},
|
|
744
|
-
"default": "'6.5rem'",
|
|
745
|
-
"description": "The height of the component.\n\nVisit https://genspectrum.github.io/dashboards/?path=/docs/components-size-of-components--docs for more information.",
|
|
746
|
-
"attribute": "height"
|
|
747
775
|
}
|
|
748
776
|
],
|
|
749
777
|
"events": [
|
|
@@ -780,15 +808,6 @@
|
|
|
780
808
|
"default": "'100%'",
|
|
781
809
|
"description": "The width of the component.\n\nVisit https://genspectrum.github.io/dashboards/?path=/docs/components-size-of-components--docs for more information.",
|
|
782
810
|
"fieldName": "width"
|
|
783
|
-
},
|
|
784
|
-
{
|
|
785
|
-
"name": "height",
|
|
786
|
-
"type": {
|
|
787
|
-
"text": "string"
|
|
788
|
-
},
|
|
789
|
-
"default": "'6.5rem'",
|
|
790
|
-
"description": "The height of the component.\n\nVisit https://genspectrum.github.io/dashboards/?path=/docs/components-size-of-components--docs for more information.",
|
|
791
|
-
"fieldName": "height"
|
|
792
811
|
}
|
|
793
812
|
],
|
|
794
813
|
"superclass": {
|