You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
176 lines
4.6 KiB
176 lines
4.6 KiB
<?php |
|
|
|
/* |
|
* This file is part of the Symfony package. |
|
* |
|
* (c) Fabien Potencier <fabien@symfony.com> |
|
* |
|
* For the full copyright and license information, please view the LICENSE |
|
* file that was distributed with this source code. |
|
*/ |
|
|
|
namespace Symfony\Component\Config\Builder; |
|
|
|
/** |
|
* Build PHP classes to generate config. |
|
* |
|
* @internal |
|
* |
|
* @author Tobias Nyholm <tobias.nyholm@gmail.com> |
|
*/ |
|
class ClassBuilder |
|
{ |
|
/** @var string */ |
|
private $namespace; |
|
|
|
/** @var string */ |
|
private $name; |
|
|
|
/** @var Property[] */ |
|
private $properties = []; |
|
|
|
/** @var Method[] */ |
|
private $methods = []; |
|
private $require = []; |
|
private $use = []; |
|
private $implements = []; |
|
private $allowExtraKeys = false; |
|
|
|
public function __construct(string $namespace, string $name) |
|
{ |
|
$this->namespace = $namespace; |
|
$this->name = ucfirst($this->camelCase($name)).'Config'; |
|
} |
|
|
|
public function getDirectory(): string |
|
{ |
|
return str_replace('\\', \DIRECTORY_SEPARATOR, $this->namespace); |
|
} |
|
|
|
public function getFilename(): string |
|
{ |
|
return $this->name.'.php'; |
|
} |
|
|
|
public function build(): string |
|
{ |
|
$rootPath = explode(\DIRECTORY_SEPARATOR, $this->getDirectory()); |
|
$require = ''; |
|
foreach ($this->require as $class) { |
|
// figure out relative path. |
|
$path = explode(\DIRECTORY_SEPARATOR, $class->getDirectory()); |
|
$path[] = $class->getFilename(); |
|
foreach ($rootPath as $key => $value) { |
|
if ($path[$key] !== $value) { |
|
break; |
|
} |
|
unset($path[$key]); |
|
} |
|
$require .= sprintf('require_once __DIR__.\DIRECTORY_SEPARATOR.\'%s\';', implode('\'.\DIRECTORY_SEPARATOR.\'', $path))."\n"; |
|
} |
|
$use = ''; |
|
foreach (array_keys($this->use) as $statement) { |
|
$use .= sprintf('use %s;', $statement)."\n"; |
|
} |
|
|
|
$implements = [] === $this->implements ? '' : 'implements '.implode(', ', $this->implements); |
|
$body = ''; |
|
foreach ($this->properties as $property) { |
|
$body .= ' '.$property->getContent()."\n"; |
|
} |
|
foreach ($this->methods as $method) { |
|
$lines = explode("\n", $method->getContent()); |
|
foreach ($lines as $line) { |
|
$body .= ' '.$line."\n"; |
|
} |
|
} |
|
|
|
$content = strtr('<?php |
|
|
|
namespace NAMESPACE; |
|
|
|
REQUIRE |
|
USE |
|
|
|
/** |
|
* This class is automatically generated to help in creating a config. |
|
*/ |
|
class CLASS IMPLEMENTS |
|
{ |
|
BODY |
|
} |
|
', ['NAMESPACE' => $this->namespace, 'REQUIRE' => $require, 'USE' => $use, 'CLASS' => $this->getName(), 'IMPLEMENTS' => $implements, 'BODY' => $body]); |
|
|
|
return $content; |
|
} |
|
|
|
public function addRequire(self $class): void |
|
{ |
|
$this->require[] = $class; |
|
} |
|
|
|
public function addUse(string $class): void |
|
{ |
|
$this->use[$class] = true; |
|
} |
|
|
|
public function addImplements(string $interface): void |
|
{ |
|
$this->implements[] = '\\'.ltrim($interface, '\\'); |
|
} |
|
|
|
public function addMethod(string $name, string $body, array $params = []): void |
|
{ |
|
$this->methods[] = new Method(strtr($body, ['NAME' => $this->camelCase($name)] + $params)); |
|
} |
|
|
|
public function addProperty(string $name, string $classType = null, string $defaultValue = null): Property |
|
{ |
|
$property = new Property($name, '_' !== $name[0] ? $this->camelCase($name) : $name); |
|
if (null !== $classType) { |
|
$property->setType($classType); |
|
} |
|
$this->properties[] = $property; |
|
$defaultValue = null !== $defaultValue ? sprintf(' = %s', $defaultValue) : ''; |
|
$property->setContent(sprintf('private $%s%s;', $property->getName(), $defaultValue)); |
|
|
|
return $property; |
|
} |
|
|
|
public function getProperties(): array |
|
{ |
|
return $this->properties; |
|
} |
|
|
|
private function camelCase(string $input): string |
|
{ |
|
$output = lcfirst(str_replace(' ', '', ucwords(str_replace('_', ' ', $input)))); |
|
|
|
return preg_replace('#\W#', '', $output); |
|
} |
|
|
|
public function getName(): string |
|
{ |
|
return $this->name; |
|
} |
|
|
|
public function getNamespace(): string |
|
{ |
|
return $this->namespace; |
|
} |
|
|
|
public function getFqcn(): string |
|
{ |
|
return '\\'.$this->namespace.'\\'.$this->name; |
|
} |
|
|
|
public function setAllowExtraKeys(bool $allowExtraKeys): void |
|
{ |
|
$this->allowExtraKeys = $allowExtraKeys; |
|
} |
|
|
|
public function shouldAllowExtraKeys(): bool |
|
{ |
|
return $this->allowExtraKeys; |
|
} |
|
}
|
|
|