Предотвращение прямого доступа к файлу, вызываемому функцией ajax

Я вызываю php-код из ajax следующим образом:

ajaxRequest.open("GET", "func.php" + queryString, true); 

Поскольку это запрос на получение, любой может видеть это, просто изучая заголовки. Передаваемые данные нечувствительны, но их потенциально можно злоупотреблять, так как также тривиально получить имена параметров.

Как предотвратить прямой доступ к http: //mysite/func.php, но разрешить доступ к моей странице ajax?

Также я пробовал решение, размещенное здесь, но оно не работает для меня – всегда получайте сообщение «Недоступный доступ».

Большинство запросов / фреймворков Ajax должны устанавливать этот конкретный заголовок, который вы можете использовать для фильтрации запросов Ajax v Non-ajax. Я использую это, чтобы определить тип ответа (json / html) в большом количестве проектов:

 if( isset( $_SERVER['HTTP_X_REQUESTED_WITH'] ) && ( $_SERVER['HTTP_X_REQUESTED_WITH'] == 'XMLHttpRequest' ) ) { // allow access.... } else { // ignore.... } 

edit: Вы можете добавить это самостоятельно в свои собственные запросы Ajax со следующим кодом javascript:

 var xhrobj = new XMLHttpRequest(); xhrobj.setRequestHeader("X-Requested-With", "XMLHttpRequest"); 

то, что я использую: PHP-сессии + хэш, который отправляется каждый раз, когда я делаю запрос. Этот хэш генерируется с использованием некоторого алгоритма на стороне сервера

Mmm … вы можете создать одноразовый пароль при запуске сеанса, который вы могли бы сохранить в _SESSION, и добавить параметр к вашему вызову ajax, который будет повторно передавать это (что-то вроде captcha). Это было бы справедливо только для этой сессии.

Это защитит вас от автоматических атак, но человек, имеющий доступ к вашему сайту, все равно может сделать это вручную, но это может быть основой для разработки чего-то более сложного.

Я бы поставил под вопрос, почему вы так убеждены, что никто не должен иметь возможность напрямую посетить этот файл. Ваше первое действие действительно должно состоять в том, чтобы предположить, что люди могут напрямую посетить страницу и действовать по этому поводу. Если вы все еще уверены, что хотите закрыть доступ к этому файлу, вы должны знать, что вы не можете доверять переменным $_SERVER для этого, так как истоки $_SERVER могут быть трудными для определения, а значения заголовков могут быть подделаны. В некоторых тестах я обнаружил, что эти заголовки ( $_SERVER['HTTP_X_REQUESTED_WITH'] & $_SERVER['HTTP_X_REQUESTED_WITH'] ) также ненадежны.

Любой в этой теме, который предложил посмотреть на заголовки, так или иначе ошибочен. Все, что содержится в запросе (HTTP_REFERER, HTTP_X_REQUESTED_WITH), может быть подделано злоумышленником, который не является полностью некомпетентным, включая общие секреты [1].

Вы не можете запретить пользователям отправлять HTTP-запрос на ваш сайт. То, что вы хотите сделать, это убедиться, что пользователи должны пройти аутентификацию, прежде чем отправлять запрос на какую-либо чувствительную часть вашего сайта, используя cookie сеанса. Если пользователь делает запросы без аутентификации, остановитесь прямо там и дайте им HTTP 403.

Ваш пример делает запрос GET, поэтому, я думаю, вы обеспокоены требованиями к ресурсу запроса [2]. Вы можете сделать некоторые простые проверки работоспособности в заголовках HTTP_REFERER или HTTP_X_REQUESTED_WITH в ваших правилах .htaccess, чтобы остановить появление новых процессов для явно поддельных запросов (или тупых поисковых искателей, которые не будут слушать robots.txt), но если злоумышленники подделывают тем вы захотите, чтобы ваш PHP-процесс завершался как можно раньше для неидентифицированных запросов.

[1] Это одна из основных проблем с клиентскими / серверными приложениями. Вот почему это не работает: скажите, что у вас есть способ для вашего клиентского приложения аутентифицироваться на сервере – будь то секретный пароль или какой-либо другой метод. Информация, необходимая для приложения, обязательно доступна для приложения (пароль скрыт где-то там или где угодно). Но поскольку он работает на компьютере пользователя, это означает, что они также имеют доступ к этой информации: все, что им нужно, – это посмотреть на источник, или на двоичный, или на сетевой трафик между вашим приложением и сервером, и в конечном итоге они выяснят механизм аутентификации вашего приложения и его тиражирование. Возможно, они даже скопируют его. Может быть, они напишут умный взломать, чтобы ваше приложение сильно поднялось (вы всегда можете просто отправить поддельный пользовательский ввод в приложение). Но как бы то ни было, у них есть вся необходимая информация, и нет способа остановить их от ее использования, что также не помешает вашему приложению иметь ее.

[2] Запросы GET в хорошо спроектированном приложении не имеют побочных эффектов, поэтому никто из них не сможет внести изменения на сервер. Ваши POST-запросы всегда должны быть аутентифицированы с помощью токена CESF, а также только для аутентифицированных пользователей. Если кто-то нападает на это, это означает, что у вас есть учетная запись, и вы хотите закрыть эту учетную запись.

Я решил эту проблему, готовя функцию проверки, которая делает три вещи

  1. check referer $ _SERVER ['HTTP_REFERER'];
  2. проверьте HTTP x request $ _SERVER ['HTTP_X_REQUESTED_WITH'];
  3. проверить происхождение через файл моста

если все три пройдут, вам удастся увидеть файл php, вызванный ajax, если только один из них не получается, вы не получите его

Точки 1 и 2 уже были объяснены, решение для файла моста работает так:

Файл моста

Иммунитет:

A.php вызов страницы через ajax B.php, и вы хотите предотвратить прямой доступ к B.php

  • 1) при загрузке страницы A.php генерирует сложный случайный код
  • 2) код копируется в файл C.txt, который напрямую не доступен из сети (httpd secure)
  • 3) в то же время этот код находится в ясной скульптуре в отображаемом html странице A.php (например, как атрибут body, es:

    Данные моста = «ehfwiehfe5435ubf37bf3834i»

  • 4) этот вылепленный код извлекается из javascript и отправляется через запрос ajax post на B.php

  • 5) Страница B.php получает код и проверяет, существует ли он в файле C.txt
  • 6) если код соответствует коду, выдается из C.txt и доступна страница B.php
  • 7) если код не отправлен (в случае, если вы пытаетесь напрямую получить доступ к странице B) или совсем не совпадают (в случае, если вы поставили старый код в ловушку или трюк с помощью специального кода), страница B.php умирает.

