Shaun Mccran

My digital playground

01
O
C
T
2009

Introducing third party applications into your frameworks, good practice?

A recent development involved some changes to a large script that was using a product called ImageMagick (link). It is an image manipulation tool that allows you to perform transformations and other actions on image files. The product seems stable enough, and can be executed from a web interface using cfexecute, in a kind of command line prompt method.

It got me thinking as to why the application wasn't using cfimage, and then lead me to examine the wider topic of whether to use ColdFusion's in built functionality, or opt for other third party products.

I can think of a few obvious deciding factors for both pro and con, the first that springs to mind is performance.

Is there a marked performance difference between a ColdFusion function, and the third party application? Is it better to pass the load of to the operating system, rather than have ColdFusion perform whatever processing function it is supposed to do? In this case it would be a race between cfexecute, and cfimage, so there may be very little difference in it.

The second major point that springs to mind is the knowledge base of the developer, and the structure of whatever framework you are using. What I really mean by this is 'if your chosen technology can perform a function, why not utilise it to its full potential?' . It seems a bizarre choice indeed to deliberately not harness a function that your platform can already provide, and instead introduce another code base or application into the framework.

It also introduces another hurdle for the development staff, they may well be familiar with how an existing Tag works, but be totally unaware of the third party application, as was my case here.

A long winded intro, but here is the code I used:

view plain print about
1<!--- setup vars --->
2<cfset variables.destination = "C:\dev\images\testimage.jpg">
3<cfset variables.source = "C:\dev\images\testimage.jpg">
4<cfset variables.width = "100">
5<cfset variables.height = "100">
6<cfset variables.exec = "C:\dev\apps\imageMagick\convert.exe">
7
8<!--- executing an external application version --->
9<cfexecute name="#variables.exec#" arguments="-size #variables.width# #variables.source# -geometry #variables.height# -strip #variables.destination#" variable="imageinfo" timeout="3" />
10
11<!--- CFimage version --->
12<cfimage source="#variables.source#" action="resize" width="#variables.width#" height="#variables.height#" destination="#variables.destination#">

30
S
E
P
2009

A simple Fusebox reset function

A simple Fusebox reset function

I am always forgetting the application URL for resetting fusebox frameworks, so instead of having to type out the entire fuseaction url, and appending the load variables, and the parsing variables you can create a fuse action for it.

view plain print about
1<cffunction name="rebuild">
2        <cfargument name="myFusebox" />
3        <cfargument name="event" />
4
5        <cfset xfa.reinit = "index.cfm?" & FUSEBOX_PARAMETERS.fuseactionVariable & "=" & "&fusebox.loadclean=true&fusebox.parseall=false&fusebox.execute=true&fusebox.password=" & FUSEBOX_PARAMETERS.password>
6        <cflocation url="#xfa.reinit#" addtoken="false">
7    </cffunction>

The code above will build the URL using the fuse action variable (IE 'action=' or whatever you have specified). It also uses the fusebox password set in your Application.cfc.

There may be a small security risk involved with this, so don't use an obvious name for the function. Also they would need your fusebox password.

Even then thought the only potential issue I can see with this is that someone may empty your framework cache and rebuild your application. Which isn't all that bad?

01
S
E
P
2009

Incorrect error message reporting using CFFile action rename

During a batch process that I was writing recently I was using a CFfile operation to rename some files.

When running it I came across this error message:

view plain print about
1Attribute validation error for tag CFFILE.
2The value of the attribute source, which is currently "C:\fullUrl.jpg", is invalid.

This is the calling cfml code. The actual variable values aren't important.

view plain print about
1<cffile action="rename" source="#variables.tmpFileLocation#" destination="#variables.dir#/#variables.photoid#.jpg">

So I checked and doubled check the source url, and manually browsed to the directory and viewed it. The file was right there! I had a wander around online and found that this isn't a new issue, but more a bad error report.

The error isn't actually relating to the 'source' attribute at all, but rather the 'destination' attribute. In this case it was a file/folder permissions problem. (I didn't have write access). It was simply a case of Coldfusion server reporting it incorrectly.

26
A
U
G
2009

Example of inserting a Struct() into a database using keys

A while ago a colleague and I were working on a timesheet application in Flex. The idea was that you could commit a custom timebar object, generated in flex, and it would update the dataset in the back end using the ColdFusion flex gateway.

I came across the code recently, and decided to tidy it up a bit, and make the query dynamic, based on the Struct contents. The obvious limitation to this is that your Struct and your database schema have to match exactly.

I won't go into the Flex application here, but I've emulated its input arguments here with a pre-populated structure.

view plain print about
1<cfscript>
2 timesheetTask = StructNew();
3 StructInsert(timesheetTask, "employeeid", '36');
4 StructInsert(timesheetTask, "timesheetDT", '0');
5 StructInsert(timesheetTask, "projectid", '6');
6 StructInsert(timesheetTask, "weekid", '25');
7 StructInsert(timesheetTask, "taskid", '39');
8 StructInsert(timesheetTask, "hours", '8');
9 StructInsert(timesheetTask, "comment", 'Comments for this task live here');
10 StructInsert(timesheetTask, "szStatus", '1');
11 StructInsert(timesheetTask, "iFirstLineApproval", '23');
12 StructInsert(timesheetTask, "iSecondLineApproval", '34');
13 StructInsert(timesheetTask, "iCurrentApprover", '');
14 StructInsert(timesheetTask, "szRejectReason", '');
15 StructInsert(timesheetTask, "szDescription", '');
16
17 updateTimesheet = createObject("component", "timesheet");
18 updateTimesheet.updateTask(timesheetTask);
19
</cfscript>

Notice that this code also calls the CFC object at the end. The data itself isn't massively important, it's a time object for recording tasks.

Next we have the function, which accepts a Struct() argument called 'taskStruct'. I then loop through the structure, and populate a SQL query using the keys from a collection. The only logic is a check to see if it is the last structure element, as this controls the ',' placement.

view plain print about
1<cffunction name="updateTask" access="remote" returntype="string" hint="Creates a record for timesheet tasks">
2 <cfargument name="taskStruct" type="struct" required="yes">
3 <cfset var count = 0>
4
5 <cfdump var="#arguments.taskStruct#">
6 <cfset variables.structSize = structCount(arguments.taskStruct)>
7
8 <cfquery datasource="#application.dsn#">
9 INSERT INTO [dbo].[timesheet]
10 (<cfloop collection="#arguments.taskStruct#" item="key">
11 [#key#]
12 <cfset count = count + 1>
13 <cfif count LT variables.structSize>,</cfif>
14 </cfloop>)
15
16 <cfset count = 0>
17
18 VALUES(<cfloop collection="#arguments.taskStruct#" item="key">
19 '#arguments.taskStruct[key]#'
20 <cfset count = count + 1>
21 <cfif count LT variables.structSize>,</cfif>
22 </cfloop>)
23 </cfquery>
24
25 <cfreturn true>
26 </cffunction>

That will insert your Struct into a database, in small and tidy manner. It was somewhere around here that we started using cfproperty tags, and creating strongly typed objects for Flex.

_UNKNOWNTRANSLATION_ /