Request: POST 본문이 μžˆλŠ” μš”μ²­μ—μ„œ νŒŒμ΄ν”„ν•  수 μ—†μŠ΅λ‹ˆλ‹€.

에 λ§Œλ“  2015λ…„ 06μ›” 30일  Β·  24μ½”λ©˜νŠΈ  Β·  좜처: request/request

Express μš”μ²­μ—μ„œ νŒŒμ΄ν•‘ν•˜μ—¬ μƒˆ μš”μ²­ 개체λ₯Ό λ§Œλ“€λ €κ³  ν•©λ‹ˆλ‹€. 이것은 GET μš”μ²­μ— λŒ€ν•΄ 잘 μž‘λ™ν•˜μ§€λ§Œ 본문이 μžˆλŠ” POST μš”μ²­μ˜ 경우 본문이 μƒˆ μš”μ²­μ— λ³΅μ‚¬λ˜μ§€ μ•ŠλŠ” 것 κ°™μŠ΅λ‹ˆλ‹€. λ‹€μŒκ³Ό 같이 μˆ˜λ™μœΌλ‘œ 본문을 볡사해 λ³΄μ•˜μŠ΅λ‹ˆλ‹€.

let pipedReq = req.pipe(request({ url: 'http://www.example.com', form: req.body }));

이것은 λ³Έλ¬Έ μœ„μ— λ³΅μ‚¬λ˜μ§€λ§Œ pipedReq κ°€ 정리될 λ•Œ "μ’…λ£Œ ν›„ μ“°κΈ°" 였λ₯˜κ°€ λ°œμƒν•©λ‹ˆλ‹€. #1659와 관련이 μžˆμ„ 수 μžˆμŠ΅λ‹ˆλ‹€.

λ‹€μŒκ³Ό 같은 κ°„λ‹¨ν•œ Express μ•±μœΌλ‘œ 문제λ₯Ό μž¬ν˜„ν•˜λŠ” 것은 μ‰½μŠ΅λ‹ˆλ‹€.

'use strict';

let express = require('express');
let request = require('request');

let app = express();

app.use('/', (req, res) => {
  req.pipe(request.post({ url: 'http://www.example.com', form: { foo: 'bar' }}));
});

app.listen(process.env.PORT || 3000);

역좔적:

Error: write after end
    at ClientRequest.OutgoingMessage.write (_http_outgoing.js:413:15)
    at Request.write (/.../node_modules/request/request.js:1354:25)
    at end (/.../node_modules/request/request.js:548:16)
    at Immediate._onImmediate (/.../node_modules/request/request.js:576:7)
    at processImmediate [as _immediateCallback] (timers.js:358:17)

κ°€μž₯ μœ μš©ν•œ λŒ“κΈ€

λ‚˜λŠ” 이것이 μ˜€λž˜λ˜μ—ˆλ‹€λŠ” 것을 μ•Œκ³  μžˆμ§€λ§Œ 이에 λŒ€ν•œ μ μ ˆν•œ 해결책을 μ°ΎλŠ” 데 어렀움을 κ²ͺμ—ˆκ³  λ‹€λ₯Έ μ‚¬λžŒλ“€μ—κ²Œ μœ μš©ν•  것이라고 μƒκ°ν–ˆμŠ΅λ‹ˆλ‹€.

'use strict';

let express = require('express');
let request = require('request');

let app = express();

app.use('/', (req, res) => {
  req.pipe(request.post({ url: 'http://www.example.com', form: { foo: 'bar' }}), {end: false}).pipe(res);
});

app.listen(process.env.PORT || 3000);

https://nodejs.org/api/stream.html#stream_readable_pipe_destination_options 에 ν‘œμ‹œλœ λŒ€λ‘œ 이λ₯Ό μΆ”κ°€ν•˜λ©΄ reqκ°€ μ’…λ£Œλ  λ•Œ μƒˆ 슀트림이 μžλ™μœΌλ‘œ μ’…λ£Œλ˜μ§€ μ•Šλ„λ‘ ν•©λ‹ˆλ‹€.

