このエントリはPlay frameworkひとりアドベントカレンダーの18日目です。
今日はトップページを動的にしてみましょう。
といっても左枠の「最近購入されたチケット」は実装がややこしそうなのでとりあえず放置。 まずは右側のみ実装してみます。
と、ここでおもむろに移植元のperlのコードを見てみます。
/webapp/perl/lib/Isucon2.pm
にあります。
get '/' => [qw(recent_sold)] => sub { my ($self, $c) = @_; my $rows = $self->dbh->select_all( 'SELECT * FROM artist ORDER BY id', ); $c->render('index.tx', { artists => $rows }); };
※recent_soldのところは無視しましょう
artistテーブルからデータをとってきて表示してるだけですね。
続いてartistテーブルの定義を見ておきましょう。
/webapp/config/database/isucon2.sql
にあります。
CREATE TABLE IF NOT EXISTS isucon2.artist ( `id` INT UNSIGNED NOT NULL AUTO_INCREMENT, `name` VARCHAR(255) NOT NULL, PRIMARY KEY (`id`) ) ENGINE=InnoDB;
そんなわけで、今日は
- modelを書く
- viewを書く
- controllerを書く
の順番でやりましょう。
modelを書く
それではさっそくmodelを作りましょう。
modelといえばEBeanなので、まずはmodelが使えるように /conf/application.conf
を設定します。
playでDBを使う設定は下記の通りでした。
とりあえず今はDBはHDBでいいにしましょう。
db.default.driver=org.h2.Driver db.default.url="jdbc:h2:mem:play" ebean.default="models.*"
ここまで設定できたら、 /app/models/Artist.java
を作成しましょう。
modelなクラスは、ひとまず下記を守って作りましょう
/app/models/
直下に作るplay.db.ebean.Model
を継承する@Entity
アノテーションをつけるfinder
を定義する
続いて属性を定義しましょう。 id
, name
の2つですね。
idはprimary keyなので @Id
のアノテーションをつけておきましょう。
package models; import javax.persistence.Entity; import javax.persistence.Id; import play.db.ebean.Model; @Entity public class Artist extends Model { @Id public Integer id; public String name; public static Finder find = new Finder( Integer.class, Artist.class); }
viewを書く
それでは定義したArtistを使う部分から書いていきましょう。
index.scala.html
を更新します。ポイントは2箇所。
- viewが
List
を受け取るよう1行目に定義 List
の中身をとりだしてくるくる回す
@(artists :List[Artist]) <!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>isucon 2</title> <link type="text/css" rel="stylesheet" href="https://netmark.jp/css/ui-lightness/jquery-ui-1.8.24.custom.css"> <link type="text/css" rel="stylesheet" href="https://netmark.jp/css/isucon2.css"> <script type="text/javascript" src="https://netmark.jp/js/jquery-1.8.2.min.js"></script> <script type="text/javascript" src="https://netmark.jp/js/jquery-ui-1.8.24.custom.min.js"></script> <script type="text/javascript" src="https://netmark.jp/js/isucon2.js"></script> </head> <body> <header> <a href="https://netmark.jp/"> <img src="https://netmark.jp/images/isucon_title.jpg"> </a> </header> <div id="sidebar"> <table> <tr><th colspan="2">最近購入されたチケット</th></tr> <tr> <td class="recent_variation">はだいろクローバーZ 横浜アリーナライブ アリーナ席</td> <td class="recent_seat_id">00-01</td> </tr> <tr> <td class="recent_variation">はだいろクローバーZ 横浜アリーナライブ アリーナ席</td> <td class="recent_seat_id">00-00</td> </tr> </table> </div> <div id="content"> <h1>TOP</h1> <ul> @for(artist <- artists){ <li> <a href="https://netmark.jp/artist/@artist.id"> <span class="artist_name">@artist.name</span> </a> </li> } </ul> </div> </body> </html>
controllerを書く
定義したmodelをcontrollerで呼び出して、viewに渡しましょう。
package controllers; import java.util.List; import models.Artist; import play.mvc.Controller; import play.mvc.Result; public class Application extends Controller { public static Result index() { List artists = Artist.find.all(); return ok(views.html.index.render(artists)); } }
renderのところでコンパイルエラーが出る場合、 play run
して一度アクセスしてからeclipseでプロジェクトを Refresh(F5)
すると消えるとおもいます。
それではアクセスしてみましょう。
なにやら怪しいエラー画面が出ました。
これは Evolution
なるものでmodelとschemaを連携させているから表示されてます。
いまはschemaがないというエラーが出ているので Apply this script now!
をクリックしましょう。
エラーなく表示できました! (ただしデータがありません)
mysqlを使うようにする
ではおもむろにmysqlを使うようにしましょう。
更新するのは2箇所。
/project/Build.scala
でmysqlドライバを取得するように定義/conf/application.conf
でmysqlを使うように定義
下記を更新してplayを再起動すると良い感じにアクセスできるようになります。
import sbt._ import Keys._ import PlayProject._ object ApplicationBuild extends Build { val appName = "isucon2-play" val appVersion = "1.0-SNAPSHOT" val appDependencies = Seq( // Add your project dependencies here, "mysql" % "mysql-connector-java" % "5.1.21" ) val main = PlayProject(appName, appVersion, appDependencies, mainLang = JAVA).settings( // Add your own project settings here ) }
db.default.driver=com.mysql.jdbc.Driver db.default.url="jdbc:mysql://127.0.0.1:3306/isucon2?useUnicode=true&characterEncoding=UTF-8" db.default.user=isucon2app db.default.password=isunageruna
※macのばあい、mysqlはbrewで入れちゃいましょう
brew install mysql /usr/local/bin/mysql.server start
そして本家isucon2アプリのschema定義とデータを投入します。
/usr/local/bin/mysql -u root < isucon2/webapp/config/database/isucon2.sql /usr/local/bin/mysql -u root < isucon2/webapp/config/database/initial_data.sql
そしたらブラウザでアクセスして、例のApply〜ボタンを押してみましょう。
あら、なんか出ましたね。もう別途schema定義したので Mark it resolved
しちゃいましょう。
デターヽ(`▽´)/
明日からもこの調子で作っていきましょう。