I am attempting to make a http.post call with angular 2. I have tested the call in postman, so I know that the api is working. I get an error, input empty which means that it isn't getting the data. I've read a few answers and articles, but not able to make a successful call with the data.
Can anyone give me some insight into what I am missing?
public upload(name: string, data: any, result, contentType: string) : Promise<Response> {
let headers = new Headers({ 'Content-Type': contentType });
let options = new RequestOptions({ headers: headers });
return this.http
.post(this.urlAPI, data, options)
.toPromise()
.then(this.extractData)
.catch(this.handleError);
}
extractData(res:Response) {
console.log('res: ', res);
let body = res.json();
return Promise.resolve(res);
}
handleError(err: any): Promise<any> {
console.error('An Error has occured: ', err);
return Promise.reject(err);
}
I am not sure what is the type of your 'data'. Data has to be stringified before sent. Below is a workable version for me.
saveNote(note: ApprovalNoteModel): Observable<ApprovalNoteModel> {
let body = JSON.stringify(note);
let headers = this.utilsSvc.getAuthHeaders();
headers.set('Content-Type', 'application/json');
return this.http.post('cloud/api/approval/note', body,
{ headers: headers }
).map(response => response.json());
}
If it is a file, then you can not do that thru 'http', I believe. Here is my workable version.
addFileRequest(referenceId: number, licenseId: number, url: string, files: File[]): Observable<any> {
return Observable.create(observer => {
this.progressObserver = observer;
let formData: FormData = new FormData(),
xhr: XMLHttpRequest = new XMLHttpRequest();
formData.append('referenceId', referenceId);
formData.append('licenseId', licenseId);
for (let i = 0; i < files.length; i++) {
formData.append("uploads[]", files[i], files[i].name);
}
xhr.onreadystatechange = () => {
if (xhr.readyState === 4) {
if (xhr.status === 200) {
observer.next(xhr.response);
observer.complete();
} else {
if (xhr.response.status)
observer.error(xhr.response);
else
observer.error({ 'status': xhr.status, '_body': xhr.response });
}
}
};
xhr.upload.onprogress = (event) => {
this.progress = Math.round(event.loaded / event.total * 100);
this.progressObserver.next(this.progress);
};
xhr.open('POST', url, true);
xhr.setRequestHeader('Authorization', this.utilsSvc.getToken());
xhr.send(formData);
});
}
Related
I'm struggling to find the solution to my problem with ionic native http.
I tried the answer to this post, but still i am getting the same error
this is my code
switchToggle(){
let url = 'https://io.adafruit.com//api/v2/myusername/feeds/my-feed-id/data/';
const headers = new Headers();
headers.set("Content-Type", "application/json")
headers.set("X-AIO-Key", "PASTED_MY_KEY_HERE");
let data = {
"datum":{
"value" : 1
}
};
this.http.setDataSerializer('json');
this.http.post(url,data,{headers:headers})
.then(data => {
console.log(data);
}).catch(error => {
console.log(error)
});
}
and this is the error I am getting
when I try other post request without headers it is working fine. But for this specific API I need to send the request together with the headers.
set your header like this =>
setHeaders() {
let headers = new Headers();
headers.append("X-AIO-Key", "PASTED_MY_KEY_HERE");
headers.append('Content-Type', 'application/json' );
const requestOptions = new RequestOptions({ headers: headers });
return requestOptions;
}
switchToggle(): Observable<any>{
let data = {
"datum":{
"value" : 1
}
};
return this.http.post(url, data, this.setHeaders())
.map(Response => Response.json())
.catch((error: any) => Observable.throw(error.json().error || 'Server error'));
}
I am trying to do http post in protractor. The status of http.post sits in pending status and doesn't return any response.
I am calling a method in onPrepare function under specDone:
jasmine.getEnv().addReporter({
specDone: function(result) {
if (result.status == "failed") {
browser.getCapabilities().then(function(caps) {
var browserName = caps.get("browserName");
browser.takeScreenshot().then(function(png) {
var stream = fs.createWriteStream(
"./reports/screenshots/" +
browserName +
"-" +
result.fullName +
".png"
);
stream.write(new Buffer(png, "base64"));
stream.end();
});
});
}
new PortalData().PushDataToPortal("");
}
});
Below function in called from onPrepare, the API takes the parameter from body. I am using protractor-http-client package for API calls.
export class PortalData {
public PushDataToPortal(result) {
const http: HttpClient = new HttpClient();
const LogFilePathInSharedLocation =
"\\\\10.101.101.11\\temp\\DocStar\\Automation\\TestLogs\\Logs.txt";
http
.post(
someurl,
LogFilePathInSharedLocation,
{ "Content-Type": "application/x-www-form-urlencoded" }
)
.then((response: ResponsePromise) => {
console.log(response);
});
}
Please advise. Thanks!
I would suggest you use Http call in beforeAll instead of onPrepare.
You can try superagent or supertest npm modules:
Example for superagent
const superagent = require('superagent');
// callback
superagent
.post('/api/pet')
.send({ name: 'Manny', species: 'cat' }) // sends a JSON post body
.set('X-API-Key', 'foobar')
.set('accept', 'json')
.end((err, res) => {
// Calling the end function will send the request
});
// promise with then/catch
superagent.post('/api/pet').then(console.log).catch(console.error);
// promise with async/await
(async () => {
try {
const res = await superagent.post('/api/pet');
console.log(res);
} catch (err) {
console.error(err);
}
})();
Example for supertest
const supertest = require('supertest');
const request = supertest(`${baseURL}`);
request.put('/test/sendlocal')
.send(profileAddressData.createData)
.set('Content-Type', 'application/json')
.set('Accept', '*/*')
.expect(200)
.end((err, res) => {
if (err) {
console.error('Error: ', err);
console.error('Response: ', res);
}
});
I am trying to upload an image using formData. The api is working fine. But the data is displaying null in the server.
My function is
capture_dl_front(){
this.camera.getPicture(this.cameraOptions)
.then(imageData => {
this.customer.dl_front = normalizeURL(imageData);
this.upload_dl_front(imageData);
}, error => {
this.func.showAlert('Error',JSON.stringify(error));
});
}
upload_dl_front(imageFileUri: any): void {
this.file.resolveLocalFilesystemUrl(imageFileUri)
.then(entry => (<FileEntry>entry).file(file => this.readFile_dl_front(file)))
.catch(err => console.log('Error',JSON.stringify(err)));
}
private readFile_dl_front(file: any) {
const reader = new FileReader();
reader.onloadend = () => {
const imgBlob = new Blob([reader.result], { type: file.type });
this.dl_front_imageUri = imgBlob;
this.dl_front_imageName = file.name;
alert(this.dl_front_imageName)
const img = new FormData();
img.append('image', this.dl_front_imageUri, this.dl_front_imageName)
this.api.test(img).then(data=>alert("final: "+data))
};
reader.readAsArrayBuffer(file);
}
and my api function is
test(image){
let headers = new HttpHeaders({
'Content-Type': 'application/x-www-form-urlencoded',
});
return new Promise( resolve => {
this.http.post(url, image, { headers: headers})
.subscribe(
data => {
resolve(data['message']);
},
error => {
resolve(error.statusText);
}
);
});
}
and i am getting the file in my laravel server as
$image = $request->file('image');
but i am getting null in the image parameter.
What am i doing wrong here?
You should remove the headers in the api call.
test(image){
return new Promise( resolve => {
this.http.post(url, image)
.subscribe(
data => {
resolve(data['message']);
},
error => {
resolve(error.statusText);
}
);
});
}
My http call is returning 200 but no response is captured. My code inside subscribe is not being hit. The API is returning data when I test in postman. Here is my code.
getToken(authcode: string) {
var data = 'client_id=InspectWebApp_client&code=' + authcode + '&redirect_uri=http://localhost:3000&grant_type=authorization_code';
let headers = new Headers({ 'Content-Type': 'application/x-www-form-urlencoded' });
let options = new RequestOptions({ headers: headers });
this.http.post('https://fedloginqa.test.com/as/token.oauth2', data, options)
.subscribe((res: Response) => {
var resultsToken = res.json();
localStorage.setItem("access_token",resultsToken.access_token)
//return this.inspections;
})
}
I was also facing the same problem. The problem was solved using the map function on Observables. Here is my implementation:
login(Username:string, Password:string) : Observable<Response>{
let headers = new Headers();
headers.append("Authorization", "Basic " + btoa(Username + ":" + Password));
headers.append("Content-Type", "application/x-www-form-urlencoded");
return this._http.post(this._baseUrl+"auth/login", " " , {headers: headers} )
.map((response: Response) => {
return response;
}).catch(this.handleError);
}
Here the handleError is a function to catch the excceptions generated. This is a function in login.service.ts that sends the username and password to the api to get data. You can see that I am returning response from the map function in this service. Now, this returned response can be caught in subscribe function in following way:
this._loginService.login(this.username, this.password)
.subscribe(
(response) => {
//Here you can map the response to a type.
this.apiResult = <IUser>response.json();
},
(err) => {
//Here you can catch the error
},
() => {this.router.navigate(['home'])}
);
I'm integrating Stripe payments with Angular2 (actually Ionic but the code is the same)
the call to Stripe.card.createToken is successful and returns a token
but in stripeResponseHandler which is an async callback, I cannot access any of the "this" variables. for example I cannot set this.amount = 10 and I cannot call this._http.post
how can I access the "this" variables ? I'm trying to http post the token and the amount to an API to make the payment
constructor(private _navController: NavController,
private _http: Http) { }
submitPayment() {
Stripe.setPublishableKey(this.key);
this.card = new Card();
this.card.number = this.cardNumber;
this.card.cvc = this.cardCVC;
this.card.exp_month = this.cardExpMonth;
this.card.exp_year = this.cardExpYear;
this.card.address_zip = this.cardAddressZip;
try {
Stripe.card.createToken(this.card, this.stripeResponseHandler);
}
catch (e) {
alert(e.message);
}
// Prevent the form from being submitted:
return false;
}
stripeResponseHandler(status, response) {
if (response.error) { // Problem!
alert(response.error);
} else { // Token was created!
// Get the token ID:
alert(response.id);
try {
this.amount = 10;
let payment = new Payment();
payment.token = response.id;
payment.amount = this.amount;
let body = JSON.stringify(payment);
let headers = new Headers({ 'Content-Type': 'application/json' });
let options = new RequestOptions({ headers: headers });
this._http.post(this.url, body, options)
.map(res => res.json())
.catch(this.handleError);
}
catch (e) {
alert(e.message);
}
}
}
handleError(error: Response) {
// may send the error to some remote logging infrastructure
// instead of just logging it to the console
console.error(error);
alert('error' + error.text + " " + error.statusText);
return Observable.throw(error.json().error || 'Server error');
}
If you just pass the function reference, then JavaScript doesn't keep the this reference. You have to take care of this explicitely:
Instead of
Stripe.card.createToken(this.card, this.stripeResponseHandler);
use
Stripe.card.createToken(this.card, (status, person) => this.stripeResponseHandler(status, person));
See also https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Functions/Arrow_functions
or
Stripe.card.createToken(this.card, this.stripeResponseHandler.bind(this));