Query pane fixes
- Show mongo execute response in seperate cards for each record - Update postgres read template - Show query execute error message in the UI.
This commit is contained in:
parent
a2086ff61b
commit
6bd79982fb
|
|
@ -10,7 +10,6 @@ import {
|
|||
ColumnsDirective,
|
||||
ColumnDirective,
|
||||
} from "@syncfusion/ej2-react-grids";
|
||||
import ReactJson from "react-json-view";
|
||||
import styled, { createGlobalStyle } from "styled-components";
|
||||
import { Popover } from "@blueprintjs/core";
|
||||
import history from "utils/history";
|
||||
|
|
@ -29,6 +28,8 @@ import { RestAction } from "api/ActionAPI";
|
|||
import { QUERY_EDITOR_FORM_NAME } from "constants/forms";
|
||||
import { PLUGIN_PACKAGE_POSTGRES } from "constants/QueryEditorConstants";
|
||||
import "@syncfusion/ej2-react-grids/styles/material.css";
|
||||
import { Colors } from "constants/Colors";
|
||||
import JSONViewer from "./JSONViewer";
|
||||
|
||||
const QueryFormContainer = styled.div`
|
||||
font-size: 20px;
|
||||
|
|
@ -178,6 +179,11 @@ const StyledGridComponent = styled(GridComponent)`
|
|||
}
|
||||
`;
|
||||
|
||||
const ErrorMessage = styled.p`
|
||||
font-size: 14px;
|
||||
color: ${Colors.RED};
|
||||
`;
|
||||
|
||||
type QueryFormProps = {
|
||||
isCreating: boolean;
|
||||
onDeleteClick: () => void;
|
||||
|
|
@ -194,6 +200,7 @@ type QueryFormProps = {
|
|||
executedQueryData: any;
|
||||
applicationId: string;
|
||||
selectedPluginPackage: string;
|
||||
runErrorMessage: string | undefined;
|
||||
pageId: string;
|
||||
location: {
|
||||
state: any;
|
||||
|
|
@ -223,6 +230,7 @@ const QueryEditorForm: React.FC<Props> = (props: Props) => {
|
|||
selectedPluginPackage,
|
||||
createTemplate,
|
||||
isCreating,
|
||||
runErrorMessage,
|
||||
} = props;
|
||||
|
||||
const [showTemplateMenu, setMenuVisibility] = useState(true);
|
||||
|
|
@ -251,6 +259,7 @@ const QueryEditorForm: React.FC<Props> = (props: Props) => {
|
|||
</LoadingContainer>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<QueryFormContainer>
|
||||
<form onSubmit={handleSubmit}>
|
||||
|
|
@ -411,6 +420,13 @@ const QueryEditorForm: React.FC<Props> = (props: Props) => {
|
|||
</NoDataSourceContainer>
|
||||
)}
|
||||
|
||||
{runErrorMessage && (
|
||||
<>
|
||||
<p className="statementTextArea">Query error</p>
|
||||
<ErrorMessage>{runErrorMessage}</ErrorMessage>
|
||||
</>
|
||||
)}
|
||||
|
||||
{executedQueryData && dataSources.length && (
|
||||
<ResponseContainer>
|
||||
<p className="statementTextArea">Query response</p>
|
||||
|
|
@ -435,16 +451,7 @@ const QueryEditorForm: React.FC<Props> = (props: Props) => {
|
|||
</ColumnsDirective>
|
||||
</StyledGridComponent>
|
||||
) : (
|
||||
<ReactJson
|
||||
src={executedQueryData.body}
|
||||
name={null}
|
||||
enableClipboard={false}
|
||||
displayObjectSize={false}
|
||||
displayDataTypes={false}
|
||||
style={{
|
||||
fontSize: "14px",
|
||||
}}
|
||||
/>
|
||||
<JSONViewer src={executedQueryData.body} />
|
||||
)}
|
||||
</ResponseContent>
|
||||
</ResponseContainer>
|
||||
|
|
|
|||
61
app/client/src/pages/Editor/QueryEditor/JSONViewer.tsx
Normal file
61
app/client/src/pages/Editor/QueryEditor/JSONViewer.tsx
Normal file
|
|
@ -0,0 +1,61 @@
|
|||
import React from "react";
|
||||
import ReactJson from "react-json-view";
|
||||
import styled from "styled-components";
|
||||
import { Card } from "@blueprintjs/core";
|
||||
|
||||
const OutputContainer = styled.div`
|
||||
background: #f5f6f7;
|
||||
border: 1px solid #d0d7dd;
|
||||
box-sizing: border-box;
|
||||
border-radius: 4px;
|
||||
padding: 6px;
|
||||
`;
|
||||
|
||||
const Record = styled(Card)`
|
||||
margin: 5px;
|
||||
`;
|
||||
|
||||
type JSONOutputProps = {
|
||||
src: [];
|
||||
};
|
||||
|
||||
type Props = JSONOutputProps;
|
||||
|
||||
class JSONOutput extends React.Component<Props> {
|
||||
render() {
|
||||
const { src } = this.props;
|
||||
const reactJsonProps = {
|
||||
name: null,
|
||||
enableClipboard: false,
|
||||
displayObjectSize: false,
|
||||
displayDataTypes: false,
|
||||
style: {
|
||||
fontSize: "14px",
|
||||
},
|
||||
};
|
||||
|
||||
if (!src.length) {
|
||||
return (
|
||||
<OutputContainer>
|
||||
<Record>
|
||||
<ReactJson src={src} {...reactJsonProps} />
|
||||
</Record>
|
||||
</OutputContainer>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<OutputContainer>
|
||||
{src.map((record, index) => {
|
||||
return (
|
||||
<Record key={index}>
|
||||
<ReactJson src={record} {...reactJsonProps} />
|
||||
</Record>
|
||||
);
|
||||
})}
|
||||
</OutputContainer>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
export default JSONOutput;
|
||||
|
|
@ -42,7 +42,7 @@ const Templates: Record<string, any> = {
|
|||
create: `INSERT INTO users(
|
||||
id, name, gender, avatar, email, address, role)
|
||||
VALUES (?, ?, ?, ?, ?, ?, ?);`,
|
||||
read: "SELECT * FROM users LIMIT 10 ORDER BY id",
|
||||
read: "SELECT * FROM users ORDER BY id LIMIT 10",
|
||||
delete: `DELETE FROM users WHERE id=?`,
|
||||
update: `UPDATE users
|
||||
Set status='APPROVED'
|
||||
|
|
|
|||
|
|
@ -45,6 +45,7 @@ type QueryPageProps = {
|
|||
submitForm: (name: string) => void;
|
||||
createAction: (values: RestAction) => void;
|
||||
runAction: (action: RestAction, actionId: string) => void;
|
||||
runErrorMessage: Record<string, string>;
|
||||
deleteAction: (id: string) => void;
|
||||
updateAction: (data: RestAction) => void;
|
||||
createTemplate: (template: string) => void;
|
||||
|
|
@ -91,6 +92,7 @@ class QueryEditor extends React.Component<Props> {
|
|||
selectedPluginPackage,
|
||||
apiPane,
|
||||
isCreating,
|
||||
runErrorMessage,
|
||||
} = this.props;
|
||||
const { applicationId, pageId } = this.props.match.params;
|
||||
|
||||
|
|
@ -139,6 +141,7 @@ class QueryEditor extends React.Component<Props> {
|
|||
DATASOURCES_OPTIONS={DATASOURCES_OPTIONS}
|
||||
selectedPluginPackage={selectedPluginPackage}
|
||||
executedQueryData={executedQueryData[queryId]}
|
||||
runErrorMessage={runErrorMessage[queryId]}
|
||||
/>
|
||||
) : (
|
||||
<QueryHomeScreen
|
||||
|
|
@ -156,6 +159,7 @@ class QueryEditor extends React.Component<Props> {
|
|||
}
|
||||
|
||||
const mapStateToProps = (state: AppState): any => {
|
||||
const { runErrorMessage } = state.ui.queryPane;
|
||||
const formData = getFormValues(QUERY_EDITOR_FORM_NAME)(state) as RestAction;
|
||||
const initialValues = getFormInitialValues(QUERY_EDITOR_FORM_NAME)(
|
||||
state,
|
||||
|
|
@ -167,6 +171,7 @@ const mapStateToProps = (state: AppState): any => {
|
|||
);
|
||||
|
||||
return {
|
||||
runErrorMessage,
|
||||
apiPane: state.ui.apiPane,
|
||||
pluginIds: getPluginIdsOfPackageNames(state, PLUGIN_PACKAGE_DBS),
|
||||
dataSources: getDataSources(state),
|
||||
|
|
|
|||
|
|
@ -5,6 +5,7 @@ import {
|
|||
ReduxAction,
|
||||
} from "constants/ReduxActionConstants";
|
||||
import { RestAction } from "api/ActionAPI";
|
||||
import _ from "lodash";
|
||||
|
||||
const initialState: QueryPaneReduxState = {
|
||||
isFetching: false,
|
||||
|
|
@ -13,6 +14,7 @@ const initialState: QueryPaneReduxState = {
|
|||
isSaving: {},
|
||||
isDeleting: {},
|
||||
runQuerySuccessData: {},
|
||||
runErrorMessage: {},
|
||||
lastUsed: "",
|
||||
};
|
||||
|
||||
|
|
@ -22,6 +24,7 @@ export interface QueryPaneReduxState {
|
|||
isSaving: Record<string, boolean>;
|
||||
isDeleting: Record<string, boolean>;
|
||||
runQuerySuccessData: {};
|
||||
runErrorMessage: Record<string, string>;
|
||||
lastUsed: string;
|
||||
isCreating: boolean;
|
||||
}
|
||||
|
|
@ -134,6 +137,8 @@ const queryPaneReducer = createReducer(initialState, {
|
|||
state: any,
|
||||
action: ReduxAction<{ actionId: string; data: object }>,
|
||||
) => {
|
||||
const { actionId } = action.payload;
|
||||
|
||||
return {
|
||||
...state,
|
||||
isRunning: {
|
||||
|
|
@ -144,17 +149,24 @@ const queryPaneReducer = createReducer(initialState, {
|
|||
...state.runQuerySuccessData,
|
||||
[action.payload.actionId]: action.payload.data,
|
||||
},
|
||||
runErrorMessage: _.omit(state.runErrorMessage, [actionId]),
|
||||
};
|
||||
},
|
||||
[ReduxActionErrorTypes.RUN_QUERY_ERROR]: (
|
||||
state: any,
|
||||
action: ReduxAction<{ actionId: string }>,
|
||||
action: ReduxAction<{ actionId: string; message: string }>,
|
||||
) => {
|
||||
const { actionId, message } = action.payload;
|
||||
|
||||
return {
|
||||
...state,
|
||||
isRunning: {
|
||||
...state.isRunning,
|
||||
[action.payload.actionId]: false,
|
||||
[actionId]: false,
|
||||
},
|
||||
runErrorMessage: {
|
||||
...state.runError,
|
||||
[actionId]: message,
|
||||
},
|
||||
};
|
||||
},
|
||||
|
|
|
|||
|
|
@ -246,6 +246,7 @@ export function* executeQuerySaga(
|
|||
type: ReduxActionErrorTypes.RUN_QUERY_ERROR,
|
||||
payload: {
|
||||
actionId: actionPayload.payload.actionId,
|
||||
message: error.message,
|
||||
show: false,
|
||||
},
|
||||
});
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user