| /** |
| * Licensed to the Apache Software Foundation (ASF) under one |
| * or more contributor license agreements. See the NOTICE file |
| * distributed with this work for additional information |
| * regarding copyright ownership. The ASF licenses this file |
| * to you 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.aries.jndi; |
| |
| import static org.junit.Assert.assertEquals; |
| import static org.junit.Assert.assertTrue; |
| import static org.junit.Assert.assertNotNull; |
| |
| import java.util.Dictionary; |
| import java.util.Hashtable; |
| import java.util.Properties; |
| import java.util.concurrent.atomic.AtomicBoolean; |
| |
| import javax.naming.Context; |
| import javax.naming.InitialContext; |
| import javax.naming.Name; |
| import javax.naming.NamingException; |
| import javax.naming.NoInitialContextException; |
| import javax.naming.ldap.Control; |
| import javax.naming.ldap.ExtendedRequest; |
| import javax.naming.ldap.InitialLdapContext; |
| import javax.naming.ldap.LdapContext; |
| import javax.naming.spi.InitialContextFactory; |
| import javax.naming.spi.InitialContextFactoryBuilder; |
| import javax.naming.spi.ObjectFactory; |
| |
| import junit.framework.Assert; |
| |
| import org.apache.aries.jndi.startup.Activator; |
| import org.apache.aries.mocks.BundleContextMock; |
| import org.apache.aries.unittest.mocks.MethodCall; |
| import org.apache.aries.unittest.mocks.Skeleton; |
| import org.junit.After; |
| import org.junit.Before; |
| import org.junit.Test; |
| import org.osgi.framework.BundleContext; |
| import org.osgi.service.jndi.JNDIConstants; |
| |
| public class InitialContextTest |
| { |
| private Activator activator; |
| private BundleContext bc; |
| private InitialContext ic; |
| |
| /** |
| * This method does the setup . |
| * @throws NoSuchFieldException |
| * @throws SecurityException |
| * @throws IllegalAccessException |
| * @throws IllegalArgumentException |
| */ |
| @Before |
| public void setup() throws SecurityException, NoSuchFieldException, IllegalArgumentException, IllegalAccessException |
| { |
| bc = Skeleton.newMock(new BundleContextMock(), BundleContext.class); |
| activator = new Activator(); |
| activator.start(bc); |
| } |
| |
| /** |
| * Make sure we clear the caches out before the next test. |
| */ |
| @After |
| public void teardown() |
| { |
| activator.stop(bc); |
| BundleContextMock.clear(); |
| } |
| |
| @Test |
| public void testLookupWithICF() throws NamingException |
| { |
| InitialContextFactory icf = Skeleton.newMock(InitialContextFactory.class); |
| bc.registerService(new String[] {InitialContextFactory.class.getName(), icf.getClass().getName()}, icf, (Dictionary) new Properties()); |
| Skeleton.getSkeleton(icf).setReturnValue(new MethodCall(Context.class, "lookup", "/"), Skeleton.newMock(Context.class)); |
| |
| Properties props = new Properties(); |
| props.put(Context.INITIAL_CONTEXT_FACTORY, icf.getClass().getName()); |
| props.put(JNDIConstants.BUNDLE_CONTEXT, bc); |
| InitialContext ctx = new InitialContext(props); |
| |
| Context namingCtx = (Context) ctx.lookup("/"); |
| assertTrue("Context returned isn't the raw naming context: " + namingCtx, Skeleton.isSkeleton(namingCtx)); |
| } |
| |
| @Test(expected=NoInitialContextException.class) |
| public void testLookupWithoutICF() throws NamingException |
| { |
| Properties props = new Properties(); |
| props.put(JNDIConstants.BUNDLE_CONTEXT, bc); |
| InitialContext ctx = new InitialContext(props); |
| |
| ctx.lookup("/"); |
| } |
| |
| @Test |
| public void testLookupWithoutICFButWithURLLookup() throws NamingException |
| { |
| ObjectFactory factory = Skeleton.newMock(ObjectFactory.class); |
| Context ctx = Skeleton.newMock(Context.class); |
| Skeleton.getSkeleton(factory).setReturnValue(new MethodCall(ObjectFactory.class, "getObjectInstance", Object.class, Name.class, Context.class, Hashtable.class), |
| ctx); |
| Skeleton.getSkeleton(ctx).setReturnValue(new MethodCall(Context.class, "lookup", String.class), "someText"); |
| |
| Properties props = new Properties(); |
| props.put(JNDIConstants.JNDI_URLSCHEME, "testURL"); |
| bc.registerService(ObjectFactory.class.getName(), factory, (Dictionary) props); |
| |
| |
| props = new Properties(); |
| props.put(JNDIConstants.BUNDLE_CONTEXT, bc); |
| InitialContext initialCtx = new InitialContext(props); |
| |
| Object someObject = initialCtx.lookup("testURL:somedata"); |
| assertEquals("Expected to be given a string, but got something else.", "someText", someObject); |
| } |
| |
| @Test |
| public void testLookFromLdapICF() throws Exception |
| { |
| InitialContextFactoryBuilder icf = Skeleton.newMock(InitialContextFactoryBuilder.class); |
| bc.registerService(new String[] {InitialContextFactoryBuilder.class.getName(), icf.getClass().getName()}, icf, (Dictionary) new Properties()); |
| |
| LdapContext backCtx = Skeleton.newMock(LdapContext.class); |
| InitialContextFactory fac = Skeleton.newMock(InitialContextFactory.class); |
| Skeleton.getSkeleton(fac).setReturnValue( |
| new MethodCall(InitialContextFactory.class, "getInitialContext", Hashtable.class), |
| backCtx); |
| Skeleton.getSkeleton(icf).setReturnValue( |
| new MethodCall(InitialContextFactoryBuilder.class, "createInitialContextFactory", Hashtable.class), |
| fac); |
| |
| Properties props = new Properties(); |
| props.put(JNDIConstants.BUNDLE_CONTEXT, bc); |
| props.put(Context.INITIAL_CONTEXT_FACTORY, "dummy.factory"); |
| InitialLdapContext ilc = new InitialLdapContext(props, new Control[0]); |
| |
| ExtendedRequest req = Skeleton.newMock(ExtendedRequest.class); |
| ilc.extendedOperation(req); |
| Skeleton.getSkeleton(backCtx).assertCalled(new MethodCall(LdapContext.class, "extendedOperation", req)); |
| } |
| |
| @Test |
| public void testURLLookup() throws Exception { |
| ObjectFactory of = new ObjectFactory() { |
| public Object getObjectInstance(Object obj, Name name, Context nameCtx, Hashtable<?, ?> environment) throws Exception { |
| return dummyContext("result"); |
| } |
| }; |
| |
| registerURLObjectFactory(of, "test"); |
| ic = initialContext(); |
| |
| assertEquals("result", ic.lookup("test:something")); |
| } |
| |
| @Test |
| public void testNoURLContextCaching() throws Exception { |
| final AtomicBoolean second = new AtomicBoolean(false); |
| final Context ctx = dummyContext("one"); |
| final Context ctx2 = dummyContext("two"); |
| |
| ObjectFactory of = new ObjectFactory() { |
| public Object getObjectInstance(Object obj, Name name, Context nameCtx, Hashtable<?, ?> environment) throws Exception { |
| if (second.get()) return ctx2; |
| else { |
| second.set(true); |
| return ctx; |
| } |
| } |
| }; |
| |
| registerURLObjectFactory(of, "test"); |
| ic = initialContext(); |
| |
| assertEquals("one", ic.lookup("test:something")); |
| assertEquals("two", ic.lookup("test:something")); |
| } |
| |
| @Test |
| public void testURLContextErrorPropagation() throws Exception { |
| ObjectFactory of = new ObjectFactory() { |
| public Object getObjectInstance(Object obj, Name name, Context nameCtx, |
| Hashtable<?, ?> environment) throws Exception { |
| throw new Exception("doh"); |
| } |
| }; |
| |
| registerURLObjectFactory(of, "test"); |
| ic = initialContext(); |
| |
| try { |
| ic.lookup("test:something"); |
| Assert.fail("Expected NamingException"); |
| } catch (NamingException ne) { |
| assertNotNull(ne.getCause()); |
| assertEquals("doh", ne.getCause().getMessage()); |
| } |
| } |
| |
| /** |
| * Create a minimal initial context with just the bundle context in the environment |
| * @return |
| * @throws Exception |
| */ |
| private InitialContext initialContext() throws Exception { |
| Properties props = new Properties(); |
| props.put(JNDIConstants.BUNDLE_CONTEXT, bc); |
| InitialContext ic = new InitialContext(props); |
| return ic; |
| } |
| |
| /** |
| * Registers an ObjectFactory to be used for creating URLContexts for the given scheme |
| * @param of |
| * @param scheme |
| */ |
| private void registerURLObjectFactory(ObjectFactory of, String scheme) { |
| Properties props = new Properties(); |
| props.setProperty(JNDIConstants.JNDI_URLSCHEME, "test"); |
| bc.registerService(ObjectFactory.class.getName(), of, (Dictionary) props); |
| } |
| |
| /** |
| * Creates a context that always returns the given object |
| * @param toReturn |
| * @return |
| */ |
| private Context dummyContext(Object toReturn) { |
| Context ctx = Skeleton.newMock(Context.class); |
| Skeleton.getSkeleton(ctx).setReturnValue(new MethodCall(Context.class, "lookup", String.class), toReturn); |
| Skeleton.getSkeleton(ctx).setReturnValue(new MethodCall(Context.class, "lookup", Name.class), toReturn); |
| return ctx; |
| } |
| } |