Skip to content

Commit 3589cac

Browse files
authored
Merge pull request #5 from phug-php/feature/allow-phug-2
Allow Phug 2
2 parents 31c7dd4 + 68370c8 commit 3589cac

9 files changed

Lines changed: 228 additions & 58 deletions

File tree

.github/workflows/coverage.yml

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
name: Coverage
2+
3+
on:
4+
push:
5+
branches: [ '**' ]
6+
pull_request:
7+
branches: [ '**' ]
8+
9+
jobs:
10+
test:
11+
runs-on: ubuntu-latest
12+
13+
strategy:
14+
fail-fast: false
15+
matrix:
16+
php: ['8.4']
17+
setup: ['stable']
18+
19+
name: PHP
20+
21+
steps:
22+
- uses: actions/checkout@v5
23+
24+
- name: Setup PHP
25+
uses: shivammathur/setup-php@v2
26+
with:
27+
php-version: ${{ matrix.php }}
28+
tools: composer:v2
29+
coverage: pcov
30+
31+
- name: Cache Composer packages
32+
id: composer-cache
33+
uses: actions/cache@v4
34+
with:
35+
path: vendor
36+
key: ${{ runner.os }}-${{ matrix.setup }}-php-${{ matrix.php }}-${{ hashFiles('**/composer.lock') }}
37+
restore-keys: |
38+
${{ runner.os }}-${{ matrix.setup }}-php-${{ matrix.php }}-
39+
40+
- name: Install dependencies
41+
if: steps.composer-cache.outputs.cache-hit != 'true'
42+
run: |
43+
composer update --prefer-dist --no-interaction ${{ format('--prefer-{0}', matrix.setup) || '' }}
44+
45+
- name: Run test suite
46+
run: vendor/bin/phpunit --coverage-text --coverage-clover=coverage.xml
47+
48+
- name: Coverage - Qltysh
49+
uses: qltysh/qlty-action/coverage@v2
50+
with:
51+
token: ${{ secrets.QLTY_COVERAGE_TOKEN }}
52+
files: clover.xml
53+
54+
- name: Coverage - Codecov
55+
uses: codecov/codecov-action@v5
56+
with:
57+
token: ${{ secrets.CODECOV_TOKEN }}

.github/workflows/tests.yml

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
name: Tests
2+
3+
on:
4+
push:
5+
branches: [ '**' ]
6+
pull_request:
7+
branches: [ '**' ]
8+
9+
jobs:
10+
test:
11+
runs-on: ubuntu-latest
12+
13+
strategy:
14+
fail-fast: false
15+
matrix:
16+
php: ['7.2', '7.4', '8.0', '8.2', '8.4', '8.5']
17+
setup: ['lowest', 'stable']
18+
19+
name: PHP ${{ matrix.php }} - ${{ matrix.setup }}
20+
21+
steps:
22+
- uses: actions/checkout@v5
23+
24+
- name: Setup PHP
25+
uses: shivammathur/setup-php@v2
26+
with:
27+
php-version: ${{ matrix.php }}
28+
tools: composer:v2
29+
30+
- name: Cache Composer packages
31+
id: composer-cache
32+
uses: actions/cache@v4
33+
with:
34+
path: vendor
35+
key: ${{ runner.os }}-${{ matrix.setup }}-php-${{ matrix.php }}-${{ hashFiles('**/composer.lock') }}
36+
restore-keys: |
37+
${{ runner.os }}-${{ matrix.setup }}-php-${{ matrix.php }}-
38+
39+
- name: Install dependencies
40+
if: steps.composer-cache.outputs.cache-hit != 'true'
41+
run: |
42+
composer update --prefer-dist --no-interaction ${{ matrix.setup != 'next' && format('--prefer-{0}', matrix.setup) || '' }}
43+
env:
44+
MULTI_TESTER_LABELS: install
45+
46+
- name: Run test suite
47+
run: vendor/bin/phpunit --no-coverage --verbose
48+
env:
49+
MULTI_TESTER_LABELS: script

.travis.yml

Lines changed: 0 additions & 32 deletions
This file was deleted.

