All Products
Search
Document Center

C# handler

Last Updated: Apr 16, 2019

To use C# in Function Compute, you must first define a C# function as a handler. This topic describes the C# handlers that can be used and their definitions.

Overview

To easily handle HTTP requests, Function Compute supports the use of HTTP triggers to call C# functions. The HTTP triggered function is known as a handler with an HTTP trigger. Currently, the C# runtime (.NET Core 2.1) supports two types of handlers:

Common handlers

Handler definition

When creating a C# function, you must specify a handler method, which is executed along with the function. This handler method can be a static method or an instance method. To access the IFcContext object in this method, you can specify IFcContext object as the second parameter in this method. The supported handler methods are defined as follows:

  1. ReturnType HandlerName(InputType input, IFcContext context); // IFcContext included
  2. ReturnType HandlerName(InputType input); // IFcContext not included
  3. Async Task<ReturnType> HandlerName(InputType input, IFcContext context);
  4. Async Task<ReturnType> HandlerName(InputType input);

Function Compute supports the use of Async in C#-written functions, where the execution of the function waits for the end of the asynchronous method execution.

In the preceding definition:

  • ReturnType: the returned object, which can be void, a System.IO.Stream object, or any JSON-serialized or -deserialized object. When void is returned, Async Task degrades to async Task. When a Stream object is returned, the Stream content is included in the response body. Otherwise, the returned object is serialized in JSON and included in the response body.

  • InputType: the input parameter, which can be System.IO.Stream or any JSON-serialized or -deserialized object.

  • IFcContext: the context object of the function, which includes the following information.

Parameter Type Description
RequestId String The GUID of the current call request, which is typically used during fault locating or historical call count.
FunctionParam Class The basic information about the currently called function, including the function name, handler, memory, and timeout period.
Credentials Class The temporary SecurityToken that Function Compute retrieves by playing the provided service role. SecurityToken is updated every 15 minutes. You can use SecurityToken to access other Alibaba Cloud services, such as OSS. This prevents the hard coding of the AccessKey in the function code.
ServiceMeta Class The information about the service to which the currently called function belongs, including the service name, accessed logproject and logstore of Log Service, and service version, such as the qualifier and version_id. The qualifier indicates the service version or alias that is specified when the function is called, and version_id indicates the service version that is actually called.
Region String The region where the currently called function is located, such as cn-shanghai. For more information, see Regions and zones.
AccountId String The Alibaba Cloud account ID of the current function caller. For more information, see Get an account ID.

more detail: fc-dotnet-libs

Handler method example

When you write functions in C# using Function Compute, the Aliyun.Serverless.Core package needs to be introduced through NuGet.

Stream Handler

The following method returns the user request input as it is.

  1. using System.IO;
  2. using System.Threading.Tasks;
  3. using Aliyun.Serverless.Core;
  4. using Microsoft.Extensions.Logging;
  5. namespace FC.Examples
  6. {
  7. public class TestHandler
  8. {
  9. public async Task<Stream> Echo(Stream input, IFcContext context)
  10. {
  11. ILogger logger = context.Logger;
  12. logger.LogInformation("Handle request: {0}", context.RequestId);
  13. MemoryStream copy = new MemoryStream();
  14. await input.CopyToAsync(copy);
  15. copy.Seek(0, SeekOrigin.Begin);
  16. return copy;
  17. }
  18. }
  19. }

POCO Handler

In addition to Stream objects, plain old CLR objects (POCOs) can also be used as input and output parameters. If a POCO does not specify a JSON serializer object, Function Compute uses Json.Net to serialize and deserialize objects in the JSON format by default.

  1. using Microsoft.Extensions.Logging;
  2. namespace FC.Examples
  3. {
  4. public class TestHandler
  5. {
  6. public class Product
  7. {
  8. public string Id { get; set; }
  9. public string Description { get; set; }
  10. }
  11. // optional serializer class, if it’s not specified, the default serializer (based on JSON.Net) will be used.
  12. // [FcSerializer(typeof(MySerialization))]
  13. public Product Echo(Product product, IFcContext context)
  14. {
  15. string Id = product.Id;
  16. string Description = product.Description;
  17. context.Logger.LogInformation("Id {0}, Description {1}", Id, Description);
  18. return product;
  19. }
  20. }
  21. }

Handler specification

Handler Signatures

When creating a function, you need to specify a handler method in the string format to tell Function Compute how to locate the method to be called. The string format is as follows:

AssemblyFileName::FullClassName::METHOD

