From 981d0c3f71dd25ba88400aa67056f23b2fa7a4fc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9A=D0=BE=D0=B7=D0=BB=D0=BE=D0=B2=D0=B8=D1=87=20=D0=90?= =?UTF-8?q?=D1=80=D1=82=D1=91=D0=BC?= Date: Fri, 7 Jul 2017 00:12:09 +0300 Subject: [PATCH] Initial commit --- YandexDiskSharp.sln | 22 + YandexDiskSharp/DiskException.cs | 27 + YandexDiskSharp/MediaTypes.cs | 102 +++ YandexDiskSharp/Models/CommentIds.cs | 93 ++ YandexDiskSharp/Models/Disk.cs | 131 +++ YandexDiskSharp/Models/Exception.cs | 99 +++ YandexDiskSharp/Models/Exif.cs | 86 ++ YandexDiskSharp/Models/FilesResourceList.cs | 102 +++ .../Models/LastUploadedResourceList.cs | 171 ++++ YandexDiskSharp/Models/Link.cs | 102 +++ YandexDiskSharp/Models/Operation.cs | 96 ++ YandexDiskSharp/Models/Resource.cs | 322 +++++++ YandexDiskSharp/Models/ResourceList.cs | 95 ++ YandexDiskSharp/Models/ShareInfo.cs | 101 +++ YandexDiskSharp/Models/SystemFolders.cs | 163 ++++ .../Models/UserPublicInformation.cs | 99 +++ YandexDiskSharp/OperationStatus.cs | 24 + YandexDiskSharp/Properties/AssemblyInfo.cs | 38 + YandexDiskSharp/RestClient.cs | 823 ++++++++++++++++++ YandexDiskSharp/Type.cs | 17 + YandexDiskSharp/Utilities/Extensions.cs | 30 + YandexDiskSharp/YandexDiskSharp.csproj | 68 ++ YandexDiskSharp/packages.config | 4 + 23 files changed, 2815 insertions(+) create mode 100644 YandexDiskSharp.sln create mode 100644 YandexDiskSharp/DiskException.cs create mode 100644 YandexDiskSharp/MediaTypes.cs create mode 100644 YandexDiskSharp/Models/CommentIds.cs create mode 100644 YandexDiskSharp/Models/Disk.cs create mode 100644 YandexDiskSharp/Models/Exception.cs create mode 100644 YandexDiskSharp/Models/Exif.cs create mode 100644 YandexDiskSharp/Models/FilesResourceList.cs create mode 100644 YandexDiskSharp/Models/LastUploadedResourceList.cs create mode 100644 YandexDiskSharp/Models/Link.cs create mode 100644 YandexDiskSharp/Models/Operation.cs create mode 100644 YandexDiskSharp/Models/Resource.cs create mode 100644 YandexDiskSharp/Models/ResourceList.cs create mode 100644 YandexDiskSharp/Models/ShareInfo.cs create mode 100644 YandexDiskSharp/Models/SystemFolders.cs create mode 100644 YandexDiskSharp/Models/UserPublicInformation.cs create mode 100644 YandexDiskSharp/OperationStatus.cs create mode 100644 YandexDiskSharp/Properties/AssemblyInfo.cs create mode 100644 YandexDiskSharp/RestClient.cs create mode 100644 YandexDiskSharp/Type.cs create mode 100644 YandexDiskSharp/Utilities/Extensions.cs create mode 100644 YandexDiskSharp/YandexDiskSharp.csproj create mode 100644 YandexDiskSharp/packages.config diff --git a/YandexDiskSharp.sln b/YandexDiskSharp.sln new file mode 100644 index 0000000..98e615a --- /dev/null +++ b/YandexDiskSharp.sln @@ -0,0 +1,22 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 15 +VisualStudioVersion = 15.0.26430.15 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "YandexDiskSharp", "YandexDiskSharp\YandexDiskSharp.csproj", "{FE0B453D-1E3B-4AB6-BBAD-F6F973356897}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Any CPU = Debug|Any CPU + Release|Any CPU = Release|Any CPU + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {FE0B453D-1E3B-4AB6-BBAD-F6F973356897}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {FE0B453D-1E3B-4AB6-BBAD-F6F973356897}.Debug|Any CPU.Build.0 = Debug|Any CPU + {FE0B453D-1E3B-4AB6-BBAD-F6F973356897}.Release|Any CPU.ActiveCfg = Release|Any CPU + {FE0B453D-1E3B-4AB6-BBAD-F6F973356897}.Release|Any CPU.Build.0 = Release|Any CPU + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/YandexDiskSharp/DiskException.cs b/YandexDiskSharp/DiskException.cs new file mode 100644 index 0000000..162b89a --- /dev/null +++ b/YandexDiskSharp/DiskException.cs @@ -0,0 +1,27 @@ +using System.Net; + +namespace YandexDiskSharp +{ + public class DiskException : WebException + { + public DiskException(Models.Exception exception, System.Exception innerException, WebExceptionStatus status, WebResponse response) : base(exception?.Message, innerException, status, response) + { + Description = exception.Description; + Error = exception.Error; + } + + #region ~Properties~ + + /// + /// Техническое описание ошибки. + /// + public string Description { get; } + + /// + /// Уникальный код ошибки. + /// + public string Error { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/MediaTypes.cs b/YandexDiskSharp/MediaTypes.cs new file mode 100644 index 0000000..956aa44 --- /dev/null +++ b/YandexDiskSharp/MediaTypes.cs @@ -0,0 +1,102 @@ +namespace YandexDiskSharp +{ + public static class MediaTypes + { + /// + /// Аудио-файлы. + /// + private const string Audio = "audio"; + + /// + /// Файлы резервных и временных копий. + /// + public const string Backup = "backup"; + + /// + /// Электронные книги. + /// + public const string Book = "book"; + + /// + /// Сжатые и архивированные файлы. + /// + public const string Compressed = "compressed"; + + /// + /// Файлы с базами данных. + /// + public const string Data = "data"; + + /// + /// Файлы с кодом (C++, C#, XML и т. п.), а также служебные файлы IDE. + /// + public const string Development = "development"; + + /// + /// Образы носителей информации в различных форматах и сопутствующие файлы (например, CUE). + /// + public const string DiskImage = "diskimage"; + + /// + /// Документы офисных форматов (Word, OpenOffice и т. п.). + /// + public const string Document = "document"; + + /// + /// зашифрованные файлы. + /// + public const string Encoded = "encoded"; + + /// + /// Исполняемые файлы. + /// + public const string Executable = "executable"; + + /// + /// Файлы с флэш-видео или анимацией. + /// + public const string Flash = "flash"; + + /// + /// Файлы шрифтов. + /// + public const string Font = "font"; + + /// + /// Изображения. + /// + public const string Image = "image"; + + /// + /// Файлы настроек для различных программ. + /// + public const string Settings = "settings"; + + /// + /// Файлы офисных таблиц (Numbers, Lotus). + /// + public const string Spreadsheet = "spreadsheet"; + + /// + /// Текстовые файлы. + /// + public const string Text = "text"; + + /// + /// Неизвестный тип. + /// + public const string Unknown = "unknown"; + + /// + /// Видео-файлы. + /// + public const string Video = "video"; + + /// + /// Различные файлы, используемые браузерами и сайтами (CSS, сертификаты, файлы закладок). + /// + public const string Web = "web"; + + + } +} diff --git a/YandexDiskSharp/Models/CommentIds.cs b/YandexDiskSharp/Models/CommentIds.cs new file mode 100644 index 0000000..e57ecbb --- /dev/null +++ b/YandexDiskSharp/Models/CommentIds.cs @@ -0,0 +1,93 @@ +using Newtonsoft.Json; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Идентификаторы комментариев. + /// + public class CommentIds + { + #region ~Constructor~ + + internal CommentIds(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + { + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "private_resource": + PrivateResource = jsonReader.ReadAsString(); + break; + case "public_resource": + PublicResource = jsonReader.ReadAsString(); + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + } + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static CommentIds Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new CommentIds(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out CommentIds result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Идентификатор комментариев для приватных ресурсов. + /// + public string PrivateResource { get; } + + /// + /// Идентификатор комментариев для публичных ресурсов. + /// + public string PublicResource { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/Models/Disk.cs b/YandexDiskSharp/Models/Disk.cs new file mode 100644 index 0000000..bbd6dbb --- /dev/null +++ b/YandexDiskSharp/Models/Disk.cs @@ -0,0 +1,131 @@ +using Newtonsoft.Json; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Данные о свободном и занятом пространстве на Диске. + /// + public class Disk + { + #region ~Constructor~ + + internal Disk(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "max_file_size": + MaxFileSize = long.Parse(jsonReader.ReadAsString()); + break; + case "total_space": + TotalSpace = long.Parse(jsonReader.ReadAsString()); + break; + case "trash_size": + TrashSize = long.Parse(jsonReader.ReadAsString()); + break; + case "is_paid": + IsPaid = jsonReader.ReadAsBoolean().Value; + break; + case "used_space": + UsedSpace = long.Parse(jsonReader.ReadAsString()); + break; + case "system_folders": + SystemFolders = new SystemFolders(jsonReader); + break; + case "revision": + Revision = long.Parse(jsonReader.ReadAsString()); + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static Disk Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new Disk(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out Disk result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Максимальный поддерживаемый размер файла. + /// + public long MaxFileSize { get; } + + /// + /// Общий объем диска (байт). + /// + public long TotalSpace { get; } + + /// + /// Общий размер файлов в Корзине (байт). Входит в . + /// + public long TrashSize { get; } + + /// + /// Признак наличия купленного места. + /// + public bool IsPaid { get; } + + /// + /// Используемый объем диска (байт). + /// + public long UsedSpace { get; } + + /// + /// Адреса системных папок в Диске пользователя. + /// + public SystemFolders SystemFolders { get; } + + /// + /// Текущая ревизия Диска. + /// + public long Revision { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/Models/Exception.cs b/YandexDiskSharp/Models/Exception.cs new file mode 100644 index 0000000..3415173 --- /dev/null +++ b/YandexDiskSharp/Models/Exception.cs @@ -0,0 +1,99 @@ +using Newtonsoft.Json; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Описание ошибки. + /// + public class Exception + { + #region ~Constructor~ + + internal Exception(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "message": + Message = jsonReader.ReadAsString(); + break; + case "description": + Description = jsonReader.ReadAsString(); + break; + case "error": + Error = jsonReader.ReadAsString(); + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static Exception Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new Exception(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out Exception result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Человекочитаемое описание ошибки. + /// + public string Message { get; } + + /// + /// Техническое описание ошибки. + /// + public string Description { get; } + + /// + /// Уникальный код ошибки. + /// + public string Error { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/Models/Exif.cs b/YandexDiskSharp/Models/Exif.cs new file mode 100644 index 0000000..b85e5c0 --- /dev/null +++ b/YandexDiskSharp/Models/Exif.cs @@ -0,0 +1,86 @@ +using Newtonsoft.Json; +using System; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Метаданные медиафайла (EXIF). + /// + public class Exif + { + #region ~Constructor~ + + internal Exif(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + { + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "private_resource": + DateTime = jsonReader.ReadAsDateTime().Value; + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + } + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static Exif Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new Exif(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out Exif result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Дата съёмки. + /// + public DateTime DateTime { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/Models/FilesResourceList.cs b/YandexDiskSharp/Models/FilesResourceList.cs new file mode 100644 index 0000000..7200ce7 --- /dev/null +++ b/YandexDiskSharp/Models/FilesResourceList.cs @@ -0,0 +1,102 @@ +using Newtonsoft.Json; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Плоский список всех файлов на Диске в алфавитном порядке. + /// + public class FilesResourceList : LastUploadedResourceList + { + #region ~Constructot~ + + internal FilesResourceList() { } + + internal FilesResourceList(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + { + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "items": + jsonReader.Read(); + while (jsonReader.Read() && jsonReader.TokenType != JsonToken.EndArray) + items.Add(new Resource(jsonReader)); + break; + case "limit": + limit = jsonReader.ReadAsInt32().Value; + break; + case "offset": + offset = jsonReader.ReadAsInt32().Value; + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + } + + #endregion + + #region ~Fields~ + + protected int offset; + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static new FilesResourceList Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new FilesResourceList(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out FilesResourceList result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Смещение начала списка от первого ресурса в папке. + /// + public int Offset => offset; + + #endregion + + } +} diff --git a/YandexDiskSharp/Models/LastUploadedResourceList.cs b/YandexDiskSharp/Models/LastUploadedResourceList.cs new file mode 100644 index 0000000..d290c02 --- /dev/null +++ b/YandexDiskSharp/Models/LastUploadedResourceList.cs @@ -0,0 +1,171 @@ +using Newtonsoft.Json; +using System; +using System.Collections; +using System.Collections.Generic; +using System.Collections.ObjectModel; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Список последних добавленных на Диск файлов, отсортированных по дате загрузки (от поздних к ранним). + /// + public class LastUploadedResourceList : IList + { + #region ~Constructor~ + + internal LastUploadedResourceList() + { + items = new List(); + Items = new ReadOnlyCollection(items); + } + + internal LastUploadedResourceList(JsonTextReader jsonReader) : this() + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + { + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "items": + jsonReader.Read(); + while (jsonReader.Read() && jsonReader.TokenType != JsonToken.EndArray) + items.Add(new Resource(jsonReader)); + break; + case "limit": + limit = jsonReader.ReadAsInt32().Value; + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + } + + public Resource this[int index] { get => items[index]; } + + #endregion + + #region ~Fields~ + + protected List items; + protected int limit; + + #endregion + + #region ~Properties~ + + public ReadOnlyCollection Items { get; } + + public int Count => items.Count; + + public bool IsReadOnly => true; + + /// + /// Максимальное количество элементов в массиве , заданное в запросе. + /// + public int Limit => limit; + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static LastUploadedResourceList Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new LastUploadedResourceList(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out LastUploadedResourceList result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + public bool Contains(Resource item) + { + return items.Contains(item); + } + + public void CopyTo(Resource[] array, int arrayIndex) + { + items.CopyTo(array, arrayIndex); + } + + public IEnumerator GetEnumerator() + { + return items.GetEnumerator(); + } + + public int IndexOf(Resource item) + { + return items.IndexOf(item); + } + + IEnumerator IEnumerable.GetEnumerator() + { + return items.GetEnumerator(); + } + + #endregion + + #region ~IList~ + + Resource IList.this[int index] { get => throw new NotImplementedException(); set => throw new NotImplementedException(); } + + void ICollection.Add(Resource item) + { + throw new NotImplementedException(); + } + + void ICollection.Clear() + { + throw new NotImplementedException(); + } + + void IList.Insert(int index, Resource item) + { + throw new NotImplementedException(); + } + + bool ICollection.Remove(Resource item) + { + throw new NotImplementedException(); + } + + void IList.RemoveAt(int index) + { + throw new NotImplementedException(); + } + + #endregion + } +} diff --git a/YandexDiskSharp/Models/Link.cs b/YandexDiskSharp/Models/Link.cs new file mode 100644 index 0000000..feb1e94 --- /dev/null +++ b/YandexDiskSharp/Models/Link.cs @@ -0,0 +1,102 @@ +using Newtonsoft.Json; +using System; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Cодержит URL для запроса метаданных ресурса. + /// + public class Link + { + #region ~Constructor~ + + internal Link(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + { + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "href": + Href = new Uri(jsonReader.ReadAsString()); + break; + case "method": + Method = jsonReader.ReadAsString(); + break; + case "templated": + Templated = jsonReader.ReadAsBoolean().Value; + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + } + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static Link Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new Link(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out Link result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// URL. Может быть шаблонизирован, см. ключ . + /// + public Uri Href { get; } + + /// + /// HTTP-метод для запроса URL из ключа href. + /// + public string Method { get; } + + /// + /// Признак URL, который был шаблонизирован согласно RFC 6570. + /// + public bool Templated { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/Models/Operation.cs b/YandexDiskSharp/Models/Operation.cs new file mode 100644 index 0000000..966d62f --- /dev/null +++ b/YandexDiskSharp/Models/Operation.cs @@ -0,0 +1,96 @@ +using Newtonsoft.Json; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Статус операции. + /// + public class Operation + { + #region ~Constructor~ + + internal Operation(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + { + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "status": + switch (jsonReader.ReadAsString()) + { + case "success": + Status = OperationStatus.Success; + break; + case "failure": + Status = OperationStatus.Failure; + break; + case "in-progress": + Status = OperationStatus.InProgress; + break; + } + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + } + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static Operation Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new Operation(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out Operation result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Статус операции. + /// + public OperationStatus Status { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/Models/Resource.cs b/YandexDiskSharp/Models/Resource.cs new file mode 100644 index 0000000..e0a3284 --- /dev/null +++ b/YandexDiskSharp/Models/Resource.cs @@ -0,0 +1,322 @@ +using Newtonsoft.Json; +using System; +using System.Collections.Generic; +using System.Collections.ObjectModel; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Описание ресурса, мета-информация о файле или папке. Включается в ответ на запрос метаинформации. + /// + public class Resource + { + #region ~Constructor~ + + internal Resource() { } + + internal Resource(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + { + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "public_key": + publicKey = jsonReader.ReadAsString(); + break; + case "_embedded": + embedded = new ResourceList(jsonReader); + break; + case "name": + name = jsonReader.ReadAsString(); + break; + case "created": + created = jsonReader.ReadAsDateTime().Value; + break; + case "custom_properties": + IDictionary customProperties = new Dictionary(); + int depth2 = jsonReader.Depth; + while (jsonReader.Read()) + { + if (jsonReader.TokenType == JsonToken.PropertyName) + customProperties.Add(jsonReader.Value.ToString(), jsonReader.ReadAsString()); + else if (jsonReader.TokenType == JsonToken.EndObject) + if (jsonReader.Depth == depth2) + break; + } + customProperties = new ReadOnlyDictionary(customProperties); + break; + case "public_url": + publicUrl = new Uri(jsonReader.ReadAsString()); + break; + case "origin_path": + originPath = jsonReader.ReadAsString(); + break; + case "modified": + modified = jsonReader.ReadAsDateTime().Value; + break; + case "path": + path = jsonReader.ReadAsString(); + break; + case "md5": + md5 = jsonReader.ReadAsString(); + break; + case "type": + type = jsonReader.ReadAsString() == "file" ? Type.file : Type.dir; + break; + case "mime_type": + mimeType = jsonReader.ReadAsString(); + break; + case "size": + size = long.Parse(jsonReader.ReadAsString()); + break; + case "sha256": + sha256 = jsonReader.ReadAsString(); + break; + case "revision": + revision = long.Parse(jsonReader.ReadAsString()); + break; + case "media_type": + mediaType = jsonReader.ReadAsString(); + break; + case "preview": + preview = new Uri(jsonReader.ReadAsString()); + break; + case "resource_id": + resourceId = jsonReader.ReadAsString(); + break; + case "comment_ids": + commentIds = new CommentIds(jsonReader); + break; + case "share": + share = new ShareInfo(jsonReader); + break; + case "views_count": + viewsCount = jsonReader.ReadAsInt32(); + break; + case "owner": + owner = new UserPublicInformation(jsonReader); + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + } + + #endregion + + #region ~Fields~ + + protected ResourceList embedded; + protected string publicKey; + protected string name; + protected DateTime created; + protected ReadOnlyDictionary customProperties; + protected Uri publicUrl; + protected string originPath; + protected DateTime modified; + protected string path; + protected string md5; + protected string sha256; + protected long revision; + protected Type type; + protected string mimeType; + protected long size; + protected string mediaType; + protected Uri preview; + protected string resourceId; + protected CommentIds commentIds; + protected ShareInfo share; + protected int? viewsCount; + protected UserPublicInformation owner; + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static Resource Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new Resource(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out Resource result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Ресурсы, непосредственно содержащиеся в папке (содержит объект ). + /// + /// + /// Включается в ответ только при запросе метаинформации о папке. + /// + public ResourceList Embedded => embedded; + + /// + /// Ключ опубликованного ресурса. + /// + /// + /// Включается в ответ только если указанный файл или папка опубликован. + /// + public string PublicKey => publicKey; + + /// + /// Имя ресурса. + /// + public string Name => name; + + /// + /// Дата и время создания ресурса. + /// + public DateTime Created => created; + +#warning добавить ссылку на метод + /// + /// Объект со всеми атрибутами, заданными с помощью запроса . + /// + /// + /// Содержит только ключи вида имя:значение (объекты или массивы содержать не может). + /// + public ReadOnlyDictionary CustomProperties => customProperties; + + /// + /// Ссылка на опубликованный ресурс. + /// + /// + /// Включается в ответ только если указанный файл или папка опубликован. + /// + public Uri PublicUrl => publicUrl; + + /// + /// Путь к ресурсу до перемещения в Корзину. + /// + /// + /// Включается в ответ только для запроса метаинформации о ресурсе в Корзине. + /// + public string OriginPath => originPath; + + /// + /// Дата и время изменения ресурса. + /// + public DateTime Modified => modified; + + /// + /// Полный путь к ресурсу на Диске. + /// + /// + /// В метаинформации опубликованной папки пути указываются относительно самой папки. Для опубликованных файлов значение ключа всегда «/». + /// Для ресурса, находящегося в Корзине, к атрибуту может быть добавлен уникальный идентификатор. + /// + /// trash:/foo_1408546879 + /// + /// С помощью этого идентификатора ресурс можно отличить от других удаленных ресурсов с тем же именем. + /// + public string Path => path; + + /// + /// MD5-хэш файла. + /// + public string Md5 => md5; + + /// + /// SHA256-хэш файла. + /// + public string Sha256 => sha256; + + /// + /// Ревизия Диска в которой этот ресурс был изменён последний раз. + /// + public long Revision => revision; + + /// + /// Тип ресурса. + /// + public Type Type => type; + + /// + /// MIME-тип файла. + /// + public string MimeType => mimeType; + + /// + /// Размер файла. + /// + public long Size => size; + + /// + /// MIME-тип файла. + /// + public string MediaType => mediaType; + + /// + /// Ссылка на уменьшенное изображение из файла(превью). Включается в ответ только для файлов поддерживаемых графических форматов. + /// + /// + /// Запросить превью можно только с OAuth-токеном пользователя, имеющего доступ к самому файлу. + /// + public Uri Preview => preview; + + /// + /// Идентификатор ресурса. + /// + public string ResourceId => resourceId; + + /// + /// Идентификаторы комментариев. + /// + public CommentIds CommentIds => commentIds; + + /// + /// Информация об общей папке. + /// + public ShareInfo Share => share; + + /// + /// Счетчик просмотров публичного ресурса. + /// + public int? ViewsCount => viewsCount; + + /// + /// Владелец опубликованного ресурса. + /// + public UserPublicInformation Owner => owner; + + #endregion + } +} diff --git a/YandexDiskSharp/Models/ResourceList.cs b/YandexDiskSharp/Models/ResourceList.cs new file mode 100644 index 0000000..b72e365 --- /dev/null +++ b/YandexDiskSharp/Models/ResourceList.cs @@ -0,0 +1,95 @@ +using Newtonsoft.Json; + +namespace YandexDiskSharp.Models +{ + public class ResourceList : FilesResourceList + { + protected ResourceList() { } + + internal ResourceList(JsonTextReader jsonReader) : base() + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + { + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "sort": + sort = jsonReader.ReadAsString(); + break; + case "public_key": + publicKey = jsonReader.ReadAsString(); + break; + case "items": + jsonReader.Read(); + while (jsonReader.Read() && jsonReader.TokenType != JsonToken.EndArray) + items.Add(new Resource(jsonReader)); + break; + case "path": + path = jsonReader.ReadAsString(); + break; + case "limit": + limit = jsonReader.ReadAsInt32().Value; + break; + case "offset": + offset = jsonReader.ReadAsInt32().Value; + break; + case "total": + total = jsonReader.ReadAsInt32().Value; + break; + case "type": + System.Diagnostics.Debug.WriteLine($"type = {jsonReader.ReadAsString()}"); + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + } + + + #region ~Fields~ + + protected string sort; + protected string publicKey; + protected string path; + protected int total; + + #endregion + + #region ~Properties~ + + /// + /// Поле, по которому отсортирован список. + /// + public string Sort => sort; + + /// + /// Ключ опубликованного ресурса. + /// + /// + /// Включается только в ответ на запрос метаинформации о публичной папке. + /// + public string PublicKey => publicKey; + + /// + /// Путь к папке, чье содержимое описывается в данном объекте . + /// + /// + /// Для публичной папки значение атрибута всегда равно «/». + /// + public string Path => path; + + /// + /// Общее количество ресурсов в папке. + /// + public int Total => total; + + #endregion + } +} diff --git a/YandexDiskSharp/Models/ShareInfo.cs b/YandexDiskSharp/Models/ShareInfo.cs new file mode 100644 index 0000000..5570b77 --- /dev/null +++ b/YandexDiskSharp/Models/ShareInfo.cs @@ -0,0 +1,101 @@ +using Newtonsoft.Json; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Информация об общей папке. + /// + public class ShareInfo + { + #region ~Constructor~ + + internal ShareInfo(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + { + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "is_root": + IsRoot = jsonReader.ReadAsBoolean().Value; + break; + case "is_owned": + IsOwned = jsonReader.ReadAsBoolean().Value; + break; + case "rights": + Rights = jsonReader.ReadAsString(); + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + } + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static ShareInfo Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new ShareInfo(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out ShareInfo result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Признак того, что папка является корневой в группе. + /// + public bool IsRoot { get; } + + /// + /// Признак, что текущий пользователь является владельцем общей папки. + /// + public bool IsOwned { get; } + + /// + /// Права доступа. + /// + public string Rights { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/Models/SystemFolders.cs b/YandexDiskSharp/Models/SystemFolders.cs new file mode 100644 index 0000000..09b0405 --- /dev/null +++ b/YandexDiskSharp/Models/SystemFolders.cs @@ -0,0 +1,163 @@ +using Newtonsoft.Json; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// Адреса системных папок в Диске пользователя. + /// + public class SystemFolders + { + #region ~Constructor~ + + internal SystemFolders(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "odnoklassniki": + Odnoklassniki = jsonReader.ReadAsString(); + break; + case "google": + Google = jsonReader.ReadAsString(); + break; + case "instagram": + Instagram = jsonReader.ReadAsString(); + break; + case "vkontakte": + Vkontakte = jsonReader.ReadAsString(); + break; + case "mailru": + MailRu = jsonReader.ReadAsString(); + break; + case "downloads": + Downloads = jsonReader.ReadAsString(); + break; + case "applications": + Applications = jsonReader.ReadAsString(); + break; + case "facebook": + Facebook = jsonReader.ReadAsString(); + break; + case "social": + Social = jsonReader.ReadAsString(); + break; + case "screenshots": + Screenshots = jsonReader.ReadAsString(); + break; + case "photostream": + Photostream = jsonReader.ReadAsString(); + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static SystemFolders Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new SystemFolders(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out SystemFolders result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Путь к папке "Социальные сети/Одноклассники". + /// + public string Odnoklassniki { get; } + + /// + /// Путь к папке "Социальные сети/Google+". + /// + public string Google { get; } + + /// + /// Путь к папке "Социальные сети/Instagram". + /// + public string Instagram { get; } + + /// + /// Путь к папке "Социальные сети/ВКонтакте". + /// + public string Vkontakte { get; } + + /// + /// Путь к папке "Социальные сети/Мой Мир". + /// + public string MailRu { get; } + + /// + /// Путь к папке "Загрузки". + /// + public string Downloads { get; } + + /// + /// Путь к папке "Приложения". + /// + public string Applications { get; } + + /// + /// Путь к папке "Социальные сети/Facebook". + /// + public string Facebook { get; } + + /// + /// Путь к папке "Социальные сети". + /// + public string Social { get; } + + /// + /// Путь к папке "Скриншоты". + /// + public string Screenshots { get; } + + /// + /// Путь к папке "Фотокамера". + /// + public string Photostream { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/Models/UserPublicInformation.cs b/YandexDiskSharp/Models/UserPublicInformation.cs new file mode 100644 index 0000000..16ca7c0 --- /dev/null +++ b/YandexDiskSharp/Models/UserPublicInformation.cs @@ -0,0 +1,99 @@ +using Newtonsoft.Json; +using System.IO; + +namespace YandexDiskSharp.Models +{ + /// + /// + /// + public class UserPublicInformation + { + #region ~Constructor~ + + internal UserPublicInformation(JsonTextReader jsonReader) + { + int depth = jsonReader.Depth; + while (jsonReader.Read()) + switch (jsonReader.TokenType) + { + case JsonToken.PropertyName: + switch (jsonReader.Value.ToString()) + { + case "login": + Login = jsonReader.ReadAsString(); + break; + case "display_name": + DisplayName = jsonReader.ReadAsString(); + break; + case "uid": + Uid = jsonReader.ReadAsString(); + break; + } + break; + case JsonToken.EndObject: + if (jsonReader.Depth == depth) + return; + break; + } + } + + #endregion + + #region ~Methods~ + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . + /// + /// Строка, содержащая преобразуемый json ответ. + /// Класс , эквивалентный json ответу, содержащемуся в параметре s. + public static UserPublicInformation Parse(string s) + { + using (var stringReader = new StringReader(s)) + using (var jsonReader = new JsonTextReader(stringReader)) + { + return new UserPublicInformation(jsonReader); + } + } + + /// + /// Преобразует строковое представление json ответа в эквивалентный ему класс . Возвращает значение, указывающее, успешно ли выполнено преобразование. + /// + /// Строка, содержащая преобразуемый json ответ. + /// При возвращении этим методом содержиткласс , эквивалентный json ответу, содержащемуся в параметре s, если преобразование выполнено успешно, или null, если оно завершилось сбоем. Преобразование завершается сбоем, если параметр s равен null или или не находится в правильном формате. Этот параметр передается неинициализированным; любое значение, первоначально предоставленное в объекте result, будет перезаписано. + /// Значение true, если параметр s успешно преобразован; в противном случае — значение false. + public static bool TryParse(string s, out UserPublicInformation result) + { + try + { + result = Parse(s); + return true; + } + catch + { + result = null; + return false; + } + } + + #endregion + + #region ~Properties~ + + /// + /// Логин. + /// + public string Login { get; } + + /// + /// Отображаемое имя пользователя. + /// + public string DisplayName { get; } + + /// + /// Идентификатор пользователя. + /// + public string Uid { get; } + + #endregion + } +} diff --git a/YandexDiskSharp/OperationStatus.cs b/YandexDiskSharp/OperationStatus.cs new file mode 100644 index 0000000..d15630d --- /dev/null +++ b/YandexDiskSharp/OperationStatus.cs @@ -0,0 +1,24 @@ +namespace YandexDiskSharp +{ + /// + /// Статус операции. + /// + /// Операции запускаются, когда вы копируете, перемещаете или удаляете непустые папки. URL для запроса статуса возвращается в ответ на такие запросы. + public enum OperationStatus + { + /// + /// Операция успешно завершена. + /// + Success, + + /// + /// Операцию совершить не удалось, попробуйте повторить изначальный запрос копирования, перемещения или удаления. + /// + Failure, + + /// + /// Операция начата, но еще не завершена. + /// + InProgress + } +} diff --git a/YandexDiskSharp/Properties/AssemblyInfo.cs b/YandexDiskSharp/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..45d02ec --- /dev/null +++ b/YandexDiskSharp/Properties/AssemblyInfo.cs @@ -0,0 +1,38 @@ +using System.Resources; +using System.Reflection; +using System.Runtime.InteropServices; + +// Общие сведения об этой сборке предоставляются следующим набором +// набора атрибутов. Измените значения этих атрибутов, чтобы изменить сведения, +// связанные со сборкой. +[assembly: AssemblyTitle("YandexDiskSharp")] +[assembly: AssemblyDescription("REST API Яндекс.Диска")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("YandexDiskSharp")] +[assembly: AssemblyCopyright("Copyright © 2017")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// Установка значения False для параметра ComVisible делает типы в этой сборке невидимыми +// для компонентов COM. Если необходимо обратиться к типу в этой сборке через +// COM, задайте атрибуту ComVisible значение TRUE для этого типа. +[assembly: ComVisible(false)] + +// Следующий GUID служит для идентификации библиотеки типов, если этот проект будет видимым для COM +[assembly: Guid("fe0b453d-1e3b-4ab6-bbad-f6f973356897")] + +// Сведения о версии сборки состоят из следующих четырех значений: +// +// Основной номер версии +// Дополнительный номер версии +// Номер сборки +// Редакция +// +// Можно задать все значения или принять номер сборки и номер редакции по умолчанию. +// используя "*", как показано ниже: +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] +[assembly: NeutralResourcesLanguage("ru")] + diff --git a/YandexDiskSharp/RestClient.cs b/YandexDiskSharp/RestClient.cs new file mode 100644 index 0000000..99170e9 --- /dev/null +++ b/YandexDiskSharp/RestClient.cs @@ -0,0 +1,823 @@ +using System; +using System.Collections.Generic; +using System.Net; +using System.Text; +using System.Threading.Tasks; +using System.Web; +using YandexDiskSharp.Models; +using YandexDiskSharp.Utilities; + +namespace YandexDiskSharp +{ + /// + /// Rest клиент, предоставляющий доступ к REST API Яндекс.Диска. + /// + public class RestClient + { + #region ~Constants~ + + /// + /// Указывает на то, что ресурс расположен в каталоге приложения. + /// + public const string UriSchemeApp = "app:/"; + + /// + /// Указывает на то, что доступ к ресурсу осществляется через корневой каталог Диска. + /// + public const string UriSchemeDisk = "disk:/"; + + /// + /// Указывает на то, что ресурс расположен в каталоге "Корзина". + /// + public const string UriSchemeTrash = "trash:/"; + + #endregion + + #region ~Constructor~ + + /// OAuth-токен, выданный вашему приложению для доступа к Диску определенного пользователя. + public RestClient(string accessToken) + { + AccessToken = accessToken; + Timeout = 100000; + ReadWriteTimeout = 300000; + } + + #endregion + + #region ~Properties~ + + /// + /// OAuth-токен приложения для доступа к Диску определенного пользователя. + /// + public string AccessToken { get; } + + /// + /// Возвращает или задает значение времени ожидания в миллисекундах для методов и . + /// + /// Количество миллисекунд, ожидаемых до остановки запроса. По умолчанию установлено значение 100 000 миллисекунд (100 секунд). + /// Указанное значение меньше нуля и не равно . + public int Timeout { get; set; } + + /// + /// Возвращает или задает время ожидания в миллисекундах при записи в поток или при чтении из него. + /// + /// Количество миллисекунд до истечения срока действия записи или чтения. По умолчанию установлено значение 300 000 миллисекунд (5 минут). + /// Запрос уже был отправлен. + /// Значение, указанное для операции задания, меньше или равно нулю и не равно + public int ReadWriteTimeout { get; set; } + + #endregion + + #region ~Methods~ + + private HttpWebRequest CreateRequest(string requestUriString, string method) + { + HttpWebRequest result = (HttpWebRequest)WebRequest.Create(requestUriString); + result.Method = method; + result.Headers["Authorization"] = $"OAuth {AccessToken}"; + result.Timeout = Timeout; + result.ReadWriteTimeout = ReadWriteTimeout; + return result; + } + + /// + /// Данные о Диске пользователя. + /// + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Если запрос был обработан без ошибок, API возвращает данные о Диске в теле ответа, в объекте . + public Disk GetDisk(IEnumerable fields = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/?" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}", + "GET").GetJsonTextReader()) + return new Disk(jsonReader); + } + + /// + /// Данные о Диске пользователя. + /// + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Если запрос был обработан без ошибок, API возвращает данные о Диске в теле ответа, в объекте . + public async Task GetDiskAsync(IEnumerable fields = null) + { + return await Task.Run(() => GetDisk(fields)); + } + + /// + /// Запрашивает метаинформация о файле или папке. + /// + /// Путь к нужному ресурсу относительно корневого каталога Диска. + /// Атрибут, по которому сортируется список ресурсов, вложенных в папку. Для сортировки в обратном порядке добавьте дефис к значению параметра, например: sort=-name. + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Метаинформация включает в себя собственные свойства файлов и папок, а также свойства и содержимое вложенных папок. + public Resource GetResource(string path, string sort = null, int limit = 20, int offset = 0, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources?" + + $"path={HttpUtility.UrlEncode(path)}" + + $"{(sort != null ? $"&sort={sort}" : null)}" + + $"{(limit != 20 ? $"&limit={limit}" : "")}" + + $"{(offset != 0 ? $"&offset={offset}" : "")}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}" + + $"{(previewSize != null ? $"&preview_size={previewSize}{(previewCrop != false ? $"&preview_crop={previewCrop.ToString()}" : null)}" : "")}", + "GET").GetJsonTextReader()) + return new Resource(jsonReader); + } + + /// + /// Запрашивает метаинформация о файле или папке. + /// + /// Путь к нужному ресурсу относительно корневого каталога Диска. + /// Атрибут, по которому сортируется список ресурсов, вложенных в папку. Для сортировки в обратном порядке добавьте дефис к значению параметра, например: sort=-name. + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Метаинформация включает в себя собственные свойства файлов и папок, а также свойства и содержимое вложенных папок. + public async Task GetResourceAsync(string path, string sort = null, int limit = 20, int offset = 0, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + return await Task.Run(() => GetResource(path, sort, limit, offset, fields, previewSize, previewCrop)); + } + + /// + /// Метаинформация о файле или папке в корзине. + /// + /// Путь к нужному ресурсу относительно корневого каталога Диска. + /// Атрибут, по которому сортируется список ресурсов, вложенных в папку. Для сортировки в обратном порядке добавьте дефис к значению параметра, например: sort=-name. + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Если запрос был обработан без ошибок, API возвращает метаинформацию о запрошенном ресурсе в теле ответа, в объекте . + public Resource GetTrashResource(string path, string sort = null, int limit = 20, int offset = 0, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/trash/resources?" + + $"path={HttpUtility.UrlEncode(path)}" + + $"{(sort != null ? $"&sort={sort}" : null)}" + + $"{(limit != 20 ? $"&limit={limit}" : "")}" + + $"{(offset != 0 ? $"&offset={offset}" : "")}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}" + + $"{(previewSize != null ? $"&preview_size={previewSize}{(previewCrop != false ? $"&preview_crop={previewCrop.ToString()}" : null)}" : "")}", + "GET").GetJsonTextReader()) + return new Resource(jsonReader); + } + + /// + /// Метаинформация о файле или папке в корзине. + /// + /// Путь к нужному ресурсу относительно корневого каталога Диска. + /// Атрибут, по которому сортируется список ресурсов, вложенных в папку. Для сортировки в обратном порядке добавьте дефис к значению параметра, например: sort=-name. + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Если запрос был обработан без ошибок, API возвращает метаинформацию о запрошенном ресурсе в теле ответа, в объекте . + public async Task GetTrashResourceAsync(string path, string sort = null, int limit = 20, int offset = 0, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + return await Task.Run(() => GetTrashResource(path, sort, limit, offset, fields, previewSize, previewCrop)); + } + + /// + /// Плоский список всех файлов. + /// + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Тип файлов, которые нужно включить в список. Диск определяет тип каждого файла при загрузке. + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Возвращает плоский список всех файлов на Диске в алфавитном порядке. Плоский список не учитывает структуру каталогов, поэтому в нем удобно искать файлы определенного типа, разбросанные по разным папкам. Диск определяет тип каждого файла при загрузке. + public FilesResourceList GetFlatFilesList(int limit = 20, IEnumerable mediaType = null, int offset = 0, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + List query = new List(); + + if (limit != 20) + query.Add($"limit={limit.ToString()}"); + if (mediaType != null) + query.Add($"media_type={string.Join(", ", mediaType)}"); + if (offset != 0) + query.Add($"offset={offset.ToString()}"); + if (fields != null) + query.Add($"fields={string.Join(",", fields)}"); + if (previewSize != null) + query.Add($"preview_size={previewSize}"); + if (previewCrop != false) + query.Add($"preview_crop={previewCrop.ToString()}"); + + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/files{(query.Count > 0 ? $"?{string.Join("&", query)}" : null)}", + "GET").GetJsonTextReader()) + return new FilesResourceList(jsonReader); + } + + /// + /// Плоский список всех файлов. + /// + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Тип файлов, которые нужно включить в список. Диск определяет тип каждого файла при загрузке. + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Возвращает плоский список всех файлов на Диске в алфавитном порядке. Плоский список не учитывает структуру каталогов, поэтому в нем удобно искать файлы определенного типа, разбросанные по разным папкам. Диск определяет тип каждого файла при загрузке. + public async Task GetFlatFilesListAsync(int limit = 20, IEnumerable mediaType = null, int offset = 0, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + return await Task.Run(() => GetFlatFilesList(limit, mediaType, offset, fields, previewSize, previewCrop)); + } + + /// + /// Последние загруженные файлы. + /// + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Тип файлов, которые нужно включить в список. Диск определяет тип каждого файла при загрузке. + /// Список ключей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Если запрос был обработан без ошибок, возвращает метаинформацию о запрошенном количестве файлов в теле ответа, в объекте . + public LastUploadedResourceList GetLastUploadedFilesList(int limit = 20, IEnumerable mediaType = null, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + List query = new List(); + + if (limit != 20) + query.Add($"limit={limit.ToString()}"); + if (mediaType != null) + query.Add($"media_type={string.Join(", ", mediaType)}"); + if (fields != null) + query.Add($"fields={HttpUtility.UrlEncode(string.Join(",", fields))}"); + if (previewSize != null) + query.Add($"preview_size={previewSize}"); + if (previewCrop != false) + query.Add($"preview_crop={previewCrop.ToString()}"); + + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/last-uploaded{(query.Count > 0 ? $"?{string.Join("&", query)}" : null)}", + "GET").GetJsonTextReader()) + return new LastUploadedResourceList(jsonReader); + } + + /// + /// Последние загруженные файлы. + /// + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Тип файлов, которые нужно включить в список. Диск определяет тип каждого файла при загрузке. + /// Список ключей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Если запрос был обработан без ошибок, возвращает метаинформацию о запрошенном количестве файлов в теле ответа, в объекте . + public async Task GetLastUploadedFilesListAsync(int limit = 20, IEnumerable mediaType = null, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + return await Task.Run(() => GetLastUploadedFilesList(limit, mediaType, fields, previewSize, previewCrop)); + } + + /// + /// Добавление метаинформации для ресурса. + /// + /// Для любого файла или папки, доступной на запись, можно задать дополнительные произвольные атрибуты. Эти атрибуты будут возвращаться в ответ на все запросы метаинформации о ресурсах (список всех файлов, последние загруженные и т. д.). + /// Путь к нужному ресурсу относительно корневого каталога Диска. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Добавляемые атрибуты. Переданные атрибуты добавляются к уже имеющимся. Чтобы удалить какой-либо ключ, следует передать его со значением null + /// Возвращает метаинформацию о запрошенном ресурсе в теле ответа, в объекте . + //public Resource ResourcePatch(string path, IDictionary properties, IEnumerable fields = null) + public Resource ResourcePatch(string path, IDictionary properties, IEnumerable fields = null) + { + var request = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources?" + + $"path={HttpUtility.UrlEncode(path)}" + + $"{(fields != null ? $"&fields={HttpUtility.UrlEncode(string.Join(",", fields))}" : "")}", + "PATCH"); + + var propertyList = new List(); + foreach (var property in properties) + propertyList.Add((property.Value != null ) ? $"\"{property.Key}\":\"{property.Value}\"" : $"\"{property.Key}\":null"); + + byte[] buffer = Encoding.UTF8.GetBytes($"{{\"custom_properties\":{{{string.Join(", ", propertyList)}}}}}"); + using (var stream = request.GetRequestStream()) + stream.Write(buffer, 0, buffer.Length); + using (var jsonReader = request.GetJsonTextReader()) + return new Resource(jsonReader); + } + + /// + /// Добавление метаинформации для ресурса. + /// + /// Для любого файла или папки, доступной на запись, можно задать дополнительные произвольные атрибуты. Эти атрибуты будут возвращаться в ответ на все запросы метаинформации о ресурсах (список всех файлов, последние загруженные и т. д.). + /// Путь к нужному ресурсу относительно корневого каталога Диска. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Добавляемые атрибуты. Переданные атрибуты добавляются к уже имеющимся. Чтобы удалить какой-либо ключ, следует передать его со значением null + /// Возвращает метаинформацию о запрошенном ресурсе в теле ответа, в объекте . + public async Task ResourcePatchAsync(string path, IDictionary properties, IEnumerable fields = null) + { + return await Task.Run(() => ResourcePatch(path, properties, fields)); + } + + /// + /// Запрос URL для загрузки. + /// + /// Сообщив API Диска желаемый путь для загружаемого файла, вы получаете URL для обращения к загрузчику файлов. + /// Путь к нужному ресурсу относительно корневого каталога Диска. + /// Признак перезаписи файла. Учитывается, если файл загружается в папку, в которой уже есть файл с таким именем. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает сгенерированный URL для загрузки файла. Если в течение 30 минут этот URL не будет запрошен, он перестанет работать, и нужно будет запросить новую ссылку. + public Link GetResourceUploadLink(string path, bool overwrite = false, IEnumerable fields = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/upload?" + + $"path={HttpUtility.UrlEncode(path)}" + + $"{(overwrite != false ? $"&overwrite=true" : "")}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}", + "GET").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Запрос URL для загрузки. + /// + /// Сообщив API Диска желаемый путь для загружаемого файла, вы получаете URL для обращения к загрузчику файлов. + /// Путь к нужному ресурсу относительно корневого каталога Диска. + /// Признак перезаписи файла. Учитывается, если файл загружается в папку, в которой уже есть файл с таким именем. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает сгенерированный URL для загрузки файла. Если в течение 30 минут этот URL не будет запрошен, он перестанет работать, и нужно будет запросить новую ссылку. + public async Task GetResourceUploadLinkAsync(string path, bool overwrite = false, IEnumerable fields = null) + { + return await Task.Run(() => GetResourceUploadLink(path, overwrite, fields)); + } + + /// + /// Скачивание файла из интернета на Диск. + /// + /// Яндекс.Диск может скачать файл на Диск пользователя. Для этого следует передать в запросе URL файла и следить за ходом операции. Если при скачивании возникла ошибка, Диск не будет пытаться скачать файл еще раз. + /// Ссылка на скачиваемый файл. + /// Путь на Диске, по которому должен быть доступен скачанный файл. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Параметр помогает запретить редиректы по адресу, заданному в параметре . + /// Скачивание файла может занять неопределенное время. Если операция скачивания была запущена, API отвечает ссылкой на статус операции (в объекте ). + public Link UploadExternalResource(Uri url, string path, IEnumerable fields = null, bool disableRedirects = false) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/upload?" + + $"url={HttpUtility.UrlEncode(url.AbsoluteUri)}" + + $"&path={HttpUtility.UrlEncode(path)}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}" + + $"{(disableRedirects != false ? "disable_redirects=true" : null)}", + "GET").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Скачивание файла из интернета на Диск. + /// + /// Яндекс.Диск может скачать файл на Диск пользователя. Для этого следует передать в запросе URL файла и следить за ходом операции. Если при скачивании возникла ошибка, Диск не будет пытаться скачать файл еще раз. + /// Ссылка на скачиваемый файл. + /// Путь на Диске, по которому должен быть доступен скачанный файл. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Параметр помогает запретить редиректы по адресу, заданному в параметре . + /// Скачивание файла может занять неопределенное время. Если операция скачивания была запущена, API отвечает ссылкой на статус операции (в объекте ). + public async Task UploadExternalResourceAsync(Uri url, string path, IEnumerable fields = null, bool disableRedirects = false) + { + return await Task.Run(() => UploadExternalResource(url, path, fields, disableRedirects)); + } + + /// + /// Запрос URL для скачивания. + /// + /// Чтобы получить URL для непосредственной загрузки файла, необходимо передать API путь на Диске, по которому загруженный файл должен быть доступен. + /// Путь к скачиваемому файлу. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает сгенерированный URL для скачивания файла в объекте + public Link GetResourceDownloadLink(string path, IEnumerable fields = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/download?" + + $"path={HttpUtility.UrlEncode(path)}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}", + "GET").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Запрос URL для скачивания. + /// + /// Чтобы получить URL для непосредственной загрузки файла, необходимо передать API путь на Диске, по которому загруженный файл должен быть доступен. + /// Путь к скачиваемому файлу. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает сгенерированный URL для скачивания файла в объекте + public async Task GetResourceDownloadLinkAsync(string path, IEnumerable fields = null) + { + return await Task.Run(() => GetResourceDownloadLink(path, fields)); + } + + /// + /// Копирование файла или папки. + /// + /// Копировать файлы и папки на Диске пользователя можно, указывая путь к ресурсу и требуемый путь к его копии. + /// Путь к копируемому ресурсу. + /// Путь к создаваемой копии ресурса. + /// Признак перезаписи файла. Учитывается, если файл загружается в папку, в которой уже есть файл с таким именем. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает ссылку на мета-информацию о созданном ресурсе для пустой папки или файла. Непустая папка может копироваться в течение произвольного времени, поэтому приложения должны самостоятельно следить за статусами запрошенных операций. + public Link CopyResource(string from, string path, bool overwrite = false, IEnumerable fields = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/copy?" + + $"from={HttpUtility.UrlEncode(from)}" + + $"&path={HttpUtility.UrlEncode(path)}" + + $"{(overwrite != false ? $"&overwrite=true" : "")}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}", + "POST").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Копирование файла или папки. + /// + /// Копировать файлы и папки на Диске пользователя можно, указывая путь к ресурсу и требуемый путь к его копии. + /// Путь к копируемому ресурсу. + /// Путь к создаваемой копии ресурса. + /// Признак перезаписи файла. Учитывается, если файл загружается в папку, в которой уже есть файл с таким именем. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает ссылку на мета-информацию о созданном ресурсе для пустой папки или файла. Непустая папка может копироваться в течение произвольного времени, поэтому приложения должны самостоятельно следить за статусами запрошенных операций. + public async Task CopyResourceAsync(string from, string path, bool overwrite = false, IEnumerable fields = null) + { + return await Task.Run(() => CopyResource(from, path, overwrite, fields)); + } + + /// + /// Перемещение файла или папки. + /// + /// Перемещать файлы и папки на Диске можно, указывая текущий путь к ресурсу и его новое положение. + /// Путь к перемещаемому ресурсу. + /// Путь к новому положению ресурса. + /// Признак перезаписи файла. Учитывается, если файл загружается в папку, в которой уже есть файл с таким именем. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает ссылку на мета-информацию о созданном ресурсе для пустой папки или файла. Непустая папка может перемещаться в течение произвольного времени, поэтому приложения должны самостоятельно следить за статусами запрошенных операций. + public Link MoveResource(string from, string path, bool overwrite = false, IEnumerable fields = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/move?" + + $"from={HttpUtility.UrlEncode(from)}" + + $"&path={HttpUtility.UrlEncode(path)}" + + $"{(overwrite != false ? $"&overwrite=true" : "")}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}", + "POST").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Перемещение файла или папки. + /// + /// Перемещать файлы и папки на Диске можно, указывая текущий путь к ресурсу и его новое положение. + /// Путь к перемещаемому ресурсу. + /// Путь к новому положению ресурса. + /// Признак перезаписи файла. Учитывается, если файл загружается в папку, в которой уже есть файл с таким именем. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает ссылку на мета-информацию о созданном ресурсе для пустой папки или файла. Непустая папка может перемещаться в течение произвольного времени, поэтому приложения должны самостоятельно следить за статусами запрошенных операций. + public async Task MoveResourceAsync(string from, string path, bool overwrite = false, IEnumerable fields = null) + { + return await Task.Run(() => MoveResource(from, path, overwrite, fields)); + } + + /// + /// Удаление файла или папки. + /// + /// Удалять файлы и папки на Диске пользователя можно, указывая путь к удаляемому ресурсу. Помните, что перемещение ресурсов в Корзину никак не влияет на доступное место на Диске. Чтобы освободить место, следует также удалять ресурсы из Корзины. + /// Путь к новому положению ресурса. + /// Признак безвозвратного удаления. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает ссылку на мета-информацию о созданном ресурсе для пустой папки или файла. Непустая папка может перемещаться в течение произвольного времени, поэтому приложения должны самостоятельно следить за статусами запрошенных операций. + public Link DeleteResource(string path, bool permanently = false, IEnumerable fields = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources?" + + $"path={HttpUtility.UrlEncode(path)}" + + $"{(permanently != false ? $"&permanently=true" : "")}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}", + "DELETE").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Удаление файла или папки. + /// + /// Удалять файлы и папки на Диске пользователя можно, указывая путь к удаляемому ресурсу. Помните, что перемещение ресурсов в Корзину никак не влияет на доступное место на Диске. Чтобы освободить место, следует также удалять ресурсы из Корзины. + /// Путь к новому положению ресурса. + /// Признак безвозвратного удаления. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Возвращает ссылку на мета-информацию о созданном ресурсе для пустой папки или файла. Непустая папка может перемещаться в течение произвольного времени, поэтому приложения должны самостоятельно следить за статусами запрошенных операций. + public async Task DeleteResourceAsync(string path, bool permanently = false, IEnumerable fields = null) + { + return await Task.Run(() => DeleteResource(path, permanently, fields)); + } + + /// + /// Создание папки. + /// + /// Создавать папки на Диске можно, указывая требуемый путь к новой папке. + /// Путь к новому положению ресурса. + /// Список ключей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// В объекте , возвращается ссылка на мета-информацию о созданном ресурсе. + public Link CreateResource(string path, IEnumerable fields = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources?" + + $"path={HttpUtility.UrlEncode(path)}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}", + "PUT").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Создание папки. + /// + /// Создавать папки на Диске можно, указывая требуемый путь к новой папке. + /// Путь к новому положению ресурса. + /// Список ключей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// В объекте , возвращается ссылка на мета-информацию о созданном ресурсе. + public async Task CreateResourceAsync(string path, IEnumerable fields = null) + { + return await Task.Run(() => CreateResource(path, fields)); + } + + /// + /// Публикация файла или папки. + /// + /// Ресурс становится доступен по прямой ссылке. + /// Путь к публикуемому ресурсу. + /// Возвращает ссылку на мета-информацию о закрытом ресурсе в объекте . + public Link PublishResource(string path) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/publish?" + + $"path={HttpUtility.UrlEncode(path)}", + "PUT").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Публикация файла или папки. + /// + /// Ресурс становится доступен по прямой ссылке. + /// Путь к публикуемому ресурсу. + /// Возвращает ссылку на мета-информацию о закрытом ресурсе в объекте . + public async Task PublishResourceAsync(string path) + { + return await Task.Run(() => PublishResource(path)); + } + + /// + /// Закрытие доступа к ресурсу. + /// + /// Ресурс теряет атрибуты public_key и public_url, публичные ссылки на него перестают работать. + /// Путь к закрываемому ресурсу. + /// Возвращает ссылку на мета-информацию о закрытом ресурсе в объекте . + public Link UnpublishResource(string path) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/unpublish?" + + $"path={HttpUtility.UrlEncode(path)}", + "PUT").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Закрытие доступа к ресурсу. + /// + /// Ресурс теряет атрибуты public_key и public_url, публичные ссылки на него перестают работать. + /// Путь к закрываемому ресурсу. + /// Возвращает ссылку на мета-информацию о закрытом ресурсе в объекте . + public async Task UnpublishResourceAsync(string path) + { + return await Task.Run(() => UnpublishResource(path)); + } + + /// + /// Список опубликованных ресурсов. + /// + /// Количество опубликованных файлов, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Тип ресурса. + /// Список возвращаемых атрибутов. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Возвращает метаинформацию о запрошенном количестве файлов в теле ответа, в объекте . + public ResourceList ListPublicResources(int limit = 20, int offset = 0, string type = null, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + List query = new List(); + + if (limit != 20) + query.Add($"limit={limit.ToString()}"); + if (offset != 0) + query.Add($"offset={offset.ToString()}"); + if (type != null) + query.Add($"type={string.Join(", ", type)}"); + if (fields != null) + query.Add($"fields={string.Join(",", fields)}"); + if (previewSize != null) + query.Add($"preview_size={previewSize}"); + if (previewCrop != false) + query.Add($"preview_crop={previewCrop.ToString()}"); + + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/public{(query.Count > 0 ? $"?{string.Join("&", query)}" : null)}", + "GET").GetJsonTextReader()) + return new ResourceList(jsonReader); + } + + /// + /// Список опубликованных ресурсов. + /// + /// Количество опубликованных файлов, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Тип ресурса. + /// Список возвращаемых атрибутов. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Возвращает метаинформацию о запрошенном количестве файлов в теле ответа, в объекте . + public async Task ListPublicResourcesAsync(int limit = 20, int offset = 0, string type = null, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + return await Task.Run(() => ListPublicResources(limit, offset, type, fields, previewSize, previewCrop)); + } + + /// + /// Метаинформация о публичном ресурсе. + /// + /// Ключ опубликованного ресурса или публичная ссылка на ресурс. + /// Относительный путь к ресурсу внутри публичной папки. + /// Атрибут, по которому сортируется список ресурсов, вложенных в папку. + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Список ключей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Возвращает метаинформацию о запрошенном ресурсе в теле ответа, в объекте . + public ResourceList GetPublicResource(string publicKey, string path = null, string sort = null, int limit = 20, int offset = 0, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/public/resources?" + + $"public_key={HttpUtility.UrlEncode(publicKey)}" + + $"{(path != null ? $"&path={HttpUtility.UrlEncode(path)}" : null)}" + + $"{(sort != null ? $"&sort={sort}" : null)}" + + $"{(limit != 20 ? $"&limit={limit}" : null)}" + + $"{(offset != 0 ? $"&offset={offset}" : null)}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}" + + $"{(previewSize != null ? $"&preview_size={previewSize}{(previewCrop != false ? $"&preview_crop={previewCrop.ToString()}" : null)}" : "")}", + "GET").GetJsonTextReader()) + return new ResourceList(jsonReader); + } + + /// + /// Метаинформация о публичном ресурсе. + /// + /// Ключ опубликованного ресурса или публичная ссылка на ресурс. + /// Относительный путь к ресурсу внутри публичной папки. + /// Атрибут, по которому сортируется список ресурсов, вложенных в папку. + /// Количество ресурсов, вложенных в папку, описание которых следует вернуть в ответе (например, для постраничного вывода). + /// Количество вложенных ресурсов с начала списка, которые следует опустить в ответе (например, для постраничного вывода). + /// Список ключей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Требуемый размер уменьшенного изображения (превью файла), ссылка на которое API возвращает в поле . + /// Параметр позволяет обрезать превью согласно размеру, заданному в значении параметра . + /// Возвращает метаинформацию о запрошенном ресурсе в теле ответа, в объекте . + public async Task GetPublicResourceAsync(string publicKey, string path = null, string sort = null, int limit = 20, int offset = 0, IEnumerable fields = null, string previewSize = null, bool previewCrop = false) + { + return await Task.Run(() => GetPublicResource(publicKey, path, sort, limit, offset, fields, previewSize, previewCrop)); + } + + /// + /// Скачивание публичного файла или папки. + /// + /// Ресурс, опубликованный на Диске, можно скачать, зная его ключ или публичную ссылку на него. Из публичных папок также можно скачивать отдельные файлы. + /// Ключ сохраняемого ресурса. + /// Путь к скачиваемому файлу. Следует указать, если в значении параметра передан ключ публичной папки, в которой находится нужный файл. + /// Возвращает сгенерированный URL для скачивания файла в объекте + public Link GetPublicResourceDownloadLink(string publicKey, string path = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/resources/download?" + + $"public_key={HttpUtility.UrlEncode(publicKey)}" + + $"{(path != null ? $"&path={path}" : "")}", + "GET").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Скачивание публичного файла или папки. + /// + /// Ресурс, опубликованный на Диске, можно скачать, зная его ключ или публичную ссылку на него. Из публичных папок также можно скачивать отдельные файлы. + /// Ключ сохраняемого ресурса. + /// Путь к скачиваемому файлу. Следует указать, если в значении параметра передан ключ публичной папки, в которой находится нужный файл. + /// Возвращает сгенерированный URL для скачивания файла в объекте + public async Task GetPublicResourceDownloadLinkAsync(string publicKey, string path = null) + { + return await Task.Run(() => GetPublicResourceDownloadLink(publicKey, path)); + } + + /// + /// Сохранение публичного файла в «Загрузки» + /// + /// Файл, опубликованный на Диске, можно скопировать в папку «Загрузки» на Диске пользователя. Для этого нужно знать ключ файла или публичную ссылку на него. Также можно копировать отдельные файлы из публичной папки. + /// Ключ сохраняемого файла. + /// Имя, под которым файл следует сохранить в папку «Загрузки». + /// Путь к скачиваемому файлу. Следует указать, если в значении параметра передан ключ публичной папки, в которой находится нужный файл. + /// Путь к папке, в которую будет сохранен ресурс. По умолчанию «Загрузки». + /// Скачивание файла может занять неопределенное время. Если операция скачивания была запущена, API отвечает ссылкой на статус операции в объекте . + public Link SaveToDiskPublicResource(string publicKey, string name, string path = null, string savePath = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/public/resources/save-to-disk/?" + + $"public_key={HttpUtility.UrlEncode(publicKey)}" + + $"{(name != null ? $"&name={HttpUtility.UrlEncode(name)}" : "")}" + + $"{(path != null ? $"&path={HttpUtility.UrlEncode(path)}" : "")}" + + $"{(savePath != null ? $"&save_path={HttpUtility.UrlEncode(savePath)}" : "")}", + "POST").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Сохранение публичного файла в «Загрузки» + /// + /// Файл, опубликованный на Диске, можно скопировать в папку «Загрузки» на Диске пользователя. Для этого нужно знать ключ файла или публичную ссылку на него. Также можно копировать отдельные файлы из публичной папки. + /// Ключ сохраняемого файла. + /// Имя, под которым файл следует сохранить в папку «Загрузки». + /// Путь к скачиваемому файлу. Следует указать, если в значении параметра передан ключ публичной папки, в которой находится нужный файл. + /// Путь к папке, в которую будет сохранен ресурс. По умолчанию «Загрузки». + /// Скачивание файла может занять неопределенное время. Если операция скачивания была запущена, API отвечает ссылкой на статус операции в объекте . + public async Task SaveToDiskPublicResourceAsync(string publicKey, string name, string path = null, string savePath = null) + { + return await Task.Run(() => SaveToDiskPublicResource(publicKey, name, path, savePath)); + } + + /// + /// Очистка Корзины. + /// + /// Файлы, перемещенные в Корзину, можно окончательно удалить. Корзина считается папкой на Диске, поэтому доступное на Диске место при этом увеличивается. Чтобы удалить из Корзины отдельный файл, можно указать путь к нему в запросе очистки. + /// Путь к удаляемому ресурсу относительно корневого каталога Корзины. Если параметр не задан, Корзина очищается полностью. + /// Очистка Корзины может занять неопределенное время. Яндекс.Диск возвращает ссылку на статус запущенной по запросу операции в объекте . + public Link ClearTrash(string path = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/trash/resources/{(path != null ? $"?path={HttpUtility.UrlEncode(path)}" : null)}", + "DELETE").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Очистка Корзины. + /// + /// Файлы, перемещенные в Корзину, можно окончательно удалить. Корзина считается папкой на Диске, поэтому доступное на Диске место при этом увеличивается. Чтобы удалить из Корзины отдельный файл, можно указать путь к нему в запросе очистки. + /// Путь к удаляемому ресурсу относительно корневого каталога Корзины. Если параметр не задан, Корзина очищается полностью. + /// Очистка Корзины может занять неопределенное время. Яндекс.Диск возвращает ссылку на статус запущенной по запросу операции в объекте . + public async Task ClearTrashAsync(string path = null) + { + return await Task.Run(() => ClearTrash(path)); + } + + /// + /// Восстановление файла или папки из Корзины. + /// + /// Перемещенный в Корзину ресурс можно восстановить на прежнем месте, указав путь к нему в корзине. Восстанавливаемый ресурс при этом можно переименовать. Если восстанавливаемый файл находился внутри папки, которая отсутствует на момент запроса, папка с таким именем будет создана в нужном месте. + /// Путь к восстанавливаемому ресурсу относительно корневого каталога Корзины. + /// Новое имя восстанавливаемого ресурса. + /// Признак перезаписи. Учитывается, если ресурс восстанавливается в папку, в которой уже есть ресурс с таким именем. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Восстановление ресурса из Корзины может занять неопределенное время. Возвращает ссылку на мета-информацию о созданном ресурсе в теле ответа, в объекте . + public Link RestoreFromTrash(string path, string name, bool overwrite = false, IEnumerable fields = null) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/trash/resources/restore?" + + $"path={HttpUtility.UrlEncode(path)}" + + $"{(name != null ? $"&name={name}" : "")}" + + $"{(overwrite != false ? $"&overwrite=true" : "")}" + + $"{(fields != null ? $"&fields={string.Join(",", fields)}" : "")}", + "PUT").GetJsonTextReader()) + return new Link(jsonReader); + } + + /// + /// Восстановление файла или папки из Корзины. + /// + /// Перемещенный в Корзину ресурс можно восстановить на прежнем месте, указав путь к нему в корзине. Восстанавливаемый ресурс при этом можно переименовать. Если восстанавливаемый файл находился внутри папки, которая отсутствует на момент запроса, папка с таким именем будет создана в нужном месте. + /// Путь к восстанавливаемому ресурсу относительно корневого каталога Корзины. + /// Новое имя восстанавливаемого ресурса. + /// Признак перезаписи. Учитывается, если ресурс восстанавливается в папку, в которой уже есть ресурс с таким именем. + /// Список полей, которые следует включить в ответ. Ключи, не указанные в этом списке, будут отброшены при составлении ответа. Если параметр не указан, ответ возвращается полностью, без сокращений. + /// Восстановление ресурса из Корзины может занять неопределенное время. Возвращает ссылку на мета-информацию о созданном ресурсе в теле ответа, в объекте . + public async Task RestoreFromTrashAsync(string path, string name, bool overwrite = false, IEnumerable fields = null) + { + return await Task.Run(() => RestoreFromTrash(path, name, overwrite, fields)); + } + + /// + /// Получить статус асинхронной операции. + /// + /// Идентификатор операции. Возвращается в составе URL запроса, если запрошенная операция может занять неопределенное время. + /// Если запрос был обработан без ошибок, API возвращает статус операции в теле ответа, в объекте . + public Operation GetOperationStatus(string operationId) + { + using (var jsonReader = CreateRequest($"https://cloud-api.yandex.net/v1/disk/trash/resources/restore?" + + $"operation_id={operationId}", + "GET").GetJsonTextReader()) + return new Operation(jsonReader); + } + + /// + /// Получить статус асинхронной операции. + /// + /// Идентификатор операции. Возвращается в составе URL запроса, если запрошенная операция может занять неопределенное время. + /// Если запрос был обработан без ошибок, API возвращает статус операции в теле ответа, в объекте . + public async Task GetOperationStatusAsync(string operationId) + { + return await Task.Run(() => GetOperationStatus(operationId)); + } + + #endregion + + } +} diff --git a/YandexDiskSharp/Type.cs b/YandexDiskSharp/Type.cs new file mode 100644 index 0000000..595ca02 --- /dev/null +++ b/YandexDiskSharp/Type.cs @@ -0,0 +1,17 @@ +namespace YandexDiskSharp +{ + /// + /// Тип ресурса. + /// + public enum Type + { + /// + /// Папка. + /// + dir, + /// + /// Файл. + /// + file + } +} diff --git a/YandexDiskSharp/Utilities/Extensions.cs b/YandexDiskSharp/Utilities/Extensions.cs new file mode 100644 index 0000000..f332ae3 --- /dev/null +++ b/YandexDiskSharp/Utilities/Extensions.cs @@ -0,0 +1,30 @@ +using Newtonsoft.Json; +using System.IO; +using System.Net; + +namespace YandexDiskSharp.Utilities +{ + internal static class Extensions + { + public static JsonTextReader GetJsonTextReader(this HttpWebRequest request) + { + try + { + return new JsonTextReader(new StreamReader(request.GetResponse().GetResponseStream())) + { + CloseInput = true + }; + } + catch (WebException ex) + { + using (var jsonReader = new JsonTextReader(new StreamReader(ex.Response.GetResponseStream())) { CloseInput = true }) + throw new DiskException(new Models.Exception(jsonReader), ex, ex.Status, ex.Response); + } + catch (System.Exception ex) + { + throw ex; + } + } + + } +} diff --git a/YandexDiskSharp/YandexDiskSharp.csproj b/YandexDiskSharp/YandexDiskSharp.csproj new file mode 100644 index 0000000..fc768ae --- /dev/null +++ b/YandexDiskSharp/YandexDiskSharp.csproj @@ -0,0 +1,68 @@ + + + + + Debug + AnyCPU + {FE0B453D-1E3B-4AB6-BBAD-F6F973356897} + Library + Properties + YandexDiskSharp + YandexDiskSharp + v4.5 + 512 + + + + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + bin\Debug\YandexDiskSharp.xml + + + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + + ..\packages\Newtonsoft.Json.10.0.2\lib\net45\Newtonsoft.Json.dll + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/YandexDiskSharp/packages.config b/YandexDiskSharp/packages.config new file mode 100644 index 0000000..c809207 --- /dev/null +++ b/YandexDiskSharp/packages.config @@ -0,0 +1,4 @@ + + + + \ No newline at end of file