Custom Tags, and cfhtmlhead

I’ve been doing a fair amount of work with custom tags and JavaScript DOM manipulation. One of the things with which I’ve struggled with is organizing my code. Do I put the JavaScript in the custom tag? Do I put it in central .js files? What if the script I’ve written will only be called from one custom tag and one custom tag only?

Well I haven’t worked out all of the answers, but I do have a solution for single use scripts: Use <cfhtmhead> to inject the script into the html header from the custom tag. It keeps all of the connected code together, but still does proper, degradable, properly-separated JavaScript and HTML.

Here’s an example of this in use:

<cfsavecontent
variable=“javascriptToInject”>


type=“text/javascript”
language=“javascript”>

window.onload = focusForm;

function focusForm(){


if(document.getElementById(“username”)){

document.getElementById(“username”).focus();

}

}


</cfsavecontent>

<cfhtmlhead
text=“#javascriptToInject#”>

<cfoutput>

<form
action=https://#application.hostSecure##cgi.script_name#&#8221;
method=“post”>

<label
for=“username”>Username</label></dt>

<input
type=“text”
id=“username”
name=“username”
/>

<label
for=“password”>Password</label></dt>

<input
type=“password”
id=“password”
name=“password”
/>


<input
type=“submit”
name=“signin”
value=“Sign In”/>

</form>
</cfoutput>

On Code Reviews… again

I gave a presentation on code reviews to the Philly CFUG a few weeks back. Then my host died, and I never posted this. I’ll try and get the presentation up on the site in the next few days. But two questions arose that I figured I would discuss here:

  1. Do you check the code after the review to make sure developers have made the changes for which the team has asked?
  2. Can developers request a code review?

Both of these speak to a subtler issue. Does your team want to be adequate or excellent? What about each member, what do they want? The answer to this question will inform the answer to the previous ones.

Now this isn’t want of these things where I’m using reverse psychology to encourage what I want others to do — “Well if you want to be only adequate…” Look, not everyone can be excellent. I don’t want to get into a whole discussion on where someone brings up “Free Markets” and someone brings up Harrison Bergeron and then we all get angry at each other. My brief statement on this is that there is plenty of value contributed by people who are only adequate.

But it’s going to make a difference with a whole lot of things, including code reviews. Those that want to be excellent welcome criticism, because the idea of their product being flawed in any way is appalling to them. It’s more appalling than letting other people find those flaws. But really, they like to show off what they’ve done, and want to be acknowledged by their peers for it too.

On the other hand, those that only want to be adequate don’t care if something has flaws, as long as it works. They may try and avoid reviews, but mostly they’ll tend to be indifferent to the whole process, and will only do it if they are mandated. Unfortunately once it’s mandated it becomes a perfunctory step for them, a hoop to jump through. Some of the more militantly adequate will say things like “Don’t bother fixing it; let’s see if we can sneak it past the code review.”

So, if you have group of developers striving to be excellent, they absolutely will ask for their own reviews (but you might need to let them know they are available) and you won’t have to check them afterwards. On the other hand, if your team is on the other end of the spectrum, you might just have to mandate them. Perfunctory code reviews while painful are better than none at all.

As for double checking the code, it comes down to trust. Do you trust your teammates? I say err on the side of trust. Code reviews tend to ruffle a few emotional feathers to begin with. To big brother people afterwards would just add insult to injury. Trust people until they give a reason not to trust them. Obviously if you are doing work with sensitive data you may want to evaluate this on your terms.

But if people have violated your trust, you’re going to be glad you followed the rest of my advice on code reviews. That way you’ll have page names and line numbers by which to judge whether or not they kept up their end of the bargain.

This tension between adequate and excellent effects many other aspects of your team. I’m thinking you may want to look at this for more than just code reviews. I figured this would be a good place to sneak it in.

New Job

