C# IBM Speech to Text 使用 APIKey 获取令牌

C# IBM Speech to Text Get Token using APIKey

基于 https://gist.github.com/nfriedly/0240e862901474a9447a600e5795d500 中的示例, 我正在尝试使用 WebSocket 来使用 IBM Speech to Text API。 但是我在身份验证部分遇到了问题。 看起来现在 IBM 不再提供 username/password。 只有一个 api 键。

所以我找不到添加该示例以使用 api 获取令牌的方法。

有人知道如何使用带有 IBM api 密钥的 WebSocket 进行身份验证吗? IBM 文档似乎也不是最新的,因为他们的示例使用带有用户名和密码的 CURL https://console.bluemix.net/docs/services/speech-to-text/getting-started.html#getting-started-tutorial

我什至在某处看到我可以用 "api" 替换用户名,用我的 api 密钥替换密码。 但这不起作用,因为我从服务器收到未经授权的错误。

也许我看错了,我应该传递一个令牌而不是密码。 但是,如何使用 websockets 从我的 API 密钥获取令牌?

我可以毫无问题地使用 HttpClient 获取令牌。 但之后我似乎无法将该令牌与 Websocket 一起使用,只能进一步调用 HttpClient。

在一些帮助下,我终于找到了如何使用 apiKey 处理 WebSocket。

我post这里的代码以防其他人需要它

IamTokenData GetIAMToken(string apikey)
{
  var wr = (HttpWebRequest)WebRequest.Create("https://iam.bluemix.net/identity/token");
  wr.Proxy = null;
  wr.Method = "POST";
  wr.Accept = "application/json";
  wr.ContentType = "application/x-www-form-urlencoded";

  using (TextWriter tw = new StreamWriter(wr.GetRequestStream()))
  {
    tw.Write($"grant_type=urn:ibm:params:oauth:grant-type:apikey&apikey={apikey}");
  }
  var resp = wr.GetResponse();
  using (TextReader tr = new StreamReader(resp.GetResponseStream()))
  {
    var s = tr.ReadToEnd();
    return JsonConvert.DeserializeObject<IamTokenData>(s);
  }
}

IamTokenData tokenData = GetIAMToken([Your IamApiKey]);

CancellationTokenSource cts = new CancellationTokenSource();

ClientWebSocket clientWebSocket = new ClientWebSocket();

clientWebSocket.Options.Proxy = null;
clientWebSocket.Options.SetRequestHeader("Authorization", $"Bearer {token.AccessToken}");

// Make the sure the following URL is that one IBM pointed you to
Uri connection = new Uri($"wss://gateway-wdc.watsonplatform.net/speech-to-text/api/v1/recognize");
try
{
  //await clientWebSocket.ConnectAsync(connection, cts.Token);
  clientWebSocket.ConnectAsync(connection, cts.Token).GetAwaiter().GetResult();
  Console.WriteLine("Connected!");
}
catch (Exception e)
{
  Console.WriteLine("Failed to connect: " + e.ToString());
  return null;
}

// ... Do what you need with the websocket after that ...