How to Display DataTable as output in rest service in XML FORMAT - c#

How to Display Data Table as output in rest service in XML FORMAT

DataTable has a method WriteXml that contains many overloaded versions. One of them is DataTable.WriteXml(string). You can use this to save the contents of DataTable as an XML file. The other option you can use is the overloaded method that writes to Stream object. You can use either FileStream, MemoryStream or similar.
Any of the overloaded methods contains a version with XmlWriterMode argument that allows you to specify whether you want to write schema or ignore it.

Related

How do I append to a CSV file using Filehelpers with multiple record types that have distinct headers?

As the question says, using the FileHelpers library I am attempting to generate a CSV file along side a report file. The report file may have different (but finite) inputs/data structures and hence my CSV generation method is not explicitly typed. The CSV contains all of the report data as well as the report's header information. For my headers, I am using the class object properties because they are descriptive enough for my end use purpose.
My relevant code snippet is below:
// File location, where the .csv goes and gets stored.
string filePath = Path.Combine(destPath, fileName);
// First, write report header details based on header list
Type type = DetermineListType(headerValues);
var headerEngine = new FileHelperEngine(type);
headerEngine.HeaderText = headerEngine.GetFileHeader();
headerEngine.WriteFile(filePath, (IEnumerable<object>)headerValues);
// Next, append the report data below the report header data.
type = DetermineListType(reportData);
var reportDataEngine = new FileHelperEngine(type);
reportDataEngine.HeaderText = reportDataEngine.GetFileHeader();
reportDataEngine.AppendToFile(filePath, (IEnumerable<object>)reportData);
When this is executed, the CSV is successfully generated however the .AppendToFile() method does not add the reportDataEngine.HeaderText. From the documentation I do not see this functionality to .AppendToFile() and I am wondering if anyone has a known work-around for this or a suggestion how to output the headers of two different class objects in a single CSV file using FileHelpers.
The desired output would look something like this however in a single CSV file (This would be a contiguous CSV obviously; not tables)
Report_Name
Operator
Timestamp
Access Report
User1
14:50:12 28 Dec 2020
UserID
Login_Time
Logout_Time
User4
09:33:23
10:45:34
User2
11:32:11
11:44:11
User4
15:14:22
16:31:09
User1
18:55:32
19:10:10
I have looked also at the MultiRecordEngine in FileHelpers and while I think this may be helpful, I cannot figure out based on the examples how to actually write a multirecord CSV file in the required fashion I have above; if it is possible at all.
Thank you!
The best way is to merge the columns and make one big table then make your classes match the columns you need to separate them out when reading. CSV only allows for the first row to define the column names and that is optional based on your use case. Look at CSVHelper https://joshclose.github.io/CsvHelper/ it has a lot of built-in features with lots of examples. Let me know if you need additional help.

Create Excel Data Table in ClosedXML C# from existing Data

I am trying to convert the data I already have in a Worksheet in to a DataTable using ClosedXML but I cannot find an overload method for what I need.
This is the code that I am trying:
NewWorksheet.Cell(1, 1).InsertTable();
The closest overload method is the single with an IEnumerable or DataTable but what would I put in there? There is no overload method that takes a range.
Here is the documentation page but nothing meets my need.
InsertTable inserts an existing DataTable into the spreadsheet. You want to do the reverse. That's not possible in ClosedXML.

Define dateTime format in xsd

