Monthly Archives: 11月 2009

Log

Sinatraの使い方を調べつつアプリのテンプレートを作ってみた

Sinatraの使い方を学びつつ、ついでにKomodo IDEで使うSinatraアプリのテンプレートを作成してみます。

Sinatraアプリの原形とセッション&Flashメッセージの組み込み

とりあえずSinatraのインストールから。

$ sudo gem install sinatra
Successfully installed rack-1.0.1
Successfully installed sinatra-0.9.4


SinatraとRackがインストールされました。

アプリのオートリロードするためにShotgunをインストール。

$ sudo gem install shotgun

セッションはRackのセッションを利用し、nakajima/rack-flash @ GitHubでRails風のFlashメッセージを利用します。

$ sudo gem install rack-flash

Sinatraアプリ本体をapp.rbとして作成。
RackのセッションとFlashメッセージを利用できるように設定。
トップページでFlashメッセージをセットして、リンク先/helloでメッセージを表示します。

# -*- encoding: UTF-8 -*-
require 'sinatra'
require 'rack/flash'
 
configure do
  use Rack::Session::Cookie,
    #:key => 'rack.session',
    #:domain => 'example.com',
    #:path => '/',
    :expire_after => 3600,
    :secret => 'IgR~tKW4YxEvzSHqp^uArcmbFeJklf5dNVQDwCUhOosyiMZTGj'
  use Rack::Flash
end
 
get '/' do
  flash[:notice] = "Hello world!"
  "<a href='/hello'>Hello world!</a>"
end
 
get '/hello' do
  flash[:notice]
end

$ shotgun app.rb


でアプリを実行して、http://localhost:9393にアクセスして、動作を確認。

したのは良いんですけど、shotgunを終了したらゾンビになってしまいました。
のでSinatraでshotgunの代わりにRack::Reloaderを使う方法 – Hello, world! – s21gを参考に

configure :development do
  class Sinatra::Reloader < Rack::Reloader
    def safe_load(file, mtime, stderr = $stderr)
      ::Sinatra::Application.reset!
      use_in_file_templates! file
      stderr.puts "#{self.class}: reseting routes"
      super
    end
  end
  use Sinatra::Reloader
end


に変更して、

$ ruby app.rb

として、リロードされるようにしました。

HamlとSassを組み込む

HamlとSassをインストール。

$ sudo gem install haml

viewsディレクトリを作成します。

ページレイアウト用にviews/layout.hamlを作成します。
タイトルを表示してflashメッセージを表示するコード。

!!! XML
!!! Strict
 
%html
  %head
    %title Sinatra Template
    %link{:href => "/styles.css", :rel => "stylesheet", :type => "text/css", :media => "screen"}
  %body
    #branding
      %h1 Sinatra Template
    - if flash[:notice]
      %p.notice= flash['notice']
    - if flash[:error]
      %p.error_notice= flash['error']
 
    #content
      != yield

indexページ用にviews/index.hamlを作成します。

%form{:method => 'POST', :action => '/hello'}
  %input{:type => 'submit', :value => 'Say hello!'}

app.rbにこれらを表示するためのコードを追加&変更。

require 'haml'
get '/' do
  haml :index
end
 
post '/hello' do
  flash[:notice] = "Hello world!"
  redirect '/hello'
end
 
get '/hello' do
  flash[:notice]
end

indexページのSay hello!ボタンをクリックすると/helloにPOSTします。さらにそのPOSTでFlashメッセージをセットして、/helloへリダイレクト。/helloでFlashメッセージが表示されます、という内容。

次にSass。
views/styles.sassを作成。内容はあとでリセット入れたり自分用にカスタマイズするとして、今は動作検証のために簡単なコードに。

body
  :font
    :size 1.5em

app.rbにスタイルシートへアクセスするコードを追加。

get '/*.css' do |path|
  content_type 'text/css', :charset => 'utf-8'
  sass path.to_sym, :sass => {:load_paths => options.views}
end

で、動作確認。期待した通りページが表示されました。

ORM => DataMapperの組み込み

ORMはDataMapperを利用します。

$ sudo gem install datamapper
$ sudo gem install do_sqlite3

