質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
HTTP

HTTP(Hypertext Transfer Protocol)とはweb上でHTML等のコンテンツを交換するために使われるアプリケーション層の通信プロトコルです。

アップロード

アップロードは特定のファイルをウェブサーバに送るプロセスのことを指します。

Kotlin

Kotlinは、ジェットブレインズ社のアンドリー・ブレスラフ、ドミトリー・ジェメロフが開発した、 静的型付けのオブジェクト指向プログラミング言語です。

ChatWork

業務の効率化を目的としたコミュニケーションツール。 グループチャット、ビデオ・音声通話、ファイル共有、タスク管理などの機能を備えています。マルチデバイス対応で、ブラウザだけでなくタブレットやスマートフォンでも利用可能です。

Spring Boot

Spring Bootは、Javaのフレームワークの一つ。Springプロジェクトが提供する様々なフレームワークを統合した、アプリケーションを高速で開発するために設計されたフレームワークです。

Q&A

0回答

3238閲覧

Chatwork APIでファイルアップロードしたい(Kotlin + SpringBoot)

maequn

総合スコア6

HTTP

HTTP(Hypertext Transfer Protocol)とはweb上でHTML等のコンテンツを交換するために使われるアプリケーション層の通信プロトコルです。

アップロード

アップロードは特定のファイルをウェブサーバに送るプロセスのことを指します。

Kotlin

Kotlinは、ジェットブレインズ社のアンドリー・ブレスラフ、ドミトリー・ジェメロフが開発した、 静的型付けのオブジェクト指向プログラミング言語です。

ChatWork

業務の効率化を目的としたコミュニケーションツール。 グループチャット、ビデオ・音声通話、ファイル共有、タスク管理などの機能を備えています。マルチデバイス対応で、ブラウザだけでなくタブレットやスマートフォンでも利用可能です。

Spring Boot

Spring Bootは、Javaのフレームワークの一つ。Springプロジェクトが提供する様々なフレームワークを統合した、アプリケーションを高速で開発するために設計されたフレームワークです。

0グッド

0クリップ

投稿2019/12/09 04:07

編集2019/12/14 01:02

前提・実現したいこと

Kotlin+SpringBoot でサーバ内で生成したファイルを連携したチャットルームに投稿する機能を実装しています。
対象チャットツールはChatworkです。
ChatWorkAPIを叩く際のHTTPクライアントはSpring RestTemplateを利用しています。

実現したいことは以下のエンドポイントへのファイルアップロードです。
http://developer.chatwork.com/ja/endpoint_rooms.html#POST-rooms-room_id-files

発生している問題・エラーメッセージ

【問題点】
エンドポイントが要求している形でリクエストボディが作成できていないのか、ステータスコード400(Bad Request)でレスポンスされてしまいます。
何が不足しているのかわからず、、、確認すべき点や修正すべき箇所があればご指摘いただきたいです。

該当のソースコード

Kotlin

