>source

이것은 기본적인 질문일 수 있습니다. 하지만 저는 각도 서비스(약속, 관찰 가능 등)에 익숙하지 않습니다.

기본적으로 로그인 페이지에 버튼(로그인)이 있습니다. 사용자가 해당 버튼을 클릭하면 토큰을 확인하고 생성하려고 합니다. 토큰이 서비스 필드에 할당되면 일부 페이지(홈 페이지)로 리디렉션됩니다. 그러나 지금 일어나고 있는 일은 내가 Angular 서비스 함수에 대한 함수 호출을 했을 때 토큰 자체를 가져오기 전에(비동기적으로) 내 페이지가 리디렉션되고 있다는 것입니다.


앱 데이터 서비스

`
    import { Injectable } from '@angular/core';
    import { HttpClient,HttpHeaders } from '@angular/common/http';
    import 'rxjs/add/operator/map';
    import 'rxjs/add/operator/mergeMap';
    import 'rxjs/add/operator/toPromise';
    @Injectable()
    export class AppDataServiceService {
      tokenGenerated:any='';
      constructor(private http: HttpClient) {
      }
      getData(){
        console.log("Started.. in service");
         this.http.get('http://host/url').toPromise()
         .then(this.extractData);
      }
      private extractData(res: Response) {
        console.log("completed.. in service");
        this.tokenGenerated=res;
        return res;
    }
    }
    `---------------------------------------------------
    login component
    import { Component, OnInit } from '@angular/core';
    import { AppDataServiceService } from '../app-data-service.service';
    import { Router } from '@angular/router';
    @Component({
      selector: 'app-login-component',
      templateUrl: './login-component.component.html',
      styleUrls: ['./login-component.component.css']
    })
    export class LoginComponentComponent implements OnInit {
      constructor(private dataService:AppDataServiceService,private router:Router) {
       }
      ngOnInit() {
      }
      submit(){
        this.dataService.getData();
        console.log('after executing service');
        this.router.navigate(['/view']);
      };
    }
-------------------------------------------------------------
   login html
<div class="container">  <label><b>Username</b></label>  <input type="text" placeholder="Enter Username" name="uname" >  <label><b>Password</b></label>  <input type="password" placeholder="Enter Password" name="psw" ></div><input type="button" (click)='submit()'  value="Login"  name="submit"/>

브라우저의 콘솔 출력:

시작.. 서비스 중

서비스 실행 후

완료.. 서비스 중

http 호출이 완료될 때까지 기다리도록 도와줄 수 있습니까? 그것이 약속을 사용하여 호출을 동기식으로 만드는 방법인지 확실하지 않습니다.

. this.router.navigate(['/view']) 사용; 구성 요소 내부의 약속 확인자 내부에서 서비스 클래스에서 약속을 반환합니다.

Niladri2021-09-20 05:22:23
  • 답변 # 1

    동기 http 요청을 아래와 같이 사용

    var request= new XMLHttpRequest();
    request.open('GET', "https://domain/api", false);
    request.send(null);
    const response= JSON.parse(request.responseText);
    

    다음을 사용하여 DI를 활용할 수 없습니다.Http클라이언트따라서 필요할 때 절대적으로 사용해야 합니다.

  • 답변 # 2

    서비스에서 약속(또는 관찰 가능)을 반환하고 구성 요소에서 이를 구독해야 합니다.

    이렇게 하지 않으면 구성 요소는 비동기 code 실행이 완료된 시점을 알 수 없으므로 해당 로그 문을 즉시 인쇄합니다.

    다음과 같이 서비스를 변경합니다.

    getData(){
        console.log("Started.. in service");
        return this.http.get('http://host/url').toPromise()
            .then(res=> this.extractData(res));
    }
    

    그런 다음 구성 요소에서

    submit(){
        this.dataService.getData().then(()=> {
            console.log('after executing service');
            this.router.navigate(['/view']);
        };
    };
    

    나는 이것에 대해 이야기하고있었습니다 .. Observable을 사용하여 동일한 작업을 수행 할 수 있습니다. OP가 Promise로 변환하는 이유는 확실하지 않습니다.

    Niladri2021-09-20 05:22:23

    user184994님 감사합니다. 위의 code를 수정한 후 오류가 발생했습니다. 오류: 잡히지 않음(약속 중): TypeError: 정의되지 않았습니다. 테스트에 사용하는 URL은 "jsonplaceholder.typicode.com/users"입니다. 테스트용으로만. 문제가 무엇인지 확실하지 않습니다.

    user122021-09-20 05:22:23

    @ user12 어느 줄에 /어떤 파일에? 그리고 어떤 방식으로 code를 수정했습니까?

    user1849942021-09-20 05:22:23

    @user184994, this.tokenGenerated=res를 할당할 때; 응답은 개체 목록입니다. 그게 문제야? 이 줄에 주석을 달면 제대로 작동합니다. 선언을 수정했습니다. tokenGenerated:any=[]; 그러나 여전히 같은 문제.

    user122021-09-20 05:22:23

    변경했습니다. 시도해 보세요. 맥락을 잃어버렸기 때문입니다. 굵은 화살표 구문(=>)을 사용하여 컨텍스트를 유지할 수 있습니다. 다른 대안은 .then(this.extractData.bind(this));를 작성하는 것입니다.

    user1849942021-09-20 05:22:23
  • 이전 amqsbcg가 MQ 클라이언트에서 메시지를 받지 못함
  • 다음 mysql : 다른 테이블의 열 합계에서 열 합계 빼기