바다가 아름다운 작은 시골 마을. 밴트리.

아침 일찍 집에서 나와 버스터미널로 갑니다.
일기예보에선 날씨가 아주 화창하다고 허세를 부리지만,
그런 격장지계에 넘어가 홀딱 젖기는 싫어 우비도 챙겨 나왔지요.
코크 버스터미널에서 236번 버스를 타고 한참을 갑니다.
조그만 마을 몇을 거쳐 밴트리로 가는 길.
갑자기 먹구름이 몰려와 비를 쏟아 부었으나,
목적지에 도착하자 날씨가 갭니다.
운이 좋아요.
근데 일요일이라 그런지 여행자 정보 센터는 문을 닫았네요.
뭐 조그마한 동네라 굳이 지도가 필요 없긴 해요.
우선 마을을 한 바퀴 쓱 돌아봅니다.

멀리 보이는 놀이기구-'Bantry, Co Cork Ireland'

저 멀리 놀이기구가 보이네요.
집 근처의 월미랜드가 생각납니다.
어릴 때 가서 많이 놀았는데 말이에요.
그곳을 찾은 지도 오래되었군요.
한국에 가면 한번 들러봐야겠습니다.

밴트리 하우스-'Bantry, Co Cork Ireland'

바닷가를 따라 쭉 걸어가면 정원을 잘 가꿔놓은 밴트리 하우스가 보입니다.
아기자기해요.
100계단을 올라가 내려다보는 바닷가 풍경이 썩 괜찮습니다.
밴트리 하우스엔 조그마한 카페도 하나 있는데,
음료와 간식거리를 팔아요.
비가 많이 내린다면, 카페 앞 테라스의 푹신한 의자에 앉아 잠시 비를 피하는 것도 좋겠지요.

수제 다크 초콜릿-'Bantry, Co Cork Ireland'

이 카페에서 파는 초콜릿이 꽤 맛납니다.
카카오가 70%라서 그리 진하진 않지만 달짝지근한 게 괜찮아요.

맑은 날씨의 바닷가-'Bantry, Co Cork Ireland'

자. 이제 밴트리 하우스를 나와 해변을 따라 쭉 걷습니다.
아.
이런 날씨라니.
하늘만 바라봐도 기분이 좋네요.

온통 푸른 풍경-'Bantry, Co Cork Ireland'

바닷가에 앉아 짭짤한 공기를 마음껏 들이마셨습니다.
물수제비를 뜨기 좋은 납작한 돌멩이가 여럿 보이는군요.
적당한 녀석을 골라 던져 보았지만 한 두 번 튀기고 물속으로 가라앉습니다.
푸른 바다가 그 돌을 감싸고 어디론가 데려가겠지요?
저도 이곳의 푸른 기운에 이끌려 이리저리 발걸음을 옮겼습니다.
아름다운 하루에요.



by


Tags : , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

Web application development References


ISO-639-1


Official languages of the United Nations

  • Arabic
  • Chinese (Mandarin)
  • English
  • French
  • Russian
  • Spanish

CLDR

Unicode Common Locale Data Repository

터미널 한글 설정

windows cmd - chcp 65001
linux shell - export LC_ALL=ko_KR.UTF-8


구글 맵스 지도 검색

https://maps.google.com/?q=이름@위도,경도

구글 정의 검색

define:something

Protocol SPDY

http://www.chromium.org/spdy

MongoDB

사용자추가 스키마생성 DB삭제

mongod 를 기동할 때는 --auth 옵션을 추가해야 함
mongoDB는 system영역 내에서 admin이라는 DB관리를 위한 스키마를 가짐
>use admin // admin DB 사용
>db.addUser('name','pswd') // 사용자 추가
>use newDB => 해당 디비가 없으면, 새로운 디비를 생성함
   mysql의 스키마 생성과 같음
>db.collectionName.drop() => 해당 collection을 삭제함
   mysql의 DROP TABLE과 같음

Mongodb eclipse

log path configuration

"C:\data\mongodb-xxxxxxxxx\bin\mongod" --service  --logpath  c:\data\test.log

import

mongoimport --host localhost --db myapp_development --collection my_collection --type csv --file C:\dev\data\test.csv --headerline --upsert

regex

mongodb regex = '^[work|accus*|planet]'
MongoDB can only use indexes on Regular Expression searches that are front (^) anchored.
RegEx searches that front-anchor and then use a wildcard query like .* will use the index for as much of the un-wildcarded area as it can before scanning --- i.e., ^foo.* will run a partial scan.


Mysql

mysql backup and restore


mysqldump -uUSER -pPASSWORD -hHOST DB > ./filename.sql
mysql -uUSER -pPASSWORD -hHOST DB < ./filename.sql

MySQL index

What should be indexed?
–All attributes where you JOIN
–All attributes where you filter (WHERE)
–All attributes where you ORDER or GROUP BY
–All attributes where you want to do an Index Scaninstead of a Table scan.
–NOT on attributes with an evenly distributed lowcardinality.
•How should be indexed?
–Indexes can only be used from left to right.
–Keep them short.
–Compound indexes: INDEX(a, b).
–Prefixed indexes: INDEX(a, b(10)).
–Do not function-cover indexed attributes

http://www.scribd.com/doc/80792061/MySQL-Performance-Tuning

MySQL Date and Time Functions


Mysql 동일 테이블에서 여러 필드 값의 합 쿼리

//쿼리1 보다 쿼리2가 두 배 이상 빠르다. 단, 하나의 칼럼 갯수를 구할 땐 where절과 count(*)를 쓰는 것이 더 빠르다.
//쿼리1
select sum(cnt) from (
    select count(*) as cnt from `my_table` WHERE `field_x` =1
    union all
    select count(*) as cnt from `my_table` WHERE `field_y` =1
    union all
    select count(*) as cnt from `my_table` WHERE `field_z` =1
) as cnt_all
//쿼리2
SELECT
(SUM(IF(`field_x` = 1,1,0)) +   
    SUM(IF(`field_y` = 1,1,0)) +
    SUM(IF(`field_z` = 1,1,0))) as cnt_all
FROM `my_table`
WHERE 1


firefox - keyword.url

http://www.google.co.kr/search?num=50&hl=ko&lr=&newwindow=1&tbo=1&as_qdr=all&aq=f&aqi=&aql=&oq=&gs_rfai=&ie=UTF-8&oe=UTF-8&sourceid=navclient&gfns=1&q=

리눅스 crontab

crontab -l

CSS FONT BASE-64

/* Fonts as files */
@font-face {
    font-family: 'MyFontFamily';
    src: url('myfont-webfont.eot?') format('eot'),
         url('myfont-webfont.woff') format('woff'),
         url('myfont-webfont.ttf')  format('truetype'),
         url('myfont-webfont.svg#svgFontName') format('svg');
    }
/* Fonts as data uris */
@font-face {
    font-family: 'MyFontFamily';
    src: url('myfont-webfont.eot?') format('embedded-opentype');
    }
   
@font-face {
    font-family: 'MyFontFamily';
         url(data:font/truetype;charset=utf-8;base64,BASE64_ENCODED_DATA_HERE)  format('truetype'),
         url(data:font/woff;charset=utf-8;base64,BASE64_ENCODED_DATA_HERE)  format('woff'),
         url('myfont-webfont.svg#svgFontName') format('svg');
    }


CSS Sticky windows

    .outer {
        width:200px;
        height:600px;
        background-color:red;
        margin:0 auto;
    }
    .inner {
        width:50px;
        border:1px solid white;
        position:fixed;
    }
 


Insert the word (image) into the alt text of an image that hasn’t loaded In Firefox

img:after   { content:" (image)"; }
img::after  { content:" (image)"; } /* New CSS3 standard notation */


FYI

References and Articles

빠른 웹 개발

도구


출처

  • 직접 작성
  • google 검색



by


Tags : , , , , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

Ruby Gems Cheat Sheet


GEM 설정

gem environment
set GEM_PATH = D:\dev\ruby192\lib\ruby\gems\1.9.1\gems
gem update --system
gem uninstall gemname
bundle update
(vendor 폴더에 bundle 설치하기)
bundle install --path vendor/bundle


devise

Controller filters and helpers

Devise will create some helpers to use inside your controllers and views. To set up a controller with user authentication, just add this before_filter:
before_filter :authenticate_user!
To verify if a user is signed in, use the following helper:
user_signed_in?
For the current signed-in user, this helper is available:
current_user
You can access the session for this scope:
user_session
Callbacks
    after_set_user
    after_authentication
    before_failure
    before_logout
    Warden::Manager.after_authentication do |user,auth,opts|
        user.last_login = Time.now
    end
   

generator

devise g view with haml
rails g devise_views -t=haml

OmniAuth

Add :password => Devise.friendly_token[0,20] when creating a new user from facebook omniauth.

Passwords Encrypt manually


Assuming you have a mysql database with a "users" table and a "password" column And an ActiveRecord model class called "user" that is hooked up to devise
Create an ActiveRecord model class in your app app/models/old_user.rb
OldUser < ActiveRecord::Base
  set_table :users
  establish_connection :database => "old_database", :user => "old user", :adapter => "mysql"
end
then create a rake task: app/lib/tasks/migrate_users.rake
task :migrate_users => :environment do
  OldUser.find_each do |old_user|
    u = User.new(:email => old_user.email, :password => old_user.password, :password_confirmation => old_user.password);
    #if your using confirmation
    u.skip_confirmation!
    u.save!
  end
