2016-05-24 66 views
3

我有一个来自客户端的请求,用于从查询生成Excel电子表格。我有查询踢出的领域,我可以生成Excel文件没有顺利。当客户端接受该Excel文件并尝试操作时,问题就出现了。无法使用ColdFusion创建适当的Excel电子表格

大部分麻烦来自于应标记为货币或日期字段。我有一些挣扎,能够产生一个“真正的”日期字段。在这个Excel没有正确排序日期之前。我可以使用下面的代码来调用Excel公式。 DateValue强制Excel将其确认为真实的日期字段。但是,这个文件通过Excel进行操作时失败。

<cfset SpreadsheetSetCellFormula(s 
      ,"DATEVALUE(#Chr(34)##Replacement_ETD##Chr(34)#)" 
      , therow 
      , 9)> 

接下来的问题是货币字段。我无法让Excel将价值确认为货币。它总是出现习惯。设置此项时,SUM函数在Excel中不起作用。您可以单独添加字段,如A1+B1+C1 = TOTAL。但是,如果有200行,这将不会有帮助。

我能够从另一个CF程序员谁也有类似的情况得到的建议。他首先用正确的标题生成Excel文件,并将列设置为适当的字段,如日期和货币等。

下一步将是逐行填写字段,并且它们应该被正确格式化。

代码:

<cfset filename = expandPath("./reports/arrivals.xlsx")> 
<cfspreadsheet action="read" src = "#filename#" name = "s" > 
<cfset therow = 0> 
<cfoutput query="myExcel" startrow="1"> 
    <cfset therow = myExcel.currentrow + 1> 
    <cfset SpreadsheetSetCellValue(s, Incumbent, therow, 1)> 
    <cfset SpreadsheetSetCellValue(s, Section, therow, 2)> 
    <cfset SpreadsheetSetCellValue(s, Position_Number, therow, 3)> 
    <cfset SpreadsheetSetCellValue(s, Position_Title, therow, 4)> 
    <cfset SpreadsheetSetCellValue(s, Incumbent_Emplyment_Type, therow, 5)> 
    <cfset SpreadsheetSetCellValue(s, Incumbent_ETD, therow, 6)> 
    <cfset SpreadsheetSetCellValue(s, Tour_Comments, therow, 7)> 
    <cfset SpreadsheetSetCellValue(s, Replacement, therow, 8)> 
    <cfset SpreadsheetSetCellValue(s, Replacement_ETA, therow, 9)> 
</cfoutput>  
<cfheader name="content-disposition" value="attachment; filename=Departures_(#DateFormat(now(),'mmddyy')#).xls"> 
<cfcontent type="application/msexcel" variable="#spreadsheetReadBinary(s)#" reset="true"> 

的数据在细胞已经被正确格式化。当此文件生成并流式传输给用户时,列未按预期格式化。

没有任何人知道,如果这个方法将工作或在得到CF产生一个适当的日期和货币领域为Excel承认一个更好的建议?这里RHEL 5

每请求

Adob​​e ColdFusion,请V10跑是使用queryNe瓦特将生成代码日期和货币的一些代码。

步骤一:我创建了第一排冻结Excel文件,它有列标题。第一列已被指定为格式为长日期的日期 - mm/dd/yyy;第二列是已设定为货币的美元。

我读文件,然后填写行和文件流给用户下载。

<cfset filename = expandPath("./reports/Test.xlsx")> 

<cfspreadsheet action="read" src = "#filename#" name = "s" > 

<cfset myQuery = QueryNew("MyDate, Dollar", "Date, Decimal")> 

<cfset newRow = QueryAddRow(MyQuery, 5)> 

<cfset temp = QuerySetCell(myQuery, "MyDate", "03-11-2000", 1)> 
<cfset temp = QuerySetCell(myQuery, "Dollar", "403.45", 1)> 

<cfset temp = QuerySetCell(myQuery, "MyDate", "01-01-2009", 2)> 
<cfset temp = QuerySetCell(myQuery, "Dollar", "603.22", 2)> 

<cfset temp = QuerySetCell(myQuery, "MyDate", "09-21-2013", 3)> 
<cfset temp = QuerySetCell(myQuery, "Dollar", "103.55", 3)> 

<cfset temp = QuerySetCell(myQuery, "MyDate", "01-15-2005", 4)> 
<cfset temp = QuerySetCell(myQuery, "Dollar", "3.33", 4)> 

