鸿蒙NEXT开发实战往期必看文章:
一分钟了解”纯血版!鸿蒙HarmonyOS Next应用开发!
“非常具体的” 鸿蒙HarmonyOS Next应用开发学习路线!(从零基础入门到醒目)
HarmonyOS NEXT应用开发案例实践总结合(一连更新......)
HarmonyOS NEXT应用开发性能优化实践总结(一连更新......)
1. Request下载文件简介
在前述文章使用HttpRequest下载文件到本地示例中,使用基础的HttpRequest模块演示了怎样下载文件到本地,整个下载过程看起来似乎不太复杂,但是,如果考虑到可靠性、网络题目以及文件范例和大小的差异,开发难度还是相当大的,幸运的是,鸿蒙提供了专门用来进行上传下载的API,把这些复杂性都封装了起来,这就是本示例要使用的request部件。
2. request的常用方法
鸿蒙封装的request对象位于模块request中,使用如下的方式导入:
import request from '@ohos.request';
request模块包罗了众多的对象和利用方法,就本文而言,重点需要掌握的是downloadFile方法:
downloadFile(context: BaseContext, config: DownloadConfig): Promise<DownloadTask>
该方法实行异步下载,使用promise形式返回结果,结果为DownloadTask范例。可以通过DownloadTask范例的on('complete'|'pause'|'remove')订阅任务下载时的状态信息,包罗任务完成、停息或移除。通过on('fail')可获取任务下载时的错误信息。
3. request下载示例
本文要下载的服务端网站和使用HttpRequest下载文件到本地示例中的网站一样,也是需要登录后才可以下载,本示例运行后的界面如图所示:
应用启动后起首配置用户名密码以及登录地点,然后单击“登录”按钮进行登录,乐成登录后就可以单击“下载”按钮进行下载了,乐成下载后会体现生存位置和下载的文件内容。
下面具体先容创建该应用的步骤。
步骤1:创建Empty Ability项目。
步骤2:在module.json5配置文件加上对权限的声明:
- "requestPermissions": [
- {
- "name": "ohos.permission.INTERNET"
- }
- ]
复制代码 这里添加了访问互联网的权限。
步骤3:在Index.ets文件里添加如下的代码:
- import http from '@ohos.net.http';
- import util from '@ohos.util';
- import fs from '@ohos.file.fs';
- import request from '@ohos.request';
- import picker from '@ohos.file.picker';
- @Entry
- @Component
- struct Index {
- //连接、通讯历史记录
- @State msgHistory: string = ''
- //首页地址
- @State downloadUrl: string = "http://192.168.100.101:8081/download?filename=demo.txt"
- //登录地址
- @State loginUrl: string = "http://192.168.100.101:8081/auth"
- //用户名
- @State loginName: string = "zhanglei"
- //密码
- @State passwd: string = "cangjie"
- //下载到本地的路径
- @State localFilePath: string = ""
- scroller: Scroller = new Scroller()
- sessionId: string = ""
- build() {
- Row() {
- Column() {
- Text("Request下载示例")
- .fontSize(14)
- .fontWeight(FontWeight.Bold)
- .width('100%')
- .textAlign(TextAlign.Center)
- .padding(10)
- Flex({ justifyContent: FlexAlign.Start, alignItems: ItemAlign.Center }) {
- Text("用户名:")
- .fontSize(14)
- .width(80)
- .flexGrow(0)
- TextInput({ text: this.loginName })
- .onChange((value) => {
- this.loginName = value
- })
- .width(110)
- .fontSize(11)
- .flexGrow(1)
- Text("密码:")
- .fontSize(14)
- .width(60)
- .flexGrow(0)
- TextInput({ text: this.passwd })
- .onChange((value) => {
- this.passwd = value
- })
- .type(InputType.Password)
- .width(100)
- .fontSize(11)
- .flexGrow(1)
- }
- .width('100%')
- .padding(10)
- Flex({ justifyContent: FlexAlign.Start, alignItems: ItemAlign.Center }) {
- Text("登录地址:")
- .fontSize(14)
- .width(80)
- .flexGrow(0)
- TextInput({ text: this.loginUrl })
- .onChange((value) => {
- this.loginUrl = value
- })
- .width(100)
- .fontSize(11)
- .flexGrow(1)
- Button("登录")
- .onClick(() => {
- this.login()
- })
- .width(70)
- .fontSize(14)
- .flexGrow(0)
- }
- .width('100%')
- .padding(10)
- Flex({ justifyContent: FlexAlign.Start, alignItems: ItemAlign.Center }) {
- Text("文件地址:")
- .fontSize(14)
- .width(80)
- .flexGrow(0)
- TextInput({ text: this.downloadUrl })
- .onChange((value) => {
- this.downloadUrl = value
- })
- .width(110)
- .fontSize(11)
- .flexGrow(1)
- Button("下载")
- .onClick(() => {
- this.downloadFile()
- })
- .width(70)
- .fontSize(14)
- .flexGrow(0)
- }
- .width('100%')
- .padding(10)
- Flex({ justifyContent: FlexAlign.Start, alignItems: ItemAlign.Center }) {
- Text("保存位置:")
- .fontSize(14)
- .width(80)
- .flexGrow(0)
- TextInput({ text: this.localFilePath })
- .width(110)
- .fontSize(11)
- .flexGrow(1)
- }
- .width('100%')
- .padding(10)
- Scroll(this.scroller) {
- Text(this.msgHistory)
- .textAlign(TextAlign.Start)
- .padding(10)
- .width('100%')
- .backgroundColor(0xeeeeee)
- }
- .align(Alignment.Top)
- .backgroundColor(0xeeeeee)
- .height(300)
- .flexGrow(1)
- .scrollable(ScrollDirection.Vertical)
- .scrollBar(BarState.On)
- .scrollBarWidth(20)
- }
- .width('100%')
- .justifyContent(FlexAlign.Start)
- .height('100%')
- }
- .height('100%')
- }
- //下载文件
- downloadFile() {
- this.localFilePath = getContext(this).tempDir + "/demo.txt"
- //文件如果已经存在,就删除
- if (fs.accessSync(this.localFilePath)) {
- fs.unlink(this.localFilePath)
- }
- let cfg: request.DownloadConfig = {
- url: this.downloadUrl,
- header: {
- 'Accept-Encoding': 'gzip, deflate, br',
- 'Accept-Language': 'zh-CN,zh;q=0.9',
- //这一步很关键,把登录成功后的cookie传递过去
- 'Cookie': 'sessionid=' + this.sessionId,
- 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36',
- },
- filePath: this.localFilePath }
- let downloadTask: request.DownloadTask;
- try {
- request.downloadFile(getContext(this), cfg
- , (err, data) => {
- if (err) {
- console.error('Failed to request the download. Cause: ' + JSON.stringify(err));
- return;
- }
- downloadTask = data;
- downloadTask.on("progress", (size, tot) => {
- this.msgHistory += `下载进度:${size}/${tot}\r\n`
- })
- downloadTask.on("complete", () => {
- this.msgHistory += "下载完成\r\n"
- //读取文件内容并显示
- this.showFileContent(this.localFilePath)
- })
- });
- } catch (err) {
- this.msgHistory += 'err.code : ' + err.code + ', err.message : ' + err.message;
- }
- }
- //显示指定文件的内容
- showFileContent(filePath: string) {
- let content = fs.readTextSync(filePath)
- this.msgHistory += "文件内容:" + content + "\r\n"
- }
- //模拟登录
- login() {
- //http请求对象
- let httpRequest = http.createHttp();
- //请求的登录名和密码参数
- let params = "username=" + this.loginName + "&password=" + this.passwd
- let opt: http.HttpRequestOptions = {
- method: http.RequestMethod.POST,
- extraData: params,
- header: { 'Content-Type': 'application/x-www-form-urlencoded' },
- expectDataType: http.HttpDataType.STRING
- }
- httpRequest.request(this.loginUrl, opt)
- .then((resp) => {
- this.msgHistory += "响应码:" + resp.responseCode + "\r\n"
- //返回的首部信息中,cookie的格式为:
- // set-cookie: sessionid=19837d50s270ms999us100ns; Max-Age=1800; Path=/
- //这里需要记录下sessionid,作为下次提交时的cookie信息
- let cookies: string = resp.header["set-cookie"]
- this.sessionId = cookies.split(";")[0].split("=")[1]
- this.msgHistory += "sessionId:" + this.sessionId + "\r\n"
- this.msgHistory += "登录成功\r\n"
- })
- .catch((e) => {
- this.msgHistory += "登录失败:" + e.message + "\r\n"
- })
- }
- }
复制代码 步骤4:编译运行,可以使用模拟器大概真机。
步骤5:配置网站首页地点和登录地点,然后单击“登录”按钮,就可以模拟登录了,登录后的页面如图所示:

步骤6:单击“下载”按钮,应用会下载文件并生存到本地,然后从本地读取文件的内容(假设文件是文本范例的),如图所示:

可以看到,文件乐成生存到了本地并读取到了文件的内容。
3. 下载功能分析
要实现下载功能,关键点和使用httpRequest一样,也是要获取sessionId,而且在发起下载任务的DownloadConfig配置里通过header附加上sessionid,代码如下:
- let cfg: request.DownloadConfig = {
- url: this.downloadUrl,
- header: {
- 'Accept-Encoding': 'gzip, deflate, br',
- 'Accept-Language': 'zh-CN,zh;q=0.9',
- //这一步很关键,把登录成功后的cookie传递过去
- 'Cookie': 'sessionid=' + this.sessionId,
- 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36',
- },
- filePath: this.localFilePath }
复制代码 另外要注意的一点是,如果文件下载过一次,再次下载时会提示本地文件已经存在,如许就会下载失败,解决方法是在下载前判断文件是否存在,如果存在就先删除,代码如下:
- this.localFilePath = getContext(this).tempDir + "/demo.txt"
- //文件如果已经存在,就删除
- if (fs.accessSync(this.localFilePath)) {
- fs.unlink(this.localFilePath)
- }
复制代码
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。 |