Formato NEON

NEON es un formato de datos estructurados legibles por humanos. En Nette, se utiliza para archivos de configuración. También se utiliza para datos estructurados como configuraciones, traducciones de idiomas, etc. Pruébalo en el sandbox.

NEON son las siglas de Nette Object Notation. Es menos complejo y desgarbado que XML o JSON, pero proporciona capacidades similares. Es muy similar a YAML. La principal ventaja es que NEON tiene las llamadas entidades, gracias a las cuales la configuración de los servicios DI es tan sexy. Y permite tabuladores para la indentación.

NEON está construido desde cero para ser fácil de usar.

Integración

Sintaxis

Un archivo escrito en NEON consiste normalmente en una secuencia o mapeo.

Asignaciones

El mapeo es un conjunto de pares clave-valor, en PHP se llamaría una matriz asociativa. Cada par se escribe como key: value, se requiere un espacio después de :. El valor puede ser cualquier cosa: cadena, número, booleano, null, secuencia u otro mapeo.

street: 742 Evergreen Terrace
city: Springfield
country: USA

En PHP, la misma estructura se escribiría como:

[ // PHP
	'street' => '742 Evergreen Terrace',
	'city' => 'Springfield',
	'country' => 'USA',
]

Esta notación se llama notación de bloque porque todos los elementos están en una línea separada y tienen la misma sangría (ninguna en este caso). NEON también admite la representación en línea para la asignación, que se encierra entre corchetes, la sangría no juega ningún papel, y el separador de cada elemento es una coma o una nueva línea:

{street: 742 Evergreen Terrace, city: Springfield, country: USA}

Esto es lo mismo escrito en varias líneas (la sangría no importa):

{
	street: 742 Evergreen Terrace
		city: Springfield, country: USA
}

Como alternativa, puede utilizarse = en lugar de : tanto en la notación en bloque como en la notación en línea:

{street=742 Evergreen Terrace, city=Springfield, country=USA}

Secuencias

Las secuencias son matrices indexadas en PHP. Se escriben como líneas que comienzan con el guión - seguido de un espacio. De nuevo, el valor puede ser cualquier cosa: cadena, número, booleano, null, secuencia, u otro mapeo.

- Cat
- Dog
- Goldfish

En PHP, la misma estructura se escribiría como:

[ // PHP
	'Cat',
	'Dog',
	'Goldfish',
]

Esta notación se llama notación de bloque porque todos los elementos están en una línea separada y tienen la misma sangría (ninguna en este caso). NEON también soporta la representación en línea para secuencias, que se encierran entre corchetes, la sangría no juega ningún papel, y el separador de cada elemento es una coma o una nueva línea:

[Cat, Dog, Goldfish]

Esto es lo mismo escrito en varias líneas (la sangría no importa):

[
	Cat, Dog
		Goldfish
]

Los guiones no pueden utilizarse en una representación en línea.

Combinación

Los valores de las correspondencias y secuencias pueden ser otras correspondencias y secuencias. El nivel de sangría desempeña un papel importante. En el siguiente ejemplo, el guión utilizado para indicar los elementos de la secuencia tiene una sangría mayor que la tecla pets, por lo que los elementos se convierten en el valor de la primera línea:

pets:
   - Cat
   - Dog
cars:
   - Volvo
   - Skoda

En PHP, la misma estructura se escribiría como:

[ // PHP
	'pets' => [
		'Cat',
		'Dog',
	],
	'cars' => [
		'Volvo',
		'Skoda',
	],
]

Es posible combinar la notación en bloque y en línea:

pets: [Cat, Dog]
cars: [
	Volvo,
	Skoda,
]

La notación en bloque ya no puede utilizarse dentro de una notación en línea, esto no funciona:

item: [
	pets:
	 - Cat     # THIS IS NOT POSSIBLE!!!
	 - Dog
]

En el caso anterior, escribimos un mapeo cuyos elementos eran secuencias. Ahora, intentémoslo al revés y creemos una secuencia que contenga mapeos:

-
	name: John
	age: 35
-
	name: Peter
	age: 28

No es necesario que las viñetas estén en líneas separadas; también pueden colocarse así:

- name: John
  age: 35
- name: Peter
  age: 28

Depende de ti si alineas las viñetas en una columna utilizando espacios o un tabulador.

