anchor/tests/controllers/test_app.py
Stanisław Pitucha 97418019e4 Move all plugins to stevedore
Move validators and authentication to stevedore backend.  There should be no
impact on normal usage. Configuration also remains the same.

Change-Id: Iea2e772efe240656c2824e36e860d8ce5147551e
2015-08-20 11:56:41 +10:00

252 lines
11 KiB
Python

# -*- coding:utf-8 -*-
#
# Copyright 2014 Hewlett-Packard Development Company, L.P.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
import json
import stat
import unittest
import mock
from anchor import app
from anchor import jsonloader
import tests
class TestApp(tests.DefaultConfigMixin, unittest.TestCase):
def setUp(self):
self.expected_key_permissions = (stat.S_IRUSR | stat.S_IFREG)
jsonloader.conf.load_extensions()
super(TestApp, self).setUp()
def tearDown(self):
jsonloader.conf._config = {}
super(TestApp, self).tearDown()
def test_self_test(self):
self.assertTrue(True)
@mock.patch('anchor.app._check_file_exists')
@mock.patch('anchor.app._check_file_permissions')
def test_config_check_domains_good(self, a, b):
self.sample_conf_ra['default_ra']['validators'] = {
"common_name": {
"allowed_domains": [".test.com"]
}
}
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
config = {'return_value.st_mode': (stat.S_IRUSR | stat.S_IFREG)}
with mock.patch("os.stat", **config):
self.assertEqual(app.validate_config(jsonloader.conf), None)
@mock.patch('anchor.app._check_file_exists')
@mock.patch('anchor.app._check_file_permissions')
def test_config_check_domains_bad(self, a, b):
self.sample_conf_ra['default_ra']['validators'] = {
"common_name": {
"allowed_domains": ["error.test.com"]
}
}
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
config = {'return_value.st_mode': (stat.S_IRUSR | stat.S_IFREG)}
with mock.patch("os.stat", **config):
self.assertRaises(
app.ConfigValidationException,
app.validate_config,
jsonloader.conf
)
def test_check_file_permissions_good(self):
config = {'return_value.st_mode': (stat.S_IRUSR | stat.S_IFREG)}
with mock.patch("os.stat", **config):
app._check_file_permissions("/mock/path")
def test_check_file_permissions_bad(self):
config = {'return_value.st_mode': (stat.S_IWOTH | stat.S_IFREG)}
with mock.patch("os.stat", **config):
self.assertRaises(app.ConfigValidationException,
app._check_file_permissions, "/mock/path")
def test_validate_old_config(self):
config = json.dumps({
"ca": {},
"auth": {},
"validators": {},
})
jsonloader.conf.load_str_data(config)
self.assertRaisesRegexp(app.ConfigValidationException,
"old version of Anchor",
app.validate_config, jsonloader.conf)
@mock.patch('anchor.app._check_file_permissions')
def test_validate_config_no_registration_authorities(self,
mock_check_perm):
del self.sample_conf['registration_authority']
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
self.assertRaisesRegexp(app.ConfigValidationException,
"No registration authorities present",
app.validate_config, jsonloader.conf)
@mock.patch('anchor.app._check_file_permissions')
def test_validate_config_no_auth(self, mock_check_perm):
del self.sample_conf['authentication']
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
self.assertRaisesRegexp(app.ConfigValidationException,
"No authentication methods present",
app.validate_config, jsonloader.conf)
@mock.patch('anchor.app._check_file_permissions')
def test_validate_config_no_auth_backend(self, mock_check_perm):
del self.sample_conf_auth['default_auth']['backend']
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
self.assertRaisesRegexp(app.ConfigValidationException,
"Authentication method .* doesn't define "
"backend",
app.validate_config, jsonloader.conf)
@mock.patch('anchor.app._check_file_permissions')
def test_validate_config_no_ra_auth(self, mock_check_perm):
del self.sample_conf_ra['default_ra']['authentication']
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
self.assertRaisesRegexp(app.ConfigValidationException,
"No authentication .* for .* default_ra",
app.validate_config, jsonloader.conf)
def test_validate_config_no_ca(self):
del self.sample_conf['signing_ca']
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
self.assertRaisesRegexp(app.ConfigValidationException,
"No signing CA configurations present",
app.validate_config, jsonloader.conf)
@mock.patch('anchor.app._check_file_permissions')
def test_validate_config_no_ra_ca(self, mock_check_perm):
del self.sample_conf_ra['default_ra']['signing_ca']
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
self.assertRaisesRegexp(app.ConfigValidationException,
"No signing CA .* for .* default_ra",
app.validate_config, jsonloader.conf)
@mock.patch('anchor.app._check_file_permissions')
def test_validate_config_ca_config_reqs(self, mock_check_perm):
ca_config_requirements = ["cert_path", "key_path", "output_path",
"signing_hash", "valid_hours"]
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
# Iterate through the ca_config_requirements, replace each one in turn
# with 'missing_req', perform validation. Each should raise in turn
for req in ca_config_requirements:
jsonloader.conf.load_str_data(config.replace(req, "missing_req"))
self.assertRaisesRegexp(app.ConfigValidationException,
"CA config missing: %s" % req,
app.validate_config, jsonloader.conf)
@mock.patch('os.path.isfile')
def test_validate_config_no_ca_cert_file(self, isfile):
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
isfile.return_value = False
self.assertRaisesRegexp(app.ConfigValidationException,
"could not read file: tests/CA/root-ca.crt",
app.validate_config, jsonloader.conf)
@mock.patch('anchor.app._check_file_permissions')
@mock.patch('os.path.isfile')
@mock.patch('os.access')
@mock.patch('os.stat')
def test_validate_config_no_validators(self, stat, access, isfile,
mock_check_perm):
self.sample_conf_ra['default_ra']['validators'] = {}
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
isfile.return_value = True
access.return_value = True
stat.return_value.st_mode = self.expected_key_permissions
self.assertRaisesRegexp(app.ConfigValidationException,
"No validators configured",
app.validate_config, jsonloader.conf)
@mock.patch('anchor.app._check_file_permissions')
@mock.patch('os.path.isfile')
@mock.patch('os.access')
@mock.patch('os.stat')
def test_validate_config_unknown_validator(self, stat, access, isfile,
mock_check_perm):
self.sample_conf_validators['unknown_validator'] = {}
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
isfile.return_value = True
access.return_value = True
stat.return_value.st_mode = self.expected_key_permissions
with self.assertRaises(app.ConfigValidationException,
msg="Unknown validator <unknown_validator> "
"found (for registration authority "
"default)"):
app.validate_config(jsonloader.conf)
@mock.patch('anchor.app._check_file_permissions')
@mock.patch('os.path.isfile')
@mock.patch('os.access')
@mock.patch('os.stat')
def test_validate_config_good(self, stat, access, isfile, mock_check_perm):
config = json.dumps(self.sample_conf)
jsonloader.conf.load_str_data(config)
isfile.return_value = True
access.return_value = True
stat.return_value.st_mode = self.expected_key_permissions
app.validate_config(jsonloader.conf)
@mock.patch('anchor.jsonloader.conf.load_file_data')
def test_config_paths_env(self, conf):
with mock.patch.dict('os.environ', {'ANCHOR_CONF': '/fake/fake'}):
app.load_config()
conf.assert_called_with('/fake/fake')
@mock.patch('anchor.jsonloader.conf.load_file_data')
def test_config_paths_local(self, conf):
ret = lambda x: True if x == 'config.json' else False
with mock.patch("os.path.isfile", ret):
app.load_config()
conf.assert_called_with('config.json')
@mock.patch('anchor.jsonloader.conf.load_file_data')
def test_config_paths_user(self, conf):
ret = (lambda x: True if x == '/fake/.config/anchor/config.json'
else False)
with mock.patch('os.path.isfile', ret):
with mock.patch.dict('os.environ', {'HOME': '/fake'}):
app.load_config()
conf.assert_called_with('/fake/.config/anchor/config.json')
@mock.patch('anchor.jsonloader.conf.load_file_data')
def test_config_paths_system(self, conf):
ret = lambda x: True if x == '/etc/anchor/config.json' else False
with mock.patch('os.path.isfile', ret):
app.load_config()
conf.assert_called_with('/etc/anchor/config.json')