Split out the redis hostname for user events and build logs as a string config. Modularize the user events and fix all callers.

This commit is contained in:
Jake Moshenko 2014-05-30 14:25:29 -04:00
parent 4c1538ca90
commit d1f4fbdacc
6 changed files with 37 additions and 12 deletions

2
app.py
View file

@ -20,6 +20,7 @@ from util.expiration import Expiration
from data.billing import Billing from data.billing import Billing
from data.buildlogs import BuildLogs from data.buildlogs import BuildLogs
from data.queue import WorkQueue from data.queue import WorkQueue
from data.userevent import UserEventsBuilderModule
from license import load_license from license import load_license
from datetime import datetime from datetime import datetime
@ -66,6 +67,7 @@ build_logs = BuildLogs(app)
queue_metrics = QueueMetrics(app) queue_metrics = QueueMetrics(app)
authentication = UserAuthentication(app) authentication = UserAuthentication(app)
expiration = Expiration(app) expiration = Expiration(app)
userevents = UserEventsBuilderModule(app)
tf = app.config['DB_TRANSACTION_FACTORY'] tf = app.config['DB_TRANSACTION_FACTORY']
image_diff_queue = WorkQueue(app.config['DIFFS_QUEUE_NAME'], tf) image_diff_queue = WorkQueue(app.config['DIFFS_QUEUE_NAME'], tf)

View file

@ -80,10 +80,11 @@ class DefaultConfig(object):
AUTHENTICATION_TYPE = 'Database' AUTHENTICATION_TYPE = 'Database'
# Build logs # Build logs
BUILDLOGS_OPTIONS = ['logs.quay.io'] BUILDLOGS_REDIS_HOSTNAME = 'logs.quay.io'
BUILDLOGS_OPTIONS = []
# Real-time user events # Real-time user events
USER_EVENTS = UserEventBuilder('logs.quay.io') USER_EVENTS_REDIS_HOSTNAME = 'logs.quay.io'
# Stripe config # Stripe config
BILLING_TYPE = 'FakeStripe' BILLING_TYPE = 'FakeStripe'
@ -132,7 +133,7 @@ class DefaultConfig(object):
SUPER_USERS = [] SUPER_USERS = []
# Feature Flag: Whether billing is required. # Feature Flag: Whether billing is required.
FEATURE_BILLING = True FEATURE_BILLING = False
# Feature Flag: Whether user accounts automatically have usage log access. # Feature Flag: Whether user accounts automatically have usage log access.
FEATURE_USER_LOG_ACCESS = False FEATURE_USER_LOG_ACCESS = False

View file

@ -89,6 +89,7 @@ class BuildLogs(object):
self.state = None self.state = None
def init_app(self, app): def init_app(self, app):
buildlogs_hostname = app.config.get('BUILDLOGS_REDIS_HOSTNAME')
buildlogs_options = app.config.get('BUILDLOGS_OPTIONS', []) buildlogs_options = app.config.get('BUILDLOGS_OPTIONS', [])
buildlogs_import = app.config.get('BUILDLOGS_MODULE_AND_CLASS', None) buildlogs_import = app.config.get('BUILDLOGS_MODULE_AND_CLASS', None)
@ -97,7 +98,7 @@ class BuildLogs(object):
else: else:
klass = import_class(buildlogs_import[0], buildlogs_import[1]) klass = import_class(buildlogs_import[0], buildlogs_import[1])
buildlogs = klass(*buildlogs_options) buildlogs = klass(buildlogs_hostname, *buildlogs_options)
# register extension with app # register extension with app
app.extensions = getattr(app, 'extensions', {}) app.extensions = getattr(app, 'extensions', {})

View file

