Skip to content
Snippets Groups Projects
Commit b59bb32c authored by Marc Orcau's avatar Marc Orcau
Browse files

Issue #2245943 by budalokko: Provide automated tests

parent fb445b4b
No related branches found
No related tags found
1 merge request!11Resolve #2245943 "Provide automated tests"
Pipeline #65959 passed with warnings
......@@ -51,6 +51,14 @@ include:
# variables:
# SKIP_ESLINT: '1'
phpunit:
extends: .phpunit-base
before_script:
- mkdir -p $CI_PROJECT_DIR/$_WEB_ROOT/libraries
- curl https://codeload.github.com/moxiecode/plupload/zip/refs/tags/v2.3.9 --output plupload.zip --silent
- unzip plupload.zip -d $CI_PROJECT_DIR/$_WEB_ROOT/libraries
- mv $CI_PROJECT_DIR/$_WEB_ROOT/libraries/plupload-2.3.9 $CI_PROJECT_DIR/$_WEB_ROOT/libraries/plupload
- rm -R $CI_PROJECT_DIR/$_WEB_ROOT/libraries/plupload/examples
###################################################################################
#
......
plupload.settings:
type: config_object
label: 'Plupload settings'
mapping:
temporary_uri:
type: string
label: 'Temporary upload uri'
......@@ -180,7 +180,7 @@ class UploadController implements ContainerInjectionInterface {
// Originally it was:
// if (empty($multipart_file['tmp_name']) ||
// !is_uploaded_file($multipart_file['tmp_name'])) {.
if (!$multipart_file->getPathname() || !is_uploaded_file($multipart_file->getPathname())) {
if (!$multipart_file->getPathname() || !$this->isUploadedFile($multipart_file->getPathname())) {
throw new UploadException(UploadException::MOVE_ERROR);
}
}
......@@ -209,4 +209,17 @@ class UploadController implements ContainerInjectionInterface {
}
}
/**
* Check if passed URI is an uploaded file.
*
* @param string $filename
* The URI to check.
*
* @return bool
* Whether the URI is an uploaded file.
*/
protected function isUploadedFile(string $filename): bool {
return is_uploaded_file($filename);
}
}
File added
<?php
namespace Drupal\Tests\plupload\FunctionalJavascript;
/**
* Test Plupload Widget.
*
* @group plupload
*/
class PluploadWebDriverTest extends PluploadWebDriverTestBase {
/**
* {@inheritdoc}
*/
protected $defaultTheme = 'stark';
/**
* {@inheritdoc}
*/
protected static $modules = [
'file',
'plupload',
'plupload_test',
];
/**
* Permissions for user that will be logged-in for test.
*
* @var array
*/
protected static $userPermissions = [
'access content',
'administer site configuration',
];
/**
* {@inheritdoc}
*/
protected function setUp(): void {
parent::setUp();
$account = $this->drupalCreateUser(static::$userPermissions);
$this->drupalLogin($account);
}
/**
* Tests the add widget with iframe form.
*/
public function testUploadFile() {
$this->drupalGet('plupload-test');
$web_assert = $this->assertSession();
$page = $this->getSession()->getPage();
// Wait for DOM load finished.
$web_assert->waitForElementVisible('css', '.plupload_wrapper');
$web_assert->pageTextContains('Drag files here.');
// Add test file.
$this->addFile($this->getTestFilePath('plupload-test-file.zip'));
// Upload file.
$web_assert->waitForElementRemoved('css', '.plupload_start.plupload_disabled');
$page->clickLink('Start Upload');
// Submit form.
$web_assert->waitForElementVisible('css', '.plupload_progress');
$page->pressButton('Submit');
$web_assert->pageTextContains('Files uploaded correctly: public://plupload-test/plupload-test-file.zip.');
}
}
<?php
namespace Drupal\Tests\plupload\FunctionalJavascript;
use Drupal\FunctionalJavascriptTests\WebDriverTestBase;
/**
* Base class for Plupload Web driver functional test base.
*
* @group plupload
*/
abstract class PluploadWebDriverTestBase extends WebDriverTestBase {
/**
* Add a predefined file to Plupload upload queue.
*
* @param string $path
* The path to the file.
*/
protected function addFile(string $path): void {
$session = $this->getSession();
// Add a fake input element.
$input = <<<JS
jQuery('#edit-plupload').append('<input type=\'file\' name=\'fakefile\'>');
JS;
$session->evaluateScript($input);
// Populate the field with uploaded file.
$session->getPage()->attachFileToField('fakefile', $path);
// Add to plupload queue.
$drop = <<<JS
jQuery('#edit-plupload').pluploadQueue().addFile(jQuery('input[name="fakefile"]')[0]);
JS;
$session->evaluateScript($drop);
}
/**
* Returns the path to a test file.
*
* @param string $name
* The name of the file.
*
* @return string
* Path of the test file.
*/
protected function getTestFilePath(string $name): string {
return \Drupal::service('extension.list.module')->getPath('plupload') . '/tests/fixtures/files/' . $name;
}
}
<?php
namespace Drupal\Tests\plupload\Kernel;
use Drupal\KernelTests\KernelTestBase;
/**
* Tests related to the PlUpload element.
*
* @group plupload
*/
class PluploadFileElementTest extends KernelTestBase {
/**
* Modules to enable.
*
* @var array
*/
protected static $modules = [
'system',
'plupload',
'plupload_test',
];
/**
* Tests that the plupload element appears.
*/
public function testPluploadElement() {
$this->container->get('router.builder')->rebuild();
$form = \Drupal::formBuilder()
->getForm('\Drupal\plupload_test\PluploadTestForm');
$this->render($form);
$xpath_base = "//div[contains(@class, 'form-item-plupload')]";
// Label.
$this->assertEmpty($this->xpath("$xpath_base/label[text()='Not Plupload element']"));
$this->assertNotEmpty($this->xpath("$xpath_base/label[text()='Plupload']"));
// Element where plupload is attached to.
$this->assertNotEmpty($this->xpath("$xpath_base/div[contains(@class, 'plupload-element')]"));
// Js is attached.
$module_dir = \Drupal::service('extension.list.module')->getPath('plupload');
$this->assertNotEmpty($this->xpath("//html/body/script[contains(@src, 'libraries/plupload/js/jquery.plupload.queue/jquery.plupload.queue.min.js')]"));
$this->assertNotEmpty($this->xpath("//html/body/script[contains(@src, '$module_dir/plupload.js')]"));
// Settings.
$result = $this->xpath("//html/body/script[contains(@data-drupal-selector, 'drupal-settings-json')]");
$this->assertNotEmpty($result);
$drupal_settings = json_decode((string) $result[0]);
$this->assertObjectHasProperty('plupload', $drupal_settings);
$this->assertObjectHasProperty('filters', $drupal_settings->plupload->{"edit-plupload"});
$filters = $drupal_settings->plupload->{"edit-plupload"}->filters;
$this->assertEquals('Allowed files', $filters[0]->title);
$this->assertEquals('zip', $filters[0]->extensions);
}
}
<?php
namespace Drupal\Tests\plupload\Kernel;
use Drupal\Core\DependencyInjection\ContainerInjectionInterface;
use Drupal\plupload\UploadController;
/**
* Mocked Plupload upload controller.
*/
class TestUploadController extends UploadController implements ContainerInjectionInterface {
/**
* {@inheritdoc}
*/
protected function isUploadedFile(string $filename): bool {
return file_exists($filename);
}
}
<?php
namespace Drupal\Tests\plupload\Kernel;
use Drupal\KernelTests\KernelTestBase;
use Symfony\Component\HttpFoundation\File\UploadedFile;
use Symfony\Component\HttpFoundation\FileBag;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Component\HttpFoundation\Request;
/**
* Tests PlUpload upload controller.
*
* @group plupload
*/
class UploadControllerTest extends KernelTestBase {
/**
* Temporary file (location + name).
*
* @var string
*/
protected $tmpFile = '';
/**
* Temp dir.
*
* @var string
*/
protected $filesDir = '';
/**
* Testfile prefix.
*
* @var string
*/
protected $testfilePrefix = 'pluploadtest_';
/**
* Testfile data.
*
* @var string
*/
protected $testfileData = 'Plupload test file data';
/**
* Modules to enable.
*
* @var array
*/
protected static $modules = ['plupload'];
/**
* {@inheritdoc}
*/
protected function setUp(): void {
parent::setUp();
$this->installConfig('plupload');
$this->filesDir = $this->siteDirectory . '/files';
$this->setSetting('file_temp_path', $this->filesDir);
$this->tmpFile = tempnam('', $this->testfilePrefix);
file_put_contents($this->tmpFile, $this->testfileData);
}
/**
* Test that Plupload correctly handles uploads.
*/
public function testUploadController() {
$this->container->get('router.builder')->rebuild();
$unicode_emoticon = json_decode('"\uD83D\uDE0E"');
$tmp_filename = 'o_loremipsum.tmp';
$controller_result = $this->sendPluploadRequest($this->tmpFile, "{$this->testfilePrefix}controller-Капля a,A;1{$unicode_emoticon}.jpg", $tmp_filename);
$this->assertInstanceOf(JsonResponse::class, $controller_result);
$this->assertEquals(200, $controller_result->getStatusCode());
$result = json_decode($controller_result->getContent());
$this->assertIsObject($result);
$this->assertEquals([
'jsonrpc' => '2.0',
'result' => NULL,
'id' => 'id',
], (array) $result);
$file_uploaded_uri = $this->config('plupload.settings')->get('temporary_uri') . '/' . $tmp_filename;
$this->assertFileExists($file_uploaded_uri);
$this->assertEquals(file_get_contents($file_uploaded_uri), $this->testfileData);
}
/**
* Test that Plupload correctly handles uploads in chunks.
*/
public function testUploadControllerInChunks() {
$this->container->get('router.builder')->rebuild();
$unicode_emoticon = json_decode('"\uD83D\uDE0E"');
$tmp_filename = 'o_loremipsum.tmp';
foreach (str_split($this->testfileData, 10) as $chunk => $data) {
// Split the test file into chunks.
$chunk_name = $this->tmpFile . '-' . $chunk;
file_put_contents($chunk_name, $data);
$controller_result = $this->sendPluploadRequest($chunk_name, "{$this->testfilePrefix}controller-Капля a,A;1{$unicode_emoticon}.jpg", $tmp_filename, $chunk);
$this->assertEquals(200, $controller_result->getStatusCode());
$result = json_decode($controller_result->getContent());
$this->assertIsObject($result);
$this->assertEquals([
'jsonrpc' => '2.0',
'result' => NULL,
'id' => 'id',
], (array) $result);
}
$file_uploaded_uri = $this->config('plupload.settings')->get('temporary_uri') . '/' . $tmp_filename;
$this->assertFileExists($file_uploaded_uri);
$this->assertEquals(file_get_contents($file_uploaded_uri), $this->testfileData);
}
/**
* Send a Plupload request.
*
* @param string $path
* The path to the file to upload.
* @param string $originalName
* The original name of the file uploaded file.
* @param string $tmp_filename
* The temporary filename sent by Plupload.
* @param int|null $chunk
* The chunk number, if chunked upload.
*
* @return \Symfony\Component\HttpFoundation\JsonResponse
* The controller response.
*/
protected function sendPluploadRequest(string $path, string $originalName, string $tmp_filename, int $chunk = NULL): JsonResponse {
$uploaded_file = new UploadedFile($path, $originalName);
$file_bag = new FileBag();
$file_bag->set('file', $uploaded_file);
$request = new Request();
$request->request->set('name', $tmp_filename);
if ($chunk !== NULL) {
$request->request->set('chunk', $chunk);
}
$request->files = $file_bag;
$request->headers->set('Content-Type', 'multipart/form-data');
$controller = new TestUploadController($request, $this->container->get('file.htaccess_writer'), $this->container->get('file_system'), $this->container->get('config.factory'));
return $controller->handleUploads();
}
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment