Publish to WordPress with Emacs 24 and org2blog

I’ve recently discovered the absolute joy that is writing and publishing wordpress blog posts using Emacs 24 and org2blog. Because it took me a while to get everything (including source code syntax highlighting by the WordPress SyntaxHighlighter plugin) going, I wanted to document the whole procedure step-by-step, using org2blog of course!

I’m using Emacs 24.3 (from the PPA) with Prelude on Ubuntu 12.04.4.

Installing required packages

org-mode is already installed in Emacs 24 with Prelude. However, we need to install org2blog and some extra dependencies.

M-x package-install RET xml-rpc
M-x package-install RET metaweblog
M-x package-install RET org2blog
M-x package-install RET htmlize

metaweblog and xml-rpc are two direct dependencies of org2blog. htmlize is to support the syntax highlighting of source code by SyntaxHighlighter on WordPress.

Configuring Emacs

I added the following to my ~/.emacs.d/init.el. Read the comments, copy and modify!

Note the org2blog/wp-use-sourcecode-shortcode variable: If you set this to nil, Emacs and org2blog will pre-colour your source code blocks in HTML and upload that. If you set it to 't, org2blog will make use of the SyntaxHighlighter Evolved shortcodes, meaning that the WordPress plugin, if installed and configured correctly as shown in the next section, will be used to syntax highlight.

Option 1 is the easiest and the most robust, and hence my preference, but you might prefer option 2. If you’re taking option 2, make sure that your org2blog is newer than 2014-05-26, as there was a bug in the HTML encoding of certain characters.

;; default is ~/org/ -- I'm putting orgmode's default dir with my other notes
(setq org-directory "~/sync/notes/org/")
;; and you need this, else you'll get symbol void errors when doing
;; fill paragraph
(setq org-list-allow-alphabetical t)

(require 'org2blog-autoloads)
(require 'netrc)

;; in my ~/.netrc/ I have:
;; machine wp-cpbotha login my_username password my_password
;; machine wp-vxlabs login my_username password my_password
;; so let's parse out each of the lines into a separate variable
(setq wp-cpbotha (netrc-machine (netrc-parse "~/.netrc") "wp-cpbotha" t))
(setq wp-vxlabs (netrc-machine (netrc-parse "~/.netrc") "wp-vxlabs" t))

;; I want to publish to both cpbotha.net and vxlabs.com
(setq org2blog/wp-blog-alist
      '(("cpbotha"
         :url "http://cpbotha.net/xmlrpc.php"
         :username (netrc-get wp-cpbotha "login")
         :password (netrc-get wp-cpbotha "password")
         :default-title "Hello World"
         :default-categories ("org2blog" "emacs")
         :tags-as-categories nil)
        ("vxlabs"
         :url "http://vxlabs.com/xmlrpc.php"
         :username (netrc-get wp-vxlabs "login")
         :password (netrc-get wp-vxlabs "password")
         :default-title "Hello World"
         :default-categories ("org2blog" "emacs"))))

;; http://blog.binchen.org/posts/how-to-use-org2blog-effectively-as-a-programmer.html
;; has half the instructions, but was missing
;; `wp-use-sourcecode-shortcode` at the time of this writing, without
;; which this does not work at all.

;; * `M-x package-install RET htmlize` is required, else you get empty
;;   code blocks https://github.com/punchagan/org2blog/blob/master/org2blog.el
;; * with wp-use-sourcecode-shortcode set to 't, org2blog will use 
;;   shortcodes, and hence the SyntaxHighlighter Evolved plugin on your blog.
;;   however, if you set this to nil, native Emacs highlighting will be used,
;;   implemented as HTML styling. Your pick!
(setq org2blog/wp-use-sourcecode-shortcode nil)
;; removed light="true"
(setq org2blog/wp-sourcecode-default-params nil)
;; target language needs to be in here
(setq org2blog/wp-sourcecode-langs
      '("actionscript3" "bash" "coldfusion" "cpp" "csharp" "css" "delphi"
        "erlang" "fsharp" "diff" "groovy" "javascript" "java" "javafx" "matlab"
        "objc" "perl" "php" "text" "powershell" "python" "ruby" "scala" "sql"
        "vb" "xml"
        "sh" "emacs-lisp" "lisp" "lua"))

;; this will use emacs syntax higlighting in your #+BEGIN_SRC
;; <language> <your-code> #+END_SRC code blocks.
(setq org-src-fontify-natively t)

Optional: Configuring your WordPress to highlight lisp code

