From c74e5d8368f8194419b66f80f628d98046947014 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=8E=E9=93=AD=E6=98=95?= Date: Wed, 16 Dec 2020 09:38:41 +0800 Subject: [PATCH] Don't format `decimal` to `float` for command `gen:model` by default. (#2979) * Don't format `decimal` to `float` for command `gen:model` by default. * Update CHANGELOG-2.1.md * Added test case. --- CHANGELOG-2.1.md | 1 + .../src/Commands/Ast/ModelUpdateVisitor.php | 7 +- src/database/tests/GenModelTest.php | 118 ++++++++++++++++++ src/database/tests/ModelTest.php | 4 +- src/database/tests/Stubs/ContainerStub.php | 15 +++ .../tests/Stubs/Model/UserExtEmpty.php | 36 ++++++ 6 files changed, 173 insertions(+), 8 deletions(-) create mode 100644 src/database/tests/GenModelTest.php create mode 100644 src/database/tests/Stubs/Model/UserExtEmpty.php diff --git a/CHANGELOG-2.1.md b/CHANGELOG-2.1.md index 0ae800909..1b54dd751 100644 --- a/CHANGELOG-2.1.md +++ b/CHANGELOG-2.1.md @@ -39,6 +39,7 @@ - [#2871](https://github.com/hyperf/hyperf/pull/2871) Use `(string) $body` instead of `$body->getContents()` for getting contents from `StreamInterface`, because method `getContents()` only returns the remaining contents in a string. - [#2909](https://github.com/hyperf/hyperf/pull/2909) Allow setting repeated middlewares. - [#2935](https://github.com/hyperf/hyperf/pull/2935) Changed the string format for default exception formatter. +- [#2979](https://github.com/hyperf/hyperf/pull/2979) Don't format `decimal` to `float` for command `gen:model` by default. ## Deprecated diff --git a/src/database/src/Commands/Ast/ModelUpdateVisitor.php b/src/database/src/Commands/Ast/ModelUpdateVisitor.php index 05e5ff9b8..435466c65 100644 --- a/src/database/src/Commands/Ast/ModelUpdateVisitor.php +++ b/src/database/src/Commands/Ast/ModelUpdateVisitor.php @@ -125,7 +125,7 @@ class ModelUpdateVisitor extends NodeVisitorAbstract $items = []; $casts = $this->class->getCasts(); foreach ($node->default->items as $item) { - $caster = $this->class->getCasts()[$item->key->value] ?? null; + $caster = $casts[$item->key->value] ?? null; if ($caster && $this->isCaster($caster)) { $items[] = $item; } @@ -350,11 +350,6 @@ class ModelUpdateVisitor extends NodeVisitorAbstract case 'int': case 'bigint': return 'integer'; - case 'decimal': - case 'float': - case 'double': - case 'real': - return 'float'; case 'bool': case 'boolean': return 'boolean'; diff --git a/src/database/tests/GenModelTest.php b/src/database/tests/GenModelTest.php new file mode 100644 index 000000000..b6ea77392 --- /dev/null +++ b/src/database/tests/GenModelTest.php @@ -0,0 +1,118 @@ +shouldReceive('get')->with(EventDispatcherInterface::class)->andReturnUsing(function () { + $dispatcher = Mockery::mock(EventDispatcherInterface::class); + $dispatcher->shouldReceive('dispatch')->withAnyArgs()->andReturn(null); + return $dispatcher; + }); + $connection = $container->get(ConnectionResolverInterface::class)->connection(); + /** @var MySqlBuilder $builder */ + $builder = $connection->getSchemaBuilder('default'); + $columns = $this->formatColumns($builder->getColumnTypeListing('user_ext')); + foreach ($columns as $i => $column) { + if ($column['column_name'] === 'created_at') { + $columns[$i]['cast'] = 'datetime'; + } + } + + $astParser = (new ParserFactory())->create(ParserFactory::ONLY_PHP7); + $stms = $astParser->parse(file_get_contents(__DIR__ . '/Stubs/Model/UserExtEmpty.php')); + $traverser = new NodeTraverser(); + $visitor = new ModelUpdateVisitor(UserExtEmpty::class, $columns, ContainerStub::getModelOption()); + $traverser->addVisitor($visitor); + $stms = $traverser->traverse($stms); + $code = (new Standard())->prettyPrintFile($stms); + $this->assertEquals($this->license . ' +namespace HyperfTest\Database\Stubs\Model; + +/** + * @property int $id + * @property int $count + * @property string $float_num + * @property string $str + * @property string $json + * @property \Carbon\Carbon $created_at + * @property string $updated_at + */ +class UserExtEmpty extends Model +{ + /** + * The table associated with the model. + * + * @var string + */ + protected $table = \'user_ext\'; + /** + * The attributes that are mass assignable. + * + * @var array + */ + protected $fillable = [\'id\', \'count\', \'float_num\', \'str\', \'json\', \'created_at\', \'updated_at\']; + /** + * The attributes that should be cast to native types. + * + * @var array + */ + protected $casts = [\'id\' => \'integer\', \'count\' => \'integer\', \'created_at\' => \'datetime\']; +}', $code); + } + + /** + * Format column's key to lower case. + */ + protected function formatColumns(array $columns): array + { + return array_map(function ($item) { + return array_change_key_case($item, CASE_LOWER); + }, $columns); + } +} diff --git a/src/database/tests/ModelTest.php b/src/database/tests/ModelTest.php index b0b58b065..bc3cbed88 100644 --- a/src/database/tests/ModelTest.php +++ b/src/database/tests/ModelTest.php @@ -1811,7 +1811,7 @@ class ModelTest extends TestCase $called = false; - ModelStub::withoutTouching(function () use (&$called, $model) { + ModelStub::withoutTouching(function () use (&$called) { $called = true; }); @@ -1824,7 +1824,7 @@ class ModelTest extends TestCase $called = false; - Model::withoutTouchingOn([ModelStub::class], function () use (&$called, $model) { + Model::withoutTouchingOn([ModelStub::class], function () use (&$called) { $called = true; }); diff --git a/src/database/tests/Stubs/ContainerStub.php b/src/database/tests/Stubs/ContainerStub.php index e1fdcaa0e..02214c0a4 100644 --- a/src/database/tests/Stubs/ContainerStub.php +++ b/src/database/tests/Stubs/ContainerStub.php @@ -11,6 +11,7 @@ declare(strict_types=1); */ namespace HyperfTest\Database\Stubs; +use Hyperf\Database\Commands\ModelOption; use Hyperf\Database\ConnectionResolver; use Hyperf\Database\ConnectionResolverInterface; use Hyperf\Database\Connectors\ConnectionFactory; @@ -52,4 +53,18 @@ class ContainerStub return $container; } + + public static function getModelOption() + { + $option = new ModelOption(); + $option->setWithComments(false) + ->setRefreshFillable(true) + ->setForceCasts(true) + ->setInheritance('Model') + ->setPath(__DIR__ . '/../Stubs/Model') + ->setPool('default') + ->setPrefix('') + ->setWithIde(false); + return $option; + } } diff --git a/src/database/tests/Stubs/Model/UserExtEmpty.php b/src/database/tests/Stubs/Model/UserExtEmpty.php new file mode 100644 index 000000000..8395a10ba --- /dev/null +++ b/src/database/tests/Stubs/Model/UserExtEmpty.php @@ -0,0 +1,36 @@ +