Namespaces

Variants
Actions

Please note that as of October 24, 2014, the Nokia Developer Wiki will no longer be accepting user contributions, including new entries, edits and comments, as we begin transitioning to our new home, in the Windows Phone Development Wiki. We plan to move over the majority of the existing entries over the next few weeks. Thanks for all your past and future contributions.

How to Export User's Data to CSV

From Wiki
Jump to: navigation, search

This article explains a method for exporting user data to CSV. Specifically, this method will serialize a custom class to CSV format and output to a file.

Template:ArticleMetaData v1.0

Contents

Introduction

Many apps require data input from the user. For example, diet trackers require users to enter daily nutritional intake. The programmer may choose to save this data in an online database, a local SQLite database, an XML file, or sometime within the app's settings container. However, these storage methods are not user-friendly. First, the user does not have direct access to this repository of data. Second, the formats are usually not suitable for transfer to any other application, whether on the phone or the desktop. This article will present a method in which data contained within a class can be serialized into comma-separated value (CSV) format. CSV files can be opened and read using any text editor, analyzed with any spreadsheet application, and imported into a variety of other applications (such as other databases).

Create a Custom Attribute

First, there must be some method by which the compiler will recognize that a class property can be serialized into a CSV file. This is done by creating a custom Attribute. Create a class called CSVAttribute with a base class of System.Attribute and a default constructor. The attribute you will use in your class to be serialized is just "CSV". The "Attribute" portion of the name is ignored. The AttributeUsage attribute attached to the CSVAttribute class itself just tells the compiler that we will be attaching our custom attribute to properties only (not classes or anything else).

    [AttributeUsage(AttributeTargets.Property)]
public class CSVAttribute : System.Attribute
{
public CSVAttribute() { }
}

Preparing Your Classes for Serialization

For the purposes of this article, the following class is an example only. Any class that contains properties can be substituted for the class below. The model below is what you might need for an app that records a user's weight daily. In this hypothetical app, each entry by the user would create a date value, weight value, an optional user comment, and an index value.

public class WeightItemModel
{
public DateTime Date {get;set;}
public double Weight {get;set;}
public string JournalEntry {get;set;}
public int Index {get;set;}
}

In order to serialize this model, the CSV attribute that was just created must be added to the properties that are to be included in the CSV file. For this hypothetical, the Date, Weight, and JournalEntry will be serialized.Index will be ignored. Add the attribute tag in brackets on top of each property to be serialized.

public class WeightItemModel
{
[CSV]
public DateTime Date {get;set;}
[CSV]
public double Weight {get;set;}
[CSV]
public string JournalEntry {get;set;}
public int Index {get;set;}
}

Initiating Serialization to CSV

At this point, the app has several instances of the WeightItemModel in memory, each containing unique data. In order to serialize them to CSV, reflection will be used to inspect the properties of the WeightItemModel class to determine which properties need to be serialized.

The sample code below assumes all of the WeightItemModel instances are in a list of some type that inherits IEnumerable. The sample code also outputs a StorageFile as the end result. Only the result of the StringBuilder is necessary for this method.

Note.pngNote: You will need a using statement for System.Linq for the Linq operations and System.Reflection for the reflection operations. All others can be added using VS2013's Resolve function. Right-click on an class name and select "Resolve" to find and add the namespace automatically.


async Task<StorageFile> GetWeightsCSV(IEnumerable<WeightItemModel> weights)
{
var build = new StringBuilder();
 
//Get a list of properties from WeightItemModel class that are tagged with the CSV Attribute
var properties = typeof(WeightItemModel).GetRuntimeProperties().Where(x => x.GetCustomAttribute(typeof(CSVAttribute)) != null);
var isNewLine = true;
 
//Create the headers for the CSV file using the property names
foreach (var property in properties)
{
build.Append((isNewLine ? "" : ",") + property.Name);
isNewLine = false;
}
build.Append("\n");
isNewLine = true;
 
//Iterate through each WeightItemModel instance
foreach (var item in weights)
{
//Get the value of each property marked with the CSV attribute
foreach (var property in properties)
{
var val = property.GetValue(item);
//If starting with a new instance, do not add a comma first. If value is a string type, put quotation marks around it.
build.Append((isNewLine ? "" : ",") + (val is string ? "\"" + val + "\"" : val));
isNewLine = false;
}
build.Append("\n");
isNewLine = true;
}
 
var result = build.ToString();
 
//Write the output of the StringBuilder to a StorageFile and return it.
var tempFile = await ApplicationData.Current.TemporaryFolder.CreateFileAsync("WeightsData.csv", CreationCollisionOption.ReplaceExisting);
using (var inputStream = await tempFile.OpenAsync(FileAccessMode.ReadWrite))
{
using (var writeStream = inputStream.GetOutputStreamAt(0))
{
DataWriter writer = new DataWriter(writeStream);
writer.WriteString(result);
await writer.StoreAsync();
writer.Dispose();
}
}
return tempFile;
}

Warning.pngWarning: This code will not work on Windows Phone Silverlight projects (WP7 and WP8). To make it compatible for WP8, change the location of the temporary StorageFile from ApplicationData.Current.TemporaryFolder to ApplicationData.Current.LocalFolder.

Note.pngNote: This code will only work with data types that can be output as strings. If you have a more complex type that you wish to serialize to CSV, consider making a new property whose only function is to get a string data-type from your more complex type. Apply the CSV attribute to the new type and remove it from the old, complex type.

Summary

The preceding code is a simple method for serializing a class to CSV format. This data can now be sent via email as an attachment or plain text, can be shared with other app expecting CSV data, or any number of options.

Version Hint

Windows Phone: [[Category:Windows Phone]]
[[Category:Windows Phone 7.5]]
[[Category:Windows Phone 8]]

Nokia Asha: [[Category:Nokia Asha]]
[[Category:Nokia Asha Platform 1.0]]

Series 40: [[Category:Series 40]]
[[Category:Series 40 1st Edition]] [[Category:Series 40 2nd Edition]]
[[Category:Series 40 3rd Edition (initial release)]] [[Category:Series 40 3rd Edition FP1]] [[Category:Series 40 3rd Edition FP2]]
[[Category:Series 40 5th Edition (initial release)]] [[Category:Series 40 5th Edition FP1]]
[[Category:Series 40 6th Edition (initial release)]] [[Category:Series 40 6th Edition FP1]] [[Category:Series 40 Developer Platform 1.0]] [[Category:Series 40 Developer Platform 1.1]] [[Category:Series 40 Developer Platform 2.0]]

Symbian: [[Category:Symbian]]
[[Category:S60 1st Edition]] [[Category:S60 2nd Edition (initial release)]] [[Category:S60 2nd Edition FP1]] [[Category:S60 2nd Edition FP2]] [[Category:S60 2nd Edition FP3]]
[[Category:S60 3rd Edition (initial release)]] [[Category:S60 3rd Edition FP1]] [[Category:S60 3rd Edition FP2]]
[[Category:S60 5th Edition]]
[[Category:Symbian^3]] [[Category:Symbian Anna]] [[Category:Nokia Belle]]

This page was last modified on 24 August 2014, at 18:22.
1137 page views in the last 30 days.

Was this page helpful?

Your feedback about this content is important. Let us know what you think.

 

Thank you!

We appreciate your feedback.

×