diff --git a/csl.api/nbproject/project.xml b/csl.api/nbproject/project.xml --- a/csl.api/nbproject/project.xml +++ b/csl.api/nbproject/project.xml @@ -196,7 +196,15 @@ 1 - 1.18 + 1.49 + + + + org.netbeans.modules.editor.settings.lib + + + + 1.49 diff --git a/editor.codetemplates/nbproject/project.xml b/editor.codetemplates/nbproject/project.xml --- a/editor.codetemplates/nbproject/project.xml +++ b/editor.codetemplates/nbproject/project.xml @@ -125,7 +125,15 @@ 1 - 1.17 + 1.49 + + + + org.netbeans.modules.editor.settings.lib + + + + 1.49 diff --git a/editor.document/nbproject/project.properties b/editor.document/nbproject/project.properties --- a/editor.document/nbproject/project.properties +++ b/editor.document/nbproject/project.properties @@ -2,3 +2,4 @@ javac.compilerargs=-Xlint -Xlint:-serial spec.version.base=1.3.0 javadoc.arch=${basedir}/arch.xml +is.autoload=true diff --git a/editor.fold.nbui/nbproject/project.xml b/editor.fold.nbui/nbproject/project.xml --- a/editor.fold.nbui/nbproject/project.xml +++ b/editor.fold.nbui/nbproject/project.xml @@ -64,7 +64,15 @@ 1 - 1.39 + 1.49 + + + + org.netbeans.modules.editor.settings.lib + + + + 1.49 diff --git a/editor.fold/nbproject/project.xml b/editor.fold/nbproject/project.xml --- a/editor.fold/nbproject/project.xml +++ b/editor.fold/nbproject/project.xml @@ -85,11 +85,10 @@ - org.netbeans.modules.editor.settings.storage + org.netbeans.modules.editor.settings.lib - 1 1.39 diff --git a/editor.indent.project/nbproject/project.xml b/editor.indent.project/nbproject/project.xml --- a/editor.indent.project/nbproject/project.xml +++ b/editor.indent.project/nbproject/project.xml @@ -47,7 +47,15 @@ 1 - 1.24 + 1.49 + + + + org.netbeans.modules.editor.settings.lib + + + + 1.49 diff --git a/editor.macros/nbproject/project.xml b/editor.macros/nbproject/project.xml --- a/editor.macros/nbproject/project.xml +++ b/editor.macros/nbproject/project.xml @@ -47,7 +47,15 @@ 1 - 1.17 + 1.49 + + + + org.netbeans.modules.editor.settings.lib + + + + 1.49 diff --git a/editor.mimelookup.impl/manifest.mf b/editor.mimelookup.impl/manifest.mf --- a/editor.mimelookup.impl/manifest.mf +++ b/editor.mimelookup.impl/manifest.mf @@ -2,4 +2,4 @@ OpenIDE-Module: org.netbeans.modules.editor.mimelookup.impl/1 OpenIDE-Module-Localizing-Bundle: org/netbeans/modules/editor/mimelookup/impl/Bundle.properties OpenIDE-Module-Provides: org.netbeans.spi.editor.mimelookup.MimeDataProvider -OpenIDE-Module-Specification-Version: 1.29 +OpenIDE-Module-Specification-Version: 1.30 diff --git a/editor.mimelookup.impl/nbproject/project.xml b/editor.mimelookup.impl/nbproject/project.xml --- a/editor.mimelookup.impl/nbproject/project.xml +++ b/editor.mimelookup.impl/nbproject/project.xml @@ -67,14 +67,6 @@ - org.openide.util.ui - - - - 9.3 - - - org.openide.util @@ -87,7 +79,7 @@ - 8.0 + 8.31 diff --git a/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/CompoundFolderChildren.java b/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/CompoundFolderChildren.java --- a/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/CompoundFolderChildren.java +++ b/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/CompoundFolderChildren.java @@ -116,7 +116,8 @@ List folders = new ArrayList(prefixes.size()); List layers = new ArrayList(prefixes.size()); for (final String prefix : prefixes) { - FileObject layer = FileUtil.getConfigFile(prefix); + // use system-wide configuration, ignore execution-local specifics + FileObject layer = FileUtil.getSystemConfigFile(prefix); if (layer != null && layer.isFolder()) { folders.add(layer); try { diff --git a/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/FolderPathLookup.java b/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/FolderPathLookup.java --- a/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/FolderPathLookup.java +++ b/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/FolderPathLookup.java @@ -48,7 +48,10 @@ import java.beans.PropertyChangeListener; import java.lang.ref.Reference; import java.lang.ref.WeakReference; +import java.lang.reflect.Constructor; +import java.lang.reflect.InvocationTargetException; import java.util.ArrayList; +import java.util.Collection; import java.util.Collections; import java.util.Enumeration; import java.util.HashMap; @@ -58,12 +61,13 @@ import java.util.logging.Logger; import org.openide.filesystems.FileObject; import org.openide.filesystems.FileStateInvalidException; +import org.openide.filesystems.spi.CustomInstanceFactory; +import org.openide.util.BaseUtilities; import org.openide.util.Exceptions; import org.openide.util.Lookup; -import org.openide.util.SharedClassObject; -import org.openide.util.Utilities; import org.openide.util.lookup.AbstractLookup; import org.openide.util.lookup.InstanceContent; +import org.openide.util.lookup.Lookups; /** * @@ -205,6 +209,39 @@ } + private static volatile Lookup.Result factories; + + private static Collection getInstanceFactories() { + Lookup.Result v = factories; + if (v != null) { + return v.allInstances(); + } + final Lookup.Result fr[] = new Lookup.Result[1]; + // ensure the system - global Lookup is used + Lookups.executeWith(null, new Runnable() { + public void run() { + fr[0] = factories = Lookup.getDefault().lookupResult(CustomInstanceFactory.class); + } + }); + return fr[0].allInstances(); + } + + public static final T createInstance(Class type) throws InstantiationException, + IllegalAccessException, InvocationTargetException, NoSuchMethodException { + T r = null; + for (CustomInstanceFactory fif : getInstanceFactories()) { + r = (T)fif.createInstance(type); + if (r != null) { + break; + } + } + if (r == null) { + Constructor init = type.getDeclaredConstructor(); + init.setAccessible(true); + r = init.newInstance(); + } + return r; + } /** * Item referencing a file object and object instance that was created from it. @@ -342,14 +379,8 @@ if (type == null) { return null; } - if (SharedClassObject.class.isAssignableFrom(type)) { - inst = SharedClassObject.findObject(type.asSubclass(SharedClassObject.class), true); - } else { - inst = type.newInstance(); - } - } catch (InstantiationException ex) { - Exceptions.printStackTrace(ex); - } catch (IllegalAccessException ex) { + inst = createInstance(type); + } catch (InstantiationException | IllegalAccessException | InvocationTargetException | NoSuchMethodException ex) { Exceptions.printStackTrace(ex); } } @@ -373,7 +404,7 @@ // first of all try "instanceClass" property of the primary file Object attr = fo.getAttribute ("instanceClass"); if (attr instanceof String) { - return Utilities.translate((String) attr); + return BaseUtilities.translate((String) attr); } else if (attr != null) { LOG.warning( "instanceClass was a " + attr.getClass().getName()); // NOI18N @@ -411,7 +442,7 @@ } name = name.replace ('-', '.'); - name = Utilities.translate(name); + name = BaseUtilities.translate(name); return name; } @@ -423,7 +454,7 @@ private final class Ref extends WeakReference implements Runnable { Ref(Object inst) { - super(inst, Utilities.activeReferenceQueue()); + super(inst, BaseUtilities.activeReferenceQueue()); } @Override diff --git a/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/SwitchLookup.java b/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/SwitchLookup.java --- a/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/SwitchLookup.java +++ b/editor.mimelookup.impl/src/org/netbeans/modules/editor/mimelookup/impl/SwitchLookup.java @@ -57,7 +57,6 @@ import org.netbeans.spi.editor.mimelookup.MimeLocation; import org.openide.util.Exceptions; import org.openide.util.Lookup; -import org.openide.util.lookup.ProxyLookup; /** * @@ -73,7 +72,7 @@ private final String LOCK = new String("SwitchLookup.LOCK"); //NOI18N - private Map,UpdatableProxyLookup> classLookups = new HashMap, UpdatableProxyLookup>(); + private Map,Lookup> classLookups = new HashMap, Lookup>(); private Map,Lookup> pathsLookups = new HashMap,Lookup>(); public SwitchLookup(MimePath mimePath) { @@ -92,15 +91,12 @@ private Lookup findLookup(Class clazz) { synchronized (LOCK) { - UpdatableProxyLookup lookup = classLookups.get(clazz); + Lookup lookup = classLookups.get(clazz); if (lookup == null) { // Create lookup - Lookup innerLookup = createLookup(clazz); - lookup = new UpdatableProxyLookup(innerLookup); - + lookup = createLookup(clazz); classLookups.put(clazz, lookup); } - return lookup; } } @@ -192,22 +188,4 @@ return Collections.singletonList(sb.toString()); } - /** - * An ordinary ProxyLookup except that it exposes the - * setLookupEx method. - */ - private static final class UpdatableProxyLookup extends ProxyLookup { - public UpdatableProxyLookup() { - super(); - } - - public UpdatableProxyLookup(Lookup... lookups) { - super(lookups); - } - - public void setLookupsEx(Lookup... lookups) { - setLookups(lookups); - } - } // End of UpdatableProxyLookup class - } diff --git a/editor.mimelookup/nbproject/project.xml b/editor.mimelookup/nbproject/project.xml --- a/editor.mimelookup/nbproject/project.xml +++ b/editor.mimelookup/nbproject/project.xml @@ -58,14 +58,6 @@ - org.openide.util.ui - - - - 9.3 - - - org.openide.util diff --git a/editor.mimelookup/src/org/netbeans/api/editor/mimelookup/MimeLookup.java b/editor.mimelookup/src/org/netbeans/api/editor/mimelookup/MimeLookup.java --- a/editor.mimelookup/src/org/netbeans/api/editor/mimelookup/MimeLookup.java +++ b/editor.mimelookup/src/org/netbeans/api/editor/mimelookup/MimeLookup.java @@ -96,7 +96,9 @@ */ public final class MimeLookup extends Lookup { - private MimePathLookup mimePathLookup; + private Lookup mimePathLookup; + + private final MimePath mimePath; /** * Gets a Lookup implementation that exposes objects specific @@ -145,8 +147,8 @@ if (mimeType == null) { throw new NullPointerException("The mimeType parameter must not be null."); //NOI18N } - - return new MimeLookup(MimePath.get(mimeType).getLookup()); + MimePath path = MimePath.get(mimeType); + return new MimeLookup(path, MimePath.get(mimeType).getLookup()); } /** @@ -156,8 +158,9 @@ * the root MimeLookup * @param mimeType non-null mime-type string representation, e.g. "text/x-java" */ - private MimeLookup(MimePathLookup lookup) { + private MimeLookup(MimePath path, Lookup lookup) { this.mimePathLookup = lookup; + this.mimePath = path; } /** @@ -177,8 +180,8 @@ throw new NullPointerException("The mimeType parameter must not be null."); //NOI18N } - MimePath mimePath = MimePath.get(mimePathLookup.getMimePath(), mimeType); - return new MimeLookup(mimePath.getLookup()); + MimePath newPath = MimePath.get(mimePath, mimeType); + return new MimeLookup(newPath, newPath.getLookup()); } /** diff --git a/editor.mimelookup/src/org/netbeans/api/editor/mimelookup/MimePath.java b/editor.mimelookup/src/org/netbeans/api/editor/mimelookup/MimePath.java --- a/editor.mimelookup/src/org/netbeans/api/editor/mimelookup/MimePath.java +++ b/editor.mimelookup/src/org/netbeans/api/editor/mimelookup/MimePath.java @@ -55,7 +55,11 @@ import java.util.Map; import java.util.Set; import java.util.regex.Pattern; +import org.netbeans.modules.editor.mimelookup.APIAccessor; +import org.netbeans.modules.editor.mimelookup.MimeLookupCacheSPI; import org.netbeans.modules.editor.mimelookup.MimePathLookup; +import org.openide.util.Lookup; +import org.openide.util.lookup.Lookups; /** * The mime path is a concatenation of one or more mime types. The purpose of @@ -328,7 +332,7 @@ /** * The lookup with objects registered for this mime path. */ - private MimePathLookup lookup; + private Lookup lookup; /** * Synchronization lock for creation of the mime path lookup. @@ -505,14 +509,30 @@ * * @return The mime path specific lookup. */ - /* package */ MimePathLookup getLookup() { + /* package */ Lookup getLookup() { + return Lookup.getDefault().lookup(MimeLookupCacheSPI.class).getLookup(this); + } + + private Lookup getLookupImpl() { synchronized (LOOKUP_LOCK) { if (lookup == null) { - lookup = new MimePathLookup(this); + lookup = new MimePathLookup(this); } return lookup; } } + + private static final Lookup systemLookup; + + static { + final Lookup[] lkp = new Lookup[1]; + Lookups.executeWith(null, new Runnable() { + public void run() { + lkp[0] = Lookup.getDefault(); + } + }); + systemLookup = lkp[0]; + } public @Override String toString() { return "MimePath[" + path + "]"; // NOI18N @@ -704,4 +724,14 @@ return array; } + private static class AccessorImpl extends APIAccessor { + @Override + public Lookup cacheMimeLookup(MimePath path) { + return path.getLookupImpl(); + } + } + + static { + new AccessorImpl(); + } } diff --git a/editor.mimelookup/src/org/netbeans/modules/editor/mimelookup/APIAccessor.java b/editor.mimelookup/src/org/netbeans/modules/editor/mimelookup/APIAccessor.java new file mode 100644 --- /dev/null +++ b/editor.mimelookup/src/org/netbeans/modules/editor/mimelookup/APIAccessor.java @@ -0,0 +1,67 @@ +/* + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. + * + * Copyright 2015 Oracle and/or its affiliates. All rights reserved. + * + * Oracle and Java are registered trademarks of Oracle and/or its affiliates. + * Other names may be trademarks of their respective owners. + * + * The contents of this file are subject to the terms of either the GNU + * General Public License Version 2 only ("GPL") or the Common + * Development and Distribution License("CDDL") (collectively, the + * "License"). You may not use this file except in compliance with the + * License. You can obtain a copy of the License at + * http://www.netbeans.org/cddl-gplv2.html + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the + * specific language governing permissions and limitations under the + * License. When distributing the software, include this License Header + * Notice in each file and include the License file at + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the GPL Version 2 section of the License file that + * accompanied this code. If applicable, add the following below the + * License Header, with the fields enclosed by brackets [] replaced by + * your own identifying information: + * "Portions Copyrighted [year] [name of copyright owner]" + * + * If you wish your version of this file to be governed by only the CDDL + * or only the GPL Version 2, indicate your decision by adding + * "[Contributor] elects to include this software in this distribution + * under the [CDDL or GPL Version 2] license." If you do not indicate a + * single choice of license, a recipient has the option to distribute + * your version of this file under either the CDDL, the GPL Version 2 or + * to extend the choice of license to its licensees as provided above. + * However, if you add GPL Version 2 code and therefore, elected the GPL + * Version 2 license, then the option applies only if the new code is + * made subject to such option by the copyright holder. + * + * Contributor(s): + * + * Portions Copyrighted 2015 Sun Microsystems, Inc. + */ +package org.netbeans.modules.editor.mimelookup; + +import org.netbeans.api.editor.mimelookup.MimePath; +import org.openide.util.Lookup; + +/** + * + * @author sdedic + */ +public abstract class APIAccessor { + private static APIAccessor INSTANCE; + + @SuppressWarnings("LeakingThisInConstructor") + protected APIAccessor() { + if (INSTANCE != null) { + throw new IllegalStateException(); + } + INSTANCE = this; + } + + public static APIAccessor get() { + return INSTANCE; + } + + public abstract Lookup cacheMimeLookup(MimePath path); +} diff --git a/editor.mimelookup/src/org/netbeans/modules/editor/mimelookup/MimeLookupCacheSPI.java b/editor.mimelookup/src/org/netbeans/modules/editor/mimelookup/MimeLookupCacheSPI.java new file mode 100644 --- /dev/null +++ b/editor.mimelookup/src/org/netbeans/modules/editor/mimelookup/MimeLookupCacheSPI.java @@ -0,0 +1,67 @@ +/* + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. + * + * Copyright 2015 Oracle and/or its affiliates. All rights reserved. + * + * Oracle and Java are registered trademarks of Oracle and/or its affiliates. + * Other names may be trademarks of their respective owners. + * + * The contents of this file are subject to the terms of either the GNU + * General Public License Version 2 only ("GPL") or the Common + * Development and Distribution License("CDDL") (collectively, the + * "License"). You may not use this file except in compliance with the + * License. You can obtain a copy of the License at + * http://www.netbeans.org/cddl-gplv2.html + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the + * specific language governing permissions and limitations under the + * License. When distributing the software, include this License Header + * Notice in each file and include the License file at + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the GPL Version 2 section of the License file that + * accompanied this code. If applicable, add the following below the + * License Header, with the fields enclosed by brackets [] replaced by + * your own identifying information: + * "Portions Copyrighted [year] [name of copyright owner]" + * + * If you wish your version of this file to be governed by only the CDDL + * or only the GPL Version 2, indicate your decision by adding + * "[Contributor] elects to include this software in this distribution + * under the [CDDL or GPL Version 2] license." If you do not indicate a + * single choice of license, a recipient has the option to distribute + * your version of this file under either the CDDL, the GPL Version 2 or + * to extend the choice of license to its licensees as provided above. + * However, if you add GPL Version 2 code and therefore, elected the GPL + * Version 2 license, then the option applies only if the new code is + * made subject to such option by the copyright holder. + * + * Contributor(s): + * + * Portions Copyrighted 2015 Sun Microsystems, Inc. + */ +package org.netbeans.modules.editor.mimelookup; + +import org.netbeans.api.editor.mimelookup.MimePath; +import org.openide.util.Lookup; + +/** + * Caching of MimeLookups. Since MimePath is a global object, it cannot cache potentially + * execution-specific data, such as the concrete MimeLookup. Instead, the MimePath looks up + * the intrinsic data in the cache, which can be potentially execution-specific. + *

+ * MimePath obtains the MimeLookupCacheSPI from the default Lookup supposing that if some + * local execution context is active, the infrastructure placed a separate MimeLookupCacheSPI + * implementation into it. + *

+ * @author sdedic + */ +public abstract class MimeLookupCacheSPI { + /** + * Obtains a MIME-specific Lookup from the cache. If the Lookup does not exist, + * it is created. The cache implementor is responsible for synchronization, only one + * Lookup instance can be returned from the cache for the given execution context and MimePath. + * @param mp MimePath to select the Lookup contents + * @return Lookup instance + */ + public abstract Lookup getLookup(MimePath mp); +} diff --git a/editor.mimelookup/src/org/netbeans/modules/editor/mimelookup/SharedMimeLookupCache.java b/editor.mimelookup/src/org/netbeans/modules/editor/mimelookup/SharedMimeLookupCache.java new file mode 100644 --- /dev/null +++ b/editor.mimelookup/src/org/netbeans/modules/editor/mimelookup/SharedMimeLookupCache.java @@ -0,0 +1,64 @@ +/* + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. + * + * Copyright 2015 Oracle and/or its affiliates. All rights reserved. + * + * Oracle and Java are registered trademarks of Oracle and/or its affiliates. + * Other names may be trademarks of their respective owners. + * + * The contents of this file are subject to the terms of either the GNU + * General Public License Version 2 only ("GPL") or the Common + * Development and Distribution License("CDDL") (collectively, the + * "License"). You may not use this file except in compliance with the + * License. You can obtain a copy of the License at + * http://www.netbeans.org/cddl-gplv2.html + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the + * specific language governing permissions and limitations under the + * License. When distributing the software, include this License Header + * Notice in each file and include the License file at + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the GPL Version 2 section of the License file that + * accompanied this code. If applicable, add the following below the + * License Header, with the fields enclosed by brackets [] replaced by + * your own identifying information: + * "Portions Copyrighted [year] [name of copyright owner]" + * + * If you wish your version of this file to be governed by only the CDDL + * or only the GPL Version 2, indicate your decision by adding + * "[Contributor] elects to include this software in this distribution + * under the [CDDL or GPL Version 2] license." If you do not indicate a + * single choice of license, a recipient has the option to distribute + * your version of this file under either the CDDL, the GPL Version 2 or + * to extend the choice of license to its licensees as provided above. + * However, if you add GPL Version 2 code and therefore, elected the GPL + * Version 2 license, then the option applies only if the new code is + * made subject to such option by the copyright holder. + * + * Contributor(s): + * + * Portions Copyrighted 2015 Sun Microsystems, Inc. + */ +package org.netbeans.modules.editor.mimelookup; + +import org.netbeans.api.editor.mimelookup.MimePath; +import org.openide.util.Lookup; +import org.openide.util.lookup.ServiceProvider; + +/** + * The default cache for MIME Lookups for single-context environment. + * This defaut implementation caches MimeLookup directly in MimePath field + * so Lookup contents live at least as long as the reference to the MimePath, + * but are not prevented from GC after the MimePath is released. + * + * @author sdedic + */ +@ServiceProvider(service = MimeLookupCacheSPI.class) +public final class SharedMimeLookupCache extends MimeLookupCacheSPI { + + @Override + public synchronized Lookup getLookup(MimePath mp) { + return APIAccessor.get().cacheMimeLookup(mp); + } + +} diff --git a/editor.settings.lib/build.xml b/editor.settings.lib/build.xml new file mode 100644 --- /dev/null +++ b/editor.settings.lib/build.xml @@ -0,0 +1,5 @@ + + + Builds, tests, and runs the project org.netbeans.modules.editor.settings.lib + + diff --git a/editor.settings.lib/manifest.mf b/editor.settings.lib/manifest.mf new file mode 100644 --- /dev/null +++ b/editor.settings.lib/manifest.mf @@ -0,0 +1,6 @@ +Manifest-Version: 1.0 +AutoUpdate-Show-In-Client: false +OpenIDE-Module: org.netbeans.modules.editor.settings.lib +OpenIDE-Module-Localizing-Bundle: org/netbeans/modules/editor/settings/lib/Bundle.properties +OpenIDE-Module-Implementation-Version: 1 + diff --git a/editor.settings.lib/nbproject/project.properties b/editor.settings.lib/nbproject/project.properties new file mode 100644 --- /dev/null +++ b/editor.settings.lib/nbproject/project.properties @@ -0,0 +1,3 @@ +javac.source=1.7 +javac.compilerargs=-Xlint -Xlint:-serial +spec.version.base=1.49.0 diff --git a/editor.settings.lib/nbproject/project.xml b/editor.settings.lib/nbproject/project.xml new file mode 100644 --- /dev/null +++ b/editor.settings.lib/nbproject/project.xml @@ -0,0 +1,112 @@ + + + org.netbeans.modules.apisupport.project + + + org.netbeans.modules.editor.settings.lib + + + org.netbeans.modules.editor.mimelookup + + + + 1 + 1.38 + + + + org.netbeans.modules.editor.util + + + + 1 + 1.60 + + + + org.openide.filesystems + + + + 9.5 + + + + org.openide.util + + + + 9.3 + + + + org.openide.util.lookup + + + + 8.30 + + + + + + unit + + org.netbeans.bootstrap + + + org.netbeans.core + + + org.netbeans.core.startup + + + + + org.netbeans.libs.junit4 + + + + org.netbeans.modules.editor.mimelookup.impl + + + org.netbeans.modules.editor.settings.storage + + + + + org.netbeans.modules.nbjunit + + + + + org.openide.awt + + + + org.openide.dialogs + + + + org.openide.loaders + + + + org.openide.modules + + + org.openide.nodes + + + + org.openide.text + + + + + org.netbeans.modules.editor.settings.storage.api + org.netbeans.modules.editor.settings.storage.spi + + + + diff --git a/editor.settings.lib/src/org/netbeans/modules/editor/settings/lib/Bundle.properties b/editor.settings.lib/src/org/netbeans/modules/editor/settings/lib/Bundle.properties new file mode 100644 --- /dev/null +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/lib/Bundle.properties @@ -0,0 +1,1 @@ +OpenIDE-Module-Name=Editor Settings Library diff --git a/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/ApiAccessor.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/ApiAccessor.java new file mode 100644 --- /dev/null +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/ApiAccessor.java @@ -0,0 +1,64 @@ +/* + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. + * + * Copyright 2015 Oracle and/or its affiliates. All rights reserved. + * + * Oracle and Java are registered trademarks of Oracle and/or its affiliates. + * Other names may be trademarks of their respective owners. + * + * The contents of this file are subject to the terms of either the GNU + * General Public License Version 2 only ("GPL") or the Common + * Development and Distribution License("CDDL") (collectively, the + * "License"). You may not use this file except in compliance with the + * License. You can obtain a copy of the License at + * http://www.netbeans.org/cddl-gplv2.html + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the + * specific language governing permissions and limitations under the + * License. When distributing the software, include this License Header + * Notice in each file and include the License file at + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the GPL Version 2 section of the License file that + * accompanied this code. If applicable, add the following below the + * License Header, with the fields enclosed by brackets [] replaced by + * your own identifying information: + * "Portions Copyrighted [year] [name of copyright owner]" + * + * If you wish your version of this file to be governed by only the CDDL + * or only the GPL Version 2, indicate your decision by adding + * "[Contributor] elects to include this software in this distribution + * under the [CDDL or GPL Version 2] license." If you do not indicate a + * single choice of license, a recipient has the option to distribute + * your version of this file under either the CDDL, the GPL Version 2 or + * to extend the choice of license to its licensees as provided above. + * However, if you add GPL Version 2 code and therefore, elected the GPL + * Version 2 license, then the option applies only if the new code is + * made subject to such option by the copyright holder. + * + * Contributor(s): + * + * Portions Copyrighted 2015 Sun Microsystems, Inc. + */ +package org.netbeans.modules.editor.settings.storage; + +import org.netbeans.modules.editor.settings.storage.api.EditorSettingsStorage; +import org.netbeans.modules.editor.settings.storage.spi.StorageDescription; + +/** + * + * @author sdedic + */ +public abstract class ApiAccessor { + private static volatile ApiAccessor INSTANCE; + + public static synchronized void register(ApiAccessor inst) { + assert INSTANCE == null; + INSTANCE = inst; + } + + static ApiAccessor get() { + return INSTANCE; + } + + public abstract EditorSettingsStorage createSettingsStorage(StorageDescription storageDescription); +} diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/Bundle.properties b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/Bundle.properties copy from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/Bundle.properties copy to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/Bundle.properties --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/Bundle.properties +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/Bundle.properties @@ -40,12 +40,5 @@ # Version 2 license, then the option applies only if the new code is # made subject to such option by the copyright holder. -OpenIDE-Module-Name=Editor Settings Storage -OpenIDE-Module-Display-Category=Editing -OpenIDE-Module-Short-Description=Implements NetBeans editor settings storage -OpenIDE-Module-Long-Description=Implements storage for NetBeans editor settings and \ - defines the structure of editor setting files. It also provides friend API for \ - modules that need read/write access to the storage. - # MIMEResolver EditorResolver=NetBeans Editor Settings Files diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/SettingsType.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/SettingsType.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/SettingsType.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/SettingsType.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/SettingsType.java +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/SettingsType.java @@ -60,8 +60,6 @@ import java.util.Map; import java.util.logging.Level; import java.util.logging.Logger; -import org.netbeans.modules.editor.settings.storage.fontscolors.ColoringStorage; -import org.netbeans.modules.editor.settings.storage.keybindings.KeyMapsStorage; import org.netbeans.modules.editor.settings.storage.preferences.PreferencesStorage; import org.netbeans.modules.editor.settings.storage.spi.StorageDescription; import org.openide.filesystems.FileObject; @@ -70,7 +68,7 @@ import org.openide.util.Lookup; import org.openide.util.LookupEvent; import org.openide.util.LookupListener; -import org.openide.util.Utilities; +import org.openide.util.BaseUtilities; import org.openide.util.WeakListeners; /** @@ -90,17 +88,17 @@ public static Locator getLocator(StorageDescription sd) { assert sd != null : "The parameter sd can't be null"; //NOI18N - Locator locator; - - if (ColoringStorage.ID.equals(sd.getId())) { - locator = new FontsColorsLocator(sd.getId(), sd.isUsingProfiles(), sd.getMimeType(), sd.getLegacyFileName()); - } else if (KeyMapsStorage.ID.equals(sd.getId()) || PreferencesStorage.ID.equals(sd.getId())) { - locator = new LegacyTextBaseLocator(sd.getId(), sd.isUsingProfiles(), sd.getMimeType(), sd.getLegacyFileName()); - } else { - locator = new DefaultLocator(sd.getId(), sd.isUsingProfiles(), sd.getMimeType(), sd.getLegacyFileName()); + Collection locators = Lookup.getDefault().lookupAll(LocatorFactory.class); + for (LocatorFactory f : locators) { + Locator l = f.createLocator(sd); + if (l != null) { + return l; + } } - - return locator; + if (PreferencesStorage.ID.equals(sd.getId())) { + return new PreferencesLocator(sd.getId(), sd.isUsingProfiles(), sd.getMimeType(), sd.getLegacyFileName()); + } + return new DefaultLocator(sd.getId(), sd.isUsingProfiles(), sd.getMimeType(), sd.getLegacyFileName()); } public static interface Locator { @@ -109,6 +107,10 @@ public boolean isUsingProfiles(); } + public static interface LocatorFactory { + public Locator createLocator(StorageDescription sd); + } + // ------------------------------------------------------------------ // private implementation // ------------------------------------------------------------------ @@ -183,10 +185,10 @@ // Locators // ------------------------------------------------------------------ - private static class DefaultLocator implements Locator { + public static class DefaultLocator implements Locator { protected static final String MODULE_FILES_FOLDER = "Defaults"; //NOI18N - protected static final String DEFAULT_PROFILE_NAME = EditorSettingsImpl.DEFAULT_PROFILE; + protected static final String DEFAULT_PROFILE_NAME = Utils.DEFAULT_PROFILE; private static final String WRITABLE_FILE_PREFIX = "org-netbeans-modules-editor-settings-Custom"; //NOI18N private static final String WRITABLE_FILE_SUFFIX = ".xml"; //NOI18N @@ -316,7 +318,7 @@ } } - private FileObject getMimeFolder(FileObject baseFolder, String mimeType) { + protected FileObject getMimeFolder(FileObject baseFolder, String mimeType) { return mimeType == null ? baseFolder : baseFolder.getFileObject(mimeType); } @@ -460,9 +462,10 @@ if (targetOs instanceof Boolean) { return ((Boolean) targetOs).booleanValue(); } else if (targetOs instanceof String) { - Field field = Utilities.class.getDeclaredField((String) targetOs); + // XXX FIXME - reflective access to Utilities + Field field = BaseUtilities.class.getDeclaredField((String) targetOs); int targetOsMask = field.getInt(null); - int currentOsId = Utilities.getOperatingSystem(); + int currentOsId = BaseUtilities.getOperatingSystem(); return (currentOsId & targetOsMask) != 0; } else { return false; @@ -607,106 +610,17 @@ } } } // End of DefaultLocator class - - private static final class FontsColorsLocator extends DefaultLocator { + + private static final class PreferencesLocator extends DefaultLocator { - private static final String [] M_LEGACY_FILE_NAMES = new String [] { - MODULE_FILES_FOLDER + "/defaultColoring.xml", // NOI18N - MODULE_FILES_FOLDER + "/coloring.xml", // NOI18N - MODULE_FILES_FOLDER + "/editorColoring.xml", // NOI18N - }; - - private static final String [] U_LEGACY_FILE_NAMES = new String [] { - "defaultColoring.xml", // NOI18N - "coloring.xml", // NOI18N - "editorColoring.xml", // NOI18N - }; - - public FontsColorsLocator(String settingTypeId, boolean hasProfiles, String mimeType, String legacyFileName) { - super(settingTypeId, hasProfiles, mimeType, legacyFileName); - } - - @Override - protected void addModulesLegacyFiles( - FileObject mimeFolder, - String profileId, - boolean fullScan, - Map> files - ) { - addFiles(mimeFolder, profileId, fullScan, M_LEGACY_FILE_NAMES, files, true); - } - - @Override - protected void addUsersLegacyFiles( - FileObject mimeFolder, - String profileId, - boolean fullScan, - Map> files - ) { - addFiles(mimeFolder, profileId, fullScan, U_LEGACY_FILE_NAMES, files, false); - } - - private void addFiles( - FileObject mimeFolder, - String profileId, - boolean fullScan, - String [] filePaths, - Map> files, - boolean moduleFiles - ) { - if (profileId == null) { - FileObject [] profileHomes = mimeFolder.getChildren(); - for(FileObject f : profileHomes) { - if (!f.isFolder()) { - continue; - } - - String id = f.getNameExt(); - addFiles(f, filePaths, fullScan, files, id, f, moduleFiles); //NOI18N - } - } else { - FileObject profileHome = mimeFolder.getFileObject(profileId); - if (profileHome != null && profileHome.isFolder()) { - addFiles(profileHome, filePaths, fullScan, files, profileId, profileHome, moduleFiles); - } - } - } - - private void addFiles(FileObject folder, String [] filePaths, boolean fullScan, Map> files, String profileId, FileObject profileHome, boolean moduleFiles) { - for(String filePath : filePaths) { - FileObject f = folder.getFileObject(filePath); - if (f != null) { - List pair = files.get(profileId); - if (pair == null) { - pair = new ArrayList(); - files.put(profileId, pair); - } - pair.add(new Object [] { profileHome, f, moduleFiles, null, true }); - - if (LOG.isLoggable(Level.INFO)) { - Utils.logOnce(LOG, Level.INFO, settingTypeId + " settings " + //NOI18N - "should reside in '" + settingTypeId + "' subfolder, " + //NOI18N - "see #90403 for details. Offending file '" + f.getPath() + "'", null); //NOI18N - } - - if (!fullScan) { - break; - } - } - } - } - } // End of FontsColorsLocator class - - private static final class LegacyTextBaseLocator extends DefaultLocator { - - public LegacyTextBaseLocator(String settingTypeId, boolean hasProfiles, String mimeType, String legacyFileName) { + public PreferencesLocator(String settingTypeId, boolean hasProfiles, String mimeType, String legacyFileName) { super(settingTypeId, hasProfiles, mimeType, legacyFileName); } @Override protected FileObject getLegacyMimeFolder(FileObject baseFolder, String mimeType) { if (mimeType == null || mimeType.length() == 0) { - return baseFolder.getFileObject(EditorSettingsImpl.TEXT_BASE_MIME_TYPE); + return baseFolder.getFileObject(Utils.TEXT_BASE_MIME_TYPE); } else { return super.getMimeFolder(baseFolder, mimeType); } diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/SpiPackageAccessor.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/SpiPackageAccessor.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/SpiPackageAccessor.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/SpiPackageAccessor.java diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/StorageImpl.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/StorageImpl.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/StorageImpl.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/StorageImpl.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/StorageImpl.java +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/StorageImpl.java @@ -61,6 +61,7 @@ import java.util.logging.Logger; import java.util.regex.Pattern; import org.netbeans.api.editor.mimelookup.MimePath; +import org.netbeans.modules.editor.settings.storage.api.EditorSettingsStorage; import org.netbeans.modules.editor.settings.storage.spi.StorageDescription; import org.netbeans.modules.editor.settings.storage.spi.StorageFilter; import org.netbeans.modules.editor.settings.storage.spi.StorageReader; @@ -78,6 +79,7 @@ import org.openide.util.LookupListener; import org.openide.util.RequestProcessor; import org.openide.util.WeakListeners; +import org.openide.util.lookup.ServiceProvider; /** * @@ -748,6 +750,39 @@ + ", path=" + event.getFile().getPath(); //NOI18N } } // End of FilesystemTracker class + + /** + * Caching provider. Storage cache cannot be held in static variable, as they initialize + * with per-execution data. + */ + public static interface StorageCache { + public EditorSettingsStorage createStorage(StorageDescription desc); + } + + /** + * Caching for individual EditorSettingStorages. Originally the cache was implemented in + * a static variable, but we need to cache the storage for each execution/user separately. + */ + @ServiceProvider(service = StorageImpl.StorageCache.class) + public static final class StorageCacheImpl implements StorageImpl.StorageCache { + private final Map, EditorSettingsStorage> cache = new HashMap<>(); + @Override + public EditorSettingsStorage createStorage(StorageDescription sd) { + synchronized (cache) { + EditorSettingsStorage ess = null; + if (sd != null) { + ess = cache.get(sd); + if (ess == null) { + ess = ApiAccessor.get().createSettingsStorage(sd); + cache.put(sd, ess); + } + } + + return ess; + } + } + + } } diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/Utils.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/Utils.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/Utils.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/Utils.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/Utils.java +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/Utils.java @@ -44,39 +44,28 @@ package org.netbeans.modules.editor.settings.storage; -import java.io.ByteArrayInputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; -import java.util.ArrayList; -import java.util.Collection; import java.util.Collections; -import java.util.Enumeration; -import java.util.HashMap; import java.util.HashSet; -import java.util.List; import java.util.Map; import java.util.MissingResourceException; import java.util.ResourceBundle; import java.util.Set; import java.util.logging.Level; import java.util.logging.Logger; -import javax.swing.text.AttributeSet; -import javax.swing.text.StyleConstants; import org.netbeans.api.editor.mimelookup.MimePath; -import org.netbeans.api.editor.settings.AttributesUtilities; import org.netbeans.modules.editor.settings.storage.spi.StorageReader; import org.netbeans.modules.editor.settings.storage.spi.StorageWriter; import org.openide.filesystems.FileLock; import org.openide.filesystems.FileObject; import org.openide.filesystems.FileStateInvalidException; +import org.openide.util.BaseUtilities; import org.openide.util.NbBundle; -import org.openide.util.Utilities; -import org.openide.util.lookup.ServiceProvider; import org.openide.xml.EntityCatalog; import org.openide.xml.XMLUtil; import org.xml.sax.InputSource; -import org.xml.sax.SAXException; import org.xml.sax.XMLReader; @@ -87,6 +76,10 @@ * @author Jan Jancura */ public class Utils { + /** The name of the default profile. */ + public static final String DEFAULT_PROFILE = "NetBeans"; //NOI18N + + public static final String TEXT_BASE_MIME_TYPE = "text/base"; //NOI18N private static final Logger LOG = Logger.getLogger(Utils.class.getName()); @@ -210,64 +203,12 @@ return mimePath; } - /** - * Creates unmodifiable copy of the original map converting AttributeSets - * to their immutable versions. - */ - public static Map immutize(Map map, Object... filterOutKeys) { - Map immutizedMap = new HashMap(); - - for(String name : map.keySet()) { - AttributeSet attribs = map.get(name); - - if (filterOutKeys.length == 0) { - immutizedMap.put(name, AttributesUtilities.createImmutable(attribs)); - } else { - List pairs = new ArrayList(); - - // filter out attributes specified by filterOutKeys - first: - for(Enumeration keys = attribs.getAttributeNames(); keys.hasMoreElements(); ) { - Object key = keys.nextElement(); - - for(Object filterOutKey : filterOutKeys) { - if (Utilities.compareObjects(key, filterOutKey)) { - continue first; - } - } - - pairs.add(key); - pairs.add(attribs.getAttribute(key)); - } - - immutizedMap.put(name, AttributesUtilities.createImmutable(pairs.toArray())); - } - } - - return Collections.unmodifiableMap(immutizedMap); - } - - public static Map immutize(Collection set) { - Map immutizedMap = new HashMap(); - - for(AttributeSet as : set) { - Object nameObject = as.getAttribute(StyleConstants.NameAttribute); - if (nameObject instanceof String) { - immutizedMap.put((String) nameObject, as); - } else { - LOG.warning("Ignoring AttributeSet with invalid StyleConstants.NameAttribute. AttributeSet: " + as); //NOI18N - } - } - - return Collections.unmodifiableMap(immutizedMap); - } - public static void diff(Map oldMap, Map newMap, Map addedEntries, Map removedEntries) { for(A key : oldMap.keySet()) { if (!newMap.containsKey(key)) { removedEntries.put(key, oldMap.get(key)); } else { - if (!Utilities.compareObjects(oldMap.get(key), newMap.get(key))) { + if (!BaseUtilities.compareObjects(oldMap.get(key), newMap.get(key))) { addedEntries.put(key, newMap.get(key)); } } @@ -285,7 +226,7 @@ if (!newMap.containsKey(key)) { return true; } else { - if (!Utilities.compareObjects(oldMap.get(key), newMap.get(key))) { + if (!BaseUtilities.compareObjects(oldMap.get(key), newMap.get(key))) { return true; } } @@ -342,15 +283,4 @@ LOG.log(Level.WARNING, "Invalid or corrupted file: " + fo.getPath(), ex); //NOI18N } } - - @ServiceProvider(service=EntityCatalog.class) - public static final class NoNetworkAccessEntityCatalog extends EntityCatalog { - private final boolean NO_NETWORK_ACCESS = Boolean.getBoolean("editor.storage.no.network.access"); - - @Override - public InputSource resolveEntity(String publicId, String systemId) throws SAXException, IOException { - if (!NO_NETWORK_ACCESS) return null; - return new InputSource(new ByteArrayInputStream(new byte[0])); - } - } } diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/api/EditorSettingsStorage.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/api/EditorSettingsStorage.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/api/EditorSettingsStorage.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/api/EditorSettingsStorage.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/api/EditorSettingsStorage.java +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/api/EditorSettingsStorage.java @@ -45,16 +45,17 @@ import java.beans.PropertyChangeListener; import java.beans.PropertyChangeSupport; import java.io.IOException; -import java.util.HashMap; import java.util.Map; import java.util.concurrent.Callable; import java.util.logging.Level; import java.util.logging.Logger; import javax.swing.SwingUtilities; import org.netbeans.api.editor.mimelookup.MimePath; +import org.netbeans.modules.editor.settings.storage.ApiAccessor; import org.netbeans.modules.editor.settings.storage.SettingsType; import org.netbeans.modules.editor.settings.storage.StorageImpl; import org.netbeans.modules.editor.settings.storage.spi.StorageDescription; +import org.openide.util.Lookup; import org.openide.util.RequestProcessor; /** @@ -75,20 +76,9 @@ @SuppressWarnings("unchecked") public static EditorSettingsStorage find(String settingsTypeId) { - synchronized (cache) { - EditorSettingsStorage ess = null; - StorageDescription sd = SettingsType.find(settingsTypeId); - - if (sd != null) { - ess = cache.get(sd); - if (ess == null) { - ess = new EditorSettingsStorage(sd); - cache.put(sd, ess); - } - } - - return ess; - } + StorageDescription sd = SettingsType.find(settingsTypeId); + // must not cache in a static cache, cache can be found in [contextual] Lookup. + return Lookup.getDefault().lookup(StorageImpl.StorageCache.class).createStorage(sd); } public Map load(MimePath mimePath, String profile, boolean defaults) throws IOException { @@ -128,8 +118,6 @@ // private implementation // ------------------------------------------ - private static final Map, EditorSettingsStorage> cache = new HashMap, EditorSettingsStorage>(); - private final PropertyChangeSupport PCS = new PropertyChangeSupport(this); private final StorageImpl storageImpl; @@ -141,4 +129,13 @@ } }); } + + static { + ApiAccessor.register(new ApiAccessor() { + @Override + public EditorSettingsStorage createSettingsStorage(StorageDescription storageDescription) { + return new EditorSettingsStorage<>(storageDescription); + } + }); + } } diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/api/MemoryPreferences.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/api/MemoryPreferences.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/api/MemoryPreferences.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/api/MemoryPreferences.java diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/api/OverridePreferences.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/api/OverridePreferences.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/api/OverridePreferences.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/api/OverridePreferences.java diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/mime-resolvers.xml b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/mime-resolvers.xml copy from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/mime-resolvers.xml copy to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/mime-resolvers.xml diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/EditorPreferences-1_0.dtd b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/EditorPreferences-1_0.dtd rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/EditorPreferences-1_0.dtd rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/EditorPreferences-1_0.dtd diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/EditorProperties-1_0.dtd b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/EditorProperties-1_0.dtd rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/EditorProperties-1_0.dtd rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/EditorProperties-1_0.dtd diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/InheritedPreferences.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/InheritedPreferences.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/InheritedPreferences.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/InheritedPreferences.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/InheritedPreferences.java +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/InheritedPreferences.java @@ -43,14 +43,13 @@ import java.util.Arrays; import java.util.Collection; -import java.util.Collections; import java.util.HashSet; -import java.util.Set; import java.util.prefs.AbstractPreferences; import java.util.prefs.BackingStoreException; import java.util.prefs.PreferenceChangeEvent; import java.util.prefs.PreferenceChangeListener; import java.util.prefs.Preferences; +import org.netbeans.modules.editor.settings.storage.api.MemoryPreferences; import org.netbeans.modules.editor.settings.storage.api.OverridePreferences; import org.openide.util.WeakListeners; diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesImpl.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesImpl.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesImpl.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesImpl.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesImpl.java +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesImpl.java @@ -49,7 +49,6 @@ import java.util.Arrays; import java.util.HashMap; import java.util.HashSet; -import java.util.List; import java.util.Map; import java.util.Set; import java.util.WeakHashMap; @@ -78,14 +77,8 @@ private static final String JAVATYPE_KEY_PREFIX = "nbeditor-javaType-for-legacy-setting_"; //NOI18N public static synchronized PreferencesImpl get(MimePath mimePath) { - PreferencesImpl prefs = INSTANCES.get(mimePath); - - if (prefs == null) { - prefs = new PreferencesImpl(mimePath.getPath()); - INSTANCES.put(mimePath, prefs); - } - - return prefs; + // must not access static-variable cache directly. + return (PreferencesImpl)DEFAULT_FACTORY.createPreferences(mimePath); } // --------------------------------------------------------------------- @@ -463,10 +456,15 @@ private Map local = null; private Preferences inherited = null; + private final PreferencesFactory factory; private PreferencesImpl(String mimePath) { - super(null, EMPTY); - + this(DEFAULT_FACTORY, mimePath); + } + + public PreferencesImpl(PreferencesFactory factory, String mimePath) { + super (null, EMPTY); + this.factory = factory; this.mimePath = mimePath; this.storage = EditorSettingsStorage.get(PreferencesStorage.ID); this.storage.addPropertyChangeListener(WeakListeners.propertyChange(storageTracker, this.storage)); @@ -488,9 +486,9 @@ if (inherited == null && mimePath.length() > 0) { String type = MimePath.parse(mimePath).getInheritedType(); if (type != null) { - inherited = get(MimePath.parse(type)); + inherited = factory.createPreferences(MimePath.parse(type)); } else { - inherited = get(MimePath.EMPTY); + inherited = factory.createPreferences(MimePath.EMPTY); } inherited.addPreferenceChangeListener(WeakListeners.create(PreferenceChangeListener.class, this, inherited)); @@ -531,4 +529,39 @@ assert false : "Can't fire preferenceChange event for null key or value, no enqueuePreferenceChangeEvent available"; //NOI18N } } + + /** + * The default preferences factory. To be GC-compatible with older NB versions, preferences cache + * is kept in a static variable. + */ + private static final PreferencesFactory DEFAULT_FACTORY = new PreferencesFactory() { + @Override + public Preferences createPreferences(MimePath mimePath) { + synchronized (INSTANCES) { + PreferencesImpl prefs = INSTANCES.get(mimePath); + + if (prefs == null) { + prefs = new PreferencesImpl(this, mimePath.getPath()); + INSTANCES.put(mimePath, prefs); + } + return prefs; + } + } + }; + + /** + * Provides cahce for preferences for individual MIME paths. Preferences cannot be + * cached in a static variable, since they hold per-execution data which depends + * on the Lookup contents. The default PreferencesFactory is provided in the system Lookup + * and can be overriden in a specialized local Lookup. + */ + public interface PreferencesFactory { + /** + * Creates or acquires Preferences instance for the given MIME path. + * + * @param path mime path + * @return Preferences instance. + */ + public Preferences createPreferences(MimePath path); + } } diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorage.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorage.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorage.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorage.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorage.java +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorage.java @@ -53,11 +53,11 @@ import java.util.TreeMap; import java.util.logging.Logger; import org.netbeans.lib.editor.util.CharacterConversions; +import org.netbeans.modules.editor.settings.storage.Utils; import org.netbeans.modules.editor.settings.storage.spi.StorageDescription; import org.netbeans.modules.editor.settings.storage.spi.StorageReader; import org.netbeans.modules.editor.settings.storage.spi.StorageWriter; import org.netbeans.modules.editor.settings.storage.spi.TypedValue; -import org.netbeans.modules.editor.settings.storage.spi.support.StorageSupport; import org.openide.filesystems.FileObject; import org.openide.xml.XMLUtil; import org.w3c.dom.Document; @@ -202,7 +202,7 @@ // Read the value and localize it String valueId = attributes.getValue(A_VALUE_ID); if (valueId != null) { - String localizedValue = StorageSupport.getLocalizingBundleMessage( + String localizedValue = getLocalizingBundleMessage( getProcessedFile(), valueId, null); if (localizedValue != null) { value = localizedValue; @@ -393,4 +393,9 @@ return doc; } } // End of Writer class + + public static String getLocalizingBundleMessage(FileObject fo, String key, String defaultValue) { + return Utils.getLocalizedName(fo, key, defaultValue, false); + } + } diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/ProxyPreferencesImpl.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/ProxyPreferencesImpl.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/preferences/ProxyPreferencesImpl.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/preferences/ProxyPreferencesImpl.java diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/StorageDescription.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/StorageDescription.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/StorageDescription.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/StorageDescription.java diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/StorageFilter.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/StorageFilter.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/StorageFilter.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/StorageFilter.java diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/StorageReader.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/StorageReader.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/StorageReader.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/StorageReader.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/StorageReader.java +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/StorageReader.java @@ -47,8 +47,8 @@ import java.util.concurrent.Callable; import java.util.logging.Level; import java.util.logging.Logger; -import org.netbeans.modules.editor.settings.storage.EditorSettingsImpl; import org.netbeans.modules.editor.settings.storage.SpiPackageAccessor; +import org.netbeans.modules.editor.settings.storage.Utils; import org.openide.filesystems.FileObject; import org.xml.sax.InputSource; import org.xml.sax.SAXException; @@ -82,7 +82,7 @@ moduleFile = parent.getNameExt().contains("Default"); //NOI18N parent = parent.getParent(); if (parent != null) { - defaultProfile = parent.getNameExt().contains(EditorSettingsImpl.DEFAULT_PROFILE); + defaultProfile = parent.getNameExt().contains(Utils.DEFAULT_PROFILE); } } this.isModuleFile = moduleFile; diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/StorageWriter.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/StorageWriter.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/StorageWriter.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/StorageWriter.java diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/TypedValue.java b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/TypedValue.java rename from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/TypedValue.java rename to editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/TypedValue.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/spi/TypedValue.java +++ b/editor.settings.lib/src/org/netbeans/modules/editor/settings/storage/spi/TypedValue.java @@ -42,7 +42,7 @@ package org.netbeans.modules.editor.settings.storage.spi; -import org.openide.util.Utilities; +import org.openide.util.BaseUtilities; /** * @@ -87,10 +87,10 @@ return false; } final TypedValue other = (TypedValue) obj; - if (!Utilities.compareObjects(this.value, other.value)) { + if (!BaseUtilities.compareObjects(this.value, other.value)) { return false; } - if (!Utilities.compareObjects(this.javaType, other.javaType)) { + if (!BaseUtilities.compareObjects(this.javaType, other.javaType)) { return false; } return true; diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/EditorSettingsStorageTest.java b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/EditorSettingsStorageTest.java rename from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/EditorSettingsStorageTest.java rename to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/EditorSettingsStorageTest.java diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/EditorTestLookup.java b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/EditorTestLookup.java copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/EditorTestLookup.java copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/EditorTestLookup.java diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/LocatorTest.java b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/LocatorTest.java rename from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/LocatorTest.java rename to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/LocatorTest.java diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/SettingsProviderTest.java b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/SettingsProviderTest.java rename from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/SettingsProviderTest.java rename to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/SettingsProviderTest.java diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/StorageFilterTest.java b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/StorageFilterTest.java rename from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/StorageFilterTest.java rename to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/StorageFilterTest.java diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/TestUtilities.java b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/TestUtilities.java copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/TestUtilities.java copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/TestUtilities.java diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-2.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-2.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-2.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-2.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-3.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-3.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-3.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-3.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-4.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-4.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-4.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-4.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-5.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-5.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-5.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-5.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-all-languages.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-all-languages.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-all-languages.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors-all-languages.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/fonts-and-colors.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/key-bindings.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/key-bindings.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/key-bindings.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/key-bindings.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/Bundle.properties b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/Bundle.properties copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/Bundle.properties copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/Bundle.properties diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorageTest.java b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorageTest.java copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorageTest.java copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesStorageTest.java diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesTest.java b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesTest.java copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesTest.java copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/PreferencesTest.java diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/ProxyPreferencesImplTest.java b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/ProxyPreferencesImplTest.java copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/ProxyPreferencesImplTest.java copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/ProxyPreferencesImplTest.java diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-all-languages.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-all-languages.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-all-languages.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-all-languages.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-testA-1.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-testA-1.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-testA-1.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-testA-1.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-testA-2.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-testA-2.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-testA-2.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/preferences-testA-2.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/test-layer-PreferencesStorageTest.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/test-layer-PreferencesStorageTest.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/test-layer-PreferencesStorageTest.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/preferences/test-layer-PreferencesStorageTest.xml diff --git a/editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/test-layer.xml b/editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/test-layer.xml copy from editor.settings.storage/test/unit/src/org/netbeans/modules/editor/settings/storage/test-layer.xml copy to editor.settings.lib/test/unit/src/org/netbeans/modules/editor/settings/storage/test-layer.xml diff --git a/editor.settings.storage/manifest.mf b/editor.settings.storage/manifest.mf --- a/editor.settings.storage/manifest.mf +++ b/editor.settings.storage/manifest.mf @@ -2,6 +2,5 @@ OpenIDE-Module: org.netbeans.modules.editor.settings.storage/1 OpenIDE-Module-Localizing-Bundle: org/netbeans/modules/editor/settings/storage/Bundle.properties OpenIDE-Module-Provides: org.netbeans.api.editor.settings.implementation -OpenIDE-Module-Specification-Version: 1.48 OpenIDE-Module-Layer: org/netbeans/modules/editor/settings/storage/layer.xml AutoUpdate-Show-In-Client: false diff --git a/api.progress/module-auto-deps.xml b/editor.settings.storage/module-auto-deps.xml copy from api.progress/module-auto-deps.xml copy to editor.settings.storage/module-auto-deps.xml --- a/api.progress/module-auto-deps.xml +++ b/editor.settings.storage/module-auto-deps.xml @@ -48,15 +48,14 @@ - Swing dependencies split away + Editor Storage NB indepenent code modularized - + - - + diff --git a/editor.settings.storage/nbproject/project.properties b/editor.settings.storage/nbproject/project.properties --- a/editor.settings.storage/nbproject/project.properties +++ b/editor.settings.storage/nbproject/project.properties @@ -45,6 +45,7 @@ javac.source=1.7 javadoc.apichanges=${basedir}/apichanges.xml javadoc.arch=${basedir}/arch.xml +spec.version.base=1.49.0 test.config.stableBTD.includes=**/*Test.class test.config.stableBTD.excludes=\ diff --git a/editor.settings.storage/nbproject/project.xml b/editor.settings.storage/nbproject/project.xml --- a/editor.settings.storage/nbproject/project.xml +++ b/editor.settings.storage/nbproject/project.xml @@ -124,6 +124,14 @@ 1.21 + + org.netbeans.modules.editor.settings.lib + + + + + + diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/EditorLocatorFactory.java b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/EditorLocatorFactory.java new file mode 100644 --- /dev/null +++ b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/EditorLocatorFactory.java @@ -0,0 +1,179 @@ +/* + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. + * + * Copyright 2015 Oracle and/or its affiliates. All rights reserved. + * + * Oracle and Java are registered trademarks of Oracle and/or its affiliates. + * Other names may be trademarks of their respective owners. + * + * The contents of this file are subject to the terms of either the GNU + * General Public License Version 2 only ("GPL") or the Common + * Development and Distribution License("CDDL") (collectively, the + * "License"). You may not use this file except in compliance with the + * License. You can obtain a copy of the License at + * http://www.netbeans.org/cddl-gplv2.html + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the + * specific language governing permissions and limitations under the + * License. When distributing the software, include this License Header + * Notice in each file and include the License file at + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the GPL Version 2 section of the License file that + * accompanied this code. If applicable, add the following below the + * License Header, with the fields enclosed by brackets [] replaced by + * your own identifying information: + * "Portions Copyrighted [year] [name of copyright owner]" + * + * If you wish your version of this file to be governed by only the CDDL + * or only the GPL Version 2, indicate your decision by adding + * "[Contributor] elects to include this software in this distribution + * under the [CDDL or GPL Version 2] license." If you do not indicate a + * single choice of license, a recipient has the option to distribute + * your version of this file under either the CDDL, the GPL Version 2 or + * to extend the choice of license to its licensees as provided above. + * However, if you add GPL Version 2 code and therefore, elected the GPL + * Version 2 license, then the option applies only if the new code is + * made subject to such option by the copyright holder. + * + * Contributor(s): + * + * Portions Copyrighted 2015 Sun Microsystems, Inc. + */ +package org.netbeans.modules.editor.settings.storage; + +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.logging.Level; +import java.util.logging.Logger; +import static org.netbeans.modules.editor.settings.storage.SettingsType.DefaultLocator.MODULE_FILES_FOLDER; +import org.netbeans.modules.editor.settings.storage.SettingsType.LocatorFactory; +import org.netbeans.modules.editor.settings.storage.fontscolors.ColoringStorage; +import org.netbeans.modules.editor.settings.storage.keybindings.KeyMapsStorage; +import org.netbeans.modules.editor.settings.storage.spi.StorageDescription; +import org.openide.filesystems.FileObject; +import org.openide.util.lookup.ServiceProvider; + +/** + * + * @author sdedic + */ +@ServiceProvider(service = LocatorFactory.class) +public class EditorLocatorFactory implements LocatorFactory { + private static final Logger LOG = Logger.getLogger(EditorLocatorFactory.class.getName()); + + @Override + public SettingsType.Locator createLocator(StorageDescription sd) { + if (ColoringStorage.ID.equals(sd.getId())) { + return new FontsColorsLocator(sd.getId(), sd.isUsingProfiles(), sd.getMimeType(), sd.getLegacyFileName()); + } else if (KeyMapsStorage.ID.equals(sd.getId())) { + return new LegacyTextBaseLocator(sd.getId(), sd.isUsingProfiles(), sd.getMimeType(), sd.getLegacyFileName()); + } + return null; + } + + private static final class FontsColorsLocator extends SettingsType.DefaultLocator { + + private static final String [] M_LEGACY_FILE_NAMES = new String [] { + MODULE_FILES_FOLDER + "/defaultColoring.xml", // NOI18N + MODULE_FILES_FOLDER + "/coloring.xml", // NOI18N + MODULE_FILES_FOLDER + "/editorColoring.xml", // NOI18N + }; + + private static final String [] U_LEGACY_FILE_NAMES = new String [] { + "defaultColoring.xml", // NOI18N + "coloring.xml", // NOI18N + "editorColoring.xml", // NOI18N + }; + + public FontsColorsLocator(String settingTypeId, boolean hasProfiles, String mimeType, String legacyFileName) { + super(settingTypeId, hasProfiles, mimeType, legacyFileName); + } + + @Override + protected void addModulesLegacyFiles( + FileObject mimeFolder, + String profileId, + boolean fullScan, + Map> files + ) { + addFiles(mimeFolder, profileId, fullScan, M_LEGACY_FILE_NAMES, files, true); + } + + @Override + protected void addUsersLegacyFiles( + FileObject mimeFolder, + String profileId, + boolean fullScan, + Map> files + ) { + addFiles(mimeFolder, profileId, fullScan, U_LEGACY_FILE_NAMES, files, false); + } + + private void addFiles( + FileObject mimeFolder, + String profileId, + boolean fullScan, + String [] filePaths, + Map> files, + boolean moduleFiles + ) { + if (profileId == null) { + FileObject [] profileHomes = mimeFolder.getChildren(); + for(FileObject f : profileHomes) { + if (!f.isFolder()) { + continue; + } + + String id = f.getNameExt(); + addFiles(f, filePaths, fullScan, files, id, f, moduleFiles); //NOI18N + } + } else { + FileObject profileHome = mimeFolder.getFileObject(profileId); + if (profileHome != null && profileHome.isFolder()) { + addFiles(profileHome, filePaths, fullScan, files, profileId, profileHome, moduleFiles); + } + } + } + + private void addFiles(FileObject folder, String [] filePaths, boolean fullScan, Map> files, String profileId, FileObject profileHome, boolean moduleFiles) { + for(String filePath : filePaths) { + FileObject f = folder.getFileObject(filePath); + if (f != null) { + List pair = files.get(profileId); + if (pair == null) { + pair = new ArrayList(); + files.put(profileId, pair); + } + pair.add(new Object [] { profileHome, f, moduleFiles, null, true }); + + if (LOG.isLoggable(Level.INFO)) { + Utils.logOnce(LOG, Level.INFO, settingTypeId + " settings " + //NOI18N + "should reside in '" + settingTypeId + "' subfolder, " + //NOI18N + "see #90403 for details. Offending file '" + f.getPath() + "'", null); //NOI18N + } + + if (!fullScan) { + break; + } + } + } + } + } // End of FontsColorsLocator class + + private static final class LegacyTextBaseLocator extends SettingsType.DefaultLocator { + + public LegacyTextBaseLocator(String settingTypeId, boolean hasProfiles, String mimeType, String legacyFileName) { + super(settingTypeId, hasProfiles, mimeType, legacyFileName); + } + + @Override + protected FileObject getLegacyMimeFolder(FileObject baseFolder, String mimeType) { + if (mimeType == null || mimeType.length() == 0) { + return baseFolder.getFileObject(Utils.TEXT_BASE_MIME_TYPE); + } else { + return super.getMimeFolder(baseFolder, mimeType); + } + } + } // End of KeybindingsLocator class +} diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/EditorSettingsImpl.java b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/EditorSettingsImpl.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/EditorSettingsImpl.java +++ b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/EditorSettingsImpl.java @@ -385,7 +385,7 @@ } highlightings.remove (profile); } else { - Map m = Utils.immutize(fontColors); + Map m = NbUtils.immutize(fontColors); // 3) save new values to disk if (!specialProfile) { @@ -485,7 +485,7 @@ } annotations.remove(profile); } else { - Map m = Utils.immutize(fontColors); + Map m = NbUtils.immutize(fontColors); // 3) save new values to disk if (!specialProfile) { diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/Utils.java b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/NbUtils.java copy from editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/Utils.java copy to editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/NbUtils.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/Utils.java +++ b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/NbUtils.java @@ -86,130 +86,10 @@ * * @author Jan Jancura */ -public class Utils { +public class NbUtils { - private static final Logger LOG = Logger.getLogger(Utils.class.getName()); + private static final Logger LOG = Logger.getLogger(NbUtils.class.getName()); - public static String getLocalizedName(FileObject fo, String defaultValue) { - try { - return fo.getFileSystem().getDecorator().annotateName(defaultValue, Collections.singleton(fo)); - } catch (FileStateInvalidException ex) { - if (LOG.isLoggable(Level.FINE)) { - logOnce(LOG, Level.FINE, "Can't find localized name of " + fo, ex); //NOI18N - } - return defaultValue; - } - } - - public static String getLocalizedName(FileObject fo, String key, String defaultValue) { - return getLocalizedName(fo, key, defaultValue, false); - } - - public static String getLocalizedName(FileObject fo, String key, String defaultValue, boolean silent) { - assert key != null : "The key can't be null"; //NOI18N - - Object [] bundleInfo = findResourceBundle(fo, silent); - if (bundleInfo[1] != null) { - try { - return ((ResourceBundle) bundleInfo[1]).getString(key); - } catch (MissingResourceException ex) { - if (!silent && LOG.isLoggable(Level.FINE)) { - logOnce(LOG, Level.FINE, "The bundle '" + bundleInfo[0] + "' is missing key '" + key + "'.", ex); //NOI18N - } - } - } - - return defaultValue; - } - -// private static final WeakHashMap bundleInfos = new WeakHashMap(); -// private static final FileChangeListener listener = new FileChangeAdapter() { -// @Override -// public void fileDeleted(FileEvent fe) { -// synchronized (bundleInfos) { -// bundleInfos.remove(fe.getFile()); -// } -// } -// -// @Override -// public void fileAttributeChanged(FileAttributeEvent fe) { -// if (fe.getName() != null && fe.getName().equals("SystemFileSystem.localizingBundle")) { //NOI18N -// synchronized (bundleInfos) { -// bundleInfos.remove(fe.getFile()); -// } -// } -// } -// }; -// private static final FileChangeListener weakListener = WeakListeners.create(FileChangeListener.class, listener, null); - private static Object [] findResourceBundle(FileObject fo, boolean silent) { - assert fo != null : "FileObject can't be null"; //NOI18N - - Object [] bundleInfo = null; -// synchronized (bundleInfos) { -// Object [] bundleInfo = bundleInfos.get(fo); -// if (bundleInfo == null) { - String bundleName = null; - Object attrValue = fo.getAttribute("SystemFileSystem.localizingBundle"); //NOI18N - if (attrValue instanceof String) { - bundleName = (String) attrValue; - } - - if (bundleName != null) { - try { - bundleInfo = new Object [] { bundleName, NbBundle.getBundle(bundleName) }; - } catch (MissingResourceException ex) { - if (!silent && LOG.isLoggable(Level.FINE)) { - logOnce(LOG, Level.FINE, "Can't find resource bundle for " + fo.getPath(), ex); //NOI18N - } - } - } else { - if (!silent && LOG.isLoggable(Level.FINE)) { - logOnce(LOG, Level.FINE, "The file " + fo.getPath() + " does not specify its resource bundle.", null); //NOI18N - } - } - - if (bundleInfo == null) { - bundleInfo = new Object [] { bundleName, null }; - } - -// bundleInfos.put(fo, bundleInfo); -// fo.removeFileChangeListener(weakListener); -// fo.addFileChangeListener(weakListener); -// } - - return bundleInfo; -// } - } - - private static final Set ALREADY_LOGGED = Collections.synchronizedSet(new HashSet()); - public static void logOnce(Logger logger, Level level, String msg, Throwable t) { - if (!ALREADY_LOGGED.contains(msg)) { - ALREADY_LOGGED.add(msg); - if (t != null) { - logger.log(level, msg, t); - } else { - logger.log(level, msg); - } - - if (ALREADY_LOGGED.size() > 100) { - ALREADY_LOGGED.clear(); - } - } - } - - /** - * Converts an array of mime types to a MimePath instance. - */ - public static MimePath mimeTypes2mimePath(String[] mimeTypes) { - MimePath mimePath = MimePath.EMPTY; - - for (int i = 0; i < mimeTypes.length; i++) { - mimePath = MimePath.get(mimePath, mimeTypes[i]); - } - - return mimePath; - } - /** * Creates unmodifiable copy of the original map converting AttributeSets * to their immutable versions. @@ -262,87 +142,7 @@ return Collections.unmodifiableMap(immutizedMap); } - public static void diff(Map oldMap, Map newMap, Map addedEntries, Map removedEntries) { - for(A key : oldMap.keySet()) { - if (!newMap.containsKey(key)) { - removedEntries.put(key, oldMap.get(key)); - } else { - if (!Utilities.compareObjects(oldMap.get(key), newMap.get(key))) { - addedEntries.put(key, newMap.get(key)); - } - } - } - - for(A key : newMap.keySet()) { - if (!oldMap.containsKey(key)) { - addedEntries.put(key, newMap.get(key)); - } - } - } - public static boolean quickDiff(Map oldMap, Map newMap) { - for(A key : oldMap.keySet()) { - if (!newMap.containsKey(key)) { - return true; - } else { - if (!Utilities.compareObjects(oldMap.get(key), newMap.get(key))) { - return true; - } - } - } - - for(A key : newMap.keySet()) { - if (!oldMap.containsKey(key)) { - return true; - } - } - - return false; - } - - public static void save(FileObject fo, StorageWriter writer) { - assert fo != null : "FileObject can't be null"; //NOI18N - assert writer != null : "StorageWriter can't be null"; //NOI18N - - try { - FileLock lock = fo.lock(); - try { - OutputStream os = fo.getOutputStream(lock); - try { - XMLUtil.write(writer.getDocument(), os, "UTF-8"); //NOI18N - } finally { - os.close(); - } - } finally { - lock.releaseLock(); - } - } catch (IOException ex) { - LOG.log(Level.WARNING, "Can't save editor settings to " + fo.getPath(), ex); //NOI18N - } - } - - public static void load(FileObject fo, StorageReader handler, boolean validate) { - assert fo != null : "Settings file must not be null"; //NOI18N - assert handler != null : "StorageReader can't be null"; //NOI18N - - try { - XMLReader reader = XMLUtil.createXMLReader(validate); - reader.setEntityResolver(EntityCatalog.getDefault()); - reader.setContentHandler(handler); - reader.setErrorHandler(handler); - reader.setProperty("http://xml.org/sax/properties/lexical-handler", handler); //NOI18N - - InputStream is = fo.getInputStream(); - try { - reader.parse(new InputSource(is)); - } finally { - is.close(); - } - } catch (Exception ex) { - LOG.log(Level.WARNING, "Invalid or corrupted file: " + fo.getPath(), ex); //NOI18N - } - } - @ServiceProvider(service=EntityCatalog.class) public static final class NoNetworkAccessEntityCatalog extends EntityCatalog { private final boolean NO_NETWORK_ACCESS = Boolean.getBoolean("editor.storage.no.network.access"); diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/fontscolors/ColoringStorage.java b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/fontscolors/ColoringStorage.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/fontscolors/ColoringStorage.java +++ b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/fontscolors/ColoringStorage.java @@ -258,7 +258,7 @@ } } - return Utils.immutize(fontsColorsMap, ATTR_MODULE_SUPPLIED); + return NbUtils.immutize(fontsColorsMap, ATTR_MODULE_SUPPLIED); } public boolean save( diff --git a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/fontscolors/FontColorSettingsImpl.java b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/fontscolors/FontColorSettingsImpl.java --- a/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/fontscolors/FontColorSettingsImpl.java +++ b/editor.settings.storage/src/org/netbeans/modules/editor/settings/storage/fontscolors/FontColorSettingsImpl.java @@ -179,7 +179,7 @@ } colorings.remove (profile); } else { - Map map = Utils.immutize(fontColors); + Map map = NbUtils.immutize(fontColors); if (!specialProfile) { try { @@ -213,7 +213,7 @@ if (fontColors == null) { ess.delete(mimePath, profile, true); } else { - ess.save(mimePath, profile, true, Utils.immutize(fontColors)); + ess.save(mimePath, profile, true, NbUtils.immutize(fontColors)); } } catch (IOException ioe) { LOG.log(Level.WARNING, null, ioe); diff --git a/ide.ergonomics/nbproject/project.xml b/ide.ergonomics/nbproject/project.xml --- a/ide.ergonomics/nbproject/project.xml +++ b/ide.ergonomics/nbproject/project.xml @@ -46,7 +46,7 @@ 1 - 1.38 + 1.60 diff --git a/ide.kit/nbproject/project.xml b/ide.kit/nbproject/project.xml --- a/ide.kit/nbproject/project.xml +++ b/ide.kit/nbproject/project.xml @@ -130,7 +130,7 @@ org.netbeans.modules.editor.settings.storage 1 - 1.48 + 1.49 diff --git a/java.hints.test/nbproject/project.xml b/java.hints.test/nbproject/project.xml --- a/java.hints.test/nbproject/project.xml +++ b/java.hints.test/nbproject/project.xml @@ -38,7 +38,7 @@ 1 - 1.41 + 1.60 diff --git a/java.source.base/src/org/netbeans/modules/java/source/base/layer.xml b/java.source.base/src/org/netbeans/modules/java/source/base/layer.xml --- a/java.source.base/src/org/netbeans/modules/java/source/base/layer.xml +++ b/java.source.base/src/org/netbeans/modules/java/source/base/layer.xml @@ -83,4 +83,14 @@ + + + + + + + + + + diff --git a/java.source.base/src/org/netbeans/modules/java/source/parsing/JavacParserFactory.java b/java.source.base/src/org/netbeans/modules/java/source/parsing/JavacParserFactory.java --- a/java.source.base/src/org/netbeans/modules/java/source/parsing/JavacParserFactory.java +++ b/java.source.base/src/org/netbeans/modules/java/source/parsing/JavacParserFactory.java @@ -61,9 +61,14 @@ */ @MimeRegistration(mimeType = "text/x-java", service = ParserFactory.class) public class JavacParserFactory extends ParserFactory { - + private static final Logger LOG = Logger.getLogger(JavacParserFactory.class.getName()); + /** used by tests to ensure that all instances of parser were GCed */ private static final Logger TIMER = Logger.getLogger("TIMER.JavacParser"); + + public JavacParserFactory() { + LOG.fine("JavacParserFactory created: " + this); + } @Override public JavacParser createParser(final Collection snapshots) { diff --git a/java.source/src/org/netbeans/modules/java/source/resources/layer.xml b/java.source/src/org/netbeans/modules/java/source/resources/layer.xml --- a/java.source/src/org/netbeans/modules/java/source/resources/layer.xml +++ b/java.source/src/org/netbeans/modules/java/source/resources/layer.xml @@ -267,12 +267,4 @@ - - - - - - - - diff --git a/languages/nbproject/project.xml b/languages/nbproject/project.xml --- a/languages/nbproject/project.xml +++ b/languages/nbproject/project.xml @@ -102,9 +102,13 @@ org.netbeans.modules.editor.settings.storage - - 1 - + 11.49 + + + org.netbeans.modules.editor.settings.lib + + + 1.49 org.netbeans.modules.editor.util diff --git a/nbbuild/cluster.properties b/nbbuild/cluster.properties --- a/nbbuild/cluster.properties +++ b/nbbuild/cluster.properties @@ -356,6 +357,7 @@ editor.plain.lib,\ editor.search,\ editor.settings,\ + editor.settings.lib,\ editor.settings.storage,\ editor.structure,\ editor.tools.storage,\ diff --git a/nbbuild/templates/common.xml b/nbbuild/templates/common.xml --- a/nbbuild/templates/common.xml +++ b/nbbuild/templates/common.xml @@ -1398,6 +1398,14 @@ + + + + + + + + diff --git a/options.api/src/org/netbeans/modules/options/classic/FileStateManager.java b/options.api/src/org/netbeans/modules/options/classic/FileStateManager.java --- a/options.api/src/org/netbeans/modules/options/classic/FileStateManager.java +++ b/options.api/src/org/netbeans/modules/options/classic/FileStateManager.java @@ -53,7 +53,6 @@ import java.util.Map.Entry; import java.util.WeakHashMap; import org.netbeans.core.startup.layers.SessionManager; -import org.netbeans.core.startup.layers.SystemFileSystem; import org.openide.filesystems.FileChangeAdapter; import org.openide.filesystems.FileChangeListener; import org.openide.filesystems.FileEvent; @@ -88,7 +87,7 @@ private static FileStateManager manager = null; /** Cache of collected information */ private WeakHashMap info = new WeakHashMap (); - /** Number of layers on {@link SystemFileSystem} */ + /** Number of layers on SystemFileSystem */ private static final int LAYERS_COUNT = 3; /** Layers of {@link SystemFileSystem}, LAYER_* constants can be used as indexes. */ private FileSystem layers [] = new FileSystem [LAYERS_COUNT]; diff --git a/options.editor/nbproject/project.xml b/options.editor/nbproject/project.xml --- a/options.editor/nbproject/project.xml +++ b/options.editor/nbproject/project.xml @@ -117,7 +117,15 @@ 1 - 1.42 + 1.49 + + + + org.netbeans.modules.editor.settings.lib + + + + 1.49 diff --git a/parsing.nb/nbproject/project.xml b/parsing.nb/nbproject/project.xml --- a/parsing.nb/nbproject/project.xml +++ b/parsing.nb/nbproject/project.xml @@ -46,7 +46,7 @@ 1 - 1.19 + 1.49