CsvWriter::createHttpHeaders()   A
last analyzed

Complexity

Conditions 2
Paths 2

Size

Total Lines 7
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 6

Importance

Changes 3
Bugs 0 Features 1
Metric Value
c 3
b 0
f 1
dl 0
loc 7
ccs 0
cts 0
cp 0
rs 9.4285
cc 2
eloc 4
nc 2
nop 1
crap 6
1
<?php
2
3
namespace CSanquer\ColibriCsv;
4
5
/**
6
 * Csv Writer
7
 *
8
 * @author Charles SANQUER - <[email protected]>
9
 */
10
class CsvWriter extends AbstractCsv
11
{
12
    /**
13
     *
14
     * Default Excel Writing configuration
15
     *
16
     * available options :
17
     * - delimiter : (default = ';')
18
     * - enclosure : (default = '"')
19
     * - encoding : (default = 'CP1252')
20
     * - eol : (default = "\r\n")
21
     * - escape : (default = "\\")
22
     * - first_row_header : (default = false) use the PHP keys as CSV headers and write the first row with them
23
     * - bom : (default = false)  add UTF8 BOM marker
24
     * - translit : (default = 'translit')  iconv translit option possible values : 'translit', 'ignore', null
25
     * - trim : (default = false) trim each values on each line
26
     *
27
     * N.B. : Be careful, the option 'trim' decrease significantly the performances
28
     *
29
     * @param array $options Dialect Options to describe CSV file parameters
30
     */
31 19
    public function __construct($options = [])
32
    {
33 19
        parent::__construct($options);
34 19
        $this->mode = self::MODE_WRITING;
35 19
        $this->fileHandlerMode = 'wb';
36 19
    }
37
38 2
    protected function getCompatibleFileHanderModes()
39
    {
40 2
        return ['wb', 'r+b', 'w+b', 'a+b', 'x+b', 'c+b'];
41
    }
42
43
    /**
44
     * open a csv file to write
45
     *
46
     * @param  string|resource $file filename or stream resource, default = null
47
     * @return AbstractCsv
48
     */
49 12
    public function open($file = null)
50
    {
51 12
        parent::open($file);
52 12
        $this->writeBom();
53
54 12
        return $this;
55
    }
56
57
    /**
58
     * get HTTP headers for streaming CSV file
59
     *
60
     * @param  string $filename
61
     * @return array
62
     */
63 1
    public function getHttpHeaders($filename)
64
    {
65
        return [
66 1
            'Content-Type' => 'application/csv',
67 1
            'Content-Disposition' => 'attachment;filename="'.$filename.'"',
68 1
        ];
69
    }
70
71
    /**
72
     * echo HTTP headers for streaming CSV file
73
     *
74
     * @param string $filename
75
     *
76
     * @codeCoverageIgnore this cannot be tested correctly by PHPUnit because it send HTTP headers
77
     */
78
    public function createHttpHeaders($filename)
79
    {
80
        $headers = $this->getHttpHeaders($filename);
81
        foreach ($headers as $key => $value) {
82
            header($key.': '.$value);
83
        }
84
    }
85
86
    /**
87
     *
88
     * @param resource|null $fileHandler
89
     * @param array         $values
90
     *
91
     * @return CsvWriter
92
     *
93
     * @throws \InvalidArgumentException
94
     */
95 13
    protected function write($fileHandler, $values)
96
    {
97 13
        if ($this->isFileOpened()) {
98 13
            $delimiter = $this->dialect->getDelimiter();
99 13
            $enclosure = $this->dialect->getEnclosure();
100 13
            $eol = $this->dialect->getLineEndings();
101 13
            $escape = $this->dialect->getEscape();
102 13
            $trim = $this->dialect->getTrim();
103 13
            $enclosingMode = $this->dialect->getEnclosingMode();
104 13
            $escapeDouble = $this->dialect->getEscapeDouble();
105 13
            $line = implode($this->dialect->getDelimiter(), array_map(
106 13
                function ($var) use ($delimiter, $enclosure, $eol, $escape, $trim, $enclosingMode, $escapeDouble) {
107
                    // Escape enclosures and enclosed string
108 13
                    if ($escapeDouble) {
109
                        // double enclosure
110 11
                        $searches = [$enclosure];
111 11
                        $replacements = [$enclosure.$enclosure];
112 11
                    } else {
113
                        // use escape character
114 2
                        $searches = [$enclosure];
115 2
                        $replacements = [$escape.$enclosure];
116
                    }
117 13
                    $clean = str_replace($searches, $replacements, $trim ? trim($var) : $var);
118
119 13
                    if ($enclosingMode === Dialect::ENCLOSING_ALL ||
120
                        (
121 12
                            $enclosingMode === Dialect::ENCLOSING_MINIMAL &&
122 11
                            preg_match('/['.preg_quote($enclosure.$delimiter.$eol, '/').']+/', $clean)
123 12
                        ) ||
124 12
                        ($enclosingMode === Dialect::ENCLOSING_NONNUMERIC && preg_match('/[^\d\.]+/', $clean))
125 13
                    ) {
126 10
                        $var = $enclosure.$clean.$enclosure;
127 10
                    } else {
128 12
                        $var = $clean;
129
                    }
130
131 13
                    return $var;
132 13
                },
133
                $values
134 13
            ))
135
            // Add line ending
136 13
            .$this->dialect->getLineEndings();
137
138
            // Write to file
139 13
            fwrite($fileHandler, $this->convertEncoding($line, 'UTF-8', $this->dialect->getEncoding()));
140 13
        }
141
142 13
        return $this;
143
    }
144
145
    /**
146
     * write a CSV row from a PHP array
147
     *
148
     * @param array $values
149
     *
150
     * @return CsvWriter
151
     */
152 14
    public function writeRow(array $values)
153
    {
154 14
        $this->openFile($this->fileHandlerMode);
155
        
156 13
        if ($this->dialect->getFirstRowHeader() && empty($this->headers)) {
157 2
            $this->headers = array_keys($values);
158 2
            $this->write($this->getFileHandler(), $this->headers);
159 2
        }
160
161 13
        return $this->write($this->getFileHandler(), $values);
162
    }
163
164
    /**
165
     * write CSV rows from a PHP arrays
166
     *
167
     * @param array rows (multiple arrays of values)
168
     *
169
     * @return CsvWriter
170
     */
171 6
    public function writeRows(array $rows)
172
    {
173 6
        foreach ($rows as $values) {
174 6
            $this->writeRow($values);
175 6
        }
176
177 6
        return $this;
178
    }
179
}
180