nur-sery/nur_src/mapper/app/datareader_command.php

260 lines
8.0 KiB
PHP

<?php
namespace nur\mapper\app;
use nur\A;
use nur\b\ValueException;
use nur\mapper\base\mappers_command;
use nur\mapper\csv\CsvReader;
use nur\mapper\csv\CsvReader_command;
use nur\mapper\csv\CsvWriter;
use nur\mapper\csv\CsvWriter_command;
use nur\mapper\fsv\FsvReader;
use nur\mapper\fsv\FsvReader_command;
use nur\mapper\fsv\FsvWriter;
use nur\mapper\fsv\FsvWriter_command;
use nur\mapper\json\JsonReader;
use nur\mapper\json\JsonReader_command;
use nur\mapper\json\JsonWriter;
use nur\mapper\json\JsonWriter_command;
use nur\mapper\json\YamlReader;
use nur\mapper\json\YamlReader_command;
use nur\mapper\json\YamlWriter;
use nur\mapper\json\YamlWriter_command;
use nur\mapper\line\LineReader;
use nur\mapper\line\LineReader_command;
use nur\mapper\line\LineWriter;
use nur\mapper\line\LineWriter_command;
use nur\str;
class datareader_command extends mappers_command {
const PRODUCER_CLASSES = [
LineReader_command::class,
CsvReader_command::class,
FsvReader_command::class,
JsonReader_command::class,
YamlReader_command::class,
];
const CONSUMER_CLASSES = [
LineWriter_command::class,
CsvWriter_command::class,
FsvWriter_command::class,
JsonWriter_command::class,
YamlWriter_command::class,
];
const MAPPER_CLASSES = [
];
protected function DYNAMIC_COMMAND_CLASSES(): array {
return array_merge(
self::PRODUCER_CLASSES, parent::PRODUCER_CLASSES,
self::CONSUMER_CLASSES, parent::CONSUMER_CLASSES,
self::MAPPER_CLASSES, parent::MAPPER_CLASSES
);
}
const DEFS = [
"csv" => [
"exts" => [".csv"],
"formats" => ["csv", "c"],
"reader" => [CsvReader_command::class, CsvReader::class],
"writer" => [CsvWriter_command::class, CsvWriter::class],
"set_input_encoding" => "setEncodingFilter",
"set_output_encoding" => "setEncodingFilter",
],
"fsv" => [
"exts" => [".fsv"],
"formats" => ["fsv", "v"],
"reader" => [FsvReader_command::class, FsvReader::class],
"writer" => [FsvWriter_command::class, FsvWriter::class],
"set_input_encoding" => "setInputEncoding",
"set_output_encoding" => "setOutputEncoding",
],
"json" => [
"exts" => [".json"],
"formats" => ["json", "j"],
"reader" => [JsonReader_command::class, JsonReader::class],
"writer" => [JsonWriter_command::class, JsonWriter::class],
"set_input_encoding" => false,
"set_output_encoding" => false,
],
"yaml" => [
"exts" => [".yaml", ".yml"],
"formats" => ["yaml", "l"],
"reader" => [YamlReader_command::class, YamlReader::class],
"writer" => [YamlWriter_command::class, YamlWriter::class],
"set_input_encoding" => false,
"set_output_encoding" => false,
],
"line" => [
"exts" => [],
"formats" => ["line"],
"reader" => [LineReader_command::class, LineReader::class],
"writer" => [LineWriter_command::class, LineWriter::class],
"set_input_encoding" => "setEncodingFilter",
"set_output_encoding" => "setEncodingFilter",
],
];
const IF_OPTION = ["-f", "--input", "args" => "file",
"action" => [self::class, "set_input_file"],
];
const IFO_OPTION = ["-F", "--input-format", "args" => "value",
"action" => [self::class, "set_input_format"],
];
const IE_OPTION = ["-e", "--input-encoding", "args" => "value",
"action" => [self::class, "set_input_encoding"],
];
const OF_OPTION = ["-o", "--output", "args" => "file",
"action" => [self::class, "set_output_file"],
];
const OFO_OPTION = ["-O", "--output-format", "args" => "value",
"action" => [self::class, "set_output_format"],
];
const OE_OPTION = ["-t", "--output-encoding", "args" => "value",
"action" => [self::class, "set_output_encoding"],
];
private static $input_file;
static function set_input_file($file): void {
self::$input_file = A::last(A::with($file));
}
private static $input_format;
static function set_input_format(string $input_format) {
self::$input_format = $input_format;
}
private static $input_encoding;
static function set_input_encoding(string $input_encoding) {
self::$input_encoding = $input_encoding;
}
private static $output_file;
static function set_output_file($file): void {
self::$output_file = A::last(A::with($file));
}
private static $output_format;
static function set_output_format(string $output_format) {
self::$output_format = $output_format;
}
private static $output_encoding;
static function set_output_encoding(string $output_encoding) {
self::$output_encoding = $output_encoding;
}
static function get(): array {
$producer = null;
$input_file = self::$input_file;
$input_format = self::$input_format;
if ($input_file !== null || $input_format !== null) {
if ($input_file !== null && $input_format === null) {
foreach (self::DEFS as $def) {
foreach (A::with($def["exts"]) as $ext) {
if (str::_ends_with($ext, $input_file)) {
$input_format = A::first(A::with($def["formats"]));
break 2;
}
}
}
if ($input_format === null) $input_format = "line";
}
$found = false;
foreach (self::DEFS as $def) {
foreach (A::with($def["formats"]) as $format) {
if ($input_format == $format) {
$found = true;
$producerClass = $def["reader"][1];
$producer = new $producerClass($input_file);
$input_encoding = self::$input_encoding;
if ($input_encoding !== null) {
$setInputEncoding = $def["set_input_encoding"];
if ($setInputEncoding) {
$producer->$setInputEncoding($input_encoding);
}
}
break 2;
}
}
}
if (!$found) {
throw new ValueException("$input_format: format invalide");
}
}
if ($producer === null) {
foreach (self::DEFS as $def) {
$commandClass = $def["reader"][0];
$producer = $commandClass::get(false);
if ($producer !== null) break;
}
}
$consumer = null;
$output_file = self::$output_file;
$output_format = self::$output_format;
if ($output_file !== null || $output_format !== null) {
if ($output_file !== null && $output_format === null) {
foreach (self::DEFS as $def) {
foreach (A::with($def["exts"]) as $ext) {
if (str::_ends_with($ext, $output_file)) {
$output_format = A::first(A::with($def["formats"]));
break 2;
}
}
}
if ($output_format === null) $output_format = "line";
}
$found = false;
foreach (self::DEFS as $def) {
foreach (A::with($def["formats"]) as $format) {
if ($output_format == $format) {
$found = true;
$consumerClass = $def["writer"][1];
$consumer = new $consumerClass($output_file);
$output_encoding = self::$output_encoding;
if ($output_encoding !== null) {
$setOutputEncoding = $def["set_output_encoding"];
if ($setOutputEncoding) {
$consumer->$setOutputEncoding($output_encoding);
}
}
break 2;
}
}
}
if (!$found) {
throw new ValueException("$output_format: format invalide");
}
}
if ($consumer === null) {
foreach (self::DEFS as $def) {
$commandClass = $def["writer"][0];
$consumer = $commandClass::get(false);
if ($consumer !== null) break;
}
}
if ($consumer === null) {
foreach (self::DEFS as $def) {
$producerClass = $def["reader"][1];
$commandClass = $def["writer"][0];
if ($producer instanceof $producerClass) {
$consumer = $commandClass::get();
break;
}
}
}
if ($producer === null) $producer = LineReader_command::get();
if ($consumer === null) $consumer = LineWriter_command::get();
return [$producer, $consumer];
}
}