Fixed the following issues for the new query tool:
1) In Dark mode > Replace/Find dialogue forward & reverse buttons are stuck to each other. 2) In Dark/High contrast mode > Checkbox is not visible for false value. 3) Wrap toolbar when size goes very small. 4) Replace functionality does not work when tried in sequence 2 times. Codemirror search is not cyclic. So, changes are made to always search from the start. 5) Replace all does not work when tried in sequence 2 times. Same reason as above. 6) Fix broken macros $SELECTION$ feature. 7) Make query history SQL readonly. 8) The Filter dialog save button should be disabled when opened.pull/85/head
parent
3d1a9624c1
commit
0795b22ae6
|
@ -134,7 +134,7 @@ export function FindDialog({editor, show, replace, onClose}) {
|
||||||
const search = ()=>{
|
const search = ()=>{
|
||||||
if(editor) {
|
if(editor) {
|
||||||
let query = parseQuery(findVal, useRegex, matchCase);
|
let query = parseQuery(findVal, useRegex, matchCase);
|
||||||
searchCursor.current = editor.getSearchCursor(query, editor.getCursor(true), !matchCase);
|
searchCursor.current = editor.getSearchCursor(query, 0, !matchCase);
|
||||||
if(findVal != '') {
|
if(findVal != '') {
|
||||||
editor.removeOverlay(highlightsearch.current);
|
editor.removeOverlay(highlightsearch.current);
|
||||||
highlightsearch.current = searchOverlay(query, matchCase);
|
highlightsearch.current = searchOverlay(query, matchCase);
|
||||||
|
@ -221,6 +221,8 @@ export function FindDialog({editor, show, replace, onClose}) {
|
||||||
};
|
};
|
||||||
|
|
||||||
const onReplaceAll = ()=>{
|
const onReplaceAll = ()=>{
|
||||||
|
/* search from start */
|
||||||
|
search();
|
||||||
while(searchCursor.current.from()) {
|
while(searchCursor.current.from()) {
|
||||||
onReplace();
|
onReplace();
|
||||||
}
|
}
|
||||||
|
@ -253,10 +255,13 @@ export function FindDialog({editor, show, replace, onClose}) {
|
||||||
/>}
|
/>}
|
||||||
|
|
||||||
<Box display="flex" className={classes.marginTop}>
|
<Box display="flex" className={classes.marginTop}>
|
||||||
<PgIconButton title={gettext('Previous')} icon={<ArrowUpwardRoundedIcon />} size="xs" noBorder onClick={onFindPrev} />
|
<PgIconButton title={gettext('Previous')} icon={<ArrowUpwardRoundedIcon />} size="xs" noBorder onClick={onFindPrev}
|
||||||
<PgIconButton title={gettext('Next')} icon={<ArrowDownwardRoundedIcon />} size="xs" noBorder onClick={onFindNext}/>
|
style={{marginRight: '2px'}} />
|
||||||
|
<PgIconButton title={gettext('Next')} icon={<ArrowDownwardRoundedIcon />} size="xs" noBorder onClick={onFindNext}
|
||||||
|
style={{marginRight: '2px'}} />
|
||||||
{replace && <>
|
{replace && <>
|
||||||
<PgIconButton title={gettext('Replace')} icon={<SwapHorizRoundedIcon style={{height: 'unset'}}/>} size="xs" noBorder onClick={onReplace} />
|
<PgIconButton title={gettext('Replace')} icon={<SwapHorizRoundedIcon style={{height: 'unset'}}/>} size="xs" noBorder onClick={onReplace}
|
||||||
|
style={{marginRight: '2px'}} />
|
||||||
<PgIconButton title={gettext('Replace All')} icon={<SwapCallsRoundedIcon />} size="xs" noBorder onClick={onReplaceAll}/>
|
<PgIconButton title={gettext('Replace All')} icon={<SwapCallsRoundedIcon />} size="xs" noBorder onClick={onReplaceAll}/>
|
||||||
</>}
|
</>}
|
||||||
<Box marginLeft="auto">
|
<Box marginLeft="auto">
|
||||||
|
|
|
@ -68,9 +68,13 @@ function setPanelTitle(panel, title, qtState, dirty=false) {
|
||||||
setQueryToolDockerTitle(panel, true, title, qtState.current_file ? true : false);
|
setQueryToolDockerTitle(panel, true, title, qtState.current_file ? true : false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function onBeforeUnload(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
e.returnValue = 'prevent';
|
||||||
|
}
|
||||||
export default function QueryToolComponent({params, pgWindow, pgAdmin, selectedNodeInfo, panel, eventBusObj}) {
|
export default function QueryToolComponent({params, pgWindow, pgAdmin, selectedNodeInfo, panel, eventBusObj}) {
|
||||||
const containerRef = React.useRef(null);
|
const containerRef = React.useRef(null);
|
||||||
const forceClose = React.useRef(false);
|
|
||||||
const [qtState, _setQtState] = useState({
|
const [qtState, _setQtState] = useState({
|
||||||
preferences: {
|
preferences: {
|
||||||
browser: {}, sqleditor: {},
|
browser: {}, sqleditor: {},
|
||||||
|
@ -111,7 +115,8 @@ export default function QueryToolComponent({params, pgWindow, pgAdmin, selectedN
|
||||||
const modal = useModal();
|
const modal = useModal();
|
||||||
|
|
||||||
/* Connection status poller */
|
/* Connection status poller */
|
||||||
let pollTime = qtState.preferences.sqleditor.connection_status_fetch_time > 0 && !qtState.obtaining_conn ?
|
let pollTime = qtState.preferences.sqleditor.connection_status_fetch_time > 0
|
||||||
|
&& !qtState.obtaining_conn && qtState.preferences?.sqleditor?.connection_status ?
|
||||||
qtState.preferences.sqleditor.connection_status_fetch_time*1000 : -1;
|
qtState.preferences.sqleditor.connection_status_fetch_time*1000 : -1;
|
||||||
/* No need to poll when the query is executing. Query poller will the txn status */
|
/* No need to poll when the query is executing. Query poller will the txn status */
|
||||||
if(qtState.connection_status === CONNECTION_STATUS.TRANSACTION_STATUS_ACTIVE && qtState.connected) {
|
if(qtState.connection_status === CONNECTION_STATUS.TRANSACTION_STATUS_ACTIVE && qtState.connected) {
|
||||||
|
@ -299,11 +304,8 @@ export default function QueryToolComponent({params, pgWindow, pgAdmin, selectedN
|
||||||
|
|
||||||
/* WC docker events */
|
/* WC docker events */
|
||||||
panel?.on(window.wcDocker.EVENT.CLOSING, function() {
|
panel?.on(window.wcDocker.EVENT.CLOSING, function() {
|
||||||
if(!forceClose.current) {
|
window.removeEventListener('beforeunload', onBeforeUnload);
|
||||||
eventBus.current.fireEvent(QUERY_TOOL_EVENTS.WARN_SAVE_DATA_CLOSE);
|
eventBus.current.fireEvent(QUERY_TOOL_EVENTS.WARN_SAVE_DATA_CLOSE);
|
||||||
} else {
|
|
||||||
panel.close();
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
|
|
||||||
pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:select_file', (fileName)=>{
|
pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:select_file', (fileName)=>{
|
||||||
|
@ -313,6 +315,8 @@ export default function QueryToolComponent({params, pgWindow, pgAdmin, selectedN
|
||||||
pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:create_file', (fileName)=>{
|
pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:create_file', (fileName)=>{
|
||||||
eventBus.current.fireEvent(QUERY_TOOL_EVENTS.SAVE_FILE, fileName);
|
eventBus.current.fireEvent(QUERY_TOOL_EVENTS.SAVE_FILE, fileName);
|
||||||
}, pgAdmin);
|
}, pgAdmin);
|
||||||
|
|
||||||
|
window.addEventListener('beforeunload', onBeforeUnload);
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
useEffect(()=>{
|
useEffect(()=>{
|
||||||
|
|
|
@ -93,7 +93,7 @@ const useStyles = makeStyles((theme)=>({
|
||||||
lineHeight: '16px',
|
lineHeight: '16px',
|
||||||
|
|
||||||
'&.checked, &.unchecked': {
|
'&.checked, &.unchecked': {
|
||||||
background: theme.palette.background.default,
|
background: theme.palette.grey[200],
|
||||||
},
|
},
|
||||||
'&.checked:after': {
|
'&.checked:after': {
|
||||||
content: '\'\\2713\'',
|
content: '\'\\2713\'',
|
||||||
|
|
|
@ -136,7 +136,7 @@ export default function FilterDialog({onClose, onSave}) {
|
||||||
getInitData={getInitData}
|
getInitData={getInitData}
|
||||||
schema={filterSchemaObj}
|
schema={filterSchemaObj}
|
||||||
viewHelperProps={{
|
viewHelperProps={{
|
||||||
mode: 'create',
|
mode: 'edit',
|
||||||
}}
|
}}
|
||||||
onSave={onSaveClick}
|
onSave={onSaveClick}
|
||||||
onClose={onClose}
|
onClose={onClose}
|
||||||
|
|
|
@ -43,6 +43,7 @@ const useStyles = makeStyles((theme)=>({
|
||||||
alignItems: 'center',
|
alignItems: 'center',
|
||||||
gap: '4px',
|
gap: '4px',
|
||||||
backgroundColor: theme.otherVars.editorToolbarBg,
|
backgroundColor: theme.otherVars.editorToolbarBg,
|
||||||
|
flexWrap: 'wrap',
|
||||||
...theme.mixins.panelBorder.bottom,
|
...theme.mixins.panelBorder.bottom,
|
||||||
},
|
},
|
||||||
}));
|
}));
|
||||||
|
@ -322,7 +323,7 @@ export function MainToolBar({containerRef, onFilterClick, onManageMacros}) {
|
||||||
eventBus.fireEvent(QUERY_TOOL_EVENTS.EXECUTION_START, 'ROLLBACK;', null, true);
|
eventBus.fireEvent(QUERY_TOOL_EVENTS.EXECUTION_START, 'ROLLBACK;', null, true);
|
||||||
};
|
};
|
||||||
const executeMacro = (m)=>{
|
const executeMacro = (m)=>{
|
||||||
eventBus.fireEvent(QUERY_TOOL_EVENTS.EXECUTION_START, m.sql, null, true);
|
eventBus.fireEvent(QUERY_TOOL_EVENTS.TRIGGER_EXECUTION, null, m.sql);
|
||||||
};
|
};
|
||||||
const onLimitChange=(e)=>{
|
const onLimitChange=(e)=>{
|
||||||
setLimit(e.target.value);
|
setLimit(e.target.value);
|
||||||
|
|
|
@ -237,11 +237,20 @@ export default function Query() {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const triggerExecution = (explainObject)=>{
|
const triggerExecution = (explainObject, macroSQL)=>{
|
||||||
if(queryToolCtx.params.is_query_tool) {
|
if(queryToolCtx.params.is_query_tool) {
|
||||||
let query = editor.current?.getSelection() || editor.current?.getValue() || '';
|
let external = null;
|
||||||
|
let query = editor.current?.getSelection();
|
||||||
|
if(!_.isUndefined(macroSQL)) {
|
||||||
|
const regex = /\$SELECTION\$/gi;
|
||||||
|
query = macroSQL.replace(regex, query);
|
||||||
|
external = true;
|
||||||
|
} else{
|
||||||
|
/* Normal execution */
|
||||||
|
query = query || editor.current?.getValue() || '';
|
||||||
|
}
|
||||||
if(query) {
|
if(query) {
|
||||||
eventBus.fireEvent(QUERY_TOOL_EVENTS.EXECUTION_START, query, explainObject);
|
eventBus.fireEvent(QUERY_TOOL_EVENTS.EXECUTION_START, query, explainObject, external);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
eventBus.fireEvent(QUERY_TOOL_EVENTS.EXECUTION_START, null, null);
|
eventBus.fireEvent(QUERY_TOOL_EVENTS.EXECUTION_START, null, null);
|
||||||
|
@ -375,7 +384,7 @@ export default function Query() {
|
||||||
});
|
});
|
||||||
}, [queryToolCtx.params.trans_id]);
|
}, [queryToolCtx.params.trans_id]);
|
||||||
|
|
||||||
const isDirty = ()=>lastSavedText.current !== editor.current.getValue();
|
const isDirty = ()=>(queryToolCtx.params.is_query_tool && lastSavedText.current !== editor.current.getValue());
|
||||||
|
|
||||||
const cursorActivity = useCallback((cmObj)=>{
|
const cursorActivity = useCallback((cmObj)=>{
|
||||||
const c = cmObj.getCursor();
|
const c = cmObj.getCursor();
|
||||||
|
|
Loading…
Reference in New Issue