이둜 인해 이 μ˜ˆμ œκ°€ μž‘λ™ν–ˆμ§€λ§Œ 이λ₯Ό μ‚¬μš©ν•˜μ—¬ λ‹€λ₯Έ λ©”μ„œλ“œμ— λŒ€ν•œ ν”„λ‘μ‹œλ₯Ό λ§Œλ“œλŠ” 데 λͺ‡ 가지 λ¬Έμ œκ°€ μžˆμŒμ„ λ°œκ²¬ν–ˆμŠ΅λ‹ˆλ‹€. λͺΈμ²΄λŠ” μ–΄λ–»κ²Œ λ“  λͺ¨λ“  것을 μ œλŒ€λ‘œ λ‹«κ²Œ ν•˜μ§€λ§Œ λͺΈμ²΄κ°€ μ—†μœΌλ©΄ μ—¬μ „νžˆ 맀달렀 μžˆμŠ΅λ‹ˆλ‹€. json λ°”λ”” νŒŒμ„œλ₯Ό μ‚¬μš©ν•˜λŠ” 경우 λ°”λ””κ°€ μ—†λŠ” κ²½μš°μ—λ„ λ°”λ””κ°€ {} 둜 읽히기 λ•Œλ¬Έμ— λ¬Έμ œκ°€ λ°œμƒν•˜μ§€ μ•Šμ§€λ§Œ λ°”λ””κ°€ μ—†μœΌλ©΄ μ—¬μ „νžˆ λ¬Έμ œκ°€ μžˆμ„ 수 μžˆμŠ΅λ‹ˆλ‹€. λ‚΄ ν˜„μž¬ μ†”λ£¨μ…˜μ€ μš”μ²­μ— λŒ€ν•œ μ½˜ν…μΈ  길이 헀더λ₯Ό ν™•μΈν•˜κ³  μ˜΅μ…˜ κ°œμ²΄κ°€ 있으면 μ‚¬μš©ν•˜λŠ” κ²ƒμž…λ‹ˆλ‹€.

λͺ¨λ“  24 λŒ“κΈ€

μ΄κ²ƒμœΌλ‘œ μ‹œλ„ν•˜μ‹­μ‹œμ˜€:

var express = require('express')
var request = require('request')

var app = express()

// put it before any other middleware
app.use(function(req, res) {
  req.pipe(
    request[req.method.toLowerCase()]('http://example.com'))
  .pipe(res)
})

app.listen(3000, function () {
  console.log('Express server listening on port 3000')
})

본문을 μˆ˜μ •ν•˜λ €λŠ” 경우 μƒˆ μš”μ²­μ„ κ΅¬μ„±ν•˜κ³  응닡에 νŒŒμ΄ν”„ν•˜λ©΄ λ©λ‹ˆλ‹€.

@simov 본문을 μˆ˜μ •ν•˜μ§€ μ•Šκ³  URL만 μˆ˜μ •ν•©λ‹ˆλ‹€. λ”°λΌμ„œ μ›λž˜ μš”μ²­μ˜ 헀더 및 기타 속성을 μœ μ§€ν•˜μ§€λ§Œ μƒˆ URL을 μ‚¬μš©ν•˜μ—¬ μƒˆ μš”μ²­μœΌλ‘œ νŒŒμ΄ν”„ν•˜κ³  μ‹ΆμŠ΅λ‹ˆλ‹€. λ¬Έμ œλŠ” 원본 μš”μ²­μ΄ μƒˆ μš”μ²­μœΌλ‘œ νŒŒμ΄ν”„λ  λ•Œ 본문이 λ³΅μ‚¬λ˜μ§€ μ•Šκ³ (버그인지 ν™•μ‹€ν•˜μ§€ μ•ŠμŒ) form 속성을 μ§€μ •ν•˜μ—¬ 본문을 λ³΅μ‚¬ν•˜λ €κ³  ν•˜λ©΄ request μƒμ„±μžμ—μ„œ μœ„μ—μ„œ μ–ΈκΈ‰ν•œ 였λ₯˜κ°€ λ°œμƒν•©λ‹ˆλ‹€.

"μƒˆ μš”μ²­ ꡬ성"이라고 λ§ν•˜λ©΄ μ›ν•˜λŠ” 본문으둜 μ²˜μŒλΆ€ν„° μƒˆ μš”μ²­μ„ λ§Œλ“€κ³  νŒŒμ΄ν•‘ν•˜λŠ” λŒ€μ‹  μ›λž˜ μš”μ²­μ˜ 헀더λ₯Ό 직접 λ³΅μ‚¬ν•œλ‹€λŠ” μ˜λ―Έμž…λ‹ˆκΉŒ? κ·Έλ ‡κ²Œ ν•  수 μžˆμ§€λ§Œ κΈ°λ³Έ 제곡 νŒŒμ΄ν”„ 지원을 μ‚¬μš©ν•˜μ—¬ μƒˆ μš”μ²­μ—μ„œ μ›λž˜ μš”μ²­μ„ 볡사할 수 μžˆλ‹€λ©΄ 덜 반볡적이고 μ·¨μ•½ν•  κ²ƒμž…λ‹ˆλ‹€.

λ‚˜λŠ” μ—¬μ „νžˆ 이 두 가지 문제 쀑 ν•˜λ‚˜ λ˜λŠ” λ‘˜ λͺ¨λ‘κ°€ 버그라고 μƒκ°ν•©λ‹ˆλ‹€(즉, 1) νŒŒμ΄ν•‘ν•  λ•Œ μš”μ²­ 본문이 λ³΅μ‚¬λ˜μ§€ μ•Šκ³  2) λ‚΄ originalak κ²Œμ‹œλ¬Όμ— μ–ΈκΈ‰λœ μ˜ˆμ™Έ).

