Skip to content
This repository was archived by the owner on Nov 14, 2020. It is now read-only.

Commit cc9c3ac

Browse files
olgamartiTheCodeTraveler
authored andcommitted
Update readme file. (#2)
* Update Readme file * Add Repo URL in Deploy Button * Fixes in Deploy Azure Button * Add URL of Xamarin repo in Azure Deploy Button * Fix images from Task 2 in Readme file
1 parent 64e4c9e commit cc9c3ac

24 files changed

+341
-26
lines changed

Diff for: README.md

+206-20
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,206 @@
1-
# Introduction
2-
TODO: Give a short introduction of your project. Let this section explain the objectives or the motivation behind this project.
3-
4-
# Getting Started
5-
TODO: Guide users through getting your code up and running on their own system. In this section you can talk about:
6-
1. Installation process
7-
2. Software dependencies
8-
3. Latest releases
9-
4. API references
10-
11-
# Build and Test
12-
TODO: Describe and show how to build your code and run the tests.
13-
14-
# Contribute
15-
TODO: Explain how other users and developers can contribute to make your code better.
16-
17-
If you want to learn more about creating good readme files then refer the following [guidelines](https://www.visualstudio.com/en-us/docs/git/create-a-readme). You can also seek inspiration from the below readme files:
18-
- [ASP.NET Core](https://github.com/aspnet/Home)
19-
- [Visual Studio Code](https://github.com/Microsoft/vscode)
20-
- [Chakra Core](https://github.com/Microsoft/ChakraCore)
1+
# Xamarin - Azure Function Challenge - 2019
2+
3+
Welcome to the Xamarin Azure Challenge! The goal of this challenge is to implement and connect your Xamarin app with an Azure Function.
4+
5+
## Objectives
6+
7+
1. Create and publish an Azure Function resource in Azure.
8+
2. Configure Xamarin Forms Application.
9+
3. Find and fix some code errors hidden in the source code.
10+
4. Submit your information through Xamarin Forms Application to the Azure Function to complete the challenge.
11+
12+
## Prerequisites
13+
14+
* Azure Suscription. If you don't have an Azure Subscription you can get one with VS Dev Essentials and a personal Microsoft Account sign up in [Microsoft VS Dev Essentials Site](https://visualstudio.microsoft.com/dev-essentials/) or you can sign up for a free [Azure trial](https://azure.microsoft.com/en-us/free/).
15+
* Visual Studio 2019 + Xamarin. If you don't have Visual Studio 2019 installed in your machine with Xamarin you can follow [this steps](https://docs.microsoft.com/en-us/xamarin/get-started/installation/).
16+
17+
## Task 1: Create and publish an Azure Function resource in Azure
18+
19+
### Clone repository
20+
21+
Ensure you are in the `master` branch, and then, [clone](https://git-scm.com/docs/git-clone) this repository in your computer. Run this command in your favorite terminal and change `<name-repository>` for the correct name.
22+
23+
``` bash
24+
git clone <name-repository>
25+
```
26+
27+
After you have cloned the repository, you have 3 options to create and publish your Azure Function.
28+
29+
1. Use Visual Studio to create and publish the Azure Function.
30+
2. Use Azure Portal to create the Azure Function and Visual Studio to publish it.
31+
3. Use Azure CLI to create and publish the Azure Function.
32+
33+
You can also use the follwing Deploy to Azure button to create the resources.
34+
35+
[![Deploy to Azure](https://azuredeploy.net/deploybutton.png)](https://azuredeploy.net/?repository=https://github.com/xamarin/XamarinAzureChallenge/doc/deploy)
36+
37+
### <a name="Option1"></a> Option 1: Use Visual Studio to create and publish the Azure Function
38+
39+
> As a prerequisite, you must have an Azure Subscription and be logged with this Microsoft account in your Visual Studio.
40+
41+
1. In Visual Studio go to the Solution Explorer and select XamarinAzureChallenge.Functions project.
42+
43+
![publish](doc/img/solution-explorer.png)
44+
45+
2. On the project, right-click and select **Publish**.
46+
47+
![start](doc/img/publish.png)
48+
49+
3. In the Publish window, select Azure Function -> Azure App Service -> Create a new profile.
50+
51+
![start](doc/img/create-profile.png)
52+
53+
3. Create and configure the App Service.
54+
55+
![start](doc/img/configure-profile.png)
56+
57+
- **App Name**: Eg: MicrosoftXamarinChallengeFunctions
58+
- **Subscription**: Your Subscription name
59+
- **New Resource Group**: Eg: XamarinAzureChallengeFunctionsRG
60+
- **New Hosting Plan**: Eg: XamarinAzureChallengeFunctionsHostP
61+
- **Azure Storage**: Eg: xamazurechallengestore1
62+
63+
4. Once you create or select the Resource Group, Hosting Plan and Storage Account click on **Create**.
64+
65+
This action will take a few minutes.
66+
67+
5. Make sure your resource group was created correctly in the [Azure Portal](http://portal.azure.com).
68+
69+
![ensureAzure](doc/img/ensure-portal-azure.png)
70+
71+
Now, every time you want to deploy your code to Azure, you will only need to click the **Publish** button.
72+
73+
![publishButton](doc/img/publish-button.png)
74+
75+
76+
### Option 2: Use Azure Portal to create the Azure Function and Visual Studio to publish it
77+
78+
1. Go to the [Azure Portal](http://portal.azure.com) and click on Create Resource. Enter Function App into the Search Bar.
79+
80+
![portalAzFunction1](doc/img/portal-createAzFunction-1.png)
81+
82+
2. Click Create:
83+
84+
![portalAzFunction2](doc/img/portal-createAzFunction-2.png)
85+
86+
87+
3. Name your Function App and choose your Azure Subscription. Configure or create a new the Resource Group, Location, and Storage Account.
88+
89+
- **App Name**: Eg: MicrosoftXamarinChallengeFunctions
90+
- **Subscription**: Your Subscription name
91+
- **New Resource Group**: Eg: XamarinAzureChallengeFunctionsRG
92+
- **New Hosting Plan**: Eg: XamarinAzureChallengeFunctionsHostP
93+
- **Azure Storage**: Eg: xamazurechallengestore1
94+
95+
4. Go to Visual Studio and click on the Solution Explorer and select XamarinAzureChallenge.Functions project.
96+
97+
![publish](doc/img/solution-explorer.png)
98+
99+
5. On the project, right-click in **Publish**
100+
101+
![start](doc/img/publish.png)
102+
103+
6. Select existing resource -> Publish
104+
105+
![portal-publish](doc/img/portal-publish-1.png)
106+
107+
7. In the App Service window, select the Azure Function that you created earlier, and click **OK**.
108+
109+
![portal-publish-2](doc/img/portal-publish-2.png)
110+
111+
Visual Studio will publish your Azure Function. This action will take a few minutes.
112+
113+
## Option 3: Use Azure CLI to create and publish your Azure Function.
114+
115+
> As a prerequisite, you must have installed [Azure Core Tools version 2.x](https://docs.microsoft.com/en-us/azure/azure-functions/functions-run-local#v2) and [Azure CLI](https://docs.microsoft.com/en-us/cli/azure/install-azure-cli) or [Azure Cloud Shell](https://shell.azure.com/bash).
116+
117+
1. Login into Azure CLI
118+
119+
```
120+
az login
121+
```
122+
123+
2. Create a resource group.
124+
125+
```
126+
az group create --name XamarinAzureChallengeRG --location westeurope
127+
```
128+
129+
If you have more than one subscription you will need to especify the subscription where the resource groups will be created with ``--subscription.``
130+
131+
3. Create an Azure storage account
132+
133+
```
134+
az storage account create --name xamazurechallengestore1 --location westeurope --resource-group XamarinAzureChallengeRG2 --sku Standard_LRS --subscription bc6ccc1f-0744-4645-99f4-52b017e3b9ba
135+
```
136+
137+
4. Use the following command to navigate to the project folder `XamarinAzureChallenge.Functions` project folder.
138+
139+
```bash
140+
cd MyPath\src\XamarinAzureChallenge\XamarinAzureChallenge.Functions
141+
```
142+
143+
5. Create a function app
144+
145+
```
146+
az functionapp create --resource-group XamarinAzureChallengeRG2 --consumption-plan-location westeurope --name XamarinAzureChallengeFunctions --storage-account xamazurechallengestore1 --runtime dotnet --subscription bc6ccc1f-0744-4645-99f4-52b017e3b9ba
147+
```
148+
149+
6. Use this command to deploy the project to Azure.
150+
151+
152+
```
153+
func azure functionapp publish XamarinAzureChallengeFunctions
154+
```
155+
156+
## Task 2: Configuring the Xamarin App
157+
158+
### Configure your deploymemt
159+
160+
After deploy and publish the Azure Function, you are ready to configure the Xamarin app with your Azure Function endpoint.
161+
162+
1. Go the Azure Portal and navigate to your Azure Function App.
163+
164+
2. Open the list of Functions and select SubmitChallengeFunction. On the right panel, go to Get function URL.
165+
166+
![AFEndpoint](/doc/img/AFEndpoint1.png)
167+
168+
3. Copy the URL.
169+
170+
![AFEndpoint2](/doc/img\AFEndpoint2.png)
171+
172+
4. Open the solution *XamarinAzureChallenge.sln* and go to *UserDetailViewModel* class and paste the url in *Endpoint* variable:
173+
174+
![ViewModel](/doc/img/BaseViewModel.png)
175+
176+
177+
## Task 3: Goal of this challenge
178+
179+
As you know, this code contains errors. Please find them and fix them to pass this challenge!
180+
181+
**Click [here](/doc/solution.md) to get the solution.**
182+
183+
## Task 4: Submit your information through Xamarin Application
184+
185+
The next step is to run the Xamarin Application and fill the form with your information. If you followed all the steps, your personal information will be sent to the Azure Function. The Azure Function will send to our internal API the data to participate in the challenge.
186+
187+
You can run the app in local using an emulator. You can find the instructions [here](https://docs.microsoft.com/en-us/xamarin/android/deploy-test/debugging/debug-on-emulator?tabs=windows).
188+
189+
In addition, you can run the app in a physical device. To setting up and configure your device you can follow [these instrucions](https://docs.microsoft.com/en-us/xamarin/android/deploy-test/debugging/debug-on-device?tabs=windows)
190+
191+
192+
## Next Steps
193+
194+
Please, read the Terms and Conditions of this challenge to know more about the next steps.
195+
196+
## Report an issue
197+
198+
If you found an issue with this challenge, please open an issue in GitHub.
199+
200+
## Additional Resources
201+
202+
If you are interested in learning more about this topic, you can refer to the following resources:
203+
204+
* [Azure Function Documentation](https://docs.microsoft.com/en-us/azure/azure-functions/)
205+
* [Xamarin Documentation](https://docs.microsoft.com/en-us/xamarin/)
206+
* [Azure Samples + Xamarin](https://github.com/Azure-Samples?utf8=%E2%9C%93&q=Xamarin&type=&language=)

Diff for: doc/deploy/azuredeploy.json

+72
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
{
2+
"$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
3+
"contentVersion": "1.0.0.0",
4+
"parameters": {
5+
"storageAccounts_xamarinazurechallenge1_name": {
6+
"defaultValue": "xamarinazurechallenge1",
7+
"type": "String"
8+
},
9+
"serverfarms_XamarinAzureChallengeFunctions1_name": {
10+
"defaultValue": "XamarinAzureChallengeFunctions1",
11+
"type": "String"
12+
}
13+
},
14+
"variables": {},
15+
"resources": [
16+
{
17+
"type": "Microsoft.Storage/storageAccounts",
18+
"apiVersion": "2018-07-01",
19+
"name": "[parameters('storageAccounts_xamarinazurechallenge1_name')]",
20+
"location": "centralus",
21+
"tags": {
22+
"hidden-related:/providers/Microsoft.Web/sites/XamarinAzureChallengeFunctions1": "empty"
23+
},
24+
"sku": {
25+
"name": "Standard_LRS",
26+
"tier": "Standard"
27+
},
28+
"kind": "Storage",
29+
"properties": {
30+
"networkAcls": {
31+
"bypass": "AzureServices",
32+
"virtualNetworkRules": [],
33+
"ipRules": [],
34+
"defaultAction": "Allow"
35+
},
36+
"supportsHttpsTrafficOnly": false,
37+
"encryption": {
38+
"services": {
39+
"file": {
40+
"enabled": true
41+
},
42+
"blob": {
43+
"enabled": true
44+
}
45+
},
46+
"keySource": "Microsoft.Storage"
47+
}
48+
}
49+
},
50+
{
51+
"type": "Microsoft.Web/serverfarms",
52+
"apiVersion": "2016-09-01",
53+
"name": "[parameters('serverfarms_XamarinAzureChallengeFunctions1_name')]",
54+
"location": "Central US",
55+
"sku": {
56+
"name": "Y1",
57+
"tier": "Dynamic",
58+
"size": "Y1",
59+
"family": "Y",
60+
"capacity": 0
61+
},
62+
"kind": "functionapp",
63+
"properties": {
64+
"name": "[parameters('serverfarms_XamarinAzureChallengeFunctions1_name')]",
65+
"perSiteScaling": false,
66+
"reserved": false,
67+
"targetWorkerCount": 0,
68+
"targetWorkerSizeId": 0
69+
}
70+
}
71+
]
72+
}

Diff for: doc/img/AFEndpoint1.png

35.1 KB
Loading

Diff for: doc/img/AFEndpoint2.png

7.97 KB
Loading

Diff for: doc/img/BaseViewModel.png

188 KB
Loading

Diff for: doc/img/binding.png

26.3 KB
Loading

Diff for: doc/img/configure-profile.png

25 KB
Loading

Diff for: doc/img/create-profile.png

13.9 KB
Loading

Diff for: doc/img/deploy-resources.png

26.8 KB
Loading

Diff for: doc/img/ensure-portal-azure.png

19.3 KB
Loading

Diff for: doc/img/new-hosting-plan.PNG

28.1 KB
Loading

Diff for: doc/img/portal-createAzFunction-1.png

26.2 KB
Loading

Diff for: doc/img/portal-createAzFunction-2.png

34.5 KB
Loading

Diff for: doc/img/portal-publish-1.png

12.7 KB
Loading

Diff for: doc/img/portal-publish-2.png

13.3 KB
Loading

Diff for: doc/img/portal-publish.png

42.3 KB
Loading

Diff for: doc/img/publish-button.png

15.5 KB
Loading

Diff for: doc/img/publish.png

30.6 KB
Loading

Diff for: doc/img/solution-explorer.png

63.6 KB
Loading

Diff for: doc/solution.md

+57
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
# Solution
2+
3+
We hope you tried to complete this challenge with all your effort and enthusiasm.
4+
5+
If you did, and are still unable to complete the challenge, here you have the solution. We assume you have followed and completed the task 1 and task 2.
6+
7+
## Fixing the errors
8+
9+
1. By POST not by GET
10+
11+
When you were trying make a POST request from Xamarin App to your Azure Function, it answered you with a **404 not found**.
12+
13+
This error is allocated in the signature of the function. This Azure Function will only be triggered by a POST request, but in this code, we specified that the function only accepts GET requests.
14+
15+
Change it to this:
16+
17+
```c#
18+
public static async Task<HttpResponseMessage> Run([HttpTrigger(AuthorizationLevel.Function, "post", Route = null)]HttpRequestMessage req)
19+
```
20+
21+
22+
2. Encoding.UTF8 not Encoding.UTF7
23+
24+
At this point, it seems that all your code is correct. However, when you try to make a request you get a 500 error, even if the JSON data is correct.
25+
26+
`SendToApi` is throwing 500, simply because the String Encoding is wrong.
27+
28+
Change it to this:
29+
30+
31+
```c#
32+
return await client.PostAsync(_uri, new StringContent(body, Encoding.UTF8, "application/json"));
33+
```
34+
35+
3. Fix Binding on *UserDataPage.xaml.cs*
36+
37+
The BindingContext of the page is not configure so the bindings and commands that are invoked from the xaml code do not work. To solve this add as the last line of the *UserDataPage* constructor:
38+
39+
```c#
40+
BindingContext = new UserDataViewModel();
41+
```
42+
43+
4. Fix serialization issue
44+
45+
The model used to send the data to the Azure Function do not serialize the *Email* to Json. In User.cs class, locate the property *Email* and replace the
46+
47+
```c#
48+
[JsonIgnore]
49+
```
50+
51+
with
52+
53+
```c#
54+
[JsonProperty(PropertyName="email")]
55+
```
56+
57+
> Remember to deploy your Azure Function with the fixes!

Diff for: src/XamarinAzureChallenge/XamarinAzureChallenge.Functions/SubmitChallengeFunction.cs

+2-2
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ public static class SubmitChallengeFunction
2222
private static HttpClient Client => clientHolder.Value;
2323

2424
[FunctionName(nameof(SubmitChallengeFunction))]
25-
public static async Task<IActionResult> Run([HttpTrigger(AuthorizationLevel.Function, "post")][FromBody] User user)
25+
public static async Task<IActionResult> Run([HttpTrigger(AuthorizationLevel.Function, "get")][FromBody] User user)
2626
{
2727
var (isDataValid, errorMessage) = IsDataValid(user);
2828

@@ -78,7 +78,7 @@ private static Task<HttpResponseMessage> SendToApi(User user)
7878
{
7979
var serializedUser = JsonConvert.SerializeObject(user);
8080

81-
var httpContent = new StringContent(serializedUser, Encoding.UTF8, "application/json");
81+
var httpContent = new StringContent(serializedUser, Encoding.UTF7, "application/json");
8282

8383
return Client.PostAsync(uri, httpContent);
8484
}
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
{
22
"IsEncrypted": false,
33
"Values": {
4-
"API_HOST": "",
5-
"END_POINT": ""
4+
"API_HOST": "https://azurexamarinchallengepro.azurewebsites.net",
5+
"END_POINT": "registers",
6+
"FUNCTIONS_WORKER_RUNTIME": "dotnet"
67
}
78
}

Diff for: src/XamarinAzureChallenge/XamarinAzureChallenge.Shared/Models/User.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ public class User
77
[JsonProperty("fullname")]
88
public string Name { get; set; } = string.Empty;
99

10-
[JsonProperty("email")]
10+
[JsonIgnore]
1111
public string Email { get; set; } = string.Empty;
1212

1313
[JsonProperty("phone")]

0 commit comments

Comments
 (0)