Формат NEON

NEON е лесно четим структуриран формат за данни. В Nette се използва за конфигурационни файлове. Използва се и за структурирани данни, като настройки, езикови преводи и т.н. Опитайте го.

NEON е съкращение от Nette Object Notation. Той е по-малко сложен и тромав от XML или JSON, но предоставя подобни функции. Много е подобен на YAML. Основното предимство е, че NEON има така наречените ентитети, благодарение на които конфигурацията на DI сървисите е също толкова секси. И позволява индентация с табулации.

NEON е създаден от основи, за да бъде лесен за използване.

Интеграция

Синтаксис

Файл, написан в 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     # ТОВА НЕ Е ВЪЗМОЖНО!!!
	 - 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 могат да бъдат затворени в единични или двойни кавички. Но както виждате, те могат да бъдат и без кавички.

- Низ в NEON без кавички
- 'Низ в NEON в единични кавички'
- "Низ в NEON в двойни кавички"

Ако низът съдържа знаците # " ' , : = - [ ] { } ( ), които могат да бъдат объркани със синтаксиса на NEON, е необходимо да го затворите в кавички. Препоръчваме да използвате единични кавички, тъй като в тях не се използва екраниране. Ако трябва да запишете кавичка в такъв низ, удвоете я:

'Кавичка '' вътре в низ в единични кавички'

Двойните кавички позволяват използването на escape последователности за запис на специални знаци с помощта на обратни наклонени черти \. Поддържат се всички escape последователности като при формата JSON, плюс \_, което е неразделящ интервал, т.е. \u00A0.

- "\t \n \r \f \b \" \\ \/ \_"
- "\u00A9"

Съществуват и други случаи, когато е необходимо низовете да се затворят в кавички:

  • започват или завършват с интервали
  • изглеждат като числа, булеви стойности или null
  • NEON би ги разбрал като дата

Многоредови низове

Многоредовият низ започва и завършва с тройни кавички на отделни редове. Индентацията на първия ред се игнорира за всички редове:

'''
	първи ред
		втори ред
	трети ред
	'''

В PHP бихме написали същото като:

"първи ред\n\tвтори ред\nтрети ред" // PHP

Escape последователностите работят само при низове, затворени в двойни кавички вместо апострофи:

"""
	Copyright \u00A9
"""

Числа

NEON разбира числа, записани в т.нар. научна нотация, както и числа в двоична, осмична и шестнадесетична бройна система:

- 12         # цяло число
- 12.3       # float
- +1.2e-34   # експоненциално число

- 0b11010    # двоично число
- 0o666      # осмично число
- 0x7A       # шестнадесетично число

Null стойности

Null може да се изрази в NEON с помощта на null или чрез пропускане на стойността. Позволени са и варианти с главна първа буква или всички главни букви.

a: null
b:

Булеви стойности

Логическите стойности се изразяват в NEON с помощта на true / false или yes / no. Позволени са и варианти с главна първа буква или всички главни букви.

[true, TRUE, True, false, yes, no]

Дата

NEON използва следните формати за изразяване на дати и автоматично ги преобразува в обекти DateTimeImmutable:

- 2016-06-03                  # дата
- 2016-06-03 19:00:00         # дата и час
- 2016-06-03 19:00:00.1234    # дата и микросекунди
- 2016-06-03 19:00:00 +0200   # дата и час и зона
- 2016-06-03 19:00:00 +02:00  # дата и час и зона

Ентитети

Ентитетът е структура, която прилича на извикване на функция:

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
)

Коментари

Коментарите започват със знака # и всички следващи знаци надясно се игнорират:

# този ред ще бъде игнориран от интерпретатора
street: 742 Evergreen Terrace
city: Springfield  # това също се игнорира
country: USA

Neon срещу JSON

JSON е подмножество на NEON. Следователно всеки JSON може да бъде парсиран като NEON:

{
"php": {
	"date.timezone": "Europe\/Prague",
	"zlib.output_compression": true
},
"database": {
	"driver": "mysql",
	"username": "root",
	"password": "beruska92"
},
"users": [
	"Dave", "Kryten", "Rimmer"
]
}

Ами ако пропуснем кавичките?

{
php: {
	date.timezone: Europe/Prague,
	zlib.output_compression: true
},
database: {
	driver: mysql,
	username: root,
	password: beruska92
},
users: [
	Dave, Kryten, Rimmer
]
}

А къдравите скоби и запетаите?

php:
	date.timezone: Europe/Prague
	zlib.output_compression: true

database:
	driver: mysql
	username: root
	password: beruska92

users: [
	Dave, Kryten, Rimmer
]

Не са ли списъците с тирета по-четими?

php:
	date.timezone: Europe/Prague
	zlib.output_compression: true

database:
	driver: mysql
	username: root
	password: beruska92

users:
	- Dave
	- Kryten
	- Rimmer

Да добавим коментари?

# конфигурация на моето уеб приложение

php:
	date.timezone: Europe/Prague
	zlib.output_compression: true  # използвай gzip

database:
	driver: mysql
	username: root
	password: beruska92

users:
	- Dave
	- Kryten
	- Rimmer

Ура, вече познавате синтаксиса на NEON!

версия: 3.4