end
Modify as necessary (make sure you're saving any app-specific user attributes)
Then$ rake migrate_users
   
Good news and bad news.
Good news:
The following works to create your user's password manually.
 pepper = nil
 cost = 10
 encrypted_password = ::BCrypt::Password.create("#{password}#{pepper}", :cost => cost).to_s
You can find your pepper and cost in your devise initializer. This method was confirmed using Devise's "valid_password?" method.
Bad news:
The entire reason I was trying to avoid "User.new(password: password).encrypted_password" was because of speed. It's terribly slow. With all my other pieces of my import task, I've intentionally avoided this.
But as it turns out, the major cost here is not instantiating a User object -- but BCrypt itself. There is very little noticeable speed boost when using BCrypt directly because it's intentionally designed to be slow.
My final answer: suck it up, run the rake script, go find a beverage.

mailer locale configuration

-ActionMailer::Base.default_url_options[:locale] = I18n.locale


Simple_form

<%= simple_form_for(@user, :builder => CustomBuilder) do |f| %>
  <%= f.input :name %>
<% end %>


Client side validations

Client side validations Registering own form builder
https://github.com/bcardarella/client_side_validations/wiki/Registering-your-own-custom-form-builder


Client MVC

Spine

Important is only that the public directory of the application is specified
as domainroot in Confixx. If the domain is called Passenger will start automatically.."
rails g spine:model Card text is_private order user_id card_type
rails g spine:controller Cards
rails g spine:scaffold card text is_private order user_id card_type
rails g spine:model Organization title description url image admins members followers
rails g spine:controller Organizations
rails g spine:scaffold organization title description url image admins members followers
var card = App.Card.create({ 
  is_private: true,
  order: 0,
  card_type: 'Reason',
  text: 'Spine & Rails, sitting in a tree!'
});
straightforward way to do that without extending Spine Model's
to allow for instances to be added in memory without syncing
Ajax.disable -> saveStuff()
Model.refresh()
extends
Contact.extend(Spine.Model.Ajax);
Contact.extend({
url: '/users/'
});
'/': ->
    if AuthenticatedUser
         @controller = new OtherController
         @replace @controller.render()
    else
         @controller = new LoginController
         @replace @controller.render()
http://spinejs.com/docs/controller_patterns         
         


Compass

compass init rails D:/dev/workspace/baksisi
compass init rails -r html5-boilerplate -u html5-boilerplate --syntax sass --force
css와 javascript를 asset 폴더로 옮겨준다. rails.js는 제외 (jquery_ujs와 동일하다)


Geo_location

https://github.com/chrisyour/geo_location
http://www.maxmind.com/app/geolitecountry


Mongoid id 변경하기

http://blog.joshdzielak.com/blog/2011/12/24/tame-the-mongoid-id-field-in-your-rails-and-backbone-js-app/
http://lostechies.com/derickbailey/2011/06/17/making-mongoid-play-nice-with-backbone-js/


Mongoid Follow unfollow

class User
  include Mongoid::Document
  field :name, type: String
  has_and_belongs_to_many :following, class_name: 'User', inverse_of: :followers, autosave: true
  has_and_belongs_to_many :followers, class_name: 'User', inverse_of: :following
  def follow!(user)
    if self.id != user.id && !self.following.include?(user)
      self.following << user
    end
  end
  def unfollow!(user)
    !self.following.include?(user)
    self.following.delete(user)
  end    
end
relation_ids instead? that is self.member_count = self.member_ids.size
self.challenged.where(_id: event.id).destroy_all
def unchallenge!(announce)
  self.announcements.destroy_all( conditions: { _id: announce.id })
  self.save!
end
Finally I successfully deleted the relation using self.challenged_ids.delete(event.id)
validates_inclusion_of :foo, in: [['foo'], ['bar']]


Mongoid polymorphic behaviour

When a child embedded document can belong to more than one type of parent document, you can tell Mongoid to support this by adding the as option to the definition on the parents, and the polymorphic option on the child.
class Doctor
  include Mongoid::Document
  embeds_one :name, as: :namable
end
class Nurse
  include Mongoid::Document
  embeds_one :name, as: :namable
end
class Name
  include Mongoid::Document
  embedded_in :namable, polymorphic: true
end


TEST

Cucumber

rails g cucumber:install ?capybara ?rspec
  ruby script/rails generate cucumber:feature user email:string password:string confirm_password:string name:string nickname:string gender:integer location_name:string location:integer email_is_priavate:boolean name_is_private:boolean danted:boolean description:string
  ruby script/rails generate scaffold post title:string body:text published:boolean
  rake db:migrate
  rake cucumber


Cucumber Errors Handling

If SystemStackError: stack level too deep 
Then add gem "rspec", ">= 2.6.0.rc2", :group => [:development, :test] to Gemfile


Cucumber & Capybara Ajax

sleep second
page.driver.browser.execute_script %Q{ $('.ui-menu-item a:contains("#{link_text}")').trigger("mouseenter").click(); }
Clicking any element with Cucumber and Capybara
class Capybara::XPath
  class << self
    def element(locator)
      append("//*[normalize-space(text())=#{s(locator)}]")
    end
  end
end
When 'I click "$locator"' do |locator|
  msg = "No element found with the content of '#{locator}'"
  locate(:xpath, Capybara::XPath.element(locator), msg).click
end
The step looks for any element with the given text. Here it is in use:
Scenario: Creating an item
  Given I am signed in as "brandon@example.com"
   When I click "Add to your list"
    And I fill in "Description" with "blog about clicking any element"
    And I press enter
   Then I should see "The item was added to your list"
    And I should see "blog about clicking any element"
   


Cucumber Capybara

selenium chrome driver
https://github.com/jnicklas/capybara
http://code.google.com/p/chromium/downloads/list
http://code.google.com/p/selenium/wiki/ChromeDriver#Overriding_the_Chrome_binary_location
Capybara.register_driver :selenium_with_firebug do |app|
  Capybara::Driver::Selenium
  profile = Selenium::WebDriver::Firefox::Profile.new
  profile.add_extension(File.expand_path("features/support/firebug-1.6.0-fx.xpi"))
  Capybara::Driver::Selenium.new(app, { :browser => :firefox, :profile => profile })
end
Before("@selenium_with_firebug") do
  Capybara.current_driver = :selenium_with_firebug
end


I18n

I18n-js initialize

layout/application.html.haml
- html_tag :class => 'no-js', :lang => "#{I18n.locale}"
applcation.js
I18n.default_locale = "en"
I18n.locale = $($("html")[0]).prop("lang")
I18n.fallbacks = true


Media - Flickraw

    flickr.upload_photo(params[:photo].tempfile.path)


Gem Trouble shooting

Q. `require': no such file to load -- thin (LoadError)
A. => Add gem 'thin' to Gemfile


Rails Performance

  • Curb for Http (libcurl)
  • Yajl, the fastest JSON library.
  • excon #=> faster http
  • Nokogiri, the fastest XML library.
  • Snappy, super fast compression tool by google.
  • fast_xs
  • Memcache. (libmemcached)
  • use Ree Garbage Collector

Fastest Server

  • Unicorn
  • Thin

Profiling Tools

  • NewRelic - Monitoring Tool (Commercial)
  • Ganglia - Monitoring Tool (OpenSource)
  • Cloudflare - Performance & Security
  • rack-perftools

Rack-bug

1. Install rack-bug (branch rails3) as plugin
cd vendor/plugins
git clone -b rails3 https://github.com/brynary/rack-bug.git
If you want to you it as gem then add following line into Gemfile
gem 'rack-bug', :git => 'https://github.com/brynary/rack-bug.git', :branch => 'rails3'
2. Replace the code from file actionview_extension.rb
which is avilable in vendor/plugins/rack-bug/lib/rack/bug/panels/templates_panel/ as specified in bug of rack_bug repository
if defined?(ActionView) && defined?(ActionView::Template)
ActionView::Template.class_eval do
def render_with_rack_bug(*args, &block)
Rack::Bug::TemplatesPanel.record(virtual_path) do
render_without_rack_bug(*args, &block)
end
end
alias_method_chain :render, :rack_bug
end
end
If you are using gem override the specified file in some way
3. Add following lines into your config.ru
require 'rack/bug'
use Rack::Bug, :secret_key => "someverylongandveryhardtoguesspreferablyrandomstring"
run myapp
4. Start your server and access the URL http://your_app/__rack_bug__/bookmarklet.html
and enter the password.
http://blog.railsupgrade.com/2011/04/configure-rack-bug-for-rails-3.html


출처



by


Tags : , , , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

Ruby on Rails Cheat Sheet


rails 데이터 타입

:string, :text, :integer, :float, :decimal, :datetime, :timestamp, :time, :date, :binary, :boolean

Rails Mimetype   

"./."                      => :all
"text/plain"               => :text
"text/html"                => :html
"application/xhtml+xml"    => :html
"text/javascript"          => :js
"application/javascript"   => :js
"application/x-javascript" => :js
"text/calendar"            => :ics  
"text/csv"                 => :csv  
"application/xml"          => :xml
"text/xml"                 => :xml
"application/x-xml"        => :xml
"text/yaml"                => :yaml
"application/x-yaml"       => :yaml
"application/rss+xml"      => :rss  
"application/atom+xml"     => :atom 
"application/json"         => :json
"text/x-json"              => :json

bundle asset precompile

bundle exec rake assets:precompile RAILS_ENV="production"
rake assets:clean< add below code if you want development environment with out precompile config.serve.static.assets = false application.rb use Bundler.require(:default, :assets, Rails.env) instead of Bundler.require(*Rails.groups(:assets => %w(development test)))

compile assets locally

Put below into development.rb
config.assets.prefix = "/temp-assets"
Also put below into application.rb
config.assets.initialize.on.precompile = false

rails logger

Rails.logger.info "My info message"
Rails.logger.debug "My debugging message"
Rails.logger.warn "My warning message"

Environment Log level

config.log_level = :debug, :info, :warn, :error, and :fatal

Validation text length CR filter

before.validation :replace.cr
  protected
  def replace.cr
    if self.description.changed?
      self.description.gsub!(/\r\n?/, "\n")
    end
  end

validation locale


// config/locales/en.yml
en:
  activerecord:
    attributes:
      user:
        email: "E-mail address"
    errors:
      models:
        user:
          attributes:
            email:
              blank: "is required"
If you are using mongoid, replace activerecord: with mongoid:

Validate associated

The answer to this turned out to be rather simple. On the parent model, you simply explicitly declare that you want the associated children validated.
parent.rb
validates_associated :children

Validate if persisted? or new_record?

validates.uniqueness.of :nickname, :message => I18n.t("user.already.taken"), :if => :new.record?
validates.uniqueness.of :nickname, :message => I18n.t("user.already_taken"), :unless => :persisted?

Session Store in rails 3

Use the database for sessions instead of the cookie-based default, which shouldn't be used to store highly confidential information
Create the session table with
rake db:sessions:create
Run the migration
rake db:migrate
Make sure you also tell rails to use ActiveRecord to manage your sessions too.
Rails 3
config/initializers/session.store.rb:
Rails.application.config.session.store :active.record.store

DB Migrate Production

rake db:migrate RAILS_ENV="production"

get rails environment

Rails.env
env["SERVER_NAME"]

rails template

rake print --silent RECIPES=jquery,haml,rspec,cucumber,guard,mongoid,action.mailer,devise,add.user,home.page,home.page.users,seed.database,users.page,css.setup,application.layout,html5,navigation,cleanup,ban.spiders,extras,git,compass,omniauth,omniauth.email,backbone > ~/Desktop/backbone.template.txt
Could you please run it again using the "-T -O -J" flags? As in
rails new template_test -m https://github.com/fortuity/rails3-application-templates/raw/master/rails3-mongoid-devise-template.rb -T -O -J
http://blog.dominicsayers.com/2011/08/16/howto-use-a-rails-template-from-github-on-windows/

thin start

D:\dev\ruby192\bin\ruby.exe -e $stdout.sync=true;$stderr.sync=true;load($0=ARGV.shift) D:/dev/workspace/baksisi/script/rails server thin -b 127.0.0.1 -p 3002 -e development
ruby ./script/rails server thin -b smoke-free-online.de -p 3000 -e development -d
thin start

Middle Man

"server" was called incorrectly. Call as "middleman server [-p 4567] [-e development]".
"middleman server [-p 4567] [-e development]" instead of "middleman server -p 4567 -e development

DB migration

Rails g migration change.data.type.for.table_column

I18n

locale join

config/application.rb
config.i18n.load_path += Dir[Rails.root.join('config', 'locales', '.*', '..{rb,yml}')]

locale path

routes.rb
  match '/:locale' => "home#index"
  root :to => "home#index"
  scope "/:locale" do   
    controller :models do
      something
    end
    resources :models, :only => :show
ApplicationController
  def default.url.options(options = {})
    options.merge!({:locale => I18n.locale})
  end   

Localize

I18n.l Time.now, :format => :short,  :locale => :"ko"

Pluralization

ko:
  pears:
    zero: ko.zero
    one: ko.one
    few: ko.few
    other: ko.other

generate rake tasks

rails g task namespace task1 task2
rake -T | grep namespace

세션 저장

config.session.store :cookie.store, :key => '.baksisi.session', :domain => :all
environment.rb 메일러에 레이아웃을 지정하고 싶다면.
DeviseMailer.layout "OMG"

show routes

rake routes

SASS

config/application.rb:
config.generators.stylesheet_engine = :sass
sass-convert style.sass style.scss

Trouble Shootings

uninitialized constant

file name confirm (if file name capital, it can be occurred.)

guard-livereload error

gem install eventmachine --pre 

open-uri.rb file in C:/Ruby1.9.2/lib/ruby/1.9.1/ (of course your path might be different).

http.verify.mode = options[:ssl.verify.mode] || OpenSSL::SSL::VERIFY.NONE

[ERROR] V8 is no longer usable

ulimit -v unlimited  

CSV Data Handling

http://www.ruby-doc.org/stdlib-1.9.2/libdoc/csv/rdoc/CSV.html

get action information at view

    params[:action]

HAML

rails helper using haml
 
def section(name)
haml.tag(:div, :class => 'section') do
  haml.tag(:h2, name)
  haml.tag(:p, :class => 'section.content') do
    yield
  end
end
end
      
def content.box
  haml.tag :div, :class => "holder" do
    haml.tag :div, :class => "top"
    haml.tag :div, :class => "content" do
      yield
    haml.tag :div, :class => "bottom"
  end
end
and in haml
%html
  %head
  %body
    Maybee some content here.
    - content.box do
      Content that goes in the content_box like news or stuff      
     
fields_for with index
<% @questions.each.with.index do |question,index| %>
    <% f.fields.for :questions, question do |fq| %> 
        # here you have both the 'question' object and the current 'index'
    <% end %>
<% end %>
It’s also possible to specify the instance to be used:
<%= form.for @person do |person.form| %>
...
<% @person.projects.each do |project| %>
  <% if project.active? %>
    <%= person.form.fields.for :projects, project do |project.fields| %>
      Name: <%= project.fields.text_field :name %>
    <% end %>
  <% end %>
<% end %>
<% end %>     

Rails Response

namespace "api" do
  resources :regions, :defaults => { :format => 'xml' }
end
Then you should be able to have the following work for your controller methods:
class Api::RegionsController < ApplicationController
  respond.to :xml, :json
  def index
    respond.with(@regions = Region.all)
  end
end
rescue.from  ActionController::MissingFile do |e|
  # User's browser probably wont display this
  # Content-Type is application/x-shockwave-flash
  render :file => File.join(Rails.public.path, '404.html'), :status => 404
end

show details or stream video

def show
  @media = Media.find params[:id]
  respond.to do |format|
    format.html
    format.flv { send.file @media.path, :disposition => 'inline' }
  end
end
render :file => File.join(Rails.public.path, '404.html'), :status => 404, :content.type => 'text/html'

render with variable

render :partial => "my/conejo", :locals => {:my.val => something}
render "my/liebre", :my.val => something

scope

default_scope order('id DESC')
Model.reorder('')
Model.unscoped

render an other action in the controller, in js.

  render 'result', :id => @item.id, :format => :js
 

layout xhr? 

  class ApplicationController < ActionController::Base
  layout proc{|c| c.request.xhr? ? false : "application" }
  end
  layout :layout.xhr?
  def layout.xhr?
    request.xhr? ? false : 'application'
  end
 

AJAX Performance stale? and touch


 def show
    @list_item = @list.list_items.find( params[ :id ] )
    if stale?( :etag => @list_item, :last_modified => @list_item.updated_at.utc, :public => true )
      respond_with( @list_item )
    end
  end
  Also instead of the update_list method being called from after_save/destroy you can pass :touch => true to the belongs_to association which will do the same

AJAX Handler - ?xhr

respond_with( @something, :layout => !request.xhr? )
or
respond_to do |wants|
  wants.html do
    if request.xhr?
      render :partial => "items"
    else
      render
    end
  end
end

Asset

exist

YourApp::Application.assets.find_asset("#{asset}.file").nil?

### pathname

<YourAppName>::Application.assets.find_asset('Rails.png').pathname

absolute asset_path in view using helper

"#{request.protocol}#{request.host.with.port}#{asset.path('person/gravatar.default.png')}"
"#{request.scheme}://#{request.host.with.port}#{request.script_name}"

Mailer

config

environment/production.rb
  config.action.mailer.default.url.options = {:host => 'localhost:3000',:locale =>I18n.locale}
  config.action.mailer.smtp.settings = {
    :address              => "server.addr",
    :port                 => 587,
    :domain               => "sever.domain",
    :user.name            => "user.name",
    :password             => "user.password",
    :authentication       => "plain",
    :enable.starttls.auto => true
  } 
  config.action.mailer.delivery.method = :smtp
  config.action.mailer.perform.deliveries = true
  config.action.mailer.raise.delivery.errors = false
  config.action.mailer.default :charset => "utf-8"

inline attachement

in mailer

attachments.inline['blank'] = {
    :data => File.read("#{Rails.root.to.s + '/app/assets/images/blank.png'}"),
    :mime.type => "image/png",
    :encoding => "base64"
}

in view

if @offer.image.nil?
  = image.tag( attachments['blank'].url, :id => 'attachement.image', :width => "400", :height => "400")
 

validates in I18n

%{attribute} - field name
%{model} - model name 
%{count} - count


rescue log

begin
  ...some code...
rescue Exception => e
  logger.error e.message
 

Ruby

Iterate

a.each.with.index do |item, index|
  puts item, b[index]
end
array.each.slice(3) do |elements|
  fire.the_event
end

Timezone

in client (js):
function set.time.zone.offset() {
    var current.time = new Date();
    $.cookie('time.zone', current.time.getTimezoneOffset());
}
in Application Controller:
before.filter :set.timezone
def set.timezone 
 min = request.cookies["time.zone"].to_i
 Time.zone = ActiveSupport::TimeZone[-min.minutes]
end

DateTime format

  %a - The abbreviated weekday name (Sun)
&nbsp; %A - The&nbsp; full&nbsp; weekday&nbsp; name (Sunday)
  %b - The abbreviated month name (Jan)
&nbsp; %B - The&nbsp; full&nbsp; month&nbsp; name (January)
  %c - The preferred local date and time representation
  %d - Day of the month (01..31)
  %H - Hour of the day, 24-hour clock (00..23)
  %I - Hour of the day, 12-hour clock (01..12)
  %j - Day of the year (001..366)
  %m - Month of the year (01..12)
  %M - Minute of the hour (00..59)
  %p - Meridian indicator (AM&nbsp; or&nbsp;PM)
  %S - Second of the minute (00..60)
  %U - Week  number  of the current year,
          starting with the first Sunday as the first
          day of the first week (00..53)
  %W - Week  number  of the current year,
          starting with the first Monday as the first
          day of the first week (00..53)
  %w - Day of the week (Sunday is 0, 0..6)
  %x - Preferred representation for the date alone, no time
  %X - Preferred representation for the time alone, no date
  %y - Year without a century (00..99)
  %Y - Year with century
  %Z - Time zone name
  %% - Literal ``%'' character
   t = Time.now
   t.strftime("Printed on %m/%d/%Y")   #=> "Printed on 04/09/2003"
   t.strftime("at %I:%M%p")            #=> "at 08:56AM"
  
   datetime seconds, hours, days, weeks, months, and years
  
    Add below lines to one of your initializer files, e.g., config/environment.rb:
    DateTime::DATE.FORMATS[:short]="short %Y-%m-%d %H:%M:%S"
    Time::DATE.FORMATS[:short] = "short %Y-%m-%d %H:%M:%S"
    Date::DATE.FORMATS[:short] = "short %Y-%m-%d"
    modify view:
    <%= item.create_date.to_s(:short) %>
distance_of_time_in_words(from_time, to_time = 0, include_seconds = false, options = {})
today = DateTime.now
=> #<DateTime: 441799066630193/180000000,-301/1440,2299161>
birthday = Date.new(2008, 4, 10)
=> #<Date: 4909133/2,0,2299161>
days_to_go = birthday - today
time_until = birthday - today
=> Rational(22903369807, 180000000)
time_until.to_i             # get the number of days until my birthday
=> 127
hours,minutes,seconds,frac = Date.day_fraction.to_time(time_until)
[3053, 46, 57, Rational(1057, 180000000)]
- mm  = (now-la    st_cigarette).divmod(Rational(1, 1440))[0]
- past.days = mm / 1440
- past.hours = (mm % 1440) / 60
- past_minutes = mm % 60

timezone

def set_api_time_zone
  utc_offset = current.user.session && current.user.session.user ? current.user.session.user.time.zone.offset.to.i.minutes : 0
  user.timezone = ActiveSupport::TimeZone[utc.offset]
  Time.zone = user.timezone if user.timezone
  Time.zone.today
  Time.now.to.date
    # => Thu, 19 May 2011
  Time.now.in.time.zone('Melbourne').to_date
    # => Fri, 20 May 2011
end

Range step

range.step(2) {|x| puts x}


benchmark

require 'benchmark'
n = 1000000
def answer1 current.subdomain
  case current.subdomain
  when 'www', 'blog', 'foo', 'bar'
  else nil
  end
end
def answer2 current.subdomain
  nil unless  ["www", "blog", "foo", "bar"].include?(current.subdomain)
end
Benchmark.bmbm do |b|
  b.report('answer1'){n.times{answer1('bar')}}
  b.report('answer2'){n.times{answer2('bar')}}
end
Rehearsal -------------------------------------------
answer1   0.290000   0.000000   0.290000 (  0.286367)
answer2   1.170000   0.000000   1.170000 (  1.175492)
---------------------------------- total: 1.460000sec
              user     system      total        real
answer1   0.290000   0.000000   0.290000 (  0.282610)
answer2   1.180000   0.000000   1.180000 (  1.186130)
Benchmark.bmbm do |b|
  b.report('answer1'){n.times{answer1('hello')}}
  b.report('answer2'){n.times{answer2('hello')}}
end
Rehearsal -------------------------------------------
answer1   0.250000   0.000000   0.250000 (  0.252618)
answer2   1.100000   0.000000   1.100000 (  1.091571)
---------------------------------- total: 1.350000sec
              user     system      total        real
answer1   0.250000   0.000000   0.250000 (  0.251833)
answer2   1.090000   0.000000   1.090000 (  1.090418)


출처




by


Tags : , , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

도심 속에서 만나는 자연. 골웨이 남쪽 바닷가 산책.

바다 건너 편-'골웨이 바닷가 산책'

골웨이 남쪽의 울페톤 다리(Wolfe tone Bridge)를 지나 클라다 길(Claddagh Quay)을 따라 걸으면,
멋진 바닷가 풍경이 나타납니다.
길이 꽤 길게 이어져서 해안선을 따라 걷다 보면 시간이 훌쩍 지나지요.
이곳을 골웨이를 떠나는 날 아침에 들렀습니다.
비가 계속 많이 내렸어요.
‘아. 비 맞기 싫어.’
‘아. 걷고 싶어.’
하기 싫은 걸 피하면 불쾌한 일이 줄지만,
하고 싶은 걸 한다면 그깟 불쾌감 따위야 뭐 대수겠어요.
모자를 뒤집어쓰고 해변을 거닐기 시작했습니다.
아침마다 뜀박질하는 사람들이 비를 쫄딱 맞으며 제 옆을 스쳐 가네요.

들풀-'골웨이 바닷가 산책'

강한 바람 탓에 바닥에 몸을 누인 들풀 너머로 조용히 출렁이는 바다가 보입니다.
조금 더 걸으니 빗살이 약해졌어요.

산책 나온 개-'골웨이 바닷가 산책'

동네 사람 하나가 개를 데리고 산책을 나왔습니다.
그들은 낯선 곳을 거니는 낯선 이를 보고 잠시 발걸음을 멈추었지만,
이내 아무것도 못 본 듯이 익숙한 길을 걸어갑니다.

바닷가-'골웨이 바닷가 산책'

빗살이 다시금 거세집니다.
모자 위를 때리는 물방울 소리가 썩 듣기 좋더군요.
잠시 멈추어 바다를 바라보았습니다.
자연은 거센 비에도 우왕좌왕하지 않습니다.
아.
저도 자연에 속하는데.
왜 그처럼 의연하지 못할까요?

방파제-'골웨이 바닷가 산책'

방파제 길을 따라 걸으니 갈매기 몇 마리가 머리 위를 스쳐 갑니다.
“끼룩~ 끼루룩~”
그들의 노랫소리에 답가라도 들려주고 싶지만, 가사가 끝까지 기억나는 노래가 없네요.
흘러간 옛 노래를 조금 흥얼거리자 갈매기들이 저 멀리 떠나갑니다.
마치 자동차 엔진 소리에 놀라 달아나는 새처럼 말이에요.
제 목소리도 그리 생소한가 봅니다.
아마 그 소리가 자연스럽지 못해 그렇겠지요.



by


Tags : , , , , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

Git cheat sheet


ssh 키페어 만들기

ssh 키 페어 만들기

git 기본 명령어


git init  - 초기화
git add * - git에 파일 목록 넣기
git commit -am 'initial commit' - 커밋
git push repository_name master - 해당 브랜치에 커밋
git clone git@app.repo.com:app/app.git - 코드를 로컬로  복제
cd app
git pull - 변경사항 풀


git 환경 설정


git config --global --list
현재 설정정보 조회할 수 있습니다. --global옵션은 전역설정에 대한 옵션이며 현재 프로젝트에만 적용할때는 주지 않습니다.
git config --global user.name "사용자명"
사용자명을 등록합니다 (필수)
git config --global user.email "이메일주소"
이메일 주소를 등록합니다. (필수)
git config --global color.ui “auto”
터미널에 표시되는 메시지에 칼라를 표시해 줍니다.



gitignore 사용하기


.gitignore
git config --global core.excludesfile ~/.gitignore_global
git rm -r --cached .
git add .
git commit -m ".gitignore 완성!"
git stash branch branchname
git fetch
git merge
git pull (git fetch + git merge branchname)


로컬 변경 무시하고 저장소에서 받아오기

모든 로컬 변경을 스태쉬 한다.
git stash save --keep-index
저장한 stash를 지운다.
git stash drop

파일 하나만 저장소에서 불러오려면 이렇게 한다.
git checkout HEAD^ path/to/file/to/revert

그리고 저장소에서 풀 한다.
git pull


특정 커밋으로 돌아가기
http://stackoverflow.com/questions/4114095/revert-to-previous-git-commit
git reset --hard 0d1d7fc32

Send a pull request on GitHub for only latest commit
http://stackoverflow.com/questions/5256021/send-a-pull-request-on-github-for-only-latest-commit
git checkout -b upstream upstream/master
git cherry-pick <SHA hash of commit>
git push origin upstream



How can I rollback a github repository to a specific commit?
http://stackoverflow.com/questions/4372435/how-can-i-rollback-a-github-repository-to-a-specific-commit
git reset --hard <old-commit-id>
git push -f



참고 자료

http://git-scm.com/
http://github.com/
아웃사이더님의 git 명령어 정리
구글 검색



by


Tags : , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

Jquery,Coffeescript Snippet 모음


스타일 변화 시키기


    $('HTML').addClass('JS');
    * In your css */
    .JS #myDiv{display:none;}

coffee script 에서 함수 호출


    contents+="<li class='city_candidate' onclick='h(\""+data[v]+"\")'>"+v+"</li>"
    @h = h = (set) ->
      $('span#cityoutput').replaceWith("<span id='cityoutput'>"+set+"</span>")

Ajax Callback


    url = "locations"
    request = $.get url,data
    request.success (data) -> $("#regionresults").html(data)
    request.error (jqXHR, textStatus, errorThrown) -> $("#region
results").append "AJAX Error: ${textStatus}."

Slide UP


jQuery ->
  $(".search input").focus ->
    if @value == "Search"
      @value = ""
      @className = "textinput"  $(".search input").blur ->
    if @value == ""
      @value = "Search"
      @className = "placeholder"
  $('#message').css { border: '1px solid red' }
  $("p").click(function () {
      $(this).slideUp();
    });
    $("p").hover(function () {
      $(this).addClass("hilite");
    }, function () {
      $(this).removeClass("hilite");
    });

Sticky layer


sticky = () ->
  y = $(window).scrollTop()
  if y > $('#topnavigation').height()
    $('#top
navigation').css({
      'position': 'fixed',
      'top': '0',
      'z-index': "4444"
        'width': $('#top_navigation').width(), 'box-shadow': '0px 20px 20px -15px #CCC'
    })
    $('#topnavigation').removeClass("sixteen columns alpha")
    $('#main').css({'padding-top': $('#top
navigation').height()})
  else
    $('#topnavigation').removeAttr('style')
    $('#main').removeAttr('style')
    $('#top
navigation').addClass("sixteen columns alpha")
$(window).scroll(sticky)
$(window).resize(sticky)
   
   

페이드인 메시지


msg = "world"
inv = "you"
show_message = (x,y) ->
  $('span#message').hide().text(x).fadeIn(1000,
  -> $('span#message').append('!')
  )
  $('#hint').hide().text(x).fadeIn(0)$ ->
  showmessage msg,inv
    [inv, msg] = [msg, inv]
 
  $('span#message').click ->
    show
message inv,msg
    [inv, msg] = [msg, inv]
message fadein and out
.fadeIn(30).fadeOut(1000);
   

다이나믹 add remove


$('input#addlanguageskill').on 'click', () ->
  num = ($('.languageskillinnerbox').length)-1
  newNum  = new Number(num+1)
  sourceElem = $('div#language
skill' +num)
  newElem = sourceElem.clone().prop('id','language
skill'+newNum)
  newElem.find("#user
languageskillsattributes"+num+"languageid").prop({id:'userlanguageskillsattributes'+newNum+'languageid',name:'user[languageskillsattributes]['+newNum+'][languageid]'})
  newElem.append('<input onclick="remove(\''+newElem.prop('id')+'\')" id="removelanguageskill"'+newNum+' type="button" value="Remove Language"/>')
  sourceElem.after(newElem)
@remove = remove = (elemid) ->
  alert "remove : "+elem
id
  $("#"+elem_id).remove()

Nested Model Form 예제


<% formfor @person do |personform| %>  <%= personform.label :name %>
  <%= person
form.text_field :name %>
  <% personform.fieldsfor :children do |child_form| %>
    <%= childform.label :name %>
    <%= child
form.text_field :name %>
    <% unless childform.object.newrecord? %>
      <% # Don't forget to name both of these 'destroy' in Rails 3 %>
      <%= child
form.checkbox 'delete' %>
      <%= childform.label 'delete', 'Remove' %>
    <% end %>
  <% end %>
  <%= submit_tag %>
<% end %>

그리즈 몽키 ajax 콜


var jqxhr = $.ajax({
  type: "POST",
  url: trackback,
  headers: {'User-Agent': 'Trackback',
                  'Content-Type':'application/x-www-form-urlencoded; charset=utf8'},
  data: inputdata,
  datatype:"text"
   });
  jqxhr.done(function() {
    GM
log("Trackback Success : "+jqxhr.responseText);           
  });
  jqxhr.fail(function(data,statusText,error) {                
        GM_log("Trackback faild : "+statusText+" [ "+error+", "+data.responseText+" ]");              
       
       
  });
 

셀렉트 박스 정렬


sortingSelectBox(selectTagId,sortBy,order)
selectTagId <select id="selectTagId"></select>
sortBy [0:Text, 1:Value] - default:0
order[0:Ascending, 1:Descending] - default:0
Examples
sortingSelectBox("mySelectTagId",1,1) sortBy Value in Descending order
sortingSelectBox("mySelectTagId",1) sortBy Value in Ascending order
sortingSelectBox("mySelectTagId") sortBy Text in Ascending order
sortingSelectBox = (selectBoxId,sortBy,order) ->
   sortBy ?= 0
   order ?= 0
   sortVal = 0
   if order is 1 then sortVal = 2
   orderValLeft = -1 + sortVal
   orderValRight = 1 - sortVal
   selectBox = $("select#"+selectBoxId)
   options = $("select#"+selectBoxId+" option")
   selectedVal = selectBox.val()
   sortedOption = options.clone()
   options.empty().remove()
   switch sortBy
     when 0
       sortedOption.sort((left,right)->
         leftText = left.text.toLowerCase()
         rightText = right.text.toLowerCase()
         if leftText < rightText then return orderValLeft
         if leftText is rightText then return 0
         orderValRight
       )
     else
       sortedOption.sort((left,right)->
         leftVal = left.value
         rightVal = right.value
         if leftVal < rightVal then return orderValLeft
         if leftVal is rightVal then return 0
         orderValRight
       )
   selectBox.append(sortedOption)
   selectBox.val(selectedVal)
  
sortingSelectBox("country")

리다이렉트


// simulates similar behavior as an HTTP redirect
window.location.replace("http://stackoverflow.com");
// simulates similar behavior as clicking on a link
window.location.href = "http://stackoverflow.com";

JQuery 데이터 타입


dataTypeString
Default: Intelligent Guess (xml, json, script, or html)
The type of data that you're expecting back from the server. If none is specified, jQuery will try to infer it based on the MIME type of the response (an XML MIME type will yield XML, in 1.4 JSON will yield a JavaScript object, in 1.4 script will execute the script, and anything else will be returned as a string). The available types (and the result passed as the first argument to your success callback) are:    "xml": Returns a XML document that can be processed via jQuery.
    "html": Returns HTML as plain text; included script tags are evaluated when inserted in the DOM.
    "script": Evaluates the response as JavaScript and returns it as plain text. Disables caching by appending a query string parameter, "=[TIMESTAMP]", to the URL unless the cache option is set to true. Note: This will turn POSTs into GETs for remote-domain requests.
    "json": Evaluates the response as JSON and returns a JavaScript object. In jQuery 1.4 the JSON data is parsed in a strict manner; any malformed JSON is rejected and a parse error is thrown. (See json.org for more information on proper JSON formatting.)
    "jsonp": Loads in a JSON block using JSONP. Adds an extra "?callback=?" to the end of your URL to specify the callback. Disables caching by appending a query string parameter, "
=[TIMESTAMP]", to the URL unless the cache option is set to true.
    "text": A plain text string.
    multiple, space-separated values: As of jQuery 1.5, jQuery can convert a dataType from what it received in the Content-Type header to what you require. For example, if you want a text response to be treated as XML, use "text xml" for the dataType. You can also make a JSONP request, have it received as text, and interpreted by jQuery as XML: "jsonp text xml." Similarly, a shorthand string such as "jsonp xml" will first attempt to convert from jsonp to xml, and, failing that, convert from jsonp to text, and then from text to xml.
/*
If you wish to use any of the meta-characters
( such as !"#$%&'()*+,./:;?@[]^`{|}~ ) as a literal part of a name,
you must escape the character with two backslashes: . For example,
if you have an an element with id="foo.bar", you can use the selector
$("#foo.bar").
*/

Session based tokens


If you are using session based tokens, you probably generate a secure token when generating the session, and store that token in the session. When a request comes back to the server, you check that the token is included in the request and compare it to what's in the session. If it's the same token, you accept the request, if not you reject it.
To use this token with jQuery, you need to make it available to javascript. You typically do this by adding it as a javascript variable.
var csrftoken = '<%= tokenvalue %>';
Next, the trick is to bind to the global ajaxSend event, and add the token to any POST request
$("body").bind("ajaxSend", function(elm, xhr, s){
if (s.type == "POST") {
xhr.setRequestHeader('X-CSRF-Token', csrf_token);
}
});

rails-3-1-and-jquery-ui-assets 설정


# http://stackoverflow.com/questions/6133818/rails-3-1-and-jquery-ui-assets
 $ cat app/assets/javascripts/application.js
    //= require jquery
    //= require jquery-ui
    $ cat app/assets/stylesheets/application.css
    /*
     *= require vendor
     *
     */
    $ cat vendor/assets/stylesheets/vendor.css
    /*
     *= requiretree ./jqueryui
     *
     */
    vendor/assets/ $ tree
     stylesheets
         vendor.css
             jqueryui
                      jquery-ui-1.8.13.custom.css
                      ...
     images
        jquery
ui
            ui-bgflat0aaaaaa40x100.png
            ...