app.rbにDataMapperの設定を記述。
データベースにはSQLiteを使用。developmentではmemory、productionではファイルを使用します。

require 'dm-core'
require 'logger'
 
configure :development do
  # リロード設定が記述してあります。
  DataMapper.setup(:default, 'sqlite3::memory:')
  DataMapper::Logger.new(STDOUT, :debug)
end
 
configure :production do
  DataMapper.setup(:default, 'sqlite3:production.db')
end

ユーザ認証はどうしましょうか。maxjustus’s sinatra-authentication at master – GitHubとかsubbarao’s sinatra-openid at master – GitHubが便利そうで試してみたんですか、どちらもうまく動かず。DataMapperのプロパティのタイプにBCryptHashがあるので、それを利用して自作するのが簡単かな。とりあえず保留。

テスト環境の導入

テストにはShouldaとCucumber+Webratを利用しようとおもいます。

まずはShoulda。一緒にrack-testも。

$ sudo gem install shoulda
$ sudo gem install rack-test


testディレクトリを作成。

Testing
Sinatra tests can be written using any Rack-based testing library or framework. Rack::Test is recommended:

Sinatra: README

を参考にtest/app_test.rbを作成。

require File.join( File.dirname(__FILE__), '../app.rb')
require 'test/unit'
require 'shoulda'
require 'rack/test'
 
class AppTest < Test::Unit::TestCase
  include Rack::Test::Methods
 
  def app
    Sinatra::Application
  end
 
  context "Access pages" do
    should "show index" do
      get '/'
      assert_match 'Say hello!', last_response.body
    end
 
    should "show hello" do
      post '/hello'
      follow_redirect!
      assert_match 'Hello world!', last_response.body
    end
  end
end

次にCucumber。

$ sudo gem install cucumbe webrat


features, featuers/support, features/step_definitionsディレクトリを作成しました。

cucumber.ymlを「default: –language ja features」という内容で作成しました。

features/support/env.rbを作成しました。

# -*- encoding: UTF-8 -*-
app_file = File.join(File.dirname(__FILE__), '../../app.rb')
require app_file
Sinatra::Application.app_file = app_file
 
require 'test/unit/assertions'
require 'shoulda'
require 'rack/test'
require 'webrat'
 
Encoding.default_external = 'UTF-8'
 
Webrat.configure do |config|
  config.mode = :rack
  config.application_framework = :sinatra
  config.application_port = 4567
end
 
World(Test::Unit::Assertions) do
  def app
    Sinatra::Application
  end
 
  include Rack::Test::Methods
  include Webrat::Methods
  include Webrat::Matchers
end
 
Before do
  DataMapper.auto_migrate!
end

features/step_definitions/webrat_steps.rbは他のシステムで利用しているものをコピー。

問題はfeatures/step_definitions/result_steps.rb。これまではRSpecを利用していたのですが、今回はtest/unitを使うので、xpathの検証とかはどうするかなど。とりあえず動いたコードがこれ。

# -*- encoding: UTF-8 -*-
 
