backlog API を使う⑤　～backlogの課題にファイルを添付する～

#1、環境
php4.5
windows7

#2、添付ファイルの送信
backlogの課題にファイルを添付をする為に、
まずは「添付ファイルの送信」apiを実行し添付IDを取得します。

**公式サイト**
https://developer.nulab-inc.com/ja/docs/backlog/api/2/post-attachment-file/

**メソッド**

```ruby:
POST
```

**URL**

```ruby:
/api/v2/space/attachment 
```

|パラメーター名 |内容|
|:-----------------|:------------------|
| apiKey             |APIキー（[backlog API を使う①](http://qiita.com/d2cdot-mmori/items/56c6abc1526fc2b13aef)参照）|

#3、コード（添付ファイルの送信）

```ruby:php5.4の場合は自前でマルチパートボディを組み立てて文字列にする
<?php
/*************************************
* バックログの課題にコメントと添付ファイルを投稿するテスト
**************************************/
$backlog_api_key = "作成したAPIキー";
$file_url = '/var/www/html/xxxxxxx/mori/backlogapi/test.csv'; // アップロードするファイルのパス
$filename = "test.csv";
// 添付ファイルの送信api
$attachment_url = 'https://xxx.backlog.jp/api/v2/space/attachment?apiKey='.$backlog_api_key;

$ch = curl_init($attachment_url);
// php5.4の為、自前でマルチパートボディを組み立てて文字列にする
curl_custom_postfields(
  $ch,
  array("filename" => $filename,'file' => $file_url)
);
$response = curl_exec($ch);
curl_close($ch);


/**
* マルチパートボディを組み立てて文字列としてセットする。
*
* @param resource $ch cURLリソース
* @param array $files 「送信するファイル名=>ファイル名, ファイルURL=>ファイルURL」の形の連想配列
* @return bool 成功 or 失敗
*/
function curl_custom_postfields($ch, array $files = array()) {
  static $disallow = array("\0", "\"", "\r", "\n");
  $body = array();
  $data = file_get_contents($files["file"]);
  $body[] = implode("\r\n", array(
    "Content-Disposition: form-data; name=file; filename=\"{$files["filename"]}\"",
    "Content-Type: application/octet-stream",
    "",
    $data,
  ));
  do {
    $boundary = "---------------------" . md5(mt_rand() . microtime());
  } while (preg_grep("/{$boundary}/", $body));
  array_walk($body, function (&$part) use ($boundary) {
    $part = "--{$boundary}\r\n{$part}";
  });
  $body[] = "--{$boundary}--";
  $body[] = "";
  return curl_setopt_array($ch, array(
    CURLOPT_CUSTOMREQUEST       => 'POST',
    CURLOPT_RETURNTRANSFER       => true,
    CURLOPT_POSTFIELDS => implode("\r\n", $body),
    CURLOPT_HTTPHEADER => array(
      "Expect: 100-continue",
      "Content-Type: multipart/form-data; boundary={$boundary}",
    ),
  ));
}
```

▼php5.5.0以上の場合はCURLFileが使用できるので、もっとスマートに書けます。

```ruby:php5.5.5の場合
<?php
/*************************************
* バックログの課題にコメントと添付ファイルを投稿するテスト
**************************************/
$backlog_api_key = "作成したAPIキー";
$file_url = '/var/www/html/xxxxxxx/mori/backlogapi/test.csv'; // アップロードするファイルのパス
$filename = "test.csv";
// 添付ファイルの送信api
$attachment_url = 'https://xxx.backlog.jp/api/v2/space/attachment?apiKey='.$backlog_api_key;

$file = new CURLFile($file_url,'text/comma-separated-values',$filename);
$postfields = array("file"=>$file);
$header = [
'Content-Disposition: form-data; name="file"; filename=' . $filename .
  'Content-Type: application/octet-stream'
];
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $attachment_url);
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'POST');
curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
curl_setopt($ch, CURLOPT_POSTFIELDS, $postfields);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
curl_close($ch);
}
```



#4、レスポンス例
```ruby:成功時レスポンス例
{
  "id": 315,
  "name": "test.csv",
  "size": 1812
}
```

```ruby:失敗時レスポンス例
{
  "errors": [
    {
      "message": "Undefined resource. /api/v2/space/attachments",
      "code": 6,
      "moreInfo": ""
    }
  ]
}
```

これで添付ファイルをバックログに送信でき、添付IDを取得することができました。

#5、「課題コメントの追加」apiを使用し、ファイルを添付する
[backlog API を使う②](http://qiita.com/d2cdot-mmori/items/11c809234f0ccb9ceef9)で解説した、「課題コメントの追加」apiを使用して課題にファイルを添付します。

**公式サイト**
https://developer.nulab-inc.com/ja/docs/backlog/api/2/add-comment/

**メソッド**

```ruby:
POST
```

**URL**

```ruby:
/api/v2/issues/:issueIdOrKey/comments 
```

|パラメーター名 |内容|
|:-----------------|:------------------|
| apiKey             |APIキー（[backlog API を使う①](http://qiita.com/d2cdot-mmori/items/56c6abc1526fc2b13aef)参照）|
| issueIdOrKey        | コメントしたい課題番号 |
| content           | コメント内容 |
|notifiedUserId[]|コメント登録の通知を受け取るユーザーID（[backlog API を使う③](http://qiita.com/d2cdot-mmori/items/d2697778b6765d994bd1)参照）|
|attachmentId[]|添付ファイルの送信APIが返すID|


#6、コード

```ruby:
<?php
/**************************
* backlogの課題にコメントを送信しユーザーに通知する
***************************/
$issueIdOrKey = "HOGE-12"; // コメントしたい課題番号
$backlog_api_key = "作成したAPIキー";
$comment = "コメント";
$notifiedUserId_001 = "コメントの通知を受け取るユーザーID（1人目）";
$notifiedUserId_002 = "コメントの通知を受け取るユーザーID（2人目）";
$attachmentId = "添付ファイルの送信apiが返す添付ID";


$comment_url = "https://xxx.backlog.jp/api/v2/issues/".$issueIdOrKey."/comments?apiKey=".$backlog_api_key;
$params = array(
  'content' => $comment,
  'notifiedUserId[0]' => $notifiedUserId_001,
  'notifiedUserId[1]' => $notifiedUserId_002,
  'attachmentId[]' => $attachmentId
);
$comment_url = $comment_url . "&".http_build_query($params, "", "&");
$comment_headers = array('Content-Type: application/x-www-form-urlencoded');
$context = array('http' => array(
  'method' => 'POST',
  'header' => $comment_headers,
  'ignore_errors' => true
));
$response = file_get_contents($comment_url, false, stream_context_create($context));
```

成功すれば、バックログの課題にコメントと特定ユーザーへの通知、さらにファイルの添付が確認できると思います！

以上です。