php-pegjs v0.8.10
PHP PEG.js
This repo is not maintained for a while please use phpegjs module instead
PHP PEG.js is a php code generation plugin for PEG.js.
Requirements
Installation
Node.js
Install PEG.js with php-pegjs plugin
$ npm install php-pegjs
Usage
Generating a Parser
In Node.js, require both the PEG.js parser generator and the php-pegjs plugin:
var pegjs = require("pegjs");
var phppegjs = require("php-pegjs");
To generate a php parser, pass to pegjs.buildParser
php-pegjs plugin and your grammar:
var parser = pegjs.buildParser("start = ('a' / 'b')+", {
plugins: [phppegjs]
});
The method will return source code of generated parser as a string. Unlike original PEG.js, generated php parser will be a class, not a function.
Supported options of pegjs.buildParser
:
cache
— iftrue
, makes the parser cache results, avoiding exponential parsing time in pathological cases but making the parser slower (default:false
). In case of php, this is strongly recommended for big grammars (like javascript.pegjs or css.pegjs in example folder)allowedStartRules
— rules the parser will be allowed to start parsing from (default: the first rule in the grammar)
Additional PHP PEG.js plugin options:
phppegjs.parserNamespace
- namespace of generated parser (default:"PhpPegJs"
). If value is""
, parser will be in global namespacephppegjs.parserClassName
- name of generated class for parser (default:"Parser"
)
Using the Parser
1) Save parser generated by pegjs.buildParser
to a file
2) In php code:
include "your.parser.file.php";
try
{
$parser = new PhpPegJs\Parser;
$result = $parser->parse($input);
}
catch (PhpPegJs\SyntaxError $ex)
{
// Handle parsing error
// [...]
}
You can use following snippet to format parsing error:
catch (PhpPegJs\SyntaxError $ex)
{
$message = "Syntax error: " . $ex->getMessage() . ' At line ' . $ex->grammarLine . ' column ' . $ex->grammarColumn . ' offset ' . $ex->grammarOffset;
}
Grammar Syntax and Semantics
See documentation of PEG.js with one difference: action blocks should be written on PHP.
Original PEG.js rule:
media_list
= head:medium tail:("," S* medium)* {
var result = [head];
for (var i = 0; i < tail.length; i++) {
result.push(tail[i][2]);
}
return result;
}
PHP PEG.js rule:
media_list
= head:medium tail:("," S* medium)* {
$result = array($head);
for ($i = 0; $i < count($tail); $i++) {
$result[] = $tail[$i][2];
}
return $result;
}
You can also use following util functions in action blocks:
chr_unicode($code)
- return character by its UTF-8 code (Analogue of javascript String.fromCharCode)
Guide of converting PEG.js action blocks to PHP PEG.js
Javascript code | PHP analogue |
---|---|
some_var | $some_var |
{f1: "val1", f2: "val2"} | array("f1" => "val1", "f2" => "val2") |
["val1", "val2"] | array("val1", "val2") |
some_array.push("val") | $some_array[] = "val" |
some_array.length | count($some_array) |
some_array.join("") | join("", $some_array) |
some_array1.concat(some_array2) | array_merge($some_array1, $some_array2) |
parseInt("23") | intval("23") |
parseFloat("23.1") | floatval("23.1") |
some_str.length | mb_strlen(some_str, "UTF-8") |
some_str.replace("b", "\b") | str_replace("b", "\b", $some_str) |
String.fromCharCode(2323) | chr_unicode(2323) |
text() | $this->text() |
location() | $this->location() |
Function $this->location()
returns object with following structure:
{
'start' => {
'offset' => int,
'line' => int,
'column' => int,
},
'end' => {
'offset' => int,
'line' => int,
'column' => int,
},
}