X-Git-Url: https://git.mxchange.org/?p=core.git;a=blobdiff_plain;f=inc%2Fclasses%2Fmain%2Ffile_directories%2Ftext%2Finput%2Fcsv%2Fclass_CsvInputFile.php;h=0c4c5a25f6568a256126927b262138bb04df466a;hp=b6c8d5e631a636ed9a6d56924af3f865de209e39;hb=1a91dabdfed365947d1ce11675aacae9d424edff;hpb=e65d661719c78867ff57607457c8abfaae2e2ee3 diff --git a/inc/classes/main/file_directories/text/input/csv/class_CsvInputFile.php b/inc/classes/main/file_directories/text/input/csv/class_CsvInputFile.php index b6c8d5e6..0c4c5a25 100644 --- a/inc/classes/main/file_directories/text/input/csv/class_CsvInputFile.php +++ b/inc/classes/main/file_directories/text/input/csv/class_CsvInputFile.php @@ -51,6 +51,121 @@ class CsvInputFile extends BaseInputTextFile implements CsvInputStreamer { // Return the prepared instance return $fileInstance; } + + /** + * Reads a line from CSV file and returns it as an indexed array. Please + * note that strings *must* be always in double-quotes, else any found + * column separators will be parsed or they may be interpreted incorrectly. + * + * @param $columnSeparator Character to use separting columns + * @return $lineArray An indexed array with the read line + */ + public function readCsvFileLine ($columnSeparator) { + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] columnSeparator=%s - CALLED!', __METHOD__, __LINE__, $columnSeparator)); + + // Read raw line + $data = $this->getPointerInstance()->readLine(); + + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] data()=%s', __METHOD__, __LINE__, strlen($data))); + + // Parse data + $lineArray = $this->parseDataToIndexedArray($data, $columnSeparator); + + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] lineArray()=%s - EXIT!', __METHOD__, __LINE__, count($lineArray))); + + // Return it + return $lineArray; + } + + /** + * Parses given data into an array + * + * @param $data Raw data e.g. returned from readLine() + * @param $columnSeparator Character to use separting columns + * @return $lineArray An indexed array with the read line + */ + private function parseDataToIndexedArray ($data, $columnSeparator) { + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] data()=%s,columnSeparator=%s - CALLED!', __METHOD__, __LINE__, strlen($data), $columnSeparator)); + + // Init return array + $lineArray = array(); + + // Whether the parser reads a quoted string (which may contain the column separator again) + $isInQuotes = FALSE; + + // Init column data + $column = ''; + + // Now parse the line + for ($idx = 0; $idx < strlen($data); $idx++) { + // "Cache" char + $char = substr($data, $idx, 1); + + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] idx=%s,char=%s ...', __METHOD__, __LINE__, $idx, $char)); + + // Is the column separator found and not within quotes? + if (($isInQuotes === FALSE) && ($char == $columnSeparator)) { + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] Adding column=%s ...', __METHOD__, __LINE__, $column)); + + // Add this line to the array + array_push($lineArray, $column); + + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] lineArray()=%s - After add!', __METHOD__, __LINE__, count($lineArray))); + + // Clear variable ... + $column = ''; + + // ... and skip it + continue; + } elseif ($char == chr(34)) { + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] column=%s ...', __METHOD__, __LINE__, $column)); + + // $column must be empty at this point if we are at starting quote + assert(($isInQuotes === TRUE) || (empty($column))); + + // Double-quote found, so flip variable + $isInQuotes = (!$isInQuotes); + + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] isInQuotes=%d ...', __METHOD__, __LINE__, intval($isInQuotes))); + + // Skip double-quote (escaping of them is not yet supported) + continue; + } + + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] Adding char=%s ...', __METHOD__, __LINE__, $idx, $char)); + + // Add char to column + $column .= $char; + } // END - for + + // Is there something outstanding? + if (!empty($column)) { + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] Adding column=%s ...', __METHOD__, __LINE__, $column)); + + // Then don't forget this. :-) + array_push($lineArray, $column); + + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] lineArray()=%s - After add!', __METHOD__, __LINE__, count($lineArray))); + } // END - if + + // Debug message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__)->debugOutput(sprintf('[%s:%d:] lineArray()=%s - EXIT!', __METHOD__, __LINE__, count($lineArray))); + + // Return it + return $lineArray; + } } // [EOF]