Skip to content

Commit 77b39dc

Browse files
committed
Method::from() added support for closures & global functions
1 parent db1db55 commit 77b39dc

File tree

5 files changed

+73
-38
lines changed

5 files changed

+73
-38
lines changed

src/PhpGenerator/Method.php

Lines changed: 19 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111

1212

1313
/**
14-
* Class method description.
14+
* Method or function description.
1515
*/
1616
class Method extends Nette\Object
1717
{
@@ -57,17 +57,26 @@ class Method extends Nette\Object
5757
*/
5858
public static function from($from)
5959
{
60-
$from = $from instanceof \ReflectionMethod ? $from : new \ReflectionMethod($from);
60+
if (is_string($from) && strpos($from, '::')) {
61+
$from = new \ReflectionMethod($from);
62+
} elseif (is_array($from)) {
63+
$from = new \ReflectionMethod($from[0], $from[1]);
64+
} elseif (!$from instanceof \ReflectionFunctionAbstract) {
65+
$from = new \ReflectionFunction($from);
66+
}
67+
6168
$method = new static;
62-
$method->name = $from->getName();
69+
$method->name = $from->isClosure() ? NULL : $from->getName();
6370
foreach ($from->getParameters() as $param) {
6471
$method->parameters[$param->getName()] = Parameter::from($param);
6572
}
66-
$method->static = $from->isStatic();
67-
$method->visibility = $from->isPrivate() ? 'private' : ($from->isProtected() ? 'protected' : NULL);
68-
$method->final = $from->isFinal();
69-
$method->abstract = $from->isAbstract() && !$from->getDeclaringClass()->isInterface();
70-
$method->body = $from->isAbstract() ? FALSE : '';
73+
if ($from instanceof \ReflectionMethod) {
74+
$method->static = $from->isStatic();
75+
$method->visibility = $from->isPrivate() ? 'private' : ($from->isProtected() ? 'protected' : NULL);
76+
$method->final = $from->isFinal();
77+
$method->abstract = $from->isAbstract() && !$from->getDeclaringClass()->isInterface();
78+
$method->body = $from->isAbstract() ? FALSE : '';
79+
}
7180
$method->returnReference = $from->returnsReference();
7281
$method->variadic = PHP_VERSION_ID >= 50600 && $from->isVariadic();
7382
$method->documents = $from->getDocComment() ? array(preg_replace('#^\s*\* ?#m', '', trim($from->getDocComment(), "/* \r\n\t"))) : array();
@@ -98,14 +107,15 @@ public function __toString()
98107
foreach ($this->uses as $param) {
99108
$uses[] = ($param->isReference() ? '&' : '') . '$' . $param->getName();
100109
}
110+
101111
return ($this->documents ? str_replace("\n", "\n * ", "/**\n" . implode("\n", $this->documents)) . "\n */\n" : '')
102112
. ($this->abstract ? 'abstract ' : '')
103113
. ($this->final ? 'final ' : '')
104114
. ($this->visibility ? $this->visibility . ' ' : '')
105115
. ($this->static ? 'static ' : '')
106116
. 'function'
107117
. ($this->returnReference ? ' &' : '')
108-
. ($this->name ? ' ' . $this->name : '')
118+
. ' ' . $this->name
109119
. '(' . implode(', ', $parameters) . ')'
110120
. ($this->uses ? ' use (' . implode(', ', $uses) . ')' : '')
111121
. ($this->abstract || $this->body === FALSE ? ';'

src/PhpGenerator/Parameter.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@ public static function from(\ReflectionParameter $from)
5757
$param->optional = PHP_VERSION_ID < 50407 ? $from->isOptional() || ($param->typeHint && $from->allowsNull()) : $from->isDefaultValueAvailable();
5858
$param->defaultValue = (PHP_VERSION_ID === 50316 ? $from->isOptional() : $from->isDefaultValueAvailable()) ? $from->getDefaultValue() : NULL;
5959

60-
$namespace = $from->getDeclaringClass()->getNamespaceName();
60+
$namespace = $from->getDeclaringClass() ? $from->getDeclaringClass()->getNamespaceName() : NULL;
6161
$namespace = $namespace ? "\\$namespace\\" : '\\';
6262
if (Nette\Utils\Strings::startsWith($param->typeHint, $namespace)) {
6363
$param->typeHint = substr($param->typeHint, strlen($namespace));

tests/PhpGenerator/Method.closure.expect

Lines changed: 0 additions & 3 deletions
This file was deleted.

tests/PhpGenerator/Method.closure.phpt

Lines changed: 0 additions & 25 deletions
This file was deleted.
Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
<?php
2+
3+
/**
4+
* Test: Nette\PhpGenerator & function.
5+
*/
6+
7+
use Nette\PhpGenerator\Method;
8+
use Tester\Assert;
9+
10+
11+
require __DIR__ . '/../bootstrap.php';
12+
13+
14+
$function = new Method;
15+
$function
16+
->setReturnReference(TRUE)
17+
->setBody('return $a + $b;');
18+
19+
$function->addParameter('a');
20+
$function->addParameter('b');
21+
$function->addUse('this');
22+
$function->addUse('vars')
23+
->setReference(TRUE);
24+
25+
Assert::match(
26+
'function & ($a, $b) use ($this, &$vars) {
27+
return $a + $b;
28+
}', (string) $function);
29+
30+
31+
/** closure */
32+
$closure = function (stdClass $a, $b = NULL) {};
33+
$function = Method::from($closure);
34+
Assert::match(
35+
'/**
36+
* closure
37+
*/
38+
function (stdClass $a, $b = NULL) {
39+
}', (string) $function);
40+
41+
42+
/** global */
43+
function func(stdClass $a, $b = NULL) {
44+
};
45+
46+
$function = Method::from('func');
47+
Assert::match(
48+
'/**
49+
* global
50+
*/
51+
function func(stdClass $a, $b = NULL)
52+
{
53+
}', (string) $function);

0 commit comments

Comments
 (0)