@ -17,6 +17,27 @@ class UserEventBuilder(object):
return UserEventListener(self._redis_host, username, events) return UserEventListener(self._redis_host, username, events)
class UserEventsBuilderModule(object):
def __init__(self, app=None):
self.app = app
if app is not None:
self.state = self.init_app(app)
else:
self.state = None
def init_app(self, app):
redis_hostname = app.config.get('USER_EVENTS_REDIS_HOSTNAME')
user_events = UserEventBuilder(redis_hostname)
# register extension with app
app.extensions = getattr(app, 'extensions', {})
app.extensions['userevents'] = user_events
return user_events
def __getattr__(self, name):
return getattr(self.state, name, None)
class UserEvent(object): class UserEvent(object):
""" """
Defines a helper class for publishing to realtime user events Defines a helper class for publishing to realtime user events

View file

@ -8,7 +8,7 @@ from collections import OrderedDict
from data import model from data import model
from data.model import oauth from data.model import oauth
from app import analytics, app, webhook_queue, authentication from app import analytics, app, webhook_queue, authentication, userevents
from auth.auth import process_auth from auth.auth import process_auth
from auth.auth_context import get_authenticated_user, get_validated_token, get_validated_oauth_token from auth.auth_context import get_authenticated_user, get_validated_token, get_validated_oauth_token
from util.names import parse_repository_name from util.names import parse_repository_name
@ -98,13 +98,13 @@ def create_user():
verified = authentication.verify_user(username, password) verified = authentication.verify_user(username, password)
if verified: if verified:
# Mark that the user was logged in. # Mark that the user was logged in.
event = app.config['USER_EVENTS'].get_event(username) event = userevents.get_event(username)
event.publish_event_data('docker-cli', {'action': 'login'}) event.publish_event_data('docker-cli', {'action': 'login'})
return success return success
else: else:
# Mark that the login failed. # Mark that the login failed.
event = app.config['USER_EVENTS'].get_event(username) event = userevents.get_event(username)
event.publish_event_data('docker-cli', {'action': 'loginfailure'}) event.publish_event_data('docker-cli', {'action': 'loginfailure'})
abort(400, 'Invalid password.', issue='login-failure') abort(400, 'Invalid password.', issue='login-failure')
@ -263,7 +263,7 @@ def create_repository(namespace, repository):
'namespace': namespace 'namespace': namespace
} }
event = app.config['USER_EVENTS'].get_event(username) event = userevents.get_event(username)
event.publish_event_data('docker-cli', user_data) event.publish_event_data('docker-cli', user_data)
elif get_validated_token(): elif get_validated_token():
@ -311,7 +311,7 @@ def update_images(namespace, repository):
'namespace': namespace 'namespace': namespace
} }
event = app.config['USER_EVENTS'].get_event(username) event = userevents.get_event(username)
event.publish_event_data('docker-cli', user_data) event.publish_event_data('docker-cli', user_data)
profile.debug('GCing repository') profile.debug('GCing repository')

View file

@ -3,8 +3,8 @@ import json
from flask import request, Blueprint, abort, Response from flask import request, Blueprint, abort, Response
from flask.ext.login import current_user from flask.ext.login import current_user
from data import userevent
from auth.auth import require_session_login from auth.auth import require_session_login
from app import userevents
logger = logging.getLogger(__name__) logger = logging.getLogger(__name__)
@ -41,7 +41,7 @@ def index():
@realtime.route("/user/test") @realtime.route("/user/test")
@require_session_login @require_session_login
def user_test(): def user_test():
evt = userevent.UserEvent('logs.quay.io', current_user.db_user().username) evt = userevents.get_event(current_user.db_user().username)
evt.publish_event_data('test', {'foo': 2}) evt.publish_event_data('test', {'foo': 2})
return 'OK' return 'OK'
@ -58,5 +58,5 @@ def user_subscribe():
if not events: if not events:
abort(404) abort(404)
listener = userevent.UserEventListener('logs.quay.io', current_user.db_user().username, events) listener = userevents.get_listener(current_user.db_user().username, events)
return Response(wrapper(listener), mimetype="text/event-stream") return Response(wrapper(listener), mimetype="text/event-stream")