Fun with Adobe ColdFusion and REST or cfhttp still doesn't support PATCH

Author: Steven Neiland
Published:

Warning: This blog entry was written two or more years ago. Therefore, it may contain broken links, out-dated or misleading content, or information that is just plain wrong. Please read on with caution.

Do you know what. I am beginning to think that Adobe ColdFusion is the real April Fool's Day joke. I mean how many times can a company fail to live up to reasonable expectations before you start to think they are having a laugh.

Take for example trying to use the <cfhttp> tag to work with REST API's.

The Common HTTP Verbs

So recently I've been working a lot with REST API's from both the creating and consuming side. In particular I have been working with the SalesForce REST API.

Now you are probably familiar with the four main VERB's used in REST API's (GET, POST, PUT, DELETE) in addition to (TRACE, HEAD & OPTIONS). These four verbs roughly correspond with the database actions (SELECT, INSERT, UPDATE, DELETE). However they are not exactly the same.

If you read the rfc's you will note that the PUT verb does not update a resource, it replaces it completely. What this means is that according to the spec you cannot update a single value in a record using PUT, you have to instead replace the entire record with new values even if all but one of them are the same.

For most cases when you only have a handful of fields to a record this is not a big deal, but if you have resources with potentially hundreds of fields then you cannot use PUT to only update a select set of fields in the record and actually be adhering to the REST specification.

A great example of this is the salesforce REST api. A single record can have any number of fields and doing a put to replace all of them for updating a single field is both wasteful and awkward. To get around this they use a different verb the PATCH verb for updating selected fields in a resource.

Enter PATCH

Per RFC 5789 this verb is used to update select parts of a record without replacing the whole record. Adding PATCH into the mix gives us this list

  • GET: Retrieve resource(s)
  • POST: Create a new resource
  • PUT: Completely replace an existing resourcewith a new resource.
  • PATCH: Update selected parts of an existing resource with new values.
  • DELETE: Delete a resource
  • OPTIONS: Query the options/requirements on a resource without modifying said resource.
  • HEAD: Returns the same meta information as the GET response on the resource but without the response body.
  • TRACE: allows the client to see what is being received at the other end of the request chain and used for testing or diagnostic information.

While it does not get used or talked about as much as the other verbs it is an IETF proposed standard and has been in use now for a while. So of course ColdFusion supports it right, right...

The PATCH that doesn't exist

To test this out I tried to do a PATCH on a record in salesforce per their developer documentation. Here is an example of the code I tried to use.

<cfhttp url="https://{salesforceurl}" method="PATCH">
      <cfhttpparam type="body" value="{body containing update instructions}" />
</cfhttp>

And here is the error I was presented with.

Attribute validation error for CFHTTP.

The value of the METHOD attribute, which is currently PATCH, must be one of the values: PUT,POST,GET,TRACE,DELETE,HEAD,OPTIONS.

I don't even know why I was surprised that once again Adobe had implemented something half arsed.

Adobe ColdFusion PATCH History

So I go and do the first thing I always do when I run into a bug, I googled for existing bug tickets and work arounds.

After only a few seconds I find a link to Elliott Sprehn's mirror of the original ColdFusion bug tracker where I see Sean Coyne raised a feature request on Fri Jun 10 2011 to add support for the PATCH verb in the cfhttp tag. That's nearly three years ago now.

This bug was subsequently migrated into the new ColdFusion bugtracker with a new ticket number of 3043855. Clicking through shows that this ticket was closed/deferred with the status of "NotEnoughTime".

So yet again, Adobe decided that they did not have time to add a simple enhancement that would allow developers to work with one of the largest API's in the corporate world because they could not find time at any point in three years.

Railo PATCH Support History

Now I would like to contrast the Adobe response of insufficient time with the railo team's response when ticket 2388 - Allow CFHTTP to send PATCH was raised last year.

  • Created: 14/Apr/13 5:33 AM
  • Updated: 15/Apr/13 1:46 PM
  • Resolved: 15/Apr/13 5:01 AM

Yup thats right. In 23 hours and 28 minutes from the ticket being raised the railo team had identified the problem, enhanced the tag, tested it and added it to the next release version.

Oh and as a bonus they gave instructions on how to patch the then current version of Railo to also support the PATCH verb.

Compare this to Adobe who two years and ten months later have still done nothing to fix this and probably will not for the next release either.

SalesForce PATCH Work Around

Fortunately for me the SalesForce api team allowed for this possibility when they built their api (they must have to deal with CF developers a lot) as they built in a work around.

To do a patch on a salesforce resource, use the POST method instead and append the _httpMethod=PATCH override to the url like so.

<cfhttp url="https://{salesforceurl}?_HttpMethod=PATCH" method="POST">
      <cfhttpparam type="body" value="{body containing update instructions}" />
</cfhttp>

So to conclude I have two things to say.

  1. It's lucky for me the salesforce developers had more foresight than the Adobe ones because otherwise I don't know how I would have gotten my task done in time
  2. I can't wait for the day we get off ColdFusion and onto Railo at work.

Reader Comments

Sean Coyne's Gravatar
Sean Coyne
Tuesday, April 1, 2014 at 11:38:47 AM Coordinated Universal Time

I couldn't believe it when I saw the defer notice in my email this morning

Jose's Gravatar
Jose
Wednesday, April 2, 2014 at 11:09:44 AM Coordinated Universal Time

Taffy should take care of this, http://taffy.io/

Steven Neiland's Gravatar
Steven Neiland
Wednesday, April 2, 2014 at 12:47:56 PM Coordinated Universal Time

Jose,
Taffy is a framework for building a rest api in ColdFusion. The problem I am highlighting is when you want to *talk* to a rest api from CF using the cfhttp tag.

sathish's Gravatar
sathish
Friday, January 30, 2015 at 11:07:28 PM Coordinated Universal Time

Hi,

I was checking something about RESTFul API in ColdFusion and came up with ur blog post. But recently there is a CF11 documentation that the PATCH method has been implemented.

https://wikidocs.adobe.com/wiki/display/coldfusionen/cfhttp


Matt W's Gravatar
Matt W
Wednesday, September 2, 2015 at 12:01:38 PM Coordinated Universal Time

If you are not yet on CF11, then you can try this work around. Of course it depends on if the API supports it or not. It worked for me when dealing with iCIMS' API.

Do a cfhttp method="post", but also add
cfhttpparam type="header" name="X-HTTP-Method-Override" value="PATCH"

  • Please keep comments on-topic.
  • Please do not post unrelated questions or large chunks of code.
  • Please do not engage in flaming/abusive behaviour.
  • Comments that contain advertisments or appear to be created for the purpose of link building, will not be published.

Archives Blog Listing