`
liudeh_009
  • 浏览: 240295 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

Jetty的启动过程

阅读更多

      Jetty 是一个轻量级的、开源的servlet容器,可以非常容易的嵌入到应用程序当中作为嵌入式服务器使用,下面我们从代码层面来看看它是如何启动的

     Jetty的启动从Server类的start()方法开始的,Server类继承了AbstractLifeCycle类,会首先执行AbstractLifeCycle的start()方法.方法如下:

     

    public final void start() throws Exception
    {
        synchronized (_lock)
        {
            try
            {
                if (_state == STARTED || _state == STARTING)
                    return;
                setStarting();//启动之前调用监听器
                doStart();//启动jetty
                Log.debug("started {}",this);
                setStarted();//启动之后调用监听器
            }
            catch (Exception e)
            {
                setFailed(e);
                throw e;
            }
            catch (Error e)
            {
                setFailed(e);
                 throw e;
            }
        }
    }

 

     doStart()方法在Server类中.如下:

       

      

    /* ------------------------------------------------------------ */
    protected void doStart() throws Exception
    {
        Log.info("jetty-"+_version);
        HttpGenerator.setServerVersion(_version);
        MultiException mex=new MultiException();
      
        for (int i=0;_realms !=null && i<_realms.length; i++)
        {
            if (_realms[i] instanceof LifeCycle)
                ((LifeCycle)_realms[i]).start();
        }

        Iterator itor = _dependentLifeCycles.iterator();
        while (itor.hasNext())
        {   
            try
            {
                ((LifeCycle)itor.next()).start(); 
            }
            catch (Throwable e) {mex.add(e);}
        }
        
        if (_threadPool==null)
        {
            QueuedThreadPool tp=new QueuedThreadPool();
            setThreadPool(tp);
        }
        
        if (_sessionIdManager!=null)
            _sessionIdManager.start();
        
        try
        {
            if (_threadPool instanceof LifeCycle)
                ((LifeCycle)_threadPool).start();
        } 
        catch(Throwable e) { mex.add(e);}
        
        try 
        { 
            super.doStart(); 
        } 
        catch(Throwable e) 
        { 
            Log.warn("Error starting handlers",e);
        }
        
        if (_connectors!=null)
        {
            for (int i=0;i<_connectors.length;i++)
            {
                try{_connectors[i].start();}
                catch(Throwable e)
                {
                    mex.add(e);
                }
            }
        }
        mex.ifExceptionThrow();
    }

 

 

      这里面启动了处理请求的线程和Session管理器,还有连接器,super.doStart()调用了HandlerWrapper类的doStart()方法,如下:

      

  protected void doStart() throws Exception
    {
        if (_handler!=null)
            _handler.start();
        super.doStart();
    }

  

      _handler.start()调用了AbstractLifeCycle的start()方法,同上面,AbstractLifeCycle里面的start()方法会调用

WebAppContext的doStart()方法,如下:

       

    protected void doStart() throws Exception
    {
        try
        {
            // 初始化四个类WebInfConfiguration,WebXmlConfiguration, JettyWebXmlConfiguration,TagLibConfiguration            
             loadConfigurations();

            for (int i=0;i<_configurations.length;i++)
                _configurations[i].setWebAppContext(this);

            // Configure classloader
            _ownClassLoader=false;
            if (getClassLoader()==null)
            {
                WebAppClassLoader classLoader = new WebAppClassLoader(this);
                setClassLoader(classLoader);//生成classloader加载应用的war
                _ownClassLoader=true;
            }

            if (Log.isDebugEnabled())//打印日志 
            {
                ClassLoader loader = getClassLoader();
                Log.debug("Thread Context class loader is: " + loader);
                loader=loader.getParent();
                while(loader!=null)
                {
                    Log.debug("Parent class loader is: " + loader); 
                    loader=loader.getParent();
                }
            }

            for (int i=0;i<_configurations.length;i++)
                _configurations[i].configureClassLoader();//WebInfConfiguration类加载war包的lib,classes目录
            getTempDirectory();
            if (_tmpDir!=null && !_isExistingTmpDir && !isTempWorkDirectory())
            {
                File sentinel = new File(_tmpDir, ".active");
                if(!sentinel.exists())
                    sentinel.mkdir();
            }

            super.doStart();

            if (isLogUrlOnStart()) 
                dumpUrl();
        }
        catch (Exception e)
        {
            //start up of the webapp context failed, make sure it is not started
            Log.warn("Failed startup of context "+this, e);
            _unavailableException=e;
            _unavailable = true;
        }
    }

    

    WebInfConfiguration类的configureClassLoader()方法如下:

    

    public  void configureClassLoader()
    throws Exception
    {
        //cannot configure if the context is already started
        if (_context.isStarted())
        {
            if (Log.isDebugEnabled()){Log.debug("Cannot configure webapp after it is started");}
            return;
        }

        Resource web_inf=_context.getWebInf();//生成临时目录将war拷过来

        // Add WEB-INF classes and lib classpaths
        if (web_inf != null && web_inf.isDirectory() && _context.getClassLoader() instanceof WebAppClassLoader)
        {
            // Look for classes directory
            Resource classes= web_inf.addPath("classes/");
            if (classes.exists())
                ((WebAppClassLoader)_context.getClassLoader()).addClassPath(classes.toString());

            // Look for jars
            Resource lib= web_inf.addPath("lib/");
            if (lib.exists() || lib.isDirectory())
                ((WebAppClassLoader)_context.getClassLoader()).addJars(lib);
        }
        
     }

    WebAppContext的start()方法里的 super.doStart()会调用ContextHandler的doStart()方法,方法如下:

  protected void doStart() throws Exception
    {
        if (_contextPath==null)
            throw new IllegalStateException("Null contextPath");
        
        _logger=Log.getLogger(getDisplayName()==null?getContextPath():getDisplayName());
        ClassLoader old_classloader=null;
        Thread current_thread=null;
        SContext old_context=null;

        _contextAttributes=new AttributesMap();
        try
        {
            
            // Set the classloader
            if (_classLoader!=null)
            {
                current_thread=Thread.currentThread();
                old_classloader=current_thread.getContextClassLoader();
                current_thread.setContextClassLoader(_classLoader);
            }
            

            if (_mimeTypes==null)
                _mimeTypes=new MimeTypes();
            
            old_context=(SContext)__context.get();
            __context.set(_scontext);
            
            if (_errorHandler==null)
                setErrorHandler(new ErrorHandler());
            
            startContext();
            
           
        }
        finally
        {
            __context.set(old_context);
            
            // reset the classloader
            if (_classLoader!=null)
            {
                current_thread.setContextClassLoader(old_classloader);
            }
        }
    }

    startContext()方法会调用WebAppContext类的startContext()方法,如下:

  

    protected void startContext()
        throws Exception
    {
        // Configure defaults
        for (int i=0;i<_configurations.length;i++)
            _configurations[i].configureDefaults();//调用WebXmlConfiguration类解析xml文件
        
        // Is there a WEB-INF work directory
        Resource web_inf=getWebInf();
        if (web_inf!=null)
        {
            Resource work= web_inf.addPath("work");
            if (work.exists()
                            && work.isDirectory()
                            && work.getFile() != null
                            && work.getFile().canWrite()
                            && getAttribute(ServletHandler.__J_S_CONTEXT_TEMPDIR) == null)
                setAttribute(ServletHandler.__J_S_CONTEXT_TEMPDIR, work.getFile());
        }
        
        // Configure webapp
        for (int i=0;i<_configurations.length;i++)
            _configurations[i].configureWebApp();

        
        super.startContext();
    }

 
super.startContext()调用父类Context的startContext()方法,如下:

 

    

    protected void startContext() throws Exception
    {
        super.startContext();//初始化xml里配置的listener
        
        // OK to Initialize servlet handler now
        if (_servletHandler != null && _servletHandler.isStarted())
            _servletHandler.initialize();//初始化xml里面配置的servlet
    }

 

      

0
3
分享到:
评论

相关推荐

    Maven_Jetty_Plugin_配置指南(翻译)

    * 自动执行插件:插件可以自动执行,在 Maven 构建过程中启动和停止 Jetty 服务器。 四、使用实例 下面是一个使用 Maven Jetty Plugin 的实例: ``` mvn jetty:run ``` 这将启动 Jetty 服务器,并将 Web 应用程序...

    maven的jetty插件提示No Transaction manager found导致启动慢的解决方法

    在使用maven开发web项目极大地方便了jar包的依赖,在测试时也可以集成Servlet容器,从启动速度和量级上看,Jetty无疑是不二选择,然而从8.x开始,如果你的web...而且启动过程会暂停十几秒,在反复调试代码时很浪费时间

    springboot-demo-helloworld-jetty.rar

    SringBoot的概述# SpringBoot解决上述Spring的缺点SpringBoot对上述Spring的缺点进行的改善和优化,基于约定优于配置的思想,...自动配置Spring Boot的自动配置是一个运行时(更准确地说,是应用程序启动时)的过程,考

    基于eclipse-maven的自动化测试环境配置大学论文.doc

    在自动化测试环境中,我们需要配置Jetty插件,以便在测试过程中使用Jetty来启动和停止Web应用程序。在Eclipse中,我们可以通过添加以下插件来配置Jetty: * org.eclipse.jetty.server: Jetty服务器插件 * org....

    agorava-socializer:使用Agorava构建的示例应用程序

    您所要做的就是输入命令mvn -Prun 然后等待那个maven下载所有需要的东西(可能是第一次),当Jetty启动时,只需将浏览器指向http://localhost:8080享受。建造您可以使用以下命令构建Agorava mvn clean install 它将...

    Spring Boot快速搭建和部署应用程序

    Spring Boot是一种基于Java的开发框架,旨在简化和加速应用程序的构建过程。它是由Spring团队开发的,构建在Spring框架之上,提供了一种的方式。 Spring Boot的主要特点之一是约定优于配置。通过使用默认的约定,...

    vSphere 故障排除

    《vSphere 故障排除》介绍了 vCenter Server 实施及相关组件的故障排除问题和过程。 A Active Directory 24 Auto Deploy 超时错误 18 重定向问题 19 coredump 20 错误的映像 18 DHCP 地址 22 故障排除 18 TFTP ...

    架构师面试题系列之Spring Boot面试专题及答案(33题).docx

    Spring Boot 是一个用于简化 Spring 应用的初始搭建和开发过程的框架。它使用特定的方式来进行配置(properties 或 yml 文件),创建独立的 Spring 引用程序 main 方法运行,并嵌入 Tomcat,无需部署 war 文件。 2....

    wssecurity:wssecurity 示例存储库

    .wsdl 生成实体定义 Web 服务实现类配置 cxf jaxws 端点参考添加spring web配置创建 Web 应用程序 web.xml 描述符将 jetty maven 插件添加到启动实现 Web 服务客户端使用拦截器保护 Web 服务使用 WS-Policy 保护 Web...

    Java-CMS-Framework-Base_jeesite.com:Java管理后台快速开发SSM框架_优化版-JDK1.8 spring,springMVC,MyBatis,mysql,shiro,redis,ehcache

    本人在开发中,使用了此项目,同时在开发过程中,对项目进行了部分优化修改,感谢原作者. 初始管理员账号:admin 密码:admin 数据库初始化 mysql&gt; create database demo; mysql&gt; create user 'work'@'%' identified by ...

    基于ssm+Vue的新冠疫苗接种管理系统(源码+部署说明+系统介绍+数据库).zip

    将生成的jar包部署到Web服务器(如Tomcat、Jetty等)上,并启动项目。f. 根据实际需求,修改前端Vue.js代码以实现所需的功能。系统介绍:该系统具有以下主要功能:a. 用户管理:管理员可以添加、编辑和删除用户,设置...

    服务器升级故障及其解决方法

    这样的话升级应该包括以下几个步骤:备份系统数据、断电,离线状态下实现硬件的升级,安装新的硬件,重新启动操作系统,增加CPU的License,利用RAID的特性,整合新加入的硬盘。 服务器升级需要遵循一定的原则和步骤...

    JuShaTa:JuShaTa是一个Java容器,提供模块隔离及模块热加载能力

    JuShaTa容器 JuShaTa是一个Java容器,提供模块隔离及...但是在一个Java应用里面包含多个SpringBoot服务时,这些服务可能会调用不同版本的jar包,那么在程序启动或者运行过程中可能会报NoSuchMethodException这样的异常

    spring-source-study:spring原始学习

    SpringBoot实际上就是一个整合很多可插拔的组件(框架),内嵌了使用工具(诸如内嵌了Tomcat,Jetty等),方便开发人员快速建造和开发的一个框架。 IoC ( Inversion of Control ,控制倒转)。这是spring的核心,...

    利用CruiseControl软件进行持续集成

    在软件开发过程中,持续集成是一个非常重要的步骤,它可以帮助开发团队更好地合作和跟踪项目的进度。CruiseControl是一种流行的持续集成工具,能够自动化地构建、测试和部署软件项目。下面是CruiseControl的知识点...

    matlab改变代码字体-invesdwin-context:软件产品线的模块系统

    在应用程序启动时,引导过程将收集配置摘要并创建完整的应用程序上下文。 它还处理用于运行和测试应用程序的生命周期(为模块提供挂钩)。 测试还得益于灵活的方法,即可以用存根替换Bean实例,根据情况选择要加载的...

    CAT实时应用监控平台-其他

    Cat产品价值:减少故障发现时间降低故障定位成本辅助应用程序优化Cat优势:实时处理:信息的价值会随时间锐减,尤其是事故处理过程中全量数据:全量采集指标数据,便于深度分析故障案例高可用:故障的还原与问题定位...

Global site tag (gtag.js) - Google Analytics