TextMate 推薦安裝 Plugins

Update(2011/5): 推薦安裝 Peepcode 快速找檔
Update(2010/5): 10 TextMate bundles/plugins to boost your Ruby on Rails development productivity

textmate_logo

Update(2009/2/21): Textmate 只有內建 Ctrl+Shift+A 的 SVN 功能,要支援 Git 請裝 Git Textmate Bundle,按 Ctrl+Shift+G 就可以有快捷功能。

Update(2009/2/22): 另外推薦一個不是 TextMate 的 Plugin,但是搭配起來非常好用的 Visor,只要使用快捷鍵就可以在螢幕上方下拉出 Terminal 畫面。

第一名是 AckMateack 是一套專門用來搜尋大型程式碼的工具,效能真是超級好。裝了這個套件之後,內建的 Find in Project 就別再用了吧。

第二名是 TextMate Plug-in: ProjectPlus,可以在顯示 SCM 的檔案狀態(例如有本地異動或有新增檔案等等),支援 SVN, Git, Mercurial, Svk 跟 Bazaar。

第三名是 CJK-Input.tmplugin,讓你可以正常輸入中文。如果有需要正常顯示,就必須換字型為 TextMateJ2 (see 解決 Textmate 中文問題)。

跟 Ruby on Rails 相關的有 Ruby on Rails TextMate bundleRuby TextMate bundleRails footnotes(會在例外錯誤畫面放有 Textmate 的連結,點下去就開出來該檔案,十分方便)。

Theme 方面,我自己用的是 Rails Envy Theme 連結失效,改放這裡 Rails Envy Theme (2011/3/20)。

另外就是官方 wiki 上的 Plugins 可以試試看。

實戰敏捷開發 Practices of an Agile Developer (6) 團隊開發篇

有效率的團隊互動是敏捷軟體開發的一個重要基石,能與人一起開發軟體是很棒的事情。

小小一本書,拖了這麼久終於整理完了,總計六篇:

Schedule Regular Face Time (進行每日的固定簡短開會)

開會是個溝通必要但又花時間討人厭的事情,在 Agile 方法論裡面提出了一種叫 Stand-up meeting 的每天開會方式,正如其名建議的:請站著開會,這樣才會提醒大家盡早開完。每個人至多兩分鐘報告三件事情 1.距離上次開會,我做了什麼? 2. 到下次開會,我打算做什麼 3. 我碰到的困難。如果有需要討論更細節特定的東西,請再約有關係的人在開完 stand-up 各自帶開即可。一般來說合理的 stand-up meeting 時間約10到15分鐘,至多絕不超過 30 分鐘。另外就是儘量不要等人,時間到了就開始吧。

Stand-up meeting 有幾個好處:1. 繼續專心每天的進度 2. 如果 developer 碰到任何問題,可以有機會發出聲音尋求幫助,加速事情解決 3. 幫助團隊成員了解其他人在做什麼事情。

Architects Must Write Code (架構設計師一定要寫程式)

軟體架構設計師已經變成有點被濫用的職稱了,一個只會畫好看的圖、講厲害的行話、用一堆 Patterns,但是真的要實做前就跑走的設計師是沒有用的。真的設計隨著實際開始實做、實際的 Feedback 之後才會逐漸演化。就像打戰一樣,一旦開打 Plan 就無用了,只能不斷地 Planning,策略決策也許千里遠可以做,但是戰術決定非得實際在戰場上了解才行。

The designer of a new kind of system must participate fully in the implementation. by Donald E. Knuth

作為一個架構設計師,要實際了解設計真的可行才算是負責。真正的 architect 是團隊中的導師,有能力解決較複雜的問題,但絕不放棄 coding。絕對不要用不 coding 的架構設計師,不實際 coding 了解系統是不可能設計好軟體的。 * Good Design evolves from active programmers. *

Practice Collective Ownership (練習集體擁有感)

“這個地方是 xxx 寫的,只有等他放假回來才能修的好”,這種事情很糟糕。請避免讓某一段 code 只能由某特定 developer 處理的情況,試著輪調 developer 去寫系統中不同的模組,分別由不同的人看過也可以讓程式更加被 checked、refactored 和 maintained 過,一旦碰到哪裡急需要修 Bugs 也不會發生等人的窘境。

當然,也許讓 developer 專屬某一領域的工作可能會開發一時會比較快速,不過放長遠一點看,透過多人共同開發的方式會獲得比較好的程式品質,也會比較好維護。整個團隊的 developers 的平均水準也可以拉高。對 developer 來說,知道寫出來的程式將來會被別人看,也會寫的更加用心。

