6 ways to go from Markdown to Azure Web App

Everything started when I wanted to share a blog post in progress to someone for review. I didn't want to create a copy, and I was looking for an extremely simple way to share; like an url. This blog post is about all my journey to find that method and all the great possibilities available. I was really happy to that Azure Web App.
I'm writing in Markdown, it's a syntax I really like because it's simple no special application is required to use it. To know more about it see my previous post: Why I switch to Markdown, First VSCode Tasks in less than 5 minutes and Meet my new best friend: Visual Studio Code. The more I use it, the more I like it. I started using it not only not only for blogging, but also for all kinds of notes.

DropBox

One very good thing about Markdown is the fact that is compatible with all platforms. Because of that, I keep my texts in Dropbox. Why not Google Drive or OneDrive? Because Dropbox automatically generates the HTML version so my reviewer could read it in a beautiful format. The file is share-able very easily and if authenticated my reviewer could write comment.
dropboxpostsharing
In the PRO version, of DropBox, you can give access only to specific user. That would be very nice for sharing files inside a business or more sensible information.
Unfortunately for me, I don't want to force my reviewer to register. Another interesting fact is that relative paths for images aren't supported. So all images/ charts need also to be share individually before added in the text.

Repositories: GitHub, Bitbucket, etc.

By default, most repositories convert markdown file to HTML so very easy to read. It's also a very good way to have a saved copy. But then you need to have a public repository or give access to people...
Only using repository was not good enough in my case because I don't wish to share unfinished work with everyone.

Jekyll


Option 1 - Jekyll

Jekyll is a static website generator written in Ruby. It's really well integrated to Github, and you can even host your blog in a Github repository. However, since I would prefer to keep my in progress work more private, I decided to go with Bitbucket. Bitbucket is a great repository that supports Git and Mercurial system and allowed private repositories.
We could have Jekyll in a Git repository host on Bitbucket that would be hook-up to an Azure Web App with a continuous deployment.
Here the steps:
  1. First create a private repository from Bitbucket.
  2. Clone that fresh repository on your local machine.
  3. Now it's time to create your Jekyll site.
    • If you don't have Ruby or Jekyll already installed on your machine now it's time. It's very easy just follow the instruction on the official website.
    • To create a new site, open a command prompt and type the command: jekyll new NameOfMySite then cd ./NameOfMySite and jekyll serve
    To see your new site you just need to browse to http:localhost:4000. Add your Markdown files to the folder _posts and be sure they respect the naming convention YYYY-MM-DD-Title.md
  4. Now it's time to add all the files to our Git repository with the command git add -A, and before pushing let create a new Azure Web App.
  5. Go to http://portal.azure.com a create a new Azure Web App.
    CreateAzureWebApp
    • From the top left click the "+ New" button.
    • Select Web+ Mobile, then click on Web App
    • Fill-up the name, subscription plan and click the create button.
  6. After few second, the Web App will be ready. It's time to add a continuous deployment to it.
    AddContinuous
    Note: that right now the deployment settings are FTP.
    • In the Web App blade, if not already go in the Setting section.
    • Scroll done the Settings to Continuous deployment and click on it.
    • Now choose your source control, in this case Bitbucket.
  7. It's now time to publish our site to our Remote repository with git push.
  8. In the Azure portal, you will see the deployment progress and history.
    DeploymentHistory
The combination Jekyll / Bitbucket / Azure Web App work great, but we need to generate the code locally and checked-in both source and generated content in the repository. Furthermore, since we need to generate the code, Ruby and Jekyll need to be installed on every machine we will be using.

Option 2 - Jekyll Extension to Azure Web App

I found a really great Azure Web App Extension Jekyll Extenstion on GitHub. That will simplify a lot the process thanks to Cory's works. To use it simple follow the four steps explain on the Github page:

  1. Create an Azure Web App 
  2. Set an App Setting for SCM_COMMAND_IDLE_TIMEOUT to 600. From the Web App blade click on Settings and select Application settings.  Add the new line, and click the save button.
     SCM_AppSetting
  3. Install the Jekyll Site Extension
    • Always From the Web App blade click on Tools, then select Extension
    • Click Add button
    • Found and select Jekyll Extension AddJekyllExtension
  4. Now we need to hook up your Git repository or Push a local (in Azure) Git repository with your Jekyll site.