λ‚˜λŠ” λͺ…μ‹œμ  λ˜λŠ” μš”μ²­μ— λŒ€ν•΄ λ„ˆλ¬΄ 많이 μ•Œμ§€ λͺ»ν•˜μ§€λ§Œ(μž‘λ™ 방식을 μ‹€μ œλ‘œ μ΄ν•΄ν•˜μ§€ μ•Šκ³  단일 νŽ˜μ΄μ§€ μ•± ν”„λ‘μ‹œμ— μ‚¬μš©ν•˜κΈ°λ§Œ ν•˜λ©΄ 됨) write after end 였λ₯˜κ°€ μˆ˜μ •λ˜μ—ˆμŠ΅λ‹ˆλ‹€.

request.post({ url: 'http://www.example.com', form: { foo: 'bar' }}).pipe(res);

λŒ€μ‹ μ—:

req.pipe(request.post({ url: 'http://www.example.com', form: { foo: 'bar' }})).pipe(res);

@matthewgertner λ‚΄ μ½”λ“œ 예제λ₯Ό μ‹œλ„ν•˜λ©΄ μž‘λ™ν•©λ‹ˆλ‹€.

@simov ν™•μ‹€νžˆ μž‘λ™ν•˜μ§€λ§Œ κ·€ν•˜μ˜ μ˜ˆλŠ” req 에 λ³΅μ‚¬ν•˜λ €λŠ” 본문이 μžˆλŠ” 경우λ₯Ό 닀루지 μ•ŠμŠ΅λ‹ˆλ‹€. μ‹€μ œλ‘œ κ·€ν•˜μ˜ μ˜ˆμ œμ™€ 거의 λ™μΌν•œ μ½”λ“œλ₯Ό μ‚¬μš©ν•˜κ³  μžˆμ—ˆμ§€λ§Œ 본문이 μƒˆ μš”μ²­ κ°œμ²΄μ— λ³΅μ‚¬λ˜μ§€ μ•ŠκΈ° λ•Œλ¬Έμ— POST μš”μ²­μ„ μ²˜λ¦¬ν•΄μ•Ό ν•  λ•Œ λ§‰ν˜”μŠ΅λ‹ˆλ‹€.

@matthewgertner μž‘λ™ν•˜μ§€ μ•ŠλŠ” _exact_ μ½”λ“œ 예제λ₯Ό μ œκ³΅ν•  수 μžˆμŠ΅λ‹ˆκΉŒ?

@simov λ‚΄ μ›λž˜ κ²Œμ‹œλ¬Όμ˜ μƒ˜ν”Œμž…λ‹ˆλ‹€. 이것을 μ‚¬μš©ν•˜λ©΄ 본문이 μ „μ†‘λ˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€.

'use strict';

let express = require('express');
let request = require('request');

let app = express();

app.use('/', (req, res) => {
  req.pipe(request.post('http://www.example.com'));
});

app.listen(process.env.PORT || 3000);

이것을 μ‚¬μš©ν•˜λ©΄ μ˜ˆμ™Έκ°€ λ°œμƒν•©λ‹ˆλ‹€.

'use strict';

let express = require('express');
let request = require('request');

let app = express();

app.use('/', (req, res) => {
  req.pipe(request.post({ url: 'http://www.example.com', form: { foo: 'bar' }}));
});

app.listen(process.env.PORT || 3000);

http://www.example.com λ₯Ό http://requestb.in/ μ—μ„œ μƒμ„±λœ URL둜 λ°”κΎΈκ³  여기에 링크λ₯Ό 뢙여넣을 수 μžˆμŠ΅λ‹ˆκΉŒ? λ‹€μŒκ³Ό κ°™μ•„μ•Ό ν•©λ‹ˆλ‹€. http://requestb.in/1mv5l8h1?inspect

λ˜λŠ” μœ„μ˜ 예제 μ½”λ“œλ₯Ό μ‚¬μš©ν•  μˆ˜λ„ μžˆμŠ΅λ‹ˆλ‹€. 이것이 μ œκ°€ μ„œλ²„μ— μ‚¬μš©ν•˜λŠ” 것이기 λ•Œλ¬Έμž…λ‹ˆλ‹€. 그런 λ‹€μŒμ΄ 슀크립트λ₯Ό μ‹€ν–‰ν•˜κ³  μžˆμŠ΅λ‹ˆλ‹€.

var request = require('request')
request.post('http://localhost:3000', {form:{some:'data'}})

λ‚΄ λ§ν¬μ—μ„œ λ³Ό 수 μžˆλ“―μ΄ λ‚˜λŠ” form:{some:'data'} λ³΄λƒˆμŠ΅λ‹ˆλ‹€.

