Validating e-mail with regular expression VB.Net - vb.net

I'm working on a small project in VB.Net where I get a input from a textbox, and need to verify that this is an e-email address.
I found this expression "^[_a-z0-9-]+(.[_a-z0-9-]+)#[a-z0-9-]+(.[a-z0-9-]+)(.[a-z]{2,4})$", but i cant find any way to test if it passes.
I want some code like:
if not txtEmail.text = regexString then
something happens..
else
something else happens..
end if

Use the System.Text.RegularExpressions.Regex class:
Function IsEmail(Byval email as string) as boolean
Static emailExpression As New Regex("^[_a-z0-9-]+(.[a-z0-9-]+)#[a-z0-9-]+(.[a-z0-9-]+)*(.[a-z]{2,4})$")
return emailExpression.IsMatch(email)
End Function
The most important thing to understand about this answer is that I didn't write the regular expression myself. There are just so many wrong ways that seem to be right, and there are several levels of detail that you could take this to. For example, do you want to restrict this to valid top level domains, and if so, how are you accounting for the fact that they are now occasionally adding new TLDs? If the regular expression the most appropriate place for that test, or should have separate code for that check? Even the expression in this answer is now very stale since it was originally authored.
I recommend finding an outside resource for the expression you know will be maintained over time.

Pick your favorite regex from my article on matching email addresses with a regex, and plug it into this Visual Basic code:
If Regex.IsMatch(SubjectString, "regex") Then
Error = False
Else
Error = True
End If
The best regex to match an email address is a controversial topic that I don't want to get into here. My article discusses the issues that you should be aware of when picking a regex. The regex in Joel Coehoorn's answer is definitely not a good one.

There is a great website for this kind of thing, http://regexlib.com/. Not only does it have a tester application where you can paste in a regular expression and test it, but there is also a library of regular expressions you can use with community feedback on their validity, etc. I'm not a regex guru, so I go here when I need a quick regular expression.
Also, if you are thinking of developing regular expressions yourself, there is an excellent tool called Regex Buddy that will allow you to create and test your regular expressions on the fly using an easy to understand English interpretation of your regex.

Possibly off-topic since it's not a regex solution, but you could just use some of the built in features of .NET 2.0:
try
{
MailAddress email = new MailAddress(txtEmail.Text);
}
catch(FormatException fe)
{
// output error
}

That regex isn't really complete... in fact... most aren't (check out this article, or this one).
Unless you really enjoy pain, regex isn't the right way to validate an email address.

Email address: RFC 2822 (simplified)
Matches a normal email address. Does not check the top-level domain.
Requires the "case insensitive" option to be ON.
Dim FoundMatch As Boolean
Try
FoundMatch = Regex.IsMatch(txtEmail.text, "\A(?:[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*#(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?)\Z", RegexOptions.IgnoreCase)
Catch ex As ArgumentException
'Syntax error in the regular expression
End Try
If Not FoundMatch Then
Error = True
Else
Error = False
End If

Related

Use String for IF statement conditions