where,

  • AssemblyFileName is the file name of Assembly where the function is located (with .dll omitted).

  • FullClassName is the full name of the class to which the function belongs, that is, Namespace.ClassName.

  • Method is the name of the method to be called.

In the preceding Handler example, if the Assembly file name is test_assembly, then the handler string is as follows:

test_assembly::FC.Examples.TestHandler::Echo

Limits

  • The Handler parameter format observes the preceding definition. That is, parameter 1 is required, whereas parameter 2 is optional, with the invariable value IFcContext.

  • The Handler function does not support Generic Method.

  • The input and output parameters must be Stream objects or can be serialized in the JSON format.

  • The Async function returns Task, in which T must be Stream objects or of a class that can be serialized in the JSON format.

Custom Serializer

For POCO handlers, Function Compute provides the default JSON . NET serializer. If the default serializer does not meet requirements, a custom serializer can be implemented based on the interface IFcSerializer in Aliyun.Serverless.Core.

  1. public interface IFcSerializer
  2. {
  3. T Deserialize<T>(Stream requestStream);
  4. void Serialize<T>(T response, Stream responseStream);
  5. }

Complete operation example of common handlers

SecurityToken is used to verify the identity and permissions of a requester. You must specify SecurityToken when you access other Alibaba Cloud services, such as OSS. In the following C# sample code, SecurityToken is used to retrieve the specified object from an OSS bucket.

  1. Create a .NET Core console project.

    1. [songluo@~/tmp]# mkdir fcdotnetsample
    2. [songluo@~/tmp]# cd fcdotnetsample
    3. [songluo@~/tmp/fcdotnetsample]# dotnet new console
  2. Add the following packages to fcdotnetsample.csproj:

    1. <ItemGroup>
    2. <PackageReference Include="Aliyun.Serverless.Core" Version="1.0.1" />
    3. <PackageReference Include="Aliyun.OSS.SDK.NetCore" Version="2.9.1" />
    4. </ItemGroup>
  3. Edit ‘Program.cs’.

    1. using System;
    2. using System.IO;
    3. using Aliyun.OSS;
    4. using Aliyun.Serverless.Core;
    5. namespace fcdotnetsample
    6. {
    7. class Program
    8. {
    9. static void Main(string[] args)
    10. {
    11. Console.WriteLine("Hello World!");
    12. }
    13. }
    14. public class OssFileHandlerRequest
    15. {
    16. public string Bucket;
    17. public string Key;
    18. public string Endpoint;
    19. }
    20. public class OSSFileHandler
    21. {
    22. public Stream GetOssFile(OssFileHandlerRequest req, IFcContext context)
    23. {
    24. if (req == null)
    25. {
    26. throw new ArgumentNullException(nameof(req));
    27. }
    28. if (context == null || context.Credentials == null)
    29. {
    30. throw new ArgumentNullException(nameof(context));
    31. }
    32. OssClient ossClient = new OssClient(req.Endpoint, context.Credentials.AccessKeyId, context.Credentials.AccessKeySecret, context.Credentials.SecurityToken);
    33. OssObject obj = ossClient.GetObject(req.Bucket, req.Key);
    34. return obj.Content;
    35. }
    36. }
    37. }
  4. Publish the project and compress the target files into a .zip package.

    1. [songluo@~/tmp/fcdotnetsample]# dotnet publish -c Release
    2. Microsoft (R) Build Engine version 15.9.20+g88f5fadfbe for .NET Core
    3. Copyright (C) Microsoft Corporation. All rights reserved.
    4. Restore completed in 47.9 ms for /Users/songluo/tmp/fcdotnetsample/fcdotnetsample.csproj.
    5. fcdotnetsample -> /Users/songluo/tmp/fcdotnetsample/bin/Release/netcoreapp2.1/fcdotnetsample.dll
    6. fcdotnetsample -> /Users/songluo/tmp/fcdotnetsample/bin/Release/netcoreapp2.1/publish/
    7. [songluo@~/tmp/fcdotnetsample]# cd /Users/songluo/tmp/fcdotnetsample/bin/Release/netcoreapp2.1/publish/
    8. [songluo@~/tmp/fcdotnetsample/bin/Release/netcoreapp2.1/publish]# zip -r fcdotnetsample.zip *
    9. adding: Aliyun.OSS.Core.dll (deflated 60%)
    10. adding: Aliyun.Serverless.Core.dll (deflated 59%)
    11. adding: Microsoft.Extensions.Logging.Abstractions.dll (deflated 53%)
    12. adding: fcdotnetsample.deps.json (deflated 73%)
    13. adding: fcdotnetsample.dll (deflated 57%)
    14. adding: fcdotnetsample.pdb (deflated 27%)
    15. adding: fcdotnetsample.runtimeconfig.json (deflated 23%)
    16. [songluo@~/tmp/fcdotnetsample/bin/Release/netcoreapp2.1/publish]# ls -ll fcdotnetsample.zip
    17. -rw-r--r-- 1 songluo staff 130276 Mar 14 17:48 fcdotnetsample.zip

