@eodash/eodash 5.0.0-rc.2.5 → 5.0.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.
Files changed (77) hide show
  1. package/core/client/composables/DefineWidgets.js +8 -1
  2. package/core/client/eodash.js +9 -9
  3. package/core/client/eodashSTAC/createLayers.js +4 -18
  4. package/core/client/eodashSTAC/helpers.js +23 -0
  5. package/core/client/store/stac.js +3 -1
  6. package/core/client/types.ts +125 -19
  7. package/core/client/utils/states.js +9 -0
  8. package/dist/client/{DashboardLayout-BX3Sm_Vx.js → DashboardLayout-CkWvOMOW.js} +2 -2
  9. package/dist/client/{DynamicWebComponent-BqoHM1np.js → DynamicWebComponent-DYBbpvUK.js} +1 -1
  10. package/dist/client/{EodashDatePicker-BoWV2vc8.js → EodashDatePicker-CALmW3SI.js} +3 -83
  11. package/dist/client/{EodashItemFilter-127fZLyK.js → EodashItemFilter-DlQiE713.js} +1 -1
  12. package/dist/client/{EodashLayerControl-B-pZaizw.js → EodashLayerControl-DEzEbft7.js} +8 -2
  13. package/dist/client/{EodashLayoutSwitcher-DwexHfOD.js → EodashLayoutSwitcher-CDeCV8F-.js} +2 -2
  14. package/dist/client/{EodashMapBtns-Jfn3bpWD.js → EodashMapBtns-CktQCfa-.js} +36 -12
  15. package/dist/client/{EodashStacInfo-STq_bW7S.js → EodashStacInfo-DPPxDkF6.js} +7 -1
  16. package/dist/client/{EodashTools-uxSuJhVJ.js → EodashTools-CUaL9s4H.js} +5 -4
  17. package/dist/client/{ExportState-Ckcb6u01.js → ExportState-DjyIZVhl.js} +27 -12
  18. package/dist/client/{Footer-C8JP-coH.js → Footer-DyL0JoWt.js} +1 -1
  19. package/dist/client/{Header-Dxx7q9FW.js → Header-B5Dgty9l.js} +3 -3
  20. package/dist/client/{MobileLayout-BE19Peep.js → MobileLayout-CRsg_5Q4.js} +5 -5
  21. package/dist/client/{PopUp-D3IyjsN4.js → PopUp-BfB8s_ki.js} +3 -3
  22. package/dist/client/ProcessList-DTefwQZx.js +484 -0
  23. package/dist/client/{VImg-BmCNSu3X.js → VImg-FD1WVphJ.js} +2 -2
  24. package/dist/client/{VMain-eZDKIfmJ.js → VMain-DJKG4SvM.js} +1 -1
  25. package/dist/client/{VOverlay-BS-E4Z6g.js → VOverlay-BzOdRu9h.js} +15 -6
  26. package/dist/client/{VTooltip-BMsliOuh.js → VTooltip-CfeefrXI.js} +3 -3
  27. package/dist/client/{WidgetsContainer-Cl6M5R5c.js → WidgetsContainer-C2TaTdb6.js} +1 -1
  28. package/dist/client/{asWebComponent-Df8nUiLs.js → asWebComponent-CLhcT715.js} +100 -96
  29. package/dist/client/eo-dash.css +2 -2
  30. package/dist/client/eo-dash.js +1 -1
  31. package/dist/client/{forwardRefs-lhDuXD-N.js → forwardRefs-Bon_Kku1.js} +9 -9
  32. package/dist/client/index-4CT7Tz83.js +85 -0
  33. package/dist/client/{index-Bt5GEGxl.js → index-Bm9cbtx5.js} +1 -1
  34. package/dist/client/{EodashMap-BSR7_wRA.js → index-CIHH_3dW.js} +101 -80
  35. package/dist/client/{EodashProcess-CpbZPYBp.js → index-DiGDvTQU.js} +346 -468
  36. package/dist/client/{transition-DHEuQX4I.js → transition-C5I57hn6.js} +1 -1
  37. package/dist/types/core/client/components/MobileLayout.vue.d.ts +9 -9
  38. package/dist/types/core/client/eodashSTAC/helpers.d.ts +3 -2
  39. package/dist/types/core/client/types.d.ts +83 -17
  40. package/dist/types/core/client/utils/states.d.ts +7 -0
  41. package/dist/types/widgets/EodashDatePicker.vue.d.ts +4 -4
  42. package/dist/types/widgets/EodashItemFilter.vue.d.ts +18 -18
  43. package/dist/types/widgets/EodashLayerControl.vue.d.ts +2 -2
  44. package/dist/types/widgets/EodashLayoutSwitcher.vue.d.ts +2 -2
  45. package/dist/types/widgets/EodashMap/methods/create-layers-config.d.ts +9 -0
  46. package/dist/types/widgets/EodashMap/methods/index.d.ts +5 -0
  47. package/dist/types/widgets/EodashMapBtns.vue.d.ts +8 -2
  48. package/dist/types/widgets/EodashProcess/ProcessList.vue.d.ts +2 -0
  49. package/dist/types/widgets/EodashProcess/methods/async.d.ts +45 -0
  50. package/dist/types/widgets/EodashProcess/methods/composables.d.ts +19 -0
  51. package/dist/types/widgets/EodashProcess/methods/handling.d.ts +78 -0
  52. package/dist/types/widgets/EodashProcess/methods/outputs.d.ts +54 -0
  53. package/dist/types/widgets/EodashProcess/methods/utils.d.ts +42 -0
  54. package/dist/types/widgets/EodashStacInfo.vue.d.ts +12 -12
  55. package/dist/types/widgets/EodashTools.vue.d.ts +44 -6
  56. package/dist/types/widgets/PopUp.vue.d.ts +4 -4
  57. package/package.json +27 -27
  58. package/widgets/EodashLayerControl.vue +8 -1
  59. package/widgets/{EodashMap.vue → EodashMap/index.vue} +51 -31
  60. package/widgets/EodashMap/methods/create-layers-config.js +151 -0
  61. package/{core/client/composables/EodashMap.js → widgets/EodashMap/methods/index.js} +4 -153
  62. package/widgets/EodashMapBtns.vue +33 -7
  63. package/widgets/EodashProcess/ProcessList.vue +82 -0
  64. package/widgets/EodashProcess/index.vue +186 -0
  65. package/widgets/EodashProcess/methods/async.js +209 -0
  66. package/widgets/EodashProcess/methods/composables.js +129 -0
  67. package/widgets/EodashProcess/methods/handling.js +254 -0
  68. package/widgets/EodashProcess/methods/outputs.js +216 -0
  69. package/widgets/EodashProcess/methods/utils.js +138 -0
  70. package/widgets/EodashStacInfo.vue +6 -0
  71. package/widgets/EodashTools.vue +1 -0
  72. package/core/client/composables/EodashProcess.js +0 -654
  73. package/dist/types/core/client/composables/EodashMap.d.ts +0 -6
  74. package/dist/types/core/client/composables/EodashProcess.d.ts +0 -162
  75. package/widgets/EodashProcess.vue +0 -206
  76. /package/dist/types/widgets/{EodashMap.vue.d.ts → EodashMap/index.vue.d.ts} +0 -0
  77. /package/dist/types/widgets/{EodashProcess.vue.d.ts → EodashProcess/index.vue.d.ts} +0 -0
