Completed
Push — master ( 776bcf...e74f71 )
by Irfaq
02:16
created

BotsManager::getDefaultBot()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 4
ccs 0
cts 2
cp 0
rs 10
cc 1
eloc 2
nc 1
nop 0
crap 2
1
<?php
2
3
namespace Telegram\Bot;
4
5
use Illuminate\Contracts\Config\Repository;
6
use Illuminate\Contracts\Foundation\Application;
7
use InvalidArgumentException;
8
9
/**
10
 * Class BotsManager
11
 *
12
 * @TODO Add methods in docblock for autocompletion from Api file.
13
 */
14
class BotsManager
15
{
16
    /**
17
     * The config instance.
18
     *
19
     * @var \Illuminate\Contracts\Config\Repository
20
     */
21
    protected $config;
22
23
    /**
24
     * The app instance.
25
     *
26
     * @var \Illuminate\Contracts\Foundation\Application
27
     */
28
    protected $app;
29
30
    /**
31
     * @var string Config Name
32
     */
33
    protected $configName = 'telegram';
34
35
    /**
36
     * The active bot instances.
37
     *
38
     * @var array
39
     */
40
    protected $bots = [];
41
42
    /**
43
     * TelegramManager constructor.
44
     *
45
     * @param Repository  $config
46
     * @param Application $app
47
     */
48
    public function __construct(Repository $config, Application $app)
49
    {
50
        $this->config = $config;
51
        $this->app = $app;
52
    }
53
54
    /**
55
     * Get the configuration for a bot.
56
     *
57
     * @param string $name
58
     *
59
     * @throws \InvalidArgumentException
60
     *
61
     * @return array
62
     */
63
    public function getBotConfig($name)
64
    {
65
        $name = $name ?: $this->getDefaultBot();
66
67
        $bots = $this->getConfig('bots');
68
        if (!is_array($config = array_get($bots, $name)) && !$config) {
69
            throw new InvalidArgumentException("Bot [$name] not configured.");
70
        }
71
72
        $config['bot'] = $name;
73
74
        return $config;
75
    }
76
77
    /**
78
     * Get a bot instance.
79
     *
80
     * @param string $name
81
     *
82
     * @return object
83
     */
84
    public function bot($name = null)
85
    {
86
        $name = $name ?: $this->getDefaultBot();
87
88
        if (!isset($this->bots[$name])) {
89
            $this->bots[$name] = $this->makeBot($name);
90
        }
91
92
        return $this->bots[$name];
93
    }
94
95
    /**
96
     * Reconnect to the given bot.
97
     *
98
     * @param string $name
99
     *
100
     * @return object
101
     */
102
    public function reconnect($name = null)
103
    {
104
        $name = $name ?: $this->getDefaultBot();
105
        $this->disconnect($name);
106
107
        return $this->bot($name);
108
    }
109
110
    /**
111
     * Disconnect from the given bot.
112
     *
113
     * @param string $name
114
     *
115
     * @return void
116
     */
117
    public function disconnect($name = null)
118
    {
119
        $name = $name ?: $this->getDefaultBot();
120
        unset($this->bots[$name]);
121
    }
122
123
    /**
124
     * Get the specified configuration value for Telegram.
125
     *
126
     * @param  string $key
127
     * @param  mixed  $default
128
     *
129
     * @return mixed
130
     */
131
    public function getConfig($key, $default = null)
132
    {
133
        return $this->config->get($this->configName.'.'.$key, $default);
134
    }
135
136
    /**
137
     * Get the default bot name.
138
     *
139
     * @return string
140
     */
141
    public function getDefaultBot()
142
    {
143
        return $this->getConfig('default');
144
    }
145
146
    /**
147
     * Set the default bot name.
148
     *
149
     * @param string $name
150
     *
151
     * @return void
152
     */
153
    public function setDefaultBot($name)
154
    {
155
        $this->config->set($this->configName.'.default', $name);
156
    }
157
158
    /**
159
     * Return all of the created bots.
160
     *
161
     * @return object[]
162
     */
163
    public function getBots()
164
    {
165
        return $this->bots;
166
    }
167
168
    /**
169
     * De-duplicate an array.
170
     *
171
     * @param array $array
172
     *
173
     * @return array
174
     */
175
    protected function deduplicateArray(array $array)
176
    {
177
        return array_values(array_unique($array));
178
    }
179
180
    /**
181
     * Make the bot instance.
182
     *
183
     * @param string $name
184
     *
185
     * @return Api
186
     */
187
    protected function makeBot($name)
188
    {
189
        $config = $this->getBotConfig($name);
190
191
        $token = array_get($config, 'token');
192
        $commands = array_get($config, 'commands', []);
193
194
        $telegram = new Api(
195
            $token,
196
            $this->getConfig('async_requests', false),
197
            $this->getConfig('http_client_handler', null)
198
        );
199
200
        // Check if DI needs to be enabled for Commands
201
        if ($this->getConfig('resolve_command_dependencies', true)) {
202
            $telegram->setContainer($this->app);
203
        }
204
205
        $commands = $this->parseBotCommands($commands);
206
207
        // Register Commands
208
        $telegram->addCommands($commands);
209
210
        return $telegram;
211
    }
212
213
    /**
214
     * Builds the list of commands for the given commands array.
215
     *
216
     * @param array $commands
217
     *
218
     * @return array An array of commands which includes global and bot specific commands.
219
     */
220
    protected function parseBotCommands(array $commands)
221
    {
222
        $globalCommands = $this->getConfig('commands', []);
223
        $parsedCommands = $this->parseCommands($commands);
224
225
        return $this->deduplicateArray(array_merge($globalCommands, $parsedCommands));
226
    }
227
228
    /**
229
     * Parse an array of commands and build a list.
230
     *
231
     * @param array $commands
232
     *
233
     * @return array
234
     */
235
    protected function parseCommands(array $commands)
236
    {
237
        if (!is_array($commands)) {
238
            return $commands;
239
        }
240
241
        $commandGroups = $this->getConfig('command_groups');
242
        $sharedCommands = $this->getConfig('shared_commands');
243
244
        $results = [];
245
        foreach ($commands as $command) {
246
            // If the command is a group, we'll parse through the group of commands
247
            // and resolve the full class name.
248
            if (isset($commandGroups[$command])) {
249
                $results = array_merge(
250
                    $results, $this->parseCommands($commandGroups[$command])
251
                );
252
253
                continue;
254
255
            }
256
257
            // If this command is actually a shared command, we'll extract the full
258
            // class name out of the command list now.
259
            if (isset($sharedCommands[$command])) {
260
                $command = $sharedCommands[$command];
261
            }
262
263
            if (!in_array($command, $results)) {
264
                $results[] = $command;
265
            }
266
        }
267
268
        return $results;
269
    }
270
271
    /**
272
     * Magically pass methods to the default bot.
273
     *
274
     * @param string $method
275
     * @param array  $parameters
276
     *
277
     * @return mixed
278
     */
279
    public function __call($method, $parameters)
280
    {
281
        return call_user_func_array([$this->bot(), $method], $parameters);
282
    }
283
}