July 1st starts the first official day of my new job. I’ll be taking on the role of IT Director for Wharton Research Data Services. WRDS (pronounced “words”), as we call it, is a suite of research applications that provide access to financial databases used around the business and business academic world. We resell it to other educational organizations, making it a very important part of the Wharton brand. I’ll be taking over direction of the web portion of the application.

My first concern will be the giving the website a direly-needed facelift. To facilitate that we hired Happy Cog to do a kick-ass redesign, that has been sitting unused for awhile. I’m going to get that new design up on the site, by October. As part of that plan, I’m going to be taking on automation and separation of content from design. Of course, I won’t be doing this alone. I’ve got a new staff of which I’m in charge

The technology that drives the site is Perl. There are no thoughts on getting rid of all of the Perl, as it’s needed to talk to the SAS databases on the backend. I’ll be adding ColdFusion where it makes sense – mostly in a community feature that we are building. Additionally I’m working on what amounts to a domain specific language (in ColdFusion) to automate page construction. Thanks Peter Bell for turning me on to that whole stuff.

It’s sort of a bittersweet sort of thing. It’s the first move for me in awhile that involves complete change, as opposed to just increasing responsibilities. I give up all my safe ColdFusion cache.

The job of running our ColdFusion environment and providing ColdFusion leadership will be falling to Dave Konopka. I’m extremely proud of him, since I hired him, and now he’s replacing me.

While today is my official start date, I have permission to sort of coast through this week and start next Monday. I’ll be wrapping up some lose ends from my old job today and tomorrow, and taking a 5 day weekend for Fourth of July holiday.

I still intend to post on ColdFusion, and I’ll still be maintaining Squidhead. However, I’m going to generalize the topics a bit. I’m going to talk a bit about my experience as a client to Happy Cog (awesome in short.) Also I’m going to talk about some developer soft skills (like influence), and how to practice them.

Re-associate Microsoft SQL Login with a Database User

I’ve had to search for this several times in the last few weeks, (ever since Mark Drew pulled me into the dark side that is local development.) I figured if I blog it, I’ll always have the answer at hand.

If you are restoring a Microsoft SQL database from a backup onto a new server, and you need to re-associate the server login name to the database username, you need to call the “sp_change_users_login” stored procedure. That will allow you to reconnect them.

ColdFusion 8 Monitoring Heisenberg Errors

I ran into my first inexplicable crash that I eventually traced back to the ColdFusion Server Monitor. Now first off, this isn’t a problem or bug with the Server Monitor. This is to be expected. The server Monitor adds overhead to requests, and if you have an intense process, it’s going to generate a lot of monitoring data. It’s possible that you might reach its limit.

I just wanted to let people know what a crash caused by the monitoring service looks like, because it doesn’t give you a message that “You have left the monitoring service on in production!”

I had a long running complicated process crashing on my local workstation. It did work on our communal development server. So it wasn’t just the process itself. I thought maybe it was that my laptop wasn’t a server class machine. But actually, the virtual machine that we are testing on wasn’t tremendously more powerful.

The browser session would error out with a message that said:

500

Java heap space

java.lang.OutOfMemoryError: Java heap space

After digging in the JRun logs for awhile I found this:

javax.servlet.ServletException: ROOT CAUSE:

java.lang.OutOfMemoryError: Java heap space

at coldfusion.monitor.event.MonitoringServletFilter. doFilter(MonitoringServletFilter.java:70)
at coldfusion.bootstrap.BootstrapFilter.doFilter(BootstrapFilter.java:46)
at jrun.servlet.FilterChain.doFilter(FilterChain.java:94)
at jrun.servlet.FilterChain.service(FilterChain.java:101)
at jrun.servlet.ServletInvoker.invoke(ServletInvoker.java:106)
at jrun.servlet.JRunInvokerChain.invokeNext(JRunInvokerChain.java:42)
at jrun.servlet.JRunRequestDispatcher.invoke(JRunRequestDispatcher.java:284)
at jrun.servlet.ServletEngineService.dispatch(ServletEngineService.java:543)
at jrun.servlet.jrpp.JRunProxyService.invokeRunnable(JRunProxyService.java:203)
at jrunx.scheduler.ThreadPool$DownstreamMetrics.invokeRunnable(ThreadPool.java:320)
at jrunx.scheduler.ThreadPool$ThreadThrottle.invokeRunnable(ThreadPool.java:428)
at jrunx.scheduler.ThreadPool$UpstreamMetrics.invokeRunnable(ThreadPool.java:266)
at jrunx.scheduler.WorkerThread.run(WorkerThread.java:66)

