Wednesday, October 29, 2014

Powershell script for starting and stopping Azure VMs

At work we've got 2 subscriptions in which we've got a bunch of Azure VMs. At night, we try to shut these things down to save a bit of cost. I was getting a bit tired of going to the portal all the time, so I decided to play around with PowerShell a bit.

So I came up with this script that allows me to shut down the VMs without having to go to the portal. Please note: so there is a subscription for DEV/TEST and one for PROD. Furthermore, I'm not shutting down the domain controllers ( macine name ends with AD01 ).


$OTASubscription = "SomeSubscriptionName"
$PRODSubscription = "AnotherSubscriptionName" 

Function PromptForAzureLogin
{
        $title = "Log in to Azure first?"
        $message = "Do you want to log in to Azure and install a management certificate ?"
 
        $yes = New-Object System.Management.Automation.Host.ChoiceDescription "&Yes", "Yes"
        $no = New-Object System.Management.Automation.Host.ChoiceDescription "&No", "No"
        $options = [System.Management.Automation.Host.ChoiceDescription[]]($yes, $no)

        $result = $host.ui.PromptForChoice($title, $message, $options, 1)

        switch ($result)
            {
                0 {
                    # This will cause a login screen to appear which lets you login
                    Add-AzureAccount

                     # Displays a list of subscriptions
                    Get-AzureSubscription
                }
                1 {
                    # Do nothing
                }
            }
}

Function SelectSubscription
{
        $title = "Select subscription"
        $message = "Please select AzureSubscription"

        $ota = New-Object System.Management.Automation.Host.ChoiceDescription "&OTA", "OTA"
        $prod = New-Object System.Management.Automation.Host.ChoiceDescription "&PROD", "PRODUCTION
        $options = [System.Management.Automation.Host.ChoiceDescription[]]($ota, $prod)

        $result = $host.ui.PromptForChoice($title, $message, $options, 0)
        switch ($result)
            {
                0 {
                    Select-AzureSubscription $OTASubscription -Current

                    Write-Host "OTA Subscription selected" -foregroundcolor green
                }
                1 {
                    Select-AzureSubscription $PRODSubscription -Current
                    Write-Host "PRODUCTION Subscription selected" -foregroundcolor green
                }
            }
}

Function PromptForStartStop
{
    $title = "Start or Stop environment?"
    $message = "Do you want to start or stop the VMs? (All except -AD01)"

    $start = New-Object System.Management.Automation.Host.ChoiceDescription "&Start", "Start"
    $stop = New-Object System.Management.Automation.Host.ChoiceDescription "S&top", "Stop"
    $cancel = New-Object System.Management.Automation.Host.ChoiceDescription "&Cancel", "Do nothing"

    $options = [System.Management.Automation.Host.ChoiceDescription[]]($start, $stop, $cancel)

    $result = $host.ui.PromptForChoice($title, $message, $options, 0)

    $vmsToStop = Get-AzureVM | where {$_.Name -notlike "*AD01" }
    switch ($result)
        {
            0 {
                # Starting VMs
                for($i = 0; $i -le $vmsToStop.count -1; $i++) {
                    $tuple = $vmsToStop[$i]
                    Write-Host "Starting box named: " $tuple.Name -foregroundcolor green
                    Write-Progress -Activity "Starting VM" -status $tuple.Name -percentComplete ($i / $vmsToStop.count*100)

                    Start-AzureVM -ServiceName $tuple.ServiceName -Name $tuple.Name
                }
            }
            1 {
                for($i = 0; $i -le $vmsToStop.count -1; $i++) {
                    $tuple = $vmsToStop[$i]
                    Write-Host "Stopping box named: " $tuple.Name -foregroundcolor green
                    Write-Progress -Activity "Stopping VM" -status $tuple.Name -percentComplete ($i / $vmsToStop.count*100)
                   
                    Stop-AzureVM -ServiceName $tuple.ServiceName -Name $tuple.Name -StayProvisioned
                }
            }
            2 {
                # Do nothing
                Write-Host "Doing nothing ..." -foregroundcolor green
            }
        }
}

cls
PromptForAzureLogin
SelectSubscription
Write-Host "Here are the boxes in the current subscription:" -foregroundcolor green
Get-AzureVM
PromptForStartStop
Write-Host "Here's the situation now:" -foregroundcolor green
Get-AzureVM


Tuesday, October 28, 2014

Generalist or specialist?

