本文整理汇总了PHP中Phan\Config类的典型用法代码示例。如果您正苦于以下问题:PHP Config类的具体用法?PHP Config怎么用?PHP Config使用的例子?那么恭喜您, 这里精选的类代码示例或许可以为您提供帮助。
在下文中一共展示了Config类的15个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的PHP代码示例。
示例1: analyze
/**
* @return null
* Analyze the node associated with this object
* in the given context
*/
public function analyze(Context $context, CodeBase $code_base) : Context
{
// Don't do anything if we care about being
// fast
if (Config::get()->quick_mode) {
return $context;
}
if (!$this->hasNode()) {
return $context;
}
// Closures depend on the context surrounding them such
// as for getting `use(...)` variables. Since we don't
// have them, we can't re-analyze them until we change
// that.
//
// TODO: Store the parent context on Analyzable objects
if ($this->getNode()->kind === \ast\AST_CLOSURE) {
return $context;
}
// Don't go deeper than one level in
if ($this->recursion_depth++ > 2) {
return $context;
}
// Analyze the node in a cloned context so that we
// don't overwrite anything
return (new BlockAnalysisVisitor($code_base, clone $context))($this->getNode());
}
示例2: analyzeParentConstructorCalled
/**
* Check to see if the given Clazz is a duplicate
*
* @return null
*/
public static function analyzeParentConstructorCalled(CodeBase $code_base, Clazz $clazz)
{
// Only look at classes configured to require a call
// to its parent constructor
if (!in_array($clazz->getName(), Config::get()->parent_constructor_required)) {
return;
}
// Don't worry about internal classes
if ($clazz->isInternal()) {
return;
}
// Don't worry if there's no parent class
if (!$clazz->hasParentClassFQSEN()) {
return;
}
if (!$code_base->hasClassWithFQSEN($clazz->getParentClassFQSEN())) {
// This is an error, but its caught elsewhere. We'll
// just roll through looking for other errors
return;
}
$parent_clazz = $code_base->getClassByFQSEN($clazz->getParentClassFQSEN());
if (!$parent_clazz->isAbstract() && !$clazz->getIsParentConstructorCalled()) {
Issue::emit(Issue::TypeParentConstructorCalled, $clazz->getContext()->getFile(), $clazz->getContext()->getLineNumberStart(), (string) $clazz->getFQSEN(), (string) $parent_clazz->getFQSEN());
}
}
示例3: testClassContext
public function testClassContext()
{
$code = "<?php\n class C {\n private function f() {\n return 42;\n }\n }";
$stmt_list_node = \ast\parse_code($code, Config::get()->ast_version);
$class_node = $stmt_list_node->children[0];
$context = new Context();
$context = (new ParseVisitor($this->code_base, $context))($class_node);
$stmt_list_node = $class_node->children['stmts'];
$method_node = $stmt_list_node->children[0];
$context = (new ParseVisitor($this->code_base, $context))($method_node);
}
示例4: getProjectRelativePath
/**
* @return string
* The path of the file relative to the project
* root directory
*/
public function getProjectRelativePath() : string
{
$cwd_relative_path = $this->file;
// Get a path relative to the project root
$path = str_replace(Config::get()->getProjectRootDirectory(), '', realpath($cwd_relative_path) ?: $cwd_relative_path);
// Strip any beginning directory separators
if (0 === ($pos = strpos($path, DIRECTORY_SEPARATOR))) {
$path = substr($path, $pos + 1);
}
return $path;
}
示例5: analyzeReferenceCounts
/**
* Take a look at all globally accessible elements and see if
* we can find any dead code that is never referenced
*
* @return void
*/
public static function analyzeReferenceCounts(CodeBase $code_base)
{
// Check to see if dead code detection is enabled. Keep
// in mind that the results here are just a guess and
// we can't tell with certainty that anything is
// definitely unreferenced.
if (!Config::get()->dead_code_detection) {
return;
}
// Get the count of all known elements
$total_count = count($code_base->getMethodMap(), COUNT_RECURSIVE) + count($code_base->getPropertyMap(), COUNT_RECURSIVE) + count($code_base->getConstantMap(), COUNT_RECURSIVE) + count($code_base->getClassMap(), COUNT_RECURSIVE);
$i = 0;
$analyze_list = function ($list) use($code_base, &$i, $total_count) {
foreach ($list as $name => $element) {
CLI::progress('dead code', ++$i / $total_count);
self::analyzeElementReferenceCounts($code_base, $element);
}
};
$analyze_map = function ($map) use($code_base, &$i, $total_count) {
foreach ($map as $fqsen_string => $list) {
foreach ($list as $name => $element) {
CLI::progress('dead code', ++$i / $total_count);
// Don't worry about internal elements
if ($element->getContext()->isInternal()) {
continue;
}
$element_fqsen = $element->getFQSEN();
if ($element_fqsen instanceof FullyQualifiedClassElement) {
$class_fqsen = $element->getDefiningClassFQSEN();
// Don't analyze elements defined in a parent
// class
if ((string) $class_fqsen !== $fqsen_string) {
continue;
}
$defining_class = $element->getDefiningClass($code_base);
// Don't analyze elements on interfaces or on
// abstract classes, as they're uncallable.
if ($defining_class->isInterface() || $defining_class->isAbstract() || $defining_class->isTrait()) {
continue;
}
// Ignore magic methods
if ($element instanceof Method && $element->getIsMagic()) {
continue;
}
}
self::analyzeElementReferenceCounts($code_base, $element);
}
}
};
$analyze_map($code_base->getMethodMap());
$analyze_map($code_base->getPropertyMap());
$analyze_map($code_base->getConstantMap());
$analyze_list($code_base->getClassMap());
}
示例6: scanFileList
/**
* Scan a list of files, applying the given closure to every
* AST node
*
* @param string[] $file_list
* A list of files to scan
*
* @param \Closure $visit_node
* A closure that is to be applied to every AST node
*
* @return void
*/
public static function scanFileList(array $file_list, \Closure $visit_node)
{
foreach ($file_list as $file_path) {
// Convert the file to an Abstract Syntax Tree
// before passing it on to the recursive version
// of this method
$node = \ast\parse_file($file_path, Config::get()->ast_version);
// Skip empty files
if (!$node) {
continue;
}
self::scanNodeInFile($node, $file_path, $visit_node);
}
}
示例7: analyze
/**
* @return null
* Analyze the node associated with this object
* in the given context
*/
public function analyze(Context $context, CodeBase $code_base) : Context
{
// Don't do anything if we care about being
// fast
if (Config::get()->quick_mode) {
return $context;
}
if (!$this->hasNode()) {
return $context;
}
// Don't go deeper than one level in
if ($this->recursion_depth++ > 2) {
return $context;
}
// Analyze the node in a cloned context so that we
// don't overwrite anything
$context = (new Phan())->analyzeNodeInContext($this->getNode(), clone $context, $code_base);
return $context;
}
示例8: analyzeReferenceCounts
/**
* Take a look at all globally accessible elements and see if
* we can find any dead code that is never referenced
*
* @return void
*/
public static function analyzeReferenceCounts(CodeBase $code_base)
{
// Check to see if dead code detection is enabled. Keep
// in mind that the results here are just a guess and
// we can't tell with certainty that anything is
// definitely unreferenced.
if (!Config::get()->dead_code_detection) {
return;
}
// Get the count of all known elements
$total_count = $code_base->totalElementCount();
$i = 0;
// Functions
self::analyzeElementListReferenceCounts($code_base, $code_base->getFunctionMap(), Issue::UnreferencedMethod, $total_count, $i);
// Constants
self::analyzeElementListReferenceCounts($code_base, $code_base->getGlobalConstantMap(), Issue::UnreferencedConstant, $total_count, $i);
// Classes
self::analyzeElementListReferenceCounts($code_base, $code_base->getClassMap(), Issue::UnreferencedClass, $total_count, $i);
// Class Maps
foreach ($code_base->getClassMapMap() as $class_map) {
self::analyzeClassMapReferenceCounts($code_base, $class_map, $total_count, $i);
}
}
示例9: err
public static function err(int $etype, string $msg, string $file = '', int $lineno = 0)
{
$log = self::getInstance();
if ($etype == self::EFATAL) {
self::display();
// Something went wrong - abort
if ($file) {
throw new \Exception("{$file}:{$lineno} {$msg}");
} else {
throw new \Exception($msg);
}
}
// If configured to do so, prepend the message
// with a trace ID which indicates where the issue
// came from allowing us to group on unique classes
// of issues
if (Config::get()->emit_trace_id) {
$msg = self::traceId(debug_backtrace()[1]) . ' ' . $msg;
}
if ($etype & $log->output_mask) {
$ukey = md5($file . $lineno . $etype . $msg);
$log->msgs[$ukey] = ['file' => $file, 'lineno' => $lineno, 'etype' => $etype, 'msg' => $msg];
}
}
示例10: addMethodWithScopeAndName
private function addMethodWithScopeAndName(FunctionInterface $method, string $scope, string $name)
{
$this->method_map[$scope][$name] = $method;
// If we're doing dead code detection, map the name
// directly to the method so we can quickly look up
// all methods with that name to add a possible
// reference
if (Config::get()->dead_code_detection) {
$this->method_name_map[strtolower($name)][] = $method;
}
// Associate the element with the file it was found in
$this->getFileByPath($method->getFileRef()->getFile())->addMethodFQSEN($method->getFQSEN());
}
示例11: contextForCode
/**
* Get a Context after parsing the given
* bit of code.
*/
private function contextForCode(string $code_stub) : Context
{
return Analysis::parseNodeInContext($this->code_base, new Context(), \ast\parse_code('<?php ' . $code_stub, Config::get()->ast_version));
}
示例12: visitReturn
/**
* Visit a node with kind `\ast\AST_RETURN`
*
* @param Node $node
* A node to parse
*
* @return Context
* A new or an unchanged context resulting from
* parsing the node
*/
public function visitReturn(Node $node) : Context
{
if (Config::get()->backward_compatibility_checks) {
(new ContextNode($this->code_base, $this->context, $node))->analyzeBackwardCompatibility();
}
// Make sure we're actually returning from a method.
if (!$this->context->isInFunctionLikeScope()) {
return $this->context;
}
// Get the method/function/closure we're in
$method = $this->context->getFunctionLikeInScope($this->code_base);
assert(!empty($method), "We're supposed to be in either method or closure scope.");
// Mark the method as returning something
$method->setHasReturn(($node->children['expr'] ?? null) !== null);
return $this->context;
}
示例13: projectPath
/**
* @return string
* The relative path appended to the project root directory.
*
* @suppress PhanUnreferencedMethod
*/
public static function projectPath(string $relative_path)
{
return implode(DIRECTORY_SEPARATOR, [Config::get()->getProjectRootDirectory(), $relative_path]);
}
示例14: analyzeOverrideSignature
/**
* Make sure signatures line up between methods and the
* methods they override
*
* @see https://en.wikipedia.org/wiki/Liskov_substitution_principle
*/
private static function analyzeOverrideSignature(CodeBase $code_base, Method $method)
{
if (!Config::get()->analyze_signature_compatibility) {
return;
}
// Hydrate the class this method is coming from in
// order to understand if its an override or not
$class = $method->getClass($code_base);
$class->hydrate($code_base);
// Check to see if the method is an override
// $method->analyzeOverride($code_base);
// Make sure we're actually overriding something
if (!$method->getIsOverride()) {
return;
}
// Dont' worry about signatures lining up on
// constructors. We just want to make sure that
// calling a method on a subclass won't cause
// a runtime error. We usually know what we're
// constructing at instantiation time, so there
// is less of a risk.
if ($method->getName() == '__construct') {
return;
}
// Get the method that is being overridden
$o_method = $method->getOverriddenMethod($code_base);
// Get the class that the overridden method lives on
$o_class = $o_method->getClass($code_base);
// PHP doesn't complain about signature mismatches
// with traits, so neither shall we
if ($o_class->isTrait()) {
return;
}
// Get the parameters for that method
$o_parameter_list = $o_method->getParameterList();
// If we have a parent type defined, map the method's
// return type and parameter types through it
$type_option = $class->getParentTypeOption();
// Map overridden method parameter types through any
// template type parameters we may have
if ($type_option->isDefined()) {
$o_parameter_list = array_map(function (Parameter $parameter) use($type_option, $code_base) : Parameter {
if (!$parameter->getUnionType()->hasTemplateType()) {
return $parameter;
}
$mapped_parameter = clone $parameter;
$mapped_parameter->setUnionType($mapped_parameter->getUnionType()->withTemplateParameterTypeMap($type_option->get()->getTemplateParameterTypeMap($code_base)));
return $mapped_parameter;
}, $o_parameter_list);
}
// Map overridden method return type through any template
// type parameters we may have
$o_return_union_type = $o_method->getUnionType();
if ($type_option->isDefined() && $o_return_union_type->hasTemplateType()) {
$o_return_union_type = $o_return_union_type->withTemplateParameterTypeMap($type_option->get()->getTemplateParameterTypeMap($code_base));
}
// Determine if the signatures match up
$signatures_match = true;
// Make sure the count of parameters matches
if ($method->getNumberOfRequiredParameters() > $o_method->getNumberOfRequiredParameters()) {
$signatures_match = false;
} else {
if ($method->getNumberOfParameters() < $o_method->getNumberOfParameters()) {
$signatures_match = false;
// If parameter counts match, check their types
} else {
foreach ($method->getParameterList() as $i => $parameter) {
if (!isset($o_parameter_list[$i])) {
continue;
}
$o_parameter = $o_parameter_list[$i];
// Changing pass by reference is not ok
// @see https://3v4l.org/Utuo8
if ($parameter->isPassByReference() != $o_parameter->isPassByReference()) {
$signatures_match = false;
break;
}
// A stricter type on an overriding method is cool
if ($o_parameter->getUnionType()->isEmpty() || $o_parameter->getUnionType()->isType(MixedType::instance())) {
continue;
}
// Its not OK to have a more relaxed type on an
// overriding method
//
// https://3v4l.org/XTm3P
if ($parameter->getUnionType()->isEmpty()) {
$signatures_match = false;
break;
}
// If we have types, make sure they line up
//
// TODO: should we be expanding the types on $o_parameter
// via ->asExpandedTypes($code_base)?
//
//.........这里部分代码省略.........
示例15: analyzeFile
/**
* Once we know what the universe looks like we
* can scan for more complicated issues.
*
* @param CodeBase $code_base
* The global code base holding all state
*
* @param string $file_path
* A list of files to scan
*
* @return Context
*/
public static function analyzeFile(CodeBase $code_base, string $file_path) : Context
{
// Convert the file to an Abstract Syntax Tree
// before passing it on to the recursive version
// of this method
$node = \ast\parse_file($file_path, Config::get()->ast_version);
// Set the file on the context
$context = (new Context())->withFile($file_path);
// Ensure we have some content
if (empty($node)) {
Issue::emit(Issue::EmptyFile, $file_path, 0, $file_path);
return $context;
}
// Start recursively analyzing the tree
return self::analyzeNodeInContext($code_base, $context, $node);
}