mirror of
https://github.com/barryvdh/laravel-ide-helper.git
synced 2026-08-18 18:13:11 +00:00
Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
981ff45b43 | ||
|
|
8174730714 | ||
|
|
ae5b623cf2 | ||
|
|
eff51d41b3 | ||
|
|
b14d983f74 | ||
|
|
1fdc866fb0 | ||
|
|
d7359b86d4 | ||
|
|
5d8d93273f | ||
|
|
30e5300e49 | ||
|
|
593e0d4aa7 | ||
|
|
e7d4cb322f | ||
|
|
5318f485e2 | ||
|
|
7db1843473 | ||
|
|
1989d0e794 | ||
|
|
09db8c9a76 | ||
|
|
4aa43fa613 | ||
|
|
d55b48476e | ||
|
|
45e84b9070 | ||
|
|
f472c26601 | ||
|
|
1deadced46 | ||
|
|
e1d1352ac5 | ||
|
|
65e3278c86 | ||
|
|
efd7e51566 | ||
|
|
2a5dda6a27 | ||
|
|
6577af8464 | ||
|
|
6c7bc371f9 | ||
|
|
217b8989c2 | ||
|
|
c003eb40d7 | ||
|
|
1a3d32f0d1 | ||
|
|
bd733b7b7c | ||
|
|
93630fdf62 | ||
|
|
f64ed52205 | ||
|
|
ba28841870 | ||
|
|
b02a0bc6c9 | ||
|
|
a665961fb9 | ||
|
|
83852e9de0 | ||
|
|
d2f29d997b | ||
|
|
cbacb28f19 | ||
|
|
930e5bd301 | ||
|
|
930d258cd4 | ||
|
|
94248adae8 | ||
|
|
50ecd8b815 | ||
|
|
1b70277203 | ||
|
|
87a03fd9c4 | ||
|
|
b8a73bcab9 | ||
|
|
0556991c69 | ||
|
|
be78ac62cd | ||
|
|
265f00c322 | ||
|
|
bbd96d3616 | ||
|
|
8d913089db | ||
|
|
9a2588cb3a | ||
|
|
e7fa36bdc3 | ||
|
|
b1e868c5fc | ||
|
|
203d60dc8c | ||
|
|
f5275b700a | ||
|
|
046a9bcc77 | ||
|
|
c6191830ab | ||
|
|
cfff7721bc | ||
|
|
4691bc5fbd | ||
|
|
b1b05b694b | ||
|
|
98d6087a1e | ||
|
|
c7b7ebf1b5 | ||
|
|
17982029f0 | ||
|
|
bda5120e9a | ||
|
|
d961482d22 | ||
|
|
8852b1ca9d | ||
|
|
b644e48801 | ||
|
|
09610da602 | ||
|
|
2d56afce8e | ||
|
|
5c304db44f | ||
|
|
1fc4284af6 | ||
|
|
ea113e8c0b | ||
|
|
387efb9b42 | ||
|
|
8ab907f219 | ||
|
|
e29e035135 | ||
|
|
7b2786ac2b | ||
|
|
76bd86dbaf | ||
|
|
7b067198a6 | ||
|
|
b6f525b320 | ||
|
|
d65f1cedcd | ||
|
|
df6b1b6f82 | ||
|
|
76a1952c41 | ||
|
|
d45b02efb1 | ||
|
|
b0abafb8c7 | ||
|
|
6b0e9ec48d | ||
|
|
28f0ac3781 | ||
|
|
721a7cd3f7 | ||
|
|
ea6d6d0105 | ||
|
|
01320a48e3 | ||
|
|
fedcb57295 | ||
|
|
ce72ff4663 | ||
|
|
cb6f52f4d6 | ||
|
|
55c9bfc33b | ||
|
|
a9ea231679 | ||
|
|
2b1273c45e | ||
|
|
08d39c125f | ||
|
|
87a02ff574 | ||
|
|
9e42ce11f4 | ||
|
|
dca7fa7b10 | ||
|
|
0e4b9b77c3 | ||
|
|
46901d2c80 | ||
|
|
25b5576f57 | ||
|
|
d6d99994c3 | ||
|
|
7e78d02d0a | ||
|
|
35d954fc39 | ||
|
|
5eeda63958 | ||
|
|
b76156b24c | ||
|
|
2a63d51496 | ||
|
|
3814fe86ca | ||
|
|
3ab73555d9 | ||
|
|
ff3844e4e1 | ||
|
|
d11bf58084 | ||
|
|
75e1f22ec6 | ||
|
|
144a50e8ee | ||
|
|
b611cb5eff |
+4
-8
@@ -1,10 +1,9 @@
|
||||
language: php
|
||||
|
||||
php:
|
||||
- 5.5
|
||||
- 5.6
|
||||
- 7.0
|
||||
- hhvm
|
||||
- 7.1
|
||||
- 7.2
|
||||
|
||||
# This triggers builds to run on the new TravisCI infrastructure.
|
||||
# See: http://docs.travis-ci.com/user/workers/container-based-infrastructure/
|
||||
@@ -17,7 +16,7 @@ cache:
|
||||
|
||||
matrix:
|
||||
include:
|
||||
- php: 5.5
|
||||
- php: 7.0
|
||||
env: 'COMPOSER_FLAGS="--prefer-stable --prefer-lowest"'
|
||||
|
||||
before_script:
|
||||
@@ -25,7 +24,4 @@ before_script:
|
||||
|
||||
script:
|
||||
- vendor/bin/phpcs --standard=psr2 src/
|
||||
- vendor/bin/phpunit --coverage-text --coverage-clover=coverage.clover
|
||||
|
||||
after_script:
|
||||
- if [[ $TRAVIS_PHP_VERSION != 'hhvm' && $TRAVIS_PHP_VERSION != '7.0' ]]; then php vendor/bin/ocular code-coverage:upload --format=php-clover coverage.clover; fi
|
||||
- vendor/bin/phpunit
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
# The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2016 Barry vd. Heuvel <barryvdh@gmail.com>
|
||||
Copyright (c) Barry vd. Heuvel <barryvdh@gmail.com>
|
||||
|
||||
> Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
> of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+18
-9
@@ -10,17 +10,20 @@
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"php": ">=5.4.0",
|
||||
"illuminate/support": "^5.0,<5.5",
|
||||
"illuminate/console": "^5.0,<5.5",
|
||||
"illuminate/filesystem": "^5.0,<5.5",
|
||||
"php": ">=7",
|
||||
"illuminate/support": "^5.5,<5.8",
|
||||
"illuminate/console": "^5.5,<5.8",
|
||||
"illuminate/filesystem": "^5.5,<5.8",
|
||||
"barryvdh/reflection-docblock": "^2.0.4",
|
||||
"symfony/class-loader": "^2.3|^3.0"
|
||||
"composer/composer": "^1.6"
|
||||
},
|
||||
"require-dev": {
|
||||
"illuminate/config": "^5.1,<5.8",
|
||||
"illuminate/view": "^5.1,<5.8",
|
||||
"phpro/grumphp": "^0.14",
|
||||
"phpunit/phpunit" : "4.*",
|
||||
"scrutinizer/ocular": "~1.1",
|
||||
"squizlabs/php_codesniffer": "~2.3",
|
||||
"squizlabs/php_codesniffer": "^3",
|
||||
"doctrine/dbal": "~2.3"
|
||||
},
|
||||
"suggest": {
|
||||
@@ -33,16 +36,22 @@
|
||||
},
|
||||
"autoload-dev": {
|
||||
"psr-4": {
|
||||
":vendor\\:package_name\\": "tests"
|
||||
"Barryvdh\\LaravelIdeHelper\\": "tests"
|
||||
}
|
||||
},
|
||||
"scripts": {
|
||||
"test": "phpunit",
|
||||
"cs": "phpcs --standard=psr2 src/"
|
||||
"check-style": "phpcs -p --standard=PSR2 src/",
|
||||
"fix-style": "phpcbf -p --standard=PSR2 src/"
|
||||
},
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "2.3-dev"
|
||||
"dev-master": "2.5-dev"
|
||||
},
|
||||
"laravel": {
|
||||
"providers": [
|
||||
"Barryvdh\\LaravelIdeHelper\\IdeHelperServiceProvider"
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+17
-4
@@ -14,6 +14,8 @@ return array(
|
||||
'filename' => '_ide_helper',
|
||||
'format' => 'php',
|
||||
|
||||
'meta_filename' => '.phpstorm.meta.php',
|
||||
|
||||
/*
|
||||
|--------------------------------------------------------------------------
|
||||
| Fluent helpers
|
||||
@@ -25,6 +27,17 @@ return array(
|
||||
|
||||
'include_fluent' => false,
|
||||
|
||||
/*
|
||||
|--------------------------------------------------------------------------
|
||||
| Write Model Magic methods
|
||||
|--------------------------------------------------------------------------
|
||||
|
|
||||
| Set to false to disable write magic methods of model
|
||||
|
|
||||
*/
|
||||
|
||||
'write_model_magic_where' => true,
|
||||
|
||||
/*
|
||||
|--------------------------------------------------------------------------
|
||||
| Helper files to include
|
||||
@@ -140,13 +153,13 @@ return array(
|
||||
|
|
||||
| For example, normally you would see this:
|
||||
|
|
||||
| * @property \Carbon\Carbon $created_at
|
||||
| * @property \Carbon\Carbon $updated_at
|
||||
| * @property \Illuminate\Support\Carbon $created_at
|
||||
| * @property \Illuminate\Support\Carbon $updated_at
|
||||
|
|
||||
| With this enabled, the properties will be this:
|
||||
|
|
||||
| * @property \Carbon\Carbon $createdAt
|
||||
| * @property \Carbon\Carbon $updatedAt
|
||||
| * @property \Illuminate\Support\Carbon $createdAt
|
||||
| * @property \Illuminate\Support\Carbon $updatedAt
|
||||
|
|
||||
| Note, it is currently an all-or-nothing option.
|
||||
|
|
||||
|
||||
+15
@@ -0,0 +1,15 @@
|
||||
parameters:
|
||||
git_dir: .
|
||||
bin_dir: vendor/bin
|
||||
tasks:
|
||||
phpunit:
|
||||
config_file: ~
|
||||
testsuite: ~
|
||||
group: []
|
||||
always_execute: false
|
||||
phpcs:
|
||||
standard: PSR2
|
||||
warning_severity: ~
|
||||
ignore_patterns:
|
||||
- tests/
|
||||
triggered_by: [php]
|
||||
+1
-8
@@ -10,7 +10,7 @@
|
||||
processIsolation="false"
|
||||
stopOnFailure="false">
|
||||
<testsuites>
|
||||
<testsuite name=":vendor Test Suite">
|
||||
<testsuite name="Unit Tests">
|
||||
<directory>tests</directory>
|
||||
</testsuite>
|
||||
</testsuites>
|
||||
@@ -19,11 +19,4 @@
|
||||
<directory suffix=".php">src/</directory>
|
||||
</whitelist>
|
||||
</filter>
|
||||
<logging>
|
||||
<log type="tap" target="build/report.tap"/>
|
||||
<log type="junit" target="build/report.junit.xml"/>
|
||||
<log type="coverage-html" target="build/coverage" charset="UTF-8" yui="true" highlight="true"/>
|
||||
<log type="coverage-text" target="build/coverage.txt"/>
|
||||
<log type="coverage-clover" target="build/logs/clover.xml"/>
|
||||
</logging>
|
||||
</phpunit>
|
||||
@@ -22,7 +22,7 @@ If you don't want to generate it, you can add a pre-generated file to the root f
|
||||
* Generated version for Lumen: https://gist.github.com/barryvdh/be17164b0ad51f832f20
|
||||
* Generated Phpstorm Meta file: https://gist.github.com/barryvdh/bb6ffc5d11e0a75dba67
|
||||
|
||||
Note: You do need CodeIntel for Sublime Text: https://github.com/SublimeCodeIntel/SublimeCodeIntel
|
||||
Note: You do need CodeComplice for Sublime Text: https://github.com/spectacles/CodeComplice
|
||||
|
||||
### Install
|
||||
|
||||
@@ -37,6 +37,7 @@ After updating composer, add the service provider to the `providers` array in `c
|
||||
```php
|
||||
Barryvdh\LaravelIdeHelper\IdeHelperServiceProvider::class,
|
||||
```
|
||||
**Laravel 5.5** uses Package Auto-Discovery, so doesn't require you to manually add the ServiceProvider.
|
||||
|
||||
To install this package on only development systems, add the `--dev` flag to your composer command:
|
||||
|
||||
@@ -66,7 +67,7 @@ You can now re-generate the docs yourself (for future updates)
|
||||
php artisan ide-helper:generate
|
||||
```
|
||||
|
||||
Note: `bootstrap/compiled.php` has to be cleared first, so run `php artisan clear-compiled` before generating (and `php artisan optimize` after).
|
||||
Note: `bootstrap/compiled.php` has to be cleared first, so run `php artisan clear-compiled` before generating.
|
||||
|
||||
You can configure your composer.json to do this after each commit:
|
||||
|
||||
@@ -75,8 +76,7 @@ You can configure your composer.json to do this after each commit:
|
||||
"post-update-cmd": [
|
||||
"Illuminate\\Foundation\\ComposerScripts::postUpdate",
|
||||
"php artisan ide-helper:generate",
|
||||
"php artisan ide-helper:meta",
|
||||
"php artisan optimize"
|
||||
"php artisan ide-helper:meta"
|
||||
]
|
||||
},
|
||||
```
|
||||
@@ -90,7 +90,7 @@ php artisan vendor:publish --provider="Barryvdh\LaravelIdeHelper\IdeHelperServic
|
||||
The generator tries to identify the real class, but if it cannot be found, you can define it in the config file.
|
||||
|
||||
Some classes need a working database connection. If you do not have a default working connection, some facades will not be included.
|
||||
You can use an in-memory SQLite driver by adding the -M option.
|
||||
You can use an in-memory SQLite driver by adding the `-M` option.
|
||||
|
||||
You can choose to include helper files. This is not enabled by default, but you can override it with the `--helpers (-H)` option.
|
||||
The `Illuminate/Support/helpers.php` is already set up, but you can add/remove your own files in the config file.
|
||||
@@ -122,8 +122,8 @@ php artisan ide-helper:models Post
|
||||
* @property integer $author_id
|
||||
* @property string $title
|
||||
* @property string $text
|
||||
* @property \Carbon\Carbon $created_at
|
||||
* @property \Carbon\Carbon $updated_at
|
||||
* @property \Illuminate\Support\Carbon $created_at
|
||||
* @property \Illuminate\Support\Carbon $updated_at
|
||||
* @property-read \User $author
|
||||
* @property-read \Illuminate\Database\Eloquent\Collection|\Comment[] $comments
|
||||
*/
|
||||
@@ -149,18 +149,24 @@ Models can be ignored using the `--ignore (-I)` option
|
||||
php artisan ide-helper:models --ignore="Post,User"
|
||||
```
|
||||
|
||||
Note: With namespaces, wrap your model name in " signs: `php artisan ide-helper:models "API\User"`, or escape the slashes (`Api\\User`)
|
||||
Note: With namespaces, wrap your model name in double-quotes (`"`): `php artisan ide-helper:models "API\User"`, or escape the slashes (`Api\\User`)
|
||||
|
||||
For properly recognition of `Model` methods (i.e. `paginate`, `findOrFail`) you should extend `\Eloquent` or add
|
||||
```php
|
||||
/** @mixin \Eloquent */
|
||||
```
|
||||
for your model class.
|
||||
|
||||
### Automatic phpDocs generation for Laravel Fluent methods
|
||||
If you need phpDocs support for Fluent methods in migration, for example
|
||||
```php
|
||||
$table->string(“somestring”)->nullable()->index();
|
||||
$table->string("somestring")->nullable()->index();
|
||||
```
|
||||
After publishing vendor, simply change the `include_fluent` line your `config/ide-helper.php` file into:
|
||||
```php
|
||||
'include_fluent' => true,
|
||||
```
|
||||
And then run `php artisan ide-helper:generate` , you will now see all of the Fluent methods are recognized by your IDE now.
|
||||
And then run `php artisan ide-helper:generate` , you will now see all of the Fluent methods are recognized by your IDE.
|
||||
|
||||
|
||||
## PhpStorm Meta for Container instances
|
||||
|
||||
+32
-20
@@ -1,67 +1,78 @@
|
||||
<?= '<?php' ?>
|
||||
<?php
|
||||
/**
|
||||
* @var \Barryvdh\LaravelIdeHelper\Alias[][] $namespaces_by_alias_ns
|
||||
* @var \Barryvdh\LaravelIdeHelper\Alias[][] $namespaces_by_extends_ns
|
||||
* @var bool $include_fluent
|
||||
* @var string $helpers
|
||||
*/
|
||||
?>
|
||||
|
||||
// @formatter:off
|
||||
|
||||
/**
|
||||
* A helper file for Laravel 5, to provide autocomplete information to your IDE
|
||||
* Generated for Laravel <?= $version ?> on <?= date("Y-m-d") ?>.
|
||||
* Generated for Laravel <?= $version ?> on <?= date("Y-m-d H:i:s") ?>.
|
||||
*
|
||||
* This file should not be included in your code, only analyzed by your IDE!
|
||||
*
|
||||
* @author Barry vd. Heuvel <[email protected]>
|
||||
* @see https://github.com/barryvdh/laravel-ide-helper
|
||||
*/
|
||||
namespace {
|
||||
exit("This file should not be included, only analyzed by your IDE");
|
||||
}
|
||||
|
||||
<?php foreach($namespaces as $namespace => $aliases): ?>
|
||||
<?php foreach($namespaces_by_extends_ns as $namespace => $aliases): ?>
|
||||
<?php if ($namespace == '\Illuminate\Database\Eloquent'): continue; endif; ?>
|
||||
namespace <?= $namespace == '__root' ? '' : trim($namespace, '\\') ?> {
|
||||
<?php foreach($aliases as $alias): ?>
|
||||
|
||||
<?= trim($alias->getDocComment(' ')) ?>
|
||||
<?= $alias->getClassType() ?> <?= $alias->getExtendsClass() ?> {
|
||||
<?php foreach($alias->getMethods() as $method): ?>
|
||||
|
||||
<?= trim($method->getDocComment(' ')) ?>
|
||||
|
||||
public static function <?= $method->getName() ?>(<?= $method->getParamsWithDefault() ?>)
|
||||
{<?php if($method->getDeclaringClass() !== $method->getRoot()): ?>
|
||||
|
||||
//Method inherited from <?= $method->getDeclaringClass() ?>
|
||||
<?php endif; ?>
|
||||
|
||||
<?= $method->shouldReturn() ? 'return ': '' ?><?= $method->getRoot() ?>::<?= $method->getName() ?>(<?= $method->getParams() ?>);
|
||||
<?= $method->shouldReturn() ? 'return ': '' ?><?= $method->getRoot() ?>::<?= $method->getRealName() ?>(<?= $method->getParams() ?>);
|
||||
}
|
||||
<?php endforeach; ?>
|
||||
|
||||
}
|
||||
<?php endforeach; ?>
|
||||
}
|
||||
|
||||
<?php endforeach; ?>
|
||||
|
||||
namespace {
|
||||
<?= $helpers ?>
|
||||
|
||||
<?php foreach($namespaces as $namespace => $aliases): ?>
|
||||
<?php foreach($namespaces_by_alias_ns as $namespace => $aliases): ?>
|
||||
namespace <?= $namespace == '__root' ? '' : trim($namespace, '\\') ?> {
|
||||
<?php foreach($aliases as $alias): ?>
|
||||
<?= $alias->getClassType() ?> <?= $alias->getShortName() ?> extends <?= $alias->getExtends() ?> {<?php if ($namespace == '\Illuminate\Database\Eloquent'): ?>
|
||||
|
||||
<?= $alias->getClassType() ?> <?= $alias->getShortName() ?> extends <?= $alias->getExtends() ?> {<?php if ($alias->getExtendsNamespace() == '\Illuminate\Database\Eloquent'): ?>
|
||||
<?php foreach($alias->getMethods() as $method): ?>
|
||||
|
||||
<?= trim($method->getDocComment(' ')) ?>
|
||||
|
||||
public static function <?= $method->getName() ?>(<?= $method->getParamsWithDefault() ?>)
|
||||
{<?php if($method->getDeclaringClass() !== $method->getRoot()): ?>
|
||||
|
||||
//Method inherited from <?= $method->getDeclaringClass() ?>
|
||||
<?php endif; ?>
|
||||
|
||||
<?= $method->shouldReturn() ? 'return ': '' ?><?= $method->getRoot() ?>::<?= $method->getName() ?>(<?= $method->getParams() ?>);
|
||||
<?= $method->shouldReturn() ? 'return ': '' ?><?= $method->getRoot() ?>::<?= $method->getRealName() ?>(<?= $method->getParams() ?>);
|
||||
}
|
||||
<?php endforeach; ?>
|
||||
<?php endif; ?>}
|
||||
|
||||
<?php endforeach; ?>
|
||||
<?php endforeach; ?>
|
||||
}
|
||||
|
||||
<?php endforeach; ?>
|
||||
|
||||
<?php if($helpers): ?>
|
||||
namespace {
|
||||
<?= $helpers ?>
|
||||
}
|
||||
<?php endif; ?>
|
||||
|
||||
<?php if($include_fluent): ?>
|
||||
namespace Illuminate\Support {
|
||||
/**
|
||||
@@ -71,7 +82,7 @@ namespace Illuminate\Support {
|
||||
* @method Fluent charset(string $charset) Add the character set modifier
|
||||
* @method Fluent collation(string $collation) Add the collation modifier
|
||||
* @method Fluent comment(string $comment) Add comment
|
||||
* @method Fluent default(mixed $value) Add the default modifier
|
||||
* @method Fluent default($value) Add the default modifier
|
||||
* @method Fluent first() Select first row
|
||||
* @method Fluent index(string $name = null) Add the in dex clause
|
||||
* @method Fluent on(string $table) `on` of a foreign key
|
||||
@@ -79,10 +90,11 @@ namespace Illuminate\Support {
|
||||
* @method Fluent onUpdate(string $action) `on update` of a foreign key
|
||||
* @method Fluent primary() Add the primary key modifier
|
||||
* @method Fluent references(string $column) `references` of a foreign key
|
||||
* @method Fluent nullable() Add the nullable modifier
|
||||
* @method Fluent nullable(bool $value = true) Add the nullable modifier
|
||||
* @method Fluent unique(string $name = null) Add unique index clause
|
||||
* @method Fluent unsigned() Add the unsigned modifier
|
||||
* @method Fluent useCurrent() Add the default timestamp value
|
||||
* @method Fluent change() Add the change modifier
|
||||
*/
|
||||
class Fluent {}
|
||||
}
|
||||
|
||||
@@ -1,21 +1,53 @@
|
||||
<?= '<?php' ?>
|
||||
|
||||
// @formatter:off
|
||||
|
||||
namespace PHPSTORM_META {
|
||||
|
||||
/**
|
||||
* PhpStorm Meta file, to provide autocomplete information for PhpStorm
|
||||
* Generated on <?= date("Y-m-d") ?>.
|
||||
* Generated on <?= date("Y-m-d H:i:s") ?>.
|
||||
*
|
||||
* @author Barry vd. Heuvel <[email protected]>
|
||||
* @see https://github.com/barryvdh/laravel-ide-helper
|
||||
*/
|
||||
$STATIC_METHOD_TYPES = [
|
||||
<?php foreach ($methods as $method): ?>
|
||||
<?= $method ?> => [
|
||||
'' == '@',
|
||||
override(<?= $method ?>, map([
|
||||
'' => '@',
|
||||
<?php foreach($bindings as $abstract => $class): ?>
|
||||
'<?= $abstract ?>' instanceof \<?= $class ?>,
|
||||
<?php endforeach ?> ],
|
||||
<?php endforeach ?>
|
||||
];
|
||||
'<?= $abstract ?>' => \<?= $class ?>::class,
|
||||
<?php endforeach; ?>
|
||||
]));
|
||||
<?php endforeach; ?>
|
||||
|
||||
override(\Illuminate\Support\Arr::add(0), type(0));
|
||||
override(\Illuminate\Support\Arr::except(0), type(0));
|
||||
override(\Illuminate\Support\Arr::first(0), elementType(0));
|
||||
override(\Illuminate\Support\Arr::last(0), elementType(0));
|
||||
override(\Illuminate\Support\Arr::get(0), elementType(0));
|
||||
override(\Illuminate\Support\Arr::only(0), type(0));
|
||||
override(\Illuminate\Support\Arr::prepend(0), type(0));
|
||||
override(\Illuminate\Support\Arr::pull(0), elementType(0));
|
||||
override(\Illuminate\Support\Arr::set(0), type(0));
|
||||
override(\Illuminate\Support\Arr::shuffle(0), type(0));
|
||||
override(\Illuminate\Support\Arr::sort(0), type(0));
|
||||
override(\Illuminate\Support\Arr::sortRecursive(0), type(0));
|
||||
override(\Illuminate\Support\Arr::where(0), type(0));
|
||||
override(\array_add(0), type(0));
|
||||
override(\array_except(0), type(0));
|
||||
override(\array_first(0), elementType(0));
|
||||
override(\array_last(0), elementType(0));
|
||||
override(\array_get(0), elementType(0));
|
||||
override(\array_only(0), type(0));
|
||||
override(\array_prepend(0), type(0));
|
||||
override(\array_pull(0), elementType(0));
|
||||
override(\array_set(0), type(0));
|
||||
override(\array_sort(0), type(0));
|
||||
override(\array_sort_recursive(0), type(0));
|
||||
override(\array_where(0), type(0));
|
||||
override(\head(0), elementType(0));
|
||||
override(\last(0), elementType(0));
|
||||
override(\with(0), type(0));
|
||||
override(\tap(0), type(0));
|
||||
|
||||
}
|
||||
|
||||
+88
-2
@@ -10,6 +10,11 @@
|
||||
|
||||
namespace Barryvdh\LaravelIdeHelper;
|
||||
|
||||
use Barryvdh\Reflection\DocBlock;
|
||||
use Barryvdh\Reflection\DocBlock\Context;
|
||||
use Barryvdh\Reflection\DocBlock\Serializer as DocBlockSerializer;
|
||||
use ReflectionClass;
|
||||
|
||||
class Alias
|
||||
{
|
||||
protected $alias;
|
||||
@@ -27,6 +32,7 @@ class Alias
|
||||
protected $valid = false;
|
||||
protected $magicMethods = array();
|
||||
protected $interfaces = array();
|
||||
protected $phpdoc = null;
|
||||
|
||||
/**
|
||||
* @param string $alias
|
||||
@@ -53,10 +59,17 @@ class Alias
|
||||
}
|
||||
|
||||
$this->addClass($this->root);
|
||||
$this->detectFake();
|
||||
$this->detectNamespace();
|
||||
$this->detectClassType();
|
||||
$this->detectExtendsNamespace();
|
||||
|
||||
if (!empty($this->namespace)) {
|
||||
//Create a DocBlock and serializer instance
|
||||
$this->phpdoc = new DocBlock(new ReflectionClass($alias), new Context($this->namespace));
|
||||
}
|
||||
|
||||
|
||||
if ($facade === '\Illuminate\Database\Eloquent\Model') {
|
||||
$this->usedMethods = array('decrement', 'increment');
|
||||
}
|
||||
@@ -158,7 +171,7 @@ class Alias
|
||||
/**
|
||||
* Get the methods found by this Alias
|
||||
*
|
||||
* @return array
|
||||
* @return array|Method[]
|
||||
*/
|
||||
public function getMethods()
|
||||
{
|
||||
@@ -167,6 +180,30 @@ class Alias
|
||||
return $this->methods;
|
||||
}
|
||||
|
||||
/**
|
||||
* Detect class returned by ::fake()
|
||||
*/
|
||||
protected function detectFake()
|
||||
{
|
||||
$facade = $this->facade;
|
||||
|
||||
if (!method_exists($facade, 'fake')) {
|
||||
return;
|
||||
}
|
||||
|
||||
$real = $facade::getFacadeRoot();
|
||||
|
||||
try {
|
||||
$facade::fake();
|
||||
$fake = $facade::getFacadeRoot();
|
||||
if ($fake !== $real) {
|
||||
$this->addClass(get_class($fake));
|
||||
}
|
||||
} finally {
|
||||
$facade::swap($real);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Detect the namespace
|
||||
*/
|
||||
@@ -273,7 +310,7 @@ class Alias
|
||||
$method = new \ReflectionMethod($className, $name);
|
||||
$class = new \ReflectionClass($className);
|
||||
|
||||
if (!in_array($method->name, $this->usedMethods)) {
|
||||
if (!in_array($magic, $this->usedMethods)) {
|
||||
if ($class !== $this->root) {
|
||||
$this->methods[] = new Method($method, $this->alias, $class, $magic, $this->interfaces);
|
||||
}
|
||||
@@ -312,8 +349,57 @@ class Alias
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Check if the class is macroable
|
||||
$traits = collect($reflection->getTraitNames());
|
||||
if ($traits->contains('Illuminate\Support\Traits\Macroable')) {
|
||||
$properties = $reflection->getStaticProperties();
|
||||
$macros = isset($properties['macros']) ? $properties['macros'] : [];
|
||||
foreach ($macros as $macro_name => $macro_func) {
|
||||
// Add macros
|
||||
$this->methods[] = new Macro(
|
||||
$this->getMacroFunction($macro_func),
|
||||
$this->alias,
|
||||
$reflection,
|
||||
$macro_name,
|
||||
$this->interfaces
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param $macro_func
|
||||
*
|
||||
* @return \ReflectionFunctionAbstract
|
||||
* @throws \ReflectionException
|
||||
*/
|
||||
protected function getMacroFunction($macro_func)
|
||||
{
|
||||
if (is_array($macro_func) && is_callable($macro_func)) {
|
||||
return new \ReflectionMethod($macro_func[0], $macro_func[1]);
|
||||
}
|
||||
|
||||
return new \ReflectionFunction($macro_func);
|
||||
}
|
||||
|
||||
/*
|
||||
* Get the docblock for this alias
|
||||
*
|
||||
* @param string $prefix
|
||||
* @return mixed
|
||||
*/
|
||||
public function getDocComment($prefix = "\t\t")
|
||||
{
|
||||
$serializer = new DocBlockSerializer(1, $prefix);
|
||||
|
||||
if ($this->phpdoc) {
|
||||
return $serializer->getDocComment($this->phpdoc);
|
||||
}
|
||||
|
||||
return '';
|
||||
}
|
||||
|
||||
/**
|
||||
* Output an error.
|
||||
|
||||
@@ -0,0 +1,61 @@
|
||||
<?php
|
||||
/**
|
||||
* Laravel IDE Helper Generator - Eloquent Model Mixin
|
||||
*
|
||||
* @author Charles A. Peterson <[email protected]>
|
||||
* @copyright 2017 Charles A. Peterson / Fruitcake Studio (http://www.fruitcakestudio.nl)
|
||||
* @license http://www.opensource.org/licenses/mit-license.php MIT
|
||||
* @link https://github.com/barryvdh/laravel-ide-helper
|
||||
*/
|
||||
|
||||
namespace Barryvdh\LaravelIdeHelper\Console;
|
||||
|
||||
use Barryvdh\LaravelIdeHelper\Eloquent;
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Filesystem\Filesystem;
|
||||
|
||||
/**
|
||||
* A command to add \Eloquent mixin to Eloquent\Model
|
||||
*
|
||||
* @author Charles A. Peterson <[email protected]>
|
||||
*/
|
||||
class EloquentCommand extends Command
|
||||
{
|
||||
/**
|
||||
* The console command name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $name = 'ide-helper:eloquent';
|
||||
|
||||
/**
|
||||
* @var Filesystem $files
|
||||
*/
|
||||
protected $files;
|
||||
|
||||
/**
|
||||
* The console command description.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $description = 'Add \Eloquent helper to \Eloquent\Model';
|
||||
|
||||
/**
|
||||
* @param Filesystem $files
|
||||
*/
|
||||
public function __construct(Filesystem $files)
|
||||
{
|
||||
parent::__construct();
|
||||
$this->files = $files;
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute the console command.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function handle()
|
||||
{
|
||||
Eloquent::writeEloquentModelHelper($this, $this->files);
|
||||
}
|
||||
}
|
||||
@@ -10,8 +10,8 @@
|
||||
|
||||
namespace Barryvdh\LaravelIdeHelper\Console;
|
||||
|
||||
use Barryvdh\LaravelIdeHelper\Eloquent;
|
||||
use Barryvdh\LaravelIdeHelper\Generator;
|
||||
use Illuminate\Config\Repository as ConfigRepository;
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Filesystem\Filesystem;
|
||||
use Symfony\Component\Console\Input\InputOption;
|
||||
@@ -74,7 +74,7 @@ class GeneratorCommand extends Command
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function fire()
|
||||
public function handle()
|
||||
{
|
||||
if (file_exists(base_path() . '/vendor/compiled.php') ||
|
||||
file_exists(base_path() . '/bootstrap/cache/compiled.php') ||
|
||||
|
||||
@@ -28,7 +28,6 @@ class MetaCommand extends Command
|
||||
* @var string
|
||||
*/
|
||||
protected $name = 'ide-helper:meta';
|
||||
protected $filename = '.phpstorm.meta.php';
|
||||
|
||||
/**
|
||||
* The console command description.
|
||||
@@ -43,22 +42,30 @@ class MetaCommand extends Command
|
||||
/** @var \Illuminate\Contracts\View\Factory */
|
||||
protected $view;
|
||||
|
||||
/** @var \Illuminate\Contracts\Config */
|
||||
protected $config;
|
||||
|
||||
protected $methods = [
|
||||
'new \Illuminate\Contracts\Container\Container',
|
||||
'\Illuminate\Contracts\Container\Container::make(\'\')',
|
||||
'\App::make(\'\')',
|
||||
'\app(\'\')',
|
||||
'\Illuminate\Contracts\Container\Container::make(0)',
|
||||
'\Illuminate\Contracts\Container\Container::makeWith(0)',
|
||||
'\App::make(0)',
|
||||
'\App::makeWith(0)',
|
||||
'\app(0)',
|
||||
'\resolve(0)',
|
||||
];
|
||||
|
||||
/**
|
||||
*
|
||||
* @param \Illuminate\Contracts\Filesystem\Filesystem $files
|
||||
* @param \Illuminate\Contracts\View\Factory $view
|
||||
* @param \Illuminate\Contracts\Config $config
|
||||
*/
|
||||
public function __construct($files, $view)
|
||||
public function __construct($files, $view, $config)
|
||||
{
|
||||
$this->files = $files;
|
||||
$this->view = $view;
|
||||
$this->config = $config;
|
||||
parent::__construct();
|
||||
}
|
||||
|
||||
@@ -67,7 +74,7 @@ class MetaCommand extends Command
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function fire()
|
||||
public function handle()
|
||||
{
|
||||
$this->registerClassAutoloadExceptions();
|
||||
|
||||
@@ -90,7 +97,7 @@ class MetaCommand extends Command
|
||||
}
|
||||
}
|
||||
|
||||
$content = $this->view->make('ide-helper::meta', [
|
||||
$content = $this->view->make('meta', [
|
||||
'bindings' => $bindings,
|
||||
'methods' => $this->methods,
|
||||
])->render();
|
||||
@@ -115,7 +122,11 @@ class MetaCommand extends Command
|
||||
$abstracts = $this->laravel->getBindings();
|
||||
|
||||
// Return the abstract names only
|
||||
return array_keys($abstracts);
|
||||
$keys = array_keys($abstracts);
|
||||
|
||||
sort($keys);
|
||||
|
||||
return $keys;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -135,8 +146,10 @@ class MetaCommand extends Command
|
||||
*/
|
||||
protected function getOptions()
|
||||
{
|
||||
$filename = $this->config->get('ide-helper.meta_filename');
|
||||
|
||||
return array(
|
||||
array('filename', 'F', InputOption::VALUE_OPTIONAL, 'The path to the meta file', $this->filename),
|
||||
array('filename', 'F', InputOption::VALUE_OPTIONAL, 'The path to the meta file', $filename),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
+141
-22
@@ -10,14 +10,15 @@
|
||||
|
||||
namespace Barryvdh\LaravelIdeHelper\Console;
|
||||
|
||||
use Composer\Autoload\ClassMapGenerator;
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Database\Eloquent\Relations\Relation;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Filesystem\Filesystem;
|
||||
use ReflectionClass;
|
||||
use Symfony\Component\Console\Input\InputOption;
|
||||
use Symfony\Component\Console\Input\InputArgument;
|
||||
use Symfony\Component\Console\Output\OutputInterface;
|
||||
use Symfony\Component\ClassLoader\ClassMapGenerator;
|
||||
use Barryvdh\Reflection\DocBlock;
|
||||
use Barryvdh\Reflection\DocBlock\Context;
|
||||
use Barryvdh\Reflection\DocBlock\Tag;
|
||||
@@ -50,11 +51,17 @@ class ModelsCommand extends Command
|
||||
*/
|
||||
protected $description = 'Generate autocompletion for models';
|
||||
|
||||
protected $write_model_magic_where;
|
||||
protected $properties = array();
|
||||
protected $methods = array();
|
||||
protected $write = false;
|
||||
protected $dirs = array();
|
||||
protected $reset;
|
||||
protected $keep_text;
|
||||
/**
|
||||
* @var bool[string]
|
||||
*/
|
||||
protected $nullableColumns = [];
|
||||
|
||||
/**
|
||||
* @param Filesystem $files
|
||||
@@ -70,7 +77,7 @@ class ModelsCommand extends Command
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function fire()
|
||||
public function handle()
|
||||
{
|
||||
$filename = $this->option('filename');
|
||||
$this->write = $this->option('write');
|
||||
@@ -81,11 +88,15 @@ class ModelsCommand extends Command
|
||||
$model = $this->argument('model');
|
||||
$ignore = $this->option('ignore');
|
||||
$this->reset = $this->option('reset');
|
||||
if ($this->option('smart-reset')) {
|
||||
$this->keep_text = $this->reset = true;
|
||||
}
|
||||
$this->write_model_magic_where = $this->laravel['config']->get('ide-helper.write_model_magic_where', true);
|
||||
|
||||
//If filename is default and Write is not specified, ask what to do
|
||||
if (!$this->write && $filename === $this->filename && !$this->option('nowrite')) {
|
||||
if ($this->confirm(
|
||||
"Do you want to overwrite the existing model files? Choose no to write to $filename instead? (Yes/No): "
|
||||
"Do you want to overwrite the existing model files? Choose no to write to $filename instead?"
|
||||
)
|
||||
) {
|
||||
$this->write = true;
|
||||
@@ -130,6 +141,7 @@ class ModelsCommand extends Command
|
||||
array('write', 'W', InputOption::VALUE_NONE, 'Write to Model file'),
|
||||
array('nowrite', 'N', InputOption::VALUE_NONE, 'Don\'t write to Model file'),
|
||||
array('reset', 'R', InputOption::VALUE_NONE, 'Remove the original phpdocs instead of appending'),
|
||||
array('smart-reset', 'r', InputOption::VALUE_NONE, 'Refresh the properties/methods list, but keep the text'),
|
||||
array('ignore', 'I', InputOption::VALUE_OPTIONAL, 'Which models to ignore', ''),
|
||||
);
|
||||
}
|
||||
@@ -139,6 +151,8 @@ class ModelsCommand extends Command
|
||||
|
||||
|
||||
$output = "<?php
|
||||
|
||||
// @formatter:off
|
||||
/**
|
||||
* A helper file for your Eloquent Models
|
||||
* Copy the phpDocs from this file to the correct Model,
|
||||
@@ -173,10 +187,9 @@ class ModelsCommand extends Command
|
||||
if (class_exists($name)) {
|
||||
try {
|
||||
// handle abstract classes, interfaces, ...
|
||||
$reflectionClass = new \ReflectionClass($name);
|
||||
$reflectionClass = new ReflectionClass($name);
|
||||
|
||||
if (!$reflectionClass->isSubclassOf('Illuminate\Database\Eloquent\Model')
|
||||
|| $reflectionClass->isSubclassOf('Illuminate\Database\Eloquent\Relations\Pivot')) {
|
||||
if (!$reflectionClass->isSubclassOf('Illuminate\Database\Eloquent\Model')) {
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -200,8 +213,10 @@ class ModelsCommand extends Command
|
||||
}
|
||||
|
||||
$this->getPropertiesFromMethods($model);
|
||||
$this->getSoftDeleteMethods($model);
|
||||
$output .= $this->createPhpDocs($name);
|
||||
$ignore[] = $name;
|
||||
$this->nullableColumns = [];
|
||||
} catch (\Exception $e) {
|
||||
$this->error("Exception: " . $e->getMessage() . "\nCould not analyze class $name.");
|
||||
}
|
||||
@@ -269,7 +284,7 @@ class ModelsCommand extends Command
|
||||
break;
|
||||
case 'date':
|
||||
case 'datetime':
|
||||
$realType = '\Carbon\Carbon';
|
||||
$realType = '\Illuminate\Support\Carbon';
|
||||
break;
|
||||
case 'collection':
|
||||
$realType = '\Illuminate\Support\Collection';
|
||||
@@ -283,6 +298,10 @@ class ModelsCommand extends Command
|
||||
continue;
|
||||
} else {
|
||||
$this->properties[$name]['type'] = $this->getTypeOverride($realType);
|
||||
|
||||
if (isset($this->nullableColumns[$name])) {
|
||||
$this->properties[$name]['type'] .= '|null';
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -329,7 +348,7 @@ class ModelsCommand extends Command
|
||||
foreach ($columns as $column) {
|
||||
$name = $column->getName();
|
||||
if (in_array($name, $model->getDates())) {
|
||||
$type = '\Carbon\Carbon';
|
||||
$type = '\Illuminate\Support\Carbon';
|
||||
} else {
|
||||
$type = $column->getType()->getName();
|
||||
switch ($type) {
|
||||
@@ -347,13 +366,21 @@ class ModelsCommand extends Command
|
||||
case 'smallint':
|
||||
$type = 'integer';
|
||||
break;
|
||||
case 'boolean':
|
||||
switch (config('database.default')) {
|
||||
case 'sqlite':
|
||||
case 'mysql':
|
||||
$type = 'integer';
|
||||
break;
|
||||
default:
|
||||
$type = 'boolean';
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 'decimal':
|
||||
case 'float':
|
||||
$type = 'float';
|
||||
break;
|
||||
case 'boolean':
|
||||
$type = 'boolean';
|
||||
break;
|
||||
default:
|
||||
$type = 'mixed';
|
||||
break;
|
||||
@@ -361,15 +388,20 @@ class ModelsCommand extends Command
|
||||
}
|
||||
|
||||
$comment = $column->getComment();
|
||||
$this->setProperty($name, $type, true, true, $comment);
|
||||
if (!$column->getNotnull()) {
|
||||
$this->nullableColumns[$name] = true;
|
||||
}
|
||||
$this->setProperty($name, $type, true, true, $comment, !$column->getNotnull());
|
||||
if ($this->write_model_magic_where) {
|
||||
$this->setMethod(
|
||||
Str::camel("where_" . $name),
|
||||
'\Illuminate\Database\Query\Builder|\\' . get_class($model),
|
||||
'\Illuminate\Database\Eloquent\Builder|\\' . get_class($model),
|
||||
array('$value')
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param \Illuminate\Database\Eloquent\Model $model
|
||||
@@ -410,8 +442,11 @@ class ModelsCommand extends Command
|
||||
$args = $this->getParameters($reflection);
|
||||
//Remove the first ($query) argument
|
||||
array_shift($args);
|
||||
$this->setMethod($name, '\Illuminate\Database\Query\Builder|\\' . $reflection->class, $args);
|
||||
$this->setMethod($name, '\Illuminate\Database\Eloquent\Builder|\\' . $reflection->class, $args);
|
||||
}
|
||||
} elseif (in_array($method, ['query', 'newQuery', 'newModelQuery'])) {
|
||||
$reflection = new \ReflectionClass($model);
|
||||
$this->setMethod($method, '\Illuminate\Database\Eloquent\Builder|\\' . $reflection->getName());
|
||||
} elseif (!method_exists('Illuminate\Database\Eloquent\Model', $method)
|
||||
&& !Str::startsWith($method, 'get')
|
||||
) {
|
||||
@@ -439,17 +474,30 @@ class ModelsCommand extends Command
|
||||
'morphOne',
|
||||
'morphTo',
|
||||
'morphMany',
|
||||
'morphToMany'
|
||||
'morphToMany',
|
||||
'morphedByMany'
|
||||
) as $relation) {
|
||||
$search = '$this->' . $relation . '(';
|
||||
if ($pos = stripos($code, $search)) {
|
||||
//Resolve the relation's model to a Relation object.
|
||||
$methodReflection = new \ReflectionMethod($model, $method);
|
||||
if ($methodReflection->getNumberOfParameters()) {
|
||||
return;
|
||||
}
|
||||
|
||||
$relationObj = $model->$method();
|
||||
|
||||
if ($relationObj instanceof Relation) {
|
||||
$relatedModel = '\\' . get_class($relationObj->getRelated());
|
||||
|
||||
$relations = ['hasManyThrough', 'belongsToMany', 'hasMany', 'morphMany', 'morphToMany'];
|
||||
$relations = [
|
||||
'hasManyThrough',
|
||||
'belongsToMany',
|
||||
'hasMany',
|
||||
'morphMany',
|
||||
'morphToMany',
|
||||
'morphedByMany',
|
||||
];
|
||||
if (in_array($relation, $relations)) {
|
||||
//Collection or array of models (because Collection is Arrayable)
|
||||
$this->setProperty(
|
||||
@@ -468,7 +516,14 @@ class ModelsCommand extends Command
|
||||
);
|
||||
} else {
|
||||
//Single model is returned
|
||||
$this->setProperty($method, $relatedModel, true, null);
|
||||
$this->setProperty(
|
||||
$method,
|
||||
$relatedModel,
|
||||
true,
|
||||
null,
|
||||
'',
|
||||
$this->isRelationForeignKeyNullable($relationObj)
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -478,14 +533,34 @@ class ModelsCommand extends Command
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the foreign key of the relation is nullable
|
||||
*
|
||||
* @param Relation $relation
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
private function isRelationForeignKeyNullable(Relation $relation)
|
||||
{
|
||||
$reflectionObj = new \ReflectionObject($relation);
|
||||
if (!$reflectionObj->hasProperty('foreignKey')) {
|
||||
return false;
|
||||
}
|
||||
$fkProp = $reflectionObj->getProperty('foreignKey');
|
||||
$fkProp->setAccessible(true);
|
||||
|
||||
return isset($this->nullableColumns[$fkProp->getValue($relation)]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param string $name
|
||||
* @param string|null $type
|
||||
* @param bool|null $read
|
||||
* @param bool|null $write
|
||||
* @param string|null $comment
|
||||
* @param bool $nullable
|
||||
*/
|
||||
protected function setProperty($name, $type = null, $read = null, $write = null, $comment = '')
|
||||
protected function setProperty($name, $type = null, $read = null, $write = null, $comment = '', $nullable = false)
|
||||
{
|
||||
if (!isset($this->properties[$name])) {
|
||||
$this->properties[$name] = array();
|
||||
@@ -495,7 +570,11 @@ class ModelsCommand extends Command
|
||||
$this->properties[$name]['comment'] = (string) $comment;
|
||||
}
|
||||
if ($type !== null) {
|
||||
$this->properties[$name]['type'] = $this->getTypeOverride($type);
|
||||
$newType = $this->getTypeOverride($type);
|
||||
if ($nullable) {
|
||||
$newType .='|null';
|
||||
}
|
||||
$this->properties[$name]['type'] = $newType;
|
||||
}
|
||||
if ($read !== null) {
|
||||
$this->properties[$name]['read'] = $read;
|
||||
@@ -523,13 +602,19 @@ class ModelsCommand extends Command
|
||||
protected function createPhpDocs($class)
|
||||
{
|
||||
|
||||
$reflection = new \ReflectionClass($class);
|
||||
$reflection = new ReflectionClass($class);
|
||||
$namespace = $reflection->getNamespaceName();
|
||||
$classname = $reflection->getShortName();
|
||||
$originalDoc = $reflection->getDocComment();
|
||||
$keyword = $this->getClassKeyword($reflection);
|
||||
|
||||
if ($this->reset) {
|
||||
$phpdoc = new DocBlock('', new Context($namespace));
|
||||
if ($this->keep_text) {
|
||||
$phpdoc->setText(
|
||||
(new DocBlock($reflection, new Context($namespace)))->getText()
|
||||
);
|
||||
}
|
||||
} else {
|
||||
$phpdoc = new DocBlock($reflection, new Context($namespace));
|
||||
}
|
||||
@@ -609,7 +694,7 @@ class ModelsCommand extends Command
|
||||
}
|
||||
}
|
||||
|
||||
$output = "namespace {$namespace}{\n{$docComment}\n\tclass {$classname} extends \Eloquent {}\n}\n\n";
|
||||
$output = "namespace {$namespace}{\n{$docComment}\n\t{$keyword}class {$classname} extends \Eloquent {}\n}\n\n";
|
||||
return $output;
|
||||
}
|
||||
|
||||
@@ -690,9 +775,43 @@ class ModelsCommand extends Command
|
||||
$phpdoc = new DocBlock($reflection);
|
||||
|
||||
if ($phpdoc->hasTag('return')) {
|
||||
$type = $phpdoc->getTagsByName('return')[0]->getContent();
|
||||
$type = $phpdoc->getTagsByName('return')[0]->getType();
|
||||
}
|
||||
|
||||
return $type;
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates methods provided by the SoftDeletes trait
|
||||
* @param \Illuminate\Database\Eloquent\Model $model
|
||||
*/
|
||||
protected function getSoftDeleteMethods($model)
|
||||
{
|
||||
$traits = class_uses(get_class($model), true);
|
||||
if (in_array('Illuminate\\Database\\Eloquent\\SoftDeletes', $traits)) {
|
||||
$this->setMethod('forceDelete', 'bool|null', []);
|
||||
$this->setMethod('restore', 'bool|null', []);
|
||||
|
||||
$this->setMethod('withTrashed', '\Illuminate\Database\Query\Builder|\\' . get_class($model), []);
|
||||
$this->setMethod('withoutTrashed', '\Illuminate\Database\Query\Builder|\\' . get_class($model), []);
|
||||
$this->setMethod('onlyTrashed', '\Illuminate\Database\Query\Builder|\\' . get_class($model), []);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param ReflectionClass $reflection
|
||||
* @return string
|
||||
*/
|
||||
private function getClassKeyword(ReflectionClass $reflection)
|
||||
{
|
||||
if ($reflection->isFinal()) {
|
||||
$keyword = 'final ';
|
||||
} elseif ($reflection->isAbstract()) {
|
||||
$keyword = 'abstract ';
|
||||
} else {
|
||||
$keyword = '';
|
||||
}
|
||||
|
||||
return $keyword;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,78 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
* Laravel IDE Helper to add \Eloquent mixin to Eloquent\Model
|
||||
*
|
||||
* @author Charles A. Peterson <[email protected]>
|
||||
*/
|
||||
namespace Barryvdh\LaravelIdeHelper;
|
||||
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Filesystem\Filesystem;
|
||||
use Barryvdh\Reflection\DocBlock;
|
||||
use Barryvdh\Reflection\DocBlock\Context;
|
||||
use Barryvdh\Reflection\DocBlock\Serializer as DocBlockSerializer;
|
||||
use Barryvdh\Reflection\DocBlock\Tag;
|
||||
|
||||
class Eloquent
|
||||
{
|
||||
/**
|
||||
* Write mixin helper to the Eloquent\Model
|
||||
* This is needed since laravel/framework v5.4.29
|
||||
*
|
||||
* @param Command $command
|
||||
* @param Filesystem $files
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public static function writeEloquentModelHelper(Command $command, Filesystem $files)
|
||||
{
|
||||
$class = 'Illuminate\Database\Eloquent\Model';
|
||||
|
||||
$reflection = new \ReflectionClass($class);
|
||||
$namespace = $reflection->getNamespaceName();
|
||||
$originalDoc = $reflection->getDocComment();
|
||||
if (!$originalDoc) {
|
||||
$command->info('Unexpected no document on ' . $class);
|
||||
}
|
||||
$phpdoc = new DocBlock($reflection, new Context($namespace));
|
||||
|
||||
$mixins = $phpdoc->getTagsByName('mixin');
|
||||
foreach ($mixins as $m) {
|
||||
if ($m->getContent() === '\Eloquent') {
|
||||
$command->info('Tag Exists: @mixin \Eloquent in ' . $class);
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// add the Eloquent mixin
|
||||
$phpdoc->appendTag(Tag::createInstance("@mixin \\Eloquent", $phpdoc));
|
||||
|
||||
$serializer = new DocBlockSerializer();
|
||||
$serializer->getDocComment($phpdoc);
|
||||
$docComment = $serializer->getDocComment($phpdoc);
|
||||
|
||||
$filename = $reflection->getFileName();
|
||||
if ($filename) {
|
||||
$contents = $files->get($filename);
|
||||
if ($contents) {
|
||||
$count = 0;
|
||||
$contents = str_replace($originalDoc, $docComment, $contents, $count);
|
||||
if ($count > 0) {
|
||||
if ($files->put($filename, $contents)) {
|
||||
$command->info('Wrote @mixin \Eloquent to ' . $filename);
|
||||
} else {
|
||||
$command->error('File write failed to ' . $filename);
|
||||
}
|
||||
} else {
|
||||
$command->error('Content did not change ' . $contents);
|
||||
}
|
||||
} else {
|
||||
$command->error('No file contents found ' . $filename);
|
||||
}
|
||||
} else {
|
||||
$command->error('Filename not found ' . $class);
|
||||
}
|
||||
}
|
||||
}
|
||||
+44
-18
@@ -12,7 +12,7 @@ namespace Barryvdh\LaravelIdeHelper;
|
||||
|
||||
use Illuminate\Foundation\Application;
|
||||
use Illuminate\Foundation\AliasLoader;
|
||||
use Illuminate\Config\Repository as ConfigRepository;
|
||||
use Illuminate\Support\Collection;
|
||||
use ReflectionClass;
|
||||
use Symfony\Component\Console\Output\OutputInterface;
|
||||
|
||||
@@ -80,18 +80,19 @@ class Generator
|
||||
public function generatePhpHelper()
|
||||
{
|
||||
$app = app();
|
||||
return $this->view->make('ide-helper::helper')
|
||||
->with('namespaces', $this->getNamespaces())
|
||||
return $this->view->make('helper')
|
||||
->with('namespaces_by_extends_ns', $this->getAliasesByExtendsNamespace())
|
||||
->with('namespaces_by_alias_ns', $this->getAliasesByAliasNamespace())
|
||||
->with('helpers', $this->helpers)
|
||||
->with('version', $app->version())
|
||||
->with('include_fluent', $this->config->get('ide-helper.include_fluent', false))
|
||||
->with('include_fluent', $this->config->get('ide-helper.include_fluent', true))
|
||||
->render();
|
||||
}
|
||||
|
||||
public function generateJsonHelper()
|
||||
{
|
||||
$classes = array();
|
||||
foreach ($this->getNamespaces() as $aliases) {
|
||||
foreach ($this->getValidAliases() as $aliases) {
|
||||
foreach ($aliases as $alias) {
|
||||
$functions = array();
|
||||
foreach ($alias->getMethods() as $method) {
|
||||
@@ -186,13 +187,13 @@ class Generator
|
||||
}
|
||||
|
||||
/**
|
||||
* Find all namespaces/aliases that are valid for us to render
|
||||
* Find all aliases that are valid for us to render
|
||||
*
|
||||
* @return array
|
||||
* @return Collection
|
||||
*/
|
||||
protected function getNamespaces()
|
||||
protected function getValidAliases()
|
||||
{
|
||||
$namespaces = array();
|
||||
$aliases = new Collection();
|
||||
|
||||
// Get all aliases
|
||||
foreach ($this->getAliases() as $name => $facade) {
|
||||
@@ -209,15 +210,35 @@ class Generator
|
||||
$alias->addClass($this->extra[$name]);
|
||||
}
|
||||
|
||||
$namespace = $alias->getExtendsNamespace() ?: $alias->getNamespace();
|
||||
if (!isset($namespaces[$namespace])) {
|
||||
$namespaces[$namespace] = array();
|
||||
}
|
||||
$namespaces[$namespace][] = $alias;
|
||||
$aliases[] = $alias;
|
||||
}
|
||||
}
|
||||
|
||||
return $namespaces;
|
||||
return $aliases;
|
||||
}
|
||||
|
||||
/**
|
||||
* Regroup aliases by namespace of extended classes
|
||||
*
|
||||
* @return Collection
|
||||
*/
|
||||
protected function getAliasesByExtendsNamespace()
|
||||
{
|
||||
return $this->getValidAliases()->groupBy(function (Alias $alias) {
|
||||
return $alias->getExtendsNamespace();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Regroup aliases by namespace of alias
|
||||
*
|
||||
* @return Collection
|
||||
*/
|
||||
protected function getAliasesByAliasNamespace()
|
||||
{
|
||||
return $this->getValidAliases()->groupBy(function (Alias $alias) {
|
||||
return $alias->getNamespace();
|
||||
});
|
||||
}
|
||||
|
||||
protected function getAliases()
|
||||
@@ -244,15 +265,20 @@ class Generator
|
||||
'Schema' => 'Illuminate\Support\Facades\Schema',
|
||||
'Session' => 'Illuminate\Support\Facades\Session',
|
||||
'Storage' => 'Illuminate\Support\Facades\Storage',
|
||||
//'Validator' => 'Illuminate\Support\Facades\Validator',
|
||||
'Validator' => 'Illuminate\Support\Facades\Validator',
|
||||
'Gate' => 'Illuminate\Support\Facades\Gate',
|
||||
];
|
||||
|
||||
$facades = array_merge($facades, $this->config->get('app.aliases', []));
|
||||
|
||||
// Only return the ones that actually exist
|
||||
return array_filter($facades, function ($alias) {
|
||||
return array_filter(
|
||||
$facades,
|
||||
function ($alias) {
|
||||
return class_exists($alias);
|
||||
});
|
||||
},
|
||||
ARRAY_FILTER_USE_KEY
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -10,10 +10,15 @@
|
||||
|
||||
namespace Barryvdh\LaravelIdeHelper;
|
||||
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Barryvdh\LaravelIdeHelper\Console\EloquentCommand;
|
||||
use Barryvdh\LaravelIdeHelper\Console\GeneratorCommand;
|
||||
use Barryvdh\LaravelIdeHelper\Console\MetaCommand;
|
||||
use Barryvdh\LaravelIdeHelper\Console\ModelsCommand;
|
||||
use Barryvdh\LaravelIdeHelper\Console\GeneratorCommand;
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\View\Engines\EngineResolver;
|
||||
use Illuminate\View\Engines\PhpEngine;
|
||||
use Illuminate\View\Factory;
|
||||
use Illuminate\View\FileViewFinder;
|
||||
|
||||
class IdeHelperServiceProvider extends ServiceProvider
|
||||
{
|
||||
@@ -53,11 +58,12 @@ class IdeHelperServiceProvider extends ServiceProvider
|
||||
{
|
||||
$configPath = __DIR__ . '/../config/ide-helper.php';
|
||||
$this->mergeConfigFrom($configPath, 'ide-helper');
|
||||
$localViewFactory = $this->createLocalViewFactory();
|
||||
|
||||
$this->app->singleton(
|
||||
'command.ide-helper.generate',
|
||||
function ($app) {
|
||||
return new GeneratorCommand($app['config'], $app['files'], $app['view']);
|
||||
function ($app) use ($localViewFactory) {
|
||||
return new GeneratorCommand($app['config'], $app['files'], $localViewFactory);
|
||||
}
|
||||
);
|
||||
|
||||
@@ -70,12 +76,24 @@ class IdeHelperServiceProvider extends ServiceProvider
|
||||
|
||||
$this->app->singleton(
|
||||
'command.ide-helper.meta',
|
||||
function ($app) {
|
||||
return new MetaCommand($app['files'], $app['view']);
|
||||
function ($app) use ($localViewFactory) {
|
||||
return new MetaCommand($app['files'], $localViewFactory, $app['config']);
|
||||
}
|
||||
);
|
||||
|
||||
$this->commands('command.ide-helper.generate', 'command.ide-helper.models', 'command.ide-helper.meta');
|
||||
$this->app->singleton(
|
||||
'command.ide-helper.eloquent',
|
||||
function ($app) use ($localViewFactory) {
|
||||
return new EloquentCommand($app['files']);
|
||||
}
|
||||
);
|
||||
|
||||
$this->commands(
|
||||
'command.ide-helper.generate',
|
||||
'command.ide-helper.models',
|
||||
'command.ide-helper.meta',
|
||||
'command.ide-helper.eloquent'
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -87,4 +105,20 @@ class IdeHelperServiceProvider extends ServiceProvider
|
||||
{
|
||||
return array('command.ide-helper.generate', 'command.ide-helper.models');
|
||||
}
|
||||
|
||||
/**
|
||||
* @return Factory
|
||||
*/
|
||||
private function createLocalViewFactory()
|
||||
{
|
||||
$resolver = new EngineResolver();
|
||||
$resolver->register('php', function () {
|
||||
return new PhpEngine();
|
||||
});
|
||||
$finder = new FileViewFinder($this->app['files'], [__DIR__ . '/../resources/views']);
|
||||
$factory = new Factory($resolver, $finder, $this->app['events']);
|
||||
$factory->addExtension('php', 'php');
|
||||
|
||||
return $factory;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,46 @@
|
||||
<?php
|
||||
|
||||
namespace Barryvdh\LaravelIdeHelper;
|
||||
|
||||
use Barryvdh\Reflection\DocBlock;
|
||||
use Barryvdh\Reflection\DocBlock\Tag;
|
||||
|
||||
class Macro extends Method
|
||||
{
|
||||
/**
|
||||
* Macro constructor.
|
||||
*
|
||||
* @param \ReflectionFunctionAbstract $method
|
||||
* @param string $alias
|
||||
* @param \ReflectionClass $class
|
||||
* @param null $methodName
|
||||
* @param array $interfaces
|
||||
*/
|
||||
public function __construct(
|
||||
$method,
|
||||
$alias,
|
||||
$class,
|
||||
$methodName = null,
|
||||
$interfaces = array()
|
||||
) {
|
||||
parent::__construct($method, $alias, $class, $methodName, $interfaces);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param \ReflectionFunctionAbstract $method
|
||||
*/
|
||||
protected function initPhpDoc($method)
|
||||
{
|
||||
$this->phpdoc = new DocBlock($method);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param \ReflectionFunctionAbstract $method
|
||||
* @param \ReflectionClass $class
|
||||
*/
|
||||
protected function initClassDefinedProperties($method, \ReflectionClass $class)
|
||||
{
|
||||
$this->namespace = $class->getNamespaceName();
|
||||
$this->declaringClassName = '\\' . ltrim($class->name, '\\');
|
||||
}
|
||||
}
|
||||
+36
-6
@@ -26,29 +26,32 @@ class Method
|
||||
protected $method;
|
||||
|
||||
protected $output = '';
|
||||
protected $declaringClassName;
|
||||
protected $name;
|
||||
protected $namespace;
|
||||
protected $params = array();
|
||||
protected $params_with_default = array();
|
||||
protected $interfaces = array();
|
||||
protected $real_name;
|
||||
protected $return = null;
|
||||
|
||||
/**
|
||||
* @param \ReflectionMethod $method
|
||||
* @param \ReflectionMethod|\ReflectionFunctionAbstract $method
|
||||
* @param string $alias
|
||||
* @param \ReflectionClass $class
|
||||
* @param string|null $methodName
|
||||
* @param array $interfaces
|
||||
*/
|
||||
public function __construct(\ReflectionMethod $method, $alias, $class, $methodName = null, $interfaces = array())
|
||||
public function __construct($method, $alias, $class, $methodName = null, $interfaces = array())
|
||||
{
|
||||
$this->method = $method;
|
||||
$this->interfaces = $interfaces;
|
||||
$this->name = $methodName ?: $method->name;
|
||||
$this->namespace = $method->getDeclaringClass()->getNamespaceName();
|
||||
$this->real_name = $method->name;
|
||||
$this->initClassDefinedProperties($method, $class);
|
||||
|
||||
//Create a DocBlock and serializer instance
|
||||
$this->phpdoc = new DocBlock($method, new Context($this->namespace));
|
||||
$this->initPhpDoc($method);
|
||||
|
||||
//Normalize the description and inherit the docs from parents/interfaces
|
||||
try {
|
||||
@@ -65,11 +68,28 @@ class Method
|
||||
$this->phpdoc->appendTag(Tag::createInstance('@static', $this->phpdoc));
|
||||
|
||||
//Reference the 'real' function in the declaring class
|
||||
$declaringClass = $method->getDeclaringClass();
|
||||
$this->declaringClassName = '\\' . ltrim($declaringClass->name, '\\');
|
||||
$this->root = '\\' . ltrim($class->getName(), '\\');
|
||||
}
|
||||
|
||||
/**
|
||||
* @param \ReflectionMethod $method
|
||||
*/
|
||||
protected function initPhpDoc($method)
|
||||
{
|
||||
$this->phpdoc = new DocBlock($method, new Context($this->namespace));
|
||||
}
|
||||
|
||||
/**
|
||||
* @param \ReflectionMethod $method
|
||||
* @param \ReflectionClass $class
|
||||
*/
|
||||
protected function initClassDefinedProperties($method, \ReflectionClass $class)
|
||||
{
|
||||
$declaringClass = $method->getDeclaringClass();
|
||||
$this->namespace = $declaringClass->getNamespaceName();
|
||||
$this->declaringClassName = '\\' . ltrim($declaringClass->name, '\\');
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the class wherein the function resides
|
||||
*
|
||||
@@ -112,6 +132,16 @@ class Method
|
||||
return $this->name;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the real method name
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function getRealName()
|
||||
{
|
||||
return $this->real_name;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the parameters for this method
|
||||
*
|
||||
|
||||
Reference in New Issue
Block a user