Ejemplo n.º 1
0
def upload_blob(cmd, client, file_path, container_name=None, blob_name=None, blob_type=None,
                metadata=None, validate_content=False, maxsize_condition=None, max_connections=2, lease_id=None,
                if_modified_since=None, if_unmodified_since=None, if_match=None, if_none_match=None,
                timeout=None, progress_callback=None, encryption_scope=None, overwrite=None, **kwargs):
    """Upload a blob to a container."""

    upload_args = {
        'blob_type': transform_blob_type(cmd, blob_type),
        'lease': lease_id,
        'max_concurrency': max_connections
    }

    if overwrite is not None:
        upload_args['overwrite'] = overwrite
    if maxsize_condition:
        upload_args['maxsize_condition'] = maxsize_condition

    if cmd.supported_api_version(min_api='2016-05-31'):
        upload_args['validate_content'] = validate_content

    if progress_callback:
        upload_args['raw_response_hook'] = progress_callback

    check_blob_args = {
        'lease': lease_id,
        'if_modified_since': if_modified_since,
        'if_unmodified_since': if_unmodified_since,
        'if_match': if_match,
        'if_none_match': if_none_match,
        'timeout': timeout
    }

    # used to check for the preconditions as upload_append_blob() cannot
    if blob_type == 'append':
        from azure.core.exceptions import HttpResponseError
        if exists(cmd, client, timeout=timeout):
            client.get_blob_properties(**check_blob_args)

    # Because the contents of the uploaded file may be too large, it should be passed into the a stream object,
    # upload_blob() read file data in batches to avoid OOM problems
    count = os.path.getsize(file_path)
    with open(file_path, 'rb') as stream:
        response = client.upload_blob(data=stream, length=count, metadata=metadata, encryption_scope=encryption_scope,
                                      **upload_args, **kwargs)

    # PageBlobChunkUploader verifies the file when uploading the chunk data, If the contents of the file are
    # all null byte("\x00"), the file will not be uploaded, and the response will be none.
    # Therefore, the compatibility logic for response is added to keep it consistent with track 1
    if response is None:
        return {
            "etag": None,
            "lastModified": None
        }

    from msrest import Serializer
    if 'content_md5' in response and response['content_md5'] is not None:
        response['content_md5'] = Serializer.serialize_bytearray(response['content_md5'])
    if 'content_crc64' in response and response['content_crc64'] is not None:
        response['content_crc64'] = Serializer.serialize_bytearray(response['content_crc64'])
    return response
Ejemplo n.º 2
0
def transform_response_with_bytearray(response):
    """ transform bytearray to string """
    from msrest import Serializer
    for item in response:
        if response[item] and isinstance(response[item], (bytes, bytearray)):
            response[item] = Serializer.serialize_bytearray(response[item])
    return response
Ejemplo n.º 3
0
def get_file_properties(client, timeout=None):
    from .._transformers import transform_fs_access_output

    prop = client.get_file_properties(timeout=timeout)
    if prop.content_settings.content_md5 is not None:
        from msrest import Serializer
        prop.content_settings.content_md5 = Serializer.serialize_bytearray(
            prop.content_settings.content_md5)

    acl = transform_fs_access_output(
        client.get_access_control(timeout=timeout))
    result = dict(prop, **acl)
    return result
