/* * � Copyright IBM Corp. 2011 * * 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 com.ibm.xsp.extlib.designer.xspprops; import java.io.ByteArrayInputStream; import java.io.IOException; import java.io.InputStream; import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; import java.util.Properties; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IProject; import org.eclipse.core.resources.IncrementalProjectBuilder; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.NullProgressMonitor; import org.eclipse.core.runtime.Platform; import org.eclipse.jdt.internal.ui.propertiesfileeditor.PropertiesFileEditor; import org.eclipse.jface.viewers.ISelection; import org.eclipse.jface.viewers.ISelectionChangedListener; import org.eclipse.jface.viewers.ISelectionProvider; import org.eclipse.jface.viewers.SelectionChangedEvent; import org.eclipse.jface.viewers.StructuredSelection; import org.eclipse.swt.SWT; import org.eclipse.swt.events.DisposeEvent; import org.eclipse.swt.events.DisposeListener; import org.eclipse.swt.widgets.Composite; import org.eclipse.ui.IEditorInput; import org.eclipse.ui.IEditorPart; import org.eclipse.ui.IEditorSite; import org.eclipse.ui.PartInitException; import org.eclipse.ui.forms.widgets.FormToolkit; import org.eclipse.ui.part.FileEditorInput; import org.eclipse.ui.part.MultiPageEditorPart; import com.ibm.commons.iloader.node.DataNode; import com.ibm.commons.iloader.node.DataNodeAdapter; import com.ibm.commons.iloader.node.IClassDef; import com.ibm.commons.iloader.node.NodeException; import com.ibm.commons.iloader.node.collections.SingleCollection; import com.ibm.commons.iloader.node.loaders.JavaBeanLoader; import com.ibm.commons.swt.dialog.LWPDMessageDialog; import com.ibm.commons.util.StringUtil; import com.ibm.designer.domino.ide.resources.extensions.DesignerProject; import com.ibm.designer.domino.ui.commons.extensions.DesignerResource; import com.ibm.domino.xsp.module.nsf.NSFComponentModule; /** * @author mleland * */ @SuppressWarnings("restriction") //$NON-NLS-1$ public class XSPParentEditor extends MultiPageEditorPart implements ISelectionProvider { private FileEditorInput dbPropInput = null; private IProject project; private IFile xspDesignProps; private XSPDesignPropsBean xspDesignPropsBean; private XSPPropBean dbBean = null; private DesignerProject dp; private XSPPropBeanLoader jbl = null; private JavaBeanLoader xspDesignLoader; private boolean bPromptRecompileOnExit = false; private IClassDef dbPropClassDef = null; private IClassDef xspDesignPropsClassDef; protected ISelection editorSelection = null; protected Collection<ISelectionChangedListener> selectionChangedListeners = new ArrayList<ISelectionChangedListener>(); private FormToolkit toolkit = null; private XSPPage page1 = null; private XSPPerfPage page2 = null; private XSPGenPage page3 = null; private PropertiesFileEditor pfe = null; private XSPAllProperties props = null; private int GENERAL_TAB = 0; private int PERF_TAB = 1; private int HTML_TAB = 2; private int sourcePageNum = 0; private int curPage = 0; private final String DESIGN_PATH = "AppProperties/xspdesign.properties"; // $NON-NLS-1$ /* (non-Javadoc) * @see org.eclipse.ui.part.EditorPart#doSave(org.eclipse.core.runtime.IProgressMonitor) */ @Override public void doSave(IProgressMonitor progress) { if (isDirty()) { // save the contents of the source editor, always pfe.doSave(progress); dbBean.save(progress); // no real saving here, but some necessary cleanup xspDesignPropsBean.save(progress); page1.getDataNode().setModelModified(false); page2.getDataNode().setModelModified(false); page3.getDataNode().setModelModified(false); setModified(false); if (isBPromptRecompileOnExit()) { if( LWPDMessageDialog.openQuestion(null, "Domino Designer", // $NLX-XSPParentEditor.DominoDesigner-1$ "You have changed the minimum supported version for XPages in this application. Do you want to rebuild this application now?") ) { // $NLX-XSPParentEditor.Youhavechangedtheminimumsupported-1$ try { getDesignerProject().build(IncrementalProjectBuilder.FULL_BUILD, new NullProgressMonitor()); } catch (CoreException e) { } } setBPromptRecompileOnExit(false); // if they chose no, still should not prompt again } NSFComponentModule.setLastDesignerSave(System.currentTimeMillis()); } } /* (non-Javadoc) * @see org.eclipse.ui.part.EditorPart#doSaveAs() */ @Override public void doSaveAs() { } /* (non-Javadoc) * @see org.eclipse.ui.part.EditorPart#init(org.eclipse.ui.IEditorSite, org.eclipse.ui.IEditorInput) */ @Override public void init(IEditorSite site, IEditorInput input) throws PartInitException { setSite(site); setInput(input); String ns = "xspdbjbl"; // $NON-NLS-1$ if (jbl == null) { jbl = new XSPPropBeanLoader(ns); //$NON-NLS-1$ } ns = "xspdesignjbl"; // $NON-NLS-1$ xspDesignLoader = new JavaBeanLoader(ns); //$NON-NLS-1$ pfe = new PropertiesFileEditor(); dbPropInput = (FileEditorInput)input; if (dbPropInput != null) { project = getDesignerProject(); dp = (DesignerProject)Platform.getAdapterManager().getAdapter(project, DesignerProject.class); if(project != null){ try { IFile f = project.getFile(DESIGN_PATH); f.getParent().refreshLocal(IFile.DEPTH_ONE, new NullProgressMonitor()); if(!f.exists()){ f.getParent().refreshLocal(IFile.DEPTH_ONE, new NullProgressMonitor()); f.create(new ByteArrayInputStream("".getBytes()), true, new NullProgressMonitor()); } if(f.exists()){ xspDesignProps = f; xspDesignPropsBean = new XSPDesignPropsBean(dp, xspDesignProps); } } catch (CoreException e) { e.printStackTrace(); } } dbBean = new XSPPropBean(dp, getBeanLoader(), this, dbPropInput, xspDesignPropsBean); jbl.setPropFile(dbPropInput, this); props = dbBean.getXspProperties(); } // this is our parent bean, that's the classdef we start with if (dbPropClassDef == null) { try { dbPropClassDef = getBeanLoader().getClassOf(dbBean); } catch (NodeException e1) { e1.printStackTrace(); } } getSite().setSelectionProvider(this); if(dbBean != null){ //We need to recompile certain xpages when the current database's external library //dependencies change. In order to do that we need to figure out what dependencies //this database has when we open the Application Properties Editor if(props != null){ //Get the current xsp.properties String dependencies = props.getDependencies(); if(project != null){ try { //figure out what dependencies we have! project.setSessionProperty(XSPAllProperties.XSP_DEPENDENCIES_PROP_INIT, dependencies); } catch (CoreException e) { } } } } } /* (non-Javadoc) * @see org.eclipse.ui.part.EditorPart#isDirty() */ @Override public boolean isDirty() { return (pfe.isDirty() || page1.getDataNode().isModelModified() || page2.getDataNode().isModelModified() || page3.getDataNode().isModelModified()); } /* (non-Javadoc) * @see org.eclipse.ui.part.EditorPart#isSaveAsAllowed() */ @Override public boolean isSaveAsAllowed() { return false; } /* (non-Javadoc) * @see org.eclipse.ui.part.WorkbenchPart#setFocus() */ @Override public void setFocus() { if (getContainer() != null){ getContainer().setFocus(); } } @Override protected void createPages() { Composite ourContainer = this.getContainer(); if ( toolkit == null){ toolkit = new FormToolkit(ourContainer.getDisplay() ); toolkit.setBackground(ourContainer.getDisplay().getSystemColor(SWT.COLOR_LIST_BACKGROUND)); toolkit.setBorderStyle(ourContainer.getBorderWidth()); } ourContainer.addDisposeListener(new DisposeListener() { public void widgetDisposed(DisposeEvent e) { if (toolkit != null) { toolkit.dispose(); toolkit = null; } getDBPropObject().release(); } }); page1 = new XSPPage(this.getContainer(), toolkit, this); addPage(page1); setPageText(GENERAL_TAB, "General"); // $NLX-XSPParentEditor.General-1$ page1.getDataNode().setClassDef(getDBPropClassDef()); page1.setDesignPropsClassDef(getXSPDesignPropClassDef()); page1.setDesignPropsProvider(new SingleCollection(xspDesignPropsBean)); SingleCollection col = new SingleCollection(dbBean); page1.getDataNode().setDataProvider(col); page1.getDataNode().addDataNodeListener(new DataNodeAdapter() { public void onModifiedChanged(DataNode source) { firePropertyChange(IEditorPart.PROP_DIRTY); } }); page1.initProject(); page1.getDataNode().setModelModified(false); page2 = new XSPPerfPage(ourContainer, toolkit, this); page2.getDataNode().setClassDef(getDBPropClassDef()); page2.getDataNode().setDataProvider(col); page2.getDataNode().addDataNodeListener(new DataNodeAdapter() { public void onModifiedChanged(DataNode source) { firePropertyChange(IEditorPart.PROP_DIRTY); } }); page2.initProject(); page2.getDataNode().setModelModified(false); addPage(page2); setPageText(PERF_TAB, "Persistence"); // $NLX-XSPParentEditor.Persistence-1$ page3 = new XSPGenPage(ourContainer, toolkit, this); page3.getDataNode().setClassDef(getDBPropClassDef()); page3.getDataNode().setDataProvider(col); page3.getDataNode().addDataNodeListener(new DataNodeAdapter() { public void onModifiedChanged(DataNode source) { firePropertyChange(IEditorPart.PROP_DIRTY); } }); page3.initProject(); page3.getDataNode().setModelModified(false); addPage(page3); setPageText(HTML_TAB, "Page Generation"); // $NLX-XSPParentEditor.PageGeneration-1$ // allow for extensions in here // since we're about to add one, this is the index of the source tab sourcePageNum = this.getPageCount(); try { addPage(pfe, getDBPropInput()); setPageText(sourcePageNum, "Source"); // $NLX-XSPParentEditor.Source-1$ } catch (PartInitException e) { e.printStackTrace(); } setPartName(getTabLabel()); } protected String getTabLabel() { String dbName = null; if (dp != null) dbName = dp.getDatabaseTitle(); else dbName = project.getName(); String partName = StringUtil.format("{0} - {1}", getTitle(), dbName); return partName; } public DesignerProject getDominoDesignerProject() { IProject ourProject = getDesignerProject(); if (ourProject != null) { dp = DesignerResource.getDesignerProject(ourProject); return dp; } else return null; } protected IProject getDesignerProject() { if (project == null) { if (dbPropInput != null) { project = dbPropInput.getFile().getProject(); return project; } } return project; } public XSPPropBeanLoader getBeanLoader() { return jbl; } public boolean isBPromptRecompileOnExit() { return bPromptRecompileOnExit; } public void setBPromptRecompileOnExit(boolean promptRecompileOnExit) { bPromptRecompileOnExit = promptRecompileOnExit; } public FileEditorInput getDBPropInput() { return dbPropInput; } public XSPPropBean getDBPropObject() { return dbBean; } public void addSelectionChangedListener(ISelectionChangedListener arg0) { } public ISelection getSelection() { if (editorSelection == null) { editorSelection = new StructuredSelection(getDominoDesignerProject()); } return editorSelection; } public void removeSelectionChangedListener(ISelectionChangedListener arg0) { } public void setSelection(ISelection selection) { editorSelection = selection; for (Iterator<ISelectionChangedListener> listeners = selectionChangedListeners.iterator(); listeners.hasNext(); ) { ISelectionChangedListener listener = listeners.next(); listener.selectionChanged(new SelectionChangedEvent(this, selection)); } } public void setModified(boolean isDirty) { firePropertyChange(IEditorPart.PROP_DIRTY); } public IClassDef getDBPropClassDef() { if (dbPropClassDef == null) { try { if (getBeanLoader() == null) { jbl = new XSPPropBeanLoader("dbjbl"); //$NON-NLS-1$ } dbPropClassDef = getBeanLoader().getClassOf(dbBean); } catch (NodeException e) { } } return dbPropClassDef; } public IClassDef getXSPDesignPropClassDef() { if (xspDesignPropsClassDef == null) { try { xspDesignPropsClassDef = xspDesignLoader.getClassOf(xspDesignPropsBean); } catch (NodeException e) { } } return xspDesignPropsClassDef; } public PropertiesFileEditor getPropertiesEditor() { return pfe; } protected void pageChange(int newPageIndex) { super.pageChange(newPageIndex); // do this so the delete key works right!! // if switching away from the source tab, update the other page data nodes if (curPage == sourcePageNum && newPageIndex != sourcePageNum) { String docContents = pfe.getDocumentProvider().getDocument(dbPropInput).get(); Properties jProps = dbBean.getXspProperties().getPropertiesObj(); byte[] bytes; InputStream is = null; try { bytes = docContents.getBytes("8859_1"); // properties files have to have this encoding is = new ByteArrayInputStream(bytes); jProps.clear(); jProps.load(is); page1.getDataNode().notifyInvalidate(null); page2.getDataNode().notifyInvalidate(null); page3.getDataNode().notifyInvalidate(null); } catch (IOException e) { } finally { if (is != null) try { is.close(); } catch (IOException e) { e.printStackTrace(); } } } curPage = this.getActivePage(); } /* (non-Javadoc) * @see org.eclipse.ui.part.MultiPageEditorPart#dispose() */ @Override public void dispose() { jbl = null; xspDesignLoader = null; super.dispose(); } }