Goでwebview + spa + storeのデスクトップアプリを試す -> 失敗
GoでGUIを作るのは難しい。
まず選択肢として大きく二つあって、WebViewかそうじゃないか。
WebViewじゃない場合は独自のフォーム機能をもってるけど、基本的にIMEには対応してくれない。
英語圏が多数やからもうしょうがない。あきらめよう。
ネイティブAPIを叩けるものもあるけど、マルチプラットフォームではない。Goのいいところがつぶれる。
WebViewはJavaScript要素が多く入ってきてGoを使っていると嫌悪感があったりする。これは個人的な問題。
HTTPベースはどうしても複雑な問題を抱えるというのもある。
それでもどうしてもGoでデスクトップアプリを作りたい。
ってことでなるべくJavaScriptを排除したWebViewの可能性を模索する。
2020/09/16 追記
フロントとバックとの通信にコストがかかりすぎて開発がつらいため中断。
webview
候補としては2つ。
lorcaはインストール済みのChromeを使う。
Chromeを使うからもちろんChromeの全機能が使える。その代わりWindowの管理等はできない。リロードやバックされる可能性もある。
muonはUltralightという軽量ブラウザを使う。
軽量ブラウザのDLLなどを追加で管理する必要がある。その代わりWindowのコントロールができる。
他にもElectronベースもあったりするけど、だいたいnode.jsが登場して複雑さが増す。
spa
※ 旧gopherjs/vecty
gopherjsと別れてからは結構活発に更新されているけど、すべてをGoで実装するコストは決して小さくない。
現時点での最新版v0.5.0のタグはgopherjs組織内のリポジトリだった名残が強いのに、リポジトリだけ先に別名になってて普通にとったら動かない。
vectyと類似した機能をもったライブラリではあるけれど、
コマンドラインツールがついていて、HTMLからGoのソースが生成できるからコンポーネントの管理が楽。
wectyに関しては実績がほとんどないと思われるし、個人で開発されて4か月くらいなにもないツールなので、
安定はしていないかも。機能も少ないかも。
でもとりあえず使ってみたいからつかってみる。
2020/09/11 追記
wectyを試していたら、wectyと同じくnobonoboさんが作っているspagoをみつけた。
wectyをベースにfluxに必要なパーツが追加されてる感じ。
まだstarもwatchもないけど、いまは試験的にlorcaとの組み合わせを試してる段階やから使ってみる。
途中までwectyで進めてたけど、あるところから急にspagoに変わります
store
デスクトップアプリにする以上、ストアは埋め込みなどの選択肢になる。
埋め込み式のドキュメントストアを探していて見つかったのは2つ。
tiedotのほうがスターが多いけど、操作が map[string]interface{} で扱いづらそう。
それに対してgenjiはstructのまま扱える利点があるから、今回はgenjiを使う。
TODO
便宜上、spaをfront、webviewのサーバサイドをbackと呼ぶ。storeはstore。
wasm(front)をbackで読み込む
とりあえずwasmはHello, Worldを出すだけ、バックは読み込むだけ。
backが出した関数をfrontから叩く
backで出したjsの関数をwasmからたたく。
wasmから叩くといっても、もとはGoなので、 js.Global().Call() を使って叩かないといけない。
Call() で与えられる引数は許可された型しかだめで、構造体は渡せない。
ってことで、一回json文字列に変換してからCallに渡して、受け取る側は文字列から構造体にパースする。
めんどっちいけど、これしか方法はなさそう。
似た方法として、 map[string]interface{} にできるけど、文字列より扱いに困りそう。
frontの関数をbackから叩く
frontでjsを出して、backがlorcaの機能を使って叩く。
この流れを使えばバックがストアの変更を検知して再描画を命令したりできる。
frontからbackにデータを要求し、データの内容にそったviewを表示する
大まかな流れ
再描画を実行する(もしくは初めての描画)
frontからbackにデータ要求
backはデータ(文字列)を返す(とりあえず決め打ち
frontは返ってきたデータ(文字列)をパースしてHTMLを作る
ここで問題にぶつかった。
lorcaからjsに出せる関数はpromiseを返す。
でもGoから吐いたwasmではawait出来なくてbackのstoreからデータが取れない。
考えられる解決策は2つ
frontからデータ寄越せってバック
frontからbackにデータの追加を要求する
frontからbackにデータの削除を要求する
frontからbackにデータの更新を要求する
backからstoreをにアクセスする
backが受け取ったfrontの要求をstoreに反映する
更新履歴
2020/09/16 中断
2020/09/09 まとめはじめ