SQL Server BCP: как поставить кавычки вокруг всех полей?

У меня есть эта команда BCP:

'bcp DBName..vieter out c:\test003.txt -c -T /t"\",\"" -S SERVER'

Выходной CSV, который я получаю, не заключает имена полей в кавычки, а заключает их в запятые! Как я могу заставить /t"\",\"" заключать в кавычки все поля.

Спасибо всем


person Abs    schedule 13.01.2010    source источник


Ответы (7)


Установка терминатора строки в дополнение к терминатору поля должна помочь.

'bcp DBName..vieter out c:\test003.txt -c -T -t"\",\"" -r"\"\n\"" -S SERVER'

Это, вероятно, сработает, но пропустите начальное " для первого поля первой строки и, возможно, последнее поле последней строки - я не уверен, просто предполагаю, что здесь нет сервера!

или попробуйте использовать QUOTENAME для переноса текстовых полей (вы также можете переносить числа, но обычно это не требуется).

'bcp "SELECT id, age, QUOTENAME(name,'"') FROM DBName..vieter" queryout c:\test003.txt -c -T -t"," -S SERVER'
person Paul Creasey    schedule 13.01.2010
comment
Есть ли способ, чтобы у первого и последнего были кавычки - мне действительно нужен хорошо отформатированный файл CSV. - person Abs; 14.01.2010
comment
То, что вы сказали, произошло, но у последнего поля было две кавычки в конце, а у первого не было кавычек. Мне просто нужно возиться с вышеперечисленным, чтобы получить то, что я хочу? Есть ли какие-то документы, на которые я могу взглянуть, поскольку я не сталкивался с этим регулярным выражением - если это регулярное выражение! - person Abs; 14.01.2010
comment
вы можете использовать QUERYOUT, а затем создать запрос, используя QUOTENAME(column,'"') для текстовых полей. - person Paul Creasey; 14.01.2010
comment
Могу ли я использовать QUOTENAME для цитирования всех столбцов без передачи имени столбца, поскольку мне нужно сделать это для разных таблиц? Я пробовал это, но у меня было довольно много ошибок - правильно ли цитируется? Я использую вышеизложенное в EXEC master..xp_cmdshell @bcpCommand - person Abs; 14.01.2010
comment
Потенциально вы могли бы установить @bcpCommand программно, запросив системные столбцы и создав запрос, но это становится очень запутанным, а не то, что я хотел бы делать. Это похоже на серьезную проблему с BCP! - person Paul Creasey; 14.01.2010
comment
Спасибо, Пол - я не уверен, смогу ли я пойти дальше с этим. Ваш ответ так близок, но я не могу поверить, что не могу добавить цитату в первое поле и удалить ее из самого последнего поля последней строки! Блин! Это вообще возможно? - person Abs; 14.01.2010
comment
Постобработка сгенерированного файла с использованием вашего любимого языка сценариев должна сделать это... - person Oliver; 16.02.2018
comment
Осторожно: QUOTENAME поддерживает только ввод строки длиной до 128 символов, поэтому он не будет работать для более длинных значений поля. - person Oliver; 16.02.2018
comment
Решение с кавычками действительно отвечает на исходный вопрос. Но он не экранирует символы со значениями поля. QUOTENAME имеет, но, как упомянул Оливер, имеет ограничение в 128 байт. Так что оба не являются надежными решениями - person Ben Ootjers; 09.01.2019

Вам нужно использовать CHAR(34) для цитаты. На этой странице есть более подробная информация: http://www.sqlteam.com/forums/topic.asp?TOPIC_ID=153000

person user1473461    schedule 20.12.2012

В качестве альтернативы, если вас устраивает сценарий на основе Powershell, вы можете попробовать приведенный ниже код, который выполняет автоматическое цитирование.

Invoke-sqlcmd -ConnectionString "Server=SERVERNAME, `
3180;Database=DATABASENAME;Trusted_Connection=True;"  `
-Query "SET NOCOUNT ON;SELECT * FROM TABLENAME" -MaxCharLength 700 | `
Export-Csv -NoTypeInformation -path C:\temp\FileName.csv -Encoding UTF8
person Venkataraman R    schedule 14.05.2020

Вот список команд, которые я использовал.

BCP "DECLARE @colnames VARCHAR(max);SELECT @colnames = COALESCE(@colnames + ',', '') + column_name from databaseName.INFORMATION_SCHEMA.COLUMNS where TABLE_NAME='tableName'; select @colnames;" queryout "C:\HeadersOnly.csv" -r"\n\""  -c -T -Uusername -Ppassword -SserverName

bcp databaseName.schema.tableName out "C:\EmployeeDatawithoutheaders.csv" -T -t"\",\"" -r"\"\n\"" -c -Uusername -Ppassword -SserverName

copy /b C:\HeadersOnly.csv+C:\EmployeeDatawithoutheaders.csv C:\EmployeeData.csv

del C:\HeadersOnly.csv

del C:\EmployeeDatawithoutheaders.csv
person Modem Rakesh goud    schedule 01.08.2017
comment
Очень нравится это решение, несколько вопросов об улучшениях: 1. Любой вариант, позволяющий избежать последней строки, чтобы быть 2. Любой вариант, чтобы быть умным и использовать дополнительный, только если ячейки содержат разделитель столбца (,) или строки (\n) внутри ? - person Velizar VESSELINOV; 05.12.2018

Я предполагаю, что ваша цель состояла в том, чтобы четко разделить значения полей с помощью уникального идентификатора, чтобы процедура импорта не вызывала проблем.

У меня была та же проблема, и я нашел этот обходной путь полезным: использование необычного терминатора поля, например | или даже строки /#/, может быть очень уникальным и не должно мешать содержимому вашей строки. Вы также можете использовать HEX-значения (ограничено, см. ">https://docs.microsoft.com/en-us/sql/tools/bcp-utility?view=sql-server-2017)

экспортировать

bcp DB.dbo.Table out /tmp/output2.csv -c -t "/#/" -U sa -P secret -S localhost

импорт

bcp TargetTable in /tmp/output2.csv -t "/#/" -k -U sa -P secret -S localhost -d DBNAME -c -b 50000 
person robie2011    schedule 29.08.2018
comment
Мне нравится это решение, но есть еще одна ситуация, в которой это вызывает проблемы. То есть, если в значениях поля используется возврат каретки/перевод строки. Поля должны быть закрыты, чтобы преодолеть это, я думаю. - person Ben Ootjers; 09.01.2019

bcp "SELECT char(34) + * +char(34) FROM atable queryout "C:\temp\out.csv" -T -N -c /t"\",\""

Это поставит кавычки до и после каждого поля (включая первое и последнее).

person Seb    schedule 26.02.2018

Фактический рабочий ответ, который удаляет начальную кавычку, таков:

A) сгенерируйте файл формата с помощью bcp:

bcp db.schema.tabel format nul -c -x -f file.xml -t"\",\"" -r"\"\r\n" -T -k

B) отредактируйте этот файл, чтобы вручную скопировать поле 1 в поле 0 выше, в качестве первого поля установите Max_Length = 1 и удалите разделитель и одну кавычку, которая была в поле 1.

<FIELD ID="0" xsi:type="CharTerm" TERMINATOR="\&quot;" MAX_LENGTH="1" COLLATION="SQL_Latin1_General_CP1_CI_AS"/>

Трюк работает, так как вы добавляете поле (интерфейс к файлу) для обнаружения первого разделителя, что всегда приводит к нулевому значению, но не добавляет строку (интерфейс для вывода запроса).

person user7511843    schedule 03.02.2017