Quarkus notes (1)

Background information I suggest to read the following for grabbing basic idea on Quarkus startup process. How Quarkus use build time to start your application faster Writing Your Own Extension Program entry point of development mode io.quarkus.runtime.Quarkus#run Since synthetic class io.quarkus.runner.ApplicationImpl is not exists, so call io.quarkus.runtime.Quarkus#launchFromIDE Program entry point of production mode io.quarkus.bootstrap.runner.QuarkusEntryPoint#main io.quarkus.bootstrap.runner.QuarkusEntryPoint#doRun io.quarkus.runner.GeneratedMain#main. Synthetic class which generated by quarkus, the method has only one statement. io.quarkus.runtime.Quarkus#run io.quarkus.runner.ApplicationImpl#doStart (Synthetic class also) About quarkus-app/quarkus/quarkus-application.dat file It store jar files and classes used, so that the special designed ClassLoader (io.quarkus.bootstrap.runner.RunnerClassLoader) can use this information to locate class quickly. File serialization method: io.quarkus.bootstrap.runner.SerializedApplication#write File deserialization method: io.quarkus.bootstrap.runner.SerializedApplication#read About synthetic class io.quarkus.runner.ApplicationImpl This is from a sample program which used RESTEasy and contain a resource org.acme.GreetingResource only. This is generated by io.quarkus.deployment.steps.MainClassBuildStep. // $FF: synthetic class public class ApplicationImpl extends Application { static Logger LOG; public static StartupContext STARTUP_CONTEXT; private static final String __QUARKUS_ANALYTICS_QUARKUS_VERSION; public ApplicationImpl() { super(false); } static { DisabledInitialContextManager.register(); System.setProperty("java.util.logging.manager", "org.jboss.logmanager.LogManager"); System.setProperty("java.util.concurrent.ForkJoinPool.common.threadFactory", "io.quarkus.bootstrap.forkjoin.QuarkusForkJoinWorkerThreadFactory"); System.setProperty("dev.resteasy.exception.mapper", "false"); System.setProperty("logging.initial-configurator.min-level", "500"); System.setProperty("io.netty.allocator.maxOrder", "3"); System.setProperty("io.netty.machineId", "00:00:00:00:00:00:00:00"); System.setProperty("io.quarkus.security.http.test-if-basic-auth-implicitly-required", "true"); LaunchMode.set(LaunchMode.NORMAL); StepTiming.configureEnabled(); ExecutionModeManager.staticInit(); Timing.staticInitStarted(false); Config.ensureInitialized(); LOG = Logger.getLogger("io.quarkus.application"); __QUARKUS_ANALYTICS_QUARKUS_VERSION = "__quarkus_analytics__quarkus.version=3.17.7"; StartupContext var0 = new StartupContext(); STARTUP_CONTEXT = var0; try { StepTiming.configureStart(); ((StartupTask)(new LoggingResourceProcessor.setupLoggingStaticInit2062061316())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new MutinyProcessor.buildTimeInit521613965())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new VertxProcessor.currentContextFactory166049300())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new VertxCoreProcessor.ioThreadDetector1463825589())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new NativeImageConfigBuildStep.build282698227())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new BlockingOperationControlBuildStep.blockingOP558072755())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new ResteasyStandaloneBuildStep.addDefaultAuthFailureHandler334719971())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new SmallRyeContextPropagationProcessor.buildStatic677493008())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new VirtualThreadsProcessor.setup282338138())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new SyntheticBeansProcessor.initStatic1190120725())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new ConfigBuildStep.validateStaticInitConfigProperty682828288())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new ArcProcessor.initializeContainer1770303700())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new ArcProcessor.notifyBeanContainerListeners1304312071())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new ResteasyCommonProcessor.setupResteasyInjection131820800())).deploy(var0); StepTiming.printStepTime(var0); ((StartupTask)(new ResteasyStandaloneBuildStep.staticInit345281060())

Jan 19, 2025 - 01:52
Quarkus notes (1)

Background information

I suggest to read the following for grabbing basic idea on Quarkus startup process.

  1. How Quarkus use build time to start your application faster
  2. Writing Your Own Extension

Program entry point of development mode

  1. io.quarkus.runtime.Quarkus#run
  2. Since synthetic class io.quarkus.runner.ApplicationImpl is not exists, so call io.quarkus.runtime.Quarkus#launchFromIDE

Program entry point of production mode

  1. io.quarkus.bootstrap.runner.QuarkusEntryPoint#main
  2. io.quarkus.bootstrap.runner.QuarkusEntryPoint#doRun
  3. io.quarkus.runner.GeneratedMain#main. Synthetic class which generated by quarkus, the method has only one statement.
  4. io.quarkus.runtime.Quarkus#run
  5. io.quarkus.runner.ApplicationImpl#doStart (Synthetic class also)

About quarkus-app/quarkus/quarkus-application.dat file

It store jar files and classes used, so that the special designed ClassLoader (io.quarkus.bootstrap.runner.RunnerClassLoader) can use this information to locate class quickly.

  • File serialization method: io.quarkus.bootstrap.runner.SerializedApplication#write
  • File deserialization method: io.quarkus.bootstrap.runner.SerializedApplication#read

About synthetic class io.quarkus.runner.ApplicationImpl

This is from a sample program which used RESTEasy and contain a resource org.acme.GreetingResource only. This is generated by io.quarkus.deployment.steps.MainClassBuildStep.

// $FF: synthetic class
public class ApplicationImpl extends Application {
    static Logger LOG;
    public static StartupContext STARTUP_CONTEXT;
    private static final String __QUARKUS_ANALYTICS_QUARKUS_VERSION;

    public ApplicationImpl() {
        super(false);
    }

    static {
        DisabledInitialContextManager.register();
        System.setProperty("java.util.logging.manager", "org.jboss.logmanager.LogManager");
        System.setProperty("java.util.concurrent.ForkJoinPool.common.threadFactory", "io.quarkus.bootstrap.forkjoin.QuarkusForkJoinWorkerThreadFactory");
        System.setProperty("dev.resteasy.exception.mapper", "false");
        System.setProperty("logging.initial-configurator.min-level", "500");
        System.setProperty("io.netty.allocator.maxOrder", "3");
        System.setProperty("io.netty.machineId", "00:00:00:00:00:00:00:00");
        System.setProperty("io.quarkus.security.http.test-if-basic-auth-implicitly-required", "true");
        LaunchMode.set(LaunchMode.NORMAL);
        StepTiming.configureEnabled();
        ExecutionModeManager.staticInit();
        Timing.staticInitStarted(false);
        Config.ensureInitialized();
        LOG = Logger.getLogger("io.quarkus.application");
        __QUARKUS_ANALYTICS_QUARKUS_VERSION = "__quarkus_analytics__quarkus.version=3.17.7";
        StartupContext var0 = new StartupContext();
        STARTUP_CONTEXT = var0;

        try {
            StepTiming.configureStart();
            ((StartupTask)(new LoggingResourceProcessor.setupLoggingStaticInit2062061316())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new MutinyProcessor.buildTimeInit521613965())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new VertxProcessor.currentContextFactory166049300())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new VertxCoreProcessor.ioThreadDetector1463825589())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new NativeImageConfigBuildStep.build282698227())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new BlockingOperationControlBuildStep.blockingOP558072755())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new ResteasyStandaloneBuildStep.addDefaultAuthFailureHandler334719971())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new SmallRyeContextPropagationProcessor.buildStatic677493008())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new VirtualThreadsProcessor.setup282338138())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new SyntheticBeansProcessor.initStatic1190120725())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new ConfigBuildStep.validateStaticInitConfigProperty682828288())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new ArcProcessor.initializeContainer1770303700())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new ArcProcessor.notifyBeanContainerListeners1304312071())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new ResteasyCommonProcessor.setupResteasyInjection131820800())).deploy(var0);
            StepTiming.printStepTime(var0);
            ((StartupTask)(new ResteasyStandaloneBuildStep.staticInit345281060())).deploy(var0);
            StepTiming.printStepTime(var0);
        } catch (Throwable var2) {
            ApplicationStateNotification.notifyStartupFailed(var2);
            var0.close();
            throw (Throwable)(new RuntimeException("Failed to start quarkus", var2));
        }
    }

    protected final void doStart(String[] var1) {
        System.setProperty("java.util.logging.manager", "org.jboss.logmanager.LogManager");
        System.setProperty("java.util.concurrent.ForkJoinPool.common.threadFactory", "io.quarkus.bootstrap.forkjoin.QuarkusForkJoinWorkerThreadFactory");
        System.setProperty("dev.resteasy.exception.mapper", "false");
        System.setProperty("logging.initial-configurator.min-level", "500");
        System.setProperty("io.netty.allocator.maxOrder", "3");
        System.setProperty("io.netty.machineId", "00:00:00:00:00:00:00:00");
        System.setProperty("io.quarkus.security.http.test-if-basic-auth-implicitly-required", "true");
        NativeImageRuntimePropertiesRecorder.doRuntime();
        ExecutionModeManager.runtimeInit();
        Timing.mainStarted();
        StartupContext var2 = STARTUP_CONTEXT;
        var2.setCommandLineArguments(var1);
        StepTiming.configureEnabled();

        try {
            StepTiming.configureStart();
            ((StartupTask)(new RuntimeConfigSetup())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new NettyProcessor.eagerlyInitClass1832577802())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new ConfigGenerationBuildStep.releaseConfigOnShutdown561040398())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new DeprecatedRuntimePropertiesBuildStep.reportDeprecatedProperties2011807353())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxCoreProcessor.eventLoopCount1012482323())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxHttpProcessor.cors1355075351())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxCoreProcessor.createVertxThreadFactory1036986175())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxCoreProcessor.createVertxContextHandlers780169010())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new ConfigGenerationBuildStep.checkForBuildTimeConfigChange1532146938())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new ThreadPoolSetup.createExecutor2117483448())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new MutinyProcessor.runtimeInit866247078())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxCoreProcessor.build1754895780())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new SmallRyeContextPropagationProcessor.build1909893707())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new BannerProcessor.recordBanner921118789())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new ArcProcessor.setupExecutor1831044820())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxHttpProcessor.bodyHandler1176441513())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxHttpProcessor.preinitializeRouter1141331088())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new ConfigGenerationBuildStep.unknownConfigFiles604069353())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new LoggingResourceProcessor.setupLoggingRuntimeInit1041640541())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxProcessor.build1689596782())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new CertificatesProcessor.initializeCertificate877524439())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new SyntheticBeansProcessor.initRuntime975230615())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new InitializationTaskProcessor.startApplicationInitializer180820092())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new ConfigBuildStep.validateRuntimeConfigProperty1282080724())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new ConfigBuildStep.registerConfigClasses1377682816())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new ResteasyStandaloneBuildStep.boot345593974())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxHttpProcessor.initializeRouter938601780())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxHttpProcessor.finalizeRouter992900573())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new LifecycleEventsBuildStep.startupEvent1144526294())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new ShutdownListenerBuildStep.setupShutdown1533204416())).deploy(var2);
            StepTiming.printStepTime(var2);
            ((StartupTask)(new VertxHttpProcessor.openSocket1753087980())).deploy(var2);
            StepTiming.printStepTime(var2);
            ExecutionModeManager.running();
            List var3 = ConfigUtils.getProfiles();
            Timing.printStartupTime("code-with-quarkus", "1.0.0-SNAPSHOT", "3.17.7", "cdi, resteasy, smallrye-context-propagation, vertx", var3, false, false);
            QuarkusConsole.start();
        } catch (PreventFurtherStepsException var8) {
            var2.close();
        } catch (Throwable var9) {
            QuarkusDelayedHandler var6 = InitialConfigurator.DELAYED_HANDLER;
            if (!var6.isActivated()) {
                Handler[] var4 = new Handler[1];
                ConsoleHandler var5 = new ConsoleHandler();
                var4[0] = (Handler)var5;
                var6.setHandlers(var4);
            }

            var2.close();
            throw (Throwable)(new RuntimeException("Failed to start quarkus", var9));
        }

    }

    protected final void doStop() {
        ExecutionModeManager.unset();
        STARTUP_CONTEXT.close();
    }

    public String getName() {
        return "code-with-quarkus";
    }
}

