Exercise - Create an Azure Functions project

Completed

At this point, the app is working to get the user's location and is ready to be sent to the Azure Functions. In this unit, you build your own Azure Functions.

Create an Azure Functions project

  1. Right-click on the ImHere solution and select Add > New Project....

  2. Search for Azure Functions, select it, and select Next.

  3. Name the project "ImHere.Functions", and then select Create.

    Screenshot that shows the Add New Project dialog.

  4. In the Create a new Azure Functions application configuration dialog, ensure the Functions version is set to .NET 6. Select Http Trigger, leave the storage account set to Storage Emulator, and set the authorization level to Anonymous. Then select Create.

    Screenshot that shows the Azure Functions project configuration dialog.

    The new project will be created and have a default function called Function1.

Note

This function was created with anonymous access. Once published to Azure, anybody who knows the URL will be able to call this function. In a real-world scenario, you would protect this with some form of authentication, such as Azure App Service authentication or Azure Active Directory B2C.

Create the function

The Azure Functions project is created with a single HTTP trigger function called Function1. HTTP triggers allow you to invoke your functions using HTTP requests. The function itself is implemented as a static Run method in the Function1 class.

  1. Rename the file in Solution Explorer from "Function1.cs" to "SendLocation.cs". When prompted to rename all references to the code element Function1, click Yes.

  2. Rename the function name in the attribute to "SendLocation".

    [FunctionName("SendLocation")]
    
  3. Delete the contents of the function, except the first line that writes an information message to the logger.

    public static async Task<IActionResult> Run([HttpTrigger(AuthorizationLevel.Anonymous,
                                                             "get", "post",
                                                             Route = null)]HttpRequestMessage req,
                                                ILogger log)
    {
        log.LogInformation("C# HTTP trigger function processed a request.");
    }
    

Create a class to share data between the mobile app and function

When data is sent to the Azure Functions, it will be sent as JSON. The mobile app will serialize data into JSON and the function will deserialize from JSON. To keep this data consistent between the mobile app and the function, create a new project that contains a class to hold the location and phone number data. This project will then be referenced by the app and function.

  1. Create a new project under the ImHere solution by right-clicking on the solution and selecting Add > New Project....

  2. Search for Class Library (.NET Standard), choose the item, and then select Next.

    Screenshot that shows the Add New Project dialog with the Class Library option highlighted.

  3. Name the project "ImHere.Data", and then select Next.

  4. For the Class Library Framework, choose .NET Standard 2.0, and then select Create.

  5. Delete the auto-generated "Class1.cs" file.

  6. Right-click on the ImHere.Data project and select Add > Class... to create a new class.

  7. Name the new class "PostData" and select Add. Mark this new class as public.

  8. Add double properties for the latitude and longitude, and a string[] property for the phone numbers to send to.

    public class PostData
    {
        public double Latitude { get; set; }
        public double Longitude { get; set; }
        public string[] ToNumbers { get; set; }
    }
    
  9. Add a reference to this project in both the ImHere.Functions and ImHere projects by right-clicking on the project and then selecting Add->Reference.... Select Projects from the tree on the left-hand side, and then check the box next to ImHere.Data.

    Screenshot that shows how to configure the project references.

Read the data sent to the function

In the Azure Functions, the req parameter contains the HTTP request that was made and the data inside this request will be a JSON serialized PostData object.

  1. Open the SendLocation class in the ImHere.Functions project.

  2. Read the contents of the HTTP request into a string, then deserialize it into a PostData object, adding a using directive for the ImHere.Data namespace.

    string requestBody = await new StreamReader(req.Body).ReadToEndAsync();
    PostData data = JsonConvert.DeserializeObject<PostData>(requestBody);
    
  3. Construct a Google Maps URL using the latitude and longitude from the PostData.

    string url = $"https://www.google.com/maps/search/?api=1&query={data.Latitude},{data.Longitude}";
    
  4. Log the URL.

    log.LogInformation($"URL created - {url}");
    
  5. Return a 200 status code to show the function completed without error.

    return new OkResult();
    

The complete function is shown below.


  using System.IO;
  using Microsoft.AspNetCore.Mvc;
  using Microsoft.Azure.WebJobs;
  using Microsoft.Azure.WebJobs.Extensions.Http;
  using Microsoft.AspNetCore.Http;
  using ImHere.Data;
  using System.Threading.Tasks;
  using Microsoft.Extensions.Logging;
  using Newtonsoft.Json;

  namespace ImHere.Functions
  {
      public static class SendLocation
      {
          [FunctionName("SendLocation")]
          public static async Task<IActionResult> Run([HttpTrigger(AuthorizationLevel.Anonymous, "get", "post",
                                                           Route = null)]HttpRequest req, ILogger log)
          {
              log.LogInformation("C# HTTP trigger function processed a request.");
              string requestBody = await new StreamReader(req.Body).ReadToEndAsync();
              PostData data = JsonConvert.DeserializeObject<PostData>(requestBody);
              string url = $"https://www.google.com/maps/search/?api=1&query={data.Latitude},{data.Longitude}";
              log.LogInformation($"URL created - {url}");
              return new OkResult();
          }
      }
  }

Run the Azure Functions locally

Functions can be run locally using a local storage account and local Azure Functions runtime. This local runtime allows you to test out your function before deploying it to Azure.

  1. Right-click on the ImHere.Functions project in the solution explorer, and then select Set as StartUp project.

  2. From the Debug menu, select Start Without Debugging. The local Azure Functions runtime will launch inside a console window and start your function, listening on an available port on localhost. If you see a dialog asking for firewall access, allow access to private networks (the default option).

    Screenshot that shows the Azure Functions running locally.

  3. Take a note of the port that the function is listening on. You'll need this in the next unit to test out the mobile app. In the image above, the function is listening on port 7071.

    Listening on http://localhost:7071/
    
  4. Leave the function running so that you can test the mobile app in the next unit.

Summary

In this unit, you learned how to create an Azure Functions project in Visual Studio, added a shared project with a data object to be shared between the mobile app and the function, and learned how to create a basic implementation of the function to deserialize the data passed in. You also learned how to run the Azure Functions locally. In the next unit, you'll call the Azure Functions from the mobile app.