2017-01-10 9 views
1

У меня есть эта функция, которая загружает файл архив в S3 ведро:Сделать UnitTest для функции, которая загружает файл в S3 с помощью boto3

def upload_file_to_s3_bucket(self, bucket, file, key, log): 
    if not os.path.exists(file): 
     log.error("File '%s' does not exist." % file) 
     tools.exit_gracefully(log) 
    log.info("Uploading file '%s' to bucket '%s' ..." % (file, bucket)) 
    try: 
     self._s3.upload_file(file, bucket, key) 
    except botocore.exceptions.ClientError as e: 
     log.error("Unexpected uploading error : %s" % e) 
     tools.exit_gracefully(log) 
    log.info("Uploading finished.") 

Я хочу сделать модульное тестирование для него, и это что я мог бы написать до сих пор:

class TestUploadFilesToS3(unittest.TestCase): 
    """ Tests unitaires upload_file_to_s3_bucket""" 


    def setUp(self): 
     conf.LOG_FILE = "/tmp/test.log" 
     conf.BUCKET_OUTPUT="name.of.the.bucket" 
     conf.Conf.get_level_log() 
     self.log = logger(conf.LOG_FILE, conf.LEVEL_LOG).logger 
     tools.create_workdir(self.log) 
     conf.WORKDIR = os.path.join(conf.LOCAL_DIR, "files/output") 
     archive = "file_archive.tar.gz" 
     archivePath = "/tmp/clients/file_archive.tar.gz" 
     _aws = None 

    def tearDown(self): 
     tools.delete_workdir(self.log) 
     os.remove(conf.LOG_FILE) 


    def test_upload_file_to_s3_bucket_success(self): 
     self._aws.upload_file_to_s3_bucket(conf.BUCKET_OUTPUT, archivePath, archive, self._log) 

Чтобы сделать модульное тестирование, я не знаю, какую функцию Assert следует использовать в функции тестирования test_upload_file_to_s3_bucket_success и что я должен точно сравнивать. Могу ли я, например, проверить, существует ли URL-адрес файла? есть идеи? Спасибо

ответ

0

Вот отрывок из теста я написал для функции загрузки s3

self.ti.uploadTemplate(contentsOfFile) # this is what is being tested 
    # also supplied from elsewhere "contentsOfFile" and "nameOfFile" 
    # bucket is assumed to be called "cloud-test-cf" 

    s3 = boto3.resource('s3') 
    mytname = nameOfFile 
    obj = s3.Object(bucket_name='cloud-test-cf', key=mytname) 
    response = obj.get() 
    self.assertEqual(response['ContentLength'], len(contentsOfFile)) 
    remoteData = response['Body'].read() 
    self.assertEqual(remoteData, contentsOfFile) 

Как вы можете видеть он получает доступ к файлу сразу после использования «uploadTemplate». Если вы используете один и тот же регион/параметры AZ, то он должен работать нормально, см http://docs.aws.amazon.com/AmazonS3/latest/dev/Introduction.html#ConsistencyModel

UnitTest метод для этого теста использует декоратор как этого

@unittest.skipIf(
     not(boto3.session.Config().region_name), 
     "aws creds not loaded") 
def testuploadTemplate(self): 
    #....test code here 

Это декоратор означает, что если UnitTest люкс запускается но клавиши AWS недоступны, этот конкретный тест пропущен

+0

Спасибо @Vorsprung, что очень помогает. но я получаю эту ошибку: '== ERROR: test_upload_file_to_s3_bucket_success (__main __. TestUploadFilesToS3) ClientError: Произошла ошибка (NoSuchKey) при вызове операции GetObject: Указанный ключ не существует. ' – JavaQueen

+0

Ну, на самом деле, я решил эту ошибку, но поставил response = obj.get()' под загрузкой. и теперь я получаю эту ошибку, что тест завершился неудачно, потому что файл и объект из S3 не имеют одинаковой длины: 'self.assertEqual (response ['ContentLength'], len (self.archive)) AssertionError: 141! = 34 ' – JavaQueen

+0

Решено. Я изменил len (contentsOfFile) на os.path.getsize (contentsOfFile) – JavaQueen

1

Я бы порекомендовал использовать ботокор stubber. На этой странице документа есть несколько примеров, которые помогут вам начать работу.