@@ -0,0 +1,209 @@
1
+ import { indicator, mapEl } from "@/store/states";
2
+ import axios from "axios";
3
+ import { ref } from "vue";
4
+ import { createLayerDefinition, download } from "./utils";
5
+ import log from "loglevel";
6
+ import { getLayers } from "@/store/actions";
7
+
8
+ /**
9
+ * The list of job result from the server
10
+ * {job_start_datetime: string, job_end_datetime: string,status: string}
11
+ * @type {import("vue").Ref<any[]>}
12
+ **/
13
+ export const jobs = ref([]);
14
+
15
+ /**
16
+ * Polls the process status and fetches a result item when the process is successful.
17
+ *
18
+ * @param {Object} params - Parameters for polling the process status.
19
+ * @param {string} params.processUrl - The URL of the process JSON report.
20
+ * @param {import("vue").Ref<boolean>} params.isPolling - checks wether the polling should continue
21
+ * @param {number} [params.pollInterval=5000] - The interval (in milliseconds) between polling attempts.
22
+ * @param {number} [params.maxRetries=60] - The maximum number of polling attempts.
23
+ * @returns {Promise<JSON>} The fetched results JSON.
24
+ * @throws {Error} If the process does not complete successfully within the maximum retries.
25
+ */
26
+ export async function pollProcessStatus({
27
+ processUrl,
28
+ isPolling,
29
+ pollInterval = 10000,
30
+ maxRetries = 560,
31
+ }) {
32
+ let retries = 0;
33
+ isPolling.value = true;
34
+ setTimeout(() => {
35
+ updateJobsStatus(jobs, indicator);
36
+ }, 500);
37
+ while (retries < maxRetries && isPolling.value) {
38
+ try {
39
+ // Fetch the process JSON report
40
+ const cacheBuster = new Date().getTime(); // Add a timestamp for cache busting
41
+ const response = await axios.get(`${processUrl}?t=${cacheBuster}`);
42
+ const processReport = response.data;
43
+
44
+ // Check if the status is "successful"
45
+ if (processReport.status === "successful") {
46
+ console.log("Process completed successfully. Fetching result item...");
47
+
48
+ // Extract the result item URL
49
+ const resultsUrl = processReport.links[1].href;
50
+ if (!resultsUrl) {
51
+ throw new Error(`Result links not found in the process report.`);
52
+ }
53
+
54
+ // Fetch the result item
55
+ const resultResponse = await axios.get(resultsUrl);
56
+ console.log("Result file fetched successfully:", resultResponse.data);
57
+ return resultResponse.data; // Return the json result list
58
+ }
59
+ if (processReport.status === "failed") {
60
+ isPolling.value = false;
61
+ throw new Error("Process failed.", processReport);
62
+ }
63
+
64
+ // Log the current status if not successful
65
+ console.log(
66
+ `Status: ${processReport.status}. Retrying in ${pollInterval / 1000} seconds...`,
67
+ );
68
+ } catch (error) {
69
+ if (error instanceof Error) {
70
+ console.error("Error while polling process status:", error.message);
71
+ } else {
72
+ console.error("Unknown error occurred:", error);
73
+ }
74
+ }
75
+
76
+ // Wait for the next poll
77
+ await new Promise((resolve) => setTimeout(resolve, pollInterval));
78
+ retries++;
79
+ }
80
+ if (!isPolling.value) {
81
+ console.warn("Polling was stopped before the process was completed.");
82
+ return JSON.parse("{}");
83
+ }
84
+
85
+ throw new Error(
86
+ "Max retries reached. Process did not complete successfully.",
87
+ );
88
+ }
89
+
90
+ /**
91
+ *
92
+ * @param {*} jobs
93
+ * @param {*} indicator
94
+ */
95
+ export async function updateJobsStatus(jobs, indicator) {
96
+ /** @type {string[]} */
97
+ const jobsUrls = JSON.parse(localStorage.getItem(indicator.value) || "[]");
98
+ const jobResults = await Promise.all(
99
+ jobsUrls.map((url) => fetch(url).then((response) => response.json())),
100
+ );
101
+ jobResults.sort((a, b) => {
102
+ return (
103
+ new Date(b.job_start_datetime).getTime() -
104
+ new Date(a.job_start_datetime).getTime()
105
+ );
106
+ });
107
+ jobs.value = jobResults;
108
+ }
109
+
110
+ /**
111
+ * Removes a job from the local storage and updates the job status
112
+ * @param {*} jobObject
113
+ */
114
+ export const deleteJob = async (jobObject) => {
115
+ /** @type {string[]} */
116
+ const jobsUrls = JSON.parse(localStorage.getItem(indicator.value) || "[]");
117
+ const newJobs = jobsUrls.filter((url) => !url.includes(jobObject.jobID));
118
+ localStorage.setItem(indicator.value, JSON.stringify(newJobs));
119
+ updateJobsStatus(jobs, indicator);
120
+ };
121
+
122
+ /**
123
+ * Downloads an existing process results
124
+ * @param {*} jobObject
125
+ * @param {*} selectedStac
126
+ */
127
+ export const downloadPreviousResults = async (jobObject, selectedStac) => {
128
+ /** @type {any[]} */
129
+ const results = [];
130
+ await fetch(jobObject.links[1].href)
131
+ .then((response) => response.json())
132
+ .then((data) => {
133
+ results.push(...data.urls);
134
+ });
135
+ results.forEach((result) => {
136
+ if (!result) {
137
+ return;
138
+ }
139
+ let fileName = "";
140
+ if (typeof result === "string") {
141
+ fileName = result.includes("/")
142
+ ? (result.split("/").pop() ?? "")
143
+ : result;
144
+ fileName = fileName.includes("?") ? fileName.split("?")[0] : fileName;
145
+ } else {
146
+ fileName = selectedStac?.id + "_process_results.json";
147
+ }
148
+ download(fileName, result);
149
+ });
150
+ };
151
+
152
+ /**
153
+ * Load the process results and update the map layers.
154
+ *
155
+ * @async
156
+ * @param {*} jobObject
157
+ * @param {*} selectedStac
158
+ */
159
+ export const loadProcess = async (jobObject, selectedStac) => {
160
+ /** @type {any[]} */
161
+ const results = [];
162
+ await axios
163
+ .get(jobObject.links[1].href)
164
+ .then((response) => results.push(response.data));
165
+
166
+ await loadPreviousProcess({
167
+ selectedStac,
168
+ results,
169
+ jobId: jobObject.jobID,
170
+ });
171
+ };
172
+
173
+ /**
174
+ * load a geotiff to the map from an existing process
175
+ *
176
+ * @param {Object} params
177
+ * @param {import("stac-ts").StacCollection | null} params.selectedStac
178
+ * @param {any[]} params.results
179
+ * @param {string} params.jobId
180
+ */
181
+ export async function loadPreviousProcess({ selectedStac, results, jobId }) {
182
+ const geotiffLinks = selectedStac?.links.filter(
183
+ (link) => link.rel === "service" && link.type === "image/tiff",
184
+ );
185
+ // const stacProjection = selectedStac
186
+ const geotiffLayer = await createLayerDefinition(
187
+ geotiffLinks?.[0],
188
+ selectedStac?.id ?? "",
189
+ results?.[0].urls,
190
+ //@ts-expect-error TODO
191
+ selectedStac?.["eodash:mapProjection"]?.["name"] ?? null,
192
+ jobId,
193
+ );
194
+
195
+ log.debug("rendered layers after loading previous process:", geotiffLayer);
196
+
197
+ if (geotiffLayer) {
198
+ const layers = [...(geotiffLayer ? [geotiffLayer] : [])];
199
+ let currentLayers = [...getLayers()];
200
+ let analysisGroup = currentLayers.find((l) =>
201
+ l.properties.id.includes("AnalysisGroup"),
202
+ );
203
+ analysisGroup?.layers.push(...layers);
204
+
205
+ if (mapEl.value) {
206
+ mapEl.value.layers = [...currentLayers];
207
+ }
208
+ }
209
+ }
@@ -0,0 +1,129 @@
1
+ import { mapEl } from "@/store/states";
2
+ import { initProcess } from "./handling";
3
+ import { useEventBus } from "@vueuse/core";
4
+ import { nextTick, onMounted, watch } from "vue";
5
+ import { eoxLayersKey } from "@/utils/keys";
6
+ import { useOnLayersUpdate } from "@/composables";
7
+
8
+ /**
9
+ * Composable resposible of timing the Initialization of the process
10
+ *
11
+ * @export
12
+ * @async
13
+ * @param {Object} params
14
+ * @param {import("vue").Ref<import("stac-ts").StacCollection>} params.selectedStac
15
+ * @param {import("vue").Ref<import("@eox/jsonform").EOxJSONForm | null>} params.jsonformEl
16
+ * @param {import("vue").Ref<Record<string,any> | null>} params.jsonformSchema
17
+ * @param {import("vue").Ref<import("@eox/chart").EOxChart["spec"] | null>} params.chartSpec
18
+ * @param {import("vue").Ref<any[]>} params.processResults
19
+ * @param {import("vue").Ref<boolean>} params.isProcessed
20
+ * @param {import("vue").Ref<boolean>} params.loading
21
+ * @param {import("vue").Ref<boolean>} params.isPolling
22
+ */
23
+ export const useInitProcess = ({
24
+ selectedStac,
25
+ jsonformEl,
26
+ jsonformSchema,
27
+ chartSpec,
28
+ isProcessed,
29
+ processResults,
30
+ loading,
31
+ isPolling,
32
+ }) => {
33
+ const layersEvents = useEventBus(eoxLayersKey);
34
+
35
+ onMounted(async () => {
36
+ // wait for the layers to be rendered
37
+ if (mapEl.value?.layers.length > 1) {
38
+ await initProcess({
39
+ selectedStac,
40
+ jsonformEl,
41
+ jsonformSchema,
42
+ chartSpec,
43
+ isProcessed,
44
+ processResults,
45
+ loading,
46
+ isPolling,
47
+ });
48
+ } else {
49
+ layersEvents.once(async () => {
50
+ await initProcess({
51
+ selectedStac,
52
+ jsonformEl,
53
+ jsonformSchema,
54
+ chartSpec,
55
+ isProcessed,
56
+ loading,
57
+ processResults,
58
+ isPolling,
59
+ });
60
+ });
61
+ }
62
+ });
63
+
64
+ useOnLayersUpdate(async (evt, _payload) => {
65
+ if (evt === "layers:updated") {
66
+ await initProcess({
67
+ selectedStac,
68
+ jsonformEl,
69
+ jsonformSchema,
70
+ chartSpec,
71
+ isProcessed,
72
+ processResults,
73
+ loading,
74
+ isPolling,
75
+ });
76
+ }
77
+ });
78
+ };
79
+
80
+ /**
81
+ * Auto execute the process when the jsonform has the execute option
82
+ *
83
+ * @param {import("vue").Ref<boolean>} autoExec
84
+ * @param {import("vue").Ref<import("@eox/jsonform").EOxJSONForm | null>} jsonformEl
85
+ * @param {import("vue").Ref<Record<string,any> | null>} jsonformSchema
86
+ * @param {() => Promise<void>} startProcess
87
+ **/
88
+ export function useAutoExec(
89
+ autoExec,
90
+ jsonformEl,
91
+ jsonformSchema,
92
+ startProcess,
93
+ ) {
94
+ /**
95
+ * @param {CustomEvent} _e
96
+ **/
97
+ const onJsonFormChange = async (_e) => {
98
+ await startProcess();
99
+ };
100
+
101
+ const addEventListener = async () => {
102
+ await nextTick(() => {
103
+ //@ts-expect-error TODO
104
+ jsonformEl.value?.addEventListener("change", onJsonFormChange);
105
+ });
106
+ };
107
+ const removeEventListener = () => {
108
+ //@ts-expect-error TODO
109
+ jsonformEl.value?.removeEventListener("change", onJsonFormChange);
110
+ };
111
+
112
+ watch(jsonformSchema, (updatedSchema) => {
113
+ autoExec.value = updatedSchema?.options?.["execute"] || false;
114
+ });
115
+
116
+ onMounted(() => {
117
+ watch(
118
+ autoExec,
119
+ async (exec) => {
120
+ if (exec) {
121
+ await addEventListener();
122
+ } else {
123
+ removeEventListener();
124
+ }
125
+ },
126
+ { immediate: true },
127
+ );
128
+ });
129
+ }
@@ -0,0 +1,254 @@
1
+ import log from "loglevel";
2
+ import { extractGeometries, getBboxProperty } from "./utils";
3
+ import { datetime, mapEl } from "@/store/states";
4
+ import axios from "@/plugins/axios";
5
+ import { getLayers } from "@/store/actions";
6
+ import {
7
+ getChartValues,
8
+ processGeoTiff,
9
+ processImage,
10
+ processVector,
11
+ } from "./outputs";
12
+
13
+ /**
14
+ * Fetch and set the jsonform schema to initialize the process
15
+ *
16
+ * @export
17
+ * @async
18
+ * @param {Object} params
19
+ * @param {import("vue").Ref<import("stac-ts").StacCollection>} params.selectedStac
20
+ * @param {import("vue").Ref<import("@eox/jsonform").EOxJSONForm | null>} params.jsonformEl
21
+ * @param {import("vue").Ref<Record<string,any> | null>} params.jsonformSchema
22
+ * @param {import("vue").Ref<import("@eox/chart").EOxChart["spec"] | null>} params.chartSpec
23
+ * @param {import("vue").Ref<any[]>} params.processResults
24
+ * @param {import("vue").Ref<boolean>} params.isProcessed
25
+ * @param {import("vue").Ref<boolean>} params.loading
26
+ * @param {import("vue").Ref<boolean>} params.isPolling
27
+ */
28
+ export async function initProcess({
29
+ selectedStac,
30
+ jsonformEl,
31
+ jsonformSchema,
32
+ chartSpec,
33
+ isProcessed,
34
+ processResults,
35
+ loading,
36
+ isPolling,
37
+ }) {
38
+ if (!selectedStac.value) {
39
+ return;
40
+ }
41
+ resetProcess({
42
+ loading,
43
+ isProcessed,
44
+ chartSpec,
45
+ jsonformSchema,
46
+ isPolling,
47
+ processResults,
48
+ });
49
+ if (selectedStac.value["eodash:jsonform"]) {
50
+ jsonformEl.value?.editor.destroy();
51
+ // wait for the layers to be rendered
52
+ jsonformSchema.value = await axios
53
+ //@ts-expect-error eodash extention
54
+ .get(selectedStac.value["eodash:jsonform"])
55
+ .then((resp) => resp.data);
56
+ // remove borders from jsonform
57
+ } else {
58
+ if (!jsonformSchema.value) {
59
+ return;
60
+ }
61
+ jsonformSchema.value = null;
62
+ }
63
+ }
64
+
65
+ /**
66
+ *
67
+ * @param {Object} params
68
+ * @param {import("vue").Ref<boolean>} params.loading
69
+ * @param {import("vue").Ref<import("stac-ts").StacCollection | null>} params.selectedStac
70
+ * @param {import("vue").Ref<import("@eox/jsonform").EOxJSONForm | null>} params.jsonformEl
71
+ * @param {import("vue").Ref<Record<string,any>|null>} params.jsonformSchema
72
+ * @param {import("vue").Ref<import("@eox/chart").EOxChart["spec"] | null>} params.chartSpec
73
+ * @param {import("vue").Ref<Record<string, any> | null>} params.chartData
74
+ * @param {import("vue").Ref<boolean>} params.isPolling
75
+ * @param {import("vue").Ref<any[]>} params.processResults
76
+ */
77
+ export async function handleProcesses({
78
+ loading,
79
+ selectedStac,
80
+ jsonformEl,
81
+ jsonformSchema,
82
+ chartSpec,
83
+ chartData,
84
+ isPolling,
85
+ processResults,
86
+ }) {
87
+ if (!jsonformEl.value || !jsonformSchema.value || !selectedStac.value) {
88
+ return;
89
+ }
90
+ log.debug("Processing...");
91
+ loading.value = true;
92
+ try {
93
+ const serviceLinks = selectedStac.value?.links?.filter(
94
+ (l) => l.rel === "service",
95
+ );
96
+ const bboxProperty = getBboxProperty(jsonformSchema.value);
97
+ const jsonformValue = /** @type {Record<string,any>} */ (
98
+ jsonformEl.value?.value
99
+ );
100
+
101
+ extractGeometries(jsonformValue, jsonformSchema.value);
102
+
103
+ const origBbox = jsonformValue[bboxProperty];
104
+
105
+ const specUrl = /** @type {string} */ (
106
+ selectedStac.value?.["eodash:vegadefinition"]
107
+ );
108
+
109
+ [chartSpec.value, chartData.value] = await getChartValues(
110
+ serviceLinks,
111
+ { ...(jsonformValue ?? {}) },
112
+ specUrl,
113
+ );
114
+ if (Object.keys(chartData.value ?? {}).length) {
115
+ processResults.value.push(chartData.value);
116
+ }
117
+
118
+ //@ts-expect-error we assume that the spec data is of type InlineData
119
+ if (chartSpec.value?.data?.values?.length) {
120
+ //@ts-expect-error we assume that the spec data is of type InlineData
121
+ processResults.value.push(chartSpec.value?.data.values);
122
+ }
123
+
124
+ if (chartSpec.value && !("background" in chartSpec.value)) {
125
+ chartSpec.value["background"] = "transparent";
126
+ }
127
+
128
+ const geotiffLayer = await processGeoTiff(
129
+ serviceLinks,
130
+ jsonformValue,
131
+ selectedStac.value?.id ?? "",
132
+ isPolling,
133
+ //@ts-expect-error TODO
134
+ selectedStac.value?.["eodash:mapProjection"]?.["name"] ?? null,
135
+ );
136
+
137
+ if (geotiffLayer && geotiffLayer.source?.sources.length) {
138
+ processResults.value.push(
139
+ ...(geotiffLayer.source?.sources?.map((source) => source.url) ?? []),
140
+ );
141
+ }
142
+ // 3. vector geojson
143
+ const vectorLayers = await processVector(
144
+ serviceLinks,
145
+ jsonformValue,
146
+ selectedStac.value?.id ?? "",
147
+ );
148
+
149
+ if (vectorLayers?.length) {
150
+ processResults.value.push(
151
+ ...vectorLayers.map((layer) => layer.source?.url),
152
+ );
153
+ }
154
+
155
+ const imageLayers = processImage(serviceLinks, jsonformValue, origBbox);
156
+ if (imageLayers?.length) {
157
+ processResults.value.push(
158
+ ...imageLayers.map((layer) => layer.source?.url),
159
+ );
160
+ }
161
+
162
+ log.debug(
163
+ "rendered layers after processing:",
164
+ geotiffLayer,
165
+ vectorLayers,
166
+ imageLayers,
167
+ );
168
+
169
+ if (geotiffLayer || vectorLayers?.length || imageLayers?.length) {
170
+ const layers = [
171
+ ...(geotiffLayer ? [geotiffLayer] : []),
172
+ ...(vectorLayers ?? []),
173
+ ...(imageLayers ?? []),
174
+ ];
175
+ let currentLayers = [...getLayers()];
176
+ let analysisGroup = currentLayers.find((l) =>
177
+ l.properties.id.includes("AnalysisGroup"),
178
+ );
179
+ analysisGroup?.layers.push(...layers);
180
+
181
+ if (mapEl.value) {
182
+ mapEl.value.layers = [...currentLayers];
183
+ }
184
+ }
185
+ loading.value = false;
186
+ } catch (error) {
187
+ console.error("[eodash] Error while running process:", error);
188
+ loading.value = false;
189
+ throw error;
190
+ }
191
+ }
192
+
193
+ /**
194
+ * Reset the process state
195
+ * @param {Object} params
196
+ * @param {import("vue").Ref<boolean>} params.loading
197
+ * @param {import("vue").Ref<boolean>} params.isProcessed
198
+ * @param {import("vue").Ref<import("@eox/chart").EOxChart["spec"] | null>} params.chartSpec
199
+ * @param {import("vue").Ref<boolean>} params.isPolling
200
+ * @param {import("vue").Ref<any[]>} params.processResults
201
+ * @param {import("vue").Ref<Record<string,any>|null>} params.jsonformSchema
202
+ */
203
+ export function resetProcess({
204
+ loading,
205
+ isProcessed,
206
+ chartSpec,
207
+ jsonformSchema,
208
+ processResults,
209
+ isPolling,
210
+ }) {
211
+ loading.value = false;
212
+ isProcessed.value = false;
213
+ isPolling.value = false;
214
+ chartSpec.value = null;
215
+ processResults.value = [];
216
+ jsonformSchema.value = null;
217
+ }
218
+
219
+ /**
220
+ * Handles the click event on a chart to extract temporal information and update the global datetime value.
221
+ *
222
+ * @param {object} evt - The click event object.
223
+ * @param {object} evt.target - The target of the event, expected to have a Vega-Lite specification (`spec`).
224
+ * @param {object} evt.target.spec - The Vega-Lite specification of the chart.
225
+ * @param {Record<string,{type?:string;field?:string;}>} [evt.target.spec.encoding] - The encoding specification of the chart.
226
+ * @param {object} evt.detail - The detail of the event, containing information about the clicked item.
227
+ * @param {import("vega").Item} evt.detail.item - The Vega item that was clicked.
228
+ */
229
+ export const onChartClick = (evt) => {
230
+ const chartSpec = evt.target?.spec;
231
+ if (!chartSpec) {
232
+ return;
233
+ }
234
+ const encodingKey = Object.keys(chartSpec.encoding ?? {}).find(
235
+ (key) => chartSpec.encoding?.[key].type === "temporal",
236
+ );
237
+ if (!encodingKey) {
238
+ return;
239
+ }
240
+ const temporalKey = chartSpec.encoding?.[encodingKey].field;
241
+ if (!temporalKey) {
242
+ return;
243
+ }
244
+ try {
245
+ const vegaItem = evt.detail.item;
246
+ const temporalValue = new Date(vegaItem.datum.datum[temporalKey]);
247
+ datetime.value = temporalValue.toISOString();
248
+ } catch (error) {
249
+ console.warn(
250
+ "[eodash] Error while setting datetime from eox-chart:",
251
+ error,
252
+ );
253
+ }
254
+ };