Reputation: 4361
I try to make implement a login feature with angular5. I have an error i don't understand.
Here is the login.component.ts class :
import { Component, OnInit } from '@angular/core';
import { Router } from '@angular/router';
import { NgForm } from '@angular/forms';
import { FormGroup, FormControl } from '@angular/forms';
import { ReactiveFormsModule } from '@angular/forms';
import { HttpErrorResponse } from '@angular/common/http';
import { UserService } from '../auth/user.services';
@Component({
selector: 'app-login',
templateUrl: './login.component.html',
styleUrls: ['./login.component.css']
})
export class LoginComponent implements OnInit {
ngForm: NgForm;
login: string;
password: string;
myForm: FormGroup;
isLoginError : boolean = false;
connected : Boolean = false;
constructor(private userService: UserService, private router: Router) { }
ngOnInit() {
}
// Execute this when submit login form
OnSubmit(form){
console.log(form.value);
console.log(form.value.login);
this.connected = this.userService.authenticate(form.value.login,form.value.password).subscribe((data : any)=>{
return data.password = form.value.password;
//return true;
});
}
}
In user.service.ts i have the authenticate method :
authenticate(login:string, password:string) :Observable<Boolean> {
console.log('Authenticate ....');
const credentials = {login:login, password:password};
let headers = new HttpHeaders();
headers.append('Content-Type', 'application/json');
console.log('Appended content type ....');
console.log(' Login '+login+' Password '+password+' Headers '+headers);
//var data = this.http.get<any>(
// '/users?login?'+JSON.stringify(login),
// { headers }
//);
//console.log('Data '+data);
return this.http.get<any>(
'/users?login?'+JSON.stringify(login),
{ headers }
) //returns a User object having password
.map(user => user.password === password); // maps result to the desired true or false value
}
Here is my login form :
<div class="row">
<div class="col-md-6 offset-md-3 text-center">
<h2> Formulaire de connexion </h2>
<form (ngSubmit)="OnSubmit(loginForm)" #loginForm="ngForm">
<div class="form-group">
<label for="exampleInputEmail1">Login</label>
<input type="text" class="form-control" id="exampleInputEmail1" [(ngModel)]="login" name="login" aria-describedby="emailHelp" placeholder="Login">
</div>
<div class="form-group">
<label for="exampleInputPassword1">Password</label>
<input type="password" class="form-control" id="exampleInputPassword1" required [(ngModel)]="password" name="password" placeholder="Mot de passe">
</div>
<!-- <button type="submit" class="btn btn-primary" (click)="login()" [disabled]="!loginForm.form.valid">Connexion</button>
-->
<button type="submit" class="btn btn-primary" [disabled]="!loginForm.form.valid">Connexion</button>
</form>
</div>
</div>
My code compile and i can access the login page. But when i enter login and password, i have an error. And i cannot see the request to my server. I think the error is before my http request. Here is the error i am getting :
TypeError: You provided 'undefined' where a stream was expected. You can provide an Observable, Promise, Array, or Iterable. Stack trace: subscribeToResult@webpack-internal:///./node_modules/rxjs/_esm5/util/subscribeToResult.js:83:27 MergeMapSubscriber.prototype._innerSub@webpack-internal:///./node_modules/rxjs/_esm5/operators/mergeMap.js:143:18 MergeMapSubscriber.prototype._tryNext@webpack-internal:///./node_modules/rxjs/_esm5/operators/mergeMap.js:140:9 MergeMapSubscriber.prototype._next@webpack-internal:///./node_modules/rxjs/_esm5/operators/mergeMap.js:123:13 Subscriber.prototype.next@webpack-internal:///./node_modules/rxjs/_esm5/Subscriber.js:97:13 ScalarObservable.prototype._subscribe@webpack-internal:///./node_modules/rxjs/_esm5/observable/ScalarObservable.js:53:13 Observable.prototype._trySubscribe@webpack-internal:///./node_modules/rxjs/_esm5/Observable.js:177:20 Observable.prototype.subscribe@webpack-internal:///./node_modules/rxjs/_esm5/Observable.js:165:88 MergeMapOperator.prototype.call@webpack-internal:///./node_modules/rxjs/_esm5/operators/mergeMap.js:97:16 Observable.prototype.subscribe@webpack-internal:///./node_modules/rxjs/_esm5/Observable.js:162:13 FilterOperator.prototype.call@webpack-internal:///./node_modules/rxjs/_esm5/operators/filter.js:63:16 Observable.prototype.subscribe@webpack-internal:///./node_modules/rxjs/_esm5/Observable.js:162:13 MapOperator.prototype.call@webpack-internal:///./node_modules/rxjs/_esm5/operators/map.js:60:16 Observable.prototype.subscribe@webpack-internal:///./node_modules/rxjs/_esm5/Observable.js:162:13 MapOperator.prototype.call@webpack-internal:///./node_modules/rxjs/_esm5/operators/map.js:60:16 Observable.prototype.subscribe@webpack-internal:///./node_modules/rxjs/_esm5/Observable.js:162:13 LoginComponent.prototype.OnSubmit@webpack-internal:///./src/app/login/login.component.ts:33:9 View_LoginComponent_0/<@ng:///AppModule/LoginComponent.ngfactory.js:29:23 handleEvent@webpack-internal:///./node_modules/@angular/core/esm5/core.js:13763:115 callWithDebugContext@webpack-internal:///./node_modules/@angular/core/esm5/core.js:15272:39 debugHandleEvent@webpack-internal:///./node_modules/@angular/core/esm5/core.js:14859:12 dispatchEvent@webpack-internal:///./node_modules/@angular/core/esm5/core.js:10178:16 eventHandlerClosure/<@webpack-internal:///./node_modules/@angular/core/esm5/core.js:12517:38 EventEmitter.prototype.subscribe/schedulerFn<@webpack-internal:///./node_modules/@angular/core/esm5/core.js:4559:36 SafeSubscriber.prototype.__tryOrUnsub@webpack-internal:///./node_modules/rxjs/_esm5/Subscriber.js:245:13 SafeSubscriber.prototype.next@webpack-internal:///./node_modules/rxjs/_esm5/Subscriber.js:192:17 Subscriber.prototype._next@webpack-internal:///./node_modules/rxjs/_esm5/Subscriber.js:133:9 Subscriber.prototype.next@webpack-internal:///./node_modules/rxjs/_esm5/Subscriber.js:97:13 Subject.prototype.next@webpack-internal:///./node_modules/rxjs/_esm5/Subject.js:65:17 EventEmitter.prototype.emit@webpack-internal:///./node_modules/@angular/core/esm5/core.js:4527:24 NgForm.prototype.onSubmit@webpack-internal:///./node_modules/@angular/forms/esm5/forms.js:5840:9 View_LoginComponent_0/<@ng:///AppModule/LoginComponent.ngfactory.js:21:23 handleEvent@webpack-internal:///./node_modules/@angular/core/esm5/core.js:13763:115 callWithDebugContext@webpack-internal:///./node_modules/@angular/core/esm5/core.js:15272:39 debugHandleEvent@webpack-internal:///./node_modules/@angular/core/esm5/core.js:14859:12 dispatchEvent@webpack-internal:///./node_modules/@angular/core/esm5/core.js:10178:16 renderEventHandlerClosure/<@webpack-internal:///./node_modules/@angular/core/esm5/core.js:10803:38 decoratePreventDefault/<@webpack-internal:///./node_modules/@angular/platform-browser/esm5/platform-browser.js:2680:53 ZoneDelegate.prototype.invokeTask@webpack-internal:///./node_modules/zone.js/dist/zone.js:421:17 onInvokeTask@webpack-internal:///./node_modules/@angular/core/esm5/core.js:4956:24 ZoneDelegate.prototype.invokeTask@webpack-internal:///./node_modules/zone.js/dist/zone.js:420:17 Zone.prototype.runTask@webpack-internal:///./node_modules/zone.js/dist/zone.js:188:28 ZoneTask.invokeTask@webpack-internal:///./node_modules/zone.js/dist/zone.js:496:24 invokeTask@webpack-internal:///./node_modules/zone.js/dist/zone.js:1517:9 globalZoneAwareCallback@webpack-internal:///./node_modules/zone.js/dist/zone.js:1543:17
The error is at line <form (ngSubmit)="OnSubmit(loginForm)" #loginForm="ngForm">
I don't see where is the problem. What am i missing ? Thanks Thanks
Upvotes: 3
Views: 14224
Reputation: 34435
I can't see anything in posted code that could cause request not to be sent. Maybe you have some http interceptors somewhere?
There are also a few errors in your code
HttpHeaders
are immutable
So if you want your headers to be sent properly, you need to change your code to
let headers = new HttpHeaders().append('Content-Type', 'application/json');
content-type
You don't need to set the content-type for a request returning json, the httpClient
automatically turns the response to a json Object by default
wrong query parameter
It should be = instead of ?
'/users?login='+JSON.stringify(login),
component
this.connected
will never be a boolean value, but a reference to the observable
In the subcribe method, data is a boolean, not an object (since you mapped it in your service)
Note I hope that authentication method you showed won't be the final one. As it stands, it assumes the server can return a user's details, password in clear text included... This is really bad from a security point of view if your users have their passwords stored in plain text server side
Upvotes: 3