Recently I had an interesting discussion with one of the Software Architects at my company about my future plans. My ambition is to remain versatile and broad, in the sense that I want to be able to work with many different languages ( C#, JavaScript, F#, PHP, Go, Python maybe ) and work with different paradigms ( OOP and functional ) and with different technologies ( SQL - NoSQL - Graph DBs ), platforms etc. etc. It's such a beautiful landscape of stuff out there right now, and I want to learn about it all!

Of course, there's the generalist vs the specialist discussion that I had many of times. I'm afraid I'm more of a generalist than I am a specialist. I know a little about a lot whereas there are people that know a lot about little. Which, according to the architect, might result in me being not as desirable for companies to hire.

This morning I decided I'm going to embrace and enjoy it, as opposed to force myself to focus on merely one technology. I'm a believer in 'the right tool for the right job' and I think that we need to start looking at that more broad than thusfar. For instance: use a graph database if you want to model things and their relations, don't use SQL. Don't build a fully fledged WCF service with n-tier application with EF on top of SQL server if you just want to store some reference values. Use a NoSQL document store in stead. If you're building highly concurrent stuff with parallel computations, consider using a functional programming language like F#. Microsoft has a rich set of technologies available for handling all of these challenges, but there's just beautiful stuff out there that's just a bit better at certain things. I want to add those to my technology toolbelt too. Thankfully, Microsoft seems embrace other technologies like Node in Azure and that's awesome! That means I'm on par with their current philosophy.

So, I'll stay true to what I enjoy doing and that's looking around me for cool new stuff. I don't think that implies having shiny-new-object syndrome since I want to know them but not necessarily apply them in my next project. Just knowing about them and knowing what problem they're trying to solve will give me a better understanding of the world of IT. And there's plenty out there too, so I can't complain !


Wednesday, October 22, 2014

InfoQ panel discussion on improving architecture

I watching this video the other day where a panel discusses 'What is the Best Way to Improve Architecture'. These guys have some really interesting insights on MicroServices, CQRS and EventSourcing.

So go and check it out here.


Monday, October 20, 2014

How we're writing CodedUI tests

A couple of sprints ago I had a bit too much time on my hands and our tester was short on time. Therefore, my colleague and me decided to help him out by writing some of the CodedUI tests for him.

We started out by looking at the way they had been doing it thusfar, but we could see some room for improvement. So we set out two write CodedUI tests that were:

  1. Easy to maintain
  2. Supported re-use of steps
  3. Easy to read

This is what we ended up with:

[TestMethod]
public void SomeScreen_Should_ShowStufIfSomething()
{
    var category = "Whatever";

    var page = new LoginPage(this.TestedPage.BrowserInstance)
        .LoginAsAdmin()
        .GoToOtherScreen()
        .SearchForAccountNumber(ValidAccountNumber)
        .ClickOnFirstResult()
        .ClickOnModelDistributionEditLink(category)
        .SetModelDistribution(null);

    page.ModelRows.Single(x => x.Category == category).HasSomething.Should().BeFalse();
}
Inspiration to write code like this came from this blogpost and this library.

What we do is we create a class per page. We create a couple of partials for that class, one for the page.cs, page.operations.cs and page.elements.cs.

The page.cs only contains the page URL, and in some cases some more stuff like items that indicate that the page is done loading as soon as they appear:

public partial class LoginPage : TestPageBase
{
    public LoginPage(){}
    public LoginPage(BrowserWindow browser): base(browser){}

    public override string PageUri
    {
        get { return "/"; }
    }
}
Then we have the .elements.cs file which contains read-only properties that point to elements on the page:
public partial class LoginPage
{
    private HtmlComboBox BankOrRoleDropDown
    {
        get { return Browser.FindAllById("bank", PropertyExpressionOperator.Contains).FirstOrDefault(); }
    }
    private HtmlEdit PasswordBox
    {
        get { return Browser.FindAllByName("ww").FirstOrDefault(); }
    }
}
And we've got the operations.cs file:
public partial class LoginPage : TestPageBase
{

    public HomePage Login(string role, string password)
    {
        this.ClearCookies();

        this.NavigateTo(BaseUrl);
        Thread.Sleep(500);
        this.BankOrRoleDropDown.SelectedItem = role;
        this.PasswordBox.Text = password;
        this.PasswordBox.SetFocus();
        Keyboard.SendKeys("{Enter}");

        return new HomePage(this.Browser);
    }

    public HomePage LoginAsAdmin()
    {
        return this.Login("Username", "Password");
    }
}
The tests just use sequences of the page.operations methods which are linted together because we implemented it fluently. In order to make querying the page a bit more easy, we wrote a generic helper, which you can find below. Lesson for use devs was to put more classes and id's on stuff that needed to be identified. Now, since all the testers adopted this way of writing CodedUI tests, the developers contribute in making the .elements.cs files for a page they made, so that writing the codedUI operations become a breeze.
public static class BrowserWindowExtensions
{

    public static T FindFirstByClass(this UITestControl browser, string @class, PropertyExpressionOperator searchOption = PropertyExpressionOperator.Contains) where T : UITestControl, new()
    {
        return browser.FindAllByClass(@class, searchOption).FirstOrDefault();
    }

    public static T FindFirstById(this UITestControl browser, string id, PropertyExpressionOperator searchOption = PropertyExpressionOperator.EqualTo) where T : UITestControl, new()
    {
        return browser.FindAllById(id, searchOption).FirstOrDefault();
    }

    public static IEnumerable FindAllById(this UITestControl browser, string id, PropertyExpressionOperator searchOption = PropertyExpressionOperator.EqualTo) where T : UITestControl, new()
    {
        return browser.FindAllByKeyCharacteristic("id", id, searchOption);
    }
    public static IEnumerable FindAllByClass(this UITestControl browser, string @class, PropertyExpressionOperator searchOption = PropertyExpressionOperator.Contains) where T : UITestControl, new()
    {
        return browser.FindAllByKeyCharacteristic("class", @class, searchOption);
    }
    public static IEnumerable FindAllByName(this UITestControl browser, string name, PropertyExpressionOperator searchOption = PropertyExpressionOperator.EqualTo) where T : UITestControl, new()
    {
        return browser.FindAllByKeyCharacteristic("name", name, searchOption);
    }

    public static IEnumerable FindAllByKeyCharacteristic(this UITestControl browser, string keyCharacteristic, string keyCharacteristicValue, PropertyExpressionOperator searchOption) where T : UITestControl, new()
    {
        var element = (T)Activator.CreateInstance(typeof(T), browser);
        element.SearchProperties.Add(keyCharacteristic, keyCharacteristicValue, searchOption);
        var result = element.FindMatchingControls().ToTypedList().ToList();
        return result;
    }

    public static IEnumerable ToTypedList(this UITestControlCollection collection) where T : UITestControl, new()
    {
        var result = new List();
        collection.ToList().ForEach(control => result.Add((T)control));
        return result;
    } 
}

Cool! I just got a pull request!

A couple of weeks ago I wrote a NuGet package because I like Common.Logging and I was under the impression that the NLog adapter for it was getting old. So, I 'rolled my own', checked it in on NuGet and put the source online in GitHub.

A couple of days ago, I got a pull request from someone who's fixed a bug in my code! Did I just start en open source project and did I just get contributers !? ;) Awesome.



The library is nothing, but I'm enjoying the fact that someone's using it and love the constructive way of working together.




Sunday, October 19, 2014

Git tools for Windows

On one of the .NET Rocks! podcasts the other day, I heard about SourceTree which is the Atlassian client for managing Git repositories on your windows machine ( or mac ). I've been using GitHub for windows thusfar, but this indeed looks very nice and I'm a fan of most Atlassian stuff.


GitHub Windows is the one I've been using thusfar. I believe I heard about this tool on Hanselminutes. It looks very nice and works very easy, which also means that the actual Git stuff is abstracted from the user a bit more.


Also on the podcast, tortoisegit was mentioned. When I was using SVN, this was my go-to-tool for doing SVN. This seems to be doing the same thing, but for Git.



Saturday, October 18, 2014

Deadlocks in Async/Await

While trying to figure out what the problem is with our app ( link ) I've been reading up on deadlocks that can occur while doing Async/Await the wrong way. Here's a very insightful article on how deadlocks occur and how they can be avoided.
Basically, if you've got async methods that you're forcing to execute synchronously ( with either .Wait or .Result ) you have to be careful. I would have considered that a code smell and as it turns out, that's true!

So check out this blog post by Stephen Cleary:


Friday, October 17, 2014

I need AngularJS service instances, not singletons

One of the apps we're working with has a bunch of WebApi controllers and a bunch of AngularJS controller talking to them.

So we've got the backend URLs like:
- /api/typeA
- /api/typeB
- /api/typeC
- /api/typeD
- /api/typeE

Yes, we could bundle all the types in one WebApi, but then the object would become quite big and the saving part would require more logic. So we've got separate controllers for every type.

Most controllers only implement GET and POST and we were discussing an elegant way to get that into our app. There were a couple of options:
- Create a Angular service for every WebApi controller
- Create one service that takes the URL with every call
- Do something else ...

AngularJS only provides singletons ( link ) but I would really love to create a service instance that talks to a specific WebApi controller. Therefore I've sent a POC over to my colleague in which I suggest to have Angular inject a factory ( which is a singleton ), which is then able to build instances for each of the WebAPI controllers.

Here's my fiddle: http://jsfiddle.net/jochenvanwylick/0qcwver5/1/


Unresolved: Async/Await call doesn't return. Forcing sync does

We've created this WebApp a while ago that nicely implemented WebApi async calls. Everything seems to have been working fine up until a point in time in which the async/await seems to have stopped working. I can't get my head around what's happened, but the async/await calls don't seem to be returning the control. If anyone has a solution - please do let me know!

StackOverflow question here: http://stackoverflow.com/questions/26231300/async-await-call-doesnt-return-forcing-sync-does

Even Jon Skeet got involed, but didn't come up with a solution. I'm thinking it's either deadlocks (although I REALLY can't see where), or it's some configuration issue.




Thursday, October 16, 2014

Protocol Buffers for the win!

OK, so after Googling for IoC benchmarks, I wondered around a bit on internet looking for serialization related stuff. I came across Protocol Buffers which seems very promising. It's a binary serialization format used by Google and according to these stats it's faster than any of the other methods AND results in a smaller payload.

Check out the project site here, and the NuGet package here.





Tuesday, October 14, 2014

Excellent IoC comparison benchmark for .NET

I was Googling around to see how much the performance suffers from dependency injection with interceptors, I came across this excellent post by Daniel Palme, who compares a bunch of IoC containers for .NET.

Turns out, Ninject isn't all that fast. We've been using it for all our projects, but after reading this post, I'll be looking into LightInject. It seems to support all my use cases: MVC, WebAPI ( with InRequestScope ) and interceptor support.