RSS

C# Check if PropertyType is Null

You want to check if a property’s PropertyType is nullable. In the example below, only property `IsStudent` is nullable.

User.cs

public class User
{
    public string FirstName { get; set; }
    public string LastName { get; set; }
    public bool? IsStudent { get; set; }
}

Checking if PropertyType is nullable is useable when adding column to `DataTable` object. If column to be added is nullable type, we need to explicitly set it.

To check if PropertyType is nullable, we can use `System.Nullable.GetUnderlyingType(Type nullableType)`, see example below and reference here.

public void GetUsers()
{
    System.Reflection.PropertyInfo[] properties = typeof(User).GetProperties();
    System.Reflection.PropertyInfo[] readableProperties = properties.Where(w => w.CanRead).ToArray();
    foreach (var property in readableProperties)
    {
        var propertyType = property.PropertyType;
        if (System.Nullable.GetUnderlyingType(propertyType) != null)
        {
            // It's a nullable type
        }
        else
        {
            // It's not a nullable type
        }
    }
}

Reference
Stackoverflow

Advertisements
 
Leave a comment

Posted by on June 20, 2019 in General

 

Tags: , , , ,

DynamicProxyGenAssembly2

DynamicProxyGenAssembly2 is a temporary assembly built by mocking systems that use CastleProxy like Moq or NSubsitute. It is generated when the mock is needed and disposed of after the tests are finished.

Tested on:
Moq 4.10 https://github.com/moq/moq4
.Net 4.5

Following is AssemblyInfo.cs in QC.Client project.

using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;

[assembly: AssemblyTitle("QC.Client")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("QC.Client")]
[assembly: AssemblyCopyright("Copyright ©  2019")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]
[assembly: ComVisible(false)]

[assembly: Guid("d62d1a60-782a-46d8-b5f5-2f6d12ad1339")]

[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: InternalsVisibleTo("QC.ClientTest")]

Following is class i want to test.
UserManagement.cs (In QC.Client project)

namespace QC.Client
{
    public class UserManagement
    {
        public void UpdateUser(string address)
        {
            var executer = new Executer();
            executer.Run();
        }
    }
}

Executer.cs (In QC.Client project)

namespace QC.Client
{
    public class Executer
    {
        internal virtual bool Run()
        {
            return true;
        }
    }
}

Following is my unit test.
UserManagementTest.cs (In QC.ClientTest project)

using Microsoft.VisualStudio.TestTools.UnitTesting;
using Moq;
using QC.Client;

namespace QC.ClientTest
{
    [TestClass]
    public class UserManagementTest
    {
        [TestMethod]
        public void UpdateUserShouldWork()
        {
            // Mock
            var mock = new Mock();
            mock.Setup(x => x.Run());

            // Act
            var userManagement = new UserManagement();
            userManagement.UpdateUser("Test Address");

            // Assert
            mock.Verify(x => x.Run(), Times.Once);
        }
    }
}

Problem
MS Test throwing following error when unit testing internal member of a class in different project.
When unit test in above `UserManagementTest.cs` is run, MS Test throw following error:

Message: Test method QC.ClientTest.UserManagementTest.UpdateUserShouldWork threw exception:
System.ArgumentException: Cannot set up Executer.Run because it is not accessible to the proxy generator used by Moq:
Can not create proxy for method Boolean Run() because it or its declaring type is not accessible. Make it public, or internal and mark your assembly with [assembly: InternalsVisibleTo("DynamicProxyGenAssembly2")] attribute, because assembly QC.Client is not strong-named.

Note:
– MS Test only throw exception if the accessor of method being tested is internal. In above example it is `Executer.Run()`.
– Virtual keyword in method being tested is to allow Moq to mock the method.

Solution is to simply add following code in AssemblyInfo.cs

[assembly: InternalsVisibleTo("DynamicProxyGenAssembly2")]

Sources
Stackoverflow

 
Leave a comment

Posted by on June 17, 2019 in General

 

Tags: , , , , , , , , ,

Shared Assembly in Visual Studio Projects

Here is steps to create shared assembly file in multiple VS projects:
1. Add new shared assembly file.
2019-06-10 16_38_40-LinqJoin - Microsoft Visual Studio (Administrator)

2. For each project that will use the shared assembly, right click on the `Properties` under the project and add existing item.
2019-06-10 16_43_15-