composer.json

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,11 +22,12 @@
2222
"prefer-stable": true,
2323
"require": {
2424
"php": ">=7.2",
25-
"phug/phug": "^1.7.2"
25+
"phug/phug": "^1.7.2 || ^2.0.1"
2626
},
2727
"require-dev": {
28-
"phpunit/phpunit": "^8.5",
29-
"pug-php/pug": "^3.3",
28+
"phpunit/phpunit": "^8.5.52",
29+
"js-phpize/js-phpize-phug": "^2.3.0",
30+
"pug-php/pug": "^3.6.0",
3031
"machy8/xhtml-formatter": "^1.0"
3132
},
3233
"autoload": {
@@ -38,5 +39,10 @@
3839
"psr-4": {
3940
"Phug\\Test\\Component\\": "./tests/Phug/Component/"
4041
}
42+
},
43+
"config": {
44+
"allow-plugins": {
45+
"nodejs-php-fallback/nodejs-php-fallback": true
46+
}
4147
}
4248
}

tests/Phug/Component/ComponentExtensionTest.php

Lines changed: 100 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@
22

33
namespace Phug\Test\Component;
44

5+
use DOMAttr;
6+
use DOMDocument;
57
use Exception;
68
use PHPUnit\Framework\TestCase;
79
use Phug\Compiler\Event\NodeEvent;
@@ -21,6 +23,7 @@
2123
use Phug\Util\Partial\ValueTrait;
2224
use Pug\Pug;
2325
use ReflectionException;
26+
use SimpleXMLElement;
2427
use XhtmlFormatter\Formatter;
2528

2629
/**
@@ -63,7 +66,7 @@ protected function format(string $html): string
6366
protected function getReadmeContents(): string
6467
{
6568
if ($this->readme === null) {
66-
$this->readme = file_get_contents(__DIR__ . '/../../../README.md');
69+
$this->readme = str_replace("\r",'', file_get_contents(__DIR__ . '/../../../README.md'));
6770
}
6871

6972
return $this->readme;
@@ -403,15 +406,16 @@ public function testNamespace()
403406
public function getPugPhpTestsTemplates(): array
404407
{
405408
return array_map(function ($file) {
406-
return [$file, substr($file, 0, -5).'.pug'];
407-
}, glob(__DIR__.'/../../templates/*.html'));
409+
$file = basename($file);
410+
411+
return [substr($file, 0, -4).'.html', $file];
412+
}, glob(__DIR__.'/../../templates/*.pug'));
408413
}
409414

410415
/**
411416
* @dataProvider getPugPhpTestsTemplates
412417
*
413418
* @covers ::attachEvents
414-
* @covers ::parseOutput
415419
*
416420
* @param string $htmlFile Expected output template file
417421
* @param string $pugFile Input template file
@@ -420,36 +424,117 @@ public function getPugPhpTestsTemplates(): array
420424
*/
421425
public function testPugPhpTestsTemplates(string $htmlFile, string $pugFile)
422426
{
427+
$templateFolder = __DIR__.'/../../templates/';
423428
$pug = new Pug([
424429
'debug' => false,
425430
'pretty' => true,
426431
]);
427432
ComponentExtension::enable($pug);
428433

434+
$actualContent = $this->rawHtml($pug->renderFile($templateFolder . $pugFile, []));
435+
$altHtmlFile = $templateFolder . strtr($htmlFile, ['.html' => '.alt.html']);
436+
437+
if (file_exists($altHtmlFile)) {
438+
if ($this->rawHtml(file_get_contents($altHtmlFile)) === $actualContent) {
439+
$this->assertTrue(true);
440+
441+
return;
442+
}
443+
}
444+
429445
$this->assertSame(
430-
$this->rawHtml(file_get_contents($htmlFile)),
431-
$this->rawHtml($pug->renderFile($pugFile, [])),
446+
$this->rawHtml(file_get_contents($templateFolder . $htmlFile)),
447+
$actualContent,
432448
basename($pugFile)
433449
);
434450
}
435451