λ‚΄ μ‚¬μš© 사둀λ₯Ό μ„€λͺ…ν•˜κ² μŠ΅λ‹ˆλ‹€. κ°„λ‹¨ν•œ μ›Ή API ν”„λ‘μ‹œλ₯Ό κ΅¬ν˜„ν–ˆμŠ΅λ‹ˆλ‹€(https://github.com/salsita/web-api-proxy μ°Έμ‘°). HTTP μš”μ²­μ„ μˆ˜μ‹ ν•˜κ³  λ‹€λ₯Έ 호슀트둜 λ¦¬λ””λ ‰μ…˜ν•˜μ—¬ ν•„μš”ν•œ 경우 URL λ§€κ°œλ³€μˆ˜λ₯Ό ν”„λ‘μ‹œ μ„œλ²„μ˜ ν™˜κ²½ λ³€μˆ˜λ‘œ κ΅μ²΄ν•˜κΈ°λ§Œ ν•˜λ©΄ λ©λ‹ˆλ‹€. μš”μ μ€ λΉ„λ°€ ν‚€λ₯Ό ν΄λΌμ΄μ–ΈνŠΈ μ½”λ“œμ— ν¬ν•¨ν•˜μ§€ μ•Šμ•„λ„ λœλ‹€λŠ” κ²ƒμž…λ‹ˆλ‹€.

GET μš”μ²­μ—λŠ” 잘 μž‘λ™ν•˜μ§€λ§Œ μ΅œκ·Όμ—λŠ” POST에도 μ‚¬μš©ν•΄μ•Ό ν•œλ‹€λŠ” μš”κ΅¬ 사항이 μžˆμ—ˆμŠ΅λ‹ˆλ‹€. λ”°λΌμ„œ 본문이 Express μš”μ²­μ„ 톡해 λ“€μ–΄μ˜€κΈ° λ•Œλ¬Έμ— 이전 μ˜κ²¬μ—μ„œμ™€ 같이 μš”μ²­ 본문을 μ΄ˆκΈ°ν™”ν•˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€. κ°€μž₯ 졜근의 μ˜ˆλŠ” ν™•μ‹€νžˆ νš¨κ³Όκ°€ μžˆμ§€λ§Œ μ‹€μ œλ‘œ 도움이 λ˜μ§€λŠ” μ•ŠμŠ΅λ‹ˆλ‹€. λ‚΄κ°€ν•΄μ•Ό ν•  일은 λ‹€μŒκ³Ό κ°™μŠ΅λ‹ˆλ‹€.

req.pipe(request.post('http://some/new/url'));

req 에 본문이 있으면 이 경우 λ³΅μ‚¬λ˜μ§€ μ•ŠλŠ” 것 κ°™μŠ΅λ‹ˆλ‹€. μ–΄μ¨Œλ“  진싀은 (ν™˜κ²½ λ³€μˆ˜λ₯Ό μ‚¬μš©ν•˜μ—¬ ꡐ체해야 ν•˜λŠ” 자리 ν‘œμ‹œμžκ°€ μžˆμ„ 수 μžˆμœΌλ―€λ‘œ) 본문을 μˆ˜μ •ν•΄μ•Ό _do_ ν•΄μ•Ό ν•˜λ―€λ‘œ λ‹€μŒμ„ μˆ˜ν–‰ν•΄μ•Ό ν•©λ‹ˆλ‹€.

req.pipe(request.post({ url: 'http://some/new/url', form: { some: 'form', data: 'here' }));

이둜 인해 request 의 λ²„κ·Έλ‘œ μ˜μ‹¬λ˜λŠ” μ˜ˆμ™Έκ°€ λ°œμƒν•©λ‹ˆλ‹€.

μ–΄μ¨Œλ“  μ™„μ „νžˆ μƒˆλ‘œμš΄ request 개체λ₯Ό 직접 λ§Œλ“€ μˆ˜λŠ” μžˆμ§€λ§Œ λˆ„λ½λœ 것이 μ—†λŠ”μ§€ ν™•μΈν•˜κ³  버그인 경우 이 문제λ₯Ό λ³΄κ³ ν•˜κ³  μ‹Άμ—ˆμŠ΅λ‹ˆλ‹€.

항상 GET μš”μ²­μ„ μ‚¬μš©ν•˜κ³  있기 λ•Œλ¬Έμ— μž‘λ™ν•˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€. λ‚΄ μ½”λ“œ 예제λ₯Ό λ‹€μ‹œ μ‚΄νŽ΄λ³΄μ‹­μ‹œμ˜€.

request[req.method.toLowerCase()]('http://example.com')) λŠ” λ“€μ–΄μ˜€λŠ” μš”μ²­μ„ 기반으둜 μš”μ²­ 방법을 μ„€μ •ν•©λ‹ˆλ‹€.

κ·Έ 외에도 λ‚΄ 첫 번째 μ˜κ²¬μ—μ„œ λ‹€μ‹œ 본문을 μˆ˜μ •ν•΄μ•Ό ν•˜λŠ” 경우:

본문을 μˆ˜μ •ν•˜λ €λŠ” 경우 μƒˆ μš”μ²­μ„ κ΅¬μ„±ν•˜κ³  응닡에 νŒŒμ΄ν”„ν•˜λ©΄ λ©λ‹ˆλ‹€.

항상 GET μš”μ²­μ„ μ‚¬μš©ν•˜κ³  있기 λ•Œλ¬Έμ— μž‘λ™ν•˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€. λ‚΄ μ½”λ“œ 예제λ₯Ό λ‹€μ‹œ μ‚΄νŽ΄λ³΄μ‹­μ‹œμ˜€.

ν•˜μ§€λ§Œ request.post μžˆμŠ΅λ‹ˆλ‹€. request['post'] 와 λ™μΌν•©λ‹ˆλ‹€.

본문을 μˆ˜μ •ν•˜λ €λŠ” 경우 μƒˆ μš”μ²­μ„ κ΅¬μ„±ν•˜κ³  응닡에 νŒŒμ΄ν”„ν•˜λ©΄ λ©λ‹ˆλ‹€.

μš”μ²­μ„ μƒˆ μš”μ²­(헀더 볡사 λ“±)으둜 νŒŒμ΄ν”„ν•˜κΈ° μœ„ν•΄ 이미 request 에 μžˆλŠ” μ½”λ“œλ₯Ό 기본적으둜 λ‹€μ‹œ μž‘μ„±ν•΄μ•Ό ν•œλ‹€λŠ” 것은 큰 λ¬Έμ œμž…λ‹ˆλ‹€. λ‚΄κ°€ μ²˜λ¦¬ν•΄μ•Ό ν•˜λŠ” λ§Žμ€ 극단적인 κ²½μš°κ°€ μžˆμ„ 수 μžˆμŠ΅λ‹ˆλ‹€. ν•˜μ§€λ§Œ λ„€, 이것이 μ œκ°€ ν•  일이라고 μƒκ°ν•©λ‹ˆλ‹€.

IMO μ˜ˆμ™Έκ°€ λ°œμƒν•˜μ§€ μ•Šκ³  양식 본문이 μžˆλŠ” λ‹€λ₯Έ μš”μ²­μœΌλ‘œ μš”μ²­μ„ νŒŒμ΄ν”„ν•  수 μžˆμ–΄μ•Ό ν•©λ‹ˆκΉŒ, μ•„λ‹ˆλ©΄ 이 λ™μž‘μ— λŒ€ν•œ λͺ‡ 가지 μ΄μœ κ°€ μžˆλ‹€κ³  μƒκ°ν•˜μ‹­λ‹ˆκΉŒ?

이것은 λͺ…μ‹œμ μœΌλ‘œ λ‹€λ₯Έ 것을 μ§€μ •ν•˜μ§€ μ•ŠκΈ° λ•Œλ¬Έμ— 항상 GET μš”μ²­μ„ ν•˜λŠ” κ²ƒμž…λ‹ˆλ‹€.

μƒˆ 객체의 ꡬ성은 본체λ₯Ό μˆ˜μ •ν•˜λ €λŠ” 경우 μ—λ§Œ 적용

λ¬Όλ‘  ν˜„μž¬ μ½”λ“œλ² μ΄μŠ€λŠ” POSTλ₯Ό μ§€μ›ν•˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€. λ‚˜λŠ” 그것을 고치렀고 λ…Έλ ₯ν•˜κ³  μžˆλŠ”λ°, μ΄λ•Œ λ‚΄κ°€ 여기에 μ„€λͺ…λœ λ¬Έμ œμ— λΆ€λ”ͺμ³€μŠ΅λ‹ˆλ‹€. μ‚¬μš© 사둀λ₯Ό 더 잘 μ„€λͺ…ν•˜κΈ° μœ„ν•΄ κΈ°μ‘΄ μ½”λ“œλ² μ΄μŠ€λ₯Ό μ°Έμ‘°ν–ˆμ„ λΏμž…λ‹ˆλ‹€.

λ°”λ””λŠ” νŒŒμ΄ν”„ μž‘μ—…μœΌλ‘œ λ³΅μ‚¬λ˜μ§€ μ•ŠκΈ° λ•Œλ¬Έμ— λ°”λ””λ₯Ό μˆ˜μ •ν•˜κ³  싢지 μ•Šλ”λΌλ„ 항상 μƒˆ 객체λ₯Ό 생성해야 ν•œλ‹€κ³  ν™•μ‹ ν•©λ‹ˆλ‹€. λ‚΄κ°€ μ œκ³΅ν•œ 예제λ₯Ό μ‹œλ„ ν–ˆμŠ΅λ‹ˆκΉŒ? request 개체둜 νŒŒμ΄ν”„ν•˜λŠ” 본문이 μžˆλŠ” Express μš”μ²­μ΄ ν•„μš”ν•©λ‹ˆλ‹€. μƒˆ κ°œμ²΄μ—μ„œ 본문이 undefined μž„μ„ μ•Œ 수 μžˆμŠ΅λ‹ˆλ‹€.

GET μš”μ²­μ—λŠ” 본문이 μ—†μŠ΅λ‹ˆλ‹€. μ΄λŠ” μ˜λ„λœ κ²ƒμž…λ‹ˆλ‹€.

이것은 μž‘λ™ν•©λ‹ˆλ‹€ (κ·€ν•˜μ˜ 예).

'use strict';

let express = require('express');
let request = require('request');

let app = express();

app.use('/', (req, res) => {
  req.pipe(request.post('http://www.example.com'));
});

app.listen(process.env.PORT || 3000);

이것을 μ‚¬μš©ν•˜μ—¬ μš”μ²­:

var request = require('request')
request.post('http://localhost:3000', {form:{some:'data'}})

some=data 을(λ₯Ό) λ³΄λƒˆμŠ΅λ‹ˆλ‹€.

μƒˆ κ°œμ²΄μ—μ„œ 본문이 μ •μ˜λ˜μ§€ μ•Šμ€ 것을 λ³Ό 수 μžˆμŠ΅λ‹ˆλ‹€.

그게 어딨어, λ‚œ 널 따라가지 μ•Šμ•„.

흠, μ•Œμ•˜μ–΄. requestb.in을 μ‚¬μš©ν•  λ•Œ(쒋은 팁!) 본문이 μ‹€μ œλ‘œ _보내진_ 것을 λ³Ό 수 μžˆμŠ΅λ‹ˆλ‹€. μ‹€μ œλ‘œ μ „μ†‘λ˜μ§€ μ•Šμ•˜λ‹€κ³  믿게 λ§Œλ“  두 가지 λ¬Έμ œκ°€ μžˆμ—ˆμŠ΅λ‹ˆλ‹€.

1) cURL을 μ‚¬μš©ν•˜μ—¬ λ‚΄ μ„œλ²„μ— μš”μ²­μ„ 보낼 λ•Œ(이전 μ£Όμ„μ˜ μ½”λ“œλ₯Ό μ‚¬μš©ν•˜μ—¬) μš”μ²­μ„ 보낸 ν›„ μ€‘λ‹¨λ©λ‹ˆλ‹€(즉, cURL이 μ’…λ£Œλ˜μ§€ μ•ŠμŒ).
2) request.body 보면 undefined 반면 request.post λ₯Ό λͺ…μ‹œμ μΈ form 속성과 ν•¨κ»˜ μ‚¬μš©ν•˜μ—¬ μš”μ²­μ„ μƒμ„±ν•˜λŠ” κ²½μš°μ—λŠ” 그렇지 μ•ŠμŠ΅λ‹ˆλ‹€.

λ‚˜λŠ” 2)λŠ” 관련이 μ—†μœΌλ©° μ‹œμ²΄λŠ” λ‹¨μˆœνžˆ λ‹€λ₯Έ 곳에 μ €μž₯λ˜μ–΄ μžˆλ‹€κ³  μƒκ°ν•©λ‹ˆλ‹€. κ·Έλž˜λ„ 1)을 μž¬ν˜„ ν•  수 μžˆλŠ”μ§€ μ•Œκ³  μ‹ΆμŠ΅λ‹ˆλ‹€. cURL( curl --data "some=data" localhost:3000 )을 톡해 localhost:3000 μš”μ²­μ„ 보내면 μ’…λ£Œλ˜κ±°λ‚˜ μ€‘λ‹¨λ©λ‹ˆκΉŒ?

1) κ·€ν•˜μ˜ μ˜ˆμ—μ„œ 아무 것도 λ°˜ν™˜ν•˜μ§€ μ•ŠκΈ° λ•Œλ¬Έμ— μš”μ²­μ΄ μ€‘λ‹¨λ©λ‹ˆλ‹€. λ™μΌν•œ νŽ˜μ΄μ§€μ— μžˆλŠ”μ§€ ν™•μΈν•˜κΈ° μœ„ν•΄ μ‚¬μš©ν–ˆμŠ΅λ‹ˆλ‹€. .pipe(res) ν•˜λ©΄ 응닡을 받을 수 μžˆμŠ΅λ‹ˆλ‹€.
2) 슀트림 APIλ₯Ό μ‚¬μš©ν•  λ•Œ request.body λŠ” undefined

