Commit 5924a7f1 authored by Avtandil Kikabidze's avatar Avtandil Kikabidze

Merge pull request #18 from MBoretto/fix

[Fix] Namespace bug for external commands
parents e5ccb10c 8d5d3435
...@@ -14,7 +14,7 @@ A Telegram Bot based on the official [Telegram Bot API](https://core.telegram.or ...@@ -14,7 +14,7 @@ A Telegram Bot based on the official [Telegram Bot API](https://core.telegram.or
## introduction ## introduction
This is a pure php Telegram Bot, fully extensible via plugins. Telegram recently announced official support for a [Bot API](https://telegram.org/blog/bot-revolution) allowing integrators of all sorts to bring automated interactions to the mobile platform. This Bot aims to provide a platform where one could simply write a plugin and have interactions in a matter of minutes. This is a pure php Telegram Bot, fully extensible via plugins. Telegram recently announced official support for a [Bot API](https://telegram.org/blog/bot-revolution) allowing integrators of all sorts to bring automated interactions to the mobile platform. This Bot aims to provide a platform where one could simply write a plugin and have interactions in a matter of minutes.
The Bot support Reply Markup and handle commands in the group chat. The Bot support Reply Markup and handle commands in the group chat.
...@@ -143,7 +143,7 @@ try { ...@@ -143,7 +143,7 @@ try {
} }
``` ```
If you want insert in database messages for further usage in commands, create database and import structure.sql and enable mysql support after object creation and BEFORE handle method If you want insert in database messages/users for further usage in commands, create database and import structure.sql and enable mysql support after object creation and BEFORE handle method
```php ```php
<?php <?php
......
...@@ -19,6 +19,7 @@ abstract class Command ...@@ -19,6 +19,7 @@ abstract class Command
protected $message; protected $message;
protected $command; protected $command;
protected $public = false;
protected $description = 'Command help'; protected $description = 'Command help';
protected $usage = 'Command usage'; protected $usage = 'Command usage';
protected $version = '1.0.0'; protected $version = '1.0.0';
...@@ -99,4 +100,9 @@ abstract class Command ...@@ -99,4 +100,9 @@ abstract class Command
{ {
return $this->enabled; return $this->enabled;
} }
public function isPublic()
{
return $this->public;
}
} }
...@@ -23,6 +23,7 @@ class CalcCommand extends Command ...@@ -23,6 +23,7 @@ class CalcCommand extends Command
protected $usage = '/calc <expression>'; protected $usage = '/calc <expression>';
protected $version = '1.0.0'; protected $version = '1.0.0';
protected $enabled = true; protected $enabled = true;
protected $public = true;
public function execute() public function execute()
{ {
......
...@@ -22,6 +22,7 @@ class DateCommand extends Command ...@@ -22,6 +22,7 @@ class DateCommand extends Command
protected $usage = '/date <location>'; protected $usage = '/date <location>';
protected $version = '1.2.0'; protected $version = '1.2.0';
protected $enabled = true; protected $enabled = true;
protected $public = true;
private $base_url = 'https://maps.googleapis.com/maps/api'; private $base_url = 'https://maps.googleapis.com/maps/api';
private $date_format = 'd-m-Y H:i:s'; private $date_format = 'd-m-Y H:i:s';
......
...@@ -21,6 +21,7 @@ class EchoCommand extends Command ...@@ -21,6 +21,7 @@ class EchoCommand extends Command
protected $usage = '/echo <text>'; protected $usage = '/echo <text>';
protected $version = '1.0.0'; protected $version = '1.0.0';
protected $enabled = true; protected $enabled = true;
protected $public = true;
public function execute() public function execute()
{ {
......
...@@ -21,6 +21,7 @@ class HelpCommand extends Command ...@@ -21,6 +21,7 @@ class HelpCommand extends Command
protected $usage = '/help or /help <command>'; protected $usage = '/help or /help <command>';
protected $version = '1.0.0'; protected $version = '1.0.0';
protected $enabled = true; protected $enabled = true;
protected $public = true;
public function execute() public function execute()
{ {
...@@ -34,22 +35,30 @@ class HelpCommand extends Command ...@@ -34,22 +35,30 @@ class HelpCommand extends Command
$commands = $this->telegram->getCommandsList(); $commands = $this->telegram->getCommandsList();
if (empty($text)) { if (empty($text)) {
$msg = 'GeoBot v. ' . $this->telegram->getVersion() . "\n\n"; $msg = 'GeoBot v. ' . $this->telegram->getVersion() . "\n\n";
$msg.= 'Commands List:' . "\n"; $msg .= 'Commands List:' . "\n";
foreach ($commands as $command) { foreach ($commands as $command) {
if (!$command->isEnabled()) { if (!$command->isEnabled()) {
continue; continue;
} }
$msg.= '/' . $command->getName() . ' - ' . $command->getDescription() . "\n"; if (!$command->isPublic()) {
continue;
}
$msg .= '/' . $command->getName() . ' - ' . $command->getDescription() . "\n";
} }
$msg.= "\n" . 'For exact command help type: /help <command>'; $msg .= "\n" . 'For exact command help type: /help <command>';
} else { } else {
$text = str_replace('/', '', $text); $text = str_replace('/', '', $text);
if (isset($commands[$text])) { if (isset($commands[$text])) {
$command = $commands[$text]; $command = $commands[$text];
$msg = 'Command: ' . $command->getName() . ' v' . $command->getVersion() . "\n"; if (!$command->isEnabled() || !$command->isPublic()) {
$msg.= 'Description: ' . $command->getDescription() . "\n"; $msg = 'Command ' . $text . ' not found';
$msg.= 'Usage: ' . $command->getUsage(); } else {
$msg = 'Command: ' . $command->getName() . ' v' . $command->getVersion() . "\n";
$msg .= 'Description: ' . $command->getDescription() . "\n";
$msg .= 'Usage: ' . $command->getUsage();
}
} else { } else {
$msg = 'Command ' . $text . ' not found'; $msg = 'Command ' . $text . ' not found';
} }
......
<?php
/*
* This file is part of the TelegramBot package.
*
* (c) Avtandil Kikabidze aka LONGMAN <akalongman@gmail.com>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace Longman\TelegramBot\Commands;
use Longman\TelegramBot\Request;
use Longman\TelegramBot\Command;
use Longman\TelegramBot\Entities\Update;
class LeftChatParticipantCommand extends Command
{
protected $name = 'left_chat_participant';
protected $description = 'Left Chat Participant';
protected $usage = '/';
protected $version = '1.0.0';
protected $enabled = true;
public function execute()
{
$update = $this->getUpdate();
$message = $this->getMessage();
$participant = $message->getLeftChatParticipant();
// temporary do nothing
}
}
<?php
/*
* This file is part of the TelegramBot package.
*
* (c) Avtandil Kikabidze aka LONGMAN <akalongman@gmail.com>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace Longman\TelegramBot\Commands;
use Longman\TelegramBot\Request;
use Longman\TelegramBot\Command;
use Longman\TelegramBot\Entities\Update;
class NewChatParticipantCommand extends Command
{
protected $name = 'new_chat_participant';
protected $description = 'New Chat Participant';
protected $usage = '/';
protected $version = '1.0.0';
protected $enabled = true;
public function execute()
{
$update = $this->getUpdate();
$message = $this->getMessage();
$participant = $message->getNewChatParticipant();
$chat_id = $message->getChat()->getId();
$data = array();
$data['chat_id'] = $chat_id;
if ($participant->getUsername() == $this->getTelegram()->getBotName()) {
$text = 'Hi there';
} else {
if ($participant->getUsername()) {
$text = 'Hi @'.$participant->getUsername();
} else {
$text = 'Hi '.$participant->getFirstName();
}
}
$data['text'] = $text;
$result = Request::sendMessage($data);
return $result;
}
}
...@@ -21,6 +21,7 @@ class WeatherCommand extends Command ...@@ -21,6 +21,7 @@ class WeatherCommand extends Command
protected $usage = '/weather <location>'; protected $usage = '/weather <location>';
protected $version = '1.0.0'; protected $version = '1.0.0';
protected $enabled = true; protected $enabled = true;
protected $public = true;
private function getWeather($location) private function getWeather($location)
{ {
......
...@@ -24,6 +24,7 @@ class WhoamiCommand extends Command ...@@ -24,6 +24,7 @@ class WhoamiCommand extends Command
protected $usage = '/whoami'; protected $usage = '/whoami';
protected $version = '1.0.0'; protected $version = '1.0.0';
protected $enabled = true; protected $enabled = true;
protected $public = true;
public function execute() public function execute()
{ {
......
...@@ -12,6 +12,16 @@ namespace Longman\TelegramBot\Entities; ...@@ -12,6 +12,16 @@ namespace Longman\TelegramBot\Entities;
class Entity class Entity
{ {
protected $bot_name;
public function getBotName()
{
return $this->bot_name;
}
public function toJSON() public function toJSON()
{ {
......
...@@ -58,12 +58,12 @@ class Message extends Entity ...@@ -58,12 +58,12 @@ class Message extends Entity
protected $command; protected $command;
protected $bot_name; private $type;
public function __construct(array $data, $bot_name) public function __construct(array $data, $bot_name)
{ {
$this->bot_name = $bot_name; $this->bot_name = $bot_name;
$this->type = 'text';
$this->message_id = isset($data['message_id']) ? $data['message_id'] : null; $this->message_id = isset($data['message_id']) ? $data['message_id'] : null;
if (empty($this->message_id)) { if (empty($this->message_id)) {
...@@ -89,6 +89,11 @@ class Message extends Entity ...@@ -89,6 +89,11 @@ class Message extends Entity
$this->text = isset($data['text']) ? $data['text'] : null; $this->text = isset($data['text']) ? $data['text'] : null;
$command = $this->getCommand();
if (!empty($command)) {
$this->type = 'command';
}
$this->forward_from = isset($data['forward_from']) ? $data['forward_from'] : null; $this->forward_from = isset($data['forward_from']) ? $data['forward_from'] : null;
if (!empty($this->forward_from)) { if (!empty($this->forward_from)) {
$this->forward_from = new User($this->forward_from); $this->forward_from = new User($this->forward_from);
...@@ -104,19 +109,29 @@ class Message extends Entity ...@@ -104,19 +109,29 @@ class Message extends Entity
$this->new_chat_participant = isset($data['new_chat_participant']) ? $data['new_chat_participant'] : null; $this->new_chat_participant = isset($data['new_chat_participant']) ? $data['new_chat_participant'] : null;
if (!empty($this->new_chat_participant)) { if (!empty($this->new_chat_participant)) {
$this->new_chat_participant = new User($this->new_chat_participant); $this->new_chat_participant = new User($this->new_chat_participant);
$this->type = 'new_chat_participant';
} }
$this->left_chat_participant = isset($data['left_chat_participant']) ? $data['left_chat_participant'] : null; $this->left_chat_participant = isset($data['left_chat_participant']) ? $data['left_chat_participant'] : null;
if (!empty($this->left_chat_participant)) { if (!empty($this->left_chat_participant)) {
$this->left_chat_participant = new User($this->left_chat_participant); $this->left_chat_participant = new User($this->left_chat_participant);
$this->type = 'left_chat_participant';
} }
$this->new_chat_title = isset($data['new_chat_title']) ? $data['new_chat_title'] : null; $this->new_chat_title = isset($data['new_chat_title']) ? $data['new_chat_title'] : null;
if ($this->new_chat_title) {
$this->type = 'new_chat_title';
}
$this->delete_chat_photo = isset($data['delete_chat_photo']) ? $data['delete_chat_photo'] : null; $this->delete_chat_photo = isset($data['delete_chat_photo']) ? $data['delete_chat_photo'] : null;
if ($this->delete_chat_photo) {
$this->type = 'delete_chat_photo';
}
$this->group_chat_created = isset($data['group_chat_created']) ? $data['group_chat_created'] : null; $this->group_chat_created = isset($data['group_chat_created']) ? $data['group_chat_created'] : null;
if ($this->group_chat_created) {
$this->type = 'group_chat_created';
}
...@@ -238,4 +253,21 @@ class Message extends Entity ...@@ -238,4 +253,21 @@ class Message extends Entity
return $text; return $text;
} }
public function botAddedInChat()
{
if (!empty($this->new_chat_participant)) {
if ($this->new_chat_participant->getUsername() == $this->getBotName()) {
return true;
}
}
return false;
}
public function getType()
{
return $this->type;
}
} }
...@@ -17,7 +17,6 @@ class Update extends Entity ...@@ -17,7 +17,6 @@ class Update extends Entity
protected $update_id; protected $update_id;
protected $message; protected $message;
protected $bot_name;
public function __construct(array $data, $bot_name) public function __construct(array $data, $bot_name)
{ {
......
...@@ -17,7 +17,7 @@ use Longman\TelegramBot\Exception\TelegramException; ...@@ -17,7 +17,7 @@ use Longman\TelegramBot\Exception\TelegramException;
/** /**
* @package Telegram * @package Telegram
* @author Avtandil Kikabidze <akalongman@gmail.com> * @author Avtandil Kikabidze <akalongman@gmail.com>
* @copyright Avtandil Kikabidze <akalongman@gmail.com> * @copyright Avtandil Kikabidze <akalongman@gmail.com>
* @license http://opensource.org/licenses/mit-license.php The MIT License (MIT) * @license http://opensource.org/licenses/mit-license.php The MIT License (MIT)
* @link http://www.github.com/akalongman/php-telegram-bot * @link http://www.github.com/akalongman/php-telegram-bot
...@@ -30,7 +30,7 @@ class Telegram ...@@ -30,7 +30,7 @@ class Telegram
* *
* @var string * @var string
*/ */
protected $version = '0.0.7'; protected $version = '0.0.11';
/** /**
* Telegram API key * Telegram API key
...@@ -112,6 +112,17 @@ class Telegram ...@@ -112,6 +112,17 @@ class Telegram
/**
* Commands config
*
* @var array
*/
protected $message_types = array('text', 'command', 'new_chat_participant',
'left_chat_participant', 'new_chat_title', 'delete_chat_photo', 'group_chat_created'
);
/** /**
...@@ -273,12 +284,95 @@ class Telegram ...@@ -273,12 +284,95 @@ class Telegram
$this->insertRequest($update); $this->insertRequest($update);
$command = $update->getMessage()->getCommand(); $message = $update->getMessage();
if (!empty($command)) {
return $this->executeCommand($command, $update);
// check type
$type = $message->getType();
switch ($type) {
default:
case 'text':
// do nothing
break;
case 'command':
// execute command
$command = $message->getCommand();
return $this->executeCommand($command, $update);
break;
case 'new_chat_participant':
// trigger new participant
$command = 'new_chat_participant';
return $this->executeCommand($command, $update);
break;
case 'left_chat_participant':
// trigger left chat participant
$command = 'left_chat_participant';
return $this->executeCommand($command, $update);
break;
case 'new_chat_title':
// trigger new_chat_title
break;
case 'delete_chat_photo':
// trigger delete_chat_photo
break;
case 'group_chat_created':
// trigger group_chat_created
break;
}
}
public function eventUserAddedToChat(Update $update)
{
$message = $update->getMessage();
$participant = $message->getNewChatParticipant();
if (!empty($participant)) {
$chat_id = $message->getChat()->getId();
$data = array();
$data['chat_id'] = $chat_id;
if ($participant->getUsername() == $this->getBotName()) {
$text = 'Hi there';
} else {
if ($participant->getUsername()) {
$text = 'Hi @'.$participant->getUsername();
} else {
$text = 'Hi '.$participant->getFirstName();
}
}
$data['text'] = $text;
$result = Request::sendMessage($data);
return $result;
} }
} }
/** /**
* Execute /command * Execute /command
* *
...@@ -291,6 +385,11 @@ class Telegram ...@@ -291,6 +385,11 @@ class Telegram
return false; return false;
} }
if (!$class->isEnabled()) {
return false;
}
return $class->execute(); return $class->execute();
} }
...@@ -303,12 +402,19 @@ class Telegram ...@@ -303,12 +402,19 @@ class Telegram
{ {
$this->commands_dir = array_unique($this->commands_dir); $this->commands_dir = array_unique($this->commands_dir);
$this->commands_dir = array_reverse($this->commands_dir); $this->commands_dir = array_reverse($this->commands_dir);
$command = $this->sanitizeCommand($command);
$class_name = ucfirst($command) . 'Command'; $class_name = ucfirst($command) . 'Command';
$class_name_space = __NAMESPACE__ . '\\Commands\\' . $class_name;
foreach ($this->commands_dir as $dir) { foreach ($this->commands_dir as $dir) {
if (is_file($dir . '/' . $class_name . '.php')) { if (is_file($dir . '/' . $class_name . '.php')) {
require_once($dir . '/' . $class_name . '.php'); require_once($dir . '/' . $class_name . '.php');
$class = new $class_name($this); if (!class_exists($class_name_space)) {
continue;
}
$class = new $class_name_space($this);
if (!empty($update)) { if (!empty($update)) {
$class->setUpdate($update); $class->setUpdate($update);
} }
...@@ -317,19 +423,31 @@ class Telegram ...@@ -317,19 +423,31 @@ class Telegram
} }
} }
$class_name = __NAMESPACE__ . '\\Commands\\' . $class_name; if (class_exists($class_name_space)) {
$class = new $class_name($this); $class = new $class_name_space($this);
if (!empty($update)) { if (!empty($update)) {
$class->setUpdate($update); $class->setUpdate($update);
} }
if (is_object($class)) { if (is_object($class)) {
return $class; return $class;
}
} }
return false; return false;
} }
protected function sanitizeCommand($string, $capitalizeFirstCharacter = false)
{
$str = str_replace(' ', '', ucwords(str_replace('_', ' ', $string)));
//$str[0] = strtolower($str[0]);
return $str;
}
/** /**
* Insert request in db * Insert request in db
* *
...@@ -341,19 +459,47 @@ class Telegram ...@@ -341,19 +459,47 @@ class Telegram
return false; return false;
} }
$message = $update->getMessage();
try { try {
$sth = $this->pdo->prepare('INSERT INTO `messages` $sth1 = $this->pdo->prepare('INSERT INTO `users`
( (
`update_id`, `message_id`, `from`, `date`, `chat`, `forward_from`, `id`, `username`, `first_name`, `last_name`
`forward_date`, `reply_to_message`, `text`
) )
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)'); VALUES (:id, :username, :first_name, :last_name)
ON DUPLICATE KEY UPDATE `username`=:username, `first_name`=:first_name, `last_name`=:last_name
');
$from = $message->getFrom();
$user_id = $from->getId();
$username = $from->getUsername();
$first_name = $from->getFirstName();
$last_name = $from->getLastName();
$sth1->bindParam(':id', $user_id, \PDO::PARAM_INT);
$sth1->bindParam(':username', $username, \PDO::PARAM_STR, 255);
$sth1->bindParam(':first_name', $first_name, \PDO::PARAM_STR, 255);
$sth1->bindParam(':last_name', $last_name, \PDO::PARAM_STR, 255);
$message = $update->getMessage();
$status = $sth1->execute();
$sth = $this->pdo->prepare('INSERT IGNORE INTO `messages`
(
`update_id`, `message_id`, `user_id`, `date`, `chat`, `forward_from`,
`forward_date`, `reply_to_message`, `text`
)
VALUES (:update_id, :message_id, :user_id,
:date, :chat, :forward_from,
:forward_date, :reply_to_message, :text)');
$update_id = $update->getUpdateId(); $update_id = $update->getUpdateId();
$message_id = $message->getMessageId(); $message_id = $message->getMessageId();
$from = $message->getFrom()->toJSON(); $from = $message->getFrom()->toJSON();
$user_id = $message->getFrom()->getId();
$date = $message->getDate(); $date = $message->getDate();
$chat = $message->getChat()->toJSON(); $chat = $message->getChat()->toJSON();
$forward_from = $message->getForwardFrom(); $forward_from = $message->getForwardFrom();
...@@ -364,15 +510,15 @@ class Telegram ...@@ -364,15 +510,15 @@ class Telegram
} }
$text = $message->getText(); $text = $message->getText();
$sth->bindParam(1, $update_id, \PDO::PARAM_INT); $sth->bindParam(':update_id', $update_id, \PDO::PARAM_INT);
$sth->bindParam(2, $message_id, \PDO::PARAM_INT); $sth->bindParam(':message_id', $message_id, \PDO::PARAM_INT);
$sth->bindParam(3, $from, \PDO::PARAM_STR, 255); $sth->bindParam(':user_id', $user_id, \PDO::PARAM_INT);
$sth->bindParam(4, $date, \PDO::PARAM_INT); $sth->bindParam(':date', $date, \PDO::PARAM_INT);
$sth->bindParam(5, $chat, \PDO::PARAM_STR); $sth->bindParam(':chat', $chat, \PDO::PARAM_STR);
$sth->bindParam(6, $forward_from, \PDO::PARAM_STR); $sth->bindParam(':forward_from', $forward_from, \PDO::PARAM_STR);
$sth->bindParam(7, $forward_date, \PDO::PARAM_INT); $sth->bindParam(':forward_date', $forward_date, \PDO::PARAM_INT);
$sth->bindParam(8, $reply_to_message, \PDO::PARAM_STR); $sth->bindParam(':reply_to_message', $reply_to_message, \PDO::PARAM_STR);
$sth->bindParam(9, $text, \PDO::PARAM_STR); $sth->bindParam(':text', $text, \PDO::PARAM_STR);
$status = $sth->execute(); $status = $sth->execute();
...@@ -383,6 +529,8 @@ class Telegram ...@@ -383,6 +529,8 @@ class Telegram
return true; return true;
} }
/** /**
* Add custom commands path * Add custom commands path
* *
...@@ -497,4 +645,14 @@ class Telegram ...@@ -497,4 +645,14 @@ class Telegram
return $this; return $this;
} }
/**
* Get available message types
*
* @return array
*/
public function getMessageTypes()
{
return $this->message_types;
}
} }
CREATE TABLE `messages` ( CREATE TABLE `messages` (
`update_id` bigint UNSIGNED COMMENT 'The update\'s unique identifier.', `update_id` bigint UNSIGNED COMMENT 'The update\'s unique identifier.',
`message_id` bigint COMMENT 'Unique message identifier', `message_id` bigint COMMENT 'Unique message identifier',
`from` CHAR(255) COMMENT 'User object', `user_id` bigint COMMENT 'User identifier',
`date` int(11) UNSIGNED COMMENT 'Date the message was sent in Unix time', `date` int(11) UNSIGNED COMMENT 'Date the message was sent in Unix time',
`chat` CHAR(255) COMMENT 'User or GroupChat object. Conversation the message belongs to — user in case of a private message, GroupChat in case of a group', `chat` CHAR(255) COMMENT 'User or GroupChat object. Conversation the message belongs to — user in case of a private message, GroupChat in case of a group',
`forward_from` CHAR(255) DEFAULT '' COMMENT 'User object. For forwarded messages, sender of the original message', `forward_from` CHAR(255) DEFAULT '' COMMENT 'User object. For forwarded messages, sender of the original message',
...@@ -22,5 +22,15 @@ CREATE TABLE `messages` ( ...@@ -22,5 +22,15 @@ CREATE TABLE `messages` (
`delete_chat_photo` tinyint(1) DEFAULT 0 COMMENT 'Informs that the group photo was deleted', `delete_chat_photo` tinyint(1) DEFAULT 0 COMMENT 'Informs that the group photo was deleted',
`group_chat_created` tinyint(1) DEFAULT 0 COMMENT 'Informs that the group has been created', `group_chat_created` tinyint(1) DEFAULT 0 COMMENT 'Informs that the group has been created',
PRIMARY KEY (`update_id`), PRIMARY KEY (`update_id`),
KEY `message_id` (`message_id`) KEY `message_id` (`message_id`),
KEY `user_id` (`user_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci
CREATE TABLE `users` (
`id` bigint UNSIGNED NOT NULL DEFAULT '0' COMMENT 'Unique user identifier',
`username` CHAR(255) NOT NULL DEFAULT '' COMMENT 'User username',
`first_name` CHAR(255) NOT NULL DEFAULT '' COMMENT 'User first name',
`last_name` CHAR(255) NOT NULL DEFAULT '' COMMENT 'User last name',
PRIMARY KEY (`id`),
KEY `username` (`username`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci ) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment