Skip to content

Commit

Permalink
Merge "Less_Parser: Refactor import_callback option and add tests a…
Browse files Browse the repository at this point in the history
…nd docs"
  • Loading branch information
jenkins-bot authored and Gerrit Code Review committed Mar 26, 2024
2 parents 9294701 + 3539122 commit 0a022bd
Show file tree
Hide file tree
Showing 6 changed files with 135 additions and 81 deletions.
17 changes: 17 additions & 0 deletions lib/Less/Environment.php
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,8 @@ class Less_Environment {

public $strictMath = false;

public $importCallback = null;

/**
* @var array
*/
Expand Down Expand Up @@ -115,6 +117,21 @@ public static function isPathRelative( $path ) {
return !preg_match( '/^(?:[a-z-]+:|\/|#)/', $path );
}

/**
* Apply legacy 'import_callback' option.
*
* See Less_Parser::$default_options to learn more about the 'import_callback' option.
* This option is deprecated in favour of Less_Parser::SetImportDirs.
*
* @param Less_Tree_Import $importNode
* @return array{0:string,1:string|null}|null Array containing path and (optional) uri or null
*/
public function callImportCallback( Less_Tree_Import $importNode ) {
if ( is_callable( $this->importCallback ) ) {
return ( $this->importCallback )( $importNode );
}
}

/**
* Canonicalize a path by resolving references to '/./', '/../'
* Does not remove leading "../"
Expand Down
3 changes: 1 addition & 2 deletions lib/Less/ImportVisitor.php
Original file line number Diff line number Diff line change
Expand Up @@ -94,8 +94,7 @@ public function processImportNode( $importNode, $env, &$importParent ) {
// import dirs resolution logic.
// TODO: We might need upstream's `tryAppendLessExtension` logic here.
// We currenlty do do this in getPath instead.
$callback = Less_Parser::$options['import_callback'];
$path_and_uri = is_callable( $callback ) ? $callback( $importNode ) : null;
$path_and_uri = $env->callImportCallback( $importNode );
if ( !$path_and_uri ) {
$path_and_uri = $importNode->PathAndUri();
}
Expand Down
27 changes: 27 additions & 0 deletions lib/Less/Parser.php
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,29 @@ class Less_Parser {
'numPrecision' => 8,

'import_dirs' => [],

// Override how imported file names are resolved.
//
// This legacy calllback exposes internal objects and their implementation
// details and is therefore deprecated. Use Less_Parser::SetImportDirs instead
// to override the resolution of imported file names.
//
// Example:
//
// $parser = new Less_Parser( [
// 'import_callback' => function ( $importNode ) {
// $path = $importNode->getPath();
// if ( $path === 'special.less' ) {
// return [ $mySpecialFilePath, null ];
// }
// }
// ] );
//
// @since 1.5.1
// @deprecated since 4.3.0
// @see Less_Environment::callImportCallback
// @see Less_Parser::SetImportDirs
//
'import_callback' => null,
'cache_dir' => null,
'cache_method' => 'serialize', // false, 'serialize', 'callback';
Expand Down Expand Up @@ -133,6 +156,10 @@ public function SetOption( $option, $value ) {
$this->SetImportDirs( $value );
return;

case 'import_callback':
$this->env->importCallback = $value;
return;

case 'cache_dir':
if ( is_string( $value ) ) {
Less_Cache::SetCacheDir( $value );
Expand Down
5 changes: 2 additions & 3 deletions lib/Less/Tree/Import.php
Original file line number Diff line number Diff line change
Expand Up @@ -164,8 +164,7 @@ public function compile( $env ) {
// about Less_Tree_Import::PathAndUri() is fixed, this can be removed by letting
// skip() call $this->PathAndUri() on its own.
// get path & uri
$callback = Less_Parser::$options['import_callback'];
$path_and_uri = is_callable( $callback ) ? $callback( $this ) : null;
$path_and_uri = $env->callImportCallback( $this );
if ( !$path_and_uri ) {
$path_and_uri = $this->PathAndUri();
}
Expand Down Expand Up @@ -217,7 +216,7 @@ public function compile( $env ) {
*/
public function PathAndUri() {
$evald_path = $this->getPath();
// TODO: Move 'import_callback' and getPath() fallback logic from callers
// TODO: Move callImportCallback() and getPath() fallback logic from callers
// to here so that PathAndUri() is equivalent to upstream fileManager.getPath()

if ( $evald_path ) {
Expand Down
76 changes: 0 additions & 76 deletions test/phpunit/ImportDirsTest.php

This file was deleted.

88 changes: 88 additions & 0 deletions test/phpunit/ParserTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,94 @@ public function testGetParsedFiles() {
);
}

public static function provideSetImportDirs() {
yield 'from-importdir' => [
'from-importdir.less',
[
__DIR__ . '/data/importdir-somevars/' => '',
],
'div{font-family:monospace}'
];
yield 'from-importdir-file' => [
'from-importdir-file.less',
[
__DIR__ . '/data/importdir-somevars/' => '',
],
'div{font-family:fantasy}'
];
yield 'from-importdir-filenosuffix' => [
'from-importdir-filenosuffix.less',
[
__DIR__ . '/data/importdir-somevars/' => '',
],
'div{font-family:fantasy}'
];
yield 'from-importcallback (backcompat)' => [
'from-importcallback.less',
[
__DIR__ . '/data/importdir-somevars/' => '',
static function ( $path ) {
// Backwards compatibility with how people used
// less.php 4.0.0 and earlier.
if ( $path === '@wikimedia/example.less' ) {
return [
Less_Environment::normalizePath( __DIR__ . '/data/importdir-somevars/callme.less' ),
Less_Environment::normalizePath( dirname( $path ) )
];
}
return [ null, null ];
}
],
'div{font-family:Call Me Maybe}'
];
yield 'from-importcallback (new)' => [
'from-importcallback.less',
[
__DIR__ . '/data/importdir-somevars/' => '',
static function ( $path ) {
if ( $path === '@wikimedia/example.less' ) {
return [
__DIR__ . '/data/importdir-somevars/callme.less',
null
];
}
}
],
'div{font-family:Call Me Maybe}'
];
}

/**
* @dataProvider provideSetImportDirs
*/
public function testSetImportDirs( string $input, array $importDirs, string $expect ) {
$file = __DIR__ . '/data/consume-somevars/' . $input;

$parser = new Less_Parser( [
'compress' => true,
] );
$parser->SetImportDirs( $importDirs );
$parser->parseFile( $file );

$this->assertEquals( $expect, $parser->getCss() );
}

public function testImportCallback() {
$file = __DIR__ . '/data/consume-somevars/from-importcallback.less';

$parser = new Less_Parser( [
'compress' => true,
'import_callback' => static function ( $importNode ) {
if ( $importNode->getPath() === '@wikimedia/example.less' ) {
return [ __DIR__ . '/data/importdir-somevars/callme.less', '/site' ];
}
}
] );
$parser->parseFile( $file );

$this->assertEquals( 'div{font-family:Call Me Maybe}', $parser->getCss() );
}

public function testOperationException() {
$lessFile = __DIR__ . '/data/exception/f2.less';

Expand Down

0 comments on commit 0a022bd

Please sign in to comment.