HTTP-аутентификация на сервере разработки приложений - PullRequest
5 голосов
/ 25 августа 2009

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

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

Есть ли хороший способ решить эту проблему?

Ответы [ 4 ]

2 голосов
/ 24 мая 2012

Вот довольно солидная реализация, которую я придумал

В результате поиска я обнаружил множество небрежных / неполных реализаций BasicAuth для GAE в Интернете. В результате я написал свой собственный. Это самый лучший / самый простой подход, который мне удалось придумать.

Я считаю хорошей практикой сохранять обработчики запросов как можно более тонкими. Чтобы сократить количество шаблонов и копипаст в самих обработчиках, я решил реализовать аутентификацию в качестве декоратора. Чтобы использовать его, просто присоедините декоратор к методам обработчика get / post / put / delete.

Например:

from decorators import basic_auth

class Handler(webapp2.RequestHandler):
  @basic_auth
  def get(self):
    # load your page here

Затем добавьте декоратор в decorators.py:

import base64
import os
from webapp2_extras import security
import yaml

def basic_auth(func):
  def callf(webappRequest, *args, **kwargs):
    # Parse the header to extract a user/password combo.
    auth_header = webappRequest.request.headers.get('Authorization')
    # if the auth header is missing popup a login dialog
    if auth_header == None:
      __basic_login(webappRequest)
    else:
      (username, password) = base64.b64decode(auth_header.split(' ')[1]).split(':')
      if(__basic_lookup(username) == __basic_hash(password)):
        return func(webappRequest, *args, **kwargs)
      else:
        __basic_login(webappRequest)
  return callf

def __basic_login(webappRequest):
  webappRequest.response.set_status(401, message="Authorization Required")
  webappRequest.response.headers['WWW-Authenticate'] = 'Basic realm="Secure Area"'

def __basic_lookup(username):
  accounts_file = os.getcwd() + os.sep + 'app' + os.sep + 'accounts.yaml'
  stream = file(accounts_file, 'r')
  for account in yaml.load(stream):
    if account['username'] == username:
      return account['password']

def __basic_hash(password):
  return security.hash_password(password, method='sha1')

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

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

Код написан так, чтобы его можно было легко настроить:

  • Измените __ basic_lookup () , если вам нужно, чтобы ваши пароли хранились где-то еще (например, в базе данных).
  • Измените __ basic_hash () , если ваши пароли имеют открытый текст или кодируются другим способом.
  • Измените __ basic_login () , если вы хотите другой ответ на неудачную попытку входа в систему. Например, искусственная задержка для предотвращения атак методом перебора или перенаправление.
2 голосов
/ 25 августа 2009

Разверните приложение на серверах appengine, но используйте другой идентификатор приложения, чем тот, который вы в конечном итоге будете использовать на производстве. Таким образом, вам не нужно разрабатывать какой-либо дополнительный механизм аутентификации, и вам не нужно беспокоиться о том, насколько хорошо сервер приложений dev будет справляться с нагрузкой нескольких пользователей.

2 голосов
/ 25 августа 2009

Не делайте dev_appserver общедоступным. Это не предназначено для этого, и это не безопасно. Чтобы назвать только одну проблему, любой посетитель может перейти к yourhost / _ah / admin / и связываться с вашим хранилищем данных, и предложения по аутентификации по lost-теории не помешают этому.

Если вам абсолютно необходимо это сделать, настройте Apache или другой веб-сервер в качестве обратного прокси-сервера, реализуя аутентификацию и блокируя доступ к URL-адресам / _ah. Однако предложение Питера о развертывании его в App Engine гораздо лучше.

2 голосов
/ 25 августа 2009

Вы используете Java или Python?

Если вы используете Python, вы можете использовать существующее промежуточное ПО WSGI для обработки базовой аутентификации HTTP. Вот несколько вариантов:

...