Use fcdotnetsample.zip to create a function with the runtime .NET Core 2.1 and the handler fcdotnetsample::fcdotnetsample.OSSFileHandler::GetOssFile.

Initializer handler

Function Compute provides the Init method for initialization. The Init method is automatically called when background containers are started. Each container is called only once.

Init method definition:

  1. public void Init(); // No context objects
  2. public void Init(IFcContext context); // Include context objects
  3. public static void Init(); // No context objects
  4. public static void Init(IFcContext context); // Include context objects

Initializer format

  • MyInitializermust map the “initializer” field when the initializer function is added. For example, if fcdotnetsample::fcdotnetsample.TestHandler::MyInitializer is specified as the initializer handler when a function is created, Function Compute first loads the MyInitializer function defined in fcdotnetsample.TestHandler after initializer configuration.

Initializer features

  • FunctionInitializer and InitializationTimeout in FunctionParam of IFcContext are designed for the initializer and are set to the user-predefined values when a function is created while the initializer is in use. Otherwise, they are empty and ineffective.
  • No value is returned. The Return operation appended to the function is invalid.

Handlers with an HTTP trigger

A handler with an HTTP trigger is different from other trigger-required handlers and is defined as follows:

If you write a function with an HTTP trigger in C#, the Aliyun.Serverless.Core and Aliyun.Serverless.Core.Http packages need to be introduced through NuGet.

  1. using System.Threading.Tasks;
  2. using Microsoft.AspNetCore.Hosting;
  3. using Microsoft.AspNetCore.Http;
  4. using Aliyun.Serverless.Core;
  5. using Aliyun.Serverless.Core.Http;
  6. namespace MySpace.TestHandlers
  7. {
  8. public class SingleHttpHandler : FcHttpEntrypoint
  9. {
  10. protected override void Init(IWebHostBuilder builder)
  11. { }
  12. public override async Task<HttpResponse> HandleRequest(HttpRequest request, HttpResponse response, IFcContext fcContext)
  13. {
  14. response.StatusCode = 200;
  15. response.ContentType = "text/plain";
  16. await response.WriteAsync("hello world");
  17. return response;
  18. }
  19. }
  20. }

Input parameters

Description

The C#-written functions with HTTP triggers must inherit FcHttpEntrypoint in Aliyun.Serverless.Core.Http. The Init function must be overridden. HandleRequest is a handler and can be overridden as needed.

  • Single function: used to override HandleRequest, which is the logical processing of HandleRequest customization.

  • Asp.net core application: Only the Init function is overridden.

The example in the following section shows how to use FcHttpEntrypoint.

Example of handlers with an HTTP trigger

Single function example

The following example shows how to use HttpRequest and HttpResponse of a handler with an HTTP trigger.

  1. using System.IO;
  2. using System.Threading.Tasks;
  3. using Microsoft.AspNetCore.Hosting;
  4. using Microsoft.AspNetCore.Http;
  5. using Aliyun.Serverless.Core;
  6. using Aliyun.Serverless.Core.Http;
  7. using Microsoft.Extensions.Logging;
  8. namespace MySpace.TestHandlers
  9. {
  10. public class SingleHttpHandler : FcHttpEntrypoint
  11. {
  12. protected override void Init(IWebHostBuilder builder)
  13. {
  14. }
  15. public override async Task<HttpResponse> HandleRequest(HttpRequest request, HttpResponse response, IFcContext fcContext)
  16. {
  17. string method = request.Method;
  18. string relativePath = request.Path.Value;
  19. fcContext.Logger.LogInformation("method = {0}; requestPath = {1}", method, relativePath);
  20. StreamReader sr = new StreamReader(request.Body);
  21. string requestBody = sr.ReadToEnd();
  22. fcContext.Logger.LogInformation("requestBody = {}", requestBody);
  23. // process request.Headers
  24. response.StatusCode = 200;
  25. response.ContentType = "text/plain";
  26. response.Headers.Add("customheader", "v1");
  27. await response.WriteAsync("hello world");
  28. return response;
  29. }
  30. }
  31. }

