Docurain Labo

Docurainサービス開発日記

【エンジニア向け】これできっと分かる。Docurainのつまづきポイント解説します

Docurainは帳票エンジンと銘打っていますが、使いこなすともっともっとたくさんのことが実現できます。この記事でははじめてDocurainに触れる方が感じるであろう疑問点や、つまづきポイントを解説します。スムーズな帳票作成を実現させるためにも、ぜひご覧ください。

Docurainとは何なのか?

Docurainとはいわばテンプレートエンジンです。Excelファイルがテンプレートファイルで、データファイルがJSONやCSVファイル、そして出力結果がPDFやExcel、画像であったりします。

f:id:moongift:20210813114118p:plain

プログラマの方であれば、MVCモデルを用いた開発はよく知っているかと思います。例えばPHPであればLarabel、RubyであればRuby on Rails、JavaであればPlayなどのフレームワークがMVCフレームワークを採用しています。この時、Vにあたるビューはコントローラ(C)によって、モデル(M)のデータをビューの中に適合させて、HTMLなどを生成します。

その際、ビューは単純にモデルの値を表示する他、簡単なロジックを記述することもできます。繰り返し処理を行って一覧を作成したり、値の種類によって出し分けを行うといった具合です。そういった表示に関わるロジックをビューに実装することで、システムの責任分担が可能になります。

Docurainで利用するExcelファイルは、このビューのテンプレートファイルに当たると考えてください。テンプレートファイルの中には描画する際のロジックが記述できます。そして、モデルに当たるのが帳票作成時に送信するJSONデータになります。テンプレートファイルとJSONデータを結合させて、PDFやExcel、画像に変換するのがDocurainになります。

f:id:moongift:20210813114130p:plain

帳票を作成するクラウドサービスというと仰々しく聞こえてしまいますが、クラウドのテンプレートエンジンであると考えると合点がいくのではないでしょうか。

Docurainがサポートするロジックについて

Docurainでは帳票を作成する際のロジックとして、2種類サポートしています。

  • A列に記述するロジック
  • 帳票テンプレートへの出力

この2つを知ることで、実現できることが分かるはずです。

A列に記述するロジック

A列に記述するロジックは主に4種類あります。

  • データを変数にセットする
  • 分岐処理
  • 繰り返し処理(ループ)
  • その他

データを変数にセットする

送信したJSONデータは $ROOT で参照できます。例えば次のようなデータを送ったとします。

{
  "foo": "bar"
}

この時 ${ROOT.foo} と書くと bar という値が表示されます。1階層であれば良いですが、これがもっと深い場合にはどうなるでしょうか。

{
  "foo": {
    "bar": {
      "hoge": {
        "fuga": {
          "key1": "val1",
          "key2": "val2",
          "key3": "val3",
          "key4": "val4"
        }
      }
    }
  }
}

val1 を出す際には ${ROOT.foo.bar.hoge.fuga.key1} を書かないといけません。これはとても長いですし、JSONデータを読み間違えれば不具合の元になります。そこで #set を使います。

#set($fuga = $ROOT.foo.bar.hoge.fuga)

このように書くと ${fuga.key1}${fuga.key2} でそれぞれの値を参照できるようになります。これでメンテナンス性が大幅に向上するはずです。

分岐処理

分岐処理はいわゆる if〜else〜end の構文になります(elseは省略可能)。条件にマッチした場合のみ、実行するものです。Docurainでは次のように記述します。

#if ($fuga.key1 == "val1")
  条件にマッチした場合の出力内容
#else
  条件にマッチしなかった場合の出力内容
#end

繰り返し処理(ループ)

明細行などで繰り返し出力を行う場合には #foreach を使います。例えば次のような明細行用のJSONデータがあったとします。

{
  "lines": [{
      "name": "項目1-1",
      "quantity": 6,
      "unit": "ヶ月",
      "unitPrice": 100,
      "amount": 600
  }, {
      "name": "項目1-2",
      "quantity": 1,
      "unit": "",
      "unitPrice": 200,
      "amount": 200
  }]
}

