Angular2-Http POST 요청 매개 변수


93

POST 요청을하려고하는데 작동 할 수 없습니다.

testRequest() {
      var body = 'username=myusername?password=mypassword';
      var headers = new Headers();
      headers.append('Content-Type', 'application/x-www-form-urlencoded');

      this.http
        .post('/api',
          body, {
            headers: headers
          })
          .subscribe(data => {
                alert('ok');
          }, error => {
              console.log(JSON.stringify(error.json()));
          });
}

기본적 으로이 http 요청 (아약스가 아님)을 html 형식에서 시작한 것처럼 복제하고 싶습니다.

URL : / api

매개 변수 : 사용자 이름 및 비밀번호


stackoverflow.com/a/34758630/5043867stackoverflow.com/a/34823818/5043867을 살펴보십시오. 이것은 POST 요청에 대한 모든 것을 자세히 설명합니다!
Pardeep Jain

@PardeepJain 저는 API를 사용하려고하지 않습니다. html 양식에서 시작된 POST를 시뮬레이션하기 위해.
Christopher

또한, 여기에서 확인하여 파일을 게시 user_name하고 password, stackoverflow.com/a/45879409/2803344
Belter

답변:


49

본문이 application/x-www-form-urlencoded콘텐츠 유형에 맞지 않는 것 같습니다 . 이것을 사용해 볼 수 있습니다.

var body = 'username=myusername&password=mypassword';

도움이 되었기를 바랍니다, Thierry


예 헤더에있는 콘텐츠 유형, 대신 JSON 문자열의 "옛날 방식"에 값을 전달하는 유일한 솔루션입니다
Nather 웨버

이것은 좋은 대답이 아닙니다. 아래에 더 많은 찬성표와 함께 URLSearchParams를 대신 사용하십시오.
Mick

Google 검색을 통해 오는 미래의 사람들 에게는 이것이 최선의 답변 이 아닙니다 (공격적인 Thierry! 귀하의 답변은 여전히 ​​기술적으로 정확합니다 :)). V Stoykov의 대답 은 지금까지 가장 정확합니다. ps import { URLSearchParams } from "@angular/http"는 기본 항목이 아닌지 확인 하므로 1) 작업을 수행 할 필요가없고 .toString2) 콘텐츠 유형을 설정할 필요가 없습니다. 각도 (참조 : 당신을 위해 자동으로 추측됩니다 github.com/angular/angular/blob/4.4.4/packages/http/src/...를 )
에 란 메단에게

안녕하세요 ! 헤더-> 'application / json'과 같은 콘텐츠 유형으로 포스트 서비스를 전달하려면 본문에 전달해야하는 내용 .... json 객체를 전달하려고하는데 제대로 작동하지 않습니다.
VjyV

107

Angualar 4.3 이상 업데이트

이제 우리는 HttpClient대신 사용할 수 있습니다.Http

가이드는 여기

샘플 코드

const myheader = new HttpHeaders().set('Content-Type', 'application/x-www-form-urlencoded')
let body = new HttpParams();
body = body.set('username', USERNAME);
body = body.set('password', PASSWORD);
http
  .post('/api', body, {
    headers: myheader),
  })
  .subscribe();

사용되지 않음

또는 다음과 같이 할 수 있습니다.

let urlSearchParams = new URLSearchParams();
urlSearchParams.append('username', username);
urlSearchParams.append('password', password);
let body = urlSearchParams.toString()

2017 년 10 월 업데이트

에서 angular4 + , 우리는 필요하지 않습니다 headers, 또는 .toString()거즈. 대신 아래 예제와 같이 할 수 있습니다.

import { URLSearchParams } from '@angular/http';

POST / PUT 방법

let urlSearchParams = new URLSearchParams();
urlSearchParams.append('username', username);
urlSearchParams.append('password', password);
this.http.post('/api', urlSearchParams).subscribe(
      data => {
        alert('ok');
      },
      error => {
        console.log(JSON.stringify(error.json()));
      }
    )

GET / DELETE 메서드

    let urlSearchParams = new URLSearchParams();
    urlSearchParams.append('username', username);
    urlSearchParams.append('password', password);
    this.http.get('/api', { search: urlSearchParams }).subscribe(
      data => {
        alert('ok');
      },
      error => {
        console.log(JSON.stringify(error.json()));
      }
    )

JSON application/json콘텐츠 유형의 경우

this.http.post('/api',
      JSON.stringify({
        username: username,
        password: password,
      })).subscribe(
      data => {
        alert('ok');
      },
      error => {
        console.log(JSON.stringify(error.json()));
      }
      )

14
URLSearchParams 클래스를 가져 오는 것을 잊지 마십시오import { URLSearchParams } from "angular2/http"
Sebastian Hernandez

10
내 가져 오기가 다르게 보입니다. import {URLSearchParams} from '@ angular / http';
dang

그러나 양식 객체를 보내는 더 간단한 방법은 없습니까? 나는 URLSearchParams ()를 사용하여 편안한 백엔드에 대한 게시물을 보내는 튜토리얼을 보지 못했습니다. 그들은 어떻게합니까? return this.http.post (this.actionUrl, body, {headers : this.headers}) .map ((response : Response) => response.json ()) .catch (this.handleError);
stackdave

부울과 어떻게 작동합니까? 부울이나 숫자를 추가 할 수 없다는 오류 메시지가
표시됨

부울 정보, 어쩌면이 항목에서는 도움이 될 수 있습니다 stackoverflow.com/questions/14774907/...
프랭크 응우 엔

41

Angular2의 이후 버전에서는 Content-Type올바른 유형의 객체 를 .NET Framework로 전달하는 경우 헤더 를 수동으로 설정 하고 본문을 인코딩 할 필요가 없습니다 body.

당신은 단순히 이것을 할 수 있습니다

import { URLSearchParams } from "@angular/http"


testRequest() {
  let data = new URLSearchParams();
  data.append('username', username);
  data.append('password', password);

  this.http
    .post('/api', data)
      .subscribe(data => {
            alert('ok');
      }, error => {
          console.log(error.json());
      });
}

이렇게하면 angular가 본문을 인코딩하고 올바른 Content-Type헤더를 설정합니다 .

추신 : 가져 오기 URLSearchParams를 잊지 마십시오 @angular/http. 그렇지 않으면 작동하지 않습니다.


2
@VStoykov 그것은 작동하지 않습니다, 당신은 매개 변수에 .toString ()해야하고 콘텐츠 유형을 지정해야하며 각도 4.0.3을 사용합니다
Konrad

1
@ i'myourhuckleberry 4.0.3에서도 작동합니다. 소스 코드를 보십시오. github.com/angular/angular/blob/4.0.3/packages/http/src/…
VStoykov 2017-04-26

1
@VStoykov 그것은 나를 위해 작동하지 않으며 Github에서 버그로보고했습니다
Konrad

1
확인. Nvm은 "@ angular / http"에서 가져와야했습니다. 그렇지 않으면 유형을 인식하지만 각도의 유형이 아닙니다.
Konrad

1
@ i'myourhuckleberry 가져 오기가 내 예의 첫 번째 줄 이었지만 아마도 놓친 것 같습니다. 브라우저의 내장 유형 FormData에서을 사용할 수 있으며 각도 도 작동하도록 설정 Content-Type됩니다 multipart/form-data.
VStoykov

10

그래서 완전한 답을 만들기 위해 :

login(username, password) {
        var headers = new Headers();
        headers.append('Content-Type', 'application/x-www-form-urlencoded');
        let urlSearchParams = new URLSearchParams();
        urlSearchParams.append('username', username);
        urlSearchParams.append('password', password);
        let body = urlSearchParams.toString()
        return this.http.post('http://localHost:3000/users/login', body, {headers:headers})
            .map((response: Response) => {
                // login successful if there's a jwt token in the response
                console.log(response);
                var body = response.json();
                console.log(body);
                if (body.response){
                    let user = response.json();
                    if (user && user.token) {
                        // store user details and jwt token in local storage to keep user logged in between page refreshes
                        localStorage.setItem('currentUser', JSON.stringify(user)); 
                    }
                }
                else{
                    return body;
                }
            });
    }

1
[ts] '{헤더 유형의 인수 : RequestOptions; } '은'RequestOptionsArgs '유형의 매개 변수에 할당 할 수 없습니다
Sonic Soul

2
@Sonic Soul 그것은 단지 : .. post ( '/ api', body, headers) ... 헤더 주위에 {}없이
Guenther

5

이 답변은 Http가 아닌 HttpClient를 사용하는 사람들에게 모두 구식입니다. "URLSearchParams 가져 오기를 수행했지만 .toString () 및 명시 적 헤더 없이는 여전히 작동하지 않습니다!"라는 생각이 들기 시작했습니다.

HttpClient를 사용하면 URLSearchParams 대신 HttpParams를 사용 body = body.append()하고 변경 불가능한 객체로 작업하기 때문에 본문에서 여러 매개 변수를 얻기위한 구문을 확인합니다.

