Local JSReport instance producing a corrupted excel file
-
Greetings. I am trying to generate an excel file from an existing excel template using the xlsx recipe and handlebars engine. This file is created with no issue in JSREport studio on our server instance. However, when running the same request locally, I get a corrupt file. Specifically, the excel file returned is missing the sharedStrings.xml file.
Excel offers to recover the content and can do so successfully. After doing so, I notice that the sharedStrings.xml file is created. I assume based on this that the lack of this file causes the corruption in the first place.
I can't see any reason why I would be getting an issue locally. This occurs with any version of the JSReport binary. However, it doesn't occur at all on a server. I use the same content and template on both.
I have tried it out on the playground and confirmed that it works. https://playground.jsreport.net/w/anon/H0EjR6M9 The issue seems to only occur locally.
The command I run is
./jsreport.exe render -r "request.json" --template.xlsx.template=$base64String --template.content="content.html" --template.helpers="helpers.js" -o "test.xlsx"
where $base64String is produced by
$base64String = [Convert]::ToBase64String([IO.File]::ReadAllBytes("[FILE_PATH_HERE]"))
The issue occurs even on the most simple content like
{{{xlsxPrint}}}
.Note that while I am posting a CLI example, I am actually generating the report in a .net application, however the exact same thing occurs (corrupt excel file).
Does anyone know why the results between 2 JSreport instances would be different? Could this be related to the missing sharedString.xml file that is removed from the intial .xlsx template? I can provide additional info if needed. Thank you
-
I've tried to replicate this but it seems to work for me. Excel doesn't complain about the result.
The .net code
var rs = new LocalReporting() .KillRunningJsReportProcesses() .UseBinary(JsReportBinary.GetBinary()) .AsUtility() .Create(); var report = await rs.RenderAsync(new RenderRequest { Template = new Template { Content = "{{{xlsxPrint}}}", Engine = Engine.Handlebars, Recipe = Recipe.Xlsx, Xlsx = new Xlsx { TemplateAsset = new Asset { Content = Convert.ToBase64String(File.ReadAllBytes("AssetExportTemplate.xlsx")), Encoding = "base64" } } } }); report.Content.CopyTo(File.OpenWrite("report.xlsx")); Console.WriteLine("Done, hit any key..."); Console.ReadKey();
The output report.xlsx
Could you try the output? If it works also the code I shared?
-
Wow, well that really did help. Your code works and was configured exactly how we have it configured.
As it turns out, I was relying on already existing code in our codebase that converted the file to a stream. My bone-headed mistake was thinking that this code produced a base64 string. It did not. I noticed after going into the debug view of your code and noticing that the string value for the asset was very different from the value in my application.
Making sure the asset got converted to base64, as well as using the
TemplateAsset= new Asset
in your example produced a working file. What's really threw me off JsReport was still able to manipulate the template and create a new file despite the original not being in the correct format. Very unexpected.Anyway, thank you for taking the time to help. Very much appreciated.