java.lang.OutOfMemoryError: GC overhead limit exceeded

Of course I didn’t bother actually reading this error until just now when I copied and pasted it. It clearly indicates that the problem is in the Monitoring Servlet Filter. In any case, after much trial and error, I turned off memory tracking and then turned off profiling. Once I turned off profiling the error went away.

Using Microsoft SQL in Ant

I had to do a repetitive database task yet again the other day, and I stumbled onto the fact that Ant has full blown support for SQL. The only challenge is getting it to work with the Microsoft SQL we use here. It’s not exactly self evident, mostly because I’m not a Java programmer, so I figured I would share the information.

First download the Microsoft SQL JDBC driver from Microsoft:

Download SQL Server 2005 JDBC Driver 1.1

Once that’s done, execute it, and place the packaged contents somewhere on your computer.

Then fire up Eclipse. You’ll have to add the JDBC driver to the classpath for ANT:

  • Go to “Window”
  • Choose “Preferences”
  • Expand “Ant”
  • Choose “Runtime”
  • Select “Ant Home Entries” This will cause buttons on right to be enabled
  • Press “Add External Jar”
  • Navigate to where you put the SQL JDBC driver
  • Add sqljdbc.jar
  • Hit Apply and hit “Ok”

Now that we have a SQL Driver on our machine, all that’s left to do is to write the Ant tasks that will use it.


<sql
driver=“com.microsoft.sqlserver.jdbc.SQLServerDriver”

url=“jdbc:sqlserver://${dbserver}:1433”

userid=“${dbusername}”
password=“${dbpassword}”

print=“TRUE”>

SELECT CURRENT_TIMESTAMP

</sql>

Obviously, you’ll want to use your application’s database password to do that. Also, I included the SQL directly, but you can also call a .sql file with statements in it.

There are a few gotcha’s:

  • “Go” intermittently causes issues. Use a semicolon to separate statements
  • Use [database name] doesn’t seem to work
  • Putting Database passwords in an .xml file will expose them.
    • Rename build.xml to build.ant.
    • Make sure you don’t expose .ant files to your webserver.

What can you do with this? Well I have a couple of ideas:

  • Delete rows created by tests.
  • Run Consistency checkers
  • In conjunction with an export script, synchronize schemas and stored procedures between two databases.

You may also want to look at the documentation for the SQL Ant Task.

Unplanned Outage

You may or may not have noticed a little unplanned downtime. The webserver that Numtopia.com is on died last Thursday. My hosting provider got ColdFusion up by Saturday. But I don’t run BlogCFC like all the other cool kids, I run Movable Type which needs Perl and a special MySQL Perl driver. Getting my hosting provider to re-install it (it was there pre-crash) was an exercise in patience. It took almost a full week for them to do so.

Now I’ve been oscillating between impatience (I want this up) and understanding (this isn’t a business, and I’ve had to deal with people with custom configs post crash.) I’ve decided that for ColdFusion hosting, for $12 a month; 1 week of downtime for my ability to post to my blog over the course of 2 years, is probably acceptable.

ColdFusion 8 Makes It Easier

ColdFusion 8 is now out as a public release candidate, and do I have a lot to say.

First off, I think the ColdFusion team did a great job at adding features across the board that would make ColdFusion a much more competitive product. But I think more interesting is looking at what the ColdFusion team is making easier for you in this release.

