Skip to content

Commit 3182f5e

Browse files
committed
Merge pull request #11 from pavelkouril/php7-features
Support for PHP7 return types and scalar type hints
2 parents 845fc5f + 89d5a34 commit 3182f5e

File tree

4 files changed

+133
-2
lines changed

4 files changed

+133
-2
lines changed

src/PhpGenerator/Method.php

Lines changed: 31 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,9 @@ class Method extends Nette\Object
5151
/** @var PhpNamespace|NULL */
5252
private $namespace;
5353

54+
/** @var string */
55+
private $returnType;
56+
5457

5558
/**
5659
* @return self
@@ -71,6 +74,10 @@ public static function from($from)
7174
$method->returnReference = $from->returnsReference();
7275
$method->variadic = PHP_VERSION_ID >= 50600 && $from->isVariadic();
7376
$method->documents = $from->getDocComment() ? [preg_replace('#^\s*\* ?#m', '', trim($from->getDocComment(), "/* \r\n\t"))] : [];
77+
if (PHP_VERSION_ID >= 70000 && $from->hasReturnType()) {
78+
$returnType = $from->getReturnType();
79+
$method->returnType = $returnType->isBuiltin() ? (string) $returnType : '\\' . $returnType;
80+
}
7481
return $method;
7582
}
7683

@@ -80,7 +87,7 @@ public static function from($from)
8087
*/
8188
public function __toString()
8289
{
83-
static $builtinTypes = ['array', 'self', 'parent', 'callable', ''];
90+
static $builtinTypes = ['array', 'self', 'parent', 'callable', 'string', 'bool', 'float', 'int', ''];
8491
$parameters = [];
8592
foreach ($this->parameters as $param) {
8693
$variadic = $this->variadic && $param === end($this->parameters);
@@ -98,6 +105,9 @@ public function __toString()
98105
foreach ($this->uses as $param) {
99106
$uses[] = ($param->isReference() ? '&' : '') . '$' . $param->getName();
100107
}
108+
$returnType = !$this->namespace || in_array($this->returnType, $builtinTypes)
109+
? $this->returnType
110+
: $this->namespace->unresolveName($this->returnType);
101111
return ($this->documents ? str_replace("\n", "\n * ", "/**\n" . implode("\n", $this->documents)) . "\n */\n" : '')
102112
. ($this->abstract ? 'abstract ' : '')
103113
. ($this->final ? 'final ' : '')
@@ -108,6 +118,7 @@ public function __toString()
108118
. ($this->name ? ' ' . $this->name : '')
109119
. '(' . implode(', ', $parameters) . ')'
110120
. ($this->uses ? ' use (' . implode(', ', $uses) . ')' : '')
121+
. ($returnType ? ': ' . $returnType : '')
111122
. ($this->abstract || $this->body === FALSE ? ';'
112123
: ($this->name ? "\n" : ' ') . "{\n" . Nette\Utils\Strings::indent(ltrim(rtrim($this->body) . "\n"), 1) . '}');
113124
}
@@ -393,4 +404,23 @@ public function setNamespace(PhpNamespace $val = NULL)
393404
return $this;
394405
}
395406

407+
/**
408+
* @param string
409+
* @return self
410+
*/
411+
public function setReturnType($val)
412+
{
413+
$this->returnType = (string) $val;
414+
return $this;
415+
}
416+
417+
418+
/**
419+
* @return string
420+
*/
421+
public function getReturnType()
422+
{
423+
return $this->returnType;
424+
}
425+
396426
}

src/PhpGenerator/Parameter.php

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,10 @@ public static function from(\ReflectionParameter $from)
3939
$param = new static;
4040
$param->name = $from->getName();
4141
$param->reference = $from->isPassedByReference();
42-
if ($from->isArray() || $from->isCallable()) {
42+
if (PHP_VERSION_ID >= 70000) {
43+
$type = $from->getType();
44+
$param->typeHint = !$type || $type->isBuiltin() ? (string) $type : '\\' . $type;
45+
} elseif ($from->isArray() || $from->isCallable()) {
4346
$param->typeHint = $from->isArray() ? 'array' : 'callable';
4447
} else {
4548
try {
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
<?php
2+
3+
/**
4+
* Test: Nette\PhpGenerator - PHP7 return type declarations
5+
* @phpversion 7.0
6+
*/
7+
8+
namespace A
9+
{
10+
class Foo {}
11+
}
12+
13+
namespace
14+
{
15+
use Nette\PhpGenerator\Method;
16+
use Tester\Assert;
17+
18+
19+
require __DIR__ . '/../bootstrap.php';
20+
21+
// test from
22+
23+
interface A
24+
{
25+
function testClass() : \A\Foo;
26+
function testScalar() : string;
27+
}
28+
29+
$method = Method::from(A::class .'::testClass');
30+
Assert::same('\A\Foo', $method->getReturnType());
31+
32+
$method = Method::from(A::class .'::testScalar');
33+
Assert::same('string', $method->getReturnType());
34+
35+
// generating methods with return type declarations
36+
37+
$method = (new Method)
38+
->setName('create')
39+
->setReturnType('Foo')
40+
->setBody('return new Foo();');
41+
42+
Assert::match(
43+
'function create(): Foo
44+
{
45+
return new Foo();
46+
}
47+
', (string) $method);
48+
49+
}
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
<?php
2+
3+
/**
4+
* Test: Nette\PhpGenerator - PHP7 scalar type hints
5+
* @phpversion 7.0
6+
*/
7+
8+
9+
use Nette\PhpGenerator\Method;
10+
use Tester\Assert;
11+
12+
13+
require __DIR__ . '/../bootstrap.php';
14+
15+
// test from
16+
17+
18+
interface Foo
19+
{
20+
function scalars(string $a, bool $b, int $c, float $d);
21+
}
22+
23+
$method = Method::from(Foo::class . '::scalars');
24+
Assert::same('string', $method->getParameters()['a']->getTypeHint());
25+
26+
$method = Method::from(Foo::class . '::scalars');
27+
Assert::same('bool', $method->getParameters()['b']->getTypeHint());
28+
29+
$method = Method::from(Foo::class . '::scalars');
30+
Assert::same('int', $method->getParameters()['c']->getTypeHint());
31+
32+
$method = Method::from(Foo::class . '::scalars');
33+
Assert::same('float', $method->getParameters()['d']->getTypeHint());
34+
35+
36+
// generating methods with scalar type hints
37+
38+
$method = (new Method)
39+
->setName('create')
40+
->setBody('return null;');
41+
$method->addParameter('a')->setTypeHint('string');
42+
$method->addParameter('b')->setTypeHint('bool');
43+
44+
Assert::match(
45+
'function create(string $a, bool $b)
46+
{
47+
return null;
48+
}
49+
', (string) $method);

0 commit comments

Comments
 (0)