1、启用HTTP服务
HttpClient是Angular通过HTTP与远程服务器通讯的机制
要让HttpClient在应用中随处可见,请
①打开根模块APPModule
②从@angular/common/http中导入HTTPClientModule符合
import { HttpClientModule } from '@angular/common/http';
③把它加入@NgModule.imports数组
2、模拟数据服务器
①使用内存 Web API(In-memory Web API)模拟出的远程数据服务器通讯
可从npm安装: npm install angular-in-memory-web-api --save
②在app.module.ts中导入HttpClientInMemoryWebApiModule 和 InMemoryDataService 类
③把 HttpClientInMemoryWebApiModule 添加到 @NgModule.imports 数组中(放在 HttpClientModule 之后), 然后使用 InMemoryDataService 来配置它。
forRoot()配置方法接受一个InMemoryDataService类(初期的内存数据库)作为参数
3、英雄与HTTP
在hero.service.ts中导入HttpClient , 将httpClient注入到构造函数中一个名叫http的私有属性中 , 通过http.get()获取数据
5、HTTP方法返回单个值
所有的HTTPClient方法都会返回某个值的RXJS Observable
HTTP是一个请求/响应式协议,你发起请求,它返回单个的响应
通常,Observable可以在一段时间内返回多个值。但来自HttpClient的Observable总是发出一个值,然后结束,再也不会发出其他值,具体到这次的HttpClient.get调用,他返回一个Observable<Her0[]>,一个英雄数组的可观察对象
6、HTTP返回响应数据
HTTPClient.get默认情况下把响应体当做无类型的JSON对象返回。如果指定了可选的模板类型<Hero[]> ,就会给你返回一个类型化的对象
JSON数据的具体形态是由服务器的数据API决定的。可借助RxJS中map操作符对Observable的结果进行处理,以便得到自已想要的数据格式
7、错误处理
①导入catchError()
②使用.pipe方法来扩展Observable的结果,并给它一个catchError()操作符
catchError()操作符会拦截失败的Observable.它把错误对象传给错误处理器,错误处理器会处理这个错误
下面的handleError()会报告这个错误,并返回一个无害的结果,以便应用能正常工作
handleError
会在很多HeroService的方法之间共享,所以要把它通用化,以支持这些彼此不同的需求,它不再直接处理这些错误,而是给catchError返回一个错误处理函数,还要用操作名和出错时要返回的安全值来对这个错误处理函数进行配置
在控制台中汇报这个错误之后,这个处理器会汇报一个用户友好的消息error.message,并给应用返回一个安全值[],让它继续工作
因为每个服务方法都会返回不同类型的Observable结果,所以handleError也需要这样一样类型参数,以便返回一个此类型的安全值
8、使用RxJS中的tap操作符,查看Observable的值,使用那些值做一些使其,并且把他们传出来,这种tap回调不会改变这些值本身
9、通过id获取英雄
10、修改英雄
http.put()需要三个参数:URL地址,需要修改的数据,选项
11、添加英雄
在service添加addHero方法
post方法会为指定的英雄创建一个id,然后把它通过Observable<Hero>返回给调用者
在heroes.component.ts中调用此方法
12、删除某个英雄
http.delete方法只需要url以及httpOptions参数
13、根据名字搜索
如果没有搜索词,则方法返回一个空数组
创建search component , 画search元素
heroes$ : $是一个命名惯例,表明此变量是一个Observable,而不是数组
*ngFor不能直接使用Observable,所以需要 async 自动订阅到Observable
下面是search.component.ts
Subject 既是可观察对象的数据源,本身也是Observable , 也可以通过调用它的next(value)方法往Observable中推送一些值
在传出最终搜索字符前,debounceTime(300)将会等待,直到新增字符串的事件暂停了300ms,你实际发起请求的间隔永远不会小于300ms
distinctUnitilChanged() 会确保只在过滤条件发生变化时才发送请求
switchMap()会为每个从debounce和distinctUntilChanged中通过的搜索词调用搜索服务。它会取消并丢弃以前的搜索可观察对象,只保留最近的
search()是通过对文本框的keystroke事件的事件绑定来调用的
// Tips
1、字面量 --在编程语言中,一般固定值称为字面量
2、模板字面量(Template Literal)是一种能够嵌入表达式的格式化字符串,有别于普通字符串,它使用(`) 包裹的字符,而不是双引号或者单引号。模板字面量包含特定形式 的占位符(${expression}),由美元符合、大括号以及合法的表达式组成。合法的表达式(expression)可以是变量,算术,或函数调用,甚至还可以是模板字面量
3、JavaScript,ES5, Es6的区别 ?
javaScript是一种动态类型,弱类型,基于原型的客户端脚本语言,用来给HTML网页增加动态功能
动态:在运行时确定数据类型,变量使用前不需要类型声明,通常变量的类型是被赋值的那个值的类型
弱类:计算时可以不同类型之间对使用者透明地隐式转换,即使类型不正确,也能通过隐式转换来得到争取的类型
原型:是为了方便实现属性的继承
新对象继承对象(作为模板),将自身的属性共享给新对象,模板对象成为原型,这样新对象实例化后,不但可以享有自已创建时和运行时定义的属性,而且可以享有原型对象的属性
①所有的对象都有"[[prototype]]"属性(通过__proto__访问),该属性对应对象的原型
②所有的函数对象都有“prototype”属性,该属性的值会被赋值给该函数创建的对象的"__proto_"属性
③所有的原型对象都有“constructor”属性,该属性对应创建所有指向该原型的实例的构造函数
④函数对象和原型对象 通过“property”和“constructor属性进行相互关联
JavaScript由三部分组成:
①ECMAScript (核心)--规定了语言的组成部分:语法,类型,语句,关键字,保留字,操作符,对象
②DOM(文档对象模型)
DOM把整个页面映射为一个多层节点的结果
③BOM (浏览器对象模型)
支持可以访问和操作浏览器窗口的浏览器对象模型
ES5是ECMAScript的第五个版本 2019年完成
Es6是ECMAScript的第六个版本,2015年完成,so ES6 => ES2015
ECMA(European Computer Manufacturers Association)欧洲计算机厂商协会
4、typeScript的函数返回值类型可以省略,ts会自动根据return的值进行判断类型