ならば /^"(.*)"と表示される$/ do |text|
  assert_match(/#{text}/m, @response.body)
end
 
ならば /^"(.*)"と表示されない$/ do |text|
  assert_no_match(/#{text}/m, @response.body)
end
 
ならば /^(\w+)メッセージが表示さる$/ do |message_type|
  assert_not_equal 0, Nokogiri::HTML.parse(@response.body).search("//*[@class='#{message_type}']").length
end
 
ならば /^(.*)リクエストが失敗する/ do |_|
  assert_not_equal 200, @response.status
end
 
ならば /ページ読み込みが成功する/ do
  assert_equal 200, @response.status
end


xpathの検査がかっこわるい…。良い方法があったらコメントください。

Rakefileは以下の内容にしました。

require 'cucumber/rake/task'
 
desc 'Run all tests'
task :test do
   require 'rake/testtask'
   Rake::TestTask.new do |t|
      t.test_files = FileList[File.join('test', '**', '*_test.rb')]
   end
end
 
desc "Run all features in features directory"
Cucumber::Rake::Task.new(:features)

あとは

  • Sassを完成させる
  • rack cacheの導入
  • モデル作成したときのためのFixtureの準備
  • configディレクトリを作成して設定ファイルをそこに置くか
  • publicディレクトリの作成
  • ほかいろいろ…

をやったりやらなかったり。

そしてKomodo IDEでプロジェクトテンプレートを作成。

Log

sinatra-genってのを見つけた

quirkey’s sinatra-gen at master – GitHubってのを見つけた。今KomodoIDEのSinatraプロジェクトテンプレート作ってるところだけど、これ使ったら簡単かも。

Log

Shouldaが良さそう

これまでRSpec使ってたけど、調べてみたらthoughtbot’s shoulda at master – GitHubが良さそうな気が。

Shoulda(もっと早く使っていれば)by 達人プログラマ。Rubyのテストには、RSpecもいいけど、Shouldaが良いよ。 « kentaroi’s weblog
RSpecよりShoulda、fixturesよりヘルパーとMocha – Unexplored Rails
Shoulda Roundup: Elegant, Maintainable Ruby Testing

を参考にして使ってみよう思う。

Log

MacPortsでphpMyAdminをインストール

phpMyAdminのインストールと設定

$ sudo port install phpmyadmin

/opt/local/www/phpmyadmin/config.inc.phpに以下を追加。

$cfg['Servers'][$i]['socket'] = '/opt/local/var/run/mysql5/mysqld.sock';


connect_typeをtcpからsocketに変更。

$cfg['Servers'][$i]['connect_type'] = 'socket';


blowfish_secretに46文字以内で文字列を指定。

Apacheの設定

/opt/local/apache2/conf/httpd.confに以下を追加

<Directory /opt/local/www/phpmyadmin>
    Options FollowSymLinks
    AllowOverride All
    Order deny,allow
    Deny from all
    Allow from all
</Directory>
Alias /phpmyadmin /opt/local/www/phpmyadmin

Log

ガントチャートにはGanttProjectを利用した

Deliciousで検索したらGanttProject Homeがヒットしたので、ダウンロードして使ってみた。

Mac専用ではないので少し使いにくかったですが、Windowsユーザの方と仕事をしているので、その点で有利。

それに現状必要な機能は十分持っているのでなかなか良かった。今後も利用することにした。

Log

工程表を作成するのでOmniPlanみてみたけどやっぱりTracかなと思った

工程表を作成する段になって、OmniPlanってどうなんだろとThe Omni Group – OmniPlanを見てみた。

解説動画でExportをHTMLでやってて、ネットに公開するのも簡単そうだなぁと思った。けど、値段に…。

それならTracでガントチャート表示するのが簡単&安上がりかなという結論に。ついでにTrac導入のチュートリアルでも加工かな。

とりあえずすぐ作らないといけないからTemplate: Project Template With Gantt Chart for Apple iWork Numbersを利用してiWorks Numbersで作成してみる。

Log

ためしてガッテンを見てパソコンで仕事するならやっぱりこれだと思った

世紀の大発見!頑固な疲れの原因“物質F” : ためしてガッテン – NHKは実に良かった。昔みたいにガッテンを10回押してもOKなくらい。

そして結局パソコン仕事するならこれ↓が正解(か)!w

Focal:ノートPC寝たままスタンド Laidback – iPhoneケースやiPhoneアクセサリ、iPodケースやiPodアクセサリ、Mac周辺機器

Amazonが¥14,008で安いかな。ノートPC寝たままスタンドLaidback LDB-ST-000001

前から気になってたけど、本気でに購入検討しようかな。

Log

LaunchBarからiTunesの現在の曲にレーティングするAppleScriptスクリプト

LaunchBarからiTunesの再生中の曲にレートをつけるスクリプトを作成。Genius Mixでは利用できないみたい。

tell application "iTunes"
	set targetId to database ID of current track
	set targetTrack to item 1 of (every track of current playlist whose database ID is targetId)
 
	set ratings to {"・・・・・", "★・・・・", "★★・・・", "★★★・・", "★★★★・", "★★★★★"}
	set selectedItem to item 1 of {choose from list ratings}
	if selectedItem = false then return
 
	set selectedRating to item 1 of selectedItem
 
	if selectedRating = "・・・・・" then
		set ratingNumber to 0
	else if selectedRating = "★・・・・" then
		set ratingNumber to 20
	else if selectedRating = "★★・・・" then
		set ratingNumber to 40
	else if selectedRating = "★★★・・" then
		set ratingNumber to 60
	else if selectedRating = "★★★★・" then
		set ratingNumber to 80
	else if selectedRating = "★★★★★" then
		set ratingNumber to 100
	end if
 
	set rating of targetTrack to ratingNumber
end tell

Log

LaunchBarからiTunesの現在の曲のレーティングを表示するAppleScriptスクリプトを作成

iTunes for Mac まとめ – AppleScriptを参考に作成。

tell application "iTunes"
	set targetTrack to rating of current track
end tell
if targetTrack = 0 then
	set hoshi to "・・・・・"
else if targetTrack = 20 then
	set hoshi to "★・・・・"
else if targetTrack = 40 then
	set hoshi to "★★・・・"
else if targetTrack = 60 then
	set hoshi to "★★★・・"
else if targetTrack = 80 then
	set hoshi to "★★★★・"
else if targetTrack = 100 then
	set hoshi to "★★★★★"
end if
tell application "LaunchBar"
	display in large type hoshi
	delay 1
	hide
end tell

Snow LeopardにMacPortsでApache+MySQL+PHPのWebアプリケーション開発環境を作成する

MacPortsでApache+MySQL+PHPをインストールしてWebアプリケーション開発環境を作成します。

Mac OS X 10.6 Snow LeopardにMacPortsとDeveloperToolsをインストールしていることを前提にしています。

Apacheのインストールと設定

MacPortsでApacheをインストールします。

$ sudo port install apache2


インストールの最後に以下の文が表示されます。

###########################################################
# A startup item has been generated that will aid in
# starting apache2 with launchd. It is disabled
# by default. Execute the following command to start it,
# and to cause it to launch at startup:
#
# sudo launchctl load -w /Library/LaunchDaemons/org.macports.apache2.plist
###########################################################

Apacheはlaunchdで開始するようになっています。デフォルトでは無効になっているので、sudo launchctl load -w /Library/LaunchDaemons/org.macports.apache2.plistを実行して有効にします。有効にするとApacheが起動します。また、OSを再起動してもApacheが自動的に起動されるようになります。

Apacheの動作確認のため、ブラウザでlocalhostもしくはシステム環境設定の共有で指定したコンピュータ名.localにアクセスします。正しく動作していれば「It works!」と表示されます。

開発環境なので、Apacheのドキュメントルートを~/Sitesフォルダに、実行ユーザを自分のユーザアカウントに変更します(ルートを変更せずに#Include conf/extra/httpd-userdir.confの#を削って有効にすれば、ユーザごとにSitesフォルダが使用できるようになります。)。さらに、機能や設定を自由に変更できるようにします。

/opt/local/apache2/conf/httpd.confファイルの
User wwwをUser yourusername
DocumentRoot “/opt/local/apache2/htdocs”をDocumentRoot “/Users/yourusername/Sites”

<Directory “/opt/local/apache2/htdocs”>を<Directory “/Users/yourusername/Sites”>

(上記Directory内の)Options Indexes FollowSymLinksをOptions All、AllowOverride NoneをAllowOverride All

に変更します。

これらの変更を以下のコマンドでApacheに適用します。

$ sudo /opt/local/apache2/bin/apachectl graceful


再度localhostにアクセスすると、/Users/yourusername/Sitesが表示されます。

MySQLのインストールと設定

続いてMySQLをインストールします。

$ sudo port install mysql5-server

起動する前にデータベースの設定をしておきます。my.cnfを設置して編集します。

$ sudo cp /opt/local/share/mysql5/mysql/my-medium.cnf /opt/local/etc/mysql5/my.cnf


[client]
default-character-set=utf8
[mysqld]
datadir=/Users/yourusername/local/var/mysql
language=/opt/local/share/mysql5/mysql/japanese
default-character-set=utf8
skip-character-set-client-handshake
[mysqldump]
default-character-set=utf8
[mysql]
default-character-set=utf8

MacPortsでインストールしたときに以下の文が表示されます。

###########################################################
# A startup item has been generated that will aid in
# starting mysql5-server with launchd. It is disabled
# by default. Execute the following command to start it,
# and to cause it to launch at startup:
#
# sudo launchctl load -w /Library/LaunchDaemons/org.macports.mysql5.plist
###########################################################
******************************************************
* In order to setup the database, you might want to run
* sudo -u mysql mysql_install_db5
* if this is a new install
******************************************************

これまでMySQLをインストールしたことがない場合はsudo -u mysql mysql_install_db5を実行します。sudo launchctl load -w /Library/LaunchDaemons/org.macports.mysql5.plistを実行して起動します。mysql5を実行するかSequel ProでMySQLサーバに接続して、動作しているか確認します。ソケットは/opt/local/var/run/mysql5/mysqld.sockです。

PHPのインストールと設定

PHP5.2系をインストールします。以下の設定が可能です。

$ port variants php52
php52 has the variants:
   apache: Add Apache 1 web server module
     * conflicts with apache2 no_web
[+]apache2: Add Apache 2.2 web server module
     * conflicts with apache no_web
   darwin_10: Platform variant, selected automatically
   dbase: Add dBase file format support
   debug: Enable debug support (useful to analyze a PHP-related core dump)
   fastcgi: Add FastCGI web server binary
     * conflicts with no_web
   gmp: Add GNU MP multiprocessing functions
   imap: Add IMAP protocol support
   ipc: Add semaphore, shared memory and IPC functions
   macosx: Platform variant, selected automatically
   macports_snmp: Add SNMP support using MacPorts SNMP
     * conflicts with snmp
   mssql: Add MS-SQL server support
   mysql4: Add MySQL 4 support
     * conflicts with mysql5
   mysql5: Add MySQL 5 support
     * conflicts with mysql4
   no_web: Don't include any web server support
     * conflicts with apache apache2 fastcgi
   oracle: Add Oracle oci8 database functions with the Oracle Instant Client
   pcntl: Add process control functions
   pear: Add PEAR
   postgresql82: Add postgresql82 support
     * conflicts with postgresql83
   postgresql83: Add postgresql83 support
     * conflicts with postgresql82
   pspell: Add pspell spell-checking functions
   readline: Add GNU readline functions
   snmp: Add SNMP support using Apple SNMP
     * conflicts with macports_snmp
   sockets: Add socket communication functions
   sqlite: Add SQLite support
   suhosin: Add Suhosin patch
   t1lib: Add PostScript Type 1 font support with t1lib
   tidy: Add Tidy support
   universal: Build for multiple architectures


とりあえずApache2 / MySQL / PEARを指定しますが、たとえばSQLiteのサポートが必要であれば+sqliteを指定したり、必要なものを指定します。また、PHP 5.3系を利用する場合はphp52ではなくphp5ポートを利用し、+mysqlではなくphp5-mysqlポートをインストールします。

$ sudo port install php52 +apache2+mysql5+pear
To customize php, copy
/opt/local/etc/php5/php.ini-dist (if this is a development server) or
/opt/local/etc/php5/php.ini-recommended (if this is a production server) to
/opt/local/etc/php5/php.ini and then make changes.
 
If this is your first install, you need to activate PHP in your web server.
 
To enable PHP in Apache, run
  cd /opt/local/apache2/modules
  /opt/local/apache2/bin/apxs -a -e -n "php5" libphp5.so

指示通りにPHP設定ファイルを配置して、PHPをApacheに組み込みます。

$ sudo cp /opt/local/etc/php5/php.ini-dist /opt/local/etc/php5/php.ini
$ sudo /opt/local/apache2/bin/apxs -a -e -n "php5" libphp5.so

/opt/local/apache/conf/httpd.confを編集します。
DirectoryIndexにindex.phpを追加します。

<IfModule dir_module>
    DirectoryIndex index.html index.php
</IfModule>


httpd.confの最後に以下を追加します。

Include conf/extra/mod_php.conf

Apacheに設定を反映させます。

$ sudo /opt/local/apache2/bin/apachectl graceful

PHPの動作をテストするために、~/Sites/info.phpファイルを以下の内容で作成します。

<?php phpinfo(); ?>

http://localhost/info.phpにアクセスして、PHPの動作を確認します。PHPの情報が表示されればインストール成功です。

Get Adobe Flash playerPlugin by wpburn.com wordpress themes