Compare commits

...
37 Commits
Author SHA1 Message Date
Barry vd. Heuvel d82e8f191f Fix meta for 5.2 seeder
Fixes #287
2015-12-21 20:48:06 +01:00
Barry vd. Heuvel 5497e7d506 Merge pull request #294 from bytestream/master
Fixes #293
2015-12-14 14:33:18 +01:00
Kieran 2f83db311f Fixes #293 2015-12-14 13:29:24 +00:00
Barry vd. Heuvel d56bbb2356 Merge pull request #290 from nikolay-zakharov/dev-resource-fails
Fixed: fails to generate with resources
2015-12-11 15:38:48 +01:00
Nikolay Zakharov 2fb1135fc5 Fixed: fails to generate with resources 2015-12-11 17:18:14 +03:00
Barry vd. Heuvel aec17e3327 Update composer.json 2015-12-11 09:26:59 +01:00
Barry vd. Heuvel 0c560cb375 Merge pull request #288 from miraage/fix/models-command
fix(models-command): check for default reflectionparameter value
2015-12-07 08:55:26 +01:00
miraage 5708012a77 fix(models-command): check for default reflectionparameter value to prevent fail in variadic params 2015-12-06 13:49:27 +03:00
Barry vd. Heuvel af6d9a7fa1 Merge pull request #275 from Houbsi/master
Automatic phpDocs for models: added copy/past
2015-10-22 14:34:24 +02:00
Mike Houben f708b9a46c Automatic phpDocs for models: added copy/past
With this information it's much easier to install.
2015-10-22 14:31:54 +02:00
Barry vd. Heuvel e3de462538 Resolve user model at runtime
Fixes #274
2015-10-22 14:26:11 +02:00
Barry vd. Heuvel 76f09aaa65 Remove magic where 2015-10-19 09:32:38 +02:00
Barry vd. Heuvel 56f89502e3 Tweak relation object
Tweaks #273
2015-10-19 09:31:08 +02:00
Barry vd. Heuvel 11037acfe6 Merge pull request #273 from klaude/custom-collection-support
Add custom collection support
2015-10-19 09:30:05 +02:00
Kevin Laude e48974e545 Add custom collection support
Add support for models that override Eloquent's newCollection() with a
custom collection type. Do this by executing the relationship on the
model then executing that relationship's newCollection() method to see
what type of colletion class is returned.