Ejemplo n.º 4
0
def upload_blob(cmd, client, file_path, container_name=None, blob_name=None, blob_type=None, content_settings=None,
                metadata=None, validate_content=False, maxsize_condition=None, max_connections=2, lease_id=None,
                tier=None, if_modified_since=None, if_unmodified_since=None, if_match=None, if_none_match=None,
                timeout=None, progress_callback=None, encryption_scope=None):
    """Upload a blob to a container."""

    if encryption_scope:
        count = os.path.getsize(file_path)
        with open(file_path, 'rb') as stream:
            data = stream.read(count)
        from azure.core import MatchConditions
        upload_args = {
            'content_settings': content_settings,
            'metadata': metadata,
            'timeout': timeout,
            'if_modified_since': if_modified_since,
            'if_unmodified_since': if_unmodified_since,
            'blob_type': transform_blob_type(cmd, blob_type),
            'validate_content': validate_content,
            'lease': lease_id,
            'max_concurrency': max_connections,
        }

        if cmd.supported_api_version(min_api='2017-04-17') and tier:
            upload_args['premium_page_blob_tier'] = tier
        if maxsize_condition:
            upload_args['maxsize_condition'] = maxsize_condition
        if cmd.supported_api_version(min_api='2016-05-31'):
            upload_args['validate_content'] = validate_content

        # Precondition Check
        if if_match:
            if if_match == '*':
                upload_args['match_condition'] = MatchConditions.IfPresent
            else:
                upload_args['etag'] = if_match
                upload_args['match_condition'] = MatchConditions.IfNotModified

        if if_none_match:
            upload_args['etag'] = if_none_match
            upload_args['match_condition'] = MatchConditions.IfModified
        response = client.upload_blob(data=data, length=count, encryption_scope=encryption_scope, **upload_args)
        if response['content_md5'] is not None:
            from msrest import Serializer
            response['content_md5'] = Serializer.serialize_bytearray(response['content_md5'])
        return response

    t_content_settings = cmd.get_models('blob.models#ContentSettings')
    content_settings = guess_content_type(file_path, content_settings, t_content_settings)

    def upload_append_blob():
        check_blob_args = {
            'container_name': container_name,
            'blob_name': blob_name,
            'lease_id': lease_id,
            'if_modified_since': if_modified_since,
            'if_unmodified_since': if_unmodified_since,
            'if_match': if_match,
            'if_none_match': if_none_match,
            'timeout': timeout
        }

        if client.exists(container_name, blob_name):
            # used to check for the preconditions as append_blob_from_path() cannot
            client.get_blob_properties(**check_blob_args)
        else:
            client.create_blob(content_settings=content_settings, metadata=metadata, **check_blob_args)

        append_blob_args = {
            'container_name': container_name,
            'blob_name': blob_name,
            'file_path': file_path,
            'progress_callback': progress_callback,
            'maxsize_condition': maxsize_condition,
            'lease_id': lease_id,
            'timeout': timeout
        }

        if cmd.supported_api_version(min_api='2016-05-31'):
            append_blob_args['validate_content'] = validate_content

        return client.append_blob_from_path(**append_blob_args)

    def upload_block_blob():
        # increase the block size to 100MB when the block list will contain more than 50,000 blocks
        if os.path.isfile(file_path) and os.stat(file_path).st_size > 50000 * 4 * 1024 * 1024:
            client.MAX_BLOCK_SIZE = 100 * 1024 * 1024
            client.MAX_SINGLE_PUT_SIZE = 256 * 1024 * 1024

        create_blob_args = {
            'container_name': container_name,
            'blob_name': blob_name,
            'file_path': file_path,
            'progress_callback': progress_callback,
            'content_settings': content_settings,
            'metadata': metadata,
            'max_connections': max_connections,
            'lease_id': lease_id,
            'if_modified_since': if_modified_since,
            'if_unmodified_since': if_unmodified_since,
            'if_match': if_match,
            'if_none_match': if_none_match,
            'timeout': timeout
        }

        if cmd.supported_api_version(min_api='2017-04-17') and tier:
            create_blob_args['premium_page_blob_tier'] = tier

        if cmd.supported_api_version(min_api='2016-05-31'):
            create_blob_args['validate_content'] = validate_content

        return client.create_blob_from_path(**create_blob_args)

    type_func = {
        'append': upload_append_blob,
        'block': upload_block_blob,
        'page': upload_block_blob  # same implementation
    }
    return type_func[blob_type]()