μ‹€μ œ μ˜ˆμ œμ—μ„œ μ‹€μ œλ‘œ .pipe(res) ν–ˆκ³  μž‘λ™ν•˜μ§€ μ•ŠλŠ” 것을 ν™•μΈν–ˆμŠ΅λ‹ˆλ‹€. μš”μ²­μ„ λ³΄λ‚΄λŠ” κ²ƒμœΌλ‘œ λ‚˜νƒ€λ‚˜μ§€ μ•Šκ³  μ€‘λ‹¨λ©λ‹ˆλ‹€. κ·€ν•˜μ˜ μ˜ˆκ°€ νš¨κ³Όκ°€ 있기 λ•Œλ¬Έμ— 문제의 원인을 λΉ λ₯΄κ²Œ μ°Ύμ•˜μŠ΅λ‹ˆλ‹€.

app.use(bodyParser.urlencoded({ extended: true }));

body-parser λ₯Ό μ‚¬μš©ν•˜λ©΄ 배관이 더 이상 μž‘λ™ν•˜μ§€ μ•ŠλŠ” 것 κ°™μŠ΅λ‹ˆλ‹€. λ™μ˜ν•˜μ‹­λ‹ˆκΉŒ? κ·Έλ ‡λ‹€λ©΄ 원인이 무엇인지 μ•„μ‹­λ‹ˆκΉŒ?

