@gen.engine
def Put(args, callback):
  assert len(args) == 2
  source = args[0]
  dest = args[1]

  res_dst = store_utils.ParseFullPath(dest)
  assert res_dst is not None, 'Destination not part of a registered bucket'
  bucket = res_dst[0]
  dest_dir = res_dst[1]
  assert dest_dir.endswith('/'), 'Destination must be a directory (with trailing slash)'

  # Check existence and readability of source file.
  if not os.access(source, os.F_OK):
    print 'Source file does not exist: %s' % source
    callback()
    return
  if not os.access(source, os.R_OK):
    print 'Source file is not readable: %s' % source
    callback()
    return

  # Check whether the destination exists.
  store = ObjectStore.GetInstance(bucket)
  dst_file = os.path.join(dest_dir, os.path.basename(source))
  exists = yield gen.Task(store_utils.FileExists, store, dst_file)
  if exists:
    answer = raw_input('Destination exists: %s/%s. Overwrite or skip? [o/S] ' % (bucket, dst_file))
    if answer != 'o':
      callback()
      return

  with open(source, 'r') as f:
    contents = f.read()
  # Assume 1MB/s transfer speed. If we don't have that good a connection, we really shouldn't be uploading big files.
  timeout = max(20.0, len(contents) / 1024 * 1024)
  yield gen.Task(store.Put, dst_file, contents, request_timeout=timeout)
  # We just assume that no exception means no failure, which is true for now.
  print '%s/%s: %d bytes OK' % (bucket, dst_file, len(contents))

  callback()
Copy a single file to a S3 directory.
dataset/ETHPy150Open viewfinderco/viewfinder/backend/storage/tools/s3util.py/Put