這件事做起來當然是要注意過猶不及,例如太頻繁的輪調造成混亂或是系統中真的有某處需要特定人的特定專業知識。重點是 “你可以不需要了解系統中的每個細節,但是你也不應該害怕要你接手處理系統中的任何一塊”。

在 XP 方法論中,這件事情更是直接透過 Pair Programming 來達成,每一段 code 至少被兩個人擁有(處理) :p

Be a Mentor (當一個導師)

當你發現你比同事都懂的多的時候,請學著分享,正所謂教學相長,讓團隊一起提昇。當 Mentor 不代表要像當老師一樣用上課的方式,透過 Pair Programming 就是一種很好的學習成長方式。

Allow People to Figure It Out (給人魚不如給釣竿)

當 Mentor 不一定就是直接回答人家答案,回答一個方向讓人去思考也是個好方法,也許他還會回報你更多好答案。

Share Code Only When Ready (只 commit 準備好的程式)

千萬不要把(已知)會爛掉的程式 commit 進入版本控制系統,不然其他人更新最新版本之後不能正常執行,影響開發進度。請在做完一個任務或解完 Bug 之後,通過 unit test 之後再 commit 進去。當然,”It’s not ready” 不是一個久久不 commit 的藉口。

Review Code (程式碼複審)

找到程式問題的最佳時機就是剛寫好的時候:也就是在寫好程式及測試之後,輪流由另一外 developer 檢查程式(review code)。另一種採行 review code 的方式就是實行 XP 方法論的 pair programming:一人寫程式打字另一人是導航員。

Review code 要做什麼事情?

  • 你可以閱讀看得懂程式嗎? (如果看不懂表示程式沒寫的好懂哩)
  • 有沒有任何明顯的錯誤?
  • 這程式有沒有任何不期望的副作用?
  • 這程式有沒有跟系統其他地方有重複的程式碼?
  • 有沒有任何合理的改進或重構可以做?

Code Review 可以大大改進程式品質、降低錯誤率,而且非常實用讓團隊彼此進步。

Keep Others Informed (資訊公開)

不要在 Deadline 那天才報告壞消息。如果任務中途碰到技術困難,也要提出來讓大家想想看怎麼解決,甚至讓客戶知道也許他們願意用其他任務交換。盡量公開進度資訊,團隊跟客戶才會對進度感到放心、知道何時幫助你,讓你贏得信任。不要等著讓別人追問你進度如何。

實戰敏捷開發 Practices of an Agile Developer (5) 除錯篇

Update(2009/9/22): 看到另一篇說明 bug report 該有什麼內容

debugging 最大問題在於,它是一個未知的時間箱子,不知道要花多久才能 debug 完。這章談的是幾個除錯上的技巧。

說到除錯,我也推薦閱讀如何有效地報告錯誤這一篇文章,談的是如何正確回報錯誤,好的錯誤回報可以節省很多時間,而不僅僅只是一句 “程式不會動” 而已。

Keep a Solutions Log (紀錄下解決問題的辦法)

解決問題一直是軟體開發者的工作項目(這裡指的問題比較像是軟體安裝、版本、函式庫使用等等問題,例如 windows 上如何把 MySQL Ruby gem 裝起來等等),不過有時候會碰到似曾相似的問題,疑?我以前是怎麼解決的?拜網路發達之賜,Google 搜尋一下通常會有不少幫助,但是還是得花不少時間找尋解答。

自己維護一份簡單的 solutions log 吧,紀錄下日期、問題描述、解法、參考網址等等資訊,之後碰到類似的問題就可以搜尋的到。將這份 log 用 wiki 維護也是不錯的主意。或是寫在 Blog 上,這樣 google 搞不好還會搜尋到自己以前寫的解法…XD

Warnings Are Really Errors (把警告當真)

編譯器(這裡泛指 complier 或 interpreter) 的警告常常有人是忽略不看的,反正可以編譯執行不會 error 就好了?書上舉了 C++ 的例子,編譯器的警告還是蠻有用的(我想特別是 static 語言)可以幫助你找到跟避免潛在的 Bugs,請不要忽略。請將編譯器的警告也當作程式錯誤或無法通過測試的程式一樣認真處理。

我自己寫 Ruby/Rails 的經驗,最常見的警告像是有:


link_to ( 'login', login_path ) # warning: don't put space before argument parentheses