3. Select the shared assembly file, but add it as a link
2019-06-10 16_39_38-LinqJoin - Microsoft Visual Studio (Administrator)
2019-06-10 16_40_12-LinqJoin - Microsoft Visual Studio (Administrator)

4. Remove attribute in the project assembly that you want to inherit from the shared. For example, if you want to share `AssemblyVersion` across projects, remove them from projects’ assembly and add it shared assembly file.

SharedAssembly.cs

using System.Reflection;

[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]
 
Leave a comment

Posted by on June 13, 2019 in General

 

Tags: , , , , , ,

Expression Func vs. Func

Func
`Func<>` is a lambda expression. A delegate. A pointer to a method. Runtime engine can not “look” inside `Func<>`, it can only execute `Func<>`.

Example usage:

Func<int> haveFunc = () => 15; // return 15

Expression Func
`Expression<Func<>>` is an expression tree. It’s a lambda expression in form of tree data structure. It only hold metadata or information and composition of the contained lambda expression. Runtime engine can look “inside” `Expression<Func<>>` and translate it to other statement you need.

Example usage:

Expression<Func<int>> notMuchFunc = () => 25;

Why is it important ?
Misuse of this could be cause compile error or in the case of EF, a performance hit.

Compile Error Example
Linq has few methods that take `Func<>` or `Expression<Func<>>` parameter, for example `Where` extension method, as seen in signature below.

System.Linq.Enumerable
public static IEnumerable<TSource> Where<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate);

System.Linq.Queryable
public static IQueryable<TSource> Where<TSource>(this IQueryable<TSource> source, Expression<Func<TSource, bool>> predicate);

Depend on parameter type we pass in, compiler know which extension method to call.

In the code below, ProcessUsers3 throw compiler error. Because we pass in `Expression<Func<>>`, compiler think we are calling `Where` extension method which accept `IQueryable<>` but `this.GetUserNames()` return `IEnumerable<>`.

The workaround is to convert `IEnumerable<>` to `IQueryable<>` using `.AsQueryable()` as can be seen on ProcessUsers4.

public IEnumerable<string> GetUserNames()
{
    return new[] { "user1", "user2" };
}

public void ProcessUsers()
{
    // Return type IEnumerable<string>
    var result = this.GetUserNames()
        .Where((item) => !string.IsNullOrEmpty(item));
}

public void ProcessUsers2()
{
    // Return type IEnumerable<string>
    Func<string, bool> predicate = (item) => !string.IsNullOrEmpty(item);
    var result = this.GetUserNames()
        .Where(predicate);
}

public void ProcessUsers3()
{
    // Compile error
    // We pass in Expression<Func<>> to Where extension method, compiler think we are calling the Where extension method for IQueryable<> - this.GetUserNames() return IEnumerable<>
    Expression<Func<string, bool>> predicate = (item) => !string.IsNullOrEmpty(item);
    var result = this.GetUserNames()
        .Where(predicate);
}

public void ProcessUsers4()
{
    Expression<Func<string, bool>> predicate = (item) => !string.IsNullOrEmpty(item);

    // Return type IQueryable<string>
    var result = this.GetUserNames()
        .AsQueryable()
        .Where(predicate);
}

Performance Hit Example
In the code below, both methods are legal, compile without error and run without error.

On GetAppConfigurations1, we query EF context by passing `Func<>`, a lambda expression. Because the context can not “look” inside the lambda expression (it can only execute it), Linq would get all AppConfiguration and run `Func<>` on each record, which increase load time.

On GetAppConfigurations2, we query EF context by passing `Expression<Func<>>`, an expression tree. It allow Linq to “look” inside the expression tree, read its metadata and composition than figure out the best and most perfomant way to query AppConfiguration with filter condition we specified.

public IEnumerable<AppConfiguration> GetAppConfigurations1()
{
    Func<AppConfiguration, bool> filter = (config) => config.Id == 1;

    using (var context = new QCEntities())
    {
        var result = context.AppConfiguration.Where(filter);
        return result;
    }
}

public IEnumerable<AppConfiguration> GetAppConfigurations2()
{
    System.Linq.Expressions.Expression<Func<AppConfiguration, bool>> filter = (config) => config.Id == 1;

    using (var context = new QCEntities())
    {
        var result = context.AppConfiguration.Where(filter);
        return result;
    }
}

References
Stackoverflow

 
Leave a comment

Posted by on June 10, 2019 in General

 

Tags: , , , , , , , , ,

Azure App Service Auto-Healing

Auto-Healing

