I am trying to use csv helper libary to parse my csv. But I am having an issue it says that the itemcode does not exist when its there in the file.
// Adding stock item code
Sage.Accounting.Stock.StockItem stockItem = new Sage.Accounting.Stock.StockItem();
string line = null;
public void ImportCsv(string filename)
{
TextReader reader = File.OpenText(filename);
var csv = new CsvReader(reader);
csv.Configuration.HasHeaderRecord = true;
csv.Read();
// Dynamic
// Using anonymous type for the class definition
var anonymousTypeDefinition = new
{
Itemcode = string.Empty,
Barcode = string.Empty
};
var records = csv.GetRecords(anonymousTypeDefinition);
}
This is the csv structure
"Itemcode","Barcode","description"
"P4S100001","303300054486","Test Product"
This is my first time using the csvhelper as showing here at https://joshclose.github.io/CsvHelper/
You are better off creating a strongly typed model to hold the data if one does not already exist
public class Item {
public string Itemcode { get; set; }
public string Barcode { get; set; }
public string description { get; set; }
}
and using GetRecords<T>() to read the records by type
TextReader reader = File.OpenText(filename);
var csv = new CsvReader(reader);
var records = csv.GetRecords<Item>();
Your GetRecords function needs a type specifier like so:
var records = csv.GetRecords<type>();
Also you may want to put csv.Read() in a while loop depending on your need.
Since all your values have quotes you need to specify it in the config. Working with quotes in csvHelper is frustrating. if not all if the values have quotes there are ways to handle that as well but not as nicely as this
var csv = new CsvReader(reader,new CsvHelper.Configuration.Configuration
{
HasHeaderRecord = true,
QuoteAllFields = true
});
var anonymousTypeDefinition = new
{
Itemcode = string.Empty,
Barcode = string.Empty
};
var records = csv.GetRecords(anonymousTypeDefinition);
I am trying to deserialize a local file in my project which is a json file. However I am getting this error with the current code:
"Unexpected character encountered while parsing value: G. Path '', line 0, position 0"
C# code
string filepath = Application.StartupPath + #"\city.list.json";
for(int i = 0; i< 40; i++)
{
foreach (string x in File.ReadLines(filepath))
{
if(x.Contains("id") || x.Contains("name"))
{
var data = JsonConvert.DeserializeObject<City.values>(filepath);
//City city = JsonConvert.DeserializeObject<City>(File.ReadAllText(filepath));
//cityList.Add(data.name, data.id);
}
else
{
}
}
}
class City
{
[JsonObject(MemberSerialization = MemberSerialization.OptIn)]
public class values
{
[JsonProperty(PropertyName = "id")]
public string id { get; set; }
[JsonProperty(PropertyName = "name")]
public string name { get; set; }
}
}
Json file I am trying to deserialize from. This is just a quick sample taken out from the file. It is quite large ^^
[
{
"id":707860,
"name":"Hurzuf",
"country":"UA",
"coord":{
"lon":34.283333,
"lat":44.549999
}
},
{
"id":519188,
"name":"Novinki",
"country":"RU",
"coord":{
"lon":37.666668,
"lat":55.683334
}
},
You seem to have some huge misconceptions of how JSON deserializing works. First thing to address is you shouldn't be iterating through the lines of the json file. As pointed out in the comments, your JSON file is very large (~1.8 million lines) so your best bet is to use the JsonReader overload of DeserializeObject(), see Json.NET performance tips:
List<City.values> cities = new List<City.values>();
string filepath = Application.StartupPath + #"\city.list.json";
using (StreamReader sr = new StreamReader(filepath))
using (JsonReader reader = new JsonTextReader(sr))
{
JsonSerializer serializer = new JsonSerializer();
// read the json from a stream
// json size doesn't matter because only a small piece is read at a time from the HTTP request
cities = JsonConvert.DeserializeObject<List<City.values>>(reader);
}
Draw your attention to this line:
cities = JsonConvert.DeserializeObject<List<City.values>>(reader);
Here we leverage JSON.NET to deserialize. The difference between your code and the code I included here is that your JSON is a collection of objects, what this means is you need to deserialize into a collection of your City.values objects, in this case I used a List<T>.
Now we have a variable cities that is a collection of City.values objects that are included in your JSON.
I am trying to parse a json and populate these values into an object with DataContractJsonSerializer. Having no luck with this yet.
The json is -
{
"0": [
547,
541,
507,
548,
519,
0
],
"1": [
573,
504
]
}
I have tried the following code:
try
{
string json = #"""0"":[547,541,507,548,519,0],""1"":[573,504]";
using (var memStream = new MemoryStream(Encoding.UTF8.GetBytes(json)))
{
var seraializer = new DataContractSerializer(typeof(MyClass));
var jsonParsed = seraializer.ReadObject(memStream);
}
}
catch(Exception ex)
{
}
Always getting an exception that the data is invalid at the root. But online json validators say this is a valid json.
MyClass -
[DataContract]
public class MyClass
{
[DataMember]
public Dictionary<string, List<int>> values { get; set; }
}
Thanks Patrick for providing me a working solution with Newtonsoft. But just to learn , I want to see what am I doing wrong with DataContractJsonSerializer. The code below gives me no exception, but I am not getting any values after the parsing is complete.
string json = #"{""0"":[547,541,507,548,519,0],""1"":[573,504]}";
using (var memStream = new MemoryStream(Encoding.UTF8.GetBytes(json)))
{
var seraializer = new DataContractJsonSerializer(typeof(Dictionary<string, List<int>>));
var jsonParsed = seraializer.ReadObject(memStream);
}
You should use Dictionary<string, List<int>> as the type to deserialize to. You also need to use the right serializer (DataContractSerializer is for XML, DataContractJsonSerializer for JSON):
var seraializer = new DataContractJsonSerializer(typeof(Dictionary<string, List<int>>), new DataContractJsonSerializerSettings() { UseSimpleDictionaryFormat = true });
var jsonParsed = seraializer.ReadObject(memStream);
Or for JSON.NET:
var x = JsonConvert.DeserializeObject<Dictionary<string, List<int>>>(json);
I have been looking at a few posts on SO about how to deserialize a date in a json string.
The posts mention doing a replace on the string to reformat the Date parts.
the json string looks like this:
"/Date(1336258800000)/\"
apparently what I need to get to is this:
"new Date(1336258800000)"
The trouble is as soon as I try and to a replace, or indexOf ')/\' it doesnt find the string to replace (indexOf is -1)
can anyone see what im doing wrong?
JavaScriptSerializer jss = new JavaScriptSerializer();
//Fix an issue with Json Dates
string json = eventArgument.Replace( #"/Date(", "new Date(" ).Replace( #")/\", ")" );
int index = json.IndexOf( #")/\", 0 );
WorkPattern wp = jss.DeserializeObject( json ) as WorkPattern;
here is the full json string:
"{\"WorkPatternDays\":[{\"WorkPatternDayShifts\":[{\"WorkPatternDayShiftRates\":[{\"Duration\":8.5,\"Sequence\":0,\"WorkPatternDayShiftID\":186,\"WorkPatternDayShiftRateID\":105,\"Deleted\":false,\"UpdatedUser\":\"\",\"UpdatedDate\":\"/Date(1336258800000)/\"}],\"WorkPatternDayShiftBreaks\":[{\"PaidBreak\":true,\"Duration\":1,\"EndTime\":\"/Date(1336050000000)/\",\"StartTime\":\"/Date(1336046400000)/\",\"WorkPatternDayShiftID\":186,\"WorkPatternDayShiftBreakID\":284,\"Deleted\":false,\"UpdatedUser\":\"\",\"UpdatedDate\":\"/Date(1336258800000)/\"},{\"PaidBreak\":false,\"Duration\":0.25,\"EndTime\":\"/Date(1336058100000)/\",\"StartTime\":\"/Date(1336057200000)/\",\"WorkPatternDayShiftID\":186,\"WorkPatternDayShiftBreakID\":285,\"Deleted\":false,\"UpdatedUser\":\"\",\"UpdatedDate\":\"/Date(1336258800000)/\"}],\"Duration\":8.5,\"EndTime\":\"/Date(1336062600000)/\",\"StartTime\":\"/Date(1336032000000)/\",\"WorkPatternDayID\":186,\"WorkPatternDayShiftID\":186,\"Deleted\":false,\"UpdatedUser\":\"\",\"UpdatedDate\":\"/Date(1336258800000)/\"}],\"DayOfWeek\":1,\"DayOfWeekNumber\":1,\"WorkPatternID\":105,\"WorkPatternDayID\":186,\"Deleted\":false,\"UpdatedUser\":\"\",\"UpdatedDate\":\"/Date(1336258800000)/\"},{\"WorkPatternDayShifts\":[{\"WorkPatternDayShiftRates\":[],\"WorkPatternDayShiftBreaks\":[{\"PaidBreak\":true,\"Duration\":0.5,\"EndTime\":\"/Date(1336041000000)/\",\"StartTime\":\"/Date(1336039200000)/\",\"WorkPatternDayShiftID\":187,\"WorkPatternDayShiftBreakID\":286,\"Deleted\":false,\"UpdatedUser\":\"\",\"UpdatedDate\":\"/Date(1336258800000)/\"}],\"Duration\":5.5,\"EndTime\":\"/Date(1336046400000)/\",\"StartTime\":\"/Date(1336026600000)/\",\"WorkPatternDayID\":187,\"WorkPatternDayShiftID\":187,\"Deleted\":false,\"UpdatedUser\":\"\",\"UpdatedDate\":\"/Date(1336258800000)/\"}],\"DayOfWeek\":3,\"DayOfWeekNumber\":3,\"WorkPatternID\":105,\"WorkPatternDayID\":187,\"Deleted\":false,\"UpdatedUser\":\"\",\"UpdatedDate\":\"/Date(1336258800000)/\"}],\"WorkPatternName\":\"Naths Test Work Pattern\",\"WorkPatternID\":105,\"Deleted\":false,\"UpdatedUser\":\"\",\"UpdatedDate\":\"/Date(1336258800000)/\"}"
A bit more info to see how it all fits together:
code behind:
public override void DataBind()
{
try
{
if ( this.WorkPattern != null )
{
//Create a javascript serializer
JavaScriptSerializer jss = new JavaScriptSerializer();
//Get the serialised object as a json string
string json = jss.Serialize( this.WorkPattern );
//Run the jquery code
base.RunjQueryCode(
String.Format( "loadWorkPattern({0});", json ) );
jss = null;
}
}
catch ( Exception )
{
throw;
}
}
protected override void HandlePostbacks( string eventTarget, string eventArgument )
{
try
{
switch ( eventTarget )
{
case "Save":
JavaScriptSerializer jss = new JavaScriptSerializer();
//Fix an issue with Json Dates
string json = eventArgument.Replace( #"/Date(", "new Date(" ).Replace( #")/\", ")" );
int index = json.IndexOf( #")/\\", 0 );
WorkPattern wp = jss.DeserializeObject( json ) as WorkPattern;
object o = jss.Deserialize<WorkPattern>( json );
break;
default: break;
}
base.HandlePostbacks( eventTarget, eventArgument );
}
catch ( Exception )
{
throw;
}
}
Markup / js:
function loadWorkPattern(jsonData) {
//Store the work pattern
_workPattern = jsonData;
//Loop through the work pattern days
$.each(_workPattern.WorkPatternDays, function (key, workPatternDay) {
//Loop through each shift
$.each(workPatternDay.WorkPatternDayShifts, function (key, workPatternShift) {
addShift(workPatternShift, workPatternDay.DayOfWeekNumber);
//Loop through each break
$.each(workPatternShift.WorkPatternDayShiftBreaks, function (key, workPatternDayShiftBreak) {
addBreak(workPatternDayShiftBreak);
});
});
});
}
function saveWorkPattern() {
__doPostBack('Save', JSON.stringify(_workPattern));
}
Im calling JSON.stringify to serialize the serialize the stored object before sending back to the server, is this what im doing wrong?
UPDATE
This is the working code:
string json = eventArgument.Replace( #"/Date(", "\\/Date(" ).Replace( #")/", ")\\/" );
Try int index = json.IndexOf( #")/\\", 0 ); - put another slash before the slash
Update
JavaScriptSerializer s = new JavaScriptSerializer();
string date = s.Serialize(DateTime.Now);
int index = date.IndexOf(#")\/", 0);
Console.WriteLine(index); // index = 21
Update - solution
The problem is the the initial string is /Date(1336258800000)/, but not /Date(1336258800000)/\ as the last slash is an escape of the " character in the JSON.
And the format for the desiarization should be dirrerent, so the working solution is
string json = eventArgument.Replace( #"/Date(", "\\/Date(" ).Replace( #")/", ")\\/" );
I used regular expressions, hope that's not a problem. The regex detect the /Date(NUMBER)/\ and gets the NUMBER as a group in the regular expression match so I use that to replace everything in the dateTimeJson that matches the regex specified in its constructor with new Date(NUMBER).
//the source JSON
string dateTimeJson = "/Date(1336258800000)/\\";
string result = "";
//you might want to do a quick IndexOf("Date") to make sure that there is a date
//so you won't trouble yourselve with regex computation unnecessarily. performance?
//find Date(NUMBER) matches and get the NUMBER then use it again with new Date in the
//call to replace
System.Text.RegularExpressions.MatchCollection matches = null;
System.Text.RegularExpressions.Regex regex = null;
try
{
//at the end is one forwared slash for regex escaping \ and another is the \ that is escaped
regex = new System.Text.RegularExpressions.Regex(#"/Date\(([0-9]*)\)/\\");
matches = regex.Matches(dateTimeJson);
string dateNumber = matches[0].Groups[1].Value;
result = regex.Replace(dateTimeJson, "new Date(" + dateNumber + ")");
}
catch (Exception iii)
{
//MessageBox.Show(iii.ToString());
}
MessageBox.Show(result);
I use jsonconvert to convert simple objects to json like
JsonConvert.SerializeObject(new { label = "MyLabel1" });
to
{ "label":"MyLabel1" }
but i want to get the keys without quotation like
{ label: "MyLabel1"}
is there a way to convert objects to json withoud "key"-quotations by using jsonconvert?
Any library that expects JSON or actual JavaScript notation for creating objects (which is a superset of JSON) should work fine with quotes.
But if you really want to remove them, you can set JsonTextWriter.QuoteName to false. Doing this requires writing some code that JsonConvert.SerializeObject() uses by hand:
private static string SerializeWithoutQuote(object value)
{
var serializer = JsonSerializer.Create(null);
var stringWriter = new StringWriter();
using (var jsonWriter = new JsonTextWriter(stringWriter))
{
jsonWriter.QuoteName = false;
serializer.Serialize(jsonWriter, value);
return stringWriter.ToString();
}
}
I complement answer #svick. For save format you need use StringBuilder for StringWriter.
static string SerializeWithoutQuote(object value)
{
var builder = new StringBuilder();
var serializer = JsonSerializer.Create();
var stringWriter = new StringWriter(builder);
using (var jsonWriter = new JsonTextWriter(stringWriter))
{
jsonWriter.Formatting = Formatting.Indented;
jsonWriter.QuoteName = false;
serializer.Serialize(jsonWriter, value);
return builder.ToString();
}
}