0

I'm running Coldfusion8 and am using the Amazon S3 Rest Wrapper CFC trying to set it up with a EU bucket.

I can use the cfc to set up buckets in the US, but whenever I'm changing to the EU setting, it does not work.

Here is the function being used:

<cffunction name="putBucket" access="public" output="false" returntype="boolean" description="Creates a bucket.">
    <cfargument name="bucketName" type="string" required="true">
    <cfargument name="acl" type="string" required="false" default="public-read">
    <cfargument name="storageLocation" type="string" required="false" default="">

    <cfset var strXML = "">
    <cfset var dateTimeString = GetHTTPTimeString(Now())>
    <cfset var destination = "http://s3.amazonaws.com/">

    <!--- Create a canonical string to send based on operation requested ---> 
    <cfset var cs = "PUT\n\ntext/html\n#dateTimeString#\nx-amz-acl:#arguments.acl#\n/#arguments.bucketName#">

    <cfset var signature = createSignature(cs)>
    <!--- added switch to EU --->
    <cfif arguments.storageLocation EQ "EU">
        <cfset destination = "http://s3-eu-west-1.amazonaws.com/">
    </cfif>

    <!--- Create a proper signature --->
    <cfif compare(arguments.storageLocation,'')>
        <cfsavecontent variable="strXML">
            <CreateBucketConfiguration xmlns="http://s3.amazonaws.com/doc/2006-03-01/"><LocationConstraint>#arguments.storageLocation#</LocationConstraint></CreateBucketConfiguration>
        </cfsavecontent>
    <cfelse>
        <cfset strXML = "">
    </cfif>

    <!--- put the bucket via REST --->
    <cfhttp method="PUT" url="#destination##arguments.bucketName#" charset="utf-8">
        <cfhttpparam type="header" name="Content-Type" value="text/html">
        <cfhttpparam type="header" name="Date" value="#dateTimeString#">
        <cfhttpparam type="header" name="x-amz-acl" value="#arguments.acl#">
        <cfhttpparam type="header" name="Authorization" value="AWS #variables.accessKeyId#:#signature#">
        <cfhttpparam type="body" value="#trim(strXML)#">
    </cfhttp>

    <cfreturn true>
</cffunction>

I have added the switch to the EU region URL, but this doesn't work either.

Any idea what I need to do in order to create a bucket in the EU?

EDIT:
I have fixed the regional values. It still doesn't work tough, because if I pass a regional value other than "", this line:

 <cfif compare(arguments.storageLocation,'')>
    <cfsavecontent variable="strXML">
       <CreateBucketConfiguration xmlns="http://s3.amazonaws.com/doc/2006-03-01/"><LocationConstraint>#arguments.storageLocation#</LocationConstraint></CreateBucketConfiguration>
     </cfsavecontent>
 <cfelse>
     <cfset strXML = "">
 </cfif>

will produce a strXML like so:

 <CreateBucketConfiguration xmlns="http://s3.amazonaws.com/doc/2006-03-01/"><LocationConstraint>#arguments.storageLocation#</LocationConstraint></CreateBucketConfiguration> 

which creates the bad request error again

frequent
  • 27,643
  • 59
  • 181
  • 333
  • You said it doesn't work, but what actually happens? What is the return value from your `PUT` request? – Dan Short Aug 10 '12 at 13:25
  • Right now I'm posting this to the function: bucketName=_my_bucket_&acl=public-read&storage=eu-west-1&createBucket=Create+Bucket. As the form posts to itself the page is just reloaded and the new bucket doesn't show up in the page listing (neither on AWS console). Where do I find the return value from the put request? – frequent Aug 10 '12 at 13:30
  • 1
    After your `cfhttp` request in the method you posted, add `` and see what the response is from Amazon. That should tell you why Amazon decided not to create your bucket. – Dan Short Aug 10 '12 at 14:36
  • Ah. 400 Bad Request (InvalidLocationConstraint) – frequent Aug 10 '12 at 14:51

2 Answers2

1

You need to use the proper values for the storage location. From the API documents, I believe those values are:

The preferred geographical location for the bucket. [Allowed values: AmazonS3::REGION_US_E1, AmazonS3::REGION_US_W1, AmazonS3::REGION_EU_W1, AmazonS3::REGION_APAC_SE1, AmazonS3::REGION_APAC_NE1]

Dan Short
  • 9,598
  • 2
  • 28
  • 53
  • You were correct about the region, but I still cannot get it to work. See my edit above – frequent Aug 16 '12 at 12:18
  • You need a `` around your `#Arguments.storageLocation#`, that's why it's just putting the pound signs in your string. – Dan Short Aug 16 '12 at 14:25
  • I tried that, still doesn't work. In the meantime I just created an EU bucket on my AWS console. While this shows up on my s3.cfc test page, trying to access the bucket or upload any images produces errors (if it tells you anything: an error occured while Searching an XML document. The Prefix must be resolved in the name scope ) refrerring to this line in s3.cfc: contents = xmlSearch(data, "//:Contents") – frequent Aug 16 '12 at 15:24
0

If you are running this on Linux, you could alternatively use the S3CMD tools

sudo apt-get install s3cmd

You will then need to run the configuration procedure or even better, build and maintain configuration in your source control and deploy to the server making the S3 commands

s3cmd --configure

Generally, the configuration includes information (in particular keys) about your S3 account. Make sure if you use a file you set permissions on the file correctly so you don't have to execute the s3cmd's as root

and then in you application

<cfexecute name="s3cmd" arguments="mb s3://my-new-bucket-name">
William Greenly
  • 3,914
  • 20
  • 18
  • Thanks for the info. Running windows though. I have not made it to uploading files, but read it needs to be acl = public-read. Is that what you mean by "...if you use a file you set permissons on the file correctly..." – frequent Aug 10 '12 at 12:54