Most of the classes exist are synthetic classes and stored in io/quarkus/deployment/steps directory in quarkus-app/quarkus/generated-bytecode.jar file. For example io.quarkus.deployment.steps.VirtualThreadsProcessor.setup282338138 class

// $FF: synthetic class
public class VirtualThreadsProcessor$setup282338138 implements StartupTask {
    public VirtualThreadsProcessor$setup282338138() {
    }

    public void deploy(StartupContext var1) {
        var1.setCurrentBuildStepName("VirtualThreadsProcessor.setup");
        Object[] var2 = this.$quarkus$createArray();
        this.deploy_0(var1, var2);
    }

    public void deploy_0(StartupContext var1, Object[] var2) {
        VirtualThreadsRecorder var3 = new VirtualThreadsRecorder();
        VirtualThreadsConfig var4 = Config.VirtualThreadsConfig;
        Object var5 = var1.getValue("io.quarkus.runtime.ShutdownContext");
        LaunchMode var6 = LaunchMode.valueOf("NORMAL");
        var3.setupVirtualThreads(var4, (ShutdownContext)var5, var6);
        Supplier var7 = var3.getCurrentSupplier();
        var1.putValue("proxykey49", var7);
    }

    public Object[] $quarkus$createArray() {
        return new Object[0];
    }
}

The class is created by io.quarkus.virtual.threads.VirtualThreadsProcessor

public class VirtualThreadsProcessor {

    @BuildStep
    @Record(ExecutionTime.STATIC_INIT)
    public void setup(VirtualThreadsConfig config, VirtualThreadsRecorder recorder,
            ShutdownContextBuildItem shutdownContextBuildItem,
            LaunchModeBuildItem launchModeBuildItem,
            BuildProducer<AdditionalBeanBuildItem> beans,
            BuildProducer<SyntheticBeanBuildItem> producer) {
        beans.produce(new AdditionalBeanBuildItem(VirtualThreads.class));
        recorder.setupVirtualThreads(config, shutdownContextBuildItem, launchModeBuildItem.getLaunchMode());
        producer.produce(
                SyntheticBeanBuildItem.configure(ExecutorService.class)
                        .addType(Executor.class)
                        .addQualifier(AnnotationInstance.builder(VirtualThreads.class).build())
                        .scope(BuiltinScope.APPLICATION.getInfo())
                        .setRuntimeInit()
                        .supplier(recorder.getCurrentSupplier())
                        .done());
    }

}

If @Record(ExecutionTime.STATIC_INIT) is annotated, recorded step will be generated in ApplicationImpl's static section. If @Record(ExecutionTime.RUNTIME_INIT) is annotated, recorded step will be generated in ApplicationImpl doStart() method.