I'm hoping someone can help answer my question, perhaps with an idea of where to go or whether what I'm trying to do is not possible with the way I want to do it.
I've been asked to write a set of rules based on the data held by our ERP form components or variables.
Unfortunately, these components and variables cannot be accessed or used outside of the ERP, so I can't use SQL to query the values and then build some kind of SQL query.
They'd like the ability to put statements like these:
C(MyComponentName) = C(MyOtherComponentName)
V(MyVariableName) > 16
(C(MyComponentName) = "") AND V(MyVariableName) <> "")
((C(MyComponentName) = "") OR C(MyOtherComponentName) = "") AND V(MyVariableName) <> "")
This should be turned into some kind of query which gets the value of MyComponentName and MyOtherComponentName and (in this case) compares them for equality.
They don't necessarily want to just compare for equality, but to be able to determine whether a component / variable value is greaterthan or lessthan etc.
Basically it's a free-form statement that gets converted into something similar to an IF statement.
I've tried this:
Sub TestCondition()
Dim Condition as string = String.Format("{0} = {1}", _
Component("MyComponent").Value, Component("MyOtherComponent").Value)
If (Condition) Then
' Do Something
Else
' Do Something Else
End If
End Sub
Obviously, this does not work and I honestly didn't think it would be so simple.
Ignoring the fact that I'd have to parse the line, extract the required operators, the values from components or variables (denoted by a C or V) - how can I do this?
I've looked at Expression Trees but these were confusing, especially as I'd never heard of them, let alone used them. (Is it possible to create an expression tree for dynamic if statements? - This link provided some detail on expression trees in C#)
I know an easier way to solve this might be to simply populate the form with a multitude of drop-down lists, so users pick what they want from lists or fill in a text box for a specific search criteria.
This wouldn't be a simple matter as the ERP doesn't allow you to dynamically create controls on its forms. You have to drag each component manually and would be next to useless as we'd potentially want at least 1 rule for every form we have (100+).
I'm either looking for someone to say you cannot do this the way you want to do it (with a suitable reason or suggestion as to how I could do it) that I can take to my manager or some hints, perhaps a link or 2 pointing me in the right direction.
If (Condition) Then
This is not possible. There is no way to treat data stored in a string as code. While the above statement is valid, it won't and can't function the way you want it to. Instead, Condition will be evaluated as what it is: a string. (Anything that doesn't boil down to 0 is treated as True; see this question.)
What you are attempting borders on allowing the user to type code dynamically to get a result. I won't say this is impossible per se in VB.Net, but it is incredibly ambitious.
Instead, I would suggest clearly defining what your application can and can't do. Enumerate the operators your code will allow and build code to support each directly. For example:
Public Function TestCondition(value1 As Object, value2 As Object, op as string) As Boolean
Select Case op
Case "="
Return value1 = value2
Case "<"
Return value1 < value2
Case ">"
Return value1 > value2
Case Else
'Error handling
End Select
End Function
Obviously you would need to tailor the above to the types of variables you will be handling and your other specific needs, but this approach should give you a workable solution.
For my particular requirements, using the NCalc library has enabled me to do most of what I was looking to do. Easy to work with and the documentation is quite extensive - lots of examples too.

How can I get ISO-based language string from FileVersionInfo?

I have a windows form in VB.net 2010 which needs to read remote .exe's language string.
Usually, this could be done via
oFileInfo = FileVersionInfo.GetVersionInfo("path to .exe here")
Dim sMyLanguage = oFileInfo.Language
Unfortunately, this will return something like "englisch", "französisch" on a German Windows which is absolutely useless for me.
The best would be an ISO-based code, like EN, DE, FR, etc. Another unique identifier like a codepage number or something similar would also be okay.
System.Globalization also doesn't seem to have kind of a mapping of language strings to something useful.
Any idea how to get such a language identification de-coupled from the language of my operating system? Currently, my idea is to use a .csv file with three gazillions of translations which doesn't sound to be appropriate.
Okay, I found a solution:
In System.Globalization, there is not quite a direct mapping, but as in https://msdn.microsoft.com/de-de/library/system.globalization.cultureinfo.lcid(v=vs.110).aspx there are just about 140 languages listed, so I made a .csv file with Culture ID and to returning string and looped thru it with a simple For loop.
For i = 1 To gsLanguages.Count - 1
Try
oLang = New System.Globalization.CultureInfo(CInt(gsLanguages(i).Split(";")(1)), True)
If oLang.DisplayName.ToLower.StartsWith(sLangString) Then
sLanguage = gsLanguages(i).Split(";")(0)
Exit For
End If
Catch ex As Exception
End Try
Next
No question, this may not be the best solution. But in my testing, it had a very high chance to hit, so this is good enough for me.

VB.Net String comparison and Wildcard values

Is it possible to do String comparison where one of the strings I am comparing against has wild cards and is generally just for formatting purposes. For example
Dim correctFormat as String = "##-##-###-##"
Dim stringToCheck = someClass.SomeFunctionThatReturnsAStringToCheck
If FormatOf(CorrectFormat) = FormatOF(StringToCheck) then
Else
End if
I am aware of the made up FormatOf syntax, but I'm just using it to show what I am asking.
No need for regular expressions.
You can simply use the Like operator, which supports ?, * and # as wildcards and also character lists ([...], [!...])
So you simply change your code to:
If stringToCheck Like correctFormat Then
and it will work as expected.
The way is to use regular expressions - that's what they are for.
This is the regular expression that matches the format you have posted:
^\d{2}-\d{2}-\d{3}-\d{2}$
As the previous post mentioned, you should use regular expressions for that purpose - they are way better for that task.
Sadly, learning them can be confusing, especially finding bugs can be really annoying.
I really like http://www.regular-expressions.info/ and http://regexpal.com/ for building and testing regexes before.
In VB.net use something like reg.ismatch

Regex email address validation fails if Underscore character present

I'm very new to Regular Expressions, but I thought it'd be the best way to validate email addresses entered on my form.
My Regex works, except if the email address entered has an underscore character (_) in it.
Because of my lack of experience with regular expressions, I'm not sure where in my pattern I'm supposed to add the offending character to allow it:
Dim pattern As String = "^[-a-zAZ0-9][-.a-zA-Z0-9]*#[-.a-zA-Z0-0]+(\.[-.a-zA-Z0-0+)*\." & _
"(com|edu|info|gov|int|mil|net|org|biz|name|museum|coop|aero|pro|tv|[a-zA-Z]{2})$"
Another guy on DreamInCode had the same problem. He said he fixed it by adding the _ after the numeric check.
I see the A-Z0-9, but I'm not sure which is the numeric check... I haven't worked much in Regex so I hope nobody minds pointing out where to add the _
Thanks in advance
If you really want a possible fix to your regexp:
Dim pattern As String = "^[a-zA-Z0-9][-\._a-zA-Z0-9]*#[a-zA-Z0-9][-\.a-zA-Z0-9]*\.(com|edu|info|gov|int|mil|net|org|biz|name|museum|coop|aero|pro|tv|[a-zA-Z]{2})$"
Anyway as explained in my comment this still validates ok for many wrong mails.
The only way to validate an email is to send a message at this address and wait for a reply.
A simple check can be to test if there is an # in it. But if you want to use your regex, you have to add the _ within the char class : [-a-zA-Z0-9_]
This is the one which prevents an underscore before the '#' if someone needs this,
^[a-zA-Z0-9][-\.a-zA-Z0-9]*#[a-zA-Z0-9][-\.a-zA-Z0-9]*\.(com|edu|info|gov|int|mil|net|org|biz|name|museum|coop|aero|pro|tv|[a-zA-Z]{2})$
but i have seen some mail address with an underscore in it..as said by M42 is send an email and wait for them to activate their account would be a good choice..but wont be instantly done..

What's bad about the VB With/End With keyword?

In this question, a user commented to never use the With block in VB. Why?
"Never" is a strong word.
I think it fine as long as you don't abuse it (like nesting)
IMHO - this is better:
With MyCommand.Parameters
.Count = 1
.Item(0).ParameterName = "#baz"
.Item(0).Value = fuz
End With
Than:
MyCommand.Parameters.Count = 1
MyCommand.Parameters.Item(0).ParameterName = "#baz"
MyCommand.Parameters.Item(0).Value = fuz
There is nothing wrong about the With keyword. It's true that it may reduce readibility when nested but the solution is simply don't use nested With.
There may be namespace problems in Delphi, which doesn't enforce a leading dot but that issue simply doesn't exist in VB.NET so the people that are posting rants about Delphi are losing their time in this question.
I think the real reason many people don't like the With keyword is that is not included in C* languages and many programmers automatically think that every feature not included in his/her favourite language is bad.
It's just not helpful compared to other options.
If you really miss it you can create a one or two character alias for your object instead. The alias only takes one line to setup, rather than two for the With block (With + End With lines).
The alias also gives you a quick mouse-over reference for the type of the variable. It provides a hook for the IDE to help you jump back to the top of the block if you want (though if the block is that large you have other problems). It can be passed as an argument to functions. And you can use it to reference an index property.
So we have an alternative that gives more function with less code.
Also see this question:
Why is the with() construct not included in C#, when it is really cool in VB.NET?
The with keyword is only sideswiped in a passing reference here in an hilarious article by the wonderful Verity Stob, but it's worth it for the vitriol: See the paragraph that starts
While we are on identifier confusion. The with keyword...
Worth reading the entire article!
The With keyword also provides another benefit - the object(s) in the With statement only need to be "qualified" once, which can improve performance. Check out the information on MSDN here:
http://msdn.microsoft.com/en-us/library/wc500chb(VS.80).aspx
So by all means, use it.