Таким образом, вы можете получить доступ к странице B только через вызов ajax, сгенерированный на странице с отцом A. Ключ для pageB.php предоставляется только и всегда из pageA.php

Основываясь на вашем описании, я предполагаю, что вы пытаетесь предотвратить прямое безудержное злоупотребление, но не нуждаетесь в прочном решении.

Из этого я бы предложил использовать файлы cookie:

Просто setcookie() на странице, использующей AJAX, и проверьте $_COOKIE за правильные значения на func.php. Это даст вам некоторую разумную уверенность в том, что кто-либо, вызывающий func.php, недавно посетил ваш сайт.

Если вы хотите стать более привлекательным, вы можете установить и проверить уникальные идентификаторы сеанса (вы можете это сделать уже) для гарантии того, что cookie не подделывается или не подвергается насилию.

Нет смысла делать это. Он не добавляет никакой реальной безопасности.

Все заголовки, указывающие, что запрос выполняется через Ajax (например, HTTP_X_REQUESTED_WITH ), могут быть HTTP_X_REQUESTED_WITH на стороне клиента.

Если ваш Ajax обслуживает конфиденциальные данные или разрешает доступ к конфиденциальным операциям, вам необходимо добавить надлежащую безопасность, например, систему входа в систему.

Поместите следующий код в самый верх вашего php-файла, который вызывается ajax. Он выполнит запросы ajax, но «умрет», если вызван непосредственно из браузера.

 define('AJAX_REQUEST', isset($_SERVER['HTTP_X_REQUESTED_WITH']) && strtolower($_SERVER['HTTP_X_REQUESTED_WITH']) == 'xmlhttprequest'); if(!AJAX_REQUEST) {die();} 

Лично я предпочитаю не выводить ничего после «die ()» в качестве дополнительной меры безопасности. Это означает, что я предпочитаю показывать только «пустую страницу» «злоумышленнику», а не давать подсказки, такие как «если» или «почему» эта страница защищена.

Я попробовал это

1) в основном php-файле (из которого отправлен запрос ajax) создать сеанс с некоторым случайным значением, например $_SESSION['random_value'] = 'code_that_creates_something_random'; Должен быть уверен, что сеанс создан выше $.post .

2), то

 $.post( "process_request.php", { input_data:$(':input').serializeArray(), random_value_to_check:'<?php echo htmlspecialchars( $_SESSION['random value'], ENT_QUOTES, "UTF-8"); ?>' }, function(result_of_processing) { //do something with result (if necessary) }); 

3) и в process_request.php

 if( isset($_POST['random_value_to_check']) and trim($_POST['random_value_to_check']) == trim($_SESSION['random value']) ){ //do what necessary } 

До того, как я определил сеанс, затем скрытое поле ввода со значением сеанса, затем значение скрытого поля ввода отправит с помощью ajax. Но потом решил, что скрытое поле ввода не нужно, потому что может отправить без него

Я пробовал много предложений, никто не решил проблему. Наконец, я защитил параметры целевого файла php, и это был единственный способ ограничить прямой доступ к файлу php. ** Puting php file и set limit by.htaccess вызвали сбой Ajax-соединения на главной странице Html.