Example of Asp.net core application

  1. using System;
  2. using Aliyun.Serverless.Core.Http;
  3. using Microsoft.AspNetCore.Hosting;
  4. namespace MySpace.TestWebApi
  5. {
  6. public class FcRemoteEntrypoint : FcHttpEntrypoint
  7. {
  8. protected override void Init(IWebHostBuilder builder)
  9. {
  10. builder
  11. .UseStartup<Startup>();
  12. }
  13. }
  14. }

Procedure

  1. Create a webapi project of asp.net core.

    1. [songluo@~/tmp]# mkdir fcaspdotnetsample
    2. [songluo@~/tmp]# cd fcaspdotnetsample
    3. [songluo@~/tmp/fcaspdotnetsample]# dotnet new webapi
  2. Add the following package to fcaspdotnetsample.csproj:

    1. <ItemGroup>
    2. <PackageReference Include="Aliyun.Serverless.Core" Version="1.0.1" />
    3. <PackageReference Include="Aliyun.Serverless.Core.Http" Version="1.0.2" />
    4. </ItemGroup>
  3. Create a file named FcRemoteEntrypoint.cs that contains the sample code of Asp.net core application.

  4. Publish the project and compress the target files into a .zip package.

    1. [songluo@~/tmp/fcaspdotnetsample]# dotnet publish -c Release
    2. Microsoft (R) Build Engine version 15.9.20+g88f5fadfbe for .NET Core
    3. Copyright (C) Microsoft Corporation. All rights reserved.
    4. Restore completed in 88.39 ms for /Users/songluo/tmp/fcaspdotnetsample/fcaspdotnetsample.csproj.
    5. fcaspdotnetsample -> /Users/songluo/tmp/fcaspdotnetsample/bin/Release/netcoreapp2.1/fcaspdotnetsample.dll
    6. fcaspdotnetsample -> /Users/songluo/tmp/fcaspdotnetsample/bin/Release/netcoreapp2.1/publish/
    7. [songluo@~/tmp/fcaspdotnetsample]# cd /Users/songluo/tmp/fcaspdotnetsample/bin/Release/netcoreapp2.1/publish/
    8. [songluo@~/tmp/fcaspdotnetsample/bin/Release/netcoreapp2.1/publish]# zip -r fcaspdotnetsample.zip *
    9. adding: appsettings.Development.json (deflated 40%)
    10. adding: appsettings.json (deflated 30%)
    11. adding: fcaspdotnetsample.deps.json (deflated 85%)
    12. adding: fcaspdotnetsample.dll (deflated 61%)
    13. adding: fcaspdotnetsample.pdb (deflated 40%)
    14. adding: fcaspdotnetsample.runtimeconfig.json (deflated 31%)
    15. adding: web.config (deflated 40%)
    16. [songluo@~/tmp/fcaspdotnetsample/bin/Release/netcoreapp2.1/publish]# ls -ll fcaspdotnetsample.zip
    17. -rw-r--r-- 1 songluo staff 39101 Mar 15 09:47 fcaspdotnetsample.zip

Use fcaspdotnetsample.zip to create a function with the runtime .NET Core 2.1 and the handler fcaspdotnetsample::MySpace.TestWebApi.FcRemoteEntrypoint::HandleRequest.

If the Single function is used, create a console project and FcRemoteEntrypoint.cs by following the instructions provided in Complete operation example of common handlers, and replace the code with the sample code of the Single function.

Limits on handlers with an HTTP trigger

Request limits

If the request for a handler with an HTTP trigger exceeds the following limits, the 400 status code and InvalidArgument error code are thrown.

Parameter Limits HTTP status code Error code
headers The size of all key-value pairs in the headers cannot exceed 4 KB. 400 InvalidArgument
path The size of the path and all query parameters cannot exceed 4 KB.
body The size of the HTTP request body cannot exceed 6 MB.

Response limits

If the response for a handler with an HTTP trigger exceeds the following limits, the 502 status code and BadResponse error code are thrown.

Parameter Limits HTTP status code Error code
headers The size of all key-value pairs in the headers cannot exceed 4 KB. 502 BadResponse
body The size of the HTTP response body cannot exceed 6 MB.

For more information about HTTP triggers, see HTTP trigger.

Reference documents

For more information about the C# runtime, see C# runtime.