36511
|
1 |
/*
|
|
2 |
* Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
|
|
3 |
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
|
4 |
*
|
|
5 |
* This code is free software; you can redistribute it and/or modify it
|
|
6 |
* under the terms of the GNU General Public License version 2 only, as
|
|
7 |
* published by the Free Software Foundation.
|
|
8 |
*
|
|
9 |
* This code is distributed in the hope that it will be useful, but WITHOUT
|
|
10 |
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
|
11 |
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
|
12 |
* version 2 for more details (a copy is included in the LICENSE file that
|
|
13 |
* accompanied this code).
|
|
14 |
*
|
|
15 |
* You should have received a copy of the GNU General Public License version
|
|
16 |
* 2 along with this work; if not, write to the Free Software Foundation,
|
|
17 |
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
|
18 |
*
|
|
19 |
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
|
20 |
* or visit www.oracle.com if you need additional information or have any
|
|
21 |
* questions.
|
|
22 |
*/
|
|
23 |
|
|
24 |
import java.nio.file.Path;
|
|
25 |
import java.nio.file.Paths;
|
|
26 |
import java.util.LinkedHashMap;
|
|
27 |
import java.util.List;
|
|
28 |
import java.util.Map;
|
|
29 |
import java.util.Arrays;
|
|
30 |
import java.io.IOException;
|
|
31 |
import java.lang.module.ModuleDescriptor;
|
|
32 |
import java.util.ArrayList;
|
|
33 |
import jdk.testlibrary.ProcessTools;
|
|
34 |
import jdk.testlibrary.OutputAnalyzer;
|
|
35 |
import org.testng.annotations.BeforeTest;
|
|
36 |
|
|
37 |
/**
|
|
38 |
* @test
|
|
39 |
* @bug 8078813
|
|
40 |
* @library /lib/testlibrary
|
|
41 |
* @library /java/security/modules
|
|
42 |
* @build CompilerUtils JarUtils
|
|
43 |
* @summary Test custom JAAS module with all possible modular option. The test
|
|
44 |
* includes different combination of JAAS client/login modules
|
|
45 |
* interaction with or without service description.
|
|
46 |
* @run testng JaasModularClientTest
|
|
47 |
*/
|
|
48 |
public class JaasModularClientTest extends ModularTest {
|
|
49 |
|
|
50 |
private static final Path S_SRC = SRC.resolve("TestLoginModule.java");
|
|
51 |
private static final String S_PKG = "login";
|
|
52 |
private static final String S_JAR_NAME = S_PKG + JAR_EXTN;
|
|
53 |
private static final String S_DESCR_JAR_NAME = S_PKG + DESCRIPTOR
|
|
54 |
+ JAR_EXTN;
|
|
55 |
private static final String MS_JAR_NAME = MODULAR + S_PKG + JAR_EXTN;
|
|
56 |
private static final String MS_DESCR_JAR_NAME = MODULAR + S_PKG + DESCRIPTOR
|
|
57 |
+ JAR_EXTN;
|
|
58 |
|
|
59 |
private static final Path C_SRC = SRC.resolve("JaasClient.java");
|
|
60 |
private static final String C_PKG = "client";
|
|
61 |
private static final String C_JAR_NAME = C_PKG + JAR_EXTN;
|
|
62 |
private static final String MC_DEPENDS_ON_AUTO_SERVICE_JAR_NAME = MODULAR
|
|
63 |
+ C_PKG + AUTO + JAR_EXTN;
|
|
64 |
private static final String MC_JAR_NAME = MODULAR + C_PKG + JAR_EXTN;
|
|
65 |
|
|
66 |
private static final Path BUILD_DIR = Paths.get(".").resolve("build");
|
|
67 |
private static final Path COMPILE_DIR = BUILD_DIR.resolve("bin");
|
|
68 |
private static final Path S_BUILD_DIR = COMPILE_DIR.resolve(S_PKG);
|
|
69 |
private static final Path S_WITH_META_DESCR_BUILD_DIR = COMPILE_DIR.resolve(
|
|
70 |
S_PKG + DESCRIPTOR);
|
|
71 |
private static final Path C_BUILD_DIR = COMPILE_DIR.resolve(C_PKG);
|
|
72 |
private static final Path M_BASE_PATH = BUILD_DIR.resolve("mbase");
|
|
73 |
private static final Path ARTIFACTS_DIR = BUILD_DIR.resolve("artifacts");
|
|
74 |
|
|
75 |
private static final Path S_ARTIFACTS_DIR = ARTIFACTS_DIR.resolve(S_PKG);
|
|
76 |
private static final Path S_JAR = S_ARTIFACTS_DIR.resolve(S_JAR_NAME);
|
|
77 |
private static final Path S_WITH_DESCRIPTOR_JAR = S_ARTIFACTS_DIR.resolve(
|
|
78 |
S_DESCR_JAR_NAME);
|
|
79 |
private static final Path MS_JAR = S_ARTIFACTS_DIR.resolve(MS_JAR_NAME);
|
|
80 |
private static final Path MS_WITH_DESCR_JAR = S_ARTIFACTS_DIR.resolve(
|
|
81 |
MS_DESCR_JAR_NAME);
|
|
82 |
|
|
83 |
private static final Path C_ARTIFACTS_DIR = ARTIFACTS_DIR.resolve(C_PKG);
|
|
84 |
private static final Path C_JAR = C_ARTIFACTS_DIR.resolve(C_JAR_NAME);
|
|
85 |
private static final Path MC_JAR = C_ARTIFACTS_DIR.resolve(MC_JAR_NAME);
|
|
86 |
private static final Path MC_DEPENDS_ON_AUTO_SERVICE_JAR = C_ARTIFACTS_DIR
|
|
87 |
.resolve(MC_DEPENDS_ON_AUTO_SERVICE_JAR_NAME);
|
|
88 |
|
|
89 |
private static final String MAIN = C_PKG + ".JaasClient";
|
|
90 |
private static final String S_INTERFACE
|
|
91 |
= "javax.security.auth.spi.LoginModule";
|
|
92 |
private static final String S_IMPL = S_PKG + ".TestLoginModule";
|
|
93 |
private static final List<String> M_REQUIRED = Arrays.asList("java.base",
|
|
94 |
"jdk.security.auth");
|
|
95 |
private static final Path META_DESCR_PATH = Paths.get("META-INF")
|
|
96 |
.resolve("services").resolve(S_INTERFACE);
|
|
97 |
private static final Path S_META_DESCR_FPATH = S_WITH_META_DESCR_BUILD_DIR
|
|
98 |
.resolve(META_DESCR_PATH);
|
|
99 |
|
|
100 |
private static final boolean WITH_S_DESCR = true;
|
|
101 |
private static final boolean WITHOUT_S_DESCR = false;
|
|
102 |
private static final String LOGIN_MODULE_NOT_FOUND_MSG
|
|
103 |
= "No LoginModule found";
|
|
104 |
private static final String NO_FAILURE = null;
|
|
105 |
private static final Map<String, String> VM_ARGS = new LinkedHashMap<>();
|
|
106 |
|
|
107 |
/**
|
|
108 |
* Generates Test specific input parameters.
|
|
109 |
*/
|
|
110 |
@Override
|
|
111 |
public Object[][] getTestInput() {
|
|
112 |
|
|
113 |
List<List<Object>> params = new ArrayList<>();
|
|
114 |
String[] args = new String[]{};
|
|
115 |
//PARAMETER ORDERS -
|
|
116 |
//client Module Type, Service Module Type,
|
|
117 |
//Service META Descriptor Required,
|
|
118 |
//Expected Failure message, mechanism used to find the provider
|
|
119 |
params.add(Arrays.asList(MODULE_TYPE.EXPLICIT, MODULE_TYPE.EXPLICIT,
|
|
120 |
WITH_S_DESCR, NO_FAILURE, args));
|
|
121 |
params.add(Arrays.asList(MODULE_TYPE.EXPLICIT, MODULE_TYPE.EXPLICIT,
|
|
122 |
WITHOUT_S_DESCR, NO_FAILURE, args));
|
|
123 |
params.add(Arrays.asList(MODULE_TYPE.EXPLICIT, MODULE_TYPE.AUTO,
|
|
124 |
WITH_S_DESCR, NO_FAILURE, args));
|
|
125 |
params.add(Arrays.asList(MODULE_TYPE.EXPLICIT, MODULE_TYPE.AUTO,
|
|
126 |
WITHOUT_S_DESCR, LOGIN_MODULE_NOT_FOUND_MSG, args));
|
|
127 |
params.add(Arrays.asList(MODULE_TYPE.EXPLICIT, MODULE_TYPE.UNNAMED,
|
|
128 |
WITH_S_DESCR, NO_FAILURE, args));
|
|
129 |
params.add(Arrays.asList(MODULE_TYPE.EXPLICIT, MODULE_TYPE.UNNAMED,
|
|
130 |
WITHOUT_S_DESCR, NO_FAILURE, args));
|
|
131 |
|
|
132 |
params.add(Arrays.asList(MODULE_TYPE.AUTO, MODULE_TYPE.EXPLICIT,
|
|
133 |
WITH_S_DESCR, NO_FAILURE, args));
|
|
134 |
params.add(Arrays.asList(MODULE_TYPE.AUTO, MODULE_TYPE.EXPLICIT,
|
|
135 |
WITHOUT_S_DESCR, NO_FAILURE, args));
|
|
136 |
params.add(Arrays.asList(MODULE_TYPE.AUTO, MODULE_TYPE.AUTO,
|
|
137 |
WITH_S_DESCR, NO_FAILURE, args));
|
|
138 |
params.add(Arrays.asList(MODULE_TYPE.AUTO, MODULE_TYPE.AUTO,
|
|
139 |
WITHOUT_S_DESCR, LOGIN_MODULE_NOT_FOUND_MSG, args));
|
|
140 |
params.add(Arrays.asList(MODULE_TYPE.AUTO, MODULE_TYPE.UNNAMED,
|
|
141 |
WITH_S_DESCR, NO_FAILURE, args));
|
|
142 |
params.add(Arrays.asList(MODULE_TYPE.AUTO, MODULE_TYPE.UNNAMED,
|
|
143 |
WITHOUT_S_DESCR, NO_FAILURE, args));
|
|
144 |
|
|
145 |
params.add(Arrays.asList(MODULE_TYPE.UNNAMED, MODULE_TYPE.EXPLICIT,
|
|
146 |
WITH_S_DESCR, NO_FAILURE, args));
|
|
147 |
params.add(Arrays.asList(MODULE_TYPE.UNNAMED, MODULE_TYPE.EXPLICIT,
|
|
148 |
WITHOUT_S_DESCR, NO_FAILURE, args));
|
|
149 |
params.add(Arrays.asList(MODULE_TYPE.UNNAMED, MODULE_TYPE.AUTO,
|
|
150 |
WITH_S_DESCR, NO_FAILURE, args));
|
|
151 |
params.add(Arrays.asList(MODULE_TYPE.UNNAMED, MODULE_TYPE.AUTO,
|
|
152 |
WITHOUT_S_DESCR, LOGIN_MODULE_NOT_FOUND_MSG, args));
|
|
153 |
params.add(Arrays.asList(MODULE_TYPE.UNNAMED, MODULE_TYPE.UNNAMED,
|
|
154 |
WITH_S_DESCR, NO_FAILURE, args));
|
|
155 |
params.add(Arrays.asList(MODULE_TYPE.UNNAMED, MODULE_TYPE.UNNAMED,
|
|
156 |
WITHOUT_S_DESCR, NO_FAILURE, args));
|
|
157 |
return params.stream().map(p -> p.toArray()).toArray(Object[][]::new);
|
|
158 |
}
|
|
159 |
|
|
160 |
/**
|
|
161 |
* Pre-compile and generate the artifacts required to run this test before
|
|
162 |
* running each test cases.
|
|
163 |
*/
|
|
164 |
@BeforeTest
|
|
165 |
public void buildArtifacts() {
|
|
166 |
|
|
167 |
boolean done = true;
|
|
168 |
try {
|
|
169 |
VM_ARGS.put("-Duser.language=", "en");
|
|
170 |
VM_ARGS.put("-Duser.region", "US");
|
|
171 |
VM_ARGS.put("-Djava.security.auth.login.config=", SRC.resolve(
|
|
172 |
"jaas.conf").toFile().getCanonicalPath());
|
|
173 |
|
|
174 |
done = CompilerUtils.compile(S_SRC, S_BUILD_DIR);
|
|
175 |
done &= CompilerUtils.compile(S_SRC, S_WITH_META_DESCR_BUILD_DIR);
|
|
176 |
done &= createMetaInfServiceDescriptor(S_META_DESCR_FPATH, S_IMPL);
|
|
177 |
//Generate regular/modular jars with(out) META-INF
|
|
178 |
//service descriptor
|
|
179 |
generateJar(true, MODULE_TYPE.EXPLICIT, MS_JAR, S_BUILD_DIR, false);
|
|
180 |
generateJar(true, MODULE_TYPE.EXPLICIT, MS_WITH_DESCR_JAR,
|
|
181 |
S_WITH_META_DESCR_BUILD_DIR, false);
|
|
182 |
generateJar(true, MODULE_TYPE.UNNAMED, S_JAR, S_BUILD_DIR, false);
|
|
183 |
generateJar(true, MODULE_TYPE.UNNAMED, S_WITH_DESCRIPTOR_JAR,
|
|
184 |
S_WITH_META_DESCR_BUILD_DIR, false);
|
|
185 |
//Generate regular/modular(depends on explicit/auto service)
|
|
186 |
//jars for client
|
|
187 |
done &= CompilerUtils.compile(C_SRC, C_BUILD_DIR);
|
|
188 |
generateJar(false, MODULE_TYPE.EXPLICIT, MC_JAR, C_BUILD_DIR, true);
|
|
189 |
generateJar(false, MODULE_TYPE.EXPLICIT,
|
|
190 |
MC_DEPENDS_ON_AUTO_SERVICE_JAR, C_BUILD_DIR, false);
|
|
191 |
generateJar(false, MODULE_TYPE.UNNAMED, C_JAR, C_BUILD_DIR, false);
|
|
192 |
System.out.format("%nArtifacts generated successfully? %s", done);
|
|
193 |
if (!done) {
|
|
194 |
throw new RuntimeException("Artifact generation failed");
|
|
195 |
}
|
|
196 |
} catch (IOException e) {
|
|
197 |
throw new RuntimeException(e);
|
|
198 |
}
|
|
199 |
}
|
|
200 |
|
|
201 |
/**
|
|
202 |
* Generate modular/regular jar based on module type for this test.
|
|
203 |
*/
|
|
204 |
private void generateJar(boolean isService, MODULE_TYPE moduleType,
|
|
205 |
Path jar, Path compilePath, boolean depends) throws IOException {
|
|
206 |
|
|
207 |
ModuleDescriptor mDescriptor = null;
|
|
208 |
if (isService) {
|
|
209 |
mDescriptor = generateModuleDescriptor(isService, moduleType, S_PKG,
|
|
210 |
S_PKG, S_INTERFACE, S_IMPL, null, M_REQUIRED, depends);
|
|
211 |
} else {
|
|
212 |
mDescriptor = generateModuleDescriptor(isService, moduleType, C_PKG,
|
|
213 |
C_PKG, S_INTERFACE, null, S_PKG, M_REQUIRED, depends);
|
|
214 |
}
|
|
215 |
generateJar(mDescriptor, jar, compilePath);
|
|
216 |
}
|
|
217 |
|
|
218 |
/**
|
|
219 |
* Holds Logic for the test client. This method will get called with each
|
|
220 |
* test parameter.
|
|
221 |
*/
|
|
222 |
@Override
|
|
223 |
public OutputAnalyzer executeTestClient(MODULE_TYPE cModuleType,
|
|
224 |
Path cJarPath, MODULE_TYPE sModuletype, Path sJarPath,
|
|
225 |
String... args) throws Exception {
|
|
226 |
|
|
227 |
OutputAnalyzer output = null;
|
|
228 |
try {
|
|
229 |
//For automated/explicit module type copy the corresponding
|
|
230 |
//jars to module base folder, which will be considered as
|
|
231 |
//module base path during execution.
|
|
232 |
if (!(cModuleType == MODULE_TYPE.UNNAMED
|
|
233 |
&& sModuletype == MODULE_TYPE.UNNAMED)) {
|
|
234 |
copyJarsToModuleBase(cModuleType, cJarPath, M_BASE_PATH);
|
|
235 |
copyJarsToModuleBase(sModuletype, sJarPath, M_BASE_PATH);
|
|
236 |
}
|
|
237 |
|
|
238 |
System.out.format("%nExecuting java client with required"
|
|
239 |
+ " custom service in class/module path.");
|
|
240 |
String mName = getModuleName(cModuleType, cJarPath,
|
|
241 |
C_PKG);
|
|
242 |
Path cmBasePath = (cModuleType != MODULE_TYPE.UNNAMED
|
|
243 |
|| sModuletype != MODULE_TYPE.UNNAMED) ? M_BASE_PATH : null;
|
|
244 |
String cPath = buildClassPath(cModuleType, cJarPath, sModuletype,
|
|
245 |
sJarPath);
|
|
246 |
output = ProcessTools.executeTestJava(
|
|
247 |
getJavaCommand(cmBasePath, cPath, mName, MAIN, VM_ARGS,
|
|
248 |
args)).outputTo(System.out).errorTo(System.out);
|
|
249 |
} finally {
|
|
250 |
//clean module path so that the modulepath can hold only
|
|
251 |
//the required jars for next run.
|
|
252 |
cleanModuleBasePath(M_BASE_PATH);
|
|
253 |
System.out.println("--------------------------------------------");
|
|
254 |
}
|
|
255 |
return output;
|
|
256 |
}
|
|
257 |
|
|
258 |
/**
|
|
259 |
* Decide the pre-generated client/service jar path for each test case
|
|
260 |
* based on client/service module type.
|
|
261 |
*/
|
|
262 |
@Override
|
|
263 |
public Path findJarPath(boolean service, MODULE_TYPE moduleType,
|
|
264 |
boolean addMetaDesc, boolean dependsOnServiceModule) {
|
|
265 |
if (service) {
|
|
266 |
if (moduleType == MODULE_TYPE.EXPLICIT) {
|
|
267 |
if (addMetaDesc) {
|
|
268 |
return MS_WITH_DESCR_JAR;
|
|
269 |
} else {
|
|
270 |
return MS_JAR;
|
|
271 |
}
|
|
272 |
} else {
|
|
273 |
if (addMetaDesc) {
|
|
274 |
return S_WITH_DESCRIPTOR_JAR;
|
|
275 |
} else {
|
|
276 |
return S_JAR;
|
|
277 |
}
|
|
278 |
}
|
|
279 |
} else {
|
|
280 |
if (moduleType == MODULE_TYPE.EXPLICIT) {
|
|
281 |
if (dependsOnServiceModule) {
|
|
282 |
return MC_JAR;
|
|
283 |
} else {
|
|
284 |
return MC_DEPENDS_ON_AUTO_SERVICE_JAR;
|
|
285 |
}
|
|
286 |
} else {
|
|
287 |
return C_JAR;
|
|
288 |
}
|
|
289 |
}
|
|
290 |
}
|
|
291 |
|
|
292 |
}
|