λ„€, 제 첫 λŒ“κΈ€μ„ λ‹€μ‹œ ν•œ 번 μ‚΄νŽ΄λ³΄λ©΄ λ‹€μŒκ³Ό κ°™μŠ΅λ‹ˆλ‹€.

// λ‹€λ₯Έ 미듀웨어보닀 λ¨Όμ € 배치

body-parser λŠ” 미듀웨어에 λ“€μ–΄κ°€κΈ° 전에 μš”μ²­μ„ μ²˜λ¦¬ν•˜μ§€λ§Œ μ„±κ³΅μ μœΌλ‘œ νŒŒμ΄ν”„ν•˜λ €λ©΄ μ›μ‹œ μš”μ²­μ΄ ν•„μš”ν•©λ‹ˆλ‹€.

휴! μ•Œκ² μŠ΅λ‹ˆλ‹€. 도움과 인내심을 κ°€μ Έ μ£Όμ…”μ„œ κ°μ‚¬ν•©λ‹ˆλ‹€. κ·Έ λ°”λ‹₯에 λ„λ‹¬ν•˜λŠ” 데 μ‹œκ°„μ΄ κ±Έλ ΈμŠ΅λ‹ˆλ‹€. λ‚˜λŠ” μ—¬μ „νžˆ λͺ¨λ“  헀더와 물건을 νŒŒμ΄ν”„ ν•œ λ‹€μŒ 본문을 μˆ˜μ •ν•  수 μ—†λ‹€λŠ” 것이 μΌμ’…μ˜ λΆˆν–‰μ΄λΌκ³  μƒκ°ν•˜μ§€λ§Œ κ·Έ μ£Όμœ„μ— 방법이 μ—†λ‹€κ³  μƒκ°ν•©λ‹ˆλ‹€.

@simov

app.use(function(req, res) {
  req.pipe(
    request[req.method.toLowerCase()]('http://example.com'))
  .pipe(res)
})

DELETE에 μ‹€νŒ¨ν•©λ‹ˆλ‹€. request.del은 req.deleteκ°€ μ•„λ‹Œ λ©”μ†Œλ“œμ΄κΈ° λ•Œλ¬Έμ—

λ‚˜λŠ” 이것이 μ˜€λž˜λ˜μ—ˆλ‹€λŠ” 것을 μ•Œκ³  μžˆμ§€λ§Œ 이에 λŒ€ν•œ μ μ ˆν•œ 해결책을 μ°ΎλŠ” 데 어렀움을 κ²ͺμ—ˆκ³  λ‹€λ₯Έ μ‚¬λžŒλ“€μ—κ²Œ μœ μš©ν•  것이라고 μƒκ°ν–ˆμŠ΅λ‹ˆλ‹€.

'use strict';

let express = require('express');
let request = require('request');

let app = express();

app.use('/', (req, res) => {
  req.pipe(request.post({ url: 'http://www.example.com', form: { foo: 'bar' }}), {end: false}).pipe(res);
});

app.listen(process.env.PORT || 3000);

https://nodejs.org/api/stream.html#stream_readable_pipe_destination_options 에 ν‘œμ‹œλœ λŒ€λ‘œ 이λ₯Ό μΆ”κ°€ν•˜λ©΄ reqκ°€ μ’…λ£Œλ  λ•Œ μƒˆ 슀트림이 μžλ™μœΌλ‘œ μ’…λ£Œλ˜μ§€ μ•Šλ„λ‘ ν•©λ‹ˆλ‹€.

