是否可以(输入)绑定到通过HTTP触发的函数中的表存储?
我正尝试在具有以下属性的常规http触发函数内部向表存储添加输入绑定:
[Table("MyTable", "MyPartition", "{httpTrigger}")] MyPoco poco
但是我执行它时却返回以下错误:
[6/5/2019 5:36:38 PM]发生未处理的主机错误。 [6/5/2019 5:36:38 PM] Microsoft.Azure.WebJobs.Host: 无法从Azure调用'tableStorageInputBindingHttpTriggered' WebJobs SDK。是否缺少Azure WebJobs SDK属性?。
另外,在启动时,我得到了这个异常:
[2019/6/5下午6:17:17] tableStorageInputBindingHttpTriggered:Microsoft.Azure.WebJobs.Host:错误索引方法“ tableStorageInputBindingHttpTriggered”。 Microsoft.Azure.WebJobs.Host:无法解析绑定参数“ httpTrigger”。绑定表达式必须映射到触发器提供的值或触发器绑定到的值的属性,或者必须是系统绑定表达式(例如sys.randguid,sys.utcnow等)。
这是全部功能:
public class MyPoco
{
public string PartitionKey { get; set; }
public string RowKey { get; set; }
public string Directory { get; set; }
}
public static class tableStorageInputBindingHttpTriggered
{
[FunctionName("tableStorageInputBindingHttpTriggered")]
public static async Task<IActionResult> Run(
[HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = null)] HttpRequest req,
[Table("MyTable", "MyPartition", "{httpTrigger}")] MyPoco poco,
ILogger log)
{
string name = req.Query["name"];
string requestBody = await new StreamReader(req.Body).ReadToEndAsync();
dynamic data = JsonConvert.DeserializeObject(requestBody);
name = name ?? data?.name;
return name != null
? (ActionResult)new OkObjectResult($"PK={poco.PartitionKey}, RK={poco.RowKey}, Text={poco.Directory}")
: new BadRequestObjectResult("");
}
}
我在做什么错?如何在http触发的azure函数中绑定到表存储?
答案 0 :(得分:2)
似乎您正在尝试从Azure Table Storage
中读取HTTP Trigger Function
。请参见下面的代码段:
您的POCO类别:
public class MyPoco
{
public string PartitionKey { get; set; }
public string RowKey { get; set; }
public string Directory { get; set; }
}
表存储类:
public class TableStorageClass
{
public TableStorageClass()
{
}
public TableStorageClass(DynamicTableEntity entity)
{
PartitionKey = entity.PartitionKey;
RowKey = entity.RowKey;
}
public string PartitionKey { get; set; }
public string RowKey { get; set; }
}
Azure HTTP触发功能V2:
public static class FunctionReadFromTableStorage
{
[FunctionName("FunctionReadFromTableStorage")]
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.");
//Read Request Body
var content = await new StreamReader(req.Body).ReadToEndAsync();
//Extract Request Body and Parse To Class
MyPoco objMyPoco = JsonConvert.DeserializeObject<MyPoco>(content);
// Validate param because PartitionKey and RowKey is required to read from Table storage In this case , so I am checking here.
dynamic validationMessage;
if (string.IsNullOrEmpty(objMyPoco.PartitionKey))
{
validationMessage = new OkObjectResult("PartitionKey is required!");
return (IActionResult)validationMessage;
}
if (string.IsNullOrEmpty(objMyPoco.RowKey))
{
validationMessage = new OkObjectResult("RowKey is required!");
return (IActionResult)validationMessage;
}
// Table Storage operation with credentials
var client = new CloudTableClient(new Uri("https://YourStorageURL.table.core.windows.net/"),
new Microsoft.WindowsAzure.Storage.Auth.StorageCredentials("YourStorageName", "xtaguZokAWbfYG4QDkBjT+YourStorageKey+T/kId/Ng+cl3TfYHtg=="));
var table = client.GetTableReference("YourTableName");
//Query filter
var query = new TableQuery()
{
FilterString = string.Format("PartitionKey eq '{0}' and RowKey eq '{1}'", objMyPoco.PartitionKey, objMyPoco.RowKey)
};
//Request for storage query with query filter
var continuationToken = new TableContinuationToken();
var storageTableQueryResults = new List<TableStorageClass>();
foreach (var entity in table.ExecuteQuerySegmentedAsync(query, continuationToken).GetAwaiter().GetResult().Results)
{
var request = new TableStorageClass(entity);
storageTableQueryResults.Add(request);
}
//As we have to return IAction Type So converting to IAction Class Using OkObjectResult We Even Can Use OkResult
var result = new OkObjectResult(storageTableQueryResults);
return (IActionResult)result;
}
}
记住点:
Azure Portal
的情况下,只需摆脱FunctionReadFromTableStorage
类using System;
using System.IO;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Azure.WebJobs;
using Microsoft.Azure.WebJobs.Extensions.Http;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Microsoft.WindowsAzure.Storage.Table;
using System.Collections.Generic;
邮递员请求模式:
函数调用示例:
{
"PartitionKey": "Your Param According to Table Storage Design" ,
"RowKey": "Your Param According to Table Storage Design",
"Directory": "Your Param According to Table Storage Design"
}
查看屏幕截图:
邮递员回复:
响应取决于我自己的表格设计
[
{
"partitionKey": "Microsoft SharePoint Server",
"rowKey": "2016"
}
]
请参见下面的屏幕截图:
注意:我喜欢以简单易懂的方式编写代码。我只是为您的情况尝试过。如果它解决了您的问题,我的努力将是 那么成功。这是到目前为止我所知道的最简单的方法
azure table storage
。
如果您还有任何问题,请随时分享。谢谢,祝您编程愉快!
答案 1 :(得分:1)
这通过绑定到CloudTable
using System;
using System.IO;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Azure.WebJobs;
using Microsoft.Azure.WebJobs.Extensions.Http;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Logging;
using Microsoft.WindowsAzure.Storage.Table;
namespace AzureFunctionsSandbox
{
public class MyPoco : TableEntity
{
public string Body { get; set; }
}
public static class Function1
{
[FunctionName("Function1")]
public static async Task<IActionResult> Run(
[HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = null)] HttpRequest req,
[Table("Sandbox", "StorageConnectionString")] CloudTable table,
ILogger log)
{
log.LogInformation("C# HTTP trigger function processed a request.");
string requestBody = await new StreamReader(req.Body).ReadToEndAsync();
var poco = new MyPoco { PartitionKey = "HttpTrigger", RowKey = Guid.NewGuid().ToString(), Body = requestBody };
var insertOperation = TableOperation.Insert(poco);
await table.ExecuteAsync(insertOperation);
return new OkObjectResult($"PK={poco.PartitionKey}, RK={poco.RowKey}, Text={poco.Body}");
}
}
}
注意:MyPoco
继承自TableEntity
,您可以创建TableOperation.Insert(poco)
,因为.Insert()
需要ITableEntity
。 / p>
local.settings.json
{
"IsEncrypted": false,
"Values": {
"AzureWebJobsStorage": "UseDevelopmentStorage=true",
"FUNCTIONS_WORKER_RUNTIME": "dotnet",
"StorageConnectionString": "UseDevelopmentStorage=true"
}
}