雄心啵啵 發表於 2020-1-26 16:32:00

Angular http

<p>&nbsp; &nbsp; &nbsp;前端应用都需要通过 HTTP 协议与后端服务器通讯,<code>@angular/common/http</code>&nbsp;中的&nbsp;<code>HttpClient</code>&nbsp;类为 Angular 应用程序提供的 API 来实现 HTTP 客户端功能。它基于浏览器提供的&nbsp;<code>XMLHttpRequest</code>&nbsp;接口。&nbsp;<code>HttpClient</code>&nbsp;带来的其它优点包括:可测试性、强类型的请求和响应对象、发起请求与接收响应时的拦截器支持,以及更好的、基于可观察(Observable)对象的 API 以及流式错误处理机制。</p>
<h3>1.使用http服务</h3>
<p>在根模块<code>AppModule</code>导入<span class="typ">HttpClientModule。因为大多数应用中,多处多都要使用到http服务,所以直接导入到根模块去。</span><span class="pln"><br></span></p>
<div class="cnblogs_code">
<pre>import { NgModule }         <span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">@angular/core</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
import { BrowserModule }    </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">@angular/platform-browser</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
import { HttpClientModule } </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">@angular/common/http</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;

@NgModule({
imports: [
    BrowserModule,
    HttpClientModule,
],
declarations: [
    AppComponent,
],
bootstrap: [ AppComponent ]
})
export </span><span style="color: rgba(0, 0, 255, 1)">class</span> AppModule {}</pre>
</div>
<p>然后就可以在服务中使用http服务了</p>
<div class="cnblogs_code">
<pre>import { Injectable } <span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">@angular/core</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
import { HttpClient } </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">@angular/common/http</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;

@Injectable()
export </span><span style="color: rgba(0, 0, 255, 1)">class</span><span style="color: rgba(0, 0, 0, 1)"> UserService {
constructor(</span><span style="color: rgba(0, 0, 255, 1)">private</span><span style="color: rgba(0, 0, 0, 1)"> http: HttpClient) { }<br><br>getUsers():<span class="typ">Observable<span class="pun">&lt;Array<span class="pun">&lt;<span class="typ">userInfo<span class="pun">&gt;&gt;</span></span></span></span></span>{<br><span class="pln"> <span class="kwd">return<span class="pln"> <span class="kwd">this<span class="pun">.<span class="pln">http<span class="pun">.<span class="kwd">get<span class="pun">&lt;Array&lt;userInfo&gt;<span class="typ"><span class="pun">&gt;(url<span class="kwd"><span class="pun"><span class="pln"><span class="pun">);</span></span></span></span></span></span></span></span></span></span></span></span></span></span></span><br>}
}</span></pre>
</div>
<p><strong>2.封装httpService</strong></p>
<p><strong>&nbsp; &nbsp;</strong>通常一个应用我们不会直接使用HttpClient,数据的访问没有这么简单,我们可能会对header 有统一的添加,错误处理,数据处理,网络异常等情况处理。如果不封装一个服务那么我们直接使用HttpClient,会出现大量的重复,冗余杂乱的代码,无法统一标准化,在长期的开发以及测试中会变得麻烦和增加维护成本。这就是为什么在一个应用程序中,无论项目多小,我们都要把数据访问封装一个单独的服务中去的原因。</p>
<p>这个是HttpClient.post 方法,我们可以看到他的返回类型是某个值的 RxJS Observable。</p>
<p><img src="https://img2018.cnblogs.com/i-beta/833855/202001/833855-20200122134103942-971074461.png"></p>
<p>默认情况下把响应体当做无类型的 JSON 对象进行返回,如果指定了模版类型Array&lt;userInfo&gt;,他就会返回一个此类型的对象回来,但是具体还是得取决于数据接口返回来的数据。</p>
<p><span style="font-family: monospace">参考上面的UserService服务里的getUsers。下面是某个组件调用。</span></p>
<p>&nbsp;</p>
<div class="cnblogs_code">
<pre>users: Array&lt;User&gt;<span style="color: rgba(0, 0, 0, 1)">;