<cfset temp = QuerySetCell(myQuery, "MyDate", "07-22-2003", 5)> 
<cfset temp = QuerySetCell(myQuery, "Dollar", "13.75", 5)> 

<cfset therow = 0> 
<cfoutput query="myQuery" startrow="1"> 
    <cfset therow = myQuery.currentrow + 1> 

    <cfset SpreadsheetSetCellValue(s, DateFormat(MyDate, 'mm/dd/yyyy'), therow, 1)> 
    <cfset SpreadsheetSetCellValue(s, Dollar, therow, 2)> 
    #myQuery.currentrow# <br> 
    #myQuery.MyDate# <br> 
    #myQuery.Dollar# <br> 
</cfoutput>   

<cfheader name="content-disposition" value="attachment; 
        filename=Departures_(#DateFormat(now(),'mmddyy')#).xls"> 
<cfcontent type="application/msexcel" variable="#spreadsheetReadBinary(s)#" reset="true"> 

您可以在MS Excel或Google表格中打开该文件。测试一个,第一行冻结,我们应该能够在日期字段上排序。我的结果是:日期未正确排序。在货币列2上,如果我们试着去做一个可以工作的SUM!这以前并没有奏效,但现在它已经完成。

此外,当我尝试打开我给出的警告,这文件已损坏,Excel将尝试打开该文件。 Google表格中没有这样的警告。

+0

像“失败”测试工作示例和“行不通”是很暧昧。你可以请提供一个我们可以测试的小型[* stand-alone * example](http://stackoverflow.com/help/mcve),它能证明这个问题?提示,你可以使用'QueryNew()'生成一个手动查询,所以这个例子不需要数据库查询。 – Leigh

+0

@好的东西。我将鞭打起来,举例并编辑帖子。 – weggie

+0

@Leigh代码更新了一个例子和我的测试结果。谢谢。 – weggie

回答

0

使用日期单元格时,CF可能有点古怪。当手动输入值时,Excel很适合猜测正确的单元格类型。但是,这对CF来说有点棘手。由于CF相对无类型,它并不总是正确匹配值和单元格类型。使用利用查询对象而不是SpreadsheetSetCellValue()的函数通常会产生更好的结果。很可能是因为查询对象包含两个值和数据类型。虽然从CF11开始,SpreadsheetSetCellValue支持新的数据参数,它允许您指定值和单元格数据类型。由于您使用的是CF10,因此请尝试使用SpreadsheetAddRows来填充值。

关于文件损坏的警告,是由于下载代码中的实际文件内容和文件扩展名不匹配造成的。该代码正在读取.xlsx文件,但下载声称它是。 xls(application/msexcel)文件。为了摆脱这个错误,确保两个匹配。

这里是CF11

<!--- 
    Test.xlsx contains two columns, with headers on row 1 
    - Column A format: *m/d/yyyy 
    - Column B format: number with 2 decimal places 
---> 
<cfspreadsheet action="read" src="c:/temp/Test.xlsx" name="sheet" > 

<cfset myQuery = QueryNew("")> 
<cfset QueryAddColumn(MyQuery, "Dollar", "Decimal", [ 403.45, 703.22, 103.55, 3.33, 13.75] )> 
<cfset QueryAddColumn(MyQuery, "MyDate", "date", [ parseDateTime("2000-03-11", "yyyy-mm-dd") 
               , parseDateTime("2009-01-01", "yyyy-mm-dd") 
               , parseDateTime("2013-09-21", "yyyy-mm-dd") 
               , parseDateTime("2005-01-15", "yyyy-mm-dd") 
               , parseDateTime("2003-07-22", "yyyy-mm-dd")]) > 

<cfset spreadsheetAddRows(sheet, myQuery)> 
<cfset spreadsheetFormatColumn(sheet, {dataFormat="m/d/yy"}, 1)> 
<cfset spreadsheetFormatColumn(sheet, {dataFormat="##,####0.00"}, 2)> 

<cfheader name="content-disposition" value="attachment; filename=Departures_(#DateFormat(now(),'mmddyy')#).xlsx"> 
<cfcontent type="application/vnd.openxmlformats-officedocument.spreadsheetml.sheet" variable="#spreadsheetReadBinary(sheet)#" reset="true"> 
+0

感谢您的帮助!我可以确认,使用这种方法,所有东西都会“干净”。 – weggie

相关问题