.Net6/C# 百度网盘下载实例
前置要求:有百度账号,实名认证以及开发者认证,创建应用并获取到关键凭证:Appid、Appkey、Secretkeyk和Signkey
平台上入门十分清楚,直接对着逐步操作即可,个人开发者审核也很快
百度网盘开放平台地址如下:https://pan.baidu.com/union/doc/nksg0sbfs
因为平台代码例子竟然没有C# ,这里主要是放授权以及下载部分代码实例
第一步:获取AuthorizeCode
string authorizeURL = @"http://openapi.baidu.com/oauth/2.0/authorize?response_type=code&client_id=你的AppKey&redirect_uri=oob&scope=basic,netdisk&device_id=你的AppID";
其中那个redirect_uri=oob的oob是一个默认返回l,如果有确切的返回链接可以写进去,如果没有就用oob
这里APIDemo类型的例子,直接把上面的代码粘进浏览器,会出一个固定的百度授权页面,授权一次既可,授权后就能拿到授权码,后续只要这个连接,就直接是授权码页面,具体如下:
第二步:通过授权码AuthorizeCode获取真正后续使用的AccessToken凭证
using (HttpClient client = new HttpClient()) { //换取AccessToken凭证 string tokenURL = @"https://openapi.baidu.com/oauth/2.0/token?grant_type=authorization_code&code=上一个步骤拿到的授权码&client_id=你的AppKey&client_secret=你的SecretKey&redirect_uri=oob"; HttpResponseMessage result = client.GetAsync(tokenURL).Result; string responseResult = result.Content.ReadAsStringAsync().Result;
client.Dispose();
}
其中responseResult即为带有access_token(接收令牌)的Json字符串,
还有两个重要的返回数据refresh_token(刷新令牌)以及expires_in(Access Token有效期(秒))
换算一下具体数据 ,access_token为12小时有效期,refresh_token有效期返回数据里没有,但从官网可知为10年
当天后续测试既可一直使用该access_token,
如果第二天开发再使用,用refresh_token通过刷新方法获取一下新的access_token以及refresh_token既可
刷新AccessToken的方法如下:
using (HttpClient client = new HttpClient()) { //刷新AccessToken凭证 string refreshURL = @"https://openapi.baidu.com/oauth/2.0/token?grant_type=refresh_token&refresh_token=你的刷新令牌&client_id=你的AppKey&client_secret=你的SecretKey"; HttpResponseMessage result = client.GetAsync(tokenURL).Result; string responseResult = result.Content.ReadAsStringAsync().Result;
client.Dispose(); }
responseResult即为带有新access_token的Json字符串
第三步:已有access_token,获取文件列表
using (HttpClient client = new HttpClient()) { string filelistURL = @"http://pan.baidu.com/rest/2.0/xpan/multimedia?method=listall&path=/BaiduCloudDiskDemo&access_token=你的接收令牌&web=1&recursion=1&start=0&limit=5"; HttpResponseMessage result = client.GetAsync(filelistURL).Result; string responseResult = result.Content.ReadAsStringAsync().Result; FileList fileList = JsonConvert.DeserializeObject<FileList>(responseResult); client.Dispose(); }
FileList是根据返回的JSon字符串里的具体数据自定义实体类
filelist即为总的文件信息列表
web为是否返回缩略图地址,1为返回,0为不返回
recursion为是否递归,1为递归,0为不递归
start为查询起点,默认为0
limit为查询数量,默认为1000
补充FileList实体类的具体代码方便复制,正式项目中建议换个名字,Demo里是我随便起的:
public class FileList { public int cursor { get; set; } public string errmsg { get; set; } public int errno { get; set; } public int has_more { get; set; } public List<ListItem> list { get; set; } public string request_id { get; set; } } public class ListItem { public int category { get; set; } public Int64 fs_id { get; set; } public int isdir { get; set; } public int local_ctime { get; set; } public int local_mtime { get; set; } public string md5 { get; set; } public string path { get; set; } public int server_ctime { get; set; } public string server_filename { get; set; } public int server_mtime { get; set; } public int size { get; set; } public Thumbs thumbs { get; set; } } public class Thumbs { public string icon { get; set; } public string url1 { get; set; } public string url2 { get; set; } public string url3 { get; set; } public string url4 { get; set; } }
第四步:文件列表成功,获取带有下载地址DLink的具体文件信息
using (HttpClient client = new HttpClient()) { //文件列表的fs_id组成的数组,再进行后续操作 string arr = ""; foreach (ListItem item in filelist.list) { arr = arr + item.fs_id.ToString() + ","; } arr = arr.TrimEnd(',');
string filedlinkURL = @"http://pan.baidu.com/rest/2.0/xpan/multimedia?method=filemetas&access_token=你的接收令牌&fsids=[" + arr + "]&thumb=1&dlink=1&extra=1"; HttpResponseMessage result = client.GetAsync(filedlinkURL).Result; string responseResult = result.Content.ReadAsStringAsync().Result; FileList_DLink fileList_dlink = JsonConvert.DeserializeObject<FileList_DLink>(responseResult); client.Dispose(); }
FileList_DLink是根据返回的JSon字符串里的具体数据自定义实体类
filelist_dlink为带有下载地址的文件信息
thumb为是否需要缩略图地址 0为否,1为是,默认为0
dlink为是否需要下载地址,0为否,1为是,默认为0
extra为是否需要拍摄时间、原图分辨率等其他信息,0 否、1 是,默认0
补充FileList_DLink实体类的具体代码方便复制,正式项目中类名最好改了,Demo是我随便起的:
public class FileList_DLink { public string errmsg { get; set; } public int errno { get; set; } public List<ListItem_Dlink> list { get; set; } public ShareItem names { get; set; } public string request_id { get; set; } } public class ListItem_Dlink { public int category { get; set; } public int date_taken { get; set; } public string dlink { get; set; } public string filename { get; set; } public Int64 fs_id { get; set; } public int height { get; set; } public int isdir { get; set; } public string md5 { get; set; } public int oper_id { get; set; } public string path { get; set; } public int server_ctime { get; set; } public int server_mtime { get; set; } public int size { get; set; } public Thumbs_Dlink thumbs { get; set; } public int width { get; set; } } public class Thumbs_Dlink { public string icon { get; set; } public string url1 { get; set; } public string url2 { get; set; } public string url3 { get; set; } public string url4 { get; set; } } public class ShareItem { public string account { get; set; } }
第五步,具体文件信息下载成功,通过dlink下载地址下载文件到本地
HttpClientHandler hander = new HttpClientHandler(); hander.AllowAutoRedirect = true; using (HttpClient client = new HttpClient(hander)) { if (filelist_dlink != null)//获取文件下载地址列表成功 下载文件 { foreach (ListItem_Dlink item in filelist_dlink.list) { string filedownloadURL = @"" + item.dlink + "&access_token=你的接收令牌"; HttpResponseMessage result = client.GetAsync(filedownloadURL).Result; if (result.StatusCode == HttpStatusCode.OK) { string responseResult = result.Content.ReadAsStringAsync().Result; } else if (result.StatusCode == HttpStatusCode.Redirect) { string AbsoluteUri = result.Headers.Location.AbsoluteUri; result = client.GetAsync(AbsoluteUri).Result; byte[] urlContents = client.GetByteArrayAsync(AbsoluteUri).Result; string path = Environment.CurrentDirectory + "\\DownloadImg\\"; if (!Directory.Exists(path)) { Directory.CreateDirectory(path); } path = path + item.filename; using (FileStream fs = new FileStream(path, FileMode.Create, FileAccess.Write)) { fs.Write(urlContents, 0, urlContents.Length); } } } }
}
这里面做了一个重定向判断,
当时测试的时候一直返回302,后面是在判断为重定向的情况下将图片下载到本地的,可根据实际情况自行调整
以上,整个下载流程结束。