Emacsでブログの原稿を書く(org2blog以外)後編

今回もSoqAlbumは関係ありません。前回に引き続き、emacsでブログの原稿を書く話を続けます。Emacs(エディタ)とwordpress(ブログツール)に興味をお持ちの人を対象にした、趣味のポストです。

前回のポスト

SoqAlbumでいらっしゃた方は、以下のポストからご一読ください。

前回はなぜorg2blogを諦めたのかという話をしました。今回はemacsで原稿を作るのに利用するorgファイルの説明から始めます。

Emacs orgとは何か?

Emacsでorgと言えば、filename.orgという拡張子orgのファイルを編集するためのモード(org-mode)のことです。orgファイルが何かと言えば、どうやら発祥はtodoやら日々のノートキーピングのためのモードであったようです。

あったようだと言ったのは、org-mode(というかoutline-mode?)でテキストの折りたたみ(必要な部分だけ表示して、邪魔な部分は隠す)ができたりしたのがユーザーの心に刺さったらしく、org-modeは超進化をとげてしまい、もはやもともとの目的がなんであったか分からない使われ方をしているからです。例えばスプレッドシート的な表計算が、テキストファイル上でできたりします。ターミナルのテキスト上でいろんなツールがピコピコ動くのが見ていて楽しいので癖になるのですねw ちなみにorg-modeをマスターするための唯一にして最大のコツは、自分が使うと決めた機能以外は勉強しないことです。全部理解しようとすると機能が果てしなさすぎて挫折します。

org => markdown でWPにペーストする

そういうわけで、emacsで原稿を書くならorg-modeが使いたいわけです。org-modeを使えば、見出しや箇条書きをテキストファイル上で簡単にマークできます。

これをそのままWPにペーストしても意味をなしませんので、orgファイルをemacs上でmarkdown形式に変換します。 WPのgutenbergはキー入力としてmarkdownを受け付ける ので、試しにmarkdownをまとめてgutenbergにペーストしてみたら、見出しや箇条書きがgutenbergにちゃんと反映されました。これで原稿の骨組みの入力は確保できそうです。

Elisp(org2wpmd)でorgファイルをmarkdownへ一発変換

Emacsから吐き出されるmarkdown形式は少々調整が必要でしたので、調整を自動化するelispをクイックハックしました。

(defun org2wpmd ()
  (interactive)

  (require 'ox-md nil t)

  (let ((org-export-with-toc nil) 
    (delete-active-region nil) ; for backward-delete-char
    orgstr mdstr p1 p2 es)
    (setq orgstr
      (if (use-region-p)
          (buffer-substring (region-beginning) (region-end))
        ;; no region
        (buffer-string)
        ))

    (with-current-buffer (get-buffer-create "*org2wpmd*")
      (erase-buffer)
      (insert "* TOP-LEVEL-HEADING\n") ; Dirty workaround to make '* ...' the top-level heading. 
      (insert orgstr)

      ;; BEGIN_SRC ... END_SRC
      (goto-char (point-min))
      (while (re-search-forward "^#\\+BEGIN_SRC\\( .*\\|\\)\n" nil t)
    ;; BEGIN_EXPORT html, for escape from (org-md-convert-region-to-md)  
    (replace-match "#+BEGIN_EXPORT html
<pre class=\"wp-block-code\"><code>" t)
    (setq p1 (point))
    (when (re-search-forward "\n#\\+END_SRC *" nil t)
      (replace-match "")
      (setq p2 (point))
      (insert "<\/code><\/pre>
#+END_EXPORT")
      (setq es (org-html-do-format-code (buffer-substring p1 p2)))
      (delete-region p1 p2)
      (goto-char p1)(insert es)(backward-delete-char 1)
      )
    )

      ;; convert to md
      (set-mark (point-min))
      (goto-char (point-max))
      (org-md-convert-region-to-md)

      ;; ](file:/// ... => ](/ ...
      (goto-char (point-min))
      (while (re-search-forward "\\](file:\/\/\/" nil t)
    (replace-match "](/")
    )

      ;; delete '# TOP-LEVEL-HEADING'
      (goto-char (point-min))
      (next-line 3)
      (delete-region (point-min) (point))

      ;; set kill
      (kill-new (buffer-string))
      )
    ))

org2wpmdの使い方

~/.emacs.d/init.elかどこかに上のelispを挿入して、emacsを再起動させるなどして反映させてください。変換したいorgファイルを表示してM-x org2wpmdとすれば*org2wpmd*というバッファにmarkdownが書き込まれる他、kill-ring(クリップボードみたいなもの)にもmarkdownが入ります。バッファの一部だけを変換したい場合は、リージョンで囲んでM-x org2wpmdしてください。

普通にemacsをディスプレイ環境で使っている場合は、org2wpmd後にそのままWPにペーストできると思います。ターミナル環境の場合は、*org2wpmd*の内容を手動でクリップボードに移して、WPにペーストしてください。

Orgファイルのすべての機能をサポートするのは不可能ですが、次の機能はだいたい動きます。

  • 見出し
  • 箇条書き
  • テキスト内のリンク、強調表示
  • BEGIN_SRC … END_SRC でソースコードをWPでcode block表示

例えば、こんなorg文章を変換してWPにペーストできます。

** 見出し、WPのデフォルトの見出し(H2)を作るにはアスタリスクが2つ必要です

*** 見出し H3

本文。改行はそのまま反映されます。LaTeXのように段落をひとまとめにしてくれたりはしません。 *強調表示。* [[https://www.google.com][Googleへのリンク]]も簡単に作れます。

- 箇条書きも、
- 書けます。
- org-modeはこういうテキストを書く時便利。

Code blockでプログラムのソースなどを表現できます。

#+BEGIN_SRC emacs-lisp
(defun my-complaint ()
  (interactive)
  (message "Emacsのhelpに出てくるnon-nilは、ちょっと頭がこんがらがる。")
  )
#+END_SRC

上の原稿をemacsでorg2wpmdして作ったmarkdownをWPにペーストした結果がこちらです。 「ライトなワークフロー(笑)」にはこれくらい書ければおおむね十分ではないでしょうか。

画像についてはgutenberg上で処理するつもりなので何もサポートしません。BEGIN_SRCについては今回のポストにelispを貼り付けたくて、今回新しくサポートしましたw 自分で使う機能しかテストしてないので、何が使えて何が使えないかは自己責任でいろいろ調べてみてください。

ちなみにどういう理屈か、orgで作った表はWPにうまく反映されるようですw

まとめ

Org文章をmarkdownに変換してWPにペーストしてブログを作る「ライトなワークフロー」を実現するemacs lispを紹介しました。とりあえずのクイックハックです。誰かWPをよく分かってる人がREST API使ってかっこいいのを作ってくれるとありがたいのですが、それまではこのelispでしのいでいこうかと思っております。

追記

当初はコマンド名をorg2wpとしていましたが、org2wpという別のperl製のツールを見つけたので、こちらのコマンド名をorg2wpmdに変更しました。

コメント

タイトルとURLをコピーしました