View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      https://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  
18  package org.apache.commons.dbcp2;
19  
20  import static org.junit.jupiter.api.Assertions.assertNotNull;
21  
22  import java.util.Hashtable;
23  
24  import javax.naming.Context;
25  import javax.naming.InitialContext;
26  import javax.naming.NamingException;
27  import javax.sql.DataSource;
28  
29  import org.apache.commons.dbcp2.datasources.PerUserPoolDataSource;
30  import org.apache.commons.dbcp2.datasources.SharedPoolDataSource;
31  import org.junit.jupiter.api.AfterEach;
32  import org.junit.jupiter.api.BeforeEach;
33  import org.junit.jupiter.api.Test;
34  
35  /**
36   * Tests JNID bind and lookup for DataSource implementations.
37   * Demonstrates problem indicated in BZ #38073.
38   */
39  public class TestJndi {
40      /**
41       * The subcontext where the data source is bound.
42       */
43      protected static final String JNDI_SUBCONTEXT = "jdbc";
44  
45      /**
46       * the full JNDI path to the data source.
47       */
48      protected static final String JNDI_PATH = JNDI_SUBCONTEXT + "/"
49              + "jndiTestDataSource";
50  
51      /** JNDI context to use in tests **/
52      protected Context context;
53  
54      /**
55       * Binds a DataSource into JNDI.
56       *
57       * @throws Exception if creation or binding fails.
58       */
59      protected void bindDataSource(final DataSource dataSource) throws Exception {
60          context.bind(JNDI_PATH, dataSource);
61      }
62  
63      /**
64       * Binds a DataSource to the JNDI and checks that we have successfully
65       * bound it by looking it up again.
66       *
67       * @throws Exception if the bind, lookup or connect fails
68       */
69      protected void checkBind(final DataSource dataSource) throws Exception {
70          bindDataSource(dataSource);
71          retrieveDataSource();
72      }
73  
74      /**
75       * Gets (or creates if it does not exist) an InitialContext.
76       *
77       * @return the InitialContext.
78       * @throws NamingException if the InitialContext cannot be retrieved
79       *         or created.
80       */
81      protected InitialContext getInitialContext() throws NamingException {
82          final Hashtable<String, String> environment = new Hashtable<>();
83          environment.put(Context.INITIAL_CONTEXT_FACTORY,
84                  org.apache.naming.java.javaURLContextFactory.class.getName());
85          return new InitialContext(environment);
86      }
87  
88      /**
89       * Retrieves a DataSource from JNDI.
90       *
91       * @throws Exception if the JNDI lookup fails or no DataSource is bound.
92       */
93      protected DataSource retrieveDataSource() throws Exception {
94          final Context ctx = getInitialContext();
95          final DataSource dataSource = (DataSource) ctx.lookup(JNDI_PATH);
96          assertNotNull(dataSource, "DataSource should not be null");
97          return dataSource;
98      }
99  
100     @BeforeEach
101     public void setUp() throws Exception {
102         context = getInitialContext();
103         context.createSubcontext(JNDI_SUBCONTEXT);
104     }
105 
106     @AfterEach
107     public void tearDown() throws Exception {
108         context.unbind(JNDI_PATH);
109         context.destroySubcontext(JNDI_SUBCONTEXT);
110     }
111 
112     /**
113      * Test BasicDatasource bind and lookup
114      *
115      * @throws Exception
116      */
117     @Test
118     void testBasicDataSourceBind() throws Exception {
119         final BasicDataSource dataSource = new BasicDataSource();
120         checkBind(dataSource);
121     }
122 
123     /**
124      * Test PerUserPoolDataSource bind and lookup
125      *
126      * @throws Exception
127      */
128     @Test
129     void testPerUserPoolDataSourceBind() throws Exception {
130         final PerUserPoolDataSource dataSource = new PerUserPoolDataSource();
131         checkBind(dataSource);
132     }
133 
134     /**
135      * Test SharedPoolDataSource bind and lookup
136      *
137      * @throws Exception
138      */
139     @Test
140     void testSharedPoolDataSourceBind() throws Exception {
141         final SharedPoolDataSource dataSource = new SharedPoolDataSource();
142         checkBind(dataSource);
143     }
144 }