At my work we load excel files and save them in the database.
This is basically the flow:
We import data into a DataSet from an Excel file, where each sheet is loaded into its own DataTable inside the DataSet. After populating the DataDet, i want to validate the data inside the DataSet, let's say the first DataTable. I get xml from the DataTable by using WriteXml() method of the DataTable class and load this xml into an XDocument. I then use the Validate() method of the XDocument class with a predefined xsd, which is loaded into a XmlSchemaSet object.
The problem is that the data in the excel is stored in a format that is different from the format of dateTime in xsd.
We get Excel files with datetime columns formatted like thie: '12/01/2015 12:44:45', whereas the dateTime format in xsd should be like this: '2015-01-12T12:44:45'
Is it possible to define custom dateTime format in an xsd file?
For example, instead of '2015-01-12T12:44:45', I would like it to be '12/01/2015 12:44:45', so my xml element would look like this:
<createDate>12/01/2015 12:44:45>/createDate>
In addition, i wouldn't mind if the time part would be ignored altogether.
In addition, another custom xsd format i need is like this: 378,216.00
Is it possible to define it in my xsd file?
Here is this code where we do the validation of the xml, retrieved from the datatable
public string[] ValidateExcelFromXsdFile(string schemaUri)
{
_validationErrors.Clear();
var schemas = new XmlSchemaSet();
schemas.Add("", schemaUri);
var doc = XDocument.Parse(GetXml(_dataSetFromExcel.Tables[0]));
doc.Validate(schemas, (sender, args) => _validationErrors.Add(args.Message));
return _validationErrors.ToArray();
}
You can define a pattern for strings in the format 'dd/mm/yyyy hh:mm:ss' using a regular expression, but the resulting value won't be an xs:dateTime, and checking for full validity (leap years etc) is a bit of a nightmare (it can be done, but leads to a regular expression that's about a mile long).
A better solution here might the transform-then-validate pattern, where you preprocess the input document (into standard XSD format) before validating it. You can even do some of the validation during the preprocessing phase if you choose.
The Saxon schema processor has an preprocess facet which allows you to declare some rearrangement of a value prior to schema processing, which is exactly what you need here (for both your use cases), but unfortunately it's not standard.
Check this site - there you have DateTime data type http://www.w3schools.com/schema/schema_dtypes_date.asp
Also Date and Time Data Types paragraph will allows you to adjust the rule to your needs.

Read Data into IDataReader from TestContext

This might sound strange but exactly this is what I want to do:
I have a TestMehod Currency_ReadItem_Test() which tests ReadItem() method in Currency class. This ReadItem() takes IDataReader object as an parameter and fills local data members in the class.
Now the problem is I want to test this ReadItem() in my TestMethod which has a Excel Sheet DataSource.
Any idea how can I first fill my Reader from Excel sheet so that it can be passed to this function in oder to test it?
Any help would be appreciated.
Thanks
One way is to read the spreadsheet via ADO.NET - then you just use ExecuteReader for some query you define.
Alternatively, you could use the Excel API and load the data you want into a DataTable, and then use a DataTableReader. Or if you don't like DataTable and you know for sure the schema of the data (i.e. fixed and rigid) you could also populate a List<SomeType> and use ObjectReader from "FastMember" (open source)

XML tag name being overwritten with a type defined

We are communicating with a 3rd party service using via an XML file based on standards that this 3rd party developed. They give us an XML template for each "transaction" and we read it into a DataSet using System.Data.DataSet.ReadXML, set the proper values in the DataSet, and then write the XML back using System.Data.DataSet.WriteXML. This process has worked for several different files. However, I am now adding an additional file which requires that an integer data type be set on one of the fields. Here is a scaled down version:
<EngineDocList>
<DocVersion>1.0</DocVersion>
<EngineDoc>
<MyData>
<FieldA></FieldA>
<FieldB></FieldB>
<ClientID DataType="S32"></ClientID>
</MyData>
</EngineDoc>
</EngineDocList>
When I look at the DataSet created by my call to ReadXML to this file, the MyData table has columns of FieldA, FieldB, and MyData_ID. If I then set the value of MyData_ID and then make the call to WriteXML, the export XML has no value for ClientID. Once again, if I take a way the DataType, then I do have a ClientID column, I can set it properly, and the exported XML has the proper value. However, the third party requires that this data type be defined.
Any thoughts on why the ReadXML would be renaming this tag or how I could otherwise get this process to work? Alternatively, I could revamp the way we are reading and writing the XML, but would obviously rather not go down this path although these suggestions would also be welcome. Thanks.
I would not do this with a DataSet. It has a specific focus on simulating a relational model. Much XML will not follow that model. When the DataSet sees things that don't match it's idea of the world, it either ignores them or changes them. In neither case is it a good thing.
I'd use an XmlDocument for this.

Categories