{"id":2458,"date":"2017-11-19T14:28:32","date_gmt":"2017-11-19T13:28:32","guid":{"rendered":"http:\/\/www.itidea.nl\/?p=2458"},"modified":"2017-11-19T14:28:32","modified_gmt":"2017-11-19T13:28:32","slug":"how-to-reference-a-file-in-azure-function-c-script-function-vs-c-function","status":"publish","type":"post","link":"https:\/\/www.itidea.nl\/index.php\/how-to-reference-a-file-in-azure-function-c-script-function-vs-c-function\/","title":{"rendered":"How to reference a file in Azure function? C# script function vs C# function"},"content":{"rendered":"<p>To explain in detail how to reference a file in an Azure function some background information on the basics of Azure functions is necessary. To complete the story it will all be explained for C# script based function as well as C# compiled functions.<\/p>\n<h4>Azure functions<\/h4>\n<p>Azure functions can be built in the Azure portal, C# script based, or by using Visual Studio by using the Azure Function Tools for Visual Studio 2017 extension.<\/p>\n<p>The Azure function tools provides a set of benefits:<\/p>\n<ul>\n<li>Functions can be edited,\u00a0 built and run from your local development computer<\/li>\n<li>Visual Studio can be used for development<\/li>\n<li>The Azure Functions project can be published directly to Azure<\/li>\n<li>Pre-compiled C# functions are deployed instead of C# script based functions which benefit from a performance perspective<\/li>\n<\/ul>\n<p>Let&#8217;s take a look at some practical differences for both options.<\/p>\n<p>Both are examples of a simple C# HttpTrigger.<\/p>\n<h4>Method signatures<\/h4>\n<h5>C# function<\/h5>\n<pre class=\"brush: csharp; title: ; notranslate\" title=\"\">\r\n&#x5B;FunctionName(&quot;Function1&quot;)]\r\npublic static async Task&lt;HttpResponseMessage&gt; Run(&#x5B;HttpTrigger(AuthorizationLevel.Function, &quot;get&quot;, &quot;post&quot;, Route = null)]HttpRequestMessage req, TraceWriter log)\r\n<\/pre>\n<h5>C# script function<\/h5>\n<pre class=\"brush: csharp; title: ; notranslate\" title=\"\">\r\n public static async Task&lt;HttpResponseMessage&gt; Run(HttpRequestMessage req, TraceWriter log)\r\n <\/pre>\n<p>It can be seen that the C# function uses attributes where the C# script function uses the settings which can be adjusted in the portal or can be maintained in a separate function.json file.<\/p>\n<h4>Project output structure<\/h4>\n<p>A C# function developed and compiled in Visual Studio and deployed to Azure has a slightly different output structure than a C# script function created in the Azure portal.<\/p>\n<p><a href=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/1-C-function-output.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-2470\" src=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/1-C-function-output.png\" alt=\"\" width=\"306\" height=\"247\" srcset=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/1-C-function-output.png 306w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/1-C-function-output-300x242.png 300w\" sizes=\"auto, (max-width: 306px) 100vw, 306px\" \/><\/a><br \/>\nFigure 1 &#8211; C# function output created in VS and deployed to Azure<\/p>\n<p>This is a copy of the directory below &#8216;\\release(or debug)\\net461&#8217; on the local file system. As you can see there is a bin folder which contains the output assembly of the project as well as all the referenced assemblies. The function.json contains the bindings generated by the Azure Function tools from the C# code attributes defined.<\/p>\n<p><a href=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/2-C-script-output.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-2469\" src=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/2-C-script-output.png\" alt=\"\" width=\"308\" height=\"219\" srcset=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/2-C-script-output.png 308w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/2-C-script-output-300x213.png 300w\" sizes=\"auto, (max-width: 308px) 100vw, 308px\" \/><\/a><br \/>\nFigure 2 &#8211; C# script output created in Azure Portal<\/p>\n<p>Bindings are defined in function.json, where the actual C# script code is listed in run.csx, un-compiled and readable in the browser.<\/p>\n<h4>How to reference a file in the project within the function<\/h4>\n<p>How hard can it be, I hear you thinking\u2026 Yeah, my thoughts also..<\/p>\n<h5>What is the current working directory in the function code?<\/h5>\n<p>There are several options for getting a path in .NET<br \/>\nAssembly.GetExecutingAssembly().CodeBase &#8211; Gets the location of the assembly as specified originally; the place where the file is found.<br \/>\nAssembly.GetExecutingAssembly().Location &#8211; Gets the full path or UNC location of the loaded file that contains the manifest.<br \/>\nEnvironment.CurrentDirectory &#8211; Gets the current directory path of the project.<br \/>\nAppDomain.CurrentDomain.BaseDirectory &#8211; Gets the path of the entrypoint of the application or where the current AppDomain is created.<\/p>\n<p>The output for the C# function, locally and published to Azure, as well as the output for the C# script function are displayed in the following figures.<\/p>\n<p><a href=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/3-output-locally.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-2468\" src=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/3-output-locally.png\" alt=\"\" width=\"834\" height=\"58\" srcset=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/3-output-locally.png 834w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/3-output-locally-300x21.png 300w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/3-output-locally-768x53.png 768w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/3-output-locally-600x42.png 600w\" sizes=\"auto, (max-width: 834px) 100vw, 834px\" \/><\/a><br \/>\nFigure 3 &#8211; C# function code output when running locally<\/p>\n<p><a href=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/4-output-Azure.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-2467\" src=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/4-output-Azure.png\" alt=\"\" width=\"711\" height=\"73\" srcset=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/4-output-Azure.png 711w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/4-output-Azure-300x31.png 300w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/4-output-Azure-600x62.png 600w\" sizes=\"auto, (max-width: 711px) 100vw, 711px\" \/><\/a><br \/>\nFigure 4 &#8211; C# function output when published to Azure<\/p>\n<p><a href=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/5-ouput-script-function.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-2466\" src=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/5-ouput-script-function.png\" alt=\"\" width=\"768\" height=\"75\" srcset=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/5-ouput-script-function.png 768w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/5-ouput-script-function-300x29.png 300w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/5-ouput-script-function-600x59.png 600w\" sizes=\"auto, (max-width: 768px) 100vw, 768px\" \/><\/a><br \/>\nFigure 5 &#8211; C# script function output running in Azure portal<\/p>\n<p>In all three situations the different possibilities result in a different location returned and none of them are usable in all three situations.<br \/>\nFor example the Codebase can be used when using a C# function, but when developing a C# script function this path is totally unusable.<\/p>\n<p>To get information about the function or directory one has to dive into the Azure WebJobs SDK. After all Azure functions are based on WebJobs.<\/p>\n<p>It seems that the method signature can take an additional parameter of type <strong>ExecutionContext<\/strong>.<br \/>\nJust add it and it&#8217;s ok, like this in a C# function:<\/p>\n<pre class=\"brush: csharp; title: ; notranslate\" title=\"\">\r\npublic static async Task&lt;HttpResponseMessage&gt; Run(&#x5B;HttpTrigger(AuthorizationLevel.Function, &quot;get&quot;, &quot;post&quot;, Route = null)]HttpRequestMessage req, TraceWriter log, ExecutionContext executionContext)\r\n<\/pre>\n<p>Or a C# script function:<\/p>\n<pre class=\"brush: csharp; title: ; notranslate\" title=\"\">\r\npublic static async Task&lt;HttpResponseMessage&gt; Run(HttpRequestMessage req, TraceWriter log, ExecutionContext executionContext)\r\n<\/pre>\n<p>Calling the property <em>FunctionDirectory<\/em> of this context in Visual Studio results in the actual local function directory:<br \/>\n<a href=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/6-paths-locally.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-2465\" src=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/6-paths-locally.png\" alt=\"\" width=\"828\" height=\"83\" srcset=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/6-paths-locally.png 828w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/6-paths-locally-300x30.png 300w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/6-paths-locally-768x77.png 768w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/6-paths-locally-600x60.png 600w\" sizes=\"auto, (max-width: 828px) 100vw, 828px\" \/><\/a><br \/>\nFigure 6 &#8211; FunctionDirectory result running locally<\/p>\n<p>So get the parent of this path to get the project directory.<\/p>\n<p>When deployed to Azure it results in D:\\home\\site\\wwwroot\\Function1<a href=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/7-paths-deployed-to-Azure.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-2473\" src=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/7-paths-deployed-to-Azure.png\" alt=\"\" width=\"714\" height=\"111\" srcset=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/7-paths-deployed-to-Azure.png 714w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/7-paths-deployed-to-Azure-300x47.png 300w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/7-paths-deployed-to-Azure-600x93.png 600w\" sizes=\"auto, (max-width: 714px) 100vw, 714px\" \/><br \/>\n<\/a>Figure 7 &#8211; FunctionDirectory result deployed to Azure<\/p>\n<p>And using an C# script function this results in &#8216;D:\\home\\site\\wwwroot\\HttpTriggerCSharp1&#8217; which is the function directory over there.<\/p>\n<p><a href=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/8-paths-script-function.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-2472\" src=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/8-paths-script-function.png\" alt=\"\" width=\"620\" height=\"107\" srcset=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/8-paths-script-function.png 620w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/8-paths-script-function-300x52.png 300w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/8-paths-script-function-600x104.png 600w\" sizes=\"auto, (max-width: 620px) 100vw, 620px\" \/><\/a><br \/>\nFigure 8 &#8211; FunctionDirectory result running C# script function<\/p>\n<p>When adding files and folders to the project in Visual Studio and deploy it to Azure, they are present in the structure:<\/p>\n<p><a href=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/9-files.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-2471\" src=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/9-files.png\" alt=\"\" width=\"302\" height=\"308\" srcset=\"https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/9-files.png 302w, https:\/\/www.itidea.nl\/wp-content\/uploads\/2017\/11\/9-files-294x300.png 294w\" sizes=\"auto, (max-width: 302px) 100vw, 302px\" \/><\/a><br \/>\nFigure 9 &#8211; File structure<\/p>\n<p>Now the working directory is a known fact, referencing these files in the project is easy.<br \/>\nlog.Info(executionContext.FunctionDirectory);<br \/>\nlog.Info($&#8221;{Directory.GetParent(executionContext.FunctionDirectory).FullName}\\\\files\\\\afile.json&#8221;);<\/p>\n<h4>Summary<\/h4>\n<p>To get the project or function directory in an Azure function in Visual Studio or in the portal isn&#8217;t rocket science, but it took me some digging around in the SDK to get it.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>To explain in detail how to reference a file in an Azure function some background information on the basics of Azure functions is necessary. To complete the story it will all be explained for C# script based function as well &#8230; <a class=\"more-link\" href=\"https:\/\/www.itidea.nl\/index.php\/how-to-reference-a-file-in-azure-function-c-script-function-vs-c-function\/\">Read More &raquo;<\/a><\/p>\n","protected":false},"author":2,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[49,39],"tags":[50,37],"class_list":["post-2458","post","type-post","status-publish","format-standard","hentry","category-azure","category-office-365","tag-azure","tag-office365"],"_links":{"self":[{"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/posts\/2458","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/comments?post=2458"}],"version-history":[{"count":15,"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/posts\/2458\/revisions"}],"predecessor-version":[{"id":2482,"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/posts\/2458\/revisions\/2482"}],"wp:attachment":[{"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/media?parent=2458"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/categories?post=2458"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.itidea.nl\/index.php\/wp-json\/wp\/v2\/tags?post=2458"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}