Debido a que PHP utiliza la misma estructura para mapeo y secuencias, es decir, arrays, ambos pueden ser fusionados. La indentación es la misma esta vez:

- Cat
street: 742 Evergreen Terrace
- Goldfish

En PHP, la misma estructura se escribiría como:

[ // PHP
	'Cat',
	'street' => '742 Evergreen Terrace',
	'Goldfish',
]

Cadenas

Las cadenas en NEON pueden ir entre comillas simples o dobles. Pero como puede ver, también pueden ir sin comillas.

- A unquoted string in NEON
- 'A singled-quoted string in NEON'
- "A double-quoted string in NEON"

Si la cadena contiene caracteres # " ' , : = - [ ] { } ( ) que puedan confundirse con la sintaxis NEON, debe ir entre comillas. Recomendamos utilizar comillas simples porque no utilizan escapes. Si necesita encerrar una comilla en una cadena de este tipo, duplíquela:

'A single quote '' inside a single-quoted string'

Las comillas dobles le permiten utilizar secuencias de escape para escribir caracteres especiales mediante barras invertidas \. All escape sequences as in the JSON format are supported, plus \_, que es un espacio que no se rompe, es decir, \u00A0.

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

Hay otros casos en los que es necesario encerrar las cadenas entre comillas:

  • empiezan o acaban con espacios
  • parecen números, booleanos o nulos
  • NEON las entendería como fechas

Cadenas multilínea

Una cadena multilínea comienza y termina con una triple comilla en líneas separadas. La sangría de la primera línea se ignora para todas las líneas:

'''
	first line
		second line
	third line
	'''

En PHP escribiríamos lo mismo que:

"first line\n\tsecond line\nthird line" // PHP

Las secuencias de escape sólo funcionan para cadenas encerradas entre comillas dobles en lugar de apóstrofes:

"""
	Copyright \u00A9
"""

Números

NEON entiende los números escritos en la llamada notación científica y también los números en binario, octal y hexadecimal:

- 12         # an integer
- 12.3       # a float
- +1.2e-34   # an exponential number

- 0b11010    # binary number
- 0o666      # octal number
- 0x7A       # hexa number

Nulos

Los nulos pueden expresarse en NEON utilizando null o no especificando un valor. También se permiten variantes con la primera mayúscula o todo en mayúsculas.

a: null
b:

Booleanos

Los valores booleanos se expresan en NEON utilizando true / false o yes / no. También se admiten variantes con la primera mayúscula o todo en mayúsculas.

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

Fechas

NEON utiliza los siguientes formatos para expresar datos y los convierte automáticamente en objetos de 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

Entidades

Una entidad es una estructura que se asemeja a una llamada de función:

Column(type: int, nulls: yes)

En PHP, se interpreta como un objeto Nette\Neon\Entity:

// PHP
new Nette\Neon\Entity('Column', ['type' => 'int', 'nulls' => true])

Las entidades también pueden encadenarse:

Column(type: int, nulls: yes) Field(id: 1)

Que se analiza en PHP de la siguiente manera:

// 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]),
])

Dentro de los paréntesis, se aplican las reglas de notación inline utilizadas para mapeo y secuencias, por lo que se puede dividir en varias líneas y no es necesario añadir comas:

Column(
	type: int
	nulls: yes
)

Comentarios

Los comentarios empiezan por # y se ignoran todos los caracteres siguientes a la derecha:

# this line will be ignored by the interpreter
street: 742 Evergreen Terrace
city: Springfield  # this is ignored too
country: USA

NEON frente a JSON

JSON es un subconjunto de NEON. Por lo tanto, cada JSON puede ser analizado como NEON:

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

¿Y si pudiéramos omitir las comillas?

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

¿Y las llaves y las comas?

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

database:
	driver: mysql
	username: root
	password: beruska92

users: [
	Dave, Kryten, Rimmer
]

¿Son más legibles las viñetas?

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

database:
	driver: mysql
	username: root
	password: beruska92

users:
	- Dave
	- Kryten
	- Rimmer

¿Y los comentarios?

# my web application config

php:
	date.timezone: Europe/Prague
	zlib.output_compression: true  # use gzip

database:
	driver: mysql
	username: root
	password: beruska92

users:
	- Dave
	- Kryten
	- Rimmer

¡Has encontrado la sintaxis NEON!

versión: 3.4