NEON フォーマット
NEON は人が読める構造化されたデータの形式です。Nette では設定ファイルに使われます。設定、言語の翻訳など、構造化されたデータにも使われます。サンドボックスで試してみてください。
NEON は Nette Object Notation の略です。XML や JSON より複雑でも面倒でもありませんが、同じような力を持ちます。YAML にとてもよく似ています。いちばんの利点はいわゆるエンティティがあることで、おかげで DI のサービスの設定がこんなに魅力的になります。そして字下げにタブを使えます。
NEON は使いやすさをはじめから目指して作られています。
組み合わせ
- NetBeans(組み込みで対応しています)
- PhpStorm(プラグイン)
- Visual Studio Code(Nette Latte + Neonまたは Nette for VS Code)
- Sublime Text 3(プラグイン)
- Sublime Text 2(プラグイン)
- VIM(プラグイン)
- Emacs(プラグイン)
- Prism.js(組み込みの言語)
構文
NEON で書かれたファイルは、ふつう並びか対応づけを表します。
対応づけ
対応づけはキーと値の組の集まりです。PHP なら連想配列と呼ぶものです。それぞれの組は
key: value と書き、:
のうしろの空白は必須です。値は何でもかまいません。文字列、数、真偽値、null、並び、あるいは別の対応づけです。
street: 742 Evergreen Terrace
city: Springfield
country: USA
PHP では同じ構造をこう書きます。
[ // PHP
'street' => '742 Evergreen Terrace',
'city' => 'Springfield',
'country' => 'USA',
]
この書き方はブロック記法と呼ばれます。すべての要素が別々の行にあり、同じ字下げ(ここでは字下げなし)を持つからです。NEON は対応づけのインライン記法にも対応しています。これはかっこで囲まれ、字下げは意味を持たず、要素の区切りはコンマか改行です。
{street: 742 Evergreen Terrace, city: Springfield, country: USA}
同じものを複数行で書きます(字下げは意味を持ちません)。
{
street: 742 Evergreen Terrace
city: Springfield, country: USA
}
あるいは : の代わりに =
を使えます。ブロック記法でもインライン記法でも同じです。
{street=742 Evergreen Terrace, city=Springfield, country=USA}
並び
並びは PHP の添字の配列です。ハイフン -
とそれに続く空白で始まる行として書きます。ここでも値は何でもかまいません。文字列、数、真偽値、null、並び、あるいは別の対応づけです。
- Cat
- Dog
- Goldfish
PHP では同じ構造をこう書きます。
[ // PHP
'Cat',
'Dog',
'Goldfish',
]
この書き方はブロック記法と呼ばれます。すべての要素が別々の行にあり、同じ字下げ(ここでは字下げなし)を持つからです。NEON は並びのインライン記法にも対応しています。これはかっこで囲まれ、字下げは意味を持たず、要素の区切りはコンマか改行です。
[Cat, Dog, Goldfish]
同じものを複数行で書きます(字下げは意味を持ちません)。
[
Cat, Dog
Goldfish
]
インライン記法ではハイフン(点)は使えません。
組み合わせ方
対応づけと並びの値は、別の対応づけや並びにもできます。字下げの段が大きな役目を果たします。次の例では、並びの要素を示すハイフンが
pets
のキーより深く字下げされているので、それらの要素が最初の行の値になります。
pets:
- Cat
- Dog
cars:
- Volvo
- Skoda
PHP では同じ構造をこう書きます。
[ // PHP
'pets' => [
'Cat',
'Dog',
],
'cars' => [
'Volvo',
'Skoda',
],
]
ブロック記法とインライン記法は組み合わせられます。
pets: [Cat, Dog]
cars: [
Volvo,
Skoda,
]
インライン記法の中でブロック記法は使えません。これは動きません。
item: [
pets:
- Cat # THIS IS NOT POSSIBLE!!!
- Dog
]
さっきの場合は、要素が並びである対応づけを書きました。今度は逆にして、対応づけを含む並びを作ってみましょう。
-
name: John
age: 35
-
name: Peter
age: 28
ハイフンは別々の行になくてもよく、次のようにも置けます。
- name: John
age: 35
- name: Peter
age: 28
キーを空白で縦にそろえるか、タブの文字を使うかはあなた次第です。
PHP は対応づけと並びに同じ構造(つまり配列)を使うので、両方を混ぜられます。今度は字下げが同じです。
- Cat
street: 742 Evergreen Terrace
- Goldfish
PHP では同じ構造をこう書きます。
[ // PHP
'Cat',
'street' => '742 Evergreen Terrace',
'Goldfish',
]
文字列
NEON の文字列は単一引用符でも二重引用符でも囲めます。とはいえご覧のとおり、引用符なしでも書けます。
- An unquoted string in NEON
- 'A single-quoted string in NEON'
- "A double-quoted string in NEON"
文字列に NEON の構文と紛らわしい文字 ` # " ' ` , : = - [ ] { } ( ) `
が入っているなら、引用符で囲まなければなりません。単一引用符をおすすめします。エスケープを使わないからです。そうした文字列の中に引用符を入れる必要があるなら、それを
2 つ重ねます。
'A single quote '' inside a single-quoted string'
二重引用符では、バックスラッシュ \
を使って特別な文字を書くエスケープの並びを使えます。JSON
の形式が対応するすべてのエスケープの並びに対応していて、さらに \_
があります。これは改行しない空白、つまり \u00A0 を表します。
- "\t \n \r \f \b \" \\ \/ \_"
- "\u00A9"
文字列を引用符で囲む必要があるほかの場合もあります。
- 空白で始まるか終わる場合
- 数、真偽値、null に見える場合
- NEON がそれを日付と解釈してしまう場合
複数行の文字列
複数行の文字列は、別々の行の 3 つ重ねた引用符で始まり終わります。最初の行の字下げは、すべての行で無視されます。
'''
first line
second line
third line
'''
PHP では同じものをこう書きます。
"first line\n\tsecond line\nthird line" // PHP
エスケープの並びが働くのは、アポストロフィではなく二重引用符で囲まれた文字列だけです。
"""
Copyright \u00A9
"""
数
NEON は科学の記法で書かれた数も、2 進数、8 進数、16 進数の数も理解します。
- 12 # integer
- 12.3 # float
- +1.2e-34 # exponential number
- 0b11010 # binary number
- 0o666 # octal number
- 0x7A # hexadecimal number
null
NEON では null は null
で表すか、値を省いて表せます。最初の文字が大文字の形や、すべて大文字の形も許されます(Null、NULL)。
a: null
b:
真偽値
NEON では真偽値は true / false か yes / no
で表します。最初の文字が大文字の形や、すべて大文字の形も許されます(True、TRUE、False、FALSE、Yes、YES、No、NO)。
[true, TRUE, True, false, yes, no]
日付
NEON は日付を表すのに次の形式を使い、自動的に DateTimeImmutable
オブジェクトへ変えます。
- 2016-06-03 # date
- 2016-06-03 19:00:00 # date & time
- 2016-06-03 19:00:00.1234 # date & microtime
- 2016-06-03 19:00:00 +0200 # date & time & timezone
- 2016-06-03 19:00:00 +02:00 # date & time & timezone
エンティティ
エンティティは関数の呼び出しに似た構造です。
Column(type: int, nulls: yes)
PHP では Nette\Neon\Entityオブジェクトとして読み解かれます。
// PHP
new Nette\Neon\Entity('Column', ['type' => 'int', 'nulls' => true])
エンティティはつなげられます。
Column(type: int, nulls: yes) Field(id: 1)
これは PHP で次のように読み解かれます。
// PHP
new Nette\Neon\Entity(Nette\Neon\Neon::Chain, [
new Nette\Neon\Entity('Column', ['type' => 'int', 'nulls' => true]),
new Nette\Neon\Entity('Field', ['id' => 1]),
])
かっこの中では、対応づけと並びのインライン記法の決まりが当てはまるので、複数行にできますし、コンマも要りません。
Column(
type: int
nulls: yes
)
コメント
コメントは # で始まり、その右のすべての文字は無視されます。
# this line will be ignored by the interpreter
street: 742 Evergreen Terrace
city: Springfield # this is ignored too
country: USA
NEON と JSON
JSON は NEON の部分集合です。ですからどんな JSON も NEON として読み解けます。
{
"php": {
"date.timezone": "Europe\/Prague",
"zlib.output_compression": true
},
"database": {
"driver": "mysql",
"username": "root",
"password": "password123"
},
"users": [
"Dave", "Kryten", "Rimmer"
]
}
引用符を省いたらどうなるでしょうか。
{
php: {
date.timezone: Europe/Prague,
zlib.output_compression: true
},
database: {
driver: mysql,
username: root,
password: password123
},
users: [
Dave, Kryten, Rimmer
]
}
波かっことコンマはどうでしょう。
php:
date.timezone: Europe/Prague
zlib.output_compression: true
database:
driver: mysql
username: root
password: password123
users: [
Dave, Kryten, Rimmer
]
点の付いた一覧のほうが読みやすくないですか。
php:
date.timezone: Europe/Prague
zlib.output_compression: true
database:
driver: mysql
username: root
password: password123
users:
- Dave
- Kryten
- Rimmer
コメントも足してみましょうか。
# my web application config
php:
date.timezone: Europe/Prague
zlib.output_compression: true # use gzip
database:
driver: mysql
username: root
password: password123
users:
- Dave
- Kryten
- Rimmer
やりました。これで NEON の構文が分かりましたね。