• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

Cecilapp / Cecil / 18438267546

12 Oct 2025 03:01AM UTC coverage: 81.901%. Remained the same
18438267546

push

github

ArnaudLigny
refactor: better error/warning messages

5 of 40 new or added lines in 15 files covered. (12.5%)

3163 of 3862 relevant lines covered (81.9%)

0.82 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

80.77
/src/Step/Pages/Save.php
1
<?php
2

3
/**
4
 * This file is part of Cecil.
5
 *
6
 * (c) Arnaud Ligny <arnaud@ligny.fr>
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
declare(strict_types=1);
13

14
namespace Cecil\Step\Pages;
15

16
use Cecil\Collection\Page\Page;
17
use Cecil\Exception\RuntimeException;
18
use Cecil\Renderer\Page as PageRenderer;
19
use Cecil\Step\AbstractStep;
20
use Cecil\Util;
21

22
/**
23
 * Save step.
24
 *
25
 * This step is responsible for saving the rendered pages to the output directory.
26
 * It iterates through the pages, checks if they have been rendered, and saves
27
 * the output in the specified format. The saved files are logged, and the
28
 * output directory is created if it does not exist. If the `dry-run` option is
29
 * enabled, the step will not perform any file operations but will still log
30
 * the intended actions.
31
 */
32
class Save extends AbstractStep
33
{
34
    /**
35
     * {@inheritdoc}
36
     */
37
    public function getName(): string
38
    {
39
        return 'Saving pages';
1✔
40
    }
41

42
    /**
43
     * {@inheritdoc}
44
     */
45
    public function init(array $options): void
46
    {
47
        if ($options['dry-run']) {
1✔
48
            return;
×
49
        }
50

51
        Util\File::getFS()->mkdir($this->config->getOutputPath());
1✔
52

53
        $this->canProcess = true;
1✔
54
    }
55

56
    /**
57
     * {@inheritdoc}
58
     *
59
     * @throws RuntimeException
60
     */
61
    public function process(): void
62
    {
63
        $filteredPages = $this->builder->getPages()->filter(function (Page $page) {
1✔
64
            return !empty($page->getRendered());
1✔
65
        });
1✔
66
        $total = \count($filteredPages);
1✔
67

68
        $count = 0;
1✔
69
        foreach ($filteredPages as $page) {
1✔
70
            $count++;
1✔
71
            $files = [];
1✔
72

73
            foreach ($page->getRendered() as $format => $rendered) {
1✔
74
                if (false === $pathname = (new PageRenderer($this->builder, $page))->getOutputFilePath($format)) {
1✔
NEW
75
                    throw new RuntimeException(\sprintf("Unable to get pathname of page '%s' (format: '%s').", $page->getId(), $format));
×
76
                }
77
                $pathname = $this->cleanPath(Util::joinFile($this->config->getOutputPath(), $pathname));
1✔
78

79
                try {
80
                    Util\File::getFS()->dumpFile($pathname, $rendered['output']);
1✔
81
                } catch (\Symfony\Component\Filesystem\Exception\IOException $e) {
×
82
                    throw new RuntimeException($e->getMessage());
×
83
                }
84

85
                $files[] = $this->builder->isDebug() ? $pathname : substr($pathname, \strlen($this->config->getOutputPath()) + 1);
1✔
86
            }
87

88
            $message = \sprintf('File(s) "%s" saved', implode(', ', $files));
1✔
89
            $this->builder->getLogger()->info($message, ['progress' => [$count, $total]]);
1✔
90
        }
91
    }
92

93
    /**
94
     * Removes unnecessary directory separators.
95
     */
96
    private function cleanPath(string $pathname): string
97
    {
98
        if (DIRECTORY_SEPARATOR == '\\') {
1✔
99
            $pathname = preg_replace('#\\\\+#', '\\', $pathname);
×
100
        }
101

102
        return preg_replace('#/+#', '/', $pathname);
1✔
103
    }
104
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc