Checking variable before use

4 posts, 0 answers
  1. Jim
    Jim avatar
    4 posts
    Member since:
    May 2012

    Posted 09 Apr 2013 Link to this post

    Hello, Again.

    I am working on an exception to ensure that developers check incoming variables to a method before they use them.  I'm having problems when they use a method like "String.IsNullOrEmpty(variable)".  Here is the example code...

    VB.NET

    Public Sub test(ByVal str As String, ByVal logLine As String)
     
        Dim Y as string = str
     
        If String.IsNullOrEmpty(logLine) Then
            Throw New Exception("LogConsoleLogInfo: empty string logLine")
        End If
     
        Dim X as String = logLine
     
    End Sub

    C#

    public void test(String str, String logLine)
    {
     
        str Y = str;
         
        If (String.IsNullOrEmpty(logLine) { Throw New Exception("LogConsoleLogInfo: empty string Logline");
         
        str X = logLine;
     
    }

    I would completely expect "str" to be underlined in my exception, but since they checked "logLine" with String.IsNullOrEmpty, it shouldn't be underlined.  I either get both or neither with my existing code. 

    Any help would be greatly appreciated!

    Thanks,

    Jim Evans
    Application Architect, eMASON, Inc.

  2. Zdravko
    Admin
    Zdravko avatar
    657 posts

    Posted 12 Apr 2013 Link to this post

    Hi Jim,

     Thanks for contacting us.
    Can you provide us your source code so we could examine it?
    Thank you.

    Greetings,
    Zdravko
    the Telerik team
    Share what you think about JustCode with us, so we can help you even better! You can use the built-in feedback tool inside JustCode, our forum, or our JustCode feedback portal.
  3. DevCraft banner
  4. Jim
    Jim avatar
    4 posts
    Member since:
    May 2012

    Posted 12 Apr 2013 Link to this post

    Here is the code.  There are no external voids called by this code...  (Note:  I'd attach the code file in ZIP format but it won't let me.)

    foreach (IMethodDeclaration md in fileModel.All<IMethodDeclaration>().Where(m => (m.Parameters.Any() &&   
                                                                                              !m.EnclosingClass.IsInterface && !m.EnclosingClass.IsStruct &&                                                                        
                                                                                              !m.Identifier.Name.ToUpper().Contains("VERIF") &&
                                                                                              !m.Identifier.Name.ToUpper().Contains("VALIDAT"))))
            {
                // An IParameter is NOT the param, but the entire parameter clause.  eg "byVal ex as System.Exception" instead of "ex"
                foreach (IParameter oParam in md.Parameters.Parameters)
                {
                    // If our param isn't null, is a complex type, and is NOT an enumeration, we want to evaluate it.
                    if (oParam != null &&
                        !oParam.Type.IsPrimitiveType &&
                        !oParam.Type.IsEnumType &&
                        !oParam.Type.Is("System.EventArgs"))
                    {
                        var allAccesses = oParam.AllAccesses();
                        var firstAccess = allAccesses.First();
                        var enclosingStatementExpression = firstAccess.EnclosingStatement().As<IExpressionStatement>().Expression;
                        if (!enclosingStatementExpression.Is<IMethodInvocation>())
                        {
                            oParam.AddCodeMarker(Constants.EM108WarningExampleID, this, Constants.EM108FixText);
                        }
                        else
                        {
                            var methodInvocation = enclosingStatementExpression.As<IMethodInvocation>();
                            if (!methodInvocation.Language.AreNamesEqual(methodInvocation.Identifier.Name, "Verify") && !methodInvocation.Language.AreNamesEqual(methodInvocation.Identifier.Name, "ASSERT"))
                            {
                                oParam.AddCodeMarker(Constants.EM108WarningExampleID, this, Constants.EM108FixText);
                            }
                        }
                    }
                }
            }

  5. Zdravko
    Admin
    Zdravko avatar
    657 posts

    Posted 15 Apr 2013 Link to this post

    Hi Jim,

     Thanks for contacting us.
    Here I will post the solution:

    protected override void AddCodeMarkers(FileModel fileModel)
            {
                // you can use fileModel.All<T> to iterate over the construct you are interested in
                // you might also use LINQ queries
                foreach (IMethodDeclaration md in fileModel.All<IMethodDeclaration>().Where(m => (m.Parameters.Any() &&
                                                                                                  !m.EnclosingClass.IsInterface && !m.EnclosingClass.IsStruct &&
                                                                                                  !m.Identifier.Name.ToUpper().Contains("VERIF") &&
                                                                                                  !m.Identifier.Name.ToUpper().Contains("VALIDAT"))))
                {
                    // An IParameter is NOT the param, but the entire parameter clause.  eg "byVal ex as System.Exception" instead of "ex"
                    foreach (IParameter oParam in md.Parameters.Parameters)
                    {
                        // If our param isn't null, is a complex type, and is NOT an enumeration, we want to evaluate it.
                        if (oParam != null &&
                            !oParam.Type.IsPrimitiveType &&
                            !oParam.Type.IsEnumType &&
                            !oParam.Type.Is("System.EventArgs"))
                        {
                            var firstAccess = oParam.AllAccesses().First();
                            if (firstAccess.Exists)
                            {
                                var enclosingStatementExpression = firstAccess.EnclosingStatement();
     
                                if (enclosingStatementExpression.Is<IIfStatement>())
                                {
                                    var ifStatement = enclosingStatementExpression.As<IIfStatement>();
                                    if (!IsMethodInvocationWithName(ifStatement.Condition, "IsNullOrEmpty") &&
                                        !ifStatement.Condition.ChildExpressions.Where(x => IsMethodInvocationWithName(x, "IsNullOrEmpty")).Exist())
                                    {
                                        oParam.AddCodeMarker(Constants.EM108WarningExampleID, this, Constants.EM108FixText);
                                    }
                                }
                                else if (enclosingStatementExpression.Is<IMethodInvocation>())
                                {
                                    var methodInv = enclosingStatementExpression.As<IMethodInvocation>();
                                    if (!methodInv.Language.AreNamesEqual(methodInv.Identifier.Name, "Verify")
                                        && !methodInv.Language.AreNamesEqual(methodInv.Identifier.Name, "ASSERT"))
                                    {
                                        oParam.AddCodeMarker(Constants.EM108WarningExampleID, this, Constants.EM108FixText);
                                    }
                                }
                                else
                                {
                                    oParam.AddCodeMarker(Constants.EM108WarningExampleID, this, Constants.EM108FixText);
                                }
                            }
                        }
                    }
                }
            }

    private bool IsMethodInvocationWithName(IExpression expression, string name)
    {
    return expression.Is<IMethodInvocation>() && expression.Language.AreNamesEqual(expression.As<IMethodInvocation>().Identifier.Name, name);
    }

    If you like to expand the check for IIfStatement just copy the 'if' and change the string and for the IMethodInvocation just add additional conditions.
    Thanks.

    I hope it helps.

    All the best,
    Zdravko
    the Telerik team
    Share what you think about JustCode with us, so we can help you even better! You can use the built-in feedback tool inside JustCode, our forum, or our JustCode feedback portal.
Back to Top