This is only necessary if you have (setq org2blog/wp-use-sourcecode-shortcode 't), i.e. you want your Syntaxhighlighter Evolved to do the highlighting.

(Personally, I prefer to let Emacs do the highlighting, and then upload the htmlized version, i.e. my org2blog/wp-use-sourcecode-shortcode is set to nil. This configuration does not require any special wordpress syntax highlighting plugins.)

There’s a lazy hack floating around that simply uses SyntaxHighlighter Evolved’s clojure support, but this yields less pretty results.

Instead of that, we copy shBrushLisp.js (github) into your WP installation’s wp-content/plugins/syntaxhighlighter/ directory. Then edit syntaxhighlighter.php in that same directory, adding the following line with all the other third-party brush we_register_script lines:

wp_register_script('syntaxhighlighter-brush-lisp', plugins_url('shBrushLisp.js',__FILE__),array('syntaxhighlighter-core'),'1.0.0');

Finally, modify the brush aliases as follows:

$this->brushes = (array) apply_filters( 'syntaxhighlighter_brushes', array(
   'as3' => 'as3',
   <bunch of other aliases>,
   'lisp' => 'lisp',
   'emacs-lisp' => 'lisp',

Let’s publish!

Create a .org file. A minimal publishable file would look like this:

#+TITLE: Emacs 24, Prelude and org2blog and WordPress

Here is some text!

* Heading

Some more text!

Let's include an image:

[[./img/screenie-org2blog.png]]

Login to your wordpress installation with M-x org2blog/wp-login.

Before posting this to your blog, you can get a quick preview by doing C-c C-e h o or more verbosely M-x org-html-export-as-html. (On my setup, I hit the invalid function: org-with-silent-modifications bug at this point. To fix this, temporarily remove ANY org-mode config settings from your init.el, restart Emacs, then do a package-install package org to get the latest greatest, and then put back your temporarily removed configuration. See this post for ever so slightly more detail.)

You can now publish your post with M-x org2blog/wp-post-buffer, which will upload the post as a draft to your weblog. You’ll have the option of previewing the post via your WordPress site, and then using the usual WordPress mechanism for publishing that post. You can also post and publish directly from org2blog using M-x org2blog/wp-post-buffer-and-publish (or C-c p).

When you link to an image, that image will be uploaded to the WordPress media library and inserted into the post. BONUS! Here’s a screenshot of my Emacs editing this post:

screenie-org2blog.png

Syntax-highlighting markdown fenced code blocks in Emacs

The syntax-highlighted fenced code blocks in GitHub flavored markdown, or GFM, are a beautiful and useful invention. One starts a code block with three or more backticks or tildes, followed by the name of the language, and then proceeds to show one’s code, which, at least on GitHub, is then syntax highlighted.

In other words, something like this in your markdown:

```python
def computer_says(no):
    print("computer says %s" % (no,))
```

Would become this in the preview:

def computer_says(no):
    print("computer says %s" % (no,))

When I’m editing my markdown, I’d obviously like to see this language-specific highlighting interspersed with my normal markdown highlighting. SublimeText’s MarkdownEditing package does a superb job of this, but of course we’re currently rediscovering the universe that is Emacs.

DuckDuckGoing around, we run into at least two Emacs packages that do this: mmm-mode and polymode. We decided to try out both of them, finally ending up (quite happy) with the result shown in this screenshot:

Editing this post with emacs, markdown-mode and mmm-mode
Editing this post with emacs, markdown-mode and mmm-mode

polymode

After git cloning polymode into my ~/.emacs.d, I installed it according to the instructions, by adding the following to my ~/.emacs.d/init.el:

(setq load-path
      (append '("~/.emacs.d/polymode/" "~/.emacs.d/polymode/modes")
              load-path))

(require 'poly-R)
(require 'poly-markdown)

Initially I had just the poly-markdown require, but that yielded an empty variable error. With this configuration, opening any .md file should activate the poly-markdown mode.

poly-markdown creates an indirect buffer for every code block that you create. This means if you switch buffers using for example C-x C-b, you’ll see for each file you’re editing with poly-markdown as many extra buffers as there are fenced code blocks in your file.

When you start a new fenced code block, polymode picks this up automatically. When you load a new colour theme, the code blocks don’t always pick it up immediately, but this can be lived with.

mmm-mode

This all worked in my case, but I wanted to try out mmm-mode as well. While not as hip and generic as polymode, this has been around for quite a while longer, and has seen much testing.

I installed mmm-mode from ELPA with M-x package-install RET mmm-mode (yes, it’s that easy) and then changed my .emacs.d/init.el as follows:

(require 'mmm-mode)

(mmm-add-classes
'((markdown-python
:submode python-mode
:face mmm-declaration-submode-face
:front "^```python[\n\r]+"
:back "^```$")))

(setq mmm-global-mode 't)
(mmm-add-mode-ext-class 'markdown-mode nil 'markdown-python)

I’m only showing Python here, but I’ve defined classes and added them to markdown-mode for JavaScript and emacs-lisp as well. There’s probably a better way to define the extra classes for a whole list of languages, but my (lack of) elisp skills doesn’t know about it yet.

conclusion

I definitely liked mmm-mode better. It doesn’t create all of those indirect buffers (which do affect my workflow). When you create a new fenced code block, it doesn’t highlight this until you do e.g. M-x mmm-parse-buffer. However, I like this sort of determinism. Other than that, mmm-mode felt generally more stable and responsive than polymode. This no surprise; although polymode shows great potential, it’s still in alpha. Because I need something that works now, I’ll hold onto my mmm-mode for a while longer.