Coldfusion CSV到电子表格

Coldfusion CSV到电子表格,csv,coldfusion,cfspreadsheet,coldfusion-2018,Csv,Coldfusion,Cfspreadsheet,Coldfusion 2018,我有几个过程利用CFSpreadsheet标签导入并操作Excel数据。这适用于.XLS和.XLSX文件,但是,如果数据作为.CSV文件发送,则不起作用,因为CFSpreadsheet显然从未更新为导入.CSV文件。在一天结束时,我只需要一个简单的预处理器,它接收一个.CSV文件并将其重新写入一个.XLSX文件,这样我的其他进程就可以从那里接收它 我的环境是Coldfusion 2018的开发者版,我已经尝试手动导入数据(如果我知道所有列定义,这可以工作,但我并不总是知道)。我最近的一次尝试是使

我有几个过程利用CFSpreadsheet标签导入并操作Excel数据。这适用于.XLS和.XLSX文件,但是,如果数据作为.CSV文件发送,则不起作用,因为CFSpreadsheet显然从未更新为导入.CSV文件。在一天结束时,我只需要一个简单的预处理器,它接收一个.CSV文件并将其重新写入一个.XLSX文件,这样我的其他进程就可以从那里接收它

我的环境是Coldfusion 2018的开发者版,我已经尝试手动导入数据(如果我知道所有列定义,这可以工作,但我并不总是知道)。我最近的一次尝试是使用Ben Nadel的CSVToArray函数(),它可以工作——我可以很容易地将.CSV文件放入一个数组中——但我不知道如何从该数组转换为一个查询,我可以使用CFSpreadsheet编写一个电子表格

下面是一个例子:

<!--- This include is the function from Ben Nadel referenced above --->
<cfinclude template="Function_CSVtoArray.cfm"> 

<cfset result = csvToArray(file="TEST_File.csv") />

<cfdump var="#result#" label="TESTING">

<!--- *** The above WORKS up to this point ***--->

<!--- Create a new query. --->
<cfset qPartsTwo = QueryNew( "" ) />

<!--- Loop over keys in the struct. --->
<cfloop index="strKey" list="#StructKeyList(result)#" delimiters=",">

<!--- Add column to new query with default values. --->
<cfset QueryAddColumn(qPartsTwo,strKey,"VARCHAR",objParts[strKey]) />

</cfloop>

<!--- This code FAILS with a "You have attempted to dereference a scalar variable of type class coldfusion.runtime.Array as a structure with members" error message --->

我想以这样的方式结束(尽管现在“result”是某种数组,而不是查询):



任何想法都将不胜感激

我打赌你可以这样做

<cfinclude template="Function_CSVtoArray.cfm"> 

<cfset result = csvToArray(file="TEST_File.csv") />

<cfdump var="#result#" label="TESTING">


<!--- setup the columns that you need --->
<cfset qPartsTwo = queryNew("id,name,amount","Integer,Varchar,Integer", result) />

<cfspreadsheet action="write" filename="<my path>\TEST.xlsx" query="result">


CSVToArray()
看起来像是生成了一个结构数组。

如果您已经从CSVToArray获得了一个结构数组。然后可以使用ArrayOfStructuresToQuery函数:

看起来您的UDF返回的是多维数组,而不是结构数组。与其尝试将数组强制转换为查询对象,不如尝试使用将数组数据写入xlsx文件

演示/样本数据

result = [ ["First Name", "Last Name", "Address"]   
           , ["John", "Doe", "123 Anywhere Ave"]    
           , ["Mary", "Smith", "456 Somewhere Street"]  
           , ["Charles", "Doe", "789 Anywhere Court"]   
];
代码:

// create spreadsheet
xlsx = SpreadSheetNew("The Results", true);
// populate with array data
SpreadSheetAddRows( xlsx, result ); 
// save to file
SpreadSheetWrite( xlsx, "c:/path/to/test.xlsx", true );
。。或者按照建议,您也可以使用:


我认为
可以将CSV目录读入查询。这可能是一个两步操作。谢谢你的回复。这是我第一次尝试,但是当你尝试读取CSV文件时,CFSpreadsheet标签失败了。它显然可以写入CSV文件,但不能读取CSV文件(我知道这是没有意义的)。运行此标记:抛出错误“读取Excel时出错:org.apache.poi.openxml4j.exceptions.InvalidFormatException:您的InputStream既不是OLE2流,也不是OOXML流。”看起来您正在尝试逐列构建查询。逐行考虑。老实说,Apache POI与CF捆绑在一起,为什么不直接使用它呢?代码>createObject(“java”,“org.apache.commons.csv.CSVParser”)是的,我在早期的故障排除中发现了这一点,但我得到了相同的错误消息“您试图将coldfusion.runtime.Array类型的标量变量作为带成员的结构取消引用”。下面是我正在运行的代码:您能在ArrayOfStructuresToQuery函数中进行转储以查看传入的数组参数包含什么吗?仅供参考,我最初在自己的CSV导入中使用了这个函数,出于性能和兼容性的原因,最终转到了Apache CSVManager。实际上,我在早期也尝试过这个功能。它的缺点是我必须明确定义每一列(并且有多个潜在的变化)。但在测试过程中,我得到了错误消息“列名名名无效。列名必须是有效的变量名。它们必须以字母开头,并且只能包含字母、数字和下划线”,因为文件有多个单词的列名(例如“First name”)……虽然方便,但
cfspreadsheet
是有限的。使用电子表格功能可能会更简单,而不是千方百计地让它工作。循环遍历数组并填充每一行。然后你可以定义你想要的任何标题。如果您必须在查询中使用
cfspreadsheet
,则必须先清除潜在的列名,以删除任何无效字符。您太棒了,谢谢!这实际上工作得非常完美,并且完全符合我的要求(获取任何.CSV文件并将其重新写入.XLSX文件);//使用数组数据SpreadSheetAddRows(xlsx,结果)填充;//保存到文件SpreadSheetWrite(xlsx,“c:\temp\TEST.xlsx”,true);很高兴它有帮助!我喜欢它直接从数组if数组到电子表格。我想知道是否可以用电子表格成员函数来完成。
// create spreadsheet
xlsx = SpreadSheetNew("The Results", true);
// populate with array data
SpreadSheetAddRows( xlsx, result ); 
// save to file
SpreadSheetWrite( xlsx, "c:/path/to/test.xlsx", true );
xlsx = SpreadSheetNew("The Results", true);
xlsx.addRows( result );
xlsx.write( "c:/path/to/test.xlsx", true );