
Все началось с того, что я захотел сделать канал в инстаграме потратив на поиски и тесты сервисов авто публикаций целый день, далее я решил посмотреть на готовые пакеты гитхаба я удивился на размер кода этих пакетов (некоторые фреймворки php меньше чем эти обертки над инстаграмом), я плюнул и решил написать свою обертку с минимальными возможностями.
Авторизация
Авторизацию будем проходить через WEB версию. Для этого нам понадобится с начало получить заголовки, куки.
/** Отправляем GET запрос на https://www.instagram.com**/ $curl = curl_init(); curl_setopt_array($curl, [ CURLOPT_URL => 'https://www.instagram.com/', CURLOPT_HEADER => true, CURLOPT_SSL_VERIFYHOST => false, CURLOPT_SSL_VERIFYPEER => false, CURLOPT_RETURNTRANSFER => true, CURLINFO_HEADER_OUT => true, CURLOPT_HTTPHEADER => ['user-agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.130 Safari/537.36'], ]); $response = curl_exec($curl); $headers = curl_getinfo($curl); /** обрезаем лишнее из headers **/ $header_content = substr($response, 0, $headers['header_size']); curl_close($curl); /** Для нас важен кукис csrftoken</b>, его мы устанавливаем в header x-csrftoken для дальнейшего запроса авторизации. Парсим куки: **/ $cookie = []; preg_match_all("/Set-Cookie:\s*(?<cookie>[^=]+=[^;]+)/mi", $header_content, $matches); foreach ($matches['cookie'] as $c) { if ($c = str_replace(['sessionid=""', 'target=""'], '', $c)) { $c = explode('=', $c); $cookie = array_merge($cookie, [trim($c[0]) => trim($c[1])]); } } if (isset($cookie['csrftoken']) { /** проверяем вернул установил нам инстаграм кукис csrftoken если нет куки возможно ваш IP или Прокси в черных списках. **/ }
Дальше я не буду приводить примеры с работой CURL.
Авторизация:
/** отправляем POST запрос на https://www.instagram.com/accounts/login/ajax/ **/ POST https://www.instagram.com/accounts/login/ajax/ HEADER Content-Type: application/x-www-form-urlencoded /** id app можно взять из заголовков инстаграм (не стал искать каким хуком он ставится) он всегда один и тот же **/ x-ig-app-id: 1217981644879628 x-csrftoken: /** полученный ранее кукис csrftoken **/ cookie: /** Все полученные куки ранее **/ user-agent: /** установленный ранее **/ BODY username=/** логин инстаграм **/&password=/** пароль инстаграм **/&queryParams={}&optIntoOneTap=false /** Если запрос прошел удачно и мы Авторизовались ответ json, сохраняем куки которые вернул нам сервер и userId **/ {"authenticated": true, "user": true, "userId": "****", "loginNonce": "****", "reactivated": true, "status": "ok"} /** Если неверный логин или пароль ответ json **/ {"authenticated": false, "user": true, "status": "ok"} /** В любых других случаях если ответ не в формате json и присутствуют редиректы (вы что то делаете не так) **/
Поиск пользователей
Для этого нам потребуются ранее полученные куки и заголовок x-csrftoken.
/** отправляем POST запрос на https://www.instagram.com/web/search/topsearch/ **/ GET https://www.instagram.com/web/search/topsearch/?context=blended&query={ключ поиска}&rank_token={рандомное число 0.87979}&include_ree=true HEADER x-csrftoken: /** полученный ранее кукис csrftoken **/ x-ig-app-id: 1217981644879628 cookie: /** Все полученные куки ранее **/ user-agent: /** установленный ранее **/ /** Ответ от сервера **/ { "users": [ {"position":0, "user":{ "pk":"ид пользователя" "username":"логин в инстаграм" "full_name":"Имя Фамилия, если установлены" ..... и еще куча всего } },{},{} ], "places":[публикации по месту положения], "hashtags":[публикации с хештагеми], "has_more": true, "rank_token": "0.44093530619864296", "clear_client_cache": false, "status: "ok" }
Отправка сообщений в direct
Для отправки сообщений в директ нам потребуются id юзеров кому будем отправлять, как найти пользователей я описал выше.
/** Отправляем POST запрос на api instagram **/ POST https://i.instagram.com/api/v1/direct_v2/threads/broadcast/text/ HEADER /** юзер агент обязательно используем мобильного устройства **/ user-agent: Instagram 10.2.2 Android (18/4.3; 320dpi; 720x1280; Huawei; HWEVA; EVA-L18; qcom; en_US) x-csrftoken: /** полученный ранее кукис csrftoken **/ x-ig-app-id: 1217981644879628 cookie: /** Все полученные куки ранее **/ content-type: application/x-www-form-urlencoded BODY text={текст сообщения}&_uuid=&_csrftoken={полученный ранее кукис csrftoken}&recipient_users="[[ид пользоветелей через запятую]]"&action=send_item&thread_ids=["0"]&client_context={UUID v4 без дефиса} /** Успешный ответ Ответ от сервера **/ {"status":"ok", "payload":{"item_id":"номер чата"} ...} /** пример генерации UUID v4 **/ function uuid4() { if (function_exists('com_create_guid') === true) { return trim(com_create_guid(), '{}'); } $data = openssl_random_pseudo_bytes(16); $data[6] = chr(ord($data[6]) & 0x0f | 0x40); $data[8] = chr(ord($data[8]) & 0x3f | 0x80); return vsprintf('%s%s%s%s%s%s%s%s', str_split(bin2hex($data), 4)); }
Загрузка фотографий через WEB версию
Перед отправкой изображений нужно их сохранить в ImageJPEG качество 100 иначе инстаграм вернет ошибку:
$photo = __DIR__ . '/source.jpg'; $file_temp = __DIR__ . '/send_images.jpg'; list($width, $height, $image_type) = getimagesize(realpath($photo)); $srcImage = ImageCreateFromJPEG($photo); $resImage = ImageCreateTrueColor($width, $height); ImageCopyResampled($resImage, $srcImage, 0, 0, 0, 0, $width, $height, $width, $height); ImageJPEG($srcImage, $file_temp, 100); ImageDestroy($srcImage);
Загружаем фото:
/** Для загрузки изображения нужно отправить POST запрос **/ /** $microtime получаем время в microtime это будет наш id photo **/ $microtime = round(microtime(true) * 1000); POST https://www.instagram.com/rupload_igphoto/fb_uploader_' . $microtime HEADER content-type: image/jpg x-entity-name: 'fb_uploader_' . $microtime /** id photo **/ offset: 0 user-agent: Mozilla/5.0 (iPhone; CPU iPhone OS 11_4_1 like Mac OS X; ru-RU) AppleWebKit/537.36 (KHTML, like Gecko) Version/11.4.1 Mobile/15G77 Safari/537.36 Puffin/5.2.2IP x-entity-length: filesize($file_temp) /** Размер фото **/ x-instagram-rupload-params: {"media_type":1,"upload_id":"' . $microtime . '","upload_media_height":' . $height . ',"upload_media_width":' . $width . '} x-csrftoken: /** полученный ранее кукис csrftoken **/ x-ig-app-id: 1217981644879628 cookie: /** Все полученные куки ранее **/ BODY /** Без параметров, в body должно быть только фото **/ file_get_contents(realpath($file_temp)) /** Успешный ответ от сервера json **/ {"upload_id":"наш ид фото $microtime", "status":"ok" ...} /** На этом еще не все, мы только загрузили фото теперь его надо опубликовать: **/ POST https://www.instagram.com/create/configure/ HEADER content-type: application/x-www-form-urlencoded user-agent: Mozilla/5.0 (iPhone; CPU iPhone OS 11_4_1 like Mac OS X; ru-RU) AppleWebKit/537.36 (KHTML, like Gecko) Version/11.4.1 Mobile/15G77 Safari/537.36 Puffin/5.2.2IP x-csrftoken: /** полученный ранее кукис csrftoken **/ x-ig-app-id: 1217981644879628 cookie: /** Все полученные куки ранее **/ BODY upload_id=$microtime&caption={текст, хештеги}&usertags=&custom_accessibility_caption=&retry_timeout= /** Успешный ответ от сервера в json должен содержать */ {"status":"ok", "media":{"id":"***", ...}}
На этом все, я реализовал минимальную обертку над instagram.
Полностью рабочую версию я выложил на github.Буду рад услышать про реализацию возможно что то я не так сделал.