Remove the now-unused
Barryvdh\LaravelIdeHelper\Console\ModelsCommand::getClassName() method.
2015-10-18 20:54:25 -05:00
Barry vd. Heuvel 38a97cf07c Swap facade/alias
See #202
2015-08-18 10:57:06 +02:00
Barry vd. Heuvel 74ee804dde Update readme 2015-08-14 09:50:36 +02:00
Barry vd. Heuvel 83999f8467 Bump version 2015-08-13 13:40:00 +02:00
Barry vd. Heuvel fab54d90dd Merge pull request #252 from mahmutbayri/master
Trim tag text.…
2015-08-13 13:12:39 +02:00
Mahmut Bayri 5d4056fe87 Trim tag text. If tag doesn't have comment or the comment has any space at the end of line, phpcs (with --standard=PSR2) dedects an error. 2015-08-13 13:42:10 +03:00
Barry vd. Heuvel 3fbe330998 Update readme.md 2015-08-10 21:05:06 +02:00
Barry vd. Heuvel 78d233fea7 Skip validator 2015-08-10 21:01:41 +02:00
Barry vd. Heuvel 0d13a51ff5 Use preset list of aliases in Lumen 2015-08-10 21:00:31 +02:00
Barry vd. Heuvel 326e8ea25f Bring back changes
Missed them from previous commit
2015-08-10 20:38:57 +02:00
Barry vd. Heuvel e7ee934bb1 Inject filesystem 2015-08-10 20:36:00 +02:00
Barry vd. Heuvel 99953adb73 Inject filesystem instance 2015-08-10 20:35:04 +02:00
Barry vd. Heuvel 0d333c6228 Check for config_path (Lumen)
For #202
2015-08-10 20:23:56 +02:00
Barry vd. Heuvel 0a717d1e79 Merge pull request #243 from bebnev/master
fix get_class($this) in relationship functions
2015-08-09 15:04:14 +02:00
bebnev dc62d35bed fix parsing relations arguments 2015-08-09 15:28:04 +03:00
Barry vd. Heuvel 2b7733c6b9 Merge pull request #242 from bebnev/master
fix model docBlocks duplicates
2015-08-01 16:59:45 +02:00
bebnev 76674be735 fix model docBlocks duplicates
Add each parsed model to ignore list, so if it exists more than once it will not be parsed twice.
2015-08-01 17:13:43 +04:00
Barry vd. Heuvel e34b7fb84b Merge pull request #232 from konomae/patch-1
Fix vendor:publish provider name
2015-07-14 11:09:59 +02:00
konomae e77a7b5a9c Fix vendor:publish provider name 2015-07-14 17:54:07 +09:00
Barry vd. Heuvel 19f7d75c10 Update readme.md 2015-06-25 13:32:53 +02:00
Barry vd. Heuvel 0373861536 Add generic factory 2015-06-25 10:58:59 +02:00
Barry vd. Heuvel 3a4671f3ea Update meta file 2015-06-18 14:58:06 +02:00
Barry vd. Heuvel 8515b7ac0b Use verbosity to hide some errors 2015-06-18 09:11:05 +02:00
9 changed files with 245 additions and 136 deletions
+4 -4
View File
@@ -11,9 +11,9 @@
], ],
"require": { "require": {
"php": ">=5.4.0", "php": ">=5.4.0",
"illuminate/support": "5.0.x|5.1.x", "illuminate/support": "5.0.x|5.1.x|5.2.x",
"illuminate/console": "5.0.x|5.1.x", "illuminate/console": "5.0.x|5.1.x|5.2.x",
"illuminate/filesystem": "5.0.x|5.1.x", "illuminate/filesystem": "5.0.x|5.1.x|5.2.x",
"phpdocumentor/reflection-docblock": "2.0.4", "phpdocumentor/reflection-docblock": "2.0.4",
"symfony/class-loader": "~2.3" "symfony/class-loader": "~2.3"
}, },
@@ -30,7 +30,7 @@
}, },
"extra": { "extra": {
"branch-alias": { "branch-alias": {
"dev-master": "2.0-dev" "dev-master": "2.1-dev"
} }
} }
} }
+1 -1
View File
@@ -83,7 +83,7 @@ return array(
*/ */
'interfaces' => array( 'interfaces' => array(
'\Illuminate\Contracts\Auth\Authenticatable' => config('auth.model', 'App\User'),
), ),
/* /*
+62 -21
View File
@@ -1,54 +1,53 @@
## Laravel 5 IDE Helper Generator ## Laravel 5 IDE Helper Generator
[![Latest Stable Version](https://poser.pugx.org/barryvdh/laravel-ide-helper/version.png)](https://packagist.org/packages/barryvdh/laravel-ide-helper) [![Total Downloads](https://poser.pugx.org/barryvdh/laravel-ide-helper/d/total.png)](https://packagist.org/packages/barryvdh/laravel-ide-helper) [![Latest Stable Version](https://poser.pugx.org/barryvdh/laravel-ide-helper/version.png)](https://packagist.org/packages/barryvdh/laravel-ide-helper) [![Total Downloads](https://poser.pugx.org/barryvdh/laravel-ide-helper/d/total.png)](https://packagist.org/packages/barryvdh/laravel-ide-helper)
### For Laravel 4.x, check [version 1.11](https://github.com/barryvdh/laravel-ide-helper/tree/1.11) __For Laravel 4.x, check [version 1.11](https://github.com/barryvdh/laravel-ide-helper/tree/1.11)__
### Complete phpDocs, directly from the source ### Complete phpDocs, directly from the source
_Checkout [this Laracasts video](https://laracasts.com/series/how-to-be-awesome-in-phpstorm/episodes/15) for a quick introduction/explanation!_ _Checkout [this Laracasts video](https://laracasts.com/series/how-to-be-awesome-in-phpstorm/episodes/15) for a quick introduction/explanation!_
* [`php artisan ide-helper:generate` - phpDoc generation for Laravel Facades ](#automatic-phpdoc-generation-for-laravel-facades)
* [`php artisan ide-helper:models` - phpDocs for models](#automatic-phpdocs-for-models)
* [`php artisan ide-helper:meta` - PhpStorm Meta file](#phpstorm-meta-for-container-instances)
This package generates a file that your IDE understands, so it can provide accurate autocompletion. Generation is done based on the files in your project, so they are always up-to-date. This package generates a file that your IDE understands, so it can provide accurate autocompletion. Generation is done based on the files in your project, so they are always up-to-date.
If you don't want to generate it, you can add a pre-generated file to the root folder of your Laravel project (but this isn't as up-to-date as self generated files). If you don't want to generate it, you can add a pre-generated file to the root folder of your Laravel project (but this isn't as up-to-date as self generated files).
* Generated version: https://gist.github.com/barryvdh/5227822 * Generated version for L5: https://gist.github.com/barryvdh/5227822
* 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 CodeIntel for Sublime Text: https://github.com/SublimeCodeIntel/SublimeCodeIntel
### New: PhpStorm Meta for Container instances ### Install
It's possible to generate a PhpStorm meta file, to [add support for factory design pattern](https://confluence.jetbrains.com/display/PhpStorm/PhpStorm+Advanced+Metadata). For Laravel, this means we can make PhpStorm understand what kind of object we are resolving from the IoC Container. For example, `events` will return an `Illuminate\Events\Dispatcher` object, so with the meta file you can call `app('events')` and it will autocomplete the Dispatcher methods.
php artisan ide-helper:meta
app('events')->fire();
\App::make('events')->fire();
/** @var \Illuminate\Foundation\Application $app */
$app->make('events')->fire();
Pre-generated example: https://gist.github.com/barryvdh/bb6ffc5d11e0a75dba67
> Note: You might need to restart PhpStorm and make sure `.phpstorm.meta.php` is indexed.
> Note: When you receive a FatalException about a class that is not found, check your config (for example, remove S3 as cloud driver when you don't have S3 configured. Remove Redis ServiceProvider when you don't use it).
### Automatic phpDoc generation for Laravel Facades
Require this package with composer using the following command: Require this package with composer using the following command:
```bash
composer require barryvdh/laravel-ide-helper composer require barryvdh/laravel-ide-helper
```
After updating composer, add the service provider to the `providers` array in `config/app.php` After updating composer, add the service provider to the `providers` array in `config/app.php`
```php
Barryvdh\LaravelIdeHelper\IdeHelperServiceProvider::class, Barryvdh\LaravelIdeHelper\IdeHelperServiceProvider::class,
```
### Automatic phpDoc generation for Laravel Facades
You can now re-generate the docs yourself (for future updates) You can now re-generate the docs yourself (for future updates)
```bash
php artisan ide-helper:generate 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 (and `php artisan optimize` after).
You can configure your composer.json to do this after each commit: You can configure your composer.json to do this after each commit:
```js
"scripts":{ "scripts":{
"post-update-cmd": [ "post-update-cmd": [
"php artisan clear-compiled", "php artisan clear-compiled",
@@ -56,10 +55,13 @@ You can configure your composer.json to do this after each commit:
"php artisan optimize" "php artisan optimize"
] ]
}, },
```
You can also publish the config file to change implementations (ie. interface to specific class) or set defaults for `--helpers` or `--sublime`. You can also publish the config file to change implementations (ie. interface to specific class) or set defaults for `--helpers` or `--sublime`.
php artisan vendor:publish --provider=barryvdh/laravel-ide-helper --tag=config ```bash
php artisan vendor:publish --provider="Barryvdh\LaravelIdeHelper\IdeHelperServiceProvider" --tag=config
```
The generator tries to identify the real class, but if it cannot be found, you can define it in the config file. The generator tries to identify the real class, but if it cannot be found, you can define it in the config file.
@@ -73,14 +75,22 @@ The `Illuminate/Support/helpers.php` is already set-up, but you can add/remove y
> You need to require `doctrine/dbal: ~2.3` in your own composer.json to get database columns. > You need to require `doctrine/dbal: ~2.3` in your own composer.json to get database columns.
```bash
composer require doctrine/dbal
```
If you don't want to write your properties yourself, you can use the command `php artisan ide-helper:models` to generate If you don't want to write your properties yourself, you can use the command `php artisan ide-helper:models` to generate
phpDocs, based on table columns, relations and getters/setters. You can write the comments directly to your Model file, using the `--write (-W)` option. By default, you are asked to overwrite or write to a separate file (`_ide_helper_models.php`). You can force No with `--nowrite (-N)`. phpDocs, based on table columns, relations and getters/setters. You can write the comments directly to your Model file, using the `--write (-W)` option. By default, you are asked to overwrite or write to a separate file (`_ide_helper_models.php`). You can force No with `--nowrite (-N)`.
Please make sure to backup your models, before writing the info. Please make sure to backup your models, before writing the info.
It should keep the existing comments and only append new properties/methods. The existing phpdoc is replaced, or added if not found. It should keep the existing comments and only append new properties/methods. The existing phpdoc is replaced, or added if not found.
With the `--reset (-R)` option, the existing phpdocs are ignored, and only the newly found columns/relations are saved as phpdocs. With the `--reset (-R)` option, the existing phpdocs are ignored, and only the newly found columns/relations are saved as phpdocs.
```bash
php artisan ide-helper:models Post php artisan ide-helper:models Post
```
```php
/** /**
* An Eloquent Model: 'Post' * An Eloquent Model: 'Post'
* *
@@ -93,23 +103,54 @@ With the `--reset (-R)` option, the existing phpdocs are ignored, and only the n
* @property-read \User $author * @property-read \User $author
* @property-read \Illuminate\Database\Eloquent\Collection|\Comment[] $comments * @property-read \Illuminate\Database\Eloquent\Collection|\Comment[] $comments
*/ */
```
By default, models in `app/models` are scanned. The optional argument tells what models to use (also outside app/models). By default, models in `app/models` are scanned. The optional argument tells what models to use (also outside app/models).
```bash
php artisan ide-helper:models Post User php artisan ide-helper:models Post User
```
You can also scan a different directory, using the `--dir` option (relative from the base path): You can also scan a different directory, using the `--dir` option (relative from the base path):
```bash
php artisan ide-helper:models --dir="path/to/models" --dir="app/src/Model" php artisan ide-helper:models --dir="path/to/models" --dir="app/src/Model"
```
You can publish the config file (`php artisan vendor:publish`) and set the default directories. You can publish the config file (`php artisan vendor:publish`) and set the default directories.
Models can be ignored using the `--ignore (-I)` option Models can be ignored using the `--ignore (-I)` option
```bash
php artisan ide-helper:models --ignore="Post,User" 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 " signs: `php artisan ide-helper:models "API\User"`, or escape the slashes (`Api\\User`)
## PhpStorm Meta for Container instances
It's possible to generate a PhpStorm meta file, to [add support for factory design pattern](https://confluence.jetbrains.com/display/PhpStorm/PhpStorm+Advanced+Metadata). For Laravel, this means we can make PhpStorm understand what kind of object we are resolving from the IoC Container. For example, `events` will return an `Illuminate\Events\Dispatcher` object, so with the meta file you can call `app('events')` and it will autocomplete the Dispatcher methods.
``` bash
php artisan ide-helper:meta
```
```php
app('events')->fire();
\App::make('events')->fire();
/** @var \Illuminate\Foundation\Application $app */
$app->make('events')->fire();
// When the key is not found, it uses the argument as class name
app('App\SomeClass');
```
Pre-generated example: https://gist.github.com/barryvdh/bb6ffc5d11e0a75dba67
> Note: You might need to restart PhpStorm and make sure `.phpstorm.meta.php` is indexed.
> Note: When you receive a FatalException about a class that is not found, check your config (for example, remove S3 as cloud driver when you don't have S3 configured. Remove Redis ServiceProvider when you don't use it).
### License ### License
The Laravel IDE Helper Generator is open-sourced software licensed under the [MIT license](http://opensource.org/licenses/MIT) The Laravel IDE Helper Generator is open-sourced software licensed under the [MIT license](http://opensource.org/licenses/MIT)
+5 -6
View File
@@ -1,4 +1,6 @@
<?= '<?php' ?> namespace PHPSTORM_META { <?= '<?php' ?>
namespace PHPSTORM_META {
/** /**
* PhpStorm Meta file, to provide autocomplete information for PhpStorm * PhpStorm Meta file, to provide autocomplete information for PhpStorm
@@ -7,13 +9,10 @@
* @author Barry vd. Heuvel <[email protected]> * @author Barry vd. Heuvel <[email protected]>
* @see https://github.com/barryvdh/laravel-ide-helper * @see https://github.com/barryvdh/laravel-ide-helper
*/ */
/** @noinspection PhpIllegalArrayKeyTypeInspection */
/** @noinspection PhpUnusedLocalVariableInspection */
/** @noinspection PhpUnnecessaryFullyQualifiedNameInspection */
$STATIC_METHOD_TYPES = [ $STATIC_METHOD_TYPES = [
<?php foreach($methods as $method): ?> <?php foreach($methods as $method): ?>
<?= $method ?>('') => [ <?= $method ?> => [
'' == '@',
<?php foreach($bindings as $abstract => $class): ?> <?php foreach($bindings as $abstract => $class): ?>
'<?= $abstract ?>' instanceof \<?= $class ?>, '<?= $abstract ?>' instanceof \<?= $class ?>,
<?php endforeach ?> ], <?php endforeach ?> ],
+12 -6
View File
@@ -12,6 +12,7 @@ namespace Barryvdh\LaravelIdeHelper\Console;
use Illuminate\Console\Command; use Illuminate\Console\Command;
use Symfony\Component\Console\Input\InputOption; use Symfony\Component\Console\Input\InputOption;
use Symfony\Component\Console\Output\OutputInterface;
/** /**
* A command to generate phpstorm meta data * A command to generate phpstorm meta data
@@ -42,12 +43,10 @@ class MetaCommand extends Command {
protected $view; protected $view;
protected $methods = [ protected $methods = [
'\Illuminate\Foundation\Application::make', 'new \Illuminate\Contracts\Container\Container',
'\Illuminate\Contracts\Foundation\Application::make', '\Illuminate\Contracts\Container\Container::make(\'\')',
'\Illuminate\Contracts\Container\Container::make', '\App::make(\'\')',
'\Illuminate\Container\Container::make', 'app(\'\')',
'\App::make',
'app',
]; ];
/** /**
@@ -72,15 +71,22 @@ class MetaCommand extends Command {
$bindings = array(); $bindings = array();
foreach ($this->getAbstracts() as $abstract) { foreach ($this->getAbstracts() as $abstract) {
// Validator and seeder cause problems
if (in_array($abstract, ['validator', 'seeder'])) {
continue;
}
try { try {
$concrete = $this->laravel->make($abstract); $concrete = $this->laravel->make($abstract);
if (is_object($concrete)) { if (is_object($concrete)) {
$bindings[$abstract] = get_class($concrete); $bindings[$abstract] = get_class($concrete);
} }
}catch (\Exception $e) { }catch (\Exception $e) {
if ($this->output->getVerbosity() >= OutputInterface::VERBOSITY_VERBOSE) {
$this->comment("Cannot make '$abstract': ".$e->getMessage()); $this->comment("Cannot make '$abstract': ".$e->getMessage());
} }
} }
}
$content = $this->view->make('ide-helper::meta', [ $content = $this->view->make('ide-helper::meta', [
'bindings' => $bindings, 'bindings' => $bindings,
+53 -31
View File
@@ -11,9 +11,12 @@
namespace Barryvdh\LaravelIdeHelper\Console; namespace Barryvdh\LaravelIdeHelper\Console;
use Illuminate\Console\Command; use Illuminate\Console\Command;
use Illuminate\Database\Eloquent\Relations\Relation;
use Illuminate\Support\Str; use Illuminate\Support\Str;
use Illuminate\Filesystem\Filesystem;
use Symfony\Component\Console\Input\InputOption; use Symfony\Component\Console\Input\InputOption;
use Symfony\Component\Console\Input\InputArgument; use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\ClassLoader\ClassMapGenerator; use Symfony\Component\ClassLoader\ClassMapGenerator;
use phpDocumentor\Reflection\DocBlock; use phpDocumentor\Reflection\DocBlock;
use phpDocumentor\Reflection\DocBlock\Context; use phpDocumentor\Reflection\DocBlock\Context;
@@ -27,6 +30,10 @@ use phpDocumentor\Reflection\DocBlock\Serializer as DocBlockSerializer;
*/ */
class ModelsCommand extends Command class ModelsCommand extends Command
{ {
/**
* @var Filesystem $files
*/
protected $files;
/** /**
* The console command name. * The console command name.
@@ -49,6 +56,14 @@ class ModelsCommand extends Command
protected $dirs = array(); protected $dirs = array();
protected $reset; protected $reset;
/**
* @param Filesystem $files
*/
public function __construct(Filesystem $files)
{
parent::__construct();
$this->files = $files;
}
/** /**
* Execute the console command. * Execute the console command.
@@ -80,7 +95,7 @@ class ModelsCommand extends Command
$content = $this->generateDocs($model, $ignore); $content = $this->generateDocs($model, $ignore);
if (!$this->write) { if (!$this->write) {
$written = \File::put($filename, $content); $written = $this->files->put($filename, $content);
if ($written !== false) { if ($written !== false) {
$this->info("Model information was written to $filename"); $this->info("Model information was written to $filename");
} else { } else {
@@ -148,7 +163,9 @@ class ModelsCommand extends Command
foreach ($models as $name) { foreach ($models as $name) {
if (in_array($name, $ignore)) { if (in_array($name, $ignore)) {
if ($this->output->getVerbosity() >= OutputInterface::VERBOSITY_VERBOSE) {
$this->comment("Ignoring model '$name'"); $this->comment("Ignoring model '$name'");
}
continue; continue;
} }
$this->properties = array(); $this->properties = array();
@@ -162,7 +179,9 @@ class ModelsCommand extends Command
continue; continue;
} }
if ($this->output->getVerbosity() >= OutputInterface::VERBOSITY_VERBOSE) {
$this->comment("Loading model '$name'"); $this->comment("Loading model '$name'");
}
if (!$reflectionClass->IsInstantiable()) { if (!$reflectionClass->IsInstantiable()) {
throw new \Exception($name . ' is not instantiable.'); throw new \Exception($name . ' is not instantiable.');
@@ -176,6 +195,7 @@ class ModelsCommand extends Command
$this->getPropertiesFromMethods($model); $this->getPropertiesFromMethods($model);
$output .= $this->createPhpDocs($name); $output .= $this->createPhpDocs($name);
$ignore[] = $name;
} catch (\Exception $e) { } catch (\Exception $e) {
$this->error("Exception: " . $e->getMessage() . "\nCould not analyze class $name."); $this->error("Exception: " . $e->getMessage() . "\nCould not analyze class $name.");
} }
@@ -270,11 +290,6 @@ class ModelsCommand extends Command
$comment = $column->getComment(); $comment = $column->getComment();
$this->setProperty($name, $type, true, true, $comment); $this->setProperty($name, $type, true, true, $comment);
$this->setMethod(
Str::camel("where_" . $name),
'\Illuminate\Database\Query\Builder|\\' . get_class($model),
array('$value')
);
} }
} }
} }
@@ -330,6 +345,7 @@ class ModelsCommand extends Command
$code .= $file->current(); $code .= $file->current();
$file->next(); $file->next();
} }
$code = trim(preg_replace('/\s\s+/', '', $code));
$begin = strpos($code, 'function('); $begin = strpos($code, 'function(');
$code = substr($code, $begin, strrpos($code, '}') - $begin + 1); $code = substr($code, $begin, strrpos($code, '}') - $begin + 1);
@@ -344,25 +360,28 @@ class ModelsCommand extends Command
) as $relation) { ) as $relation) {
$search = '$this->' . $relation . '('; $search = '$this->' . $relation . '(';
if ($pos = stripos($code, $search)) { if ($pos = stripos($code, $search)) {
$code = substr($code, $pos + strlen($search));
$arguments = explode(',', substr($code, 0, strpos($code, ')'))); //Resolve the relation's model to a Relation object.
//Remove quotes, ensure 1 \ in front of the model $relationObj = $model->$method();
$returnModel = $this->getClassName($arguments[0], $model);
if ($relation === "belongsToMany" or $relation === 'hasMany' or $relation === 'morphMany' or $relation === 'morphToMany') { if ($relationObj instanceof Relation) {
$relatedModel = '\\' . get_class($relationObj->getRelated());
if (in_array($relation, ['belongsToMany', 'hasMany', 'morphMany', 'morphToMany'])) {
//Collection or array of models (because Collection is Arrayable) //Collection or array of models (because Collection is Arrayable)
$this->setProperty( $this->setProperty(
$method, $method,
'\Illuminate\Database\Eloquent\Collection|' . $returnModel . '[]', $this->getCollectionClass($relatedModel) . '|' . $relatedModel . '[]',
true, true,
null null
); );
} else { } else {
//Single model is returned //Single model is returned
$this->setProperty($method, $returnModel, true, null); $this->setProperty($method, $relatedModel, true, null);
}
} }
} }
} }
} }
} }
} }
@@ -397,7 +416,9 @@ class ModelsCommand extends Command
protected function setMethod($name, $type = '', $arguments = array()) protected function setMethod($name, $type = '', $arguments = array())
{ {
if (!isset($this->methods[$name])) { $methods = array_change_key_case($this->methods, CASE_LOWER);
if (!isset($methods[strtolower($name)])) {
$this->methods[$name] = array(); $this->methods[$name] = array();
$this->methods[$name]['type'] = $type; $this->methods[$name]['type'] = $type;
$this->methods[$name]['arguments'] = $arguments; $this->methods[$name]['arguments'] = $arguments;
@@ -449,7 +470,8 @@ class ModelsCommand extends Command
} else { } else {
$attr = 'property-read'; $attr = 'property-read';
} }
$tag = Tag::createInstance("@{$attr} {$property['type']} {$name} {$property['comment']}", $phpdoc); $tagLine = trim("@{$attr} {$property['type']} {$name} {$property['comment']}");
$tag = Tag::createInstance($tagLine, $phpdoc);
$phpdoc->appendTag($tag); $phpdoc->appendTag($tag);
} }
@@ -469,7 +491,7 @@ class ModelsCommand extends Command
if ($this->write) { if ($this->write) {
$filename = $reflection->getFileName(); $filename = $reflection->getFileName();
$contents = \File::get($filename); $contents = $this->files->get($filename);
if ($originalDoc) { if ($originalDoc) {
$contents = str_replace($originalDoc, $docComment, $contents); $contents = str_replace($originalDoc, $docComment, $contents);
} else { } else {
@@ -480,7 +502,7 @@ class ModelsCommand extends Command
$contents = substr_replace($contents, $replace, $pos, strlen($needle)); $contents = substr_replace($contents, $replace, $pos, strlen($needle));
} }
} }
if (\File::put($filename, $contents)) { if ($this->files->put($filename, $contents)) {
$this->info('Written new phpDocBlock to ' . $filename); $this->info('Written new phpDocBlock to ' . $filename);
} }
} }
@@ -500,10 +522,11 @@ class ModelsCommand extends Command
//Loop through the default values for paremeters, and make the correct output string //Loop through the default values for paremeters, and make the correct output string
$params = array(); $params = array();
$paramsWithDefault = array(); $paramsWithDefault = array();
/** @var \ReflectionParameter $param */
foreach ($method->getParameters() as $param) { foreach ($method->getParameters() as $param) {
$paramStr = '$' . $param->getName(); $paramStr = '$' . $param->getName();
$params[] = $paramStr; $params[] = $paramStr;
if ($param->isOptional()) { if ($param->isOptional() && $param->isDefaultValueAvailable()) {
$default = $param->getDefaultValue(); $default = $param->getDefaultValue();
if (is_bool($default)) { if (is_bool($default)) {
$default = $default ? 'true' : 'false'; $default = $default ? 'true' : 'false';
@@ -524,23 +547,22 @@ class ModelsCommand extends Command
} }
/** /**
* Determine a model classes' collection type.
*
* @see http://laravel.com/docs/eloquent-collections#custom-collections
* @param string $className * @param string $className
* @param \Illuminate\Database\Eloquent\Model $model
* @return string * @return string
*/ */
private function getClassName($className, $model) private function getCollectionClass($className)
{ {
// If the class name was resolved via get_class($this) or static::class // Return something in the very very unlikely scenario the model doesn't
if (strpos($className, 'get_class($this)') !== false || strpos($className, 'static::class') !== false) { // have a newCollection() method.
return get_class($model); if (!method_exists($className, 'newCollection')) {
return '\Illuminate\Database\Eloquent\Collection';
} }
// If the class name was resolved via ::class (PHP 5.5+) /** @var \Illuminate\Database\Eloquent\Model $model */
if (strpos($className, '::class') !== false) { $model = new $className;
$end = -1 * strlen('::class'); return '\\' . get_class($model->newCollection());
return substr($className, 0, $end);
}
return "\\" . ltrim(trim($className, " \"'"), "\\") ;
} }
} }
+37 -3
View File
@@ -80,7 +80,7 @@ class Generator
return $this->view->make('ide-helper::helper') return $this->view->make('ide-helper::helper')
->with('namespaces', $this->getNamespaces()) ->with('namespaces', $this->getNamespaces())
->with('helpers', $this->helpers) ->with('helpers', $this->helpers)
->with('version', $app::VERSION) ->with('version', $app->version())
->render(); ->render();
} }
@@ -113,6 +113,8 @@ class Generator
protected function detectDrivers() protected function detectDrivers()
{ {
$this->interfaces['\Illuminate\Contracts\Auth\Authenticatable'] = config('auth.model', 'App\User');
try{ try{
if (class_exists('Auth') && is_a('Auth', '\Illuminate\Support\Facades\Auth', true)) { if (class_exists('Auth') && is_a('Auth', '\Illuminate\Support\Facades\Auth', true)) {
$class = get_class(\Auth::driver()); $class = get_class(\Auth::driver());
@@ -166,8 +168,7 @@ class Generator
$namespaces = array(); $namespaces = array();
// Get all aliases // Get all aliases
foreach (AliasLoader::getInstance()->getAliases() as $name => $facade) { foreach ($this->getAliases() as $name => $facade) {
// Skip the Redis facade, if not available (otherwise Fatal PHP Error) // Skip the Redis facade, if not available (otherwise Fatal PHP Error)
if ($facade == 'Illuminate\Support\Facades\Redis' && !class_exists('Predis\Client')) { if ($facade == 'Illuminate\Support\Facades\Redis' && !class_exists('Predis\Client')) {
continue; continue;
@@ -194,6 +195,39 @@ class Generator
return $namespaces; return $namespaces;
} }
protected function getAliases()
{
// For Laravel, use the AliasLoader
if (class_exists('Illuminate\Foundation\AliasLoader')) {
return AliasLoader::getInstance()->getAliases();
}
$facades = [
'App' => 'Illuminate\Support\Facades\App',
'Auth' => 'Illuminate\Support\Facades\Auth',
'Bus' => 'Illuminate\Support\Facades\Bus',
'DB' => 'Illuminate\Support\Facades\DB',
'Cache' => 'Illuminate\Support\Facades\Cache',
'Cookie' => 'Illuminate\Support\Facades\Cookie',
'Crypt' => 'Illuminate\Support\Facades\Crypt',
'Event' => 'Illuminate\Support\Facades\Event',
'Hash' => 'Illuminate\Support\Facades\Hash',
'Log' => 'Illuminate\Support\Facades\Log',
'Mail' => 'Illuminate\Support\Facades\Mail',
'Queue' => 'Illuminate\Support\Facades\Queue',
'Request' => 'Illuminate\Support\Facades\Request',
'Schema' => 'Illuminate\Support\Facades\Schema',
'Session' => 'Illuminate\Support\Facades\Session',
'Storage' => 'Illuminate\Support\Facades\Storage',
//'Validator' => 'Illuminate\Support\Facades\Validator',
];
// Only return the ones that actually exist
return array_filter($facades, function($alias){
return class_exists($alias);
});
}
/** /**
* Get the driver/connection/store from the managers * Get the driver/connection/store from the managers
* *
+8 -3
View File
@@ -36,7 +36,12 @@ class IdeHelperServiceProvider extends ServiceProvider
$this->loadViewsFrom($viewPath, 'ide-helper'); $this->loadViewsFrom($viewPath, 'ide-helper');
$configPath = __DIR__ . '/../config/ide-helper.php'; $configPath = __DIR__ . '/../config/ide-helper.php';
$this->publishes([$configPath => config_path('ide-helper.php')], 'config'); if (function_exists('config_path')) {
$publishPath = config_path('ide-helper.php');
} else {
$publishPath = base_path('config/ide-helper.php');
}
$this->publishes([$configPath => $publishPath], 'config');
} }
/** /**
@@ -56,8 +61,8 @@ class IdeHelperServiceProvider extends ServiceProvider
); );
$this->app['command.ide-helper.models'] = $this->app->share( $this->app['command.ide-helper.models'] = $this->app->share(
function () { function ($app) {
return new ModelsCommand(); return new ModelsCommand($app['files']);
} }
); );
+2
View File
@@ -270,6 +270,8 @@ class Method
$default = 'null'; $default = 'null';
} elseif (is_int($default)) { } elseif (is_int($default)) {
//$default = $default; //$default = $default;
} elseif (is_resource($default)) {
//skip to not fail
} else { } else {
$default = "'" . trim($default) . "'"; $default = "'" . trim($default) . "'";
} }