Print this Post

Automate downloads of Microsoft Dynamics NAV Cumulative Updates

Yesterday, I blogged about the availability of the first Cumulative Update of NAV 2017. In that post, I talked about the fact that Microsoft recently changed the place where to download them.

This also means the way of automating the download had to be changed. In fact, the PowerShell function that was part of my repository (and built by Kamil originally), didn’t work anymore. I didn’t really know how to get around this – but luckily, I have a really clever colleague (well, I do have more than one ;-)) that did find a way in .Net. And we managed to transfer the logic to PowerShell .. (literally “transfer”, not rewrite … you’ll see what I mean ;-)).

I’m not going to tell you “how” it works – you can find out in the code. I’ll just show you what we created, and how it works.


The main functionality is in C# .. and you can make it available by loading and compiling it by simply calling “Load-NAVCumulativeUpdateHelper”. In C#, you’re just that more flexible – and since we’re working in HTML, and figuring stuff out in HTML, it’s just much nicer to do so in C#. And .. the fact that this is the preferred environment of my colleague might have a reason in that as well ;-).

The PowerShell function is loading (compiling) two functions in memory and make them available to me:

Let me show you some examples on how to use them.

This example, is going to show you a gridview of all download URLs in a gridview, and when you select one and press ok, it starts the download. It uses the “GetDownloadLocales” to get all the languages one-by-one:


The other function “GetDownloadDetail”, you need to specify the Locale (like “en-US”), which can be used to speed up the process (no need to generate and navigate to all the URLs of all the “Locales”), like:


You also see that the functions need a ProductID. Well, that’s how Download Center works .. If you have the ID, you know what to download .. and to get to that ProductID, let’s look into the next function.


This function is based on the good old function that Kamil Sacek once wrote – based on the ideas of my colleague. It is going to look at the Microsoft Dynamics NAV Team Blog to figure out the link to the Download Center – and yes – to figure out the ProductID. And obviously, going to use the Helper above to be able to start the download(s). It’s still limited to only search for the latest Cumulative Update. I’m working on a solution (probably a new function) to start the download from a specific blog article, or KB article.

The function above can simply be used in this way (and here are some more examples) which will simply start the download to the specified folder:

The function also creates a JSON with specifics about the download. Not because it’s necessary .. just because we can ;-).

Do I need the complete module to be able to do this?

No. You basically only need these two functions. So go ahead and automate! :-). The result is a much more stable way to automate these downloads, simply because Download Center doesn’t require you to run through a complicated login process ..

5.00 avg. rating (96% score) - 1 vote

Permanent link to this article: http://www.waldo.be/2016/12/09/automate-downloads-of-cumulative-updates/


3 pings

