Подтвердить что ты не робот

Как ограничить доступ JSON?

У меня есть веб-приложение, которое извлекает данные из моего недавно созданного API JSON.

Мои статические HTML-страницы динамически вызывают JSON API через JavaScript со статической HTML-страницы.

Как ограничить доступ к моему JSON API, чтобы только я (мой веб-сайт) мог вызывать его?

В случае, если это помогает, мой API-интерфейс примерно такой: http://example.com/json/?var1=x&var2=y&var3=z... который генерирует соответствующий JSON на основе запроса.

Я использую PHP для генерации моих результатов JSON... может ли ограничение доступа к JSON API быть таким же простым, как проверка $_SERVER['HTTP_REFERER'], чтобы гарантировать, что API только вызывается из моего домена, а не из удаленного пользователя?

4b9b3361

Ответ 1

Обычный способ ограничения доступа к вашему домену - это добавить содержимое к чему-то бесконечному.

Например:

while(1);{"json": "here"} // google uses this method
for (;;);{"json": "here"} // facebook uses this method

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

<script src="http://some.server/secret_api?..."></script>

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

Ответ 2

Я думаю, что вы можете не понимать ту часть, где запрос JSON инициируется из пользовательского браузера, а не из вашего собственного сервера. Статическая страница HTML доставляется в браузер пользователя, затем она поворачивается и выполняет код Javascript на странице. Этот код открывает новое соединение с сервером для получения данных JSON. С точки зрения PHP script запрос JSON поступает откуда-то из внешнего мира.

Учитывая описанный выше механизм, вы не можете сделать так, чтобы кто-либо не вызывал JSON API вне контекста вашей HTML-страницы.

Ответ 3

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

Итак, что мы можем сделать?

Определите слабость здесь:

http://www.example.com/json/getUserInfo.php?id=443

Теперь злоумышленник может легко запросить всю информацию о пользователе от 1 до 1.000.000 в цикле. Слабой точкой идентификаторов auto_increment является их линейность и что их легко угадать.

Решение: используйте нечисловые уникальные идентификаторы для ваших данных.

http://www.example.com/json/getUserInfo.php?userid=XijjP4ow

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

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

Ответ 4

Любое решение здесь будет несовершенным, если ваши статические страницы, использующие API, должны быть в общедоступном Интернете. Поскольку вы должны иметь возможность, чтобы клиентский браузер отправил запрос и удостоверился, что он может быть удостоен чести, возможно, для кого-либо, чтобы точно узнать, как вы формируете этот URL.

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

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

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

Ответ 5

Короткий ответ: любой, кто может получить доступ к страницам вашего сайта, также сможет получить доступ к вашему API.

Вы можете попытаться упростить использование вашего API, зашифровав его различными способами, но поскольку вам придется включать код JavaScript для дешифрования вывода вашего API, вы просто собираетесь настроить себя на гонку вооружений с любым, кто решает, что они хотят использовать ваш API с помощью других средств. Даже если вы используете краткосрочные ключи, определенный "атакующий" всегда может просто очистить ваш HTML (вместе с текущим ключом) непосредственно перед использованием API.

Если все, что вы хотите сделать, - это запретить другим веб-сайтам использовать ваш API на своих веб-страницах, тогда вы можете использовать заголовки Referrer, но имейте в виду, что не все браузеры отправляют Referrers (и некоторые прокси тоже стирают их!). Это означает, что вы хотите разрешить всем запросам отсутствие реферера, и это даст вам только частичную защиту. Кроме того, Referrers можно легко подделать, поэтому, если какой-либо другой сайт действительно хочет использовать ваш API, он всегда может просто обмануть браузер и получить доступ к вашему API со своих серверов.

Ответ 6

Извините, может быть, я ошибаюсь, но... можно ли это сделать с помощью HTTPS?

Вы можете (?) получить свой API через http s://example.com/json/? var1 = x & var2 = y, поэтому только аутентифицированный потребитель может получить ваши данные..

Ответ 7

Можете ли вы использовать аутентификацию на основе cookie? Мой опыт основан на аутентификации форм ASP.NET, но тот же подход должен быть жизнеспособным с PHP с небольшим кодом.

Основная идея заключается в том, что когда пользователь аутентифицируется через веб-приложение, cookie с зашифрованным значением возвращается в браузер клиента. Затем json api будет использовать этот файл cookie для проверки личности вызывающего.

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

Ответ 8

Извините, там нет DRM в Интернете: -)

Вы не можете рассматривать HTML как доверенный клиент. Это простой текст script интерпретируется на компьютерах других людей по своему усмотрению. Независимо от того, что вы разрешите своим "собственным" кодом JavaScript, вы разрешаете кому-либо. Вы даже не можете определить, как долго он "твой" с Greasemonkey и Firebug в дикой природе.

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

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