@@ -3,10 +3,339 @@ Nette PHP Generator
3
3
4
4
[ ![ Downloads this Month] ( https://img.shields.io/packagist/dm/nette/php-generator.svg )] ( https://packagist.org/packages/nette/php-generator )
5
5
[ ![ Build Status] ( https://travis-ci.org/nette/php-generator.svg?branch=master )] ( https://travis-ci.org/nette/php-generator )
6
- [ ![ Coverage Status] ( https://coveralls.io/repos/github/nette/php-generator/badge.svg?branch=master )] ( https://coveralls.io/github/nette/php-generator?branch=master )
6
+ [ ![ Coverage Status] ( https://coveralls.io/repos/github/nette/php-generator/badge.svg?branch=master&v=1 )] ( https://coveralls.io/github/nette/php-generator?branch=master )
7
7
[ ![ Latest Stable Version] ( https://poser.pugx.org/nette/php-generator/v/stable )] ( https://github.com/nette/php-generator/releases )
8
8
[ ![ License] ( https://img.shields.io/badge/license-New%20BSD-blue.svg )] ( https://github.com/nette/php-generator/blob/master/license.md )
9
9
10
- Generate PHP code with a simple programmatical API.
10
+ Generate PHP code, classes, namespaces etc. with a simple programmatical API.
11
11
12
- [ Sample PHP code definition] ( https://github.com/nette/php-generator/blob/master/tests/PhpGenerator/ClassType.phpt ) &rarr ; [ sample output] ( https://github.com/nette/php-generator/blob/master/tests/PhpGenerator/ClassType.expect ) with magic ``` __toString() ``` method.
12
+ Usage is very easy. In first, install it using Composer:
13
+
14
+ ```
15
+ composer require nette/php-generator
16
+ ```
17
+
18
+ Examples
19
+ --------
20
+
21
+ ``` php
22
+ $class = new Nette\PhpGenerator\ClassType('Demo');
23
+
24
+ $class
25
+ ->setAbstract()
26
+ ->setFinal()
27
+ ->setExtends('ParentClass')
28
+ ->addImplement('Countable')
29
+ ->addTrait('Nette\SmartObject')
30
+ ->addComment("Description of class.\nSecond line\n")
31
+ ->addComment('@property-read Nette\Forms\Form $form');
32
+
33
+ $class->addConstant('ID', 123);
34
+
35
+ $class->addProperty('items', [1, 2, 3])
36
+ ->setVisibility('private')
37
+ ->setStatic()
38
+ ->addComment('@var int[]');
39
+
40
+ $method = $class->addMethod('count')
41
+ ->addComment('Count it.')
42
+ ->addComment('@return int')
43
+ ->setFinal()
44
+ ->setVisibility('protected')
45
+ ->setBody('return count($items ?: $this->items);');
46
+
47
+ $method->addParameter('items', []) // $items = []
48
+ ->setReference() // & $items = []
49
+ ->setTypeHint('array'); // array & $items = []
50
+ ```
51
+
52
+ To generate PHP code simply cast to string or use echo:
53
+
54
+ ``` php
55
+ echo $class;
56
+ ```
57
+
58
+ It will render this result:
59
+
60
+ ``` php
61
+ /**
62
+ * Description of class.
63
+ * Second line
64
+ *
65
+ * @property-read Nette\Forms\Form $form
66
+ */
67
+ abstract final class Demo extends ParentClass implements Countable
68
+ {
69
+ use Nette\SmartObject;
70
+
71
+ const ID = 123;
72
+
73
+ /** @var int[] */
74
+ private static $items = [1, 2, 3];
75
+
76
+ /**
77
+ * Count it.
78
+ * @return int
79
+ */
80
+ final protected function count(array & $items = [])
81
+ {
82
+ return count($items ?: $this->items);
83
+ }
84
+
85
+ }
86
+ ```
87
+
88
+ PHP Generator supports all new PHP 7.1 features:
89
+
90
+ ``` php
91
+ $class = new Nette\PhpGenerator\ClassType('Demo');
92
+
93
+ $class->addConstant('ID', 123)
94
+ ->setVisibility('private'); // constant visiblity
95
+
96
+ $method = $class->addMethod('getValue')
97
+ ->setReturnType('int') // method return type
98
+ ->setReturnNullable() // nullable return type
99
+ ->setBody('return count($this->items);');
100
+
101
+ $method->addParameter('id')
102
+ ->setTypeHint('int') // scalar type hint
103
+ ->setNullable(); // nullable type hint
104
+
105
+ echo $class;
106
+ ```
107
+
108
+ Result:
109
+
110
+ ``` php
111
+ class Demo
112
+ {
113
+ private const ID = 123;
114
+
115
+ public function getValue(?int $id): ?int
116
+ {
117
+ return count($this->items);
118
+ }
119
+
120
+ }
121
+ ```
122
+
123
+ Literals
124
+ --------
125
+
126
+ You can pass any PHP code to property or parameter default values via ` Nette\PhpGenerator\PhpLiteral ` :
127
+
128
+ ``` php
129
+ use Nette\PhpGenerator\PhpLiteral;
130
+
131
+ $class = new Nette\PhpGenerator\ClassType('Demo');
132
+
133
+ $class->addProperty('foo', new PhpLiteral('Iterator::SELF_FIRST'));
134
+
135
+ $class->addMethod('bar')
136
+ ->addParameter('id', new PhpLiteral('1 + 2'));
137
+
138
+ echo $class;
139
+ ```
140
+
141
+ Result:
142
+
143
+ ``` php
144
+ class Demo
145
+ {
146
+ public $foo = Iterator::SELF_FIRST;
147
+
148
+ public function bar($id = 1 + 2)
149
+ {
150
+ }
151
+
152
+ }
153
+ ```
154
+
155
+ Interface or trait
156
+ ------------------
157
+
158
+ ``` php
159
+ $class = new Nette\PhpGenerator\ClassType('DemoInterface');
160
+ $class->setType('interface');
161
+ $class->setType('trait'); // or trait
162
+ ```
163
+
164
+ Trait resolutions and visibility
165
+ --------------------------------
166
+
167
+ ``` php
168
+ $class = new Nette\PhpGenerator\ClassType('Demo');
169
+ $class->addTrait('SmartObject', ['sayHello as protected']);
170
+ echo $class;
171
+ ```
172
+
173
+ Result:
174
+
175
+ ``` php
176
+ class Demo
177
+ {
178
+ use SmartObject {
179
+ sayHello as protected;
180
+ }
181
+ }
182
+ ```
183
+
184
+ Anonymous class
185
+ ---------------
186
+
187
+ ``` php
188
+ $class = new Nette\PhpGenerator\ClassType(NULL);
189
+ $class->addMethod('__construct')
190
+ ->addParameter('foo');
191
+
192
+ echo '$obj = new class ($val) ' . $class . ';';
193
+ ```
194
+
195
+ Result:
196
+
197
+ ``` php
198
+ $obj = new class ($val) {
199
+
200
+ public function __construct($foo)
201
+ {
202
+ }
203
+ };
204
+ ```
205
+
206
+ Global function
207
+ ---------------
208
+
209
+ ``` php
210
+ $function = new Nette\PhpGenerator\GlobalFunction('foo');
211
+ $function->setBody('return $a + $b;');
212
+ $function->addParameter('a');
213
+ $function->addParameter('b');
214
+ echo $function;
215
+ ```
216
+
217
+ Result:
218
+
219
+ ``` php
220
+ function foo($a, $b)
221
+ {
222
+ return $a + $b;
223
+ }
224
+ ```
225
+
226
+ Closure
227
+ -------
228
+
229
+ ``` php
230
+ $closure = new Nette\PhpGenerator\Closure;
231
+ $closure->setBody('return $a + $b;');
232
+ $closure->addParameter('a');
233
+ $closure->addParameter('b');
234
+ $closure->addUse('c')
235
+ ->setReference();
236
+ echo $closure;
237
+ ```
238
+
239
+ Result:
240
+
241
+ ``` php
242
+ function ($a, $b) use (& $c) {
243
+ return $a + $b;
244
+ }
245
+ ```
246
+
247
+ Method body generator
248
+ ---------------------
249
+
250
+ You can use special placeholders for handy way to generate method or function body.
251
+
252
+ Simple placeholders:
253
+
254
+ ``` php
255
+ $str = 'any string';
256
+ $num = 3;
257
+ $function = new Nette\PhpGenerator\GlobalFunction('foo');
258
+ $function->addBody('$a = strlen(?, ?);', [$str, $num]);
259
+ $function->addBody('return $a \? 10 : ?;', [$num]); // escaping
260
+ echo $function;
261
+ ```
262
+
263
+ Result:
264
+
265
+ ``` php
266
+ function foo()
267
+ {
268
+ $a = strlen('any string', 3);
269
+ return $a ? 10 : 3;
270
+ }
271
+ ```
272
+
273
+ Variadic placeholder:
274
+
275
+ ``` php
276
+ $items = [1, 2, 3];
277
+ $function = new Nette\PhpGenerator\GlobalFunction('foo');
278
+ $function->setBody('myfunc(...?);', [$items]);
279
+ echo $function;
280
+ ```
281
+
282
+ Result:
283
+
284
+ ``` php
285
+ function foo()
286
+ {
287
+ myfunc(1, 2, 3);
288
+ }
289
+ ```
290
+
291
+
292
+ Namespace
293
+ ---------
294
+
295
+ ``` php
296
+ $namespace = new Nette\PhpGenerator\PhpNamespace('Foo');
297
+ $namespace->addUse('Bar\AliasedClass');
298
+
299
+ $class = $namespace->addClass('Demo');
300
+ $class->addImplement('Foo\A') // resolves to A
301
+ ->addTrait('Bar\AliasedClass'); // resolves to AliasedClass
302
+
303
+ $method = $class->addMethod('method');
304
+ $method->addParameter('arg')
305
+ ->setTypeHint('Bar\OtherClass'); // resolves to \Bar\OtherClass
306
+
307
+ echo $namespace;
308
+ ```
309
+
310
+ Result:
311
+
312
+ ``` php
313
+ namespace Foo;
314
+
315
+ use Bar\AliasedClass;
316
+
317
+ class Demo implements A
318
+ {
319
+ use AliasedClass;
320
+
321
+ public function method(\Bar\OtherClass $arg)
322
+ {
323
+ }
324
+
325
+ }
326
+ ```
327
+
328
+ Factories
329
+ ---------
330
+
331
+ Another common use case is to create class or method form existing ones:
332
+
333
+ ``` php
334
+ $class = Nette\PhpGenerator\ClassType::from(PDO::class);
335
+
336
+ $function = Nette\PhpGenerator\GlobalFunction::from('trim');
337
+
338
+ $closure = Nette\PhpGenerator\Closure::from(
339
+ function (stdClass $a, $b = NULL) {}
340
+ );
341
+ ```
0 commit comments