이둜 인해 이 μ˜ˆμ œκ°€ μž‘λ™ν–ˆμ§€λ§Œ 이λ₯Ό μ‚¬μš©ν•˜μ—¬ λ‹€λ₯Έ λ©”μ„œλ“œμ— λŒ€ν•œ ν”„λ‘μ‹œλ₯Ό λ§Œλ“œλŠ” 데 λͺ‡ 가지 λ¬Έμ œκ°€ μžˆμŒμ„ λ°œκ²¬ν–ˆμŠ΅λ‹ˆλ‹€. λͺΈμ²΄λŠ” μ–΄λ–»κ²Œ λ“  λͺ¨λ“  것을 μ œλŒ€λ‘œ λ‹«κ²Œ ν•˜μ§€λ§Œ λͺΈμ²΄κ°€ μ—†μœΌλ©΄ μ—¬μ „νžˆ 맀달렀 μžˆμŠ΅λ‹ˆλ‹€. json λ°”λ”” νŒŒμ„œλ₯Ό μ‚¬μš©ν•˜λŠ” 경우 λ°”λ””κ°€ μ—†λŠ” κ²½μš°μ—λ„ λ°”λ””κ°€ {} 둜 읽히기 λ•Œλ¬Έμ— λ¬Έμ œκ°€ λ°œμƒν•˜μ§€ μ•Šμ§€λ§Œ λ°”λ””κ°€ μ—†μœΌλ©΄ μ—¬μ „νžˆ λ¬Έμ œκ°€ μžˆμ„ 수 μžˆμŠ΅λ‹ˆλ‹€. λ‚΄ ν˜„μž¬ μ†”λ£¨μ…˜μ€ μš”μ²­μ— λŒ€ν•œ μ½˜ν…μΈ  길이 헀더λ₯Ό ν™•μΈν•˜κ³  μ˜΅μ…˜ κ°œμ²΄κ°€ 있으면 μ‚¬μš©ν•˜λŠ” κ²ƒμž…λ‹ˆλ‹€.

@JeffreyAngell 은 해상도λ₯Ό μ‹œλ„ν•˜λ©΄ λ©λ‹ˆλ‹€. κ³ λ§ˆμ›Œ

이것은 λ‚˜λ₯Ό μœ„ν•΄ μž‘λ™ν•©λ‹ˆλ‹€.
`router.put('/', ν•¨μˆ˜(client_req, client_res, λ‹€μŒ) {
var json = JSON.stringify(client_req.body);
var μ˜΅μ…˜ = createOptions('PUT', client_req.baseUrl, json);

var proxy = https.request(options, function (res) {
    client_res.statusCode = res.statusCode;
    res.pipe(client_res, {
        end: true
    });
});

client_req.pipe(proxy, {
    end: true
});

proxy.write(json);
proxy.end();

});

ν•¨μˆ˜ createOptions(λ©”μ„œλ“œ, targetUrl, json) {
targetUrl = targetUrl.replace('지라/', '');
console.log("검색: " + targetUrl);

const auth = 'Basic ' + new Buffer('usr' + ':' + 'pass').toString('base64');
var headers = {
    'Authorization': auth,
    'Content-Type': 'application/json'
};

return {
    hostname: 'jira.acme.com',
    port: 443,
    path: targetUrl,
    method: method,
    headers: headers
};

}`

@simov

λ„€, 제 첫 λŒ“κΈ€μ„ λ‹€μ‹œ ν•œ 번 μ‚΄νŽ΄λ³΄λ©΄ λ‹€μŒκ³Ό κ°™μŠ΅λ‹ˆλ‹€.

// λ‹€λ₯Έ 미듀웨어보닀 λ¨Όμ € 배치

body-parserλŠ” 미듀웨어에 λ“€μ–΄κ°€κΈ° 전에 μš”μ²­μ„ μ²˜λ¦¬ν•˜μ§€λ§Œ μ„±κ³΅μ μœΌλ‘œ νŒŒμ΄ν”„ν•˜λ €λ©΄ μ›μ‹œ μš”μ²­μ΄ ν•„μš”ν•©λ‹ˆλ‹€.

같은 λ¬Έμ œκ°€ λ°œμƒν–ˆμŠ΅λ‹ˆλ‹€. λ‚΄ κ²½μš°μ—λŠ” bodyParser 미듀웨어

νŽΈμ§‘ν•˜λ‹€:
λͺ¨λ“  미듀웨어가 λ‘œλ“œλœ ν›„ 경둜λ₯Ό λ‘œλ“œν•˜κ³  μ‹ΆκΈ° λ•Œλ¬Έμ— μ²˜μŒμ— proxy κ°€ μžˆλŠ” λͺ¨λ“  κ²½λ‘œμ—μ„œ bodyParserλ₯Ό μ œμ™Έν•˜λŠ” 이 μ†”λ£¨μ…˜μ„ μ„ νƒν–ˆμŠ΅λ‹ˆλ‹€.

pathToRegexp = require('path-to-regexp')
exports.excludeMiddleware = (path, middleware) ->
  (req, res, next) ->
    if pathToRegexp(path).test req.path
      next()
    else
      middleware req, res, next
  app.use(routesService.excludeMiddleware '/proxy/(.*)', bodyParser.json({
    extended: false,
    parameterLimit: 10000,
    limit: 1024 * 1024 * 10
  }))

https://stackoverflow.com/questions/27117337/exclude-route-from-express-middleware

이 νŽ˜μ΄μ§€κ°€ 도움이 λ˜μ—ˆλ‚˜μš”?
0 / 5 - 0 λ“±κΈ‰