寫(xiě)一個(gè)漂亮Rakefile的方法
Rake 我就不再介紹了,Ruby 的 Make ,許多方面都比 Make 要更好用一些。和 Makefile 不同的是,Rakefile 本身其實(shí)就是一段 Ruby 代碼,這樣的好處有很多,一方面在 Rake 里面就可以很直接地做任何 Ruby 能做的事了,另一方面由于 Ruby 對(duì) DSL 支持良好,所以 Rakefile 通??雌饋?lái)也并不那么“代碼”。
不過(guò),代碼始終是代碼,Makefile 尚且可以寫(xiě)得很亂,Rakefile 要寫(xiě)亂就更容易了,幸運(yùn)地是,Rake 提供了一些功能讓我們可以來(lái)對(duì) Rakefile 做一些組織工作。
其中之一就是 import 功能,把不同功能的 task 寫(xiě)到不同的文件中,例如,像這個(gè)樣子:
Rakefile
task/
+-- doc.rake
+-- compile.rake
`-- deploy.rake
這樣,在 Rakefile 里寫(xiě)上
import("task/doc.rake")
這樣的語(yǔ)句導(dǎo)入各個(gè)子任務(wù)即可,不同的任務(wù)寫(xiě)到不同的文件里面就不會(huì)一團(tuán)糟了。而且,import 同 Ruby 自己的 require 不一樣,import 并不是立即進(jìn)行導(dǎo)入的,而是在整個(gè) Rakefile 執(zhí)行結(jié)束之后才全部導(dǎo)入,因此,可以在任意的地方寫(xiě) import ,而不用擔(dān)心依賴(lài)關(guān)系,需要共享的變量之類(lèi)的只要在主 Rakefile 中定義了即可。
import 是組織不同的功能模塊,除此之外,Rake 還允許我們對(duì)一些重復(fù)性的任務(wù)進(jìn)行抽象,具體來(lái)說(shuō),就是自定義的 task 。通常情況下,我們使用 Rake 提供的通用 task 和文件 task 來(lái)構(gòu)造我們需要完成的工作,除此之外,Rake 還自帶了一些針對(duì)特殊任務(wù)的 task 類(lèi)型,例如構(gòu)建 rdoc 或者運(yùn)行 test 等。實(shí)際上,一種任務(wù)就是一個(gè)普通的 Ruby 類(lèi),我們可以繼承 Rake 里的 Task 類(lèi)并重新定義相關(guān)的函數(shù)來(lái)實(shí)現(xiàn)自定義的 task 類(lèi)型。不過(guò),這樣多少有些麻煩,實(shí)際上,很多時(shí)候我們要定義的任務(wù)都可以分解為一些小任務(wù)用內(nèi)置的通用 task 和 file task 來(lái)實(shí)現(xiàn)的,這個(gè)時(shí)候可以用 Tasklib 來(lái)更方便地定義自定義的任務(wù)。
具體地來(lái)說(shuō),就是寫(xiě)一個(gè)類(lèi),繼承自 Tasklib (雖然實(shí)際上只是約定而并不是必須的),然后在這個(gè)類(lèi)的初始化函數(shù)里用 task 或者 file 來(lái)定義實(shí)際完成任務(wù)的子 task 即可。用一個(gè)實(shí)際的例子來(lái)說(shuō),比如說(shuō),我們可以定義一個(gè) ErlcTask ,可以用來(lái)把一些 Erlang 文件編譯到某個(gè)目錄下,并在 clean 的時(shí)候自動(dòng)能把編譯出來(lái)的 .beam 文件清理掉:
require 'rake'
require 'rake/clean'
require 'rake/tasklib'
class ErlcTask < Rake::TaskLib
attr_accessor :name
attr_accessor :sources
attr_accessor :dest_dir
attr_accessor :include_path
attr_accessor :flags
attr_accessor :extra_dep
def initialize(name = :erlc)
# default values
if name.is_a? Hash
@name = name.keys.first
@extra_dep = name.values.first
else
@name = name
@extra_dep = []
end
@sources = FileList[]
@dest_dir = '.'
@include_path = []
@flags = "-W +warn_unused_vars +warn_unused_import"
yield self if block_given?
define
end
def define
beams = @sources.pathmap(File.join(@dest_dir, '%n.beam'))
include_path = Array(@include_path).map{|incl|"-I"+incl}.join(" ")
directory @dest_dir
beams.zip(@sources).each do |beam, source|
file beam => source do
sh "erlc -pa #{@dest_dir} #{@flags} #{include_path} -o #{@dest_dir} #{source}"
end
end
task @name => beams + Array(@extra_dep)
CLEAN.include(beams)
end
end
首先定義一些 Task 相關(guān)的屬性,在初始化函數(shù)里設(shè)置初值,然后調(diào)用 block 來(lái)填充實(shí)際的值,最后調(diào)用 define 函數(shù),define 函數(shù)就使用 directory 、file 和 task 分別定義了建立目錄、編譯和清理的任務(wù)。如果了解 Ruby 和 Rake 的基本語(yǔ)法的話(huà),應(yīng)該很容易看明白了。
接下來(lái)把這個(gè)文件保存到某個(gè) .rb 里,然后在 Rakefile 里 require 之,就可以這樣寫(xiě)了:
ErlcTask.new :compile do |t|
t.sources = FileList['src/*.erl']
t.dest_dir = '../ebin'
t.include_path = '../include'
t.extra_dep = :library
end
看起來(lái)就清爽多了!并且可以重復(fù)利用。 末了,順便再感嘆一下,雖然最近都是用 Python 用得多一些,但是每次再寫(xiě) Ruby 都能感覺(jué)到寫(xiě)起來(lái)很舒服,這是基本不可能在 Python 里找到的感覺(jué)??!
相關(guān)文章
Ruby On Rails上手筆記(安裝使用全過(guò)程)
有機(jī)會(huì)再試一試Rails了,只是原來(lái)接觸的是2,現(xiàn)在已然變成了4,似乎現(xiàn)在的安裝比原來(lái)會(huì)快些。2014-05-05
rails "No route matches" 錯(cuò)誤的解決方法
有時(shí)候 rails 會(huì)出現(xiàn)2008-12-12
Ruby中Hash哈希結(jié)構(gòu)的基本操作方法小結(jié)
Hash是一種鍵值對(duì)應(yīng)的數(shù)據(jù)結(jié)構(gòu),Ruby中直接帶有Hash類(lèi)來(lái)對(duì)其提供支持,這里我們整理了Ruby中Hash哈希結(jié)構(gòu)的基本操作方法小結(jié),首先來(lái)回顧一下Hash的基本知識(shí):2016-06-06
win7安裝ruby on rails開(kāi)發(fā)環(huán)境
看到很多文章都說(shuō)ruby環(huán)境在windows上是非常難搭建,會(huì)出現(xiàn)各種各樣的怪問(wèn)題,所以都推薦到linux和mac上安裝開(kāi)發(fā)。但是我按照教程搭了下,問(wèn)題也不算太多。總過(guò)大概花費(fèi)了2個(gè)半小時(shí)左右就完成了。下面就把安裝的步驟及具體的版本記錄了一下供大家參考。2014-07-07
實(shí)例解析Ruby中的數(shù)值類(lèi)型以及常量
這篇文章主要介紹了Ruby中的數(shù)值類(lèi)型以及常量,是Ruby入門(mén)學(xué)習(xí)中的基礎(chǔ)知識(shí),需要的朋友可以參考下2015-10-10
CentOS7下搭建ruby on rails開(kāi)發(fā)環(huán)境
聽(tīng)說(shuō)rails是一個(gè)比較流行的快速開(kāi)發(fā)框架,對(duì)于我這個(gè)web不熟悉的人來(lái)說(shuō),那是極好的!可以快速上手,又能真正了解服務(wù)器端的各種,所以rails搞起來(lái)。不過(guò)一個(gè)完整的開(kāi)發(fā)環(huán)境搭建過(guò)程完成后,真的只能用各種坑來(lái)形容~2016-02-02
Ruby中執(zhí)行Linux shell命令的六種方法詳解
這篇文章主要介紹了Ruby中執(zhí)行Linux shell命令的六種方法詳解,這些方法包括exec、system、反引號(hào)、IO、Open3、Open4等命令,需要的朋友可以參考下2015-01-01

