PHP Classes

File: scripts/generate-docs.php

Recommend this page to a friend!
  Classes of Mohamed Ahmed   Laravel MCP SDK   scripts/generate-docs.php   Download  
File: scripts/generate-docs.php
Role: Example script
Content typex: text/plain
Description: Example script
Class: Laravel MCP SDK
Create tools to process user requests with prompts
Author: By
Last change:
Date: 2 days ago
Size: 6,999 bytes
 

Contents

Class file image Download
<?php

require __DIR__ . '/../vendor/autoload.php';

use
Nette\PhpGenerator\ClassType;
use
Nette\PhpGenerator\PhpNamespace;

// Configuration
$srcDir = realpath(__DIR__ . '/../src');
$docsDir = realpath(__DIR__ . '/../docs') . '/api';

// Create docs directory if it doesn't exist
if (!is_dir($docsDir)) {
   
mkdir($docsDir, 0777, true);
}

// Function to parse PHPDoc comments
function parseDocComment($docComment) {
    if (empty(
$docComment)) {
        return
'';
    }
   
$docComment = trim(preg_replace('/^\s*\/\*+|\s*\*+\/\s*$/s', '', $docComment));
   
$docComment = preg_replace('/^\s*\* ?/m', '', $docComment);
    return
$docComment;
}

// Function to generate documentation for a file
function generateFileDoc($file, $docsDir) {
   
$content = file_get_contents($file);
   
$tokens = token_get_all($content);
   
$namespace = '';
   
$classes = [];
   
$currentClass = null;

    foreach (
$tokens as $token) {
        if (!
is_array($token)) {
            continue;
        }

        switch (
$token[0]) {
            case
T_NAMESPACE:
               
$namespace = '';
               
$i = array_search($token, $tokens) + 2;
                while (isset(
$tokens[$i]) && is_array($tokens[$i])) {
                    if (
$tokens[$i][0] === T_STRING || $tokens[$i][0] === T_NS_SEPARATOR) {
                       
$namespace .= $tokens[$i][1];
                    }
                   
$i++;
                }
                break;

            case
T_CLASS:
               
$i = array_search($token, $tokens) + 2;
                if (isset(
$tokens[$i]) && is_array($tokens[$i])) {
                   
$className = trim($tokens[$i][1]);
                    if (empty(
$className)) {
                        continue
2;
                    }
                   
                   
$currentClass = [
                       
'name' => $className,
                       
'namespace' => $namespace,
                       
'docComment' => '',
                       
'methods' => []
                    ];
                   
                   
// Look for class doc comment
                   
$j = array_search($token, $tokens) - 2;
                    while (isset(
$tokens[$j]) && is_array($tokens[$j])) {
                        if (
$tokens[$j][0] === T_DOC_COMMENT) {
                           
$currentClass['docComment'] = parseDocComment($tokens[$j][1]);
                            break;
                        }
                       
$j--;
                    }
                   
                   
$classes[] = $currentClass;
                }
                break;

            case
T_FUNCTION:
                if (
$currentClass !== null) {
                   
$i = array_search($token, $tokens) + 2;
                    if (isset(
$tokens[$i]) && is_array($tokens[$i])) {
                       
$methodName = trim($tokens[$i][1]);
                        if (empty(
$methodName)) {
                            continue
2;
                        }
                       
                       
$method = ['name' => $methodName, 'docComment' => ''];
                       
                       
// Look for method doc comment
                       
$j = array_search($token, $tokens) - 2;
                        while (isset(
$tokens[$j]) && is_array($tokens[$j])) {
                            if (
$tokens[$j][0] === T_DOC_COMMENT) {
                               
$method['docComment'] = parseDocComment($tokens[$j][1]);
                                break;
                            }
                           
$j--;
                        }
                       
                       
$classes[count($classes) - 1]['methods'][] = $method;
                    }
                }
                break;
        }
    }

   
// Generate documentation
   
foreach ($classes as $class) {
        if (empty(
trim($class['name']))) {
            continue;
        }
       
       
$classDoc = "# {$class['name']}\n\n";
       
$classDoc .= "Namespace: `{$class['namespace']}`\n\n";
       
        if (!empty(
$class['docComment'])) {
           
$classDoc .= "{$class['docComment']}\n\n";
        }

        if (!empty(
$class['methods'])) {
           
$classDoc .= "## Methods\n\n";
            foreach (
$class['methods'] as $method) {
                if (empty(
trim($method['name']))) {
                    continue;
                }
               
$classDoc .= "### {$method['name']}\n\n";
                if (!empty(
$method['docComment'])) {
                   
$classDoc .= "{$method['docComment']}\n\n";
                }
            }
        }

       
$safeFilename = preg_replace('/[^a-zA-Z0-9_-]/', '_', $class['namespace'] . '_' . $class['name']);
       
$filename = $docsDir . '/' . $safeFilename . '.md';
       
file_put_contents($filename, $classDoc);
    }

    return
$classes;
}

// Generate index file
$indexContent = "# API Documentation\n\n";
$indexContent .= "Welcome to the Laravel MCP SDK API documentation.\n\n";
$indexContent .= "## Classes\n\n";

// Process all PHP files in src directory
$iterator = new RecursiveIteratorIterator(new RecursiveDirectoryIterator($srcDir));
$allClasses = [];
$seenClasses = [];

foreach (
$iterator as $file) {
    if (
$file->isFile() && $file->getExtension() === 'php') {
       
$classes = generateFileDoc($file, $docsDir);
        foreach (
$classes as $class) {
            if (empty(
trim($class['name']))) {
                continue;
            }
           
           
// Skip duplicate classes
           
$classKey = $class['namespace'] . '\\' . $class['name'];
            if (isset(
$seenClasses[$classKey])) {
                continue;
            }
           
$seenClasses[$classKey] = true;
           
           
$allClasses[] = [
               
'name' => $class['name'],
               
'namespace' => $class['namespace'],
               
'file' => preg_replace('/[^a-zA-Z0-9_-]/', '_', $class['namespace'] . '_' . $class['name']) . '.md'
           
];
        }
    }
}

// Sort classes by namespace and name
usort($allClasses, function($a, $b) {
   
$nsCompare = strcmp($a['namespace'], $b['namespace']);
    return
$nsCompare !== 0 ? $nsCompare : strcmp($a['name'], $b['name']);
});

// Group classes by namespace
$groupedClasses = [];
foreach (
$allClasses as $class) {
    if (empty(
trim($class['name']))) {
        continue;
    }
   
$namespace = trim($class['namespace']) ?: 'Global';
    if (!isset(
$groupedClasses[$namespace])) {
       
$groupedClasses[$namespace] = [];
    }
   
$groupedClasses[$namespace][] = $class;
}

// Generate index content
foreach ($groupedClasses as $namespace => $classes) {
   
$indexContent .= "\n### {$namespace}\n\n";
    foreach (
$classes as $class) {
        if (!empty(
trim($class['name']))) {
           
$indexContent .= "* [{$class['name']}](api/{$class['file']})\n";
        }
    }
}

file_put_contents(dirname($docsDir) . '/index.md', $indexContent);

echo
"Documentation generated successfully in {$docsDir}\n";