refactored endpoints.api.subscribe to use abstracted data interface

This commit is contained in:
alecmerdler 2017-06-27 14:00:23 -07:00 committed by Alec Merdler
parent 0cbe3bdf73
commit 791bd5aefc
4 changed files with 99 additions and 11 deletions

View file

@ -1,32 +1,28 @@
""" Subscribe to plans. """
import logging
import stripe
import features
from app import billing
from endpoints.api import request_error, log_action
from endpoints.exception import NotFound
from data import model
from data.billing import PLANS
import features
from endpoints.api.subscribe_models_pre_oci import data_model as model
from endpoints.exception import NotFound
logger = logging.getLogger(__name__)
def check_repository_usage(user_or_org, plan_found):
private_repos = model.user.get_private_repo_count(user_or_org.username)
private_repos = model.get_private_repo_count(user_or_org.username)
if plan_found is None:
repos_allowed = 0
else:
repos_allowed = plan_found['privateRepos']
if private_repos > repos_allowed:
model.notification.create_unique_notification('over_private_usage', user_or_org,
{'namespace': user_or_org.username})
model.create_unique_notification('over_private_usage', user_or_org.username, {'namespace': user_or_org.username})
else:
model.notification.delete_notifications_by_kind(user_or_org, 'over_private_usage')
model.delete_notifications_by_kind(user_or_org.username, 'over_private_usage')
def carderror_response(exc):
@ -70,7 +66,7 @@ def subscribe(user, plan, token, require_business_plan):
user.username)
raise request_error(message='No matching plan found')
private_repos = model.user.get_private_repo_count(user.username)
private_repos = model.get_private_repo_count(user.username)
# This is the default response
response_json = {

View file

@ -0,0 +1,26 @@
from abc import ABCMeta, abstractmethod
from six import add_metaclass
@add_metaclass(ABCMeta)
class SubscribeInterface(object):
"""
Interface that represents all data store interactions required by the subscribe API endpoint.
"""
@abstractmethod
def get_private_repo_count(self, username):
"""
Returns the number of private repositories for a given username or namespace.
"""
@abstractmethod
def create_unique_notification(self, kind_name, target_username, metadata={}):
"""
Creates a notification using the given parameters.
"""
@abstractmethod
def delete_notifications_by_kind(self, target_username, kind_name):
"""
Remove notifications for a target based on given kind.
"""

View file

@ -0,0 +1,23 @@
from data.model.notification import create_unique_notification, delete_notifications_by_kind
from data.model.user import get_private_repo_count, get_user_or_org
from endpoints.api.subscribe_models_interface import SubscribeInterface
class PreOCIModel(SubscribeInterface):
"""
PreOCIModel implements the data model for build triggers using a database schema
before it was changed to support the OCI specification.
"""
def get_private_repo_count(self, username):
return get_private_repo_count(username)
def create_unique_notification(self, kind_name, target_username, metadata={}):
target = get_user_or_org(target_username)
create_unique_notification(kind_name, target, metadata)
def delete_notifications_by_kind(self, target_username, kind_name):
target = get_user_or_org(target_username)
delete_notifications_by_kind(target, kind_name)
data_model = PreOCIModel()

View file

@ -0,0 +1,43 @@
import pytest
from mock import patch
from endpoints.api.subscribe_models_pre_oci import data_model
@pytest.mark.parametrize('username,repo_count', [
('devtable', 3)
])
def test_get_private_repo_count(username, repo_count):
with patch('endpoints.api.subscribe_models_pre_oci.get_private_repo_count') as mock_get_private_reop_count:
mock_get_private_reop_count.return_value = repo_count
count = data_model.get_private_repo_count(username)
mock_get_private_reop_count.assert_called_once_with(username)
assert count == repo_count
@pytest.mark.parametrize('kind_name,target_username,metadata', [
('over_private_usage', 'devtable', {'namespace': 'devtable'})
])
def test_create_unique_notification(kind_name, target_username, metadata):
with patch('endpoints.api.subscribe_models_pre_oci.get_user_or_org') as mock_get_user_or_org:
mock_get_user_or_org.return_value = {'username': target_username}
with patch('endpoints.api.subscribe_models_pre_oci.create_unique_notification') as mock_create_unique_notification:
data_model.create_unique_notification(kind_name, target_username, metadata)
mock_get_user_or_org.assert_called_once_with(target_username)
mock_create_unique_notification.assert_called_once_with(kind_name, mock_get_user_or_org.return_value, metadata)
@pytest.mark.parametrize('target_username,kind_name', [
('devtable', 'over_private_usage')
])
def test_delete_notifications_by_kind(target_username, kind_name):
with patch('endpoints.api.subscribe_models_pre_oci.get_user_or_org') as mock_get_user_or_org:
mock_get_user_or_org.return_value = {'username': target_username}
with patch('endpoints.api.subscribe_models_pre_oci.delete_notifications_by_kind') as mock_delete_notifications_by_kind:
data_model.delete_notifications_by_kind(target_username, kind_name)
mock_get_user_or_org.assert_called_once_with(target_username)
mock_delete_notifications_by_kind.assert_called_once_with(mock_get_user_or_org.return_value, kind_name)