この場合は次のようにして繰り返し処理を記述できます。

#foreach ($line in $ROOT.lines)
  この中で各行の出力内容
#end

この場合も #foreach ($line in $ROOT.lines)#end が書かれた行は帳票として出力されません。

その他

この他、よく使われるものとしては #with があります。この #with は、withを宣言した後の出力時において、オブジェクトの明記を省略(省略記法)できます。たとえば次のようなJSONがあったとします。

{
  "備考": [
    { "内容": "項目1" },
    { "内容": "項目2" },
  ]
}

ここでループしながら #with を使います。

# A B
1 内容
2 #foreach ($e in $ROOT['備考'])
3 #with($e)
4 %{内容}
5 #end

このようにExcelファイルに記述をすると、出力結果は次のようになります(Excelで出力した場合です)。 ${e['内容']} と書かずに省略できます。

# A B
1 内容
2 項目1
3 項目2

帳票テンプレートへの出力

帳票テンプレート内に出力する場合、いくつかの書き方があります。 fieldName JSONのキーになります。

書き方 注意点
${ROOT.fieldName} JSONのキーが英数字の場合のみ
${ROOT['fieldName']} JSONのキーが英数字、またはマルチバイト
${ROOT.get('fieldName')} JSONのキーが英数字、またはマルチバイト
%{fieldName} 【省略記法】JSONのキーが英数字、またはマルチバイト

上記の4つはいずれも同じ結果になります。通常は省略記法を使うことをお勧めします。 書き方によって、マルチバイト(日本語など)をサポートしていない場合があるので注意してください。

マクロ

Docurainでは文字列をそのまま出力する以外にも、便利な関数(マクロ)が用意されています。ここでは一部を紹介します。

  • #QRCODE([任意の文字列])
    QRコードを出力します。
  • #FORMAT_DATE([日付], [書式])
    日付をフォーマット指定して出力します。
  • #IMAGE([画像データ(DATA URI表現)], [オプション]) 画像を表示します。なおシェイプ内のテキストとして記述する必要があります。
  • #CODE39([CODE39準拠の文字列])
    CODE39バーコードを出力します。

マクロについてはドキュメントの定義済みマクロ一覧(要ログイン)にて詳細を確認してください。

Tips

ここからはDocurainを使っていく上での、ちょっとした便利な機能を紹介します。

ネストしたJSONキーにアクセスする

たとえば次のようなJSONがあったとします。

{
  "company": {
    "name": "ルート42株式会社",
    "message": "クラウド帳票開発のドキュレイン"
  },
}

この時 ルート42株式会社 という文字を出力したい場合には、次のように記述します。

${ROOT.company.name}

さらに、ROOTが長い場合には #set を使って、次のように書くこともできます。

# A B
1 #set($e=$ROOT)
2 ${e.company.name}

companyの情報が多いなど、何度も書くのが面倒な場合には #with を使った省略記法も可能です。

# A B
1 #set($e=$ROOT)
2 #with($e.company)
3 %{name}
4 %{message}

メンテナンスのしやすさ、分かりやすさによって、最適な記述を選んでください。

#set や #if などを使った行は出力に関する記述はできません

帳票の途中で #set を使った場合、その行には表示に関する記述はできません。そのため、ロジックは装飾などのない、独立した行に書いてください。もしロジックと出力があると、次のようなエラーが発生します。

Sheet1!C2: there should be no other cells in the instruction row

値が存在しない場合がある

帳票で指定したキーが存在しないと、出力結果に問題が出ます(nullと出てしまうことも)。そこで $!{...} という記述方式(サイレント記法)を使って、存在しない場合には出力しない指定ができます。

$!{ROOT.key}

尚、省略記法の場合は最初からサイレント記法相当の動作になります。

計算式を埋め込みたい

たとえば消費税や小計など、明細ごとに計算式を使いたい場合は、次のように記述します。 %= という記述がポイントです。

