Обработка файла CSV - удалите кавычки и замените разделитель запятой на табуляцию

Протокол ssh не основан на HTTP и, как таковой, не может быть проксирован через обычный proxy_pass of ngx_http_proxy_module

Однако недавно, начиная с nginx 1.9.0 (выпущен как стабильный с 1.10.0 26.04.2016), nginx действительно получил поддержку для выполнения TCP stream проксирование, что означает, что если у вас достаточно последняя версия nginx, вы можете фактически проксировать ssh-соединения с ней (однако обратите внимание, что вы не сможете добавить что-либо вроде X-Real-IP к прокси-соединению, так как это не основано на HTTP).

Для получения дополнительной информации и примеров посетите:

3
18.11.2018, 11:41
5 ответов

Этот короткий sedскрипт может обрабатывать оба типа файлов (или даже смешанные со строками первого и второго типа):

sed '/"/!s/,/\t/g;s/","/\t/g; s/"//g'

Поскольку он не группирует выражения и не зацикливается, он должен быть намного быстрее, чем ваш скрипт.

Похоже, у вас GNU sed, так что \tработает, в противном случае вместо этого используйте литерал TAB.

2
27.01.2020, 21:13

Несколько подходов:

Для file1(с двойными кавычками):

--awkподход:

awk -F'"' '{ r=""; for(i=1;i<NF;i++) 
     if ($i~/^[[:alnum:]]/) r=(r!="")? r OFS $i : $i; print r }' OFS='\t' file1

--sedподход:

sed 's/","/\t/g; s/"//g;' file1

Вывод (для обоих подходов):

Jhon    Carpenter   CA,TX,NJ
Mike    Painter WA,GA,MI

----------

Для файл2(без двойных кавычек) - достаточно применить trкоманда:

tr ',' '\t' <file2

Вывод:

EMP1    123456  CA
EMP2    456789  TX

----------

Унифицированный подход для условия «одной и той же команды должно быть достаточно для обоих типов файлов »:

awk -v quoted=$(grep -cm1 '"' file1) 'BEGIN{ FS=(quoted)? "\"" : ","; }
     { r=""; for(i=1;i<=NF;i++) if(!quoted || $i~/^[[:alnum:]]/) r=(r!="")? r OFS $i : $i; 
             print r }' OFS='\t' file1
2
27.01.2020, 21:13

Использованиеcsvkit:

$ csvformat -T file1.csv
Jhon    Carpenter       CA,TX,NJ
Mike    Painter WA,GA,MI

$ csvformat -T file2.csv
EMP1    123456  CA
EMP2    456789  TX

Вывод для file1.csvвыглядит немного не так, но это только потому, что вкладки не совпадают правильно. Между всеми столбцами есть вкладка.

CSVKit — это основанный на Python набор инструментов для различных утилит оболочки, связанных с CSV. Он правильно анализирует CSV и может использоваться для запроса, форматирования и преобразования файлов CSV.

Если бы, например, первый файл имел правильные заголовки, то преобразовать его в JSON было бы так же просто, как

$ csvjson file1.csv
[{"First": "Jhon", "Last": "Carpenter", "Stuff": "CA,TX,NJ"}, {"First": "Mike", "Last": "Painter", "Stuff": "WA,GA,MI"}]
3
27.01.2020, 21:13

Что ж, это решение не такое элегантное, как ответ Кусалананды, и я думаю, оно будет не таким быстрым, как хотелось бы, но оно должно работать нормально.

#!/usr/bin/env bash

for file; do

  while read -r line; do

    if <<< "${line}" grep -F -e '"' > '/dev/null' 2>&1; then
      <<< "${line}" \
      grep -P -o -e '(?<=")([^,].*?)(?=")' |
      tr $'\n' $'\t' | rev | cut -c 2- | rev
    else
      <<< "${line}" \
      tr ',' $'\t'
    fi

  done < "${file}"

done

Пример:

$ cat file1
"Jhon","Carpenter","CA,TX,NJ"
"Mike","Painter","WA,GA,MI"

$ cat file2
EMP1,123456,CA
EMP2,456789,TX

$ script.sh file1 file2
Jhon    Carpenter   CA,TX,NJ
Mike    Painter WA,GA,MI
EMP1    123456  CA
EMP2    456789  TX
0
27.01.2020, 21:13

Для данных CSV требуется соответствующий синтаксический анализатор CSV. Мне нравится ответ Кусалананды. Вы также можете использовать такой язык, как Ruby, который поставляется с модулем csv :

.
ruby -rcsv -e '
  out = CSV.new($stdout, {:col_sep => "\t"})
  CSV.foreach(ARGV.shift) {|row| out << row} 
' file1.csv
0
27.01.2020, 21:13

Теги

Похожие вопросы