Приветствую, уважаемые форумчане! Чуть более суток просидел над решением одной задачи и к сожалению так и не смог найти правильного подхода. По-этому решил обратиться за помощью. При написании очередного парсера (PHP/CURL) столкнулся со следующей проблемой: Нужно получить картинку по URL-адресу, что как правило получалось без проблем, но, как оказалось, не в случае со следующим доменом. URL адрес картинки: https://www.cb01.uno/imgk/hunt_for_the_wilderpeople_subita_2016.jpg Сразу отмечу что на целевом сервере стоит защита от ddos атак (cloudFlare). Защиту я обошёл, спокойно получаю нужные мне страницы, что касается и самой картинки. Проблема заключается в том что если копировать картинку напрямую из браузера (ручками), то картинка успешно сохраняется и после чего успешно открывается. Пример: Когда же я картинку сохраняю с помощью CURL, то она также сохраняется, но в конечном результате, при открытии картинки, пишет что не удалось открыть картинку, поскольку она либо повреждена либо имеет слишком большой вес. Обычно после сохранения одной картинки через браузер и с помощью курла, при открытии их с помощью блокнота, я вижу абсолютно одинаковый текст, и соответственно и сами картинки открываются "на ура". В моём же случае, при сохранении картинки через браузер (успешное сохранение / размер 152кб.) и последующем открытии через блокнот я вижу в начале следующий текст: яШяа JFIF яю ;CREATOR: gd-jpeg v1.0 (using IJG JPEG v80), quality = 92 яЫ C При сохранении той же картинки с помощью CURL (неудачное сохранение / размер 228кб.) и последующем открытии через блокнот выдаёт в начале следующий текст: ÿØÿà JFIF ÿþ ;CREATOR: gd-jpeg v1.0 (using IJG JPEG v80), quality = 92 ÿÛ C Собственно говоря в глаза сразу бросается разница в кодировке. С помощью CURL я отправлял необходимые заголовки в всё тому подобное, но результат так и не изменился. Пожалуйста, поделитесь дельным советом, или в какую сторону копать дальше, или может как то сразу решить данную задачу. Спасибо за внимание!
Для решения этой задачи тебе подойдет PhantomJS. 1. Скачиваешь бинарку от сюда под свою OS. Альтернативно ты можешь установить PhantomJS на сервер, если такой имеется. 2. Допустим, если ты выбрал для Windows, то скачиваешь архив, вытаскиваешь phantomjs.exe из bin директории и кладешь в любую папку, куда ты будешь сохранять картинки (допустим в D:\dev\). 3. Далее внутри этой директории создаешь файл film.js и добавляешь туда следующее: Code: var antoligy = antoligy || {}; /** * Simple wrapper to retrieve Cloudflare's 'solved' cookie. * @type {Object} */ antoligy.cloudflareChallenge = { webpage: false, system: false, page: false, url: false, userAgent: false, /** * Initiate object. */ init: function() { this.webpage = require('webpage'); this.page = this.webpage.create(); this.system = require('system'); this.url = this.system.args[1]; this.userAgent = 'Mozilla/5.0 (Windows NT 6.3; rv:36.0) Gecko/20100101 Firefox/36.0'; this.timeout = 6000; }, /** * "Solve" Cloudflare's challenge using PhantomJS's engine. * @return {String} JSON containing our cookies. */ solve: function() { var self = this; self.page.settings.userAgent = this.userAgent; self.page.open(self.url, function(status) { self.page.viewportSize = { width: 1024, height: 900 }; try { setTimeout(function() { var res = self.page.evaluate(function() { var reImgName = /\/((...){1,})\.jpg/gi; var obj = { rect: document.getElementsByTagName('img')[0].getBoundingClientRect(), name: reImgName.exec( document.getElementsByTagName('img')[0].getAttribute('src').trim() ) }; return obj; }); var rect = res.rect; self.page.rect = { top: rect.top, left: rect.left, width: rect.width, height: rect.height }; self.page.viewportSize = { width: rect.width, height: rect.height}; var imgName = res.name[1].replace(/\/imgk|imgk/gi, ''); self.page.render("images/" + imgName + '.jpg'); phantom.exit(); }, self.timeout); } catch(e) { console.log('PhantomJS has unexpectable stopped working. Date: ' + new Date().toUTCString()); phantom.exit(); } }); } } /** * In order to carry on making requests, both user agent and IP address must what is returned here. */ antoligy.cloudflareChallenge.init(); antoligy.cloudflareChallenge.solve(); 4. С помощью Windows cmd заходишь в dev папку и пишешь следующее: "phantomjs film.js https://www.cb01.uno/imgk/hunt_for_the_wilderpeople_subita_2016.jpg" 5. Ждешь 6-7 сек и картинка должна находиться в папке images внутри dev папки. Повторяешь 4-5 шаги для скачивания нужных тебе картинок. Если ты хочешь соединить это все с PHP, то читай ссылку из первого шага, там все подробно описано как и что нужно делать. Update: Я случайно удалил первую версию моего ответа, переписал заново, теперь он выглядит немного по другому.
Спасибо за оперативную помощь. К сожалению сегодня у меня не получается проверить описанный выше метод. Завтра буду тестировать. Думаю если можно запустить из командной строки, то свяжу с PHP через функцию exec(). Благо ресурсы позволяют. Как проверю - отпишу по результатам.
Если сервер есть, то супер, потому что можете установить PhantomJS прямо на сервер (в первом шаге подробно написано как его установить) и запускать через exec(), shell_exec(), как угодно Думаю, что про парсинг с CURL вы забудете после использоваться этой библиотеки Будите чисто для API запросов его использовать
Сделал всё поэтапно как вы и описывали вsше. Заняло времени не более пяти минут. Тестировал на Windows. Запустил PHP скрипт с командой exec('C:\OpenServer\domains\cb01.local\phantomjs film.js https://www.cb01.uno/imgk/mercy_2016.jpg?x76134'); Всё работает замечательно - то что нужно. Еще раз спасибо. Единственный не критичный, но мне не совсем понятный момент: почему то большинство картинок сохраняются в папку 'images', но некоторые, как например https://www.cb01.uno/imgk/Il_peso_del_ricordo_1988.jpg?x76134 сохраняются в папку 'images/название_домена'. Интересно с чем это связано.
Не добавляйте "?x76134" для картинок, так как регулярка, которая получает название картинки для сохранения не расчитана на GET параметры из её ссылки. То есть когда пишите ссылку для картинки, после .jpg или .png не пишите GET параметры вообще, иначе может слететь скачивание. Или допишите регулярку так, чтобы она убирала эта параметры из ссылки и будет вам счастье. P.s. Для "Спасибо" есть кнопка "Одобрить"