Как вставить CSV-файл из Azure Repo в базу данных SQL Azure через конвейер выпуска?

Я пытаюсь опубликовать файл csv, который в настоящее время хранится в репозитории Azure, и хотел бы вставить содержимое csv в базу данных SQL Azure с помощью конвейера выпуска. Технически это осуществимо? Поскольку я продолжаю нажимать «Код ошибки операционной системы 997 (выполняется операция перекрывающегося ввода-вывода.)». ошибка.

Пример данных CSV:

"True", "123,234325", "abc"

Вот скрипт, который я использовал:

Bulk Insert TargetTableName
from 'ArtifactAlias\foldername\filename.csv'
with
(
    FIRSTROW = 2,
    FIELDTERMINATOR = ',', 
    ROWTERMINATOR = '\n',
    FIELDQUOTE = '"'
)

Нам нужно больше подробностей…

Dai 06.08.2024 07:32

Да, это технически осуществимо. Какой фрагмент кода вызывает эту ошибку? Используете ли вы самостоятельное размещение или конвейеры Azure?

Nick.Mc 06.08.2024 07:48

@Nick.Mc, я использую Azure Pipelines. Согласно журналу развертывания, в нем не указано, какая часть кода вызывает эту ошибку. На самом деле, я также тестировал вставку CSV-файла из локальной версии в ту же базу данных SQL Azure через SSMS. показывает ту же ошибку.

akaya_1992 06.08.2024 09:28

@Dai, я дополнил скрипт. Спасибо.

akaya_1992 06.08.2024 09:36

Сможете ли вы запустить этот сценарий без использования конвейеров? Похоже, вам нужно запустить этот сценарий на сервере SQL, а не на других машинах, таких как агенты конвейера. Информацию смотрите здесь.

Alvin Zhao - MSFT 06.08.2024 09:46

@AlvinZhao-MSFT, я пытался запустить его в SSMS. Выдает ту же ошибку.

akaya_1992 06.08.2024 09:52

Вероятно, нам нужно найти другие варианты, такие как инструмент bcp.

Alvin Zhao - MSFT 06.08.2024 10:08

@AlvinZhao-MSFT, я тоже исследовал bcp. Однако мой файл csv содержит текстовый квалификатор, а bcp не предоставляет этот аргумент. Вся история усложнится.

akaya_1992 06.08.2024 10:25

Это действительно сложнее. Можете ли вы предоставить образец содержимого CSV, чтобы объяснить ваши требования? Кстати, Azure Pipelines — это всего лишь тип инструмента автоматизации. Если вы не можете использовать этот инструмент локально, он, вероятно, выйдет из строя в конвейерах. Вы можете отредактировать исходное сообщение с учетом всех требований, чтобы воспользоваться идеями экспертов сообщества.

Alvin Zhao - MSFT 06.08.2024 10:39

@akaya_1992, я обновил ответ, чтобы экспортировать ожидаемое содержимое в новый файл csv во время задания агента конвейера и использовать его для запуска команды bcp. Надеюсь, что он сможет решить ваш вопрос в этом посте. Спасибо за обмен и усилия.

Alvin Zhao - MSFT 06.08.2024 11:59
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
0
10
74
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Обновлять

В соответствии с вашим дополнением и вашим возможным требованием защитить ,, который можно использовать в каждом поле вашего содержимого CSV, я бы предложил запустить приведенный ниже сценарий PowerShell во время работы агента, чтобы создать новый файл CSV без заголовков, где ваш текущий разделитель (, ) меняется на другой (| в моем случае), который не будет конфликтовать с данными в полях; это также изменит поле True/False на 1/0 для импорта.

Таблица образцов

CREATE TABLE [dbo].[SampleTable] (
    [IsTrueFalse] BIT NOT NULL,
    [Number] NVARCHAR(50) NOT NULL,
    [Remark] NVARCHAR(50) NOT NULL
);

образец.csv

IsTrueFalse,Number,Remark
"True", "123,234325", "abc"
"False", "456,567890", "efg"

noheaders.csv

1| 123,234325| abc
0| 456,567890| efg

Скрипт PowerShell, используемый в конвейере выпуска

# Define file paths
$inputFile = "$(System.DefaultWorkingDirectory)\_azuresql\sample.csv"
$outputFile = "$(System.DefaultWorkingDirectory)\_azuresql\noheaders.csv"

# Read the input file content
$content = Get-Content $inputFile

# Process each line: replace `",` with `|`, remove quotes, and convert "True"/"False" to 1/0
$content | Select-Object -Skip 1 | ForEach-Object {
    # Replace `",` with `|` and then remove all remaining quotes
    $line = $_ -replace '",', '|' -replace '"', ''
   
    # Convert "True"/"False" to 1/0 for the IsTrueFalse column
    $fields = $line -split '\|'
    $fields[0] = if ($fields[0] -eq 'True') { '1' } elseif ($fields[0] -eq 'False') { '0' } else { $fields[0] }
    $fields -join '|'
} | Set-Content $outputFile

echo "Checking the contents of $outputFile..."
Get-Content $outputFile

echo "Checking bcp version..."
bcp -v

echo "Running bcp command..."
bcp SampleTable in "$outputFile" -S $(AzureSQLServer) -d $(AzureSQLDB) -U $(AzureSQLServerAdmin) -P $(AzureSQLServerAdminPWD) -q -c -t "|"  # Pipe delimiter


Из выражения FIRSTROW = 2 вашего SQL-скрипта я увидел, что ваш CSV-файл должен иметь первую строку заголовков. Для этого вы можете удалить первую строку и вывести ожидаемое содержимое в новый файл во время задания агента конвейера. Вот обновленный сценарий PowerShell для справки.

# Define file paths
$inputFile = "$(System.DefaultWorkingDirectory)\_azuresql\test.csv"
$outputFile = "$(System.DefaultWorkingDirectory)\_azuresql\noheaders.csv"

# Read the input CSV file, skip the first line (header), and write the result to the output file
Get-Content $inputFile | Select-Object -Skip 1 | Set-Content $outputFile

echo "Checking bcp version..."
bcp -v

echo "Running bcp command..."
bcp Users in "$outputFile" -S $(AzureSQLServer) -d $(AzureSQLDB) -U $(AzureSQLServerAdmin) -P $(AzureSQLServerAdminPWD) -q -c -t ","

Судя по вашему описанию, похоже, что вам нужно запустить SQL-скрипт на SQL, а не на машине агента конвейера, как обсуждалось в этой теме.

В соответствии с этим документом о том, как загрузить данные из CSV-файла в базу данных (bcp) — Azure SQL | Microsoft Learn, мы могли бы использовать инструмент BCP для импорта содержимого CSV в таблицу базы данных SQL Azure.

Следуя этому направлению, я протестировал пример конвейера выпуска, работающего на агенте windows-latest, размещенном в Microsoft, и сумел импортировать содержимое CSV-файла.

  1. I created a table Users for test in Azure SQL DB;

  2. Added a test.csv file in my repo with the contents like below;

  3. In a release pipeline, added the repo as artifacts and ran the PowerShell script;

    echo "Checking bcp version..."
    bcp -v
    
    echo "Running bcp command..."
    bcp Users in "$(System.DefaultWorkingDirectory)/_azuresql/test.csv" -S 
    $(AzureSQLServer) -d $(AzureSQLDB) -U $(AzureSQLServerAdmin) -P 
    $(AzureSQLServerAdminPWD) -q -c -t ","
    

  4. As the release was succeeded, we could check the update in the table;

Привет @Alvin Zhao, очень благодарен за твою помощь~ Могу ли я узнать, тестировали ли вы также файл csv, имеющий текстовый квалификатор?

akaya_1992 07.08.2024 03:01

Я не совсем понимаю, что вы имеете в виду под текстовым квалификатором. Можете ли вы поделиться образцом в исходном посте? Спасибо.

Alvin Zhao - MSFT 07.08.2024 04:03

без проблем. дополнено.

akaya_1992 07.08.2024 07:40

@akaya_1992, смотрите мой обновленный ответ в соответствии с вашим дополнением.

Alvin Zhao - MSFT 07.08.2024 11:57

Чжао, мне удалось получить тот же результат, добавив этап запуска сценария Python, но я все равно ценю ваши большие усилия в этом направлении.

akaya_1992 08.08.2024 05:25

Другие вопросы по теме