Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit a80409a

Browse files
OskarStarkfabpot
authored andcommitted
[Notifier] Fix parsing Dsn with empty user/password
1 parent bc6550e commit a80409a

File tree

2 files changed

+125
-2
lines changed

2 files changed

+125
-2
lines changed
Lines changed: 123 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,123 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <[email protected]>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Component\Notifier\Tests\Transport;
13+
14+
use PHPUnit\Framework\TestCase;
15+
use Symfony\Component\Notifier\Exception\InvalidArgumentException;
16+
use Symfony\Component\Notifier\Transport\Dsn;
17+
18+
final class DsnTest extends TestCase
19+
{
20+
/**
21+
* @dataProvider fromStringProvider
22+
*/
23+
public function testFromString(string $string, Dsn $expectedDsn)
24+
{
25+
$actualDsn = Dsn::fromString($string);
26+
27+
$this->assertSame($expectedDsn->getScheme(), $actualDsn->getScheme());
28+
$this->assertSame($expectedDsn->getHost(), $actualDsn->getHost());
29+
$this->assertSame($expectedDsn->getPort(), $actualDsn->getPort());
30+
$this->assertSame($expectedDsn->getUser(), $actualDsn->getUser());
31+
$this->assertSame($expectedDsn->getPassword(), $actualDsn->getPassword());
32+
$this->assertSame($expectedDsn->getPath(), $actualDsn->getPath());
33+
$this->assertSame($expectedDsn->getOption('from'), $actualDsn->getOption('from'));
34+
35+
$this->assertSame($string, $actualDsn->getOriginalDsn());
36+
}
37+
38+
public function fromStringProvider(): iterable
39+
{
40+
yield 'simple dsn' => [
41+
'scheme://localhost',
42+
new Dsn('scheme', 'localhost', null, null, null, [], null),
43+
];
44+
45+
yield 'simple dsn including @ sign, but no user/password/token' => [
46+
'scheme://@localhost',
47+
new Dsn('scheme', 'localhost', null, null),
48+
];
49+
50+
yield 'simple dsn including : sign and @ sign, but no user/password/token' => [
51+
'scheme://:@localhost',
52+
new Dsn('scheme', 'localhost', null, null),
53+
];
54+
55+
yield 'simple dsn including user, : sign and @ sign, but no password' => [
56+
'scheme://user1:@localhost',
57+
new Dsn('scheme', 'localhost', 'user1', null),
58+
];
59+
60+
yield 'simple dsn including : sign, password, and @ sign, but no user' => [
61+
'scheme://:pass@localhost',
62+
new Dsn('scheme', 'localhost', null, 'pass'),
63+
];
64+
65+
yield 'dsn with user and pass' => [
66+
'scheme://u$er:pa$s@localhost',
67+
new Dsn('scheme', 'localhost', 'u$er', 'pa$s', null, [], null),
68+
];
69+
70+
yield 'dsn with user and pass and custom port' => [
71+
'scheme://u$er:pa$s@localhost:8000',
72+
new Dsn('scheme', 'localhost', 'u$er', 'pa$s', '8000', [], null),
73+
];
74+
75+
yield 'dsn with user and pass, custom port and custom path' => [
76+
'scheme://u$er:pa$s@localhost:8000/channel',
77+
new Dsn('scheme', 'localhost', 'u$er', 'pa$s', '8000', [], '/channel'),
78+
];
79+
80+
yield 'dsn with user and pass, custom port, custom path and custom options' => [
81+
'scheme://u$er:pa$s@localhost:8000/channel?from=FROM',
82+
new Dsn('scheme', 'localhost', 'u$er', 'pa$s', '8000', ['from' => 'FROM'], '/channel'),
83+
];
84+
}
85+
86+
/**
87+
* @dataProvider invalidDsnProvider
88+
*/
89+
public function testInvalidDsn(string $dsn, string $exceptionMessage)
90+
{
91+
$this->expectException(InvalidArgumentException::class);
92+
$this->expectExceptionMessage($exceptionMessage);
93+
Dsn::fromString($dsn);
94+
}
95+
96+
public function invalidDsnProvider(): iterable
97+
{
98+
yield [
99+
'some://',
100+
'The "some://" notifier DSN is invalid.',
101+
];
102+
103+
yield [
104+
'//slack',
105+
'The "//slack" notifier DSN must contain a scheme.',
106+
];
107+
108+
yield [
109+
'file:///some/path',
110+
'The "file:///some/path" notifier DSN must contain a host (use "default" by default).',
111+
];
112+
}
113+
114+
public function testGetOption()
115+
{
116+
$options = ['with_value' => 'some value', 'nullable' => null];
117+
$dsn = new Dsn('scheme', 'localhost', 'u$er', 'pa$s', '8000', $options, '/channel');
118+
119+
$this->assertSame('some value', $dsn->getOption('with_value'));
120+
$this->assertSame('default', $dsn->getOption('nullable', 'default'));
121+
$this->assertSame('default', $dsn->getOption('not_existent_property', 'default'));
122+
}
123+
}

src/Symfony/Component/Notifier/Transport/Dsn.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -54,8 +54,8 @@ public static function fromString(string $dsn): self
5454
throw new InvalidArgumentException(sprintf('The "%s" notifier DSN must contain a host (use "default" by default).', $dsn));
5555
}
5656

57-
$user = isset($parsedDsn['user']) ? urldecode($parsedDsn['user']) : null;
58-
$password = isset($parsedDsn['pass']) ? urldecode($parsedDsn['pass']) : null;
57+
$user = '' !== ($parsedDsn['user'] ?? '') ? urldecode($parsedDsn['user']) : null;
58+
$password = '' !== ($parsedDsn['pass'] ?? '') ? urldecode($parsedDsn['pass']) : null;
5959
$port = $parsedDsn['port'] ?? null;
6060
$path = $parsedDsn['path'] ?? null;
6161
parse_str($parsedDsn['query'] ?? '', $query);

0 commit comments

Comments
 (0)