Handle 503 status (maintenance mode)

This commit is contained in:
Marcin Kulik
2013-10-14 18:13:36 +02:00
parent fc526a4ffa
commit fe60ee75e3
4 changed files with 43 additions and 15 deletions

View File

@@ -1,7 +1,8 @@
import sys
import subprocess import subprocess
from asciinema.recorder import Recorder from asciinema.recorder import Recorder
from asciinema.uploader import Uploader from asciinema.uploader import Uploader, ServerMaintenanceError
from asciinema.confirmator import Confirmator from asciinema.confirmator import Confirmator
@@ -44,8 +45,9 @@ class RecordCommand(object):
try: try:
url = self.uploader.upload(self.api_url, self.api_token, asciicast) url = self.uploader.upload(self.api_url, self.api_token, asciicast)
print(url) print(url)
except SystemExit: except ServerMaintenanceError:
print('~ Error during upload. Try again in a minute.') print('~ Upload failed: The server is down for maintenance. Try again in a minute.')
sys.exit(1)
def _upload_confirmed(self): def _upload_confirmed(self):
if self.skip_confirmation: if self.skip_confirmation:

View File

@@ -7,6 +7,10 @@ from asciinema import __version__
from .requests_http_adapter import RequestsHttpAdapter from .requests_http_adapter import RequestsHttpAdapter
class ServerMaintenanceError(Exception):
pass
class Uploader(object): class Uploader(object):
def __init__(self, http_adapter=None): def __init__(self, http_adapter=None):
@@ -19,6 +23,8 @@ class Uploader(object):
status, headers, body = self.http_adapter.post(url, files=files, status, headers, body = self.http_adapter.post(url, files=files,
headers=headers) headers=headers)
if status == 503:
raise ServerMaintenanceError()
return body return body

View File

@@ -1,8 +1,9 @@
import sys import sys
import subprocess import subprocess
from nose.tools import assert_equal from nose.tools import assert_equal, assert_raises
from asciinema.commands.record import RecordCommand from asciinema.commands.record import RecordCommand
from asciinema.uploader import ServerMaintenanceError
from .test_helper import assert_printed, assert_not_printed, Test, FakeAsciicast from .test_helper import assert_printed, assert_not_printed, Test, FakeAsciicast
@@ -18,10 +19,14 @@ class FakeRecorder(object):
class FakeUploader(object): class FakeUploader(object):
def __init__(self): def __init__(self, raises=False):
self.uploaded = None self.uploaded = None
self.raises = raises
def upload(self, api_url, api_token, asciicast): def upload(self, api_url, api_token, asciicast):
if self.raises:
raise ServerMaintenanceError()
self.uploaded = [api_url, api_token, asciicast] self.uploaded = [api_url, api_token, asciicast]
return 'http://asciicast/url' return 'http://asciicast/url'
@@ -82,6 +87,13 @@ class TestRecordCommand(Test):
assert 'Do you want to upload' in self.confirmator.text assert 'Do you want to upload' in self.confirmator.text
self.assert_recorded_but_not_uploaded() self.assert_recorded_but_not_uploaded()
def test_execute_when_server_in_maintenance_mode(self):
self.uploader = FakeUploader(True)
command = self.create_command(True)
assert_raises(SystemExit, command.execute)
assert_printed('maintenance')
def assert_recorded_but_not_uploaded(self): def assert_recorded_but_not_uploaded(self):
asciicast = self.recorder.asciicast asciicast = self.recorder.asciicast
assert asciicast, 'asciicast not recorded' assert asciicast, 'asciicast not recorded'

View File

@@ -1,15 +1,16 @@
import json import json
import bz2 import bz2
import platform import platform
from nose.tools import assert_equal from nose.tools import assert_equal, assert_raises
from .test_helper import Test, FakeAsciicast from .test_helper import Test, FakeAsciicast
from asciinema import __version__ from asciinema import __version__
from asciinema.uploader import Uploader from asciinema.uploader import Uploader, ServerMaintenanceError
class FakeHttpAdapter(object): class FakeHttpAdapter(object):
def __init__(self): def __init__(self, status):
self.status = status
self.url = None self.url = None
self.files = None self.files = None
self.headers = None self.headers = None
@@ -19,7 +20,7 @@ class FakeHttpAdapter(object):
self.files = files self.files = files
self.headers = headers self.headers = headers
return (200, { 'Content-type': 'text/plain' }, b'success!') return (self.status, { 'Content-type': 'text/plain' }, b'success!')
class FakeStdout(object): class FakeStdout(object):
@@ -33,7 +34,6 @@ class TestUploader(Test):
def setUp(self): def setUp(self):
Test.setUp(self) Test.setUp(self)
self.http_adapter = FakeHttpAdapter()
self.stdout = FakeStdout(b'data123', b'timing456') self.stdout = FakeStdout(b'data123', b'timing456')
self.asciicast = FakeAsciicast(cmd='ls -l', title='tit', self.asciicast = FakeAsciicast(cmd='ls -l', title='tit',
stdout=self.stdout, meta_data={ 'shell': '/bin/sh' }) stdout=self.stdout, meta_data={ 'shell': '/bin/sh' })
@@ -44,15 +44,23 @@ class TestUploader(Test):
Test.tearDown(self) Test.tearDown(self)
platform.platform = self.real_platform platform.platform = self.real_platform
def test_upload(self): def test_upload_when_status_201_returned(self):
uploader = Uploader(self.http_adapter) http_adapter = FakeHttpAdapter(201)
uploader = Uploader(http_adapter)
response_body = uploader.upload('http://api/url', 'a1b2c3', self.asciicast) response_body = uploader.upload('http://api/url', 'a1b2c3', self.asciicast)
assert_equal(b'success!', response_body) assert_equal(b'success!', response_body)
assert_equal('http://api/url/api/asciicasts', self.http_adapter.url) assert_equal('http://api/url/api/asciicasts', http_adapter.url)
assert_equal(self._expected_files(), self.http_adapter.files) assert_equal(self._expected_files(), http_adapter.files)
assert_equal(self._expected_headers(), self.http_adapter.headers) assert_equal(self._expected_headers(), http_adapter.headers)
def test_upload_when_status_503_returned(self):
http_adapter = FakeHttpAdapter(503)
uploader = Uploader(http_adapter)
assert_raises(ServerMaintenanceError, uploader.upload,
'http://api/url', 'a1b2c3', self.asciicast)
def _expected_files(self): def _expected_files(self):
return { return {