Small bugfixes

This commit is contained in:
Xavier Bustamante Talavera 2019-01-19 19:19:35 +01:00
parent b1aa79fd0a
commit f0f1376b7d
9 changed files with 56 additions and 8 deletions

View File

@ -2,6 +2,7 @@ from distutils.version import StrictVersion
from itertools import chain from itertools import chain
from typing import Set from typing import Set
import boltons.urlutils
from teal.auth import TokenAuth from teal.auth import TokenAuth
from teal.config import Config from teal.config import Config
from teal.enums import Currency from teal.enums import Currency
@ -59,8 +60,14 @@ class DevicehubConfig(Config):
""" """
Official versions Official versions
""" """
TAG_BASE_URL = None
TAG_TOKEN = None
"""Access to the tag provider."""
def __init__(self, db: str = None) -> None: def __init__(self, db: str = None) -> None:
if not self.ORGANIZATION_NAME or not self.ORGANIZATION_TAX_ID: if not self.ORGANIZATION_NAME or not self.ORGANIZATION_TAX_ID:
raise ValueError('You need to set the main organization parameters.') raise ValueError('You need to set the main organization parameters.')
if not self.TAG_BASE_URL or not self.TAG_TOKEN:
raise ValueError('You need a tag service.')
self.TAG_BASE_URL = boltons.urlutils.URL(self.TAG_BASE_URL)
super().__init__(db) super().__init__(db)

View File

@ -1,5 +1,6 @@
from typing import Type from typing import Type
from ereuse_utils.session import DevicehubClient
from flask_sqlalchemy import SQLAlchemy from flask_sqlalchemy import SQLAlchemy
from sqlalchemy import event from sqlalchemy import event
from teal.config import Config as ConfigClass from teal.config import Config as ConfigClass
@ -33,6 +34,7 @@ class Devicehub(Teal):
super().__init__(config, db, import_name, static_url_path, static_folder, static_host, super().__init__(config, db, import_name, static_url_path, static_folder, static_host,
host_matching, subdomain_matching, template_folder, instance_path, host_matching, subdomain_matching, template_folder, instance_path,
instance_relative_config, root_path, Auth) instance_relative_config, root_path, Auth)
self.tag_provider = DevicehubClient(**self.config.get_namespace('TAG_'))
self.dummy = Dummy(self) self.dummy = Dummy(self)
self.before_request(self.register_db_events_listeners) self.before_request(self.register_db_events_listeners)
self.cli.command('regenerate-search')(self.regenerate_search) self.cli.command('regenerate-search')(self.regenerate_search)

View File

@ -108,7 +108,7 @@ class Tag(Thing):
Only tags that are from the default organization can be Only tags that are from the default organization can be
printed by the user. printed by the user.
""" """
return Organization.get_default_org_id == self.org_id return Organization.get_default_org_id() == self.org_id
def __repr__(self) -> str: def __repr__(self) -> str:
return '<Tag {0.id} org:{0.org_id} device:{0.device_id}>'.format(self) return '<Tag {0.id} org:{0.org_id} device:{0.device_id}>'.format(self)

View File

@ -1,4 +1,5 @@
from flask import Response, current_app as app, redirect, request from ereuse_utils.session import DevicehubClient
from flask import Response, current_app, current_app as app, jsonify, redirect, request
from teal.marshmallow import ValidationError from teal.marshmallow import ValidationError
from teal.resource import View, url_for_resource from teal.resource import View, url_for_resource
@ -10,6 +11,25 @@ from ereuse_devicehub.resources.tag import Tag
class TagView(View): class TagView(View):
def post(self): def post(self):
"""Creates a tag.""" """Creates a tag."""
num = request.args.get('num', type=int)
if num:
res = self._create_many_regular_tags(num)
else:
res = self._post_one()
return res
def _create_many_regular_tags(self, num: int):
tag_provider = current_app.tag_provider # type: DevicehubClient
tags_id, _ = tag_provider.post('/', {}, query=[('num', num)])
tags = [Tag(id=tag_id, provider=current_app.config['TAG_BASE_URL']) for tag_id in tags_id]
db.session.add_all(tags)
db.session.commit()
response = jsonify(items=self.schema.dump(tags, many=True, nested=1)) # type: Response
response.status_code = 201
return response
def _post_one(self):
# todo do we use this?
t = request.get_json() t = request.get_json()
tag = Tag(**t) tag = Tag(**t)
if tag.like_etag(): if tag.like_etag():

View File

@ -1,9 +1,8 @@
from base64 import b64encode
from marshmallow import post_dump from marshmallow import post_dump
from marshmallow.fields import Email, String, UUID from marshmallow.fields import Email, String, UUID
from teal.marshmallow import SanitizedStr from teal.marshmallow import SanitizedStr
from ereuse_devicehub import auth
from ereuse_devicehub.marshmallow import NestedOn from ereuse_devicehub.marshmallow import NestedOn
from ereuse_devicehub.resources.agent.schemas import Individual from ereuse_devicehub.resources.agent.schemas import Individual
from ereuse_devicehub.resources.schemas import Thing from ereuse_devicehub.resources.schemas import Thing
@ -42,5 +41,5 @@ class User(Thing):
if 'token' in data: if 'token' in data:
# In many cases we don't dump the token (ex. relationships) # In many cases we don't dump the token (ex. relationships)
# Framework needs ':' at the end # Framework needs ':' at the end
data['token'] = b64encode(str.encode(str(data['token']) + ':')).decode() data['token'] = auth.Auth.encode(data['token'])
return data return data

View File

@ -32,7 +32,7 @@ setup(
'teal>=0.2.0a32', # teal always first 'teal>=0.2.0a32', # teal always first
'click', 'click',
'click-spinner', 'click-spinner',
'ereuse-utils[Naming]>=0.4b13', 'ereuse-utils[Naming]>=0.4b14',
'hashids', 'hashids',
'marshmallow_enum', 'marshmallow_enum',
'psycopg2-binary', 'psycopg2-binary',

View File

@ -31,6 +31,8 @@ class TestConfig(DevicehubConfig):
ORGANIZATION_NAME = 'FooOrg' ORGANIZATION_NAME = 'FooOrg'
ORGANIZATION_TAX_ID = 'foo-org-id' ORGANIZATION_TAX_ID = 'foo-org-id'
SERVER_NAME = 'localhost' SERVER_NAME = 'localhost'
TAG_BASE_URL = 'https://example.com'
TAG_TOKEN = 'tagToken'
@pytest.fixture(scope='session') @pytest.fixture(scope='session')

View File

@ -1,6 +1,7 @@
import pathlib import pathlib
import pytest import pytest
import requests_mock
from boltons.urlutils import URL from boltons.urlutils import URL
from pytest import raises from pytest import raises
from teal.db import MultipleResourcesFound, ResourceNotFound, UniqueViolation from teal.db import MultipleResourcesFound, ResourceNotFound, UniqueViolation
@ -232,3 +233,20 @@ def test_tag_multiple_secondary_org(user: UserClient):
"""Ensures two secondary ids cannot be part of the same Org.""" """Ensures two secondary ids cannot be part of the same Org."""
user.post({'id': 'foo', 'secondary': 'bar'}, res=Tag) user.post({'id': 'foo', 'secondary': 'bar'}, res=Tag)
user.post({'id': 'foo1', 'secondary': 'bar'}, res=Tag, status=UniqueViolation) user.post({'id': 'foo1', 'secondary': 'bar'}, res=Tag, status=UniqueViolation)
def test_crate_num_regular_tags(user: UserClient, requests_mock: requests_mock.mocker.Mocker):
"""Create regular tags. This is done using a tag provider that
returns IDs. These tags are printable.
"""
requests_mock.post('https://example.com/',
# request
request_headers={'Authorization': 'Basic tagToken'},
# response
json=['tag1id', 'tag2id'],
status_code=201)
data, _ = user.post({}, res=Tag, query=[('num', 2)])
assert data['items'][0]['id'] == 'tag1id'
assert data['items'][0]['printable'], 'Tags made this way are printable'
assert data['items'][1]['id'] == 'tag2id'
assert data['items'][1]['printable']

View File

@ -1,4 +1,3 @@
from base64 import b64decode
from uuid import UUID from uuid import UUID
import pytest import pytest
@ -7,6 +6,7 @@ from teal.enums import Country
from teal.marshmallow import ValidationError from teal.marshmallow import ValidationError
from werkzeug.exceptions import NotFound from werkzeug.exceptions import NotFound
from ereuse_devicehub import auth
from ereuse_devicehub.client import Client from ereuse_devicehub.client import Client
from ereuse_devicehub.db import db from ereuse_devicehub.db import db
from ereuse_devicehub.devicehub import Devicehub from ereuse_devicehub.devicehub import Devicehub
@ -77,7 +77,7 @@ def test_login_success(client: Client, app: Devicehub):
uri='/users/login/', uri='/users/login/',
status=200) status=200)
assert user['email'] == 'foo@foo.com' assert user['email'] == 'foo@foo.com'
assert UUID(b64decode(user['token'].encode()).decode()[:-1]) assert UUID(auth.Auth.decode(user['token']))
assert 'password' not in user assert 'password' not in user
assert user['individuals'][0]['name'] == 'Timmy' assert user['individuals'][0]['name'] == 'Timmy'
assert user['individuals'][0]['type'] == 'Person' assert user['individuals'][0]['type'] == 'Person'