Azure App Service provide feature to auto-heal your service whenever it detects anomaly with the service.

Auto-Healing allows you to restart, log or perform custom actions (action) whenever a certain criteria about your App Service is met (trigger), for example, recycle service when slow requests is detected.

You define these triggers and actions to determine what triggers / actions to take.

Azure Web Sites

Before it was renamed to Azure App Service, the service is called Azure Web Sites. To enable auto-heal in Azure Web Sites, you would have to add configuration in the web.config file.

<system.webServer>
  <monitoring>
    <triggers>
      <requests count="100" timeInterval="00:05:00" />
    </triggers>
    <actions value="Recycle" />
  </monitoring>
</system.webServer>

To see different scenarios on how to use this, head over to this link. Some of the scenarios are:

  • Recycle based on Request count (code example above).
  • Recycle based on slow requests.
  • Logging an event or recycle based on HTTP status code(s).
  • Take custom actions or recycle / log event based on memory limit.

Azure App Service

In the new Azure App Service, however, auto-heal works little bit differently. Announced in September 2018 (https://azure.github.io/AppService/2018/09/10/Announcing-the-New-Auto-Healing-Experience-in-App-Service-Diagnostics.html), the auto-heal is now available through Azure Portal.

To get to Auto-Healing setting, go to Azure App Service > Diagnose and solve problems > Diagnostic Tools > Auto Healing.

azure-app-service-auto-healing-1

azure-app-service-auto-healing-2

Azure App Service offers two types of auto-heal. First is ProActive Auto-Healing which is enabled by default. And custom Auto-Healing.

You can turn off ProActive Auto-Healing under Azure Portal as well.

To add custom Auto-Healing setting, follow this link.

azure-app-service-auto-healing-3

As the screenshot shows, the first tab (“Configure Mitigation Rules”) is the custom Auto-Healing settings. By default it’s turned off. The second tab (“ProActive Auto-Healing”) is ProActive Auto-Healing and it’s turned on by default.

Reference

https://docs.microsoft.com/en-us/azure/app-service/overview-diagnostics

https://azure.github.io/AppService/2018/09/10/Announcing-the-New-Auto-Healing-Experience-in-App-Service-Diagnostics.html

 
Leave a comment

Posted by on May 20, 2019 in General

 

Tags: , , , , ,

Comparing Linq Join and GroupJoin

Tested on:
.Net 4.5
Entity Framework 6 – Github

This is a post comparing Linq Join and GroupJoin for querying database.

I created simple database consist of 2 tables, `Instructor` and `Class`, which has 1 to many relationship.

SQL instructor table

SQL class table

Entity Framework diagram looks like this.
EF diagram

The console app using Linq to join these 2 tables look like this.

using System.Linq;

namespace LinqJoin
{
    class Program
    {
        static void Main(string[] args)
        {
            using (var db = new TestEntities())
            {
                var join = db.Instructor
                    .Join(
                        db.Class,
                        i => i.InstructorId,
                        c => c.InstructorId,
                        (i, c) => new
                        {
                            Instructor = i,
                            Class = c
                        })
                    .ToList();

                var groupJoin = db.Instructor
                    .GroupJoin(
                        db.Class,
                        i => i.InstructorId,
                        c => c.InstructorId,
                        (i, c) => new
                        {
                            Instructor = i,
                            Class = c
                        })
                    .ToList();

                var flattenGroupJoin = db.Instructor
                    .GroupJoin(
                        db.Class,
                        i => i.InstructorId,
                        c => c.InstructorId,
                        (i, c) => new
                        {
                            Instructor = i,
                            Class = c
                        })
                    .SelectMany(r => r.Class, (r, c) => new
                    {
                        Instructor = r.Instructor,
                        Class = c
                    })
                    .ToList();
            }
        }
    }
}

Following are the result.

** Join **

Visual Studio Debug
VS join result

SQL Profiler

SELECT 
    [Extent1].[InstructorId] AS [InstructorId], 
    [Extent1].[FirstName] AS [FirstName], 
    [Extent1].[LastName] AS [LastName], 
    [Extent2].[ClassId] AS [ClassId], 
    [Extent2].[Name] AS [Name], 
    [Extent2].[ClassNumber] AS [ClassNumber], 
    [Extent2].[InstructorId] AS [InstructorId1]
    FROM  [dbo].[Instructor] AS [Extent1]
    INNER JOIN [dbo].[Class] AS [Extent2] ON [Extent1].[InstructorId] = [Extent2].[InstructorId]

** Group Join **

`GroupJoin` result in grouped data by specified entity. In this case I grouped by `Instructor`.

Visual Studio Debug
VS groupjoin result

SQL Profiler

SELECT 
    [Project1].[InstructorId] AS [InstructorId], 
    [Project1].[FirstName] AS [FirstName], 
    [Project1].[LastName] AS [LastName], 
    [Project1].[C1] AS [C1], 
    [Project1].[ClassId] AS [ClassId], 
    [Project1].[Name] AS [Name], 
    [Project1].[ClassNumber] AS [ClassNumber], 
    [Project1].[InstructorId1] AS [InstructorId1]
    FROM ( SELECT 
        [Extent1].[InstructorId] AS [InstructorId], 
        [Extent1].[FirstName] AS [FirstName], 
        [Extent1].[LastName] AS [LastName], 
        [Extent2].[ClassId] AS [ClassId], 
        [Extent2].[Name] AS [Name], 
        [Extent2].[ClassNumber] AS [ClassNumber], 
        [Extent2].[InstructorId] AS [InstructorId1], 
        CASE WHEN ([Extent2].[ClassId] IS NULL) THEN CAST(NULL AS int) ELSE 1 END AS [C1]
        FROM  [dbo].[Instructor] AS [Extent1]
        LEFT OUTER JOIN [dbo].[Class] AS [Extent2] ON [Extent1].[InstructorId] = [Extent2].[InstructorId]
    )  AS [Project1]
    ORDER BY [Project1].[InstructorId] ASC, [Project1].[C1] ASC

** Flatten Group Join **

Visual Studio Debug
VS flatten groupjoin result

SQL Profiler

SELECT 
    [Extent1].[InstructorId] AS [InstructorId], 
    [Extent1].[FirstName] AS [FirstName], 
    [Extent1].[LastName] AS [LastName], 
    [Extent2].[ClassId] AS [ClassId], 
    [Extent2].[Name] AS [Name], 
    [Extent2].[ClassNumber] AS [ClassNumber], 
    [Extent2].[InstructorId] AS [InstructorId1]
    FROM  [dbo].[Instructor] AS [Extent1]
    INNER JOIN [dbo].[Class] AS [Extent2] ON [Extent1].[InstructorId] = [Extent2].[InstructorId]
 
Leave a comment

Posted by on May 14, 2019 in General

 

Tags: , , , , , ,

Iterator, Enumerator and Yield Keyword

Note: The example code below is only used to demonstrate my point, by all means it’s not SOLID.

In Object Oriented Programming
Iterating is a process of repeating similar steps or functions.
Enumerating is an action of going through an entire collection of objects.

In C#
Iterator refers to set of functions to be executed on a collection.
For example:

Func<User, User> deactivate = (User u) =>
{
    u.IsActive = false;
    return u;
};

Enumerator refer to an object type that result from iterating through a collection.
For example:

IEnumerable<User> result = Users.Select(x => deactivate(x));

Complete code:

public class User
{
    public bool IsActive { get; set; }
}

public IEnumerable<User> DeactivateUsers()
{
    User[] Users = {
        new User { IsActive = true },
        new User { IsActive = true },
        new User { IsActive = true }
    };

    Func<User, User> deactivate = (User u) =>
    {
        u.IsActive = false;
        return u;
    };

    IEnumerable<User> result = Users.Select(x => deactivate(x));
    return result;
}

Yield Keyword
Yield keyword allow you to indicate that the code where it is being used is an iterator. The code must return a type of IEnumerable or IEnumerable<T>.

Continue from example above. We can write it different way, such as:

public IEnumerable<User> DeactivateUsers()
{
    User[] Users = {
        new User { IsActive = true },
        new User { IsActive = true },
        new User { IsActive = true }
    };

    List<User> result = new List<User>();

    foreach (var u in Users)
    {
        u.IsActive = false;
        result.Add(u);
    }

    return result;
}

Or another way, which utilize yield keyword to return Enumerator object for us.

public IEnumerable<User> DeactivateUsers()
{
    User[] Users = {
        new User { IsActive = true },
        new User { IsActive = true },
        new User { IsActive = true }
    };

    foreach (var u in Users)
    {
        u.IsActive = false;
        yield return u;
    }
}

References:
MSDN
Stackoverflow

 
Leave a comment

Posted by on May 10, 2019 in General

 

Tags: , , , , , ,

 
%d bloggers like this: