I've been looking through filehelpers documentation, but there doesn't seem anything to handle empty values in columns. I need to be able to set a 'non-empty' string attribute on all the columns.
Can anyone point me in the right direction?
You can perform any validation you want in the AfterReadRecord event. If you want to continue processing the rest of the file if there is an error, you also need to set the ErrorMode to SaveAndContinue. See below for a working example.
[DelimitedRecord("|")]
public class MyClass
{
public string Field1;
public string Field2;
public string Field3;
}
class Program
{
static void Main(string[] args)
{
var engine = new FileHelperEngine<MyClass>();
engine.AfterReadRecord += new FileHelpers.Events.AfterReadHandler<MyClass>(engine_AfterReadRecord);
engine.ErrorMode = ErrorMode.SaveAndContinue;
// import a record with an invalid Email
MyClass[] validRecords = engine.ReadString("Hello||World");
ErrorInfo[] errors = engine.ErrorManager.Errors;
Assert.AreEqual(1, engine.TotalRecords); // 1 record was processed
Assert.AreEqual(0, validRecords.Length); // 0 records were valid
Assert.AreEqual(1, engine.ErrorManager.ErrorCount); // 1 error was found
Assert.That(errors[0].ExceptionInfo.Message == "Field2 is invalid");
}
static void engine_AfterReadRecord(EngineBase engine, FileHelpers.Events.AfterReadEventArgs<MyClass> e)
{
if (String.IsNullOrWhiteSpace(e.Record.Field1))
throw new Exception("Field1 is invalid");
if (String.IsNullOrWhiteSpace(e.Record.Field2))
throw new Exception("Field2 is invalid");
if (String.IsNullOrWhiteSpace(e.Record.Field3))
throw new Exception("Field3 is invalid");
}
}
By default an empty string will be parsed as String.Empty in FileHelpers, but you can override this with a custom converter:
public class EmptyStringConverter : ConverterBase
{
public override object StringToField(string sourceString)
{
if (String.IsNullOrWhiteSpace(sourceString))
return null;
return sourceString;
}
}
Then you define your record class property like this
[FieldConverter(typeof(EmptyStringConverter))]
public string Field1;
If the string corresponding to Field1 is empty or blank, it will be converted to null.
Using a Converter will not work, as FileHelpers.FieldBase checks for a zero length field, and returns Null, before invoking the Converter.
Using the public static FileHelperEngine GetEngine() ensures that the AfterReadRecord event validation is wired up correctly.
[DelimitedRecord(",")]
public class RequiredField
{
public string Required;
public static FileHelperEngine GetEngine()
{
var result = new FileHelperEngine(typeof(RequiredField));
result.AfterReadRecord += AfterReadValidation;
return result;
}
private static void AfterReadValidation(EngineBase sender, AfterReadRecordEventArgs args)
{
if (String.IsNullOrWhiteSpace(((RequiredField)args.Record).Required))
{
throw new ConvertException("RequiredField is Null or WhiteSpace", typeof(String));
}
}
}
I needed the same thing for one of our projects that utilizes FileHelpers heavily and contributed to provide the new FieldNotEmptyAttribute, which could be used like so:
[DelimitedRecord("|")]
public class MyClass
{
[FieldNotEmpty()]
public string Field1;
public string Field2;
[FieldNotEmpty()]
public string Field3;
}
In the example above, if Field1 or Field3 is empty in the source file, then a ConvertException is thrown.
Related
Simply put how do you establish a connection between method variable decloration and connect it with class properties (or inner objects), lets say you have default or hard set values in a class like this (obviously they could be other types but for simplicity its set to strings) :
public class SampleClass
{
public string strA = "Something 1";
public string strB = "Something 2";
public string strC = "Something 3";
}
//think of it as a data layer where strings are pointers to dbSets
How do you leverage the same SampleClass in a method that allows ONLY pick of properties Method(property).
Easy sample that does what its supposed to:
public class ProccessClass
{
private string _dummyOut;
public ProccessClass Pick(string input)
{
this._dummyOut = input;
return this;
}
}
class Program
{
static void Main(string[] args)
{
var Test = new ProccessClass().Pick(new SampleClass().strB);
// we know this works and compiles and returns the strB
}
}
What would you have to convert to ommit the new instantiation and skip the class declaration (if possible but in theory should be doable)
new SampleClass().strB
needs to be just
strB
So how to get the final code to execute??
public class SampleClass
{
public string strA = "Something 1";
public string strB = "Something 2";
public string strC = "Something 3";
}
public class ProccessClass
{
private string _dummyOut;
public ProccessClass Pick(SampleClass sampleClass) //is it the variable declaration?
{
this._dummyOut = input;
return this;
}
}
class Program
{
static void Main(string[] args)
{
string Test = new ProccessClass().Pick(strB);
//so NO new keywords clean and easy set based on class provided above
}
}
Constructor and void setters but no go, the goal is to set the Hard relation ship between the method intake value and setters
I am trying to create a custom attribute in console application but it is not working. My custom attribute never gets called. I found a good example here Custom Attribute not being hit
but not happy with its implementation.
I am wondering how data annotations works in MVC. we don't have to call it separately.
Is MVC calling those data annotations attribute behind the scene?
I wish to create custom attribute that I can use it on any class property same like data annotations attribute. But calling it separately like in above link is not what i am looking.
Here is what I have tried:
using System;
namespace AttributePractice
{
[AttributeUsage(AttributeTargets.Property)]
public class CustomMessageAttribute : Attribute
{
public static readonly CustomMessageAttribute Default = new CustomMessageAttribute();
protected string Message { get; set; }
public CustomMessageAttribute() : this(string.Empty)
{
Console.WriteLine("Default message is empty");
}
public CustomMessageAttribute(string message)
{
Message = message;
}
public string MyMessage =>
Message;
public override bool Equals(object obj)
{
if (obj == this)
return true;
if (obj is CustomMessageAttribute customMessageAttribute)
return customMessageAttribute.Message == MyMessage;
return false;
}
public override int GetHashCode()
{
return MyMessage.GetHashCode();
}
public override bool IsDefaultAttribute()
{
return Equals(Default);
}
}
public class Person
{
//This never works
// I am looking to use this attribute anywhere without calling it
// separately , same like data annotations
[CustomMessage("Hello world")]
public string Name { get; set; }
public int Age { get; set; }
public void DisplayPerson()
{
Console.WriteLine(Name);
Console.WriteLine(Age);
}
}
internal static class Program
{
private static void Main(string[] args)
{
var personObj = new Person
{
Name = "Tom",
Age = 28
};
personObj.DisplayPerson();
}
}
}
Can anybody tell me how to make my custom attribute works like data annotation way?
yes, if you need 10 custom attributes, you should create 10 separate.
public class Program
{
public static void Main(string[] args)
{
var c = check.myValue("Example 1"); //This is the pattern I've to use, don't want to create an object (Is it possible to use it with static class)
Console.WriteLine(c.result1);
Console.WriteLine(c.result2);
}
}
public static class check
{
public static void myValue(string qr)
{
public string result1 = "My Name" + qr;
public string result1 = "You're" + qr;
}
}
See here Online Example (Code is not working)
Every thing on main function I've to use exactly the same pattern because I'll use it in a lot of different classes and I don't want to create object each and every time by using non-static class.
Please correct me if I'm wrong
There's a lot wrong with the syntax of that code, which #Sergey addresses in his answer.
You appear to want to return an instance of a class from a static method, and that class should contain two properties.
You can do that by creating the actual, nonstatic class containing the properties:
public class Check
{
public string Result1 { get; set; }
public string Result2 { get; set; }
}
Then return a new instance from the static method therein:
public static Check MyValue(string qr)
{
var result = new Check();
result.Result1 = "My Name" + qr;
result.Result2 = "You're" + qr;
return result;
}
However, you're saying in the comments in your code that you don't want to use an object.
In that case it appears you want to use static properties. That's generally not recommendable, but it would look like this:
public static class Check
{
public static string Result1 { get; set; }
public static string Result2 { get; set; }
public static void MyValue(string qr)
{
Result1 = "My Name" + qr;
Result2 = "You're" + qr;
}
}
Then you can read Check.Result1 after calling the method MyValue().
Your code is totally wrong
myValue method returns void. You cannot assign void return value to variable.
You cannot have public modifiers for local variables.
You cannot have local variables with same name in same scope
If you want to return two values from method, then you should return object with two fields - custom class or tuple. You can also use out parameters, but I don't think it's your case
public static class Check
{
public static Tuple<string, string> MyValue(string qr)
{
return Tuple.Create($"My Name {qr}", $"You're {qr}");
}
}
With C# 7 it's a little bit better. You can write this method in one line and provide names for tuple properties
(string MyName, string YourName) MyValue(string qr) => ($"My Name {qr}", $"You're {qr}");
Usage
var result = Check.MyValue("Example 1");
Console.WriteLine(result.Item1); // result.MyName
Console.WriteLine(result.Item2); // result.YourName
You can practice with creating custom class with nicely named properties instead of using tuples.
I'm about to design a class that more often then not will contain a reference to a Null value. It reminded me of nullable Datetime which has a boolean value to indicate if there is an actual value stored.
DateTime? dt = new DateTime?();
if(dt.HasValue)
{
//DoStuff
}
Is it a good coding practice to design a class as follows?
class Computer
{
public string Name;
public string ID;
//...
public bool IsHiveMind;
public HiveMindInfo RegInfo;
}
class HiveMindInfo
{
string SecretLocation;
int BaudRate;
int Port;
}
...and to use it...
Computer aComputer = GetComputer(...);
if(aComputer.IsHiveMind)
{
Network.DoHostileTakeOver(aComputer); //!
}
How about this code below?
It seems you can remove IsHiveMind variable since HiveMindInfo variable has the same meaning by checking its null or not.
class Computer
{
public string Name;
public string ID;
public HiveMindInfo RegInfo;
}
class HiveMindInfo
{
string SecretLocation;
int BaudRate;
int Port;
}
Computer aComputer = GetComputer(...);
if (aComputer != null && aComputer.RegInfo != null)
{
Network.DoHostileTakeOver(aComputer);
}
To answer your question, you could implement the code as proposed.
An alternative would be to consider the following design patterns:
Proxy Design Pattern
Strategy Design Pattern
Sample Code
interface ITakeOverStrategy
{
void Execute();
}
class KevinFlynnHackerStrategy : ITakeOverStrategy
{
public void Execute()
{
// a nod to Tron
}
}
class NeoHackerStrategy: ITakeOverStrategy
{
private readonly HiveMindInfo _hiveMindInfo;
public NeoHackerStrategy(HiveMindInfo info)
{
_hiveMindInfo = info;
}
public void Execute()
{
// Mr. Anderson!
}
}
// This is a surrogate class.
// ... The value returned by String.Empty is often used as a surrogate.
class IdleStrategy : ITakeOverStrategy
{
public void Execute()
{
// do nothing
}
}
class Computer
{
private readonly ITakeOverStrategy _takeoverStrategy ;
public Computer(ITakeOverStrategy strategy)
{
_takeoverStrategy = strategy;
}
public Subjugate()
{
// insert epic code here
_takeoverStrategy.Execute();
}
}
Then somewhere in your code you create an instance of Computer with the appropriate strategy:
var info = new HiveMindInfo();
// update instance parameters
var computer = new Computer(new NeoHackerStrategy(info));
computer.Subjugate();
UPDATES
August 13th, 2015 # 10:13 EST
My comment about structs is not within the scope of the original question, and has been removed:
If your classes are only going to contain fields/properties then I would consider converting them into struct.
Just add ? to your object:
class Computer
{
public string Name;
public string ID;
//...
public HiveMindInfo? RegInfo;
}
struct HiveMindInfo
{
string SecretLocation;
int BaudRate;
int Port;
}
And then check it exactly as you did with datetime:
Computer aComputer = GetComputer(...);
if (aComputer.RegInfo.HasValue)
{
// Do something
}
I have a validation class, and within this I want to verify various properties received form a web service are valid, and report a descriptive error message if not.
Currently the webservice returns all strings, and I want to convert/validate these into more useful types. The problem is I am currently passing the property name through as a string parameter in the method call. Is there a way to get the name of a property for display in the error message without passing it through as a string?
public class WebserviceAccess
{
public MyUsefulDataObject ConvertToUsefulDataObject(WebserviceResponse webserviceResponse)
{
var usefulData = new MyUsefulDataObject();
usefulData.LastUpdated = webserviceResponse.LastUpdated.IsValidDateTime("LastUpdated");
// etc . . .
// But I don't want to have to pass "LastUpdated" through.
// I'd like IsValidDateTime to work out the name of the property when required (in the error message).
return usefulData ;
}
}
public static class WebServiceValidator
{
public static DateTime IsValidDateTime(this string propertyValue, string propertyName)
{
DateTime convertedDate;
if (!DateTime.TryParse(propertyValue, out convertedDate))
{
throw new InvalidDataException(string.Format("Webservice property '{0}' value of '{1}' could not be converted to a DateTime.", propertyName, propertyValue));
}
return convertedDate;
}
}
Any assistance is much appreciated.
Thanks in advance.
EDIT: Using Oblivion2000's suggestion, I now have the following:
public class Nameof<T>
{
public static string Property<TProp>(Expression<Func<T, TProp>> expression)
{
var body = expression.Body as MemberExpression;
if (body == null)
{
throw new ArgumentException("'expression' should be a member expression");
}
return body.Member.Name;
}
}
public class WebserviceAccess
{
public MyUsefulDataObject ConvertToUsefulDataObject(WebserviceResponse webserviceResponse)
{
var usefulData = new MyUsefulDataObject();
usefulData.LastUpdated = Nameof<WebserviceResponse>.Property(e => e.LastUpdated).IsValidDateTime(webserviceResponse.LastUpdated);
// etc . . .
return usefulData ;
}
}
public static class WebServiceValidator
{
public static DateTime IsValidDateTime(this string propertyName, string propertyValue)
{
DateTime convertedDate;
if (!DateTime.TryParse(propertyValue, out convertedDate))
{
throw new InvalidDataException(string.Format("Webservice property '{0}' value of '{1}' could not be converted to a DateTime.", propertyName, propertyValue));
}
return convertedDate;
}
}
In Visual Studio 2011, there is a new feature to handle this: http://www.mitchelsellers.com/blogs/2012/02/29/visual-studio-11-caller-member-info-attributes.aspx
In current/older versions, you have to use tricks like Oblivion2000 posted
Here's Câ„“inton Sheppard's post on this:
http://handcraftsman.wordpress.com/2008/11/11/how-to-get-c-property-names-without-magic-strings/
It is so useful to me I keep it in my bookmarks.
Personally, I like his static nested class way (quoted from above):
public class Sample2
{
public static class BoundPropertyNames
{
public static readonly string Foo = ((MemberExpression)((Expression<Func<Sample2, int>>)(s => s.Foo)).Body).Member.Name;
}
public int Foo { get; set; }
}