IEnumerator GetImages() { foreach (var result in results) { GoogleDriveFiles.DownloadTextureRequest request; request = GoogleDriveFiles.DownloadTexture(result.Key); request.Send().OnDone += ImageRequested; yield return(requestFilled); } }
private void ListFiles(string nextPageToken = null) { request = GoogleDriveFiles.List(); request.Fields = new List <string> { "nextPageToken, files(id, name, size, createdTime)" }; request.PageSize = ResultsPerPage; //if (!string.IsNullOrEmpty(query)) // request.Q = string.Format("name contains '{0}'", query); request.Q = string.Format("name contains '{0}' or name contains '{1}' or name contains '{2}'", ".png", ".jpg", ".jpeg"); if (!string.IsNullOrEmpty(nextPageToken)) { request.PageToken = nextPageToken; } request.Send().OnDone += BuildResults; }
private IEnumerator GetFileByPathRoutine(string filePath) { // A folder in Google Drive is actually a file with the MIME type 'application/vnd.google-apps.folder'. // Hierarchy relationship is implemented via File's 'Parents' property. To get the actual file using it's path // we have to find ID of the file's parent folder, and for this we need IDs of all the folders in the chain. // Thus, we need to traverse the entire hierarchy chain using List requests. // More info about the Google Drive folders: https://developers.google.com/drive/v3/web/folder. var fileName = filePath.Contains("/") ? filePath.GetAfter("/") : filePath; var parentNames = filePath.Contains("/") ? filePath.GetBeforeLast("/").Split('/') : null; // Resolving folder IDs one by one to find ID of the file's parent folder. var parendId = "root"; // 'root' is alias ID for the root folder in Google Drive. if (parentNames != null) { for (int i = 0; i < parentNames.Length; i++) { request = new GoogleDriveFiles.ListRequest(); request.Fields = new List <string> { "files(id)" }; request.Q = string.Format("'{0}' in parents and name = '{1}' and mimeType = 'application/vnd.google-apps.folder' and trashed = false", parendId, parentNames[i]); yield return(request.Send()); if (request.IsError || request.ResponseData.Files == null || request.ResponseData.Files.Count == 0) { result = string.Format("Failed to retrieve '{0}' part of '{1}' file path.", parentNames[i], filePath); yield break; } if (request.ResponseData.Files.Count > 1) { Debug.LogWarning(string.Format("Multiple '{0}' folders been found.", parentNames[i])); } parendId = request.ResponseData.Files[0].Id; } } // Searching the file. request = new GoogleDriveFiles.ListRequest(); request.Fields = new List <string> { "files(id, size, modifiedTime)" }; request.Q = string.Format("'{0}' in parents and name = '{1}'", parendId, fileName); yield return(request.Send()); if (request.IsError || request.ResponseData.Files == null || request.ResponseData.Files.Count == 0) { result = string.Format("Failed to retrieve '{0}' file.", filePath); yield break; } if (request.ResponseData.Files.Count > 1) { Debug.LogWarning(string.Format("Multiple '{0}' files been found.", filePath)); } var file = request.ResponseData.Files[0]; result = string.Format("ID: {0} Size: {1:0.00}MB Modified: {2:dd.MM.yyyy HH:MM:ss}", file.Id, file.Size * .000001f, file.CreatedTime); }
/// <summary> /// Traverses the entire path and returns ID of the top-level folder(s) (if found), null otherwise. /// </summary> /// <param name="path">Path to validate.</param> /// <param name="appData">Whether to use the AppData space instead of the drive root.</param> /// <param name="parentId">ID of the parent folder, when path starts not from the root level.</param> /// <returns>ID of the final folders in the path; null if the path is not valid.</returns> public static async System.Threading.Tasks.Task <HashSet <string> > ValidatePath(string path, bool appData, string parentId = null) { if (parentId == null) { parentId = appData ? AppDataAlias : RootAlias; } if (string.IsNullOrWhiteSpace(path)) { return new HashSet <string> { parentId } } ; path = Path.GetDirectoryName(path).Replace('\\', '/'); if (string.IsNullOrWhiteSpace(path) || path.Trim() == "/" || path.Trim() == "\\") { return new HashSet <string> { parentId } } ; var parentNames = path.Split('/').Where(s => !string.IsNullOrWhiteSpace(s)).ToArray(); var result = new HashSet <string>(); for (int i = 0; i < parentNames.Length; i++) { using (var listRequest = new GoogleDriveFiles.ListRequest()) { listRequest.Fields = new List <string> { "files(id)" }; listRequest.Spaces = appData ? AppDataAlias : DriveSpace; listRequest.PageSize = 1000; // Assume we can't have more than 1K folders with equal names at the same level and skip the pagination. listRequest.Q = $"'{parentId}' in parents and name = '{parentNames[i]}' and mimeType = '{FolderMimeType}' and trashed = false"; await listRequest.Send(); if (listRequest == null || listRequest.IsError || listRequest.ResponseData.Files == null || listRequest.ResponseData.Files.Count == 0) { return(null); } // When at the top level, add all the folder's IDs. if (i + 1 == parentNames.Length) { result.UnionWith(listRequest.ResponseData.Files.Select(f => f.Id)); break; } // Multiple folders with equal names found at the same level (but not top), travers them recursively. if (listRequest.ResponseData.Files.Count > 1) { var nextPath = string.Join("/", parentNames.Skip(i + 1)) + "/"; foreach (var folder in listRequest.ResponseData.Files) { var topFolderIds = await ValidatePath(nextPath, appData, folder.Id); if (topFolderIds != null) { result.UnionWith(topFolderIds); } } break; } // Only one folder found, use it's ID to travers higher. else { parentId = listRequest.ResponseData.Files[0].Id; } } } return(result.Count == 0 ? null : result); }
/// <summary> /// Creates a new (or update existsing) <see cref="Data.File"/> at the provided path. /// Will also create any missing folders at the provided path. /// </summary> /// <param name="file">Metadata for the created (updated) file.</param> /// <param name="path">Created file's path (including file name).</param> /// <param name="appData">Whether to use the AppData space instead of the drive root.</param> /// <param name="forceUploadContent">Whether to always upload <see cref="Data.File.Content"/>, even when checksum of the content is equal to the one kept on drive.</param> /// <param name="uploadMimeType">When the uploaded content differs from the target type (Eg when uploading plain text to create a google document), specify the uploaded content MIME type here.</param> /// <returns>ID of the created (updated) file. Null if failed.</returns> public static async System.Threading.Tasks.Task <string> CreateOrUpdateFileAtPathAsync(UnityGoogleDrive.Data.File file, string path, bool appData = false, bool forceUploadContent = false, string uploadMimeType = null) { var fileName = Path.GetFileName(path); if (string.IsNullOrWhiteSpace(fileName)) { return(null); } if (string.IsNullOrWhiteSpace(file.Name)) { file.Name = fileName; } // Just modify the file if already exists. var files = await FindFilesByPathAsync(path, appData, new List <string> { "files(md5Checksum)" }, file.MimeType); if (files.Count > 0) { if (files.Count > 1) { Debug.LogWarning($"UnityGoogleDrive: Multiple '{path}' files found while attempting to modify the file. Operation will modify only the first found file."); } if (!forceUploadContent && file.Content != null && CalculateMD5Checksum(file.Content) == files[0].Md5Checksum) { file.Content = null; } using (var updateRequest = GoogleDriveFiles.Update(files[0].Id, file, uploadMimeType)) { updateRequest.Fields = new List <string> { "id" }; var updatedFile = await updateRequest.Send(); return(updatedFile.Id); } } // Check if all the folders in the path exist. var parentIds = await ValidatePath(path, appData); if (parentIds == null) { parentIds = new HashSet <string>(); } if (parentIds.Count > 1) { Debug.LogWarning($"UnityGoogleDrive: Multiple '{Path.GetDirectoryName(path)}' pathes found while attempting to create a file. Operation will create a file at the first found path."); } // Some of the folders are missing; create them. if (parentIds.Count == 0) { var parentId = appData ? AppDataAlias : RootAlias; path = Path.GetDirectoryName(path).Replace('\\', '/'); var parentNames = path.Split('/').Where(s => !string.IsNullOrWhiteSpace(s)).ToArray(); for (int i = 0; i < parentNames.Length; i++) { using (var listRequest = new GoogleDriveFiles.ListRequest()) { listRequest.Fields = new List <string> { "files(id)" }; listRequest.Spaces = appData ? AppDataAlias : DriveSpace; listRequest.Q = $"'{parentId}' in parents and name = '{parentNames[i]}' and mimeType = '{FolderMimeType}' and trashed = false"; await listRequest.Send(); if (listRequest == null || listRequest.IsError) { return(null); } // Next folder at the current level is missing; create it. if (listRequest.ResponseData.Files == null || listRequest.ResponseData.Files.Count == 0) { var folder = new UnityGoogleDrive.Data.File { Name = parentNames[i], MimeType = FolderMimeType, Parents = new List <string> { parentId } }; using (var createRequest = GoogleDriveFiles.Create(folder)) { createRequest.Fields = new List <string> { "id" }; var createdFolder = await createRequest.Send(); parentId = createdFolder.Id; continue; } } // Next folder exists; use it's ID and travers higher. else { parentId = listRequest.ResponseData.Files[0].Id; } } } parentIds.Add(parentId); } // Create the file. file.Parents = new List <string> { parentIds.First() }; using (var createRequest = GoogleDriveFiles.Create(file, uploadMimeType)) { createRequest.Fields = new List <string> { "id" }; var createdFile = await createRequest.Send(); return(createdFile?.Id); } }