Switch to python-freezerclient
Implements: blueprint switch-to-python-freezer-client Closes-Bug: #1642921 Depends-On: Ie108d99d56ca76614cdf6927f614a44106a0a922 Change-Id: I2627a5326c8ad4acc96177605f0250925748fb67 Signed-off-by: Ruslan Aliev <raliev@mirantis.com>
This commit is contained in:
parent
db19b04d7f
commit
d98de1ac2b
|
@ -1,80 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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 requests
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
|
||||
|
||||
class ActionManager(object):
|
||||
|
||||
def __init__(self, client, verify=True):
|
||||
self.client = client
|
||||
self.endpoint = self.client.endpoint + '/v1/actions/'
|
||||
self.verify = verify
|
||||
|
||||
@property
|
||||
def headers(self):
|
||||
return {'X-Auth-Token': self.client.auth_token}
|
||||
|
||||
def create(self, doc, action_id=''):
|
||||
action_id = action_id or doc.get('action_id', '')
|
||||
endpoint = self.endpoint + action_id
|
||||
r = requests.post(endpoint,
|
||||
data=json.dumps(doc),
|
||||
headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 201:
|
||||
raise exceptions.ApiClientException(r)
|
||||
action_id = r.json()['action_id']
|
||||
return action_id
|
||||
|
||||
def delete(self, action_id):
|
||||
endpoint = self.endpoint + action_id
|
||||
r = requests.delete(endpoint,
|
||||
headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 204:
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
def list(self, limit=10, offset=0, search=None):
|
||||
data = json.dumps(search) if search else None
|
||||
query = {'limit': int(limit), 'offset': int(offset)}
|
||||
r = requests.get(self.endpoint, headers=self.headers,
|
||||
params=query, data=data, verify=self.verify)
|
||||
if r.status_code != 200:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()['actions']
|
||||
|
||||
def get(self, action_id):
|
||||
endpoint = self.endpoint + action_id
|
||||
r = requests.get(endpoint, headers=self.headers, verify=self.verify)
|
||||
if r.status_code == 200:
|
||||
return r.json()
|
||||
if r.status_code == 404:
|
||||
return None
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
def update(self, action_id, update_doc):
|
||||
endpoint = self.endpoint + action_id
|
||||
r = requests.patch(endpoint,
|
||||
headers=self.headers,
|
||||
data=json.dumps(update_doc), verify=self.verify)
|
||||
if r.status_code != 200:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()['version']
|
|
@ -1,89 +0,0 @@
|
|||
"""
|
||||
(c) Copyright 2014,2015 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 requests
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
|
||||
|
||||
class BackupsManager(object):
|
||||
|
||||
def __init__(self, client, verify=True):
|
||||
self.client = client
|
||||
self.endpoint = self.client.endpoint + '/v1/backups/'
|
||||
self.verify = verify
|
||||
|
||||
@property
|
||||
def headers(self):
|
||||
return {'X-Auth-Token': self.client.auth_token}
|
||||
|
||||
def create(self, backup_metadata):
|
||||
if not backup_metadata.get('client_id', ''):
|
||||
backup_metadata['client_id'] = self.client.client_id
|
||||
r = requests.post(self.endpoint,
|
||||
data=json.dumps(backup_metadata),
|
||||
headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 201:
|
||||
raise exceptions.ApiClientException(r)
|
||||
backup_id = r.json()['backup_id']
|
||||
return backup_id
|
||||
|
||||
def delete(self, backup_id):
|
||||
endpoint = self.endpoint + backup_id
|
||||
r = requests.delete(endpoint, headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 204:
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
def list_all(self, limit=10, offset=0, search=None):
|
||||
"""
|
||||
Retrieves a list of backups
|
||||
|
||||
:param limit: number of result to return (optional, default 10)
|
||||
:param offset: order of first document (optional, default 0)
|
||||
:param search: structured query (optional)
|
||||
can contain:
|
||||
* "time_before": timestamp
|
||||
* "time_after": timestamp
|
||||
Example:
|
||||
{ "time_before": 1428529956 }
|
||||
"""
|
||||
data = json.dumps(search) if search else None
|
||||
query = {'limit': int(limit), 'offset': int(offset)}
|
||||
r = requests.get(self.endpoint, headers=self.headers,
|
||||
params=query, data=data, verify=self.verify)
|
||||
if r.status_code != 200:
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
return r.json()['backups']
|
||||
|
||||
def list(self, limit=10, offset=0, search={}, client_id=None):
|
||||
client_id = client_id or self.client.client_id
|
||||
new_search = search.copy()
|
||||
new_search['match'] = search.get('match', [])
|
||||
new_search['match'].append({'client_id': client_id})
|
||||
return self.list_all(limit, offset, new_search)
|
||||
|
||||
def get(self, backup_id):
|
||||
endpoint = self.endpoint + backup_id
|
||||
r = requests.get(endpoint, headers=self.headers, verify=self.verify)
|
||||
if r.status_code == 200:
|
||||
return r.json()
|
||||
if r.status_code == 404:
|
||||
return None
|
||||
raise exceptions.ApiClientException(r)
|
|
@ -1,275 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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.
|
||||
|
||||
client interface to the Freezer API
|
||||
"""
|
||||
|
||||
import os
|
||||
import socket
|
||||
|
||||
from keystoneauth1.identity import v2
|
||||
from keystoneauth1.identity import v3
|
||||
from keystoneauth1 import session as ksa_session
|
||||
from oslo_config import cfg
|
||||
|
||||
from freezer.apiclient import actions
|
||||
from freezer.apiclient import backups
|
||||
from freezer.apiclient import jobs
|
||||
from freezer.apiclient import registration
|
||||
from freezer.apiclient import sessions
|
||||
from freezer.utils import utils
|
||||
|
||||
FREEZER_SERVICE_TYPE = 'backup'
|
||||
|
||||
|
||||
def env(*vars, **kwargs):
|
||||
for v in vars:
|
||||
value = os.environ.get(v, None)
|
||||
if value:
|
||||
return value
|
||||
return kwargs.get('default', '')
|
||||
|
||||
|
||||
class cached_property(object):
|
||||
|
||||
def __init__(self, func):
|
||||
self.__doc__ = getattr(func, '__doc__')
|
||||
self.func = func
|
||||
|
||||
def __get__(self, obj, cls):
|
||||
if obj is None:
|
||||
return self
|
||||
value = obj.__dict__[self.func.__name__] = self.func(obj)
|
||||
return value
|
||||
|
||||
|
||||
def build_os_options():
|
||||
osclient_opts = [
|
||||
cfg.StrOpt('os-username',
|
||||
default=env('OS_USERNAME'),
|
||||
help='Name used for authentication with the OpenStack '
|
||||
'Identity service. Defaults to env[OS_USERNAME].',
|
||||
dest='os_username'),
|
||||
cfg.StrOpt('os-password',
|
||||
default=env('OS_PASSWORD'),
|
||||
help='Password used for authentication with the OpenStack '
|
||||
'Identity service. Defaults to env[OS_PASSWORD].',
|
||||
dest='os_password'),
|
||||
cfg.StrOpt('os-project-name',
|
||||
default=env('OS_PROJECT_NAME'),
|
||||
help='Project name to scope to. Defaults to '
|
||||
'env[OS_PROJECT_NAME].',
|
||||
dest='os_project_name'),
|
||||
cfg.StrOpt('os-project-domain-name',
|
||||
default=env('OS_PROJECT_DOMAIN_NAME'),
|
||||
help='Domain name containing project. Defaults to '
|
||||
'env[OS_PROJECT_DOMAIN_NAME].',
|
||||
dest='os_project_domain_name'),
|
||||
cfg.StrOpt('os-user-domain-name',
|
||||
default=env('OS_USER_DOMAIN_NAME'),
|
||||
help='User\'s domain name. Defaults to '
|
||||
'env[OS_USER_DOMAIN_NAME].',
|
||||
dest='os_user_domain_name'),
|
||||
cfg.StrOpt('os-tenant-name',
|
||||
default=env('OS_TENANT_NAME'),
|
||||
help='Tenant to request authorization on. Defaults to '
|
||||
'env[OS_TENANT_NAME].',
|
||||
dest='os_tenant_name'),
|
||||
cfg.StrOpt('os-tenant-id',
|
||||
default=env('OS_TENANT_ID'),
|
||||
help='Tenant to request authorization on. Defaults to '
|
||||
'env[OS_TENANT_ID].',
|
||||
dest='os_tenant_id'),
|
||||
cfg.StrOpt('os-auth-url',
|
||||
default=env('OS_AUTH_URL'),
|
||||
help='Specify the Identity endpoint to use for '
|
||||
'authentication. Defaults to env[OS_AUTH_URL].',
|
||||
dest='os_auth_url'),
|
||||
cfg.StrOpt('os-backup-url',
|
||||
default=env('OS_BACKUP_URL'),
|
||||
help='Specify the Freezer backup service endpoint to use. '
|
||||
'Defaults to env[OS_BACKUP_URL].',
|
||||
dest='os_backup_url'),
|
||||
cfg.StrOpt('os-region-name',
|
||||
default=env('OS_REGION_NAME'),
|
||||
help='Specify the region to use. Defaults to '
|
||||
'env[OS_REGION_NAME].',
|
||||
dest='os_region_name'),
|
||||
cfg.StrOpt('os-token',
|
||||
default=env('OS_TOKEN'),
|
||||
help='Specify an existing token to use instead of '
|
||||
'retrieving one via authentication '
|
||||
'(e.g. with username & password). Defaults '
|
||||
'to env[OS_TOKEN].',
|
||||
dest='os_token'),
|
||||
cfg.StrOpt('os-identity-api-version',
|
||||
default=env('OS_IDENTITY_API_VERSION'),
|
||||
help='Identity API version: 2.0 or 3. '
|
||||
'Defaults to env[OS_IDENTITY_API_VERSION]',
|
||||
dest='os_identity_api_version'),
|
||||
cfg.StrOpt('os-endpoint-type',
|
||||
choices=['public', 'publicURL', 'internal', 'internalURL',
|
||||
'admin', 'adminURL'],
|
||||
default=env('OS_ENDPOINT_TYPE') or 'public',
|
||||
help='Endpoint type to select. Valid endpoint types: '
|
||||
'"public" or "publicURL", "internal" or "internalURL",'
|
||||
' "admin" or "adminURL". Defaults to '
|
||||
'env[OS_ENDPOINT_TYPE] or "public"',
|
||||
dest='os_endpoint_type'),
|
||||
cfg.StrOpt('os-cert',
|
||||
default=env('OS_CERT'),
|
||||
help='Specify a cert file to use in verifying a TLS '
|
||||
'(https) server certificate',
|
||||
dest='os_cert'),
|
||||
cfg.StrOpt('os-cacert',
|
||||
default=env('OS_CACERT'),
|
||||
help='Specify a CA bundle file to use in verifying a TLS '
|
||||
'(https) server certificate. Defaults to',
|
||||
dest='os_cacert'),
|
||||
]
|
||||
|
||||
return osclient_opts
|
||||
|
||||
|
||||
def guess_auth_version(opts):
|
||||
if opts.os_identity_api_version == '3':
|
||||
return '3'
|
||||
elif opts.os_identity_api_version == '2.0':
|
||||
return '2.0'
|
||||
elif opts.os_auth_url.endswith('v3'):
|
||||
return '3'
|
||||
elif opts.os_auth_url.endswith('v2.0'):
|
||||
return '2.0'
|
||||
raise Exception('Please provide valid keystone auth url with valid'
|
||||
' keystone api version to use')
|
||||
|
||||
|
||||
def get_auth_plugin(opts):
|
||||
auth_version = guess_auth_version(opts)
|
||||
if opts.os_username:
|
||||
if auth_version == '3':
|
||||
return v3.Password(auth_url=opts.os_auth_url,
|
||||
username=opts.os_username,
|
||||
password=opts.os_password,
|
||||
project_name=opts.os_project_name,
|
||||
user_domain_name=opts.os_user_domain_name,
|
||||
project_domain_name=opts.os_project_domain_name)
|
||||
elif auth_version == '2.0':
|
||||
return v2.Password(auth_url=opts.os_auth_url,
|
||||
username=opts.os_username,
|
||||
password=opts.os_password,
|
||||
tenant_name=opts.os_tenant_name)
|
||||
elif opts.os_token:
|
||||
if auth_version == '3':
|
||||
return v3.Token(auth_url=opts.os_auth_url,
|
||||
token=opts.os_token,
|
||||
project_name=opts.os_project_name,
|
||||
project_domain_name=opts.os_project_domain_name)
|
||||
elif auth_version == '2.0':
|
||||
return v2.Token(auth_url=opts.os_auth_url,
|
||||
token=opts.os_token,
|
||||
tenant_name=opts.os_tenant_name)
|
||||
raise Exception('Unable to determine correct auth method, please provide'
|
||||
' either username or token')
|
||||
|
||||
|
||||
class Client(object):
|
||||
def __init__(self,
|
||||
version='1',
|
||||
token=None,
|
||||
username=None,
|
||||
password=None,
|
||||
tenant_name=None,
|
||||
auth_url=None,
|
||||
session=None,
|
||||
endpoint=None,
|
||||
opts=None,
|
||||
project_name=None,
|
||||
user_domain_name=None,
|
||||
project_domain_name=None,
|
||||
cert=False,
|
||||
cacert=False,
|
||||
insecure=False):
|
||||
|
||||
self.opts = opts
|
||||
# this creates a namespace for self.opts when the client is
|
||||
# created from other method rather than command line arguments.
|
||||
if self.opts is None:
|
||||
self.opts = utils.Namespace({})
|
||||
if token:
|
||||
self.opts.os_token = token
|
||||
if username:
|
||||
self.opts.os_username = username
|
||||
if password:
|
||||
self.opts.os_password = password
|
||||
if tenant_name:
|
||||
self.opts.os_tenant_name = tenant_name
|
||||
if auth_url:
|
||||
self.opts.os_auth_url = auth_url
|
||||
if endpoint:
|
||||
self.opts.os_backup_url = endpoint
|
||||
if project_name:
|
||||
self.opts.os_project_name = project_name
|
||||
if user_domain_name:
|
||||
self.opts.os_user_domain_name = user_domain_name
|
||||
if project_domain_name:
|
||||
self.opts.os_project_domain_name = project_domain_name
|
||||
if insecure:
|
||||
self.verify = False
|
||||
elif cacert:
|
||||
# verify arg in keystone sessions could be True/False/Path to cert
|
||||
self.verify = cacert
|
||||
else:
|
||||
self.verify = True
|
||||
if cert:
|
||||
self.opts.os_cert = cert
|
||||
|
||||
self._session = session
|
||||
self.version = version
|
||||
|
||||
self.backups = backups.BackupsManager(self, verify=self.verify)
|
||||
self.registration = registration.RegistrationManager(
|
||||
self, verify=self.verify)
|
||||
self.jobs = jobs.JobManager(self, verify=self.verify)
|
||||
self.actions = actions.ActionManager(self, verify=self.verify)
|
||||
self.sessions = sessions.SessionManager(self, verify=self.verify)
|
||||
|
||||
@cached_property
|
||||
def session(self):
|
||||
if self._session:
|
||||
return self._session
|
||||
auth_plugin = get_auth_plugin(self.opts)
|
||||
return ksa_session.Session(auth=auth_plugin, verify=self.verify)
|
||||
|
||||
@cached_property
|
||||
def endpoint(self):
|
||||
if self.opts.os_backup_url:
|
||||
return self.opts.os_backup_url
|
||||
else:
|
||||
auth_ref = self.session.auth.get_auth_ref(self.session)
|
||||
endpoint = auth_ref.service_catalog.url_for(
|
||||
service_type=FREEZER_SERVICE_TYPE,
|
||||
interface=self.opts.os_endpoint_type,
|
||||
)
|
||||
return endpoint
|
||||
|
||||
@property
|
||||
def auth_token(self):
|
||||
return self.session.get_token()
|
||||
|
||||
@cached_property
|
||||
def client_id(self):
|
||||
return '{0}_{1}'.format(self.session.get_project_id(),
|
||||
socket.gethostname())
|
|
@ -1,70 +0,0 @@
|
|||
"""
|
||||
(c) Copyright 2014,2015 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
|
||||
|
||||
|
||||
class ApiClientException(Exception):
|
||||
@staticmethod
|
||||
def get_message_from_api_response(r):
|
||||
"""
|
||||
returns a message based on information from a api-formatted response
|
||||
if available, otherwise None
|
||||
api-formatted response should be:
|
||||
{
|
||||
title: "error title string",
|
||||
description: "error description string"
|
||||
}
|
||||
|
||||
:param r: response object
|
||||
:return: string with error message or None if it fails
|
||||
"""
|
||||
try:
|
||||
body = json.loads(r.text)
|
||||
message = "Error {0}: {1}".format(
|
||||
r.status_code,
|
||||
body['description'])
|
||||
except Exception:
|
||||
message = None
|
||||
return message
|
||||
|
||||
@staticmethod
|
||||
def get_message_from_response(r):
|
||||
"""
|
||||
composes the error message using information eventually present
|
||||
in the response (http error code and the http response body)
|
||||
|
||||
:param r: response object
|
||||
:return: string with error message or None if it fails
|
||||
"""
|
||||
try:
|
||||
message = "Error {0}: {1}".format(
|
||||
r.status_code,
|
||||
r.text)
|
||||
except Exception:
|
||||
message = None
|
||||
return message
|
||||
|
||||
def __init__(self, r):
|
||||
message = self.get_message_from_api_response(r) or \
|
||||
self.get_message_from_response(r) or \
|
||||
str(r)
|
||||
try:
|
||||
self.status_code = r.status_code
|
||||
except Exception:
|
||||
self.status_code = None
|
||||
super(ApiClientException, self).__init__(message)
|
|
@ -1,150 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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 requests
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
|
||||
|
||||
class JobManager(object):
|
||||
|
||||
def __init__(self, client, verify=True):
|
||||
self.client = client
|
||||
self.endpoint = self.client.endpoint + '/v1/jobs/'
|
||||
self.verify = verify
|
||||
|
||||
@property
|
||||
def headers(self):
|
||||
return {'X-Auth-Token': self.client.auth_token}
|
||||
|
||||
def create(self, doc, job_id=''):
|
||||
job_id = job_id or doc.get('job_id', '')
|
||||
endpoint = self.endpoint + job_id
|
||||
doc['client_id'] = doc.get('client_id', '') or self.client.client_id
|
||||
r = requests.post(endpoint,
|
||||
data=json.dumps(doc),
|
||||
headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 201:
|
||||
raise exceptions.ApiClientException(r)
|
||||
job_id = r.json()['job_id']
|
||||
return job_id
|
||||
|
||||
def delete(self, job_id):
|
||||
endpoint = self.endpoint + job_id
|
||||
r = requests.delete(endpoint, headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 204:
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
def list_all(self, limit=10, offset=0, search=None):
|
||||
data = json.dumps(search) if search else None
|
||||
query = {'limit': int(limit), 'offset': int(offset)}
|
||||
r = requests.get(self.endpoint, headers=self.headers,
|
||||
params=query, data=data, verify=self.verify)
|
||||
if r.status_code != 200:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()['jobs']
|
||||
|
||||
def list(self, limit=10, offset=0, search={}, client_id=None):
|
||||
client_id = client_id or self.client.client_id
|
||||
new_search = search.copy()
|
||||
new_search['match'] = search.get('match', [])
|
||||
new_search['match'].append({'client_id': client_id})
|
||||
return self.list_all(limit, offset, new_search)
|
||||
|
||||
def get(self, job_id):
|
||||
endpoint = self.endpoint + job_id
|
||||
r = requests.get(endpoint, headers=self.headers, verify=self.verify)
|
||||
if r.status_code == 200:
|
||||
return r.json()
|
||||
if r.status_code == 404:
|
||||
return None
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
def update(self, job_id, update_doc):
|
||||
endpoint = self.endpoint + job_id
|
||||
r = requests.patch(endpoint,
|
||||
headers=self.headers,
|
||||
data=json.dumps(update_doc),
|
||||
verify=self.verify)
|
||||
if r.status_code != 200:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()['version']
|
||||
|
||||
def start_job(self, job_id):
|
||||
"""
|
||||
Request to start a job
|
||||
|
||||
:param job_id: the id of the job to start
|
||||
:return: the response obj:
|
||||
{
|
||||
result: string 'success' or 'already started'
|
||||
}
|
||||
"""
|
||||
# endpoint /v1/jobs/{job_id}/event
|
||||
endpoint = '{0}{1}/event'.format(self.endpoint, job_id)
|
||||
doc = {"start": None}
|
||||
r = requests.post(endpoint,
|
||||
headers=self.headers,
|
||||
data=json.dumps(doc),
|
||||
verify=self.verify)
|
||||
if r.status_code != 202:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()
|
||||
|
||||
def stop_job(self, job_id):
|
||||
"""
|
||||
Request to stop a job
|
||||
|
||||
:param job_id: the id of the job to start
|
||||
:return: the response obj:
|
||||
{
|
||||
result: string 'success' or 'already stopped'
|
||||
}
|
||||
"""
|
||||
# endpoint /v1/jobs/{job_id}/event
|
||||
endpoint = '{0}{1}/event'.format(self.endpoint, job_id)
|
||||
doc = {"stop": None}
|
||||
r = requests.post(endpoint,
|
||||
headers=self.headers,
|
||||
data=json.dumps(doc),
|
||||
verify=self.verify)
|
||||
if r.status_code != 202:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()
|
||||
|
||||
def abort_job(self, job_id):
|
||||
"""
|
||||
Request to abort a job
|
||||
|
||||
:param job_id: the id of the job to start
|
||||
:return: the response obj:
|
||||
{
|
||||
result: string 'success' or 'already stopped'
|
||||
}
|
||||
"""
|
||||
# endpoint /v1/jobs/{job_id}/event
|
||||
endpoint = '{0}{1}/event'.format(self.endpoint, job_id)
|
||||
doc = {"abort": None}
|
||||
r = requests.post(endpoint,
|
||||
headers=self.headers,
|
||||
data=json.dumps(doc),
|
||||
verify=self.verify)
|
||||
if r.status_code != 202:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()
|
|
@ -1,83 +0,0 @@
|
|||
"""
|
||||
(c) Copyright 2014,2015 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 requests
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
|
||||
|
||||
class RegistrationManager(object):
|
||||
|
||||
def __init__(self, client, verify=True):
|
||||
self.client = client
|
||||
self.endpoint = self.client.endpoint + '/v1/clients/'
|
||||
self.verify = verify
|
||||
|
||||
@property
|
||||
def headers(self):
|
||||
return {'X-Auth-Token': self.client.auth_token}
|
||||
|
||||
def create(self, client_info):
|
||||
r = requests.post(self.endpoint,
|
||||
data=json.dumps(client_info),
|
||||
headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 201:
|
||||
raise exceptions.ApiClientException(r)
|
||||
client_id = r.json()['client_id']
|
||||
return client_id
|
||||
|
||||
def delete(self, client_id):
|
||||
endpoint = self.endpoint + client_id
|
||||
r = requests.delete(endpoint, headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 204:
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
def list(self, limit=10, offset=0, search=None):
|
||||
"""
|
||||
Retrieves a list of client info structures
|
||||
|
||||
:param limit: number of result to return (optional, default 10)
|
||||
:param offset: order of first document (optional, default 0)
|
||||
:param search: structured query (optional)
|
||||
can contain:
|
||||
* "match": list of {field, value}
|
||||
Example:
|
||||
{ "match": [
|
||||
{"description": "some search text here"},
|
||||
{"client_id": "giano"},
|
||||
...
|
||||
],
|
||||
}
|
||||
"""
|
||||
data = json.dumps(search) if search else None
|
||||
query = {'limit': int(limit), 'offset': int(offset)}
|
||||
r = requests.get(self.endpoint, headers=self.headers,
|
||||
params=query, data=data, verify=self.verify)
|
||||
if r.status_code != 200:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()['clients']
|
||||
|
||||
def get(self, client_id):
|
||||
endpoint = self.endpoint + client_id
|
||||
r = requests.get(endpoint, headers=self.headers, verify=self.verify)
|
||||
if r.status_code == 200:
|
||||
return r.json()
|
||||
if r.status_code == 404:
|
||||
return None
|
||||
raise exceptions.ApiClientException(r)
|
|
@ -1,163 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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 requests
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
|
||||
|
||||
class SessionManager(object):
|
||||
|
||||
def __init__(self, client, verify=True):
|
||||
self.client = client
|
||||
self.endpoint = self.client.endpoint + '/v1/sessions/'
|
||||
self.verify = verify
|
||||
|
||||
@property
|
||||
def headers(self):
|
||||
return {'X-Auth-Token': self.client.auth_token}
|
||||
|
||||
def create(self, doc, session_id=''):
|
||||
session_id = session_id or doc.get('session_id', '')
|
||||
endpoint = self.endpoint + session_id
|
||||
r = requests.post(endpoint,
|
||||
data=json.dumps(doc),
|
||||
headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 201:
|
||||
raise exceptions.ApiClientException(r)
|
||||
session_id = r.json()['session_id']
|
||||
return session_id
|
||||
|
||||
def delete(self, session_id):
|
||||
endpoint = self.endpoint + session_id
|
||||
r = requests.delete(endpoint, headers=self.headers,
|
||||
verify=self.verify)
|
||||
if r.status_code != 204:
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
def list_all(self, limit=10, offset=0, search=None):
|
||||
data = json.dumps(search) if search else None
|
||||
query = {'limit': int(limit), 'offset': int(offset)}
|
||||
r = requests.get(self.endpoint, headers=self.headers,
|
||||
params=query, data=data, verify=self.verify)
|
||||
if r.status_code != 200:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()['sessions']
|
||||
|
||||
def list(self, limit=10, offset=0, search={}):
|
||||
new_search = search.copy()
|
||||
new_search['match'] = search.get('match', [])
|
||||
return self.list_all(limit, offset, new_search)
|
||||
|
||||
def get(self, session_id):
|
||||
endpoint = self.endpoint + session_id
|
||||
r = requests.get(endpoint, headers=self.headers, verify=self.verify)
|
||||
if r.status_code == 200:
|
||||
return r.json()
|
||||
if r.status_code == 404:
|
||||
return None
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
def update(self, session_id, update_doc):
|
||||
endpoint = self.endpoint + session_id
|
||||
r = requests.patch(endpoint,
|
||||
headers=self.headers,
|
||||
data=json.dumps(update_doc),
|
||||
verify=self.verify)
|
||||
if r.status_code != 200:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()['version']
|
||||
|
||||
def add_job(self, session_id, job_id):
|
||||
# endpoint /v1/sessions/{sessions_id}/jobs/{job_id}
|
||||
endpoint = '{0}{1}/jobs/{2}'.format(self.endpoint, session_id, job_id)
|
||||
r = requests.put(endpoint,
|
||||
headers=self.headers, verify=self.verify)
|
||||
if r.status_code != 204:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return
|
||||
|
||||
def remove_job(self, session_id, job_id):
|
||||
# endpoint /v1/sessions/{sessions_id}/jobs/{job_id}
|
||||
endpoint = '{0}{1}/jobs/{2}'.format(self.endpoint, session_id, job_id)
|
||||
retry = 5
|
||||
r = ''
|
||||
while retry:
|
||||
r = requests.delete(endpoint,
|
||||
headers=self.headers, verify=self.verify)
|
||||
if r.status_code == 204:
|
||||
return
|
||||
retry -= 1
|
||||
raise exceptions.ApiClientException(r)
|
||||
|
||||
def start_session(self, session_id, job_id, session_tag):
|
||||
"""
|
||||
Informs the api that the client is starting the session
|
||||
identified by the session_id and request the session_tag
|
||||
to be incremented up to the requested value.
|
||||
The returned session_id could be:
|
||||
* current_tag + 1 if the session has started
|
||||
* > current_tag + 1 if the action had already been started
|
||||
by some other node and this node was out of sync
|
||||
|
||||
:param session_id:
|
||||
:param job_id:
|
||||
:param session_tag: the new session_id
|
||||
:return: the response obj:
|
||||
{ result: string 'running' or 'error',
|
||||
'session_tag': the new session_tag )
|
||||
"""
|
||||
# endpoint /v1/sessions/{sessions_id}/action
|
||||
endpoint = '{0}{1}/action'.format(self.endpoint, session_id)
|
||||
doc = {"start": {
|
||||
"job_id": job_id,
|
||||
"current_tag": session_tag
|
||||
}}
|
||||
r = requests.post(endpoint,
|
||||
headers=self.headers,
|
||||
data=json.dumps(doc),
|
||||
verify=self.verify)
|
||||
if r.status_code != 202:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()
|
||||
|
||||
def end_session(self, session_id, job_id, session_tag, result):
|
||||
"""
|
||||
Informs the freezer service that the job has ended.
|
||||
Provides information about the job's result and the session tag
|
||||
|
||||
:param session_id:
|
||||
:param job_id:
|
||||
:param session_tag:
|
||||
:param result:
|
||||
:return:
|
||||
"""
|
||||
# endpoint /v1/sessions/{sessions_id}/action
|
||||
endpoint = '{0}{1}/action'.format(self.endpoint, session_id)
|
||||
doc = {"end": {
|
||||
"job_id": job_id,
|
||||
"current_tag": session_tag,
|
||||
"result": result
|
||||
}}
|
||||
r = requests.post(endpoint,
|
||||
headers=self.headers,
|
||||
data=json.dumps(doc),
|
||||
verify=self.verify)
|
||||
if r.status_code != 202:
|
||||
raise exceptions.ApiClientException(r)
|
||||
return r.json()
|
|
@ -19,7 +19,6 @@ import os
|
|||
import sys
|
||||
|
||||
from freezer import __version__ as FREEZER_VERSION
|
||||
from freezer.apiclient import client as api_client
|
||||
from freezer.utils import winutils
|
||||
from oslo_config import cfg
|
||||
from oslo_log import log
|
||||
|
@ -47,6 +46,14 @@ def add_filter():
|
|||
addFilter(log_filter)
|
||||
|
||||
|
||||
def env(*args, **kwargs):
|
||||
for v in args:
|
||||
value = os.environ.get(v, None)
|
||||
if value:
|
||||
return value
|
||||
return kwargs.get('default', '')
|
||||
|
||||
|
||||
def get_common_opts():
|
||||
scheduler_conf_d = os.environ.get('FREEZER_SCHEDULER_CONF_D',
|
||||
DEFAULT_FREEZER_SCHEDULER_CONF_D)
|
||||
|
@ -126,10 +133,98 @@ def get_common_opts():
|
|||
return _COMMON
|
||||
|
||||
|
||||
def build_os_options():
|
||||
osclient_opts = [
|
||||
cfg.StrOpt('os-username',
|
||||
default=env('OS_USERNAME'),
|
||||
help='Name used for authentication with the OpenStack '
|
||||
'Identity service. Defaults to env[OS_USERNAME].',
|
||||
dest='os_username'),
|
||||
cfg.StrOpt('os-password',
|
||||
default=env('OS_PASSWORD'),
|
||||
help='Password used for authentication with the OpenStack '
|
||||
'Identity service. Defaults to env[OS_PASSWORD].',
|
||||
dest='os_password'),
|
||||
cfg.StrOpt('os-project-name',
|
||||
default=env('OS_PROJECT_NAME'),
|
||||
help='Project name to scope to. Defaults to '
|
||||
'env[OS_PROJECT_NAME].',
|
||||
dest='os_project_name'),
|
||||
cfg.StrOpt('os-project-domain-name',
|
||||
default=env('OS_PROJECT_DOMAIN_NAME'),
|
||||
help='Domain name containing project. Defaults to '
|
||||
'env[OS_PROJECT_DOMAIN_NAME].',
|
||||
dest='os_project_domain_name'),
|
||||
cfg.StrOpt('os-user-domain-name',
|
||||
default=env('OS_USER_DOMAIN_NAME'),
|
||||
help='User\'s domain name. Defaults to '
|
||||
'env[OS_USER_DOMAIN_NAME].',
|
||||
dest='os_user_domain_name'),
|
||||
cfg.StrOpt('os-tenant-name',
|
||||
default=env('OS_TENANT_NAME'),
|
||||
help='Tenant to request authorization on. Defaults to '
|
||||
'env[OS_TENANT_NAME].',
|
||||
dest='os_tenant_name'),
|
||||
cfg.StrOpt('os-tenant-id',
|
||||
default=env('OS_TENANT_ID'),
|
||||
help='Tenant to request authorization on. Defaults to '
|
||||
'env[OS_TENANT_ID].',
|
||||
dest='os_tenant_id'),
|
||||
cfg.StrOpt('os-auth-url',
|
||||
default=env('OS_AUTH_URL'),
|
||||
help='Specify the Identity endpoint to use for '
|
||||
'authentication. Defaults to env[OS_AUTH_URL].',
|
||||
dest='os_auth_url'),
|
||||
cfg.StrOpt('os-backup-url',
|
||||
default=env('OS_BACKUP_URL'),
|
||||
help='Specify the Freezer backup service endpoint to use. '
|
||||
'Defaults to env[OS_BACKUP_URL].',
|
||||
dest='os_backup_url'),
|
||||
cfg.StrOpt('os-region-name',
|
||||
default=env('OS_REGION_NAME'),
|
||||
help='Specify the region to use. Defaults to '
|
||||
'env[OS_REGION_NAME].',
|
||||
dest='os_region_name'),
|
||||
cfg.StrOpt('os-token',
|
||||
default=env('OS_TOKEN'),
|
||||
help='Specify an existing token to use instead of '
|
||||
'retrieving one via authentication '
|
||||
'(e.g. with username & password). Defaults '
|
||||
'to env[OS_TOKEN].',
|
||||
dest='os_token'),
|
||||
cfg.StrOpt('os-identity-api-version',
|
||||
default=env('OS_IDENTITY_API_VERSION'),
|
||||
help='Identity API version: 2.0 or 3. '
|
||||
'Defaults to env[OS_IDENTITY_API_VERSION]',
|
||||
dest='os_identity_api_version'),
|
||||
cfg.StrOpt('os-endpoint-type',
|
||||
choices=['public', 'publicURL', 'internal', 'internalURL',
|
||||
'admin', 'adminURL'],
|
||||
default=env('OS_ENDPOINT_TYPE') or 'public',
|
||||
help='Endpoint type to select. Valid endpoint types: '
|
||||
'"public" or "publicURL", "internal" or "internalURL",'
|
||||
' "admin" or "adminURL". Defaults to '
|
||||
'env[OS_ENDPOINT_TYPE] or "public"',
|
||||
dest='os_endpoint_type'),
|
||||
cfg.StrOpt('os-cert',
|
||||
default=env('OS_CERT'),
|
||||
help='Specify a cert file to use in verifying a TLS '
|
||||
'(https) server certificate',
|
||||
dest='os_cert'),
|
||||
cfg.StrOpt('os-cacert',
|
||||
default=env('OS_CACERT'),
|
||||
help='Specify a CA bundle file to use in verifying a TLS '
|
||||
'(https) server certificate. Defaults to',
|
||||
dest='os_cacert'),
|
||||
]
|
||||
|
||||
return osclient_opts
|
||||
|
||||
|
||||
def parse_args(choices):
|
||||
default_conf = cfg.find_config_files('freezer', 'scheduler', '.conf')
|
||||
CONF.register_cli_opts(api_client.build_os_options())
|
||||
CONF.register_cli_opts(get_common_opts())
|
||||
CONF.register_cli_opts(build_os_options())
|
||||
log.register_options(CONF)
|
||||
|
||||
positional = [
|
||||
|
|
|
@ -22,11 +22,11 @@ import threading
|
|||
import time
|
||||
|
||||
from apscheduler.schedulers import background
|
||||
from freezerclient.v1 import client
|
||||
from oslo_config import cfg
|
||||
from oslo_log import log
|
||||
import six
|
||||
|
||||
from freezer.apiclient import client
|
||||
from freezer.scheduler import arguments
|
||||
from freezer.scheduler import scheduler_job
|
||||
from freezer.scheduler import shell
|
||||
|
@ -229,13 +229,13 @@ def main():
|
|||
" from python-freezerclient.\n")
|
||||
|
||||
apiclient = None
|
||||
insecure = False
|
||||
verify = True
|
||||
if CONF.insecure:
|
||||
insecure = True
|
||||
verify = False
|
||||
|
||||
if CONF.no_api is False:
|
||||
try:
|
||||
apiclient = client.Client(opts=CONF, insecure=insecure)
|
||||
apiclient = client.Client(opts=CONF, verify=verify)
|
||||
if CONF.client_id:
|
||||
apiclient.client_id = CONF.client_id
|
||||
except Exception as e:
|
||||
|
|
|
@ -228,7 +228,7 @@ def do_job_list(client, args):
|
|||
|
||||
def do_client_list(client, args):
|
||||
table = prettytable.PrettyTable(["client_id", "hostname", "description"])
|
||||
l = client.registration.list()
|
||||
l = client.clients.list()
|
||||
offset = 0
|
||||
while l:
|
||||
offset += len(l)
|
||||
|
@ -237,7 +237,7 @@ def do_client_list(client, args):
|
|||
table.add_row([client_doc['client_id'],
|
||||
client_doc.get('hostname', ''),
|
||||
client_doc.get('description', '')])
|
||||
l = client.registration.list(offset=offset)
|
||||
l = client.clients.list(offset=offset)
|
||||
print(table)
|
||||
|
||||
|
||||
|
|
|
@ -17,15 +17,14 @@ limitations under the License.
|
|||
|
||||
import json
|
||||
import os
|
||||
import psutil
|
||||
import signal
|
||||
import socket
|
||||
import uuid
|
||||
|
||||
|
||||
from freezerclient import exceptions
|
||||
from oslo_log import log
|
||||
import psutil
|
||||
|
||||
import freezer.apiclient.exceptions
|
||||
|
||||
LOG = log.getLogger(__name__)
|
||||
|
||||
|
@ -39,8 +38,8 @@ def do_register(client, args=None):
|
|||
"hostname": socket.gethostname()
|
||||
}
|
||||
try:
|
||||
client.registration.create(client_info)
|
||||
except freezer.apiclient.exceptions.ApiClientException as e:
|
||||
client.clients.create(client_info)
|
||||
except exceptions.ApiClientException as e:
|
||||
if e.status_code == 409:
|
||||
print("Client already registered")
|
||||
return 73 # os.EX_CANTCREAT
|
||||
|
|
|
@ -57,8 +57,8 @@ class PySvc(win32serviceutil.ServiceFramework):
|
|||
win32event.SetEvent(self.hWaitStop)
|
||||
|
||||
def main(self):
|
||||
import freezer.apiclient.client
|
||||
from freezer.scheduler.freezer_scheduler import FreezerScheduler
|
||||
from freezerclient.v1.client import Client
|
||||
|
||||
servicemanager.LogMsg(
|
||||
servicemanager.EVENTLOG_INFORMATION_TYPE,
|
||||
|
@ -95,7 +95,7 @@ class PySvc(win32serviceutil.ServiceFramework):
|
|||
'insecure': self.insecure
|
||||
}
|
||||
|
||||
client = freezer.apiclient.client.Client(**credentials)
|
||||
client = Client(**credentials)
|
||||
|
||||
scheduler = FreezerScheduler(
|
||||
apiclient=client, interval=int(os.environ['SERVICE_INTERVAL']),
|
||||
|
|
|
@ -1,128 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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 unittest
|
||||
from mock import Mock, patch
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
from freezer.apiclient import actions
|
||||
|
||||
|
||||
class TestActionManager(unittest.TestCase):
|
||||
|
||||
def setUp(self):
|
||||
self.mock_client = Mock()
|
||||
self.mock_response = Mock()
|
||||
self.mock_client.endpoint = 'http://testendpoint:9999'
|
||||
self.mock_client.auth_token = 'testtoken'
|
||||
self.mock_client.client_id = 'test_client_id_78900987'
|
||||
self.action_manager = actions.ActionManager(self.mock_client)
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_create(self, mock_requests):
|
||||
self.assertEqual('http://testendpoint:9999/v1/actions/', self.action_manager.endpoint)
|
||||
self.assertEqual({'X-Auth-Token': 'testtoken'}, self.action_manager.headers)
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_create_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 201
|
||||
self.mock_response.json.return_value = {'action_id': 'qwerqwer'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
retval = self.action_manager.create({'action': 'metadata'})
|
||||
self.assertEqual('qwerqwer', retval)
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_create_fail_when_api_return_error_code(self, mock_requests):
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.action_manager.create, {'action': 'metadata'})
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_delete_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 204
|
||||
mock_requests.delete.return_value = self.mock_response
|
||||
retval = self.action_manager.delete('test_action_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_delete_fail(self, mock_requests):
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.delete.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.action_manager.delete, 'test_action_id')
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_get_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 200
|
||||
self.mock_response.json.return_value = {'action_id': 'qwerqwer'}
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
retval = self.action_manager.get('test_action_id')
|
||||
self.assertEqual({'action_id': 'qwerqwer'}, retval)
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_get_fails_on_error_different_from_404(self, mock_requests):
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.action_manager.get, 'test_action_id')
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_get_none(self, mock_requests):
|
||||
self.mock_response.status_code = 404
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
retval = self.action_manager.get('test_action_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_list_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 200
|
||||
action_list = [{'action_id_0': 'bomboloid'}, {'action_id_1': 'asdfasdf'}]
|
||||
self.mock_response.json.return_value = {'actions': action_list}
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
retval = self.action_manager.list()
|
||||
self.assertEqual(action_list, retval)
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_list_error(self, mock_requests):
|
||||
self.mock_response.status_code = 404
|
||||
action_list = [{'action_id_0': 'bomboloid'}, {'action_id_1': 'asdfasdf'}]
|
||||
self.mock_response.json.return_value = {'clients': action_list}
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.action_manager.list)
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_update_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 200
|
||||
self.mock_response.json.return_value = {
|
||||
"patch": {"status": "bamboozled"},
|
||||
"version": 12,
|
||||
"action_id": "d454beec-1f3c-4d11-aa1a-404116a40502"
|
||||
}
|
||||
mock_requests.patch.return_value = self.mock_response
|
||||
retval = self.action_manager.update('d454beec-1f3c-4d11-aa1a-404116a40502', {'status': 'bamboozled'})
|
||||
self.assertEqual(12, retval)
|
||||
|
||||
@patch('freezer.apiclient.actions.requests')
|
||||
def test_update_raise_MetadataUpdateFailure_when_api_return_error_code(self, mock_requests):
|
||||
self.mock_response.json.return_value = {
|
||||
"patch": {"status": "bamboozled"},
|
||||
"version": 12,
|
||||
"action_id": "d454beec-1f3c-4d11-aa1a-404116a40502"
|
||||
}
|
||||
self.mock_response.status_code = 404
|
||||
self.mock_response.text = '{"title": "Not Found","description":"No document found with ID d454beec-1f3c-4d11-aa1a-404116a40502x"}'
|
||||
mock_requests.patch.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.action_manager.update,
|
||||
'd454beec-1f3c-4d11-aa1a-404116a40502', {'status': 'bamboozled'})
|
|
@ -1,169 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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 unittest
|
||||
from mock import Mock, patch
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
from freezer.apiclient import backups
|
||||
|
||||
|
||||
class CallArgs(object):
|
||||
|
||||
def __init__(self, mock_obj=Mock()):
|
||||
self.args = mock_obj.call_args[0]
|
||||
self.kwargs = mock_obj.call_args[1]
|
||||
|
||||
def _check_arg(self, arg, value, load_json):
|
||||
if load_json:
|
||||
arg = json.loads(arg)
|
||||
if (arg != value):
|
||||
raise Exception("Argument doesn't match: {0} != {1}".format(arg, value))
|
||||
return
|
||||
|
||||
def check_arg(self, pos, value, load_json=False):
|
||||
if isinstance(pos, int):
|
||||
return self._check_arg(self.args[pos], value, load_json)
|
||||
return self._check_arg(self.kwargs[pos], value, load_json)
|
||||
|
||||
|
||||
class TestBackupManager(unittest.TestCase):
|
||||
|
||||
def setUp(self):
|
||||
self.mock_client = Mock()
|
||||
self.mock_client.client_id = "jumpingjack"
|
||||
self.mock_client.endpoint = 'http://testendpoint:9999'
|
||||
self.mock_client.auth_token = 'testtoken'
|
||||
self.b = backups.BackupsManager(self.mock_client)
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_create(self, mock_requests):
|
||||
self.assertEqual('http://testendpoint:9999/v1/backups/', self.b.endpoint)
|
||||
self.assertEqual({'X-Auth-Token': 'testtoken'}, self.b.headers)
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_create_ok(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 201
|
||||
mock_response.json.return_value = {'backup_id': 'qwerqwer'}
|
||||
mock_requests.post.return_value = mock_response
|
||||
retval = self.b.create(backup_metadata={'backup': 'metadata'})
|
||||
ca = CallArgs(mock_requests.post)
|
||||
ca.check_arg(0, 'http://testendpoint:9999/v1/backups/')
|
||||
ca.check_arg('data', {"backup": "metadata", "client_id": "jumpingjack"}, load_json=True)
|
||||
ca.check_arg('headers', {'X-Auth-Token': 'testtoken'})
|
||||
ca.check_arg('verify', True)
|
||||
self.assertEqual('qwerqwer', retval)
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_create_ok_with_client_id(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 201
|
||||
mock_response.json.return_value = {'backup_id': 'qwerqwer'}
|
||||
mock_requests.post.return_value = mock_response
|
||||
retval = self.b.create(backup_metadata={'backup': 'metadata', 'client_id': 'wahwah'})
|
||||
ca = CallArgs(mock_requests.post)
|
||||
ca.check_arg(0, 'http://testendpoint:9999/v1/backups/')
|
||||
ca.check_arg('data', {"backup": "metadata", "client_id": "wahwah"}, load_json=True)
|
||||
ca.check_arg('headers', {'X-Auth-Token': 'testtoken'})
|
||||
ca.check_arg('verify', True)
|
||||
self.assertEqual('qwerqwer', retval)
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_create_fail_when_api_return_error_code(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 500
|
||||
mock_requests.post.return_value = mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.b.create, {'backup': 'metadata'})
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_delete_ok(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 204
|
||||
mock_requests.delete.return_value = mock_response
|
||||
retval = self.b.delete('test_backup_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_delete_fail(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 500
|
||||
mock_requests.delete.return_value = mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.b.delete, 'test_backup_id')
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_get_ok(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 200
|
||||
mock_response.json.return_value = {'backup_id': 'qwerqwer'}
|
||||
mock_requests.get.return_value = mock_response
|
||||
retval = self.b.get('test_backup_id')
|
||||
self.assertEqual({'backup_id': 'qwerqwer'}, retval)
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_get_none(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 404
|
||||
mock_requests.get.return_value = mock_response
|
||||
retval = self.b.get('test_backup_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_get_error(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 403
|
||||
mock_requests.get.return_value = mock_response
|
||||
self.assertRaises(exceptions.ApiClientException,
|
||||
self.b.get, 'test_backup_id')
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_list_ok(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 200
|
||||
backup_list = [{'backup_id_0': 'qwerqwer'}, {'backup_id_1': 'asdfasdf'}]
|
||||
mock_response.json.return_value = {'backups': backup_list}
|
||||
mock_requests.get.return_value = mock_response
|
||||
retval = self.b.list()
|
||||
self.assertEqual(backup_list, retval)
|
||||
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_list_parameters(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 200
|
||||
backup_list = [{'backup_id_0': 'qwerqwer'}, {'backup_id_1': 'asdfasdf'}]
|
||||
mock_response.json.return_value = {'backups': backup_list}
|
||||
mock_requests.get.return_value = mock_response
|
||||
retval = self.b.list(limit=5,
|
||||
offset=5,
|
||||
search={"time_before": 1428529956})
|
||||
ca = CallArgs(mock_requests.get)
|
||||
ca.check_arg(0, 'http://testendpoint:9999/v1/backups/')
|
||||
ca.check_arg('data', {"time_before": 1428529956, "match": [{"client_id": "jumpingjack"}]}, load_json=True)
|
||||
ca.check_arg('headers', {'X-Auth-Token': 'testtoken'})
|
||||
ca.check_arg('verify', True)
|
||||
self.assertEqual(backup_list, retval)
|
||||
|
||||
@patch('freezer.apiclient.backups.requests')
|
||||
def test_list_error(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 404
|
||||
backup_list = [{'backup_id_0': 'qwerqwer'}, {'backup_id_1': 'asdfasdf'}]
|
||||
mock_response.json.return_value = {'backups': backup_list}
|
||||
mock_requests.get.return_value = mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.b.list)
|
|
@ -1,166 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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 unittest
|
||||
from mock import Mock, patch
|
||||
|
||||
from freezer.apiclient import client
|
||||
|
||||
|
||||
class TestSupportFunctions(unittest.TestCase):
|
||||
|
||||
@patch('freezer.apiclient.client.os')
|
||||
def test_env_return_env_var(self, mock_os):
|
||||
mock_os.environ = {'TEST_ENV_VAR': 'qwerty'}
|
||||
var = client.env('TEST_ENV_VAR')
|
||||
self.assertEqual('qwerty', var)
|
||||
|
||||
@patch('freezer.apiclient.client.os')
|
||||
def test_env_return_default(self, mock_os):
|
||||
mock_os.environ = {}
|
||||
var = client.env('TEST_ENV_VAR')
|
||||
self.assertEqual('', var)
|
||||
|
||||
def test_guess_auth_version_returns_none(self):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_identity_api_version = ''
|
||||
mock_opts.os_auth_url = ''
|
||||
self.assertRaises(Exception, client.guess_auth_version, mock_opts)
|
||||
|
||||
def test_guess_auth_version_explicit_3(self):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_identity_api_version = '3'
|
||||
self.assertEqual('3', client.guess_auth_version(mock_opts))
|
||||
|
||||
def test_guess_auth_version_explicit_2(self):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_identity_api_version = '2.0'
|
||||
self.assertEqual('2.0', client.guess_auth_version(mock_opts))
|
||||
|
||||
def test_guess_auth_version_implicit_3(self):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_auth_url = 'http://whatever/v3'
|
||||
self.assertEqual('3', client.guess_auth_version(mock_opts))
|
||||
|
||||
def test_guess_auth_version_implicit_2(self):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_auth_url = 'http://whatever/v2.0'
|
||||
self.assertEqual('2.0', client.guess_auth_version(mock_opts))
|
||||
|
||||
@patch('freezer.apiclient.client.v3')
|
||||
@patch('freezer.apiclient.client.v2')
|
||||
def test_get_auth_plugin_v3_Password(self, mock_v2, mock_v3):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_identity_api_version = '3'
|
||||
mock_opts.os_user_name = 'myuser'
|
||||
mock_opts.os_token = ''
|
||||
client.get_auth_plugin(mock_opts)
|
||||
self.assertTrue(mock_v3.Password.called)
|
||||
|
||||
@patch('freezer.apiclient.client.v3')
|
||||
@patch('freezer.apiclient.client.v2')
|
||||
def test_get_auth_plugin_v3_Token(self, mock_v2, mock_v3):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_identity_api_version = '3'
|
||||
mock_opts.os_username = ''
|
||||
mock_opts.os_token = 'mytoken'
|
||||
client.get_auth_plugin(mock_opts)
|
||||
self.assertTrue(mock_v3.Token.called)
|
||||
|
||||
@patch('freezer.apiclient.client.v3')
|
||||
@patch('freezer.apiclient.client.v2')
|
||||
def test_get_auth_plugin_v2_Password(self, mock_v2, mock_v3):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_identity_api_version = '2.0'
|
||||
mock_opts.os_user_name = 'myuser'
|
||||
mock_opts.os_token = ''
|
||||
client.get_auth_plugin(mock_opts)
|
||||
self.assertTrue(mock_v2.Password.called)
|
||||
|
||||
@patch('freezer.apiclient.client.v3')
|
||||
@patch('freezer.apiclient.client.v2')
|
||||
def test_get_auth_plugin_v2_Token(self, mock_v2, mock_v3):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_identity_api_version = '2.0'
|
||||
mock_opts.os_username = ''
|
||||
mock_opts.os_token = 'mytoken'
|
||||
client.get_auth_plugin(mock_opts)
|
||||
self.assertTrue(mock_v2.Token.called)
|
||||
|
||||
@patch('freezer.apiclient.client.v3')
|
||||
@patch('freezer.apiclient.client.v2')
|
||||
def test_get_auth_plugin_raises_when_no_username_token(self, mock_v2, mock_v3):
|
||||
mock_opts = Mock()
|
||||
mock_opts.os_identity_api_version = '2.0'
|
||||
mock_opts.os_username = ''
|
||||
mock_opts.os_token = ''
|
||||
self.assertRaises(Exception, client.get_auth_plugin, mock_opts)
|
||||
|
||||
|
||||
class TestClientMock(unittest.TestCase):
|
||||
|
||||
@patch('freezer.apiclient.client.ksa_session')
|
||||
@patch('freezer.apiclient.client.get_auth_plugin')
|
||||
def test_client_new(self, mock_get_auth_plugin, mock_ksa_session):
|
||||
c = client.Client(opts=Mock(), endpoint='blabla')
|
||||
self.assertIsInstance(c, client.Client)
|
||||
|
||||
@patch('freezer.apiclient.client.ksa_session')
|
||||
@patch('freezer.apiclient.client.get_auth_plugin')
|
||||
def test_client_new_with_kwargs(self, mock_get_auth_plugin, mock_ksa_session):
|
||||
kwargs = {'token': 'alpha',
|
||||
'username': 'bravo',
|
||||
'password': 'charlie',
|
||||
'tenant_name': 'delta',
|
||||
'auth_url': 'echo',
|
||||
'session': 'foxtrot',
|
||||
'endpoint': 'golf',
|
||||
'version': 'hotel',
|
||||
'cert': 'india',
|
||||
'insecure': 'juliet',
|
||||
'opts': Mock()}
|
||||
c = client.Client(**kwargs)
|
||||
self.assertIsInstance(c, client.Client)
|
||||
self.assertEqual('alpha', c.opts.os_token)
|
||||
self.assertEqual('bravo', c.opts.os_username)
|
||||
self.assertEqual('charlie', c.opts.os_password)
|
||||
self.assertEqual('delta', c.opts.os_tenant_name)
|
||||
self.assertEqual('echo', c.opts.os_auth_url)
|
||||
self.assertEqual('foxtrot', c._session)
|
||||
self.assertEqual('foxtrot', c.session)
|
||||
self.assertEqual('golf', c.endpoint)
|
||||
self.assertEqual('hotel', c.version)
|
||||
|
||||
@patch('freezer.apiclient.client.ksa_session')
|
||||
@patch('freezer.apiclient.client.get_auth_plugin')
|
||||
def test_get_token(self, mock_get_auth_plugin, mock_ksa_session):
|
||||
mock_session = Mock()
|
||||
mock_session.get_token.return_value = 'antaniX2'
|
||||
c = client.Client(session=mock_session, endpoint='justtest', opts=Mock())
|
||||
self.assertIsInstance(c, client.Client)
|
||||
self.assertEqual('antaniX2', c.auth_token)
|
||||
|
||||
@patch('freezer.apiclient.client.socket')
|
||||
@patch('freezer.apiclient.client.ksa_session')
|
||||
@patch('freezer.apiclient.client.get_auth_plugin')
|
||||
def test_get_client_id(self, mock_get_auth_plugin, mock_ksa_session, mock_socket):
|
||||
mock_socket.gethostname.return_value = 'parmenide'
|
||||
mock_session = Mock()
|
||||
mock_session.get_project_id.return_value = 'H2O'
|
||||
c = client.Client(session=mock_session, endpoint='justtest', opts=Mock())
|
||||
self.assertIsInstance(c, client.Client)
|
||||
self.assertEqual('H2O_parmenide', c.client_id)
|
|
@ -1,25 +0,0 @@
|
|||
# (c) Copyright 2014,2015 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 unittest
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
|
||||
|
||||
class TestApiClientException(unittest.TestCase):
|
||||
|
||||
def test_get_message_from_response_string(self):
|
||||
e = exceptions.ApiClientException('some error message')
|
||||
self.assertEqual(str(e), 'some error message')
|
|
@ -1,240 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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 unittest
|
||||
from mock import Mock, patch
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
from freezer.apiclient import jobs
|
||||
|
||||
|
||||
class TestJobManager(unittest.TestCase):
|
||||
|
||||
def setUp(self):
|
||||
self.mock_client = Mock()
|
||||
self.mock_response = Mock()
|
||||
self.mock_client.endpoint = 'http://testendpoint:9999'
|
||||
self.mock_client.auth_token = 'testtoken'
|
||||
self.headers = {'X-Auth-Token': 'testtoken'}
|
||||
self.mock_client.client_id = 'test_client_id_78900987'
|
||||
self.job_manager = jobs.JobManager(self.mock_client)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_create(self, mock_requests):
|
||||
self.assertEqual('http://testendpoint:9999/v1/jobs/', self.job_manager.endpoint)
|
||||
self.assertEqual({'X-Auth-Token': 'testtoken'}, self.job_manager.headers)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_create_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 201
|
||||
self.mock_response.json.return_value = {'job_id': 'qwerqwer'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
retval = self.job_manager.create({'job': 'metadata'})
|
||||
self.assertEqual('qwerqwer', retval)
|
||||
|
||||
@patch('freezer.apiclient.jobs.json')
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_create_adds_client_id_if_not_provided(self, mock_requests, mock_json):
|
||||
self.mock_response.status_code = 201
|
||||
self.mock_response.json.return_value = {'job_id': 'qwerqwer'}
|
||||
mock_json.dumps.return_value = {'job': 'mocked'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
|
||||
retval = self.job_manager.create({'job': 'metadata'})
|
||||
|
||||
mock_json.dumps.assert_called_with({'job': 'metadata',
|
||||
'client_id': 'test_client_id_78900987'})
|
||||
self.assertEqual('qwerqwer', retval)
|
||||
|
||||
@patch('freezer.apiclient.jobs.json')
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_create_leaves_provided_client_id(self, mock_requests, mock_json):
|
||||
self.mock_response.status_code = 201
|
||||
self.mock_response.json.return_value = {'job_id': 'qwerqwer'}
|
||||
mock_json.dumps.return_value = {'job': 'mocked'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
|
||||
retval = self.job_manager.create({'job': 'metadata', 'client_id': 'parmenide'})
|
||||
|
||||
mock_json.dumps.assert_called_with({'job': 'metadata',
|
||||
'client_id': 'parmenide'})
|
||||
self.assertEqual('qwerqwer', retval)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_create_fail_when_api_return_error_code(self, mock_requests):
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.job_manager.create, {'job': 'metadata'})
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_delete_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 204
|
||||
mock_requests.delete.return_value = self.mock_response
|
||||
retval = self.job_manager.delete('test_job_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_delete_fail(self, mock_requests):
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.delete.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.job_manager.delete, 'test_job_id')
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_get_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 200
|
||||
self.mock_response.json.return_value = {'job_id': 'qwerqwer'}
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
retval = self.job_manager.get('test_job_id')
|
||||
self.assertEqual({'job_id': 'qwerqwer'}, retval)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_get_fails_on_error_different_from_404(self, mock_requests):
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.job_manager.get, 'test_job_id')
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_get_none(self, mock_requests):
|
||||
self.mock_response.status_code = 404
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
retval = self.job_manager.get('test_job_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_list_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 200
|
||||
job_list = [{'job_id_0': 'bomboloid'}, {'job_id_1': 'asdfasdf'}]
|
||||
self.mock_response.json.return_value = {'jobs': job_list}
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
retval = self.job_manager.list()
|
||||
self.assertEqual(job_list, retval)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_list_error(self, mock_requests):
|
||||
self.mock_response.status_code = 404
|
||||
job_list = [{'job_id_0': 'bomboloid'}, {'job_id_1': 'asdfasdf'}]
|
||||
self.mock_response.json.return_value = {'clients': job_list}
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.job_manager.list)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_update_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 200
|
||||
self.mock_response.json.return_value = {
|
||||
"patch": {"status": "bamboozled"},
|
||||
"version": 12,
|
||||
"job_id": "d454beec-1f3c-4d11-aa1a-404116a40502"
|
||||
}
|
||||
mock_requests.patch.return_value = self.mock_response
|
||||
retval = self.job_manager.update('d454beec-1f3c-4d11-aa1a-404116a40502', {'status': 'bamboozled'})
|
||||
self.assertEqual(12, retval)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_update_raise_MetadataUpdateFailure_when_api_return_error_code(self, mock_requests):
|
||||
self.mock_response.json.return_value = {
|
||||
"patch": {"status": "bamboozled"},
|
||||
"version": 12,
|
||||
"job_id": "d454beec-1f3c-4d11-aa1a-404116a40502"
|
||||
}
|
||||
self.mock_response.status_code = 404
|
||||
self.mock_response.text = '{"title": "Not Found","description":"No document found with ID d454beec-1f3c-4d11-aa1a-404116a40502x"}'
|
||||
mock_requests.patch.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.job_manager.update,
|
||||
'd454beec-1f3c-4d11-aa1a-404116a40502', {'status': 'bamboozled'})
|
||||
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_start_job_posts_proper_data(self, mock_requests):
|
||||
job_id = 'jobdfsfnqwerty1234'
|
||||
self.mock_response.status_code = 202
|
||||
self.mock_response.json.return_value = {'result': 'success'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
# /v1/jobs/{job_id}/event
|
||||
|
||||
endpoint = '{0}/v1/jobs/{1}/event'.format(self.mock_client.endpoint, job_id)
|
||||
data = {"start": None}
|
||||
retval = self.job_manager.start_job(job_id)
|
||||
self.assertEqual({'result': 'success'}, retval)
|
||||
|
||||
args = mock_requests.post.call_args[0]
|
||||
kwargs = mock_requests.post.call_args[1]
|
||||
self.assertEqual(endpoint, args[0])
|
||||
self.assertEqual(data, json.loads(kwargs['data']))
|
||||
self.assertEqual(self.headers, kwargs['headers'])
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_start_job_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
job_id = 'jobdfsfnqwerty1234'
|
||||
self.mock_response.status_code = 500
|
||||
self.mock_response.json.return_value = {'result': 'success'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.job_manager.start_job, job_id)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_stop_job_posts_proper_data(self, mock_requests):
|
||||
job_id = 'jobdfsfnqwerty1234'
|
||||
self.mock_response.status_code = 202
|
||||
self.mock_response.json.return_value = {'result': 'success'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
# /v1/jobs/{job_id}/event
|
||||
|
||||
endpoint = '{0}/v1/jobs/{1}/event'.format(self.mock_client.endpoint, job_id)
|
||||
data = {"stop": None}
|
||||
retval = self.job_manager.stop_job(job_id)
|
||||
self.assertEqual({'result': 'success'}, retval)
|
||||
|
||||
args = mock_requests.post.call_args[0]
|
||||
kwargs = mock_requests.post.call_args[1]
|
||||
self.assertEqual(endpoint, args[0])
|
||||
self.assertEqual(data, json.loads(kwargs['data']))
|
||||
self.assertEqual(self.headers, kwargs['headers'])
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_stop_job_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
job_id = 'jobdfsfnqwerty1234'
|
||||
self.mock_response.status_code = 500
|
||||
self.mock_response.json.return_value = {'result': 'success'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.job_manager.start_job, job_id)
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_abort_job_posts_proper_data(self, mock_requests):
|
||||
job_id = 'jobdfsfnqwerty1234'
|
||||
self.mock_response.status_code = 202
|
||||
self.mock_response.json.return_value = {'result': 'success'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
# /v1/jobs/{job_id}/event
|
||||
|
||||
endpoint = '{0}/v1/jobs/{1}/event'.format(self.mock_client.endpoint, job_id)
|
||||
data = {"abort": None}
|
||||
retval = self.job_manager.abort_job(job_id)
|
||||
self.assertEqual({'result': 'success'}, retval)
|
||||
|
||||
args = mock_requests.post.call_args[0]
|
||||
kwargs = mock_requests.post.call_args[1]
|
||||
self.assertEqual(endpoint, args[0])
|
||||
self.assertEqual(data, json.loads(kwargs['data']))
|
||||
self.assertEqual(self.headers, kwargs['headers'])
|
||||
|
||||
@patch('freezer.apiclient.jobs.requests')
|
||||
def test_abort_job_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
job_id = 'jobdfsfnqwerty1234'
|
||||
self.mock_response.status_code = 500
|
||||
self.mock_response.json.return_value = {'result': 'success'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.job_manager.abort_job, job_id)
|
|
@ -1,111 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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 unittest
|
||||
from mock import Mock, patch
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
from freezer.apiclient import registration
|
||||
|
||||
|
||||
class TestRegistrationManager(unittest.TestCase):
|
||||
|
||||
def setUp(self):
|
||||
self.mock_client = Mock()
|
||||
self.mock_client.endpoint = 'http://testendpoint:9999'
|
||||
self.mock_client.auth_token = 'testtoken'
|
||||
self.r = registration.RegistrationManager(self.mock_client)
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_create(self, mock_requests):
|
||||
self.assertEqual('http://testendpoint:9999/v1/clients/', self.r.endpoint)
|
||||
self.assertEqual({'X-Auth-Token': 'testtoken'}, self.r.headers)
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_create_ok(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 201
|
||||
mock_response.json.return_value = {'client_id': 'qwerqwer'}
|
||||
mock_requests.post.return_value = mock_response
|
||||
retval = self.r.create(client_info={'client': 'metadata'})
|
||||
self.assertEqual('qwerqwer', retval)
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_create_fail_when_api_return_error_code(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 500
|
||||
mock_requests.post.return_value = mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.r.create, {'client': 'metadata'})
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_delete_ok(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 204
|
||||
mock_requests.delete.return_value = mock_response
|
||||
retval = self.r.delete('test_client_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_delete_fail(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 500
|
||||
mock_requests.delete.return_value = mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.r.delete, 'test_client_id')
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_get_ok(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 200
|
||||
mock_response.json.return_value = {'client_id': 'qwerqwer'}
|
||||
mock_requests.get.return_value = mock_response
|
||||
retval = self.r.get('test_client_id')
|
||||
self.assertEqual({'client_id': 'qwerqwer'}, retval)
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_get_none(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 404
|
||||
mock_requests.get.return_value = mock_response
|
||||
retval = self.r.get('test_client_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_get_raises_ApiClientException_on_error_not_404(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 500
|
||||
mock_requests.get.return_value = mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.r.get, 'test_client_id')
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_list_ok(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 200
|
||||
client_list = [{'client_id_0': 'qwerqwer'}, {'client_id_1': 'asdfasdf'}]
|
||||
mock_response.json.return_value = {'clients': client_list}
|
||||
mock_requests.get.return_value = mock_response
|
||||
retval = self.r.list()
|
||||
self.assertEqual(client_list, retval)
|
||||
|
||||
@patch('freezer.apiclient.registration.requests')
|
||||
def test_list_error(self, mock_requests):
|
||||
mock_response = Mock()
|
||||
mock_response.status_code = 404
|
||||
client_list = [{'client_id_0': 'qwerqwer'}, {'client_id_1': 'asdfasdf'}]
|
||||
mock_response.json.return_value = {'clients': client_list}
|
||||
mock_requests.get.return_value = mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.r.list)
|
||||
|
|
@ -1,223 +0,0 @@
|
|||
"""
|
||||
Copyright 2015 Hewlett-Packard
|
||||
|
||||
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 unittest
|
||||
from mock import Mock, patch
|
||||
|
||||
from freezer.apiclient import exceptions
|
||||
from freezer.apiclient import sessions
|
||||
|
||||
|
||||
class TestSessionManager(unittest.TestCase):
|
||||
|
||||
def setUp(self):
|
||||
self.mock_client = Mock()
|
||||
self.mock_response = Mock()
|
||||
self.mock_client.endpoint = 'http://testendpoint:9999'
|
||||
self.mock_client.auth_token = 'testtoken'
|
||||
self.mock_client.client_id = 'test_client_id_78900987'
|
||||
self.session_manager = sessions.SessionManager(self.mock_client)
|
||||
self.endpoint = 'http://testendpoint:9999/v1/sessions/'
|
||||
self.headers = {'X-Auth-Token': 'testtoken'}
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_create(self, mock_requests):
|
||||
self.assertEqual(self.endpoint, self.session_manager.endpoint)
|
||||
self.assertEqual(self.headers, self.session_manager.headers)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_create_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 201
|
||||
self.mock_response.json.return_value = {'session_id': 'qwerqwer'}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
retval = self.session_manager.create({'session': 'metadata'})
|
||||
self.assertEqual('qwerqwer', retval)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_create_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.session_manager.create, {'session': 'metadata'})
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_delete_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 204
|
||||
mock_requests.delete.return_value = self.mock_response
|
||||
retval = self.session_manager.delete('test_session_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_delete_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.delete.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.session_manager.delete, 'test_session_id')
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_get_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 200
|
||||
self.mock_response.json.return_value = {'session_id': 'qwerqwer'}
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
retval = self.session_manager.get('test_session_id')
|
||||
self.assertEqual({'session_id': 'qwerqwer'}, retval)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_get_raise_ApiClientException_when_api_return_error_different_from_404(self, mock_requests):
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.session_manager.get, 'test_session_id')
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_get_none(self, mock_requests):
|
||||
self.mock_response.status_code = 404
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
retval = self.session_manager.get('test_session_id')
|
||||
self.assertIsNone(retval)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_list_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 200
|
||||
session_list = [{'session_id_0': 'bomboloid'}, {'session_id_1': 'asdfasdf'}]
|
||||
self.mock_response.json.return_value = {'sessions': session_list}
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
retval = self.session_manager.list()
|
||||
self.assertEqual(session_list, retval)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_list_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
self.mock_response.status_code = 404
|
||||
session_list = [{'session_id_0': 'bomboloid'}, {'session_id_1': 'asdfasdf'}]
|
||||
self.mock_response.json.return_value = {'clients': session_list}
|
||||
mock_requests.get.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.session_manager.list)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_update_ok(self, mock_requests):
|
||||
self.mock_response.status_code = 200
|
||||
self.mock_response.json.return_value = {
|
||||
"patch": {"status": "bamboozled"},
|
||||
"version": 12,
|
||||
"session_id": "d454beec-1f3c-4d11-aa1a-404116a40502"
|
||||
}
|
||||
mock_requests.patch.return_value = self.mock_response
|
||||
retval = self.session_manager.update('d454beec-1f3c-4d11-aa1a-404116a40502', {'status': 'bamboozled'})
|
||||
self.assertEqual(12, retval)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_update_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
self.mock_response.json.return_value = {
|
||||
"patch": {"status": "bamboozled"},
|
||||
"version": 12,
|
||||
"session_id": "d454beec-1f3c-4d11-aa1a-404116a40502"
|
||||
}
|
||||
self.mock_response.status_code = 404
|
||||
self.mock_response.text = '{"title": "Not Found","description":"No document found with ID d454beec-1f3c-4d11-aa1a-404116a40502x"}'
|
||||
mock_requests.patch.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.session_manager.update,
|
||||
'd454beec-1f3c-4d11-aa1a-404116a40502', {'status': 'bamboozled'})
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_add_job_uses_proper_endpoint(self, mock_requests):
|
||||
session_id, job_id = 'sessionqwerty1234', 'jobqwerty1234'
|
||||
self.mock_response.status_code = 204
|
||||
mock_requests.put.return_value = self.mock_response
|
||||
endpoint = '{0}{1}/jobs/{2}'.format(self.endpoint, session_id, job_id)
|
||||
|
||||
retval = self.session_manager.add_job(session_id, job_id)
|
||||
|
||||
self.assertIsNone(retval)
|
||||
mock_requests.put.assert_called_with(endpoint, headers=self.headers, verify=True)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_add_job_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
session_id, job_id = 'sessionqwerty1234', 'jobqwerty1234'
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.put.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.session_manager.add_job, session_id, job_id)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_remove_job_uses_proper_endpoint(self, mock_requests):
|
||||
session_id, job_id = 'sessionqwerty1234', 'jobqwerty1234'
|
||||
self.mock_response.status_code = 204
|
||||
mock_requests.delete.return_value = self.mock_response
|
||||
endpoint = '{0}{1}/jobs/{2}'.format(self.endpoint, session_id, job_id)
|
||||
|
||||
retval = self.session_manager.remove_job(session_id, job_id)
|
||||
|
||||
self.assertIsNone(retval)
|
||||
mock_requests.delete.assert_called_with(endpoint, headers=self.headers, verify=True)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_remove_job_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
session_id, job_id = 'sessionqwerty1234', 'jobqwerty1234'
|
||||
self.mock_response.status_code = 500
|
||||
mock_requests.delete.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.session_manager.remove_job, session_id, job_id)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_start_session_posts_proper_data(self, mock_requests):
|
||||
session_id, job_id, tag = 'sessionqwerty1234', 'jobqwerty1234', 23
|
||||
self.mock_response.status_code = 202
|
||||
self.mock_response.json.return_value = {'result': 'success', 'session_tag': 24}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
# /v1/sessions/{sessions_id}/action
|
||||
endpoint = '{0}{1}/action'.format(self.endpoint, session_id)
|
||||
data = {"start": {"current_tag": 23, "job_id": "jobqwerty1234"}}
|
||||
retval = self.session_manager.start_session(session_id, job_id, tag)
|
||||
self.assertEqual({'result': 'success', 'session_tag': 24}, retval)
|
||||
|
||||
args = mock_requests.post.call_args[0]
|
||||
kwargs = mock_requests.post.call_args[1]
|
||||
self.assertEqual(endpoint, args[0])
|
||||
self.assertEqual(data, json.loads(kwargs['data']))
|
||||
self.assertEqual(self.headers, kwargs['headers'])
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_start_session_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
session_id, job_id, tag = 'sessionqwerty1234', 'jobqwerty1234', 23
|
||||
self.mock_response.status_code = 500
|
||||
self.mock_response.json.return_value = {'result': 'success', 'session_tag': 24}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.session_manager.start_session,
|
||||
session_id, job_id, tag)
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_end_session_posts_proper_data(self, mock_requests):
|
||||
session_id, job_id, tag = 'sessionqwerty1234', 'jobqwerty1234', 23
|
||||
self.mock_response.status_code = 202
|
||||
self.mock_response.json.return_value = {'result': 'success', 'session_tag': 24}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
# /v1/sessions/{sessions_id}/action
|
||||
endpoint = '{0}{1}/action'.format(self.endpoint, session_id)
|
||||
data = {"end": {"current_tag": 23, "job_id": "jobqwerty1234", "result": "fail"}}
|
||||
retval = self.session_manager.end_session(session_id, job_id, tag, 'fail')
|
||||
self.assertEqual({'result': 'success', 'session_tag': 24}, retval)
|
||||
|
||||
args = mock_requests.post.call_args[0]
|
||||
kwargs = mock_requests.post.call_args[1]
|
||||
self.assertEqual(endpoint, args[0])
|
||||
self.assertEqual(data, json.loads(kwargs['data']))
|
||||
self.assertEqual(self.headers, kwargs['headers'])
|
||||
|
||||
@patch('freezer.apiclient.sessions.requests')
|
||||
def test_end_session_raise_ApiClientException_when_api_return_error_code(self, mock_requests):
|
||||
session_id, job_id, tag = 'sessionqwerty1234', 'jobqwerty1234', 23
|
||||
self.mock_response.status_code = 500
|
||||
self.mock_response.json.return_value = {'result': 'success', 'session_tag': 24}
|
||||
mock_requests.post.return_value = self.mock_response
|
||||
self.assertRaises(exceptions.ApiClientException, self.session_manager.end_session,
|
||||
session_id, job_id, tag, 'fail')
|
|
@ -9,6 +9,7 @@ python-cinderclient!=1.7.0,!=1.7.1,>=1.6.0 # Apache-2.0
|
|||
python-glanceclient>=2.5.0 # Apache-2.0
|
||||
python-novaclient!=2.33.0,>=2.29.0 # Apache-2.0
|
||||
python-openstackclient>=3.3.0 # Apache-2.0
|
||||
python-freezerclient>=1.0.0 # Apache-2.0
|
||||
oslo.utils>=3.18.0 # Apache-2.0
|
||||
oslo.i18n>=2.1.0 # Apache-2.0
|
||||
oslo.log>=3.11.0 # Apache-2.0
|
||||
|
@ -24,3 +25,4 @@ six>=1.9.0 # MIT
|
|||
apscheduler # MIT License
|
||||
|
||||
psutil<2.0.0,>=1.1.1 # BSD
|
||||
|
||||
|
|
Loading…
Reference in New Issue