Return-Path: Delivered-To: apmail-geronimo-scm-archive@www.apache.org Received: (qmail 73056 invoked from network); 23 Aug 2006 21:51:01 -0000 Received: from hermes.apache.org (HELO mail.apache.org) (209.237.227.199) by minotaur.apache.org with SMTP; 23 Aug 2006 21:51:01 -0000 Received: (qmail 65745 invoked by uid 500); 23 Aug 2006 21:50:58 -0000 Delivered-To: apmail-geronimo-scm-archive@geronimo.apache.org Received: (qmail 65726 invoked by uid 500); 23 Aug 2006 21:50:58 -0000 Mailing-List: contact scm-help@geronimo.apache.org; run by ezmlm Precedence: bulk list-help: list-unsubscribe: List-Post: Reply-To: dev@geronimo.apache.org List-Id: Delivered-To: mailing list scm@geronimo.apache.org Received: (qmail 65715 invoked by uid 99); 23 Aug 2006 21:50:58 -0000 Received: from asf.osuosl.org (HELO asf.osuosl.org) (140.211.166.49) by apache.org (qpsmtpd/0.29) with ESMTP; Wed, 23 Aug 2006 14:50:58 -0700 X-ASF-Spam-Status: No, hits=-9.4 required=10.0 tests=ALL_TRUSTED,NO_REAL_NAME X-Spam-Check-By: apache.org Received-SPF: pass (asf.osuosl.org: local policy) Received: from [140.211.166.113] (HELO eris.apache.org) (140.211.166.113) by apache.org (qpsmtpd/0.29) with ESMTP; Wed, 23 Aug 2006 14:50:56 -0700 Received: by eris.apache.org (Postfix, from userid 65534) id 98DED1A981D; Wed, 23 Aug 2006 14:50:36 -0700 (PDT) Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Subject: svn commit: r434204 - in /geronimo/xbean/branches/colossus/xbean-naming/src: main/java/org/apache/xbean/naming/context/ test/java/org/apache/xbean/naming/context/ Date: Wed, 23 Aug 2006 21:50:35 -0000 To: scm@geronimo.apache.org From: dain@apache.org X-Mailer: svnmailer-1.0.8 Message-Id: <20060823215036.98DED1A981D@eris.apache.org> X-Virus-Checked: Checked by ClamAV on apache.org X-Spam-Rating: minotaur.apache.org 1.6.2 0/1000/N Author: dain Date: Wed Aug 23 14:50:34 2006 New Revision: 434204 URL: http://svn.apache.org/viewvc?rev=434204&view=rev Log: Merged WritableContext and UnmodifiableContext together by adding fine grained a ContextAccess object to AbstractFederatedContext. Currently only a blunt "the whole tree is (un)modifible" flag is implemented but we can easily implement a more fine grained approach. Added: geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/ContextAccess.java Removed: geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/UnmodifiableContext.java Modified: geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/AbstractFederatedContext.java geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/WritableContext.java geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/AbstractContextTest.java geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/UnmodifiableContextTest.java Modified: geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/AbstractFederatedContext.java URL: http://svn.apache.org/viewvc/geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/AbstractFederatedContext.java?rev=434204&r1=434203&r2=434204&view=diff ============================================================================== --- geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/AbstractFederatedContext.java (original) +++ geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/AbstractFederatedContext.java Wed Aug 23 14:50:34 2006 @@ -20,6 +20,7 @@ import javax.naming.Name; import javax.naming.NamingEnumeration; import javax.naming.Context; +import javax.naming.OperationNotSupportedException; import java.util.Map; import java.util.HashMap; import java.util.Iterator; @@ -29,13 +30,21 @@ */ public abstract class AbstractFederatedContext extends AbstractContext { private final ContextFederation contextFederation = new ContextFederation(this); + private final ContextAccess contextAccess; + private final boolean modifiable; public AbstractFederatedContext() { - this(""); + this("", ContextAccess.MODIFIABLE); } public AbstractFederatedContext(String nameInNamespace) { + this(nameInNamespace, ContextAccess.MODIFIABLE); + } + + protected AbstractFederatedContext(String nameInNamespace, ContextAccess contextAccess) { super(nameInNamespace); + this.contextAccess = contextAccess; + modifiable = contextAccess.isModifiable(getParsedNameInNamespace()); } protected Object faultLookup(String stringName, Name parsedName) { @@ -82,14 +91,100 @@ return false; } + public void bind(String name, Object obj) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.bind(name, obj); + } + + public void bind(Name name, Object obj) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.bind(name, obj); + } + + public void rebind(String name, Object obj) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.rebind(name, obj); + } + + public void rebind(Name name, Object obj) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.rebind(name, obj); + } + + public void rename(String oldName, String newName) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.rename(oldName, newName); + } + + public void rename(Name oldName, Name newName) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.rename(oldName, newName); + } + + public void unbind(String name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.unbind(name); + } + + public void unbind(Name name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.unbind(name); + } + + public Context createSubcontext(String name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + return super.createSubcontext(name); + } + + public Context createSubcontext(Name name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + return super.createSubcontext(name); + } + + public void destroySubcontext(String name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.destroySubcontext(name); + } + + public void destroySubcontext(Name name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.destroySubcontext(name); + } + public abstract class AbstractNestedFederatedContext extends AbstractContext { private final ContextFederation contextFederation; + private final boolean modifiable; public AbstractNestedFederatedContext(String path) throws NamingException { super(AbstractFederatedContext.this.getNameInNamespace(path)); - ContextFederation outerContextFederation = getOuterContext().contextFederation; - this.contextFederation = outerContextFederation.createSubcontextFederation(path, this); + AbstractFederatedContext outerContext = getOuterContext(); + this.contextFederation = outerContext.contextFederation.createSubcontextFederation(path, this); + this.modifiable = outerContext.contextAccess.isModifiable(getParsedNameInNamespace()); } public boolean isNestedSubcontext(Object value) { @@ -138,6 +233,90 @@ nestedContext.addFederatedContext(federatedContext); } } + } + + public void bind(String name, Object obj) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.bind(name, obj); + } + + public void bind(Name name, Object obj) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.bind(name, obj); + } + + public void rebind(String name, Object obj) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.rebind(name, obj); + } + + public void rebind(Name name, Object obj) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.rebind(name, obj); + } + + public void rename(String oldName, String newName) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.rename(oldName, newName); + } + + public void rename(Name oldName, Name newName) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.rename(oldName, newName); + } + + public void unbind(String name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.unbind(name); + } + + public void unbind(Name name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.unbind(name); + } + + public Context createSubcontext(String name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + return super.createSubcontext(name); + } + + public Context createSubcontext(Name name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + return super.createSubcontext(name); + } + + public void destroySubcontext(String name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.destroySubcontext(name); + } + + public void destroySubcontext(Name name) throws NamingException { + if (!modifiable) { + throw new OperationNotSupportedException("Context is read only"); + } + super.destroySubcontext(name); } } } Added: geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/ContextAccess.java URL: http://svn.apache.org/viewvc/geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/ContextAccess.java?rev=434204&view=auto ============================================================================== --- geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/ContextAccess.java (added) +++ geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/ContextAccess.java Wed Aug 23 14:50:34 2006 @@ -0,0 +1,38 @@ +/** + * + * Copyright 2006 The Apache Software Foundation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.apache.xbean.naming.context; + +import javax.naming.Name; + +/** + * @version $Rev$ $Date$ + */ +public interface ContextAccess { + ContextAccess MODIFIABLE = new ContextAccess() { + public boolean isModifiable(Name name) { + return true; + } + }; + + ContextAccess UNMODIFIABLE = new ContextAccess() { + public boolean isModifiable(Name name) { + return false; + } + }; + + boolean isModifiable(Name name); +} Modified: geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/WritableContext.java URL: http://svn.apache.org/viewvc/geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/WritableContext.java?rev=434204&r1=434203&r2=434204&view=diff ============================================================================== --- geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/WritableContext.java (original) +++ geronimo/xbean/branches/colossus/xbean-naming/src/main/java/org/apache/xbean/naming/context/WritableContext.java Wed Aug 23 14:50:34 2006 @@ -38,24 +38,29 @@ private final AtomicReference indexRef; public WritableContext() throws NamingException { - this("", Collections.EMPTY_MAP, true); + this("", Collections.EMPTY_MAP, ContextAccess.MODIFIABLE, true); } public WritableContext(String nameInNamespace) throws NamingException { - this(nameInNamespace, Collections.EMPTY_MAP, true); + this(nameInNamespace, Collections.EMPTY_MAP, ContextAccess.MODIFIABLE, true); } - public WritableContext(Map bindings) throws NamingException { - this("", bindings, true); + public WritableContext(String nameInNamespace, Map bindings) throws NamingException { + this(nameInNamespace, bindings, ContextAccess.MODIFIABLE, true); } - public WritableContext(Map bindings, boolean cacheReferences) throws NamingException { - this("", bindings, cacheReferences); + public WritableContext(String nameInNamespace, Map bindings, boolean cacheReferences) throws NamingException { + this(nameInNamespace, bindings, ContextAccess.MODIFIABLE, cacheReferences); } - public WritableContext(String nameInNamespace, Map bindings, boolean cacheReferences) throws NamingException { - super(nameInNamespace); + public WritableContext(String nameInNamespace, Map bindings, ContextAccess contextAccess) throws NamingException { + this(nameInNamespace, bindings, contextAccess, true); + } + + public WritableContext(String nameInNamespace, Map bindings, ContextAccess contextAccess, boolean cacheReferences) throws NamingException { + super(nameInNamespace, contextAccess); + // todo we need to wrap any reference bound, not just the initial bindings if (cacheReferences) { bindings = CachingReference.wrapReferences(bindings); } Modified: geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/AbstractContextTest.java URL: http://svn.apache.org/viewvc/geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/AbstractContextTest.java?rev=434204&r1=434203&r2=434204&view=diff ============================================================================== --- geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/AbstractContextTest.java (original) +++ geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/AbstractContextTest.java Wed Aug 23 14:50:34 2006 @@ -22,6 +22,7 @@ import javax.naming.NamingException; import javax.naming.Name; import javax.naming.NamingEnumeration; +import javax.naming.OperationNotSupportedException; import java.util.Map; import java.util.Iterator; import java.util.TreeSet; @@ -144,6 +145,104 @@ extraNames.removeAll(node.keySet()); if (!extraNames.isEmpty()) { fail("list of " + name + " on " + contextName + " did not find values: " + extraNames); + } + } + + public static void assertUnmodifiable(Context context) throws Exception { + Object value = "VALUE"; + String nameString = "TEST_NAME"; + Name name = context.getNameParser("").parse(nameString); + + // + // bind + // + try { + context.bind(nameString, value); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + try { + context.bind(name, value); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + // + // rebind + // + try { + context.rebind(nameString, value); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + try { + context.rebind(name, value); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + // + // rename + // + String newNameString = "NEW_TEST_NAME"; + Name newName = context.getNameParser("").parse(newNameString); + try { + context.rename(nameString, newNameString); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + try { + context.rename(name, newName); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + // + // unbind + // + try { + context.unbind(nameString); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + try { + context.unbind(name); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + // + // createSubcontext + // + try { + context.createSubcontext(nameString); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + try { + context.createSubcontext(name); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + // + // destroySubcontext + // + try { + context.destroySubcontext(nameString); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { + } + + try { + context.destroySubcontext(name); + fail("Expected an OperationNotSupportedException"); + } catch(OperationNotSupportedException expected) { } } } Modified: geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/UnmodifiableContextTest.java URL: http://svn.apache.org/viewvc/geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/UnmodifiableContextTest.java?rev=434204&r1=434203&r2=434204&view=diff ============================================================================== --- geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/UnmodifiableContextTest.java (original) +++ geronimo/xbean/branches/colossus/xbean-naming/src/test/java/org/apache/xbean/naming/context/UnmodifiableContextTest.java Wed Aug 23 14:50:34 2006 @@ -29,9 +29,9 @@ public class UnmodifiableContextTest extends AbstractContextTest { private static final String STRING_VAL = "some string"; - private final class MutableContext extends UnmodifiableContext { + private final class MutableContext extends WritableContext { public MutableContext(Map bindings) throws NamingException { - super(bindings); + super("", bindings, ContextAccess.UNMODIFIABLE); } public void addDeepBinding(Name name, Object value, boolean rebind, boolean createIntermediateContexts) throws NamingException { @@ -52,9 +52,10 @@ map.put("a/b/c/d/e/two", new Integer(2)); map.put("a/b/c/d/e/three", new Integer(3)); - Context context = new UnmodifiableContext(map); + Context context = new WritableContext("", map, ContextAccess.UNMODIFIABLE); assertEq(map, context); + assertUnmodifiable(context); } public void testAddBinding() throws Exception { @@ -69,6 +70,7 @@ MutableContext context = new MutableContext(map); assertEq(map, context); + assertUnmodifiable(context); // add a new deep tree map.put("uno/dos/tres", new Integer(123)); @@ -76,12 +78,14 @@ context.addDeepBinding(parser.parse("uno/dos/tres"), new Integer(123), false, true); assertEq(map, context); + assertUnmodifiable(context); // modify an existing context map.put("a/b/c/d/e/four", new Integer(4)); context.addDeepBinding(parser.parse("a/b/c/d/e/four"), new Integer(4), false, true); assertEq(map, context); + assertUnmodifiable(context); } @@ -97,6 +101,7 @@ MutableContext context = new MutableContext(map); assertEq(map, context); + assertUnmodifiable(context); // remove from an exisitng node map.remove("a/b/c/d/e/three"); @@ -104,13 +109,13 @@ context.removeDeepBinding(parser.parse("a/b/c/d/e/three"), true); assertEq(map, context); + assertUnmodifiable(context); // remove a deep single element element... empty nodes should be removed map.remove("nested/context/string"); context.removeDeepBinding(parser.parse("nested/context/string"), true); assertEq(map, context); + assertUnmodifiable(context); } - - }