filesystemMap = $this->getMockBuilder(FilesystemMap::class)->disableOriginalConstructor()->getMock(); $this->entityManager = $this->getMockBuilder(EntityManagerInterface::class)->disableOriginalConstructor()->getMock(); $this->accessRepository = $this->getMockBuilder(AccessRepository::class)->disableOriginalConstructor()->getMock(); $this->dataManager = $this->getMockBuilder(DataManager::class)->disableOriginalConstructor()->getMock(); $this->cacheManager = $this->getMockBuilder(CacheManager::class)->disableOriginalConstructor()->getMock(); $this->imageFactory = $this->getMockBuilder(ImageFactory::class)->disableOriginalConstructor()->getMock(); $this->fileUtils = $this->getMockBuilder(FileUtils::class)->disableOriginalConstructor()->getMock(); $this->urlBuilder = $this->getMockBuilder(UrlBuilder::class)->disableOriginalConstructor()->getMock(); $this->filesystem = $this->getMockBuilder(Filesystem::class)->disableOriginalConstructor()->getMock(); $this->filesystemMap->method('get')->with(TestableLocalStorage::FS_KEY)->willReturn($this->filesystem); } public function getMockForMethod(string $methodName): TestableLocalStorage|MockObject { return $this->getMockBuilder(TestableLocalStorage::class) ->setConstructorArgs([ $this->filesystemMap, $this->entityManager, $this->accessRepository, $this->dataManager, $this->cacheManager, $this->imageFactory, $this->fileUtils, $this->urlBuilder, '/file/storage/dir/', ]) ->setMethodsExcept([$methodName]) ->getMock(); } /** * @see LocalStorage::exists() */ public function testExists(): void { $fileStorage = $this->getMockForMethod('exists'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('foo'); $this->filesystem->expects(self::once())->method('has')->with('foo')->willReturn(true); $this->assertTrue($fileStorage->exists($file)); } /** * @see LocalStorage::exists() */ public function testExistsInexistant(): void { $fileStorage = $this->getMockForMethod('exists'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('foo'); $this->filesystem->expects(self::once())->method('has')->with('foo')->willReturn(false); $this->assertFalse($fileStorage->exists($file)); } /** * @see LocalStorage::listByOwner() */ public function testListByOwner(): void { $fileStorage = $this->getMockForMethod('listByOwner'); $owner = $this->getMockBuilder(Organization::class)->getMock(); $fileStorage->method('getPrefix')->with($owner, false, FileTypeEnum::LICENCE_CMF)->willReturn('foo'); $this->filesystem->method('listKeys')->with('foo')->willReturn(['foo/a.txt', 'foo/b.pdf']); $this->assertEquals( ['foo/a.txt', 'foo/b.pdf'], $fileStorage->listByOwner($owner, FileTypeEnum::LICENCE_CMF) ); } /** * @see LocalStorage::read() */ public function testReadPdf(): void { $fileStorage = $this->getMockForMethod('read'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('foo'); $this->filesystem->method('read')->with('foo')->willReturn('12345679'); $this->assertEquals( '12345679', $fileStorage->read($file) ); } public function testGetImageUrl(): void { $localStorage = $this->getMockForMethod('getImageUrl'); $localStorage ->method('getFilterFromSizeAndConfig') ->with('sm', true) ->willReturn('crop_sm'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('abc'); $file->method('getConfig')->willReturn('xyz'); $this->cacheManager ->method('isStored') ->with('abc', 'crop_sm') ->willReturn(false); $this->cacheManager ->method('resolve') ->with('abc', 'crop_sm') ->willReturn('publicUrl/xyz'); $this->assertEquals( 'publicUrl/xyz', $localStorage->getImageUrl($file, 'sm', false, false) ); } public function testGetImageUrlRelativePath(): void { $localStorage = $this->getMockForMethod('getImageUrl'); $localStorage ->method('getFilterFromSizeAndConfig') ->with('sm', true) ->willReturn('crop_sm'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('abc'); $file->method('getConfig')->willReturn('xyz'); $this->cacheManager ->method('isStored') ->with('abc', 'crop_sm') ->willReturn(false); $this->cacheManager ->method('resolve') ->with('abc', 'crop_sm') ->willReturn('publicUrl/xyz'); $this->urlBuilder ->method('getRelativeUrl') ->with('publicUrl/xyz') ->willReturn('xyz'); $this->assertEquals( 'xyz', $localStorage->getImageUrl($file, 'sm', true, false) ); } public function testGetImageUrlNotCached(): void { $localStorage = $this->getMockForMethod('getImageUrl'); $localStorage ->method('getFilterFromSizeAndConfig') ->with('sm', true) ->willReturn('crop_sm'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('abc'); $file->method('getConfig')->willReturn('xyz'); $this->cacheManager ->method('isStored') ->with('abc', 'crop_sm') ->willReturn(false); $this->imageFactory ->expects(self::once()) ->method('createImageContent') ->with($file, 'crop_sm', false); $this->cacheManager ->method('resolve') ->with('abc', 'crop_sm') ->willReturn('publicUrl/xyz'); $this->assertEquals( 'publicUrl/xyz', $localStorage->getImageUrl($file, 'sm', false, false) ); } public function testGetImageUrlNotCachedMissingFile(): void { $localStorage = $this->getMockForMethod('getImageUrl'); $localStorage ->method('getFilterFromSizeAndConfig') ->with('sm', true) ->willReturn('crop_sm'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('abc'); $file->method('getConfig')->willReturn('xyz'); $this->cacheManager ->method('isStored') ->with('abc', 'crop_sm') ->willReturn(false); $this->imageFactory ->expects(self::once()) ->method('createImageContent') ->with($file, 'crop_sm', false) ->willThrowException(new \Exception('File not found')); $this->cacheManager ->expects(self::never()) ->method('resolve'); $this->urlBuilder ->method('getAbsoluteUrl') ->with('images/missing-file.png') ->willReturn('publicUrl/images/missing-file.png'); $this->assertEquals( 'publicUrl/images/missing-file.png', $localStorage->getImageUrl($file, 'sm', false, false) ); } public function testGetImageUrlNotCachedMissingFileRelativePath(): void { $localStorage = $this->getMockForMethod('getImageUrl'); $localStorage ->method('getFilterFromSizeAndConfig') ->with('sm', true) ->willReturn('crop_sm'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('abc'); $file->method('getConfig')->willReturn('xyz'); $this->cacheManager ->method('isStored') ->with('abc', 'crop_sm') ->willReturn(false); $this->imageFactory ->expects(self::once()) ->method('createImageContent') ->with($file, 'crop_sm', false) ->willThrowException(new \Exception('File not found')); $this->cacheManager ->expects(self::never()) ->method('resolve'); $this->assertEquals( 'images/missing-file.png', $localStorage->getImageUrl($file, 'sm', true, false) ); } public function testGetFilterFromSizeAndConfig(): void { $fileStorage = $this->getMockForMethod('getFilterFromSizeAndConfig'); $this->assertEquals( 'crop_sm', $fileStorage->getFilterFromSizeAndConfig(FileSizeEnum::SM->value, true) ); $this->assertEquals( 'sm', $fileStorage->getFilterFromSizeAndConfig(FileSizeEnum::SM->value, false) ); $this->assertEquals( 'crop_md', $fileStorage->getFilterFromSizeAndConfig(FileSizeEnum::MD->value, true) ); $this->assertEquals( 'md', $fileStorage->getFilterFromSizeAndConfig(FileSizeEnum::MD->value, false) ); $this->assertEquals( 'crop_lg', $fileStorage->getFilterFromSizeAndConfig(FileSizeEnum::LG->value, true) ); $this->assertEquals( 'lg', $fileStorage->getFilterFromSizeAndConfig(FileSizeEnum::LG->value, false) ); } /** * @see LocalStorage::prepareFile() */ public function testPrepareFile(): void { $fileStorage = $this->getMockForMethod('prepareFile'); $owner = $this->getMockBuilder(Organization::class)->getMock(); $author = $this->getMockBuilder(Access::class)->getMock(); $author->method('getId')->willReturn(123); $fileStorage->method('getOrganizationAndPersonFromOwner')->with($owner)->willReturn([$owner, null]); $this->entityManager->expects(self::once())->method('persist'); $this->entityManager->expects(self::once())->method('flush'); $file = $fileStorage->prepareFile( $owner, 'file.ext', FileTypeEnum::LICENCE_CMF, $author, true, FileVisibilityEnum::ONLY_ORGANIZATION, 'application/pdf' ); $this->assertEquals($owner, $file->getOrganization()); $this->assertEquals(null, $file->getPerson()); $this->assertEquals('file.ext', $file->getName()); $this->assertEquals(FileTypeEnum::LICENCE_CMF, $file->getType()); $this->assertTrue($file->getIsTemporaryFile()); $this->assertEquals(FileVisibilityEnum::ONLY_ORGANIZATION, $file->getVisibility()); $this->assertEquals('application/pdf', $file->getMimeType()); $this->assertEquals(123, $file->getCreatedBy()); } /** * @see LocalStorage::prepareFile() */ public function testPrepareFileDefaultValues(): void { $fileStorage = $this->getMockForMethod('prepareFile'); $owner = $this->getMockBuilder(Person::class)->getMock(); $author = $this->getMockBuilder(Access::class)->getMock(); $fileStorage->method('getOrganizationAndPersonFromOwner')->with($owner)->willReturn([null, $owner]); $this->entityManager->expects(self::once())->method('persist'); $this->entityManager->expects(self::once())->method('flush'); $this->fileUtils->method('guessMimeTypeFromFilename')->with('file.txt')->willReturn('text/plain'); $file = $fileStorage->prepareFile($owner, 'file.txt', FileTypeEnum::NONE, $author); $this->assertEquals(null, $file->getOrganization()); $this->assertEquals($owner, $file->getPerson()); $this->assertEquals('file.txt', $file->getName()); $this->assertEquals(FileTypeEnum::NONE, $file->getType()); $this->assertFalse($file->getIsTemporaryFile()); $this->assertEquals(FileVisibilityEnum::NOBODY, $file->getVisibility()); $this->assertEquals('text/plain', $file->getMimeType()); } /** * @see LocalStorage::prepareFile() */ public function testPrepareFileNoFlush(): void { $fileStorage = $this->getMockForMethod('prepareFile'); $owner = $this->getMockBuilder(Organization::class)->getMock(); $author = $this->getMockBuilder(Access::class)->getMock(); $fileStorage->method('getOrganizationAndPersonFromOwner')->with($owner)->willReturn([$owner, null]); $this->entityManager->expects(self::once())->method('persist'); $this->entityManager->expects(self::never())->method('flush'); $this->fileUtils->method('guessMimeTypeFromFilename')->willReturn('text/plain'); $fileStorage->prepareFile( $owner, 'file.txt', FileTypeEnum::NONE, $author, false, FileVisibilityEnum::NOBODY, 'text/plain', false ); } /** * @see LocalStorage::write() */ public function testWriteNewFile(): void { $fileStorage = $this->getMockForMethod('write'); $organization = $this->getMockBuilder(Organization::class)->getMock(); $author = $this->getMockBuilder(Access::class)->getMock(); $author->method('getId')->willReturn(123); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getName')->willReturn('foo.txt'); $file->method('getOrganization')->willReturn($organization); $file->method('getPerson')->willReturn(null); $file->method('getIsTemporaryFile')->willReturn(false); $file->method('getSlug')->willReturn(null); $file->method('getType')->willReturn(FileTypeEnum::NONE); $fileStorage ->method('getPrefix') ->with($organization, false, FileTypeEnum::NONE) ->willReturn('prefix/'); $content = '123456789'; $size = strlen($content); $this->filesystem ->expects(self::once()) ->method('write') ->with(self::matchesRegularExpression('/^prefix\/\w{16,24}\/foo.txt/'), $content, true) ->willReturn($size); $file->expects(self::once())->method('setSize')->with($size)->willReturnSelf(); $file->expects(self::once())->method('setStatus')->with(FileStatusEnum::READY)->willReturnSelf(); $file->expects(self::once()) ->method('setSlug') ->with(self::matchesRegularExpression('/^prefix\/\w{16,24}\/foo.txt/')) ->willReturnSelf(); $file->expects(self::once())->method('setCreateDate')->with(self::isInstanceOf(\DateTime::class))->willReturnSelf(); $file->expects(self::once())->method('setCreatedBy')->with(123)->willReturnSelf(); $file->expects(self::never())->method('setUpdateDate'); $file->expects(self::never())->method('setUpdatedBy'); $this->entityManager->expects(self::once())->method('flush'); $returned = $fileStorage->write($file, $content, $author); $this->assertSame($file, $returned); } /** * @see LocalStorage::write() */ public function testWriteExistingFile(): void { $fileStorage = $this->getMockForMethod('write'); $person = $this->getMockBuilder(Person::class)->getMock(); $author = $this->getMockBuilder(Access::class)->getMock(); $author->method('getId')->willReturn(123); $key = 'prefix/uid/bar.txt'; $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getName')->willReturn('bar.txt'); $file->method('getOrganization')->willReturn(null); $file->method('getPerson')->willReturn($person); $file->method('getIsTemporaryFile')->willReturn(true); $file->method('getSlug')->willReturn($key); $file->method('getType')->willReturn(FileTypeEnum::NONE); $fileStorage->expects(self::never())->method('getPrefix'); $content = '123 Soleil'; $size = strlen($content); $this->filesystem ->expects(self::once()) ->method('write') ->with($key, $content, true) ->willReturn($size); $this->filesystem->method('has')->with($key)->willReturn(true); $file->expects(self::once())->method('setSize')->with($size)->willReturnSelf(); $file->expects(self::once())->method('setStatus')->with(FileStatusEnum::READY)->willReturnSelf(); $file->expects(self::never())->method('setSlug'); $file->expects(self::never())->method('setCreateDate'); $file->expects(self::never())->method('setCreatedBy'); $file->expects(self::once())->method('setUpdateDate')->with(self::isInstanceOf(\DateTime::class))->willReturnSelf(); $file->expects(self::once())->method('setUpdatedBy')->with(123)->willReturnSelf(); $this->entityManager->expects(self::once())->method('flush'); $returned = $fileStorage->write($file, $content, $author); $this->assertEquals($file, $returned); } /** * @see LocalStorage::write() */ public function testWriteExistingButMissingFile(): void { $fileStorage = $this->getMockForMethod('write'); $person = $this->getMockBuilder(Person::class)->getMock(); $author = $this->getMockBuilder(Access::class)->getMock(); $key = 'prefix/uid/bar.txt'; $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getName')->willReturn('bar.txt'); $file->method('getOrganization')->willReturn(null); $file->method('getPerson')->willReturn($person); $file->method('getIsTemporaryFile')->willReturn(true); $file->method('getSlug')->willReturn($key); $file->method('getType')->willReturn(FileTypeEnum::NONE); $this->filesystem->expects(self::never())->method('write'); $this->entityManager->expects(self::never())->method('flush'); $this->filesystem->method('has')->with($key)->willReturn(false); $this->expectException(\RuntimeException::class); $this->expectExceptionMessage('The file `'.$key.'` does not exist in the file storage'); $fileStorage->write($file, '12346', $author); } /** * @see LocalStorage::write() */ public function testWriteWithAccessOwner(): void { $fileStorage = $this->getMockForMethod('write'); $access = $this->getMockBuilder(Access::class)->getMock(); $person = $this->getMockBuilder(Person::class)->getMock(); $organization = $this->getMockBuilder(Organization::class)->getMock(); $author = $this->getMockBuilder(Access::class)->getMock(); $author->method('getId')->willReturn(123); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getName')->willReturn('bar.txt'); $file->method('getOrganization')->willReturn($organization); $file->method('getPerson')->willReturn($person); $file->method('getIsTemporaryFile')->willReturn(true); $file->method('getSlug')->willReturn(null); $file->method('getType')->willReturn(FileTypeEnum::NONE); $this->accessRepository ->expects(self::once()) ->method('findOneBy') ->with(['organization' => $organization, 'person' => $person]) ->willReturn($access); $fileStorage ->expects(self::once()) ->method('getPrefix') ->with($access, true, FileTypeEnum::NONE) ->willReturn('prefix/'); $content = '1'; $this->filesystem->method('write')->willReturn(1); $fileStorage->write($file, $content, $author); } /** * @see LocalStorage::write() */ public function testWriteWithNoName(): void { $fileStorage = $this->getMockForMethod('write'); $author = $this->getMockBuilder(Access::class)->getMock(); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getName')->willReturn(''); $this->expectException(\RuntimeException::class); $this->expectExceptionMessage('File has no filename'); $fileStorage->write($file, '...', $author); } /** * @see LocalStorage::makeFile() */ public function testMakeFile(): void { $fileStorage = $this->getMockForMethod('makeFile'); $organization = $this->getMockBuilder(Organization::class)->getMock(); $author = $this->getMockBuilder(Access::class)->getMock(); $file = $this->getMockBuilder(File::class)->getMock(); $fileStorage ->expects(self::once()) ->method('prepareFile') ->with($organization, 'foo.txt', FileTypeEnum::NONE, $author, true, FileVisibilityEnum::ONLY_ORGANIZATION, 'mime/type') ->willReturn($file); $fileStorage ->expects(self::once()) ->method('write') ->with($file, '...', $author) ->willReturn($file); $fileStorage->makeFile( $organization, 'foo.txt', FileTypeEnum::NONE, '...', $author, true, FileVisibilityEnum::ONLY_ORGANIZATION, 'mime/type'); } /** * @see LocalStorage::softDelete() */ public function testSoftdelete(): void { $fileStorage = $this->getMockForMethod('softDelete'); $author = $this->getMockBuilder(Access::class)->getMock(); $author->method('getId')->willReturn(123); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('key'); $file->expects(self::once())->method('setStatus')->with(FileStatusEnum::DELETED)->willReturnSelf(); $file->expects(self::once())->method('setSize')->with(0)->willReturnSelf(); $file->expects(self::once())->method('setUpdatedBy')->with(123)->willReturnSelf(); $returned = $fileStorage->softDelete($file, $author); $this->assertEquals($file, $returned); } /** * @see LocalStorage::hardDelete() */ public function testHardDelete(): void { $fileStorage = $this->getMockForMethod('hardDelete'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('key'); $this->filesystem->expects(self::once())->method('delete')->with('key')->willReturn(true); $fileStorage->hardDelete($file); } /** * @see LocalStorage::hardDelete() */ public function testHardDeleteFailed(): void { $fileStorage = $this->getMockForMethod('hardDelete'); $file = $this->getMockBuilder(File::class)->getMock(); $file->method('getSlug')->willReturn('key'); $this->filesystem->expects(self::once())->method('delete')->with('key')->willReturn(false); $this->expectException(\RuntimeException::class); $this->expectExceptionMessage('File `'.$file->getSlug().'` could\'nt be deleted'); $fileStorage->hardDelete($file); } public function testDeleteOrganizationFiles(): void { $fileStorage = $this->getMockForMethod('deleteOrganizationFiles'); $fileStorage ->expects(self::exactly(2)) ->method('rrmDir') ->withConsecutive( ['organization/123'], ['temp/organization/123'], ); $fileStorage->deleteOrganizationFiles(123); } public function testDeletePersonFiles(): void { $fileStorage = $this->getMockForMethod('deletePersonFiles'); $fileStorage ->expects(self::exactly(2)) ->method('rrmDir') ->withConsecutive( ['person/123'], ['temp/person/123'], ); $fileStorage->deletePersonFiles(123); } public function testSupport(): void { $apiLegacyStorage = $this->getMockForMethod('support'); $file1 = $this->getMockBuilder(File::class)->getMock(); $file1->method('getHost')->willReturn(FileHostEnum::API1); $file2 = $this->getMockBuilder(File::class)->getMock(); $file2->method('getHost')->willReturn(FileHostEnum::AP2I); $this->assertFalse($apiLegacyStorage->support($file1)); $this->assertTrue($apiLegacyStorage->support($file2)); } /** * @see LocalStorage::getPrefix() */ public function testGetPrefixAccess(): void { $fileStorage = $this->getMockForMethod('getPrefix'); $organization = $this->getMockBuilder(Organization::class)->getMock(); $organization->method('getId')->willReturn(2); $access = $this->getMockBuilder(Access::class)->getMock(); $access->method('getOrganization')->willReturn($organization); $access->method('getId')->willReturn(1); $prefix = $fileStorage->getPrefix($access, false); $this->assertEquals('organization/2/1', $prefix); } /** * @see LocalStorage::getPrefix() */ public function testGetPrefixOrganization(): void { $fileStorage = $this->getMockForMethod('getPrefix'); $organization = $this->getMockBuilder(Organization::class)->getMock(); $organization->method('getId')->willReturn(1); $prefix = $fileStorage->getPrefix($organization, false); $this->assertEquals('organization/1', $prefix); } /** * @see LocalStorage::getPrefix() */ public function testGetPrefixPerson(): void { $fileStorage = $this->getMockForMethod('getPrefix'); $person = $this->getMockBuilder(Person::class)->getMock(); $person->method('getId')->willReturn(1); $prefix = $fileStorage->getPrefix($person, false); $this->assertEquals('person/1', $prefix); } /** * @see LocalStorage::getPrefix() */ public function testGetPrefixTemp(): void { $fileStorage = $this->getMockForMethod('getPrefix'); $organization = $this->getMockBuilder(Organization::class)->getMock(); $organization->method('getId')->willReturn(1); $prefix = $fileStorage->getPrefix($organization, true); $this->assertEquals('temp/organization/1', $prefix); } /** * @see LocalStorage::getPrefix() */ public function testGetPrefixWithType(): void { $fileStorage = $this->getMockForMethod('getPrefix'); $organization = $this->getMockBuilder(Organization::class)->getMock(); $organization->method('getId')->willReturn(1); $prefix = $fileStorage->getPrefix($organization, false, FileTypeEnum::LICENCE_CMF); $this->assertEquals('organization/1/licence_cmf', $prefix); } /** * @see LocalStorage::getOrganizationAndPersonFromOwner() */ public function testGetOrganizationAndPersonFromOwner(): void { $fileStorage = $this->getMockForMethod('getOrganizationAndPersonFromOwner'); $organization = $this->getMockBuilder(Organization::class)->getMock(); $organization->method('getId')->willReturn(2); $person = $this->getMockBuilder(Person::class)->getMock(); $person->method('getId')->willReturn(1); $access = $this->getMockBuilder(Access::class)->getMock(); $access->method('getOrganization')->willReturn($organization); $access->method('getPerson')->willReturn($person); $access->method('getId')->willReturn(1); $this->assertEquals([$organization, $person], $fileStorage->getOrganizationAndPersonFromOwner($access)); $this->assertEquals([$organization, null], $fileStorage->getOrganizationAndPersonFromOwner($organization)); $this->assertEquals([null, $person], $fileStorage->getOrganizationAndPersonFromOwner($person)); } }