mirror of
https://github.com/ansible/awx.git
synced 2026-03-27 13:55:04 -02:30
Merge pull request #4285 from olia-dev/issue-4274
related #4274 - added option to verify server certificate with a specific CA Reviewed-by: Jake McDermott <yo@jakemcdermott.me> https://github.com/jakemcdermott
This commit is contained in:
@@ -1,14 +1,14 @@
|
|||||||
from .plugin import CredentialPlugin
|
from .plugin import CredentialPlugin
|
||||||
|
|
||||||
import os
|
|
||||||
import stat
|
|
||||||
import tempfile
|
|
||||||
import threading
|
|
||||||
from urllib.parse import quote, urlencode, urljoin
|
from urllib.parse import quote, urlencode, urljoin
|
||||||
|
|
||||||
from django.utils.translation import ugettext_lazy as _
|
from django.utils.translation import ugettext_lazy as _
|
||||||
import requests
|
import requests
|
||||||
|
|
||||||
|
# AWX
|
||||||
|
from awx.main.utils import (
|
||||||
|
create_temporary_fifo,
|
||||||
|
)
|
||||||
|
|
||||||
aim_inputs = {
|
aim_inputs = {
|
||||||
'fields': [{
|
'fields': [{
|
||||||
@@ -60,24 +60,6 @@ aim_inputs = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
def create_temporary_fifo(data):
|
|
||||||
"""Open fifo named pipe in a new thread using a temporary file path. The
|
|
||||||
thread blocks until data is read from the pipe.
|
|
||||||
|
|
||||||
Returns the path to the fifo.
|
|
||||||
|
|
||||||
:param data(bytes): Data to write to the pipe.
|
|
||||||
"""
|
|
||||||
path = os.path.join(tempfile.mkdtemp(), next(tempfile._get_candidate_names()))
|
|
||||||
os.mkfifo(path, stat.S_IRUSR | stat.S_IWUSR)
|
|
||||||
|
|
||||||
threading.Thread(
|
|
||||||
target=lambda p, d: open(p, 'wb').write(d),
|
|
||||||
args=(path, data)
|
|
||||||
).start()
|
|
||||||
return path
|
|
||||||
|
|
||||||
|
|
||||||
def aim_backend(**kwargs):
|
def aim_backend(**kwargs):
|
||||||
url = kwargs['url']
|
url = kwargs['url']
|
||||||
client_cert = kwargs.get('client_cert', None)
|
client_cert = kwargs.get('client_cert', None)
|
||||||
|
|||||||
@@ -1,15 +1,16 @@
|
|||||||
from .plugin import CredentialPlugin
|
from .plugin import CredentialPlugin
|
||||||
|
|
||||||
import base64
|
import base64
|
||||||
import os
|
|
||||||
import stat
|
|
||||||
import tempfile
|
|
||||||
import threading
|
|
||||||
from urllib.parse import urljoin, quote_plus
|
from urllib.parse import urljoin, quote_plus
|
||||||
|
|
||||||
from django.utils.translation import ugettext_lazy as _
|
from django.utils.translation import ugettext_lazy as _
|
||||||
import requests
|
import requests
|
||||||
|
|
||||||
|
# AWX
|
||||||
|
from awx.main.utils import (
|
||||||
|
create_temporary_fifo,
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
conjur_inputs = {
|
conjur_inputs = {
|
||||||
'fields': [{
|
'fields': [{
|
||||||
@@ -51,24 +52,6 @@ conjur_inputs = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
def create_temporary_fifo(data):
|
|
||||||
"""Open fifo named pipe in a new thread using a temporary file path. The
|
|
||||||
thread blocks until data is read from the pipe.
|
|
||||||
|
|
||||||
Returns the path to the fifo.
|
|
||||||
|
|
||||||
:param data(bytes): Data to write to the pipe.
|
|
||||||
"""
|
|
||||||
path = os.path.join(tempfile.mkdtemp(), next(tempfile._get_candidate_names()))
|
|
||||||
os.mkfifo(path, stat.S_IRUSR | stat.S_IWUSR)
|
|
||||||
|
|
||||||
threading.Thread(
|
|
||||||
target=lambda p, d: open(p, 'wb').write(d),
|
|
||||||
args=(path, data)
|
|
||||||
).start()
|
|
||||||
return path
|
|
||||||
|
|
||||||
|
|
||||||
def conjur_backend(**kwargs):
|
def conjur_backend(**kwargs):
|
||||||
url = kwargs['url']
|
url = kwargs['url']
|
||||||
api_key = kwargs['api_key']
|
api_key = kwargs['api_key']
|
||||||
|
|||||||
@@ -8,6 +8,10 @@ from .plugin import CredentialPlugin
|
|||||||
import requests
|
import requests
|
||||||
from django.utils.translation import ugettext_lazy as _
|
from django.utils.translation import ugettext_lazy as _
|
||||||
|
|
||||||
|
# AWX
|
||||||
|
from awx.main.utils import (
|
||||||
|
create_temporary_fifo,
|
||||||
|
)
|
||||||
|
|
||||||
base_inputs = {
|
base_inputs = {
|
||||||
'fields': [{
|
'fields': [{
|
||||||
@@ -22,6 +26,12 @@ base_inputs = {
|
|||||||
'type': 'string',
|
'type': 'string',
|
||||||
'secret': True,
|
'secret': True,
|
||||||
'help_text': _('The access token used to authenticate to the Vault server'),
|
'help_text': _('The access token used to authenticate to the Vault server'),
|
||||||
|
}, {
|
||||||
|
'id': 'cacert',
|
||||||
|
'label': _('CA Certificate'),
|
||||||
|
'type': 'string',
|
||||||
|
'multiline': True,
|
||||||
|
'help_text': _('The CA certificate used to verify the SSL certificate of the Vault server')
|
||||||
}],
|
}],
|
||||||
'metadata': [{
|
'metadata': [{
|
||||||
'id': 'secret_path',
|
'id': 'secret_path',
|
||||||
@@ -78,31 +88,34 @@ def kv_backend(**kwargs):
|
|||||||
url = urljoin(kwargs['url'], 'v1')
|
url = urljoin(kwargs['url'], 'v1')
|
||||||
secret_path = kwargs['secret_path']
|
secret_path = kwargs['secret_path']
|
||||||
secret_key = kwargs.get('secret_key', None)
|
secret_key = kwargs.get('secret_key', None)
|
||||||
|
cacert = kwargs.get('cacert', None)
|
||||||
api_version = kwargs['api_version']
|
api_version = kwargs['api_version']
|
||||||
|
|
||||||
|
request_kwargs = {'timeout': 30}
|
||||||
|
if cacert:
|
||||||
|
request_kwargs['verify'] = create_temporary_fifo(cacert.encode())
|
||||||
|
|
||||||
sess = requests.Session()
|
sess = requests.Session()
|
||||||
sess.headers['Authorization'] = 'Bearer {}'.format(token)
|
sess.headers['Authorization'] = 'Bearer {}'.format(token)
|
||||||
|
|
||||||
if api_version == 'v2':
|
if api_version == 'v2':
|
||||||
params = {}
|
|
||||||
if kwargs.get('secret_version'):
|
if kwargs.get('secret_version'):
|
||||||
params['version'] = kwargs['secret_version']
|
request_kwargs['params'] = {'version': kwargs['secret_version']}
|
||||||
try:
|
try:
|
||||||
mount_point, *path = pathlib.Path(secret_path.lstrip(os.sep)).parts
|
mount_point, *path = pathlib.Path(secret_path.lstrip(os.sep)).parts
|
||||||
'/'.join(path)
|
'/'.join(path)
|
||||||
except Exception:
|
except Exception:
|
||||||
mount_point, path = secret_path, []
|
mount_point, path = secret_path, []
|
||||||
# https://www.vaultproject.io/api/secret/kv/kv-v2.html#read-secret-version
|
# https://www.vaultproject.io/api/secret/kv/kv-v2.html#read-secret-version
|
||||||
response = sess.get(
|
request_url = '/'.join([url, mount_point, 'data'] + path).rstrip('/')
|
||||||
'/'.join([url, mount_point, 'data'] + path).rstrip('/'),
|
response = sess.get(request_url, **request_kwargs)
|
||||||
params=params,
|
|
||||||
timeout=30
|
|
||||||
)
|
|
||||||
response.raise_for_status()
|
response.raise_for_status()
|
||||||
json = response.json()['data']
|
json = response.json()['data']
|
||||||
else:
|
else:
|
||||||
# https://www.vaultproject.io/api/secret/kv/kv-v1.html#read-secret
|
request_url = '/'.join([url, secret_path]).rstrip('/')
|
||||||
response = sess.get('/'.join([url, secret_path]).rstrip('/'), timeout=30)
|
response = sess.get(request_url, **request_kwargs)
|
||||||
|
|
||||||
response.raise_for_status()
|
response.raise_for_status()
|
||||||
json = response.json()
|
json = response.json()
|
||||||
|
|
||||||
@@ -121,20 +134,22 @@ def ssh_backend(**kwargs):
|
|||||||
url = urljoin(kwargs['url'], 'v1')
|
url = urljoin(kwargs['url'], 'v1')
|
||||||
secret_path = kwargs['secret_path']
|
secret_path = kwargs['secret_path']
|
||||||
role = kwargs['role']
|
role = kwargs['role']
|
||||||
|
cacert = kwargs.get('cacert', None)
|
||||||
|
|
||||||
|
request_kwargs = {'timeout': 30}
|
||||||
|
if cacert:
|
||||||
|
request_kwargs['verify'] = create_temporary_fifo(cacert.encode())
|
||||||
|
|
||||||
|
request_kwargs['json'] = {'public_key': kwargs['public_key']}
|
||||||
|
if kwargs.get('valid_principals'):
|
||||||
|
request_kwargs['json']['valid_principals'] = kwargs['valid_principals']
|
||||||
|
|
||||||
sess = requests.Session()
|
sess = requests.Session()
|
||||||
sess.headers['Authorization'] = 'Bearer {}'.format(token)
|
sess.headers['Authorization'] = 'Bearer {}'.format(token)
|
||||||
json = {
|
|
||||||
'public_key': kwargs['public_key']
|
|
||||||
}
|
|
||||||
if kwargs.get('valid_principals'):
|
|
||||||
json['valid_principals'] = kwargs['valid_principals']
|
|
||||||
# https://www.vaultproject.io/api/secret/ssh/index.html#sign-ssh-key
|
# https://www.vaultproject.io/api/secret/ssh/index.html#sign-ssh-key
|
||||||
resp = sess.post(
|
request_url = '/'.join([url, secret_path, 'sign', role]).rstrip('/')
|
||||||
'/'.join([url, secret_path, 'sign', role]).rstrip('/'),
|
resp = sess.post(request_url, **request_kwargs)
|
||||||
json=json,
|
|
||||||
timeout=30
|
|
||||||
)
|
|
||||||
resp.raise_for_status()
|
resp.raise_for_status()
|
||||||
return resp.json()['data']['signed_key']
|
return resp.json()['data']['signed_key']
|
||||||
|
|
||||||
|
|||||||
@@ -44,7 +44,7 @@ __all__ = ['get_object_or_400', 'camelcase_to_underscore', 'underscore_to_camelc
|
|||||||
'wrap_args_with_proot', 'build_proot_temp_dir', 'check_proot_installed', 'model_to_dict',
|
'wrap_args_with_proot', 'build_proot_temp_dir', 'check_proot_installed', 'model_to_dict',
|
||||||
'model_instance_diff', 'parse_yaml_or_json', 'RequireDebugTrueOrTest',
|
'model_instance_diff', 'parse_yaml_or_json', 'RequireDebugTrueOrTest',
|
||||||
'has_model_field_prefetched', 'set_environ', 'IllegalArgumentError', 'get_custom_venv_choices', 'get_external_account',
|
'has_model_field_prefetched', 'set_environ', 'IllegalArgumentError', 'get_custom_venv_choices', 'get_external_account',
|
||||||
'task_manager_bulk_reschedule', 'schedule_task_manager', 'classproperty']
|
'task_manager_bulk_reschedule', 'schedule_task_manager', 'classproperty', 'create_temporary_fifo']
|
||||||
|
|
||||||
|
|
||||||
def get_object_or_400(klass, *args, **kwargs):
|
def get_object_or_400(klass, *args, **kwargs):
|
||||||
@@ -1015,3 +1015,20 @@ class classproperty:
|
|||||||
|
|
||||||
def __get__(self, instance, ownerclass):
|
def __get__(self, instance, ownerclass):
|
||||||
return self.fget(ownerclass)
|
return self.fget(ownerclass)
|
||||||
|
|
||||||
|
|
||||||
|
def create_temporary_fifo(data):
|
||||||
|
"""Open fifo named pipe in a new thread using a temporary file path. The
|
||||||
|
thread blocks until data is read from the pipe.
|
||||||
|
Returns the path to the fifo.
|
||||||
|
:param data(bytes): Data to write to the pipe.
|
||||||
|
"""
|
||||||
|
path = os.path.join(tempfile.mkdtemp(), next(tempfile._get_candidate_names()))
|
||||||
|
os.mkfifo(path, stat.S_IRUSR | stat.S_IWUSR)
|
||||||
|
|
||||||
|
threading.Thread(
|
||||||
|
target=lambda p, d: open(p, 'wb').write(d),
|
||||||
|
args=(path, data)
|
||||||
|
).start()
|
||||||
|
return path
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user