ColdFusion has, in my opinion, always been about taking the operations that everyone has to do to build web applications and make them easier. Early versions were focused on making talking to databases easier. ColdFusion MX 6 was about porting the codebase over to Java. You could argue that it was about making ColdFusion easier to work cross platform. That’s a stretch, so if you prefer we can say it was a rebuilding release. ColdFusion MX 7 was about making interfacing easier. Between <cfreport> and <cfdocument> ColdFusion gained new ways of output data. Flash Forms was intended to make writing form based interfaces easier. Gateways make ColdFusion easier to interact with in non-traditional, non-browser based ways.

So what does this version of ColdFusion make easier? I’ve been searching for an answer to that for a few hours now and I think I have a few answers.

First, from the original Scorpio Labs Page:

  1. ColdFusion 8 will allow ColdFusion developers to create richer, more engaging web applications
  2. ColdFusion 8 will provide powerful new insight into server performance and simplify application troubleshooting
  3. ColdFusion 8 will give developers broader platform support and enterprise integration

Here’s my translation:

  1. ColdFusion 8 makes Web 2.0 Easier
  2. ColdFusion 8 makes Administration Easier
  3. ColdFusion 8 makes selling ColdFusion to the Enterprise easier

ColdFusion 8 makes Web 2.0 easier

Cheesy, unliked, overused and unfortunately for me, necessary, the Web 2.0 moniker is unfortunately here to stay. It’s about many things. But I’ve always liked it, because I’ve always looked at it not from a technology perspective, (It’s Ajax, or Flex) but from an authority focus. Web 2.0 is about user content, not “authority” based content. It’s about users choosing how to consume their applications, not site owners dictating how to consume it.

One could make the argument, that there are only two types of typical, Web 2.0 user data that ColdFusion has to date, not dealt well with. They are Video and Images. Video is still shaking out, and still isn’t addressed by ColdFusion. (Adobe as a whole has direction on this.) But at least on the image side of things, ColdFusion 8 makes it easier to handle with <cfimage> and the suite of image functions.

It has always been easy to do Flex development against ColdFusion, but now <cfajaxproxy> and the JSON functions are making it easier to do Ajax development against ColdFusion. This further separates the choice of ColdFusion from the front end used to access it. This is a good thing, it expands a bit on what they did with 7, but also allows “ColdFusion and Ajax” to be said a lot together in press releases and technical news articles. This is good for us as a community.

ColdFusion 8 does not abandon the interface side of things though. There are a bunch of new display management tags including <cflayoutarea>, <cfpod>, <cfmenu>, <cftooltip>, <cflayout>, <cfmenuitem>, <cfwindow>. This shows that ColdFusion is still trying to make it easier to do things that everyone has to do. This time, they are clearly going after the interactivity of “Ajaxy” sites. Now, in the past, in ColdFusion, these types of interfaces have not always been usable on a forward facing application. This is no longer the case. Not only do they look completely modern and professional by themselves. But if you don’t like them, they can be styled by CSS.

Lastly on the Web 2.0 side of things, there is a <cffeed> tag. This makes both creating and consuming RSS or Atom XML feeds much, much easier. Not much to say about it, this is something that all of us have to do now, ColdFusion makes it easier.

ColdFusion 8 makes Administration Easier

The new ColdFusion Monitor tool is perhaps the best improvement to my job ColdFusion has ever made. The ability to track down an errant template is simply stunning. The ability to kill a running template is beyond stunning, it’s ginormous. You can actually see the stack trace of a running template if it’s causing a problem. You can even see every variable in every conceivable scope in a request. This is truly stunning.

Even though we central administrators love exercising iron-fisted control over our shared servers, it’s really nice for Adobe to open up limited capabilities of the administrator to distributed users. I do wish they had made it easier to tie it into a third party directory tool like Active Directory, but I’ll take what I can get.

