|
21 | 21 | import com.sun.tools.xjc.model.CClassInfo; |
22 | 22 | import com.sun.tools.xjc.outline.ClassOutline; |
23 | 23 | import com.sun.tools.xjc.outline.Outline; |
24 | | -import jakarta.xml.bind.JAXBContext; |
25 | 24 | import jakarta.xml.bind.JAXBElement; |
26 | | -import jakarta.xml.bind.JAXBException; |
27 | 25 | import jakarta.xml.bind.annotation.*; |
28 | 26 | import jakarta.xml.bind.annotation.adapters.XmlJavaTypeAdapter; |
29 | 27 | import jakarta.xml.bind.annotation.adapters.XmlJavaTypeAdapters; |
@@ -105,7 +103,7 @@ public boolean run(Outline outline, Options opt, ErrorHandler errorHandler) thro |
105 | 103 | } |
106 | 104 |
|
107 | 105 | if (opt.debugMode) { |
108 | | - fixJAXBDebugClass(outline); |
| 106 | + JaxbClassRefactorUtil.fixJAXBDebugClass(outline); |
109 | 107 | } |
110 | 108 |
|
111 | 109 | return true; |
@@ -322,135 +320,22 @@ private boolean removeWrapperClass(JDefinedClass wrapperClass, Set<JDefinedClass |
322 | 320 | allClasses.removeIf(definedClass -> definedClass.equals(wrapperClass)); |
323 | 321 | var wrapperClassName = wrapperClass.fullName(); |
324 | 322 | var existsReference = allClasses.stream() |
325 | | - .anyMatch(definedClass -> hasReference(definedClass, wrapperClassName)); |
| 323 | + .anyMatch(definedClass -> JaxbClassRefactorUtil.hasReference(definedClass, wrapperClassName)); |
326 | 324 | if (!existsReference) { |
327 | 325 | return removeWrapperClass(wrapperClass); |
328 | 326 | } |
329 | 327 |
|
330 | 328 | return false; |
331 | 329 | } |
332 | 330 |
|
333 | | - /** |
334 | | - * Returns true if the definedClass references the classFullName. |
335 | | - * |
336 | | - * @param definedClass the class to check for references |
337 | | - * @param classFullName the full name of the class to check for references |
338 | | - * @return true if the definedClass references the classFullName |
339 | | - */ |
340 | | - private boolean hasReference(JDefinedClass definedClass, String classFullName) { |
341 | | - var superClass = definedClass.superClass(); |
342 | | - var isRefBySuperClass = superClass != null && ClassNameDetector.detect(superClass.fullName(), classFullName); |
343 | | - |
344 | | - return isRefBySuperClass |
345 | | - || isRefByAnnotation(definedClass, classFullName) |
346 | | - || definedClass.fields().values().stream() |
347 | | - .anyMatch(field -> isRefInField(field, classFullName)) |
348 | | - |
349 | | - || definedClass.methods().stream() |
350 | | - .anyMatch(method -> isRefInMethod(method, classFullName)); |
351 | | - } |
352 | | - |
353 | | - /** |
354 | | - * Returns true if the field type or annotation references the classFullName. |
355 | | - */ |
356 | | - private boolean isRefInField(JFieldVar fieldVar, String classFullName) { |
357 | | - var typeName = fieldVar.type().fullName(); |
358 | | - var isRefByType = ClassNameDetector.detect(typeName, classFullName); |
359 | | - |
360 | | - return isRefByType || isRefByAnnotation(fieldVar, classFullName); |
361 | | - } |
362 | | - |
363 | | - /** |
364 | | - * Returns true if the method return type or annotation references the classFullName. |
365 | | - */ |
366 | | - private boolean isRefInMethod(JMethod method, String classFullName) { |
367 | | - var returnTypeName = method.type().fullName(); |
368 | | - var isRefByReturn = ClassNameDetector.detect(returnTypeName, classFullName); |
369 | | - |
370 | | - return isRefByReturn || isRefByAnnotation(method, classFullName) |
371 | | - || method.params().stream() |
372 | | - .anyMatch(param -> isRefInMethodParam(param, classFullName)); |
373 | | - } |
374 | | - |
375 | | - /** |
376 | | - * Returns true if the method parameter type or annotation references the classFullName. |
377 | | - */ |
378 | | - private boolean isRefInMethodParam(JVar param, String classFullName) { |
379 | | - var typeName = param.type().fullName(); |
380 | | - var isRefByType = ClassNameDetector.detect(typeName, classFullName); |
381 | | - |
382 | | - return isRefByType || isRefByAnnotation(param, classFullName); |
383 | | - } |
384 | | - |
385 | | - /** |
386 | | - * Returns true if the annotatable contains a reference to the classFullName. |
387 | | - */ |
388 | | - private boolean isRefByAnnotation(JAnnotatable annotatable, String classFullName) { |
389 | | - if (annotatable == null) { |
390 | | - return false; |
391 | | - } |
392 | | - return annotatable.annotations().stream() |
393 | | - .anyMatch(annotation -> isRefInAnnotation(annotation, classFullName)); |
394 | | - } |
395 | | - |
396 | | - /** |
397 | | - * Returns true if the annotation contains a reference to the classFullName. |
398 | | - */ |
399 | | - private boolean isRefInAnnotation(JAnnotationUse annotation, String classFullName) { |
400 | | - if (annotation == null) { |
401 | | - return false; |
402 | | - } |
403 | | - return annotation.getAnnotationMembers().values().stream().anyMatch(value -> switch (value) { |
404 | | - case JAnnotationClassValue classValue -> |
405 | | - ClassNameDetector.detect(classValue.type().fullName(), classFullName); |
406 | | - case JAnnotationArrayMember arrayMember -> isRefInAnnotationArrayMember(arrayMember, classFullName); |
407 | | - case JAnnotationUse annotationUse -> isRefInAnnotation(annotationUse, classFullName); |
408 | | - default -> false; |
409 | | - }); |
410 | | - } |
411 | | - |
412 | | - /** |
413 | | - * Returns true if the annotation array member contains a reference to the classFullName. |
414 | | - */ |
415 | | - private boolean isRefInAnnotationArrayMember(JAnnotationArrayMember arrayMember, String classFullName) { |
416 | | - if (arrayMember == null) { |
417 | | - return false; |
418 | | - } |
419 | | - return arrayMember.annotations2().stream().anyMatch(value -> switch (value) { |
420 | | - case JAnnotationClassValue classValue -> |
421 | | - ClassNameDetector.detect(classValue.type().fullName(), classFullName); |
422 | | - case JAnnotationArrayMember subArrayMember -> isRefInAnnotationArrayMember(subArrayMember, classFullName); |
423 | | - case JAnnotationUse annotationUse -> isRefInAnnotation(annotationUse, classFullName); |
424 | | - default -> false; |
425 | | - }); |
426 | | - } |
427 | | - |
428 | 331 | /** |
429 | 332 | * Removes the wrapper class from the parent container and ObjectFactory. |
430 | 333 | * |
431 | 334 | * @param wrapperClass The wrapper class to remove. |
432 | 335 | */ |
433 | 336 | private boolean removeWrapperClass(JDefinedClass wrapperClass) { |
434 | | - // Remove the wrapper class from the parent container |
435 | | - var parentContainer = wrapperClass.parentContainer(); |
436 | | - var classes = switch (parentContainer) { |
437 | | - case JDefinedClass clazz -> clazz.classes(); |
438 | | - case JPackage jPackage -> jPackage.classes(); |
439 | | - default -> throw new IllegalArgumentException("Unknown parent container type: " + parentContainer); |
440 | | - }; |
441 | | - while (classes.hasNext()) { |
442 | | - if (wrapperClass.equals(classes.next())) { |
443 | | - classes.remove(); |
444 | | - break; |
445 | | - } |
446 | | - } |
447 | | - |
448 | | - // Remove the wrapper class from the ObjectFactory |
449 | | - var jPackage = wrapperClass._package(); |
450 | | - var objectFactoryClass = jPackage._getClass("ObjectFactory"); |
451 | | - |
452 | | - objectFactoryClass.methods().removeIf(method -> |
453 | | - ClassNameDetector.detect(method.type().fullName(), wrapperClass.fullName())); |
| 337 | + JaxbClassRefactorUtil.removeFromParentContainer(wrapperClass); |
| 338 | + JaxbClassRefactorUtil.removeFromObjectFactory(wrapperClass); |
454 | 339 |
|
455 | 340 | return true; |
456 | 341 | } |
@@ -565,46 +450,6 @@ private boolean isConflictingJaxbAnnotation(String className) { |
565 | 450 | || className.equals(XmlTransient.class.getName()); |
566 | 451 | } |
567 | 452 |
|
568 | | - /** |
569 | | - * Fixes the JAXBDebug class in the JAXB outline. |
570 | | - * |
571 | | - * @param outline The JAXB outline to fix. |
572 | | - */ |
573 | | - private void fixJAXBDebugClass(Outline outline) { |
574 | | - var model = outline.getModel(); |
575 | | - var codeModel = outline.getCodeModel(); |
576 | | - var rootPackage = codeModel.rootPackage(); |
577 | | - var jaxbDebugClass = rootPackage._getClass("JAXBDebug"); |
578 | | - if (jaxbDebugClass == null) return; |
579 | | - |
580 | | - jaxbDebugClass.methods().removeIf(method -> method.name().equals("createContext")); |
581 | | - |
582 | | - var createContextMethod = jaxbDebugClass.method(JMod.PUBLIC | JMod.STATIC, JAXBContext.class, "createContext"); |
583 | | - var classLoader = createContextMethod.param(ClassLoader.class, "classLoader"); |
584 | | - createContextMethod._throws(JAXBException.class); |
585 | | - var invoke = codeModel.ref(JAXBContext.class).staticInvoke("newInstance"); |
586 | | - createContextMethod.body()._return(invoke); |
587 | | - |
588 | | - var packageContexts = outline.getAllPackageContexts(); |
589 | | - switch (model.strategy) { |
590 | | - case INTF_AND_IMPL -> { |
591 | | - var joiner = new StringJoiner(":"); |
592 | | - for (var packageOutline : packageContexts) { |
593 | | - joiner.add(packageOutline._package().name()); |
594 | | - } |
595 | | - invoke.arg(joiner.toString()).arg(classLoader); |
596 | | - } |
597 | | - case BEAN_ONLY -> { |
598 | | - for (var packageContext : packageContexts) { |
599 | | - var jPackage = packageContext._package(); |
600 | | - jPackage.classes().forEachRemaining(classInfo -> { |
601 | | - invoke.arg(JExpr.dotclass(classInfo)); |
602 | | - }); |
603 | | - } |
604 | | - } |
605 | | - default -> throw new IllegalStateException(); |
606 | | - } |
607 | | - } |
608 | 453 |
|
609 | 454 | /** |
610 | 455 | * Gets the annotation of the specified type for the given annotatable element. |
|
0 commit comments