436452
private function rawHtml($html)
437453
{
438-
$html = strtr($html, [
439-
"'" => '"',
440-
"\r" => '',
441-
]);
454+
$html = strtr($html, ["\r" => '']);
442455
$html = preg_replace('`\n{2,}`', "\n", $html);
443456
$html = preg_replace('`(?<!\n) {2,}`', ' ', $html);
444457
$html = preg_replace('` *$`m', '', $html);
445458
$html = $this->format($html);
446-
$html = preg_replace_callback('`(<(?:style|script)(?:[^>]*)>)([\s\S]+)(</(?:style|script)>)`', function ($matches) {
447-
[, $start, $content, $end] = $matches;
448-
$content = trim(preg_replace('`^ *`m', '', $content));
459+
$html = preg_replace_callback(
460+
'`(<(?:style|script)[^>]*>)([\s\S]+)(</(?:style|script)>)`',
461+
function ($matches) {
462+
[, $start, $content, $end] = $matches;
463+
$content = trim(preg_replace('`^ *`m', '', $content));
449464

450-
return "$start\n$content\n$end";
451-
}, $html);
465+
return "$start\n$content\n$end";
466+
},
467+
$html
468+
);
469+
$html = preg_replace_callback(
470+
'`class="([^"]+)"`',
471+
function ($matches) {
472+
$classes = preg_split('/\s+/', $matches[1]);
473+
sort($classes);
474+
475+
return 'class="' . implode(' ', $classes) . '"';
476+
},
477+
$html
478+
);
479+
$document = new DOMDocument();
480+
$html = preg_replace_callback(
481+
'/(?<start><(?<tag>\w+)\s(?<parameters>[^>]+))>/',
482+
function ($matches) use ($document) {
483+
try {
484+
$tag = rtrim($matches['start'], '/') . '/>';
485+
$document->loadHTML("<html><body>$tag</body></html>");
486+
$node = $document->getElementsByTagName('body')[0]->firstChild;
487+
} catch (Exception $error) {
488+
return $matches[0];
489+
}
490+
491+
$attributes = iterator_to_array($node->attributes);
492+
ksort($attributes);
493+
494+
return '<' . $matches['tag'] .
495+
implode('', array_map(
496+
[$this, 'formatAttribute'],
497+
$attributes
498+
)) .
499+
'>';
500+
},
501+
$html
502+
);
503+
$html = preg_replace_callback(
504+
'/(?<start><(\w+)(?:\s[^>]+)?>)(?<content>[^<]+)(?<end><\/\2>)/',
505+
function ($matches) use ($document) {
506+
return $matches['start'] .
507+
$this->escapeQuotes($matches['content']) .
508+
$matches['end'];
509+
},
510+
$html
511+
);
452512

453513
return $html;
454514
}
515+
516+
private function formatAttribute(DOMAttr $attribute): string
517+
{
518+
$name = $attribute->name;
519+
$value = $attribute->textContent;
520+
521+
if ($name === 'data-items') {
522+
var_dump($value);
523+
exit;
524+
}
525+
526+
if ($value === '') {
527+
return " $name";
528+
}
529+
530+
return " $name=\"" . $this->escapeQuotes($value) . '"';
531+
}
532+
533+
private function escapeQuotes(string $input): string
534+
{
535+
return strtr($input, [
536+
'"' => '&quot;',
537+
"'" => '&#039;',
538+
]);
539+
}
455540
}
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
<foo data-items="{&quot;foo&quot;:&quot;bar&quot;,&quot;yah&quot;:42,&quot;yoh&quot;:&quot;yah: 42&quot;,&quot;bar&quot;:&quot;a&#039;a\&quot;\\\&quot;\\&#039;\\\\&quot;}"></foo>
2+
<foo data-items="{&quot;foo&quot;:&quot;#{foo}, \\#{foo}&quot;,&quot;bar&quot;:&quot;#{foo}, \\#{foo}&quot;}"></foo>
3+
<foo data-items="[&quot;#{foo} [a]&quot;,&quot;#{foo} =&gt;&quot;]"></foo>
4+
<foo data-items="{&quot;a\\\&quot;\\&quot;:&quot;a&quot;}"></foo>
5+
<foo a'="&#039;a"></foo>

tests/templates/inline-tags.html

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,13 +4,13 @@
44
</small>
55
tag
66
<h1>
7-
J"aime
7+
J'aime
88
<strong>
99
Pug
1010
</strong>
1111
</h1>
1212
<h1>
13-
J"aime
13+
J'aime
1414
<strong>
1515
beaucoup
1616
</strong>
@@ -19,7 +19,7 @@ <h1>
1919
</strong>
2020
</h1>
2121
<h1>
22-
J"aime #[strong beaucoup]
22+
J'aime #[strong beaucoup]
2323
<strong>
2424
beaucoup
2525
</strong>
@@ -28,7 +28,7 @@ <h1>
2828
<div>
2929
<div>
3030
<h1>
31-
J"aime
31+
J'aime
3232
<strong>
3333
beaucoup
3434
</strong>
@@ -78,4 +78,4 @@ <h1>
7878
!
7979
This line has no tag.
8080
</article>
81-
</div>
81+
</div>

tests/templates/mixin.attrs.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ <h1 class="foo bar">
2222
<div class="stretch">
2323
<div class="centered">
2424
<h1 class="highlight">
25-
Section 3" and quote&quot;&quot;
25+
Section 3' and quote&quot;&quot;
2626
</h1>
2727
<p>Last content.</p>
2828
<div class="footer">

0 commit comments

Comments
 (0)