185

When I make a post request the angular 2 http is not sending this request

this.http.post(this.adminUsersControllerRoute, JSON.stringify(user), this.getRequestOptions())

the http post is not sent to the server but if I make the request like this

this.http.post(this.adminUsersControllerRoute, JSON.stringify(user), this.getRequestOptions()).subscribe(r=>{});

Is this intended and if it is can someone explain me why ? Or it is a bug ?

3 Answers 3

303

Since the post method of the Http class returns an observable you need to call subscribe() to execute its initialization processing. Observables are lazy.

You should have a look at this video for more details:

Sign up to request clarification or add additional context in comments.

2 Comments

@Thiery Can't watch the video, since it's for members only
Always [I forget this].
83

You must subscribe to the returned observable if you want the call to execute.

See also the following angular documentation "Communicating with backend services using HTTP".

Starting the request

For all HttpClient methods, the method doesn't begin its HTTP request until you call subscribe() on the observable the method returns.

This is true for all HttpClient methods.

You should always unsubscribe from an observable when a component is destroyed.

All observables returned from HttpClient methods are cold by design. Execution of the HTTP request is deferred, letting you extend the observable with additional operations such as tap and catchError before anything actually happens.

Calling subscribe() triggers execution of the observable and causes HttpClient to compose and send the HTTP request to the server.

Think of these observables as blueprints for actual HTTP requests.

In fact, each subscribe() initiates a separate, independent execution of the observable. Subscribing twice results in two HTTP requests.

const req = http.get<Heroes>('/api/heroes');
// 0 requests made - .subscribe() not called.
req.subscribe();
// 1 request made.
req.subscribe();
// 2 requests made.

On a related note: The AsyncPipe subscribes (and unsubscribes) for you automatically.

Comments

48

Get method doesn't require to use the subscribe method but post method requires the subscribe. Get and post sample codes are below.

import { Component, OnInit } from '@angular/core'
import { Http, RequestOptions, Headers } from '@angular/http'
import 'rxjs/add/operator/map'
import 'rxjs/add/operator/catch'
import { Post } from './model/post'
import { Observable } from "rxjs/Observable";

@Component({
    templateUrl: './test.html',
    selector: 'test'
})
export class NgFor implements OnInit {

    posts: Observable<Post[]>
    model: Post = new Post()

    /**
     *
     */
    constructor(private http: Http) {

    }

    ngOnInit(){
        this.list()
    }

    private list(){
        this.posts = this.http.get("http://localhost:3000/posts").map((val, i) => <Post[]>val.json())
    }

    public addNewRecord(){
        let bodyString = JSON.stringify(this.model); // Stringify payload
        let headers      = new Headers({ 'Content-Type': 'application/json' }); // ... Set content type to JSON
        let options       = new RequestOptions({ headers: headers }); // Create a request option

        this.http.post("http://localhost:3000/posts", this.model, options) // ...using post request
                         .map(res => res.json()) // ...and calling .json() on the response to return data
                         .catch((error:any) => Observable.throw(error.json().error || 'Server error')) //...errors if
                         .subscribe();
    }
}

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.