Refactor public API: full encapsulation and strict typing
This commit is contained in:
parent
9899d34b11
commit
894470a147
@ -21,6 +21,7 @@ namespace danog\MadelineProto;
|
|||||||
|
|
||||||
use Amp\Promise;
|
use Amp\Promise;
|
||||||
use danog\MadelineProto\TL\TL;
|
use danog\MadelineProto\TL\TL;
|
||||||
|
use danog\MadelineProto\TL\TLCallback;
|
||||||
use phpDocumentor\Reflection\DocBlockFactory;
|
use phpDocumentor\Reflection\DocBlockFactory;
|
||||||
|
|
||||||
class AnnotationsBuilder
|
class AnnotationsBuilder
|
||||||
@ -78,9 +79,11 @@ class AnnotationsBuilder
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create file InternalDoc with all interfaces.
|
* Create internalDoc.
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
*/
|
*/
|
||||||
private function createInternalClasses()
|
private function createInternalClasses(): void
|
||||||
{
|
{
|
||||||
\danog\MadelineProto\Logger::log('Creating internal classes...', \danog\MadelineProto\Logger::NOTICE);
|
\danog\MadelineProto\Logger::log('Creating internal classes...', \danog\MadelineProto\Logger::NOTICE);
|
||||||
$handle = \fopen($this->output, 'w');
|
$handle = \fopen($this->output, 'w');
|
||||||
@ -92,6 +95,13 @@ class AnnotationsBuilder
|
|||||||
foreach ($methods as $method) {
|
foreach ($methods as $method) {
|
||||||
$ignoreMethods[$method->getName()] = $method->getName();
|
$ignoreMethods[$method->getName()] = $method->getName();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$class = new \ReflectionClass(TLCallback::class);
|
||||||
|
$methods = $class->getMethods(\ReflectionMethod::IS_STATIC | \ReflectionMethod::IS_PUBLIC);
|
||||||
|
foreach ($methods as $method) {
|
||||||
|
$ignoreMethods[$method->getName()] = $method->getName();
|
||||||
|
}
|
||||||
|
|
||||||
\fclose($handle);
|
\fclose($handle);
|
||||||
$handle = \fopen($this->output, 'w');
|
$handle = \fopen($this->output, 'w');
|
||||||
|
|
||||||
@ -169,6 +179,9 @@ class AnnotationsBuilder
|
|||||||
if (isset($ignoreMethods[$name])) {
|
if (isset($ignoreMethods[$name])) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
if (\strpos($method->getDocComment() ?? '', '@internal') !== false) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
if ($name == 'methodCallAsyncRead') {
|
if ($name == 'methodCallAsyncRead') {
|
||||||
$name = 'methodCall';
|
$name = 'methodCall';
|
||||||
@ -249,6 +262,13 @@ class AnnotationsBuilder
|
|||||||
$doc .= " $ret \$this->__call(__FUNCTION__, $paramList);\n";
|
$doc .= " $ret \$this->__call(__FUNCTION__, $paramList);\n";
|
||||||
$doc .= "}\n";
|
$doc .= "}\n";
|
||||||
|
|
||||||
|
if (!$method->getDocComment()) {
|
||||||
|
Logger::log("$name has no PHPDOC!", Logger::FATAL_ERROR);
|
||||||
|
}
|
||||||
|
if (!$type) {
|
||||||
|
Logger::log("$name has no return type!", Logger::FATAL_ERROR);
|
||||||
|
}
|
||||||
|
|
||||||
$internalDoc['InternalDoc'][$name]['method'] = $method->getDocComment() ?? '';
|
$internalDoc['InternalDoc'][$name]['method'] = $method->getDocComment() ?? '';
|
||||||
$internalDoc['InternalDoc'][$name]['method'] .= "\n ".\implode("\n ", \explode("\n", $doc));
|
$internalDoc['InternalDoc'][$name]['method'] .= "\n ".\implode("\n ", \explode("\n", $doc));
|
||||||
}
|
}
|
||||||
|
@ -635,7 +635,6 @@ class Lang
|
|||||||
public static function addToLang(string $key, string $value = '', bool $force = false)
|
public static function addToLang(string $key, string $value = '', bool $force = false)
|
||||||
{
|
{
|
||||||
if (!isset(\danog\MadelineProto\Lang::$lang['en'][$key]) || $force) {
|
if (!isset(\danog\MadelineProto\Lang::$lang['en'][$key]) || $force) {
|
||||||
\var_dump("Adding $key");
|
|
||||||
\danog\MadelineProto\Lang::$lang['en'][$key] = $value;
|
\danog\MadelineProto\Lang::$lang['en'][$key] = $value;
|
||||||
\file_put_contents(__DIR__.'/Lang.php', \sprintf(self::$template, \var_export(\danog\MadelineProto\Lang::$lang, true), \var_export(\danog\MadelineProto\Lang::$lang['en'], true)));
|
\file_put_contents(__DIR__.'/Lang.php', \sprintf(self::$template, \var_export(\danog\MadelineProto\Lang::$lang, true), \var_export(\danog\MadelineProto\Lang::$lang['en'], true)));
|
||||||
}
|
}
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -257,10 +257,10 @@ class Logger
|
|||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function logger($param, int $level = self::NOTICE, string $file = '')
|
public function logger($param, int $level = self::NOTICE, string $file = ''): void
|
||||||
{
|
{
|
||||||
if ($level > $this->level || $this->mode === 0) {
|
if ($level > $this->level || $this->mode === 0) {
|
||||||
return false;
|
return;
|
||||||
}
|
}
|
||||||
if (!self::$printed) {
|
if (!self::$printed) {
|
||||||
self::$printed = true;
|
self::$printed = true;
|
||||||
@ -274,7 +274,8 @@ class Logger
|
|||||||
$this->colors[self::NOTICE] = \implode(';', [self::FOREGROUND['yellow'], self::SET['bold']]);
|
$this->colors[self::NOTICE] = \implode(';', [self::FOREGROUND['yellow'], self::SET['bold']]);
|
||||||
}
|
}
|
||||||
if ($this->mode === 4) {
|
if ($this->mode === 4) {
|
||||||
return \call_user_func_array($this->optional, [$param, $level]);
|
\call_user_func_array($this->optional, [$param, $level]);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
$prefix = $this->prefix;
|
$prefix = $this->prefix;
|
||||||
if (\danog\MadelineProto\Magic::$has_thread && \is_object(\Thread::getCurrentThread())) {
|
if (\danog\MadelineProto\Magic::$has_thread && \is_object(\Thread::getCurrentThread())) {
|
||||||
|
@ -581,9 +581,9 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
/**
|
/**
|
||||||
* Cleanup memory and session file.
|
* Cleanup memory and session file.
|
||||||
*
|
*
|
||||||
* @return void
|
* @return self
|
||||||
*/
|
*/
|
||||||
public function cleanup()
|
public function cleanup(): self
|
||||||
{
|
{
|
||||||
$this->referenceDatabase = new ReferenceDatabase($this);
|
$this->referenceDatabase = new ReferenceDatabase($this);
|
||||||
$callbacks = [$this, $this->referenceDatabase];
|
$callbacks = [$this, $this->referenceDatabase];
|
||||||
@ -603,13 +603,13 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function logger($param, int $level = Logger::NOTICE, string $file = '')
|
public function logger($param, int $level = Logger::NOTICE, string $file = ''): void
|
||||||
{
|
{
|
||||||
if ($file === null) {
|
if ($file === null) {
|
||||||
$file = \basename(\debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 1)[0]['file'], '.php');
|
$file = \basename(\debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 1)[0]['file'], '.php');
|
||||||
}
|
}
|
||||||
|
|
||||||
return isset($this->logger) ? $this->logger->logger($param, $level, $file) : Logger::$default->logger($param, $level, $file);
|
isset($this->logger) ? $this->logger->logger($param, $level, $file) : Logger::$default->logger($param, $level, $file);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -767,6 +767,8 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
/**
|
/**
|
||||||
* Clean up properties from previous versions of MadelineProto.
|
* Clean up properties from previous versions of MadelineProto.
|
||||||
*
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
private function cleanupProperties()
|
private function cleanupProperties()
|
||||||
@ -1358,7 +1360,7 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function parseSettings(array $settings)
|
private function parseSettings(array $settings): void
|
||||||
{
|
{
|
||||||
$settings = self::getSettings($settings, $this->settings);
|
$settings = self::getSettings($settings, $this->settings);
|
||||||
if ($settings['app_info'] === null) {
|
if ($settings['app_info'] === null) {
|
||||||
@ -1377,7 +1379,7 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function setupLogger()
|
public function setupLogger(): void
|
||||||
{
|
{
|
||||||
$this->logger = Logger::getLoggerFromSettings($this->settings, isset($this->authorization['user']) ? isset($this->authorization['user']['username']) ? $this->authorization['user']['username'] : $this->authorization['user']['id'] : '');
|
$this->logger = Logger::getLoggerFromSettings($this->settings, isset($this->authorization['user']) ? isset($this->authorization['user']['username']) ? $this->authorization['user']['username'] : $this->authorization['user']['id'] : '');
|
||||||
}
|
}
|
||||||
@ -1388,9 +1390,11 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
* @param boolean $de Whether to reset the session ID
|
* @param boolean $de Whether to reset the session ID
|
||||||
* @param boolean $auth_key Whether to reset the auth key
|
* @param boolean $auth_key Whether to reset the auth key
|
||||||
*
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function resetMTProtoSession(bool $de = true, bool $auth_key = false)
|
public function resetMTProtoSession(bool $de = true, bool $auth_key = false): void
|
||||||
{
|
{
|
||||||
if (!\is_object($this->datacenter)) {
|
if (!\is_object($this->datacenter)) {
|
||||||
throw new Exception(Lang::$current_lang['session_corrupted']);
|
throw new Exception(Lang::$current_lang['session_corrupted']);
|
||||||
@ -1440,6 +1444,8 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
/**
|
/**
|
||||||
* Whether we're initing authorization.
|
* Whether we're initing authorization.
|
||||||
*
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
* @return boolean
|
* @return boolean
|
||||||
*/
|
*/
|
||||||
public function isInitingAuthorization()
|
public function isInitingAuthorization()
|
||||||
@ -1493,7 +1499,7 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function resetSession()
|
public function resetSession(): void
|
||||||
{
|
{
|
||||||
if (isset($this->seqUpdater)) {
|
if (isset($this->seqUpdater)) {
|
||||||
$this->seqUpdater->signal(true);
|
$this->seqUpdater->signal(true);
|
||||||
@ -1539,7 +1545,7 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function resetUpdateState()
|
public function resetUpdateState(): void
|
||||||
{
|
{
|
||||||
if (isset($this->seqUpdater)) {
|
if (isset($this->seqUpdater)) {
|
||||||
$this->seqUpdater->signal(true);
|
$this->seqUpdater->signal(true);
|
||||||
@ -1571,9 +1577,11 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
*
|
*
|
||||||
* @param boolean $anyway Force start update system?
|
* @param boolean $anyway Force start update system?
|
||||||
*
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function startUpdateSystem($anyway = false)
|
public function startUpdateSystem($anyway = false): void
|
||||||
{
|
{
|
||||||
if ($this->asyncInitPromise && !$anyway) {
|
if ($this->asyncInitPromise && !$anyway) {
|
||||||
$this->logger("Not starting update system");
|
$this->logger("Not starting update system");
|
||||||
@ -1617,9 +1625,11 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
*
|
*
|
||||||
* @param mixed $watcherId Watcher ID
|
* @param mixed $watcherId Watcher ID
|
||||||
*
|
*
|
||||||
* @return void
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \Generator<void>
|
||||||
*/
|
*/
|
||||||
public function getPhoneConfig($watcherId = null)
|
public function getPhoneConfig($watcherId = null): \Generator
|
||||||
{
|
{
|
||||||
if ($this->authorized === self::LOGGED_IN && \class_exists(VoIPServerConfigInternal::class) && !$this->authorization['user']['bot'] && $this->datacenter->getDataCenterConnection($this->settings['connection_settings']['default_dc'])->hasTempAuthKey()) {
|
if ($this->authorized === self::LOGGED_IN && \class_exists(VoIPServerConfigInternal::class) && !$this->authorization['user']['bot'] && $this->datacenter->getDataCenterConnection($this->settings['connection_settings']['default_dc'])->hasTempAuthKey()) {
|
||||||
$this->logger->logger('Fetching phone config...');
|
$this->logger->logger('Fetching phone config...');
|
||||||
@ -1747,16 +1757,35 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
return $this->authorization['user'];
|
return $this->authorization['user'];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called right before serialization of method starts.
|
||||||
|
*
|
||||||
|
* Pass the method name
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function getMethodCallbacks(): array
|
public function getMethodCallbacks(): array
|
||||||
{
|
{
|
||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called right before serialization of method starts.
|
||||||
|
*
|
||||||
|
* Pass the method name
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function getMethodBeforeCallbacks(): array
|
public function getMethodBeforeCallbacks(): array
|
||||||
{
|
{
|
||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called right after deserialization of object, passing the final object.
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function getConstructorCallbacks(): array
|
public function getConstructorCallbacks(): array
|
||||||
{
|
{
|
||||||
return \array_merge(
|
return \array_merge(
|
||||||
@ -1766,16 +1795,38 @@ class MTProto extends AsyncConstruct implements TLCallback
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called right before deserialization of object.
|
||||||
|
*
|
||||||
|
* Pass only the constructor name
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function getConstructorBeforeCallbacks(): array
|
public function getConstructorBeforeCallbacks(): array
|
||||||
{
|
{
|
||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called right before serialization of constructor.
|
||||||
|
*
|
||||||
|
* Passed the object, will return a modified version.
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function getConstructorSerializeCallbacks(): array
|
public function getConstructorSerializeCallbacks(): array
|
||||||
{
|
{
|
||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called if objects of the specified type cannot be serialized.
|
||||||
|
*
|
||||||
|
* Passed the unserializable object,
|
||||||
|
* will try to convert it to an object of the proper type.
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function getTypeMismatchCallbacks(): array
|
public function getTypeMismatchCallbacks(): array
|
||||||
{
|
{
|
||||||
return \array_merge(
|
return \array_merge(
|
||||||
|
@ -56,7 +56,7 @@ trait Files
|
|||||||
* @param callable $cb Callback (DEPRECATED, use FileCallbackInterface)
|
* @param callable $cb Callback (DEPRECATED, use FileCallbackInterface)
|
||||||
* @param boolean $encrypted Whether to encrypt file for secret chats
|
* @param boolean $encrypted Whether to encrypt file for secret chats
|
||||||
*
|
*
|
||||||
* @return array
|
* @return \Generator<array>
|
||||||
*/
|
*/
|
||||||
public function upload($file, string $file_name = '', $cb = null, bool $encrypted = false): \Generator
|
public function upload($file, string $file_name = '', $cb = null, bool $encrypted = false): \Generator
|
||||||
{
|
{
|
||||||
@ -229,9 +229,9 @@ trait Files
|
|||||||
* @param boolean $seekable Whether chunks can be fetched out of order
|
* @param boolean $seekable Whether chunks can be fetched out of order
|
||||||
* @param boolean $encrypted Whether to encrypt file for secret chats
|
* @param boolean $encrypted Whether to encrypt file for secret chats
|
||||||
*
|
*
|
||||||
* @return array
|
* @return \Generator<array>
|
||||||
*/
|
*/
|
||||||
public function uploadFromCallable($callable, int $size, string $mime, string $file_name = '', $cb = null, bool $seekable = true, bool $encrypted = false)
|
public function uploadFromCallable($callable, int $size, string $mime, string $file_name = '', $cb = null, bool $seekable = true, bool $encrypted = false): \Generator
|
||||||
{
|
{
|
||||||
if (\is_object($callable) && $callable instanceof FileCallbackInterface) {
|
if (\is_object($callable) && $callable instanceof FileCallbackInterface) {
|
||||||
$cb = $callable;
|
$cb = $callable;
|
||||||
@ -360,9 +360,9 @@ trait Files
|
|||||||
* @param string $file_name File name
|
* @param string $file_name File name
|
||||||
* @param callable $cb Callback (DEPRECATED, use FileCallbackInterface)
|
* @param callable $cb Callback (DEPRECATED, use FileCallbackInterface)
|
||||||
*
|
*
|
||||||
* @return array
|
* @return \Generator<array>
|
||||||
*/
|
*/
|
||||||
public function uploadEncrypted($file, string $file_name = '', $cb = null)
|
public function uploadEncrypted($file, string $file_name = '', $cb = null): \Generator
|
||||||
{
|
{
|
||||||
return $this->upload($file, $file_name, $cb, true);
|
return $this->upload($file, $file_name, $cb, true);
|
||||||
}
|
}
|
||||||
@ -374,9 +374,9 @@ trait Files
|
|||||||
* @param callable $cb Callback (DEPRECATED, use FileCallbackInterface)
|
* @param callable $cb Callback (DEPRECATED, use FileCallbackInterface)
|
||||||
* @param boolean $encrypted Whether to encrypt file for secret chats
|
* @param boolean $encrypted Whether to encrypt file for secret chats
|
||||||
*
|
*
|
||||||
* @return array
|
* @return \Generator<array>
|
||||||
*/
|
*/
|
||||||
public function uploadFromTgfile($media, $cb = null, bool $encrypted = false)
|
public function uploadFromTgfile($media, $cb = null, bool $encrypted = false): \Generator
|
||||||
{
|
{
|
||||||
if (\is_object($media) && $media instanceof FileCallbackInterface) {
|
if (\is_object($media) && $media instanceof FileCallbackInterface) {
|
||||||
$cb = $media;
|
$cb = $media;
|
||||||
@ -447,7 +447,7 @@ trait Files
|
|||||||
return $res;
|
return $res;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function genAllFile($media)
|
private function genAllFile($media)
|
||||||
{
|
{
|
||||||
$res = [$this->TL->getConstructors()->findByPredicate($media['_'])['type'] => $media];
|
$res = [$this->TL->getConstructors()->findByPredicate($media['_'])['type'] => $media];
|
||||||
switch ($media['_']) {
|
switch ($media['_']) {
|
||||||
@ -540,7 +540,14 @@ trait Files
|
|||||||
return $res;
|
return $res;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getFileInfo($constructor)
|
/**
|
||||||
|
* Get info about file.
|
||||||
|
*
|
||||||
|
* @param mixed $constructor File ID
|
||||||
|
*
|
||||||
|
* @return \Generator<array>
|
||||||
|
*/
|
||||||
|
public function getFileInfo($constructor): \Generator
|
||||||
{
|
{
|
||||||
if (\is_string($constructor)) {
|
if (\is_string($constructor)) {
|
||||||
$constructor = $this->unpackFileId($constructor)['MessageMedia'];
|
$constructor = $this->unpackFileId($constructor)['MessageMedia'];
|
||||||
@ -932,6 +939,15 @@ trait Files
|
|||||||
header('Content-Length: '.$info['size']);
|
header('Content-Length: '.$info['size']);
|
||||||
header('Content-Type: '.$info['mime']);
|
header('Content-Type: '.$info['mime']);
|
||||||
}*/
|
}*/
|
||||||
|
/**
|
||||||
|
* Extract photo size.
|
||||||
|
*
|
||||||
|
* @param mixed $photo Photo
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function extractPhotosize($photo)
|
public function extractPhotosize($photo)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
@ -1224,7 +1240,7 @@ trait Files
|
|||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
$x = 0;
|
//$x = 0;
|
||||||
while (true) {
|
while (true) {
|
||||||
try {
|
try {
|
||||||
$res = yield $this->methodCallAsyncRead(
|
$res = yield $this->methodCallAsyncRead(
|
||||||
@ -1241,7 +1257,7 @@ trait Files
|
|||||||
break;
|
break;
|
||||||
} catch (\danog\MadelineProto\RPCErrorException $e) {
|
} catch (\danog\MadelineProto\RPCErrorException $e) {
|
||||||
if (\strpos($e->rpc, 'FLOOD_WAIT_') === 0) {
|
if (\strpos($e->rpc, 'FLOOD_WAIT_') === 0) {
|
||||||
if ($x++ === 5) {
|
/*if ($x++ === 5) {
|
||||||
if (isset($message_media['MessageMedia']) && !$this->authorization['user']['bot'] && $this->settings['download']['report_broken_media']) {
|
if (isset($message_media['MessageMedia']) && !$this->authorization['user']['bot'] && $this->settings['download']['report_broken_media']) {
|
||||||
try {
|
try {
|
||||||
yield $this->methodCallAsyncRead('messages.sendMedia', ['peer' => 'support', 'media' => $message_media['MessageMedia'], 'message' => "I can't download this file, could you please help?"], ['datacenter' => $this->datacenter->curdc]);
|
yield $this->methodCallAsyncRead('messages.sendMedia', ['peer' => 'support', 'media' => $message_media['MessageMedia'], 'message' => "I can't download this file, could you please help?"], ['datacenter' => $this->datacenter->curdc]);
|
||||||
@ -1253,7 +1269,7 @@ trait Files
|
|||||||
}
|
}
|
||||||
|
|
||||||
throw new \danog\MadelineProto\Exception('The media server where this file is hosted is offline/overloaded, please try again later. Send the media to the telegram devs or to @danogentili to fix this.');
|
throw new \danog\MadelineProto\Exception('The media server where this file is hosted is offline/overloaded, please try again later. Send the media to the telegram devs or to @danogentili to fix this.');
|
||||||
}
|
}*/
|
||||||
yield Tools::sleep(1);
|
yield Tools::sleep(1);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -51,7 +51,7 @@ trait PeerHandler
|
|||||||
*
|
*
|
||||||
* @return int
|
* @return int
|
||||||
*/
|
*/
|
||||||
public static function fromSupergroup($id)
|
public static function fromSupergroup($id): int
|
||||||
{
|
{
|
||||||
return -$id - \pow(10, (int) \floor(\log(-$id, 10)));
|
return -$id - \pow(10, (int) \floor(\log(-$id, 10)));
|
||||||
}
|
}
|
||||||
@ -70,12 +70,28 @@ trait PeerHandler
|
|||||||
return ($log - \intval($log)) * 1000 < 10;
|
return ($log - \intval($log)) * 1000 < 10;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function addSupport($support)
|
/**
|
||||||
|
* Set support info.
|
||||||
|
*
|
||||||
|
* @param array $support Support info
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function addSupport(array $support): void
|
||||||
{
|
{
|
||||||
$this->supportUser = $support['user']['id'];
|
$this->supportUser = $support['user']['id'];
|
||||||
}
|
}
|
||||||
|
|
||||||
public function addUser($user)
|
/**
|
||||||
|
* Add user info.
|
||||||
|
*
|
||||||
|
* @param array $user User info
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function addUser(array $user): void
|
||||||
{
|
{
|
||||||
if (!isset($user['access_hash']) && !($user['min'] ?? false)) {
|
if (!isset($user['access_hash']) && !($user['min'] ?? false)) {
|
||||||
if (isset($this->chats[$user['id']]['access_hash']) && $this->chats[$user['id']]['access_hash']) {
|
if (isset($this->chats[$user['id']]['access_hash']) && $this->chats[$user['id']]['access_hash']) {
|
||||||
@ -117,11 +133,19 @@ trait PeerHandler
|
|||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
throw new \danog\MadelineProto\Exception('Invalid user provided', $user);
|
throw new \danog\MadelineProto\Exception('Invalid user provided', $user);
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function addChat($chat)
|
/**
|
||||||
|
* Add chat to database.
|
||||||
|
*
|
||||||
|
* @param array $chat Chat
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function addChat($chat): \Generator
|
||||||
{
|
{
|
||||||
switch ($chat['_']) {
|
switch ($chat['_']) {
|
||||||
case 'chat':
|
case 'chat':
|
||||||
@ -182,7 +206,7 @@ trait PeerHandler
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function cachePwrChat($id, $full_fetch, $send)
|
private function cachePwrChat($id, $full_fetch, $send)
|
||||||
{
|
{
|
||||||
\danog\MadelineProto\Tools::callFork((function () use ($id, $full_fetch, $send) {
|
\danog\MadelineProto\Tools::callFork((function () use ($id, $full_fetch, $send) {
|
||||||
try {
|
try {
|
||||||
@ -220,7 +244,16 @@ trait PeerHandler
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function entitiesPeerIsset($entities): \Generator
|
/**
|
||||||
|
* Check if all peer entities are in db.
|
||||||
|
*
|
||||||
|
* @param array $entities Entity list
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \Generator<bool>
|
||||||
|
*/
|
||||||
|
public function entitiesPeerIsset(array $entities): \Generator
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
foreach ($entities as $entity) {
|
foreach ($entities as $entity) {
|
||||||
@ -237,7 +270,16 @@ trait PeerHandler
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function fwdPeerIsset($fwd): \Generator
|
/**
|
||||||
|
* Check if fwd peer is set.
|
||||||
|
*
|
||||||
|
* @param array $fwd Forward info
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function fwdPeerIsset(array $fwd): \Generator
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
if (isset($fwd['user_id']) && !yield $this->peerIsset($fwd['user_id'])) {
|
if (isset($fwd['user_id']) && !yield $this->peerIsset($fwd['user_id'])) {
|
||||||
@ -260,7 +302,7 @@ trait PeerHandler
|
|||||||
*
|
*
|
||||||
* @return ?int
|
* @return ?int
|
||||||
*/
|
*/
|
||||||
public function getFolderId($id)
|
public function getFolderId($id): ?int
|
||||||
{
|
{
|
||||||
if (!\is_array($id)) {
|
if (!\is_array($id)) {
|
||||||
return null;
|
return null;
|
||||||
@ -593,7 +635,7 @@ trait PeerHandler
|
|||||||
throw new \danog\MadelineProto\Exception('This peer is not present in the internal peer database');
|
throw new \danog\MadelineProto\Exception('This peer is not present in the internal peer database');
|
||||||
}
|
}
|
||||||
|
|
||||||
public function genAll($constructor, $folder_id = null)
|
private function genAll($constructor, $folder_id = null)
|
||||||
{
|
{
|
||||||
$res = [$this->TL->getConstructors()->findByPredicate($constructor['_'])['type'] => $constructor];
|
$res = [$this->TL->getConstructors()->findByPredicate($constructor['_'])['type'] => $constructor];
|
||||||
switch ($constructor['_']) {
|
switch ($constructor['_']) {
|
||||||
@ -655,7 +697,14 @@ trait PeerHandler
|
|||||||
return $res;
|
return $res;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function fullChatLastUpdated($id)
|
/**
|
||||||
|
* When were full info for this chat last cached.
|
||||||
|
*
|
||||||
|
* @param mixed $id Chat ID
|
||||||
|
*
|
||||||
|
* @return integer
|
||||||
|
*/
|
||||||
|
public function fullChatLastUpdated($id): int
|
||||||
{
|
{
|
||||||
return isset($this->full_chats[$id]['last_update']) ? $this->full_chats[$id]['last_update'] : 0;
|
return isset($this->full_chats[$id]['last_update']) ? $this->full_chats[$id]['last_update'] : 0;
|
||||||
}
|
}
|
||||||
@ -845,7 +894,7 @@ trait PeerHandler
|
|||||||
return $res;
|
return $res;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function recurseAlphabetSearchParticipants($channel, $filter, $q, $total_count, &$res)
|
private function recurseAlphabetSearchParticipants($channel, $filter, $q, $total_count, &$res)
|
||||||
{
|
{
|
||||||
if (!yield $this->fetchParticipants($channel, $filter, $q, $total_count, $res)) {
|
if (!yield $this->fetchParticipants($channel, $filter, $q, $total_count, $res)) {
|
||||||
return false;
|
return false;
|
||||||
@ -856,7 +905,7 @@ trait PeerHandler
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function fetchParticipants($channel, $filter, $q, $total_count, &$res)
|
private function fetchParticipants($channel, $filter, $q, $total_count, &$res)
|
||||||
{
|
{
|
||||||
$offset = 0;
|
$offset = 0;
|
||||||
$limit = 200;
|
$limit = 200;
|
||||||
@ -942,12 +991,12 @@ trait PeerHandler
|
|||||||
return $has_more;
|
return $has_more;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function fetchParticipantsCache($channel, $filter, $q, $offset, $limit)
|
private function fetchParticipantsCache($channel, $filter, $q, $offset, $limit)
|
||||||
{
|
{
|
||||||
return $this->channel_participants[$channel['channel_id']][$filter][$q][$offset][$limit];
|
return $this->channel_participants[$channel['channel_id']][$filter][$q][$offset][$limit];
|
||||||
}
|
}
|
||||||
|
|
||||||
public function storeParticipantsCache($gres, $channel, $filter, $q, $offset, $limit)
|
private function storeParticipantsCache($gres, $channel, $filter, $q, $offset, $limit)
|
||||||
{
|
{
|
||||||
//return;
|
//return;
|
||||||
unset($gres['users']);
|
unset($gres['users']);
|
||||||
@ -960,12 +1009,12 @@ trait PeerHandler
|
|||||||
$this->channel_participants[$channel['channel_id']][$filter][$q][$offset][$limit] = $gres;
|
$this->channel_participants[$channel['channel_id']][$filter][$q][$offset][$limit] = $gres;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getParticipantsHash($channel, $filter, $q, $offset, $limit)
|
private function getParticipantsHash($channel, $filter, $q, $offset, $limit)
|
||||||
{
|
{
|
||||||
return isset($this->channel_participants[$channel['channel_id']][$filter][$q][$offset][$limit]) ? $this->channel_participants[$channel['channel_id']][$filter][$q][$offset][$limit]['hash'] : 0;
|
return isset($this->channel_participants[$channel['channel_id']][$filter][$q][$offset][$limit]) ? $this->channel_participants[$channel['channel_id']][$filter][$q][$offset][$limit]['hash'] : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function storeDb($res, $force = false)
|
private function storeDb($res, $force = false)
|
||||||
{
|
{
|
||||||
$settings = isset($this->settings['connection_settings'][$this->datacenter->curdc]) ? $this->settings['connection_settings'][$this->datacenter->curdc] : $this->settings['connection_settings']['all'];
|
$settings = isset($this->settings['connection_settings'][$this->datacenter->curdc]) ? $this->settings['connection_settings'][$this->datacenter->curdc] : $this->settings['connection_settings']['all'];
|
||||||
if (!isset($this->settings['pwr']) || $this->settings['pwr']['pwr'] === false || $settings['test_mode']) {
|
if (!isset($this->settings['pwr']) || $this->settings['pwr']['pwr'] === false || $settings['test_mode']) {
|
||||||
@ -1007,7 +1056,14 @@ trait PeerHandler
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function resolveUsername($username)
|
/**
|
||||||
|
* Resolve username (use getInfo instead).
|
||||||
|
*
|
||||||
|
* @param string $username Username
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function resolveUsername(string $username): \Generator
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
$this->caching_simple_username[$username] = true;
|
$this->caching_simple_username[$username] = true;
|
||||||
|
@ -35,6 +35,15 @@ trait UpdateHandler
|
|||||||
public $updates = [];
|
public $updates = [];
|
||||||
public $updates_key = 0;
|
public $updates_key = 0;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* PWR update handler.
|
||||||
|
*
|
||||||
|
* @param array $update Update
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
public function pwrUpdateHandler($update)
|
public function pwrUpdateHandler($update)
|
||||||
{
|
{
|
||||||
if (isset($this->settings['pwr']['updateHandler'])) {
|
if (isset($this->settings['pwr']['updateHandler'])) {
|
||||||
@ -48,7 +57,16 @@ trait UpdateHandler
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getUpdatesUpdateHandler($update)
|
/**
|
||||||
|
* Getupdates update handler.
|
||||||
|
*
|
||||||
|
* @param array $update Update
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function getUpdatesUpdateHandler(array $update): void
|
||||||
{
|
{
|
||||||
if (!$this->settings['updates']['handle_updates']) {
|
if (!$this->settings['updates']['handle_updates']) {
|
||||||
return;
|
return;
|
||||||
@ -56,7 +74,16 @@ trait UpdateHandler
|
|||||||
$this->updates[$this->updates_key++] = $update;
|
$this->updates[$this->updates_key++] = $update;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getUpdates($params = [])
|
/**
|
||||||
|
* Get updates.
|
||||||
|
*
|
||||||
|
* @param array $params Params
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \Generator<array>
|
||||||
|
*/
|
||||||
|
public function getUpdates($params = []): \Generator
|
||||||
{
|
{
|
||||||
if (!$this->settings['updates']['handle_updates']) {
|
if (!$this->settings['updates']['handle_updates']) {
|
||||||
$this->settings['updates']['handle_updates'] = true;
|
$this->settings['updates']['handle_updates'] = true;
|
||||||
@ -98,7 +125,14 @@ trait UpdateHandler
|
|||||||
public $update_resolved = false;
|
public $update_resolved = false;
|
||||||
public $update_deferred;
|
public $update_deferred;
|
||||||
|
|
||||||
public function waitUpdate()
|
/**
|
||||||
|
* Wait for update.
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function waitUpdate(): \Generator
|
||||||
{
|
{
|
||||||
if (!$this->update_deferred) {
|
if (!$this->update_deferred) {
|
||||||
$this->update_deferred = new Deferred();
|
$this->update_deferred = new Deferred();
|
||||||
@ -108,7 +142,14 @@ trait UpdateHandler
|
|||||||
$this->update_deferred = new Deferred();
|
$this->update_deferred = new Deferred();
|
||||||
}
|
}
|
||||||
|
|
||||||
public function signalUpdate()
|
/**
|
||||||
|
* Signal update.
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function signalUpdate(): void
|
||||||
{
|
{
|
||||||
if (!$this->update_deferred) {
|
if (!$this->update_deferred) {
|
||||||
$this->update_deferred = new Deferred();
|
$this->update_deferred = new Deferred();
|
||||||
@ -121,7 +162,17 @@ trait UpdateHandler
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public function checkMsgId($message)
|
|
||||||
|
/**
|
||||||
|
* Check message ID.
|
||||||
|
*
|
||||||
|
* @param array $message Message
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return boolean
|
||||||
|
*/
|
||||||
|
public function checkMsgId(array $message): bool
|
||||||
{
|
{
|
||||||
if (!isset($message['to_id'])) {
|
if (!isset($message['to_id'])) {
|
||||||
return true;
|
return true;
|
||||||
@ -144,6 +195,13 @@ trait UpdateHandler
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get channel state.
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return UpdatesState|UpdatesState[]
|
||||||
|
*/
|
||||||
public function loadUpdateState()
|
public function loadUpdateState()
|
||||||
{
|
{
|
||||||
if (!$this->got_state) {
|
if (!$this->got_state) {
|
||||||
@ -154,17 +212,41 @@ trait UpdateHandler
|
|||||||
return $this->channels_state->get(false);
|
return $this->channels_state->get(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Load channel state.
|
||||||
|
*
|
||||||
|
* @param ?int $channelId Channel ID
|
||||||
|
* @param array $init Init
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return UpdatesState|UpdatesState[]
|
||||||
|
*/
|
||||||
public function loadChannelState($channelId = null, $init = [])
|
public function loadChannelState($channelId = null, $init = [])
|
||||||
{
|
{
|
||||||
return $this->channels_state->get($channelId, $init);
|
return $this->channels_state->get($channelId, $init);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get channel states.
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return CombinedUpdatesState
|
||||||
|
*/
|
||||||
public function getChannelStates()
|
public function getChannelStates()
|
||||||
{
|
{
|
||||||
return $this->channels_state;
|
return $this->channels_state;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getUpdatesState()
|
/**
|
||||||
|
* Get update state.
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function getUpdatesState(): \Generator
|
||||||
{
|
{
|
||||||
$data = yield $this->methodCallAsyncRead('updates.getState', [], ['datacenter' => $this->settings['connection_settings']['default_dc']]);
|
$data = yield $this->methodCallAsyncRead('updates.getState', [], ['datacenter' => $this->settings['connection_settings']['default_dc']]);
|
||||||
yield $this->getCdnConfig($this->settings['connection_settings']['default_dc']);
|
yield $this->getCdnConfig($this->settings['connection_settings']['default_dc']);
|
||||||
@ -173,7 +255,17 @@ trait UpdateHandler
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public function handleUpdates($updates, $actual_updates = null)
|
/**
|
||||||
|
* Undocumented function.
|
||||||
|
*
|
||||||
|
* @param array $updates Updates
|
||||||
|
* @param array $actual_updates Actual updates for deferred
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function handleUpdates($updates, $actual_updates = null): \Generator
|
||||||
{
|
{
|
||||||
if (!$this->settings['updates']['handle_updates']) {
|
if (!$this->settings['updates']['handle_updates']) {
|
||||||
return;
|
return;
|
||||||
@ -252,7 +344,16 @@ trait UpdateHandler
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
public function saveUpdate($update)
|
/**
|
||||||
|
* Save update.
|
||||||
|
*
|
||||||
|
* @param array $update Update to save
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function saveUpdate(array $update): \Generator
|
||||||
{
|
{
|
||||||
if ($update['_'] === 'updateConfig') {
|
if ($update['_'] === 'updateConfig') {
|
||||||
$this->config['expires'] = 0;
|
$this->config['expires'] = 0;
|
||||||
@ -388,14 +489,21 @@ trait UpdateHandler
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function pwrWebhook($update)
|
/**
|
||||||
|
* Send update to webhook.
|
||||||
|
*
|
||||||
|
* @param array $update Update
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
private function pwrWebhook(array $update): void
|
||||||
{
|
{
|
||||||
$payload = \json_encode($update);
|
$payload = \json_encode($update);
|
||||||
//$this->logger->logger($update, $payload, json_last_error());
|
//$this->logger->logger($update, $payload, json_last_error());
|
||||||
if ($payload === '') {
|
if ($payload === '') {
|
||||||
$this->logger->logger('EMPTY UPDATE');
|
$this->logger->logger('EMPTY UPDATE');
|
||||||
|
|
||||||
return false;
|
return;
|
||||||
}
|
}
|
||||||
\danog\MadelineProto\Tools::callFork((function () use ($payload) {
|
\danog\MadelineProto\Tools::callFork((function () use ($payload) {
|
||||||
$request = new Request($this->hook_url, 'POST');
|
$request = new Request($this->hook_url, 'POST');
|
||||||
|
@ -24,7 +24,17 @@ namespace danog\MadelineProto\SecretChats;
|
|||||||
*/
|
*/
|
||||||
trait MessageHandler
|
trait MessageHandler
|
||||||
{
|
{
|
||||||
public function encryptSecretMessage($chat_id, $message)
|
/**
|
||||||
|
* Encrypt secret chat message.
|
||||||
|
*
|
||||||
|
* @param integer $chat_id Chat ID
|
||||||
|
* @param array $message Message to encrypt
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function encryptSecretMessage(int $chat_id, array $message): \Generator
|
||||||
{
|
{
|
||||||
if (!isset($this->secret_chats[$chat_id])) {
|
if (!isset($this->secret_chats[$chat_id])) {
|
||||||
$this->logger->logger(\sprintf(\danog\MadelineProto\Lang::$current_lang['secret_chat_skipping'], $chat_id));
|
$this->logger->logger(\sprintf(\danog\MadelineProto\Lang::$current_lang['secret_chat_skipping'], $chat_id));
|
||||||
@ -61,7 +71,7 @@ trait MessageHandler
|
|||||||
return $message;
|
return $message;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function handleEncryptedUpdate($message, $test = false)
|
private function handleEncryptedUpdate(array $message): \Generator
|
||||||
{
|
{
|
||||||
if (!isset($this->secret_chats[$message['message']['chat_id']])) {
|
if (!isset($this->secret_chats[$message['message']['chat_id']])) {
|
||||||
$this->logger->logger(\sprintf(\danog\MadelineProto\Lang::$current_lang['secret_chat_skipping'], $message['message']['chat_id']));
|
$this->logger->logger(\sprintf(\danog\MadelineProto\Lang::$current_lang['secret_chat_skipping'], $message['message']['chat_id']));
|
||||||
@ -122,7 +132,7 @@ trait MessageHandler
|
|||||||
yield $this->handleDecryptedUpdate($message);
|
yield $this->handleDecryptedUpdate($message);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function tryMTProtoV1Decrypt($message_key, $chat_id, $old, $encrypted_data)
|
private function tryMTProtoV1Decrypt($message_key, $chat_id, $old, $encrypted_data)
|
||||||
{
|
{
|
||||||
list($aes_key, $aes_iv) = $this->oldAesCalculate($message_key, $this->secret_chats[$chat_id][$old ? 'old_key' : 'key']['auth_key'], true);
|
list($aes_key, $aes_iv) = $this->oldAesCalculate($message_key, $this->secret_chats[$chat_id][$old ? 'old_key' : 'key']['auth_key'], true);
|
||||||
$decrypted_data = $this->igeDecrypt($encrypted_data, $aes_key, $aes_iv);
|
$decrypted_data = $this->igeDecrypt($encrypted_data, $aes_key, $aes_iv);
|
||||||
@ -144,7 +154,7 @@ trait MessageHandler
|
|||||||
return $message_data;
|
return $message_data;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function tryMTProtoV2Decrypt($message_key, $chat_id, $old, $encrypted_data)
|
private function tryMTProtoV2Decrypt($message_key, $chat_id, $old, $encrypted_data)
|
||||||
{
|
{
|
||||||
list($aes_key, $aes_iv) = $this->aesCalculate($message_key, $this->secret_chats[$chat_id][$old ? 'old_key' : 'key']['auth_key'], !$this->secret_chats[$chat_id]['admin']);
|
list($aes_key, $aes_iv) = $this->aesCalculate($message_key, $this->secret_chats[$chat_id][$old ? 'old_key' : 'key']['auth_key'], !$this->secret_chats[$chat_id]['admin']);
|
||||||
$decrypted_data = $this->igeDecrypt($encrypted_data, $aes_key, $aes_iv);
|
$decrypted_data = $this->igeDecrypt($encrypted_data, $aes_key, $aes_iv);
|
||||||
|
@ -24,7 +24,7 @@ namespace danog\MadelineProto\SecretChats;
|
|||||||
*/
|
*/
|
||||||
trait ResponseHandler
|
trait ResponseHandler
|
||||||
{
|
{
|
||||||
public function handleDecryptedUpdate($update)
|
private function handleDecryptedUpdate($update)
|
||||||
{
|
{
|
||||||
/*if (isset($update['message']['decrypted_message']['random_bytes']) && strlen($update['message']['decrypted_message']['random_bytes']) < 15) {
|
/*if (isset($update['message']['decrypted_message']['random_bytes']) && strlen($update['message']['decrypted_message']['random_bytes']) < 15) {
|
||||||
throw new \danog\MadelineProto\ResponseException(\danog\MadelineProto\Lang::$current_lang['rand_bytes_too_short']);
|
throw new \danog\MadelineProto\ResponseException(\danog\MadelineProto\Lang::$current_lang['rand_bytes_too_short']);
|
||||||
|
@ -24,7 +24,7 @@ namespace danog\MadelineProto\SecretChats;
|
|||||||
*/
|
*/
|
||||||
trait SeqNoHandler
|
trait SeqNoHandler
|
||||||
{
|
{
|
||||||
public function checkSecretInSeqNo($chat_id, $seqno)
|
private function checkSecretInSeqNo($chat_id, $seqno)
|
||||||
{
|
{
|
||||||
$seqno = ($seqno - $this->secret_chats[$chat_id]['out_seq_no_x']) / 2;
|
$seqno = ($seqno - $this->secret_chats[$chat_id]['out_seq_no_x']) / 2;
|
||||||
$last = 0;
|
$last = 0;
|
||||||
@ -47,7 +47,7 @@ trait SeqNoHandler
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function checkSecretOutSeqNo($chat_id, $seqno)
|
private function checkSecretOutSeqNo($chat_id, $seqno)
|
||||||
{
|
{
|
||||||
$seqno = ($seqno - $this->secret_chats[$chat_id]['in_seq_no_x']) / 2;
|
$seqno = ($seqno - $this->secret_chats[$chat_id]['in_seq_no_x']) / 2;
|
||||||
$C = 0;
|
$C = 0;
|
||||||
@ -78,12 +78,12 @@ trait SeqNoHandler
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function generateSecretInSeqNo($chat)
|
private function generateSecretInSeqNo($chat)
|
||||||
{
|
{
|
||||||
return $this->secret_chats[$chat]['layer'] > 8 ? $this->secret_chats[$chat]['in_seq_no'] * 2 + $this->secret_chats[$chat]['in_seq_no_x'] : -1;
|
return $this->secret_chats[$chat]['layer'] > 8 ? $this->secret_chats[$chat]['in_seq_no'] * 2 + $this->secret_chats[$chat]['in_seq_no_x'] : -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function generateSecretOutSeqNo($chat)
|
private function generateSecretOutSeqNo($chat)
|
||||||
{
|
{
|
||||||
return $this->secret_chats[$chat]['layer'] > 8 ? $this->secret_chats[$chat]['out_seq_no'] * 2 + $this->secret_chats[$chat]['out_seq_no_x'] : -1;
|
return $this->secret_chats[$chat]['layer'] > 8 ? $this->secret_chats[$chat]['out_seq_no'] * 2 + $this->secret_chats[$chat]['out_seq_no_x'] : -1;
|
||||||
}
|
}
|
||||||
|
@ -23,12 +23,19 @@ use danog\MadelineProto\Logger;
|
|||||||
|
|
||||||
trait BotAPI
|
trait BotAPI
|
||||||
{
|
{
|
||||||
public function htmlEntityDecode($stuff)
|
private function htmlEntityDecode($stuff)
|
||||||
{
|
{
|
||||||
return \html_entity_decode(\preg_replace('#< *br */? *>#', "\n", $stuff));
|
return \html_entity_decode(\preg_replace('#< *br */? *>#', "\n", $stuff));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function mbStrlen($text)
|
/**
|
||||||
|
* Get Telegram UTF-8 length of string.
|
||||||
|
*
|
||||||
|
* @param string $text Text
|
||||||
|
*
|
||||||
|
* @return int
|
||||||
|
*/
|
||||||
|
public function mbStrlen(string $text): int
|
||||||
{
|
{
|
||||||
$length = 0;
|
$length = 0;
|
||||||
$textlength = \strlen($text);
|
$textlength = \strlen($text);
|
||||||
@ -42,7 +49,16 @@ trait BotAPI
|
|||||||
return $length;
|
return $length;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function mbSubstr($text, $offset, $length = null)
|
/**
|
||||||
|
* Telegram UTF-8 multibyte substring.
|
||||||
|
*
|
||||||
|
* @param string $text Text to substring
|
||||||
|
* @param integer $offset Offset
|
||||||
|
* @param ?int $length Length
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function mbSubstr(string $text, int $offset, $length = null): string
|
||||||
{
|
{
|
||||||
$mb_text_length = $this->mbStrlen($text);
|
$mb_text_length = $this->mbStrlen($text);
|
||||||
if ($offset < 0) {
|
if ($offset < 0) {
|
||||||
@ -75,7 +91,15 @@ trait BotAPI
|
|||||||
return $new_text;
|
return $new_text;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function mbStrSplit($text, $length)
|
/**
|
||||||
|
* Telegram UTF-8 multibyte split.
|
||||||
|
*
|
||||||
|
* @param string $text Text
|
||||||
|
* @param integer $length Length
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function mbStrSplit(string $text, int $length): string
|
||||||
{
|
{
|
||||||
$tlength = \mb_strlen($text, 'UTF-8');
|
$tlength = \mb_strlen($text, 'UTF-8');
|
||||||
$result = [];
|
$result = [];
|
||||||
@ -86,7 +110,7 @@ trait BotAPI
|
|||||||
return $result;
|
return $result;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function parseButtons($rows)
|
private function parseButtons($rows)
|
||||||
{
|
{
|
||||||
$newrows = [];
|
$newrows = [];
|
||||||
$key = 0;
|
$key = 0;
|
||||||
@ -125,7 +149,7 @@ trait BotAPI
|
|||||||
return $newrows;
|
return $newrows;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function parseReplyMarkup($markup)
|
private function parseReplyMarkup($markup)
|
||||||
{
|
{
|
||||||
if (isset($markup['force_reply']) && $markup['force_reply']) {
|
if (isset($markup['force_reply']) && $markup['force_reply']) {
|
||||||
$markup['_'] = 'replyKeyboardForceReply';
|
$markup['_'] = 'replyKeyboardForceReply';
|
||||||
@ -157,7 +181,15 @@ trait BotAPI
|
|||||||
return $markup;
|
return $markup;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function MTProtoToBotAPI($data, $sent_arguments = [])
|
/**
|
||||||
|
* Convert MTProto parameters to bot API parameters.
|
||||||
|
*
|
||||||
|
* @param array $data Data
|
||||||
|
* @param array $sent_arguments Sent arguments
|
||||||
|
*
|
||||||
|
* @return \Generator<array>
|
||||||
|
*/
|
||||||
|
public function MTProtoToBotAPI(array $data, array $sent_arguments = []): \Generator
|
||||||
{
|
{
|
||||||
$newd = [];
|
$newd = [];
|
||||||
if (!isset($data['_'])) {
|
if (!isset($data['_'])) {
|
||||||
@ -382,7 +414,14 @@ trait BotAPI
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function botAPIToMTProto($arguments)
|
/**
|
||||||
|
* Convert bot API parameters to MTProto parameters.
|
||||||
|
*
|
||||||
|
* @param array $arguments Arguments
|
||||||
|
*
|
||||||
|
* @return \Generator<array>
|
||||||
|
*/
|
||||||
|
public function botAPIToMTProto(array $arguments): \Generator
|
||||||
{
|
{
|
||||||
foreach (self::BOTAPI_PARAMS_CONVERSION as $bot => $mtproto) {
|
foreach (self::BOTAPI_PARAMS_CONVERSION as $bot => $mtproto) {
|
||||||
if (isset($arguments[$bot]) && !isset($arguments[$mtproto])) {
|
if (isset($arguments[$bot]) && !isset($arguments[$mtproto])) {
|
||||||
@ -400,7 +439,7 @@ trait BotAPI
|
|||||||
return $arguments;
|
return $arguments;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function parseNode($node, &$entities, &$new_message, &$offset)
|
private function parseNode($node, &$entities, &$new_message, &$offset)
|
||||||
{
|
{
|
||||||
switch ($node->nodeName) {
|
switch ($node->nodeName) {
|
||||||
case 'br':
|
case 'br':
|
||||||
@ -518,7 +557,7 @@ trait BotAPI
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function parseMode($arguments)
|
private function parseMode($arguments)
|
||||||
{
|
{
|
||||||
if ($arguments['message'] === '' || !isset($arguments['message']) || !isset($arguments['parse_mode'])) {
|
if ($arguments['message'] === '' || !isset($arguments['message']) || !isset($arguments['parse_mode'])) {
|
||||||
return $arguments;
|
return $arguments;
|
||||||
@ -555,7 +594,7 @@ trait BotAPI
|
|||||||
return $arguments;
|
return $arguments;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function splitToChunks($args)
|
private function splitToChunks($args)
|
||||||
{
|
{
|
||||||
$args = yield $this->parseMode($args);
|
$args = yield $this->parseMode($args);
|
||||||
if (!isset($args['entities'])) {
|
if (!isset($args['entities'])) {
|
||||||
@ -665,7 +704,7 @@ trait BotAPI
|
|||||||
return $multiple_args;
|
return $multiple_args;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function multipleExplodeKeepDelimiters($delimiters, $string)
|
private function multipleExplodeKeepDelimiters($delimiters, $string)
|
||||||
{
|
{
|
||||||
$initialArray = \explode(\chr(1), \str_replace($delimiters, \chr(1), $string));
|
$initialArray = \explode(\chr(1), \str_replace($delimiters, \chr(1), $string));
|
||||||
$finalArray = [];
|
$finalArray = [];
|
||||||
@ -681,7 +720,7 @@ trait BotAPI
|
|||||||
return $finalArray;
|
return $finalArray;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function htmlFixtags($text)
|
private function htmlFixtags($text)
|
||||||
{
|
{
|
||||||
$diff = 0;
|
$diff = 0;
|
||||||
\preg_match_all('#(.*?)(<(\bu\b|\bs\b|\ba\b|\bb\b|\bstrong\b|\bblockquote\b|\bstrike\b|\bdel\b|\bem\b|i|\bcode\b|\bpre\b)[^>]*>)(.*?)([<]\s*/\s*\3[>])#is', $text, $matches, PREG_SET_ORDER | PREG_OFFSET_CAPTURE);
|
\preg_match_all('#(.*?)(<(\bu\b|\bs\b|\ba\b|\bb\b|\bstrong\b|\bblockquote\b|\bstrike\b|\bdel\b|\bem\b|i|\bcode\b|\bpre\b)[^>]*>)(.*?)([<]\s*/\s*\3[>])#is', $text, $matches, PREG_SET_ORDER | PREG_OFFSET_CAPTURE);
|
||||||
@ -724,7 +763,7 @@ trait BotAPI
|
|||||||
return \htmlentities($text);
|
return \htmlentities($text);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function buildRows($button_list)
|
private function buildRows($button_list)
|
||||||
{
|
{
|
||||||
$end = false;
|
$end = false;
|
||||||
$rows = [];
|
$rows = [];
|
||||||
|
@ -21,7 +21,7 @@ namespace danog\MadelineProto\TL\Conversion;
|
|||||||
|
|
||||||
trait BotAPIFiles
|
trait BotAPIFiles
|
||||||
{
|
{
|
||||||
public function photosizeToBotAPI($photoSize, $photo, $thumbnail = false)
|
private function photosizeToBotAPI($photoSize, $photo, $thumbnail = false)
|
||||||
{
|
{
|
||||||
$ext = '.jpg';//$this->getExtensionFromLocation(['_' => 'inputFileLocation', 'volume_id' => $photoSize['location']['volume_id'], 'local_id' => $photoSize['location']['local_id'], 'secret' => $photoSize['location']['secret'], 'dc_id' => $photoSize['location']['dc_id']], '.jpg');
|
$ext = '.jpg';//$this->getExtensionFromLocation(['_' => 'inputFileLocation', 'volume_id' => $photoSize['location']['volume_id'], 'local_id' => $photoSize['location']['local_id'], 'secret' => $photoSize['location']['secret'], 'dc_id' => $photoSize['location']['dc_id']], '.jpg');
|
||||||
$photoSize['location']['access_hash'] = $photo['access_hash'] ?? 0;
|
$photoSize['location']['access_hash'] = $photo['access_hash'] ?? 0;
|
||||||
@ -41,7 +41,14 @@ trait BotAPIFiles
|
|||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
public function unpackFileId($file_id)
|
/**
|
||||||
|
* Unpack bot API file ID.
|
||||||
|
*
|
||||||
|
* @param string $file_id Bot API file ID
|
||||||
|
*
|
||||||
|
* @return array Unpacked file ID
|
||||||
|
*/
|
||||||
|
public function unpackFileId(string $file_id): array
|
||||||
{
|
{
|
||||||
$file_id = \danog\MadelineProto\Tools::rleDecode(\danog\MadelineProto\Tools::base64urlDecode($file_id));
|
$file_id = \danog\MadelineProto\Tools::rleDecode(\danog\MadelineProto\Tools::base64urlDecode($file_id));
|
||||||
if ($file_id[\strlen($file_id) - 1] !== \chr(2)) {
|
if ($file_id[\strlen($file_id) - 1] !== \chr(2)) {
|
||||||
|
@ -14,22 +14,39 @@ If not, see <http://www.gnu.org/licenses/>.
|
|||||||
|
|
||||||
namespace danog\MadelineProto\TL\Conversion;
|
namespace danog\MadelineProto\TL\Conversion;
|
||||||
|
|
||||||
|
use danog\MadelineProto\MTProto;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Manages generation of extensions for files.
|
* Manages generation of extensions for files.
|
||||||
*/
|
*/
|
||||||
trait Extension
|
trait Extension
|
||||||
{
|
{
|
||||||
public function getMimeFromExtension($extension, $default)
|
/**
|
||||||
|
* Get mime type from file extension.
|
||||||
|
*
|
||||||
|
* @param string $extension File extension
|
||||||
|
* @param string $default Default mime type
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function getMimeFromExtension(string $extension, string $default): string
|
||||||
{
|
{
|
||||||
$ext = \ltrim($extension, '.');
|
$ext = \ltrim($extension, '.');
|
||||||
if (isset(self::ALL_MIMES[$ext])) {
|
if (isset(MTProto::ALL_MIMES[$ext])) {
|
||||||
return self::ALL_MIMES[$ext][0];
|
return MTProto::ALL_MIMES[$ext][0];
|
||||||
}
|
}
|
||||||
|
|
||||||
return $default;
|
return $default;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getExtensionFromMime($mime)
|
/**
|
||||||
|
* Get extension from mime type.
|
||||||
|
*
|
||||||
|
* @param string $mime MIME type
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function getExtensionFromMime(string $mime): string
|
||||||
{
|
{
|
||||||
foreach (self::ALL_MIMES as $key => $value) {
|
foreach (self::ALL_MIMES as $key => $value) {
|
||||||
if (\array_search($mime, $value) !== false) {
|
if (\array_search($mime, $value) !== false) {
|
||||||
@ -40,7 +57,15 @@ trait Extension
|
|||||||
return '';
|
return '';
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getExtensionFromLocation($location, $default)
|
/**
|
||||||
|
* Get extension from file location.
|
||||||
|
*
|
||||||
|
* @param mixed $location File location
|
||||||
|
* @param string $default Default extension
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function getExtensionFromLocation($location, string $default): string
|
||||||
{
|
{
|
||||||
return $default;
|
return $default;
|
||||||
//('upload.getFile', ['location' => $location, 'offset' => 0, 'limit' => 2], ['heavy' => true, 'datacenter' => $location['dc_id']]);
|
//('upload.getFile', ['location' => $location, 'offset' => 0, 'limit' => 2], ['heavy' => true, 'datacenter' => $location['dc_id']]);
|
||||||
@ -69,14 +94,28 @@ trait Extension
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getMimeFromFile($file)
|
/**
|
||||||
|
* Get mime type of file.
|
||||||
|
*
|
||||||
|
* @param string $file File
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function getMimeFromFile(string $file): string
|
||||||
{
|
{
|
||||||
$finfo = new \finfo(FILEINFO_MIME_TYPE);
|
$finfo = new \finfo(FILEINFO_MIME_TYPE);
|
||||||
|
|
||||||
return $finfo->file($file);
|
return $finfo->file($file);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getMimeFromBuffer($buffer)
|
/**
|
||||||
|
* Get mime type from buffer.
|
||||||
|
*
|
||||||
|
* @param string $buffer Buffer
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function getMimeFromBuffer(string $buffer): string
|
||||||
{
|
{
|
||||||
$finfo = new \finfo(FILEINFO_MIME_TYPE);
|
$finfo = new \finfo(FILEINFO_MIME_TYPE);
|
||||||
|
|
||||||
|
@ -21,7 +21,15 @@ namespace danog\MadelineProto\TL\Conversion;
|
|||||||
|
|
||||||
trait TD
|
trait TD
|
||||||
{
|
{
|
||||||
public function tdcliToTd(&$params, $key = null)
|
/**
|
||||||
|
* Convert tdcli parameters to tdcli.
|
||||||
|
*
|
||||||
|
* @param array $params Params
|
||||||
|
* @param array $key Key
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
|
public function tdcliToTd(&$params, $key = null): array
|
||||||
{
|
{
|
||||||
if (!\is_array($params)) {
|
if (!\is_array($params)) {
|
||||||
return $params;
|
return $params;
|
||||||
@ -44,7 +52,14 @@ trait TD
|
|||||||
return $params;
|
return $params;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function tdToMTProto($params)
|
/**
|
||||||
|
* Convert TD to MTProto parameters.
|
||||||
|
*
|
||||||
|
* @param array $params Parameters
|
||||||
|
*
|
||||||
|
* @return \Generator<array>
|
||||||
|
*/
|
||||||
|
public function tdToMTProto(array $params): \Generator
|
||||||
{
|
{
|
||||||
$newparams = ['_' => self::REVERSE[$params['_']]];
|
$newparams = ['_' => self::REVERSE[$params['_']]];
|
||||||
foreach (self::TD_PARAMS_CONVERSION[$newparams['_']] as $td => $mtproto) {
|
foreach (self::TD_PARAMS_CONVERSION[$newparams['_']] as $td => $mtproto) {
|
||||||
@ -75,12 +90,26 @@ trait TD
|
|||||||
return $newparams;
|
return $newparams;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function MTProtoToTdcli($params)
|
/**
|
||||||
|
* MTProto to TDCLI params.
|
||||||
|
*
|
||||||
|
* @param mixed $params Params
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function MTProtoToTdcli($params): \Generator
|
||||||
{
|
{
|
||||||
return $this->tdToTdcli(yield $this->MTProtoToTd($params));
|
return $this->tdToTdcli(yield $this->MTProtoToTd($params));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function MTProtoToTd(&$params)
|
/**
|
||||||
|
* MTProto to TD params.
|
||||||
|
*
|
||||||
|
* @param mixed $params Params
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function MTProtoToTd(&$params): \Generator
|
||||||
{
|
{
|
||||||
if (!\is_array($params)) {
|
if (!\is_array($params)) {
|
||||||
return $params;
|
return $params;
|
||||||
@ -163,6 +192,13 @@ trait TD
|
|||||||
return $newparams;
|
return $newparams;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert TD parameters to tdcli.
|
||||||
|
*
|
||||||
|
* @param mixed $params Parameters
|
||||||
|
*
|
||||||
|
* @return mixed
|
||||||
|
*/
|
||||||
public function tdToTdcli($params)
|
public function tdToTdcli($params)
|
||||||
{
|
{
|
||||||
if (!\is_array($params)) {
|
if (!\is_array($params)) {
|
||||||
|
@ -45,7 +45,7 @@ interface TLCallback
|
|||||||
*
|
*
|
||||||
* Pass the method name and arguments
|
* Pass the method name and arguments
|
||||||
*
|
*
|
||||||
* @var array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getMethodCallbacks(): array;
|
public function getMethodCallbacks(): array;
|
||||||
|
|
||||||
@ -54,14 +54,14 @@ interface TLCallback
|
|||||||
*
|
*
|
||||||
* Pass the method name
|
* Pass the method name
|
||||||
*
|
*
|
||||||
* @var array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getMethodBeforeCallbacks(): array;
|
public function getMethodBeforeCallbacks(): array;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Called right after deserialization of object, passing the final object.
|
* Called right after deserialization of object, passing the final object.
|
||||||
*
|
*
|
||||||
* @var array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getConstructorCallbacks(): array;
|
public function getConstructorCallbacks(): array;
|
||||||
|
|
||||||
@ -70,7 +70,7 @@ interface TLCallback
|
|||||||
*
|
*
|
||||||
* Pass only the constructor name
|
* Pass only the constructor name
|
||||||
*
|
*
|
||||||
* @var array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getConstructorBeforeCallbacks(): array;
|
public function getConstructorBeforeCallbacks(): array;
|
||||||
|
|
||||||
@ -79,7 +79,7 @@ interface TLCallback
|
|||||||
*
|
*
|
||||||
* Passed the object, will return a modified version.
|
* Passed the object, will return a modified version.
|
||||||
*
|
*
|
||||||
* @var array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getConstructorSerializeCallbacks(): array;
|
public function getConstructorSerializeCallbacks(): array;
|
||||||
|
|
||||||
@ -89,7 +89,7 @@ interface TLCallback
|
|||||||
* Passed the unserializable object,
|
* Passed the unserializable object,
|
||||||
* will try to convert it to an object of the proper type.
|
* will try to convert it to an object of the proper type.
|
||||||
*
|
*
|
||||||
* @var array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getTypeMismatchCallbacks(): array;
|
public function getTypeMismatchCallbacks(): array;
|
||||||
}
|
}
|
||||||
|
@ -480,7 +480,7 @@ trait Tools
|
|||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public static function callForkDefer($promise)
|
public static function callForkDefer($promise): void
|
||||||
{
|
{
|
||||||
Loop::defer([__CLASS__, 'callFork'], $promise);
|
Loop::defer([__CLASS__, 'callFork'], $promise);
|
||||||
}
|
}
|
||||||
@ -493,7 +493,7 @@ trait Tools
|
|||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public static function rethrow(\Throwable $e, $file = '')
|
public static function rethrow(\Throwable $e, $file = ''): void
|
||||||
{
|
{
|
||||||
$zis = isset($this) ? $this : null;
|
$zis = isset($this) ? $this : null;
|
||||||
$logger = isset($zis->logger) ? $zis->logger : Logger::$default;
|
$logger = isset($zis->logger) ? $zis->logger : Logger::$default;
|
||||||
@ -593,6 +593,8 @@ trait Tools
|
|||||||
* @param integer $operation Locking mode
|
* @param integer $operation Locking mode
|
||||||
* @param float $polling Polling interval
|
* @param float $polling Polling interval
|
||||||
*
|
*
|
||||||
|
* @internal Generator function
|
||||||
|
*
|
||||||
* @return \Generator
|
* @return \Generator
|
||||||
*/
|
*/
|
||||||
public static function flockGenerator(string $file, int $operation, float $polling): \Generator
|
public static function flockGenerator(string $file, int $operation, float $polling): \Generator
|
||||||
@ -646,6 +648,8 @@ trait Tools
|
|||||||
*
|
*
|
||||||
* @param string $prompt Prompt
|
* @param string $prompt Prompt
|
||||||
*
|
*
|
||||||
|
* @internal Generator function
|
||||||
|
*
|
||||||
* @return \Generator
|
* @return \Generator
|
||||||
*/
|
*/
|
||||||
public static function readLineGenerator(string $prompt = ''): \Generator
|
public static function readLineGenerator(string $prompt = ''): \Generator
|
||||||
|
@ -29,22 +29,57 @@ trait AuthKeyHandler
|
|||||||
{
|
{
|
||||||
private $calls = [];
|
private $calls = [];
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Request call (synchronous).
|
||||||
|
*
|
||||||
|
* @param mixed $user User info
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return \danog\MadelineProto\VoIPController
|
||||||
|
*/
|
||||||
public function requestCall($user)
|
public function requestCall($user)
|
||||||
{
|
{
|
||||||
return \danog\MadelineProto\Tools::wait($this->requestCallAsync($user));
|
return \danog\MadelineProto\Tools::wait($this->requestCallAsync($user));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function acceptCall($user)
|
/**
|
||||||
|
* Accept call (synchronous).
|
||||||
|
*
|
||||||
|
* @param mixed $user Accept call
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
|
public function acceptCall($user): bool
|
||||||
{
|
{
|
||||||
return \danog\MadelineProto\Tools::wait($this->acceptCallAsync($user));
|
return \danog\MadelineProto\Tools::wait($this->acceptCallAsync($user));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function discardCall($call, $reason, $rating = [], $need_debug = true)
|
/**
|
||||||
|
* Discard call (synchronous).
|
||||||
|
*
|
||||||
|
* @param array $call Call
|
||||||
|
* @param string $reason Discard reason
|
||||||
|
* @param array $rating Rating
|
||||||
|
* @param boolean $need_debug Need debug?
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
|
public function discardCall($call, $reason, $rating = [], $need_debug = true): void
|
||||||
{
|
{
|
||||||
return \danog\MadelineProto\Tools::wait($this->discardCallAsync($call, $reason, $rating, $need_debug));
|
\danog\MadelineProto\Tools::wait($this->discardCallAsync($call, $reason, $rating, $need_debug));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function requestCallAsync($user)
|
/**
|
||||||
|
* Request VoIP call.
|
||||||
|
*
|
||||||
|
* @param mixed $user User
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function requestCallAsync($user): \Generator
|
||||||
{
|
{
|
||||||
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
||||||
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
||||||
@ -71,7 +106,14 @@ trait AuthKeyHandler
|
|||||||
return $controller;
|
return $controller;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function acceptCallAsync($call)
|
/**
|
||||||
|
* Accept call.
|
||||||
|
*
|
||||||
|
* @param array $call Call
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function acceptCallAsync($call): \Generator
|
||||||
{
|
{
|
||||||
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
||||||
throw new \danog\MadelineProto\Exception();
|
throw new \danog\MadelineProto\Exception();
|
||||||
@ -111,7 +153,14 @@ trait AuthKeyHandler
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function confirmCall($params)
|
/**
|
||||||
|
* Confirm call.
|
||||||
|
*
|
||||||
|
* @param array $params Params
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function confirmCall($params): \Generator
|
||||||
{
|
{
|
||||||
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
||||||
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
||||||
@ -160,7 +209,14 @@ trait AuthKeyHandler
|
|||||||
return $res;
|
return $res;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function completeCall($params)
|
/**
|
||||||
|
* Complete call handshake.
|
||||||
|
*
|
||||||
|
* @param array $params Params
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function completeCall($params): \Generator
|
||||||
{
|
{
|
||||||
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
||||||
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
||||||
@ -195,7 +251,14 @@ trait AuthKeyHandler
|
|||||||
return $this->calls[$params['id']]->startTheMagic();
|
return $this->calls[$params['id']]->startTheMagic();
|
||||||
}
|
}
|
||||||
|
|
||||||
public function callStatus($id)
|
/**
|
||||||
|
* Get call status.
|
||||||
|
*
|
||||||
|
* @param array $id Call ID
|
||||||
|
*
|
||||||
|
* @return integer
|
||||||
|
*/
|
||||||
|
public function callStatus($id): int
|
||||||
{
|
{
|
||||||
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
||||||
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
||||||
@ -207,7 +270,14 @@ trait AuthKeyHandler
|
|||||||
return \danog\MadelineProto\VoIP::CALL_STATE_NONE;
|
return \danog\MadelineProto\VoIP::CALL_STATE_NONE;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getCall($call)
|
/**
|
||||||
|
* Get call info.
|
||||||
|
*
|
||||||
|
* @param mixed $call Call ID
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
|
public function getCall($call): array
|
||||||
{
|
{
|
||||||
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
||||||
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
||||||
@ -216,7 +286,17 @@ trait AuthKeyHandler
|
|||||||
return $this->calls[$call];
|
return $this->calls[$call];
|
||||||
}
|
}
|
||||||
|
|
||||||
public function discardCallAsync($call, $reason, $rating = [], $need_debug = true)
|
/**
|
||||||
|
* Discard call.
|
||||||
|
*
|
||||||
|
* @param array $call Call
|
||||||
|
* @param string $reason Discard reason
|
||||||
|
* @param array $rating Rating
|
||||||
|
* @param boolean $need_debug Need debug?
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function discardCallAsync($call, $reason, $rating = [], $need_debug = true): \Generator
|
||||||
{
|
{
|
||||||
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
if (!\class_exists('\\danog\\MadelineProto\\VoIP')) {
|
||||||
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
throw \danog\MadelineProto\Exception::extension('libtgvoip');
|
||||||
@ -249,7 +329,12 @@ trait AuthKeyHandler
|
|||||||
}
|
}
|
||||||
unset($this->calls[$call['id']]);
|
unset($this->calls[$call['id']]);
|
||||||
}
|
}
|
||||||
public function checkCalls()
|
/**
|
||||||
|
* Check state of calls.
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function checkCalls(): void
|
||||||
{
|
{
|
||||||
\array_walk($this->calls, function ($controller, $id) {
|
\array_walk($this->calls, function ($controller, $id) {
|
||||||
if ($controller->getCallState() === \danog\MadelineProto\VoIP::CALL_STATE_ENDED) {
|
if ($controller->getCallState() === \danog\MadelineProto\VoIP::CALL_STATE_ENDED) {
|
||||||
|
@ -108,7 +108,7 @@ Note that you can also provide the API parameters directly in the code using the
|
|||||||
exit;
|
exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function webAPIPhoneLogin($settings)
|
private function webAPIPhoneLogin($settings)
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
$this->my_telegram_org_wrapper = new \danog\MadelineProto\MyTelegramOrgWrapper($settings);
|
$this->my_telegram_org_wrapper = new \danog\MadelineProto\MyTelegramOrgWrapper($settings);
|
||||||
@ -119,7 +119,7 @@ Note that you can also provide the API parameters directly in the code using the
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function webAPICompleteLogin()
|
private function webAPICompleteLogin()
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
yield $this->my_telegram_org_wrapper->completeLogin($_POST['code']);
|
yield $this->my_telegram_org_wrapper->completeLogin($_POST['code']);
|
||||||
@ -130,7 +130,7 @@ Note that you can also provide the API parameters directly in the code using the
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function webAPICreateApp()
|
private function webAPICreateApp()
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
$params = $_POST;
|
$params = $_POST;
|
||||||
|
@ -38,22 +38,32 @@ trait ApiTemplates
|
|||||||
</body>
|
</body>
|
||||||
</html>';
|
</html>';
|
||||||
|
|
||||||
public function webAPIEchoTemplate($message, $form)
|
private function webAPIEchoTemplate($message, $form)
|
||||||
{
|
{
|
||||||
return \sprintf($this->web_api_template, $message, $form);
|
return \sprintf($this->web_api_template, $message, $form);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getWebAPITemplate()
|
/**
|
||||||
|
* Get web API login HTML template string.
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function getWebAPITemplate(): string
|
||||||
{
|
{
|
||||||
return $this->web_template;
|
return $this->web_template;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function setWebAPITemplate($template)
|
/**
|
||||||
|
* Set web API login HTML template string.
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
public function setWebAPITemplate(string $template)
|
||||||
{
|
{
|
||||||
$this->web_template = $template;
|
$this->web_template = $template;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function webAPIEcho($message = '')
|
private function webAPIEcho(string $message = '')
|
||||||
{
|
{
|
||||||
$stdout = getOutputBufferStream();
|
$stdout = getOutputBufferStream();
|
||||||
if (!isset($this->my_telegram_org_wrapper)) {
|
if (!isset($this->my_telegram_org_wrapper)) {
|
||||||
|
@ -52,7 +52,7 @@ trait Events
|
|||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function setEventHandler($event_handler)
|
public function setEventHandler($event_handler): void
|
||||||
{
|
{
|
||||||
if (!\class_exists($event_handler) || !\is_subclass_of($event_handler, '\danog\MadelineProto\EventHandler')) {
|
if (!\class_exists($event_handler) || !\is_subclass_of($event_handler, '\danog\MadelineProto\EventHandler')) {
|
||||||
throw new \danog\MadelineProto\Exception('Wrong event handler was defined');
|
throw new \danog\MadelineProto\Exception('Wrong event handler was defined');
|
||||||
|
@ -27,7 +27,13 @@ use danog\MadelineProto\MTProtoTools\PasswordCalculator;
|
|||||||
*/
|
*/
|
||||||
trait Login
|
trait Login
|
||||||
{
|
{
|
||||||
public function logout()
|
|
||||||
|
/**
|
||||||
|
* Log out currently logged in user.
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function logout(): \Generator
|
||||||
{
|
{
|
||||||
yield $this->methodCallAsyncRead('auth.logOut', [], ['datacenter' => $this->datacenter->curdc]);
|
yield $this->methodCallAsyncRead('auth.logOut', [], ['datacenter' => $this->datacenter->curdc]);
|
||||||
$this->resetSession();
|
$this->resetSession();
|
||||||
@ -37,7 +43,14 @@ trait Login
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function botLogin($token)
|
/**
|
||||||
|
* Login as bot.
|
||||||
|
*
|
||||||
|
* @param string $token Bot token
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function botLogin(string $token): \Generator
|
||||||
{
|
{
|
||||||
if ($this->authorized === self::LOGGED_IN) {
|
if ($this->authorized === self::LOGGED_IN) {
|
||||||
$this->logger->logger(\danog\MadelineProto\Lang::$current_lang['already_loggedIn'], \danog\MadelineProto\Logger::NOTICE);
|
$this->logger->logger(\danog\MadelineProto\Lang::$current_lang['already_loggedIn'], \danog\MadelineProto\Logger::NOTICE);
|
||||||
@ -61,7 +74,15 @@ trait Login
|
|||||||
return $this->authorization;
|
return $this->authorization;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function phoneLogin($number, $sms_type = 5)
|
/**
|
||||||
|
* Login as user.
|
||||||
|
*
|
||||||
|
* @param string $number Phone number
|
||||||
|
* @param integer $sms_type SMS type
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function phoneLogin($number, $sms_type = 5): \Generator
|
||||||
{
|
{
|
||||||
if ($this->authorized === self::LOGGED_IN) {
|
if ($this->authorized === self::LOGGED_IN) {
|
||||||
$this->logger->logger(\danog\MadelineProto\Lang::$current_lang['already_loggedIn'], \danog\MadelineProto\Logger::NOTICE);
|
$this->logger->logger(\danog\MadelineProto\Lang::$current_lang['already_loggedIn'], \danog\MadelineProto\Logger::NOTICE);
|
||||||
@ -80,7 +101,14 @@ trait Login
|
|||||||
return $this->authorization;
|
return $this->authorization;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function completePhoneLogin($code)
|
/**
|
||||||
|
* Complet user login using login code.
|
||||||
|
*
|
||||||
|
* @param string $code Login code
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function completePhoneLogin($code): \Generator
|
||||||
{
|
{
|
||||||
if ($this->authorized !== self::WAITING_CODE) {
|
if ($this->authorized !== self::WAITING_CODE) {
|
||||||
throw new \danog\MadelineProto\Exception(\danog\MadelineProto\Lang::$current_lang['login_code_uncalled']);
|
throw new \danog\MadelineProto\Exception(\danog\MadelineProto\Lang::$current_lang['login_code_uncalled']);
|
||||||
@ -131,7 +159,14 @@ trait Login
|
|||||||
return $this->authorization;
|
return $this->authorization;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function importAuthorization($authorization)
|
/**
|
||||||
|
* Import authorization.
|
||||||
|
*
|
||||||
|
* @param mixed $authorization Authorization info
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function importAuthorization($authorization): \Generator
|
||||||
{
|
{
|
||||||
if ($this->authorized === self::LOGGED_IN) {
|
if ($this->authorized === self::LOGGED_IN) {
|
||||||
$this->logger->logger(\danog\MadelineProto\Lang::$current_lang['already_loggedIn'], \danog\MadelineProto\Logger::NOTICE);
|
$this->logger->logger(\danog\MadelineProto\Lang::$current_lang['already_loggedIn'], \danog\MadelineProto\Logger::NOTICE);
|
||||||
@ -166,7 +201,12 @@ trait Login
|
|||||||
return $res;
|
return $res;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function exportAuthorization()
|
/**
|
||||||
|
* Export authorization.
|
||||||
|
*
|
||||||
|
* @return \Generator<array>
|
||||||
|
*/
|
||||||
|
public function exportAuthorization(): \Generator
|
||||||
{
|
{
|
||||||
if ($this->authorized !== self::LOGGED_IN) {
|
if ($this->authorized !== self::LOGGED_IN) {
|
||||||
throw new \danog\MadelineProto\Exception(\danog\MadelineProto\Lang::$current_lang['not_loggedIn']);
|
throw new \danog\MadelineProto\Exception(\danog\MadelineProto\Lang::$current_lang['not_loggedIn']);
|
||||||
@ -177,7 +217,15 @@ trait Login
|
|||||||
return [$this->datacenter->curdc, $this->datacenter->getDataCenterConnection($this->datacenter->curdc)->getPermAuthKey()->getAuthKey()];
|
return [$this->datacenter->curdc, $this->datacenter->getDataCenterConnection($this->datacenter->curdc)->getPermAuthKey()->getAuthKey()];
|
||||||
}
|
}
|
||||||
|
|
||||||
public function completeSignup($first_name, $last_name)
|
/**
|
||||||
|
* Complete signup to Telegram.
|
||||||
|
*
|
||||||
|
* @param string $first_name First name
|
||||||
|
* @param string $last_name Last name
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function completeSignup(string $first_name, string $last_name = ''): \Generator
|
||||||
{
|
{
|
||||||
if ($this->authorized !== self::WAITING_SIGNUP) {
|
if ($this->authorized !== self::WAITING_SIGNUP) {
|
||||||
throw new \danog\MadelineProto\Exception(\danog\MadelineProto\Lang::$current_lang['signup_uncalled']);
|
throw new \danog\MadelineProto\Exception(\danog\MadelineProto\Lang::$current_lang['signup_uncalled']);
|
||||||
@ -196,7 +244,14 @@ trait Login
|
|||||||
return $this->authorization;
|
return $this->authorization;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function complete2faLogin($password)
|
/**
|
||||||
|
* Complete 2FA login.
|
||||||
|
*
|
||||||
|
* @param string $password Password
|
||||||
|
*
|
||||||
|
* @return \Generator
|
||||||
|
*/
|
||||||
|
public function complete2faLogin(string $password): \Generator
|
||||||
{
|
{
|
||||||
if ($this->authorized !== self::WAITING_PASSWORD) {
|
if ($this->authorized !== self::WAITING_PASSWORD) {
|
||||||
throw new \danog\MadelineProto\Exception(\danog\MadelineProto\Lang::$current_lang['2fa_uncalled']);
|
throw new \danog\MadelineProto\Exception(\danog\MadelineProto\Lang::$current_lang['2fa_uncalled']);
|
||||||
@ -222,9 +277,10 @@ trait Login
|
|||||||
* The params array can contain password, new_password, email and hint params.
|
* The params array can contain password, new_password, email and hint params.
|
||||||
*
|
*
|
||||||
* @param array $params The params
|
* @param array $params The params
|
||||||
* @return void
|
*
|
||||||
|
* @return \Generator
|
||||||
*/
|
*/
|
||||||
public function update2fa(array $params)
|
public function update2fa(array $params): \Generator
|
||||||
{
|
{
|
||||||
$hasher = new PasswordCalculator($this->logger);
|
$hasher = new PasswordCalculator($this->logger);
|
||||||
$hasher->addInfo(yield $this->methodCallAsyncRead('account.getPassword', [], ['datacenter' => $this->datacenter->curdc]));
|
$hasher->addInfo(yield $this->methodCallAsyncRead('account.getPassword', [], ['datacenter' => $this->datacenter->curdc]));
|
||||||
|
@ -88,7 +88,7 @@ trait Start
|
|||||||
exit;
|
exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function webPhoneLogin()
|
private function webPhoneLogin()
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
yield $this->phoneLogin($_POST['phone_number']);
|
yield $this->phoneLogin($_POST['phone_number']);
|
||||||
@ -100,7 +100,7 @@ trait Start
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function webCompletePhoneLogin()
|
private function webCompletePhoneLogin()
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
yield $this->completePhoneLogin($_POST['phone_code']);
|
yield $this->completePhoneLogin($_POST['phone_code']);
|
||||||
@ -112,7 +112,7 @@ trait Start
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function webComplete2faLogin()
|
private function webComplete2faLogin()
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
yield $this->complete2faLogin($_POST['password']);
|
yield $this->complete2faLogin($_POST['password']);
|
||||||
@ -124,7 +124,7 @@ trait Start
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function webCompleteSignup()
|
private function webCompleteSignup()
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
yield $this->completeSignup($_POST['first_name'], isset($_POST['last_name']) ? $_POST['last_name'] : '');
|
yield $this->completeSignup($_POST['first_name'], isset($_POST['last_name']) ? $_POST['last_name'] : '');
|
||||||
@ -136,7 +136,7 @@ trait Start
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function webBotLogin()
|
private function webBotLogin()
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
yield $this->botLogin($_POST['token']);
|
yield $this->botLogin($_POST['token']);
|
||||||
|
@ -23,7 +23,7 @@ use function Amp\ByteStream\getOutputBufferStream;
|
|||||||
|
|
||||||
trait Templates
|
trait Templates
|
||||||
{
|
{
|
||||||
public function webEcho(string $message = '')
|
private function webEcho(string $message = '')
|
||||||
{
|
{
|
||||||
$stdout = getOutputBufferStream();
|
$stdout = getOutputBufferStream();
|
||||||
switch ($this->authorized) {
|
switch ($this->authorized) {
|
||||||
@ -68,7 +68,7 @@ trait Templates
|
|||||||
</body>
|
</body>
|
||||||
</html>';
|
</html>';
|
||||||
|
|
||||||
public function webEchoTemplate($message, $form): string
|
private function webEchoTemplate($message, $form): string
|
||||||
{
|
{
|
||||||
return \sprintf($this->web_template, $form, $message);
|
return \sprintf($this->web_template, $form, $message);
|
||||||
}
|
}
|
||||||
|
@ -64,59 +64,60 @@ $settings = \json_decode(\getenv('MTPROTO_SETTINGS'), true) ?: [];
|
|||||||
*/
|
*/
|
||||||
echo 'Loading MadelineProto...'.PHP_EOL;
|
echo 'Loading MadelineProto...'.PHP_EOL;
|
||||||
$MadelineProto = new \danog\MadelineProto\API(\getcwd().'/testing.madeline', $settings);
|
$MadelineProto = new \danog\MadelineProto\API(\getcwd().'/testing.madeline', $settings);
|
||||||
$MadelineProto->fileGetContents('https://google.com');
|
$MadelineProto->async(true);
|
||||||
$MadelineProto->start();
|
$MadelineProto->loop(function () use ($MadelineProto) {
|
||||||
$MadelineProto->async(false);
|
yield $MadelineProto->fileGetContents('https://google.com');
|
||||||
|
yield $MadelineProto->start();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
$MadelineProto->getSelf();
|
yield $MadelineProto->getSelf();
|
||||||
} catch (\danog\MadelineProto\Exception $e) {
|
} catch (\danog\MadelineProto\Exception $e) {
|
||||||
if ($e->getMessage() === 'TOS action required, check the logs') {
|
if ($e->getMessage() === 'TOS action required, check the logs') {
|
||||||
$MadelineProto->acceptTos();
|
yield $MadelineProto->acceptTos();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
//var_dump(count($MadelineProto->getPwrChat('@madelineproto')['participants']));
|
//var_dump(count($MadelineProto->getPwrChat('@madelineproto')['participants']));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Test logging
|
* Test logging
|
||||||
*/
|
*/
|
||||||
\danog\MadelineProto\Logger::log('hey', \danog\MadelineProto\Logger::ULTRA_VERBOSE);
|
$MadelineProto->logger('hey', \danog\MadelineProto\Logger::ULTRA_VERBOSE);
|
||||||
\danog\MadelineProto\Logger::log('hey', \danog\MadelineProto\Logger::VERBOSE);
|
$MadelineProto->logger('hey', \danog\MadelineProto\Logger::VERBOSE);
|
||||||
\danog\MadelineProto\Logger::log('hey', \danog\MadelineProto\Logger::NOTICE);
|
$MadelineProto->logger('hey', \danog\MadelineProto\Logger::NOTICE);
|
||||||
\danog\MadelineProto\Logger::log('hey', \danog\MadelineProto\Logger::WARNING);
|
$MadelineProto->logger('hey', \danog\MadelineProto\Logger::WARNING);
|
||||||
\danog\MadelineProto\Logger::log('hey', \danog\MadelineProto\Logger::ERROR);
|
$MadelineProto->logger('hey', \danog\MadelineProto\Logger::ERROR);
|
||||||
\danog\MadelineProto\Logger::log('hey', \danog\MadelineProto\Logger::FATAL_ERROR);
|
$MadelineProto->logger('hey', \danog\MadelineProto\Logger::FATAL_ERROR);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A small example message to use for tests.
|
* A small example message to use for tests.
|
||||||
*/
|
*/
|
||||||
$message = (\getenv('TRAVIS_COMMIT') == '') ? 'I iz works always (io laborare sembre) (yo lavorar siempre) (mi labori ĉiam) (я всегда работать) (Ik werkuh altijd) (Ngimbonga ngaso sonke isikhathi ukusebenza)' : ('Travis ci tests in progress: commit '.\getenv('TRAVIS_COMMIT').', job '.\getenv('TRAVIS_JOB_NUMBER').', PHP version: '.\getenv('TRAVIS_PHP_VERSION'));
|
$message = (\getenv('TRAVIS_COMMIT') == '') ? 'I iz works always (io laborare sembre) (yo lavorar siempre) (mi labori ĉiam) (я всегда работать) (Ik werkuh altijd) (Ngimbonga ngaso sonke isikhathi ukusebenza)' : ('Travis ci tests in progress: commit '.\getenv('TRAVIS_COMMIT').', job '.\getenv('TRAVIS_JOB_NUMBER').', PHP version: '.\getenv('TRAVIS_PHP_VERSION'));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Try making a phone call
|
* Try making a phone call
|
||||||
*/
|
*/
|
||||||
if (!\getenv('TRAVIS_COMMIT') && \stripos($MadelineProto->readline('Do you want to make a call? (y/n): '), 'y') !== false) {
|
if (!\getenv('TRAVIS_COMMIT') && \stripos(yield $MadelineProto->readline('Do you want to make a call? (y/n): '), 'y') !== false) {
|
||||||
$controller = $MadelineProto->requestCall(\getenv('TEST_SECRET_CHAT'))->play('input.raw')->then('input.raw')->playOnHold(['input.raw'])->setOutputFile('output.raw');
|
$controller = yield $MadelineProto->requestCall(\getenv('TEST_SECRET_CHAT'))->play('input.raw')->then('input.raw')->playOnHold(['input.raw'])->setOutputFile('output.raw');
|
||||||
while ($controller->getCallState() < \danog\MadelineProto\VoIP::CALL_STATE_READY) {
|
while ($controller->getCallState() < \danog\MadelineProto\VoIP::CALL_STATE_READY) {
|
||||||
$MadelineProto->getUpdates();
|
yield $MadelineProto->getUpdates();
|
||||||
}
|
}
|
||||||
\danog\MadelineProto\Logger::log($controller->configuration);
|
$MadelineProto->logger($controller->configuration);
|
||||||
while ($controller->getCallState() < \danog\MadelineProto\VoIP::CALL_STATE_ENDED) {
|
while ($controller->getCallState() < \danog\MadelineProto\VoIP::CALL_STATE_ENDED) {
|
||||||
$MadelineProto->getUpdates();
|
yield $MadelineProto->getUpdates();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Try receiving a phone call
|
* Try receiving a phone call
|
||||||
*/
|
*/
|
||||||
if (!\getenv('TRAVIS_COMMIT') && \stripos($MadelineProto->readline('Do you want to handle incoming calls? (y/n): '), 'y') !== false) {
|
if (!\getenv('TRAVIS_COMMIT') && \stripos(yield $MadelineProto->readline('Do you want to handle incoming calls? (y/n): '), 'y') !== false) {
|
||||||
$howmany = $MadelineProto->readline('How many calls would you like me to handle? ');
|
$howmany = yield $MadelineProto->readline('How many calls would you like me to handle? ');
|
||||||
$offset = 0;
|
$offset = 0;
|
||||||
while ($howmany > 0) {
|
while ($howmany > 0) {
|
||||||
$updates = $MadelineProto->getUpdates(['offset' => $offset, 'limit' => 50, 'timeout' => 0]); // Just like in the bot API, you can specify an offset, a limit and a timeout
|
$updates = yield $MadelineProto->getUpdates(['offset' => $offset, 'limit' => 50, 'timeout' => 0]); // Just like in the bot API, you can specify an offset, a limit and a timeout
|
||||||
foreach ($updates as $update) {
|
foreach ($updates as $update) {
|
||||||
\danog\MadelineProto\Logger::log($update);
|
$MadelineProto->logger($update);
|
||||||
$offset = $update['update_id'] + 1; // Just like in the bot API, the offset must be set to the last update_id
|
$offset = $update['update_id'] + 1; // Just like in the bot API, the offset must be set to the last update_id
|
||||||
switch ($update['update']['_']) {
|
switch ($update['update']['_']) {
|
||||||
case 'updatePhoneCall':
|
case 'updatePhoneCall':
|
||||||
@ -127,29 +128,29 @@ if (!\getenv('TRAVIS_COMMIT') && \stripos($MadelineProto->readline('Do you want
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Secret chat usage
|
* Secret chat usage
|
||||||
*/
|
*/
|
||||||
if (!\getenv('TRAVIS_COMMIT') && \stripos($MadelineProto->readline('Do you want to make the secret chat tests? (y/n): '), 'y') !== false) {
|
if (!\getenv('TRAVIS_COMMIT') && \stripos(yield $MadelineProto->readline('Do you want to make the secret chat tests? (y/n): '), 'y') !== false) {
|
||||||
/**
|
/**
|
||||||
* Request a secret chat.
|
* Request a secret chat.
|
||||||
*/
|
*/
|
||||||
$secret_chat_id = $MadelineProto->requestSecretChat(\getenv('TEST_SECRET_CHAT'));
|
$secret_chat_id = yield $MadelineProto->requestSecretChat(\getenv('TEST_SECRET_CHAT'));
|
||||||
echo 'Waiting for '.\getenv('TEST_SECRET_CHAT').' (secret chat id '.$secret_chat_id.') to accept the secret chat...'.PHP_EOL;
|
echo 'Waiting for '.\getenv('TEST_SECRET_CHAT').' (secret chat id '.$secret_chat_id.') to accept the secret chat...'.PHP_EOL;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Wait until the other party accepts it
|
* Wait until the other party accepts it
|
||||||
*/
|
*/
|
||||||
while ($MadelineProto->secretChatStatus($secret_chat_id) !== 2) {
|
while (yield $MadelineProto->secretChatStatus($secret_chat_id) !== 2) {
|
||||||
$MadelineProto->getUpdates();
|
yield $MadelineProto->getUpdates();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Send a markdown-formatted text message with expiration after 10 seconds.
|
* Send a markdown-formatted text message with expiration after 10 seconds.
|
||||||
*/
|
*/
|
||||||
$sentMessage = $MadelineProto->messages->sendEncrypted([
|
$sentMessage = yield $MadelineProto->messages->sendEncrypted([
|
||||||
'peer' => $secret_chat_id,
|
'peer' => $secret_chat_id,
|
||||||
'message' => [
|
'message' => [
|
||||||
'_' => 'decryptedMessage',
|
'_' => 'decryptedMessage',
|
||||||
@ -159,7 +160,7 @@ if (!\getenv('TRAVIS_COMMIT') && \stripos($MadelineProto->readline('Do you want
|
|||||||
'parse_mode' => 'Markdown',
|
'parse_mode' => 'Markdown',
|
||||||
],
|
],
|
||||||
]);
|
]);
|
||||||
\danog\MadelineProto\Logger::log($sentMessage, \danog\MadelineProto\Logger::NOTICE);
|
$MadelineProto->logger($sentMessage, \danog\MadelineProto\Logger::NOTICE);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Send secret media.
|
* Send secret media.
|
||||||
@ -228,54 +229,56 @@ if (!\getenv('TRAVIS_COMMIT') && \stripos($MadelineProto->readline('Do you want
|
|||||||
$secret_media['voice'] = ['peer' => $secret_chat_id, 'file' => 'tests/mosconi.mp3', 'message' => ['_' => 'decryptedMessage', 'ttl' => 0, 'message' => '', 'media' => ['_' => 'decryptedMessageMediaDocument', 'thumb' => \file_get_contents('tests/faust.preview.jpg'), 'thumb_w' => 90, 'thumb_h' => 90, 'mime_type' => \mime_content_type('tests/mosconi.mp3'), 'caption' => 'test', 'file_name' => 'mosconi.mp3', 'size' => \filesize('tests/mosconi.mp3'), 'attributes' => [['_' => 'documentAttributeAudio', 'voice' => true, 'title' => 'AH NON LO SO IO', 'performer' => 'IL DIO GERMANO MOSCONI']]]]];
|
$secret_media['voice'] = ['peer' => $secret_chat_id, 'file' => 'tests/mosconi.mp3', 'message' => ['_' => 'decryptedMessage', 'ttl' => 0, 'message' => '', 'media' => ['_' => 'decryptedMessageMediaDocument', 'thumb' => \file_get_contents('tests/faust.preview.jpg'), 'thumb_w' => 90, 'thumb_h' => 90, 'mime_type' => \mime_content_type('tests/mosconi.mp3'), 'caption' => 'test', 'file_name' => 'mosconi.mp3', 'size' => \filesize('tests/mosconi.mp3'), 'attributes' => [['_' => 'documentAttributeAudio', 'voice' => true, 'title' => 'AH NON LO SO IO', 'performer' => 'IL DIO GERMANO MOSCONI']]]]];
|
||||||
|
|
||||||
foreach ($secret_media as $type => $smessage) {
|
foreach ($secret_media as $type => $smessage) {
|
||||||
\danog\MadelineProto\Logger::log("Encrypting and uploading $type...");
|
$MadelineProto->logger("Encrypting and uploading $type...");
|
||||||
$type = $MadelineProto->messages->sendEncryptedFile($smessage);
|
$type = yield $MadelineProto->messages->sendEncryptedFile($smessage);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
$mention = $MadelineProto->getInfo(\getenv('TEST_USERNAME')); // Returns an array with all of the constructors that can be extracted from a username or an id
|
$mention = yield $MadelineProto->getInfo(\getenv('TEST_USERNAME')); // Returns an array with all of the constructors that can be extracted from a username or an id
|
||||||
$mention = $mention['user_id']; // Selects only the numeric user id
|
$mention = $mention['user_id']; // Selects only the numeric user id
|
||||||
$media = [];
|
$media = [];
|
||||||
|
|
||||||
// Image
|
// Image
|
||||||
$media['photo'] = ['_' => 'inputMediaUploadedPhoto', 'file' => 'tests/faust.jpg'];
|
$media['photo'] = ['_' => 'inputMediaUploadedPhoto', 'file' => 'tests/faust.jpg'];
|
||||||
|
|
||||||
// Sticker
|
// Sticker
|
||||||
$media['sticker'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/lel.webp', 'attributes' => [['_' => 'documentAttributeSticker', 'alt' => 'LEL']]];
|
$media['sticker'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/lel.webp', 'attributes' => [['_' => 'documentAttributeSticker', 'alt' => 'LEL']]];
|
||||||
|
|
||||||
// Video
|
// Video
|
||||||
$media['video'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/swing.mp4', 'attributes' => [['_' => 'documentAttributeVideo']]];
|
$media['video'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/swing.mp4', 'attributes' => [['_' => 'documentAttributeVideo']]];
|
||||||
|
|
||||||
// audio
|
// audio
|
||||||
$media['audio'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/mosconi.mp3', 'attributes' => [['_' => 'documentAttributeAudio', 'voice' => false, 'title' => 'AH NON LO SO IO', 'performer' => 'IL DIO GERMANO MOSCONI']]];
|
$media['audio'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/mosconi.mp3', 'attributes' => [['_' => 'documentAttributeAudio', 'voice' => false, 'title' => 'AH NON LO SO IO', 'performer' => 'IL DIO GERMANO MOSCONI']]];
|
||||||
|
|
||||||
// voice
|
// voice
|
||||||
$media['voice'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/mosconi.mp3', 'attributes' => [['_' => 'documentAttributeAudio', 'voice' => true, 'title' => 'AH NON LO SO IO', 'performer' => 'IL DIO GERMANO MOSCONI']]];
|
$media['voice'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/mosconi.mp3', 'attributes' => [['_' => 'documentAttributeAudio', 'voice' => true, 'title' => 'AH NON LO SO IO', 'performer' => 'IL DIO GERMANO MOSCONI']]];
|
||||||
|
|
||||||
// Document
|
// Document
|
||||||
$media['document'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/60', 'mime_type' => 'magic/magic', 'attributes' => [['_' => 'documentAttributeFilename', 'file_name' => 'magic.magic']]];
|
$media['document'] = ['_' => 'inputMediaUploadedDocument', 'file' => 'tests/60', 'mime_type' => 'magic/magic', 'attributes' => [['_' => 'documentAttributeFilename', 'file_name' => 'magic.magic']]];
|
||||||
|
|
||||||
$message = 'yay '.\PHP_VERSION_ID;
|
$message = 'yay '.\PHP_VERSION_ID;
|
||||||
$mention = $MadelineProto->getInfo(\getenv('TEST_USERNAME')); // Returns an array with all of the constructors that can be extracted from a username or an id
|
$mention = yield $MadelineProto->getInfo(\getenv('TEST_USERNAME')); // Returns an array with all of the constructors that can be extracted from a username or an id
|
||||||
$mention = $mention['user_id']; // Selects only the numeric user id
|
$mention = $mention['user_id']; // Selects only the numeric user id
|
||||||
|
|
||||||
/*
|
/*
|
||||||
$t = time();
|
$t = time();
|
||||||
$MadelineProto->upload('big');
|
yield $MadelineProto->upload('big');
|
||||||
var_dump(time()-$t);
|
var_dump(time()-$t);
|
||||||
*/
|
*/
|
||||||
|
|
||||||
foreach (\json_decode(\getenv('TEST_DESTINATION_GROUPS'), true) as $peer) {
|
foreach (\json_decode(\getenv('TEST_DESTINATION_GROUPS'), true) as $peer) {
|
||||||
$sentMessage = $MadelineProto->messages->sendMessage(['peer' => $peer, 'message' => $message, 'entities' => [['_' => 'inputMessageEntityMentionName', 'offset' => 0, 'length' => \mb_strlen($message), 'user_id' => $mention]]]);
|
$sentMessage = yield $MadelineProto->messages->sendMessage(['peer' => $peer, 'message' => $message, 'entities' => [['_' => 'inputMessageEntityMentionName', 'offset' => 0, 'length' => \mb_strlen($message), 'user_id' => $mention]]]);
|
||||||
\danog\MadelineProto\Logger::log($sentMessage, \danog\MadelineProto\Logger::NOTICE);
|
$MadelineProto->logger($sentMessage, \danog\MadelineProto\Logger::NOTICE);
|
||||||
|
|
||||||
foreach ($media as $type => $inputMedia) {
|
foreach ($media as $type => $inputMedia) {
|
||||||
\danog\MadelineProto\Logger::log("Sending $type");
|
$MadelineProto->logger("Sending $type");
|
||||||
$type = $MadelineProto->messages->sendMedia(['peer' => $peer, 'media' => $inputMedia, 'message' => '['.$message.'](mention:'.$mention.')', 'parse_mode' => 'markdown']);
|
$type = yield $MadelineProto->messages->sendMedia(['peer' => $peer, 'media' => $inputMedia, 'message' => '['.$message.'](mention:'.$mention.')', 'parse_mode' => 'markdown']);
|
||||||
|
yield $MadelineProto->downloadToDir(yield $MadelineProto->messages->uploadMedia(['peer' => '@me', 'media' => $inputMedia]), '/tmp');
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
foreach (\json_decode(\getenv('TEST_DESTINATION_GROUPS'), true) as $peer) {
|
foreach (\json_decode(\getenv('TEST_DESTINATION_GROUPS'), true) as $peer) {
|
||||||
$sentMessage = $MadelineProto->messages->sendMessage(['peer' => $peer, 'message' => $message, 'entities' => [['_' => 'inputMessageEntityMentionName', 'offset' => 0, 'length' => \mb_strlen($message), 'user_id' => $mention]]]);
|
$sentMessage = yield $MadelineProto->messages->sendMessage(['peer' => $peer, 'message' => $message, 'entities' => [['_' => 'inputMessageEntityMentionName', 'offset' => 0, 'length' => \mb_strlen($message), 'user_id' => $mention]]]);
|
||||||
\danog\MadelineProto\Logger::log($sentMessage, \danog\MadelineProto\Logger::NOTICE);
|
$MadelineProto->logger($sentMessage, \danog\MadelineProto\Logger::NOTICE);
|
||||||
}
|
}
|
||||||
|
});
|
||||||
|
Loading…
Reference in New Issue
Block a user