showUser() {
</span><span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.userService.getUsers()
    .subscribe((data:Array</span>&lt;User&gt;) =&gt; <span style="color: rgba(0, 0, 255, 1)">this</span>.users =<span style="color: rgba(0, 0, 0, 1)"> { ...data });
}</span></pre>
</div>
<p>&nbsp;</p>
<p><strong>返回数据结果统一处理</strong></p>
<p>通常我们API返回来的数据结构是统一的规范化结果,有利于项目前后端分离,团队合作开发。</p>
<div class="cnblogs_code">
<pre>export <span style="color: rgba(0, 0, 255, 1)">class</span> ResultData&lt;T&gt;<span style="color: rgba(0, 0, 0, 1)"> {</span><span style="color: rgba(0, 0, 0, 1)">
    success: boolean;
    msg</span>?: <span style="color: rgba(0, 0, 255, 1)">string</span><span style="color: rgba(0, 0, 0, 1)">;
    data</span>?<span style="color: rgba(0, 0, 0, 1)">: T;
    errorcode</span>?: <span style="color: rgba(0, 0, 255, 1)">string</span><span style="color: rgba(0, 0, 0, 1)">;
    timestamp</span>?<span style="color: rgba(0, 0, 0, 1)">: number;
}</span></pre>
</div>
<p>例子在下面👇</p>
<p><strong>错误处理</strong></p>
<p>&nbsp; &nbsp; &nbsp; 当你发起一个网络请求,你不知道服务器会给你返回什么,你不知道请求是否能到达服务器,会不会出现网络堵塞,服务器错误等等等的问题,这时候就需要要捕获错误,并对错误进行处理。使用 RxJS 的 catchError() 操作符来建立对 Observable 结果的处理管道(pipe)</p>
<div class="cnblogs_code">
<pre>//post 请求<br><span style="color: rgba(0, 0, 255, 1)">public</span> post(url: <span style="color: rgba(0, 0, 255, 1)">string</span>, data = {}): Observable&lt;any&gt;<span style="color: rgba(0, 0, 0, 1)"> {
    </span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.http.post(url, data, httpOptions).pipe(
      map(</span><span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.extractData),
      catchError(</span><span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.handleError)//获取了由 HttpClient 方法返回的 Observable,并把它们通过管道传给错误处理器
    );
}
<br>// 返回结果
</span><span style="color: rgba(0, 0, 255, 1)">private</span><span style="color: rgba(0, 0, 0, 1)"> extractData(res: Response) {
    </span><span style="color: rgba(0, 0, 255, 1)">return</span> res <span style="color: rgba(0, 0, 255, 1)">as</span> ResultData&lt;any&gt;<span style="color: rgba(0, 0, 0, 1)">;
}<br>
// 错误消息类
</span><span style="color: rgba(0, 0, 255, 1)">private</span><span style="color: rgba(0, 0, 0, 1)"> handleError(error: HttpErrorResponse) {
    </span><span style="color: rgba(0, 0, 255, 1)">if</span><span style="color: rgba(0, 0, 0, 1)"> (error.error instanceof ErrorEvent) {
      console.error(</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">An error occurred:</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">, error.error.message);
    } </span><span style="color: rgba(0, 0, 255, 1)">else</span><span style="color: rgba(0, 0, 0, 1)"> {
      console.error(
      `Backend returned code ${error.status}, ` </span>+<span style="color: rgba(0, 0, 0, 1)"> `body was: ${error.error}`
      );
    }
    </span><span style="color: rgba(0, 0, 255, 1)">return</span> throwError(<span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">Something bad happened; please try again later.</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">);
}</span></pre>
</div>
<p id="retry"><strong><code>retry()</code></strong></p>
<p>&nbsp; &nbsp; &nbsp; 有时候,错误只是临时性的,只要重试就可能会自动消失。RxJS 库提供了几个 retry 操作符,retry()可以对失败的 Observable 自动重新订阅几次。对 HttpClient 方法调用的结果进行重新订阅会导致重新发起 HTTP 请求。</p>
<div class="cnblogs_code">
<pre><span style="color: rgba(0, 0, 255, 1)">public</span> post(url: <span style="color: rgba(0, 0, 255, 1)">string</span>, data = {}): Observable&lt;any&gt;<span style="color: rgba(0, 0, 0, 1)"> {
    </span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.http.post(url, data, httpOptions).pipe(
      map(</span><span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.extractData),
      retry(</span><span style="color: rgba(128, 0, 128, 1)">3</span>),<span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">重试失败的请求,最多3次</span>
      catchError(<span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.handleError)
    );
}</span></pre>
</div>
<p><strong>添加请求头</strong></p>
<p>&nbsp; &nbsp; 在向API发起请求很多需要添加额外的请求头。 比如,它们可能需要一个 Content-Type 头来显式定义请求体的 MIME 类型。 也可能服务器会需要一个认证用的令牌(token)。</p>
<p>HeroesService 在 httpOptions 对象中就定义了一些这样的请求头,并把它传给每个 HttpClient 的保存型方法。</p>
<div class="cnblogs_code">
<pre>    <span style="color: rgba(0, 0, 255, 1)">public</span> getJsonHeader(header?<span style="color: rgba(0, 0, 0, 1)">: HttpHeaders): HttpHeaders {
      </span><span style="color: rgba(0, 0, 255, 1)">if</span> (header == <span style="color: rgba(0, 0, 255, 1)">null</span><span style="color: rgba(0, 0, 0, 1)">) {
            header </span>= <span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> HttpHeaders();
      }
      </span><span style="color: rgba(0, 0, 255, 1)">return</span> header.<span style="color: rgba(0, 0, 255, 1)">set</span>(<span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">Content-Type</span><span style="color: rgba(128, 0, 0, 1)">'</span>, <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">application/json</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">)<br>                     .set('Authorization', 'Bearer ' + this.token);
    }</span></pre>
</div>
<div class="cnblogs_code">
<pre>addUser (user: UserInfo): Observable&lt;boolean&gt;<span style="color: rgba(0, 0, 0, 1)"> {
</span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(0, 0, 255, 1)">this</span>.http.post&lt;boolean&gt;(url, user, <span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.getJsonHeader())
    .pipe(
      catchError(</span><span style="color: rgba(0, 0, 255, 1)">this</span>.handleError(<span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">addUser</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">, user))
    );
}</span></pre>
</div>
<p><strong>3.拦截请求</strong></p>
<p>&nbsp; &nbsp; &nbsp; http 拦截机制是&nbsp;<code>@angular/common/http</code>&nbsp;中的主要特性之一。&nbsp; 可以声明一些拦截器,用于监视和记录从应用发送到服务器的 HTTP 请求。 拦截器还可以用监视和转换从服务器返回到本应用的那些响应。实现拦截器,就要实现一个实现了&nbsp;<code>HttpInterceptor</code>&nbsp;接口中的&nbsp;<code>intercept()</code>&nbsp;方法的类。大多数拦截器拦截都会在传入时检查请求,然后把(可能被修改过的)请求转发给&nbsp;<code>next</code>&nbsp;对象的&nbsp;<code>handle()</code>&nbsp;方法,而&nbsp;<code>next</code>&nbsp;对象实现了&nbsp;<code>HttpHandler</code>&nbsp;接口。</p>
<div class="cnblogs_code">
<pre>import { HttpRequest, HttpHandler, HttpEvent } <span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">@angular/common/http</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
import { Observable } </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">rxjs</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;

export </span><span style="color: rgba(0, 0, 255, 1)">interface</span><span style="color: rgba(0, 0, 0, 1)"> HttpInterceptor {
intercept(req: HttpRequest</span>&lt;any&gt;, next: HttpHandler): Observable&lt;HttpEvent&lt;any&gt;&gt;<span style="color: rgba(0, 0, 0, 1)">;
}</span></pre>
</div>
<div class="cnblogs_code">
<pre>import { Injectable } <span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">@angular/core</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
import { HttpRequest, HttpHandler, HttpResponse } </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">@angular/common/http</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
import { finalize, tap } </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">rxjs/operators</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
import { HttpInterceptor } </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">./HttpInterceptor</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
import { LOGACTION } </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">../types/model</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
import { V5LogSQLService } </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">../v5logSql.service</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;

@Injectable()
export </span><span style="color: rgba(0, 0, 255, 1)">class</span><span style="color: rgba(0, 0, 0, 1)"> NoopInterceptor implements HttpInterceptor {

constructor(</span><span style="color: rgba(0, 0, 255, 1)">private</span><span style="color: rgba(0, 0, 0, 1)"> log: V5LogSQLService) { }
intercept(req: HttpRequest</span>&lt;any&gt;<span style="color: rgba(0, 0, 0, 1)">, next: HttpHandler) {
    </span><span style="color: rgba(0, 0, 255, 1)">const</span> startTime =<span style="color: rgba(0, 0, 0, 1)"> Date.now();
    let status: number;

    </span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> next.handle(req).pipe(
      tap(
      </span><span style="color: rgba(0, 0, 255, 1)">event</span> =&gt;<span style="color: rgba(0, 0, 0, 1)"> {
          </span><span style="color: rgba(0, 0, 255, 1)">if</span> (<span style="color: rgba(0, 0, 255, 1)">event</span><span style="color: rgba(0, 0, 0, 1)"> instanceof HttpResponse) {
            status </span>= <span style="color: rgba(0, 0, 255, 1)">event</span><span style="color: rgba(0, 0, 0, 1)">.status;
          }
      },
      error </span>=&gt; status =<span style="color: rgba(0, 0, 0, 1)"> error.status
      ),
      finalize(() </span>=&gt;<span style="color: rgba(0, 0, 0, 1)"> {
      </span><span style="color: rgba(0, 0, 255, 1)">this</span>.log.log(LOGACTION.HTTP, <span style="color: rgba(128, 0, 0, 1)">''</span> , JSON.stringify({ elapsedTime: (Date.now() - startTime) + <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">ms</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">, url: req.urlWithParams, status: status, param: req.body }));
      })
    );
}
}</span></pre>
</div>
<p>&nbsp; &nbsp; &nbsp; &nbsp;next 对象表示拦截器链表中的下一个拦截器。 这个链表中的最后一个 next 对象就是 HttpClient 的后端处理器(backend handler),它会把请求发给服务器,并接收服务器的响应。大多数的拦截器都会调用 next.handle(),以便这个请求流能走到下一个拦截器,并最终传给后端处理器。 拦截器也可以不调用 next.handle(),使这个链路短路,并返回一个带有人工构造出来的服务器响应的 自己的 Observable,这是一种常见的中间件模式。</p>
<p><strong>使用这个拦截器</strong><br>&nbsp; &nbsp; &nbsp; 这个 NoopInterceptor 就是一个由 Angular 依赖注入 (DI)系统管理的服务。 像其它服务一样,你也必须先提供这个拦截器类,应用才能使用它。</p>
<p>由于拦截器是 HttpClient 服务的(可选)依赖,所以你必须在提供 HttpClient 的同一个(或其各级父注入器)注入器中提供这些拦截器。 那些在 DI 创建完 HttpClient 之后再提供的拦截器将会被忽略。由于在 AppModule 中导入了 HttpClientModule,导致本应用在其根注入器中提供了 HttpClient。所以你也同样要在 AppModule 中提供这些拦截器。</p>
<p>注意&nbsp;<code>multi: true</code>&nbsp;选项。 这个必须的选项会告诉 Angular&nbsp;<code>HTTP_INTERCEPTORS</code>&nbsp;是一个多重提供商的令牌,表示它会注入一个多值的数组,而不是单一的值。</p>
<p>在从 @angular/common/http 中导入了 HTTP_INTERCEPTORS 注入令牌之后,编写如下的 NoopInterceptor 提供商注册语句:</p>
<p>AppModule根模块</p>
<div class="cnblogs_code">
<pre>{ provide: HTTP_INTERCEPTORS, useClass: NoopInterceptor, multi: <span style="color: rgba(0, 0, 255, 1)">true</span> },</pre>
</div>
<p>创建一个封装桶(barrel)文件,用于把所有拦截器都收集起来,一起提供给&nbsp;<code>httpInterceptorProviders</code>&nbsp;数组。</p>
<div class="cnblogs_code">
<pre>import { HTTP_INTERCEPTORS } <span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">@angular/common/http</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;

import { NoopInterceptor } </span><span style="color: rgba(0, 0, 255, 1)">from</span> <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">./noop-interceptor</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;

export </span><span style="color: rgba(0, 0, 255, 1)">const</span> httpInterceptorProviders =<span style="color: rgba(0, 0, 0, 1)"> [
{ provide: HTTP_INTERCEPTORS, useClass: NoopInterceptor, multi: </span><span style="color: rgba(0, 0, 255, 1)">true</span><span style="color: rgba(0, 0, 0, 1)"> },
];</span></pre>
</div>
<p>使用:</p>
<div class="cnblogs_code">
<pre><span style="color: rgba(0, 0, 0, 1)">providers: [
httpInterceptorProviders
],</span></pre>
</div>
<p>&nbsp; &nbsp; &nbsp; 拦截请求还有,拦截的顺序,以及httpEvent等。&nbsp;<code>HttpRequest</code>&nbsp;和&nbsp;<code>HttpResponse是只读的,只可对其监视 or 日志记录,要想修改该请求,就要先克隆它,并修改这个克隆体,然后再把这个克隆体传给&nbsp;<code>next.handle(),</code>你可以用一步操作中完成对请求的克隆和修改。具体看&nbsp;https://angular.cn/guide/http#intercepting-requests-and-responses,因为我对这个不熟现实开发中并未使用,仅仅使用拦截器记录监听请求记录日志而已</code><code>。&nbsp;</code></p>
<p>&nbsp; &nbsp; &nbsp;拦截器的使用场景有:设置默认请求头,记日志,缓存,返回多值可观察对象,监听进度事件等。</p>
<p><strong>4.其他</strong></p>
<p>1.前面提到过默认情况下把响应体当做无类型的 JSON 对象进行返回,如果请求返回来的是文件流等,就要另外做处理。</p>
<p>例如</p>
<div class="cnblogs_code">
<pre>getTextFile(filename: <span style="color: rgba(0, 0, 255, 1)">string</span><span style="color: rgba(0, 0, 0, 1)">) {
</span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(0, 0, 255, 1)">this</span>.http.<span style="color: rgba(0, 0, 255, 1)">get</span>(filename, {responseType: <span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">text</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">})
    .pipe(
      tap(
      data </span>=&gt; <span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.log(filename, data),
      error </span>=&gt; <span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.logError(filename, error)
      )
    );
}</span></pre>
</div>
<p>2.RxJS 是一个库,用于把异步调用和基于回调的代码组合成函数式(functional)的、响应式(reactive)的风格。 很多 Angular API,包括 HttpClient 都会生成和消费 RxJS 的 Observable。在整个httpService中我们用了RxJS库提供的几个操作符 catchError Observable retry 等,学习RxJS,有利于开发者在整个应用程序开发的开发,可以提高效率,以及代码质量。</p>
<p>&nbsp;</p>
<p>此随笔乃本人学习工作记录,如有疑问欢迎在下面评论,转载请标明出处。</p>
<p>如果对您有帮助请动动鼠标右下方给我来个赞,您的支持是我最大的动力。</p><br><br>
来源:https://www.cnblogs.com/huangenai/p/12218982.html
頁: [1]
查看完整版本: Angular http