Csv 如何在awk脚本中传递命令行参数

Csv 如何在awk脚本中传递命令行参数,csv,awk,Csv,Awk,这类问题以前有人问过,但不完全是这个问题。我是bash和awk脚本的新手。所以我不知道如何实现我的目标 我的目标是从csv文件生成sql insert 以下是我的csv文件内容:- ID;NAME;AGE;TITLE;DATE;SALARY 1;Test1;36;Engineer;date '2022-10-12';50.40 2;Test2;45;Manager;date '2020-01-15';100.50 我的awk脚本是sql.awk:- #!/bin/awk -f BEG

这类问题以前有人问过,但不完全是这个问题。我是bash和awk脚本的新手。所以我不知道如何实现我的目标

我的目标是从csv文件生成sql insert

以下是我的csv文件内容:-

ID;NAME;AGE;TITLE;DATE;SALARY
1;Test1;36;Engineer;date '2022-10-12';50.40
2;Test2;45;Manager;date '2020-01-15';100.50
我的awk脚本是sql.awk:-

    #!/bin/awk -f

BEGIN {
  FS=";"
  OFS=","
  quotation="'"
}
FNR==1 {
    $1=$1; head=$0
    next
}
{
  dat=""
  for(i=1;i<=NF;i++) {
      val=($i~/[[:alpha:]]$/)?quotation $i quotation:$i
      dat=(dat)?dat OFS val:val
  }
  printf("INSERT INTO  DATA ( %s) VALUES ( %s );\n", head, dat) > "data.sql"
}
END {
    print ENVIRON["strftime"] 
    printf("\n-- Generated by %s at %s\n", ENVIRON["USERNAME"], strftime("%Y-%m-%d %T")) >> "data.sql"
}
我的目标是获取sql表名作为命令行参数。我希望它来自命令行参数,而不是硬编码数据

我尝试将其作为sript修改为:-

./sql.awk-f data.csv gievn_table_name

    #!/bin/awk -f

BEGIN {
  FS=";"
  OFS=","
  quotation="'"
  tableName=ARGV[2]
}
FNR==1 {
    $1=$1; head=$0
    next
}
{
  dat=""
  for(i=1;i<=NF;i++) {
      val=($i~/[[:alpha:]]$/)?quotation $i quotation:$i
      dat=(dat)?dat OFS val:val
  }
  printf("INSERT INTO  %s VALUES ( %s );\n",tableName, head, dat) > tableName.sql
}
END {
    print ENVIRON["strftime"] 
    printf("\n-- Generated by %s at %s\n", ENVIRON["USERNAME"], strftime("%Y-%m-%d %T")) >> tableName.sql
}
#/垃圾箱/awk-f
开始{
FS=“;”
OFS=“,”
QUOTE=“””
tableName=ARGV[2]
}
FNR==1{
$1=$1;人头=$0
下一个
}
{
dat=“”
对于(i=1;i tableName.sql)
}
结束{
打印环境[“strftime”]
printf(“\n--由%s在%s\n处生成”,环境[“用户名”],strftime(“%Y-%m-%d%T”))>>tableName.sql
}
我有一个错误:

./sql.awk-f data.csv gievn_table_name awk:./sql.awk:19:printf(“插入到%s值(%s);\n”,tableName,head,dat)>tableName.sql awk:./sql.awk:19:^语法错误 awk:./sql.awk:23:printf(“\n--由%s在%s处生成”\n”、环境[“用户名”]、strftime(“%Y-%m-%d%T”)>>tableName.sql awk:./sql.awk:23:^语法错误 awk:data.csv:2:1;Test1;36;工程师;日期'2022-10-12';50.40 awk:data.csv:2:^表达式中的字符“”无效 awk:data.csv:2:1;Test2;36;工程师;日期'2022-10-12';50.40 awk:data.csv:2:^语法错误

如何获取表名和输出文件名的命令行参数?

如果不希望awk以后将其作为文件处理,则需要在从
ARGV
数组中读取值后执行
ARGC--

cat sql.awk

BEGIN {
  FS=";"
  OFS=","
  quotation="'"
  tableName=ARGV[2]
  ARGC--
}
FNR==1 {
    $1 = $1
    head = $0
    next
}
{
  dat = ""
  for(i=1; i<=NF; i++) {
      val = ($i~/[[:alpha:]]$/) ? quotation $i quotation : $i
      dat = (dat != "") ? dat OFS val : val
  }
  printf("INSERT INTO %s ( %s ) VALUES ( %s );\n", tableName, head, dat)
}
END {
    printf("\n-- Generated by %s at %s\n", ENVIRON["USER"], strftime("%Y-%m-%d %T"))
}

或者,您可以在awk命令中使用更常见的
-v tableName=DATA

数据库服务器具有从CSV加载数据的内置函数,您应该使用这些函数,而不是编写可能容易受到攻击的脚本。要将
tableName
添加到脚本中,请使用:
/csv2sql.awk-v选项卡leName=gievn_table_name data.csv
和您需要修复的代码中的tableName.sql“(然后是一些)。同意使用
bcp
或其他供应商提供的实用程序的建议,但为了您的理解,请使用shell传递命令行参数,将上面的内容保存到myAwkScript,使用正确的
!/bin/bash
(或任何一行)作为第一行,然后用
myAwkScript“$@”
调用
bash
脚本,如
myBashAwker f1 f2 f3….fn
。祝你好运。不要用shebang来调用awk解释器,这只会让你的生活更加艰难。如果你想调用shell命令,那么就用shebang来调用shell(例如,
#!/usr/bin/env bash
)然后像从命令行一样调用awk,如果希望它将传递给shell脚本的所有参数都视为awk脚本的参数,则在末尾添加
“${@:}”
,即
awk'script'${:}”
。同样为了测试,我升级了csv文件并删除了所有单引号。然后我得到了以下错误:
/test.awk-f data.csv tablename awk:./test.awk:5:fatal:无法打开文件
tablename'进行读取(没有这样的文件或目录)`@masiboo,在调用脚本时停止使用
-f
。您是在告诉awk将csv文件作为awk脚本处理。@masiboo:对此脚本,请使用:
awk-f sql.awk data.csv data
其中
sql.awk
是我在回答中包含的脚本。
cat sql.awk

BEGIN {
  FS=";"
  OFS=","
  quotation="'"
  tableName=ARGV[2]
  ARGC--
}
FNR==1 {
    $1 = $1
    head = $0
    next
}
{
  dat = ""
  for(i=1; i<=NF; i++) {
      val = ($i~/[[:alpha:]]$/) ? quotation $i quotation : $i
      dat = (dat != "") ? dat OFS val : val
  }
  printf("INSERT INTO %s ( %s ) VALUES ( %s );\n", tableName, head, dat)
}
END {
    printf("\n-- Generated by %s at %s\n", ENVIRON["USER"], strftime("%Y-%m-%d %T"))
}
awk -f sql.awk data.csv DATA