diff --git a/CHANGELOG.md b/CHANGELOG.md
index 5e610c9a75..ca479e4797 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -29,7 +29,7 @@ You can also check the
makes Visualize winding order agnostic and fixes a specific bug with newer
CCW geometries from Swisstopo where map diagrams were zoomed to the world
instead of Switzerland (older geometries all had CW winding order).
- - Improve dimension values query performance.
+ - Improve dimension values query performance.
- Maintenance
- Remove Google Analytics integration (it is no longer in use)
- Set Maptiler API key from `MAPTILER_API_KEY` environment variable at
@@ -40,6 +40,7 @@ You can also check the
- Remove dependencies which used old versions of `node-fetch`
- Upgrade dependencies which used old versions of `nth-check`
- Updated `@deck.gl/*` packages and `fast-xml-parser`
+ - Upgrade playwright to v1.60
- Rename package
- Documentation
- Add publiccode.yml for discoverability
diff --git a/app/docs/chart-selection-tabs.docs.mdx b/app/docs/chart-selection-tabs.docs.mdx
index 146ba963ff..e80299fe79 100644
--- a/app/docs/chart-selection-tabs.docs.mdx
+++ b/app/docs/chart-selection-tabs.docs.mdx
@@ -3,28 +3,31 @@ import {
ConfiguratorStateConfiguringChart,
ConfiguratorStateProvider,
} from "@/configurator";
-import palmerPenguinsFixture from "@/test/__fixtures/config/int/scatterplot-palmer-penguins.json";
-import { Canvas, Meta } from '@storybook/blocks';
-import * as ChartSelectionTabsStories from './chart-selection-tabs.stories';
+import scatterplotGreenhouseGasesFixture from "@/test/__fixtures/config/int/scatterplot-greenhouse-gases.json";
+import { Canvas, Meta } from "@storybook/blocks";
+import * as ChartSelectionTabsStories from "./chart-selection-tabs.stories";
-> Chart Selection Tabs are used in ChartPreview and ChartPublished to enable selecting a chart type in any stage of creating a chart.
+> Chart Selection Tabs are used in ChartPreview and ChartPublished to enable
+> selecting a chart type in any stage of creating a chart.
-They can be either _editable_, to display a button to show ChartTypeSelector (used when creating a chart) or not, to disable that functionality (used in published charts).
+They can be either _editable_, to display a button to show ChartTypeSelector
+(used when creating a chart) or not, to disable that functionality (used in
+published charts).
-
## Editable
-
## Non-editable
## For developers
-This component is based on MUI's Tabs & Tab components, styled in the federal theme.
+This component is based on MUI's Tabs & Tab components, styled in the federal
+theme.
-Currently it does not support multiple tabs, as this will be implemented together with chart composition.
+Currently it does not support multiple tabs, as this will be implemented
+together with chart composition.
diff --git a/app/docs/chart-selection-tabs.stories.tsx b/app/docs/chart-selection-tabs.stories.tsx
index d4df7131cc..7bec07ad55 100644
--- a/app/docs/chart-selection-tabs.stories.tsx
+++ b/app/docs/chart-selection-tabs.stories.tsx
@@ -2,7 +2,7 @@ import { Meta, StoryObj } from "@storybook/react";
import { ChartSelectionTabs } from "@/components/chart-selection-tabs";
import { ConfiguratorState, ConfiguratorStateProvider } from "@/configurator";
-import palmerPenguinsFixture from "@/test/__fixtures/config/int/scatterplot-palmer-penguins.json";
+import scatterplotGreenhouseGasesFixture from "@/test/__fixtures/config/int/scatterplot-greenhouse-gases.json";
type Story = StoryObj;
const meta: Meta = {
@@ -12,7 +12,7 @@ const meta: Meta = {
(Story, ctx) => {
return (
@@ -27,7 +27,7 @@ export const Editable: Story = {
args: {},
parameters: {
state: {
- ...palmerPenguinsFixture.data,
+ ...scatterplotGreenhouseGasesFixture.data,
state: "CONFIGURING_CHART",
},
},
@@ -37,7 +37,7 @@ export const NonEditable: Story = {
args: {},
parameters: {
state: {
- ...palmerPenguinsFixture.data,
+ ...scatterplotGreenhouseGasesFixture.data,
state: "PUBLISHING",
},
},
diff --git a/app/package.json b/app/package.json
index f623c4a91d..2aa8f03946 100644
--- a/app/package.json
+++ b/app/package.json
@@ -196,8 +196,7 @@
"@lingui/cli": "^4.0.0",
"@lingui/macro": "^4.0.0",
"@mdx-js/loader": "^1.6.22",
- "@playwright-testing-library/test": "^4.5.0",
- "@playwright/test": "^1.49.1",
+ "@playwright/test": "^1.60.0",
"@svgr/cli": "^7",
"@types/autosuggest-highlight": "^3.2.0",
"@types/clownface": "^2.0.7",
@@ -249,7 +248,6 @@
"eslint-plugin-unused-imports": "^4.1.4",
"io-ts-to-json-schema": "^0.2.0",
"jsdom": "^26.1.0",
- "playwright-testing-library": "^4.5.0",
"prettier": "^3.2.5"
}
}
diff --git a/app/test/__fixtures/config/int/bathing-water-quality-hierarchie.json b/app/test/__fixtures/config/int/bathing-water-quality-hierarchie.json
index 632f742d1f..b83d1c6f51 100644
--- a/app/test/__fixtures/config/int/bathing-water-quality-hierarchie.json
+++ b/app/test/__fixtures/config/int/bathing-water-quality-hierarchie.json
@@ -15,9 +15,9 @@
"it": ""
}
},
- "dataSet": "https://environment.ld.admin.ch/foen/ubd0104/11",
+ "dataSet": "https://environment.ld.admin.ch/foen/ubd01041prod/13",
"dataSource": {
- "url": "https://int.cached.lindas.admin.ch/query",
+ "url": "https://cached.lindas.admin.ch/query",
"type": "sparql"
},
"chartConfig": {
@@ -27,18 +27,18 @@
"sortingType": "byAuto",
"sortingOrder": "asc"
},
- "componentIri": "https://environment.ld.admin.ch/foen/ubd0104/dateofprobing"
+ "componentIri": "https://environment.ld.admin.ch/foen/ubd01041prod/dateofprobing"
},
"y": {
- "componentIri": "https://environment.ld.admin.ch/foen/ubd0104/value"
+ "componentIri": "https://environment.ld.admin.ch/foen/ubd01041prod/value"
}
},
"filters": {
- "https://environment.ld.admin.ch/foen/ubd0104/location": {
+ "https://environment.ld.admin.ch/foen/ubd01041prod/location": {
"type": "single",
- "value": "https://ld.admin.ch/dimension/bgdi/inlandwaters/bathingwater/CH19007"
+ "value": "https://ld.admin.ch/dimension/bgdi/inlandwaters/bathingwater/CH21089"
},
- "https://environment.ld.admin.ch/foen/ubd0104/parametertype": {
+ "https://environment.ld.admin.ch/foen/ubd01041prod/parametertype": {
"type": "single",
"value": "E.coli"
}
@@ -62,7 +62,7 @@
"dataFilters": {
"active": true,
"componentIris": [
- "https://environment.ld.admin.ch/foen/ubd0104/location"
+ "https://environment.ld.admin.ch/foen/ubd01041prod/location"
]
},
"calculation": {
diff --git a/app/test/__fixtures/config/int/column-heavy-metals.json b/app/test/__fixtures/config/int/column-heavy-metals.json
index 2cd74d391a..f4d1ac174f 100644
--- a/app/test/__fixtures/config/int/column-heavy-metals.json
+++ b/app/test/__fixtures/config/int/column-heavy-metals.json
@@ -15,10 +15,10 @@
"it": ""
}
},
- "dataSet": "https://environment.ld.admin.ch/foen/ubd0066/15",
+ "dataSet": "https://environment.ld.admin.ch/foen/ubd006601/5",
"dataSource": {
"type": "sparql",
- "url": "https://int.cached.lindas.admin.ch/query"
+ "url": "https://cached.lindas.admin.ch/query"
},
"chartConfig": {
"version": "1.2.1",
@@ -28,20 +28,20 @@
"sortingType": "byDimensionLabel",
"sortingOrder": "asc"
},
- "componentIri": "https://environment.ld.admin.ch/foen/ubd0066/messparameter"
+ "componentIri": "https://environment.ld.admin.ch/foen/ubd006601/messparameter"
},
"y": {
- "componentIri": "https://environment.ld.admin.ch/foen/ubd0066/wert"
+ "componentIri": "https://environment.ld.admin.ch/foen/ubd006601/wert"
}
},
"filters": {
"https://environment.ld.admin.ch/foen/ubd0066/station": {
"type": "single",
- "value": "https://environment.ld.admin.ch/foen/ubd0066/Station/100_1"
+ "value": "https://environment.ld.admin.ch/foen/ubd006601/Station/100_1"
},
"https://environment.ld.admin.ch/foen/ubd0066/samplingperiod": {
"type": "single",
- "value": "https://environment.ld.admin.ch/foen/ubd0066/samplingperiod/1"
+ "value": "https://environment.ld.admin.ch/foen/ubd006601/samplingperiod/1"
}
},
"chartType": "column",
diff --git a/app/test/__fixtures/config/int/configs.ts b/app/test/__fixtures/config/int/configs.ts
index a82bdb6481..e62c426d26 100644
--- a/app/test/__fixtures/config/int/configs.ts
+++ b/app/test/__fixtures/config/int/configs.ts
@@ -18,7 +18,7 @@ export const configs: TestConfig[] = [
},
{
chartId: "cfNkIaMvN_xL",
- name: "Scatterplot - Palmer Penguins",
- slug: "scatterplot-palmer-penguins",
+ name: "Scatterplot - Greenhouse Gases",
+ slug: "scatterplot-greenhouse-gases",
},
];
diff --git a/app/test/__fixtures/config/int/pie-red-list.json b/app/test/__fixtures/config/int/pie-red-list.json
index f05c1892e5..959a7edf9c 100644
--- a/app/test/__fixtures/config/int/pie-red-list.json
+++ b/app/test/__fixtures/config/int/pie-red-list.json
@@ -1,59 +1,145 @@
{
"key": "Z6Re21LHbOoP",
"data": {
- "dataSet": "https://environment.ld.admin.ch/foen/UBD003002/5",
+ "version": "5.3.0",
+ "state": "CONFIGURING_CHART",
"dataSource": {
"type": "sparql",
- "url": "https://int.cached.lindas.admin.ch/query"
+ "url": "https://cached.lindas.admin.ch/query"
},
- "meta": {
- "title": {
- "de": "",
- "fr": "",
- "it": "",
- "en": "Amphibians red list status"
- },
- "description": { "de": "", "fr": "", "it": "", "en": "" }
- },
- "chartConfig": {
- "version": "1.2.1",
- "chartType": "pie",
- "filters": {
- "https://environment.ld.admin.ch/foen/UBD003002/artengruppe": {
- "type": "single",
- "value": "https://environment.ld.admin.ch/foen/UBD003002/ArtenGruppe/AMPH"
+ "layout": {
+ "type": "tab",
+ "meta": {
+ "title": {
+ "de": "",
+ "en": "",
+ "fr": "",
+ "it": ""
+ },
+ "description": {
+ "de": "",
+ "en": "",
+ "fr": "",
+ "it": ""
+ },
+ "label": {
+ "de": "",
+ "en": "",
+ "fr": "",
+ "it": ""
}
},
- "interactiveFiltersConfig": {
- "legend": { "active": false, "componentIri": "" },
- "timeRange": {
- "active": false,
- "componentIri": "",
- "presets": { "type": "range", "from": "", "to": "" }
+ "blocks": [
+ {
+ "type": "chart",
+ "key": "soEEFsNM4O7g",
+ "initialized": false
+ }
+ ]
+ },
+ "chartConfigs": [
+ {
+ "key": "soEEFsNM4O7g",
+ "version": "5.3.0",
+ "meta": {
+ "title": {
+ "en": "",
+ "de": "",
+ "fr": "",
+ "it": ""
+ },
+ "description": {
+ "en": "",
+ "de": "",
+ "fr": "",
+ "it": ""
+ },
+ "label": {
+ "en": "",
+ "de": "",
+ "fr": "",
+ "it": ""
+ }
},
- "dataFilters": { "active": false, "componentIris": [] }
- },
- "fields": {
- "y": {
- "componentIri": "https://environment.ld.admin.ch/foen/UBD003002/value"
+ "cubes": [
+ {
+ "iri": "https://environment.ld.admin.ch/foen/ubd003001/10",
+ "filters": {
+ "https://environment.ld.admin.ch/foen/ubd003001(VISUALIZE.ADMIN_COMPONENT_ID_SEPARATOR)https://environment.ld.admin.ch/foen/ubd003001/groupid": {
+ "type": "single",
+ "value": "https://environment.ld.admin.ch/vocabulary/foen_species_classification/100000"
+ }
+ }
+ }
+ ],
+ "interactiveFiltersConfig": {
+ "legend": {
+ "active": false,
+ "componentId": ""
+ },
+ "timeRange": {
+ "active": false,
+ "componentId": "https://environment.ld.admin.ch/foen/ubd003001(VISUALIZE.ADMIN_COMPONENT_ID_SEPARATOR)https://environment.ld.admin.ch/foen/ubd003001/groupid",
+ "presets": {
+ "type": "range",
+ "from": "",
+ "to": ""
+ }
+ },
+ "dataFilters": {
+ "active": false,
+ "componentIds": [],
+ "defaultValueOverrides": {},
+ "filterTypes": {}
+ },
+ "calculation": {
+ "active": false,
+ "type": "identity"
+ }
},
- "segment": {
- "componentIri": "https://environment.ld.admin.ch/foen/UBD003002/status",
- "palette": "category10",
- "sorting": { "sortingType": "byMeasure", "sortingOrder": "asc" },
- "colorMapping": {
- "https://environment.ld.admin.ch/foen/UBD003002/Status/DD": "#1f77b4",
- "https://environment.ld.admin.ch/foen/UBD003002/Status/LC": "#ff7f0e",
- "https://environment.ld.admin.ch/foen/UBD003002/Status/NT": "#2ca02c",
- "https://environment.ld.admin.ch/foen/UBD003002/Status/VU": "#d62728",
- "https://environment.ld.admin.ch/foen/UBD003002/Status/EN": "#9467bd",
- "https://environment.ld.admin.ch/foen/UBD003002/Status/CR": "#8c564b",
- "https://environment.ld.admin.ch/foen/UBD003002/Status/RE": "#e377c2",
- "https://environment.ld.admin.ch/foen/UBD003002/Status/EX": "#7f7f7f"
+ "annotations": [],
+ "limits": {},
+ "conversionUnitsByComponentId": {},
+ "activeField": "segment",
+ "chartType": "pie",
+ "fields": {
+ "y": {
+ "componentId": "https://environment.ld.admin.ch/foen/ubd003001(VISUALIZE.ADMIN_COMPONENT_ID_SEPARATOR)https://environment.ld.admin.ch/foen/ubd003001/value"
+ },
+ "segment": {
+ "componentId": "https://environment.ld.admin.ch/foen/ubd003001(VISUALIZE.ADMIN_COMPONENT_ID_SEPARATOR)https://environment.ld.admin.ch/foen/ubd003001/statuscode",
+ "showValuesMapping": {}
+ },
+ "color": {
+ "type": "segment",
+ "paletteId": "category10",
+ "colorMapping": {
+ "https://environment.ld.admin.ch/vocabulary/iucn_conservation_categories/DD": "#1f77b4",
+ "https://environment.ld.admin.ch/vocabulary/iucn_conservation_categories/LC": "#ff7f0e",
+ "https://environment.ld.admin.ch/vocabulary/iucn_conservation_categories/NT": "#2ca02c",
+ "https://environment.ld.admin.ch/vocabulary/iucn_conservation_categories/VU": "#d62728",
+ "https://environment.ld.admin.ch/vocabulary/iucn_conservation_categories/EN": "#9467bd",
+ "https://environment.ld.admin.ch/vocabulary/iucn_conservation_categories/CR": "#8c564b",
+ "https://environment.ld.admin.ch/vocabulary/iucn_conservation_categories/RE": "#e377c2"
+ }
}
}
}
- },
- "activeField": "title"
+ ],
+ "activeChartKey": "soEEFsNM4O7g",
+ "dashboardFilters": {
+ "timeRange": {
+ "active": false,
+ "timeUnit": "",
+ "presets": {
+ "from": "",
+ "to": ""
+ }
+ },
+ "dataFilters": {
+ "componentIds": [],
+ "filters": {}
+ }
+ }
}
}
diff --git a/app/test/__fixtures/config/int/scatterplot-greenhouse-gases.json b/app/test/__fixtures/config/int/scatterplot-greenhouse-gases.json
new file mode 100644
index 0000000000..ceed599ba1
--- /dev/null
+++ b/app/test/__fixtures/config/int/scatterplot-greenhouse-gases.json
@@ -0,0 +1,145 @@
+{
+ "key": "kHovM7MmR4uw",
+ "data": {
+ "version": "5.3.0",
+ "state": "CONFIGURING_CHART",
+ "dataSource": {
+ "type": "sparql",
+ "url": "https://cached.lindas.admin.ch/query"
+ },
+ "layout": {
+ "type": "tab",
+ "meta": {
+ "title": {
+ "de": "",
+ "en": "",
+ "fr": "",
+ "it": ""
+ },
+ "description": {
+ "de": "",
+ "en": "",
+ "fr": "",
+ "it": ""
+ },
+ "label": {
+ "de": "",
+ "en": "",
+ "fr": "",
+ "it": ""
+ }
+ },
+ "blocks": [
+ {
+ "type": "chart",
+ "key": "kHovM7MmR4uw",
+ "initialized": false
+ }
+ ]
+ },
+ "chartConfigs": [
+ {
+ "key": "kHovM7MmR4uw",
+ "version": "5.3.0",
+ "meta": {
+ "title": {
+ "en": "",
+ "de": "",
+ "fr": "",
+ "it": ""
+ },
+ "description": {
+ "en": "",
+ "de": "",
+ "fr": "",
+ "it": ""
+ },
+ "label": {
+ "en": "",
+ "de": "",
+ "fr": "",
+ "it": ""
+ }
+ },
+ "cubes": [
+ {
+ "iri": "https://environment.ld.admin.ch/foen/ubd000503/10",
+ "filters": {
+ "https://environment.ld.admin.ch/foen/ubd000503(VISUALIZE.ADMIN_COMPONENT_ID_SEPARATOR)https://environment.ld.admin.ch/foen/ubd000503/jahr": {
+ "type": "single",
+ "value": "1990"
+ }
+ }
+ }
+ ],
+ "interactiveFiltersConfig": {
+ "legend": {
+ "active": false,
+ "componentId": ""
+ },
+ "timeRange": {
+ "active": false,
+ "componentId": "https://environment.ld.admin.ch/foen/ubd000503(VISUALIZE.ADMIN_COMPONENT_ID_SEPARATOR)https://environment.ld.admin.ch/foen/ubd000503/jahr",
+ "presets": {
+ "type": "range",
+ "from": "",
+ "to": ""
+ }
+ },
+ "dataFilters": {
+ "active": false,
+ "componentIds": [],
+ "defaultValueOverrides": {},
+ "filterTypes": {},
+ "defaultOpen": true
+ },
+ "calculation": {
+ "active": false,
+ "type": "identity"
+ }
+ },
+ "annotations": [],
+ "limits": {},
+ "conversionUnitsByComponentId": {},
+ "chartType": "scatterplot",
+ "fields": {
+ "x": {
+ "componentId": "https://environment.ld.admin.ch/foen/ubd000503(VISUALIZE.ADMIN_COMPONENT_ID_SEPARATOR)https://environment.ld.admin.ch/foen/ubd000503/werte"
+ },
+ "y": {
+ "componentId": "https://environment.ld.admin.ch/foen/ubd000503(VISUALIZE.ADMIN_COMPONENT_ID_SEPARATOR)https://environment.ld.admin.ch/foen/ubd000503/werteNichtGerundet"
+ },
+ "color": {
+ "type": "segment",
+ "paletteId": "category10",
+ "colorMapping": {
+ "https://environment.ld.admin.ch/foen/ubd000503/Treibstoffe/treib1": "#1f77b4",
+ "https://environment.ld.admin.ch/foen/ubd000503/Treibstoffe/treib2": "#ff7f0e",
+ "https://environment.ld.admin.ch/foen/ubd000503/Treibstoffe/treib3": "#2ca02c",
+ "https://environment.ld.admin.ch/foen/ubd000503/Treibstoffe/treib4": "#d62728"
+ }
+ },
+ "segment": {
+ "componentId": "https://environment.ld.admin.ch/foen/ubd000503(VISUALIZE.ADMIN_COMPONENT_ID_SEPARATOR)https://environment.ld.admin.ch/foen/ubd000503/treibstoffe",
+ "showValuesMapping": {}
+ }
+ }
+ }
+ ],
+ "activeChartKey": "kHovM7MmR4uw",
+ "dashboardFilters": {
+ "timeRange": {
+ "active": false,
+ "timeUnit": "",
+ "presets": {
+ "from": "",
+ "to": ""
+ }
+ },
+ "dataFilters": {
+ "componentIds": [],
+ "filters": {}
+ }
+ }
+ }
+}
diff --git a/app/test/__fixtures/config/int/scatterplot-palmer-penguins.json b/app/test/__fixtures/config/int/scatterplot-palmer-penguins.json
deleted file mode 100644
index f69bbaac9a..0000000000
--- a/app/test/__fixtures/config/int/scatterplot-palmer-penguins.json
+++ /dev/null
@@ -1,66 +0,0 @@
-{
- "key": "cfNkIaMvN_xL",
- "data": {
- "state": "DESCRIBING_CHART",
- "dataSet": "https://environment.ld.admin.ch/foen/palmer-penguins/18",
- "dataSource": {
- "type": "sparql",
- "url": "https://int.cached.lindas.admin.ch/query"
- },
- "meta": {
- "title": {
- "de": "",
- "fr": "",
- "it": "",
- "en": "Mean bill depth vs mean bill depth for Adelie Penguins"
- },
- "description": { "de": "", "fr": "", "it": "", "en": "" }
- },
- "chartConfig": {
- "version": "1.2.1",
- "chartType": "scatterplot",
- "filters": {
- "https://environment.ld.admin.ch/foen/palmer-penguins/species": {
- "type": "single",
- "value": "https://environment.ld.admin.ch/foen/palmer-penguins/species/Adelie"
- },
- "https://environment.ld.admin.ch/foen/palmer-penguins/sex": {
- "type": "single",
- "value": "female"
- },
- "https://environment.ld.admin.ch/foen/palmer-penguins/year": {
- "type": "single",
- "value": "2007"
- }
- },
- "cubes": [],
- "interactiveFiltersConfig": {
- "legend": { "active": false, "componentIri": "" },
- "timeRange": {
- "active": false,
- "componentIri": "",
- "presets": { "type": "range", "from": "", "to": "" }
- },
- "dataFilters": { "active": false, "componentIris": [] }
- },
- "fields": {
- "x": {
- "componentIri": "https://environment.ld.admin.ch/foen/palmer-penguins/billlengthmm"
- },
- "y": {
- "componentIri": "https://environment.ld.admin.ch/foen/palmer-penguins/billdepthmm"
- },
- "segment": {
- "componentIri": "https://environment.ld.admin.ch/foen/palmer-penguins/islands",
- "palette": "category10",
- "colorMapping": {
- "https://environment.ld.admin.ch/foen/palmer-penguins/islands/Biscoe": "#1f77b4",
- "https://environment.ld.admin.ch/foen/palmer-penguins/islands/Dream": "#ff7f0e",
- "https://environment.ld.admin.ch/foen/palmer-penguins/islands/Torgersen": "#2ca02c"
- }
- }
- }
- },
- "activeField": "title"
- }
-}
diff --git a/e2e/abbreviations.spec.ts b/e2e/abbreviations.spec.ts
index 3433fb1e1c..5b5272c39e 100644
--- a/e2e/abbreviations.spec.ts
+++ b/e2e/abbreviations.spec.ts
@@ -25,12 +25,10 @@ test("it should be possible to enable abbreviations for colors & x field (column
expect(await checkbox.isDisabled()).toEqual(true);
- await (
- await selectors.panels
- .drawer()
- .within()
- .getByLabelText("Jahr der Vergütung")
- ).click();
+ await selectors.panels
+ .drawer()
+ .getByRole("combobox", { name: "Jahr der Vergütung" })
+ .click();
await actions.mui.selectOption("Kanton");
@@ -43,12 +41,13 @@ test("it should be possible to enable abbreviations for colors & x field (column
await sleep(3_000);
- const xAxis = await selectors.chart.axisWidthBand();
+ const xAxis = selectors.chart.axisWidthBand();
const ticks = (await xAxis.textContent()) as string;
- await (
- await selectors.panels.drawer().within().getByLabelText("Kanton")
- ).click();
+ await selectors.panels
+ .drawer()
+ .getByRole("combobox", { name: "Kanton" })
+ .click();
await actions.mui.selectOption("Jahr der Vergütung");
@@ -59,9 +58,10 @@ test("it should be possible to enable abbreviations for colors & x field (column
await actions.editor.selectActiveField("Segmentation");
await selectors.edition.drawerLoaded();
- await (
- await selectors.panels.drawer().within().getByLabelText("None")
- ).click();
+ await selectors.panels
+ .drawer()
+ .getByRole("combobox", { name: "None" })
+ .click();
await actions.mui.selectOption("Kanton");
@@ -71,7 +71,7 @@ test("it should be possible to enable abbreviations for colors & x field (column
// Wait for the data to load.
await selectors.chart.loaded();
await selectors.edition.filtersLoaded();
- await selectors.chart.colorLegend(undefined, { timeout: 3_000 });
+ await selectors.chart.colorLegend({ timeout: 3_000 });
await sleep(3_000);
@@ -98,9 +98,10 @@ test("hierarchies: it should be possible to enable abbreviations for colors", as
await selectors.edition.drawerLoaded();
await actions.editor.selectActiveField("Segmentation");
- await (
- await selectors.panels.drawer().within().getByLabelText("None")
- ).click();
+ await selectors.panels
+ .drawer()
+ .getByRole("combobox", { name: "None" })
+ .click();
await actions.mui.selectOption("Greenhouse gas");
await selectors.edition.drawerLoaded();
@@ -110,7 +111,7 @@ test("hierarchies: it should be possible to enable abbreviations for colors", as
await selectors.chart.loaded();
await selectors.edition.filtersLoaded();
- await selectors.chart.colorLegend(undefined, { timeout: 3_000 });
+ await selectors.chart.colorLegend({ timeout: 3_000 });
await sleep(3_000);
@@ -153,7 +154,7 @@ test("localized abbreviations", async ({
await selectors.chart.loaded();
await selectors.edition.filtersLoaded();
- await selectors.chart.colorLegend(undefined, { timeout: 3_000 });
+ await selectors.chart.colorLegend({ timeout: 3_000 });
await sleep(3_000);
diff --git a/e2e/actions.ts b/e2e/actions.ts
index 657e28ba49..bcc58f3613 100644
--- a/e2e/actions.ts
+++ b/e2e/actions.ts
@@ -4,31 +4,27 @@ import { TestContext } from "./types";
type ActionTestContext = TestContext & { selectors: Selectors };
const selectActiveEditorField =
- ({ selectors, within }: ActionTestContext) =>
+ ({ selectors }: ActionTestContext) =>
async (field: string) => {
const chartOptions =
selectors.edition.controlSectionByTitle("Chart Options");
await chartOptions.scrollIntoViewIfNeeded();
- const fieldLocator = await within(chartOptions).findByText(
- field,
- undefined,
- { timeout: 3000 }
- );
+ const fieldLocator = chartOptions.getByText(field);
+ await fieldLocator.waitFor({ timeout: 3000 });
await fieldLocator.click();
await selectors.panels
.drawer()
- .within()
- .findByText(field, undefined, { timeout: 3000 });
+ .getByText(field)
+ .first()
+ .waitFor({ timeout: 3000 });
};
export const createActions = ({
page,
- screen,
selectors,
- within,
}: TestContext & { selectors: Selectors }) => ({
search: {
- clear: async () => await screen.getByTestId("clearSearch").click(),
+ clear: async () => await page.getByTestId("clearSearch").click(),
},
datasetPreview: {
load: async ({
@@ -73,15 +69,17 @@ export const createActions = ({
await selectors.chart.loaded();
},
switchToTableView: async () => {
- await (await selectors.chart.tablePreviewSwitch()).click();
+ await selectors.chart.tablePreviewSwitch().click();
},
},
/** Actions on MUI elements, options, selects, dialogs */
mui: {
selectOption: async (optionText: string) => {
- const item = await selectors.mui.popover().findByText(optionText);
+ const item = selectors.mui
+ .popover()
+ .getByText(optionText, { exact: true });
await item.click();
- const select = await item.locator("..").locator("text=Select");
+ const select = item.locator("..").locator("text=Select");
const count = await select.count();
if (count) {
await select.click();
@@ -112,19 +110,16 @@ export const createActions = ({
selectActiveField: selectActiveEditorField({
selectors,
page,
- screen,
- within,
}),
},
metadataPanel: {
toggle: async () => {
- const toggleButton = await screen.findByTestId("panel-metadata-toggle");
- await toggleButton.click();
+ await page.getByTestId("panel-metadata-toggle").click();
},
},
drawer: {
close: async () =>
- await screen.locator('button[aria-label="Back to main"]').click(),
+ await page.locator('button[aria-label="Back to main"]').click(),
},
common: {
switchLang: async (lang: "de" | "fr" | "en" | "it") => {
diff --git a/e2e/chart-actions.spec.ts b/e2e/chart-actions.spec.ts
index 81e9d19e4b..ee0fedcd6e 100644
--- a/e2e/chart-actions.spec.ts
+++ b/e2e/chart-actions.spec.ts
@@ -18,7 +18,7 @@ test("it should be possible to duplicate a chart", async ({
await selectors.chart.loaded();
const chartMoreButton = await selectors.chart.moreButton();
await chartMoreButton.click();
- await (await selectors.mui.popover().findByText("Duplicate")).click();
+ await selectors.mui.popover().getByText("Duplicate").click();
const chartTabs = await selectors.chart.tabs();
expect(await chartTabs.count()).toBe(2);
const layoutOptionsButton = page.locator(
@@ -28,7 +28,7 @@ test("it should be possible to duplicate a chart", async ({
await selectors.chart.loaded();
const chartMoreButtonLayout = await selectors.chart.moreButton();
await chartMoreButtonLayout.click();
- await (await selectors.mui.popover().findByText("Duplicate")).click();
+ await selectors.mui.popover().getByText("Duplicate").click();
const chartTabsLayout = await selectors.chart.tabs();
expect(await chartTabsLayout.count()).toBe(3);
});
@@ -47,7 +47,7 @@ test.skip("it should be possible to make a screenshot of a chart", async ({
const chartMoreButton = await selectors.chart.moreButton();
await chartMoreButton.click();
const downloadPromise = page.waitForEvent("download");
- await (await selectors.mui.popover().findByText("Export PNG")).click();
+ await selectors.mui.popover().getByText("Export PNG").click();
const download = await downloadPromise;
const filePath = await download.path();
diff --git a/e2e/chart-snapshots.spec.ts b/e2e/chart-snapshots.spec.ts
index f3e778eefa..75b6884054 100644
--- a/e2e/chart-snapshots.spec.ts
+++ b/e2e/chart-snapshots.spec.ts
@@ -1,6 +1,6 @@
import { configs as intConfigs } from "../app/test/__fixtures/config/int/configs";
-import { setup, sleep } from "./common";
+import { setup } from "./common";
import { harReplayGraphqlEndpointQueryParam } from "./har-utils";
const { test } = setup();
@@ -29,11 +29,9 @@ for (let [viewportName, viewportSize] of Object.entries(viewports)) {
await replayFromHAR();
await page.setViewportSize(viewportSize);
await page.goto(
- `/en/__test/${env}/${slug}?dataSource=Int&${harReplayGraphqlEndpointQueryParam}`
+ `/en/__test/${env}/${slug}?dataSource=Prod&${harReplayGraphqlEndpointQueryParam}`
);
await selectors.chart.loaded();
-
- await sleep(2_000);
});
}
}
diff --git a/e2e/color-mapping-maps.spec.ts b/e2e/color-mapping-maps.spec.ts
index 2f6499b756..6dc8b22274 100644
--- a/e2e/color-mapping-maps.spec.ts
+++ b/e2e/color-mapping-maps.spec.ts
@@ -7,7 +7,6 @@ const { test } = setup();
test("@noci should be possible to de-select options from color component in maps", async ({
page,
- within,
actions,
selectors,
replayFromHAR,
@@ -29,17 +28,11 @@ test("@noci should be possible to de-select options from color component in maps
await selectors.chart.loaded();
- const filterControlSection = within(
- page.locator("[data-testid=chart-edition-multi-filters]", {
- has: page.locator(`h5:text-is("Filter")`),
- })
- );
-
await page.getByRole("button", { name: "Edit filters" }).click();
- const filters = selectors.edition.filterDrawer().within();
- await (await filters.findByText("Canton of Zurich")).click();
- await (await filters.findByText("Apply filters")).click();
+ const filters = selectors.edition.filterDrawer();
+ await filters.getByText("Canton of Zurich").click();
+ await filters.getByText("Apply filters").click();
await selectors.chart.loaded();
});
diff --git a/e2e/color-palettes.spec.ts b/e2e/color-palettes.spec.ts
index 6e2a353405..fa7bbf6baa 100644
--- a/e2e/color-palettes.spec.ts
+++ b/e2e/color-palettes.spec.ts
@@ -14,9 +14,7 @@ describe("Color Picker Swatches", () => {
await selectors.chart.loaded();
await actions.editor.selectActiveField("Segmentation");
await selectors.edition.drawerLoaded();
- await (
- await selectors.panels.drawer().within().getByLabelText("None")
- ).click();
+ await selectors.panels.drawer().getByRole("combobox", { name: "None" }).click();
await actions.mui.selectOption("Kanton");
await page.evaluate(() => window.scrollTo(0, document.body.scrollHeight));
diff --git a/e2e/common.ts b/e2e/common.ts
index 5402b695d7..831e50e031 100644
--- a/e2e/common.ts
+++ b/e2e/common.ts
@@ -1,8 +1,4 @@
import { Page, PlaywrightTestOptions, test as base } from "@playwright/test";
-import {
- locatorFixtures as fixtures,
- LocatorFixtures as TestingLibraryFixtures,
-} from "@playwright-testing-library/test/fixture";
import { sleep } from "../app/utils/sleep";
@@ -13,7 +9,7 @@ import { slugify } from "./slugify";
type RouteFromHAROptions = Parameters[1];
const setup = (contextOptions?: PlaywrightTestOptions["contextOptions"]) => {
- const test = base.extend(fixtures).extend<{
+ const test = base.extend<{
selectors: Selectors;
actions: Actions;
replayFromHAR: (routeFromHAROptions?: RouteFromHAROptions) => Promise;
@@ -27,26 +23,34 @@ const setup = (contextOptions?: PlaywrightTestOptions["contextOptions"]) => {
};
await use(auth);
},
- selectors: async ({ page, screen, within }, use) => {
- const ctx = { page, screen, within };
- const selectors = createSelectors(ctx);
+ selectors: async ({ page }, use) => {
+ const selectors = createSelectors({ page });
await use(selectors);
},
- actions: async ({ page, screen, selectors, within }, use) => {
- const ctx = { page, screen, selectors, within };
- const actions = createActions(ctx);
+ actions: async ({ page, selectors }, use) => {
+ const actions = createActions({ page, selectors });
await use(actions);
},
replayFromHAR: async ({ page }, use, testInfo) => {
let index = 0;
+ const harPaths: string[] = [];
const replay = async (routeFromHAROptions?: RouteFromHAROptions) => {
const name = `${testInfo.titlePath
.map((x) => x.replace(/\.spec\.ts$/, ""))
.map((x) => x.replace(/@[^\s]+$/, ""))
.map(slugify)
.join(" > ")} ${index++}`;
- if (process.env.E2E_HAR && process.env.E2E_HAR !== "false") {
- await page.routeFromHAR(`./e2e/har/${name}.zip`, {
+ const harPath = `./e2e/har/${name}.zip`;
+ if (process.env.E2E_HAR === "update") {
+ harPaths.push(harPath);
+ await page.context().routeFromHAR(harPath, {
+ url: /api\/graphql/,
+ notFound: "fallback",
+ update: true,
+ ...routeFromHAROptions,
+ });
+ } else if (process.env.E2E_HAR && process.env.E2E_HAR !== "false") {
+ await page.routeFromHAR(harPath, {
url: /api\/graphql/,
notFound: "abort",
...routeFromHAROptions,
diff --git a/e2e/edition.spec.ts b/e2e/edition.spec.ts
index 2fdb564112..c3bd5dd798 100644
--- a/e2e/edition.spec.ts
+++ b/e2e/edition.spec.ts
@@ -7,7 +7,6 @@ const { expect, test } = setup();
// skipped due to probable issues with query for multiple cubes (see chart config)
test.skip("should be possible to edit filters of a hierarchy", async ({
page,
- screen,
selectors,
}) => {
const key = "WtHYbmsehQKo";
@@ -16,23 +15,19 @@ test.skip("should be possible to edit filters of a hierarchy", async ({
await page.goto(`/en/create/${key}`);
await selectors.chart.loaded();
- (
- await screen.findByText(
- "Edit filters",
- { selector: "button" },
- { timeout: 5_000 }
- )
- ).click();
+ await page
+ .getByRole("button", { name: "Edit filters" })
+ .click({ timeout: 5_000 });
- const filters = selectors.edition.filterDrawer().within();
+ const filters = selectors.edition.filterDrawer();
- await (await filters.findByText("Economic affairs")).click();
- await (await filters.findByText("Social protection")).click();
- await (await filters.findByText("Health")).click();
- await (await filters.findByText("Apply filters")).click();
+ await filters.getByText("Economic affairs").click();
+ await filters.getByText("Social protection").click();
+ await filters.getByText("Health").click();
+ await filters.getByText("Apply filters").click();
await selectors.chart.loaded();
- const middlePanel = await selectors.panels.middle();
+ const middlePanel = selectors.panels.middle();
await middlePanel.evaluate((panel) => {
panel.scrollTo(0, 200);
});
@@ -46,7 +41,7 @@ test("changing of locale shouldn't make the chart disappear", async ({
selectors,
}) => {
await actions.chart.createFrom({
- iri: "https://agriculture.ld.admin.ch/foag/cube/MilkDairyProducts/Consumption_Price_Month",
+ iri: "https://environment.ld.admin.ch/foen/ubd000502/8",
dataSource: "Prod",
});
await selectors.chart.loaded();
diff --git a/e2e/filter-position.spec.ts b/e2e/filter-position.spec.ts
index bc7fe549c0..ca8018f6bd 100644
--- a/e2e/filter-position.spec.ts
+++ b/e2e/filter-position.spec.ts
@@ -12,26 +12,19 @@ test("Filters should be sorted by position", async ({ selectors, actions }) => {
await actions.editor.selectActiveField("Segmentation");
- const selectorLocator = await selectors.panels
- .drawer()
- .within()
- .getByLabelText("None");
+ const selectorLocator = selectors.panels.drawer().getByRole("combobox", { name: "None" });
await selectorLocator.click();
await actions.mui.selectOption("Status IUCN");
- const panelLeft = await selectors.panels.drawer().within();
- await panelLeft.findByText("Selected filters", undefined, {
- timeout: 10_000,
- });
+ const panelLeft = selectors.panels.drawer();
+ await panelLeft
+ .getByText("Selected filters")
+ .first()
+ .waitFor({ timeout: 10_000 });
- const filtersValueLocator = await panelLeft.findAllByTestId(
- "chart-filters-value",
- undefined,
- {
- timeout: 3000,
- }
- );
+ const filtersValueLocator = panelLeft.getByTestId("chart-filters-value");
+ await filtersValueLocator.first().waitFor({ timeout: 3000 });
const rawTexts = await filtersValueLocator.allTextContents();
const texts = rawTexts.map((x) =>
diff --git a/e2e/filters.spec.ts b/e2e/filters.spec.ts
index 154079c6ad..81a4c1d3e2 100644
--- a/e2e/filters.spec.ts
+++ b/e2e/filters.spec.ts
@@ -94,9 +94,7 @@ describe("Filters", () => {
await selectors.edition.drawerLoaded();
- await (
- await selectors.panels.drawer().within().getByLabelText("None")
- ).click();
+ await selectors.panels.drawer().getByRole("combobox", { name: "None" }).click();
await actions.mui.selectOption("Kanton");
@@ -105,9 +103,7 @@ describe("Filters", () => {
await legend.waitFor({ state: "hidden", timeout: 5000 });
await expect(legend).toHaveCount(0);
- await (
- await selectors.panels.drawer().within().findByText("Show legend titles")
- ).click();
+ await selectors.panels.drawer().getByText("Show legend titles").click();
expect(legend).toHaveCount(1);
diff --git a/e2e/har-utils.ts b/e2e/har-utils.ts
index 929794787b..5a019c908a 100644
--- a/e2e/har-utils.ts
+++ b/e2e/har-utils.ts
@@ -49,8 +49,8 @@ export const testAndSaveHar = async (
const { baseUrl } = getEnv(env);
const { test } = setup({ recordHar: { path } });
test.slow();
- test(name, async ({ browser, page, screen, actions, selectors, within }) => {
- await run({ browser, page, screen, selectors, actions, within, baseUrl });
+ test(name, async ({ browser, page, actions, selectors }) => {
+ await run({ browser, page, selectors, actions, baseUrl });
cleanupHAR(path);
});
};
diff --git a/e2e/har/chart-snapshots > chart-snapshots-bathing-water-quality-hierarchie-int-ipad-mini-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-bathing-water-quality-hierarchie-int-ipad-mini-portrait 0.zip
index ae2f2d05ba..d812a711f3 100644
Binary files a/e2e/har/chart-snapshots > chart-snapshots-bathing-water-quality-hierarchie-int-ipad-mini-portrait 0.zip and b/e2e/har/chart-snapshots > chart-snapshots-bathing-water-quality-hierarchie-int-ipad-mini-portrait 0.zip differ
diff --git a/e2e/har/chart-snapshots > chart-snapshots-bathing-water-quality-hierarchie-int-iphone-8-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-bathing-water-quality-hierarchie-int-iphone-8-portrait 0.zip
index 008a67d5c4..bee6f9aeac 100644
Binary files a/e2e/har/chart-snapshots > chart-snapshots-bathing-water-quality-hierarchie-int-iphone-8-portrait 0.zip and b/e2e/har/chart-snapshots > chart-snapshots-bathing-water-quality-hierarchie-int-iphone-8-portrait 0.zip differ
diff --git a/e2e/har/chart-snapshots > chart-snapshots-column-heavy-metals-int-ipad-mini-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-column-heavy-metals-int-ipad-mini-portrait 0.zip
index b2d75079f7..8ea2ff4b45 100644
Binary files a/e2e/har/chart-snapshots > chart-snapshots-column-heavy-metals-int-ipad-mini-portrait 0.zip and b/e2e/har/chart-snapshots > chart-snapshots-column-heavy-metals-int-ipad-mini-portrait 0.zip differ
diff --git a/e2e/har/chart-snapshots > chart-snapshots-column-heavy-metals-int-iphone-8-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-column-heavy-metals-int-iphone-8-portrait 0.zip
index 6fcd38b3bd..095a13422b 100644
Binary files a/e2e/har/chart-snapshots > chart-snapshots-column-heavy-metals-int-iphone-8-portrait 0.zip and b/e2e/har/chart-snapshots > chart-snapshots-column-heavy-metals-int-iphone-8-portrait 0.zip differ
diff --git a/e2e/har/chart-snapshots > chart-snapshots-pie-red-list-int-ipad-mini-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-pie-red-list-int-ipad-mini-portrait 0.zip
index 6ffd615c5d..6b806acf27 100644
Binary files a/e2e/har/chart-snapshots > chart-snapshots-pie-red-list-int-ipad-mini-portrait 0.zip and b/e2e/har/chart-snapshots > chart-snapshots-pie-red-list-int-ipad-mini-portrait 0.zip differ
diff --git a/e2e/har/chart-snapshots > chart-snapshots-pie-red-list-int-iphone-8-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-pie-red-list-int-iphone-8-portrait 0.zip
index 89ab26f3cd..ae349d6ef1 100644
Binary files a/e2e/har/chart-snapshots > chart-snapshots-pie-red-list-int-iphone-8-portrait 0.zip and b/e2e/har/chart-snapshots > chart-snapshots-pie-red-list-int-iphone-8-portrait 0.zip differ
diff --git a/e2e/har/chart-snapshots > chart-snapshots-scatterplot-greenhouse-gases-int-ipad-mini-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-scatterplot-greenhouse-gases-int-ipad-mini-portrait 0.zip
new file mode 100644
index 0000000000..1ae5549bf2
Binary files /dev/null and b/e2e/har/chart-snapshots > chart-snapshots-scatterplot-greenhouse-gases-int-ipad-mini-portrait 0.zip differ
diff --git a/e2e/har/chart-snapshots > chart-snapshots-scatterplot-greenhouse-gases-int-iphone-8-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-scatterplot-greenhouse-gases-int-iphone-8-portrait 0.zip
new file mode 100644
index 0000000000..d849063a31
Binary files /dev/null and b/e2e/har/chart-snapshots > chart-snapshots-scatterplot-greenhouse-gases-int-iphone-8-portrait 0.zip differ
diff --git a/e2e/har/chart-snapshots > chart-snapshots-scatterplot-palmer-penguins-int-ipad-mini-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-scatterplot-palmer-penguins-int-ipad-mini-portrait 0.zip
deleted file mode 100644
index e01c21ad8f..0000000000
Binary files a/e2e/har/chart-snapshots > chart-snapshots-scatterplot-palmer-penguins-int-ipad-mini-portrait 0.zip and /dev/null differ
diff --git a/e2e/har/chart-snapshots > chart-snapshots-scatterplot-palmer-penguins-int-iphone-8-portrait 0.zip b/e2e/har/chart-snapshots > chart-snapshots-scatterplot-palmer-penguins-int-iphone-8-portrait 0.zip
deleted file mode 100644
index b529e4f068..0000000000
Binary files a/e2e/har/chart-snapshots > chart-snapshots-scatterplot-palmer-penguins-int-iphone-8-portrait 0.zip and /dev/null differ
diff --git a/e2e/home.spec.ts b/e2e/home.spec.ts
index 6234b683be..3d7c537cfa 100644
--- a/e2e/home.spec.ts
+++ b/e2e/home.spec.ts
@@ -5,39 +5,41 @@ import { setup } from "./common";
const { test, describe, expect } = setup();
describe("The Home Page", () => {
- test("default language (de) should render on /", async ({ page, screen }) => {
+ test("default language (de) should render on /", async ({ page }) => {
await page.setExtraHTTPHeaders({
"Accept-Language": "de",
});
await page.goto("/");
- await screen.findByText("Visualisieren Sie Schweizer Open Government Data");
+ await page
+ .getByText("Visualisieren Sie Schweizer Open Government Data")
+ .first()
+ .waitFor();
expect(await page.locator("html").getAttribute("lang")).toEqual("de");
});
test("Accept-Language header for alternative language (fr) should display French", async ({
page,
- screen,
}) => {
await page.setExtraHTTPHeaders({
"Accept-Language": "fr",
});
await page.goto("/fr");
- await screen.findByText(
- "Visualisez les données ouvertes de l’administration publique suisse"
- );
+ await page
+ .getByText("Visualisez les données ouvertes de l’administration publique suisse")
+ .first()
+ .waitFor();
expect(await page.locator("html").getAttribute("lang")).toEqual("fr");
});
- test("language switch should work", async ({ page, screen, actions }) => {
+ test("language switch should work", async ({ page, actions }) => {
await page.goto("/");
await actions.common.switchLang("fr");
- await screen.findByText(
- "Visualisez les données ouvertes de l’administration publique suisse",
- undefined,
- { timeout: 20 * 1000 }
- );
+ await page
+ .getByText("Visualisez les données ouvertes de l’administration publique suisse")
+ .first()
+ .waitFor({ timeout: 20 * 1000 });
expect(new URL(page.url()).pathname).toEqual("/fr");
expect(await page.locator("html").getAttribute("lang")).toBe("fr");
@@ -45,17 +47,14 @@ describe("The Home Page", () => {
});
describe("content pages", () => {
- test("language switch should work", async ({ page, actions, screen }) => {
+ test("language switch should work", async ({ page, actions }) => {
await page.goto("/en/legal-framework");
await actions.common.switchLang("fr");
- await screen.findByText(
- "Utilisation des jeux de données publiés sur visualize.admin.ch",
- undefined,
- {
- timeout: 20 * 1000,
- }
- );
+ await page
+ .getByText("Utilisation des jeux de données publiés sur visualize.admin.ch")
+ .first()
+ .waitFor({ timeout: 20 * 1000 });
expect(await page.locator("html").getAttribute("lang")).toBe("fr");
});
});
diff --git a/e2e/interactive-filters.spec.ts b/e2e/interactive-filters.spec.ts
index 8a6301b2df..97c4b5f236 100644
--- a/e2e/interactive-filters.spec.ts
+++ b/e2e/interactive-filters.spec.ts
@@ -5,14 +5,10 @@ const { expect, test } = setup();
test.skip("it should display values in interactive filters as hierarchie", async ({
page,
selectors,
- within,
}) => {
await page.goto("/en/__test/int/bathing-water-quality-hierarchie");
await selectors.chart.loaded();
await page.locator('text="Show Filters"').click();
- const interactiveFilters = await within(
- selectors.published.interactiveFilters()
- );
await page.locator("[value=Seerose]").click();
await selectors.mui.popover().getByText("BAQUA_FR").click();
await selectors.mui.popover().getByText("Nouvelle plage").click();
diff --git a/e2e/metadata-panel.spec.ts b/e2e/metadata-panel.spec.ts
index e6104c1dc1..f8a202106b 100644
--- a/e2e/metadata-panel.spec.ts
+++ b/e2e/metadata-panel.spec.ts
@@ -12,15 +12,15 @@ test("it should be possible to open a metadata panel by clicking on elements in
});
const checkKantonDescription = async () => {
- const kantonDimensionDescription = await selectors.panels
- .metadata()
- .within()
- .findByText("Kanton, in welchem die geförderten Anlagen stehen");
-
- expect(kantonDimensionDescription).toBeDefined();
+ await expect(
+ selectors.panels
+ .metadata()
+ .getByText("Kanton, in welchem die geförderten Anlagen stehen")
+ .first()
+ ).toBeVisible();
};
- const chartFilters = await selectors.edition.chartFilters();
+ const chartFilters = selectors.edition.chartFilters();
await chartFilters.locator("button >> text='Kanton'").click();
diff --git a/e2e/ordinal-measures.spec.ts b/e2e/ordinal-measures.spec.ts
index f1fdecc7a1..be0224cbc0 100644
--- a/e2e/ordinal-measures.spec.ts
+++ b/e2e/ordinal-measures.spec.ts
@@ -46,10 +46,8 @@ describe("viewing a dataset with only ordinal measures", () => {
test("should be possible to select ordinal measure as area color", async ({
page,
- screen,
selectors,
actions,
- within,
replayFromHAR,
}) => {
test.slow();
@@ -69,8 +67,9 @@ describe("viewing a dataset with only ordinal measures", () => {
await selectors.chart.loaded();
- await within(selectors.edition.controlSectionByTitle("Symbols"))
- .getByLabelText("None")
+ await selectors.edition
+ .controlSectionByTitle("Symbols")
+ .getByRole("combobox", { name: "None" })
.click();
// Select options open in portal
@@ -82,8 +81,9 @@ describe("viewing a dataset with only ordinal measures", () => {
// Chart needs to re-load when symbol layer is selected
await selectors.chart.loaded();
- await within(selectors.edition.controlSectionByTitle("Color"))
- .getByLabelText("None")
+ await selectors.edition
+ .controlSectionByTitle("Color")
+ .getByRole("combobox", { name: "None" })
.click();
const options = await selectors.mui.options();
diff --git a/e2e/preview-via-api.spec.ts b/e2e/preview-via-api.spec.ts
index e91a070945..f771e2ce91 100644
--- a/e2e/preview-via-api.spec.ts
+++ b/e2e/preview-via-api.spec.ts
@@ -1,7 +1,6 @@
import { Page } from "@playwright/test";
import { setup } from "./common";
-import { Selectors } from "./selectors";
const { test } = setup();
@@ -12,17 +11,17 @@ type IframeDef = {
const waitForIframe = async ({
page,
- selectors,
elLocator,
chartLocator,
}: {
page: Page;
- selectors: Selectors;
} & IframeDef) => {
await page.waitForSelector(elLocator);
const iframe = page.locator(elLocator);
const contentFrame = iframe.contentFrame();
- await selectors.chart.loaded();
+ await contentFrame
+ .locator('[data-chart-loaded="true"]')
+ .waitFor({ timeout: 30_000 });
await contentFrame.locator(chartLocator).first().waitFor({ timeout: 10_000 });
};
@@ -39,10 +38,7 @@ const iframeDefs: IframeDef[] = [
test("should be possible to preview charts via API (iframe)", async ({
page,
- selectors,
}) => {
await page.goto("/en/_preview");
- await Promise.all(
- iframeDefs.map((def) => waitForIframe({ page, selectors, ...def }))
- );
+ await Promise.all(iframeDefs.map((def) => waitForIframe({ page, ...def })));
});
diff --git a/e2e/search.spec.ts b/e2e/search.spec.ts
index e540a8722b..5f6c293e09 100644
--- a/e2e/search.spec.ts
+++ b/e2e/search.spec.ts
@@ -1,5 +1,4 @@
import { Locator, Page } from "@playwright/test";
-import { within } from "@playwright-testing-library/test";
import { setup } from "./common";
import { harReplayGraphqlEndpointQueryParam } from "./har-utils";
@@ -61,13 +60,11 @@ test("search results count coherence", async ({
await selectors.search.resultsCount();
- const panelLeft = await selectors.panels.left();
+ const panelLeft = selectors.panels.left();
- await (
- await within(panelLeft).locator(`button:has-text("Show all")`).first()
- ).click();
+ await panelLeft.locator(`button:has-text("Show all")`).first().click();
- await within(panelLeft).findByText(t, undefined, { timeout: 10_000 });
+ await panelLeft.getByText(t).first().waitFor({ timeout: 10_000 });
const countChip = panelLeft
.locator(`:text("${t}")`)
@@ -82,13 +79,7 @@ test("search results count coherence", async ({
}
});
-test("sort order", async ({
- page,
- selectors,
- screen,
- actions,
- replayFromHAR,
-}) => {
+test("sort order", async ({ page, selectors, actions, replayFromHAR }) => {
test.slow();
await replayFromHAR();
@@ -97,12 +88,12 @@ test("sort order", async ({
);
const resultCount = await selectors.search.resultsCount();
const text = await resultCount.textContent();
- const select = screen.locator("input[name='datasetSort']");
+ const select = page.locator("input[name='datasetSort']");
expect(await getSelectValue(select)).toBe("CREATED_DESC");
- const searchInput = screen.getAllByPlaceholderText(
- "Name, organization, keyword..."
- );
+ const searchInput = page
+ .getByPlaceholder("Name, organization, keyword...")
+ .first();
// Search something, order should be score
await searchInput.type("NFI");
diff --git a/e2e/selectors.ts b/e2e/selectors.ts
index b1559ea82c..76a1851814 100644
--- a/e2e/selectors.ts
+++ b/e2e/selectors.ts
@@ -1,28 +1,27 @@
-import { MatcherOptions, waitForOptions } from "@testing-library/dom";
-
import { sleep } from "./common";
import { TestContext as Ctx } from "./types";
/**
* Creates a fixture for Playwright
*/
-export const createSelectors = ({ screen, page, within }: Ctx) => {
+export const createSelectors = ({ page }: Ctx) => {
const selectors = {
mui: {
select: () => page.locator(".MuiSelect-select"),
- popover: () => within(page.locator(".MuiPopover-paper")),
+ popover: () => page.locator(".MuiPopover-paper"),
options: () => page.locator('li[role="option"]'),
},
search: {
- searchInput: () => screen.getByTestId("datasetSearch"),
+ searchInput: () => page.getByTestId("datasetSearch"),
draftsCheckbox: () => page.locator("#dataset-include-drafts"),
- datasetSort: () => screen.getByTestId("datasetSort"),
- navItem: () => screen.findByTestId("navItem"),
- navChip: () => screen.findByTestId("navChip"),
- resultsCount: () =>
- screen.findByTestId("search-results-count", undefined, {
- timeout: 10_000,
- }),
+ datasetSort: () => page.getByTestId("datasetSort"),
+ navItem: () => page.getByTestId("navItem"),
+ navChip: () => page.getByTestId("navChip"),
+ resultsCount: async () => {
+ const loc = page.getByTestId("search-results-count");
+ await loc.waitFor({ timeout: 10_000 });
+ return loc;
+ },
},
datasetPreview: {
loaded: () =>
@@ -46,91 +45,92 @@ export const createSelectors = ({ screen, page, within }: Ctx) => {
},
},
panels: {
- left: () => screen.getByTestId("panel-body-L"),
- drawer: () => screen.getByTestId("panel-drawer"),
- middle: () => screen.getByTestId("panel-body-M"),
- metadata: () => screen.getByTestId("panel-metadata"),
+ left: () => page.getByTestId("panel-body-L"),
+ drawer: () => page.getByTestId("panel-drawer"),
+ middle: () => page.getByTestId("panel-body-M"),
+ metadata: () => page.getByTestId("panel-metadata"),
},
edition: {
- configFilters: () =>
- screen.findByTestId("configurator-filters", undefined, {
- timeout: 20 * 1000,
- }),
- drawerLoaded: () =>
- screen.findByText(
- "Chart Type",
- { selector: "h6" },
- { timeout: 10_000 }
- ),
- chartFilters: () => screen.findByTestId("chart-filters-list"),
- filterDrawer: () => screen.findByTestId("edition-filters-drawer"),
+ configFilters: async () => {
+ const loc = page.getByTestId("configurator-filters");
+ await loc.waitFor({ timeout: 20 * 1000 });
+ return loc;
+ },
+ drawerLoaded: async () => {
+ await page
+ .locator("h6", { hasText: "Chart Type" })
+ .first()
+ .waitFor({ timeout: 10_000 });
+ },
+ chartFilters: () => page.getByTestId("chart-filters-list"),
+ filterDrawer: () => page.getByTestId("edition-filters-drawer"),
filterCheckbox: (value: string) =>
page.locator(`[data-value="${value}"]`),
- chartTypeSelectorRegular: () =>
- screen.findByTestId("chart-type-selector-regular", undefined, {
- timeout: 10_000,
- }),
- chartTypeSelectorCombo: () =>
- screen.findByTestId("chart-type-selector-combo", undefined, {
- timeout: 10_000,
- }),
- filtersLoaded: () =>
- screen.findByText("Selected filters", undefined, { timeout: 10_000 }),
+ chartTypeSelectorRegular: async () => {
+ const loc = page.getByTestId("chart-type-selector-regular");
+ await loc.waitFor({ timeout: 10_000 });
+ return loc;
+ },
+ chartTypeSelectorCombo: async () => {
+ const loc = page.getByTestId("chart-type-selector-combo");
+ await loc.waitFor({ timeout: 10_000 });
+ return loc;
+ },
+ filtersLoaded: async () => {
+ await page
+ .getByText("Selected filters")
+ .first()
+ .waitFor({ timeout: 10_000 });
+ },
controlSectionByTitle: (title: string) =>
page.locator("[data-testid=controlSection]", {
has: page.locator(`h6:text-is("${title}")`),
}),
dataFilterInput: (label: string) =>
page.locator(`div[role="button"]:has-text("${label}")`),
- useAbbreviationsCheckbox: () =>
- screen
+ useAbbreviationsCheckbox: async () => {
+ const loc = page
.getByTestId("panel-drawer")
- .within()
- .findByText("Use abbreviations", {}, { timeout: 10_000 }),
+ .getByText("Use abbreviations");
+ await loc.waitFor({ timeout: 10_000 });
+ return loc;
+ },
},
published: {
interactiveFilters: () =>
- screen.getByTestId("published-chart-interactive-filters"),
+ page.getByTestId("published-chart-interactive-filters"),
},
chart: {
- axisWidthBand: async () => screen.findByTestId("axis-width-band"),
- colorLegend: async (
- options?: MatcherOptions,
- waitForOptions?: waitForOptions
- ) => {
+ axisWidthBand: () => page.getByTestId("axis-width-band"),
+ colorLegend: async (waitForOptions?: { timeout?: number }) => {
// There can be multiple color legends for hierarchical dimensions.
// Generally, we want the first one.
- const colorLegend = await screen.findAllByTestId(
- "colorLegend",
- options,
- waitForOptions
- );
-
- return colorLegend.first();
+ const colorLegend = page.getByTestId("colorLegend").first();
+ if (waitForOptions) {
+ await colorLegend.waitFor(waitForOptions);
+ }
+ return colorLegend;
},
colorLegendItems: async () =>
(await selectors.chart.colorLegend()).locator("div"),
- moreButton: () =>
- screen.findByTestId("chart-more-button", undefined, {
- timeout: 10_000,
- }),
+ moreButton: async () => {
+ const loc = page.getByTestId("chart-more-button");
+ await loc.waitFor({ timeout: 10_000 });
+ return loc;
+ },
legendTicks: async () => {},
loaded: async () => {
- await page.waitForLoadState("networkidle");
+ await page.waitForSelector('[data-chart-loaded="true"]', {
+ timeout: 30_000,
+ });
// Let the map tiles fade in and enter animations finish
await sleep(1_000);
},
screenshot: {
- png: async () => {
- return await screen.findByTestId("screenshot-png");
- },
- },
- tablePreviewSwitch: async () => {
- return await screen.findByText("Table view");
- },
- tabs: async () => {
- return await screen.findAllByTestId("chart-selection-tab");
+ png: () => page.getByTestId("screenshot-png"),
},
+ tablePreviewSwitch: () => page.getByText("Table view"),
+ tabs: () => page.getByTestId("chart-selection-tab"),
},
};
return selectors;
diff --git a/e2e/sorting.spec.ts b/e2e/sorting.spec.ts
index 6431a1a221..aedc82182a 100644
--- a/e2e/sorting.spec.ts
+++ b/e2e/sorting.spec.ts
@@ -10,13 +10,7 @@ const { test, expect } = setup();
* - For each type of chart, changes the sorting between Name and Automatic
* - Checks that the legend item order is coherent.
*/
-test("Segment sorting", async ({
- selectors,
- actions,
- within,
- screen,
- replayFromHAR,
-}) => {
+test("Segment sorting", async ({ selectors, actions, page, replayFromHAR }) => {
test.setTimeout(60_000);
await replayFromHAR();
@@ -34,8 +28,9 @@ test("Segment sorting", async ({
// Switch color on the first chart
if (chartType === "Columns") {
- await within(selectors.edition.controlSectionByTitle("Segmentation"))
- .getByLabelText("None")
+ await selectors.edition
+ .controlSectionByTitle("Segmentation")
+ .getByRole("combobox", { name: "None" })
.click();
await actions.mui.selectOption("Kanton");
@@ -43,14 +38,15 @@ test("Segment sorting", async ({
await selectors.chart.loaded();
await selectors.edition.filtersLoaded();
- await selectors.chart.colorLegend(undefined, { timeout: 5_000 });
+ await selectors.chart.colorLegend({ timeout: 5_000 });
const legendItems = await selectors.chart.colorLegendItems();
const legendTexts = await legendItems.allInnerTexts();
expect(legendTexts[0]).toEqual("Zurich");
- await within(selectors.edition.controlSectionByTitle("Sort"))
- .getByLabelText("Automatic")
+ await selectors.edition
+ .controlSectionByTitle("Sort")
+ .getByRole("combobox", { name: "Automatic" })
.click();
await actions.mui.selectOption("Name");
@@ -60,16 +56,17 @@ test("Segment sorting", async ({
const legendTexts2 = await legendItems.allInnerTexts();
expect(legendTexts2[0]).toBe("Aargau");
- await screen.getByText("Z → A").click();
+ await page.getByText("Z → A").click();
const legendTexts3 = await legendItems.allInnerTexts();
expect(legendTexts3[0]).toEqual("Zurich");
// Re-initialize for future tests
- await screen.getByText("A → Z").click();
+ await page.getByText("A → Z").click();
- await within(selectors.edition.controlSectionByTitle("Sort"))
- .getByLabelText("Name")
+ await selectors.edition
+ .controlSectionByTitle("Sort")
+ .getByRole("combobox", { name: "Name" })
.click();
await actions.mui.selectOption("Automatic");
@@ -82,8 +79,7 @@ test("Segment sorting", async ({
test("Segment sorting with hierarchy", async ({
actions,
selectors,
- screen,
- within,
+ page,
replayFromHAR,
}) => {
await replayFromHAR();
@@ -100,19 +96,18 @@ test("Segment sorting with hierarchy", async ({
await sleep(3_000);
const colorSection = selectors.edition.controlSectionByTitle("Segmentation");
- await within(colorSection).getByLabelText("None").click();
+ await colorSection.getByRole("combobox", { name: "None" }).click();
await actions.mui.selectOption("Region");
await selectors.chart.loaded();
await selectors.edition.filtersLoaded();
- await selectors.chart.colorLegend(undefined, { timeout: 30_000 });
+ await selectors.chart.colorLegend({ timeout: 30_000 });
- await within(await selectors.chart.colorLegend()).findByText(
- "Appenzell Innerrhoden",
- undefined,
- { timeout: 10_000 }
- );
+ await (await selectors.chart.colorLegend())
+ .getByText("Appenzell Innerrhoden")
+ .first()
+ .waitFor({ timeout: 10_000 });
const legendItems = await selectors.chart.colorLegendItems();
@@ -171,7 +166,7 @@ test("Segment sorting with hierarchy", async ({
expect(await legendItems.allInnerTexts()).toEqual(expectedLegendItems);
- await screen.getByText("Z → A").click();
+ await page.getByText("Z → A").click();
expect(await legendItems.allInnerTexts()).toEqual(
[...expectedLegendItems].reverse()
);
diff --git a/e2e/symbol-layer-colors.spec.ts b/e2e/symbol-layer-colors.spec.ts
index 58208cd53c..a127828c48 100644
--- a/e2e/symbol-layer-colors.spec.ts
+++ b/e2e/symbol-layer-colors.spec.ts
@@ -9,7 +9,6 @@ test.skip("Selecting SymbolLayer colors > should be possible to select geo dimen
page,
selectors,
actions,
- within,
}) => {
const key = "jky5IEw6poT3";
await loadChartInLocalStorage(page, key, configuratorState);
@@ -18,8 +17,9 @@ test.skip("Selecting SymbolLayer colors > should be possible to select geo dimen
await selectors.chart.loaded();
- await within(selectors.edition.controlSectionByTitle("Color"))
- .getByLabelText("None")
+ await selectors.edition
+ .controlSectionByTitle("Color")
+ .getByRole("combobox", { name: "None" })
.click();
await actions.mui.selectOption("Region");
diff --git a/e2e/table-links.spec.ts b/e2e/table-links.spec.ts
index b3d06ab393..3aa57fc4f3 100644
--- a/e2e/table-links.spec.ts
+++ b/e2e/table-links.spec.ts
@@ -7,7 +7,6 @@ test("it updates per-locale table link base URLs and renders the correct href pe
actions,
selectors,
page,
- within,
replayFromHAR,
}) => {
await replayFromHAR();
@@ -30,11 +29,7 @@ test("it updates per-locale table link base URLs and renders the correct href pe
await linksSection.locator("h6:text-is('Links')").click();
// Enable links
- await (
- await within(linksSection).findByText("Enable links", undefined, {
- timeout: 5_000,
- })
- ).click();
+ await linksSection.getByText("Enable links").click({ timeout: 5_000 });
// Fill the per-locale base URL inputs
for (const loc of ["de", "fr", "it", "en"] as const) {
diff --git a/e2e/tooltip.spec.ts b/e2e/tooltip.spec.ts
index 0f989190e3..aa7d6a99f3 100644
--- a/e2e/tooltip.spec.ts
+++ b/e2e/tooltip.spec.ts
@@ -6,7 +6,6 @@ const { test, expect } = setup();
test("should have correct tooltip content", async ({
actions,
selectors,
- within,
page,
replayFromHAR,
}) => {
@@ -20,15 +19,17 @@ test("should have correct tooltip content", async ({
await selectors.edition.drawerLoaded();
- const filterLocator = await within(
- selectors.edition.controlSectionByTitle("Filters")
- );
+ const filterLocator = selectors.edition.controlSectionByTitle("Filters");
- await filterLocator.getByLabelText("All greenhouse gas").click();
+ await filterLocator
+ .getByRole("combobox", { name: "All greenhouse gas" })
+ .click();
await selectors.mui
.popover()
- .findByText("Methane", undefined, { timeout: 10_000 });
+ .getByText("Methane")
+ .first()
+ .waitFor({ timeout: 10_000 });
await actions.mui.selectOption("Methane");
@@ -57,7 +58,7 @@ test("should keep correct position after scrolling", async ({
actions,
}) => {
await actions.chart.createFrom({
- iri: "https://agriculture.ld.admin.ch/foag/cube/MilkDairyProducts/Consumption_Price_Month",
+ iri: "https://environment.ld.admin.ch/foen/ubd000502/8",
dataSource: "Prod",
});
await actions.editor.changeRegularChartType("Bars");
@@ -66,8 +67,8 @@ test("should keep correct position after scrolling", async ({
const rect0 = chart.locator('[data-index="0"]');
await rect0.hover({ force: true });
await sleep(3_000);
- const rect50 = chart.locator('[data-index="50"]');
- await rect50.hover({ force: true });
+ const rect30 = chart.locator('[data-index="30"]');
+ await rect30.hover({ force: true });
await sleep(3_000);
const tooltip = page.locator('[data-testid="chart-tooltip"]');
await tooltip.waitFor({ state: "attached", timeout: 1_000 });
diff --git a/e2e/types.ts b/e2e/types.ts
index 913981e3d1..51f12133a4 100644
--- a/e2e/types.ts
+++ b/e2e/types.ts
@@ -1,10 +1,5 @@
-import { LocatorFixtures } from "@playwright-testing-library/test/fixture";
import { Page } from "@playwright/test";
-type Screen = LocatorFixtures["screen"];
-
export type TestContext = {
- screen: Screen;
page: Page;
- within: LocatorFixtures["within"];
};
diff --git a/e2e/unversioned.spec.ts b/e2e/unversioned.spec.ts
index 5dfb10b5e9..79114031fa 100644
--- a/e2e/unversioned.spec.ts
+++ b/e2e/unversioned.spec.ts
@@ -3,14 +3,15 @@ import { setup } from "./common";
const { test } = setup();
test("Unversioned dataset > should be possible to open a link to an unversioned dataset", async ({
- screen,
+ page,
actions,
}) => {
await actions.datasetPreview.load({
iri: "https://culture.ld.admin.ch/sfa/StateAccounts_Function",
dataSource: "Int",
});
- await screen.findAllByText("State accounts - Function", undefined, {
- timeout: 10 * 1000,
- });
+ await page
+ .getByText("State accounts - Function")
+ .first()
+ .waitFor({ timeout: 10 * 1000 });
});
diff --git a/knip.config.ts b/knip.config.ts
index 77c4283b6d..736b814755 100644
--- a/knip.config.ts
+++ b/knip.config.ts
@@ -45,8 +45,6 @@ const config: KnipConfig = {
"pngjs",
"@types/pngjs",
"@playwright/test",
- "playwright-testing-library",
- "@playwright-testing-library/test",
// Codegen packages are used through scripts.
"@graphql-codegen/*",
"@lingui/cli",
diff --git a/package.json b/package.json
index a8eef79b8d..78f85d7a90 100644
--- a/package.json
+++ b/package.json
@@ -36,6 +36,7 @@
"setup:dev": "yarn && yarn locales:compile && yarn db:migrate:dev",
"postversion": "git push --follow-tags",
"release:npm": "yarn build:npm && yarn publish app",
+ "e2e:har-update": "E2E_HAR=update E2E_BASE_URL=http://localhost:3000 yarn playwright test",
"e2e:dev": "E2E_BASE_URL=http://localhost:3000 yarn playwright test",
"e2e:dev:ssl": "E2E_BASE_URL=https://localhost:3000 yarn playwright test",
"e2e:ui": "E2E_BASE_URL=http://localhost:3000 yarn playwright test --ui",
diff --git a/readme/testing-functional.md b/readme/testing-functional.md
index 5cee857d3f..e7e0504fa8 100644
--- a/readme/testing-functional.md
+++ b/readme/testing-functional.md
@@ -42,6 +42,15 @@ To launch the Playwright UI and run tests interactively:
yarn e2e:ui
```
+Some e2e use har files to mock the backend. To update the har files, you can use
+the following command:
+
+```sh
+yarn e2e:har-update
+```
+
+Commit the updated zip file(s) to the repository.
+
## Visual regression tests
It's sometimes useful to run visual regression tests, especially when modifying
diff --git a/yarn.lock b/yarn.lock
index a705f25bda..2b0881ab4b 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -1200,15 +1200,7 @@
resolved "https://registry.yarnpkg.com/@babel/regjsgen/-/regjsgen-0.8.0.tgz#f0ba69b075e1f05fb2825b7fad991e7adbb18310"
integrity sha512-x/rqGMdzj+fWZvCOYForTghzbtqPDZ5gPwaoNGHdgDfF2QA/XZbCBp4Moo5scrkAMPhB7z26XM/AaHuIJdgauA==
-"@babel/runtime-corejs3@^7.10.2":
- version "7.14.6"
- resolved "https://registry.npmjs.org/@babel/runtime-corejs3/-/runtime-corejs3-7.14.6.tgz"
- integrity sha512-Xl8SPYtdjcMoCsIM4teyVRg7jIcgl8F2kRtoCcXuHzXswt9UxZCS6BzRo8fcnCuP6u2XtPgvyonmEPF57Kxo9Q==
- dependencies:
- core-js-pure "^3.14.0"
- regenerator-runtime "^0.13.4"
-
-"@babel/runtime@^7.0.0", "@babel/runtime@^7.1.2", "@babel/runtime@^7.10.2", "@babel/runtime@^7.11.2", "@babel/runtime@^7.12.1", "@babel/runtime@^7.12.5", "@babel/runtime@^7.13.10", "@babel/runtime@^7.14.8", "@babel/runtime@^7.17.2", "@babel/runtime@^7.17.8", "@babel/runtime@^7.20.13", "@babel/runtime@^7.21.0", "@babel/runtime@^7.23.9", "@babel/runtime@^7.24.4", "@babel/runtime@^7.29.2", "@babel/runtime@^7.3.1", "@babel/runtime@^7.5.5", "@babel/runtime@^7.7.2", "@babel/runtime@^7.7.7", "@babel/runtime@^7.8.3", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7", "@babel/runtime@^7.9.2":
+"@babel/runtime@^7.0.0", "@babel/runtime@^7.1.2", "@babel/runtime@^7.11.2", "@babel/runtime@^7.12.1", "@babel/runtime@^7.12.5", "@babel/runtime@^7.13.10", "@babel/runtime@^7.14.8", "@babel/runtime@^7.17.2", "@babel/runtime@^7.17.8", "@babel/runtime@^7.20.13", "@babel/runtime@^7.21.0", "@babel/runtime@^7.23.9", "@babel/runtime@^7.24.4", "@babel/runtime@^7.29.2", "@babel/runtime@^7.3.1", "@babel/runtime@^7.5.5", "@babel/runtime@^7.7.2", "@babel/runtime@^7.7.7", "@babel/runtime@^7.8.3", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7", "@babel/runtime@^7.9.2":
version "7.29.2"
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.29.2.tgz#9a6e2d05f4b6692e1801cd4fb176ad823930ed5e"
integrity sha512-JiDShH45zKHWyGe4ZNVRrCjBz8Nh9TMmZG1kh4QTK8hCBTWBi8Da+i7s1fJw7/lYpM4ccepSNfqzZ/QvABBi5g==
@@ -3671,17 +3663,6 @@
dependencies:
"@sinclair/typebox" "^0.27.8"
-"@jest/types@^26.6.2":
- version "26.6.2"
- resolved "https://registry.npmjs.org/@jest/types/-/types-26.6.2.tgz"
- integrity sha512-fC6QCp7Sc5sX6g8Tvbmj4XUTbyrik0akgRy03yjXbQaBWWNWGE7SGtJk98m0N8nzegD/7SggrUlivxo5ax4KWQ==
- dependencies:
- "@types/istanbul-lib-coverage" "^2.0.0"
- "@types/istanbul-reports" "^3.0.0"
- "@types/node" "*"
- "@types/yargs" "^15.0.0"
- chalk "^4.0.0"
-
"@jest/types@^29.6.3":
version "29.6.3"
resolved "https://registry.yarnpkg.com/@jest/types/-/types-29.6.3.tgz#1131f8cf634e7e84c5e77bab12f052af585fba59"
@@ -5354,20 +5335,12 @@
dependencies:
"@changesets/cli" "^2.29.7"
-"@playwright-testing-library/test@^4.5.0":
- version "4.5.0"
- resolved "https://registry.yarnpkg.com/@playwright-testing-library/test/-/test-4.5.0.tgz#62f5c21f1eb1bbb7a08e9bf1f73302844c1bd791"
- integrity sha512-jdGlDJyRhQ/fD10EuQr5D65aNzLn6rQIoVj6jVwXP6ebdr2PFiftf/zBF/rmCAcLo6XjHpE2MkSX59JvY+CCWA==
+"@playwright/test@^1.60.0":
+ version "1.60.0"
+ resolved "https://registry.yarnpkg.com/@playwright/test/-/test-1.60.0.tgz#e696c31427e8882851235cd556dc2490c3206d97"
+ integrity sha512-O71yZIbAh/PxDMNGns37GHBIfrVkEVyn+AXyIa5dOTfb4/xNvRWV+Vv/NMbNCtODB/pO7vLlF2OTmMVLhmr7Ag==
dependencies:
- "@testing-library/dom" "^7.31.2"
- wait-for-expect "^3.0.2"
-
-"@playwright/test@^1.49.1":
- version "1.49.1"
- resolved "https://registry.yarnpkg.com/@playwright/test/-/test-1.49.1.tgz#55fa360658b3187bfb6371e2f8a64f50ef80c827"
- integrity sha512-Ky+BVzPz8pL6PQxHqNRW1k3mIyv933LML7HktS8uik0bUXNCdPhoS/kLihiO1tMf/egaJb4IutXd7UywvXEW+g==
- dependencies:
- playwright "1.49.1"
+ playwright "1.60.0"
"@pmmmwh/react-refresh-webpack-plugin@^0.5.11":
version "0.5.11"
@@ -7116,20 +7089,6 @@
lz-string "^1.5.0"
pretty-format "^27.0.2"
-"@testing-library/dom@^7.31.2":
- version "7.31.2"
- resolved "https://registry.yarnpkg.com/@testing-library/dom/-/dom-7.31.2.tgz#df361db38f5212b88555068ab8119f5d841a8c4a"
- integrity sha512-3UqjCpey6HiTZT92vODYLPxTBWlM8ZOOjr3LX5F37/VRipW2M1kX6I/Cm4VXzteZqfGfagg8yXywpcOgQBlNsQ==
- dependencies:
- "@babel/code-frame" "^7.10.4"
- "@babel/runtime" "^7.12.5"
- "@types/aria-query" "^4.2.0"
- aria-query "^4.2.2"
- chalk "^4.1.0"
- dom-accessibility-api "^0.5.6"
- lz-string "^1.4.4"
- pretty-format "^26.6.2"
-
"@testing-library/jest-dom@6.5.0":
version "6.5.0"
resolved "https://registry.yarnpkg.com/@testing-library/jest-dom/-/jest-dom-6.5.0.tgz#50484da3f80fb222a853479f618a9ce5c47bfe54"
@@ -7358,11 +7317,6 @@
resolved "https://registry.yarnpkg.com/@types/argparse/-/argparse-2.0.10.tgz#664e84808accd1987548d888b9d21b3e9c996a6c"
integrity sha512-C4wahC3gz3vQtvPazrJ5ONwmK1zSDllQboiWvpMM/iOswCYfBREFnjFbq/iWKIVOCl8+m5Pk6eva6/ZSsDuIGA==
-"@types/aria-query@^4.2.0":
- version "4.2.2"
- resolved "https://registry.npmjs.org/@types/aria-query/-/aria-query-4.2.2.tgz"
- integrity sha512-HnYpAE1Y6kRyKM/XkEuiRQhTHvkzMBurTHnpFLYLBGPIylZNPs9jJcuOOYWxPLJCSEtmZT0Y8rHDokKN7rRTig==
-
"@types/aria-query@^5.0.1":
version "5.0.4"
resolved "https://registry.yarnpkg.com/@types/aria-query/-/aria-query-5.0.4.tgz#1a31c3d378850d2778dabb6374d036dcba4ba708"
@@ -8076,13 +8030,6 @@
resolved "https://registry.npmjs.org/@types/yargs-parser/-/yargs-parser-20.2.0.tgz"
integrity sha512-37RSHht+gzzgYeobbG+KWryeAW8J33Nhr69cjTqSYymXVZEN9NbRYWoYlRtDhHKPVT1FyNKwaTPC1NynKZpzRA==
-"@types/yargs@^15.0.0":
- version "15.0.13"
- resolved "https://registry.npmjs.org/@types/yargs/-/yargs-15.0.13.tgz"
- integrity sha512-kQ5JNTrbDv3Rp5X2n/iUu37IJBDU2gsZ5R/g1/KHOOEc5IKfUFjXT6DENPGduh08I/pamwtEq4oul7gUqKTQDQ==
- dependencies:
- "@types/yargs-parser" "*"
-
"@types/yargs@^17.0.8":
version "17.0.33"
resolved "https://registry.yarnpkg.com/@types/yargs/-/yargs-17.0.33.tgz#8c32303da83eec050a84b3c7ae7b9f922d13e32d"
@@ -9055,7 +9002,7 @@ ansi-regex@^4.1.0:
resolved "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.1.0.tgz"
integrity sha512-1apePfXM1UOSqw0o9IiFAovVz9M5S1Dg+4TrDwfMewQ6p/rmMueb7tWZjQ1rx4Loy1ArBggoqGpfqqdI4rondg==
-ansi-regex@^5.0.0, ansi-regex@^5.0.1:
+ansi-regex@^5.0.1:
version "5.0.1"
resolved "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz"
integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==
@@ -9286,14 +9233,6 @@ aria-query@5.3.0:
dependencies:
dequal "^2.0.3"
-aria-query@^4.2.2:
- version "4.2.2"
- resolved "https://registry.npmjs.org/aria-query/-/aria-query-4.2.2.tgz"
- integrity sha512-o/HelwhuKpTj/frsOsbNLNgnNGVIFsVP/SW2BSF14gVl7kAfMOJ6/8wUAUvG1R1NHKrfG+2sHZTu0yauT1qBrA==
- dependencies:
- "@babel/runtime" "^7.10.2"
- "@babel/runtime-corejs3" "^7.10.2"
-
aria-query@^5.0.0, aria-query@^5.3.2:
version "5.3.2"
resolved "https://registry.yarnpkg.com/aria-query/-/aria-query-5.3.2.tgz#93f81a43480e33a338f19163a3d10a50c01dcd59"
@@ -10667,7 +10606,7 @@ core-js-compat@^3.31.0, core-js-compat@^3.36.1, core-js-compat@^3.40.0:
dependencies:
browserslist "^4.24.4"
-core-js-pure@^3.14.0, core-js-pure@^3.23.3:
+core-js-pure@^3.23.3:
version "3.36.0"
resolved "https://registry.yarnpkg.com/core-js-pure/-/core-js-pure-3.36.0.tgz#ffb34330b14e594d6a9835cf5843b4123f1d95db"
integrity sha512-cN28qmhRNgbMZZMc/RFu5w8pK9VJzpb2rJVR/lHuZJKwmXnoWOpXmMkxqBB514igkp1Hu8WGROsiOAzUcKdHOQ==
@@ -11555,7 +11494,7 @@ doctrine@^3.0.0:
dependencies:
esutils "^2.0.2"
-dom-accessibility-api@^0.5.6, dom-accessibility-api@^0.5.9:
+dom-accessibility-api@^0.5.9:
version "0.5.16"
resolved "https://registry.yarnpkg.com/dom-accessibility-api/-/dom-accessibility-api-0.5.16.tgz#5a7429e6066eb3664d911e33fb0e45de8eb08453"
integrity sha512-X7BJ2yElsnOJ30pZF4uIIDfBEVgF4XEBxL9Bxhy6dnrm5hkzqmsWHGTiHqRiITNhMyFLyAiWndIJP7Z1NTteDg==
@@ -12291,6 +12230,7 @@ eslint-plugin-unused-imports@^4.1.4:
"eslint-plugin-visualize-admin@link:./eslint/visualize-admin":
version "0.0.0"
+ uid ""
eslint-scope@5.1.1, eslint-scope@^5.1.1:
version "5.1.1"
@@ -17366,25 +17306,17 @@ pkg-up@^3.1.0:
dependencies:
find-up "^3.0.0"
-playwright-core@1.49.1:
- version "1.49.1"
- resolved "https://registry.yarnpkg.com/playwright-core/-/playwright-core-1.49.1.tgz#32c62f046e950f586ff9e35ed490a424f2248015"
- integrity sha512-BzmpVcs4kE2CH15rWfzpjzVGhWERJfmnXmniSyKeRZUs9Ws65m+RGIi7mjJK/euCegfn3i7jvqWeWyHe9y3Vgg==
-
-playwright-testing-library@^4.5.0:
- version "4.5.0"
- resolved "https://registry.yarnpkg.com/playwright-testing-library/-/playwright-testing-library-4.5.0.tgz#abe31799e966b89b61dbf51fb539c853da05c2ab"
- integrity sha512-jgeb/L9Xs1PI3LMQ0eup5w5AyYhHAvc0WyoIFn4RHxc16eZUqamu7Hkq7BYO24zP+byMAbUfk1G+xob/JlOqTg==
- dependencies:
- "@testing-library/dom" "^7.31.2"
- wait-for-expect "^3.0.2"
+playwright-core@1.60.0:
+ version "1.60.0"
+ resolved "https://registry.yarnpkg.com/playwright-core/-/playwright-core-1.60.0.tgz#24e0d9cc4730713db5dffcace29b5e4696b1907a"
+ integrity sha512-9bW6zvX/m0lEbgTKJ6YppOKx8H3VOPBMOCFh2irXFOT4BbHgrx5hPjwJYLT40Lu+4qtD36qKc/Hn56StUW57IA==
-playwright@1.49.1:
- version "1.49.1"
- resolved "https://registry.yarnpkg.com/playwright/-/playwright-1.49.1.tgz#830266dbca3008022afa7b4783565db9944ded7c"
- integrity sha512-VYL8zLoNTBxVOrJBbDuRgDWa3i+mfQgDTrL8Ah9QXZ7ax4Dsj0MSq5bYgytRnDVVe+njoKnfsYkH3HzqVj5UZA==
+playwright@1.60.0:
+ version "1.60.0"
+ resolved "https://registry.yarnpkg.com/playwright/-/playwright-1.60.0.tgz#89710863a51f21112633ef8b6b182594d3bfd7b5"
+ integrity sha512-hheHdokM8cdqCb0lcE3s+zT4t4W+vvjpGxsZlDnikarzx8tSzMebh3UiFtgqwFwnTnjYQcsyMF8ei2mCO/tpeA==
dependencies:
- playwright-core "1.49.1"
+ playwright-core "1.60.0"
optionalDependencies:
fsevents "2.3.2"
@@ -17602,16 +17534,6 @@ pretty-error@^4.0.0:
lodash "^4.17.20"
renderkid "^3.0.0"
-pretty-format@^26.6.2:
- version "26.6.2"
- resolved "https://registry.npmjs.org/pretty-format/-/pretty-format-26.6.2.tgz"
- integrity sha512-7AeGuCYNGmycyQbCqd/3PWH4eOoX/OiCa0uphp57NVTeAGdJGaAliecxwBDHYQCIvrW7aDBZCYeNTP/WX69mkg==
- dependencies:
- "@jest/types" "^26.6.2"
- ansi-regex "^5.0.0"
- ansi-styles "^4.0.0"
- react-is "^17.0.1"
-
pretty-format@^27.0.2:
version "27.5.1"
resolved "https://registry.yarnpkg.com/pretty-format/-/pretty-format-27.5.1.tgz#2181879fdea51a7a5851fb39d920faa63f01d88e"
@@ -18477,11 +18399,6 @@ regenerate@^1.4.2:
resolved "https://registry.yarnpkg.com/regenerate/-/regenerate-1.4.2.tgz#b9346d8827e8f5a32f7ba29637d398b69014848a"
integrity sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A==
-regenerator-runtime@^0.13.4:
- version "0.13.7"
- resolved "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.7.tgz"
- integrity sha512-a54FxoJDIr27pgf7IgeQGxmqUNYrcV338lf/6gH456HZ/PhX+5BcwHXG9ajESmwe6WRO0tAzRUrRmNONWgkrew==
-
regenerator-transform@^0.15.2:
version "0.15.2"
resolved "https://registry.yarnpkg.com/regenerator-transform/-/regenerator-transform-0.15.2.tgz#5bbae58b522098ebdf09bca2f83838929001c7a4"
@@ -21204,11 +21121,6 @@ w3c-xmlserializer@^5.0.0:
dependencies:
xml-name-validator "^5.0.0"
-wait-for-expect@^3.0.2:
- version "3.0.2"
- resolved "https://registry.yarnpkg.com/wait-for-expect/-/wait-for-expect-3.0.2.tgz#d2f14b2f7b778c9b82144109c8fa89ceaadaa463"
- integrity sha512-cfS1+DZxuav1aBYbaO/kE06EOS8yRw7qOFoD3XtjTkYvCvh3zUvNST8DXK/nPaeqIzIv3P3kL3lRJn8iwOiSag==
-
walkdir@^0.4.1:
version "0.4.1"
resolved "https://registry.yarnpkg.com/walkdir/-/walkdir-0.4.1.tgz#dc119f83f4421df52e3061e514228a2db20afa39"