Adding Auto Generated Code Downloads to BlogCFC

I just finished my mod for BlogCFC to add auto generated code downloads to any post containing 'code' blocks. This mod simply parses the blog entry to find any and all code samples and if the entry contains code samples it creates a link for 'Download Code' below the entry. If you'd like to add this mod to your blog, follow the steps below (this was created and tested on version 5.5). If you'd like the code, download it below.

Update: I just found out there is a glitch when used with 'more' - I will check into this later today.

Step 1:

Add a simple entry to the resource bundle located at /client/includes/main_en_US.properties called downloadcode and assign it the value 'Download Code'.

Step 2:

Download the png file below and place it in /client/images.

Step 3:

Add a new page under client called downloadCode.cfm - place the following code in that page.

<cfsetting enablecfoutputonly=true>
<cfprocessingdirective pageencoding="utf-8">
<cfset theCode = application.blog.getCodeSamples(url.id, "true")>
<cfheader name="Content-Disposition" value="inline; filename=codeDownload.cfm">
<cfcontent type="application/x-cfm">
<cfoutput>
#theCode#
</cfoutput>
<cfsetting enablecfoutputonly="false">

Step 4:

Add the following function to the utils.cfc located at /client/org/camden/blog/utils.cfc. This UDF is a modified version of the getTagContent UDF from cflib.org. It has been modified to return all occurences of the specified tag.

<cfscript>
/**
* Returns the content occurences in an array.
*
* @param tag     The tag to look for. Should be passed without < or > and without attributes. (Required)
* @param string     The string to search. (Required)
* @return Returns an array
* @author Johan Steenkamp (johan@orbital.co.nz)
* @version 1, September 16, 2002
* @version 2, October 9, 2006 todd sharp (todd@cfsilence.com) modified to return all occurences of tag
*/
function getTagContentAll(tag,str) {
var matchStruct = structNew();
var matchPos = "";
var matchLen = "";
var startTag = "<#tag#[^>]*>";
var endTag = "</#tag#>";
var endTagStart = 0;
var returnArray = ArrayNew(1);


matchStruct = REFindNoCase(startTag,str,1,"true");
matchPos = matchStruct.pos[1];
matchLen = matchStruct.len[1];
if(matchLen eq 0) return returnArray;
endTagStart = REFindNoCase(endTag,str,matchPos,"false");
ArrayAppend(returnArray, Mid(str,matchPos+matchLen,endTagStart-matchPos-matchLen));

while (matchLen neq 0){
   matchStruct = REFindNoCase(startTag,str,matchPos+matchLen,"true");
   matchPos = matchStruct.pos[1];
   matchLen = matchStruct.len[1];
   if(matchLen eq 0) return returnArray;
   endTagStart = REFindNoCase(endTag,str,matchPos,"false");
   ArrayAppend(returnArray, Mid(str,matchPos+matchLen,endTagStart-matchPos-matchLen));
}
return returnArray;
}

</cfscript>

Step 5:

Modify the blog.cfc file located at /client/org/camden/blog/blog.cfc. Add the two methods below. The first method is used to check if the current blog entry contains any code blocks and the second handles the creation of the downloadable code samples. A simple header is included which will point folks back to you and your blog with questions about the code.

<cffunction name="hasCodeSamples" access="remote" returntype="boolean" hint="does the entry contain any code samples">
   <cfargument name="entryId" type="uuid" required="true">
   <cfargument name="dontlog" type="boolean" required="true" hint="we don't want to log this request as a view so pass true">
   <cfset var hasCode = false>
   <cfset var theEntry = getEntry(arguments.entryId, arguments.dontlog)>
   <cfset var theBody = theEntry.body & theEntry.morebody>
   <cfif ArrayLen(utils.getTagContentAll("code", theBody))>
      <cfset hasCode = true>
   </cfif>
   <cfreturn hasCode/>
</cffunction>

<cffunction name="getCodeSamples" access="remote" returntype="string" hint="gets the code samples for download">
   <cfargument name="entryId" type="uuid" required="true">
   <cfargument name="dontlog" type="boolean" required="true" hint="we don't want to log this request as a view so pass true">
   <cfset var renderedCode = "">
   <cfset var theHeader = "">
   <cfset var theEntry = getEntry(arguments.entryId, arguments.dontlog)>
   <cfset var theBody = theEntry.body & theEntry.morebody>
   <cfset var theCode = utils.getTagContentAll("code", theBody)>

   <cfsavecontent variable="theHeader">
   <cfoutput>
&lt;!---
** BlogCFC Auto Generated code download**
Generated from blog post: #makeLink(entryId)#
Author: #theEntry.name# (#instance.ownerEmail#)
Generated On: #dateFormat(now(), "full")# #timeFormat(now(), "hh:mm tt")#
---&gt;

   </cfoutput>
   </cfsavecontent>
   <cfsavecontent variable="theBody">
   <cfoutput>
      <cfloop from="1" to="#ArrayLen(theCode)#" index="i">
&lt;!--- Code Sample ## #i# ---&gt;
#theCode[i]#
      </cfloop>
   </cfoutput>
   </cfsavecontent>
   <cfset renderedCode = theHeader & theBody>
   <cfset renderedCode = replace(renderedCode, "&lt;", "<", "all")>
   <cfset renderedCode = replace(renderedCode, "&gt;", ">", "all")>
   <cfreturn renderedCode/>
</cffunction>

Step 6:

Modify /client/index.cfm to include the link for the downloadable code.

<!--- I put this right next to the existing link for enclosures --->

<cfif application.blog.hasCodeSamples(id, "true")><img src="#application.rooturl#/images/page_white_code_red.png" align="absmiddle" title="#rb("downloadcode")#" height="16" width="16"> <a href="#application.rooturl#/downloadCode.cfm?id=#id#">#rb("downloadcode")#</a> | </cfif>

And thats it! One thing worth mentioning - the generated file is being created as a .cfm file - this works for me, but I'm not sure it should stay that way.

Please drop a note in the comments if you decide to use this feature or if you have problems or questions.



Related Blog Entries

Calendar

Sun Mon Tue Wed Thu Fri Sat
      1
2 3 4 5 6 7 8
9 10 11 12 13 14 15
16 17 18 19 20 21 22
23 24 25 26 27 28 29
30       

Subscribe

Enter your email address to subscribe to this blog.

Tags

actionscript ajax blogging cfsnippets coldfusion flash forms flex funny stuff misc model-glue off topic personal project learn slidesix sql

Recent Comments

Editing A Query In A SQL Server DTS Package
JD said: Thanks for your post. Never unlike Microsoft to hide stuff in the hardest part time find. [More]

Mashing Spry Effects With CF8 Ajax Goodness
Mark Pitts said: I have had moderate success implementing Spry Accordian. Sadly the part that does is not working wil... [More]

Chinese Birth Calendar Accuracy Test
Toni Lehman said: This calendar was accurate for both my daughters and 4 grandchildren. I tried it for 11 of my other ... [More]

Virtual Memory - Am I The Last To Know?
Larry Miller said: The authors friend was right. Windows virtual memory system was designed by experts and they fully u... [More]

Using A PlayStation 2 HDD In Your PC
Alacres said: Thanks so much for the guide man! I did have a more specific question though, since I didn't see it ... [More]

RSS


coldfusionbloggers

FullAsAGoog MXNA

Consumed By Feed-Squirrel.com