StreamWriter::initialiseForWriting()   A
last analyzed

Complexity

Conditions 4
Paths 4

Size

Total Lines 15
Code Lines 10

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 11
CRAP Score 4

Importance

Changes 0
Metric Value
dl 0
loc 15
ccs 11
cts 11
cp 1
rs 9.2
c 0
b 0
f 0
cc 4
eloc 10
nc 4
nop 0
crap 4
1
<?php
2
/**
3
 * This file is part of graze/data-file
4
 *
5
 * Copyright (c) 2016 Nature Delivered Ltd. <https://www.graze.com>
6
 *
7
 * For the full copyright and license information, please view the LICENSE
8
 * file that was distributed with this source code.
9
 *
10
 * @license https://github.com/graze/data-file/blob/master/LICENSE.md
11
 * @link    https://github.com/graze/data-file
12
 */
13
14
namespace Graze\DataFile\IO;
15
16
use Graze\DataFile\Format\Formatter\FormatterInterface;
17
use Graze\DataFile\Helper\OptionalLoggerTrait;
18
use InvalidArgumentException;
19
use Psr\Log\LoggerAwareInterface;
20
use Psr\Log\LogLevel;
21
use Traversable;
22
23
class StreamWriter implements WriterInterface, LoggerAwareInterface
24
{
25
    use OptionalLoggerTrait;
26
27
    /** @var FormatterInterface */
28
    private $formatter;
29
    /** @var resource */
30
    private $stream;
31
32
    /**
33
     * @param resource           $stream
34
     * @param FormatterInterface $formatter  Optional formatter, if not specified shall be determined based on the
35
     *                                       format of the file
36
     */
37 10
    public function __construct($stream, FormatterInterface $formatter)
38
    {
39 10
        $this->stream = $stream;
40 10
        $this->formatter = $formatter;
41 10
    }
42
43
    /**
44
     * Adds multiple lines to the CSV document
45
     *
46
     * a simple wrapper method around insertOne
47
     *
48
     * @param Traversable|array $rows a multidimensional array or a Traversable object
49
     *
50
     * @throws InvalidArgumentException If the given rows format is invalid
51
     *
52
     * @return static
53
     */
54 5
    public function insertAll($rows)
55
    {
56 5
        $this->writeBlock($rows);
57
58 5
        return $this;
59
    }
60
61
    /**
62
     * @param Traversable|array $rows
63
     */
64 7
    private function writeBlock($rows)
65
    {
66 7
        $this->log(LogLevel::INFO, 'Writing rows to file');
67
68 7
        $this->initialiseForWriting();
69
70 7
        $first = true;
71 7
        foreach ($rows as $row) {
72 7
            if ($first === false) {
73 5
                fwrite($this->stream, $this->formatter->getRowSeparator());
74
            }
75 7
            fwrite($this->stream, $this->formatter->format($row));
76 7
            $first = false;
77
        }
78 7
        fwrite($this->stream, $this->formatter->getClosingBlock());
79 7
    }
80
81
    /**
82
     * Initialise the resource for writing.
83
     *
84
     * If we are at 0, then write initial block, otherwise, remove closing block and add a row separator
85
     *
86
     * This is so we can append a file with special characters at the beginning and end
87
     */
88 7
    private function initialiseForWriting()
89
    {
90
        // move to the end of the file to always append
91 7
        fseek($this->stream, 0, SEEK_END);
92
93 7
        if (ftell($this->stream) === 0) {
94 7
            fwrite($this->stream, $this->formatter->getInitialBlock());
95 3
        } elseif (strlen($this->formatter->getClosingBlock()) > 0) {
96 2
            $endBlock = $this->formatter->getClosingBlock();
97 2
            fseek($this->stream, strlen($endBlock) * -1, SEEK_CUR);
98 2
            fwrite($this->stream, $this->formatter->getRowSeparator());
99 1
        } elseif (strlen($this->formatter->getRowSeparator()) > 0) {
100 1
            fwrite($this->stream, $this->formatter->getRowSeparator());
101
        }
102 7
    }
103
104
    /**
105
     * Adds a single line
106
     *
107
     * @param mixed $row an item to insert
108
     *
109
     * @return static
110
     */
111 3
    public function insert($row)
112
    {
113 3
        $this->writeBlock([$row]);
114 3
        return $this;
115
    }
116
}
117