Finally run this command:
    vendor/assets/images $ ln -s jquery_ui/ images
   

Get center


$(document).ready(function(){
  jQuery.fn.center = function () {
      this.css("top",$(window).height()/2-this.height()/2 + "px");
      this.css("left",$(window).width()/2-this.width()/2  + "px");
      return this;
  }
  $("#container").center();
 });
 

Multiple selector

$("#txt1, #txt2, #txt3").keyup(fn);

Jquery check CKEditor


$(this).data('initialForm', $(this).serialize());
to
$(this).data('initialForm', $(this).serialize() + '&' + FieldNameOfEditor + '=' + escape(ContentsOfEditor));
And a similar change to line 4 from
if ($(this).data('initialForm') != $(this).serialize()) {
to
var formData = $(this).serialize() + '&' + FieldNameOfEditor + '=' + escape(ContentsOfEditor);
if ($(this).data('initialForm') != formData) {

Jquery Defer


(function() {
      function getScript(url,success){
        var script=document.createElement('script');
        script.src=url;
        var head=document.getElementsByTagName('head')[0],
            done=false;
        script.onload=script.onreadystatechange = function(){
          if ( !done && (!this.readyState || this.readyState == 'loaded' || this.readyState == 'complete') ) {
            done=true;
            success();
            script.onload = script.onreadystatechange = null;
            head.removeChild(script);
          }
        };
        head.appendChild(script);
      }
        getScript('http://ajax.googleapis.com/ajax/libs/jquery/1.5.2/jquery.min.js',function(){
            // YOUR CODE GOES HERE AND IS EXECUTED AFTER JQUERY LOADS
        });
    })();

Scroll to top   


var destination = $(‘#idToScrollTo’).offset().top;
$(‘html’).animate({scrollTop: destination},600);

CKEDITOR


config.toolbar = 'Modati'
config.toolbar_Modati = [['Bold', 'Italic', 'Underline','Strike', '-', 'RemoveFormat','-', 'Outdent','Indent','-','Blockquote','HorizontalRule', '-', 'JustifyLeft','JustifyCenter','JustifyRight','JustifyBlock','-','FontSize','TextColor','BGColor']]CKEDITOR.editorConfig = function( config )
{
    config.toolbar = 'MyToolbar';
 
    config.toolbar_MyToolbar =
    [
        { name: 'document', items : [ 'NewPage','Preview' ] },
        { name: 'clipboard', items : [ 'Cut','Copy','Paste','PasteText','PasteFromWord','-','Undo','Redo' ] },
        { name: 'editing', items : [ 'Find','Replace','-','SelectAll','-','Scayt' ] },
        { name: 'insert', items : [ 'Image','Flash','Table','HorizontalRule','Smiley','SpecialChar','PageBreak'
                 ,'Iframe' ] },
                '/',
        { name: 'styles', items : [ 'Styles','Format' ] },
        { name: 'basicstyles', items : [ 'Bold','Italic','Strike','-','RemoveFormat' ] },
        { name: 'paragraph', items : [ 'NumberedList','BulletedList','-','Outdent','Indent','-','Blockquote' ] },
        { name: 'links', items : [ 'Link','Unlink','Anchor' ] },
        { name: 'tools', items : [ 'Maximize','-','About' ] }
    ];
};
config.toolbar = 'Full';
 
config.toolbarFull =
[
    { name: 'document', items : [ 'Source','-','Save','NewPage','DocProps','Preview','Print','-','Templates' ] },
    { name: 'clipboard', items : [ 'Cut','Copy','Paste','PasteText','PasteFromWord','-','Undo','Redo' ] },
    { name: 'editing', items : [ 'Find','Replace','-','SelectAll','-','SpellChecker', 'Scayt' ] },
    { name: 'forms', items : [ 'Form', 'Checkbox', 'Radio', 'TextField', 'Textarea', 'Select', 'Button', 'ImageButton',
 
         'HiddenField' ] },
    '/',
    { name: 'basicstyles', items : [ 'Bold','Italic','Underline','Strike','Subscript','Superscript','-','RemoveFormat' ] },
    { name: 'paragraph', items : [ 'NumberedList','BulletedList','-','Outdent','Indent','-','Blockquote','CreateDiv','-
 
        ','JustifyLeft','JustifyCenter','JustifyRight','JustifyBlock','-','BidiLtr','BidiRtl' ] },
    { name: 'links', items : [ 'Link','Unlink','Anchor' ] },
    { name: 'insert', items : [ 'Image','Flash','Table','HorizontalRule','Smiley','SpecialChar','PageBreak','Iframe' ] },
    '/',
    { name: 'styles', items : [ 'Styles','Format','Font','FontSize' ] },
    { name: 'colors', items : [ 'TextColor','BGColor' ] },
    { name: 'tools', items : [ 'Maximize', 'ShowBlocks','-','About' ] }
];
 
config.toolbar
Basic =
[
    ['Bold', 'Italic', '-', 'NumberedList', 'BulletedList', '-', 'Link', 'Unlink','-','About']
];
CKEDITOR.editorConfig = function( config )
{
    config.extraPlugins = "customparagraph";
    config.toolbar = [ [ 'ThinyP' ] ]; // add other toolbars and keep in mid this can be overwritten in page which loads CKEditor
};
<script type="text/javascript">
//<![CDATA[
    // Replace the <textarea id="editor1"> with a CKEditor
    // instance, using default configuration.
    CKEDITOR.replace( 'editor1',
        {
            extraPlugins : 'customparagraph',
            toolbar :
            [
                [ 'Bold', 'Italic', '-', 'NumberedList', 'BulletedList', '-', 'Link', 'Unlink' ],
                [ 'ThinyP' ]
            ]
        });
//]]>
</script>
in the main ckeditor config-file there is an option to disable automatic <p> inserts. try to change the value of CKConfig.EnterMode and CKConfig.ShiftEnterMode for example to 'br'.
config.enterMode = CKEDITOR.ENTER_BR
lostmorethanfive, lostbeetweenfourandfive, lostbeetweenthreeandfour, lostbeetweentwoandthree, lostbeetweenoneandtwo, lostbeetweenzeroandone, gainedbeetweenzeroandone, gainedbeetweenoneandtwo,gainedbeetweentwoandthree, gainedbeetweenthreeandfour, gainedbeetweenfourandfive,gainedbeetweenfiveandsix, gainedbeetweensixandseven,gainedmorethanseven


출처




by


Tags : , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

아란섬 이니스 모어의 깎아지른 절벽. 둔 앵구스.

전에 한 아이리시 친구한테 물었습니다.
“아일랜드에서 가장 마음에 드는 곳이 어디야?”
그 친구는 한 치의 망설임 없이 대답했어요.
“아란섬. 아! 거기 만한 곳이 없지.”
‘그렇게 멋지단 말이야?’
하긴 저는 섬을 좋아하는 편입니다.
집에서 가까운 자월도나 석모도만 해도 좋고요.
따뜻한 남쪽의 제주도는 정말 멋지잖아요?
아. 설레라.
아란섬으로 떠나는 날이에요.
그런데 날씨가 미쳤습니다.
폭풍우라니요!

돌담길-'Dún Aonghasa Inis Mór Aran Island'

물방울 필터를 쓰고 싶은 것도 아닌데,
제 마음과는 상관없이 렌즈엔 물방울 효과가 자동으로 적용됩니다.
방수 점퍼를 입고 갔는데도 튼튼한 판초 우의를 따로 빌렸어요.
비가 엄청나게 많이 왔거든요.

폭풍우를 뚫고 도착한 사람들-'Dún Aonghasa Inis Mór Aran Island'

둔 앵구스 절벽-'Dún Aonghasa Inis Mór Aran Island'

둔 엥구스 절벽은 탄성을 자아내는 곳입니다.
우와아아악!
정말 멋진 곳인데, 비가 십방에서 휘몰아칩니다.
감탄사와 비명이 함께 터져 나왔어요.
최고급 판초 우의도 다 소용없습니다.
머리 끝에서 발끝까지 홀딱 젖었어요.
지금껏 아일랜드에 지내면서 이렇게까지 무서운 날씨는 없었어요.
사진 찍다가 감전된 적은 처음입니다.
사진 찍을 때만 잠깐 꺼내 쓰고 비 맞지 않게 꽁꽁 싸매 놨는데도 그래요.
그 폭풍우에서도 살아남은 카메라가 대견하네요.

거센 바람을 맞으며-'Dún Aonghasa Inis Mór Aran Island'

이 우비 날리는 것 좀 보세요.
이 친구는 지금 영국에 산다는데, 거기서도 이런 날씨는 못 봤답니다.
거센 바람을 맞으며 절벽을 걷다가 문득 날을 참 잘 잡았단 생각이 들었습니다.
아일랜드에 맑은 날이야 한 달에 두세 번은 있지만,
이런 사람 날아갈 날씨는 지금껏 처음 겪으니까요.

둔 앵구스 절별-'Dún Aonghasa Inis Mór Aran Island'

폭풍과 절벽.
그 둘이 참 잘 어울러요.
날씨 탓인지 도로에 차도 하나 뒤집어져 있던데,
저는 좀 떨긴 했지만 어디 한 곳 부러지지도 않고 대자연을 느끼고 왔습니다.

아란섬은 참 강렬한 이미지로 남았어요.
듣던 대로 참 멋진 곳입니다.



by


Tags : , , , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

인도의 구도자 오쇼 라즈니쉬의 가르침. 기적을 찾아서.

뭔가 겉도는 기분이었습니다.
앞으로 발걸음을 옮기지만, 뫼비우스 띠를 따라 맴도는 듯했어요.
그때 이 책이 큰 도움이 되었습니다.
그동안 가졌던 의문 중 몇이 해소되었거든요.
불교, 기독교, 힌두교, 이슬람교 등에선 정파처럼 가르친다면,
오쇼 라즈니쉬는 정사지간 같다는 느낌을 받았습니다.
사파의 시각으로도 한번 바라보고 싶은데 아직까진 기회가 없었네요.
뭐 언젠가 인연이 닿는다면 마주치겠죠.
이 책에는 오쇼 라즈니쉬의 흥미로운 관점이 잘 담겼습니다.
그렇다고 제가 그것을 덥석 믿진 않아요.
그것을 직접 겪는다면 사실이 될 테니 믿음이 필요치 않고,
경험하지 못한 것이라면 믿는다고 해도 달라질 게 없으니까요.
무지개를 한 번도 못 본 사람이 그게 하늘에 뜬다고 믿어 봤자 뭐합니까?
그것을 본 사람은 말합니다.
“비가 그치면 뜬다!”
그리고 어떤 사람들은 말합니다.
“동쪽 하늘에 뜬다.”
“아니다. 서쪽 하늘이다!”
동쪽과 서쪽은 정 반대의 방향이지만, 무지개는 어디서고 상황만 맞으면 뜹니다.
이렇게 무지개에 대한 정보를 얻었다면 우리는 밖으로 나가야 합니다.
좀 헤매면 결국 무지개를 보게 되죠.
“오! 무지개는 비가 내린 뒤에 태양을 등지고 서야 보이는군.”
스스로 깨닫지 못한다면 그것은 단지 남의 이야기일 뿐입니다.

바투 동굴-'기적을 찾아서'

오쇼 라즈니쉬의 관점과 명상 철학

얼마나 많이 달렸느냐는 것은 무의미하다. 그가 원주에 있는 한 중심과의 거리는 항상 똑같다.

불행이 시간을 길게 연장하는 반면 행복은 시간을 짧게 단축시킨다.

위험이 없는 곳으로 가지 말라. 절대 그런 곳으로는 가지 말라. 거기에는 죽음 외에 아무것도 없기 때문이다.

생각을 통제할 수 없다면 그들은 미친 사람들이다. 그리고 주인의 입장에서 자신을 다룰 수 있는 사람들만이 건강한 정상인이다.

폭력적인 사람이 비폭력주의자가 되려고 애쓴다. 화를 잘 내는 사람이 유순해 지려고 애쓴다. 거친 사람이 상냥해지려고 노력한다. 도둑이 관대해지려 하고, 사악한 사람이 성자처럼 되려고 애쓴다.
이것이 우리가 살아가는 방식이다. 우리는 있는 그대로의 우리 모습을 부정하고 항상 그 위에 무엇인가 부과하려고 애쓴다.

사하자 요가는 말한다.
“있는 그대로의 그대가 아닌 다른 존재가 되려고 하지 말라. 그대가 어떤 존재 인지를 알고 그에 충실하게 살아라. 그대가 도둑이라면, 그대가 도둑이라는 사실을 알고 그에 충실하게 살아라.”
“만약 그대가 도둑이라면 그 사실을 분명히 알아라. 도둑질을 하더라도 그 사실을 알고 하라. 내일은 도둑이 아닐 것이라는 희망을 갖고 도둑질을 하지 말라.”

영적인 삶의 길에 퇴보는 없다. 다만 진보나 정체가 있을 뿐이다.

자신이 처한 단계에서 주어지는 가르침을 신뢰하고 받아들여야 한다.

돌아서 가는 길이 더 쉽고 지름길이 가장 험난하다는 것은 수없이 증명된 바 있다.

자기 자신을 알고 깨닫는 것은 분명히 기쁜 일이다. 그러나 자기 자신을 잃어 버리는 것이야 말로 궁극적인 지복이다.

가정을 꾸려 나가면서 쓰이는 에너지를 다른 일을 위해 보존하자는 것이 출가의 이유였다.
우리가 활용하는 에너지가 매우 제한되어 있기 때문이다. 이 에너지를 다른 목적, 더 높은 목적을 위해 사용해야 한다는 것이 그 취지였다.
우리가 일상 생활에 소비하는 에너지는 아주 소량이다. 보존하고 자시고 할 것도 없다. 그리고 이 에너지를 보존하기 위해 더 많은 에너지를 소비해야 할 것이다. 에너지를 보존하기 위해서도 에너지를 소모해야 한다.
이런 종류의 산야스는 자신이 가진 빈약한 에너지를 보존하려는 인색한 사람들의 길이다. 이렇게 인색하고 옹졸한 접근 방식은 아무 소용이 없다. 여기저기에서 조금의 에너지를 저축하는데 급급해서는 안된다. 그보다도 우리 안에 잠 자는 에너지, 그 풍부하고 무한한 에너지를 일깨워야 한다.

명상가(sadhak)와 헌신자(bhakta)라는 두 가지 길이 있다. 헌신자의 신은 하늘 위에 있다. 그러므로 헌신자는 두 손을 모으고 기도하면서 기다린다. 반면, 명상가의 신은 그의 내면 깊은 곳에 잠 들어있다. 따라서 명상가는 신을 깨우려고 노력한다.

수피는 수면이라는 자연현상에 정면 공격을 가함으로써 매우 생소하고 이상한 상황을 창조한다.

날숨과 들숨의 중간 지점에 호흡이 멈춰 버린 이 순간, 완벽한 균형이 이루어진 이 순간에 삼매가 온다. 이 순간에 그대는 생명(life)이 아니라 존재(existence)를 안다.

사드구루(sadguru), 완벽한 스승에 대한 정의는 ‘구루가 되지 않는 사람’이다. 이 말은 스스로 구루라고 지칭하는 사람들은 구루가 될 자격이 없음을 뜻한다.

이해의 차원에 도달한 사람들은 인간이 꿈꾸는 두 가지 목표에 대해 말한다.
섹스와 해탈이 그것이다. 부와 종교라는 다른 두 가지 목적은 단지 수단에 불과하다. 부는 섹스를 위한 수단이다. 그러므로 성적인 시대일수록 부를 지향하며, 해탈을 구하는 시대일수록 종교를 지향한다. 부가 수단이듯이 종교 또한 수단에 지나지 않는다.

어제로 돌아가기를 원한다면 그대는 눈을 감고 어제를 떠올릴 수 있다. 그러나 그런 상태가 얼마나 가겠는가? 눈을 뜨는 순간 그대는 현재에 있는 자신을 발견할 것이다.

일시적인 행복은 동물적인 차원에서도 가능하지만 영원한 행복은 신과 하나가 되었을 때 만 가능하다.

타인이라는 현상 자체가 환상이다. 일단 이것을 깨달으면 삶이 아주 단순해진다. 타인을 지향하는 모든 행동이 중단된다. 이 때는 타인을 위해 어떤 일을 하건, 그대 자신을 위해 어떤 일을 하건 오직 그대만 남는다. 그대는 타인을 도와 줄 때도 그를 타인으로 간주하지 않으며, 타인으로부터 도움을 받을 때도 그를 타인으로 간주하지 않는다.

사실 착취(exploitation)와 실용화(utilization) 사이에는 엄청난 차이가 있다. 내가 나의 에고를 위해 무엇인가 이용한다면 그것은 착취다. 그러나 재가 온 세상을 위해, 모든 사람을 위해 어떤 것을 이용한다면 거기에 착취의 문제는 없다.

구루를 찾는다면 그대는 그 자리에 정체될 것이다. 이정표 위에 멈춰 서지 말라.

실제로, 마음은 어디로 갈지 갈피를 잡지 못한다. 마음은 천국으로 가야 행복할지 지옥으로 가야 행복할지 결정하지 못한다. 항상 두려워한다. 이렇게 두 발을 각기 다른 배에 올려놓으면 아무데로도 가지 못한다. 그대는 물에 빠져 죽고 말 것이다.

쿤달리니가 각성된 후에는 폭력적인 성향이 완벽하게 사라진다. 폭력을 행사하지 않을 뿐만 아니라 내면의 폭력성도 사라진다. 폭력을 행사하고 싶은 충동, 남에게 해를 입히고 싶은 충동은 쿤달리니가 잠자고 있는 상태에서만 가능하다. 쿤달리니가 깨어나는 순간 타인은 더 이상 타인이 아니다. 그러므로 타인에게 해를 입히려는 충동은 불가능하다. 이 때는 폭력적인 충동을 억누를 필요가 없다. 그런 충동 자체가 없으므로 폭력적으로 되는 것이 불가능하다.
만일 폭력적인 충동을 억눌러야 한다면 쿤달리니가 아직 깨어나지 않은 것이다. 그렇게 알면 된다. 눈을 뜬 다음에도 여전히 지팡이가 필요하다면 그대의 눈은 아직 사물을 보지 못하는 것이다.

인간의 일곱가지 신체

객관적 평가 가능한 영역

  • 첫 번째 - 물질적 육체 - 육체만이 형성
  • 두 번째 - 에텔체(etheric body) - 감정의 성장
  • 세 번째 - 아스트랄체(astral body) - 이성과 사유, 지성

주관적인 영역

  • 네 번째 - 멘탈체 (metal body) 또는 심령체(physic body)
  • 다섯 번째 - 영체(spiritual body)
  • 여섯 번째 - 코스믹체 (cosmic body)
  • 일곱 번째 - 니르바나 사리르 (nirvana sharir), 열반체 (nirvanic body), 무체의 체(bodiless body)

다섯번째 신체에서 모크샤(moksha)가 경험된다. 그 전에 있는 네가지 신체의 한계가 무너지고 영혼이 완전히 자유롭게 된다. 그러므로 해탈은 다섯 번째 신체의 경험이다. 천국과 지옥은 네 번째 신체의 차원에 속한다. 이 차원에 정체된 사람은 천국과 지옥을 경험할 것이다. 첫 번째나 두 번째, 또는 세 번째 신체에 머무는 사람들에게는 탄생과 죽음 사이의 삶이 전부다 그들에게는 죽음 너머의 삶이 존재하지 않는다.

모든 남자는 내부에 여성체를 갖고 있으며, 모든 여자는 내부에 남성체를 갖고 있다.
그러므로 우연히 어떤 여자가 자신의 남성체와 일치하는 남자를 배우자로 얻거나, 어떤 남자가 자신이 여성체와 일치하는 여자를 배우자로 얻는다면 그야말로 성공적인 결혼이다.

구도자는 안전을 경계해야 한다. 구도자에게는 안전에 대한 욕망이 가장 큰 집착이다. 한순간이라도 안전을 추구한다면 그는 이미 길을 잃어버린 것이다.
구도자는 항상 ‘나는 안전을 구하고 있지 않다.’는 것을 마음에 새겨야 한다. 그대는 안전이 아니라 진리를 구하는 것이다.

속박이 있는 곳에 관계는 없다. 그리고 관계가 있는 곳에서 속박은 불가능하다.

눈먼 사람은 등잔이나 전깃불을 만나도, 밝은 태양 아래에 나서도 결코 빛을 보지 못할 것이다.

탐구(seek)하는 것과 요구(ask)하는 것은 다른 일이다. 실제로, 탐구를 원하지 않는 사람만이 요구한다.

에고와 ‘나의 존재성’이 어떻게 다른지 이해해야 한다. 에고, 즉 ‘나(I)’라는 느낌은 죽겠지만 ‘존재(am)’라는 느낌은 죽지 않을 것이다. ‘I am’ 안에는 두 가지가 있다. ‘I’는 에고고 ‘am’은 아스미타(asmita), 존재의 느낌이다.

전세계에 만연한 남녀간의 불평등은 남자가 자신을 ‘주는 자’로 생각하고 여성은 자신을 ‘받는 자’로 생각한다는 사실에서 비롯되었다. 받는 쪽은 왜 반드시 열등해야 하는가? 누가 그렇게 말하던가? 받는 자가 없다면 주는 자가 무슨 소용인가? 그 반대의 경우도 성립된다. 주는 자가 없다면 받는 자가 무슨 소용인가? 이것은 열등함과 우월함의 문제가 아니다. 둘이 서로 보완적인 위치에 있다.

우리는 항상 값을 치를 준비를 해야 한다. 실제로 값을 치를 준비가 되어 있을수록 우리는 더 가치 있는 것을 얻는다.

동물에게는 내일이 없다. 그들에게는 오늘이 전부다. 어떤 면에서는 오늘조차 없다. 내일이 없는 그들에게 오늘이 무슨 의미가 있겠는가?

행복은 지겨움을 낳는다. 행복만큼 권태를 불러 오는 것은 없다. 불행은 지겹지 않다. 불행한 마음은 결코 권태롭지 않다.

성교에는 두 종류가 있다. 하나는 단순히 음식을 먹는 것이고, 다른 하나는 음식을 소화시키는 것이다. 우리가 흔히 알고 있는 성교는 음식을 먹고 토하는 행위에 불과 하다. 아무것도 소화되지 않는다. 무엇인가 소화되면 그 만족감은 훨씬 더 깊어지고 오래간다. 그러나 소화 흡수 작용은 에너지의 순환이 형성되었을 때만 가능하다.

가정을 가진 사람에게는 섹스가 많은 문제 중 하나에 불과하다. 그러나 전통적인 산야신에게는 섹스가 유일한 고민거리다.

사념(thought)과 사유(thinking)사이에는 차이점이 있다. 사념은 자동적인 현상이다. 사념은 항상 이방인처럼 왔다가 떠난다. 사념은 항상 이방인이라고 말하는 것이 옳은 표현이다. 그러나 사유는 우리의 것이다. 이 사유는 다섯 번째 신체에서 시작될 것이다. 이 때 그대는 단순히 다른 사람들의 사념을 수집하는 것이 아니라 그대 스스로 사유하게 될 것이다.

하나의 차원 안에서 삼매가 일어난다면 그것은 가짜 삼매다. 진짜 삼매는 차원들 사이에서 일어난다. 그것은 하나의 문일 뿐이지, 방안에 존재하지 않는다. 그것은 방밖에 있어야 한다. 다음 방과 연결되는 지점에 있어야 한다.



by


Tags : , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

아일랜드에서 스윙 추기 가장 좋은 동네. 골웨이로 린디합 출빠 하세요.

아일랜드에서 지낸 지 어느덧 십 개월이 흘렀습니다.
한 번 정도는 살아볼 만한 곳이지만,
다시 이곳에서 한 해를 보낼 일은 없을 것 같은 나라라고 생각했죠.
‘언제 또 여기 발을 디딜지 모르니 골웨이나 한번 놀러 가자.’
별 기대 없이 갔던 서부의 작은 도시.
그곳에 도착했을 때 날씨는 아일랜드에 살던 중 최악이었지요.

massimo-'Swing dance Galway'

이틀 동안 출빠를 하곤 아일랜드에 대한 생각이 바뀌었습니다.
‘내가 만약 춤에 제대로 빠진다면, 골웨이에 와서 일 년을 사는 것도 괜찮겠다.’
더블린이나 코크보다 스윙 댄서가 유달리 많은 건 아닙니다.
춤추는 사람 수는 거기서 거기에요.
얼마 안 되죠.

live band-'Swing dance Galway'

춤추는 환경이 좋은 거냐 하면 그도 아니지요.
첫날 출빠한 곳은 춤 판 한복판에 기둥이 떡 하니 서 있습니다.
가볍게 스윙 아웃 하다가 기둥을 깜빡해서, 팔로워 백본 브레이커가 될 뻔 했어요.
그럼 골웨이에서 무엇이 그리 마음에 드느냐고요?

live band-'Swing dance Galway'

춤추는 분위기가 참 편안하고 좋았습니다.
출빠를 할 땐 보통 ‘춤을 추러’ 가잖아요?
그런데 여기서 출빠할 땐 ‘춤도 출겸’ 갔습니다.

라이브 공연과 춤-'Swing dance Galway'

그냥 굳이 춤 안 추고 남들 추는 거만 봐도 재미나고 그랬어요.
게다가 이틀 연속 라이브 공연에 춤을 춘 지라 더욱이 마음에 들었나 봅니다.
제가 만약 린디합 마니아라면.
이곳을 베이스캠프로 일 년 내내 유럽 스윙 페스티벌을 다니며 지내고 싶네요.:D


골웨이 스윙 이벤트 정보



by


Tags : , , , , , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

부드러운 아이리시 위스키. 제임슨.

술병-'Jameson'

동네 슈퍼마켓에 가면 주류 판매대에 대표 아일랜드를 대표하는 위스키가 진열되어 있습니다.
부쉬밀(Bushmill), 패디 (Paddy), 파워 (Power) 그리고 제임슨(Jameson).
이렇게 네 제품이 눈에 띄는데요.
아이리시 위스키는 세 번 증류하여 맛이 깔끔합니다.
부쉬밀과 패디는 맛봤고 이번이 세 병째 위스키군요.
술을 고르기 전에 고민이 좀 되었습니다.
칵테일이나 가끔 만들어 마시니 한 병사면 오래가거든요.
아마도 둘 중 한 병은 아일랜드를 떠나기 전에 맛보지 못할듯합니다.
'파워? 아일랜드의 힘인데?!'
결국 이름이 친근한 제임슨을 집어 들고 나왔어요.
맛을 보니 탁월한 선택이었습니다.
부쉬밀은 깊은 맛이 인상적이라면,
제임슨은 부드러운 맛이 일품이랄까요?
스트레이트로 마시기에 참 좋아요.
그러나 전 주로 칵테일을 만들어 마십니다.
겨울에 춥고 비가 많이 와서 여름이 오면 좀 날이 풀리려나 했는데,
여름이 되니 폭풍우가 몰아칩니다.
난방하기엔 뭐하지만, 가만히 앉아있으면 쌀쌀한 날씨에요.
이런 날씨에 마시기 좋은 칵테일입니다.
이름하야 아이리시 헤일스톰!
그 제조법을 적어 볼게요.

칵테일 아이리시 헤일스톰 비방


재료
  • 카카오 100% - 3TS
  • 커피 - 1TS
  • 뜨거운 물 - 60ml
  • 아이리시 위스키(제임슨이나 부쉬밀) - 50 ml
  • 베일리스 - 25 ml

만드는 법
우선 카카오와 커피에 뜨거운 물을 부어 잘 젓습니다.
삼 분 후에 아이리시 위스키를 부어주세요.
세상의 모든 애주가가 행복하길 바라는 마음을 담아 잘 흔들어 줍니다.
그럼 시커먼 액체가 위스키를 집어삼켜요.
그리곤 베일리스를 얹어주면 끝!

간단하죠?
폭풍우가 몰아치는 밤에 마시기 좋은 달콤쌉싸름한 칵테일이에요.



by


Tags : , , , , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

스페인 카미노 데 산티아고 도보 여행 안내서. 은의 길 (욕하지 말고) 웃으며 걸으세요.

은의 길 (욕하지 말고) 웃으며 걸으세요.

제목이 좀 깁니다.
하지만 유쾌한 이 책의 성격을 잘 나타내 준다고 생각해요.
‘스페인의 도보 여행길. 비아델라플라타를 완벽하게 파헤친다! 상세 지도와 현지 정보 전격 수록.’
이런 제목이 붙었다면, 지도 코너나, 덩치 좋은 가이드북 사이에 파묻히지 않았겠어요?
정보로 꽉 찬 안내 책자는 왠지 교과서를 읽는듯하여 머리가 아픕니다.
간혹 서점에 가더라도 가이드북 코너는 잽싸게 지나치는 편이죠.
그래도 가끔은 안내서를 뒤적이게 될 일이 생깁니다.
새로운 마을에 도착하여 동네 지도를 구하지 못했을 때에요.
물론 지나가는 사람에게 물어보면 되지만,
날씨가 궂거나 사람이 잘 지나다니지 않는다면 그러기 어렵습니다.
그럴 때 마을 지도 한 장이 참 큰 도움이 돼요.
‘은의 길 (욕하지 말고) 웃으며 걸으세요’엔 마을 약도가 잘 나온 편입니다.
숙소나 슈퍼 정보도 간략히 소개해 두었어요.
도보 여행안내서인 만큼 코스 공략도 되어 있지만,
보통의 안내서처럼 자세한 설명이 된 건 아닙니다.

코스 시작 지점에서 전방으로 백 미터를 걷고, 그다음엔 오른쪽 45도 각도로 꺾습니다.
직진으로 이백칠십 미터를 간 후, 아홉 시 방향의 길로 들어섭니다.
다시 사백 미터를 전진하면 과속 단속 카메라가 있으니 시속 이 킬로미터로 서행하세요.

이런 식으로 처음부터 도착지까지 길을 안내해 두었다면,
네비게이션을 보고 가는 것과 별다르지 않겠죠.
그러면 길을 걷는 내내 책을 들여다봐야 하니,
도보 여행의 재미를 느끼기 어렵습니다.
걷다가 책을 꺼내 볼 일이 없는 게 가장 좋다고 봐요.
하지만 도저히 길을 찾기 어려울 땐 먼저 간 여행자가 남기고 간 표식이 도움됩니다.
“이 갈림길에서 왼쪽 길로 가시면 마을입니다. 오른쪽 길로 갔더니 막다른 골목이더라고요.”
딱 이 정도만 귀띔합니다.
그럼 책의 나머지 부분은?
글쓴이가 길을 걸으며 겪은 그날그날의 일화가 담겼어요.
여행기 + 안내서라고 보면 되겠네요.
꼭 은의 길을 가지 않더라도 재미로 읽기 좋은 책입니다.
읽다가 한 번 정도는 웃으실 거에요. :D
앞으로도 이처럼 독특하고 술술 읽히는 여행 안내서가 책방에 모습을 드러내길 바랍니다.



리오네그로델푸엔테 가는 길 - 죽여주는 댐(God dam)

이미 틀이 잡힌 분야의 관례를 뒤집는 건 위험이 큽니다.
그럼에도 이 안내서를 출판하는 모험을 감행하신 푸른길 출판사의 김선기 대표님.
책이 나올 때까지 꼼꼼히 신경 써주신 편집자 이유정님.
고맙습니다.




by


Tags : , , , , , , , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

동화속으로의 여행. 골웨이 코네마라. 킬모어 수도원.

골웨이에서 서북쪽으로 80Km 정도 달려가면 킬모어 수도원이 나옵니다.
교통편이 마땅치 않아 여행사를 통해 다녀왔어요.
여행사를 이용하면 왠지 정신이 없을듯하지만,
코네마라 투어는 킬모어 수도원 왕복 교통편 정도입니다.
중간마다 잠시 내려 쉬어가긴 하지만 특별히 시간에 쫓기지 않아요.
주 목적지인 킬모어 수도원도 두 시간 반 동안 충분히 돌아봤거든요.

입구-'Kylemore Abbey Connemara'

차에서 내리면 입구부터 감탄사가 나옵니다.
“이야~~ 멋진데.”
호수를 끼고 서 있는 이 성에서라면 오랜 세월을 보내도 지루할 턱이 없겠습니다.

호수-'Kylemore Abbey Connemara'

그리고 성 쪽으로 걸어가 호수를 바라보았어요.
아. 자연의 신비란!
호숫가에 비친 산과 나무를 보니 신나서 펄쩍 뛰고 싶군요.
전에 아이리쉬 댄스를 보았을 때 우스울 정도로 너무 촐랑댄다 싶었는데,
이곳에 와보니 그 모습이 이해됩니다.
이런 곳을 보고 어찌 기쁘지 않겠어요.

거울-'Kylemore Abbey Connemara'

산책로를 따라 거닐다 보니 웬 거울이 서 있습니다.
“뭐야 쌩뚱 맞게 웬 거울이지?”
사실 이건 다른 세계로 통하는 차원 문 입니다.
이런 곳에 서있는 거울이 평범할 리가 없잖아요?
보름달이 뜨는 날 밤 자정에 이 거울로 손을 뻗으면 다른 차원으로 이동합니다.

정원-'Kylemore Abbey Connemara'

사람이 잘 가꾼 정원도 하나 보입니다.
이 정원을 먼저 보고 다른 곳을 걸을 걸 그랬다는 아쉬움이 들더군요.
저는 아무래도 자연이 가꾼 정원이 더 마음에 드니까요.



by


Tags : , , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

태국·중국·유럽 음식을 한 곳에서! 코크 에덴 레스토랑.

입구-'Eden Restaurant Cork'

에덴 음식점은 엄청난 가짓수의 메뉴를 자랑하는 음식점입니다.

메뉴-'Eden Restaurant Cork'

태국과 중국 요리가 주를 이루고, 행여나 아시아 음식이 입맛에 안 맞는 손님을 위한 유럽피언 메뉴도 갖추어 놓았죠.
음식 맛이 특별히 뛰어난 곳은 아니지만,
위치가 좋아요.
시내 한복판에 자리를 잡았거든요.
선호하는 음식이 다른 사람들끼리 모인다면, 약속 장소로 딱입니다.

새우 튀김-'Eden Restaurant Cork'

어묵 튀김-'Eden Restaurant Cork'

전체요리인 새우튀김·어묵이 꽤 바삭하고 맛이 좋습니다.

오리 요리-'Eden Restaurant Cork'

오리 요리-'Eden Restaurant Cork'

주요리로 먹은 태국식 오리 요리도 맛이 괜찮았어요.
이날 왠지 기름진 음식이 땡겨서,
기름진 튀김에 기름 좔좔 흐르는 오리 요리를 코코넛 밥에 얹어 먹었더니 좀 느끼했습니다.
전체와 주 요리 중 하나는 스프링롤처럼 좀 깔끔한 걸 시킬 걸 그랬어요.
배가 그리 고프지 않았는지, 음식량이 많은 건지 밥을 반공기도 안 먹었는데 배가 찼습니다.
밥그릇이 좀 크긴 해요.
생긴 건 밥그릇인데 크기는 대접이거든요.
배를 든든히 채우고, 간단한 후식으로 마무리합니다.

베일리스 케이크-'Eden Restaurant Cork'

베일리스 케이크에요!
이렇게 먹고 나면, 배에 기름이 좔좔 흐릅니다.^^;

에덴 레스토랑 위치



by


Tags : , , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.

아일랜드의 몽마르뜨. 타이타닉이 마지막으로 들렀던 항구 마을. 코브.

코브엔 관광객의 발걸음이 끊이지 않습니다.
타이타닉의 마지막 기항지로 널리 알려졌기 때문인데요.
그래서인지 마을을 돌아다니면서 ‘타이타닉’이란 글씨가 심심치 않게 보입니다.

Heritage Center-'Cobh'

기차역 부근에 상점과 박물관이 몰려있는데요.
사람들은 주로 그 주변에서 시간을 보내다가 집으로 돌아갑니다.
그럼 코브는 타이타닉이 유명한 관광지라는 기억으로만 남을 테지요.
그건 참 아쉬운 일입니다.
언덕을 올라가면 코브의 소박한 풍경이 한눈에 들어 오거든요.

성당-'Cobh'

가장 경치 좋은 곳엔 신고딕 양식(?)으로 지어진 성당이 서 있어요.
이 성당 앞마당에서 코브를 내려다보면 마치 파리의 몽마르뜨에 온 듯 합니다.
저는 이곳이 마음에 들어요.
몽마르뜨는 워낙 유명한 장소라 사람으로 붐비지만,
코브의 언덕배기엔 그리 많은 사람이 올라오진 않거든요.

오래된 집-'Cobh'

마을을 내려다보니 오랜 세월 한 자리에 서 있던 집들이 보입니다.
요즘 지어지는 집과 별다른 점이 없어 보이죠?
잘 보면 집마다 굴뚝이 여러 개입니다.
코크에도 이런 집들이 좀 되지만 무심코 지나쳤었는데,
여기선 그것이 유난히 눈에 띄어 오랫동안 바라봤어요.
굴뚝이 네 개인 곳도 보이고, 여덟 개씩이나 되는 집도 있죠.
중앙난방이 안되던 시절엔, 방마다 벽난로가 있었답니다.
그래서 방 개수만큼 굴뚝이 필요하던 거죠.
겨울이면 방마다 먼지 날리고 청소하기 참 어려웠겠어요.
우리나라 선조의 지혜에 다시 한번 감탄했습니다.
지리산 칠불사(七佛寺)의 아자방(亞字房)은 한번 불을 지피면 49일이나 따뜻했다는 이야기도 있잖아요. :D

벽화-'Cobh'

코브 구경을 마치고 기차역으로 돌아가는 길에 커다란 벽화가 보입니다.
타이타닉이 침몰한 지 100년이 흘렀다네요.
내년엔 이곳에 101주년을 알리는 벽화가 그려지겠지요.



by


Tags : , , , ,

  • 재미있게 읽으셨나요?
    방랑자의 이야기.
    월풍도원에선 기부를 받습니다.