繁体   English   中英

Angular2 Http Call未触发

[英]Angular2 Http Call not firing

内容:

在完成了几篇教程之后,我将测试Angular2和JWT的身份验证。 我带有一个组件和一个服务:

app.component.ts
user.service.ts

应用程序组件(和模板)包含对可观察对象的订阅,该订阅显示了用户的登录状态。 “可观察”项保留在用户服务中,并且在用户登录和注销时进行更改(精细)。

身份验证令牌在“ localStorage”中写为“ auth_token”。 它包含一个有效性值(时间),该值应迫使用户在一段时间后再次登录。

我想做的是在应用程序初始化中检查令牌的有效性。 首先,我尝试从user.service构造器执行此操作,然后(失败),尝试从app.component中的ngOnInit执行操作,然后(再次失败),我尝试在事件调用时执行操作(单击a按钮),但再次失败!

一些缩短的代码:

//app.component.html
//...
    <a md-button class="app-icon-button" aria-label="checklogin" (click)="checkLogin()">
        <md-icon svgIcon="check"></md-icon>
    </a>
//...

//app.component.ts
//...
    checkLogin(){
        console.log('CHECK LOGIN FUNCTION');
        let token = localStorage.getItem('auth_token');
        if(token){
            console.log('TOKEN FOUND');
            this.userService.checkToken(token);
        }else{
            console.log('NO TOKEN FOUND');
        }
    }
//...

//user.service.ts
//...
    checkToken(token){
        console.log('CHECK TOKEN FUNCTION');
        console.log('TOKEN : '+token);
        let headers = new Headers();
        headers.append('Content-Type','application/json');
        return this.http
            .post(
                '/url/script.php',
                JSON.stringify(token),
                { headers }
            )
            .map(res => res.json())
            .map((res) => {
                console.log('SCRIPT RESULT : ');
                if(res.valid){
                    console.log('TOKEN IS VALID');
                    return true;
                }else{
                    console.log('TOKEN NOT VALID');
                    return false;
                }
            });
    }
//...

我确实跳过了可观察的部分和订阅。

问题:

问题实际上是该应用程序从不调用脚本!

当我确实点击“ checkLogin”按钮时(如果存在令牌),

console shows 'CHECK LOGIN FUNCTION',
console shows 'TOKEN FOUND',
console shows 'CHECK TOKEN FUNCTION',
console shows 'TOKEN : '****************************** (token),

但是它永远不会显示“ SCRIPT RESULT”,并且在使用Firebug检查http调用是否完成时,script.php没有调用。 看起来this.http部分只是被忽略了...

感谢您的阅读/帮助

仅当您有一个subscriber ,使用Observables Ajax调用才有效。

因此,您需要subscribeObservable 这是Angular 2功能。 当您不订阅Observable ,它将永远不会进行该调用。

同样,您也不需要从订阅服务器返回任何内容,因为您实际上无法返回任何内容。

this.userService.checkToken(token).subscribe((res) => {
   console.log('SCRIPT RESULT : ');
   if(res.valid) {
      console.log('TOKEN IS VALID');          
   } else {
      console.log('TOKEN NOT VALID');
   }
});

checkToken(token){
   console.log('CHECK TOKEN FUNCTION');
   console.log('TOKEN : '+token);
   let headers = new Headers();
   headers.append('Content-Type','application/json');
   return this.http
       .post(
           '/url/script.php',
           JSON.stringify(token),
           { headers }
       )
       .map(res => res.json());           
}

当订阅仅在使用者使用.subscribe方法订阅输出结果时使用时,服务才能开始工作。

您需要: this.userService.checkToken(token).subscribe()

您的checkToken()方法返回一个需要subsrcibeObservable 可观察对象除非已订阅,否则将永远不会执行。

checkLogin(){
        console.log('CHECK LOGIN FUNCTION');
        let token = localStorage.getItem('auth_token');
        if(token){
            console.log('TOKEN FOUND');
            this.userService.checkToken(token).subscribe(result => {
               console.log(result); 
            }),
            error => { 
               console.log(error); 
            });
        } else {
            console.log('NO TOKEN FOUND');
        }
    }

您是否尝试过使用Postman并尝试调用所需的函数?

另外,如果angular2-jwt可以为您做到这一点,为什么还要验证令牌?

您可以这样做:

使用npm安装angular2-jwt

包含在app.module.ts

import { AUTH_PROVIDERS } from 'angular2-jwt';

添加到提供者:

providers: [
    AUTH_PROVIDERS,
],

例如auth.service.ts看起来像这样:

import { Injectable, Inject }                                               from '@angular/core';
import { Http, Response, Headers, RequestOptions, RequestMethod }           from '@angular/http';
import { Router }                                                           from '@angular/router';

import { Observable }                                                       from 'rxjs/Observable';
import { Configuration }                                                    from '../../app.config';

import { RegisterViewModel }                                                from '../../model/viewModel/registerViewModel';
import { LoginViewModel }                                                   from '../../model/viewModel/loginViewModel';

import { tokenNotExpired, AuthHttp }                                        from 'angular2-jwt';

@Injectable()
export class AuthService {

private actionUrl: string; 

constructor(private _http: Http, private _config: Configuration, private _router: Router, private _authHttp: AuthHttp){
    this.actionUrl = _config.apiUrl;
}

register(user: RegisterViewModel){
    let headers = new Headers({ 'Content-Type': 'application/json' });
    //Admin in this system can only register users. that is why auth
    return this._authHttp.post(this.actionUrl + '/Account/Register', JSON.stringify(user), { headers : headers })
        .do(response => {
            console.log(response.toString());
        });
}

login(user: LoginViewModel) {
    let headers = new Headers({ 'Content-Type': 'application/x-www-form-urlencoded' });
    return this._http.post('http://localhost:56181/api/token', "username=" + user.userName + "&password=" + user.password + "&userId=" + user.userId, { headers : headers })
        .do(response => {
            if(response){
                let authResult = response.json();
                this.setUser(authResult);
                this._router.navigate(['']);
            }
        });
}

public isAuthenticated(): boolean {
    //angular2-jwt has this function to check if token is valid
    return tokenNotExpired();
}

private setUser(authResult: any): void {
    localStorage.setItem('id_token', authResult.id_token);
}

public logout(): void {
    localStorage.removeItem('id_token');
    this._router.navigate(['']);
}

}

还要记住, angular2-jwtlocalstorage id_token令牌的默认名称为id_token ,否则您将不得不使用angular2-jwt帮助类来指定其他令牌名称。

您只需执行以下操作即可检查其是否正常工作:

app.component.ts

export class AppComponent { 
constructor(private _auth: AuthService){
}
}

并在app.component.html

 <li>
 <a class="nav-link" [routerLink]="['/login']" *ngIf="!_auth.isAuthenticated()">Login</a>
 </li>
 <li>
 <a class="nav-link" (click)="_auth.logout()" *ngIf="_auth.isAuthenticated()">Log Out</a>
 </li>

您也可以在以下位置阅读有关它的一些文档:

https://auth0.com/blog/introducing-angular2-jwt-a-library-for-angular2-authentication/

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM