Скриншоти і інші зображення можна зберігати в різних місцях. Я вже розказував про те, як можна завантажити зображення на сервери Telegra.ph, але відправивши туди зображення у нас немає можливості для його видалення у випадку такої необхідності. Тому, коли потрібно мати можливість видалення скриншота – зручно використовувати сервери imgbb.com.
Власне щоб завантажити зображення можна скористатись плагіном, веб версією чи API доступом. Але, це не завжди зручно, адже щоб просто відправити зображення в інтернет не хочеться додатково реєструвати аккаунт щоб одержати API ключ до imgbb.com, і встановлення додаткових плагінів чи скриптів собі на сайт, щоб користуватись веб версією – також не підходить (саме використання браузера використовує багато ресурсів оперативної пам’яті).
Тому приходиться викручуватись, а саме пробувати повторити HTTP запити до imgbb.com з відправкою туди зображення з метою одержати посилання на нього. Проте, зразу відправити зображення не получається, тому що запит потребує API ключа авторизації. І, якщо уважно подивитись в консолі розробника цей ключик находиться на головній сторінці. Тому, перший запит потрібно відправити на головну сторінку, і зберегти цей ключик.
Після чого вже можна відправити HTTP запит методом POST з форматуванням даних multipart/form-data, і одержати результат в JSON, з якого мені буде цікавим саме посилання на зображення і посилання на сторінку видалення зображення. Саме їх я буду зберігати додатково с текстовий файл, щоб в будь-який час мати можливість видалити потрібне зображення.
Також я замітив, що при відправці одного і того самого зображення – посилання виглядає ідентично, тобто не змінюється. Тому, щоб при завантаженні одного зображення декілька разів одержувати різні посилання я вирішив згенерувати ім’я файла.
Також, моє завдання заключається не в тому, щоб завантажувати саме картинки з файлів, а в тому, щоб я міг натиснути кнопку Print Screen на клавіатурі, а потім запустити на виконання проєкт, і в результаті в буфері обміну одержати посилання на зображення. Тому, я не буду зберігати скриншот у файлі, а зразу буду відправляти його на сервери imgbb.com і одержувати необхідне посилання на мій скриншот в інтернеті.
Ось фрагмент C# коду, який я використовую у своєму проєкті у тих випадках, коли мені потрібно відправити скриншот в інтернет і одержати на нього посилання в буфер обміну (одночасно дублюю посилання також в список разом із посиланням на видалення цього скриншота, щоб мати можливість видаляти його якщо появиться така необхідність):
// В GAS добавити потрібно System.Net.Http.dll string url = @"https://imgbb.com"; string proxy =string.Empty; // "127.0.0.1:8888"; string file_name = project.Profile.RegenerateLogin("[Lat|4][RndNum|1970|1990]") +".jpg"; string auth_token = Regex.Match(ZennoPoster.HttpGet(url), @"(?<=PF\.obj\.config\.auth_token="").*?(?="";)").Value; if(string.IsNullOrEmpty(auth_token)) throw new Exception("Відсутній токен авторизації"); // Тут я одержую скриншот з буферу обміну в масив байт byte[] data = new byte[0]; using(var img = System.Windows.Forms.Clipboard.GetImage()) { using (var m = new MemoryStream()) { try { img.Save(m, System.Drawing.Imaging.ImageFormat.Jpeg); data = m.ToArray(); } catch { project.SendWarningToLog("В буфері обміну немає зображення",true); } } } if(data.Length == 0) throw new Exception("Буфер не містить зображення"); // Тут я формую масив байт в дані multipart var bytes = new System.Net.Http.ByteArrayContent(data, 0, data.Length); bytes.Headers.ContentType = System.Net.Http.Headers.MediaTypeHeaderValue.Parse("image/jpg"); bytes.Headers.ContentDisposition = new System.Net.Http.Headers.ContentDispositionHeaderValue("form-data") { Name = "source", FileName = file_name }; // Власне формую всі необхідні поля multipart var sBoundary = DateTime.Now.Ticks.ToString("x"); var content = new MultipartFormDataContent(sBoundary); content.Add(bytes, "source"); content.Add(new StringContent("file"), "type"); content.Add(new StringContent("upload"), "action"); content.Add(new StringContent(string.Format(@"{0}",(int)(DateTime.UtcNow.Subtract(new DateTime(1970, 1, 1))).TotalSeconds)), "timestamp"); //content.Add(new StringContent("P6D"), "expiration"); //якщо не вказувати - зображення буде зберігатись максимальний термін content.Add(new StringContent(auth_token), "auth_token"); // Формую необхідні параметри для відправки зображення в інтернет url += "/json"; string content_type = string.Format("multipart/form-data;boundary={0}", sBoundary); byte[] multipart_byte = content.ReadAsByteArrayAsync().Result.ToArray(); var method = ZennoLab.InterfacesLibrary.Enums.Http.HttpMethod.POST; string encoding =Encoding.UTF8.WebName; var type = ZennoLab.InterfacesLibrary.Enums.Http.ResponceType.BodyOnly; string post = ZennoPoster.HTTP.Request( method: method, // метод яким буде відправлено запит url: url,// по якому адресу буде відправлено запит content: multipart_byte, // які дані буде відправляти запит contentPostingType: content_type, // який тип контенту буде відправляти запит proxy: proxy, // з якого IP відправляти запит Encoding: encoding, // в якому кодуванні відправляти запит respType: type, // в якому вигляді повернути результат Timeout: 180 * 1000, // скільки часу очікувати результат UseRedirect: false, // включити слідування переадресаціям MaxRedirectCount: 0, // слідувати php переадресаціям UseOriginalUrl: true, // не змінювати параметри запиту removeDefaultHeaders: true // видалення стандартних заголовків ); // З результату який прийде в JSON пробую витягнути необхідні посилання project.Json.FromString(post); string image_url = project.Json.image.url; string image_delete = project.Json.image.delete_url; // Добавляю результат в текстовий список, який прив'язаний до тектового файла, який находиться поряд з проєктом if(!string.IsNullOrEmpty(image_url)) { lock(SyncObjects.ListSyncer) project.Lists["list"].Add(string.Join("|", new[]{image_url, image_delete} )); System.Windows.Forms.Clipboard.SetText(image_url); // Добавляю посилання на скриншот в буфер обміну } // Дублюю посилання в лог ZennoPoster project.SendInfoToLog(image_url,true);
Тепер прямо в такому вигляді я добавляю собі проєкт в ZennoPoster і використовую його завжди, коли мені потрібно поділитись з кимось зображенням – я просто відправляю людині посилання на зображення.