33 import java.io.IOException; 34 import java.io.InputStream; 35 import java.lang.module.InvalidModuleDescriptorException; 36 import java.lang.module.ModuleDescriptor; 37 import java.lang.module.ModuleDescriptor.Builder; 38 import java.lang.module.ModuleDescriptor.Exports; 39 import java.lang.module.ModuleDescriptor.Opens; 40 import java.lang.module.ModuleDescriptor.Requires; 41 import java.lang.module.ModuleDescriptor.Provides; 42 import java.lang.module.ModuleDescriptor.Requires.Modifier; 43 import java.lang.module.ModuleDescriptor.Version; 44 import java.lang.reflect.Module; 45 import java.nio.ByteBuffer; 46 import java.util.ArrayList; 47 import java.util.Collections; 48 import java.util.EnumSet; 49 import java.util.HashSet; 50 import java.util.Iterator; 51 import java.util.List; 52 import java.util.Objects; 53 import java.util.Set; 54 import java.util.stream.Collectors; 55 56 import static java.lang.module.ModuleDescriptor.Requires.Modifier.*; 57 58 import jdk.internal.misc.SharedSecrets; 59 import jdk.internal.module.ModuleInfoWriter; 60 import org.testng.annotations.DataProvider; 61 import org.testng.annotations.Test; 62 import static org.testng.Assert.*; 63 64 @Test 65 public class ModuleDescriptorTest { 66 67 @DataProvider(name = "invalidjavaidentifiers") 68 public Object[][] invalidJavaIdentifiers() { 69 return new Object[][]{ 70 71 { null, null }, 72 { "1", null }, 73 { "1foo", null }, 74 { ".foo", null }, 75 { "foo.", null }, 76 { "[foo]", null }, 77 { "foo.1", null }, 971 Version v2 = Version.parse(vs); 972 assertEquals(v1, v2); 973 } 974 975 @Test(expectedExceptions = NullPointerException.class ) 976 public void testNullVersion1() { 977 ModuleDescriptor.newModule("foo").version((Version) null); 978 } 979 980 @Test(expectedExceptions = IllegalArgumentException.class ) 981 public void testNullVersion2() { 982 ModuleDescriptor.newModule("foo").version((String) null); 983 } 984 985 @Test(expectedExceptions = IllegalArgumentException.class ) 986 public void testEmptyVersion() { 987 ModuleDescriptor.newModule("foo").version(""); 988 } 989 990 991 // toNameAndVersion 992 993 public void testToNameAndVersion() { 994 ModuleDescriptor md1 = ModuleDescriptor.newModule("foo").build(); 995 assertEquals(md1.toNameAndVersion(), "foo"); 996 997 ModuleDescriptor md2 = ModuleDescriptor.newModule("foo").version("1.0").build(); 998 assertEquals(md2.toNameAndVersion(), "foo@1.0"); 999 } 1000 1001 1002 // open modules 1003 1004 public void testOpenModule() { 1005 ModuleDescriptor descriptor = ModuleDescriptor.newOpenModule("foo") 1006 .requires("bar") 1007 .exports("p") 1008 .provides("p.Service", List.of("q.ServiceImpl")) 1009 .build(); 1010 1153 1154 public void testMainClass() { 1155 String mainClass 1156 = ModuleDescriptor.newModule("foo").mainClass("p.Main").build().mainClass().get(); 1157 assertEquals(mainClass, "p.Main"); 1158 } 1159 1160 @Test(expectedExceptions = IllegalArgumentException.class) 1161 public void testMainClassWithSimpleIdentifier() { 1162 ModuleDescriptor.newModule("foo").mainClass("Main"); 1163 } 1164 1165 @Test(dataProvider = "invalidjavaidentifiers", 1166 expectedExceptions = IllegalArgumentException.class ) 1167 public void testMainClassWithBadName(String mainClass, String ignore) { 1168 Builder builder = ModuleDescriptor.newModule("foo"); 1169 builder.mainClass(mainClass); 1170 } 1171 1172 1173 // osName 1174 1175 public void testOsName() { 1176 String osName = ModuleDescriptor.newModule("foo").osName("Linux").build().osName().get(); 1177 assertEquals(osName, "Linux"); 1178 } 1179 1180 @Test(expectedExceptions = IllegalArgumentException.class) 1181 public void testNullOsName() { 1182 ModuleDescriptor.newModule("foo").osName(null); 1183 } 1184 1185 @Test(expectedExceptions = IllegalArgumentException.class) 1186 public void testEmptyOsName() { 1187 ModuleDescriptor.newModule("foo").osName(""); 1188 } 1189 1190 1191 // osArch 1192 1193 public void testOsArch() { 1194 String osArch = ModuleDescriptor.newModule("foo").osName("arm").build().osName().get(); 1195 assertEquals(osArch, "arm"); 1196 } 1197 1198 @Test(expectedExceptions = IllegalArgumentException.class) 1199 public void testNullOsArch() { 1200 ModuleDescriptor.newModule("foo").osArch(null); 1201 } 1202 1203 @Test(expectedExceptions = IllegalArgumentException.class) 1204 public void testEmptyOsArch() { 1205 ModuleDescriptor.newModule("foo").osArch(""); 1206 } 1207 1208 1209 // osVersion 1210 1211 public void testOsVersion() { 1212 String osVersion = ModuleDescriptor.newModule("foo").osName("11.2").build().osName().get(); 1213 assertEquals(osVersion, "11.2"); 1214 } 1215 1216 @Test(expectedExceptions = IllegalArgumentException.class) 1217 public void testNullOsVersion() { 1218 ModuleDescriptor.newModule("foo").osVersion(null); 1219 } 1220 1221 @Test(expectedExceptions = IllegalArgumentException.class) 1222 public void testEmptyOsVersion() { 1223 ModuleDescriptor.newModule("foo").osVersion(""); 1224 } 1225 1226 // reads 1227 1228 private static InputStream EMPTY_INPUT_STREAM = new InputStream() { 1229 @Override 1230 public int read() { 1231 return -1; 1232 } 1233 }; 1234 1235 private static InputStream FAILING_INPUT_STREAM = new InputStream() { 1236 @Override 1237 public int read() throws IOException { 1238 throw new IOException(); 1239 } 1240 }; 1241 1242 // basic test reading module-info.class 1243 public void testRead() throws Exception { 1244 Module base = Object.class.getModule(); 1245 1246 try (InputStream in = base.getResourceAsStream("module-info.class")) { 1247 ModuleDescriptor descriptor = ModuleDescriptor.read(in); 1248 assertTrue(in.read() == -1); // all bytes read 1249 assertEquals(descriptor.name(), "java.base"); 1250 } 1251 1252 try (InputStream in = base.getResourceAsStream("module-info.class")) { 1253 ByteBuffer bb = ByteBuffer.wrap(in.readAllBytes()); 1254 ModuleDescriptor descriptor = ModuleDescriptor.read(bb); 1255 assertFalse(bb.hasRemaining()); // no more remaining bytes 1256 assertEquals(descriptor.name(), "java.base"); 1257 } 1258 } 1259 /** 1260 * Test ModuleDescriptor with a packager finder 1261 */ 1262 public void testReadsWithPackageFinder() throws Exception { 1263 ModuleDescriptor descriptor = ModuleDescriptor.newModule("foo") 1264 .requires("java.base") 1265 .build(); 1266 1267 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 1268 ModuleInfoWriter.write(descriptor, baos); 1269 ByteBuffer bb = ByteBuffer.wrap(baos.toByteArray()); 1270 1271 descriptor = ModuleDescriptor.read(bb, () -> Set.of("p", "q")); 1272 1273 assertTrue(descriptor.packages().size() == 2); 1274 assertTrue(descriptor.packages().contains("p")); 1275 assertTrue(descriptor.packages().contains("q")); 1276 } 1277 1278 /** | 33 import java.io.IOException; 34 import java.io.InputStream; 35 import java.lang.module.InvalidModuleDescriptorException; 36 import java.lang.module.ModuleDescriptor; 37 import java.lang.module.ModuleDescriptor.Builder; 38 import java.lang.module.ModuleDescriptor.Exports; 39 import java.lang.module.ModuleDescriptor.Opens; 40 import java.lang.module.ModuleDescriptor.Requires; 41 import java.lang.module.ModuleDescriptor.Provides; 42 import java.lang.module.ModuleDescriptor.Requires.Modifier; 43 import java.lang.module.ModuleDescriptor.Version; 44 import java.lang.reflect.Module; 45 import java.nio.ByteBuffer; 46 import java.util.ArrayList; 47 import java.util.Collections; 48 import java.util.EnumSet; 49 import java.util.HashSet; 50 import java.util.Iterator; 51 import java.util.List; 52 import java.util.Objects; 53 import java.util.Optional; 54 import java.util.Set; 55 import java.util.stream.Collectors; 56 57 import static java.lang.module.ModuleDescriptor.Requires.Modifier.*; 58 59 import jdk.internal.misc.JavaLangModuleAccess; 60 import jdk.internal.misc.SharedSecrets; 61 import jdk.internal.module.ModuleInfoWriter; 62 import org.testng.annotations.DataProvider; 63 import org.testng.annotations.Test; 64 import static org.testng.Assert.*; 65 66 @Test 67 public class ModuleDescriptorTest { 68 69 @DataProvider(name = "invalidjavaidentifiers") 70 public Object[][] invalidJavaIdentifiers() { 71 return new Object[][]{ 72 73 { null, null }, 74 { "1", null }, 75 { "1foo", null }, 76 { ".foo", null }, 77 { "foo.", null }, 78 { "[foo]", null }, 79 { "foo.1", null }, 973 Version v2 = Version.parse(vs); 974 assertEquals(v1, v2); 975 } 976 977 @Test(expectedExceptions = NullPointerException.class ) 978 public void testNullVersion1() { 979 ModuleDescriptor.newModule("foo").version((Version) null); 980 } 981 982 @Test(expectedExceptions = IllegalArgumentException.class ) 983 public void testNullVersion2() { 984 ModuleDescriptor.newModule("foo").version((String) null); 985 } 986 987 @Test(expectedExceptions = IllegalArgumentException.class ) 988 public void testEmptyVersion() { 989 ModuleDescriptor.newModule("foo").version(""); 990 } 991 992 993 @DataProvider(name = "unparseableVersions") 994 public Object[][] unparseableVersions() { 995 return new Object[][]{ 996 997 { null, "A1" }, // no version < unparseable 998 { "A1", "A2" }, // unparseable < unparseable 999 { "A1", "1.0" }, // unparseable < parseable 1000 1001 }; 1002 } 1003 1004 /** 1005 * Basic test for unparseable module versions 1006 */ 1007 @Test(dataProvider = "unparseableVersions") 1008 public void testUnparseableModuleVersion(String vs1, String vs2) { 1009 ModuleDescriptor descriptor1 = newModule("m", vs1); 1010 ModuleDescriptor descriptor2 = newModule("m", vs2); 1011 1012 if (vs1 != null && !isParsableVersion(vs1)) { 1013 assertFalse(descriptor1.version().isPresent()); 1014 assertTrue(descriptor1.rawVersion().isPresent()); 1015 assertEquals(descriptor1.rawVersion().get(), vs1); 1016 } 1017 1018 if (vs2 != null && !isParsableVersion(vs2)) { 1019 assertFalse(descriptor2.version().isPresent()); 1020 assertTrue(descriptor2.rawVersion().isPresent()); 1021 assertEquals(descriptor2.rawVersion().get(), vs2); 1022 } 1023 1024 assertFalse(descriptor1.equals(descriptor2)); 1025 assertFalse(descriptor2.equals(descriptor1)); 1026 assertTrue(descriptor1.compareTo(descriptor2) == -1); 1027 assertTrue(descriptor2.compareTo(descriptor1) == 1); 1028 } 1029 1030 /** 1031 * Basic test for requiring a module with an unparseable version recorded 1032 * at compile version. 1033 */ 1034 @Test(dataProvider = "unparseableVersions") 1035 public void testUnparseableCompiledVersion(String vs1, String vs2) { 1036 Requires r1 = newRequires("m", vs1); 1037 Requires r2 = newRequires("m", vs2); 1038 1039 if (vs1 != null && !isParsableVersion(vs1)) { 1040 assertFalse(r1.compiledVersion().isPresent()); 1041 assertTrue(r1.rawCompiledVersion().isPresent()); 1042 assertEquals(r1.rawCompiledVersion().get(), vs1); 1043 } 1044 1045 if (vs2 != null && !isParsableVersion(vs2)) { 1046 assertFalse(r2.compiledVersion().isPresent()); 1047 assertTrue(r2.rawCompiledVersion().isPresent()); 1048 assertEquals(r2.rawCompiledVersion().get(), vs2); 1049 } 1050 1051 assertFalse(r1.equals(r2)); 1052 assertFalse(r2.equals(r1)); 1053 assertTrue(r1.compareTo(r2) == -1); 1054 assertTrue(r2.compareTo(r1) == 1); 1055 } 1056 1057 private ModuleDescriptor newModule(String name, String vs) { 1058 JavaLangModuleAccess JLMA = SharedSecrets.getJavaLangModuleAccess(); 1059 Builder builder = JLMA.newModuleBuilder(name, false, Set.of()); 1060 if (vs != null) 1061 builder.version(vs); 1062 builder.requires("java.base"); 1063 ByteBuffer bb = ModuleInfoWriter.toByteBuffer(builder.build()); 1064 return ModuleDescriptor.read(bb); 1065 } 1066 1067 private Requires newRequires(String name, String vs) { 1068 JavaLangModuleAccess JLMA = SharedSecrets.getJavaLangModuleAccess(); 1069 Builder builder = JLMA.newModuleBuilder("foo", false, Set.of()); 1070 if (vs == null) { 1071 builder.requires(name); 1072 } else { 1073 JLMA.requires(builder, Set.of(), name, vs); 1074 } 1075 Set<ModuleDescriptor.Requires> requires = builder.build().requires(); 1076 Iterator<ModuleDescriptor.Requires> iterator = requires.iterator(); 1077 ModuleDescriptor.Requires r = iterator.next(); 1078 if (r.name().equals("java.base")) { 1079 r = iterator.next(); 1080 } 1081 return r; 1082 } 1083 1084 private boolean isParsableVersion(String vs) { 1085 try { 1086 Version.parse(vs); 1087 return true; 1088 } catch (IllegalArgumentException e) { 1089 return false; 1090 } 1091 } 1092 1093 1094 // toNameAndVersion 1095 1096 public void testToNameAndVersion() { 1097 ModuleDescriptor md1 = ModuleDescriptor.newModule("foo").build(); 1098 assertEquals(md1.toNameAndVersion(), "foo"); 1099 1100 ModuleDescriptor md2 = ModuleDescriptor.newModule("foo").version("1.0").build(); 1101 assertEquals(md2.toNameAndVersion(), "foo@1.0"); 1102 } 1103 1104 1105 // open modules 1106 1107 public void testOpenModule() { 1108 ModuleDescriptor descriptor = ModuleDescriptor.newOpenModule("foo") 1109 .requires("bar") 1110 .exports("p") 1111 .provides("p.Service", List.of("q.ServiceImpl")) 1112 .build(); 1113 1256 1257 public void testMainClass() { 1258 String mainClass 1259 = ModuleDescriptor.newModule("foo").mainClass("p.Main").build().mainClass().get(); 1260 assertEquals(mainClass, "p.Main"); 1261 } 1262 1263 @Test(expectedExceptions = IllegalArgumentException.class) 1264 public void testMainClassWithSimpleIdentifier() { 1265 ModuleDescriptor.newModule("foo").mainClass("Main"); 1266 } 1267 1268 @Test(dataProvider = "invalidjavaidentifiers", 1269 expectedExceptions = IllegalArgumentException.class ) 1270 public void testMainClassWithBadName(String mainClass, String ignore) { 1271 Builder builder = ModuleDescriptor.newModule("foo"); 1272 builder.mainClass(mainClass); 1273 } 1274 1275 1276 // reads 1277 1278 private static InputStream EMPTY_INPUT_STREAM = new InputStream() { 1279 @Override 1280 public int read() { 1281 return -1; 1282 } 1283 }; 1284 1285 private static InputStream FAILING_INPUT_STREAM = new InputStream() { 1286 @Override 1287 public int read() throws IOException { 1288 throw new IOException(); 1289 } 1290 }; 1291 1292 /** 1293 * Basic test reading module-info.class 1294 */ 1295 public void testRead() throws Exception { 1296 Module base = Object.class.getModule(); 1297 1298 try (InputStream in = base.getResourceAsStream("module-info.class")) { 1299 ModuleDescriptor descriptor = ModuleDescriptor.read(in); 1300 assertTrue(in.read() == -1); // all bytes read 1301 assertEquals(descriptor.name(), "java.base"); 1302 } 1303 1304 try (InputStream in = base.getResourceAsStream("module-info.class")) { 1305 ByteBuffer bb = ByteBuffer.wrap(in.readAllBytes()); 1306 ModuleDescriptor descriptor = ModuleDescriptor.read(bb); 1307 assertFalse(bb.hasRemaining()); // no more remaining bytes 1308 assertEquals(descriptor.name(), "java.base"); 1309 } 1310 } 1311 1312 /** 1313 * Test ModuleDescriptor with a packager finder 1314 */ 1315 public void testReadsWithPackageFinder() throws Exception { 1316 ModuleDescriptor descriptor = ModuleDescriptor.newModule("foo") 1317 .requires("java.base") 1318 .build(); 1319 1320 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 1321 ModuleInfoWriter.write(descriptor, baos); 1322 ByteBuffer bb = ByteBuffer.wrap(baos.toByteArray()); 1323 1324 descriptor = ModuleDescriptor.read(bb, () -> Set.of("p", "q")); 1325 1326 assertTrue(descriptor.packages().size() == 2); 1327 assertTrue(descriptor.packages().contains("p")); 1328 assertTrue(descriptor.packages().contains("q")); 1329 } 1330 1331 /** |