/* * DBeaver - Universal Database Manager * Copyright (C) 2010-2017 Serge Rider (serge@jkiss.org) * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.jkiss.dbeaver.ui.editors.sql.handlers; import org.eclipse.core.commands.ExecutionEvent; import org.eclipse.core.commands.ExecutionException; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IFolder; import org.eclipse.core.resources.IProject; import org.eclipse.core.runtime.CoreException; import org.eclipse.jface.viewers.ISelection; import org.eclipse.jface.viewers.IStructuredSelection; import org.eclipse.ui.IEditorInput; import org.eclipse.ui.IWorkbenchPart; import org.eclipse.ui.IWorkbenchWindow; import org.eclipse.ui.PartInitException; import org.eclipse.ui.handlers.HandlerUtil; import org.jkiss.code.NotNull; import org.jkiss.code.Nullable; import org.jkiss.dbeaver.core.CoreCommands; import org.jkiss.dbeaver.core.DBeaverCore; import org.jkiss.dbeaver.core.DBeaverUI; import org.jkiss.dbeaver.model.DBPContextProvider; import org.jkiss.dbeaver.model.DBPDataSourceContainer; import org.jkiss.dbeaver.model.DBUtils; import org.jkiss.dbeaver.model.IDataSourceContainerProvider; import org.jkiss.dbeaver.model.exec.DBCExecutionContext; import org.jkiss.dbeaver.model.navigator.DBNDataSource; import org.jkiss.dbeaver.model.navigator.DBNLocalFolder; import org.jkiss.dbeaver.model.navigator.DBNResource; import org.jkiss.dbeaver.model.runtime.DBRProgressMonitor; import org.jkiss.dbeaver.model.runtime.DBRRunnableWithProgress; import org.jkiss.dbeaver.model.struct.DBSObject; import org.jkiss.dbeaver.registry.DataSourceRegistry; import org.jkiss.dbeaver.registry.ProjectRegistry; import org.jkiss.dbeaver.ui.UIUtils; import org.jkiss.dbeaver.ui.actions.AbstractDataSourceHandler; import org.jkiss.dbeaver.ui.actions.navigator.NavigatorHandlerObjectOpen; import org.jkiss.dbeaver.ui.controls.ScriptSelectorPanel; import org.jkiss.dbeaver.ui.dialogs.connection.SelectDataSourceDialog; import org.jkiss.dbeaver.ui.editors.EditorUtils; import org.jkiss.dbeaver.ui.editors.StringEditorInput; import org.jkiss.dbeaver.ui.editors.sql.SQLEditor; import org.jkiss.dbeaver.ui.resources.ResourceUtils; import org.jkiss.dbeaver.utils.GeneralUtils; import java.lang.reflect.InvocationTargetException; import java.util.ArrayList; import java.util.List; public class OpenHandler extends AbstractDataSourceHandler { @Override public Object execute(ExecutionEvent event) throws ExecutionException { String actionId = event.getCommand().getId(); try { switch (actionId) { case CoreCommands.CMD_SQL_EDITOR_OPEN: openEditor(event); break; case CoreCommands.CMD_SQL_EDITOR_NEW: openNewEditor(event); break; case CoreCommands.CMD_SQL_EDITOR_RECENT: openRecentEditor(event); break; } } catch (CoreException e) { UIUtils.showErrorDialog(HandlerUtil.getActiveShell(event), "Open editor", "Can execute command '" + actionId + "'", e); } return null; } private static void openEditor(ExecutionEvent event) throws ExecutionException, CoreException { List<DBPDataSourceContainer> containers = getDataSourceContainers(event); IWorkbenchWindow workbenchWindow = HandlerUtil.getActiveWorkbenchWindow(event); IProject project = !containers.isEmpty() ? containers.get(0).getRegistry().getProject() : DBeaverCore.getInstance().getProjectRegistry().getActiveProject(); checkProjectIsOpen(project); final DBPDataSourceContainer[] containerList = containers.toArray(new DBPDataSourceContainer[containers.size()]); final IFolder rootFolder = ResourceUtils.getScriptsFolder(project, true); final List<ResourceUtils.ResourceInfo> scriptTree = ResourceUtils.findScriptTree(rootFolder, containerList.length == 0 ? null : containerList); if (scriptTree.isEmpty() && containerList.length == 1) { // Create new script final IFile newScript = ResourceUtils.createNewScript(project, rootFolder, containers.isEmpty() ? null : containers.get(0)); NavigatorHandlerObjectOpen.openResource(newScript, workbenchWindow); } else { // Show script chooser ScriptSelectorPanel selector = new ScriptSelectorPanel(workbenchWindow, containerList, rootFolder); selector.showTree(scriptTree); } } private static boolean openNewEditor(ExecutionEvent event) throws CoreException { IWorkbenchWindow workbenchWindow = HandlerUtil.getActiveWorkbenchWindow(event); DBPDataSourceContainer dataSourceContainer = getCurrentConnection(event); IFolder scriptFolder = getCurrentFolder(event); IProject project = dataSourceContainer != null ? dataSourceContainer.getRegistry().getProject() : DBeaverCore.getInstance().getProjectRegistry().getActiveProject(); checkProjectIsOpen(project); IFile scriptFile = ResourceUtils.createNewScript(project, scriptFolder, dataSourceContainer); NavigatorHandlerObjectOpen.openResource(scriptFile, workbenchWindow); return true; } private static void openRecentEditor(ExecutionEvent event) throws ExecutionException, CoreException { DBPDataSourceContainer dataSourceContainer = getCurrentConnection(event); if (dataSourceContainer == null) { return; } openRecentScript(HandlerUtil.getActiveWorkbenchWindow(event), dataSourceContainer, null); } @Nullable private static DBPDataSourceContainer getCurrentConnection(ExecutionEvent event) { DBPDataSourceContainer dataSourceContainer = getDataSourceContainer(event, false); final ProjectRegistry projectRegistry = DBeaverCore.getInstance().getProjectRegistry(); IProject project = dataSourceContainer != null ? dataSourceContainer.getRegistry().getProject() : projectRegistry.getActiveProject(); if (dataSourceContainer == null) { final DataSourceRegistry dataSourceRegistry = projectRegistry.getDataSourceRegistry(project); if (dataSourceRegistry == null) { return null; } if (dataSourceRegistry.getDataSources().size() == 1) { dataSourceContainer = dataSourceRegistry.getDataSources().get(0); } else if (!dataSourceRegistry.getDataSources().isEmpty()) { dataSourceContainer = SelectDataSourceDialog.selectDataSource( HandlerUtil.getActiveShell(event), project); } } return dataSourceContainer; } @Nullable private static IFolder getCurrentFolder(ExecutionEvent event) { final ISelection selection = HandlerUtil.getCurrentSelection(event); if (selection != null && !selection.isEmpty() && selection instanceof IStructuredSelection) { final Object element = ((IStructuredSelection) selection).getFirstElement(); if (element instanceof DBNResource && ((DBNResource)element).getResource() instanceof IFolder) { return (IFolder) ((DBNResource)element).getResource(); } } return null; } private static List<DBPDataSourceContainer> getDataSourceContainers(ExecutionEvent event) { List<DBPDataSourceContainer> containers = new ArrayList<>(); ISelection selection = HandlerUtil.getCurrentSelection(event); if (selection instanceof IStructuredSelection) { for (Object obj : ((IStructuredSelection) selection).toArray()) { if (obj instanceof DBNLocalFolder) { for (DBNDataSource ds : ((DBNLocalFolder) obj).getDataSources()) { containers.add(ds.getDataSourceContainer()); } } else { DBSObject selectedObject = DBUtils.getFromObject(obj); if (selectedObject != null) { if (selectedObject instanceof DBPDataSourceContainer) { containers.add((DBPDataSourceContainer) selectedObject); } else { containers.add(selectedObject.getDataSource().getContainer()); } } } } } if (containers.isEmpty()) { IWorkbenchPart activePart = HandlerUtil.getActivePart(event); DBPDataSourceContainer partContainer = getDataSourceContainers(activePart); if (partContainer != null) { containers.add(partContainer); } } return containers; } private static DBPDataSourceContainer getDataSourceContainers(IWorkbenchPart activePart) { if (activePart instanceof IDataSourceContainerProvider) { return ((IDataSourceContainerProvider) activePart).getDataSourceContainer(); } if (activePart instanceof DBPContextProvider) { DBCExecutionContext context = ((DBPContextProvider) activePart).getExecutionContext(); return context == null ? null : context.getDataSource().getContainer(); } return null; } public static void openRecentScript(@NotNull IWorkbenchWindow workbenchWindow, @Nullable DBPDataSourceContainer dataSourceContainer, @Nullable IFolder scriptFolder) throws CoreException { final IProject project = dataSourceContainer != null ? dataSourceContainer.getRegistry().getProject() : DBeaverCore.getInstance().getProjectRegistry().getActiveProject(); checkProjectIsOpen(project); ResourceUtils.ResourceInfo res = ResourceUtils.findRecentScript(project, dataSourceContainer); if (res != null) { NavigatorHandlerObjectOpen.openResourceEditor(workbenchWindow, res); } else { IFile scriptFile = ResourceUtils.createNewScript(project, scriptFolder, dataSourceContainer); NavigatorHandlerObjectOpen.openResource(scriptFile, workbenchWindow); } } private static void checkProjectIsOpen(final IProject project) throws CoreException { if (project == null) { throw new CoreException(GeneralUtils.makeExceptionStatus(new IllegalStateException("No active project."))); } if (!project.isOpen()) { try { DBeaverUI.runInProgressService(new DBRRunnableWithProgress() { @Override public void run(DBRProgressMonitor monitor) throws InvocationTargetException, InterruptedException { try { project.open(monitor.getNestedMonitor()); } catch (CoreException e) { throw new InvocationTargetException(e); } } }); } catch (InvocationTargetException e) { throw (CoreException)e.getTargetException(); } catch (InterruptedException e) { // ignore } } } public static SQLEditor openSQLConsole( IWorkbenchWindow workbenchWindow, DBPDataSourceContainer dataSourceContainer, String name, String sqlText) { StringEditorInput sqlInput = new StringEditorInput(name, sqlText, false, GeneralUtils.DEFAULT_ENCODING); EditorUtils.setInputDataSource(sqlInput, dataSourceContainer, false); return openSQLEditor(workbenchWindow, sqlInput); } public static SQLEditor openSQLEditor( IWorkbenchWindow workbenchWindow, IEditorInput sqlInput) { try { return (SQLEditor)workbenchWindow.getActivePage().openEditor( sqlInput, SQLEditor.class.getName()); } catch (PartInitException e) { UIUtils.showErrorDialog(workbenchWindow.getShell(), "Can't open editor", null, e); } return null; } }