提供: Minecraft Modding Wiki
移動先: 案内検索
(設定ファイルのオブジェクト)
(利用例: コードミスの修正)
 
(2人の利用者による、間の37版が非表示)
1行目: 1行目:
Configuration APIは、人が読み書き可能な形式のコンフィグファイルの、<br/>
+
Configuration APIは、人が読み書き可能な形式のコンフィグファイルの解析と出力を素早く行う機能のセットです。<br/>
解析と出力を素早く行う機能のセットです。<br/>
 
  
 
~APIという名前によらず、簡単にプラグインのデータを、コンフィグファイルへ保管する事が出来ます。<br/>
 
~APIという名前によらず、簡単にプラグインのデータを、コンフィグファイルへ保管する事が出来ます。<br/>
[http://en.wikipedia.org/wiki/YAML YAML] 形式のファイルのみに対応しています。<br/>
+
[http://ja.wikipedia.org/wiki/YAML YAML] 形式のファイルのみに対応しています。<br/>
 
APIは、いかに独自の拡張に対応しやすくするかを考えて設計されています。<br/>
 
APIは、いかに独自の拡張に対応しやすくするかを考えて設計されています。<br/>
  
16行目: 15行目:
  
 
== 基礎 ==
 
== 基礎 ==
=== 設定ファイルのオブジェクト ===
+
=== コンフィグファイルのオブジェクト ===
 
あなたのプラグインが[http://jd.bukkit.org/doxygen/d7/deb/classorg_1_1bukkit_1_1plugin_1_1java_1_1JavaPlugin.html JavaPlugin]をextendsし、フィールドとメソッドを継承しているものとして話を進めます。
 
あなたのプラグインが[http://jd.bukkit.org/doxygen/d7/deb/classorg_1_1bukkit_1_1plugin_1_1java_1_1JavaPlugin.html JavaPlugin]をextendsし、フィールドとメソッドを継承しているものとして話を進めます。
  
22行目: 21行目:
 
このオブジェクトは、プラグインのデータフォルダ配下の''config.yml''に相当します。
 
このオブジェクトは、プラグインのデータフォルダ配下の''config.yml''に相当します。
  
初めて''getConfig()''が呼び出されたタイミングで、''config.yml''はディスクからロードされ、プラグインのJarファイル中に定義されたデフォルト値もロードされます。
+
初めて''getConfig()''が呼び出されたタイミングでは、ディスク上の''config.yml''の内容と、プラグインのJarファイル中に定義されたデフォルト値が、メモリ上にロードされ、その内容が戻り値として返されます。2回目以降の''getConfig()''の呼び出しでは、メモリ上に存在する''FileConfiguration''オブジェクトが戻り値として返されます。
その後の''getConfig()''の呼び出しでは、メモリ上に存在する''FileConfiguration''オブジェクトがreturnされます。
 
  
 
このオブジェクトは、明示的に保存しない限りディスクへ保持されません。同様に、''config.yml''ファイルに加えられた変更も、メモリ上にロード済みのオブジェクトには反映されません。
 
このオブジェクトは、明示的に保存しない限りディスクへ保持されません。同様に、''config.yml''ファイルに加えられた変更も、メモリ上にロード済みのオブジェクトには反映されません。
  
 
''config.yml''がデータフォルダ配下に存在しない場合は、空の''config.yml''ファイルを読み込んだ事と等しい結果となり、''FileConfiguration''オブジェクトも空の状態でロードされます。
 
''config.yml''がデータフォルダ配下に存在しない場合は、空の''config.yml''ファイルを読み込んだ事と等しい結果となり、''FileConfiguration''オブジェクトも空の状態でロードされます。
 +
 
{{warning}} ''getConfig()''の戻り値は、staticなフィールドに割り当てないで下さい。
 
{{warning}} ''getConfig()''の戻り値は、staticなフィールドに割り当てないで下さい。
{{warning}} このような割り当てを行うと、''getConfig()''はreloadConfigの後でも再び割り当て処理を繰り返してしまいます。{{note}}''getConfig()''の戻り値は一旦適切なフィールドに割り当ててから利用する事をお勧めします
 
  
=== デフォルトのコンフィグ値 ===
+
{{warning}} このような割り当てを行うと、''getConfig()''はreloadConfigの後でも再び割り当て処理を繰り返してしまいます。
 +
 
 +
{{note}}''getConfig()''の戻り値は一旦適切なフィールドに割り当ててから利用する事をお勧めします
 +
 
 +
 
 +
=== キー ===
 +
 
 +
コンフィグファイルは、すべての設定内容が、Stringのkeyと、valueのペアで構成されています。
 +
valueは、ConfigurationSection または、単一値の型になります。
 +
 
 +
FileConfigurationSection の ''getKeys(boolean)'' メソッドは、指定されたセクション以下のkeyを返します。
 +
 
 +
falseが指定された場合は、セクション直下にあるkeyが返されます。
 +
trueが指定された場合は、セクション直下だけでなく、その子セクションや孫セクションも含めて全てのkeyが返されます。
 +
ある特定のセクションを取得したい場合は、''getKeys(boolean)'' で探して取得する方法もありますが、''getConfigurationSection(String)'' を使って直接取得することもできます。
 +
 
 +
{{warning}} ''getKeys(boolean)'' メソッドは、Set<String> を返します。
 +
 
 +
 
 +
=== パス ===
 +
 
 +
コンフィグAPIは、キーと値を階層的に持つことができます。
 +
ピリオド(.)で区切ることで、階層をそのまま指定して、セクションやvalueを取得することができます。
 +
実例を見てみましょう。
 +
 
 +
<blockquote><source lang="yaml">
 +
key: 'value'
 +
one:
 +
  two: 'value'
 +
  three:
 +
    - 1
 +
    - 2
 +
    - 3
 +
  four:
 +
    five: 'value'
 +
  '*':
 +
    six: 'value'
 +
    seven: 'value'
 +
</source></blockquote>
 +
 
 +
上記の例では、次のようにkeyを指定することで、valueを取得できます。
 +
 
 +
*getString("key") → value というStringが取得されます
 +
*getConfigurationSection("one") → one の部分がConfigurationSectionで取得されます
 +
*getString("one.two") → value というStringが取得されます
 +
*getIntegerList("one.three") → [1, 2, 3] というIntegerの配列が取得されます
 +
*getConfigurationSection("one.four") → four の部分がConfigurationSectionで取得されます
 +
*getString("one.four.five") → value というStringが取得されます
 +
*getConfigurationSection("one.*") → '*' の部分がConfigurationSectionで取得されます
 +
*getString("one.*.six") → value というStringが取得されます
 +
*getString("one.*.seven") → value というStringが取得されます
 +
 
 +
=== デフォルト値 ===
 +
 
 +
あなたのプラグインの設定ファイル''config.yml''は、プラグイン利用者のために、デフォルト値を設定するようにしてください。
 +
 
 +
もし''config.yml''が、プラグインのデータフォルダ配下に存在しない, 空である, キーが無い・・・といった状態である場合には、プラグインのJarファイル内に含まれる''config.yml''に定義された値が、デフォルト値として使用されます。
 +
 
 +
デフォルト値として使用する''config.yml''は、Jarファイルのトップに配置されるようにしてください。
 +
[[Plugin YAML|plugin.yml]]と同一の場所になります。
 +
 
 +
プラグインのデータフォルダ配下の''config.yml''をデフォルト値で上書きしたい場合は、JavaPluginクラスの''saveDefaultConfig()''メソッドを呼び出してください。
 +
 
 +
<blockquote><source lang="java">this.saveDefaultConfig()</source></blockquote>
 +
 
 +
データフォルダにある''config.yml''の既存の設定値を上書きしたくないが、Jarファイル内にある''config.yml''に定義されている新しいキーと値のペアを追加したい場合は、copyDefaults(true) を実行してください。
 +
 
 +
<blockquote><source lang="java">this.getConfig().options().copyDefaults(true)</source></blockquote>
 +
 
 +
<strike>config.ymlに ShiftJISで日本語を含めたプラグインは、Windowsでしか正常に起動しなくなります。</strike><br>
 +
<strike>逆に、UTF-8N(BOM無し) で日本語を含めたプラグインは、MacintoshとLinuxでしか正常に起動しなくなります。</strike><br>
 +
Bukkit 1.9 以降のバージョンでは、config.yml に日本語などのマルチバイト文字を含めたい場合は、常に UTF-8N(BOM無し) のエンコードで作成してください。
 +
 
 
=== コンフィグ値の取得 ===
 
=== コンフィグ値の取得 ===
==== Keys ====
+
 
 +
コンフィグ値の読み込み処理は、複数のgetterメソッドの呼び出し処理から成ります。全てのgetterメソッドの一覧は[http://jd.bukkit.org/doxygen/dd/d7c/classorg_1_1bukkit_1_1configuration_1_1file_1_1FileConfiguration.html こちら]です。一般的な用途のgetterメソッドは下記です。
 +
*getBoolean(String)
 +
*getInt(String)
 +
*getString(String)
 +
*getList(String)
 +
*getStringList(String)
 +
 
 +
 
 
=== コンフィグ値のセット ===  
 
=== コンフィグ値のセット ===  
==== HashMaps ====
+
コンフィグ値をセットするには、設定ファイルのインスタンスの''set(String, Object)''メソッドを利用します。''FileConfiguration''のgetメソッドとは異なり、setメソッドは1種類しか存在しません。setメソッドであらゆる型のオブジェクトがセット出来る訳ではく、下記のデータ型のオブジェクトだけがセット可能です。
=== コンフィグファイルのセーブ ===  
+
*プリミティブ
=== ディスクからのリロード ===  
+
*''String''
 +
*''List''
 +
*''Vector''や''ItemStack''のような''ConfigurationSerializable''インタフェースを実装した型
 +
 
 +
コンフィグ値を削除するにはnullをセットします。セット処理は、メモリ上に展開されたコンフィグ値に対してのみ行われ、コンフィグ値をファイルにセーブしなければ、サーバを再起動したタイミング(正確にはプラグインがdisabledされたタイミング)で失われます。
 +
 
 +
利用例: <blockquote><source lang="java">
 +
// boolean値をセットします。
 +
this.getConfig().set("path.to.boolean", true);
 +
 
 +
// String値をセットします。
 +
this.getConfig().set("path.to.string", "みなさんこんにちは!");
 +
 
 +
// StringのListをセットします。
 +
// 配列はセットできないので、List<String>型に変換してセットします。
 +
String[] listOfStrings = {"こんにちは!", "いらっしゃいませ!", "楽しんでね!"};
 +
this.getConfig().set("path.to.list", Arrays.asList(listOfStrings));
 +
 
 +
// Vector(Bukkitのクラス)の値をセットします。
 +
Vector vector = event.getPlayer().getLocation().toVector();
 +
this.getConfig().set("path.to.vector", vector);
 +
 
 +
// 値を削除します。
 +
this.getConfig().set("path.to.boolean", null);
 +
</source></blockquote>
 +
 
 +
==== HashMapの活用 ====
 +
''HashMap''をコンフィグ値としてセーブする場合は、''ConfigurationSection''を利用して下さい。
 +
また、HashMapはキーがString型、値が''ConfigurationSerializable''を実装したデータ型でなければなりません。
 +
<blockquote><source lang="java">createSection (String path, Map< String, Object > map)</source></blockquote>
 +
 
 +
=== コンフィグファイルのセーブ ===
 +
setメソッドを利用して''FileConfiguration''に多くの変更を加えるか、''Lists''(設定値インスタンスの内部値がList派生型になっている領域を指している)の内容を変更した場合、プラグインの無効化後も残したい設定値であればディスクに書き出すべきです。'''saveConfig'''メソッドを呼び出して、既存の(ディスク上の)コンフィグファイルに上書き保存しましょう。<blockquote><source lang="java">this.saveConfig();</source></blockquote>
 +
 
 +
 
 +
=== ディスクからのリロード ===
 +
プラグインのデータフォルダ上の''config.yml''が、ユーザによって変更されている可能性を疑って下さい。この変更点はメモリ上の設定値に反映されていません。''reloadConfig()''メソッドを呼び出して、ディスク上の設定値をプラグインにロードする事ができます。ただしメモリ上の設定値が、ロード内容で上書きされる事にも留意して下さい。
 +
<blockquote><source lang="java">this.reloadConfig();</source></blockquote>
 +
 
 +
 
 +
=== 別の設定ファイルを利用する ===
 +
もしあなたが、''config.yml''ではなく、別のYamlファイルを利用したい場合は、YamlConfiguration クラスを使って読み込むことができます。
 +
 
 +
<blockquote><source lang="java">
 +
FileConfiguration data = YamlConfiguration.loadConfiguration(new File(getDataFolder(), "data.yml"));
 +
</source></blockquote>
 +
 
 +
上記のサンプルコードは、データフォルダにある''data.yml''ファイルを読み込んで、FileConfiguration を返します。<br/>
 +
もし、データフォルダに''data.yml''が存在しない場合は、空っぽの FileConfiguration が返されます。<br/>
 +
 
 +
<!-- なんか微妙。この説明、要るかなあ?
 +
もしあなたが、Jarファイル内の''data.yml''を読み出したいなら、InputStreamを使って次のようにロードすることが可能です。
 +
 
 +
<blockquote><source lang="java">
 +
FileConfiguration data = YamlConfiguration.loadConfiguration(getResource("data.yml"))
 +
</source></blockquote>
  
 +
This takes the InputStream from getResource, which gets a file embedded in the jar, and retreives a FileConfiguration from that.
 +
-->
 +
 +
<!-- 下記の内容は、内容が難しくて、かえって混乱を生むので、いまのところ非表示にしています。
 
== 応用 ==
 
== 応用 ==
 +
 +
以下は、より高度なプラグインを製作するための、応用のトピックです。<br>
 +
あなたが既定の''config.yml''を作成したり読み込んだり保存したいだけであれば、下記を読む必要はありません。
 +
 
=== コンフィグのオプション ===
 
=== コンフィグのオプション ===
==== デフォルト値のコピー ====
+
 
==== パスのセパレータ ====
+
全ての''FileConfiguration''インスタンスは、[http://jd.bukkit.org/apidocs/index.html?org/bukkit/configuration/file/FileConfigurationOptions.html FileConfigurationOptions] オブジェクトに紐付いています。<br>
==== ヘッダ ====
+
''FileConfigurationOptions''オブジェクトは、''FileConfiguration''の動作を制御することができます。<br>
 +
''FileConfiguration''の''options()''メソッドは、対応した''FileConfigurationOptions''を返します。<br>
 +
これを使って、オプションの現在内容の確認をしたり、設定を行うことができます。<br>
 +
現在、4つのオプションがあります。<br>
 +
メソッドはオーバーロードされているものがあり、例えば、''copyDefaults()''はブール値を返しますが、''copyDefaults(boolean)''は自分自身を返します。<br>
 +
'''訳者注''' 引数を指定しないメソッドは現在のオプション値を返し、引数を指定するメソッドはオプション値を設定するメソッドです。
 +
 
 +
==== CopyDefaults ====
 +
 
 +
''CopyDefaults''オプションは''Configuration''クラスのsaveメソッドの動作を変更します。<br>
 +
既定はfalseで、デフォルトのコンフィグを保存先ファイルに上書きしません。<br>
 +
引数にtrueを設定した場合、ファイルの上書きをするようになります。<br>
 +
しかし、1度書き込みが行われるのみで、あなたがデフォルト値を変更したとしてもその値が即座に反映されるわけではありません。
 +
 
 +
==== PathSeparator ====
 +
 
 +
PathSeparatorは、コンフィグの階層を示すセパレータ文字の変更を行うことができます。<br>
 +
既定では「.」(ピリオド)ですが、好きな文字へ変更することが可能です。
 +
 
 +
==== Header ====
 +
 
 +
HeaderはYAMLファイルの上部のコメントブロックの変更を行うことができます。<br>
 +
HeaderはコンフィグAPIの中で、唯一、コメントをコピーすることができる手段です。
 +
 
 
==== copyHeader() ====
 
==== copyHeader() ====
=== 取得・リロード・セーブとカスタマイズ ===
+
 
=== シリアライズとデ・シリアライズ ===
+
もし''copyHeader()''がtrueを返したら、既定のconfig.ymlから保存先にヘッダーを保存したことを示します。
 +
 
 +
=== 任意の設定 ===
 +
 
 +
構成情報の格納やゲームの追加情報を保存する追加の YAML ファイルが必要な場合は、追加のコンフィグファイルにアクセスするための独自のメソッドを記述する必要があります。<br>
 +
JavaPlugin クラスの getConfig、reloadConfig、saveConfig メソッドをモデルとして、カスタムコンフィグファイルを保存する独自のメソッドを記述する方法を示します。<br>
 +
これらの config ファイルはプラグインに属しているため、config.yml が配置されるパッケージにおいて、アクセス権をもったメソッドからアクセスされる必要があります。<br>
 +
これらのメソッドの各 YAML ファイルのセットを記述する必要があります。<br>
 +
ここでは、利点はであるデフォルトの config.yml を提供されているメソッドと同じ方法で各セットを使用することができます。<br>
 +
代わりに、追加メソッドは少なくすみ、複数ファイルへのアクセスをすることもできます。
 +
 
 +
==== JavaPlugin 実装をミラーリング ====
 +
 
 +
JavaPlugin メソッドの config.yml を実装します。<br>
 +
プラグインはプラグインに固有のコンフィグファイルにアクセスする独自のメソッドを実装する必要があります。<br>
 +
プラグインのメソッドを実装した後、それと同じコンテキストで継承された''getConfig()''、 ''reloadConfig()''、 ''saveConfig()''、および ''saveDefaultConfig()''メソッドで呼び出すことができます。<br>
 +
下記のコード例では、1つのクラスで複数の yaml ファイルにアクセスすることができます。<br>
 +
このようなクラス実装例を、 [https://gist.github.com/3174347 ここに] 示します。
 +
 
 +
まず、2つのフィールドを宣言し、カスタム構成ファイルごとに null に初期化する必要があります。<br>
 +
1つは''FileConfiguration''オブジェクトを保持し、1つは''File''オブジェクトを保持します。<br>
 +
Fileオブジェクトはディスク上のファイル、FileConfiguration は設定の内容を表します。
 +
 
 +
<blockquote><source lang="java">
 +
private FileConfiguration customConfig = null;
 +
private File customConfigFile = null;
 +
</source></blockquote>
 +
 
 +
===== リロードの実装 =====
 +
 
 +
次に、ディスクからコンフィグを読み込むメソッドを記述します。<br>
 +
ファイルをロードし、デフォルトの customConfig.yml の jar を検索します。
 +
 
 +
<blockquote><source lang="java">
 +
public void reloadCustomConfig() {
 +
    if (customConfigFile == null) {
 +
        customConfigFile = new File(getDataFolder(), "customConfig.yml");
 +
    }
 +
    customConfig = YamlConfiguration.loadConfiguration(customConfigFile);
 +
 
 +
    // jarファイルの中からデフォルトを探します。
 +
    InputStream defConfigStream = this.getResource("customConfig.yml");
 +
    if (defConfigStream != null) {
 +
        YamlConfiguration defConfig = YamlConfiguration.loadConfiguration(defConfigStream);
 +
        customConfig.setDefaults(defConfig);
 +
    }
 +
}
 +
</source></blockquote>
 +
 
 +
===== 取得処理の実装 =====
 +
 
 +
次に、取得処理メソッドを記述する必要があります。<br>
 +
CustomConfigをディスクから読み込む場合、nullであるかを確認します。
 +
 
 +
<blockquote><source lang="java">
 +
public FileConfiguration getCustomConfig() {
 +
    if (customConfig == null) {
 +
        this.reloadCustomConfig();
 +
    }
 +
    return customConfig;
 +
}
 +
</source></blockquote>
 +
 
 +
===== 保存の実装 =====
 +
 
 +
最後に、変更を保存しディスク上のファイルを上書きする、保存メソッドを記述します。
 +
 
 +
<blockquote><source lang="java">
 +
public void saveCustomConfig() {
 +
    if (customConfig == null || customConfigFile == null) {
 +
        return;
 +
    }
 +
    try {
 +
        getCustomConfig().save(customConfigFile);
 +
    } catch (IOException ex) {
 +
        this.getLogger().log(Level.SEVERE, "Could not save config to " + customConfigFile, ex);
 +
    }
 +
}
 +
</source></blockquote>
 +
 
 +
===== 規定値の実装 =====
 +
 
 +
必要に応じて、JavaPlugin の saveDefaultConfig() メソッドを模倣するメソッドを記述することができます。
 +
 
 +
<blockquote><source lang="java">
 +
public void saveDefaultConfig() {
 +
    if (customConfigFile == null) {
 +
        customConfigFile = new File(getDataFolder(), "customConfig.yml");
 +
    }
 +
    if (!configFile.exists()) {
 +
        this.plugin.saveResource(fileName, false);
 +
    }
 +
}
 +
</source></blockquote>
 +
 
 +
=== シリアライズとデシリアライズ ===
 +
 
 +
コンフィグAPI は、前述のように''ConfigurationSerializable''インターフェイスを実装する Java オブジェクトを格納することができます。<br>
 +
オブジェクトのシリアル化では、各種オブジェクトを簡単に保存したり読み込んだりする仕組みを、実装者に提供してくれています。<br>
 +
例えば開発者は、''[http://jd.bukkit.org/doxygen/da/dac/classorg_1_1bukkit_1_1Location.html Location]''を取得できるシリアライズラッパークラスを使うことで、YAMLに''Location''を保存するような処理がとても簡単に使用することができます。
 +
 
 +
API でシリアル化することができるクラスを実装するには、''ConfigurationSerializable''インターフェイスを実装するだけでなく、以下のいずれかを実装する必要があります。<br>
 +
* '''1つの''Map''を受け入れるコンストラクター''' <source lang="java">public PlayerData(Map data) {</source>
 +
* '''1つの''Map''を受け入れてクラスを返す、"deserialize" という名前のstaticメソッド''' <source lang="java">public static PlayerData deserialize(Map data) {</source>
 +
* '''1つの''Map''を受け入れてクラスを返す、"valueOf" という名前のstaticメソッド''' <source lang="java">public static PlayerData valueOf(Map data) {</source>
 +
 
 +
シリアライズされたオブジェクトをデシリアライズするには、ConfigurationSerialization に登録されている必要があります。<br>
 +
registerClass メソッドは、シリアル化されたクラスごとに1回ずつ実行してください。
 +
 
 +
このステートメントは、メインクラスの初期化ブロックに記述することができます。
 +
 
 +
<blockquote><source lang="java">
 +
ConfigurationSerialization.registerClass(Class<? extends ConfigurationSerializable>)
 +
</source></blockquote>
 +
 
 
==== エイリアス ====
 
==== エイリアス ====
 +
 +
クラスがシリアル化されるとき、完全修飾名でマークされています。
 +
 +
エイリアスをクラスに設定しておくと、完全修飾名の代わりにエイリアスでマークされます。<br>
 +
''SerializeAs''アノテーションを、ConfigurationSerializableを実装するクラスに指定します。
 +
<source lang="java">@SerilizeAs(String)</source>
 +
 +
エイリアスをクラス登録と共に行いたい場合は、登録時に引数に一緒に指定します。
 +
 +
<blockquote><source lang="java">
 +
ConfigurationSerialization.registerClass(Class<? extends ConfigurationSerializable>, String)
 +
</source></blockquote>
 +
 +
-->
  
 
== 利用例 ==
 
== 利用例 ==
 +
 +
以下は、新しい Configuration API を使ってプラグインを実装した例です。<br>
 +
プレイヤー参加時に config.yml から message を取得して MOTD としてメッセージを表示したり、
 +
rulesコマンド実行時に config.yml から rules を取得して表示したりします。<br>
 +
なるべく手短な例を示したので、最適な実装例になっていないことをご了承ください。
 +
 +
<blockquote><source lang="java">
 +
import java.util.*;
 +
import org.bukkit.command.*;
 +
import org.bukkit.event.*;
 +
import org.bukkit.plugin.java.JavaPlugin;
 +
import org.bukkit.configuration.file.FileConfiguration;
 +
 +
public class SimpleMOTD extends JavaPlugin {
 +
 +
    @Override
 +
    public void onEnable() {
 +
        // もしconfig.ymlが存在しないなら、既定のconfig.ymlをコピーします。
 +
        this.saveDefaultConfig();
 +
 +
        // 新しいリスナーを登録します。
 +
        getServer().getPluginManager().registerEvents(new Listener() {
 +
 +
            @EventHandler
 +
            public void playerJoin(PlayerJoinEvent event) {
 +
                // プレイヤーがサーバーに参加したときに、config.ymlに書かれたメッセージを送ります。
 +
                event.getPlayer().sendMessage(SimpleMOTD.this.getConfig().getString("message"));
 +
 +
                // 特定のプレイヤーだった場合は、追加メッセージを送ります。
 +
                if ( SimpleMOTD.this.getConfig().contains("additional." + event.getPlayer().getName()) ) {
 +
                    event.getPlayer().sendMessage(SimpleMOTD.this.getConfig().getString(
 +
                            "additional." + event.getPlayer().getName()));
 +
                }
 +
            }
 +
        }, this);
 +
 +
        // rulesコマンドのCommandExecutorを登録します。
 +
        this.getCommand("rules").setExecutor(new CommandExecutor() {
 +
 +
            public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
 +
                // コマンド実行時にコマンド実行者へ、config.ymlのrulesの内容を送ります。
 +
                List<String> rules = SimpleMOTD.this.getConfig().getStringList("rules");
 +
                for (String s : rules) {
 +
                    sender.sendMessage(s);
 +
                }
 +
                return true;
 +
            }
 +
        });
 +
    }
 +
}
 +
</source></blockquote>
 +
 +
デフォルトのconfig.ymlの内容は、下記のとおりです。
 +
<source lang="yaml">
 +
# default config.yml
 +
message: Hello World and Welcome! :)
 +
rules:
 +
  - Play Nice
 +
  - Respect others
 +
  - Have Fun
 +
additional:
 +
  Anna: Hi Anna!
 +
  Billy: Hey Billy!
 +
</source>

2016年10月1日 (土) 14:35時点における最新版

Configuration APIは、人が読み書き可能な形式のコンフィグファイルの解析と出力を素早く行う機能のセットです。

~APIという名前によらず、簡単にプラグインのデータを、コンフィグファイルへ保管する事が出来ます。
YAML 形式のファイルのみに対応しています。
APIは、いかに独自の拡張に対応しやすくするかを考えて設計されています。

Configuration APIは、org.bukkit.configurationorg.bukkit.configuration.file パッケージの配下にあります。
Bukkit1.1-R5以前に作られたプラグインは、org.bukkit.util.configurationパッケージ配下に存在した、
古いライブラリを利用した実装を採用しているかもしれません。
新旧の実装方法には互換性がありませんので、古いパッケージを使う処理は除去して下さい。

このページの解説は、オブジェクト指向とJava、Bukkitプラグインの基本的な設計に関する知識が、
いくらかある読者に読まれる事を想定しています。
このページは、BukkitのJavadoc内のFileConfiguration Classに取って代わる内容ではありません。

基礎[編集]

コンフィグファイルのオブジェクト[編集]

あなたのプラグインがJavaPluginをextendsし、フィールドとメソッドを継承しているものとして話を進めます。

継承メソッドgetConfig()は、 org.bukkit.configuration.file.FileConfiguration型のオブジェクトをreturnしますが、 このオブジェクトは、プラグインのデータフォルダ配下のconfig.ymlに相当します。

初めてgetConfig()が呼び出されたタイミングでは、ディスク上のconfig.ymlの内容と、プラグインのJarファイル中に定義されたデフォルト値が、メモリ上にロードされ、その内容が戻り値として返されます。2回目以降のgetConfig()の呼び出しでは、メモリ上に存在するFileConfigurationオブジェクトが戻り値として返されます。

このオブジェクトは、明示的に保存しない限りディスクへ保持されません。同様に、config.ymlファイルに加えられた変更も、メモリ上にロード済みのオブジェクトには反映されません。

config.ymlがデータフォルダ配下に存在しない場合は、空のconfig.ymlファイルを読み込んだ事と等しい結果となり、FileConfigurationオブジェクトも空の状態でロードされます。

Attention.pngWarning: getConfig()の戻り値は、staticなフィールドに割り当てないで下さい。
Attention.pngWarning: このような割り当てを行うと、getConfig()はreloadConfigの後でも再び割り当て処理を繰り返してしまいます。
File Lightbulb.pngNote:getConfig()の戻り値は一旦適切なフィールドに割り当ててから利用する事をお勧めします


キー[編集]

コンフィグファイルは、すべての設定内容が、Stringのkeyと、valueのペアで構成されています。 valueは、ConfigurationSection または、単一値の型になります。

FileConfigurationSection の getKeys(boolean) メソッドは、指定されたセクション以下のkeyを返します。

falseが指定された場合は、セクション直下にあるkeyが返されます。 trueが指定された場合は、セクション直下だけでなく、その子セクションや孫セクションも含めて全てのkeyが返されます。 ある特定のセクションを取得したい場合は、getKeys(boolean) で探して取得する方法もありますが、getConfigurationSection(String) を使って直接取得することもできます。

Attention.pngWarning: getKeys(boolean) メソッドは、Set<String> を返します。


パス[編集]

コンフィグAPIは、キーと値を階層的に持つことができます。 ピリオド(.)で区切ることで、階層をそのまま指定して、セクションやvalueを取得することができます。 実例を見てみましょう。

key: 'value'
one:
  two: 'value'
  three:
    - 1
    - 2
    - 3
  four: 
    five: 'value'
  '*':
    six: 'value'
    seven: 'value'

上記の例では、次のようにkeyを指定することで、valueを取得できます。

  • getString("key") → value というStringが取得されます
  • getConfigurationSection("one") → one の部分がConfigurationSectionで取得されます
  • getString("one.two") → value というStringが取得されます
  • getIntegerList("one.three") → [1, 2, 3] というIntegerの配列が取得されます
  • getConfigurationSection("one.four") → four の部分がConfigurationSectionで取得されます
  • getString("one.four.five") → value というStringが取得されます
  • getConfigurationSection("one.*") → '*' の部分がConfigurationSectionで取得されます
  • getString("one.*.six") → value というStringが取得されます
  • getString("one.*.seven") → value というStringが取得されます

デフォルト値[編集]

あなたのプラグインの設定ファイルconfig.ymlは、プラグイン利用者のために、デフォルト値を設定するようにしてください。

もしconfig.ymlが、プラグインのデータフォルダ配下に存在しない, 空である, キーが無い・・・といった状態である場合には、プラグインのJarファイル内に含まれるconfig.ymlに定義された値が、デフォルト値として使用されます。

デフォルト値として使用するconfig.ymlは、Jarファイルのトップに配置されるようにしてください。 plugin.ymlと同一の場所になります。

プラグインのデータフォルダ配下のconfig.ymlをデフォルト値で上書きしたい場合は、JavaPluginクラスのsaveDefaultConfig()メソッドを呼び出してください。

this.saveDefaultConfig()

データフォルダにあるconfig.ymlの既存の設定値を上書きしたくないが、Jarファイル内にあるconfig.ymlに定義されている新しいキーと値のペアを追加したい場合は、copyDefaults(true) を実行してください。

this.getConfig().options().copyDefaults(true)

config.ymlに ShiftJISで日本語を含めたプラグインは、Windowsでしか正常に起動しなくなります。
逆に、UTF-8N(BOM無し) で日本語を含めたプラグインは、MacintoshとLinuxでしか正常に起動しなくなります。
Bukkit 1.9 以降のバージョンでは、config.yml に日本語などのマルチバイト文字を含めたい場合は、常に UTF-8N(BOM無し) のエンコードで作成してください。

コンフィグ値の取得[編集]

コンフィグ値の読み込み処理は、複数のgetterメソッドの呼び出し処理から成ります。全てのgetterメソッドの一覧はこちらです。一般的な用途のgetterメソッドは下記です。

  • getBoolean(String)
  • getInt(String)
  • getString(String)
  • getList(String)
  • getStringList(String)


コンフィグ値のセット[編集]

コンフィグ値をセットするには、設定ファイルのインスタンスのset(String, Object)メソッドを利用します。FileConfigurationのgetメソッドとは異なり、setメソッドは1種類しか存在しません。setメソッドであらゆる型のオブジェクトがセット出来る訳ではく、下記のデータ型のオブジェクトだけがセット可能です。

  • プリミティブ
  • String
  • List
  • VectorItemStackのようなConfigurationSerializableインタフェースを実装した型

コンフィグ値を削除するにはnullをセットします。セット処理は、メモリ上に展開されたコンフィグ値に対してのみ行われ、コンフィグ値をファイルにセーブしなければ、サーバを再起動したタイミング(正確にはプラグインがdisabledされたタイミング)で失われます。

利用例:

// boolean値をセットします。
this.getConfig().set("path.to.boolean", true);

// String値をセットします。
this.getConfig().set("path.to.string", "みなさんこんにちは!");

// StringのListをセットします。
// 配列はセットできないので、List<String>型に変換してセットします。
String[] listOfStrings = {"こんにちは!", "いらっしゃいませ!", "楽しんでね!"};
this.getConfig().set("path.to.list", Arrays.asList(listOfStrings));

// Vector(Bukkitのクラス)の値をセットします。
Vector vector = event.getPlayer().getLocation().toVector();
this.getConfig().set("path.to.vector", vector);

// 値を削除します。
this.getConfig().set("path.to.boolean", null);

HashMapの活用[編集]

HashMapをコンフィグ値としてセーブする場合は、ConfigurationSectionを利用して下さい。 また、HashMapはキーがString型、値がConfigurationSerializableを実装したデータ型でなければなりません。

createSection (String path, Map< String, Object > map)

コンフィグファイルのセーブ[編集]

setメソッドを利用してFileConfigurationに多くの変更を加えるか、Lists(設定値インスタンスの内部値がList派生型になっている領域を指している)の内容を変更した場合、プラグインの無効化後も残したい設定値であればディスクに書き出すべきです。saveConfigメソッドを呼び出して、既存の(ディスク上の)コンフィグファイルに上書き保存しましょう。

this.saveConfig();


ディスクからのリロード[編集]

プラグインのデータフォルダ上のconfig.ymlが、ユーザによって変更されている可能性を疑って下さい。この変更点はメモリ上の設定値に反映されていません。reloadConfig()メソッドを呼び出して、ディスク上の設定値をプラグインにロードする事ができます。ただしメモリ上の設定値が、ロード内容で上書きされる事にも留意して下さい。

this.reloadConfig();


別の設定ファイルを利用する[編集]

もしあなたが、config.ymlではなく、別のYamlファイルを利用したい場合は、YamlConfiguration クラスを使って読み込むことができます。

FileConfiguration data = YamlConfiguration.loadConfiguration(new File(getDataFolder(), "data.yml"));

上記のサンプルコードは、データフォルダにあるdata.ymlファイルを読み込んで、FileConfiguration を返します。
もし、データフォルダにdata.ymlが存在しない場合は、空っぽの FileConfiguration が返されます。


利用例[編集]

以下は、新しい Configuration API を使ってプラグインを実装した例です。
プレイヤー参加時に config.yml から message を取得して MOTD としてメッセージを表示したり、 rulesコマンド実行時に config.yml から rules を取得して表示したりします。
なるべく手短な例を示したので、最適な実装例になっていないことをご了承ください。

import java.util.*;
import org.bukkit.command.*;
import org.bukkit.event.*;
import org.bukkit.plugin.java.JavaPlugin;
import org.bukkit.configuration.file.FileConfiguration;

public class SimpleMOTD extends JavaPlugin {

    @Override
    public void onEnable() {
        // もしconfig.ymlが存在しないなら、既定のconfig.ymlをコピーします。
        this.saveDefaultConfig();

        // 新しいリスナーを登録します。
        getServer().getPluginManager().registerEvents(new Listener() {

            @EventHandler
            public void playerJoin(PlayerJoinEvent event) {
                // プレイヤーがサーバーに参加したときに、config.ymlに書かれたメッセージを送ります。
                event.getPlayer().sendMessage(SimpleMOTD.this.getConfig().getString("message"));

                // 特定のプレイヤーだった場合は、追加メッセージを送ります。
                if ( SimpleMOTD.this.getConfig().contains("additional." + event.getPlayer().getName()) ) {
                    event.getPlayer().sendMessage(SimpleMOTD.this.getConfig().getString(
                            "additional." + event.getPlayer().getName()));
                }
            }
        }, this);

        // rulesコマンドのCommandExecutorを登録します。
        this.getCommand("rules").setExecutor(new CommandExecutor() {

            public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
                // コマンド実行時にコマンド実行者へ、config.ymlのrulesの内容を送ります。
                List<String> rules = SimpleMOTD.this.getConfig().getStringList("rules");
                for (String s : rules) {
                    sender.sendMessage(s);
                }
                return true;
            }
        });
    }
}

デフォルトのconfig.ymlの内容は、下記のとおりです。

# default config.yml
message: Hello World and Welcome! :)
rules:
  - Play Nice
  - Respect others
  - Have Fun
additional:
  Anna: Hi Anna!
  Billy: Hey Billy!