[日本語訳] PREFERENCES - DEVELOPER GUIDE | SPREE COMMERCE

Spreeのドキュメントを日本語に訳しました。意訳や怪しい部分もあるのでおかしなところがあればご指摘いただけますと幸いです。

[PREFERENCES - DEVELOPER GUIDE | SPREE COMMERCE](https://guides.spreecommerce.com/developer/preferences.html)

## 概要

Spreeプリファレンスはアプリケーション全体の設定のサポートと、モデルインスタンスごとのプリファレンスがあります。Spreeはあなたのストアの`logo`や`currency`にプリファレンスを使っています。追加プリファレンスはあなたのアプリケーションやエクステンションに追加することができます。

モデルにプリファレンスを使う場合、ただ`preferences`という新しいカラムを追加するだけです。これは`spree_products`テーブルに対するマイグレーションの例です。

```rb
class AddPreferencesColumnToSpreeProducts < ActiveRecord::Migration
  def up
    add_column :spree_products, :preferences, :text
  end

  def down
    remove_column :spree_products, :preferences
  end
end
```

これは`Spree::Product`が`Spree::Base`のサブクラスなので動作します。それが見つかった場合、`preferences`アトリビュートは`Hash`としてシリアライズされ、デフォルト値とともにマージされます。

別の例を挙げると、ユーザーに対して通知設定を管理するためにプリファレンスを追加したいとします。`User`モデルが`Spree::Base`を継承していることを確認したうえで`preferences`カラムを追加してください。そうすれば特別なカラム等をデータベースに追加することなく、プリファレンスを`User`に使うことができるでしょう。

もし`spree_auth_devise`を使っているならば、提供されている`Spree::User`は`Spree::Base`を継承していないことにご留意ください。

エクステンションはSpreeの全般設定を追加したり、独自のネームスペースのプリファレンスを作る場合があります。

このガイドの最初のいくつかのセクションではごく一般的なプリファレンスについて記述します。もし設定済みのプリファレンスの変更について知りたいならば、Configuring Spree Preferences sectionまでスキップしてください。もしプリファレンスのシステムの根本的なコンセプトについて深く理解したいならばこのまま読み進めてください。

### Motivation

アプリケーションにおけるモデルのプリファレンスは大変一般的です。あくまでも原則は、利用できるプリファレンスの数を最小限に保つことですが、ユーザーへの電子メール通知を無効化したいなど、時としてそれが必要な場合もあります。

いずれのユースケースも、Spreeプリファレンスにより管理されています。これらは簡単に定義でき、読み込みも早く、再起動しても消えず、モデルのテーブルに追加カラムを必要としません。

## Gereral Settings

Spreeは、アプリケーション全体に関わる多くのプリファレンスを持っています。それらは`core/app/models/spree/app_configuration.rb`で管理されており、`Spree::Config`や`Spree::Config.site_name`などのコードを通して取得できます。

全般設定のいくつかは、あなたのストアの管理者インターフェースでも扱えます。（`/admin/general_settings`）

追加のプリファレンスは`spree/app_configuration`のネームスペース下で追加するか、`Preferences::Configuration`のサブクラスを作ることで設定できます。

```rb
# These will be saved with key: spree/app_configuration/hot_salsa
Spree::AppConfiguration.class_eval do
  preference :hot_salsa, :boolean
  preference :dark_chocolate, :boolean, :default => true
  preference :color, :string
  preference :favorite_number
  preference :language, :string, :default => 'English'
end

# Spree::Config is an instance of Spree::AppConfiguration
Spree::Config.hot_salsa = false

# Create your own class
# These will be saved with key: kona/store_configuration/hot_coffee
Kona::StoreConfiguration < Preferences::Configuration
  preference :hot_coffee, :boolean
  preference :color, :string, :default => 'black'
end

KONA::STORE_CONFIG = Kona::StoreConfiguration.new
puts KONA::STORE_CONFIG.hot_coffee
```

## プリファレンスの定義

モデルのプリファレンスは、モデル内で定義することができます。

```rb
class User < ActiveRecord::Base
  preference :hot_salsa, :boolean
  preference :dark_chocolate, :boolean, :default => true
  preference :color, :string
  preference :favorite_number, :integer
  preference :language, :string, :default => "English"
end
```

上記のモデルでは５つのプリファレンスが定義されています。

* hot_salsa
* dark_chocolate
* color
* favorite_number
* language

プリファレンスごとにデータ型が提供されています。下記の型が利用可能です。

* boolean
* string
* password
* integer
* text
* array
* hash

特定のインスタンスで値がセットされずに使われる場合には、オプションであるデフォルト値を使うこともできます。

## Accessing Preferences

一旦モデルに対してプリファレンスが定義されると、各プリファレンスに対して自動生成されるショートカットメソッド、特定のプリファレンスを対象としない汎用メソッドのいずれかでアクセスができます。

### ショートカットメソッド

生成されるのは、いくつかのショートカットメソッドがあります。以下に示します。

#### Query methods

```
user.prefers_hot_salsa? # => false
user.prefers_dark_chocolate? # => false
```

#### Reader methods

```
user.preferred_color      # => nil
user.preferred_language   # => "English"
```

#### Writer methods

```
user.prefers_hot_salsa = false         # => false
user.preferred_language = "English"    # => "English"
```

#### Check if a preference is available

```
user.has_preference? :hot_salsa
```

### Generic Methods

各ショートカットメソッドは、基本的に、以下に示す様々な汎用メソッドのラッパーです。

#### Query method

```
user.prefers?(:hot_salsa)       # => false
user.prefers?(:dark_chocolate)  # => false
```

#### Reader methods

```
user.preferred(:color)      # => nil
user.preferred(:language)   # => "English"

user.get_preference :color
user.get_preference :language
```

#### Writer method

```
user.set_preference(:hot_salsa, false)     # => false
user.set_preference(:language, "English")  # => "English"
```

### Accessing All Preferences

全ての記録されたプリファレンスに、`preferences`ヘルパーを使って取得できます。

```
user.preferences # => {"language"=>"English", "color"=>nil}
```

このハッシュは、値が初期値か保存されているかに関わらず、モデルインスタンスに定義された全てのプリファレンスの値を取得します。

### Default and Type

プリファレンスのデフォルト値にアクセスすることもできます。

```
user.preferred_color_default # => 'blue'
```

型はフォームの生成やプリファレンスの表示に使われます。またプリファレンスの型の取得も可能です。

```
user.preferred_color_type # => :string
```

## Spreeプリファレンスの変更

ここまで、我々はSpreeにおける一般的なプリファレンスについてお話してきました。これは、一般的なプリファレンスに関しての考え方でした。次は、Spreeが環境設定にどのようにプリファレンスを用いているかしっかりと見てゆきましょう。

### Reading the Current Preferences

Spreeプリファレンスの心臓部は`Spree::Config`定数にあります。このオブジェクトはアプリケーションのどこからでも設定状況にアクセスすることを提供しています。

この設定はinitializer、モデル、コントローラ、ビューなど色々な場所から読み込むことができます。

`Spree::Config`定数は、`Spree::AppConfiguration`のインスタンスを返し、これはSpree全体のプリファレンスのデフォルト値が格納されている場所です。

またコード内で直接プリファレンスにアクセスすることもできます。`rails console`を起動して、下記を試してみてください。

```
>> Spree::Config.admin_interface_logo
=> "logo/spree_50.png"
>> Spree::Config.admin_products_per_page
=> 10
```

上記の例は、これらのプリファレンスの初期値を表示しています。デフォルト値そのものは`Spree::AppConfiguration`クラスにかかれています。

```
class Spree::AppConfiguration < Configuration
  #... snip ...
  preference :allow_guest_checkout, :boolean, default: true
  #... snip ...
end
```

もしあなたが一切の変更をせずにデフォルトプリファレンスを使用したい場合には、データベースに何も保存しないでください。もしプリファレンスの値をセットして`spree_preferences`か`preferences`カラムに保存すると、パフォーマンスを維持するためにメモリにキャッシュされた値を使用します。

### デフォルトプリファレンスの上書き

`Spree::AppConfiguration`内にあるSpreeプリファレンスのデフォルト値は`Spree::Config`モジュールの`set`メソッドを使うことで変更できます。例えば、管理者インターフェース内、商品リストの数を変更したい場合は下記のように行います。

```
>> Spree::Config.admin_products_per_page = 20
=> 20
>> Spree::Config.admin_products_per_page
=> 20
```

ここで、プリファレンスを`Spree::AppConfiguration`に指定されていたものから他の値に変更しました。この場合、プリファレンスのシステムは`spree_preferences`テーブル内にある新しい値を優先します。

### Configuration Through the Spree Initializer

Spreeのインストールプロセスの間に、initializerファイルがアプリケーションソースコードの中に生成されました。このinitializerファイルは`config/initializers/spree.rb`に存在します。

```
Spree.config do |config|
  # Example:
  # Uncomment to override the default site name.
  # config.site_name = "Spree Demo Site"
end
```

`Spree.config`ブロックは、`Spree::Config`へのショートカットです。もし複数のプリファレンスをコード内で上書きしたい場合にはここに記述してください。デフォルトセッティング用のイニシャライザーは素晴らしいショートカットで、プリファレンスを正しい場所に設置するのに便利です。

例えば、もしロゴの場所を変更したい、もし配送先住所の税率を変更したい場合には下記のコードで実現することができます。

```
Spree.config do |config|
  config.admin_interface_logo = 'logo/my_store.png'
  config.tax_using_ship_address = true
end
```

`config/initializer.rb`内にあるイニシャライザーのプリファレンスは、再起動したときに管理者インターフェースにより上書きされます。

### Configuration Through the Admin Interface

Spreeの管理者インターフェースは様々な設定ができるいくつかの画面から構成されています。例えば`admin/general_settings`URLはSpreeアプリケーションのサイト名、サイトURLを変更することが可能です。これは基本的に`Spree::Config.set(currency: "CDN", currency_thousands_separator: " ")`をRubyのコードにて呼び出すのと同意義です。

## Site-Wide Preferences

`Spree::Preferences::Configuration`を継承した設定ファイルをを作ることで、特定のモデルインスタンスだけではない、サイト全体に適用されるプリファレンスを定義することができます。

```
class Spree::MyApplicationConfiguration < Spree::Preferences::Configuration
  preference :theme, :string, :default => "Default"
  preference :show_splash_page, :boolean
  preference :number_of_articles, :integer
end
```

上記の設定ファイルは、３つのプリファレンスが定義されています。

* theme
* sho_splash_page
* number_of_articles

設定ファイルは、`lib/`ディレクトリに作ることをオススメします。

エクステンションもまたサイト全体のプリファレンスを定義できます。エクステンションでプリファレンスを使うより詳しい情報は、エクステンションチュートリアルをご覧ください。

### Configuring Site-Wide Preferences

サイト全体のプリファレンスを設定する場合は、イニシャライザーを使うのがオススメです。プリファレンスを設定する先ほどの例を見てみましょう。

```rb
module Spree
  MyApp::Config = Spree::MyApplicationConfiguration.new
end

MyApp::Config[:theme] = "blue_theme"
MyApp::Config[:show_spash_page] = true
MyApp::Config[:number_of_articles] = 5
```

`config/application.rb`です。`MyApp`という名前は例として用いられていますので、実際のアプリケーション名に置き換える必要があります。

上記の例では、以前に定義したプリファレンスを設定します。二行目に注意してください。プリファレンスをセット、取得するために`MyApp::Config`を使っていますが、最初にオブジェクト化しなければなりません。

## Spree Configuration Options (割愛)

このセクションでは、Spreeの現在のバージョンに用いられているオプション項目をリスト化します。

こちらは翻訳を割愛しておりますので、原文をご覧ください。