Skip to comment form

  1. Thomas

    Good job!!

    1. waldo

      Thanks 🙂

  2. The D

    Actually you could do without instancing an Internet Explorer COM object in “Get-NAVCumulativeUpdateFile”. Just download the plain HTML page and parse through it using RegEx. It is much easier to REALLY automate it and have it run in an non-interactive session (we are actually doing it using a JobQueue Codeunit)

    1. waldo

      Thanks for the suggestion! Something needs to change indeed – must get much more stable :-/

  3. Kristof

    Didn’t an older version allow me to download a dedicated CU Version?

    Due to the latest “mess from MS” with 2017 Cu2 or 2016CU15 or … the script will of course fail as it won’t be able to download CU2 at all … I was about to use and test this scripts which i can’t right now… [get file, unzip, unblock files, create platform hotfixfolder – all in one script]

    However, would be nice to allow the CU Version to be part [again?] of the parameters and used like the following:

    $blogurl = $feed.SelectNodes(“/rss/channel/item[./category=’NAV $version’ and ./category=’Cumulative Updates’ and ./title=’Cumulative Update $CUVersion for Microsoft Dynamics NAV $version has been released’]”).link | Select-Object -First 1

    Br and a nice Weekend,

    1. waldo

      You are right. It’s still on my list to do. but please, don’t hold yourself to create issues on GitHub 😉

  4. Nicolai Hansen

    When I use Get-NAVCumulativeUpdateFile and set version to 2015, it get’s the wrong build (41779) I guess because it appears on https://blogs.msdn.microsoft.com/nav/2017/02/08/cumulative-update-28-for-microsoft-dynamics-nav-2015-has-been-released/ before the real buildnumber. It does download the correct file though. Maybe it would be better to fetch the buildnumber from the KB article, but I guess that could also go wrong if Microsoft decides to put multiple KB numbers on the blog post? 🙂

  5. Robert

    Awesome job….

  6. Robert

    Just a small addition to eliminate an issue I found with 2013/ 2013 R2 blog page not supplying the “Build No.”

    Insert this line into the Get-NAVCumulativeUpdateFile after the line “112”-> $Build = $ie.Document.body.inner……

    if ($Build.length -gt 5) {$Build = ‘xxxxx’}

  7. Rafał

    This would be great but right now it is not working for me:

    PS >Get-NAVCumulativeUpdateFile -versions 2017 -CountryCode W1 -DownloadFolder C:\TMP
    Processing parameters W1 2017
    Searching for RSS item
    Reading blog page https://blogs.msdn.microsoft.com/nav/2017/03/06/cumulative-update-04-for-microsoft-dynamics-nav-2017-has-been-released/
    Searching KB Url
    Microsoft Download Center link
    Found Product ID 54802
    Loading NAVCumulativeUpdateHelper
    An error occurred while enumerating through a collection: Object reference not set to an instance of an object..
    At C:\Program Files\WindowsPowerShell\Modules\Cloud.Ready.Software.NAV\\Upgrade\Get-NAVCumulativeUpdateFile.ps1:97 char:21
    + … $DownloadLinks = [MicrosoftDownload.MicrosoftDownloadPars …
    + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo : InvalidOperation: (MicrosoftDownlo…oadLocales>d__2:d__2) [], RuntimeException
    + FullyQualifiedErrorId : BadEnumeration

    1. waldo

      Works like a charm here (just tested it).

      Sure you have the last version of the function? I noticed your “version”-parameter is wrong (should be “version” not “versions”)

  8. dbabas

    Hi Waldo and thanks for the post.

    When I am trying your first example I am getting the following error. Could you please let me know what could be wrong?

    An error occurred while enumerating through a collection: The remote server returned an error: (404) Not Found..
    At C:\Tools\test.ps1:3 char:1
    + $MyDownload = $Locales | out-gridview -PassThru | foreach {$_.Downloa …
    + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo : InvalidOperation: (MicrosoftDownlo…oadLocales>d__2:d__2) [], RuntimeExcep
    + FullyQualifiedErrorId : BadEnumeration

    Thanks in advance.

    1. waldo

      Sorry for the late reply – is this still the case?

    2. dbabas

      Hi, yes I just tried again and I am getting the same error.

    3. waldo

      I just tried this:
      Get-NAVCumulativeUpdateFile -version 2017 -CountryCode W1 -DownloadFolder C:\_Downloads
      on a new pc, and it works.

      – did you update the modules to the latest version?
      – do you have internet connection? (the error states a 404)
      – can you access “https://blogs.msdn.microsoft.com/nav/2017/05/08/cumulative-update-06-for-microsoft-dynamics-nav-2017-has-been-released/” with that user on that machine?

    4. dbabas

      Hi waldo,

      Thanks for your reply.

      Get-NAVCumulativeUpdateFile works for me too. I’m getting the error when I’m trying to run your first example:

      $Locales = [MicrosoftDownload.MicrosoftDownloadParser]::GetDownloadLocales(54317)
      $MyDownload = $Locales | out-gridview -PassThru | foreach {
      Start-BitsTransfer -Source $_.DownloadUrl -Destination C:\_Download\Filename.zip

      It seems that the call to [MicrosoftDownload.MicrosoftDownloadParser]::GetDownloadLocales(54317) returns the 404 error.

      The answer to all your questions is yes.

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.

%d bloggers like this: