Node.js http 模块

Java FileNode.js 内置模块


Node.js 的 http 模块是 Node.js 内置的核心模块之一,它允许开发者创建 HTTP 服务器和客户端。通过这个模块,我们可以轻松地处理 HTTP 请求和响应,构建 Web 应用程序或 API 服务。

http 模块提供了创建服务器和发起 HTTP 请求的能力,是构建 Web 应用的基础。它支持 HTTP/1.1 协议,并提供了丰富的 API 来处理各种 HTTP 相关的操作。


创建 HTTP 服务器

使用 http 模块创建服务器非常简单,下面是一个最基本的示例:

实例

const http = require('http');

// 创建 HTTP 服务器
const server = http.createServer((req, res) => {
  // 设置响应头
  res.writeHead(200, {'Content-Type': 'text/plain'});
 
  // 发送响应数据
  res.end('Hello, World!\n');
});

// 监听 3000 端口
server.listen(3000, () => {
  console.log('Server running at http://localhost:3000/');
});

代码解析

  1. require('http') - 导入 Node.js 的 http 模块
  2. http.createServer() - 创建一个 HTTP 服务器实例
  3. 回调函数 (req, res) => {...} - 处理每个 HTTP 请求
    • req - 请求对象,包含客户端发来的请求信息
    • res - 响应对象,用于向客户端发送响应
  4. res.writeHead() - 设置响应头
  5. res.end() - 结束响应并发送数据
  6. server.listen() - 启动服务器监听指定端口

处理 HTTP 请求

HTTP 服务器需要能够处理不同类型的请求,下面我们来看如何解析请求信息:

实例

const http = require('http');

const server = http.createServer((req, res) => {
  // 获取请求方法、URL 和请求头
  const { method, url, headers } = req;
 
  // 记录请求信息
  console.log(`收到 ${method} 请求,路径: ${url}`);
  console.log('请求头:', headers);
 
  // 根据请求方法处理
  if (method === 'GET') {
    res.writeHead(200, {'Content-Type': 'text/plain'});
    res.end('这是一个 GET 请求\n');
  } else if (method === 'POST') {
    let body = '';
   
    // 收集 POST 数据
    req.on('data', chunk => {
      body += chunk;
    });
   
    // 数据接收完毕
    req.on('end', () => {
      console.log('POST 数据:', body);
      res.writeHead(200, {'Content-Type': 'text/plain'});
      res.end('数据已接收\n');
    });
  } else {
    res.writeHead(405, {'Content-Type': 'text/plain'});
    res.end('方法不允许\n');
  }
});

server.listen(3000);

请求对象 (req) 常用属性

  • req.method: HTTP 请求方法 (GET, POST, PUT, DELETE 等)
  • req.url: 请求的 URL 路径
  • req.headers: 请求头对象
  • req.httpVersion: HTTP 协议版本

响应对象 (res) 常用方法

  • res.writeHead(statusCode, headers): 设置响应状态码和头
  • res.write(data): 写入响应体
  • res.end([data]): 结束响应,可选发送最后的数据
  • res.setHeader(name, value): 设置响应头

发起 HTTP 请求

http 模块不仅可以创建服务器,还可以作为客户端发起 HTTP 请求:

实例

const http = require('http');

// 发起 GET 请求
http.get('http://jsonplaceholder.typicode.com/posts/1', (res) => {
  let data = '';
 
  // 接收数据
  res.on('data', (chunk) => {
    data += chunk;
  });
 
  // 数据接收完成
  res.on('end', () => {
    console.log('响应数据:', JSON.parse(data));
  });
}).on('error', (err) => {
  console.error('请求出错:', err);
});

发起 POST 请求

实例

const http = require('http');

// 请求选项
const options = {
  hostname: 'jsonplaceholder.typicode.com',
  port: 80,
  path: '/posts',
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
  }
};

// 创建请求
const req = http.request(options, (res) => {
  let data = '';
 
  res.on('data', (chunk) => {
    data += chunk;
  });
 
  res.on('end', () => {
    console.log('响应:', JSON.parse(data));
  });
});

// 处理错误
req.on('error', (err) => {
  console.error('请求出错:', err);
});

// 写入请求数据
const postData = JSON.stringify({
  title: 'foo',
  body: 'bar',
  userId: 1
});

req.write(postData);
req.end();

实际应用场景

1. 创建 RESTful API

实例

const http = require('http');

const server = http.createServer((req, res) => {
  const { method, url } = req;
 
  // 简单路由处理
  if (method === 'GET' && url === '/api/users') {
    res.writeHead(200, {'Content-Type': 'application/json'});
    res.end(JSON.stringify([{id: 1, name: 'Alice'}, {id: 2, name: 'Bob'}]));
  } else if (method === 'POST' && url === '/api/users') {
    let body = '';
    req.on('data', chunk => body += chunk);
    req.on('end', () => {
      const newUser = JSON.parse(body);
      // 这里可以保存到数据库
      res.writeHead(201, {'Content-Type': 'application/json'});
      res.end(JSON.stringify({id: Date.now(), ...newUser}));
    });
  } else {
    res.writeHead(404, {'Content-Type': 'text/plain'});
    res.end('Not Found\n');
  }
});

server.listen(3000);

2. 代理服务器

实例

const http = require('http');

const proxy = http.createServer((clientReq, clientRes) => {
  // 向目标服务器发起请求
  const options = {
    hostname: 'example.com',
    port: 80,
    path: clientReq.url,
    method: clientReq.method,
    headers: clientReq.headers
  };
 
  const proxyReq = http.request(options, (proxyRes) => {
    // 将目标服务器的响应转发给客户端
    clientRes.writeHead(proxyRes.statusCode, proxyRes.headers);
    proxyRes.pipe(clientRes);
  });
 
  // 转发客户端请求体
  clientReq.pipe(proxyReq);
});

proxy.listen(8080);

最佳实践

  1. 错误处理:始终处理请求和响应中的错误事件
  2. 性能考虑:对于高并发应用,考虑使用连接池
  3. 安全性
    • 验证所有输入
    • 设置适当的安全头
    • 限制请求体大小防止 DOS 攻击
  4. 使用流:对于大文件传输,使用流式处理
  5. 考虑框架:对于复杂应用,考虑使用 Express、Koa 等框架

总结

Node.js 的 http 模块提供了构建网络应用的基础能力。虽然现在有许多更高级的框架可用,但理解 http 模块的工作原理对于任何 Node.js 开发者都至关重要。通过掌握这个核心模块,你可以更好地理解 Web 应用的工作机制,并能够根据需求构建自定义的解决方案。

Java FileNode.js 内置模块