現在、共有OneDriveフォルダーからのファイルの一覧表示、アップロード、ダウンロードを含むいくつかのタスクを実装しようとしています。このフォルダーは、ログインしているユーザーのOneDriveからアクセスできます(ルートフォルダーに表示されます)。リストの部分は、次のコードを使用して、これまでかなりうまくいきます。
string remoteDriveId = string.Empty;
private GraphServiceClient graphClient { get; set; }
// Get the root of the owners OneDrive
DriveItem ownerRoot = await this.graphClient.Drive.Root.Request().Expand("thumbnails,children($expand=thumbnails)").GetAsync();
// Select the shared folders general information
DriveItem sharedFolder = ownerRoot.Children.Where(c => c.Name == "sharedFolder").FirstOrDefault();
// Check if it is a remote folder
if(sharedFolder.Remote != null)
{
remoteDriveId = item.RemoteItem.ParentReference.DriveId;
// Get complete Information of the shared folder
sharedFolder = await graphClient.Drives[remoteDriveId].Items[sharedFolder.RemoteItem.Id].Request().Expand("thumbnails,children").GetAsync();
}
したがって、他のOneDriveと共有しているOneDriveから共有フォルダー情報を取得する必要があるのは明らかです。次の部分は、この共有フォルダの内容を一覧表示することです。これも、次のように非常によく機能します。
foreach (DriveItem child in sharedFolder.Children)
{
DriveItem childItem = await graphClient.Drives[remoteDriveId].Items[child.Id].Request().Expand("thumbnails,children").GetAsync();
if(childItem.Folder == null)
{
string path = Path.GetTempPath() + Guid.NewGuid();
// Download child item to path
}
}
私の問題は、「子アイテムをパスにダウンロード」の部分から始まります。そこでは一時ファイルのフォルダではない、すべてをダウンロードしたいと思います。問題は、OneDriveが常に私の要求にエラーメッセージで応答し、ファイルが見つからなかったことです。これまでに試したことは次のとおりです。
using (var stream = await graphClient.Drives[remoteDriveId].Items[childItem.Id].Content.Request().GetAsync())
using (var outputStream = new System.IO.FileStream(path, System.IO.FileMode.Create))
{
await stream.CopyToAsync(outputStream);
}
別のバリアントでは、childItem ParentReferenceのIDを使用しようとしました(ただし、これは、私をsharedFolderのリモートOneDrives IDに導くだけだと思います)。
using (var stream = await graphClient.Drives[remoteDriveId].Items[childItem.ParentReference.Id].Content.Request().GetAsync())
using (var outputStream = new System.IO.FileStream(path, System.IO.FileMode.Create))
{
await stream.CopyToAsync(outputStream);
}
ファイルをダウンロードした後、それらを編集して共有フォルダーの別のパスに再アップロードします。そのパスは次のように私が作成しました(すでに機能しています)。
DriveItem folderToCreate = new DriveItem { Name = "folderName", Folder = new Folder() };
await graphClient.Drives[remoteDriveId].Items[sharedFolder.Id].Children.Request().AddAsync(folderToCreate);
その後、アップロードは失敗します。私はこのようにそれを試しました:
using (var stream = new System.IO.FileStream(@"C:\temp\testfile.txt", System.IO.FileMode.Open))
{
await graphClient.Drives[remoteDriveId].Items[sharedFolder.Id].Content.Request().PutAsync<DriveItem>(stream);
}
そして、これも同様です(共有フォルダーではないため、Drive
ではなくDrives
を使用する場合に機能します)。
using (var stream = new System.IO.FileStream(@"C:\temp\testfile.txt", System.IO.FileMode.Open))
{
string folderPath = sharedFolder.ParentReference == null ? "" : sharedFolder.ParentReference.Path.Remove(0, 12) + "/" + Uri.EscapeUriString(sharedFolder.Name);
var uploadPath = folderPath + "/" + uploadFileName;
await graphClient.Drives[remoteDriveId].Root.ItemWithPath(uploadPath).Content.Request().PutAsync<DriveItem>(stream);
}
AddAsync
からDriveItem
を作成する方法がわからないため、(フォルダーの作成のように)Stream
メソッドを機能させることができませんでした。
誰かが私を正しい方向に向けることができれば、私はそれを高く評価します!ありがとうございました!
リクエスト:
graphClient.Drives[remoteDriveId].Items[childItem.ParentReference.Id].Content.Request().GetAsync()
DriveItemのコンテンツをダウンロード エンドポイントに対応し、childItem.ParentReference.Id
が---を参照する場合、のみが有効です File
resource 、別のケースでは、予期された例外で失敗します:
Microsoft.Graph.ServiceException:コード:itemNotFoundメッセージ:フォルダーのコンテンツを取得できません
したがって、フォルダからコンテンツをダウンロードするには、解決策は次のようになります:
GET /drives/{drive-id}/items/{folderItem-id}/children
driveItem
がFile
ファセットに対応する場合、すべてのアイテムごとに明示的にコンテンツをダウンロードします:GET /drives/{drive-id}/items/{fileItem-id}/content
例
var sharedItem = await graphClient.Drives[driveId].Items[folderItemId].Request().Expand(i => i.Children).GetAsync();
foreach (var item in sharedItem.Children)
{
if (item.File != null)
{
var fileContent = await graphClient.Drives[item.ParentReference.DriveId].Items[item.Id].Content.Request()
.GetAsync();
using (var fileStream = new FileStream(item.Name, FileMode.Create, System.IO.FileAccess.Write))
fileContent.CopyTo(fileStream);
}
}
例2
この例は、sourceフォルダーからファイルをダウンロードし、targetフォルダーにアップロードする方法を示しています。
var sourceDriveId = "--source drive id goes here--";
var sourceItemFolderId = "--source folder id goes here--";
var targetDriveId = "--target drive id goes here--";
var targetItemFolderId = "--target folder id goes here--";
var sourceFolder = await graphClient.Drives[sourceDriveId].Items[sourceItemFolderId].Request().Expand(i => i.Children).GetAsync();
foreach (var item in sourceFolder.Children)
{
if (item.File != null)
{
//1. download a file as a stream
var fileContent = await graphClient.Drives[item.ParentReference.DriveId].Items[item.Id].Content.Request()
.GetAsync();
//save it into file
//using (var fileStream = new FileStream(item.Name, FileMode.Create, System.IO.FileAccess.Write))
// fileContent.CopyTo(fileStream);
//2.Upload file into target folder
await graphClient.Drives[targetDriveId]
.Items[targetItemFolderId]
.ItemWithPath(item.Name)
.Content
.Request()
.PutAsync<DriveItem>(fileContent);
}
}
ファイルのコンテンツをダウンロード/アップロードする代わりに、実際にはDriveItem
copy
または move
操作だと思います。 1つの(source
)フォルダーから別の(target
)にコピーする必要があるファイルがあるとしましょう。次の例はその方法を示しています。それを達成するために:
var sourceDriveId = "--source drive id goes here--";
var sourceItemFolderId = "--source folder id goes here--";
var targetDriveId = "--target drive id goes here--";
var targetItemFolderId = "--target folder id goes here--";
var sourceFolder = await graphClient.Drives[sourceDriveId].Items[sourceItemFolderId].Request().Expand(i => i.Children).GetAsync();
foreach (var item in sourceFolder.Children)
{
if (item.File != null)
{
var parentReference = new ItemReference
{
DriveId = targetDriveId,
Id = targetItemFolderId
};
await graphClient.Drives[sourceDriveId].Items[item.Id]
.Copy(item.Name, parentReference)
.Request()
.PostAsync();
}
}
}