Commit 4a60c2bd authored by David Mendez's avatar David Mendez
Browse files

Merge branch 'staging' into 'master'

Job Status: show times in ISO format

See merge request !70
parents 24a91708 0bc7a36d
......@@ -3,6 +3,7 @@ Tests for the status namespace
"""
import json
import unittest
import datetime
from app import create_app
from app.authorisation import token_generator
......@@ -45,12 +46,20 @@ class TestStatus(unittest.TestCase):
response = client.get(f'/status/{job_id}')
resp_data = json.loads(response.data.decode('utf-8'))
for prop in ['type', 'status', 'status_log', 'progress', 'created_at', 'started_at', 'finished_at',
'raw_params', 'expires_at', 'api_initial_url', 'docker_image_url', 'timezone', 'num_failures',
for prop in ['type', 'status', 'status_log', 'progress', 'raw_params', 'api_initial_url',
'docker_image_url', 'timezone', 'num_failures',
'status_description']:
type_must_be = str(getattr(job_must_be, prop))
type_got = resp_data[prop]
self.assertEqual(type_must_be, type_got, msg=f'The returned job {prop} is not correct.')
value_must_be = str(getattr(job_must_be, prop))
value_got = resp_data[prop]
self.assertEqual(value_must_be, value_got, msg=f'The returned job {prop} is not correct.')
for prop in ['created_at', 'started_at', 'finished_at', 'expires_at']:
raw_value = getattr(job_must_be, prop)
value_must_be = raw_value
if raw_value is not None:
value_must_be = raw_value.replace(tzinfo=datetime.timezone.utc).isoformat()
value_got = resp_data[prop]
self.assertEqual(value_must_be, value_got, msg=f'The returned job {prop} is not correct.')
def test_get_non_existing_job_status(self):
"""
......
......@@ -103,6 +103,18 @@ class OutputFile(DB.Model):
job_id = DB.Column(DB.String(length=120), DB.ForeignKey('delayed_job.id'), nullable=False)
def standardise_public_date(public_time):
"""
All the times in the server are assumed to be UTC
:param public_time: time to make public
:return: a string with the iso format of the date passed as parameter
"""
if public_time is None:
return None
return public_time.replace(tzinfo=datetime.timezone.utc).isoformat()
class DelayedJob(DB.Model):
"""
Class that represents a delayed job in the database.
......@@ -140,9 +152,7 @@ class DelayedJob(DB.Model):
:param server_base_url: url to use as base for building the output files urls
"""
plain_properties = {key: str(getattr(self, key)) for key in ['id', 'type', 'status', 'status_log', 'progress',
'created_at', 'started_at', 'finished_at',
'raw_params',
'expires_at', 'api_initial_url',
'raw_params', 'api_initial_url',
'docker_image_url',
'timezone', 'num_failures', 'status_description']}
......@@ -151,6 +161,10 @@ class DelayedJob(DB.Model):
return {
**plain_properties,
'created_at': standardise_public_date(self.created_at),
'started_at': standardise_public_date(self.started_at),
'finished_at': standardise_public_date(self.finished_at),
'expires_at': standardise_public_date(self.expires_at),
'input_files_urls': input_files_urls,
'output_files_urls': output_files_urls
}
......
......@@ -34,7 +34,7 @@ def run_test(server_base_url, admin_username, admin_password):
started_at_0, job_status = get_job_started_at_and_status(server_base_url, job_id)
assert job_status == 'ERROR', 'Job should have failed!'
max_retries = 7 # The server only allows to retry a job 6 times
max_retries = 7 # The server only allows to retry a job 6 times
retries = 0
previous_started_at_time = started_at_0
original_job_id = job_id
......@@ -53,7 +53,7 @@ def run_test(server_base_url, admin_username, admin_password):
print('Waiting until job fails')
started_at_1 = assert_job_must_have_not_been_started_with_retries(server_base_url, job_id, retries, max_retries,
previous_started_at_time)
previous_started_at_time)
previous_started_at_time = started_at_1
......@@ -61,8 +61,8 @@ def run_test(server_base_url, admin_username, admin_password):
shutil.rmtree(tmp_dir)
def submit_job_and_confirm(server_base_url, test_job_to_submit):
def submit_job_and_confirm(server_base_url, test_job_to_submit):
submit_url = utils.get_submit_url(server_base_url)
print('submit_url: ', submit_url)
submit_request = requests.post(submit_url, data=test_job_to_submit['payload'],
......@@ -77,8 +77,8 @@ def submit_job_and_confirm(server_base_url, test_job_to_submit):
return job_id
def get_job_started_at_and_status(server_base_url, job_id):
def get_job_started_at_and_status(server_base_url, job_id):
status_url = utils.get_status_url(server_base_url, job_id)
print('status_url: ', status_url)
......@@ -87,7 +87,7 @@ def get_job_started_at_and_status(server_base_url, job_id):
status_request = requests.get(status_url)
status_response = status_request.json()
started_at = datetime.datetime.strptime(status_response.get('started_at'), '%Y-%m-%d %H:%M:%S.%f')
started_at = datetime.datetime.fromisoformat(status_response.get('started_at'))
print(f'started_at: {started_at}')
job_status = status_response.get('status')
......@@ -95,8 +95,8 @@ def get_job_started_at_and_status(server_base_url, job_id):
return started_at, job_status
def get_job_started_at_and_assert_status_with_retries(server_base_url, job_id):
def get_job_started_at_and_assert_status_with_retries(server_base_url, job_id):
status_url = utils.get_status_url(server_base_url, job_id)
utils.assert_job_status_with_retries(status_url, 'ERROR')
......@@ -105,6 +105,7 @@ def get_job_started_at_and_assert_status_with_retries(server_base_url, job_id):
return started_at_1
def assert_job_must_have_not_been_started_with_retries(server_base_url, job_id, job_retries, max_job_retries,
previous_started_at_time):
max_test_retries = 1000
......@@ -134,6 +135,6 @@ def assert_job_must_have_not_been_started_with_retries(server_base_url, job_id,
assert assertion_passed, 'The job must have started again'
else:
assert assertion_passed, 'The job must have NOT started again, ' \
'max retries have been reached'
'max retries have been reached'
return started_at_1
\ No newline at end of file
return started_at_1
......@@ -48,7 +48,7 @@ def run_test(server_base_url, admin_username, admin_password):
status_response = status_request.json()
print('status_response: ', status_response)
started_at_0 = datetime.datetime.strptime(status_response.get('started_at'), '%Y-%m-%d %H:%M:%S.%f')
started_at_0 = datetime.datetime.fromisoformat(status_response.get('started_at'))
timestamp_0 = started_at_0.timestamp()
print(f'timestamp_0: {timestamp_0}')
print(f'started_at_0: {started_at_0}')
......@@ -71,7 +71,7 @@ def run_test(server_base_url, admin_username, admin_password):
status_response = status_request.json()
print('status_response: ', status_response)
started_at_1 = datetime.datetime.strptime(status_response.get('started_at'), '%Y-%m-%d %H:%M:%S.%f')
started_at_1 = datetime.datetime.fromisoformat(status_response.get('started_at'))
timestamp_1 = started_at_1.timestamp()
print(f'timestamp_1: {timestamp_1}')
print(f'started_at_1: {started_at_1}')
......
......@@ -46,7 +46,7 @@ def run_test(server_base_url, admin_username, admin_password):
status_request = requests.get(status_url)
status_response = status_request.json()
print('status_response: ', status_response)
started_at_0 = datetime.datetime.strptime(status_response.get('started_at'), '%Y-%m-%d %H:%M:%S.%f')
started_at_0 = datetime.datetime.fromisoformat(status_response.get('started_at'))
timestamp_0 = started_at_0.timestamp()
print(f'timestamp_0: {timestamp_0}')
print(f'started_at_0: {started_at_0}')
......@@ -69,7 +69,7 @@ def run_test(server_base_url, admin_username, admin_password):
status_response = status_request.json()
print('status_response: ', status_response)
started_at_1 = datetime.datetime.strptime(status_response.get('started_at'), '%Y-%m-%d %H:%M:%S.%f')
started_at_1 = datetime.datetime.fromisoformat(status_response.get('started_at'))
timestamp_1 = started_at_1.timestamp()
print(f'timestamp_1: {timestamp_1}')
print(f'started_at_1: {started_at_1}')
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment