使用 shell 将值粘贴到 xlsx

pasting a value to xlsx using shell

我有一个 xlsx 格式的模板文件,我想在一个特定的单元格中粘贴一个动态值,即根据程序流程,该单元格中的值将发生变化,这反过来又会改变 xlsx 文件中的条件以获得不同的过程。

我试过像

这样的代码
awk -v value=$value -v row=$row -v col=$col 'BEGIN{FS=OFS="@"} NR==row {$col=value}1' file.csv 

但问题是我无法将此代码用于 xlsx 文件格式。有什么方法可以对 xlsx 文件格式执行此操作,因为它是一个模板文件,我需要保留 xlsx 文件格式。

当我必须从我的 Windows PC 上的 Excel 工作簿中提取值时,我安装了 cygwin,然后编写了一个小的 shell 脚本来执行以下操作:

cygstart "/path/to/xls2csv.vbs" 'C:/cygwin64/path/to/bookName.xlsx'
awk 'whatever' '/path/to/bookName/sheetName.csv'

以及从工作簿中提取每个 sheet 作为单独的 CSV 的工作,该 CSV 的命名基于 sheet 名称,在以工作簿命名的公共目录下以“.csv”为后缀这个视觉基本脚本:

$ cat xls2csv.vbs
csv_format = 6

Dim strFilename
Dim objFSO
Set objFSO = CreateObject("scripting.filesystemobject")
strFilename = objFSO.GetAbsolutePathName(WScript.Arguments(0))
If objFSO.fileexists(strFilename) Then
  Call Writefile(strFilename)
Else
  wscript.echo "no such file!"
  wscript.echo strFilename
End If
Set objFSO = Nothing

Sub Writefile(ByVal strFilename)
Dim objExcel
Dim objWB
Dim objws

Set objExcel = CreateObject("Excel.Application")
Set objWB = objExcel.Workbooks.Open(strFilename)

For Each objws In objWB.Sheets
  objws.Copy
  objExcel.ActiveWorkbook.SaveAs objWB.Path & "\" & objws.Name & ".csv", csv_format
  objExcel.ActiveWorkbook.Close False
Next

objWB.Close False
objExcel.Quit
Set objExcel = Nothing
End Sub

如果文件名或目录名中有空格,该命令将失败,因此我们需要将其替换为下划线。实际上,我通常将 Xls 文件复制到一个临时目录,并在 运行 上面的内容之前给它一个临时名称,这样我就可以 运行 上面的内容而不影响原始文件,而不必关心原始文件的路径。它需要输入 Excel 工作簿的绝对路径。

您可能需要在 awk 命令之前添加 wait and/or sleep 以确保 VB 脚本在 awk 命令之前完成运行秒。我未显示的 shell 代码是对 VB 脚本的复杂测试,创建然后删除 tmp 文件以确保 VB 脚本完成并循环尝试然后杀死 Excel 如果它在调用 awk 之前不启动或挂起 - 我很久以前写的,一团糟,我怀疑它是否真的有必要或一个好的方法,这就是为什么我不在这里包括它。

要将这些值返回到多 sheet 工作簿中,您必须使用 Excel(或 copy/paste)打开任何 updated/generated CSV。可能还有其他一些 VB 脚本可以编写来为您导入 CSV,就像我在上面导出它们一样,但我从来不需要那个功能,所以我知道它看起来像什么。

不过我不知道您是否需要它 - 如果您的 awk 脚本写入 CSV,那么您只需双击输出 .csv 并且 Excel 会很高兴地打开并显示它,就像任何其他文件一样.xls 或 .xlsx Excel 文件。

因此,如果您的原始内容在 "Sheet1" of single-sheet Excel workbook "MyStuff.xlsx" 中,您可以从 cygwin 中执行此操作:

cygstart "/path/to/xls2csv.vbs" 'C:/cygwin64/path/to/MyStuff.xlsx'
wait; sleep 10     # or similar
awk -v value="$value" -v row="$row" -v col="$col" 'BEGIN{FS=OFS=","} NR==row {$col=value}1' '/path/to/MyStuff/Sheet1.csv' > "/tmp/tmp$$" &&
mv "/tmp/tmp$$" '/path/to/MyStuff/Sheet1.csv'

然后在Windows中只需双击/path/to/MyStuff/Sheet1.csv即可在Excel中打开它(您可能需要将.csv文件后缀与Excel相关联你第一次这样做)。

请注意,以上内容仅处理简单的 CSV,请参阅 了解如何使用 awk 稳健地处理 CSV。