Konda.eu

Tag Archives: asp.net 5

No comments

Continuous Integration from Visual Studio Team Services to Azure with NodeJs, ASP.NET 5, PHP...

NodeJs, ASP.NET 5, PHP, you name it, it can run on Azure as an App Service (previously known as Web App). But in modern development cycle this simply isn't enough. Things like CD (continuous deployment) and CI (continuous integration) are a must for a modern development process. Azure supports continuous integration of out the box, but you can quickly stumble upon an obstacle if you want to perform custom build/install steps such as NodeJs or ASP.NET 5 package restore, JavaScript bundling and minimisation...

Visual Studio Team Services (VS TS ex - Visual Studio Online) is absolutely awesome at this. It gives you free source control, managing work items and most importantly for me, continuous deployment and integration. But as always, not everything is as good as it seems. Things may quickly complicate when you go outside of Microsoft's waters.

Setting up the build process

My usual build process (bellow is specific for ASP.NET 5 website I used, if you're interested in ASP.NET 5 Build script, take a look at it here):

build-process

Note: Azure Web App Deployment is DISABLED, replaced by PowerShell script.

I solved all of my problems with a simple PowerShell script:

param($websiteName, $packOutput)

$website = Get-AzureWebsite -Name $websiteName

# get the scm url to use with MSDeploy.  By default this will be the second in the array
$msdeployurl = $website.EnabledHostNames[1]


$publishProperties = @{'WebPublishMethod'='MSDeploy';
                        'MSDeployServiceUrl'=$msdeployurl;
                        'DeployIisAppPath'=$website.Name;
                        'Username'=$website.PublishingUsername;
                        'Password'=$website.PublishingPassword}


$publishScript = "${env:ProgramFiles(x86)}\Microsoft Visual Studio 14.0\Common7\IDE\Extensions\Microsoft\Web Tools\Publish\Scripts\default-publish.ps1"


Stop-AzureWebsite -Name $websiteName
. $publishScript -publishProperties $publishProperties  -packOutput $packOutput
Start-AzureWebsite -Name $websiteName

In short what it does, it connects to Azure, finds required Web App, stops it, syncs only differences to Azure to keep it up to date, and starts the Web App back up.

Usage itself is pretty simple. Add an Azure PowerShell build step in your build process. On the right side in the configurations, specify Azure connection type and subscription. In the path select path to the PowerShell script and provide arguments, which are which Web App and which directories to sync (example below).

My usual configuration is something like:

-websiteName WebsiteName -packOutput $(Build.SourcesDirectory)\bin\output

Don't forget to replace WebsiteName with your actual website name and build variables on msdn.

build-setting

Enabling continuous integration

Simply go to Triggers tab and check Continuous integration (CI) checkbox to enable it.

enable-ci

Conclusion

I am aware, that Azure also supports Custom Deployment Scripts, but I prefer things described above. That way you keep unnecessary files produced during build or things that don't really need to be deployed away, keeping your production environment clean and also integrating your entire development cycle with unit testing, load tests or building a C++ library if your app needs it.

No comments

ASP.NET 5 install and build script

I really like ASP.NET 5, but hate it when I'm left without Visual Studio to deploy it or am doing continuous integration from Visual Studio Team Services or other tools (such as vscode). To ease my pain I came up with a simple powershell script that does everything for me. By everything I mean install dot net execution environment, install required packages for selected project, build it and publish it.

# bootstrap DNVM into this session.
&{$Branch='dev';iex ((new-object net.webclient).DownloadString('https://raw.githubusercontent.com/aspnet/Home/dev/dnvminstall.ps1'))}

# load up the global.json so we can find the DNX version
$globalJson = Get-Content -Path $PSScriptRoot\global.json -Raw -ErrorAction Ignore | ConvertFrom-Json -ErrorAction Ignore

if($globalJson)
{
    $dnxVersion = $globalJson.sdk.version
}
else
{
    Write-Warning "Unable to locate global.json to determine using 'latest'"
    $dnxVersion = "latest"
}

# install DNX
# only installs the default (x86, clr) runtime of the framework.
# If you need additional architectures or runtimes you should add additional calls
# ex: & $env:USERPROFILE\.dnx\bin\dnvm install $dnxVersion -r coreclr
& $env:USERPROFILE\.dnx\bin\dnvm install $dnxVersion -Persistent

 # run DNU restore on all project.json files in the src folder including 2>1 to redirect stderr to stdout for badly behaved tools
Get-ChildItem -Path $PSScriptRoot\src -Filter project.json -Recurse | ForEach-Object { & dnu restore $_.FullName 2>1 }

# Restore packages
dnu restore

# Build to check for errors
dnu build

# Pack 
dnu publish --runtime active

Usage, extremely simple. Open powershell and run it!

 

5 comments

ASP.NET 5 and SignalR 3

SignalR is a great library from Microsoft for working with WebSockets. It's really fast and supports various fallbacks even for people that use browsers from stone age itself (IE6 for example, but let just hope nobody uses it anymore).

Of course not everything is that nice... When it comes to implementing it in ASP.NET 5 with absolutely NO documentation the entire process of setting this two frameworks/libraries together can be very, very painful.

First thing, to be able to download latest version of SignalR 3 for ASP.NET 5 MyGet repository needs to be referenced. I Added Nuget.config with the following content, but you can also add an URL to global NuGet configuration:

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <packageRestore>
    <add key="enabled" value="True" /> <!-- Allow NuGet to download missing packages -->
    <add key="automatic" value="True" /> <!-- Automatically check for missing packages during build in Visual Studio -->
  </packageRestore>
  <packageSources>
    <add key="aspnetmaster" value="https://www.myget.org/F/aspnetmaster/api/v3/index.json" />
  </packageSources>
</configuration>

After that is set up, go to project.json and add the following line to dependencies:

"Microsoft.AspNet.SignalR.Server": "3.0.0-*"

The last thing needed to be done is to add SignalR to the application. To do that go to Startup.cs and make sure that you have the following line somewhere in Configure method.

public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
{
    // ...
    app.UseSignalR();
    // ...
}

At this step everything is ready to go. You can follow any SignalR tutorial, like this chat room for example. At this point there are no updated client side JavaScript libraries, version 2.2.0 works just fine but on the bad side you're still stuck with jQuery...

Some unfortunate souls like myself may stumble upon the following exception:

InvalidOperationException: No service for type 'Microsoft.AspNet.SignalR.Hubs.IJavaScriptProxyGenerator' has been registered.

At this point there are two choices. First one is to manually generate JavaScript files for all Hubs in the project, more about this you can read here, or the second option that I prefer is to register the default provider and all of the JavaScript code is automatically generated. To do this, simply go back to your Startup.cs into ConfigureServices method, and make sure that you have the following line inside:

public void ConfigureServices(IServiceCollection services)
{
    // ...
    services.AddSignalR();
    // ...
}

That's it! SignalR 3 should now successfully work together with ASP.NET 5 with automatic code generation.

1 comment

C# and AngularJS - Receive Post data

AngularJS is awesome, C# also. But AngularJS has slightly unstandardized way of sending data over networks. Data is packet body instead of header, which may cause quite some problems  if you're unaware of this.

MVC Framework will automatically deserialize data into object when it receives, you only need to tell it that it should look for data in body instead of header.

[HttpPost]
public int method([FromBody]Model m)
{
        // ...

 

No comments

ASP.NET 5 Change Default Views Directory

Testing out new asp.net 5 MVC project template and integrating it into an existing project, predefined project structure didn't really suite my needs. Most of the things work if you move them into a subdirectory, Views directory isn't one of those. You need to create IViewLocationExpander and add it to appropriate service. Example bellow remaps everything into Server subdirectory.

public class ViewsLocationRemapper : IViewLocationExpander
{
    public void PopulateValues(ViewLocationExpanderContext context)
    {
        // Do nothing
    }

    public IEnumerable<string> ExpandViewLocations(ViewLocationExpanderContext context, IEnumerable<string> viewLocations)
    {
        return viewLocations.Select(loc => "Server" + loc);
    } 
}

And then in Startup.cs, ConfigureServices. method, simply call:

services.Configure<RazorViewEngineOptions>(o =>
{
    o.ViewLocationExpanders.Add(new ViewsLocationRemapper());
});

Of course it can be used for simple tasks like prefixing Shader directory with _ (underscore), so that it can be easily found in Solution Explorer.