giscus comments
[mdref/mdref] / bin / ext2ref
1 #!/usr/bin/env php
2 <?php
3
4 require_once $_composer_autoload_path ?? __DIR__."/../vendor/autoload.php";
5
6 use mdref\Repo;
7 use mdref\Structure;
8 use mdref\StructureOfClass;
9 use mdref\StructureOfFunc;
10 use mdref\StructureOfNs;
11
12 if ($argc != 2) {
13 fprintf(STDERR, "Usage: cd ref-<extname> && %s <extname>\n", $argv[0]);
14 exit(1);
15 }
16
17 $repo = new Repo(".");
18 $ext = new ReflectionExtension($argv[1]);
19
20 $constants = array();
21 $functions = array();
22 $classes = array();
23
24 // split up by namespace first
25 foreach ($ext->getConstants() as $constant => $value) {
26 $ns_name = ($nsend = strrpos($constant, "\\")) ? substr($constant, 0, $nsend++) : "";
27 $cn = substr($constant, $nsend);
28 $constants[$ns_name][$cn] = $value;
29 }
30 foreach ($ext->getFunctions() as $f) {
31 /* @var $f ReflectionFunction */
32 $ns_name = $f->inNamespace() ? $f->getNamespaceName() : "";
33 $functions[$ns_name][$f->getShortName()] = $f;
34 }
35 foreach ($ext->getClasses() as $c) {
36 /* @var $c ReflectionClass */
37 $ns_name = $c->inNamespace() ? $c->getNamespaceName() : "";
38 $classes[$ns_name][$c->getShortName()] = $c;
39 }
40
41 $namespaces = array_unique(array_merge(
42 array_keys($constants),
43 array_keys($functions),
44 array_keys($classes)
45 ));
46
47 // simple sort
48 natsort($namespaces);
49
50 foreach ($namespaces as $ns_name) {
51 $ns_path = strtr($ns_name, "\\", "/");
52 if (!$repo->hasEntry($ns_path, $cn_path)) {
53 fprintf(STDERR, "Missing namespace %s\t%s.md\n", $ns_name, $ns_path);
54 } else {
55 $ns_entry = $repo->getEntry($cn_path ?? $ns_path);
56 $ns_struct = Structure::of($ns_entry);
57 /** @var StructureOfNs $ns_struct */
58 if (isset($constants[$ns_name])) foreach ($constants[$ns_name] as $const => $value) {
59 if (!isset($ns_struct->consts[$const])) {
60 fprintf(STDERR, "Missing constant %s in namespace %s\t%s.md\n",
61 $const, $ns_name, $cn_path ?? $ns_path);
62 }
63 }
64 // FIXME: functions are unconditionally assumed to be class methods by \mdref\Structure
65 if (isset($classes[$ns_name])) foreach ($classes[$ns_name] as $class_name => $class) {
66 $class_path = ($cn_path ?? $ns_path) . "/$class_name";
67 if (!isset($ns_struct->classes[$class_name])) {
68 fprintf(STDERR, "Missing class %s in namespace %s\t%s.md\n",
69 $class_name, $ns_name, $class_path);
70 } else {
71 $class_entry = $repo->getEntry($class_path);
72 /** @var StructureOfClass $class_struct */
73 $class_struct = Structure::of($class_entry);
74 /** @var ReflectionClass $class */
75 foreach ($class->getReflectionConstants() as $const) {
76 if ($const->getDeclaringClass()->getName() !== $class_entry->getNsName()) {
77 continue;
78 }
79 if (!isset($class_struct->consts[$const->getName()])) {
80 fprintf(STDERR, "Missing constant %s in class %s\t%s.md\n",
81 $const->getName(), $class->getName(), $class_path);
82 }
83 }
84 foreach ($class->getMethods() as $meth) {
85 //fprintf(STDERR, "Checking %s !== %s\n", $meth->getDeclaringClass()->getName(), $class_entry->getNsName());
86 if ($meth->getDeclaringClass()->getName() !== $class_entry->getNsName()) {
87 continue;
88 }
89 $meth_path = $class_path ."/". $meth->getName();
90 if (!isset($class_struct->funcs[$meth->getName()])) {
91 fprintf(STDERR, "Missing method %s in class %s\t%s.md\n",
92 $meth->getName(), $class->getName(), $meth_path);
93 } else {
94 $meth_entry = $repo->getEntry($meth_path);
95 /** @var StructureOfFunc $meth_struct */
96 $meth_struct = Structure::of($meth_entry);
97 if (count($meth_struct->params) != $meth->getNumberOfParameters()) {
98 fprintf(STDERR, "Missing params in method %s(%s) != arginfo(%s)\t%s\n",
99 $meth->getName(), implode(", ", array_keys($meth_struct->params)),
100 implode(", ", array_map(function($p){return "\$".$p->getName();}, $meth->getParameters())),
101 $meth_path);
102 }
103 }
104 }
105 }
106 }
107 }
108 }