gcloud 0.0.4 → 0.0.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data.tar.gz.sig +0 -0
- data/CHANGELOG +4 -0
- data/Makefile +4 -0
- data/Manifest +760 -1
- data/bin/gcloud +7 -0
- data/bin/{gcutil → gcutil.symlink} +0 -0
- data/bin/gsutil-symlink +377 -0
- data/gcloud.gemspec +5 -5
- data/packages/gsutil/CHECKSUM +1 -0
- data/packages/gsutil/COPYING +202 -0
- data/packages/gsutil/LICENSE.third_party +295 -0
- data/packages/gsutil/MANIFEST.in +5 -0
- data/packages/gsutil/README +38 -0
- data/packages/gsutil/README.pkg +49 -0
- data/packages/gsutil/ReleaseNotes.txt +780 -0
- data/packages/gsutil/VERSION +1 -0
- data/packages/gsutil/boto/Changelog.rst +35 -0
- data/packages/gsutil/boto/LICENSE +18 -0
- data/packages/gsutil/boto/MANIFEST.in +12 -0
- data/packages/gsutil/boto/README.rst +163 -0
- data/packages/gsutil/boto/bin/asadmin +290 -0
- data/packages/gsutil/boto/bin/bundle_image +27 -0
- data/packages/gsutil/boto/bin/cfadmin +108 -0
- data/packages/gsutil/boto/bin/cq +89 -0
- data/packages/gsutil/boto/bin/cwutil +140 -0
- data/packages/gsutil/boto/bin/elbadmin +284 -0
- data/packages/gsutil/boto/bin/fetch_file +43 -0
- data/packages/gsutil/boto/bin/glacier +154 -0
- data/packages/gsutil/boto/bin/instance_events +145 -0
- data/packages/gsutil/boto/bin/kill_instance +35 -0
- data/packages/gsutil/boto/bin/launch_instance +252 -0
- data/packages/gsutil/boto/bin/list_instances +90 -0
- data/packages/gsutil/boto/bin/lss3 +77 -0
- data/packages/gsutil/boto/bin/mturk +465 -0
- data/packages/gsutil/boto/bin/pyami_sendmail +52 -0
- data/packages/gsutil/boto/bin/route53 +205 -0
- data/packages/gsutil/boto/bin/s3put +374 -0
- data/packages/gsutil/boto/bin/sdbadmin +194 -0
- data/packages/gsutil/boto/bin/taskadmin +116 -0
- data/packages/gsutil/boto/boto/__init__.py +793 -0
- data/packages/gsutil/boto/boto/__init__.pyc +0 -0
- data/packages/gsutil/boto/boto/auth.py +682 -0
- data/packages/gsutil/boto/boto/auth.pyc +0 -0
- data/packages/gsutil/boto/boto/auth_handler.py +58 -0
- data/packages/gsutil/boto/boto/auth_handler.pyc +0 -0
- data/packages/gsutil/boto/boto/beanstalk/__init__.py +65 -0
- data/packages/gsutil/boto/boto/beanstalk/exception.py +64 -0
- data/packages/gsutil/boto/boto/beanstalk/layer1.py +1153 -0
- data/packages/gsutil/boto/boto/beanstalk/response.py +703 -0
- data/packages/gsutil/boto/boto/beanstalk/wrapper.py +29 -0
- data/packages/gsutil/boto/boto/cacerts/__init__.py +22 -0
- data/packages/gsutil/boto/boto/cacerts/__init__.pyc +0 -0
- data/packages/gsutil/boto/boto/cacerts/cacerts.txt +633 -0
- data/packages/gsutil/boto/boto/cloudformation/__init__.py +68 -0
- data/packages/gsutil/boto/boto/cloudformation/connection.py +364 -0
- data/packages/gsutil/boto/boto/cloudformation/stack.py +360 -0
- data/packages/gsutil/boto/boto/cloudformation/template.py +43 -0
- data/packages/gsutil/boto/boto/cloudfront/__init__.py +324 -0
- data/packages/gsutil/boto/boto/cloudfront/distribution.py +745 -0
- data/packages/gsutil/boto/boto/cloudfront/exception.py +26 -0
- data/packages/gsutil/boto/boto/cloudfront/identity.py +122 -0
- data/packages/gsutil/boto/boto/cloudfront/invalidation.py +216 -0
- data/packages/gsutil/boto/boto/cloudfront/logging.py +38 -0
- data/packages/gsutil/boto/boto/cloudfront/object.py +48 -0
- data/packages/gsutil/boto/boto/cloudfront/origin.py +150 -0
- data/packages/gsutil/boto/boto/cloudfront/signers.py +60 -0
- data/packages/gsutil/boto/boto/cloudsearch/__init__.py +45 -0
- data/packages/gsutil/boto/boto/cloudsearch/document.py +265 -0
- data/packages/gsutil/boto/boto/cloudsearch/domain.py +394 -0
- data/packages/gsutil/boto/boto/cloudsearch/layer1.py +738 -0
- data/packages/gsutil/boto/boto/cloudsearch/layer2.py +67 -0
- data/packages/gsutil/boto/boto/cloudsearch/optionstatus.py +248 -0
- data/packages/gsutil/boto/boto/cloudsearch/search.py +365 -0
- data/packages/gsutil/boto/boto/cloudsearch/sourceattribute.py +75 -0
- data/packages/gsutil/boto/boto/compat.py +28 -0
- data/packages/gsutil/boto/boto/compat.pyc +0 -0
- data/packages/gsutil/boto/boto/connection.py +1081 -0
- data/packages/gsutil/boto/boto/connection.pyc +0 -0
- data/packages/gsutil/boto/boto/contrib/__init__.py +22 -0
- data/packages/gsutil/boto/boto/contrib/ymlmessage.py +52 -0
- data/packages/gsutil/boto/boto/core/README +58 -0
- data/packages/gsutil/boto/boto/core/__init__.py +23 -0
- data/packages/gsutil/boto/boto/core/auth.py +78 -0
- data/packages/gsutil/boto/boto/core/credentials.py +154 -0
- data/packages/gsutil/boto/boto/core/dictresponse.py +178 -0
- data/packages/gsutil/boto/boto/core/service.py +67 -0
- data/packages/gsutil/boto/boto/datapipeline/__init__.py +0 -0
- data/packages/gsutil/boto/boto/datapipeline/exceptions.py +42 -0
- data/packages/gsutil/boto/boto/datapipeline/layer1.py +546 -0
- data/packages/gsutil/boto/boto/dynamodb/__init__.py +66 -0
- data/packages/gsutil/boto/boto/dynamodb/batch.py +262 -0
- data/packages/gsutil/boto/boto/dynamodb/condition.py +170 -0
- data/packages/gsutil/boto/boto/dynamodb/exceptions.py +64 -0
- data/packages/gsutil/boto/boto/dynamodb/item.py +196 -0
- data/packages/gsutil/boto/boto/dynamodb/layer1.py +575 -0
- data/packages/gsutil/boto/boto/dynamodb/layer2.py +798 -0
- data/packages/gsutil/boto/boto/dynamodb/schema.py +112 -0
- data/packages/gsutil/boto/boto/dynamodb/table.py +540 -0
- data/packages/gsutil/boto/boto/dynamodb/types.py +326 -0
- data/packages/gsutil/boto/boto/ec2/__init__.py +96 -0
- data/packages/gsutil/boto/boto/ec2/address.py +103 -0
- data/packages/gsutil/boto/boto/ec2/autoscale/__init__.py +781 -0
- data/packages/gsutil/boto/boto/ec2/autoscale/activity.py +74 -0
- data/packages/gsutil/boto/boto/ec2/autoscale/group.py +337 -0
- data/packages/gsutil/boto/boto/ec2/autoscale/instance.py +60 -0
- data/packages/gsutil/boto/boto/ec2/autoscale/launchconfig.py +209 -0
- data/packages/gsutil/boto/boto/ec2/autoscale/policy.py +166 -0
- data/packages/gsutil/boto/boto/ec2/autoscale/request.py +38 -0
- data/packages/gsutil/boto/boto/ec2/autoscale/scheduled.py +60 -0
- data/packages/gsutil/boto/boto/ec2/autoscale/tag.py +84 -0
- data/packages/gsutil/boto/boto/ec2/blockdevicemapping.py +141 -0
- data/packages/gsutil/boto/boto/ec2/bundleinstance.py +78 -0
- data/packages/gsutil/boto/boto/ec2/buyreservation.py +84 -0
- data/packages/gsutil/boto/boto/ec2/cloudwatch/__init__.py +603 -0
- data/packages/gsutil/boto/boto/ec2/cloudwatch/alarm.py +316 -0
- data/packages/gsutil/boto/boto/ec2/cloudwatch/datapoint.py +40 -0
- data/packages/gsutil/boto/boto/ec2/cloudwatch/dimension.py +38 -0
- data/packages/gsutil/boto/boto/ec2/cloudwatch/listelement.py +31 -0
- data/packages/gsutil/boto/boto/ec2/cloudwatch/metric.py +175 -0
- data/packages/gsutil/boto/boto/ec2/connection.py +3409 -0
- data/packages/gsutil/boto/boto/ec2/ec2object.py +107 -0
- data/packages/gsutil/boto/boto/ec2/elb/__init__.py +553 -0
- data/packages/gsutil/boto/boto/ec2/elb/healthcheck.py +89 -0
- data/packages/gsutil/boto/boto/ec2/elb/instancestate.py +62 -0
- data/packages/gsutil/boto/boto/ec2/elb/listelement.py +36 -0
- data/packages/gsutil/boto/boto/ec2/elb/listener.py +75 -0
- data/packages/gsutil/boto/boto/ec2/elb/loadbalancer.py +324 -0
- data/packages/gsutil/boto/boto/ec2/elb/policies.py +89 -0
- data/packages/gsutil/boto/boto/ec2/elb/securitygroup.py +38 -0
- data/packages/gsutil/boto/boto/ec2/group.py +39 -0
- data/packages/gsutil/boto/boto/ec2/image.py +350 -0
- data/packages/gsutil/boto/boto/ec2/instance.py +661 -0
- data/packages/gsutil/boto/boto/ec2/instanceinfo.py +51 -0
- data/packages/gsutil/boto/boto/ec2/instancestatus.py +207 -0
- data/packages/gsutil/boto/boto/ec2/keypair.py +113 -0
- data/packages/gsutil/boto/boto/ec2/launchspecification.py +105 -0
- data/packages/gsutil/boto/boto/ec2/networkinterface.py +247 -0
- data/packages/gsutil/boto/boto/ec2/placementgroup.py +51 -0
- data/packages/gsutil/boto/boto/ec2/regioninfo.py +34 -0
- data/packages/gsutil/boto/boto/ec2/reservedinstance.py +227 -0
- data/packages/gsutil/boto/boto/ec2/securitygroup.py +357 -0
- data/packages/gsutil/boto/boto/ec2/snapshot.py +170 -0
- data/packages/gsutil/boto/boto/ec2/spotdatafeedsubscription.py +63 -0
- data/packages/gsutil/boto/boto/ec2/spotinstancerequest.py +188 -0
- data/packages/gsutil/boto/boto/ec2/spotpricehistory.py +55 -0
- data/packages/gsutil/boto/boto/ec2/tag.py +87 -0
- data/packages/gsutil/boto/boto/ec2/vmtype.py +58 -0
- data/packages/gsutil/boto/boto/ec2/volume.py +293 -0
- data/packages/gsutil/boto/boto/ec2/volumestatus.py +200 -0
- data/packages/gsutil/boto/boto/ec2/zone.py +80 -0
- data/packages/gsutil/boto/boto/ecs/__init__.py +90 -0
- data/packages/gsutil/boto/boto/ecs/item.py +153 -0
- data/packages/gsutil/boto/boto/elasticache/__init__.py +62 -0
- data/packages/gsutil/boto/boto/elasticache/layer1.py +1252 -0
- data/packages/gsutil/boto/boto/elastictranscoder/__init__.py +62 -0
- data/packages/gsutil/boto/boto/elastictranscoder/exceptions.py +46 -0
- data/packages/gsutil/boto/boto/elastictranscoder/layer1.py +509 -0
- data/packages/gsutil/boto/boto/emr/__init__.py +73 -0
- data/packages/gsutil/boto/boto/emr/bootstrap_action.py +44 -0
- data/packages/gsutil/boto/boto/emr/connection.py +531 -0
- data/packages/gsutil/boto/boto/emr/emrobject.py +176 -0
- data/packages/gsutil/boto/boto/emr/instance_group.py +43 -0
- data/packages/gsutil/boto/boto/emr/step.py +281 -0
- data/packages/gsutil/boto/boto/exception.py +476 -0
- data/packages/gsutil/boto/boto/exception.pyc +0 -0
- data/packages/gsutil/boto/boto/file/README +49 -0
- data/packages/gsutil/boto/boto/file/__init__.py +28 -0
- data/packages/gsutil/boto/boto/file/bucket.py +112 -0
- data/packages/gsutil/boto/boto/file/connection.py +33 -0
- data/packages/gsutil/boto/boto/file/key.py +199 -0
- data/packages/gsutil/boto/boto/file/simpleresultset.py +30 -0
- data/packages/gsutil/boto/boto/fps/__init__.py +21 -0
- data/packages/gsutil/boto/boto/fps/connection.py +369 -0
- data/packages/gsutil/boto/boto/fps/exception.py +344 -0
- data/packages/gsutil/boto/boto/fps/response.py +175 -0
- data/packages/gsutil/boto/boto/glacier/__init__.py +57 -0
- data/packages/gsutil/boto/boto/glacier/concurrent.py +409 -0
- data/packages/gsutil/boto/boto/glacier/exceptions.py +58 -0
- data/packages/gsutil/boto/boto/glacier/job.py +152 -0
- data/packages/gsutil/boto/boto/glacier/layer1.py +637 -0
- data/packages/gsutil/boto/boto/glacier/layer2.py +93 -0
- data/packages/gsutil/boto/boto/glacier/response.py +48 -0
- data/packages/gsutil/boto/boto/glacier/utils.py +163 -0
- data/packages/gsutil/boto/boto/glacier/vault.py +387 -0
- data/packages/gsutil/boto/boto/glacier/writer.py +242 -0
- data/packages/gsutil/boto/boto/gs/__init__.py +22 -0
- data/packages/gsutil/boto/boto/gs/__init__.pyc +0 -0
- data/packages/gsutil/boto/boto/gs/acl.py +304 -0
- data/packages/gsutil/boto/boto/gs/acl.pyc +0 -0
- data/packages/gsutil/boto/boto/gs/bucket.py +870 -0
- data/packages/gsutil/boto/boto/gs/bucket.pyc +0 -0
- data/packages/gsutil/boto/boto/gs/bucketlistresultset.py +64 -0
- data/packages/gsutil/boto/boto/gs/bucketlistresultset.pyc +0 -0
- data/packages/gsutil/boto/boto/gs/connection.py +103 -0
- data/packages/gsutil/boto/boto/gs/connection.pyc +0 -0
- data/packages/gsutil/boto/boto/gs/cors.py +169 -0
- data/packages/gsutil/boto/boto/gs/cors.pyc +0 -0
- data/packages/gsutil/boto/boto/gs/key.py +704 -0
- data/packages/gsutil/boto/boto/gs/key.pyc +0 -0
- data/packages/gsutil/boto/boto/gs/resumable_upload_handler.py +659 -0
- data/packages/gsutil/boto/boto/gs/resumable_upload_handler.pyc +0 -0
- data/packages/gsutil/boto/boto/gs/user.py +54 -0
- data/packages/gsutil/boto/boto/gs/user.pyc +0 -0
- data/packages/gsutil/boto/boto/handler.py +44 -0
- data/packages/gsutil/boto/boto/handler.pyc +0 -0
- data/packages/gsutil/boto/boto/https_connection.py +124 -0
- data/packages/gsutil/boto/boto/https_connection.pyc +0 -0
- data/packages/gsutil/boto/boto/iam/__init__.py +74 -0
- data/packages/gsutil/boto/boto/iam/connection.py +1317 -0
- data/packages/gsutil/boto/boto/iam/summarymap.py +42 -0
- data/packages/gsutil/boto/boto/jsonresponse.py +163 -0
- data/packages/gsutil/boto/boto/jsonresponse.pyc +0 -0
- data/packages/gsutil/boto/boto/manage/__init__.py +23 -0
- data/packages/gsutil/boto/boto/manage/cmdshell.py +241 -0
- data/packages/gsutil/boto/boto/manage/propget.py +64 -0
- data/packages/gsutil/boto/boto/manage/server.py +556 -0
- data/packages/gsutil/boto/boto/manage/task.py +175 -0
- data/packages/gsutil/boto/boto/manage/test_manage.py +34 -0
- data/packages/gsutil/boto/boto/manage/volume.py +420 -0
- data/packages/gsutil/boto/boto/mashups/__init__.py +23 -0
- data/packages/gsutil/boto/boto/mashups/interactive.py +97 -0
- data/packages/gsutil/boto/boto/mashups/iobject.py +115 -0
- data/packages/gsutil/boto/boto/mashups/order.py +211 -0
- data/packages/gsutil/boto/boto/mashups/server.py +395 -0
- data/packages/gsutil/boto/boto/mturk/__init__.py +23 -0
- data/packages/gsutil/boto/boto/mturk/connection.py +1027 -0
- data/packages/gsutil/boto/boto/mturk/layoutparam.py +55 -0
- data/packages/gsutil/boto/boto/mturk/notification.py +103 -0
- data/packages/gsutil/boto/boto/mturk/price.py +48 -0
- data/packages/gsutil/boto/boto/mturk/qualification.py +137 -0
- data/packages/gsutil/boto/boto/mturk/question.py +455 -0
- data/packages/gsutil/boto/boto/mws/__init__.py +21 -0
- data/packages/gsutil/boto/boto/mws/connection.py +813 -0
- data/packages/gsutil/boto/boto/mws/exception.py +75 -0
- data/packages/gsutil/boto/boto/mws/response.py +655 -0
- data/packages/gsutil/boto/boto/plugin.py +90 -0
- data/packages/gsutil/boto/boto/plugin.pyc +0 -0
- data/packages/gsutil/boto/boto/provider.py +337 -0
- data/packages/gsutil/boto/boto/provider.pyc +0 -0
- data/packages/gsutil/boto/boto/pyami/__init__.py +22 -0
- data/packages/gsutil/boto/boto/pyami/__init__.pyc +0 -0
- data/packages/gsutil/boto/boto/pyami/bootstrap.py +134 -0
- data/packages/gsutil/boto/boto/pyami/config.py +229 -0
- data/packages/gsutil/boto/boto/pyami/config.pyc +0 -0
- data/packages/gsutil/boto/boto/pyami/copybot.cfg +60 -0
- data/packages/gsutil/boto/boto/pyami/copybot.py +97 -0
- data/packages/gsutil/boto/boto/pyami/helloworld.py +28 -0
- data/packages/gsutil/boto/boto/pyami/installers/__init__.py +64 -0
- data/packages/gsutil/boto/boto/pyami/installers/ubuntu/__init__.py +22 -0
- data/packages/gsutil/boto/boto/pyami/installers/ubuntu/apache.py +43 -0
- data/packages/gsutil/boto/boto/pyami/installers/ubuntu/ebs.py +238 -0
- data/packages/gsutil/boto/boto/pyami/installers/ubuntu/installer.py +96 -0
- data/packages/gsutil/boto/boto/pyami/installers/ubuntu/mysql.py +109 -0
- data/packages/gsutil/boto/boto/pyami/installers/ubuntu/trac.py +139 -0
- data/packages/gsutil/boto/boto/pyami/launch_ami.py +178 -0
- data/packages/gsutil/boto/boto/pyami/scriptbase.py +44 -0
- data/packages/gsutil/boto/boto/pyami/startup.py +60 -0
- data/packages/gsutil/boto/boto/rds/__init__.py +1194 -0
- data/packages/gsutil/boto/boto/rds/dbinstance.py +357 -0
- data/packages/gsutil/boto/boto/rds/dbsecuritygroup.py +177 -0
- data/packages/gsutil/boto/boto/rds/dbsnapshot.py +108 -0
- data/packages/gsutil/boto/boto/rds/event.py +49 -0
- data/packages/gsutil/boto/boto/rds/parametergroup.py +201 -0
- data/packages/gsutil/boto/boto/rds/regioninfo.py +32 -0
- data/packages/gsutil/boto/boto/regioninfo.py +63 -0
- data/packages/gsutil/boto/boto/regioninfo.pyc +0 -0
- data/packages/gsutil/boto/boto/resultset.py +169 -0
- data/packages/gsutil/boto/boto/resultset.pyc +0 -0
- data/packages/gsutil/boto/boto/roboto/__init__.py +1 -0
- data/packages/gsutil/boto/boto/roboto/awsqueryrequest.py +504 -0
- data/packages/gsutil/boto/boto/roboto/awsqueryservice.py +121 -0
- data/packages/gsutil/boto/boto/roboto/param.py +147 -0
- data/packages/gsutil/boto/boto/route53/__init__.py +75 -0
- data/packages/gsutil/boto/boto/route53/connection.py +403 -0
- data/packages/gsutil/boto/boto/route53/exception.py +27 -0
- data/packages/gsutil/boto/boto/route53/hostedzone.py +56 -0
- data/packages/gsutil/boto/boto/route53/record.py +306 -0
- data/packages/gsutil/boto/boto/route53/status.py +42 -0
- data/packages/gsutil/boto/boto/route53/zone.py +412 -0
- data/packages/gsutil/boto/boto/s3/__init__.py +84 -0
- data/packages/gsutil/boto/boto/s3/__init__.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/acl.py +164 -0
- data/packages/gsutil/boto/boto/s3/acl.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/bucket.py +1634 -0
- data/packages/gsutil/boto/boto/s3/bucket.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/bucketlistresultset.py +139 -0
- data/packages/gsutil/boto/boto/s3/bucketlistresultset.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/bucketlogging.py +83 -0
- data/packages/gsutil/boto/boto/s3/bucketlogging.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/connection.py +540 -0
- data/packages/gsutil/boto/boto/s3/connection.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/cors.py +210 -0
- data/packages/gsutil/boto/boto/s3/cors.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/deletemarker.py +55 -0
- data/packages/gsutil/boto/boto/s3/deletemarker.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/key.py +1712 -0
- data/packages/gsutil/boto/boto/s3/key.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/keyfile.py +134 -0
- data/packages/gsutil/boto/boto/s3/keyfile.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/lifecycle.py +231 -0
- data/packages/gsutil/boto/boto/s3/lifecycle.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/multidelete.py +138 -0
- data/packages/gsutil/boto/boto/s3/multidelete.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/multipart.py +315 -0
- data/packages/gsutil/boto/boto/s3/multipart.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/prefix.py +42 -0
- data/packages/gsutil/boto/boto/s3/prefix.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/resumable_download_handler.py +339 -0
- data/packages/gsutil/boto/boto/s3/resumable_download_handler.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/tagging.py +71 -0
- data/packages/gsutil/boto/boto/s3/tagging.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/user.py +49 -0
- data/packages/gsutil/boto/boto/s3/user.pyc +0 -0
- data/packages/gsutil/boto/boto/s3/website.py +237 -0
- data/packages/gsutil/boto/boto/s3/website.pyc +0 -0
- data/packages/gsutil/boto/boto/sdb/__init__.py +67 -0
- data/packages/gsutil/boto/boto/sdb/connection.py +617 -0
- data/packages/gsutil/boto/boto/sdb/db/__init__.py +20 -0
- data/packages/gsutil/boto/boto/sdb/db/blob.py +75 -0
- data/packages/gsutil/boto/boto/sdb/db/key.py +59 -0
- data/packages/gsutil/boto/boto/sdb/db/manager/__init__.py +85 -0
- data/packages/gsutil/boto/boto/sdb/db/manager/sdbmanager.py +732 -0
- data/packages/gsutil/boto/boto/sdb/db/manager/xmlmanager.py +517 -0
- data/packages/gsutil/boto/boto/sdb/db/model.py +294 -0
- data/packages/gsutil/boto/boto/sdb/db/property.py +703 -0
- data/packages/gsutil/boto/boto/sdb/db/query.py +85 -0
- data/packages/gsutil/boto/boto/sdb/db/sequence.py +226 -0
- data/packages/gsutil/boto/boto/sdb/db/test_db.py +231 -0
- data/packages/gsutil/boto/boto/sdb/domain.py +377 -0
- data/packages/gsutil/boto/boto/sdb/item.py +181 -0
- data/packages/gsutil/boto/boto/sdb/queryresultset.py +92 -0
- data/packages/gsutil/boto/boto/sdb/regioninfo.py +32 -0
- data/packages/gsutil/boto/boto/services/__init__.py +23 -0
- data/packages/gsutil/boto/boto/services/bs.py +179 -0
- data/packages/gsutil/boto/boto/services/message.py +58 -0
- data/packages/gsutil/boto/boto/services/result.py +136 -0
- data/packages/gsutil/boto/boto/services/service.py +161 -0
- data/packages/gsutil/boto/boto/services/servicedef.py +91 -0
- data/packages/gsutil/boto/boto/services/sonofmmm.cfg +43 -0
- data/packages/gsutil/boto/boto/services/sonofmmm.py +81 -0
- data/packages/gsutil/boto/boto/services/submit.py +88 -0
- data/packages/gsutil/boto/boto/ses/__init__.py +54 -0
- data/packages/gsutil/boto/boto/ses/connection.py +521 -0
- data/packages/gsutil/boto/boto/ses/exceptions.py +77 -0
- data/packages/gsutil/boto/boto/sns/__init__.py +78 -0
- data/packages/gsutil/boto/boto/sns/connection.py +431 -0
- data/packages/gsutil/boto/boto/sqs/__init__.py +56 -0
- data/packages/gsutil/boto/boto/sqs/attributes.py +46 -0
- data/packages/gsutil/boto/boto/sqs/batchresults.py +95 -0
- data/packages/gsutil/boto/boto/sqs/connection.py +417 -0
- data/packages/gsutil/boto/boto/sqs/jsonmessage.py +43 -0
- data/packages/gsutil/boto/boto/sqs/message.py +253 -0
- data/packages/gsutil/boto/boto/sqs/queue.py +478 -0
- data/packages/gsutil/boto/boto/sqs/regioninfo.py +32 -0
- data/packages/gsutil/boto/boto/storage_uri.py +835 -0
- data/packages/gsutil/boto/boto/storage_uri.pyc +0 -0
- data/packages/gsutil/boto/boto/sts/__init__.py +55 -0
- data/packages/gsutil/boto/boto/sts/connection.py +207 -0
- data/packages/gsutil/boto/boto/sts/credentials.py +215 -0
- data/packages/gsutil/boto/boto/swf/__init__.py +60 -0
- data/packages/gsutil/boto/boto/swf/exceptions.py +44 -0
- data/packages/gsutil/boto/boto/swf/layer1.py +1512 -0
- data/packages/gsutil/boto/boto/swf/layer1_decisions.py +287 -0
- data/packages/gsutil/boto/boto/swf/layer2.py +342 -0
- data/packages/gsutil/boto/boto/utils.py +927 -0
- data/packages/gsutil/boto/boto/utils.pyc +0 -0
- data/packages/gsutil/boto/boto/vpc/__init__.py +910 -0
- data/packages/gsutil/boto/boto/vpc/customergateway.py +54 -0
- data/packages/gsutil/boto/boto/vpc/dhcpoptions.py +72 -0
- data/packages/gsutil/boto/boto/vpc/internetgateway.py +72 -0
- data/packages/gsutil/boto/boto/vpc/routetable.py +109 -0
- data/packages/gsutil/boto/boto/vpc/subnet.py +57 -0
- data/packages/gsutil/boto/boto/vpc/vpc.py +54 -0
- data/packages/gsutil/boto/boto/vpc/vpnconnection.py +60 -0
- data/packages/gsutil/boto/boto/vpc/vpngateway.py +83 -0
- data/packages/gsutil/boto/docs/BotoCheatSheet.pdf +0 -0
- data/packages/gsutil/boto/docs/Makefile +89 -0
- data/packages/gsutil/boto/docs/make.bat +113 -0
- data/packages/gsutil/boto/docs/source/_templates/layout.html +3 -0
- data/packages/gsutil/boto/docs/source/autoscale_tut.rst +220 -0
- data/packages/gsutil/boto/docs/source/boto_config_tut.rst +125 -0
- data/packages/gsutil/boto/docs/source/boto_theme/static/boto.css_t +239 -0
- data/packages/gsutil/boto/docs/source/boto_theme/static/pygments.css +61 -0
- data/packages/gsutil/boto/docs/source/boto_theme/theme.conf +3 -0
- data/packages/gsutil/boto/docs/source/cloudfront_tut.rst +196 -0
- data/packages/gsutil/boto/docs/source/cloudsearch_tut.rst +411 -0
- data/packages/gsutil/boto/docs/source/cloudwatch_tut.rst +116 -0
- data/packages/gsutil/boto/docs/source/conf.py +32 -0
- data/packages/gsutil/boto/docs/source/contributing.rst +204 -0
- data/packages/gsutil/boto/docs/source/documentation.rst +59 -0
- data/packages/gsutil/boto/docs/source/dynamodb_tut.rst +339 -0
- data/packages/gsutil/boto/docs/source/ec2_tut.rst +86 -0
- data/packages/gsutil/boto/docs/source/elb_tut.rst +257 -0
- data/packages/gsutil/boto/docs/source/emr_tut.rst +108 -0
- data/packages/gsutil/boto/docs/source/index.rst +146 -0
- data/packages/gsutil/boto/docs/source/rds_tut.rst +108 -0
- data/packages/gsutil/boto/docs/source/ref/autoscale.rst +62 -0
- data/packages/gsutil/boto/docs/source/ref/beanstalk.rst +26 -0
- data/packages/gsutil/boto/docs/source/ref/boto.rst +47 -0
- data/packages/gsutil/boto/docs/source/ref/cloudformation.rst +34 -0
- data/packages/gsutil/boto/docs/source/ref/cloudfront.rst +68 -0
- data/packages/gsutil/boto/docs/source/ref/cloudsearch.rst +59 -0
- data/packages/gsutil/boto/docs/source/ref/cloudwatch.rst +27 -0
- data/packages/gsutil/boto/docs/source/ref/contrib.rst +32 -0
- data/packages/gsutil/boto/docs/source/ref/datapipeline.rst +26 -0
- data/packages/gsutil/boto/docs/source/ref/dynamodb.rst +61 -0
- data/packages/gsutil/boto/docs/source/ref/ec2.rst +140 -0
- data/packages/gsutil/boto/docs/source/ref/ecs.rst +19 -0
- data/packages/gsutil/boto/docs/source/ref/elasticache.rst +19 -0
- data/packages/gsutil/boto/docs/source/ref/elastictranscoder.rst +26 -0
- data/packages/gsutil/boto/docs/source/ref/elb.rst +47 -0
- data/packages/gsutil/boto/docs/source/ref/emr.rst +34 -0
- data/packages/gsutil/boto/docs/source/ref/file.rst +34 -0
- data/packages/gsutil/boto/docs/source/ref/fps.rst +19 -0
- data/packages/gsutil/boto/docs/source/ref/glacier.rst +63 -0
- data/packages/gsutil/boto/docs/source/ref/gs.rst +72 -0
- data/packages/gsutil/boto/docs/source/ref/iam.rst +27 -0
- data/packages/gsutil/boto/docs/source/ref/index.rst +40 -0
- data/packages/gsutil/boto/docs/source/ref/manage.rst +47 -0
- data/packages/gsutil/boto/docs/source/ref/mturk.rst +54 -0
- data/packages/gsutil/boto/docs/source/ref/mws.rst +33 -0
- data/packages/gsutil/boto/docs/source/ref/pyami.rst +103 -0
- data/packages/gsutil/boto/docs/source/ref/rds.rst +47 -0
- data/packages/gsutil/boto/docs/source/ref/route53.rst +34 -0
- data/packages/gsutil/boto/docs/source/ref/s3.rst +111 -0
- data/packages/gsutil/boto/docs/source/ref/sdb.rst +45 -0
- data/packages/gsutil/boto/docs/source/ref/sdb_db.rst +83 -0
- data/packages/gsutil/boto/docs/source/ref/services.rst +61 -0
- data/packages/gsutil/boto/docs/source/ref/ses.rst +21 -0
- data/packages/gsutil/boto/docs/source/ref/sns.rst +17 -0
- data/packages/gsutil/boto/docs/source/ref/sqs.rst +61 -0
- data/packages/gsutil/boto/docs/source/ref/sts.rst +25 -0
- data/packages/gsutil/boto/docs/source/ref/swf.rst +22 -0
- data/packages/gsutil/boto/docs/source/ref/vpc.rst +54 -0
- data/packages/gsutil/boto/docs/source/s3_tut.rst +450 -0
- data/packages/gsutil/boto/docs/source/security_groups.rst +82 -0
- data/packages/gsutil/boto/docs/source/ses_tut.rst +171 -0
- data/packages/gsutil/boto/docs/source/simpledb_tut.rst +188 -0
- data/packages/gsutil/boto/docs/source/sqs_tut.rst +246 -0
- data/packages/gsutil/boto/docs/source/vpc_tut.rst +100 -0
- data/packages/gsutil/boto/pylintrc +305 -0
- data/packages/gsutil/boto/requirements.txt +10 -0
- data/packages/gsutil/boto/setup.py +89 -0
- data/packages/gsutil/boto/tests/__init__.py +20 -0
- data/packages/gsutil/boto/tests/db/test_lists.py +96 -0
- data/packages/gsutil/boto/tests/db/test_password.py +128 -0
- data/packages/gsutil/boto/tests/db/test_query.py +152 -0
- data/packages/gsutil/boto/tests/db/test_sequence.py +109 -0
- data/packages/gsutil/boto/tests/devpay/__init__.py +0 -0
- data/packages/gsutil/boto/tests/devpay/test_s3.py +181 -0
- data/packages/gsutil/boto/tests/fps/__init__.py +0 -0
- data/packages/gsutil/boto/tests/fps/test.py +100 -0
- data/packages/gsutil/boto/tests/fps/test_verify_signature.py +12 -0
- data/packages/gsutil/boto/tests/integration/__init__.py +0 -0
- data/packages/gsutil/boto/tests/integration/beanstalk/test_wrapper.py +209 -0
- data/packages/gsutil/boto/tests/integration/cloudformation/__init__.py +21 -0
- data/packages/gsutil/boto/tests/integration/cloudformation/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/cloudformation/test_connection.py +110 -0
- data/packages/gsutil/boto/tests/integration/cloudsearch/__init__.py +21 -0
- data/packages/gsutil/boto/tests/integration/cloudsearch/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/datapipeline/test_layer1.py +122 -0
- data/packages/gsutil/boto/tests/integration/dynamodb/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/dynamodb/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/dynamodb/test_layer1.py +266 -0
- data/packages/gsutil/boto/tests/integration/dynamodb/test_layer2.py +484 -0
- data/packages/gsutil/boto/tests/integration/dynamodb/test_table.py +84 -0
- data/packages/gsutil/boto/tests/integration/ec2/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/ec2/autoscale/__init__.py +21 -0
- data/packages/gsutil/boto/tests/integration/ec2/autoscale/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/ec2/autoscale/test_connection.py +167 -0
- data/packages/gsutil/boto/tests/integration/ec2/cloudwatch/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/ec2/cloudwatch/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/ec2/cloudwatch/test_connection.py +277 -0
- data/packages/gsutil/boto/tests/integration/ec2/elb/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/ec2/elb/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/ec2/elb/test_connection.py +130 -0
- data/packages/gsutil/boto/tests/integration/ec2/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/ec2/test_connection.py +192 -0
- data/packages/gsutil/boto/tests/integration/ec2/vpc/__init__.py +0 -0
- data/packages/gsutil/boto/tests/integration/ec2/vpc/test_connection.py +95 -0
- data/packages/gsutil/boto/tests/integration/elasticache/__init__.py +0 -0
- data/packages/gsutil/boto/tests/integration/elasticache/test_layer1.py +67 -0
- data/packages/gsutil/boto/tests/integration/elastictranscoder/__init__.py +0 -0
- data/packages/gsutil/boto/tests/integration/elastictranscoder/test_cert_verification.py +35 -0
- data/packages/gsutil/boto/tests/integration/elastictranscoder/test_layer1.py +115 -0
- data/packages/gsutil/boto/tests/integration/emr/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/emr/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/glacier/__init__.py +22 -0
- data/packages/gsutil/boto/tests/integration/glacier/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/glacier/test_layer1.py +44 -0
- data/packages/gsutil/boto/tests/integration/glacier/test_layer2.py +45 -0
- data/packages/gsutil/boto/tests/integration/gs/__init__.py +0 -0
- data/packages/gsutil/boto/tests/integration/gs/cb_test_harness.py +71 -0
- data/packages/gsutil/boto/tests/integration/gs/test_basic.py +379 -0
- data/packages/gsutil/boto/tests/integration/gs/test_generation_conditionals.py +399 -0
- data/packages/gsutil/boto/tests/integration/gs/test_resumable_downloads.py +358 -0
- data/packages/gsutil/boto/tests/integration/gs/test_resumable_uploads.py +525 -0
- data/packages/gsutil/boto/tests/integration/gs/test_storage_uri.py +125 -0
- data/packages/gsutil/boto/tests/integration/gs/test_versioning.py +268 -0
- data/packages/gsutil/boto/tests/integration/gs/testcase.py +116 -0
- data/packages/gsutil/boto/tests/integration/gs/util.py +63 -0
- data/packages/gsutil/boto/tests/integration/iam/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/iam/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/mws/__init__.py +0 -0
- data/packages/gsutil/boto/tests/integration/mws/test.py +100 -0
- data/packages/gsutil/boto/tests/integration/rds/__init__.py +21 -0
- data/packages/gsutil/boto/tests/integration/rds/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/route53/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/route53/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/route53/test_zone.py +132 -0
- data/packages/gsutil/boto/tests/integration/s3/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/s3/mock_storage_service.py +589 -0
- data/packages/gsutil/boto/tests/integration/s3/other_cacerts.txt +70 -0
- data/packages/gsutil/boto/tests/integration/s3/test_bucket.py +263 -0
- data/packages/gsutil/boto/tests/integration/s3/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/s3/test_connection.py +245 -0
- data/packages/gsutil/boto/tests/integration/s3/test_cors.py +78 -0
- data/packages/gsutil/boto/tests/integration/s3/test_encryption.py +115 -0
- data/packages/gsutil/boto/tests/integration/s3/test_https_cert_validation.py +141 -0
- data/packages/gsutil/boto/tests/integration/s3/test_key.py +375 -0
- data/packages/gsutil/boto/tests/integration/s3/test_mfa.py +95 -0
- data/packages/gsutil/boto/tests/integration/s3/test_multidelete.py +181 -0
- data/packages/gsutil/boto/tests/integration/s3/test_multipart.py +139 -0
- data/packages/gsutil/boto/tests/integration/s3/test_pool.py +246 -0
- data/packages/gsutil/boto/tests/integration/s3/test_versioning.py +158 -0
- data/packages/gsutil/boto/tests/integration/sdb/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/sdb/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/sdb/test_connection.py +119 -0
- data/packages/gsutil/boto/tests/integration/ses/__init__.py +0 -0
- data/packages/gsutil/boto/tests/integration/ses/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/ses/test_connection.py +38 -0
- data/packages/gsutil/boto/tests/integration/sns/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/sns/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/sqs/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/sqs/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/sqs/test_connection.py +217 -0
- data/packages/gsutil/boto/tests/integration/sts/__init__.py +20 -0
- data/packages/gsutil/boto/tests/integration/sts/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/sts/test_session_token.py +65 -0
- data/packages/gsutil/boto/tests/integration/swf/__init__.py +0 -0
- data/packages/gsutil/boto/tests/integration/swf/test_cert_verification.py +40 -0
- data/packages/gsutil/boto/tests/integration/swf/test_layer1.py +246 -0
- data/packages/gsutil/boto/tests/integration/swf/test_layer1_workflow_execution.py +173 -0
- data/packages/gsutil/boto/tests/mturk/__init__.py +0 -0
- data/packages/gsutil/boto/tests/mturk/_init_environment.py +28 -0
- data/packages/gsutil/boto/tests/mturk/all_tests.py +24 -0
- data/packages/gsutil/boto/tests/mturk/cleanup_tests.py +47 -0
- data/packages/gsutil/boto/tests/mturk/common.py +45 -0
- data/packages/gsutil/boto/tests/mturk/create_free_text_question_regex.doctest +100 -0
- data/packages/gsutil/boto/tests/mturk/create_hit.doctest +92 -0
- data/packages/gsutil/boto/tests/mturk/create_hit_binary.doctest +94 -0
- data/packages/gsutil/boto/tests/mturk/create_hit_external.py +21 -0
- data/packages/gsutil/boto/tests/mturk/create_hit_from_hit_type.doctest +103 -0
- data/packages/gsutil/boto/tests/mturk/create_hit_test.py +21 -0
- data/packages/gsutil/boto/tests/mturk/create_hit_with_qualifications.py +16 -0
- data/packages/gsutil/boto/tests/mturk/hit_persistence.py +27 -0
- data/packages/gsutil/boto/tests/mturk/mocks.py +11 -0
- data/packages/gsutil/boto/tests/mturk/reviewable_hits.doctest +129 -0
- data/packages/gsutil/boto/tests/mturk/run-doctest.py +13 -0
- data/packages/gsutil/boto/tests/mturk/search_hits.doctest +16 -0
- data/packages/gsutil/boto/tests/mturk/selenium_support.py +61 -0
- data/packages/gsutil/boto/tests/mturk/support.py +7 -0
- data/packages/gsutil/boto/tests/mturk/test_disable_hit.py +11 -0
- data/packages/gsutil/boto/tests/test.py +59 -0
- data/packages/gsutil/boto/tests/unit/__init__.py +79 -0
- data/packages/gsutil/boto/tests/unit/auth/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/auth/test_sigv4.py +73 -0
- data/packages/gsutil/boto/tests/unit/beanstalk/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/beanstalk/test_layer1.py +128 -0
- data/packages/gsutil/boto/tests/unit/cloudformation/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/cloudformation/test_connection.py +605 -0
- data/packages/gsutil/boto/tests/unit/cloudformation/test_stack.py +63 -0
- data/packages/gsutil/boto/tests/unit/cloudfront/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/cloudfront/test_invalidation_list.py +113 -0
- data/packages/gsutil/boto/tests/unit/cloudfront/test_signed_urls.py +354 -0
- data/packages/gsutil/boto/tests/unit/cloudsearch/__init__.py +1 -0
- data/packages/gsutil/boto/tests/unit/cloudsearch/test_connection.py +241 -0
- data/packages/gsutil/boto/tests/unit/cloudsearch/test_document.py +324 -0
- data/packages/gsutil/boto/tests/unit/cloudsearch/test_search.py +325 -0
- data/packages/gsutil/boto/tests/unit/dynamodb/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/dynamodb/test_batch.py +103 -0
- data/packages/gsutil/boto/tests/unit/dynamodb/test_layer2.py +119 -0
- data/packages/gsutil/boto/tests/unit/dynamodb/test_types.py +82 -0
- data/packages/gsutil/boto/tests/unit/ec2/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/ec2/autoscale/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/ec2/autoscale/test_group.py +162 -0
- data/packages/gsutil/boto/tests/unit/ec2/test_address.py +39 -0
- data/packages/gsutil/boto/tests/unit/ec2/test_blockdevicemapping.py +79 -0
- data/packages/gsutil/boto/tests/unit/ec2/test_connection.py +480 -0
- data/packages/gsutil/boto/tests/unit/ec2/test_instance.py +243 -0
- data/packages/gsutil/boto/tests/unit/ec2/test_networkinterface.py +140 -0
- data/packages/gsutil/boto/tests/unit/ec2/test_volume.py +248 -0
- data/packages/gsutil/boto/tests/unit/emr/test_emr_responses.py +373 -0
- data/packages/gsutil/boto/tests/unit/glacier/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/glacier/test_concurrent.py +120 -0
- data/packages/gsutil/boto/tests/unit/glacier/test_job.py +60 -0
- data/packages/gsutil/boto/tests/unit/glacier/test_layer1.py +98 -0
- data/packages/gsutil/boto/tests/unit/glacier/test_layer2.py +266 -0
- data/packages/gsutil/boto/tests/unit/glacier/test_utils.py +116 -0
- data/packages/gsutil/boto/tests/unit/glacier/test_vault.py +100 -0
- data/packages/gsutil/boto/tests/unit/glacier/test_writer.py +185 -0
- data/packages/gsutil/boto/tests/unit/provider/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/provider/test_provider.py +176 -0
- data/packages/gsutil/boto/tests/unit/rds/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/rds/test_connection.py +131 -0
- data/packages/gsutil/boto/tests/unit/s3/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/s3/test_cors_configuration.py +77 -0
- data/packages/gsutil/boto/tests/unit/s3/test_key.py +75 -0
- data/packages/gsutil/boto/tests/unit/s3/test_keyfile.py +101 -0
- data/packages/gsutil/boto/tests/unit/s3/test_lifecycle.py +97 -0
- data/packages/gsutil/boto/tests/unit/s3/test_tagging.py +47 -0
- data/packages/gsutil/boto/tests/unit/s3/test_uri.py +257 -0
- data/packages/gsutil/boto/tests/unit/s3/test_website.py +188 -0
- data/packages/gsutil/boto/tests/unit/sns/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/sns/test_connection.py +99 -0
- data/packages/gsutil/boto/tests/unit/sqs/__init__.py +0 -0
- data/packages/gsutil/boto/tests/unit/sqs/test_connection.py +98 -0
- data/packages/gsutil/boto/tests/unit/sqs/test_queue.py +40 -0
- data/packages/gsutil/boto/tests/unit/sts/test_connection.py +74 -0
- data/packages/gsutil/boto/tests/unit/test_connection.py +60 -0
- data/packages/gsutil/boto/tests/unit/utils/test_utils.py +109 -0
- data/packages/gsutil/boto/tox.ini +8 -0
- data/packages/gsutil/gslib/README +5 -0
- data/packages/gsutil/gslib/__init__.py +22 -0
- data/packages/gsutil/gslib/__init__.pyc +0 -0
- data/packages/gsutil/gslib/addlhelp/__init__.py +15 -0
- data/packages/gsutil/gslib/addlhelp/acls.py +234 -0
- data/packages/gsutil/gslib/addlhelp/anon.py +57 -0
- data/packages/gsutil/gslib/addlhelp/command_opts.py +116 -0
- data/packages/gsutil/gslib/addlhelp/dev.py +139 -0
- data/packages/gsutil/gslib/addlhelp/metadata.py +186 -0
- data/packages/gsutil/gslib/addlhelp/naming.py +173 -0
- data/packages/gsutil/gslib/addlhelp/prod.py +160 -0
- data/packages/gsutil/gslib/addlhelp/projects.py +130 -0
- data/packages/gsutil/gslib/addlhelp/subdirs.py +110 -0
- data/packages/gsutil/gslib/addlhelp/support.py +86 -0
- data/packages/gsutil/gslib/addlhelp/versioning.py +242 -0
- data/packages/gsutil/gslib/addlhelp/wildcards.py +170 -0
- data/packages/gsutil/gslib/bucket_listing_ref.py +175 -0
- data/packages/gsutil/gslib/bucket_listing_ref.pyc +0 -0
- data/packages/gsutil/gslib/command.py +722 -0
- data/packages/gsutil/gslib/command.pyc +0 -0
- data/packages/gsutil/gslib/command_runner.py +101 -0
- data/packages/gsutil/gslib/command_runner.pyc +0 -0
- data/packages/gsutil/gslib/commands/__init__.py +15 -0
- data/packages/gsutil/gslib/commands/__init__.pyc +0 -0
- data/packages/gsutil/gslib/commands/cat.py +131 -0
- data/packages/gsutil/gslib/commands/cat.pyc +0 -0
- data/packages/gsutil/gslib/commands/chacl.py +532 -0
- data/packages/gsutil/gslib/commands/chacl.pyc +0 -0
- data/packages/gsutil/gslib/commands/config.py +694 -0
- data/packages/gsutil/gslib/commands/config.pyc +0 -0
- data/packages/gsutil/gslib/commands/cp.py +1818 -0
- data/packages/gsutil/gslib/commands/cp.pyc +0 -0
- data/packages/gsutil/gslib/commands/disablelogging.py +101 -0
- data/packages/gsutil/gslib/commands/disablelogging.pyc +0 -0
- data/packages/gsutil/gslib/commands/enablelogging.py +149 -0
- data/packages/gsutil/gslib/commands/enablelogging.pyc +0 -0
- data/packages/gsutil/gslib/commands/getacl.py +82 -0
- data/packages/gsutil/gslib/commands/getacl.pyc +0 -0
- data/packages/gsutil/gslib/commands/getcors.py +121 -0
- data/packages/gsutil/gslib/commands/getcors.pyc +0 -0
- data/packages/gsutil/gslib/commands/getdefacl.py +86 -0
- data/packages/gsutil/gslib/commands/getdefacl.pyc +0 -0
- data/packages/gsutil/gslib/commands/getlogging.py +137 -0
- data/packages/gsutil/gslib/commands/getlogging.pyc +0 -0
- data/packages/gsutil/gslib/commands/getversioning.py +116 -0
- data/packages/gsutil/gslib/commands/getversioning.pyc +0 -0
- data/packages/gsutil/gslib/commands/getwebcfg.py +122 -0
- data/packages/gsutil/gslib/commands/getwebcfg.pyc +0 -0
- data/packages/gsutil/gslib/commands/help.py +218 -0
- data/packages/gsutil/gslib/commands/help.pyc +0 -0
- data/packages/gsutil/gslib/commands/ls.py +578 -0
- data/packages/gsutil/gslib/commands/ls.pyc +0 -0
- data/packages/gsutil/gslib/commands/mb.py +172 -0
- data/packages/gsutil/gslib/commands/mb.pyc +0 -0
- data/packages/gsutil/gslib/commands/mv.py +159 -0
- data/packages/gsutil/gslib/commands/mv.pyc +0 -0
- data/packages/gsutil/gslib/commands/perfdiag.py +903 -0
- data/packages/gsutil/gslib/commands/perfdiag.pyc +0 -0
- data/packages/gsutil/gslib/commands/rb.py +113 -0
- data/packages/gsutil/gslib/commands/rb.pyc +0 -0
- data/packages/gsutil/gslib/commands/rm.py +239 -0
- data/packages/gsutil/gslib/commands/rm.pyc +0 -0
- data/packages/gsutil/gslib/commands/setacl.py +138 -0
- data/packages/gsutil/gslib/commands/setacl.pyc +0 -0
- data/packages/gsutil/gslib/commands/setcors.py +145 -0
- data/packages/gsutil/gslib/commands/setcors.pyc +0 -0
- data/packages/gsutil/gslib/commands/setdefacl.py +105 -0
- data/packages/gsutil/gslib/commands/setdefacl.pyc +0 -0
- data/packages/gsutil/gslib/commands/setmeta.py +428 -0
- data/packages/gsutil/gslib/commands/setmeta.pyc +0 -0
- data/packages/gsutil/gslib/commands/setversioning.py +114 -0
- data/packages/gsutil/gslib/commands/setversioning.pyc +0 -0
- data/packages/gsutil/gslib/commands/setwebcfg.py +190 -0
- data/packages/gsutil/gslib/commands/setwebcfg.pyc +0 -0
- data/packages/gsutil/gslib/commands/test.py +228 -0
- data/packages/gsutil/gslib/commands/test.pyc +0 -0
- data/packages/gsutil/gslib/commands/update.py +305 -0
- data/packages/gsutil/gslib/commands/update.pyc +0 -0
- data/packages/gsutil/gslib/commands/version.py +150 -0
- data/packages/gsutil/gslib/commands/version.pyc +0 -0
- data/packages/gsutil/gslib/exception.py +76 -0
- data/packages/gsutil/gslib/exception.pyc +0 -0
- data/packages/gsutil/gslib/help_provider.py +81 -0
- data/packages/gsutil/gslib/help_provider.pyc +0 -0
- data/packages/gsutil/gslib/name_expansion.py +550 -0
- data/packages/gsutil/gslib/name_expansion.pyc +0 -0
- data/packages/gsutil/gslib/no_op_auth_plugin.py +30 -0
- data/packages/gsutil/gslib/plurality_checkable_iterator.py +56 -0
- data/packages/gsutil/gslib/plurality_checkable_iterator.pyc +0 -0
- data/packages/gsutil/gslib/project_id.py +67 -0
- data/packages/gsutil/gslib/project_id.pyc +0 -0
- data/packages/gsutil/gslib/storage_uri_builder.py +56 -0
- data/packages/gsutil/gslib/storage_uri_builder.pyc +0 -0
- data/packages/gsutil/gslib/tests/__init__.py +15 -0
- data/packages/gsutil/gslib/tests/__init__.pyc +0 -0
- data/packages/gsutil/gslib/tests/test_chacl.py +236 -0
- data/packages/gsutil/gslib/tests/test_cp.py +267 -0
- data/packages/gsutil/gslib/tests/test_data/test.gif +0 -0
- data/packages/gsutil/gslib/tests/test_data/test.mp3 +0 -0
- data/packages/gsutil/gslib/tests/test_ls.py +66 -0
- data/packages/gsutil/gslib/tests/test_mv.py +69 -0
- data/packages/gsutil/gslib/tests/test_naming.py +989 -0
- data/packages/gsutil/gslib/tests/test_perfdiag.py +41 -0
- data/packages/gsutil/gslib/tests/test_plurality_checkable_iterator.py +67 -0
- data/packages/gsutil/gslib/tests/test_rm.py +143 -0
- data/packages/gsutil/gslib/tests/test_setacl.py +152 -0
- data/packages/gsutil/gslib/tests/test_setcors.py +168 -0
- data/packages/gsutil/gslib/tests/test_setmeta.py +91 -0
- data/packages/gsutil/gslib/tests/test_setversioning.py +44 -0
- data/packages/gsutil/gslib/tests/test_setwebcfg.py +63 -0
- data/packages/gsutil/gslib/tests/test_thread_pool.py +92 -0
- data/packages/gsutil/gslib/tests/test_wildcard_iterator.py +364 -0
- data/packages/gsutil/gslib/tests/testcase/__init__.py +18 -0
- data/packages/gsutil/gslib/tests/testcase/base.py +89 -0
- data/packages/gsutil/gslib/tests/testcase/integration_testcase.py +197 -0
- data/packages/gsutil/gslib/tests/testcase/unit_testcase.py +230 -0
- data/packages/gsutil/gslib/tests/util.py +125 -0
- data/packages/gsutil/gslib/tests/util.pyc +0 -0
- data/packages/gsutil/gslib/thread_pool.py +79 -0
- data/packages/gsutil/gslib/thread_pool.pyc +0 -0
- data/packages/gsutil/gslib/util.py +151 -0
- data/packages/gsutil/gslib/util.pyc +0 -0
- data/packages/gsutil/gslib/wildcard_iterator.py +492 -0
- data/packages/gsutil/gslib/wildcard_iterator.pyc +0 -0
- data/packages/gsutil/gsutil +377 -0
- data/packages/gsutil/gsutil.spec.in +75 -0
- data/packages/gsutil/oauth2_plugin/__init__.py +22 -0
- data/packages/gsutil/oauth2_plugin/__init__.pyc +0 -0
- data/packages/gsutil/oauth2_plugin/oauth2_client.py +642 -0
- data/packages/gsutil/oauth2_plugin/oauth2_client.pyc +0 -0
- data/packages/gsutil/oauth2_plugin/oauth2_client_test.py +374 -0
- data/packages/gsutil/oauth2_plugin/oauth2_helper.py +110 -0
- data/packages/gsutil/oauth2_plugin/oauth2_helper.pyc +0 -0
- data/packages/gsutil/oauth2_plugin/oauth2_plugin.py +24 -0
- data/packages/gsutil/oauth2_plugin/oauth2_plugin.pyc +0 -0
- data/packages/gsutil/pkg_gen.sh +54 -0
- data/packages/gsutil/pkg_util.py +60 -0
- data/packages/gsutil/setup.py +141 -0
- data/packages/gsutil/third_party/__init__.py +0 -0
- data/packages/gsutil/third_party/__init__.pyc +0 -0
- data/packages/gsutil/third_party/fancy_urllib/README +21 -0
- data/packages/gsutil/third_party/fancy_urllib/__init__.py +398 -0
- data/packages/gsutil/third_party/fancy_urllib/__init__.pyc +0 -0
- data/tasks/rubygem.rake +3 -1
- metadata +770 -7
- metadata.gz.sig +0 -0
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
# -*- coding: utf-8 -*-
|
|
2
|
+
# Copyright (c) 2012 Thomas Parslow http://almostobsolete.net/
|
|
3
|
+
#
|
|
4
|
+
# Permission is hereby granted, free of charge, to any person obtaining a
|
|
5
|
+
# copy of this software and associated documentation files (the
|
|
6
|
+
# "Software"), to deal in the Software without restriction, including
|
|
7
|
+
# without limitation the rights to use, copy, modify, merge, publish, dis-
|
|
8
|
+
# tribute, sublicense, and/or sell copies of the Software, and to permit
|
|
9
|
+
# persons to whom the Software is furnished to do so, subject to the fol-
|
|
10
|
+
# lowing conditions:
|
|
11
|
+
#
|
|
12
|
+
# The above copyright notice and this permission notice shall be included
|
|
13
|
+
# in all copies or substantial portions of the Software.
|
|
14
|
+
#
|
|
15
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
|
16
|
+
# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABIL-
|
|
17
|
+
# ITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT
|
|
18
|
+
# SHALL THE AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
|
19
|
+
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
|
21
|
+
# IN THE SOFTWARE.
|
|
22
|
+
#
|
|
23
|
+
from boto.compat import json
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
class UnexpectedHTTPResponseError(Exception):
|
|
27
|
+
def __init__(self, expected_responses, response):
|
|
28
|
+
self.status = response.status
|
|
29
|
+
self.body = response.read()
|
|
30
|
+
self.code = None
|
|
31
|
+
try:
|
|
32
|
+
body = json.loads(self.body)
|
|
33
|
+
self.code = body["code"]
|
|
34
|
+
msg = 'Expected %s, got ' % expected_responses
|
|
35
|
+
msg += '(%d, code=%s, message=%s)' % (response.status,
|
|
36
|
+
self.code,
|
|
37
|
+
body["message"])
|
|
38
|
+
except Exception:
|
|
39
|
+
msg = 'Expected %s, got (%d, %s)' % (expected_responses,
|
|
40
|
+
response.status,
|
|
41
|
+
self.body)
|
|
42
|
+
super(UnexpectedHTTPResponseError, self).__init__(msg)
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
class ArchiveError(Exception):
|
|
46
|
+
pass
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
class UploadArchiveError(ArchiveError):
|
|
50
|
+
pass
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
class DownloadArchiveError(ArchiveError):
|
|
54
|
+
pass
|
|
55
|
+
|
|
56
|
+
|
|
57
|
+
class TreeHashDoesNotMatchError(ArchiveError):
|
|
58
|
+
pass
|
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
# -*- coding: utf-8 -*-
|
|
2
|
+
# Copyright (c) 2012 Thomas Parslow http://almostobsolete.net/
|
|
3
|
+
#
|
|
4
|
+
# Permission is hereby granted, free of charge, to any person obtaining a
|
|
5
|
+
# copy of this software and associated documentation files (the
|
|
6
|
+
# "Software"), to deal in the Software without restriction, including
|
|
7
|
+
# without limitation the rights to use, copy, modify, merge, publish, dis-
|
|
8
|
+
# tribute, sublicense, and/or sell copies of the Software, and to permit
|
|
9
|
+
# persons to whom the Software is furnished to do so, subject to the fol-
|
|
10
|
+
# lowing conditions:
|
|
11
|
+
#
|
|
12
|
+
# The above copyright notice and this permission notice shall be included
|
|
13
|
+
# in all copies or substantial portions of the Software.
|
|
14
|
+
#
|
|
15
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
|
16
|
+
# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABIL-
|
|
17
|
+
# ITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT
|
|
18
|
+
# SHALL THE AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
|
19
|
+
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
|
21
|
+
# IN THE SOFTWARE.
|
|
22
|
+
#
|
|
23
|
+
from __future__ import with_statement
|
|
24
|
+
import math
|
|
25
|
+
import socket
|
|
26
|
+
|
|
27
|
+
from .exceptions import TreeHashDoesNotMatchError, DownloadArchiveError
|
|
28
|
+
from .utils import tree_hash_from_str
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
class Job(object):
|
|
32
|
+
|
|
33
|
+
DefaultPartSize = 4 * 1024 * 1024
|
|
34
|
+
|
|
35
|
+
ResponseDataElements = (('Action', 'action', None),
|
|
36
|
+
('ArchiveId', 'archive_id', None),
|
|
37
|
+
('ArchiveSizeInBytes', 'archive_size', 0),
|
|
38
|
+
('Completed', 'completed', False),
|
|
39
|
+
('CompletionDate', 'completion_date', None),
|
|
40
|
+
('CreationDate', 'creation_date', None),
|
|
41
|
+
('InventorySizeInBytes', 'inventory_size', 0),
|
|
42
|
+
('JobDescription', 'description', None),
|
|
43
|
+
('JobId', 'id', None),
|
|
44
|
+
('SHA256TreeHash', 'sha256_treehash', None),
|
|
45
|
+
('SNSTopic', 'sns_topic', None),
|
|
46
|
+
('StatusCode', 'status_code', None),
|
|
47
|
+
('StatusMessage', 'status_message', None),
|
|
48
|
+
('VaultARN', 'arn', None))
|
|
49
|
+
|
|
50
|
+
def __init__(self, vault, response_data=None):
|
|
51
|
+
self.vault = vault
|
|
52
|
+
if response_data:
|
|
53
|
+
for response_name, attr_name, default in self.ResponseDataElements:
|
|
54
|
+
setattr(self, attr_name, response_data[response_name])
|
|
55
|
+
else:
|
|
56
|
+
for response_name, attr_name, default in self.ResponseDataElements:
|
|
57
|
+
setattr(self, attr_name, default)
|
|
58
|
+
|
|
59
|
+
def __repr__(self):
|
|
60
|
+
return 'Job(%s)' % self.arn
|
|
61
|
+
|
|
62
|
+
def get_output(self, byte_range=None, validate_checksum=False):
|
|
63
|
+
"""
|
|
64
|
+
This operation downloads the output of the job. Depending on
|
|
65
|
+
the job type you specified when you initiated the job, the
|
|
66
|
+
output will be either the content of an archive or a vault
|
|
67
|
+
inventory.
|
|
68
|
+
|
|
69
|
+
You can download all the job output or download a portion of
|
|
70
|
+
the output by specifying a byte range. In the case of an
|
|
71
|
+
archive retrieval job, depending on the byte range you
|
|
72
|
+
specify, Amazon Glacier returns the checksum for the portion
|
|
73
|
+
of the data. You can compute the checksum on the client and
|
|
74
|
+
verify that the values match to ensure the portion you
|
|
75
|
+
downloaded is the correct data.
|
|
76
|
+
|
|
77
|
+
:type byte_range: tuple
|
|
78
|
+
:param range: A tuple of integer specifying the slice (in bytes)
|
|
79
|
+
of the archive you want to receive
|
|
80
|
+
|
|
81
|
+
:type validate_checksum: bool
|
|
82
|
+
:param validate_checksum: Specify whether or not to validate
|
|
83
|
+
the associate tree hash. If the response does not contain
|
|
84
|
+
a TreeHash, then no checksum will be verified.
|
|
85
|
+
|
|
86
|
+
"""
|
|
87
|
+
response = self.vault.layer1.get_job_output(self.vault.name,
|
|
88
|
+
self.id,
|
|
89
|
+
byte_range)
|
|
90
|
+
if validate_checksum and 'TreeHash' in response:
|
|
91
|
+
data = response.read()
|
|
92
|
+
actual_tree_hash = tree_hash_from_str(data)
|
|
93
|
+
if response['TreeHash'] != actual_tree_hash:
|
|
94
|
+
raise TreeHashDoesNotMatchError(
|
|
95
|
+
"The calculated tree hash %s does not match the "
|
|
96
|
+
"expected tree hash %s for the byte range %s" % (
|
|
97
|
+
actual_tree_hash, response['TreeHash'], byte_range))
|
|
98
|
+
return response
|
|
99
|
+
|
|
100
|
+
def download_to_file(self, filename, chunk_size=DefaultPartSize,
|
|
101
|
+
verify_hashes=True, retry_exceptions=(socket.error,)):
|
|
102
|
+
"""Download an archive to a file.
|
|
103
|
+
|
|
104
|
+
:type filename: str
|
|
105
|
+
:param filename: The name of the file where the archive
|
|
106
|
+
contents will be saved.
|
|
107
|
+
|
|
108
|
+
:type chunk_size: int
|
|
109
|
+
:param chunk_size: The chunk size to use when downloading
|
|
110
|
+
the archive.
|
|
111
|
+
|
|
112
|
+
:type verify_hashes: bool
|
|
113
|
+
:param verify_hashes: Indicates whether or not to verify
|
|
114
|
+
the tree hashes for each downloaded chunk.
|
|
115
|
+
|
|
116
|
+
"""
|
|
117
|
+
num_chunks = int(math.ceil(self.archive_size / float(chunk_size)))
|
|
118
|
+
with open(filename, 'wb') as output_file:
|
|
119
|
+
self._download_to_fileob(output_file, num_chunks, chunk_size,
|
|
120
|
+
verify_hashes, retry_exceptions)
|
|
121
|
+
|
|
122
|
+
def _download_to_fileob(self, fileobj, num_chunks, chunk_size, verify_hashes,
|
|
123
|
+
retry_exceptions):
|
|
124
|
+
for i in xrange(num_chunks):
|
|
125
|
+
byte_range = ((i * chunk_size), ((i + 1) * chunk_size) - 1)
|
|
126
|
+
data, expected_tree_hash = self._download_byte_range(
|
|
127
|
+
byte_range, retry_exceptions)
|
|
128
|
+
if verify_hashes:
|
|
129
|
+
actual_tree_hash = tree_hash_from_str(data)
|
|
130
|
+
if expected_tree_hash != actual_tree_hash:
|
|
131
|
+
raise TreeHashDoesNotMatchError(
|
|
132
|
+
"The calculated tree hash %s does not match the "
|
|
133
|
+
"expected tree hash %s for the byte range %s" % (
|
|
134
|
+
actual_tree_hash, expected_tree_hash, byte_range))
|
|
135
|
+
fileobj.write(data)
|
|
136
|
+
|
|
137
|
+
def _download_byte_range(self, byte_range, retry_exceptions):
|
|
138
|
+
# You can occasionally get socket.errors when downloading
|
|
139
|
+
# chunks from Glacier, so each chunk can be retried up
|
|
140
|
+
# to 5 times.
|
|
141
|
+
for _ in xrange(5):
|
|
142
|
+
try:
|
|
143
|
+
response = self.get_output(byte_range)
|
|
144
|
+
data = response.read()
|
|
145
|
+
expected_tree_hash = response['TreeHash']
|
|
146
|
+
return data, expected_tree_hash
|
|
147
|
+
except retry_exceptions, e:
|
|
148
|
+
continue
|
|
149
|
+
else:
|
|
150
|
+
raise DownloadArchiveError("There was an error downloading"
|
|
151
|
+
"byte range %s: %s" % (byte_range,
|
|
152
|
+
e))
|
|
@@ -0,0 +1,637 @@
|
|
|
1
|
+
# -*- coding: utf-8 -*-
|
|
2
|
+
# Copyright (c) 2012 Mitch Garnaat http://garnaat.org/
|
|
3
|
+
# Copyright (c) 2012 Amazon.com, Inc. or its affiliates. All Rights Reserved
|
|
4
|
+
#
|
|
5
|
+
# Permission is hereby granted, free of charge, to any person obtaining a
|
|
6
|
+
# copy of this software and associated documentation files (the
|
|
7
|
+
# "Software"), to deal in the Software without restriction, including
|
|
8
|
+
# without limitation the rights to use, copy, modify, merge, publish, dis-
|
|
9
|
+
# tribute, sublicense, and/or sell copies of the Software, and to permit
|
|
10
|
+
# persons to whom the Software is furnished to do so, subject to the fol-
|
|
11
|
+
# lowing conditions:
|
|
12
|
+
#
|
|
13
|
+
# The above copyright notice and this permission notice shall be included
|
|
14
|
+
# in all copies or substantial portions of the Software.
|
|
15
|
+
#
|
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
|
17
|
+
# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABIL-
|
|
18
|
+
# ITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT
|
|
19
|
+
# SHALL THE AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
|
20
|
+
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
21
|
+
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
|
22
|
+
# IN THE SOFTWARE.
|
|
23
|
+
#
|
|
24
|
+
|
|
25
|
+
import os
|
|
26
|
+
|
|
27
|
+
import boto.glacier
|
|
28
|
+
from boto.compat import json
|
|
29
|
+
from boto.connection import AWSAuthConnection
|
|
30
|
+
from .exceptions import UnexpectedHTTPResponseError
|
|
31
|
+
from .response import GlacierResponse
|
|
32
|
+
from .utils import ResettingFileSender
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
class Layer1(AWSAuthConnection):
|
|
36
|
+
|
|
37
|
+
Version = '2012-06-01'
|
|
38
|
+
"""Glacier API version."""
|
|
39
|
+
|
|
40
|
+
def __init__(self, aws_access_key_id=None, aws_secret_access_key=None,
|
|
41
|
+
account_id='-', is_secure=True, port=None,
|
|
42
|
+
proxy=None, proxy_port=None,
|
|
43
|
+
proxy_user=None, proxy_pass=None, debug=0,
|
|
44
|
+
https_connection_factory=None, path='/',
|
|
45
|
+
provider='aws', security_token=None,
|
|
46
|
+
suppress_consec_slashes=True,
|
|
47
|
+
region=None, region_name='us-east-1'):
|
|
48
|
+
|
|
49
|
+
if not region:
|
|
50
|
+
for reg in boto.glacier.regions():
|
|
51
|
+
if reg.name == region_name:
|
|
52
|
+
region = reg
|
|
53
|
+
break
|
|
54
|
+
|
|
55
|
+
self.region = region
|
|
56
|
+
self.account_id = account_id
|
|
57
|
+
AWSAuthConnection.__init__(self, region.endpoint,
|
|
58
|
+
aws_access_key_id, aws_secret_access_key,
|
|
59
|
+
is_secure, port, proxy, proxy_port,
|
|
60
|
+
proxy_user, proxy_pass, debug,
|
|
61
|
+
https_connection_factory,
|
|
62
|
+
path, provider, security_token,
|
|
63
|
+
suppress_consec_slashes)
|
|
64
|
+
|
|
65
|
+
def _required_auth_capability(self):
|
|
66
|
+
return ['hmac-v4']
|
|
67
|
+
|
|
68
|
+
def make_request(self, verb, resource, headers=None,
|
|
69
|
+
data='', ok_responses=(200,), params=None,
|
|
70
|
+
sender=None, response_headers=None):
|
|
71
|
+
if headers is None:
|
|
72
|
+
headers = {}
|
|
73
|
+
headers['x-amz-glacier-version'] = self.Version
|
|
74
|
+
uri = '/%s/%s' % (self.account_id, resource)
|
|
75
|
+
response = AWSAuthConnection.make_request(self, verb, uri,
|
|
76
|
+
params=params,
|
|
77
|
+
headers=headers,
|
|
78
|
+
sender=sender,
|
|
79
|
+
data=data)
|
|
80
|
+
if response.status in ok_responses:
|
|
81
|
+
return GlacierResponse(response, response_headers)
|
|
82
|
+
else:
|
|
83
|
+
# create glacier-specific exceptions
|
|
84
|
+
raise UnexpectedHTTPResponseError(ok_responses, response)
|
|
85
|
+
|
|
86
|
+
# Vaults
|
|
87
|
+
|
|
88
|
+
def list_vaults(self, limit=None, marker=None):
|
|
89
|
+
"""
|
|
90
|
+
This operation lists all vaults owned by the calling user’s
|
|
91
|
+
account. The list returned in the response is ASCII-sorted by
|
|
92
|
+
vault name.
|
|
93
|
+
|
|
94
|
+
By default, this operation returns up to 1,000 items. If there
|
|
95
|
+
are more vaults to list, the marker field in the response body
|
|
96
|
+
contains the vault Amazon Resource Name (ARN) at which to
|
|
97
|
+
continue the list with a new List Vaults request; otherwise,
|
|
98
|
+
the marker field is null. In your next List Vaults request you
|
|
99
|
+
set the marker parameter to the value Amazon Glacier returned
|
|
100
|
+
in the responses to your previous List Vaults request. You can
|
|
101
|
+
also limit the number of vaults returned in the response by
|
|
102
|
+
specifying the limit parameter in the request.
|
|
103
|
+
|
|
104
|
+
:type limit: int
|
|
105
|
+
:param limit: The maximum number of items returned in the
|
|
106
|
+
response. If you don't specify a value, the List Vaults
|
|
107
|
+
operation returns up to 1,000 items.
|
|
108
|
+
|
|
109
|
+
:type marker: str
|
|
110
|
+
:param marker: A string used for pagination. marker specifies
|
|
111
|
+
the vault ARN after which the listing of vaults should
|
|
112
|
+
begin. (The vault specified by marker is not included in
|
|
113
|
+
the returned list.) Get the marker value from a previous
|
|
114
|
+
List Vaults response. You need to include the marker only
|
|
115
|
+
if you are continuing the pagination of results started in
|
|
116
|
+
a previous List Vaults request. Specifying an empty value
|
|
117
|
+
("") for the marker returns a list of vaults starting
|
|
118
|
+
from the first vault.
|
|
119
|
+
"""
|
|
120
|
+
params = {}
|
|
121
|
+
if limit:
|
|
122
|
+
params['limit'] = limit
|
|
123
|
+
if marker:
|
|
124
|
+
params['marker'] = marker
|
|
125
|
+
return self.make_request('GET', 'vaults', params=params)
|
|
126
|
+
|
|
127
|
+
def describe_vault(self, vault_name):
|
|
128
|
+
"""
|
|
129
|
+
This operation returns information about a vault, including
|
|
130
|
+
the vault Amazon Resource Name (ARN), the date the vault was
|
|
131
|
+
created, the number of archives contained within the vault,
|
|
132
|
+
and the total size of all the archives in the vault. The
|
|
133
|
+
number of archives and their total size are as of the last
|
|
134
|
+
vault inventory Amazon Glacier generated. Amazon Glacier
|
|
135
|
+
generates vault inventories approximately daily. This means
|
|
136
|
+
that if you add or remove an archive from a vault, and then
|
|
137
|
+
immediately send a Describe Vault request, the response might
|
|
138
|
+
not reflect the changes.
|
|
139
|
+
|
|
140
|
+
:type vault_name: str
|
|
141
|
+
:param vault_name: The name of the new vault
|
|
142
|
+
"""
|
|
143
|
+
uri = 'vaults/%s' % vault_name
|
|
144
|
+
return self.make_request('GET', uri)
|
|
145
|
+
|
|
146
|
+
def create_vault(self, vault_name):
|
|
147
|
+
"""
|
|
148
|
+
This operation creates a new vault with the specified name.
|
|
149
|
+
The name of the vault must be unique within a region for an
|
|
150
|
+
AWS account. You can create up to 1,000 vaults per
|
|
151
|
+
account. For information on creating more vaults, go to the
|
|
152
|
+
Amazon Glacier product detail page.
|
|
153
|
+
|
|
154
|
+
You must use the following guidelines when naming a vault.
|
|
155
|
+
|
|
156
|
+
Names can be between 1 and 255 characters long.
|
|
157
|
+
|
|
158
|
+
Allowed characters are a–z, A–Z, 0–9, '_' (underscore),
|
|
159
|
+
'-' (hyphen), and '.' (period).
|
|
160
|
+
|
|
161
|
+
This operation is idempotent, you can send the same request
|
|
162
|
+
multiple times and it has no further effect after the first
|
|
163
|
+
time Amazon Glacier creates the specified vault.
|
|
164
|
+
|
|
165
|
+
:type vault_name: str
|
|
166
|
+
:param vault_name: The name of the new vault
|
|
167
|
+
"""
|
|
168
|
+
uri = 'vaults/%s' % vault_name
|
|
169
|
+
return self.make_request('PUT', uri, ok_responses=(201,),
|
|
170
|
+
response_headers=[('Location', 'Location')])
|
|
171
|
+
|
|
172
|
+
def delete_vault(self, vault_name):
|
|
173
|
+
"""
|
|
174
|
+
This operation deletes a vault. Amazon Glacier will delete a
|
|
175
|
+
vault only if there are no archives in the vault as per the
|
|
176
|
+
last inventory and there have been no writes to the vault
|
|
177
|
+
since the last inventory. If either of these conditions is not
|
|
178
|
+
satisfied, the vault deletion fails (that is, the vault is not
|
|
179
|
+
removed) and Amazon Glacier returns an error.
|
|
180
|
+
|
|
181
|
+
This operation is idempotent, you can send the same request
|
|
182
|
+
multiple times and it has no further effect after the first
|
|
183
|
+
time Amazon Glacier delete the specified vault.
|
|
184
|
+
|
|
185
|
+
:type vault_name: str
|
|
186
|
+
:param vault_name: The name of the new vault
|
|
187
|
+
"""
|
|
188
|
+
uri = 'vaults/%s' % vault_name
|
|
189
|
+
return self.make_request('DELETE', uri, ok_responses=(204,))
|
|
190
|
+
|
|
191
|
+
def get_vault_notifications(self, vault_name):
|
|
192
|
+
"""
|
|
193
|
+
This operation retrieves the notification-configuration
|
|
194
|
+
subresource set on the vault.
|
|
195
|
+
|
|
196
|
+
:type vault_name: str
|
|
197
|
+
:param vault_name: The name of the new vault
|
|
198
|
+
"""
|
|
199
|
+
uri = 'vaults/%s/notification-configuration' % vault_name
|
|
200
|
+
return self.make_request('GET', uri)
|
|
201
|
+
|
|
202
|
+
def set_vault_notifications(self, vault_name, notification_config):
|
|
203
|
+
"""
|
|
204
|
+
This operation retrieves the notification-configuration
|
|
205
|
+
subresource set on the vault.
|
|
206
|
+
|
|
207
|
+
:type vault_name: str
|
|
208
|
+
:param vault_name: The name of the new vault
|
|
209
|
+
|
|
210
|
+
:type notification_config: dict
|
|
211
|
+
:param notification_config: A Python dictionary containing
|
|
212
|
+
an SNS Topic and events for which you want Amazon Glacier
|
|
213
|
+
to send notifications to the topic. Possible events are:
|
|
214
|
+
|
|
215
|
+
* ArchiveRetrievalCompleted - occurs when a job that was
|
|
216
|
+
initiated for an archive retrieval is completed.
|
|
217
|
+
* InventoryRetrievalCompleted - occurs when a job that was
|
|
218
|
+
initiated for an inventory retrieval is completed.
|
|
219
|
+
|
|
220
|
+
The format of the dictionary is:
|
|
221
|
+
|
|
222
|
+
{'SNSTopic': 'mytopic',
|
|
223
|
+
'Events': [event1,...]}
|
|
224
|
+
"""
|
|
225
|
+
uri = 'vaults/%s/notification-configuration' % vault_name
|
|
226
|
+
json_config = json.dumps(notification_config)
|
|
227
|
+
return self.make_request('PUT', uri, data=json_config,
|
|
228
|
+
ok_responses=(204,))
|
|
229
|
+
|
|
230
|
+
def delete_vault_notifications(self, vault_name):
|
|
231
|
+
"""
|
|
232
|
+
This operation deletes the notification-configuration
|
|
233
|
+
subresource set on the vault.
|
|
234
|
+
|
|
235
|
+
:type vault_name: str
|
|
236
|
+
:param vault_name: The name of the new vault
|
|
237
|
+
"""
|
|
238
|
+
uri = 'vaults/%s/notification-configuration' % vault_name
|
|
239
|
+
return self.make_request('DELETE', uri, ok_responses=(204,))
|
|
240
|
+
|
|
241
|
+
# Jobs
|
|
242
|
+
|
|
243
|
+
def list_jobs(self, vault_name, completed=None, status_code=None,
|
|
244
|
+
limit=None, marker=None):
|
|
245
|
+
"""
|
|
246
|
+
This operation lists jobs for a vault including jobs that are
|
|
247
|
+
in-progress and jobs that have recently finished.
|
|
248
|
+
|
|
249
|
+
:type vault_name: str
|
|
250
|
+
:param vault_name: The name of the vault.
|
|
251
|
+
|
|
252
|
+
:type completed: boolean
|
|
253
|
+
:param completed: Specifies the state of the jobs to return.
|
|
254
|
+
If a value of True is passed, only completed jobs will
|
|
255
|
+
be returned. If a value of False is passed, only
|
|
256
|
+
uncompleted jobs will be returned. If no value is
|
|
257
|
+
passed, all jobs will be returned.
|
|
258
|
+
|
|
259
|
+
:type status_code: string
|
|
260
|
+
:param status_code: Specifies the type of job status to return.
|
|
261
|
+
Valid values are: InProgress|Succeeded|Failed. If not
|
|
262
|
+
specified, jobs with all status codes are returned.
|
|
263
|
+
|
|
264
|
+
:type limit: int
|
|
265
|
+
:param limit: The maximum number of items returned in the
|
|
266
|
+
response. If you don't specify a value, the List Jobs
|
|
267
|
+
operation returns up to 1,000 items.
|
|
268
|
+
|
|
269
|
+
:type marker: str
|
|
270
|
+
:param marker: An opaque string used for pagination. marker
|
|
271
|
+
specifies the job at which the listing of jobs should
|
|
272
|
+
begin. Get the marker value from a previous List Jobs
|
|
273
|
+
response. You need only include the marker if you are
|
|
274
|
+
continuing the pagination of results started in a previous
|
|
275
|
+
List Jobs request.
|
|
276
|
+
|
|
277
|
+
"""
|
|
278
|
+
params = {}
|
|
279
|
+
if limit:
|
|
280
|
+
params['limit'] = limit
|
|
281
|
+
if marker:
|
|
282
|
+
params['marker'] = marker
|
|
283
|
+
if status_code:
|
|
284
|
+
params['statuscode'] = status_code
|
|
285
|
+
if completed is not None:
|
|
286
|
+
params['completed'] = 'true' if completed else 'false'
|
|
287
|
+
uri = 'vaults/%s/jobs' % vault_name
|
|
288
|
+
return self.make_request('GET', uri, params=params)
|
|
289
|
+
|
|
290
|
+
def describe_job(self, vault_name, job_id):
|
|
291
|
+
"""
|
|
292
|
+
This operation returns information about a job you previously
|
|
293
|
+
initiated, including the job initiation date, the user who
|
|
294
|
+
initiated the job, the job status code/message and the Amazon
|
|
295
|
+
Simple Notification Service (Amazon SNS) topic to notify after
|
|
296
|
+
Amazon Glacier completes the job.
|
|
297
|
+
|
|
298
|
+
:type vault_name: str
|
|
299
|
+
:param vault_name: The name of the new vault
|
|
300
|
+
|
|
301
|
+
:type job_id: str
|
|
302
|
+
:param job_id: The ID of the job.
|
|
303
|
+
"""
|
|
304
|
+
uri = 'vaults/%s/jobs/%s' % (vault_name, job_id)
|
|
305
|
+
return self.make_request('GET', uri, ok_responses=(200,))
|
|
306
|
+
|
|
307
|
+
def initiate_job(self, vault_name, job_data):
|
|
308
|
+
"""
|
|
309
|
+
This operation initiates a job of the specified
|
|
310
|
+
type. Retrieving an archive or a vault inventory are
|
|
311
|
+
asynchronous operations that require you to initiate a job. It
|
|
312
|
+
is a two-step process:
|
|
313
|
+
|
|
314
|
+
* Initiate a retrieval job.
|
|
315
|
+
* After the job completes, download the bytes.
|
|
316
|
+
|
|
317
|
+
The retrieval is executed asynchronously. When you initiate
|
|
318
|
+
a retrieval job, Amazon Glacier creates a job and returns a
|
|
319
|
+
job ID in the response.
|
|
320
|
+
|
|
321
|
+
:type vault_name: str
|
|
322
|
+
:param vault_name: The name of the new vault
|
|
323
|
+
|
|
324
|
+
:type job_data: dict
|
|
325
|
+
:param job_data: A Python dictionary containing the
|
|
326
|
+
information about the requested job. The dictionary
|
|
327
|
+
can contain the following attributes:
|
|
328
|
+
|
|
329
|
+
* ArchiveId - The ID of the archive you want to retrieve.
|
|
330
|
+
This field is required only if the Type is set to
|
|
331
|
+
archive-retrieval.
|
|
332
|
+
* Description - The optional description for the job.
|
|
333
|
+
* Format - When initiating a job to retrieve a vault
|
|
334
|
+
inventory, you can optionally add this parameter to
|
|
335
|
+
specify the output format. Valid values are: CSV|JSON.
|
|
336
|
+
* SNSTopic - The Amazon SNS topic ARN where Amazon Glacier
|
|
337
|
+
sends a notification when the job is completed and the
|
|
338
|
+
output is ready for you to download.
|
|
339
|
+
* Type - The job type. Valid values are:
|
|
340
|
+
archive-retrieval|inventory-retrieval
|
|
341
|
+
* RetrievalByteRange - Optionally specify the range of
|
|
342
|
+
bytes to retrieve.
|
|
343
|
+
|
|
344
|
+
"""
|
|
345
|
+
uri = 'vaults/%s/jobs' % vault_name
|
|
346
|
+
response_headers = [('x-amz-job-id', u'JobId'),
|
|
347
|
+
('Location', u'Location')]
|
|
348
|
+
json_job_data = json.dumps(job_data)
|
|
349
|
+
return self.make_request('POST', uri, data=json_job_data,
|
|
350
|
+
ok_responses=(202,),
|
|
351
|
+
response_headers=response_headers)
|
|
352
|
+
|
|
353
|
+
def get_job_output(self, vault_name, job_id, byte_range=None):
|
|
354
|
+
"""
|
|
355
|
+
This operation downloads the output of the job you initiated
|
|
356
|
+
using Initiate a Job. Depending on the job type
|
|
357
|
+
you specified when you initiated the job, the output will be
|
|
358
|
+
either the content of an archive or a vault inventory.
|
|
359
|
+
|
|
360
|
+
You can download all the job output or download a portion of
|
|
361
|
+
the output by specifying a byte range. In the case of an
|
|
362
|
+
archive retrieval job, depending on the byte range you
|
|
363
|
+
specify, Amazon Glacier returns the checksum for the portion
|
|
364
|
+
of the data. You can compute the checksum on the client and
|
|
365
|
+
verify that the values match to ensure the portion you
|
|
366
|
+
downloaded is the correct data.
|
|
367
|
+
|
|
368
|
+
:type vault_name: str :param
|
|
369
|
+
:param vault_name: The name of the new vault
|
|
370
|
+
|
|
371
|
+
:type job_id: str
|
|
372
|
+
:param job_id: The ID of the job.
|
|
373
|
+
|
|
374
|
+
:type byte_range: tuple
|
|
375
|
+
:param range: A tuple of integers specifying the slice (in bytes)
|
|
376
|
+
of the archive you want to receive
|
|
377
|
+
"""
|
|
378
|
+
response_headers = [('x-amz-sha256-tree-hash', u'TreeHash'),
|
|
379
|
+
('Content-Range', u'ContentRange'),
|
|
380
|
+
('Content-Type', u'ContentType')]
|
|
381
|
+
headers = None
|
|
382
|
+
if byte_range:
|
|
383
|
+
headers = {'Range': 'bytes=%d-%d' % byte_range}
|
|
384
|
+
uri = 'vaults/%s/jobs/%s/output' % (vault_name, job_id)
|
|
385
|
+
response = self.make_request('GET', uri, headers=headers,
|
|
386
|
+
ok_responses=(200, 206),
|
|
387
|
+
response_headers=response_headers)
|
|
388
|
+
return response
|
|
389
|
+
|
|
390
|
+
# Archives
|
|
391
|
+
|
|
392
|
+
def upload_archive(self, vault_name, archive,
|
|
393
|
+
linear_hash, tree_hash, description=None):
|
|
394
|
+
"""
|
|
395
|
+
This operation adds an archive to a vault. For a successful
|
|
396
|
+
upload, your data is durably persisted. In response, Amazon
|
|
397
|
+
Glacier returns the archive ID in the x-amz-archive-id header
|
|
398
|
+
of the response. You should save the archive ID returned so
|
|
399
|
+
that you can access the archive later.
|
|
400
|
+
|
|
401
|
+
:type vault_name: str :param
|
|
402
|
+
:param vault_name: The name of the vault
|
|
403
|
+
|
|
404
|
+
:type archive: bytes
|
|
405
|
+
:param archive: The data to upload.
|
|
406
|
+
|
|
407
|
+
:type linear_hash: str
|
|
408
|
+
:param linear_hash: The SHA256 checksum (a linear hash) of the
|
|
409
|
+
payload.
|
|
410
|
+
|
|
411
|
+
:type tree_hash: str
|
|
412
|
+
:param tree_hash: The user-computed SHA256 tree hash of the
|
|
413
|
+
payload. For more information on computing the
|
|
414
|
+
tree hash, see http://goo.gl/u7chF.
|
|
415
|
+
|
|
416
|
+
:type description: str
|
|
417
|
+
:param description: An optional description of the archive.
|
|
418
|
+
"""
|
|
419
|
+
response_headers = [('x-amz-archive-id', u'ArchiveId'),
|
|
420
|
+
('Location', u'Location'),
|
|
421
|
+
('x-amz-sha256-tree-hash', u'TreeHash')]
|
|
422
|
+
uri = 'vaults/%s/archives' % vault_name
|
|
423
|
+
try:
|
|
424
|
+
content_length = str(len(archive))
|
|
425
|
+
except (TypeError, AttributeError):
|
|
426
|
+
# If a file like object is provided, try to retrieve
|
|
427
|
+
# the file size via fstat.
|
|
428
|
+
content_length = str(os.fstat(archive.fileno()).st_size)
|
|
429
|
+
headers = {'x-amz-content-sha256': linear_hash,
|
|
430
|
+
'x-amz-sha256-tree-hash': tree_hash,
|
|
431
|
+
'Content-Length': content_length}
|
|
432
|
+
if description:
|
|
433
|
+
headers['x-amz-archive-description'] = description
|
|
434
|
+
if self._is_file_like(archive):
|
|
435
|
+
sender = ResettingFileSender(archive)
|
|
436
|
+
else:
|
|
437
|
+
sender = None
|
|
438
|
+
return self.make_request('POST', uri, headers=headers,
|
|
439
|
+
sender=sender,
|
|
440
|
+
data=archive, ok_responses=(201,),
|
|
441
|
+
response_headers=response_headers)
|
|
442
|
+
|
|
443
|
+
def _is_file_like(self, archive):
|
|
444
|
+
return hasattr(archive, 'seek') and hasattr(archive, 'tell')
|
|
445
|
+
|
|
446
|
+
def delete_archive(self, vault_name, archive_id):
|
|
447
|
+
"""
|
|
448
|
+
This operation deletes an archive from a vault.
|
|
449
|
+
|
|
450
|
+
:type vault_name: str
|
|
451
|
+
:param vault_name: The name of the new vault
|
|
452
|
+
|
|
453
|
+
:type archive_id: str
|
|
454
|
+
:param archive_id: The ID for the archive to be deleted.
|
|
455
|
+
"""
|
|
456
|
+
uri = 'vaults/%s/archives/%s' % (vault_name, archive_id)
|
|
457
|
+
return self.make_request('DELETE', uri, ok_responses=(204,))
|
|
458
|
+
|
|
459
|
+
# Multipart
|
|
460
|
+
|
|
461
|
+
def initiate_multipart_upload(self, vault_name, part_size,
|
|
462
|
+
description=None):
|
|
463
|
+
"""
|
|
464
|
+
Initiate a multipart upload. Amazon Glacier creates a
|
|
465
|
+
multipart upload resource and returns it's ID. You use this
|
|
466
|
+
ID in subsequent multipart upload operations.
|
|
467
|
+
|
|
468
|
+
:type vault_name: str
|
|
469
|
+
:param vault_name: The name of the vault.
|
|
470
|
+
|
|
471
|
+
:type description: str
|
|
472
|
+
:param description: An optional description of the archive.
|
|
473
|
+
|
|
474
|
+
:type part_size: int
|
|
475
|
+
:param part_size: The size of each part except the last, in bytes.
|
|
476
|
+
The part size must be a multiple of 1024 KB multiplied by
|
|
477
|
+
a power of 2. The minimum allowable part size is 1MB and the
|
|
478
|
+
maximum is 4GB.
|
|
479
|
+
"""
|
|
480
|
+
response_headers = [('x-amz-multipart-upload-id', u'UploadId'),
|
|
481
|
+
('Location', u'Location')]
|
|
482
|
+
headers = {'x-amz-part-size': str(part_size)}
|
|
483
|
+
if description:
|
|
484
|
+
headers['x-amz-archive-description'] = description
|
|
485
|
+
uri = 'vaults/%s/multipart-uploads' % vault_name
|
|
486
|
+
response = self.make_request('POST', uri, headers=headers,
|
|
487
|
+
ok_responses=(201,),
|
|
488
|
+
response_headers=response_headers)
|
|
489
|
+
return response
|
|
490
|
+
|
|
491
|
+
def complete_multipart_upload(self, vault_name, upload_id,
|
|
492
|
+
sha256_treehash, archive_size):
|
|
493
|
+
"""
|
|
494
|
+
Call this to inform Amazon Glacier that all of the archive parts
|
|
495
|
+
have been uploaded and Amazon Glacier can now assemble the archive
|
|
496
|
+
from the uploaded parts.
|
|
497
|
+
|
|
498
|
+
:type vault_name: str
|
|
499
|
+
:param vault_name: The name of the vault.
|
|
500
|
+
|
|
501
|
+
:type upload_id: str
|
|
502
|
+
:param upload_id: The unique ID associated with this upload
|
|
503
|
+
operation.
|
|
504
|
+
|
|
505
|
+
:type sha256_treehash: str
|
|
506
|
+
:param sha256_treehash: The SHA256 tree hash of the entire
|
|
507
|
+
archive. It is the tree hash of SHA256 tree hash of the
|
|
508
|
+
individual parts. If the value you specify in the request
|
|
509
|
+
does not match the SHA256 tree hash of the final assembled
|
|
510
|
+
archive as computed by Amazon Glacier, Amazon Glacier
|
|
511
|
+
returns an error and the request fails.
|
|
512
|
+
|
|
513
|
+
:type archive_size: int
|
|
514
|
+
:param archive_size: The total size, in bytes, of the entire
|
|
515
|
+
archive. This value should be the sum of all the sizes of
|
|
516
|
+
the individual parts that you uploaded.
|
|
517
|
+
"""
|
|
518
|
+
response_headers = [('x-amz-archive-id', u'ArchiveId'),
|
|
519
|
+
('Location', u'Location')]
|
|
520
|
+
headers = {'x-amz-sha256-tree-hash': sha256_treehash,
|
|
521
|
+
'x-amz-archive-size': str(archive_size)}
|
|
522
|
+
uri = 'vaults/%s/multipart-uploads/%s' % (vault_name, upload_id)
|
|
523
|
+
response = self.make_request('POST', uri, headers=headers,
|
|
524
|
+
ok_responses=(201,),
|
|
525
|
+
response_headers=response_headers)
|
|
526
|
+
return response
|
|
527
|
+
|
|
528
|
+
def abort_multipart_upload(self, vault_name, upload_id):
|
|
529
|
+
"""
|
|
530
|
+
Call this to abort a multipart upload identified by the upload ID.
|
|
531
|
+
|
|
532
|
+
:type vault_name: str
|
|
533
|
+
:param vault_name: The name of the vault.
|
|
534
|
+
|
|
535
|
+
:type upload_id: str
|
|
536
|
+
:param upload_id: The unique ID associated with this upload
|
|
537
|
+
operation.
|
|
538
|
+
"""
|
|
539
|
+
uri = 'vaults/%s/multipart-uploads/%s' % (vault_name, upload_id)
|
|
540
|
+
return self.make_request('DELETE', uri, ok_responses=(204,))
|
|
541
|
+
|
|
542
|
+
def list_multipart_uploads(self, vault_name, limit=None, marker=None):
|
|
543
|
+
"""
|
|
544
|
+
Lists in-progress multipart uploads for the specified vault.
|
|
545
|
+
|
|
546
|
+
:type vault_name: str
|
|
547
|
+
:param vault_name: The name of the vault.
|
|
548
|
+
|
|
549
|
+
:type limit: int
|
|
550
|
+
:param limit: The maximum number of items returned in the
|
|
551
|
+
response. If you don't specify a value, the operation
|
|
552
|
+
returns up to 1,000 items.
|
|
553
|
+
|
|
554
|
+
:type marker: str
|
|
555
|
+
:param marker: An opaque string used for pagination. marker
|
|
556
|
+
specifies the item at which the listing should
|
|
557
|
+
begin. Get the marker value from a previous
|
|
558
|
+
response. You need only include the marker if you are
|
|
559
|
+
continuing the pagination of results started in a previous
|
|
560
|
+
request.
|
|
561
|
+
"""
|
|
562
|
+
params = {}
|
|
563
|
+
if limit:
|
|
564
|
+
params['limit'] = limit
|
|
565
|
+
if marker:
|
|
566
|
+
params['marker'] = marker
|
|
567
|
+
uri = 'vaults/%s/multipart-uploads' % vault_name
|
|
568
|
+
return self.make_request('GET', uri, params=params)
|
|
569
|
+
|
|
570
|
+
def list_parts(self, vault_name, upload_id, limit=None, marker=None):
|
|
571
|
+
"""
|
|
572
|
+
Lists in-progress multipart uploads for the specified vault.
|
|
573
|
+
|
|
574
|
+
:type vault_name: str
|
|
575
|
+
:param vault_name: The name of the vault.
|
|
576
|
+
|
|
577
|
+
:type upload_id: str
|
|
578
|
+
:param upload_id: The unique ID associated with this upload
|
|
579
|
+
operation.
|
|
580
|
+
|
|
581
|
+
:type limit: int
|
|
582
|
+
:param limit: The maximum number of items returned in the
|
|
583
|
+
response. If you don't specify a value, the operation
|
|
584
|
+
returns up to 1,000 items.
|
|
585
|
+
|
|
586
|
+
:type marker: str
|
|
587
|
+
:param marker: An opaque string used for pagination. marker
|
|
588
|
+
specifies the item at which the listing should
|
|
589
|
+
begin. Get the marker value from a previous
|
|
590
|
+
response. You need only include the marker if you are
|
|
591
|
+
continuing the pagination of results started in a previous
|
|
592
|
+
request.
|
|
593
|
+
"""
|
|
594
|
+
params = {}
|
|
595
|
+
if limit:
|
|
596
|
+
params['limit'] = limit
|
|
597
|
+
if marker:
|
|
598
|
+
params['marker'] = marker
|
|
599
|
+
uri = 'vaults/%s/multipart-uploads/%s' % (vault_name, upload_id)
|
|
600
|
+
return self.make_request('GET', uri, params=params)
|
|
601
|
+
|
|
602
|
+
def upload_part(self, vault_name, upload_id, linear_hash,
|
|
603
|
+
tree_hash, byte_range, part_data):
|
|
604
|
+
"""
|
|
605
|
+
Lists in-progress multipart uploads for the specified vault.
|
|
606
|
+
|
|
607
|
+
:type vault_name: str
|
|
608
|
+
:param vault_name: The name of the vault.
|
|
609
|
+
|
|
610
|
+
:type linear_hash: str
|
|
611
|
+
:param linear_hash: The SHA256 checksum (a linear hash) of the
|
|
612
|
+
payload.
|
|
613
|
+
|
|
614
|
+
:type tree_hash: str
|
|
615
|
+
:param tree_hash: The user-computed SHA256 tree hash of the
|
|
616
|
+
payload. For more information on computing the
|
|
617
|
+
tree hash, see http://goo.gl/u7chF.
|
|
618
|
+
|
|
619
|
+
:type upload_id: str
|
|
620
|
+
:param upload_id: The unique ID associated with this upload
|
|
621
|
+
operation.
|
|
622
|
+
|
|
623
|
+
:type byte_range: tuple of ints
|
|
624
|
+
:param byte_range: Identfies the range of bytes in the assembled
|
|
625
|
+
archive that will be uploaded in this part.
|
|
626
|
+
|
|
627
|
+
:type part_data: bytes
|
|
628
|
+
:param part_data: The data to be uploaded for the part
|
|
629
|
+
"""
|
|
630
|
+
headers = {'x-amz-content-sha256': linear_hash,
|
|
631
|
+
'x-amz-sha256-tree-hash': tree_hash,
|
|
632
|
+
'Content-Range': 'bytes %d-%d/*' % byte_range}
|
|
633
|
+
response_headers = [('x-amz-sha256-tree-hash', u'TreeHash')]
|
|
634
|
+
uri = 'vaults/%s/multipart-uploads/%s' % (vault_name, upload_id)
|
|
635
|
+
return self.make_request('PUT', uri, headers=headers,
|
|
636
|
+
data=part_data, ok_responses=(204,),
|
|
637
|
+
response_headers=response_headers)
|