mirror of
https://github.com/saltstack/salt.git
synced 2025-04-17 10:10:20 +00:00
Merge pull request #31702 from rallytime/merge-2015.8
This commit is contained in:
commit
aa5c13f0b8
8 changed files with 95 additions and 515 deletions
|
@ -84,6 +84,11 @@ Glossary
|
|||
command are a single job. *See also*: :py:mod:`jobs runner
|
||||
<salt.runners.jobs>`.
|
||||
|
||||
Job Cache
|
||||
A storage location for job results, which may then be queried by a
|
||||
salt runner or an external system. May be local to a salt master
|
||||
or stored externally.
|
||||
|
||||
Job ID
|
||||
A unique identifier to represent a given :term:`job`.
|
||||
|
||||
|
@ -252,3 +257,4 @@ Glossary
|
|||
A master process which can send notices and receive replies from
|
||||
minions. *See also*:
|
||||
:conf_master:`worker_threads`.
|
||||
|
||||
|
|
|
@ -13,6 +13,21 @@ There are a number of ways to contribute to Salt development.
|
|||
For details on how to contribute documentation improvements please review
|
||||
:ref:`Writing Salt Documentation <salt-docs>`.
|
||||
|
||||
|
||||
Salt Coding Style
|
||||
-----------------
|
||||
|
||||
SaltStack has its own coding style guide that informs contributors on various coding
|
||||
approaches. Please review the :ref:`Salt Coding Style<coding-style>`_ documentation
|
||||
for information about Salt's particular coding patterns.
|
||||
|
||||
Within the :ref:`Salt Coding Style<coding-style>`_ documentation, there is a section
|
||||
about running Salt's ``.pylintrc`` file. SaltStack recommends running the ``.pylintrc``
|
||||
file on any files you are changing with your code contribution before submitting a
|
||||
pull request to Salt's repository. Please see the :ref:`Linting<pylint-instructions>`_
|
||||
documentation for more information.
|
||||
|
||||
|
||||
.. _github-pull-request:
|
||||
|
||||
Sending a GitHub pull request
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
.. _coding-style:
|
||||
|
||||
=================
|
||||
Salt Coding Style
|
||||
=================
|
||||
|
@ -15,18 +17,29 @@ no grounds to treat others without respect, especially people working to
|
|||
improve Salt)!!
|
||||
|
||||
|
||||
.. _pylint-instructions:
|
||||
|
||||
Linting
|
||||
=======
|
||||
|
||||
Most Salt style conventions are codified in Salt's ``.pylintrc`` file. This file
|
||||
is found in the root of the Salt project and can be passed as an argument to the
|
||||
pylint_ program as follows:
|
||||
Most Salt style conventions are codified in Salt's ``.pylintrc`` file. Salt's
|
||||
pylint file has two dependencies: pylint_ and saltpylint_. You can install
|
||||
these dependencies with ``pip``:
|
||||
|
||||
.. code-block:: bash
|
||||
|
||||
pip install pylint
|
||||
pip install saltpylint
|
||||
|
||||
The ``.pylintrc`` file is found in the root of the Salt project and can be passed
|
||||
as an argument to the pylint_ program as follows:
|
||||
|
||||
.. code-block:: bash
|
||||
|
||||
pylint --rcfile=/path/to/salt/.pylintrc salt/dir/to/lint
|
||||
|
||||
.. _pylint: http://www.pylint.org
|
||||
.. _saltpylint: https://github.com/saltstack/salt-pylint
|
||||
|
||||
Variables
|
||||
=========
|
||||
|
|
|
@ -558,7 +558,7 @@ VALID_OPTS = {
|
|||
'autosign_timeout': int,
|
||||
|
||||
# A mapping of external systems that can be used to generate topfile data.
|
||||
'master_tops': bool, # FIXME Should be dict?
|
||||
'master_tops': dict,
|
||||
|
||||
# A flag that should be set on a top-level master when it is ordering around subordinate masters
|
||||
# via the use of a salt syndic
|
||||
|
|
|
@ -1292,6 +1292,13 @@ def install(name=None,
|
|||
# not None, since the only way version_num is not None is if RPM
|
||||
# metadata parsing was successful.
|
||||
if pkg_type == 'repository':
|
||||
if _yum() == 'yum':
|
||||
# yum install does not support epoch without the arch, and
|
||||
# we won't know what the arch will be when it's not
|
||||
# provided. It could either be the OS architecture, or
|
||||
# 'noarch', and we don't make that distinction in the
|
||||
# pkg.list_pkgs return data.
|
||||
version_num = version_num.split(':', 1)[-1]
|
||||
arch = ''
|
||||
try:
|
||||
namepart, archpart = pkgname.rsplit('.', 1)
|
||||
|
|
|
@ -56,7 +56,8 @@ def state(
|
|||
fail_minions=None,
|
||||
allow_fail=0,
|
||||
concurrent=False,
|
||||
timeout=None):
|
||||
timeout=None,
|
||||
queue=False):
|
||||
'''
|
||||
Invoke a state run on a given target
|
||||
|
||||
|
@ -117,6 +118,9 @@ def state(
|
|||
for use when multiple state runs can safely be run at the same
|
||||
Do not use this flag for performance optimization.
|
||||
|
||||
queue
|
||||
Pass ``queue=true`` through to the state function
|
||||
|
||||
Examples:
|
||||
|
||||
Run a list of sls files via :py:func:`state.sls <salt.state.sls>` on target
|
||||
|
@ -205,6 +209,7 @@ def state(
|
|||
cmd_kw['kwarg']['pillar'] = pillar
|
||||
|
||||
cmd_kw['kwarg']['saltenv'] = __env__
|
||||
cmd_kw['kwarg']['queue'] = queue
|
||||
|
||||
if isinstance(concurrent, bool):
|
||||
cmd_kw['kwarg']['concurrent'] = concurrent
|
||||
|
|
|
@ -45,14 +45,20 @@ _PKG_TARGETS_DOT = {
|
|||
'7': 'tomcat-el-2.2-api'}
|
||||
}
|
||||
|
||||
# Test packages with epoch in version
|
||||
# (https://github.com/saltstack/salt/issues/31619)
|
||||
_PKG_TARGETS_EPOCH = {
|
||||
'RedHat': {'7': 'comps-extras'},
|
||||
}
|
||||
|
||||
|
||||
@destructiveTest
|
||||
@requires_salt_modules('pkg.version', 'pkg.latest_version')
|
||||
class PkgTest(integration.ModuleCase,
|
||||
integration.SaltReturnAssertsMixIn):
|
||||
'''
|
||||
pkg.installed state tests
|
||||
'''
|
||||
@destructiveTest
|
||||
@skipIf(salt.utils.is_windows(), 'minion is windows')
|
||||
@requires_system_grains
|
||||
def test_pkg_001_installed(self, grains=None):
|
||||
|
@ -80,7 +86,6 @@ class PkgTest(integration.ModuleCase,
|
|||
ret = self.run_state('pkg.removed', name=target)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
|
||||
@destructiveTest
|
||||
@skipIf(salt.utils.is_windows(), 'minion is windows')
|
||||
@requires_system_grains
|
||||
def test_pkg_002_installed_with_version(self, grains=None):
|
||||
|
@ -122,7 +127,6 @@ class PkgTest(integration.ModuleCase,
|
|||
ret = self.run_state('pkg.removed', name=target)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
|
||||
@destructiveTest
|
||||
@skipIf(salt.utils.is_windows(), 'minion is windows')
|
||||
@requires_system_grains
|
||||
def test_pkg_003_installed_multipkg(self, grains=None):
|
||||
|
@ -148,7 +152,6 @@ class PkgTest(integration.ModuleCase,
|
|||
ret = self.run_state('pkg.removed', name=None, pkgs=pkg_targets)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
|
||||
@destructiveTest
|
||||
@skipIf(salt.utils.is_windows(), 'minion is windows')
|
||||
@requires_system_grains
|
||||
def test_pkg_004_installed_multipkg_with_version(self, grains=None):
|
||||
|
@ -166,7 +169,7 @@ class PkgTest(integration.ModuleCase,
|
|||
# Make sure that we have targets that match the os_family. If this
|
||||
# fails then the _PKG_TARGETS dict above needs to have an entry added,
|
||||
# with two packages that are not installed before these tests are run
|
||||
self.assertTrue(pkg_targets)
|
||||
self.assertTrue(bool(pkg_targets))
|
||||
|
||||
if os_family == 'Arch':
|
||||
for idx in range(13):
|
||||
|
@ -182,7 +185,7 @@ class PkgTest(integration.ModuleCase,
|
|||
# If this assert fails, we need to find new targets, this test needs to
|
||||
# be able to test successful installation of packages, so these
|
||||
# packages need to not be installed before we run the states below
|
||||
self.assertTrue(version)
|
||||
self.assertTrue(bool(version))
|
||||
|
||||
pkgs = [{pkg_targets[0]: version}, pkg_targets[1]]
|
||||
|
||||
|
@ -191,7 +194,6 @@ class PkgTest(integration.ModuleCase,
|
|||
ret = self.run_state('pkg.removed', name=None, pkgs=pkg_targets)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
|
||||
@destructiveTest
|
||||
@skipIf(salt.utils.is_windows(), 'minion is windows')
|
||||
@requires_system_grains
|
||||
def test_pkg_005_installed_32bit(self, grains=None):
|
||||
|
@ -216,14 +218,13 @@ class PkgTest(integration.ModuleCase,
|
|||
# needs to be able to test successful installation of packages, so
|
||||
# the target needs to not be installed before we run the states
|
||||
# below
|
||||
self.assertFalse(version)
|
||||
self.assertFalse(bool(version))
|
||||
|
||||
ret = self.run_state('pkg.installed', name=target)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
ret = self.run_state('pkg.removed', name=target)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
|
||||
@destructiveTest
|
||||
@skipIf(salt.utils.is_windows(), 'minion is windows')
|
||||
@requires_system_grains
|
||||
def test_pkg_006_installed_32bit_with_version(self, grains=None):
|
||||
|
@ -257,14 +258,13 @@ class PkgTest(integration.ModuleCase,
|
|||
# needs to be able to test successful installation of the package, so
|
||||
# the target needs to not be installed before we run the states
|
||||
# below
|
||||
self.assertTrue(version)
|
||||
self.assertTrue(bool(version))
|
||||
|
||||
ret = self.run_state('pkg.installed', name=target, version=version)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
ret = self.run_state('pkg.removed', name=target)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
|
||||
@destructiveTest
|
||||
@skipIf(salt.utils.is_windows(), 'minion is windows')
|
||||
@requires_system_grains
|
||||
def test_pkg_007_with_dot_in_pkgname(self, grains=None):
|
||||
|
@ -276,13 +276,42 @@ class PkgTest(integration.ModuleCase,
|
|||
'''
|
||||
os_family = grains.get('os_family', '')
|
||||
os_version = grains.get('osmajorrelease', [''])[0]
|
||||
if os_family in _PKG_TARGETS_DOT:
|
||||
target = _PKG_TARGETS_DOT.get(os_family, '').get(os_version, '')
|
||||
else:
|
||||
target = None
|
||||
target = _PKG_TARGETS_DOT.get(os_family, {}).get(os_version)
|
||||
if target:
|
||||
version = self.run_function('pkg.latest_version', [target])
|
||||
# If this assert fails, we need to find a new target. This test
|
||||
# needs to be able to test successful installation of the package, so
|
||||
# the target needs to not be installed before we run the
|
||||
# pkg.installed state below
|
||||
self.assertTrue(bool(version))
|
||||
ret = self.run_state('pkg.installed', name=target)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
ret = self.run_state('pkg.removed', name=target)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
|
||||
@skipIf(salt.utils.is_windows(), 'minion is windows')
|
||||
@requires_system_grains
|
||||
def test_pkg_with_epoch_in_version(self, grains=None):
|
||||
'''
|
||||
This tests for the regression found in the following issue:
|
||||
https://github.com/saltstack/salt/issues/8614
|
||||
|
||||
This is a destructive test as it installs a package
|
||||
'''
|
||||
os_family = grains.get('os_family', '')
|
||||
os_version = grains.get('osmajorrelease', [''])[0]
|
||||
target = _PKG_TARGETS_EPOCH.get(os_family, {}).get(os_version)
|
||||
if target:
|
||||
version = self.run_function('pkg.latest_version', [target])
|
||||
# If this assert fails, we need to find a new target. This test
|
||||
# needs to be able to test successful installation of the package, so
|
||||
# the target needs to not be installed before we run the
|
||||
# pkg.installed state below
|
||||
self.assertTrue(bool(version))
|
||||
ret = self.run_state('pkg.installed', name=target, version=version)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
ret = self.run_state('pkg.removed', name=target)
|
||||
self.assertSaltTrueReturn(ret)
|
||||
|
||||
@destructiveTest
|
||||
@skipIf(salt.utils.is_windows(), 'minion is windows')
|
||||
|
|
|
@ -1,495 +0,0 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
'''
|
||||
:codeauthor: :email:`Jayesh Kariya <jayeshk@saltstack.com>`
|
||||
'''
|
||||
|
||||
# Import Python Libs
|
||||
from __future__ import absolute_import
|
||||
|
||||
# Import Salt Testing Libs
|
||||
from salttesting import TestCase, skipIf
|
||||
from salttesting.mock import (
|
||||
MagicMock,
|
||||
mock_open,
|
||||
patch,
|
||||
NO_MOCK,
|
||||
NO_MOCK_REASON
|
||||
)
|
||||
|
||||
from salttesting.helpers import ensure_in_syspath
|
||||
|
||||
ensure_in_syspath('../../')
|
||||
|
||||
# Import Salt Libs
|
||||
from salt.modules import gpg
|
||||
from salt.exceptions import SaltInvocationError
|
||||
|
||||
gpg.__salt__ = {}
|
||||
|
||||
RET = [{'created': '2014-07-25',
|
||||
'fingerprint': u'F321F',
|
||||
'keyLength': u'1024',
|
||||
'keyid': u'3F0C8E90D459D89A',
|
||||
'ownerTrust': 'Ultimately Trusted',
|
||||
'trust': 'u',
|
||||
'uids': [u'Autogenerated Key (Generated by SaltStack)']}]
|
||||
|
||||
|
||||
class Mockgnupg(object):
|
||||
'''
|
||||
Mock gnupg class
|
||||
'''
|
||||
__version__ = '1.3.1'
|
||||
fingerprint = u'F321F'
|
||||
counts = {}
|
||||
count = ''
|
||||
imported = False
|
||||
imported_rsa = False
|
||||
results = [{'ok': '1', 'fingerprint': u'F321F'}]
|
||||
data = True
|
||||
trust_level = None
|
||||
ok = True
|
||||
unchanged = False
|
||||
not_imported = False
|
||||
|
||||
class GPG(object):
|
||||
'''
|
||||
Mock gnupg class
|
||||
'''
|
||||
def __init__(self, gnupghome='/tmp/salt/.gnupg',
|
||||
homedir='/tmp/salt/.gnupg'):
|
||||
self.gnupghome = gnupghome
|
||||
self.homedir = homedir
|
||||
self.text = None
|
||||
self.keyserver = None
|
||||
self.kwargs = None
|
||||
self.obj = None
|
||||
self.fingerprints = None
|
||||
self.keyserver = None
|
||||
self.secret = None
|
||||
self.keyids = None
|
||||
self.default_key = None
|
||||
self.recipients = None
|
||||
self.passphrase = None
|
||||
|
||||
def search_keys(self, text, keyserver):
|
||||
'''
|
||||
Mock of search_keys method
|
||||
'''
|
||||
self.text = text
|
||||
self.keyserver = keyserver
|
||||
return RET
|
||||
|
||||
def gen_key_input(self, **kwargs):
|
||||
'''
|
||||
Mock of gen_key_input method
|
||||
'''
|
||||
self.kwargs = kwargs
|
||||
return Mockgnupg
|
||||
|
||||
def gen_key(self, obj):
|
||||
'''
|
||||
Mock of gen_key method
|
||||
'''
|
||||
self.obj = obj
|
||||
return Mockgnupg
|
||||
|
||||
def list_keys(self, obj):
|
||||
'''
|
||||
Mock of list_keys method
|
||||
'''
|
||||
self.obj = obj
|
||||
return RET
|
||||
|
||||
def delete_keys(self, fingerprints, secret=False):
|
||||
'''
|
||||
Mock of delete_keys method
|
||||
'''
|
||||
self.fingerprints = fingerprints
|
||||
self.secret = secret
|
||||
return 'ok'
|
||||
|
||||
def import_keys(self, text):
|
||||
'''
|
||||
Mock of import_keys method
|
||||
'''
|
||||
self.text = text
|
||||
return Mockgnupg
|
||||
|
||||
def export_keys(self, keyids, secret):
|
||||
'''
|
||||
Mock of export_keys method
|
||||
'''
|
||||
self.secret = secret
|
||||
self.keyids = keyids
|
||||
return (keyids, secret)
|
||||
|
||||
def recv_keys(self, keyserver, *keyids):
|
||||
'''
|
||||
Mock of recv_keys method
|
||||
'''
|
||||
self.keyserver = keyserver
|
||||
self.keyids = keyids
|
||||
return Mockgnupg
|
||||
|
||||
def sign(self, text, default_key, passphrase):
|
||||
'''
|
||||
Mock of sign method
|
||||
'''
|
||||
self.text = text
|
||||
self.default_key = default_key
|
||||
self.passphrase = passphrase
|
||||
return Mockgnupg
|
||||
|
||||
def verify(self, text):
|
||||
'''
|
||||
Mock of verify method
|
||||
'''
|
||||
self.text = text
|
||||
return Mockgnupg
|
||||
|
||||
def encrypt(self, text, recipients, passphrase):
|
||||
'''
|
||||
Mock of encrypt method
|
||||
'''
|
||||
self.text = text
|
||||
self.recipients = recipients
|
||||
self.passphrase = passphrase
|
||||
return Mockgnupg
|
||||
|
||||
def decrypt(self, text, passphrase):
|
||||
'''
|
||||
Mock of decrypt method
|
||||
'''
|
||||
self.text = text
|
||||
self.passphrase = passphrase
|
||||
return Mockgnupg
|
||||
|
||||
gpg.gnupg = Mockgnupg()
|
||||
|
||||
|
||||
@skipIf(NO_MOCK, NO_MOCK_REASON)
|
||||
class GpgTestCase(TestCase):
|
||||
'''
|
||||
TestCase for salt.modules.gpg
|
||||
'''
|
||||
# 'search_keys' function tests: 1
|
||||
|
||||
def test_search_keys(self):
|
||||
'''
|
||||
Tests if it search keys from keyserver.
|
||||
'''
|
||||
ret = [{'keyid': u'3F0C8E90D459D89A',
|
||||
'uids': [u'Autogenerated Key (Generated by SaltStack)']}]
|
||||
mock = MagicMock(return_value={'home': 'salt'})
|
||||
with patch.dict(gpg.__salt__, {'user.info': mock}):
|
||||
self.assertListEqual(gpg.search_keys('user@example.com',
|
||||
user='username'), ret)
|
||||
|
||||
gpg.GPG_1_3_1 = True
|
||||
self.assertRaises(SaltInvocationError, gpg.search_keys,
|
||||
'user@example.com')
|
||||
|
||||
# 'list_keys' function tests: 1
|
||||
|
||||
def test_list_keys(self):
|
||||
'''
|
||||
Tests if it list keys in GPG keychain
|
||||
'''
|
||||
ret = [{'fingerprint': u'F321F', 'keyid': u'3F0C8E90D459D89A',
|
||||
'trust': 'Ultimately Trusted',
|
||||
'uids': [u'Autogenerated Key (Generated by SaltStack)']}]
|
||||
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user}):
|
||||
self.assertListEqual(gpg.list_keys(), ret)
|
||||
|
||||
# 'list_secret_keys' function tests: 1
|
||||
|
||||
def test_list_secret_keys(self):
|
||||
'''
|
||||
Tests if it list secret keys in GPG keychain
|
||||
'''
|
||||
ret = [{'fingerprint': u'F321F', 'keyid': u'3F0C8E90D459D89A',
|
||||
'trust': 'Ultimately Trusted',
|
||||
'uids': [u'Autogenerated Key (Generated by SaltStack)']}]
|
||||
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user}):
|
||||
self.assertListEqual(gpg.list_secret_keys(), ret)
|
||||
|
||||
# 'create_key' function tests: 1
|
||||
|
||||
def test_create_key(self):
|
||||
'''
|
||||
Tests if it create a key in the GPG keychain
|
||||
'''
|
||||
ret = {'res': True, 'fingerprint': u'F321F',
|
||||
'message': 'GPG key pair successfully generated.'}
|
||||
|
||||
ret1 = {'fingerprint': '', 'res': False,
|
||||
'message': 'gpg_passphrase not available in pillar.'}
|
||||
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
mock_item = MagicMock(return_value=False)
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user,
|
||||
'pillar.item': mock_item}):
|
||||
self.assertDictEqual(gpg.create_key(), ret)
|
||||
|
||||
self.assertDictEqual(gpg.create_key(use_passphrase=True), ret1)
|
||||
|
||||
# 'delete_key' function tests: 1
|
||||
|
||||
def test_delete_key(self):
|
||||
'''
|
||||
Tests if it delete a key from the GPG keychain
|
||||
'''
|
||||
ret = {'message': 'Only specify one argument, fingerprint or keyid',
|
||||
'res': False}
|
||||
|
||||
ret1 = {'message': 'Required argument, fingerprint or keyid',
|
||||
'res': False}
|
||||
|
||||
ret2 = {'message': ('Secret key exists, delete first'
|
||||
' or pass delete_secret=True.'), 'res': False}
|
||||
|
||||
ret3 = {'message': ('Secret key for F321F deleted\nPublic'
|
||||
' key for F321F deleted'), 'res': True}
|
||||
|
||||
ret4 = {'message': 'Key not available in keychain.', 'res': False}
|
||||
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user}):
|
||||
self.assertDictEqual(gpg.delete_key(keyid='3FAD9F1E',
|
||||
fingerprint='53C'), ret)
|
||||
|
||||
self.assertDictEqual(gpg.delete_key(), ret1)
|
||||
|
||||
self.assertDictEqual(gpg.delete_key(keyid='3F0C8E90D459D89A'), ret2)
|
||||
|
||||
self.assertDictEqual(gpg.delete_key(keyid='3F0C8E90D459D89A',
|
||||
delete_secret=True), ret3)
|
||||
|
||||
self.assertDictEqual(gpg.delete_key(keyid='3F0C'), ret4)
|
||||
|
||||
# 'get_key' function tests: 1
|
||||
|
||||
def test_get_key(self):
|
||||
'''
|
||||
Tests if it get a key from the GPG keychain
|
||||
'''
|
||||
ret = {'fingerprint': u'F321F', 'keyid': u'3F0C8E90D459D89A',
|
||||
'trust': 'Ultimately Trusted',
|
||||
'uids': [u'Autogenerated Key (Generated by SaltStack)']}
|
||||
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user}):
|
||||
self.assertFalse(gpg.get_key())
|
||||
|
||||
self.assertDictEqual(gpg.get_key(keyid='3F0C8E90D459D89A'), ret)
|
||||
|
||||
# 'get_secret_key' function tests: 1
|
||||
|
||||
def test_get_secret_key(self):
|
||||
'''
|
||||
Tests if it get a secret key from the GPG keychain
|
||||
'''
|
||||
ret = {'fingerprint': u'F321F', 'keyid': u'3F0C8E90D459D89A',
|
||||
'trust': 'Ultimately Trusted',
|
||||
'uids': [u'Autogenerated Key (Generated by SaltStack)']}
|
||||
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user}):
|
||||
self.assertFalse(gpg.get_secret_key())
|
||||
|
||||
self.assertDictEqual(gpg.get_secret_key(keyid='3F0C8E90D459D89A'),
|
||||
ret)
|
||||
|
||||
# 'import_key' function tests: 1
|
||||
|
||||
def test_import_key(self):
|
||||
'''
|
||||
Tests if it import a key from text or file.
|
||||
'''
|
||||
ret = {'message': 'Unable to import key.', 'res': False}
|
||||
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user}):
|
||||
self.assertRaises(SaltInvocationError, gpg.import_key)
|
||||
|
||||
with patch('salt.utils.flopen', mock_open(read_data='')) as fp:
|
||||
fp.side_effect = IOError()
|
||||
self.assertRaises(SaltInvocationError, gpg.import_key,
|
||||
filename='/path/to/public-key-file')
|
||||
|
||||
gpg.GPG_1_3_1 = True
|
||||
self.assertDictEqual(gpg.import_key(text='-BEGIN PGP PUBLIC KEY BLOCK-'), ret)
|
||||
|
||||
gpg.GPG_1_3_1 = False
|
||||
self.assertDictEqual(gpg.import_key(text='-BEGIN PGP PUBLIC KEY BLOCK-'), ret)
|
||||
|
||||
# 'export_key' function tests: 1
|
||||
|
||||
def test_export_key(self):
|
||||
'''
|
||||
Tests if it export a key from the GPG keychain
|
||||
'''
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user}):
|
||||
self.assertTrue(gpg.export_key(keyids='3F0C8E90D459D89A'))
|
||||
|
||||
# 'receive_keys' function tests: 1
|
||||
|
||||
def test_receive_keys(self):
|
||||
'''
|
||||
Tests if it receive key(s) from keyserver and add them to keychain
|
||||
'''
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user}):
|
||||
self.assertDictEqual(gpg.receive_keys(keys=['3F0C8E90D459D89A']),
|
||||
{'res': True,
|
||||
'message': ['Key F321F added to keychain'],
|
||||
'changes': {}})
|
||||
|
||||
# 'trust_key' function tests: 1
|
||||
|
||||
def test_trust_key(self):
|
||||
'''
|
||||
Tests if it set the trust level for a key in GPG keychain
|
||||
'''
|
||||
ret = {'message': 'Only specify one argument, fingerprint or keyid',
|
||||
'res': False}
|
||||
|
||||
ret1 = {'message': 'KeyID 3F0C8 not in GPG keychain', 'res': False}
|
||||
|
||||
ret2 = {'message': 'Required argument, fingerprint or keyid',
|
||||
'res': False}
|
||||
|
||||
ret3 = ('ERROR: Valid trust levels - expired,unknown,'
|
||||
'not_trusted,marginally,fully,ultimately')
|
||||
|
||||
ret4 = {'res': False,
|
||||
'message': 'Fingerprint not found for keyid 3F0C8E90D459D89A'}
|
||||
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
mock_cmd = MagicMock(return_value={'retcode': 1, 'stderr': 'error'})
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user,
|
||||
'cmd.run_all': mock_cmd}):
|
||||
self.assertDictEqual(gpg.trust_key(keyid='3F0C8E90D459D89A',
|
||||
fingerprint='53C'), ret)
|
||||
|
||||
self.assertDictEqual(gpg.trust_key(keyid='3F0C8'), ret1)
|
||||
|
||||
self.assertDictEqual(gpg.trust_key(), ret2)
|
||||
|
||||
self.assertEqual(gpg.trust_key(fingerprint='53C9'), ret3)
|
||||
|
||||
self.assertEqual(gpg.trust_key(fingerprint='53C96',
|
||||
trust_level='not_trusted'),
|
||||
{'res': False, 'message': 'error'})
|
||||
|
||||
with patch.object(gpg, 'get_key', MagicMock(return_value=RET)):
|
||||
self.assertDictEqual(gpg.trust_key(keyid='3F0C8E90D459D89A'),
|
||||
ret4)
|
||||
|
||||
# 'sign' function tests: 1
|
||||
|
||||
def test_sign(self):
|
||||
'''
|
||||
Tests if it sign message or file
|
||||
'''
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
mock_pillar = MagicMock(return_value=False)
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user,
|
||||
'pillar.item': mock_pillar}):
|
||||
self.assertRaises(SaltInvocationError, gpg.sign,
|
||||
use_passphrase=True)
|
||||
|
||||
self.assertRaises(SaltInvocationError, gpg.sign)
|
||||
|
||||
self.assertTrue(gpg.sign(text='Hello there. How are you?'))
|
||||
|
||||
# 'verify' function tests: 1
|
||||
|
||||
def test_verify(self):
|
||||
'''
|
||||
Tests if it verify a message or file
|
||||
'''
|
||||
ret = {'message': 'The signature could not be verified.', 'res': False}
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
mock_pillar = MagicMock(return_value=False)
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user,
|
||||
'pillar.item': mock_pillar}):
|
||||
self.assertRaises(SaltInvocationError, gpg.verify)
|
||||
|
||||
self.assertDictEqual(gpg.verify(text='Hello there. How are you?'),
|
||||
ret)
|
||||
|
||||
# 'encrypt' function tests: 1
|
||||
|
||||
def test_encrypt(self):
|
||||
'''
|
||||
Tests if it encrypt a message or file
|
||||
'''
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
mock_pillar = MagicMock(return_value=False)
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user,
|
||||
'pillar.item': mock_pillar}):
|
||||
self.assertRaises(SaltInvocationError, gpg.encrypt,
|
||||
use_passphrase=True)
|
||||
|
||||
self.assertRaises(SaltInvocationError, gpg.encrypt)
|
||||
|
||||
self.assertDictEqual(gpg.encrypt(text='Hello there. How are you?'),
|
||||
{'comment': True, 'res': True})
|
||||
|
||||
# 'decrypt' function tests: 1
|
||||
|
||||
def test_decrypt(self):
|
||||
'''
|
||||
Tests if it decrypt a message or file
|
||||
'''
|
||||
mock_conf = MagicMock(return_value='')
|
||||
mock_user = MagicMock(return_value={'home': 'salt'})
|
||||
mock_pillar = MagicMock(return_value=False)
|
||||
with patch.dict(gpg.__salt__, {'config.option': mock_conf,
|
||||
'user.info': mock_user,
|
||||
'pillar.item': mock_pillar}):
|
||||
self.assertRaises(SaltInvocationError, gpg.decrypt,
|
||||
use_passphrase=True)
|
||||
|
||||
self.assertRaises(SaltInvocationError, gpg.decrypt)
|
||||
|
||||
self.assertDictEqual(gpg.decrypt(text='Hello there. How are you?'),
|
||||
{'comment': True, 'res': True})
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
from integration import run_tests
|
||||
run_tests(GpgTestCase, needs_daemon=False)
|
Loading…
Add table
Reference in a new issue