用java实现简单版tomcat

本文介绍了使用Java实现一个简单Tomcat的过程,包括处理静态资源、模拟Request和Response对象。通过该项目,作者对Tomcat的工作机制有了初步理解。在实现过程中遇到并解决了几个关键问题:如HTTP请求的 favicon.ico 请求处理、Servlet service方法中的outputstream关闭时机、以及request读取HTTP请求时的阻塞问题等。

更新:现在的tomcat已经可以实现调用servlet中的service()方法了,把在这个阶段遇到的问题总结一下。

1.在对网页进行访问时,访问会请求2次。第二次是请求/favicon.ico(网页图标)这个东西。(不知道是每个浏览器都会还是个别才有),因为测试的index.html等网页是没有设这个图标的,所以第二次请求会导致抛很多错。在项目中放个图片进去就好了。

 

2.在servlet调用service(request,response)方法后,如果不进行outputstream.close(),write()的内容不会到网页上,而且会显示“网页重定向”。

查了一下相关文档,当socket中的outpustream关闭时会把这个socket也关掉,但是为什么要在特定的地方close才可以呢??

—————————————————————————更新分界线————————————————————————— 

这个简单版tomcat现在是只能处理静态资源的,它用自定义的request和response模拟tomcat接收到客户请求后把请求的静态资源返回给客户端的过程。

  通过写了这个东西(虽然刚开始看了很多别人的代码),但是对于tomcat的处理机制终于有了一点简单的了解。以及,tomcat是每个客户端都开一个线程的。

项目结构图:

request作用:解析http请求,把其中的请求资源地址拿出来(例如"hello.html")。

response作用:把指定的uri中的资源找到,然后返回给客户端。

遇到的问题

1.request中读取http请求的时候,如果用以下的方式

            while ((count =bufferedReader.read(buffer,0,1024)) != -1){
                stringBuilder.append(buffer);
            }

则启动时,会报“socket write error”。

问题原因:inputstream的read()方法,只有当到达流结尾才会返回-1,否则它会阻塞等待数据;但是socket未被关闭时,它不会关闭inpustream,所以read()方法无法结束。故这里的read()会一直阻塞。

解决方法之一可以用InpuStream.avalable()来同时判断(这个方法会在socket的inpustream中没有数据时返回0)

 

2.注意serversocket和socket的放置位置


    public static void main(String[] args){

        try (ServerSocket serverSocket = new ServerSocket(8080,1, InetAddress.getByName("127.0.0.1"))){

            while (true){
                Socket socket = serverSocket.accept();
                Thread thread = new Thread(new ServerThread(socket));
                thread.start();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        
    }

我做了两种操作,1,把serversocket放到了ServerThread的构造函数;2,把socket放到ServerThread的构造函数。

第一种做法中,我的电脑黑屏了。第一种做法中,它会无限量地创建线程,然后执行。因为serverSocket刚开始就创建了,一直存在。第二种做法中,它会在有服务请求的时候创建线程,并且执行。因为要在serversocket检测到有客户请求的时候,才会返回一个socket。

 

3.注意关闭资源,及时回收哦。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值