因為中間多了一個沒用的空白。或是

p Array.new 3, 1 # warning: parenthesize argument(s) for future version

因為 interpreter 覺得 ambiguities 不清楚,這時要請你括號括清楚。另外就是 DEPRECATION WARNING 警告了,告訴你這函式將來的版本將會移除,請不要再用了 :p

Attack Problems in Isolation (隔離除錯)

要在一個大系統找特定問題,不要整個系統一起測,而是將分開隔離找出病因。如果有做 unit tests,我們知道可以將 dependence 的東西用 mock object 隔離出來,這樣測試的時候就不會被外部因素干擾。同理在抓整個系統中的特定 Bugs 的時候,必要的話可以做一些假的 prototype 元件用以隔離抓出問題所在,同時也比較好除錯測試。

我自己土法煉鋼除錯 CSS 也是如此,先移除 CSS 檔案的一半,看看問題是不是出在這裡,然後再砍一半直到找到有問題的那一行。(Binary search?)

Report All Exceptions (回報所有的例外)

如果呼叫一個可能會丟例外的函式,當碰到例外時,盡量可以處理就處理,不然請讓他自然傳播(Propagate)上去給上一層 Caller 處理,不要攔下來又什麼都不做。如果在整個 call stack 中有個傢伙寫了個空個 catch 所有例外,然後 return null 什麼都不做,到時候要找 Bugs 你就會很想殺人了,因為非得 trace 進去 call stack 才能找到原因。

不要覺得自己不會這樣寫,其實常常我們會想”暫時”不想處理這個例外,於是就留下這樣空的例外處理程式碼(然後繼續留到 Production code)。決定要在哪一層處理例外是個設計上的考量,但是如果呼叫一個函式卻要考慮處理二三十種以上的例外可能就有設計上的問題了。

Provide Useful Error Messages (提供使用者有用的錯誤訊息)

一般性的錯誤訊息如 “Something went wrong” 對使用者來說,可說是一點幫助也沒有,既沒有告訴用戶可以怎麼解決,就算使用者想要求助也不知道發生什麼事情。所以盡量提供詳細的訊息告訴使用者發生什麼事情。

當然,如果是比較嚴重的程式例外錯誤,對開發者來說,因為有 logging 的關係,所以看 log 應該可以知道大概的情況並排除,這類的錯誤對使用者來說也沒辦法自行排除,也只能告訴用戶說這不是因為他們操作錯誤的原因。

關於這個議題這一節講的不是很清楚,我個人推薦有本 37 signals 的小書可以翻翻:Defensive Design for the Web 圖文並茂共有40條 Guideline 告訴你如何改進網站的錯誤提示訊息、表單填寫等等,例如:

  • 錯誤訊息要明顯,使用顏色、Icons 等效果
  • 錯誤訊息包含這是什麼錯誤以及如何修復
  • 整個網站用一致的錯誤提示方式
  • 在錯誤提示後,不需要再回上一頁才能修正問題
  • 用易懂、禮貌的字句

實戰敏捷開發 Practices of an Agile Developer (4) 程式篇

趁著新年連續假期,終於把這一章念完了:隨著開發的進展,程式逐漸變得怪獸。這章談幾個重點幫助你讓程式容易了解、擴充及維護。

Program Intently and Expressively (寫清楚了解的程式)

厲害的程式是沒有人可以看懂的程式?程式的可閱讀性比寫得方便還重要,寫只會寫一遍,看卻會看很多次。很多時候會有機會要修 Bugs 或是新增功能,這時搞懂本來的程式常常是一開始最困難的地方,如果一開始寫的人就以可讀性為重要目標,那你就會輕鬆的多。

舉個我自己常見的例子就是 Magic Number,很多人喜歡是一個數字來代表 Type code。例如 1 代表 foo、2 代表 bar、3代表…etc,然後程式裡面就直接寫 1, 2, 3。方便是方便,但是沒多久就會忘記這個 1,2,3 各代表什麼意義。最簡單的解決手法就是請改用字串 constant 處理,或者是用 class 來表示 type。

透過程式語言本身的特色可以寫出更有表達力的程式,函數名稱應該傳達出意圖、參數名稱應該表達出他們的用途,寫出好閱讀的程式我們可以避免很多不必要的註解跟說明文件。一些你覺得明顯簡單的地方,不一定對別人也是如此明顯,甚至是幾個月後的你自己。請想想看幾個月後自己來看還會看得懂嗎?

Communicate in Code (寫出可以閱讀的程式)

我們都討厭寫文件的一大理由是:所謂的文件跟程式碼常是分開的兩碼子事,因此很難讓文件跟的上程式的更新,最終變得難以維護。因此最好的寫文件方式,就是透過程式本身和程式中的註解。

註解是用來寫目的、限制條件跟預期結果等,而不是寫出以下這些程式一行行會做些什麼(請不要拿註解再寫一次程式碼在寫的事情)。一個簡單的判斷方式是:寫在函式 “裡面” 的註解多半是不需要的 (尤其是註解寫 what? 而不是註解 why?)。在重構一書更直言回答哪裡需要重構?那就是有註解的地方:如果程式碼前方有一行註釋,就是在提醒你,可以將這段程式碼替換成一個函式,而且可以在註釋的基礎上給這個函式命名。

你要做的事情應該是讓 source code 本身容易了解,而不是透過註解。透過正確的變數命名、好的空白間隔、邏輯分離清楚的執行路徑等手法,我們很少需要在函式裡面註明這些程式在做什麼,我自己的經驗除非是有參考外部的程式碼或複雜演算法,我會多註明參考來源(網址)。否則沒有必要的註解對我來說就像噪音一樣,妨礙閱讀。

變數跟函式的命名是件非常重要的事情,有意義的命名可以傳達出程式怎麼進行,我舉個 Rails 例子:

p = Post.find(param[:id])
if p
   p.destroy
else
   p = Post.new( param[:post] )
   p.save
end


可以改寫成以下這樣具有清楚意含:

existed_post = Post.find(param[:id])
if existed_post
  existed_post.destroy
else
  new_post = Post.new( param[:post] )
  new_post.save
end

有一種 Job security 的方式就是把程式中所有的變數名稱都代換成亂碼,保證拿到的人超級難看得懂。這就是為什麼手工打造的程式碼有其不可取代的重要性,只要拿到整合型 IDE 像是 Dreamweaver 產生出來的 HTML/CSS code 都很想殺人,因為裡面的變數都是編號產生出來的,根本沒辦法閱讀及擴充。

另外就是大家很喜歡用縮寫,這在我之前寫的文章 物件導向程式的九個體操練習 也有提到,這些只有一個字母的暫時變數並沒有辦法傳達出任何可以幫助了解的資訊。

Class, module, method 前面是個寫註解的好地方,而且每個語言都有工具(例如 RDoc, Javadoc… 等)可以幫忙從程式碼中整理出好看的純文件,這些說明通常有:

  • Purpose 目的
  • Requirements(pre-conditions) 預期的輸入是什麼
  • Promises(post-conditions) 什麼樣的輸入,會有什麼樣的預期輸出
  • Exceptions: 有哪些例外(exceptions)情況

這些說明可以幫助我們由大局觀了解程式是怎麼運作的,而不需要仔細看其中每個 method。
閱讀全文〈實戰敏捷開發 Practices of an Agile Developer (4) 程式篇〉

Ruby Advent 2008 摘要 (下)

