1818import static io .github .ascopes .jct .utils .IterableUtils .requireNonNullValues ;
1919import static java .util .Objects .requireNonNull ;
2020
21+ import io .github .ascopes .jct .compilers .impl .JctCompilationFactoryImpl ;
2122import io .github .ascopes .jct .compilers .impl .JctCompilationImpl ;
22- import io .github .ascopes .jct .compilers .impl .JctJsr199Interop ;
23+ import io .github .ascopes .jct .diagnostics .TracingDiagnosticListener ;
24+ import io .github .ascopes .jct .ex .JctCompilerException ;
2325import io .github .ascopes .jct .filemanagers .AnnotationProcessorDiscovery ;
26+ import io .github .ascopes .jct .filemanagers .JctFileManagerFactory ;
2427import io .github .ascopes .jct .filemanagers .LoggingMode ;
2528import io .github .ascopes .jct .workspaces .Workspace ;
29+ import java .io .IOException ;
2630import java .nio .charset .Charset ;
2731import java .util .ArrayList ;
2832import java .util .Collection ;
2933import java .util .List ;
3034import java .util .Locale ;
3135import javax .annotation .Nullable ;
36+ import javax .annotation .WillNotClose ;
3237import javax .annotation .concurrent .NotThreadSafe ;
3338import javax .annotation .processing .Processor ;
3439import org .apiguardian .api .API ;
5560@ API (since = "0.0.1" , status = Status .STABLE )
5661@ NotThreadSafe
5762public abstract class AbstractJctCompiler <A extends AbstractJctCompiler <A >>
58- implements JctCompiler <A , JctCompilationImpl > {
63+ implements JctCompiler <A , JctCompilation > {
5964
6065 private final List <Processor > annotationProcessors ;
6166 private final List <String > annotationProcessorOptions ;
@@ -113,19 +118,13 @@ protected AbstractJctCompiler(String defaultName) {
113118 }
114119
115120 @ Override
116- public JctCompilationImpl compile (Workspace workspace ) {
117- var flagBuilder = getJctFlagBuilderFactory ().createFlagBuilder ();
118- var compiler = getJsr199CompilerFactory ().createCompiler ();
119-
120- return JctJsr199Interop .compile (workspace , myself (), compiler , flagBuilder , null );
121+ public JctCompilation compile (Workspace workspace ) {
122+ return compileInternal (workspace , null );
121123 }
122124
123125 @ Override
124- public JctCompilationImpl compile (Workspace workspace , Collection <String > classNames ) {
125- var flagBuilder = getJctFlagBuilderFactory ().createFlagBuilder ();
126- var compiler = getJsr199CompilerFactory ().createCompiler ();
127-
128- return JctJsr199Interop .compile (workspace , myself (), compiler , flagBuilder , classNames );
126+ public JctCompilation compile (Workspace workspace , Collection <String > classNames ) {
127+ return compileInternal (workspace , classNames );
129128 }
130129
131130 @ Override
@@ -249,6 +248,19 @@ public A addCompilerOptions(Iterable<String> compilerOptions) {
249248 return myself ();
250249 }
251250
251+ @ Override
252+ public String getEffectiveRelease () {
253+ if (release != null ) {
254+ return release ;
255+ }
256+
257+ if (target != null ) {
258+ return target ;
259+ }
260+
261+ return getDefaultRelease ();
262+ }
263+
252264 @ Nullable
253265 @ Override
254266 public String getRelease () {
@@ -432,14 +444,37 @@ public final String toString() {
432444 *
433445 * @return the factory.
434446 */
435- public abstract JctFlagBuilderFactory getJctFlagBuilderFactory ();
447+ public abstract JctFlagBuilderFactory getFlagBuilderFactory ();
436448
437449 /**
438450 * Get the JSR-199 compiler factory to use for initialising an internal compiler.
439451 *
440452 * @return the factory.
441453 */
442- public abstract Jsr199CompilerFactory getJsr199CompilerFactory ();
454+ public abstract Jsr199CompilerFactory getCompilerFactory ();
455+
456+ /**
457+ * Get the file manager factory to use for building a file manager during compilation.
458+ *
459+ * @return the factory.
460+ */
461+ public abstract JctFileManagerFactory getFileManagerFactory ();
462+
463+ /**
464+ * Get the compilation factory to use for building a compilation.
465+ *
466+ * <p>By default, this uses a common internal implementation that is designed to work with
467+ * compilers that have interfaces the same as, and behave the same as Javac.
468+ *
469+ * <p>Some obscure compiler implementations with potentially satanic rituals for initialising
470+ * and configuring components correctly may need to provide a custom implementation here instead.
471+ * In this case, this method should be overridden.
472+ *
473+ * @return the compilation factory.
474+ */
475+ public JctCompilationFactory getCompilationFactory () {
476+ return new JctCompilationFactoryImpl (this );
477+ }
443478
444479 /**
445480 * {@inheritDoc}
@@ -460,4 +495,47 @@ protected final A myself() {
460495
461496 return me ;
462497 }
498+
499+ /**
500+ * Build the list of flags from this compiler object using the flag builder.
501+ *
502+ * <p>Implementations should not need to override this unless there is a special edge case
503+ * that needs configuring differently. This is exposed to assist in these kinds of cases.
504+ *
505+ * @param flagBuilder the flag builder to apply the flag configuration to.
506+ * @return the string flags to use.
507+ */
508+ protected List <String > buildFlags (JctFlagBuilder flagBuilder ) {
509+ return flagBuilder
510+ .annotationProcessorOptions (getAnnotationProcessorOptions ())
511+ .showDeprecationWarnings (isShowDeprecationWarnings ())
512+ .failOnWarnings (isFailOnWarnings ())
513+ .compilerOptions (getCompilerOptions ())
514+ .previewFeatures (isPreviewFeatures ())
515+ .release (getRelease ())
516+ .source (getSource ())
517+ .target (getTarget ())
518+ .verbose (isVerbose ())
519+ .showWarnings (isShowWarnings ())
520+ .build ();
521+ }
522+
523+ @ SuppressWarnings ("NullableProblems" ) // https://youtrack.jetbrains.com/issue/IDEA-311124
524+ private JctCompilation compileInternal (
525+ @ WillNotClose Workspace workspace ,
526+ @ Nullable Collection <String > classNames
527+ ) {
528+ var fileManagerFactory = getFileManagerFactory ();
529+ var flagBuilderFactory = getFlagBuilderFactory ();
530+ var compilerFactory = getCompilerFactory ();
531+ var compilationFactory = getCompilationFactory ();
532+
533+ try (var fileManager = fileManagerFactory .createFileManager (workspace )) {
534+ var flags = buildFlags (flagBuilderFactory .createFlagBuilder ());
535+ var compiler = compilerFactory .createCompiler ();
536+ return compilationFactory .createCompilation (flags , fileManager , compiler , classNames );
537+ } catch (IOException ex ) {
538+ throw new JctCompilerException ("Failed to close file manager" , ex );
539+ }
540+ }
463541}
0 commit comments