login(userName: string, password: string): Promise<boolean> {
    if (!userName || !password) {
      return Promise.resolve(false);
    }

    let body: HttpParams = new HttpParams();
    body = body.append('grant_type', 'password');
    body = body.append('username', userName);
    body = body.append('password', password);

    return this.http.post(this.url, body)
      .map(res => {
        if (res) {          
          return true;
        }
        return false;
      })
      .toPromise();
  }

위의 솔루션에 감사드립니다. 하지만 ng build --prod를 실행할 때 내 body param은 "{"params ": {"rawParams ":" ","queryEncoder ": {},"paramsMap ": {}}} :"처럼 보입니다. 해결 방법이 있습니까?
Hemanth Poluru

4

누구나 앵귤러 버전 4+ 로 어려움을 겪고 있다면 (내 4.3.6) . 이것은 나를 위해 일한 샘플 코드였습니다.

먼저 필요한 가져 오기를 추가하십시오.

import { Http, Headers, Response, URLSearchParams } from '@angular/http';

그런 다음 api 함수에 대해. 필요에 따라 변경할 수있는 로그인 샘플입니다.

login(username: string, password: string) {
    var headers = new Headers();
    headers.append('Content-Type', 'application/x-www-form-urlencoded');
    let urlSearchParams = new URLSearchParams();
    urlSearchParams.append('email', username);
    urlSearchParams.append('password', password);
    let body = urlSearchParams.toString()

    return this.http.post('http://localhost:3000/api/v1/login', body, {headers: headers})
        .map((response: Response) => {
            // login successful if user.status = success in the response
            let user = response.json();
            console.log(user.status)
            if (user && "success" == user.status) {
                // store user details and jwt token in local storage to keep user logged in between page refreshes
                localStorage.setItem('currentUser', JSON.stringify(user.data));
            }
        });
}

1
angular: 
    MethodName(stringValue: any): Observable<any> {
    let params = new HttpParams();
    params = params.append('categoryName', stringValue);

    return this.http.post('yoururl', '', {
      headers: new HttpHeaders({
        'Content-Type': 'application/json'
      }),
      params: params,
      responseType: "json"
    })
  }

api:   
  [HttpPost("[action]")]
  public object Method(string categoryName)

안녕하세요, Stackoverflow에 오신 것을 환영합니다. 이 질문에 답 해주셔서 감사합니다.하지만 코드 블록을 게시하는 것만으로는 OP 나 앞으로이 질문을 접하게되는 사람에게는 이해하기 어렵습니다. 질문 을 편집 하고 해결 한 문제와 해결 방법에 대한 (짧은) 설명을 제공하여 솔루션을 더 잘 이해할 수 있도록 도와 주시겠습니까?
Plutian

1
안녕하세요 @Plutian 내가 게시물 요청의 두 번째 매개 변수에 값을 전달했을 때 API에 null 값을 반환하므로 두 번째 매개 변수를 빈 문자열로 전달하고 세 번째 매개 변수의 params 속성 값을 전달하여이 방법이 저를 위해 일했습니다
Muniyan

0

여러 매개 변수를 사용하는 모든 접근 방식에 문제가 있었지만 단일 개체에서 잘 작동합니다.

API :

    [HttpPut]
    [Route("addfeeratevalue")]
    public object AddFeeRateValue(MyValeObject val)

모난:

var o = {ID:rateId, AMOUNT_TO: amountTo, VALUE: value};
return this.http.put('/api/ctrl/mymethod', JSON.stringify(o), this.getPutHeaders());


private getPutHeaders(){
    let headers = new Headers();
    headers.append('Content-Type', 'application/json');
    return new RequestOptions({
        headers: headers
        , withCredentials: true // optional when using windows auth
    });
}

1
OP의 문제는 application / x-www-form-urlencoded의 콘텐츠 유형입니다. 답변은 완전히 다른 문제입니다.
Christian Ulbrich

-2

비슷한 일을하려고 할 때 여기에 착륙했습니다. application / x-www-form-urlencoded 콘텐츠 유형의 경우 본문에 대해 다음을 사용할 수 있습니다.

var body = 'username' =myusername & 'password'=mypassword;

당신이 시도한 것과 함께 body에 할당 된 값은 문자열이 될 것입니다.


Joshua가 지적했듯이 이것은 유효한 JavaScript 나 TypeScript가 아닙니다. 나는 당신이 의미하는 것이 정확히 현재 받아 들여지는 대답이라고 생각합니다.
Christian Ulbrich
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.