IBM Watson speech to text WebSocket authorization with IAM API 密钥

IBM Watson speech to text WebSocket authorization with IAM API key

我正在尝试使用仅具有 IAM 授权的新帐户连接到 IBM Watson 的语音以发送文本 WebSocket。

我的 WS 端点是 wss://stream-fra.watsonplatform.net/text-to-speech/api/v1/recognize,我通过 https://iam.bluemix.net/identity/token 获得了一个访问令牌。现在,当我用 Authorization header 和值 Bearer token 打开套接字连接时,我得到一个错误的握手响应:websocket: bad handshake, Unauthorized 401。语言是围棋。

我是不是做错了什么,或者在没有 username/password 身份验证的情况下无法将 Watson 的语音连接到文本 WebSocket,即已弃用的 watson-token

编辑:

打开WebSocket的代码:

headers := http.Header{}
headers.Set("Authorization", "Bearer " + access_token)
conn, resp, err := websocket.DefaultDialer.Dial("wss://stream-fra.watsonplatform.net/text-to-speech/api/v1/recognize", headers)

我也尝试过 apikey:**api_key** 的基本授权,结果是一样的:401.

编辑 2:

用于获取成功的访问令牌(基于 Watson Swift 和 Python SDK)以及 returns 访问和刷新令牌的代码:

func getWatsonToken(apiKey string) (string, error) {
    // Base on the Watson Swift and Python SDKs
    // https://github.com/watson-developer-cloud/restkit/blob/master/Sources/RestKit/Authentication.swift
    // https://github.com/watson-developer-cloud/python-sdk/blob/master/watson_developer_cloud/iam_token_manager.py

    const tokenUrl = "https://iam.bluemix.net/identity/token"

    form := url.Values{}
    form.Set("grant_type", "urn:ibm:params:oauth:grant-type:apikey")
    form.Set("apikey", apiKey)
    form.Set("response_type", "cloud_iam")

    // Token from simple "http.PostForm" does not work either
    //resp, err := http.PostForm(tokenUrl, form)

    req, err := http.NewRequest(http.MethodPost, tokenUrl, nil)
    if err != nil {
        log.Printf("could not create HTTP request to get Watson token: %+v", err)
        return "", nil
    }

    header := http.Header{}
    header.Set("Content-Type", "application/x-www-form-urlencoded")
    header.Set("Accept", "application/json")
    // "Yng6Yng=" is "bx:bx"
    header.Set("Authorization", "Basic Yng6Yng=")
    req.Header = header

    req.Body = ioutil.NopCloser(bytes.NewReader([]byte(form.Encode())))

    resp, err := http.DefaultClient.Do(req)
    if err != nil {
        log.Printf("problem executing HTTP request to get Watson token: %+v", err)
        return "", err
    }

    defer resp.Body.Close()

    if resp.StatusCode != 200 {
        return "", errors.New(fmt.Sprintf("failed to get Watson token: %d", resp.StatusCode))
    }

    jsonBody, err := ioutil.ReadAll(resp.Body)
    if err != nil {
        log.Printf("problem reading Watson token from response body: %+v", err)
    }

    tokenResponse := &struct {
        AccessToken  string `json:"access_token"`
        RefreshToken string `json:"refresh_token"`
        TokenType    string `json:"token_type"`
        ExpiresIn    int64  `json:"expires_in"`
        Expiration   int64  `json:"expiration"`
    }{}

    err = json.Unmarshal(jsonBody, tokenResponse)
    if err != nil {
        log.Printf("could not parse Watson token response: %+v", err)
        return "", err
    }

    return tokenResponse.AccessToken, err
}

我在端点中出错,使用了文本转语音而不是语音转文本。使用正确的 URL WebSocket API 工作。

wss://stream-fra.watsonplatform.net/text-to-speech/api/v1/recognize 应该是 wss://stream-fra.watsonplatform.net/speech-to-text/api/v1/recognize