1
|
|
|
<?php |
2
|
|
|
|
3
|
|
|
namespace Tgallice\FBMessenger; |
4
|
|
|
|
5
|
|
|
use GuzzleHttp\Client; |
6
|
|
|
use GuzzleHttp\ClientInterface; |
7
|
|
|
use GuzzleHttp\Exception\GuzzleException; |
8
|
|
|
use GuzzleHttp\RequestOptions; |
9
|
|
|
use Psr\Http\Message\ResponseInterface; |
10
|
|
|
use Tgallice\FBMessenger\Attachment\Structured; |
11
|
|
|
use Tgallice\FBMessenger\Exception\ApiException; |
12
|
|
|
use Tgallice\FBMessenger\Message\Message; |
13
|
|
|
use Tgallice\FBMessenger\Model\MessageResponse; |
14
|
|
|
use Tgallice\FBMessenger\Model\UserProfile; |
15
|
|
|
|
16
|
|
|
class Messenger |
17
|
|
|
{ |
18
|
|
|
const API_BASE_URI = 'https://graph.facebook.com/v2.6'; |
19
|
|
|
|
20
|
|
|
/** |
21
|
|
|
* @var string |
22
|
|
|
*/ |
23
|
|
|
private $token; |
24
|
|
|
|
25
|
|
|
/** |
26
|
|
|
* @var ClientInterface |
27
|
|
|
*/ |
28
|
|
|
private $client; |
29
|
|
|
|
30
|
|
|
/** |
31
|
|
|
* @var ResponseInterface |
32
|
|
|
*/ |
33
|
|
|
private $lastResponse; |
34
|
|
|
|
35
|
|
|
/** |
36
|
|
|
* @param string $token |
37
|
|
|
* @param ClientInterface $client |
38
|
|
|
*/ |
39
|
9 |
|
public function __construct($token, ClientInterface $client = null) |
40
|
|
|
{ |
41
|
9 |
|
$this->token = $token; |
42
|
9 |
|
$this->client = $client ?: new Client([ |
43
|
|
|
'base_uri' => self::API_BASE_URI, |
44
|
|
|
]); |
45
|
9 |
|
} |
46
|
|
|
|
47
|
|
|
/** |
48
|
|
|
* @param Message $message |
49
|
|
|
* |
50
|
|
|
* @return MessageResponse |
51
|
|
|
* |
52
|
|
|
* @throws ApiException |
53
|
|
|
*/ |
54
|
1 |
|
public function sendMessage(Message $message) |
55
|
|
|
{ |
56
|
1 |
|
$options = RequestOptionsFactory::create($message); |
57
|
1 |
|
$responseData = $this->send('POST', '/me/messages', $options); |
58
|
|
|
|
59
|
1 |
|
return new MessageResponse($responseData['recipient_id'], $responseData['message_id']); |
60
|
|
|
} |
61
|
|
|
|
62
|
|
|
/** |
63
|
|
|
* @param string $userId |
64
|
|
|
* @param array $fields |
65
|
|
|
* |
66
|
|
|
* @return UserProfile |
67
|
|
|
*/ |
68
|
1 |
|
public function getUserProfile( |
69
|
|
|
$userId, |
70
|
|
|
array $fields = [ |
71
|
|
|
UserProfile::FIRST_NAME, |
72
|
|
|
UserProfile::LAST_NAME, |
73
|
|
|
UserProfile::PROFILE_PIC, |
74
|
|
|
] |
75
|
|
|
) { |
76
|
|
|
$options = [ |
77
|
1 |
|
RequestOptions::QUERY => [ |
78
|
1 |
|
'fields' => implode(',', $fields) |
79
|
1 |
|
] |
80
|
1 |
|
]; |
81
|
|
|
|
82
|
1 |
|
$responseData = $this->send('GET', sprintf('/%s', $userId), $options); |
83
|
|
|
|
84
|
1 |
|
return UserProfile::create($responseData); |
85
|
|
|
} |
86
|
|
|
|
87
|
|
|
/** |
88
|
|
|
* @param string|Structured $message |
89
|
|
|
* @param string $pageId |
90
|
|
|
* |
91
|
|
|
* @return array |
92
|
|
|
*/ |
93
|
2 |
View Code Duplication |
public function setWelcomeMessage($message, $pageId) |
|
|
|
|
94
|
|
|
{ |
95
|
|
|
$options = [ |
96
|
2 |
|
RequestOptions::JSON => $this->buildWelcomeData($message), |
97
|
2 |
|
]; |
98
|
|
|
|
99
|
2 |
|
return $this->send('POST', sprintf('/%s/thread_settings', $pageId), $options); |
100
|
|
|
} |
101
|
|
|
|
102
|
|
|
/** |
103
|
|
|
* Subscribe the app to the page |
104
|
|
|
* |
105
|
|
|
* @return bool |
106
|
|
|
*/ |
107
|
1 |
|
public function subscribe() |
108
|
|
|
{ |
109
|
1 |
|
$response = $this->send('POST', '/me/subscribed_apps'); |
110
|
|
|
|
111
|
1 |
|
return $response['success']; |
112
|
|
|
} |
113
|
|
|
|
114
|
|
|
/** |
115
|
|
|
* @param string $pageId |
116
|
|
|
* |
117
|
|
|
* @return array |
118
|
|
|
*/ |
119
|
1 |
View Code Duplication |
public function deleteWelcomeMessage($pageId) |
|
|
|
|
120
|
|
|
{ |
121
|
|
|
$options = [ |
122
|
1 |
|
RequestOptions::JSON => $this->buildWelcomeData(), |
123
|
1 |
|
]; |
124
|
|
|
|
125
|
1 |
|
return $this->send('POST', sprintf('/%s/thread_settings', $pageId), $options); |
126
|
|
|
} |
127
|
|
|
|
128
|
|
|
/** |
129
|
|
|
* @param $method |
130
|
|
|
* @param $uri |
131
|
|
|
* @param array $options |
132
|
|
|
* |
133
|
|
|
* @return array |
134
|
|
|
* |
135
|
|
|
* @throws ApiException |
136
|
|
|
*/ |
137
|
8 |
|
public function send($method, $uri, array $options = []) |
138
|
|
|
{ |
139
|
|
|
try { |
140
|
8 |
|
$response = $this->client->request($method, $uri, $this->buildOptions($options)); |
141
|
|
|
// Catch all Guzzle\Request exceptions |
142
|
8 |
|
} catch (GuzzleException $e) { |
143
|
1 |
|
throw new ApiException($e->getMessage(), [ |
144
|
1 |
|
'code' => $e->getCode(), |
145
|
1 |
|
'exception' => $e, |
146
|
1 |
|
]); |
147
|
|
|
} |
148
|
|
|
|
149
|
7 |
|
$this->lastResponse = $response; |
150
|
|
|
|
151
|
7 |
|
return $this->getResponseData($response); |
152
|
|
|
} |
153
|
|
|
|
154
|
|
|
/** |
155
|
|
|
* Return the decoded body data |
156
|
|
|
* |
157
|
|
|
* @param ResponseInterface $response |
158
|
|
|
* |
159
|
|
|
* @return array |
160
|
|
|
* |
161
|
|
|
* @throws ApiException |
162
|
|
|
*/ |
163
|
7 |
|
private function getResponseData(ResponseInterface $response) |
164
|
|
|
{ |
165
|
7 |
|
$responseData = $this->decodeResponseBody($response); |
166
|
|
|
|
167
|
7 |
|
if (isset($responseData['error'])) { |
168
|
1 |
|
$message = isset($responseData['error']['message']) ? $responseData['error']['message'] : 'Unknown error'; |
169
|
1 |
|
throw new ApiException($message, $responseData['error']); |
170
|
|
|
} |
171
|
|
|
|
172
|
6 |
|
return $responseData; |
173
|
|
|
} |
174
|
|
|
|
175
|
|
|
/** |
176
|
|
|
* @param ResponseInterface $response |
177
|
|
|
* |
178
|
|
|
* @return null|array |
179
|
|
|
*/ |
180
|
7 |
|
private function decodeResponseBody(ResponseInterface $response) |
181
|
|
|
{ |
182
|
7 |
|
return json_decode((string) $response->getBody(), true); |
183
|
|
|
} |
184
|
|
|
|
185
|
|
|
/** |
186
|
|
|
* @param array $options |
187
|
|
|
* |
188
|
|
|
* @return array |
189
|
|
|
*/ |
190
|
8 |
|
private function buildOptions(array $options = []) |
191
|
|
|
{ |
192
|
8 |
|
$options[RequestOptions::QUERY]['access_token'] = $this->token; |
193
|
|
|
|
194
|
8 |
|
return $options; |
195
|
|
|
} |
196
|
|
|
|
197
|
|
|
/** |
198
|
|
|
* @param mixed $message |
199
|
|
|
* |
200
|
|
|
* @return array |
201
|
|
|
*/ |
202
|
3 |
|
private function buildWelcomeData($message = null) |
203
|
|
|
{ |
204
|
|
|
$data = [ |
205
|
3 |
|
'setting_type' => 'call_to_actions', |
206
|
3 |
|
'thread_state' => 'new_thread', |
207
|
3 |
|
'call_to_actions' => [], |
208
|
3 |
|
]; |
209
|
|
|
|
210
|
3 |
|
if (null === $message) { |
211
|
1 |
|
return $data; |
212
|
|
|
} |
213
|
|
|
|
214
|
2 |
|
$type = is_string($message) ? 'text' : 'attachment'; |
215
|
|
|
|
216
|
2 |
|
$data['call_to_actions'][] = [ |
217
|
2 |
|
'message' => [$type => $message], |
218
|
|
|
]; |
219
|
|
|
|
220
|
2 |
|
return $data; |
221
|
|
|
} |
222
|
|
|
} |
223
|
|
|
|
Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.
You can also find more detailed suggestions in the “Code” section of your repository.