This is a "fact finding" question to see how difficult it would be to create a ColdFusion UDF to parse markdown on the server using the showdown.js parser. There is already a java implementation that utilizes showdown.js (see code at the end of this post) and I want to see how to go about implementing it for ColdFusion. I have no experience in Java and I would not particularly call myself "a programmer," but I don't want this to stop me from trying.
Summary
I would like to run Shadown.js server-side in order to convert markdown to HTML.
Why?
Saving two versions of a user entry, one in markdown format and another in HTML, allows us to display the raw markdown version to the end user in case they wanted to edit their entry.
Why not use a server-side parser?
For two reasons:
- As of now there are no ColdFusion markdown parsers for this specific purpose
- Using Showdown.js on the client-side, and then a different parser on the server-side will result in inconsistent markup between the preview displayed to the client and the version stored in the database. Given that markdown is loosely defined, most parser implementations will have subtle differences.
There is a very good blog entry that discusses the issue.
Why not do all the parsing on the client-side and post both versions?
This does not strike me as a secure solution. I also think users would potentially be able to post markdown with HTML that does not match.
Are there any existing implementations?
There is one implementation called CFShowdown, but it's not for this specific purpose. Rather, it's for handling output on a page. The comments section of the aforementioned blog features a pure Java implementation written by a user called David:
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine jsEngine = manager.getEngineByName("js");
try
{
jsEngine.eval(new InputStreamReader(getClass().getResourceAsStream("showdown.js")));
showdownConverter = jsEngine.eval("new Showdown.converter()");
}
catch (Exception e)
{
log.error("could not create showdown converter", e);
}
try
{
return ((Invocable) jsEngine).invokeMethod(
showdownConverter,
"makeHtml",
markdownString
) + "";
}
catch (Exception e)
{
log.error("error while converting markdown to html", e);
return "[could not convert input]";
}
Objective
Create a java class that would allow us to use this implementation with a ColdFusion UDF or a custom tag inside a component, something along the lines of <cfset html = getMarkdown(string)>
Since I have no experience with Java, I want to get some advice and input from users on where and how to start going about this task. I created a
Have files showdown.js and a file markdown.txt (example below) in the same directory.
showdown.cfm
markdown.txt
Update
Here's a version that takes Adam Presley's work in Java and does it all in a CFC. Note I took that little bit of magic he added at the end of showdown.js and put it into a CFC function whose return value is appended (i.e.
showdownAdapterJS()
).CFC
Usage
You can run server-side javascript in CF by using CFGroovy - which basically allows you to run any JSR-223 scripting language inline with CFML.
Ben Nadel has an example of running server-side javascript using CFGroovy and Rhino
The example has everything you need - assuming you have the javascript code already put together.
Actually, I've already wrapped up Showdown in a Java library that can be used in ColdFusion. The example I provide, in what I admit is poor documentation, uses a custom tag, but you can use the Java component just as easily like so.
Perhaps that helps? Either way, long live Markdown! :)
Given that Markdown is not a regular language, and a majority of implementations are a series of regular expressions, there are bound to be differences between them, as you noted. There is almost no avoiding it.
If your objective is just to:
Then I see only two real options:
Personally I would go with option 2.