javascript/ajaxでIncoming WebhookにPOSTするまでにつまづいた箇所


Incoming Webhookをslackに追加する

実装

とりあえず最終形態。

function submit() {
  const url = "https://hooks.slack.com/services/xxxxxxxxxx";
  const data = {
    text: "testです"
  };

  const xml = new XMLHttpRequest();
  xml.open("POST", url, false);
  xml.setRequestHeader("content-type", "application/x-www-form-urlencoded;charset=UTF-8");
  xml.send(`payload=${JSON.stringify(data)}`)
}

詰まったところ

エラー

Access to fetch at 'https://hooks.slack.com/services/・・・' from origin 'null' has been blocked by CORS policy: Request header field content-type is not allowed by Access-Control-Allow-Headers in preflight response.

該当箇所

"Content-Type": "application/json; charset=utf-8"

理由

https://stackoverflow.com/questions/45752537/slack-incoming-webhook-request-header-field-content-type-is-not-allowed-by-acce

フロントエンドのJavaScriptからJSONを想定しているAPIエンドポイントに投稿するときは、そのContent-Type: application/jsonヘッダーをリクエストに追加することが、まさにあなたがする必要があり、すべきことです。しかし、この場合ではありません - その特定のAPIエンドポイントはそれを適切に処理しないからです。

'Content-type': 'application/json'
を削除しろとのこと。

なので削除して見たら、400が返ってくる。

Ajax (XMLHttpRequest) を使用していたが、jQueryの$.ajaxで送信している人がいたので参考に$.ajaxで試したら、送信できた。

差異を確認すると、どうやらcontentTypeが違っているようだ。
$.ajaxの初期値は'application/x-www-form-urlencoded; charset=UTF-8'
http://js.studio-kingdom.com/jquery/ajax/ajax

しかし、Ajax (XMLHttpRequest) の初期値は'text/plain;charset=UTF-8'

xml.setRequestHeader("content-type", "application/x-www-form-urlencoded;charset=UTF-8");

を追記することで解決できた。

ただのテキストだよって送ってたからエラーになってたんですね。