Finally the administrator now has more options for tweaking performance. You can set limits on number of simultaneous page requests, CFC calls, Flash Remoting calls, and web service requests. All of these tweaks do make it easier for administrators to control their environments.

ColdFusion 8 makes Selling as an Enterprise Solution easier.

I’ve never been one to demand Java like features in ColdFusion. However there are a few areas, where it would be nice if more Java like behaviors were exposed. One case I’m talking about is file processing. ColdFusion 8 now lets you parse files line by line, instead of forcing you to load an entire file into memory at once. But that doesn’t even mention the addition of native Zip tools, which now exist. Granted you could have always dropped down into Java to handle this stuff, but the more you force that to be a solution for people, the more entry-level programmers that run into walls.

But, ColdFusion 8 doesn’t just play with Java better. Adobe’s been hanging out in Redmond. First ColdFusion 8 can call .Net objects like it can Java classes or CFC’s. I think a little cooler, is the fact that ColdFusion 8 can talk with Exchange. Granted, I’m a little sad to be out of an expertise, but happy that everyone can now play with Microsoft’s groupware offering. I’ll probably be saying even more on this feature in the upcoming weeks. But make no mistake about it, this is hands down the easiest way interact with Exchange other than Outlook. It’s really, seriously, that good.

There’s a lot of touting of the performance enhancements to ColdFusion 8. But in addition to just running faster, ColdFusion 8 allows developers to have more control over the performance of their applications through the addition of <cfthread>. This technology will allow developers optimize sequential behaviors like emailing, or rebuilding static files by running them asynchronously. Up until now, the only clean option for asynchronous operations was the Asynchronous CFML Gateway. It does the job, but is a little unwieldy to use if you aren’t an administrator on the machine. <Cfthread> doesn’t replace the Asynchronous CFML Gateway, it just allows another option in the continuum of asynchronous operations.

All in all, developers can now make faster performing applications, on a faster platform, which can talk to many more systems now.

Conclusion

This is just the tip of the iceberg. Every one of these one sentence blurbs represents a feature that deserves its own blog post. (They also probably represent years of developer’s time.) Additionally there are a ton of features, functions and tags I didn’t mention. This is by far the best release of ColdFusion yet.

Squidhead and CFUnit

I published a change to Squidhead earlier today that included an option for Squidhead to write its own unit tests today. These unit tests are compatible with and require CFUnit. Here’s a little bit about the reasons behind this.

I originally started fooling around with unit testing because after drinking Pragmatic Programmer Kool-Aid, and attending cf.Objective, it was the next thing on my list. I figured I would be pulling them into Squidhead, as it’s pretty easy to tell if Squidhead worked (the application is either written or not,) but it’s hard to tell if the created application is working. So I started to write unit tests for my DAO Objects figuring it would be an easy place to start. Once I got one working, I realized it was relatively rule based and could stand to be generated itself.

What it does is:

  • Create a mock struct of the record.
  • Create a mock struct of the record slightly different from the first.
  • Create a record from the mock record.
  • Read it back and compares it to the source.
  • Update it according to the different mock record.
  • Read it back and compares it to the source.
  • Delete the record
  • Read again to make sure the item is gone.

All that is wrapped in a <cftransaction> making sure the thing never happened. Additionally it reads in and honors foreign key constraints. It’s got some weaknesses: it doesn’t like binaries or images; its smalldatetime check is only accurate to the hour; and there are probably more bugs lurking.

Now once I got them working, they were in, but what’s the point for users of the application? One should expect that the parts work.

So to make this worthwhile I added some logic that will run any test that is in the test directory structure. So if you’re using Squidhead and looking to dip your feet in the waters of CFunit or unit testing in general here’s your chance.

If you’re wondering why CFUnit, and not CFCUnit, it’s because as far as I can tell CFCUnit requires Mach II, and I figured one requirement was better than two.

So if anyone has any suggestion on how to test gateways or dao’s I’d be curious. Otherwise check it out.