I really liked this solution. It's very simple to install. Because it used a repository, I can keep a historic of all my texts. Moreover, only the texts and images are in the repository, and since the site is generated in the cloud, no need to install anything on other machines.
WriteFromVSCode
Directly from Visual Studio Code, I can write my article, and when I'm read I just need to do a push (still inside VSCode). The site will automatically be built and deployed in my Azure Web App.

Santra.Snow

NancylogoWhile doing my research, I found Sandra.Snow another static site generator inspired from Jekyll but in .Net using Nancy library.
To use it, a little bit of work is required. The easiest way is to fork the Github project and compile the solution to get dlls and exes.
  • Create a new folder for your site [MySnowSite].
  • In MySnowSite folder, create another folder Sandra.Snow.Processor and copy/paste: Nancy.dll, Nancy.Testing.dll, Nancy.ViewEngines.Razor.dll and Snow.exe generated previously.
  • You can now copy the Sandra.Snow/SnowSite/Snow folder into MySnowSite folder.
  • Add deployment and deploy.cmd files from Sandra.Snow/SnowSite into MySnowSite folder.
SandraSnowFolder
Few changes were required in deploy.cmd (line: 29, 31, 56, 57)
@echo off

:: ----------------------
:: KUDU Deployment Script
:: ----------------------

:: Setup
:: -----

setlocal enabledelayedexpansion

SET ARTIFACTS=%~dp0%artifacts

IF NOT DEFINED DEPLOYMENT_SOURCE (
  SET DEPLOYMENT_SOURCE=%~dp0%.
)

IF NOT DEFINED DEPLOYMENT_TARGET (
  SET DEPLOYMENT_TARGET=%ARTIFACTS%\wwwroot
)

::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:: Deployment
:: ----------

:: 3. Build Snow Site
echo -----
echo Start - Building the Snow Site
echo Running Snow.exe config=%DEPLOYMENT_SOURCE%\Snow\
pushd %DEPLOYMENT_SOURCE%
call  %DEPLOYMENT_SOURCE%\Sandra.Snow.Processor\Snow.exe config=%DEPLOYMENT_SOURCE%\Snow\
IF !ERRORLEVEL! NEQ 0 goto error
echo Finish - Building the Snow Site
echo -----


IF NOT DEFINED NEXT_MANIFEST_PATH (
  SET NEXT_MANIFEST_PATH=%ARTIFACTS%\manifest

  IF NOT DEFINED PREVIOUS_MANIFEST_PATH (
SET PREVIOUS_MANIFEST_PATH=%ARTIFACTS%\manifest
  )
)

IF NOT DEFINED KUDU_SYNC_COMMAND (
  :: Install kudu sync
  echo Installing Kudu Sync
  call npm install kudusync -g --silent
  IF !ERRORLEVEL! NEQ 0 goto error

  :: Locally just running "kuduSync" would also work
  SET KUDU_SYNC_COMMAND=node "%appdata%\npm\node_modules\kuduSync\bin\kuduSync"
)


echo Kudu Sync from "%DEPLOYMENT_SOURCE%\Snow\Website" to "%DEPLOYMENT_TARGET%"
call %KUDU_SYNC_COMMAND% -q -f "%DEPLOYMENT_SOURCE%\Snow\Website" -t "%DEPLOYMENT_TARGET%" -n "%NEXT_MANIFEST_PATH%" -p "%PREVIOUS_MANIFEST_PATH%" -i ".git;.deployment;deploy.cmd" 2>nul
IF !ERRORLEVEL! NEQ 0 goto error

::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

goto end

:error
echo An error has occured during web site deployment.
exit /b 1

:end
echo Finished successfully.
Like previously created a Azure Web App and hook up a Git repository or push to an Azure one. You can find a lot of information on the blog of Sandra.Snow creator Phillip Haydon.

Bonus

For both Jekyll (option 2) and Sandra.Snow that used Azure Web App continuous deployment use can use Dropbox instead of Git repository. Why would you use Dropbox? Well, since Dropbox is available on any kind of platform, you would be able to write from your iPad or android tablet, or anything! To learn more about how to do it, see one of my previous post: Setup an automatic deployment on Azure with Dropbox in 5 minutes.
Just for the fun, I created one theme for Sandra.Snow that I put on GitHub: Sandra.Snow.NotesTheme, feel free to use it.

Enjoy!

~Frank Boucher