Ruby Advent 2008連載完畢,來繼續整理完下集。

  1. GUIfy your Ruby apps with Shoes
    介紹 Shoes 這套有趣的跨平台 GUI 小型開發工具。
  2. Ansuz: Rails based CMS for the Masses
    介紹 Ansuz 這套 Rails-based CMS。裝起來玩了一下,看起來功能蠻多的。不過我個人還是推薦 Radiant 這套比較精簡些。
  3. A Collection of Rack middlewares
    Rack 幾乎要變成 Ruby 社群要做 web framework/apps 標準規格了,Edge Rails 最近在做的 Metal 就是在 Rails 裡也可以撰寫低階的 Rack 操作(效能++)。這篇文章則介紹幾套基於 Rack 的 middleware 函式庫,任何基於 Rack 的 Web framework/apps 都可以使用。也就是對將採用 Rack 的 Rails 來說,這些 Rack middleware 都無需經過 Rails router 和 Action Controller path 就可以把事情做完,真是太厲害了。
  4. Rails 2.2 Internationalization
    介紹及經驗分享 Rails 2.2 的 i18n 功能。有興趣可以看看我之前在 Ruby Tuesday 分享的投影片
  5. Prawn and the future of Ruby PDF generation
    傳統上 Ruby 要產生 PDF 文件,會考慮使用 PDF Writer 等等工具,不過現在有執行速度更快、API設計更好的選擇了(而且 PDF Writer 也不會再出新版了),那就是 Prawn,這是一套 pure Ruby 的 PDF Generator,內建支援 UTF-8,預計2009年中就會推出穩定的正式版。
  6. Full-Cycle Feature Development in Merb
    作者分享他使用 BDD 開發功能的流程:1. 點子 2. 用 Cucumber 寫出規格 3. 用 RSpec 寫 model specs
  7. Ruby Graphs and Java Monitoring with JRuby
    介紹如何使用 RMagick4J,一個 ImageMagick/RMagick 在 JRuby 上的實做品,以及搭配 Gruff 工具。下段介紹 Java Management Extensions (JMX)

  8. Easy Dependency Management for Git with Braid
    如何管理外部程式碼一直是個頭痛的問題,最常見的處理方式就是 copy 一份回來,但是萬一碰到自己有修改,加上這個套件升級了,就會很麻煩。在 Git 流行之前大家推薦用 Piston 來管理,不過現在又多了不少選擇:

    這篇文章介紹 braid 這套管理 vendor dependencies 版本的工具,支援 git 跟 svn。

    其他選擇可以參考這篇 Easy Git External Dependency Management with Giternal 所介紹的有 Tim Dysinger 的 rake tasks、37signal 的 cached_externals、Pat Maddox 的 giternal 等等,也許更適合你。

  9. Jump Start Credit Card Processing
    製作精美 PDF 介紹信用卡金流及 Active Merchant。看起來很棒可是台灣的金流公司都沒有… XD
  10. Dance in the Clouds with PoolParty
    PoolParty 是一套以雲端運算平台為目標的佈署工具,目前支援 Amazon EC2。
  11. HTML Scraping with scRUBYt! for Fun and Profit
    介紹 scRUBYt! 是一套基於 HpricotMechanize 的多功能 web scraping 工具。
  12. Life Beyond Code
    耶誕夜的這最後一篇連載跟技術不太有關係… XD

Ruby Advent 2008 摘要 (上)

Ruby Advent 2008 到耶誕節有一系列的 Ruby 連載:

  1. Simple Blog Engine in Ruby
    介紹 Scanty 這套由 Sinatra 做的 Blog 系統
  2. Deploying Ruby Apps with Passenger
  3. Passenger 其實不只支援 Rails,任何支援 Rack 的 web framework 都可以使用。

  4. Hoptoad for better Exception Notification

    Hoptoad之前有介紹過,是 ThoughtBot 出的網路服務,用來追蹤 Rails 的 exception notifications,最近也剛推出收費版支援 SSL。

  5. Cool as a Cucumber

    Cucumber 是一套基於 Rspec 的 Acceptance Testing Framework。這種驗收測試的作法是用純文字的方式把規格文件(feature documentation)寫出來,然後用這套工具來寫一個可以執行它(parse)它的測試程式。

  6. Machinist for your Test Data Factory

    因為 fixtures 實在不惹人喜愛,所以有些人改用工廠機制,例如 Factory Girl 這套 plugin 可以預先定義好資料形式,方便隨時建立出測試假資料。我的經驗是程式會漂亮不少,但代價是如果假資料量大的話,執行會花不少時間。

    而這裡介紹的 Machinist 也是概念類似的一套實作品(算是 Factory girl 的重新發明)。

  7. SOA with Merb?

    要做 REST calls 目前有幾種 library 可以用 Net::HTTP、RestClient、HTTParty 和 ActiveResource。其中 Net::HTTP 太基本了,而 ActiveReource 太肥不適合搭配 Merb,所以這裡推薦的是 RestClient

  8. Generating (Real) Fake Content

    開發網站的時候,常有要塞滿一些假資料來 Demo 的需求,這裡介紹了 Faker gem 可以產生假文字。

  9. A Simple Distributed Queue in Ruby

    使用 DRb 用九行 Ruby code 就實作出一個 Shared Queue。

  10. Git it done, Rubyists

    介紹 Git 跟一些 Ruby 工具,對 Git 還不太知道的朋友可以看看 Why Git is Better than X (有中文翻譯)

  11. Listening to Your Specs

    這篇長文蠻深入的講解 RSpec 的 BDD(Behavior-Driven Development) coding style。

  12. Thinking out of the Box with Enumerable#inject

    火力展示 Ruby Enumerable#inject 的進階用法,雖然我覺得還挺難懂的。

  13. Meet the Splat

    介紹 Ruby splat operator (也就是asterisk *) 的用法,可以將陣列展開成參數列。