Надежное хранение секретных данных в клиентском веб-приложении

11

У меня есть это веб-приложение, которое будет полностью на стороне клиента (HTML, CSS, JavaScript / AngularJS и т. Д.). Это веб-приложение будет взаимодействовать с REST API для доступа и изменения данных. В настоящее время неясно, какой тип системы аутентификации будет использовать REST API.

Насколько я понимаю, любой тип системы аутентификации API (API Keys, OAuth 1/2 и т. Д.) Будет иметь определенные данные, которые должны храниться в секрете, иначе доступ может быть скомпрометирован. Для API-ключей сами ключи должны быть секретными, для OAuth 2 секретные / клиентские токены / токены обновления должны храниться в секрете, я уверен, что некоторые из 4 ключей, задействованных в OAuth 1, должны храниться в секрете (не слишком много опыта с OAuth 1). Я пытался подумать, есть ли способ сохранить этот секретный материал в чистом клиентском веб-приложении без каких-либо промежуточных уровней на стороне сервера.

Я пытался думать об этом, и я не могу думать ни о каком месте, чтобы сделать это. Я имею в виду, что не могу сохранить его в javascript, потому что любой может просто просмотреть исходный код или открыть консоль и получить данные. Я не уверен на 100%, насколько безопасен localStorage и могут ли пользователи получать доступ к этим данным или изменять их. Даже если локальное хранилище было безопасным, два способа ввода данных в него - нет. Один из способов - просто сохранить данные в исходном коде javascript, и это самая небезопасная вещь, о которой я только могу подумать. Теперь, если бы я использовал что-то наподобие OAuth 2, в котором остальные API-интерфейсы давали бы мне токены, это все равно было бы небезопасно (лучше, чем первый вариант), потому что эти токены были бы возвращены в виде простого текста, который любой, кто может видеть запросы, которые делает компьютер, могли видеть.

Есть ли способ, чтобы приложение, полностью работающее на стороне клиента, могло безопасно хранить секретные фрагменты данных без какого-либо промежуточного уровня на стороне сервера?

ryanzec
источник
Связанный: stackoverflow.com/q/7847121/421245 , stackoverflow.com/q/2256305/421245
Майк Партридж
Localstorage зависит от браузера, но, взяв в качестве примера Opera для Windows, это всего лишь некоторые файлы на диске в папке профиля пользователя, поэтому он практически не защищен.
Росс Паттерсон
Одним из способов было бы сохранить секрет на сервере в БД и иметь только application_id на клиенте. Затем выполните запрос oauth с сервера, так что это своего рода прокси-подход.
Симон Полак

Ответы:

9

Нет, это никогда не может быть абсолютно безопасно. Пользователь контролирует аппаратное обеспечение, а вы пытаетесь держать что-то в его руках. В конечном счете, они МОГУТ получить это тем или иным способом. Поскольку вы работаете из javascript, ваше положение НАМНОГО хуже, чем у обычного компьютерного приложения, поскольку пользователь не только контролирует аппаратное обеспечение, но и песочницу, в которой вы работаете.

Вы можете прятать вещи и мешать им добраться до вещей, но, в конце концов, они МОГУТ вывести это, если будут стараться.

Майкл Кон
источник
4
^ это. Насколько «секретными» являются секретные данные и сколько времени и денег они защищают? Усилия "отраслевого стандарта" могут быть достаточными.
Дэйв
+1 Отличный ответ. С помощью отладчика JavaScript я могу изменить ваше приложение, просмотреть промежуточные значения и т. Д. Если мне понадобится информация, я ее получу.
Росс Паттерсон
2

При проектировании систем безопасности всегда нужно думать о модели угроз. « Сделать это безопасным » - глупое требование, не подлежащее действию или проверке. « Запретить пользователю извлекать токены доступа из приложения » гораздо лучше и определяет границы решения. « Запретить другим доступ к токенам пользователя » также лучше и определяет совершенно другое пространство решений. Решения для одного не обязательно решат другое ( например , последний обязательно требует SSL, если включен WiFi, но это никак не повлияет на первое).

Росс Паттерсон
источник
0

одним из вариантов является предоставление REST API доступа или не на основании имени пользователя; он может вернуть основанный на сеансе токен (guid, хэшированную строку, что угодно), который можно передать другим вызовам API REST для аутентификации доступа

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

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

Стивен А. Лоу
источник
Что касается причин, всегда есть «комфорт», который, очевидно, является заклятым врагом «безопасности» и «безопасности».
Хенон