# A B C D E
1 数量 単価 割引 小計
2 #foreach($o in $e.orders)
3 ${o.num} ${o.unit} ${o.discount} %= $o.unit * $o.num - $o.discount
4 #end

%= と書くと、まずそのセルがテンプレート文字列として解釈されます。たとえば $e.orders が次のようなJSONデータだったとします。

{
  "orders": [
    {
      num: 3,
      unit: 100,
      discount: 50
    },
    {
      num: 10,
      unit: 200,
      discount: 100
    },
  ]
}

そうすると、1行目は次のように展開されます。

%= $o.unit * $o.num - $o.discount
  ↓
%= 100 * 3 - 50
  ↓
250

そして2行目は次のように展開されます。

%= $o.unit * $o.num - $o.discount
  ↓
%= 200 * 10 - 100
  ↓
1900

なお、Docurainでは数式自動シフトという機能でセル指定を自動的に調整してくれる機能もあります。使いやすい方を利用してください。

明細行(行数可変)の合計を出したい

帳票のヘッダーやフッターに、合計金額を出す場合がありますが、そこで必要になるのが明細行の合計計算です。やり方は以下の2つがあるかと思います。

  • JSONデータにあらかじめ計算結果を持たせる
  • Excel上で計算する

JSONデータにあらかじめ合計金額を持たせるのであれば、ただその数字を出力するだけなのでシステム上は簡単になりそうです。ただ、そうした計算ロジックをシステム上に持たせたくない、というケースもあるでしょう。そこでExcel上で計算して載せる方法を紹介します。

明細行で範囲に名前を付ける

たとえば明細行ごとに設定した値引き金額を集計する場合です。例として、このような設定になっていることとします。

# A B C D E
1 数量 単価 割引 小計
2 #foreach($o in $e.orders)
3 ${o.num} ${o.unit} ${o.discount} %= $o.unit * $o.num - $o.discount
4 #end

ここで D2D4 をマウスで選択します。そして左上にあるセルの名前ボックスに 値引き という名前を付けます。

f:id:moongift:20210813114951p:plain

後は任意のセルに =SUM(値引き) と記述すれば、明細行の値引き合計数が入ります。明細行が増減しても、範囲は自動的に拡張されます。

画像を表示する場合のDATA URI形式とは?

画像を帳票に埋め込む場合、画像データをDATA URI形式で送信します。このDATA URIというのは、次のようなフォーマットになります。

data:MIME_TYPE;base64,BASE64_ENCODE

MIME_TYPEimage/pngimage/jpeg といったデータフォーマットを表すMimeタイプになります。 BASE64_ENCODE は画像データをBase46エンコードした文字列になります。なお、Docurainで対応しているのはGIF/JPEG/PNG/TIFF/SVG/PDFになります。PDFはPDF出力時のみ対応しています。

印刷範囲の設定

DocurainではA列やロジックを記述した行が出力されないので、想定と最終結果が合わないかも知れません。特に横幅が広くて、別ページになる可能性があります。そこであらかじめ印刷範囲を設定しておきます。

Excelのページレイアウトメニューで、印刷範囲の設定をします。A列を除いて(場合によっては1行目も除いて)帳票として作成したい部分を選択して、印刷範囲の設定を選択します。

f:id:moongift:20210813115122p:plain

次に表示メニューで、改ページプレビューにしておくと、実際に帳票が作成される範囲が分かりやすくなります。

f:id:moongift:20210813115140p:plain

明細行を追加してみて、幾つまでであれば1ページ内に収まるか確認するのも良いでしょう。

まとめ

Docurainには他にも機能やロジックが多数ありますが、まず知って欲しいのはDocurainはExcelファイルをテンプレートファイルとした、テンプレートエンジンであるということです。そして、A列にロジックを書いて、セル内に出力内容やマクロを記述する点だけ押さえれば、これまで利用してきたシステム開発と同じように扱えるでしょう。

帳票だけでなく、簡易的なDTP(チラシ作成など)も行えるDocurainをぜひ活用してください。