* @author Brion Vibber * @author Alexandre Emsenhuber * @version first release */ require_once __DIR__ . '/Maintenance.php'; /** * Maintenance script that builds doxygen documentation. * @ingroup Maintenance */ class MWDocGen extends Maintenance { /** * Prepare Maintenance class */ public function __construct() { parent::__construct(); $this->addDescription( 'Build doxygen documentation' ); $this->addOption( 'doxygen', 'Path to doxygen', false, true ); $this->addOption( 'version', 'Pass a MediaWiki version', false, true ); $this->addOption( 'generate-man', 'Whether to generate man files' ); $this->addOption( 'file', "Only process given file or directory. Multiple values " . "accepted with comma separation. Path relative to \$IP.", false, true ); $this->addOption( 'output', 'Path to write doc to', false, true ); $this->addOption( 'no-extensions', 'Ignore extensions' ); } public function getDbType() { return Maintenance::DB_NONE; } protected function init() { global $wgPhpCli, $IP; $this->doxygen = $this->getOption( 'doxygen', 'doxygen' ); $this->mwVersion = $this->getOption( 'version', 'master' ); $this->input = ''; $inputs = explode( ',', $this->getOption( 'file', '' ) ); foreach ( $inputs as $input ) { # Doxygen inputs are space separted and double quoted $this->input .= " \"$IP/$input\""; } $this->output = $this->getOption( 'output', "$IP/docs" ); // Do not use wfShellWikiCmd, because mwdoc-filter.php is not // a Maintenance script. $this->inputFilter = wfEscapeShellArg( [ $wgPhpCli, $IP . '/maintenance/mwdoc-filter.php' ] ); $this->template = $IP . '/maintenance/Doxyfile'; $this->excludes = [ 'vendor', 'node_modules', 'images', 'static', ]; $this->excludePatterns = []; if ( $this->hasOption( 'no-extensions' ) ) { $this->excludePatterns[] = 'extensions'; } $this->doDot = shell_exec( 'which dot' ); $this->doMan = $this->hasOption( 'generate-man' ); } public function execute() { global $IP; $this->init(); # Build out directories we want to exclude $exclude = ''; foreach ( $this->excludes as $item ) { $exclude .= " $IP/$item"; } $excludePatterns = implode( ' ', $this->excludePatterns ); $conf = strtr( file_get_contents( $this->template ), [ '{{OUTPUT_DIRECTORY}}' => $this->output, '{{STRIP_FROM_PATH}}' => $IP, '{{CURRENT_VERSION}}' => $this->mwVersion, '{{INPUT}}' => $this->input, '{{EXCLUDE}}' => $exclude, '{{EXCLUDE_PATTERNS}}' => $excludePatterns, '{{HAVE_DOT}}' => $this->doDot ? 'YES' : 'NO', '{{GENERATE_MAN}}' => $this->doMan ? 'YES' : 'NO', '{{INPUT_FILTER}}' => $this->inputFilter, ] ); $tmpFile = tempnam( wfTempDir(), 'MWDocGen-' ); if ( file_put_contents( $tmpFile, $conf ) === false ) { $this->fatalError( "Could not write doxygen configuration to file $tmpFile\n" ); } $command = $this->doxygen . ' ' . $tmpFile; $this->output( "Executing command:\n$command\n" ); $exitcode = 1; system( $command, $exitcode ); $this->output( <<fatalError( "Something went wrong (exit: $exitcode)\n", $exitcode ); } } } $maintClass = MWDocGen::class; require_once RUN_MAINTENANCE_IF_MAIN;