Node.jsform[method="post"]
의 HTTP POST
메소드에서 전송 된 양식 데이터 ( ) 및 파일 업로드를 어떻게 추출 합니까?
나는 googled 문서를 읽었으며 아무것도 찾지 못했습니다.
function (request, response) {
//request.post????
}
도서관이나 해킹이 있습니까?
답변
당신이 사용하는 경우 익스프레스 (Node.js를위한 고성능, 높은 수준의 웹 개발), 당신은이 작업을 수행 할 수 있습니다 :
HTML :
<form method="post" action="/">
<input type="text" name="user[name]">
<input type="text" name="user[email]">
<input type="submit" value="Submit">
</form>
API 클라이언트 :
fetch('/', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
user: {
name: "John",
email: "john@example.com"
}
})
});
Node.js : (Express v4.16.0부터)
// Parse URL-encoded bodies (as sent by HTML forms)
app.use(express.urlencoded());
// Parse JSON bodies (as sent by API clients)
app.use(express.json());
// Access the parse results as request.body
app.post('/', function(request, response){
console.log(request.body.user.name);
console.log(request.body.user.email);
});
Node.js : (Express <4.16.0의 경우)
const bodyParser = require("body-parser");
/** bodyParser.urlencoded(options)
* Parses the text as URL encoded data (which is how browsers tend to send form data from regular forms set to POST)
* and exposes the resulting object (containing the keys and values) on req.body
*/
app.use(bodyParser.urlencoded({
extended: true
}));
/**bodyParser.json(options)
* Parses the text as JSON and exposes the resulting object on req.body.
*/
app.use(bodyParser.json());
app.post("/", function (req, res) {
console.log(req.body.user.name)
});
답변
querystring
모듈을 사용할 수 있습니다 :
var qs = require('querystring');
function (request, response) {
if (request.method == 'POST') {
var body = '';
request.on('data', function (data) {
body += data;
// Too much POST data, kill the connection!
// 1e6 === 1 * Math.pow(10, 6) === 1 * 1000000 ~~~ 1MB
if (body.length > 1e6)
request.connection.destroy();
});
request.on('end', function () {
var post = qs.parse(body);
// use post['blah'], etc.
});
}
}
예를 들어, input
name 필드 가 있다면 age
변수를 사용하여 액세스 할 수 있습니다 post
.
console.log(post.age);
답변
누군가 RAM을 넘치려고하면 연결을 끊어야합니다!
var qs = require('querystring');
function (request, response) {
if (request.method == 'POST') {
var body = '';
request.on('data', function (data) {
body += data;
// 1e6 === 1 * Math.pow(10, 6) === 1 * 1000000 ~~~ 1MB
if (body.length > 1e6) {
// FLOOD ATTACK OR FAULTY CLIENT, NUKE REQUEST
request.connection.destroy();
}
});
request.on('end', function () {
var POST = qs.parse(body);
// use POST
});
}
}
답변
여기에 많은 답변이 더 이상 모범 사례가 아니거나 설명하지 않으므로이 글을 쓰는 이유입니다.
기초
http.createServer의 콜백이 호출되면 서버가 실제로 요청에 대한 모든 헤더를 수신했지만 데이터가 아직 수신되지 않았을 수 있으므로 기다려야합니다. HTTP 요청 객체 (http.IncomingMessage 인스턴스) 사실입니다 읽을 스트림 . 데이터 청크가 도착할 때마다 읽을 수있는 스트림에서 이벤트가 발생하고 (콜백을 등록했다고 가정) 모든 청크가 도착하면 이벤트가 발생합니다. 다음은 이벤트를 듣는 방법에 대한 예입니다.data
end
http.createServer((request, response) => {
console.log('Now we have a http message with headers but no data yet.');
request.on('data', chunk => {
console.log('A chunk of data has arrived: ', chunk);
});
request.on('end', () => {
console.log('No more data');
})
}).listen(8080)
버퍼를 문자열로 변환
이 작업을 시도하면 청크가 버퍼 임을 알 수 있습니다. 이진 데이터를 다루지 않고 문자열을 사용해야하는 경우 request.setEncoding을 사용하는 것이 좋습니다. 하는 경우 스트림이 지정된 인코딩으로 해석 된 문자열을 내보내고 멀티 바이트 문자를 올바르게 처리 메서드를 .
버퍼링 청크
이제는 각 청크 자체에 관심이 없으므로이 경우 다음과 같이 버퍼링하려고합니다.
http.createServer((request, response) => {
const chunks = [];
request.on('data', chunk => chunks.push(chunk));
request.on('end', () => {
const data = Buffer.concat(chunks);
console.log('Data: ', data);
})
}).listen(8080)
여기서는 모든 버퍼를 연결하고 하나의 큰 버퍼를 반환하는 Buffer.concat 이 사용됩니다. 당신은 또한 사용할 수 있습니다동일한 작업을 수행하는 concat-stream 모듈 을 .
const http = require('http');
const concat = require('concat-stream');
http.createServer((request, response) => {
concat(request, data => {
console.log('Data: ', data);
});
}).listen(8080)
컨텐츠 파싱
당신이 HTML 아무 파일이나 나눠로 POST 제출을 형성 동의하려는 경우 jQuery를 아약스 의 기본 콘텐츠 형식으로 호출 한 다음 콘텐츠 형식입니다 application/x-www-form-urlencoded
으로 uft-8
인코딩. querystring 모듈 을 사용하여 직렬화 해제하고 속성에 액세스 할 수 있습니다.
const http = require('http');
const concat = require('concat-stream');
const qs = require('querystring');
http.createServer((request, response) => {
concat(request, buffer => {
const data = qs.parse(buffer.toString());
console.log('Data: ', data);
});
}).listen(8080)
컨텐츠 유형이 JSON 인 경우 qs.parse 대신 JSON.parse를 사용하면 됩니다 .
파일을 다루거나 멀티 파트 컨텐츠 유형을 처리하는 경우, 그와 관련된 모든 고통을 제거하는 강력한 것 같은 것을 사용해야합니다. 멀티 파트 콘텐츠를위한 유용한 링크 및 모듈을 게시 한이 다른 답변 을 살펴보십시오 .
관
내용을 파싱하고 싶지 않고 다른 곳으로 전달하는 경우, 예를 들어 다른 http 요청에 데이터로 보내거나 파일에 저장하십시오. 버퍼링보다는 파이핑하는 것이 코드를 작성하고, 압력을 더 잘 처리하며, 메모리가 적게 들고 경우에 따라 더 빠릅니다.
콘텐츠를 파일로 저장하려면 다음을 수행하십시오.
http.createServer((request, response) => {
request.pipe(fs.createWriteStream('./request'));
}).listen(8080)
데이터 양 제한
다른 답변에서 알 수 있듯이 악의적 인 클라이언트는 응용 프로그램을 중단하거나 메모리를 채우기 위해 엄청난 양의 데이터를 보내 데이터를 방출하는 요청을 삭제하여 특정 제한을 초과하지 않도록 할 수 있습니다. 라이브러리를 사용하여 수신 데이터를 처리하지 않는 경우 지정된 제한에 도달하면 요청을 중단 할 수있는 stream-meter 와 같은 것을 사용하는 것이 좋습니다 .
limitedStream = request.pipe(meter(1e7));
limitedStream.on('data', ...);
limitedStream.on('end', ...);
또는
request.pipe(meter(1e7)).pipe(createWriteStream(...));
또는
concat(request.pipe(meter(1e7)), ...);
NPM 모듈
단순히 콘텐츠를 버퍼링하고 파싱하기 위해 HTTP 요청 본문을 사용하는 방법에 대해 위에서 설명했지만이 모듈 중 하나를 사용하면 가장자리를 더 잘 처리 할 수 있으므로 직접 구현하는 것이 좋습니다. Express의 경우 body-parser를 사용하는 것이 좋습니다 . koa의 경우 비슷한 모듈이 있습니다.
프레임 워크를 사용하지 않으면 몸 이 좋습니다.
답변
여기에 게시 된 다른 답변과 기사를 기반으로하는 매우 간단한 프레임 워크 래퍼가 있습니다.
var http = require('http');
var querystring = require('querystring');
function processPost(request, response, callback) {
var queryData = "";
if(typeof callback !== 'function') return null;
if(request.method == 'POST') {
request.on('data', function(data) {
queryData += data;
if(queryData.length > 1e6) {
queryData = "";
response.writeHead(413, {'Content-Type': 'text/plain'}).end();
request.connection.destroy();
}
});
request.on('end', function() {
request.post = querystring.parse(queryData);
callback();
});
} else {
response.writeHead(405, {'Content-Type': 'text/plain'});
response.end();
}
}
사용 예 :
http.createServer(function(request, response) {
if(request.method == 'POST') {
processPost(request, response, function() {
console.log(request.post);
// Use request.post here
response.writeHead(200, "OK", {'Content-Type': 'text/plain'});
response.end();
});
} else {
response.writeHead(200, "OK", {'Content-Type': 'text/plain'});
response.end();
}
}).listen(8000);
답변
데이터를 JSON으로 인코딩 한 다음 Node.js로 보내면 더 깨끗해집니다 .
function (req, res) {
if (req.method == 'POST') {
var jsonString = '';
req.on('data', function (data) {
jsonString += data;
});
req.on('end', function () {
console.log(JSON.parse(jsonString));
});
}
}
답변
웹 프레임 워크를 설치하지 않고이 사소한 작업을 수행하는 방법을 궁금해하는 사람은 이것을 함께 관리했습니다. 생산 준비가 거의되지 않았지만 작동하는 것 같습니다.
function handler(req, res) {
var POST = {};
if (req.method == 'POST') {
req.on('data', function(data) {
data = data.toString();
data = data.split('&');
for (var i = 0; i < data.length; i++) {
var _data = data[i].split("=");
POST[_data[0]] = _data[1];
}
console.log(POST);
})
}
}