From 514d64ee68e015c297482f5d7cb1a1c1a640a855 Mon Sep 17 00:00:00 2001 From: broknloop <90255202+broknloop@users.noreply.github.com> Date: Mon, 20 Nov 2023 22:30:58 +0100 Subject: [PATCH] fix(json-query-error-handling): Fix missing error handling in query. Also swap order of tabs (#52) Co-authored-by: Broknloop --- .../components/query-result/query-result.js | 112 +++++++++++------- src/main/js/routes/schema/preview.js | 14 ++- src/main/js/routes/schema/query.js | 21 ++-- src/main/js/routes/schema/schema.js | 10 +- 4 files changed, 97 insertions(+), 60 deletions(-) diff --git a/src/main/js/components/query-result/query-result.js b/src/main/js/components/query-result/query-result.js index 1bbdc27..73442ea 100644 --- a/src/main/js/components/query-result/query-result.js +++ b/src/main/js/components/query-result/query-result.js @@ -24,7 +24,6 @@ function QueryResult({containerUrl, vispanaClient, query, showResults, schema, r default: 'rgb(20 27 45 / var(--tw-bg-opacity))', }, }); - const revalidator = useRevalidator(); // data state const [data, setData] = useState({columns: [], content: []}); @@ -43,47 +42,55 @@ function QueryResult({containerUrl, vispanaClient, query, showResults, schema, r }); async function postQuery(offset, perPage) { - const queryObject = JSON.parse(query) - const response = await vispanaClient - .postQuery(containerUrl, queryObject, offset, perPage) - .then(response => { - if (response.status && response.status !== 200) { - const error = response.message ? response.message : "Failed to execute the query" - return { - success: undefined, - error: error - } - } else { - return { - success: response, - error: undefined - } - } - }) - .catch(error => { - return { - success: undefined, - error: error.message - } - }) - - if (response.error) { + try { + const queryObject = JSON.parse(query) + const response = await vispanaClient + .postQuery(containerUrl, queryObject, offset, perPage) + .then(response => { + if (response.status && response.status !== 200) { + const error = response.message ? response.message : "Failed to execute the query" + return { + success: undefined, + error: error + } + } else { + return { + success: response, + error: undefined + } + } + }) + .catch(error => { + return { + success: undefined, + error: error.message + } + }) + + if (response.error) { + setError({ + hasError: true, + error: response.error + }) + } else { + const vespaState = response.success; + setTotalRows(vespaState.root.fields.totalCount); + + const gridData = processResult(vespaState); + setData(gridData); + + setError({ + hasError: false, + error: undefined + }) + } + } catch (exception) { setError({ hasError: true, - error: response.error - }) - } else { - const vespaState = response.success; - setTotalRows(vespaState.root.fields.totalCount); - - const gridData = processResult(vespaState); - setData(gridData); - - setError({ - hasError: false, - error: undefined + error: exception.message }) } + } const load = async () => { @@ -108,9 +115,18 @@ function QueryResult({containerUrl, vispanaClient, query, showResults, schema, r setPerPage(newPerPage); }; + useEffect(() => { + setPage(1) + setPerPage(defaultPageSize) + setError({ + hasError: false, + error: "" + }) + }, [schema]); + useEffect(() => { load(); - }, [schema, showResults, perPage, page]); + }, [showResults, perPage, page]); useEffect(() => { setError({ @@ -153,7 +169,7 @@ function QueryResult({containerUrl, vispanaClient, query, showResults, schema, r ) } -function processResult(previewResults) { +function processResult(result) { function extractData(rawData) { if (rawData === null || rawData === undefined) { return null; @@ -167,14 +183,17 @@ function processResult(previewResults) { } // if empty result, just skip - if (!previewResults || !previewResults.root.fields.totalCount) { + if (!result || !result.root.fields.totalCount) { return { columns: [], content: [] } } - const children = previewResults.root.children; + const children = result.root.children; + const resultFields = children.flatMap(child => Object.keys(child.fields)); + resultFields.push("relevance") + const columns = [...new Set(resultFields)] .map(column => ( { @@ -185,9 +204,14 @@ function processResult(previewResults) { const rawData = row[column] return extractData(rawData) }, - })) - const data = children.map(child => child.fields) + + const data = children.map(child => { + const fields = child.fields; + fields.relevance = child.relevance + return fields + }) + return { columns: columns, content: data diff --git a/src/main/js/routes/schema/preview.js b/src/main/js/routes/schema/preview.js index 00a7f13..2c6e95f 100644 --- a/src/main/js/routes/schema/preview.js +++ b/src/main/js/routes/schema/preview.js @@ -1,13 +1,18 @@ -import React from "react"; +import React, {useEffect, useState} from "react"; import QueryResult from "../../components/query-result/query-result"; import VispanaApiClient from "../../client/vispana-api-client"; +import {defaultQuery} from "./query"; +import {v4 as uuidv4} from "uuid"; function Preview({containerUrl, schema}) { const vispanaClient = new VispanaApiClient() + const [query, setQuery] = useState(defaultQuery(schema)) + const [refreshQuery, setRefreshQuery] = useState(uuidv4()) - const query = JSON.stringify({ - yql: `SELECT * from ${schema} where true` - }, null, 2) + useEffect(() => { + setQuery(defaultQuery(schema)) + setRefreshQuery(uuidv4()) + }, [schema]) return (
) } diff --git a/src/main/js/routes/schema/query.js b/src/main/js/routes/schema/query.js index e011561..93f2ff8 100644 --- a/src/main/js/routes/schema/query.js +++ b/src/main/js/routes/schema/query.js @@ -1,5 +1,5 @@ import Editor from "../../components/editor/editor"; -import React, {useState} from "react"; +import React, {useEffect, useState} from "react"; import VispanaApiClient from "../../client/vispana-api-client"; import QueryResult from "../../components/query-result/query-result"; import { v4 as uuidv4 } from 'uuid'; @@ -12,15 +12,15 @@ function Query({containerUrl, schema}) { } const vispanaClient = new VispanaApiClient() - const defaultQuery = JSON.stringify({ - yql: `SELECT *from ${schema} where true`, - hits: 30 - }, null, 2) - - const [query, setQuery] = useState(defaultQuery) + const [query, setQuery] = useState(defaultQuery(schema)) const [showResults, setShowResults] = useState(false) const [refreshQuery, setRefreshQuery] = useState(uuidv4()) + useEffect(() => { + setQuery(defaultQuery(schema)) + setShowResults(false) + }, [schema]) + return
@@ -51,4 +51,11 @@ function Query({containerUrl, schema}) {
} +export function defaultQuery(schema) { + return JSON.stringify({ + yql: `SELECT * from ${schema} where true`, + hits: 30 + }, null, 2); +} + export default Query diff --git a/src/main/js/routes/schema/schema.js b/src/main/js/routes/schema/schema.js index 0932c40..e77235b 100644 --- a/src/main/js/routes/schema/schema.js +++ b/src/main/js/routes/schema/schema.js @@ -12,14 +12,14 @@ function Schema() { return (<> - }, { "header": "Query", "content": - }]} /> + }, + { + "header": "Data preview", + "content": + },]} /> ) /* finds a valid container to issue the query */