Play frameworkを使ってscala.jsを試してみる
Scala.jsとは
ScalaをJavaScriptに変換して実行してくれるものです。なんとScala本体のコードを丸々JavaScriptにコンバートして実行しているようです。圧縮前は22MBのコード。圧縮すると200KB近くになるようですが、最適化処理に結構時間がかかるようです。こちらは日々性能改善されている模様。
Playframework2.4で実行
Play Frameworkを導入して以下のコマンドで新規プロジェクトを作成します。
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 | C:\Users\v>activator new Fetching the latest list of templates... Browse the list of templates: http://typesafe.com/activator/templates Choose from these featured templates or enter a template name:   1) minimal-akka-java-seed   2) minimal-akka-scala-seed   3) minimal-java   4) minimal-scala   5) play-java   6) play-scala (hit tab to see a list of all templates) > 4 Enter a name for your application (just press enter for 'minimal-scala') > scala-js OK, application "scala-js" is being created using the "minimal-scala" template. To run "scala-js" from the command line, "cd scala-js" then: | 
次に、project/plugins.sbtファイルを作成して、以下の内容を書きます。Eclipseでプロジェクトをインポートできるようにするプラグインとscala.jsのプラグインを追加しています。
| 1 2 3 | addSbtPlugin("com.typesafe.sbteclipse" % "sbteclipse-plugin" % "3.0.0") addSbtPlugin("org.scala-js" % "sbt-scalajs" % "0.6.8") | 
次にbuild.propertiesに記述されているsbtのバージョンを変更します。
| 1 2 3 4 | #Activator-generated Properties #Sun Mar 20 23:46:46 JST 2016 template.uuid=e17acfbb-1ff5-41f5-b8cf-2c40be6a8340 sbt.version=0.13.9 | 
次にbuild.sbtにscala.jsを追加します。
| 1 2 3 4 5 6 7 8 9 10 11 12 | name := """scala-js""" version := "1.0" scalaVersion := "2.11.7" enablePlugins(ScalaJSPlugin) libraryDependencies ++= Seq (  "org.scalatest" %% "scalatest" % "2.2.4" % "test",  "org.scala-js" %%% "scalajs-dom" % "0.8.0" ) | 
activator eclipseでeclipseにインポートできる状態にします。
| 1 | activator eclipse | 
eclipseのプロジェクトをインポートして、src/main/scala/com/example/Hello.scalaを編集します。
| 1 2 3 4 5 6 7 8 9 | package com.example import scala.scalajs.js object Hello extends js.JSApp {   def main() {     println("hello world")   } } | 
js.JSAppをextendsします。
その状態で「activator fastOptJS」コマンドまたは「activator fullOptJS」を入力すると
| 1 2 3 | activator fastOptJS (または) activator fullOptJS | 
するとtarget/scala-2.11/scala-js-fastopt.jsが出来上がります。
次にプロジェクトのルートにindex-dev.htmlを作ります。先ほど生成した「target/scala-2.11/scala-js-fastopt.js」をロードするように設定してscript要素に先ほど作成したHello.scalaを実行できるようメソッドを作ります。
| 1 2 3 4 5 6 7 8 9 10 11 12 13 | <!DOCTYPE html> <html>  <head>  <meta charset="UTF-8">  <title>The Scala.js Tutorial</title>  <script type="text/javascript" src="./target/scala-2.11/scala-js-fastopt.js"></script>  </head>  <body>  <script>  com.example.Hello().main();  </script>  </body> </html> | 
さあ、作製したindex-dev.htmlをブラウザで開いてみましょう。なんとこのindex-dev.htmlをビルドする必要はありません。scalaのコードはjavascriptに変換されており、「com.example.Hello().main();」で実行することができます。
コンソールログに以下が出力されます。
| 1 | hello world | 
scalaのprintlnがjavascriptのconsole.logに変換されているようですね。
jQueryを使ってみる
jQueryを導入することもできるようです。build.sbtにscalajs-jqueryを導入します。
| 1 2 3 4 5 | libraryDependencies ++= Seq (  "org.scalatest" %% "scalatest" % "2.2.4" % "test",  "org.scala-js" %%% "scalajs-dom" % "0.8.0",  "be.doeraene" %%% "scalajs-jquery" % "0.8.0" ) | 
eclipseに追加
| 1 | activator eclipse | 
Hello.scalaにjQueryっぽい文字列を書きます。
| 1 2 3 4 5 6 7 8 9 10 | package com.example import scala.scalajs.js import org.scalajs.jquery.jQuery object Hello extends js.JSApp {   def main() {     jQuery("body").text("hoge")   } } | 
最後にindex-dev.htmlにjqueryをロードするように記述。
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 | <!DOCTYPE html> <html>   <head>     <meta charset="UTF-8">     <title>The Scala.js Tutorial</title>     <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>     <script type="text/javascript" src="./target/scala-2.11/scala-js-fastopt.js"></script>   </head>   <body>     <script>       com.example.Hello().main();     </script>   </body> </html> | 
(activator fastOptJSを忘れずに実行して)index-dev.htmlを開くと、ブラウザ上に文字列が出力されます。これでscalaでクライアントサイドの動きも記述できてしまいそうですね。
無理にScalaで書く必要があるかといわれるとうーん・・。関数型っぽい記述がしたいだけならlodashで事足りるだろうし、それよりもScalaとJS間のやりとり等々の学習コストが高そうだなぁという印象です。あとはフロントエンドエンジニアがScalaの勉強するのに使えたり・・・?するかもしれませんね。
