A better way to validate URL in C# than try-catch?

前端 未结 10 962
栀梦
栀梦 2020-12-13 12:08

I\'m building an application to retrieve an image from internet. Even though it works fine, it is slow (on wrong given URL) when using try-catch statements in the applicatio

10条回答
  •  执笔经年
    2020-12-13 12:38

    I ran into a very similar case so I wrote a static class which can be easily used along with xUnit tests to verify the logic passed several cases.

    Usage (returns ValidationModel):

    var message = UrlValidator.Validate(input).ValidationMessage;

    or

    var result = UrlValidator.Validate(input).IsValid;

    ValidationModel.cs

        public class ValidationModel
        {
            public const string InvalidScheme = "Invalid URI scheme.";
            public const string EmptyInputValue = "Empty input value.";
            public const string InvalidUriFormat = "Invalid URI format.";
            public const string PassedValidation = "Passed validation";
            public const string HttpScheme = "http://";
            public const string HttpsScheme = "https://";
    
            public bool IsValid { get; set; }
            public string ValidationMessage { get; set; }
            
        }
    

    UrlValidator.cs

        public static class UrlValidator
        {
            public static ValidationModel Validate(string input)
            {
                var validation = new ValidationModel();
    
                if (input == string.Empty)
                {
                    validation.IsValid = false;
                    validation.ValidationMessage = ValidationModel.EmptyInputValue;
                    return validation;
                }
    
                try
                {
                    var uri = new Uri(input);
                    var leftPart = uri.GetLeftPart(UriPartial.Scheme);
    
                    if (leftPart.Equals(ValidationModel.HttpScheme) || leftPart.Equals(ValidationModel.HttpsScheme))
                    {
                        validation.IsValid = true;
                        validation.ValidationMessage = ValidationModel.PassedValidation;
                        return validation;
                    }
                    
                    validation.IsValid = false;
                    validation.ValidationMessage = ValidationModel.InvalidScheme;
                }
                catch (UriFormatException)
                {
                    validation.IsValid = false;
                    validation.ValidationMessage = ValidationModel.InvalidUriFormat;
                }
                
                return validation;
            }
        }
    

    UrlValidatorTests.cs

        public class UrlValidatorTests
        {
            [Theory]
            [InlineData("http://intel.com", true, ValidationModel.PassedValidation)]
            [InlineData("https://intel.com", true, ValidationModel.PassedValidation)]
            [InlineData("https://intel.com/index.html", true, ValidationModel.PassedValidation)]
            [InlineData("", false, ValidationModel.EmptyInputValue)]
            [InlineData("http://", false, ValidationModel.InvalidUriFormat)]
            [InlineData("//intel.com", false, ValidationModel.InvalidScheme)]
            [InlineData("://intel.com", false, ValidationModel.InvalidUriFormat)]
            [InlineData("f://intel.com", false, ValidationModel.InvalidScheme)]
            [InlineData("htttp://intel.com", false, ValidationModel.InvalidScheme)]
            [InlineData("intel.com", false, ValidationModel.InvalidUriFormat)]
            [InlineData("ftp://intel.com", false, ValidationModel.InvalidScheme)]
            [InlineData("http:intel.com", false, ValidationModel.InvalidUriFormat)]
            public void Validate_Input_ExpectedResult(string input, bool expectedResult, string expectedInvalidMessage)
            {
                //Act
                var result = UrlValidator.Validate(input);
    
                //Assert
                Assert.Equal(expectedResult, result.IsValid);
                Assert.Equal(expectedInvalidMessage, result.ValidationMessage);
            }
        }
    

    TEST RESULTS:

提交回复
热议问题