diff --git a/src/danog/MadelineProto/Db/DbPropertiesFabric.php b/src/danog/MadelineProto/Db/DbPropertiesFabric.php index cc2dce8c..40c75d92 100644 --- a/src/danog/MadelineProto/Db/DbPropertiesFabric.php +++ b/src/danog/MadelineProto/Db/DbPropertiesFabric.php @@ -2,6 +2,7 @@ namespace danog\MadelineProto\Db; +use Amp\Promise; use danog\MadelineProto\MTProto; class DbPropertiesFabric @@ -12,13 +13,13 @@ class DbPropertiesFabric * @param string $name * @param $value * - * @return DbType + * @return Promise * * @uses \danog\MadelineProto\Db\MemoryArray * @uses \danog\MadelineProto\Db\SharedMemoryArray * @uses \danog\MadelineProto\Db\MysqlArray */ - public static function get(MTProto $madelineProto, string $propertyType, string $name, $value = null): DbType + public static function get(MTProto $madelineProto, string $propertyType, string $name, $value = null): Promise { $class = __NAMESPACE__; $dbSettings = $madelineProto->settings['db']; diff --git a/src/danog/MadelineProto/Db/DbType.php b/src/danog/MadelineProto/Db/DbType.php index f816a778..19f15e04 100644 --- a/src/danog/MadelineProto/Db/DbType.php +++ b/src/danog/MadelineProto/Db/DbType.php @@ -2,7 +2,17 @@ namespace danog\MadelineProto\Db; +use Amp\Promise; + interface DbType { - static function getInstance(string $name, $value = null, string $tablePrefix = '', array $settings = []): self; + /** + * @param string $name + * @param null $value + * @param string $tablePrefix + * @param array $settings + * + * @return Promise + */ + static function getInstance(string $name, $value = null, string $tablePrefix = '', array $settings = []): Promise; } \ No newline at end of file diff --git a/src/danog/MadelineProto/Db/MemoryArray.php b/src/danog/MadelineProto/Db/MemoryArray.php index 5951a32a..a7f65584 100644 --- a/src/danog/MadelineProto/Db/MemoryArray.php +++ b/src/danog/MadelineProto/Db/MemoryArray.php @@ -13,12 +13,14 @@ class MemoryArray extends \ArrayIterator implements DbArray parent::__construct((array) $array, $flags | self::STD_PROP_LIST); } - public static function getInstance(string $name, $value = null, string $tablePrefix = '', array $settings = []): DbArray + public static function getInstance(string $name, $value = null, string $tablePrefix = '', array $settings = []): Promise { - if ($value instanceof DbArray) { - $value = $value->getArrayCopy(); - } - return new static($value); + return call(function() use ($value) { + if ($value instanceof DbArray) { + $value = $value->getArrayCopy(); + } + return new static($value); + }); } public function offsetExists($offset): Promise diff --git a/src/danog/MadelineProto/Db/MysqlArray.php b/src/danog/MadelineProto/Db/MysqlArray.php index 565bc080..85c14e00 100644 --- a/src/danog/MadelineProto/Db/MysqlArray.php +++ b/src/danog/MadelineProto/Db/MysqlArray.php @@ -40,7 +40,7 @@ class MysqlArray implements DbArray } - public static function getInstance(string $name, $value = null, string $tablePrefix = '', array $settings = []): DbType + public static function getInstance(string $name, $value = null, string $tablePrefix = '', array $settings = []): Promise { $instance = new static(); @@ -49,43 +49,51 @@ class MysqlArray implements DbArray $instance->db = static::getDbConnection($settings); $instance->ttl = $settings['cache_ttl'] ?? $instance->ttl; - Loop::defer(static function() use($value, $instance) { - if ($value instanceof static && $value->table) { - if ( - mb_strpos($value->table, 'tmp') === 0 && - mb_strpos($instance->table, 'tmp') !== 0 - ) { - yield from $instance->renameTable($value->table, $instance->table); - } elseif (mb_strpos($instance->table, 'tmp') === 0){ - $instance->table = $value->table; - } - } - + return call(static function() use($instance, $value) { + yield from static::renameTmpTable($instance, $value); yield from $instance->prepareTable(); + Loop::defer(fn() => static::migrateDataToDb($instance, $value)); - if (!empty($value) && !$value instanceof static) { - Logger::log('Converting database.', Logger::ERROR); - if ($value instanceof DbArray) { - $value = $value->getArrayCopy(); - } - $value = (array) $value; - $counter = 0; - $total = count($value); - foreach ((array) $value as $key => $item) { - $counter++; - if ($counter % 100 === 0) { - yield $instance->offsetSet($key, $item); - Logger::log("Converting database. $counter/$total", Logger::WARNING); - } else { - $instance->offsetSet($key, $item); - } - - } - Logger::log('Converting database done.', Logger::ERROR); - } + return $instance; }); + } - return $instance; + private static function renameTmpTable(MysqlArray $instance, ?DbArray $value): \Generator + { + if ($value instanceof static && $value->table) { + if ( + mb_strpos($value->table, 'tmp') === 0 && + mb_strpos($instance->table, 'tmp') !== 0 + ) { + yield from $instance->renameTable($value->table, $instance->table); + } elseif (mb_strpos($instance->table, 'tmp') === 0) { + $instance->table = $value->table; + } + } + } + + private static function migrateDataToDb(MysqlArray $instance, ?DbArray $value): \Generator + { + if (!empty($value) && !$value instanceof static) { + Logger::log('Converting database.', Logger::ERROR); + if ($value instanceof DbArray) { + $value = $value->getArrayCopy(); + } + $value = (array) $value; + $counter = 0; + $total = count($value); + foreach ((array) $value as $key => $item) { + $counter++; + if ($counter % 100 === 0) { + yield $instance->offsetSet($key, $item); + Logger::log("Converting database. $counter/$total", Logger::WARNING); + } else { + $instance->offsetSet($key, $item); + } + + } + Logger::log('Converting database done.', Logger::ERROR); + } } /** @@ -262,6 +270,7 @@ class MysqlArray implements DbArray */ private function prepareTable() { + Logger::log("Creating/checking table {$this->table}", Logger::WARNING); return yield $this->request(" CREATE TABLE IF NOT EXISTS `{$this->table}` ( @@ -278,6 +287,7 @@ class MysqlArray implements DbArray private function renameTable(string $from, string $to) { + Logger::log("Renaming table {$from} to {$to}", Logger::WARNING); yield $this->request(" ALTER TABLE `{$from}` RENAME TO `{$to}`; "); diff --git a/src/danog/MadelineProto/MTProto.php b/src/danog/MadelineProto/MTProto.php index d9e15291..e71ad4fe 100644 --- a/src/danog/MadelineProto/MTProto.php +++ b/src/danog/MadelineProto/MTProto.php @@ -572,7 +572,7 @@ class MTProto extends AsyncConstruct implements TLCallback if ($reset) { unset($this->{$property}); } else { - $this->{$property} = DbPropertiesFabric::get($this, $type, $property, $this->{$property}); + $this->{$property} = yield DbPropertiesFabric::get($this, $type, $property, $this->{$property}); } }