1 사용법
template을 적용하려면 -m
옵션을 사용하여 적용하고자 하는 template의 위치를 Rails generator에 제공해야 합니다. 이는 파일 경로나 URL이 될 수 있습니다.
$ rails new blog -m ~/template.rb
$ rails new blog -m http://example.com/template.rb
app:template
rails 명령어를 사용하여 기존 Rails 애플리케이션에 template을 적용할 수 있습니다. template의 위치는 LOCATION 환경 변수를 통해 전달해야 합니다. 마찬가지로 이는 파일 경로나 URL이 될 수 있습니다.
$ bin/rails app:template LOCATION=~/template.rb
$ bin/rails app:template LOCATION=http://example.com/template.rb
2 Template API
Rails template API는 이해하기 쉽습니다. 다음은 일반적인 Rails template의 예시입니다:
# template.rb
generate(:scaffold, "person name:string")
route "root to: 'people#index'"
rails_command("db:migrate")
after_bundle do
git :init
git add: "."
git commit: %Q{ -m '최초 커밋' }
end
다음 섹션에서는 API가 제공하는 주요 메서드들을 설명합니다:
2.1 gem(*args)
생성된 애플리케이션의 Gemfile
에 제공된 gem을 위한 gem
항목을 추가합니다.
예를 들어, 애플리케이션이 bj
와 nokogiri
gem들에 의존성이 있다면:
gem "bj"
gem "nokogiri"
Gem을 추가할 때 이 메소드는 Gemfile
에만 gem을 추가하며, gem을 설치하지는 않는다는 점에 유의하세요.
정확한 버전을 지정할 수도 있습니다:
gem "nokogiri", "~> 1.16.4"
이는 nokogiri gem의 버전 1.16.4 또는 그 이후의 패치 레벨 릴리스를 사용하겠다는 의미입니다. 하지만 1.17.0과 같은 마이너 버전 변경은 하지 않습니다.
Gemfile
에 추가될 주석도 추가할 수 있습니다:
gem "nokogiri", "~> 1.16.4", comment: "XML 파싱을 위한 nokogiri gem 추가"
2.2 gem_group(*names, &block)
gem 항목들을 그룹으로 감싸줍니다.
예를 들어, rspec-rails
를 development
와 test
그룹에서만 로드하고 싶을 때:
gem_group :development, :test do
gem "rspec-rails"
end
2.3 add_source(source, options={}, &block)
생성된 애플리케이션의 Gemfile
에 주어진 source를 추가합니다.
예를 들어, gem을 "http://gems.github.com"
에서 가져와야 하는 경우:
add_source "http://gems.github.com"
gem 소스를 추가합니다
블록이 주어진 경우, 블록 내의 gem 항목들은 source 그룹으로 묶입니다.
add_source "http://gems.github.com/" do
gem "rspec-rails"
end
source를 추가할 때 블록을 사용하여 해당 source에서만 사용할 gem들을 지정할 수 있습니다.
2.4 environment/application(data=nil, options={}, &block)
config/application.rb
의 Application
클래스 내부에 한 줄을 추가합니다.
만약 options[:env]
가 지정되어 있다면, 해당 줄이 config/environments
의 해당하는 파일에 추가됩니다.
environment 'config.action_mailer.default_url_options = {host: "http://yourwebsite.example.com"}', env: "production"
data
인자 대신 block을 사용할 수 있습니다.
2.5 vendor/lib/file/initializer(filename, data = nil, &block)
생성된 애플리케이션의 config/initializers
디렉토리에 initializer를 추가합니다.
예를 들어 Object#not_nil?
와 Object#not_blank?
를 사용하고 싶다고 가정해봅시다:
initializer "bloatlol.rb", <<-CODE
class Object
def not_nil?
!nil?
end
def not_blank?
!blank?
end
end
CODE
비슷하게, lib()
는 lib/
디렉터리에 파일을 생성하고 vendor()
는 vendor/
디렉터리에 파일을 생성합니다.
심지어 file()
도 있는데, 이는 Rails.root
로부터의 상대 경로를 받아 필요한 모든 디렉터리/파일들을 생성합니다:
file "app/components/foo.rb", <<-CODE
class Foo
end
CODE
app/components
디렉터리를 생성하고 그 안에 foo.rb
를 넣을 것입니다.
2.6 rakefile(filename, data = nil, &block)
lib/tasks
아래에 지정된 task들을 포함하는 새로운 rake 파일을 생성합니다:
rakefile("bootstrap.rake") do
<<-TASK
namespace :boot do
task :strap do
puts "난 부츠가 좋아!"
end
end
TASK
end
위 작업은 boot:strap
rake 태스크를 가진 lib/tasks/bootstrap.rake
파일을 생성합니다.
2.7 generate(what, *args)
주어진 인자와 함께 지정된 rails generator를 실행합니다.
generate(:scaffold, "person", "name:string", "address:text", "age:number")
2.8 run(command)
임의의 명령어를 실행합니다. backtick과 동일하게 동작합니다. 예를 들어 README.rdoc
파일을 제거하고 싶다면 다음과 같이 합니다:
run "rm README.rdoc"
README.rdoc
파일을 삭제합니다.
2.9 rails_command(command, options = {})
Rails 애플리케이션에서 제공된 명령어를 실행합니다. 예를 들어 데이터베이스를 마이그레이션하고 싶다고 해봅시다:
rails_command "db:migrate"
다른 Rails environment로도 명령을 실행할 수 있습니다:
rails_command "db:migrate", env: "production"
```를 통해 production 환경에서 데이터베이스 마이그레이션을 실행합니다.
명령어를 super-user로 실행할 수도 있습니다:
```ruby
rails_command "log:clear", sudo: true
실패시 애플리케이션 생성이 중단되어야 하는 명령어를 실행할 수도 있습니다:
rails_command "db:migrate", abort_on_failure: true
실패시 중단(abort)하도록 설정하여 rails_command "db:migrate"를 실행합니다.
2.10 route(routing_code)
config/routes.rb
파일에 라우팅 항목을 추가합니다. 위의 단계에서 우리는 person scaffold를 생성하고 README.rdoc
를 제거했습니다. 이제 PeopleController#index
를 애플리케이션의 기본 페이지로 만들기 위해:
route "root to: 'person#index'"
```을 라우트 파일에 추가합니다. 이는 애플리케이션의 루트("/")를 person 컨트롤러의 index 액션으로 매핑합니다.
### inside(dir)
주어진 디렉토리에서 명령어를 실행할 수 있게 합니다. 예를 들어, 새로운 앱에서 심볼릭 링크를 걸고 싶은 edge rails의 복사본이 있다면 다음과 같이 할 수 있습니다:
```ruby
"vendor" 내부에서 다음을 실행합니다:
run "ln -s ~/commit-rails/rails rails"
end
2.11 ask(question)
ask()
는 사용자로부터 피드백을 받아 템플릿에서 활용할 수 있는 기회를 제공합니다. 예를 들어 새로 추가하는 멋진 라이브러리의 이름을 사용자가 지정하도록 하고 싶다고 가정해보겠습니다:
lib_name = ask("반짜반짜한 library의 이름을 무엇으로 하시겠습니까?")
lib_name << ".rb" unless lib_name.index(".rb")
lib lib_name, <<-CODE
class Shiny
end
CODE
2.12 yes?(question) 또는 no?(question)
이 메소드들은 템플릿에서 사용자에게 질문하고 사용자의 답변에 따라 흐름을 결정할 수 있게 합니다. 예를 들어 사용자에게 migration을 실행할지 물어보고 싶다면:
yes?("데이터베이스 마이그레이션을 실행하시겠습니까?")의 응답이 참이면 rails_command("db:migrate")를 실행합니다.
# no?(question)는 정반대로 동작합니다.
2.13 git(:command)
Rails templates를 사용하면 어떤 git 명령어도 실행할 수 있습니다:
git :init
git add: "."
git commit: "-a -m '최초 커밋'"
2.14 after_bundle(&block)
gem들이 bundle되고 binstub들이 생성된 후에 실행될 callback을 등록합니다. 생성된 파일들을 버전 관리에 추가할 때 유용합니다:
after_bundle do
git :init
git add: "."
git commit: "-a -m '최초 커밋'"
end
Rails::Generators::AppGenerator 인스턴스 컨텍스트에서 애플리케이션 템플릿이 평가됩니다. Thor가 제공하는 apply
액션을 사용합니다.
--skip-bundle
옵션이 전달되어도 콜백들은 실행됩니다.
3 고급 사용법
이것은 필요에 따라 인스턴스를 확장하고 변경할 수 있다는 것을 의미합니다.
예를 들어 source_paths
메서드를 오버라이드하여 템플릿의 위치를 포함하도록 할 수 있습니다. 이제 copy_file
과 같은 메서드가 템플릿 위치에 대한 상대 경로를 허용합니다.
def source_paths
[__dir__]
end
소스 경로를 설정합니다.