Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Re-work how BasicValetDriver serves files in projects with and without public/ directory #1311

Merged
merged 3 commits into from
Dec 15, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
104 changes: 9 additions & 95 deletions cli/Valet/Drivers/BasicValetDriver.php
Original file line number Diff line number Diff line change
Expand Up @@ -27,11 +27,7 @@ public function serves($sitePath, $siteName, $uri)
*/
public function isStaticFile($sitePath, $siteName, $uri)
{
if (file_exists($staticFilePath = $sitePath.'/public'.rtrim($uri, '/').'/index.html')) {
return $staticFilePath;
} elseif (file_exists($staticFilePath = $sitePath.'/public'.rtrim($uri, '/').'/index.php')) {
return $staticFilePath;
} elseif (file_exists($staticFilePath = $sitePath.'/public'.$uri)) {
if (file_exists($staticFilePath = $sitePath.rtrim($uri, '/').'/index.html')) {
return $staticFilePath;
} elseif ($this->isActualFile($staticFilePath = $sitePath.$uri)) {
return $staticFilePath;
Expand All @@ -54,13 +50,16 @@ public function frontControllerPath($sitePath, $siteName, $uri)
$_SERVER['SERVER_ADDR'] = '127.0.0.1';
$_SERVER['SERVER_NAME'] = $_SERVER['HTTP_HOST'];

$dynamicCandidates = [
$this->asActualFile($sitePath, $uri),
$this->asPhpIndexFileInDirectory($sitePath, $uri),
$this->asHtmlIndexFileInDirectory($sitePath, $uri),
$uri = rtrim($uri, '/');

$candidates = [
$sitePath.$uri,
$sitePath.$uri.'/index.php',
$sitePath.'/index.php',
$sitePath.'/index.html',
];

foreach ($dynamicCandidates as $candidate) {
foreach ($candidates as $candidate) {
if ($this->isActualFile($candidate)) {
$_SERVER['SCRIPT_FILENAME'] = $candidate;
$_SERVER['SCRIPT_NAME'] = str_replace($sitePath, '', $candidate);
Expand All @@ -69,90 +68,5 @@ public function frontControllerPath($sitePath, $siteName, $uri)
return $candidate;
}
}

$fixedCandidatesAndDocroots = [
$this->asRootPhpIndexFile($sitePath) => $sitePath,
$this->asPublicPhpIndexFile($sitePath) => $sitePath.'/public',
$this->asPublicHtmlIndexFile($sitePath) => $sitePath.'/public',
];

foreach ($fixedCandidatesAndDocroots as $candidate => $docroot) {
if ($this->isActualFile($candidate)) {
$_SERVER['SCRIPT_FILENAME'] = $candidate;
$_SERVER['SCRIPT_NAME'] = '/index.php';
$_SERVER['DOCUMENT_ROOT'] = $docroot;

return $candidate;
}
}
}

/**
* Concatenate the site path and URI as a single file name.
*
* @param string $sitePath
* @param string $uri
* @return string
*/
protected function asActualFile($sitePath, $uri)
{
return $sitePath.$uri;
}

/**
* Format the site path and URI with a trailing "index.php".
*
* @param string $sitePath
* @param string $uri
* @return string
*/
protected function asPhpIndexFileInDirectory($sitePath, $uri)
{
return $sitePath.rtrim($uri, '/').'/index.php';
}

/**
* Format the site path and URI with a trailing "index.html".
*
* @param string $sitePath
* @param string $uri
* @return string
*/
protected function asHtmlIndexFileInDirectory($sitePath, $uri)
{
return $sitePath.rtrim($uri, '/').'/index.html';
}

/**
* Format the incoming site path as root "index.php" file path.
*
* @param string $sitePath
* @return string
*/
protected function asRootPhpIndexFile($sitePath)
{
return $sitePath.'/index.php';
}

/**
* Format the incoming site path as a "public/index.php" file path.
*
* @param string $sitePath
* @return string
*/
protected function asPublicPhpIndexFile($sitePath)
{
return $sitePath.'/public/index.php';
}

/**
* Format the incoming site path as a "public/index.php" file path.
*
* @param string $sitePath
* @return string
*/
protected function asPublicHtmlIndexFile($sitePath)
{
return $sitePath.'/public/index.html';
}
}
75 changes: 75 additions & 0 deletions cli/Valet/Drivers/BasicWithPublicValetDriver.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
<?php

namespace Valet\Drivers;

class BasicWithPublicValetDriver extends ValetDriver
{
/**
* Determine if the driver serves the request.
*
* @param string $sitePath
* @param string $siteName
* @param string $uri
* @return bool
*/
public function serves($sitePath, $siteName, $uri)
{
return is_dir($sitePath.'/public/');
}

/**
* Determine if the incoming request is for a static file.
*
* @param string $sitePath
* @param string $siteName
* @param string $uri
* @return string|false
*/
public function isStaticFile($sitePath, $siteName, $uri)
{
$publicPath = $sitePath.'/public/'.trim($uri, '/');

if ($this->isActualFile($publicPath)) {
return $publicPath;
} elseif (file_exists($publicPath.'/index.html')) {
return $publicPath.'/index.html';
}

return false;
}

/**
* Get the fully resolved path to the application's front controller.
*
* @param string $sitePath
* @param string $siteName
* @param string $uri
* @return string
*/
public function frontControllerPath($sitePath, $siteName, $uri)
{
$_SERVER['PHP_SELF'] = $uri;
$_SERVER['SERVER_ADDR'] = '127.0.0.1';
$_SERVER['SERVER_NAME'] = $_SERVER['HTTP_HOST'];

$docRoot = $sitePath.'/public';
$uri = rtrim($uri, '/');

$candidates = [
$docRoot.$uri,
$docRoot.$uri.'/index.php',
$docRoot.'/index.php',
$docRoot.'/index.html',
];

foreach ($candidates as $candidate) {
if ($this->isActualFile($candidate)) {
$_SERVER['SCRIPT_FILENAME'] = $candidate;
$_SERVER['SCRIPT_NAME'] = str_replace($sitePath.'/public', '', $candidate);
$_SERVER['DOCUMENT_ROOT'] = $sitePath.'/public';

return $candidate;
}
}
}
}
1 change: 1 addition & 0 deletions cli/Valet/Drivers/ValetDriver.php
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@ public static function assign($sitePath, $siteName, $uri)
$drivers[] = 'NeosValetDriver';
$drivers[] = 'Magento2ValetDriver';

$drivers[] = 'BasicWithPublicValetDriver';
$drivers[] = 'BasicValetDriver';

foreach ($drivers as $driver) {
Expand Down
5 changes: 5 additions & 0 deletions tests/Drivers/BaseDriverTestCase.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,11 @@

class BaseDriverTestCase extends Yoast\PHPUnitPolyfills\TestCases\TestCase
{
public function set_up(): void
{
$_SERVER['HTTP_HOST'] = 'this is set in Valet requests but not phpunit';
}

public function projects(): array
{
return Filesystem::scanDir(__DIR__.'/projects');
Expand Down
55 changes: 55 additions & 0 deletions tests/Drivers/BasicValetDriverTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -12,4 +12,59 @@ public function test_it_serves_anything()
$this->assertTrue($driver->serves($projectDir, 'my-site', '/'));
}
}

public function test_it_serves_php_files_from_root()
{
$projectPath = $this->projectDir('basic-no-public');
$driver = new BasicValetDriver();

$this->assertEquals(
$projectPath.'/file-in-root.php',
$driver->frontControllerPath($projectPath, 'my-site', '/file-in-root.php')
);
}

public function test_it_serves_directory_with_index_php()
{
$projectPath = $this->projectDir('basic-no-public');
$driver = new BasicValetDriver();

$this->assertEquals(
$projectPath.'/about/index.php',
$driver->frontControllerPath($projectPath, 'my-site', '/about')
);
}

public function test_it_routes_to_index_if_404()
{
$projectPath = $this->projectDir('basic-no-public');
$driver = new BasicValetDriver();

$this->assertEquals(
$projectPath.'/index.php',
$driver->frontControllerPath($projectPath, 'my-site', '/not-a-real-url')
);
}

public function test_it_serves_directory_with_index_html()
{
$projectPath = $this->projectDir('basic-no-public');
$driver = new BasicValetDriver();

$this->assertEquals(
$projectPath.'/team/index.html',
$driver->isStaticFile($projectPath, 'my-site', '/team')
);
}

public function test_it_serves_static_files()
{
$projectPath = $this->projectDir('basic-no-public');
$driver = new BasicValetDriver();

$this->assertEquals(
$projectPath.'/assets/document.txt',
$driver->isStaticFile($projectPath, 'my-site', '/assets/document.txt')
);
}
}
86 changes: 86 additions & 0 deletions tests/Drivers/BasicWithPublicValetDriverTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
<?php

use Valet\Drivers\BasicWithPublicValetDriver;

class BasicWithPublicValetDriverTest extends BaseDriverTestCase
{
public function test_it_serves_anything_with_public()
{
$driver = new BasicWithPublicValetDriver();

$this->assertTrue($driver->serves($this->projectDir('public-with-index-non-laravel'), 'my-site', '/'));
}

public function test_it_doesnt_serve_from_not_public()
{
$driver = new BasicWithPublicValetDriver();

$this->assertFalse($driver->serves($this->projectDir('basic-no-public'), 'my-site', '/'));
}

public function test_it_serves_php_files_from_public()
{
$projectPath = $this->projectDir('public-with-index-non-laravel');
$driver = new BasicWithPublicValetDriver();

$this->assertEquals(
$projectPath.'/public/file-in-public.php',
$driver->frontControllerPath($projectPath, 'my-site', '/file-in-public.php')
);
}

public function test_it_doesnt_serve_php_files_from_root()
{
$projectPath = $this->projectDir('public-with-index-non-laravel');
$driver = new BasicWithPublicValetDriver();

$this->assertEquals(
$projectPath.'/public/index.php',
$driver->frontControllerPath($projectPath, 'my-site', '/file-in-root.php')
);
}

public function test_it_serves_directory_with_index_php()
{
$projectPath = $this->projectDir('public-with-index-non-laravel');
$driver = new BasicWithPublicValetDriver();

$this->assertEquals(
$projectPath.'/public/about/index.php',
$driver->frontControllerPath($projectPath, 'my-site', '/about')
);
}

public function test_it_route_to_public_index_if_404()
{
$projectPath = $this->projectDir('public-with-index-non-laravel');
$driver = new BasicWithPublicValetDriver();

$this->assertEquals(
$projectPath.'/public/index.php',
$driver->frontControllerPath($projectPath, 'my-site', '/not-a-real-url')
);
}

public function test_it_serves_directory_with_index_html()
{
$projectPath = $this->projectDir('public-with-index-non-laravel');
$driver = new BasicWithPublicValetDriver();

$this->assertEquals(
$projectPath.'/public/team/index.html',
$driver->isStaticFile($projectPath, 'my-site', '/team')
);
}

public function test_it_serves_static_files()
{
$projectPath = $this->projectDir('public-with-index-non-laravel');
$driver = new BasicWithPublicValetDriver();

$this->assertEquals(
$projectPath.'/public/assets/document.txt',
$driver->isStaticFile($projectPath, 'my-site', '/assets/document.txt')
);
}
}
2 changes: 0 additions & 2 deletions tests/Drivers/BedrockValetDriverTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,6 @@ public function test_it_gets_front_controller()
{
$driver = new BedrockValetDriver();

$_SERVER['HTTP_HOST'] = 'this is set in Valet requests but not phpunit';

$projectPath = $this->projectDir('bedrock');
$this->assertEquals($projectPath.'/web/index.php', $driver->frontControllerPath($projectPath, 'my-site', '/'));
}
Expand Down
2 changes: 0 additions & 2 deletions tests/Drivers/CraftValetDriverTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,6 @@ public function test_it_gets_front_controller()
{
$driver = new CraftValetDriver();

$_SERVER['HTTP_HOST'] = 'this is set in Valet requests but not phpunit';

$projectPath = $this->projectDir('craft');
$this->assertEquals($projectPath.'/public/index.php', $driver->frontControllerPath($projectPath, 'my-site', '/'));
}
Expand Down
2 changes: 0 additions & 2 deletions tests/Drivers/DrupalValetDriverTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,6 @@ public function test_it_gets_front_controller()
{
$driver = new DrupalValetDriver();

$_SERVER['HTTP_HOST'] = 'this is set in Valet requests but not phpunit';

$projectPath = $this->projectDir('drupal');
$this->assertEquals($projectPath.'/public/index.php', $driver->frontControllerPath($projectPath, 'my-site', '/'));
}
Expand Down
Loading