onedrive检测文件变化

什么是增量查询

相比于百度网盘、阿里云盘,onedrive提供了接口用来获取两个时间点之间的文件状态变化[1],即:增量查询。

相应的接口形式为:路径/delta。举例如下:

  1. 查询应用目录delta:https://graph.microsoft.com/v1.0/me/drive/special/approot/delta
  2. 查询应用目录中文件夹A的delta:https://graph.microsoft.com/v1.0/me/drive/special/approot:/A:delta

通过两次delta查询,就能知道在这两次查询之间云盘发生了什么变化,这样通常可以更加高效地实现和云盘之间的内容同步。

增量查询中的关键数据和接口

如上所述,当我们向对应的delta地址发送GET请求就能获取delta信息。返回的内容如下:

{
    "@odata.context": "https://graph.microsoft.com/v1.0/$metadata#Collection(driveItem)",
    "@odata.deltaLink": "https://graph.microsoft.com/v1.0/me/drive/root/delta?$select=*%2csharepointIds&token=MzslMjM0OyUyMzE7MzsyM2YwNDVhMS1lNmRmLTQ1N2MtOGQ5NS1hNmViZDVmZWRhNWQ7NjM2NzExNzY2MzIxMDcwMDAwOzE5ODAzMzU5ODslMjM7JTIzOyUyMzQ",
    "value": [
        {
            "@odata.type": "#microsoft.graph.driveItem",
            "createdDateTime": "2017-07-27T02:41:36Z",
…
}

deltaLink

deltaLink是onedrive用于获取delta变化的地址,在首次获取delta后,onedrive会返回deltaLink。当再次从delteLink获取内容后,onedrive就会返回和上一次delta请求之间的变化项。

nextLink

在单次请求中,可能存在分页返回的情况,nextLink属性就用来指示下一个分页地址。通过不断访问nextLink,直到返回结果中没有nextLink属性,表示本次所有结果已经全部返回。

driveItem

onedrive的所有内容都以driveItem的形式返回,在增量查询中也不例外。

driveItem的形式如下:

{
  "audio": { "@odata.type": "microsoft.graph.audio" },
  "content": { "@odata.type": "Edm.Stream" },
  "cTag": "string (etag)",
  "deleted": { "@odata.type": "microsoft.graph.deleted"},
  "description": "string",
  "file": { "@odata.type": "microsoft.graph.file" },
  "fileSystemInfo": { "@odata.type": "microsoft.graph.fileSystemInfo" },
  "folder": { "@odata.type": "microsoft.graph.folder" },
  "image": { "@odata.type": "microsoft.graph.image" },
  "location": { "@odata.type": "microsoft.graph.geoCoordinates" },
  "malware": { "@odata.type": "microsoft.graph.malware" },
  "package": { "@odata.type": "microsoft.graph.package" },
  "photo": { "@odata.type": "microsoft.graph.photo" },
  "publication": {"@odata.type": "microsoft.graph.publicationFacet"},
  "remoteItem": { "@odata.type": "microsoft.graph.remoteItem" },
  "root": { "@odata.type": "microsoft.graph.root" },
  "searchResult": { "@odata.type": "microsoft.graph.searchResult" },
  "shared": { "@odata.type": "microsoft.graph.shared" },
  "sharepointIds": { "@odata.type": "microsoft.graph.sharepointIds" },
  "size": 1024,
  "specialFolder": { "@odata.type": "microsoft.graph.specialFolder" },
  "video": { "@odata.type": "microsoft.graph.video" },
  "webDavUrl": "string",

  /* relationships */
  "activities": [{"@odata.type": "microsoft.graph.itemActivity"}],
  "children": [{ "@odata.type": "microsoft.graph.driveItem" }],
  "permissions": [ {"@odata.type": "microsoft.graph.permission"} ],
  "thumbnails": [ {"@odata.type": "microsoft.graph.thumbnailSet"}],
  "versions": [ {"@odata.type": "microsoft.graph.driveItemVersion"}],

  /* inherited from baseItem */
  "id": "string (identifier)",
  "createdBy": {"@odata.type": "microsoft.graph.identitySet"},
  "createdDateTime": "String (timestamp)",
  "eTag": "string",
  "lastModifiedBy": {"@odata.type": "microsoft.graph.identitySet"},
  "lastModifiedDateTime": "String (timestamp)",
  "name": "string",
  "parentReference": {"@odata.type": "microsoft.graph.itemReference"},
  "webUrl": "string",

  /* instance annotations */
  "@microsoft.graph.conflictBehavior": "string",
  "@microsoft.graph.downloadUrl": "url",
  "@microsoft.graph.sourceUrl": "url"
}

针对增量查询,其实是created, updated, or deleted三种事件,对应的属性是:

  1. deleted属性,表示内容项(文件或者文件夹)已经被删除。
  2. file属性,如果文件有更改,则会携带此属性。
  3. folder属性,文件夹有更改。

增量查询的过程

第一种:轮询获取

GET deltaLink -> 解析delta.value数组,基于deleted、file和folder三个属性即能知道具体的内容改动。

第二种:订阅webhook通知

当需要快速地获取云盘内容变化的时候,就需要通过webhook完成。更多资料可以参考 官网:配置webhook接收变化通知

[1] 大规模发现文件和检测更改的最佳做法