1package com.***.***.domain.service.api.chatwork.impl 2 3import com.***.***.domain.service.api.chatwork.ChatWorkRoomID 4import com.***.***.domain.service.api.chatwork.ChatWorkToken 5import com.***.***.domain.service.api.chatwork.ChatworkService 6import org.springframework.core.io.ByteArrayResource 7import org.springframework.core.io.Resource 8import org.springframework.http.ContentDisposition 9import org.springframework.http.HttpEntity 10import org.springframework.http.HttpHeaders 11import org.springframework.http.MediaType 12import org.springframework.stereotype.Service 13import org.springframework.util.LinkedMultiValueMap 14import org.springframework.util.MultiValueMap 15import org.springframework.web.client.RestTemplate 16import java.io.File 17import java.nio.file.Files 18import java.nio.file.Path 19 20 21@Service 22class ChatworkServiceImpl(private val restTemplate: RestTemplate) : ChatworkService { 23 24 /** 25 * ファイル + メッセージ 投稿. 26 */ 27 override fun post(message: String, filePath: Path, roomID: ChatWorkRoomID, token: ChatWorkToken): Boolean { 28 // エンドポイント 29 val url = "https://api.chatwork.com/v2/rooms/${roomID}/files" 30 // アップロードファイル 31 val file: File = filePath.toFile() 32 // アップロードファイルのコンテンツタイプ 33 val contentType: String = Files.probeContentType(filePath) 34 35 // HTTPリクエストヘッダ作成 36 val headers = HttpHeaders() 37 headers.contentType = MediaType.MULTIPART_FORM_DATA 38 headers.set("X-ChatWorkToken", token) 39 40 // HTTPリクエストボディ作成 41 val fileHeaders = HttpHeaders() 42 fileHeaders.contentType = MediaType.parseMediaType(contentType) 43 val uploadFileData: Resource = object : ByteArrayResource(file.readBytes()) { 44 override fun getFilename(): String { 45 return file.name 46 } 47 48 override fun contentLength(): Long { 49 return file.length() 50 } 51 } 52 val fileEntity = HttpEntity(uploadFileData, fileHeaders) 53 val body: MultiValueMap<String, Object> = LinkedMultiValueMap<String, Object>() 54 body.add("file", fileEntity as Object) 55 body.add("message", "テスト" as Object) 56 57 // リクエスト & レスポンス 58 val request = HttpEntity(body, headers) 59 val response = restTemplate.postForEntity(url, request, String::class.java) 60 return response.statusCode.is2xxSuccessful 61 } 62}

試したこと

ファイルアップロードで使用したAPIトークンやRoomIDは以下のメッセージ送信処理では有効でしたので必要なパラメータは用意できていると判断しています。
Chatworkのサポートにアドバイスを求めるもAPIについてはサポート対象外とのこと...

HTTPリクエストのログ

[API:Request(5c1b57c0-228e-4c05-a605-92e019721ac5)] Request=[POST:https://api.chatwork.com/v2/rooms/00000000/files], Headers=[[Accept:"text/plain, application/json, application/*+json, */*", Content-Type:"multipart/form-data;charset=UTF-8;boundary=tQc3hQBjk3FyTcoV9i2q5WDRKyraUHhMY_1WPY", X-ChatWorkToken:"***********", Content-Length:"9287"]], Body=[--tQc3hQBjk3FyTcoV9i2q5WDRKyraUHhMY_1WPY Content-Disposition: form-data; name="file"; filename="template.xlsx" Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet Content-Length: 8861 �k��q�:&zw����`Ⱥ%�e9v�7;�[f��nĠh]�����8x���X�V�� �u�2���b��ޒ��*���'�p�^ՉRI-����Y�������JҺ�*�W�˟��h�صF-��ߤ[�~��PK! ��GI{docProps/core.xml . . 省略 . ��GI{�docProps/core.xmlPK-!EO�U�#-docProps/app.xmlPK � --tQc3hQBjk3FyTcoV9i2q5WDRKyraUHhMY_1WPY Content-Disposition: form-data; name="message" Content-Type: text/plain;charset=UTF-8 Content-Length: 9 テスト --tQc3hQBjk3FyTcoV9i2q5WDRKyraUHhMY_1WPY-- ]

HTTPレスポンスのログ

[API:Response(5c1b57c0-228e-4c05-a605-92e019721ac5)] Status=[400:Bad Request], Headers=[[Content-Type:"application/json", Content-Length:"64", Connection:"keep-alive", Date:"Wed, 11 Dec 2019 10:25:45 GMT", x-amzn-RequestId:"01c2efde-74d2-46c2-ab03-3f3478abf844", x-amzn-ErrorType:"AccessDeniedException", x-amz-apigw-id:"EiOWeEQiNjMFnkg=", X-Cache:"Error from cloudfront", Via:"1.1 c6a9836e54cf7bc2bb59e3fb86f871e1.cloudfront.net (CloudFront)", X-Amz-Cf-Pop:"NRT20-C1", X-Amz-Cf-Id:"LgV5C-NNYcwt52lodk8KhLRct-35xCyLYPqG71tNqIQpoSxWGkHtCw=="]], Body=[{"errors":["Please upload the file with `multipart/form-data`"]}]

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

maequn

2019/12/11 10:49

コメントで載せていただいた記事を参考にログを出力し、追記させていただきました! レスポンスログの末尾で「Please upload the file with `multipart/form-data`」って言われちゃってるのですが、リクエストのContent-Typeはmultipart/form-dataになっているので問題なさそうに思えます。。。
IT_hippie

2020/04/22 05:04

初めまして! こちらの問題はすでに解決されたのですか?
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだ回答がついていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問