Repository: barryvdh/laravel-ide-helper Branch: master Commit: 1002cb567df7 Files: 286 Total size: 745.3 KB Directory structure: gitextract_re81t364/ ├── .editorconfig ├── .gitattributes ├── .github/ │ ├── FUNDING.yml │ ├── ISSUE_TEMPLATE/ │ │ ├── 1_Bug_report.md │ │ ├── 2_Feature_request.md │ │ └── 3_Support_question.md │ ├── PULL_REQUEST_TEMPLATE.md │ ├── dependabot.yaml │ ├── release-drafter.yml │ ├── stale.yml │ └── workflows/ │ ├── composer-normalize.yml │ ├── fix-code-style.yml │ ├── release-drafter.yml │ ├── run-integration-tests.yml │ ├── run-static-analysis.yml │ ├── run-tests.yml │ └── update-changelog.yaml ├── .gitignore ├── .php-cs-fixer.common.php ├── .php-cs-fixer.dist.php ├── .php-cs-fixer.tests.php ├── CHANGELOG.md ├── LICENSE.md ├── README.md ├── composer.json ├── config/ │ └── ide-helper.php ├── php-templates/ │ ├── LICENSE.md │ ├── README.md │ ├── auth.php │ ├── configs.php │ ├── middleware.php │ ├── routes.php │ ├── translations.php │ └── views.php ├── phpstan-baseline.neon ├── phpstan.neon ├── phpunit.xml.dist ├── resources/ │ └── views/ │ ├── helper.php │ └── meta.php ├── src/ │ ├── Alias.php │ ├── Console/ │ │ ├── EloquentCommand.php │ │ ├── GeneratorCommand.php │ │ ├── MetaCommand.php │ │ └── ModelsCommand.php │ ├── Contracts/ │ │ └── ModelHookInterface.php │ ├── Eloquent.php │ ├── Generator.php │ ├── IdeHelperServiceProvider.php │ ├── Listeners/ │ │ └── GenerateModelHelper.php │ ├── Macro.php │ ├── Method.php │ └── Parsers/ │ └── PhpDocReturnTypeParser.php └── tests/ ├── AliasTest.php ├── Console/ │ ├── EloquentCommandTest.php │ ├── GeneratorCommand/ │ │ ├── AbstractGeneratorCommand.php │ │ ├── GenerateEloquentOnly/ │ │ │ └── Test.php │ │ └── GenerateIdeHelper/ │ │ └── Test.php │ ├── MetaCommand/ │ │ └── MetaCommandTest.php │ ├── ModelsCommand/ │ │ ├── AbstractModelsCommand.php │ │ ├── AdvancedCasts/ │ │ │ ├── Collections/ │ │ │ │ ├── AdvancedCastCollection.php │ │ │ │ └── AdvancedCastMap.php │ │ │ ├── Enums/ │ │ │ │ └── AdvancedCastEnum.php │ │ │ ├── Models/ │ │ │ │ └── AdvancedCast.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── AllowGlobDirectory/ │ │ │ ├── Services/ │ │ │ │ └── Post/ │ │ │ │ └── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── ArrayCastsWithComment/ │ │ │ ├── Models/ │ │ │ │ └── ArrayCastsWithComment.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Attributes/ │ │ │ ├── Models/ │ │ │ │ ├── BackedAttribute.php │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Comment/ │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── CustomCollection/ │ │ │ ├── Collections/ │ │ │ │ └── SimpleCollection.php │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── CustomDate/ │ │ │ ├── Models/ │ │ │ │ └── CustomDate.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── CustomPhpdocTags/ │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__testNoSpaceAfterCustomPhpdocTag__1.php │ │ ├── DnfTypes/ │ │ │ ├── Models/ │ │ │ │ └── DnfTypeModel.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── DoesNotGeneratePhpdocWithExternalEloquentBuilder/ │ │ │ ├── Builders/ │ │ │ │ └── PostExternalQueryBuilder.php │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── DynamicRelations/ │ │ │ ├── Models/ │ │ │ │ └── Dynamic.php │ │ │ ├── OtherModels/ │ │ │ │ └── Account.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Factories/ │ │ │ ├── CustomSpace/ │ │ │ │ └── ModelWithCustomNamespaceFactory.php │ │ │ ├── Factories/ │ │ │ │ ├── ModelWithFactoryFactory.php │ │ │ │ └── ModelWithNestedFactoryFactory.php │ │ │ ├── Models/ │ │ │ │ ├── ModelWithCustomNamespace.php │ │ │ │ ├── ModelWithFactory.php │ │ │ │ ├── ModelWithNestedFactory.php │ │ │ │ └── ModelWithoutFactory.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__testFactory__1.php │ │ ├── GenerateBasicPhpDocWithEnumDefaults/ │ │ │ ├── Enums/ │ │ │ │ └── PostStatus.php │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GenerateBasicPhpdoc/ │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GenerateBasicPhpdocCamel/ │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GenerateBasicPhpdocFinal/ │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GenerateBasicPhpdocWithEloquentHelper/ │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GenerateMixinCollection/ │ │ │ ├── Models/ │ │ │ │ └── WithCollection.php │ │ │ ├── NonModels/ │ │ │ │ ├── CollectionModel.php │ │ │ │ └── NonModel.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GeneratePhpDocWithTypedScopeParameter/ │ │ │ ├── Models/ │ │ │ │ └── Comment.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GeneratePhpdocWithExternalEloquentBuilder/ │ │ │ ├── Builders/ │ │ │ │ └── PostExternalQueryBuilder.php │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GeneratePhpdocWithExternalEloquentBuilderWithFqn/ │ │ │ ├── Builders/ │ │ │ │ └── PostExternalQueryBuilder.php │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GeneratePhpdocWithForcedFqn/ │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GeneratePhpdocWithFqn/ │ │ │ ├── Casts/ │ │ │ │ └── CastType.php │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GeneratePhpdocWithFqnInExternalFile/ │ │ │ ├── Builders/ │ │ │ │ └── EMaterialQueryBuilder.php │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GeneratePhpdocWithMixin/ │ │ │ ├── Models/ │ │ │ │ ├── FinalPost.php │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── GenericsSyntaxDisabled/ │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Getter/ │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Ignored/ │ │ │ ├── Models/ │ │ │ │ ├── Ignored.php │ │ │ │ └── NotIgnored.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Interfaces/ │ │ │ ├── Models/ │ │ │ │ └── User.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── LaravelCustomCasts/ │ │ │ ├── Casts/ │ │ │ │ ├── CastableReturnsAnonymousCaster.php │ │ │ │ ├── CastableReturnsCustomCaster.php │ │ │ │ ├── CastableWithoutReturnType.php │ │ │ │ ├── CastedProperty.php │ │ │ │ ├── CustomCasterWithDocblockReturn.php │ │ │ │ ├── CustomCasterWithDocblockReturnFqn.php │ │ │ │ ├── CustomCasterWithNullablePrimitiveReturn.php │ │ │ │ ├── CustomCasterWithParam.php │ │ │ │ ├── CustomCasterWithPrimitiveDocblockReturn.php │ │ │ │ ├── CustomCasterWithPrimitiveReturn.php │ │ │ │ ├── CustomCasterWithReturnType.php │ │ │ │ ├── CustomCasterWithStaticReturnType.php │ │ │ │ ├── CustomCasterWithoutReturnType.php │ │ │ │ ├── ExtendedSelfCastingCasterWithStaticDocblockReturn.php │ │ │ │ ├── ExtendedSelfCastingCasterWithThisDocblockReturn.php │ │ │ │ ├── InboundAttributeCaster.php │ │ │ │ ├── SelfCastingCasterWithStaticDocblockReturn.php │ │ │ │ └── SelfCastingCasterWithThisDocblockReturn.php │ │ │ ├── Models/ │ │ │ │ └── CustomCast.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── MagicWhere/ │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── ModelHooks/ │ │ │ ├── Hooks/ │ │ │ │ ├── CustomMethod.php │ │ │ │ ├── CustomProperty.php │ │ │ │ └── UnsetMethod.php │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── MorphToIntersection/ │ │ │ ├── Models/ │ │ │ │ ├── BaseModel.php │ │ │ │ ├── CanBeAssigned.php │ │ │ │ └── MorphToIntersection.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Morphs/ │ │ │ ├── Models/ │ │ │ │ └── Morphs.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── PHPStormNoInspection/ │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ ├── Test__testNoinspectionNotPresent__1.php │ │ │ └── Test__testNoinspectionPresent__1.php │ │ ├── PhpAttributesBeforeClass/ │ │ │ ├── Models/ │ │ │ │ ├── FinalWithNested.php │ │ │ │ ├── MultipleAttributes.php │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Pivot/ │ │ │ ├── Models/ │ │ │ │ ├── ModelWithPivot.php │ │ │ │ └── Pivots/ │ │ │ │ ├── CustomPivot.php │ │ │ │ └── DifferentCustomPivot.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── QueryMethods/ │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── QueryScopes/ │ │ │ ├── Models/ │ │ │ │ ├── Comment.php │ │ │ │ ├── Post.php │ │ │ │ └── PostParent.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── RelationCountProperties/ │ │ │ ├── Models/ │ │ │ │ └── Post.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Relations/ │ │ │ ├── Models/ │ │ │ │ ├── BelongsToVariation.php │ │ │ │ ├── CompositeBelongsToVariation.php │ │ │ │ └── Simple.php │ │ │ ├── ModelsOtherNamespace/ │ │ │ │ └── AnotherModel.php │ │ │ ├── Test.php │ │ │ ├── Traits/ │ │ │ │ └── HasTestRelations.php │ │ │ ├── Types/ │ │ │ │ ├── SampleToAnyMorphedRelationType.php │ │ │ │ ├── SampleToAnyRelationType.php │ │ │ │ ├── SampleToBadlyNamedNotManyRelationType.php │ │ │ │ ├── SampleToManyRelationType.php │ │ │ │ └── SampleToOneRelationType.php │ │ │ └── __snapshots__/ │ │ │ ├── Test__testRelationNotNullable__1.php │ │ │ └── Test__test__1.php │ │ ├── ResetAndSmartReset/ │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ ├── Test__testNoReset__1.php │ │ │ ├── Test__testReset__1.php │ │ │ └── Test__testSmartReset__1.php │ │ ├── SimpleCasts/ │ │ │ ├── Models/ │ │ │ │ └── SimpleCast.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── SoftDeletes/ │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── SoftDeletesRelations/ │ │ │ ├── Models/ │ │ │ │ ├── ModelWithRelations.php │ │ │ │ ├── NonSoftDeletableModel.php │ │ │ │ └── SoftDeletableModel.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ ├── Test__testSoftDeletesForceNullableDisabled__1.php │ │ │ └── Test__test__1.php │ │ ├── UnionTypes/ │ │ │ ├── Models/ │ │ │ │ └── UnionTypeModel.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ ├── Variadic/ │ │ │ ├── Models/ │ │ │ │ └── Simple.php │ │ │ ├── Test.php │ │ │ └── __snapshots__/ │ │ │ └── Test__test__1.php │ │ └── migrations/ │ │ ├── ____advanced_casts_table.php │ │ ├── ____backed_attribute_table.php │ │ ├── ____belongs_to_variation_table.php │ │ ├── ____custom_casts_table.php │ │ ├── ____custom_dates_table.php │ │ ├── ____morphs_table.php │ │ ├── ____posts_table.php │ │ ├── ____simple_casts_table.php │ │ ├── ____simple_table.php │ │ └── ____soft_deletes_relations_table.php │ └── __snapshots__/ │ └── EloquentCommandTest__testCommand__1.txt ├── MacroTest.php ├── MethodTest.php ├── RealTimeFacadesTest.php ├── SnapshotPhpDriver.php ├── SnapshotTxtDriver.php ├── TestCase.php └── stubs/ ├── facade-0e0385307adf5db34c7986ecbd11646061356ec8.php └── facade-9431b04ec1494fc71a1bc848f020044aba2af7b1.php ================================================ FILE CONTENTS ================================================ ================================================ FILE: .editorconfig ================================================ ; This file is for unifying the coding style for different editors and IDEs. ; More information at http://editorconfig.org root = true [*] charset = utf-8 indent_size = 4 indent_style = space end_of_line = lf insert_final_newline = true trim_trailing_whitespace = true [*.md] trim_trailing_whitespace = false ================================================ FILE: .gitattributes ================================================ # Path-based git attributes # https://www.kernel.org/pub/software/scm/git/docs/gitattributes.html # Ignore all test and documentation with "export-ignore". /.editorconfig export-ignore /.gitattributes export-ignore /.github export-ignore /.gitignore export-ignore /.php-cs-fixer* export-ignore /phpunit.xml.dist export-ignore /psalm-baseline.xml export-ignore /psalm.xml export-ignore /tests export-ignore ================================================ FILE: .github/FUNDING.yml ================================================ # These are supported funding model platforms github: barryvdh custom: ['https://fruitcake.nl'] ================================================ FILE: .github/ISSUE_TEMPLATE/1_Bug_report.md ================================================ --- name: "🐛 Bug Report" about: 'Report a general bug.' labels: bug --- ### Versions: - ide-helper Version: #.#.# - Laravel Version: #.#.# - PHP Version: #.#.# ### Description: ### Steps To Reproduce: - … ================================================ FILE: .github/ISSUE_TEMPLATE/2_Feature_request.md ================================================ --- name: "✨ Feature request" about: 'Suggest a new feature or other improvements.' labels: enhancement --- ### Summary ================================================ FILE: .github/ISSUE_TEMPLATE/3_Support_question.md ================================================ --- name: "🙋🏼‍♂️ Support question" about: 'I need assistance or clarification on usage of this library.' labels: question --- ### Versions: - ide-helper Version: #.#.# - Laravel Version: #.#.# - PHP Version: #.#.# ### Question: ================================================ FILE: .github/PULL_REQUEST_TEMPLATE.md ================================================ ## Summary ## Type of change - [ ] Bug fix (non-breaking change which fixes an issue) - [ ] New feature (non-breaking change which adds functionality) - [ ] Breaking change (fix or feature that would cause existing functionality to not work as expected) - [ ] This change requires a documentation update - [ ] Misc. change (internal, infrastructure, maintenance, etc.) ### Checklist - [ ] Existing tests have been adapted and/or new tests have been added - [ ] Update the README.md - [ ] Code style has been fixed via `composer fix-style` ================================================ FILE: .github/dependabot.yaml ================================================ version: 2 updates: - package-ecosystem: github-actions directory: / schedule: interval: monthly groups: deps: patterns: - '*' ================================================ FILE: .github/release-drafter.yml ================================================ template: | ## What’s Changed $CHANGES ================================================ FILE: .github/stale.yml ================================================ # Number of days of inactivity before an issue becomes stale daysUntilStale: 90 # Number of days of inactivity before a stale issue is closed daysUntilClose: 60 # Issues with these labels will never be considered stale exemptLabels: - bug - enhancement - discussion # Label to use when marking an issue as stale staleLabel: stale # Comment to post when marking an issue as stale. Set to `false` to disable markComment: > This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. If this issue is still present on the latest version of this library on supported Laravel versions, please let us know by replying to this issue so we can investigate further. Thank you for your contribution! Apologies for any delayed response on our side. # Comment to post when closing a stale issue. Set to `false` to disable closeComment: false # Limit to only `issues` or `pulls` only: issues ================================================ FILE: .github/workflows/composer-normalize.yml ================================================ name: normalize composer.json on: push: paths: - .github/workflows/composer-normalize.yml - composer.json jobs: normalize: timeout-minutes: 15 runs-on: ubuntu-22.04 steps: - name: Git checkout uses: actions/checkout@v6 - name: Validate Composer configuration run: composer validate --strict - name: Normalize composer.json run: | composer global config --no-plugins allow-plugins.ergebnis/composer-normalize true composer global require ergebnis/composer-normalize composer normalize - uses: stefanzweifel/git-auto-commit-action@v7 with: commit_message: normalize composer.json ================================================ FILE: .github/workflows/fix-code-style.yml ================================================ name: Fix Code Style on: push: jobs: fix-style: name: Fix Code Style timeout-minutes: 15 runs-on: ubuntu-22.04 env: COMPOSER_NO_INTERACTION: 1 steps: - name: Checkout code uses: actions/checkout@v6 - name: Setup PHP uses: shivammathur/setup-php@v2 with: php-version: 8.3 coverage: none - name: Install dependencies run: composer update --prefer-dist --no-progress - run: composer fix-style continue-on-error: true - uses: stefanzweifel/git-auto-commit-action@v7 with: commit_message: composer fix-style commit_author: laravel-ide-helper ================================================ FILE: .github/workflows/release-drafter.yml ================================================ name: Release Drafter on: push: # branches to consider in the event; optional, defaults to all branches: - master # pull_request event is required only for autolabeler pull_request: # Only following types are handled by the action, but one can default to all as well types: [opened, reopened, synchronize] # pull_request_target event is required for autolabeler to support PRs from forks # pull_request_target: # types: [opened, reopened, synchronize] permissions: contents: read jobs: update_release_draft: permissions: # write permission is required to create a github release contents: write # write permission is required for autolabeler # otherwise, read permission is required at least pull-requests: write runs-on: ubuntu-latest steps: # (Optional) GitHub Enterprise requires GHE_HOST variable set #- name: Set GHE_HOST # run: | # echo "GHE_HOST=${GITHUB_SERVER_URL##https:\/\/}" >> $GITHUB_ENV # Drafts your next Release notes as Pull Requests are merged into "master" - uses: release-drafter/release-drafter@v6 # (Optional) specify config name to use, relative to .github/. Default: release-drafter.yml # with: # config-name: my-config.yml # disable-autolabeler: true env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} ================================================ FILE: .github/workflows/run-integration-tests.yml ================================================ name: Integration Tests on: push: branches: - master pull_request: branches: - "*" jobs: php-laravel-integration-tests: runs-on: ubuntu-22.04 timeout-minutes: 15 env: COMPOSER_NO_INTERACTION: 1 strategy: fail-fast: false matrix: php: [8.5, 8.4, 8.3, 8.2] laravel: [11.x, 12.x, 13.x] exclude: - laravel: 13.x php: 8.2 name: P${{ matrix.php }} - Laravel${{ matrix.laravel }} steps: - name: Checkout code uses: actions/checkout@v6 with: path: src - name: Setup PHP uses: shivammathur/setup-php@v2 with: php-version: ${{ matrix.php }} coverage: none - name: Install dependencies run: | composer create-project --prefer-dist laravel/laravel:${{ matrix.laravel }} --stability=dev --no-progress sample cd sample composer config minimum-stability dev composer update --prefer-stable --prefer-dist --no-progress - name: Add package from source run: | cd sample sed -e 's|"type": "project",|&\n"repositories": [ { "type": "path", "url": "../src" } ],|' -i composer.json composer require --dev "barryvdh/laravel-ide-helper:*" --with-all-dependencies - name: Execute generate run run: | cd sample php artisan ide-helper:generate - name: Execute meta run run: | cd sample php artisan ide-helper:meta -v - name: Check file existence run: | ls sample/_ide_helper.php ls sample/.phpstorm.meta.php - name: Check logs run: | if [ `ls -1q "sample/storage/logs/" | wc -l` -gt 0 ]; then for logfile in sample/storage/logs/*; do echo "-- $logfile --" cat $logfile done exit 1 fi ================================================ FILE: .github/workflows/run-static-analysis.yml ================================================ name: Run Static Analysis on: push: pull_request: schedule: - cron: '0 0 * * *' jobs: build: timeout-minutes: 15 runs-on: ubuntu-22.04 steps: - uses: actions/checkout@v6 - name: Setup PHP uses: shivammathur/setup-php@v2 with: php-version: 8.3 coverage: none extensions: pdo_sqlite - name: Install dependencies run: composer install --prefer-dist --no-progress --no-suggest - name: Analyze run: vendor/bin/phpstan --no-progress --error-format=github ================================================ FILE: .github/workflows/run-tests.yml ================================================ name: Tests on: push: branches: - master pull_request: branches: - "*" jobs: php-tests: runs-on: ${{ matrix.os }} timeout-minutes: 15 env: COMPOSER_NO_INTERACTION: 1 strategy: fail-fast: false matrix: os: [ubuntu-latest] php: [8.5, 8.4, 8.3, 8.2] laravel: [12.x, 13.x, ~11.15] stability: [prefer-lowest, prefer-stable] include: - os: windows-latest php: 8.3 laravel: 12.x stability: prefer-stable exclude: - laravel: 13.x php: 8.2 steps: - name: Set git to use LF if: "${{ matrix.os == 'windows-latest' }}" run: | git config --global core.autocrlf false git config --global core.eol lf - name: Checkout code uses: actions/checkout@v6 - name: Setup PHP uses: shivammathur/setup-php@v2 with: php-version: ${{ matrix.php }} coverage: none extensions: pdo_sqlite, fileinfo - name: Install dependencies run: | composer remove vimeo/psalm --no-update --dev composer remove friendsofphp/php-cs-fixer --no-update --dev composer require "laravel/framework:${{ matrix.laravel }}" --no-update --no-progress composer update --prefer-dist --no-progress --${{ matrix.stability }} - name: Execute Unit Tests run: composer test-ci ================================================ FILE: .github/workflows/update-changelog.yaml ================================================ name: "Update Changelog" on: release: types: [released] jobs: update: runs-on: ubuntu-latest permissions: # Give the default GITHUB_TOKEN write permission to commit and push the # updated CHANGELOG back to the repository. # https://github.blog/changelog/2023-02-02-github-actions-updating-the-default-github_token-permissions-to-read-only/ contents: write steps: - name: Checkout code uses: actions/checkout@v6 with: ref: ${{ github.event.release.target_commitish }} - name: Update Changelog uses: stefanzweifel/changelog-updater-action@v1 with: latest-version: ${{ github.event.release.tag_name }} release-notes: ${{ github.event.release.body }} - name: Commit updated CHANGELOG uses: stefanzweifel/git-auto-commit-action@v7 with: branch: ${{ github.event.release.target_commitish }} commit_message: Update CHANGELOG file_pattern: CHANGELOG.md ================================================ FILE: .gitignore ================================================ .phpunit.result.cache /auth.json /build /.idea /.php-cs-fixer.cache /.php-cs-fixer.php /.php-cs-fixer.tests.cache /composer.lock /vendor ================================================ FILE: .php-cs-fixer.common.php ================================================ true, 'blank_line_after_opening_tag' => true, 'braces' => [ 'allow_single_line_anonymous_class_with_empty_body' => true, ], 'compact_nullable_typehint' => true, 'declare_equal_normalize' => true, 'lowercase_cast' => true, 'lowercase_static_reference' => true, 'new_with_braces' => true, 'no_blank_lines_after_class_opening' => true, 'no_leading_import_slash' => true, 'no_whitespace_in_blank_line' => true, 'ordered_class_elements' => [ 'order' => [ 'use_trait', ], ], 'ordered_imports' => [ 'imports_order' => [ 'class', 'function', 'const', ], 'sort_algorithm' => 'alpha', ], 'return_type_declaration' => true, 'short_scalar_cast' => true, 'single_trait_insert_per_statement' => true, 'ternary_operator_spaces' => true, 'visibility_required' => [ 'elements' => [ 'const', 'method', 'property', ], ], // Further quality-of-life improvements 'array_syntax' => [ 'syntax' => 'short', ], 'concat_space' => [ 'spacing' => 'one', ], 'fully_qualified_strict_types' => true, 'native_function_invocation' => [ 'include' => [], 'strict' => true, ], 'no_unused_imports' => true, 'single_quote' => true, 'space_after_semicolon' => true, 'trailing_comma_in_multiline' => true, 'trim_array_spaces' => true, 'unary_operator_spaces' => true, 'whitespace_after_comma_in_array' => true, ]; ================================================ FILE: .php-cs-fixer.dist.php ================================================ in(__DIR__) ->exclude(['tests', 'build']); $config = require __DIR__ . '/.php-cs-fixer.common.php'; return (new PhpCsFixer\Config()) ->setFinder($finder) ->setRules($config) ->setRiskyAllowed(true) ->setCacheFile(__DIR__ . '/.php-cs-fixer.cache'); ================================================ FILE: .php-cs-fixer.tests.php ================================================ in(__DIR__ . '/tests') ->exclude('__snapshots__'); $config = require __DIR__ . '/.php-cs-fixer.common.php'; // Additional rules for tests $config = array_merge( $config, [ 'declare_strict_types' => true, ] ); return (new PhpCsFixer\Config()) ->setFinder($finder) ->setRules($config) ->setRiskyAllowed(true) ->setCacheFile(__DIR__ . '/.php-cs-fixer.tests.cache'); ================================================ FILE: CHANGELOG.md ================================================ # Changelog ## v3.7.0 - 2026-03-17 ### What's Changed * Skip calling fake() when required parameters exist (Socialite compatibility) by @Jaspur in https://github.com/barryvdh/laravel-ide-helper/pull/1746 * Make Soft Deleted Relationships Nullable by @evan-burrell in https://github.com/barryvdh/laravel-ide-helper/pull/1749 * Support all DNF types from PHP RFC by @gurmanolog in https://github.com/barryvdh/laravel-ide-helper/pull/1751 * Replace psalm with larastan by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1755 * perf: reduce redundant lookups and file I/O in generation hot paths by @pataar in https://github.com/barryvdh/laravel-ide-helper/pull/1757 * fix: wrap bare intersection types in parentheses when adding nullable by @pataar in https://github.com/barryvdh/laravel-ide-helper/pull/1756 * feat(ModelsCommand): add configuration option to disable model query methods by @pataar in https://github.com/barryvdh/laravel-ide-helper/pull/1692 * ci: add PHP 8.5 to integration test matrix by @pataar in https://github.com/barryvdh/laravel-ide-helper/pull/1760 * chore: update test snapshots after merge order issue by @pataar in https://github.com/barryvdh/laravel-ide-helper/pull/1762 * Laravel 13.x Compatibility by @laravel-shift in https://github.com/barryvdh/laravel-ide-helper/pull/1763 * fix: Correct indentation in camel case config comment block by @isaackaara in https://github.com/barryvdh/laravel-ide-helper/pull/1767 * fix: Place PHPDoc before class attributes when writing to models by @isaackaara in https://github.com/barryvdh/laravel-ide-helper/pull/1765 * fix: Don't extend root's parent class for facade stubs in helper file by @isaackaara in https://github.com/barryvdh/laravel-ide-helper/pull/1766 * Fix PHPDoc placement before PHP 8 class attributes and add regression tests by @Copilot in https://github.com/barryvdh/laravel-ide-helper/pull/1769 * fix: Skip autoload exception when class existence is being checked by @isaackaara in https://github.com/barryvdh/laravel-ide-helper/pull/1764 * Remove closure in attribute test by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1772 * Bump branch alias to 3.6 by @jnoordsij in https://github.com/barryvdh/laravel-ide-helper/pull/1774 ### New Contributors * @Jaspur made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1746 * @evan-burrell made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1749 * @gurmanolog made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1751 * @laravel-shift made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1763 * @isaackaara made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1767 * @Copilot made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1769 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.6.1...v3.7.0 ## v3.6.1 - 2025-12-10 ### What's Changed * Fix `methodsto` typo in README by @peterchrjoergensen in https://github.com/barryvdh/laravel-ide-helper/pull/1723 * Bump actions/checkout from 4 to 5 in the deps group by @dependabot[bot] in https://github.com/barryvdh/laravel-ide-helper/pull/1731 * Fix typos in documentation and code comments by @kei1111 in https://github.com/barryvdh/laravel-ide-helper/pull/1733 * Add php 8.5 support by @sergiy-petrov in https://github.com/barryvdh/laravel-ide-helper/pull/1735 * Fix alias fake error by @WentTheFox in https://github.com/barryvdh/laravel-ide-helper/pull/1745 * Remove calls to PHP 8.5-deprecated `setAccessible` by @jnoordsij in https://github.com/barryvdh/laravel-ide-helper/pull/1744 * Bump the deps group across 1 directory with 2 updates by @dependabot[bot] in https://github.com/barryvdh/laravel-ide-helper/pull/1743 * Add support for `decimal` column type by @BrainStone in https://github.com/barryvdh/laravel-ide-helper/pull/1739 ### New Contributors * @peterchrjoergensen made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1723 * @kei1111 made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1733 * @WentTheFox made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1745 * @BrainStone made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1739 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.6.0...v3.6.1 ## v3.6.0 - 2025-07-18 ### What's Changed * fix: Change AsArrayObject cast to be Laravel's ArrayObject by @wsamoht in https://github.com/barryvdh/laravel-ide-helper/pull/1675 * Add extends declaration for Macroable classes to fix missing inherited methods by @KentarouTakeda in https://github.com/barryvdh/laravel-ide-helper/pull/1674 * fix(meta): ignore aliases in the autoloader (Fixes #1671) by @pataar in https://github.com/barryvdh/laravel-ide-helper/pull/1686 * feat(ModelsCommand): add support for the new Scope attribute by @pataar in https://github.com/barryvdh/laravel-ide-helper/pull/1694 * fix type change for scope default float parameter by @nivseb in https://github.com/barryvdh/laravel-ide-helper/pull/1697 * Revert #1629 - *Allow adding custom Macroable classes* by @erikn69 in https://github.com/barryvdh/laravel-ide-helper/pull/1707 * Configurable macro return type defaults by @erikn69 in https://github.com/barryvdh/laravel-ide-helper/pull/1711 * docs(readme): add Laravel 12 support information by @SantosVilanculos in https://github.com/barryvdh/laravel-ide-helper/pull/1717 * Add multi-level directory support for translation files by @RosiersRobin in https://github.com/barryvdh/laravel-ide-helper/pull/1718 * Support `AsCollection::of($map)`, `AsCollection::using($class, $map)` by @erikn69 in https://github.com/barryvdh/laravel-ide-helper/pull/1714 * fix: Fixed wrong doc for SoftDeletes `withTrashed` method by @eldair in https://github.com/barryvdh/laravel-ide-helper/pull/1688 * Support other OS on tests by @erikn69 in https://github.com/barryvdh/laravel-ide-helper/pull/1715 * Fix tests on windows by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1720 * Bump stefanzweifel/git-auto-commit-action from 5 to 6 in the deps group by @dependabot[bot] in https://github.com/barryvdh/laravel-ide-helper/pull/1719 * Update .gitattributes - avoid all `.php-cs-fixer` files on vendor by @erikn69 in https://github.com/barryvdh/laravel-ide-helper/pull/1708 * fix(ModelsCommand): use 'string' as realType for 'encrypted' casts by @pataar in https://github.com/barryvdh/laravel-ide-helper/pull/1698 * Trim strings and bump reflection docblock by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1721 * Add magic *_exists properties by @erikn69 in https://github.com/barryvdh/laravel-ide-helper/pull/1712 ### New Contributors * @wsamoht made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1675 * @nivseb made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1697 * @SantosVilanculos made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1717 * @RosiersRobin made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1718 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.5.5...v3.6.0 ## v3.5.5 - 2025-02-21 ### What's Changed * Fix for incorrect config item types in meta file by @eldair in https://github.com/barryvdh/laravel-ide-helper/pull/1662 * Prevent generation of incorrect property annotation by @skyler544 in https://github.com/barryvdh/laravel-ide-helper/pull/1665 * Fix MorphTo Model Doc Generation by @yparitcher in https://github.com/barryvdh/laravel-ide-helper/pull/1668 * Laravel 12 support by @jonnott in https://github.com/barryvdh/laravel-ide-helper/pull/1672 ### New Contributors * @eldair made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1662 * @skyler544 made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1665 * @yparitcher made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1668 * @jonnott made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1672 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.5.4...v3.5.5 ## v3.5.4 - 2025-01-14 ### What's Changed * Convert auth() helper to use Auth facade by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1656 * Check if returnType from docblock is not null by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1658 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.5.3...v3.5.4 ## v3.5.3 - 2025-01-08 ### What's Changed * Catch meta, tweak auth by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1654 * Check if macro is valid by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1655 * feat: use generics of return type to determine resulting models by @Bloemendaal in https://github.com/barryvdh/laravel-ide-helper/pull/1653 ### New Contributors * @Bloemendaal made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1653 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.5.2...v3.5.3 ## v3.5.2 - 2025-01-06 ### Fixes Fix empty/anonymous closure in meta command. **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.5.1...v3.5.2 ## v3.5.1 - 2025-01-06 ### What's Changed * Remove duplicate config, fix ->can() by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1650 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.5.0...v3.5.1 ## v3.5.0 - 2025-01-06 ### What's Changed * Add phpstorm meta argument hints by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1640 * Add meta override for user return types by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1642 * Use forked ContextFactory by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1643 * Remove php parser by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1644 * Also add eloquent template tags from base class by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1645 * Add more metadata by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1646 * Fixed generating PHPDoc for methods with class templates by @chack1172 in https://github.com/barryvdh/laravel-ide-helper/pull/1647 * Feat guess macro types by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1648 * Allow adding custom Macroable classes. by @mathieutu in https://github.com/barryvdh/laravel-ide-helper/pull/1629 * Add special `dev` to composer keywords by @jnoordsij in https://github.com/barryvdh/laravel-ide-helper/pull/1649 ### New Contributors * @chack1172 made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1647 * @mathieutu made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1629 * @jnoordsij made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1649 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.4.0...v3.5.0 ## v3.4.0 - 2024-12-29 ### What's Changed * fix: add @template TModel of static for Eloquent by @imzyf in https://github.com/barryvdh/laravel-ide-helper/pull/1631 * Add templates to Eloquent by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1634 * Update testsuite for Generator, simplify service provider and mock by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1635 * Add option for only eloquent by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1636 * Add weak generics for array type objects by @LauJosefsen in https://github.com/barryvdh/laravel-ide-helper/pull/1621 * Make all "note" in README apply quote style by @hms5232 in https://github.com/barryvdh/laravel-ide-helper/pull/1590 * Update README.md by @Mtillmann in https://github.com/barryvdh/laravel-ide-helper/pull/1587 * Rename view var by @barryvdh and @pb30 in https://github.com/barryvdh/laravel-ide-helper/pull/1637 and https://github.com/barryvdh/laravel-ide-helper/pull/1563 * Format IDE helper by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1638 * Add TLDR section, update options by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1639 ### New Contributors * @imzyf made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1631 * @LauJosefsen made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1621 * @hms5232 made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1590 * @Mtillmann made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1587 * @pb30 made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1563 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.3.0...v3.4.0 ## v3.3.0 - 2024-12-18 ### What's Changed * Feature: Add Config Option to Enforce Nullable Relationships by @jeramyhing in https://github.com/barryvdh/laravel-ide-helper/pull/1580 * Improve replacement of return type for methods from Query\Builder by @pjio in https://github.com/barryvdh/laravel-ide-helper/pull/1575 * Update CHANGELOG.md, fix typo(s) by @NicholasWilsonDEV in https://github.com/barryvdh/laravel-ide-helper/pull/1613 * Fixed PHP 8.4 deprecation warning by @eusonlito in https://github.com/barryvdh/laravel-ide-helper/pull/1622 * Fix PHP 8.4 deprecations by @JeppeKnockaert in https://github.com/barryvdh/laravel-ide-helper/pull/1618 * Assign $output method parameter to $this->output on Generator by @eusonlito in https://github.com/barryvdh/laravel-ide-helper/pull/1623 ### New Contributors * @jeramyhing made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1580 * @pjio made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1575 * @NicholasWilsonDEV made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1613 * @eusonlito made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1622 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.2.2...v3.3.0 ## v3.2.2 - 2024-10-29 ### What’s Changed * fix(pivot): only use unique classes in the pivot union (Fixes #1606) (#1607) @pataar * docs(pr): remove the changelog checklist item (#1608) @pataar * Create update-changelog.yaml (#1605) @barryvdh **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.2.1...v3.2.2 ## 3.2.1 - 2024-10-28 ### What's Changed * chore: Fix the description of unused option by @KentarouTakeda in https://github.com/barryvdh/laravel-ide-helper/pull/1600 * feat(pivot): add support for multiple pivot types when using the same accessor by @pataar in https://github.com/barryvdh/laravel-ide-helper/pull/1597 * Add support for `AsCollection::using` and `AsEnumCollection::of` casts by @uno-sw in https://github.com/barryvdh/laravel-ide-helper/pull/1577 * Smarter reset by @barryvdh in https://github.com/barryvdh/laravel-ide-helper/pull/1603 * feat: use `numeric` type on fields with `decimal` casts by @ekisu in https://github.com/barryvdh/laravel-ide-helper/pull/1583 ### New Contributors * @uno-sw made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1577 * @ekisu made their first contribution in https://github.com/barryvdh/laravel-ide-helper/pull/1583 **Full Changelog**: https://github.com/barryvdh/laravel-ide-helper/compare/v3.2.0...v3.2.1 ## 3.2.0 - 2024-10-18 ### Fixed - Fix type of hashed model property to `string` ### Changed - Update view "version" variable name to avoid potential conflicts - Add support for EloquentBuilder generics introduced in Laravel 11.15. - Drop support for Laravel versions earlier than 11.15. ### Added - Introduce `enforce_nullable_relationships` configuration option to control how nullable Eloquent relationships are enforced during static analysis. This provides flexibility for scenarios where application logic ensures data integrity without relying on database constraints. [#1580 / jeramyhing](https://github.com/barryvdh/laravel-ide-helper/pull/1580) - Add support for AsCollection::using and AsEnumCollection::of casts [#1577 / uno-sw](https://github.com/barryvdh/laravel-ide-helper/pull/1577) ## 3.1.0 - 2024-07-12 ### Fixed - Fix return value of query scopes from parent class [#1366 / sforward](https://github.com/barryvdh/laravel-ide-helper/pull/1366) - Add static to isBuiltin() check in ide-helper:models [#1541 / bram-pkg](https://github.com/barryvdh/laravel-ide-helper/pull/1541) - Fix for getSomethingAttribute functions which return a collection with type templating in the phpDoc. [#1567 / stefanScrumble](https://github.com/barryvdh/laravel-ide-helper/pull/1567) ### Added - Add type to pivot when using a custom pivot class [#1518 / d3v2a](https://github.com/barryvdh/laravel-ide-helper/pull/1518) - Add support in morphTo relationship for null values [#1547 / matysekmichal](https://github.com/barryvdh/laravel-ide-helper/pull/1547) - Add support for AsEnumCollection casts [#1557 / Braunson](https://github.com/barryvdh/laravel-ide-helper/pull/1557) - Support for Attribute class in attributes [#1567 / stefanScrumble](https://github.com/barryvdh/laravel-ide-helper/pull/1567) ## 3.0.0 - 2024-03-01 ### Added - Support for Laravel 11 [#1520 / KentarouTakeda](https://github.com/barryvdh/laravel-ide-helper/pull/1520) ### Changed - Make `--reset` always keep the text and remove `--smart-reset`. Always skip the classname [#1523 / barryvdh](https://github.com/barryvdh/laravel-ide-helper/pull/1523) & [#1525 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/1525) - Use short types (`int` and `bool` instead of `integer` and `boolean`) [#1524 / barryvdh](https://github.com/barryvdh/laravel-ide-helper/pull/1524) ### Removed - Support for Laravel 9 and use of doctrine/dbal [#1512 / barryvdh](https://github.com/barryvdh/laravel-ide-helper/pull/1512) With this functionality gone, a few changes have been made: - support for custom datatypes has been dropped (config `custom_db_types`) unknown data types default to `string` now and to fix the type, add a proper cast in Eloquent - You *might* have top-level dependency on doctrine/dbal. This may have been in the past due to ide-helper, we suggest to check if you still need it and remove it otherwise - Minimum PHP version, due to Laravel 10, is now PHP 8.1 ## 2024-02-15, 2.15.1 ### Fixed - Fix final class keyword in wrong position [#1517 / barryvdh](https://github.com/barryvdh/laravel-ide-helper/pull/1517) ### Changed ### Added ## 2024-02-14, 2.15.0 ### Fixed - Fix case issue in `ModelsCommand::unsetMethod()` [#1453 / leo108](https://github.com/barryvdh/laravel-ide-helper/pull/1453) - Fix non-facade classes will result in no autocomplete [#841 / netpok](https://github.com/barryvdh/laravel-ide-helper/pull/841) - Skip swoole, otherwise fatal error [#1477 / TimoFrenzel](https://github.com/barryvdh/laravel-ide-helper/pull/1477) - Fix vulnerability CVE-2021-43608 [#1392 / allanlaal](https://github.com/barryvdh/laravel-ide-helper/pull/1392) - Reset foreignKeyConstraintsColumns on model loop start [#1461 / snmatsui](https://github.com/barryvdh/laravel-ide-helper/pull/1461) - Accept scope & scopes as relation [#1452 / Muetze42](https://github.com/barryvdh/laravel-ide-helper/pull/1452) - Fix #1300 relation_return_type must take precedence if it is defined [#1394 / menthol](https://github.com/barryvdh/laravel-ide-helper/pull/1394) ### Changed - Disable inspections of helper files [#1486 / eidng8](https://github.com/barryvdh/laravel-ide-helper/pull/1486) - Removed support for Laravel 8 and therefore for PHP < 8.0 [#1504 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/1504) ### Added - Add support for enum default arguments using enum cases. [#1464 / d8vjork](https://github.com/barryvdh/laravel-ide-helper/pull/1464) - Add support for real-time facades in the helper file. [#1455 / filipac](https://github.com/barryvdh/laravel-ide-helper/pull/1455) - Add support for relations with composite keys. [#1479 / calebdw](https://github.com/barryvdh/laravel-ide-helper/pull/1479) - Add support for attribute accessors with no backing field or type hinting [#1411 / pindab0ter](https://github.com/barryvdh/laravel-ide-helper/pull/1411). - Add support for AsCollection and AsArrayObject casts [#1393 / pataar](https://github.com/barryvdh/laravel-ide-helper/pull/1393) - Reintroduce support for multi-db setups [#1426 / benpoulson](https://github.com/barryvdh/laravel-ide-helper/pull/1426) - Support the BINARY(...) database field type [#1434 / Sfonxs](https://github.com/barryvdh/laravel-ide-helper/pull/1434) - Add AllowDynamicProperties Attribute to cooperate with php8.2 deprecation [#1428 / GeoSot](https://github.com/barryvdh/laravel-ide-helper/pull/1428) ## 2024-02-05, 2.14.0 ### Changed - Official support for Lumen has been dropped [#1425 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/1425) - Refactor resolving of null information for custom casted attribute types [#1330 / wimski](https://github.com/barryvdh/laravel-ide-helper/pull/1330) ### Fixed - Catch exceptions when loading aliases [#1465 / dongm2ez](https://github.com/barryvdh/laravel-ide-helper/pull/1465) ### Added - Add support for nikic/php-parser 5 (next to 4) [#1502 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/1502) - Add support for `immutable_date:*` and `immutable_datetime:*` casts. [#1380 / thekonz](https://github.com/barryvdh/laravel-ide-helper/pull/1380) - Add support for attribute accessors marked as protected. [#1339 / pindab0ter](https://github.com/barryvdh/laravel-ide-helper/pull/1339) ## 2023-02-04, 2.13.0 ### Fixed - Fix return type of methods provided by `SoftDeletes` [#1345 / KentarouTakeda](https://github.com/barryvdh/laravel-ide-helper/pull/1345) - Handle PHP 8.1 deprecation warnings when passing `null` to `new \ReflectionClass` [#1351 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/1351) - Fix issue where \Eloquent is not included when using write_mixin [#1352 / Jefemy](https://github.com/barryvdh/laravel-ide-helper/pull/1352) - Fix model factory method arguments for Laravel >= 9 [#1361 / wimski](https://github.com/barryvdh/laravel-ide-helper/pull/1361) - Improve return type of mock helper methods in tests [#1405 / bentleyo](https://github.com/barryvdh/laravel-ide-helper/pull/1405) - Fix Castable class if failed to detect it from return types [#1388 / kwarcu](https://github.com/barryvdh/laravel-ide-helper/pull/1388) ### Added - Added Laravel 10 support [#1407 / lptn](https://github.com/barryvdh/laravel-ide-helper/pull/1407) - Add support for custom casts that implement `CastsInboundAttributes` [#1329 / sforward](https://github.com/barryvdh/laravel-ide-helper/pull/1329) - Add option `use_generics_annotations` for collection type hints [#1298 / tanerkay](https://github.com/barryvdh/laravel-ide-helper/pull/1298) ## 2022-03-06, 2.12.3 ### Fixed - Fix date and datetime handling for attributes that set a serialization format option for the Carbon instance [#1324 / FLeudts](https://github.com/barryvdh/laravel-ide-helper/pull/1324) - Fix composer conflict with composer/pcre version 2/3. [#1327 / barryvdh](https://github.com/barryvdh/laravel-ide-helper/pull/1327) ## 2022-02-08, 2.12.2 ### Fixed - Remove composer dependency, use copy of ClassMapGenerator [#1313 / barryvdh](https://github.com/barryvdh/laravel-ide-helper/pull/1313) ## 2022-01-24, 2.12.1 ### Fixed - Properly handle `Castable`s without return type. [#1306 / binotaliu](https://github.com/barryvdh/laravel-ide-helper/pull/1306) ## 2022-01-23, 2.12.0 ### Added - Add support for custom casts that using `Castable` [#1287 / binotaliu](https://github.com/barryvdh/laravel-ide-helper/pull/1287) - Added Laravel 9 support [#1297 / rcerljenko](https://github.com/barryvdh/laravel-ide-helper/pull/1297) - Added option `additional_relation_return_types` for custom relations that don't fit the typical naming scheme ## 2022-01-03, 2.11.0 ### Added - Add support for Laravel 8.77 Attributes [#1289 / SimonJnsson](https://github.com/barryvdh/laravel-ide-helper/pull/1289) - Add support for cast types `decimal:*`, `encrypted:*`, `immutable_date`, `immutable_datetime`, `custom_datetime`, and `immutable_custom_datetime` [#1262 / miken32](https://github.com/barryvdh/laravel-ide-helper/pull/1262) - Add support of variadic parameters in `ide-helper:models` [#1234 / shaffe-fr](https://github.com/barryvdh/laravel-ide-helper/pull/1234) - Add support of custom casts without properties [#1267 / sparclex](https://github.com/barryvdh/laravel-ide-helper/pull/1267) ### Fixed - Fix recursively searching for `HasFactory` and `Macroable` traits [#1216 / daniel-de-wit](https://github.com/barryvdh/laravel-ide-helper/pull/1216) - Use platformName to determine db type when casting boolean types [#1212 / stockalexander](https://github.com/barryvdh/laravel-ide-helper/pull/1212) ### Changed - Move default models helper filename to config [#1241 / wimski](https://github.com/barryvdh/laravel-ide-helper/pull/1241) ## 2021-06-18, 2.10.1 ### Added - Added Type registration according to [Custom Mapping Types documentation](https://www.doctrine-project.org/projects/doctrine-dbal/en/latest/reference/types.html#custom-mapping-types) [#1228 / wimski](https://github.com/barryvdh/laravel-ide-helper/pull/1241) ### Fixed - Fixing issue where configured custom_db_types could cause a DBAL exception to be thrown while running `ide-helper:models` [#1228 / wimski](https://github.com/barryvdh/laravel-ide-helper/pull/1241) ## 2021-04-09, 2.10.0 ### Added - Allowing Methods to be set or unset in ModelHooks [#1198 / jenga201](https://github.com/barryvdh/laravel-ide-helper/pull/1198) Note: the visibility of `\Barryvdh\LaravelIdeHelper\Console\ModelsCommand::setMethod` has been changed to **public**! ### Fixed - Fixing issue where incorrect autoloader unregistered [#1210 / tezhm](https://github.com/barryvdh/laravel-ide-helper/pull/1210) ## 2021-04-02, 2.9.3 ### Fixed - Support both customized namespace factories as well as default resolvable ones [#1201 / wimski](https://github.com/barryvdh/laravel-ide-helper/pull/1201) ## 2021-04-01, 2.9.2 ### Added - Model hooks for adding custom information from external sources to model classes through the ModelsCommand [#945 / wimski](https://github.com/barryvdh/laravel-ide-helper/pull/945) ### Fixed - Fix ide-helper:models exception if model doesn't have factory [#1196 / ahmed-aliraqi](https://github.com/barryvdh/laravel-ide-helper/pull/1196) - Running tests triggering post_migrate hooks [#1193 / netpok](https://github.com/barryvdh/laravel-ide-helper/pull/1193) - Array_merge error when config is cached prior to package install [#1184 / netpok](https://github.com/barryvdh/laravel-ide-helper/pull/1184) ## 2021-03-15, 2.9.1 ### Added - Generate PHPDoc for Laravel 8.x factories [#1074 / ahmed-aliraqi](https://github.com/barryvdh/laravel-ide-helper/pull/1074) - Add a comment to a property like table columns [#1168 / biiiiiigmonster](https://github.com/barryvdh/laravel-ide-helper/pull/1168) - Added `post_migrate` hook to run commands after a migration [#1163 / netpok](https://github.com/barryvdh/laravel-ide-helper/pull/1163) - Allow for PhpDoc for macros with union types [#1148 / riesjart](https://github.com/barryvdh/laravel-ide-helper/pull/1148) ### Fixed - Error when generating helper for invokable classes [#1124 / standaniels](https://github.com/barryvdh/laravel-ide-helper/pull/1124) - Fix broken ReflectionUnionTypes [#1132 / def-studio](https://github.com/barryvdh/laravel-ide-helper/pull/1132) - Relative class names are not converted to fully-qualified class names [#1005 / SavKS](https://github.com/barryvdh/laravel-ide-helper/pull/1005) ## 2020-12-30, 2.9.0 ### Changed - Dropped support for Laravel 6 and Laravel 7, as well as support for PHP 7.2 and added support for doctrine/dbal:^3 [#1114 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/1114) ### Fixed - `Macro::initPhpDoc()` will save original docblock if present [#1116 / LastDragon-ru](https://github.com/barryvdh/laravel-ide-helper/pull/1116) - `Alias` will grab macros from `\Illuminate\Database\Eloquent\Builder` too [#1118 / LastDragon-ru](https://github.com/barryvdh/laravel-ide-helper/pull/1118) ## 2020-12-08, 2.8.2 ### Added - Fix phpdoc generate for custom cast with parameter [#986 / artelkr](https://github.com/barryvdh/laravel-ide-helper/pull/986) - Created a possibility to add custom relation type [#987 / efinder2](https://github.com/barryvdh/laravel-ide-helper/pull/987) - Added `@see` with macro/mixin definition location to PhpDoc [#1054 / riesjart](https://github.com/barryvdh/laravel-ide-helper/pull/1054) - Initial compatibility for PHP8 [#1106 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/1106) ### Changed - Implement DeferrableProvider [#914 / kon-shou](https://github.com/barryvdh/laravel-ide-helper/pull/914) ### Fixed - Compatibility with Lumen [#1043 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/1043) - Allow model_locations to have glob patterns [#1059 / saackearl](https://github.com/barryvdh/laravel-ide-helper/pull/1059) - Error when generating helper for macroable classes which are not facades and contain a "fake" method [#1066 / domkrm] (https://github.com/barryvdh/laravel-ide-helper/pull/1066) - Casts with a return type of `static` or `$this` now resolve to an instance of the cast [#1103 / riesjart](https://github.com/barryvdh/laravel-ide-helper/pull/1103) ### Removed - Removed format and broken generateJsonHelper [#1053 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/1053) ## 2020-09-07, 2.8.1 ### Added - Support Laravel 8 [#1022 / barryvdh](https://github.com/barryvdh/laravel-ide-helper/pull/1022) - Add option to force usage of FQN [#1031 / edvordo](https://github.com/barryvdh/laravel-ide-helper/pull/1031) - Add support for macros of all macroable classes [#1006 / domkrm](https://github.com/barryvdh/laravel-ide-helper/pull/1006) ## 2020-08-11, 2.8.0 ### Added - Add static return type to builder methods [#924 / dmason30](https://github.com/barryvdh/laravel-ide-helper/pull/924) - Add `optional` to meta generator for PhpStorm [#932 / halaei](https://github.com/barryvdh/laravel-ide-helper/pull/932) - Decimal columns as string in Models [#948 / fgibaux](https://github.com/barryvdh/laravel-ide-helper/pull/948) - Simplify full namespaces for already included resources [#954 / LANGERGabriel](https://github.com/barryvdh/laravel-ide-helper/pull/954) - Make writing relation count properties optional [#969 / AegirLeet](https://github.com/barryvdh/laravel-ide-helper/pull/969) - Add more methods able to resolve container instances [#996 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/996) ### Fixed - Test `auth` is bound before detect Auth driver [#946 / zhwei](https://github.com/barryvdh/laravel-ide-helper/pull/946) - Fix inline doc-block for final models [#944 / Gummibeer](https://github.com/barryvdh/laravel-ide-helper/pull/955) ## 2020-04-22, 2.7.0 ### Added - Add `ignored_models` as config option [#890 / pataar](https://github.com/barryvdh/laravel-ide-helper/pull/890) - Infer return type from reflection if no phpdoc given [#906 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/906) - Add custom collection support for get and all methods [#903 / dmason30](https://github.com/barryvdh/laravel-ide-helper/pull/903) - if a model implements interfaces, include them in the stub [#920 / mr-feek](https://github.com/barryvdh/laravel-ide-helper/pull/920) - Generate noinspections PHPStorm tags [#905 / mzglinski](https://github.com/barryvdh/laravel-ide-helper/pull/905) - Added support for Laravel 7 custom casts [#913 / belamov](https://github.com/barryvdh/laravel-ide-helper/pull/913) - Ability to use patterns for model_locations [#921 / 4n70w4](https://github.com/barryvdh/laravel-ide-helper/pull/921) ### Fixed - MorphToMany relations with query not working [#894 / UksusoFF](https://github.com/barryvdh/laravel-ide-helper/pull/894) - Fix camelCase duplicated properties generator [#881 / bop10](https://github.com/barryvdh/laravel-ide-helper/pull/881) - Prevent generation of invalid code for certain parameter default values [#901 / loilo](https://github.com/barryvdh/laravel-ide-helper/pull/901) - Make hasOne and morphOne nullable [#864 / leo108](https://github.com/barryvdh/laravel-ide-helper/pull/864) - Remove unnecessary and wrong definition of SoftDelete methods [#918 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/918) - Unregister meta command custom autoloader when it is no longer needed [#919 / mr-feek](https://github.com/barryvdh/laravel-ide-helper/pull/919) ## 2020-02-25, 2.6.7 ### Added - Support for Laravel 7 [commit by barryvdh](https://github.com/barryvdh/laravel-ide-helper/commit/edd69c5e0508972c81f1f7173236de2459c45814) ## 2019-12-02, 2.6.6 ### Added - Add splat operator (...) support [#860 / ngmy](https://github.com/barryvdh/laravel-ide-helper/pull/860) - Add support for custom date class via Date::use() [#859 / mfn](https://github.com/barryvdh/laravel-ide-helper/pull/859) ### Fixed - Prevent undefined property errors [#877 / matt-allan](https://github.com/barryvdh/laravel-ide-helper/pull/877) --- Missing an older changelog? Feel free to submit a PR! ================================================ FILE: LICENSE.md ================================================ # The MIT License (MIT) Copyright (c) Barry vd. Heuvel > Permission is hereby granted, free of charge, to any person obtaining a copy > of this software and associated documentation files (the "Software"), to deal > in the Software without restriction, including without limitation the rights > to use, copy, modify, merge, publish, distribute, sublicense, and/or sell > copies of the Software, and to permit persons to whom the Software is > furnished to do so, subject to the following conditions: > > The above copyright notice and this permission notice shall be included in > all copies or substantial portions of the Software. > > THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR > IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, > FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE > AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER > LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, > OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN > THE SOFTWARE. ================================================ FILE: README.md ================================================ # IDE Helper Generator for Laravel [![Tests](https://github.com/barryvdh/laravel-ide-helper/actions/workflows/run-tests.yml/badge.svg)](https://github.com/barryvdh/laravel-ide-helper/actions) [![Packagist License](https://img.shields.io/badge/Licence-MIT-blue)](http://choosealicense.com/licenses/mit/) [![Latest Stable Version](https://img.shields.io/packagist/v/barryvdh/laravel-ide-helper?label=Stable)](https://packagist.org/packages/barryvdh/laravel-ide-helper) [![Total Downloads](https://img.shields.io/packagist/dt/barryvdh/laravel-ide-helper?label=Downloads)](https://packagist.org/packages/barryvdh/laravel-ide-helper) [![Fruitcake](https://img.shields.io/badge/Powered%20By-Fruitcake-b2bc35.svg)](https://fruitcake.nl/) **Complete PHPDocs, directly from the source** This package generates helper files that enable your IDE to provide accurate autocompletion. Generation is done based on the files in your project, so they are always up-to-date. The 3.x branch supports Laravel 10 and later. For older version, use the 2.x releases. - [Installation](#installation) - [Usage](#usage) - [Automatic PHPDoc generation for Laravel Facades](#automatic-phpdoc-generation-for-laravel-facades) - [Automatic PHPDocs for models](#automatic-phpdocs-for-models) - [Model Directories](#model-directories) - [Ignore Models](#ignore-models) - [Model Hooks](#model-hooks) - [Automatic PHPDocs generation for Laravel Fluent methods](#automatic-phpdocs-generation-for-laravel-fluent-methods) - [Auto-completion for factory builders](#auto-completion-for-factory-builders) - [PhpStorm Meta for Container instances](#phpstorm-meta-for-container-instances) - [License](#license) ## Installation Require this package with composer using the following command: ```bash composer require --dev barryvdh/laravel-ide-helper ``` ## Usage ### TL;DR Run this to generate autocompletion for Facades. This creates _ide_helper.php ``` php artisan ide-helper:generate ``` Run this to add phpdocs for your models. Add -RW to Reset existing phpdocs and Write to the models directly. ``` php artisan ide-helper:models -RW ``` If you don't want the full _ide_helper.php file, you can run add `--write-eloquent-helper` to the model command to generate small version, which is required for the `@mixin \Eloquent` to be able to add the QueryBuilder methods. If you don't want to add all the phpdocs to your Models directly, you can use `--nowrite` to create a separate file. The `--write-mixin` option can be used to only add a `@mixin` to your models, but add the generated phpdocs in a separate file. This avoids having the results marked as duplicate. _Check out [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) > Note: You do need CodeComplice for Sublime Text: https://github.com/spectacles/CodeComplice ### Automatic PHPDoc generation for Laravel Facades You can now re-generate the docs yourself (for future updates) ```bash php artisan ide-helper:generate ``` This will generate the file `_ide_helper.php` which is expected to be additionally parsed by your IDE for autocomplete. You can use the config `filename` to change its name. You can configure your `composer.json` to do this each time you update your dependencies: ```js "scripts": { "post-update-cmd": [ "Illuminate\\Foundation\\ComposerScripts::postUpdate", "@php artisan ide-helper:generate", "@php artisan ide-helper:meta" ] }, ``` You can also publish the config file to change implementations (ie. interface to specific class) or set defaults for `--helpers`. ```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. 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. If you use [real-time facades](https://laravel.com/docs/master/facades#real-time-facades) in your app, those will also be included in the generated file using a `@mixin` annotation and extending the original class underneath the facade. > **Note**: this feature uses the generated real-time facades files in the `storage/framework/cache` folder. Those files are generated on-demand as you use the real-time facade, so if the framework has not generated that first, it will not be included in the helper file. Run the route/command/code first and then regenerate the helper file and this time the real-time facade will be included in it. 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. ### Automatic PHPDoc generation for macros and mixins This package can generate PHPDocs for macros and mixins which will be added to the `_ide_helper.php` file. But this only works if you use type hinting when declaring a macro. ```php Str::macro('concat', function(string $str1, string $str2) : string { return $str1 . $str2; }); ``` ### Automatic PHPDocs for models 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. > Note: this command requires a working database connection to introspect the table of each model By default, you are asked to overwrite or write to a separate file (`_ide_helper_models.php`). You can write the comments directly to your Model file, using the `--write (-W)` option, or force to not write with `--nowrite (-N)`. Alternatively using the `--write-mixin (-M)` option will only add a mixin tag to your Model file, writing the rest in (`_ide_helper_models.php`). The class name will be different from the model, avoiding the IDE duplicate annoyance. > Please make sure to back up your models, before writing the info. > You need the _ide_helper.php file to add the QueryBuilder methods. You can add --write-eloquent-helper/-E to generate a minimal version. If this file does not exist, you will be prompted for it. Writing to the models should keep the existing comments and only append new properties/methods. It will not update changed properties/methods. With the `--reset (-R)` option, the whole existing PHPDoc is replaced, including any comments that have been made. ```bash php artisan ide-helper:models "App\Models\Post" ``` ```php /** * App\Models\Post * * @property integer $id * @property integer $author_id * @property string $title * @property string $text * @property \Illuminate\Support\Carbon $created_at * @property \Illuminate\Support\Carbon $updated_at * @property-read \User $author * @property-read \Illuminate\Database\Eloquent\Collection|\Comment[] $comments * @method static \Illuminate\Database\Eloquent\Builder|\App\Models\Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|\App\Models\Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|\App\Models\Post query() * @method static \Illuminate\Database\Eloquent\Builder|\App\Models\Post whereTitle($value) * @method static \Illuminate\Database\Eloquent\Builder|\App\Models\Post forAuthors(\User ...$authors) * … */ ``` With the `--write-mixin (-M)` option ```php /** * … * @mixin IdeHelperPost */ ``` #### Model Directories 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 "App\Models\Post" "App\Models\User" ``` 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" ``` You can publish the config file (`php artisan vendor:publish`) and set the default directories. #### Ignore Models Models can be ignored using the `--ignore (-I)` option ```bash php artisan ide-helper:models --ignore="App\Models\Post,App\Models\User" ``` Or can be ignored by setting the `ignored_models` config ```php 'ignored_models' => [ App\Post::class, Api\User::class ], ``` #### Magic `where*` methods Eloquent allows calling `where` on your models, e.g. `Post::whereTitle(…)` and automatically translates this to e.g. `Post::where('title', '=', '…')`. If for some reason it's undesired to have them generated (one for each column), you can disable this via config `write_model_magic_where` and setting it to `false`. #### Magic `*_count` and `*_exists` properties You may use the [`::withCount`](https://laravel.com/docs/master/eloquent-relationships#counting-related-models) and [`::withExists`](https://laravel.com/docs/master/eloquent-relationships#other-aggregate-functions) methods to count the number results from a relationship without actually loading them. Those results are then placed in attributes following the `_count` and `_exists` convention. By default, these attributes are generated in the phpdoc. You can turn them off by setting the config `write_model_relation_count_properties` and `write_model_relation_exists_properties` to `false`. #### Generics annotations Laravel 9 introduced generics annotations in DocBlocks for collections. PhpStorm 2022.3 and above support the use of generics annotations within `@property` and `@property-read` declarations in DocBlocks, e.g. `Collection` instead of `Collection|User[]`. These can be disabled by setting the config `use_generics_annotations` to `false`. #### Support `@comment` based on DocBlock In order to better support IDEs, relations and getters/setters can also add a comment to a property like table columns. Therefore a custom docblock `@comment` is used: ```php class Users extends Model { /** * @comment Get User's full name * * @return string */ public function getFullNameAttribute(): string { return $this->first_name . ' ' .$this->last_name ; } } // => after generate models /** * App\Models\Users * * @property-read string $full_name Get User's full name * … */ ``` #### Dedicated Eloquent Builder methods A new method to the eloquent models was added called `newEloquentBuilder` [Reference](https://timacdonald.me/dedicated-eloquent-model-query-builders/) where we can add support for creating a new dedicated class instead of using local scopes in the model itself. If for some reason it's undesired to have them generated (one for each column), you can disable this via config `write_model_external_builder_methods` and setting it to `false`. #### Custom Relationship Types If you are using relationships not built into Laravel you will need to specify the name and returning class in the config to get proper generation. ```php 'additional_relation_types' => [ 'externalHasMany' => \My\Package\externalHasMany::class ], ``` Found relationships will typically generate a return value based on the name of the relationship. If your custom relationships don't follow this traditional naming scheme you can define its return type manually. The available options are `many` and `morphTo`. ```php 'additional_relation_return_types' => [ 'externalHasMultiple' => 'many' ], ``` #### Model Hooks If you need additional information on your model from sources that are not handled by default, you can hook in to the generation process with model hooks to add extra information on the fly. Simply create a class that implements `ModelHookInterface` and add it to the `model_hooks` array in the config: ```php 'model_hooks' => [ MyCustomHook::class, ], ``` The `run` method will be called during generation for every model and receives the current running `ModelsCommand` and the current `Model`, e.g.: ```php class MyCustomHook implements ModelHookInterface { public function run(ModelsCommand $command, Model $model): void { if (! $model instanceof MyModel) { return; } $command->setProperty('custom', 'string', true, false, 'My custom property'); $command->unsetMethod('method'); $command->setMethod('method', $command->getMethodType($model, '\Some\Class'), ['$param']); } } ``` ```php /** * MyModel * * @property integer $id * @property-read string $custom ``` ### 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(); ``` After publishing vendor, simply change the `include_fluent` line in your `config/ide-helper.php` file into: ```php 'include_fluent' => true, ``` Then run `php artisan ide-helper:generate`, you will now see all Fluent methods recognized by your IDE. ### Auto-completion for factory builders If you would like the `factory()->create()` and `factory()->make()` methods to return the correct model class, you can enable custom factory builders with the `include_factory_builders` line in your `config/ide-helper.php` file. Deprecated for Laravel 8 or latest. ```php 'include_factory_builders' => true, ``` For this to work, you must also publish the PhpStorm Meta file (see below). ## PhpStorm Meta for Container instances It's possible to generate a PhpStorm meta file to [add support for factory design pattern](https://www.jetbrains.com/help/phpstorm/ide-advanced-metadata.html). 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'); // Also works with app(App\SomeClass::class); ``` > Note: You might need to restart PhpStorm and make sure `.phpstorm.meta.php` is indexed. > Note: When you receive a FatalException: class 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). You can change the generated filename via the config `meta_filename`. This can be useful for cases where you want to take advantage of PhpStorm's support of the _directory_ `.phpstorm.meta.php/`: all files placed there are parsed, should you want to provide additional files to PhpStorm. ## License The Laravel IDE Helper Generator is open-sourced software licensed under the [MIT license](http://opensource.org/licenses/MIT) ================================================ FILE: composer.json ================================================ { "name": "barryvdh/laravel-ide-helper", "description": "Laravel IDE Helper, generates correct PHPDocs for all Facade classes, to improve auto-completion.", "license": "MIT", "keywords": [ "laravel", "autocomplete", "ide", "helper", "phpstorm", "netbeans", "sublime", "codeintel", "phpdoc", "dev" ], "authors": [ { "name": "Barry vd. Heuvel", "email": "barryvdh@gmail.com" } ], "require": { "php": "^8.2", "ext-json": "*", "barryvdh/reflection-docblock": "^2.4", "composer/class-map-generator": "^1.0", "illuminate/console": "^11.15 || ^12 || ^13.0", "illuminate/database": "^11.15 || ^12 || ^13.0", "illuminate/filesystem": "^11.15 || ^12 || ^13.0", "illuminate/support": "^11.15 || ^12 || ^13.0" }, "require-dev": { "ext-pdo_sqlite": "*", "friendsofphp/php-cs-fixer": "^3", "illuminate/config": "^11.15 || ^12 || ^13.0", "illuminate/view": "^11.15 || ^12 || ^13.0", "larastan/larastan": "^3.1", "mockery/mockery": "^1.4", "orchestra/testbench": "^9.2 || ^10 || ^11.0", "phpstan/phpstan-phpunit": "^2.0", "phpunit/phpunit": "^10.5 || ^11.5.3 || ^12.5.12", "spatie/phpunit-snapshot-assertions": "^4 || ^5", "vlucas/phpdotenv": "^5" }, "suggest": { "illuminate/events": "Required for automatic helper generation (^6|^7|^8|^9|^10|^11)." }, "minimum-stability": "dev", "prefer-stable": true, "autoload": { "psr-4": { "Barryvdh\\LaravelIdeHelper\\": "src" } }, "autoload-dev": { "psr-4": { "Barryvdh\\LaravelIdeHelper\\Tests\\": "tests" } }, "config": { "allow-plugins": { "composer/package-versions-deprecated": true }, "sort-packages": true }, "extra": { "branch-alias": { "dev-master": "3.7-dev" }, "laravel": { "providers": [ "Barryvdh\\LaravelIdeHelper\\IdeHelperServiceProvider" ] } }, "scripts": { "analyze": "phpstan", "analyze-set-baseline": "phpstan --generate-baseline", "check-style": [ "php-cs-fixer fix --diff --diff-format=udiff --dry-run", "php-cs-fixer fix --diff --diff-format=udiff --dry-run --config=.php_cs.tests.php" ], "fix-style": [ "php-cs-fixer fix", "php-cs-fixer fix --config=.php-cs-fixer.tests.php" ], "test": "phpunit", "test-ci": "phpunit", "test-regenerate": "phpunit -d --update-snapshots" } } ================================================ FILE: config/ide-helper.php ================================================ '_ide_helper.php', /* |-------------------------------------------------------------------------- | Models filename |-------------------------------------------------------------------------- | | The default filename for the models helper file. | */ 'models_filename' => '_ide_helper_models.php', /* |-------------------------------------------------------------------------- | PhpStorm meta filename |-------------------------------------------------------------------------- | | PhpStorm also supports the directory `.phpstorm.meta.php/` with arbitrary | files in it, should you need additional files for your project; e.g. | `.phpstorm.meta.php/laravel_ide_Helper.php'. | */ 'meta_filename' => '.phpstorm.meta.php', /* |-------------------------------------------------------------------------- | Fluent helpers |-------------------------------------------------------------------------- | | Set to true to generate commonly used Fluent methods. | */ 'include_fluent' => false, /* |-------------------------------------------------------------------------- | Write model query methods |-------------------------------------------------------------------------- | | Set to false to disable generated docs for the 'query()', 'newQuery()' and 'newModelQuery()' methods. | */ 'write_query_methods' => true, /* |-------------------------------------------------------------------------- | Write model magic methods |-------------------------------------------------------------------------- | | Set to false to disable write magic methods of model. | */ 'write_model_magic_where' => true, /* |-------------------------------------------------------------------------- | Write model external Eloquent builder methods |-------------------------------------------------------------------------- | | Set to false to disable write external Eloquent builder methods. | */ 'write_model_external_builder_methods' => true, /* |-------------------------------------------------------------------------- | Write model relation count and exists properties |-------------------------------------------------------------------------- | | Set to false to disable writing of relation count and exists properties | to model DocBlocks. | */ 'write_model_relation_count_properties' => true, 'write_model_relation_exists_properties' => false, /* |-------------------------------------------------------------------------- | Write Eloquent model mixins |-------------------------------------------------------------------------- | | This will add the necessary DocBlock mixins to the model class | contained in the Laravel framework. This helps the IDE with | auto-completion. | | Please be aware that this setting changes a file within the /vendor directory. | */ 'write_eloquent_model_mixins' => false, /* |-------------------------------------------------------------------------- | Helper files to include |-------------------------------------------------------------------------- | | Include helper files. By default not included, but can be toggled with the | -- helpers (-H) option. Extra helper files can be included. | */ 'include_helpers' => false, 'helper_files' => [ base_path() . '/vendor/laravel/framework/src/Illuminate/Support/helpers.php', base_path() . '/vendor/laravel/framework/src/Illuminate/Foundation/helpers.php', ], /* |-------------------------------------------------------------------------- | Model locations to include |-------------------------------------------------------------------------- | | Define in which directories the ide-helper:models command should look | for models. | | glob patterns are supported to easier reach models in sub-directories, | e.g. `app/Services/* /Models` (without the space). | */ 'model_locations' => [ 'app', ], /* |-------------------------------------------------------------------------- | Models to ignore |-------------------------------------------------------------------------- | | Define which models should be ignored. | */ 'ignored_models' => [ // App\MyModel::class, ], /* |-------------------------------------------------------------------------- | Models hooks |-------------------------------------------------------------------------- | | Define which hook classes you want to run for models to add custom information. | | Hooks should implement Barryvdh\LaravelIdeHelper\Contracts\ModelHookInterface. | */ 'model_hooks' => [ // App\Support\IdeHelper\MyModelHook::class ], /* |-------------------------------------------------------------------------- | Extra classes |-------------------------------------------------------------------------- | | These implementations are not really extended, but called with magic functions. | */ 'extra' => [ 'Eloquent' => ['Illuminate\Database\Eloquent\Builder', 'Illuminate\Database\Query\Builder'], 'Session' => ['Illuminate\Session\Store'], ], 'magic' => [], /* |-------------------------------------------------------------------------- | Interface implementations |-------------------------------------------------------------------------- | | These interfaces will be replaced with the implementing class. Some interfaces | are detected by the helpers, others can be listed below. | */ 'interfaces' => [ // App\MyInterface::class => App\MyImplementation::class, ], /* |-------------------------------------------------------------------------- | Support for camel cased models |-------------------------------------------------------------------------- | | There are some Laravel packages (such as Eloquence) that allow for accessing | Eloquent model properties via camel case, instead of snake case. | | Enabling this option will support these packages by saving all model | properties as camel case, instead of snake case. | | For example, normally you would see this: | | * @property \Illuminate\Support\Carbon $created_at | * @property \Illuminate\Support\Carbon $updated_at | | With this enabled, the properties will be this: | | * @property \Illuminate\Support\Carbon $createdAt | * @property \Illuminate\Support\Carbon $updatedAt | | Note, it is currently an all-or-nothing option. | */ 'model_camel_case_properties' => false, /* |-------------------------------------------------------------------------- | Property casts |-------------------------------------------------------------------------- | | Cast the given "real type" to the given "type". | */ 'type_overrides' => [ 'integer' => 'int', 'boolean' => 'bool', ], /* |-------------------------------------------------------------------------- | Include DocBlocks from classes |-------------------------------------------------------------------------- | | Include DocBlocks from classes to allow additional code inspection for | magic methods and properties. | */ 'include_class_docblocks' => false, /* |-------------------------------------------------------------------------- | Force FQN usage |-------------------------------------------------------------------------- | | Use the fully qualified (class) name in DocBlocks, | even if the class exists in the same namespace | or there is an import (use className) of the class. | */ 'force_fqn' => false, /* |-------------------------------------------------------------------------- | Use generics syntax |-------------------------------------------------------------------------- | | Use generics syntax within DocBlocks, | e.g. `Collection` instead of `Collection|User[]`. | */ 'use_generics_annotations' => true, /* |-------------------------------------------------------------------------- | Default return types for macros |-------------------------------------------------------------------------- | | Define default return types for macros without explicit return types. | e.g. `\Illuminate\Database\Query\Builder::class => 'static'`, | `\Illuminate\Support\Str::class => 'string'` | */ 'macro_default_return_types' => [ Illuminate\Http\Client\Factory::class => Illuminate\Http\Client\PendingRequest::class, ], /* |-------------------------------------------------------------------------- | Additional relation types |-------------------------------------------------------------------------- | | Sometimes it's needed to create custom relation types. The key of the array | is the relationship method name. The value of the array is the fully-qualified | class name of the relationship, e.g. `'relationName' => RelationShipClass::class`. | */ 'additional_relation_types' => [], /* |-------------------------------------------------------------------------- | Additional relation return types |-------------------------------------------------------------------------- | | When using custom relation types its possible for the class name to not contain | the proper return type of the relation. The key of the array is the relationship | method name. The value of the array is the return type of the relation ('many' | or 'morphTo'). | e.g. `'relationName' => 'many'`. | */ 'additional_relation_return_types' => [], /* |-------------------------------------------------------------------------- | Enforce nullable Eloquent relationships on not null columns |-------------------------------------------------------------------------- | | When set to true (default), this option enforces nullable Eloquent relationships. | However, in cases where the application logic ensures the presence of related | records it may be desirable to set this option to false to avoid unwanted null warnings. | | Default: true | A not null column with no foreign key constraint will have a "nullable" relationship. | * @property int $not_null_column_with_no_foreign_key_constraint | * @property-read BelongsToVariation|null $notNullColumnWithNoForeignKeyConstraint | | Option: false | A not null column with no foreign key constraint will have a "not nullable" relationship. | * @property int $not_null_column_with_no_foreign_key_constraint | * @property-read BelongsToVariation $notNullColumnWithNoForeignKeyConstraint | */ 'enforce_nullable_relationships' => true, /* |-------------------------------------------------------------------------- | Make soft deletable relations nullable |-------------------------------------------------------------------------- | | When set to true (default), relationships to models using SoftDeletes trait | will be marked as nullable. This is because soft-deleted records are excluded | from queries by default, meaning even non-nullable foreign keys can return | null when the related model is soft-deleted. | | Default: true | A relationship to a soft-deletable model will include |null in the type: | * @property-read Team|null $team | | Option: false | A relationship to a soft-deletable model will NOT include |null (unless | nullable for other reasons such as nullable foreign key column): | * @property-read Team $team | */ 'soft_deletes_force_nullable' => true, /* |-------------------------------------------------------------------------- | Run artisan commands after migrations to generate model helpers |-------------------------------------------------------------------------- | | The specified commands should run after migrations are finished running. | */ 'post_migrate' => [ // 'ide-helper:models --nowrite', ], ]; ================================================ FILE: php-templates/LICENSE.md ================================================ The MIT License (MIT) Copyright (c) Taylor Otwell Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. ================================================ FILE: php-templates/README.md ================================================ The templates here are based on the official VS Code extension by Laravel https://github.com/laravel/vs-code-extension Modifications: - return instead of echo - do not serialize to JSON ================================================ FILE: php-templates/auth.php ================================================ map(function ($policy, $key) { $reflection = new ReflectionFunction($policy); $policyClass = null; $closureThis = $reflection->getClosureThis(); if ($closureThis && get_class($closureThis) === Illuminate\Auth\Access\Gate::class) { $vars = $reflection->getClosureUsedVariables(); if (isset($vars['callback'])) { [$policyClass, $method] = explode('@', $vars['callback']); $reflection = new ReflectionMethod($policyClass, $method); } } return [ 'key' => $key, 'uri' => $reflection->getFileName(), 'policy_class' => $policyClass, 'lineNumber' => $reflection->getStartLine(), ]; }) ->merge( collect(Illuminate\Support\Facades\Gate::policies())->flatMap(function ($policy, $model) { $methods = (new ReflectionClass($policy))->getMethods(); return collect($methods)->map(function (ReflectionMethod $method) use ($policy) { return [ 'key' => $method->getName(), 'uri' => $method->getFileName(), 'policy_class' => $policy, 'lineNumber' => $method->getStartLine(), ]; })->filter(function ($ability) { return !in_array($ability['key'], ['allow', 'deny']); }); }), ) ->values() ->groupBy('key'); ================================================ FILE: php-templates/configs.php ================================================ merge(glob(config_path('**/*.php'))) ->map(fn ($path) => [ (string) Illuminate\Support\Str::of($path) ->replace([config_path('/'), '.php'], '') ->replace('/', '.'), $path, ]); $vendor = collect(glob(base_path('vendor/**/**/config/*.php')))->map(fn ( $path ) => [ (string) Illuminate\Support\Str::of($path) ->afterLast('/config/') ->replace('.php', '') ->replace('/', '.'), $path, ]); $configPaths = $local ->merge($vendor) ->groupBy(0) ->map(fn ($items) => $items->pluck(1)); $cachedContents = []; $cachedParsed = []; function vsCodeGetConfigValue($value, $key, $configPaths) { $parts = explode('.', $key); $toFind = $key; $found = null; while (count($parts) > 0) { array_pop($parts); $toFind = implode('.', $parts); if ($configPaths->has($toFind)) { $found = $toFind; break; } } if ($found === null) { return null; } $file = null; $line = null; if ($found === $key) { $file = $configPaths->get($found)[0]; } else { foreach ($configPaths->get($found) as $path) { $cachedContents[$path] ??= file_get_contents($path); $cachedParsed[$path] ??= token_get_all($cachedContents[$path]); $keysToFind = Illuminate\Support\Str::of($key) ->replaceFirst($found, '') ->ltrim('.') ->explode('.'); if (is_numeric($keysToFind->last())) { $index = $keysToFind->pop(); if ($index !== '0') { return null; } $key = collect(explode('.', $key)); $key->pop(); $key = $key->implode('.'); $value = []; } $nextKey = $keysToFind->shift(); $expectedDepth = 1; $depth = 0; foreach ($cachedParsed[$path] as $token) { if ($token === '[') { $depth++; } if ($token === ']') { $depth--; } if (!is_array($token)) { continue; } $str = trim($token[1], '"\''); if ( $str === $nextKey && $depth === $expectedDepth && $token[0] === T_CONSTANT_ENCAPSED_STRING ) { $nextKey = $keysToFind->shift(); $expectedDepth++; if ($nextKey === null) { $file = $path; $line = $token[2]; break; } } } if ($file) { break; } } } return [ 'name' => $key, 'value' => $value, 'file' => $file === null ? null : str_replace(base_path('/'), '', $file), 'line' => $line, ]; } return collect(Illuminate\Support\Arr::dot(config()->all())) ->map(fn ($value, $key) => vsCodeGetConfigValue($value, $key, $configPaths)) ->filter() ->values(); ================================================ FILE: php-templates/middleware.php ================================================ getMiddlewareGroups()) ->merge(app("Illuminate\Contracts\Http\Kernel")->getRouteMiddleware()) ->map(function ($middleware, $key) { $result = [ 'class' => null, 'uri' => null, 'startLine' => null, 'parameters' => null, 'groups' => [], ]; if (is_array($middleware)) { $result['groups'] = collect($middleware)->map(function ($m) { if (!class_exists($m)) { return [ 'class' => $m, 'uri' => null, 'startLine' => null, ]; } $reflected = new ReflectionClass($m); $reflectedMethod = $reflected->getMethod('handle'); return [ 'class' => $m, 'uri' => $reflected->getFileName(), 'startLine' => $reflectedMethod->getFileName() === $reflected->getFileName() ? $reflectedMethod->getStartLine() : null, ]; })->all(); return $result; } $reflected = new ReflectionClass($middleware); $reflectedMethod = $reflected->getMethod('handle'); $result = array_merge($result, [ 'class' => $middleware, 'uri' => $reflected->getFileName(), 'startLine' => $reflectedMethod->getStartLine(), ]); $parameters = collect($reflectedMethod->getParameters()) ->filter(function ($rc) { return $rc->getName() !== 'request' && $rc->getName() !== 'next'; }) ->map(function ($rc) { return $rc->getName() . ($rc->isVariadic() ? '...' : ''); }); if ($parameters->isEmpty()) { return $result; } return array_merge($result, [ 'parameters' => $parameters->implode(','), ]); }); ================================================ FILE: php-templates/routes.php ================================================ getActionName() === 'Closure') { return new ReflectionFunction($route->getAction()['uses']); } if (!str_contains($route->getActionName(), '@')) { return new ReflectionClass($route->getActionName()); } try { return new ReflectionMethod($route->getControllerClass(), $route->getActionMethod()); } catch (Throwable $e) { $namespace = app(Illuminate\Routing\UrlGenerator::class)->getRootControllerNamespace() ?? (app()->getNamespace() . 'Http\Controllers'); return new ReflectionMethod( $namespace . '\\' . ltrim($route->getControllerClass(), '\\'), $route->getActionMethod(), ); } } return collect(app('router')->getRoutes()->getRoutes()) ->map(function (Illuminate\Routing\Route $route) { try { $reflection = vsCodeGetRouterReflection($route); } catch (Throwable $e) { $reflection = null; } return [ 'method' => collect($route->methods())->filter(function ($method) { return $method !== 'HEAD'; })->implode('|'), 'uri' => $route->uri(), 'name' => $route->getName(), 'action' => $route->getActionName(), 'parameters' => $route->parameterNames(), 'filename' => $reflection ? $reflection->getFileName() : null, 'line' => $reflection ? $reflection->getStartLine() : null, ]; }) ; ================================================ FILE: php-templates/translations.php ================================================ getExtension() !== 'php') { return null; } $filePath = $file->getRealPath(); $relativePath = trim(str_replace($path, '', $file->getPath()), DIRECTORY_SEPARATOR); $lang = explode(DIRECTORY_SEPARATOR, $relativePath)[0] ?? null; if (!$lang) { return null; } $keyPath = str_replace($path . DIRECTORY_SEPARATOR . $lang . DIRECTORY_SEPARATOR, '', $filePath); $keyWithSlashes = str_replace('.php', '', $keyPath); $baseKey = str_replace(DIRECTORY_SEPARATOR, '.', $keyWithSlashes); if ($namespace) { $baseKey = "{$namespace}::{$baseKey}"; } try { $translations = require $filePath; } catch (Throwable $e) { return null; } if (!is_array($translations)) { return null; } $fileLines = Illuminate\Support\Facades\File::lines($filePath); $lines = []; $inComment = false; foreach ($fileLines as $index => $line) { $trimmed = trim($line); if (str_starts_with($trimmed, '/*')) { $inComment = true; } if ($inComment) { if (str_ends_with($trimmed, '*/')) { $inComment = false; } continue; } if (str_starts_with($trimmed, '//')) { continue; } $lines[] = [$index + 1, $trimmed]; } return [ 'k' => $baseKey, 'la' => $lang, 'vs' => collect(Illuminate\Support\Arr::dot($translations)) ->map( fn ($value, $dotKey) => vsCodeTranslationValue( $dotKey, $value, str_replace(base_path(DIRECTORY_SEPARATOR), '', $filePath), $lines ) ) ->filter(), ]; } function vsCodeTranslationValue($key, $value, $file, $lines): ?array { if (is_array($value)) { return null; } $lineNumber = 1; $keys = explode('.', $key); $currentKey = array_shift($keys); foreach ($lines as $line) { if ( strpos($line[1], '"' . $currentKey . '"') !== false || strpos($line[1], "'" . $currentKey . "'") !== false ) { $lineNumber = $line[0]; $currentKey = array_shift($keys); } if ($currentKey === null) { break; } } return [ 'v' => $value, 'p' => $file, 'li' => $lineNumber, 'pa' => preg_match_all("/\:([A-Za-z0-9_]+)/", $value, $matches) ? $matches[1] : [], ]; } function vscodeCollectTranslations(string $path, ?string $namespace = null) { $realPath = realpath($path); if (!is_dir($realPath)) { return collect(); } return collect(Illuminate\Support\Facades\File::allFiles($realPath)) ->map(fn ($file) => vsCodeGetTranslationsFromFile($file, $path, $namespace)) ->filter(); } $loader = app('translator')->getLoader(); $namespaces = $loader->namespaces(); $reflection = new ReflectionClass($loader); $property = $reflection->hasProperty('paths') ? $reflection->getProperty('paths') : $reflection->getProperty('path'); $paths = Illuminate\Support\Arr::wrap($property->getValue($loader)); $default = collect($paths)->flatMap( fn ($path) => vscodeCollectTranslations($path) ); $namespaced = collect($namespaces)->flatMap( fn ($path, $namespace) => vscodeCollectTranslations($path, $namespace) ); $final = []; foreach ($default->merge($namespaced) as $value) { if (!isset($value['vs']) || !is_iterable($value['vs'])) { continue; } foreach ($value['vs'] as $key => $v) { $dotKey = "{$value['k']}.{$key}"; if (!isset($final[$dotKey])) { $final[$dotKey] = []; } $final[$dotKey][$value['la']] = $v; if ($value['la'] === Illuminate\Support\Facades\App::currentLocale()) { $final[$dotKey]['default'] = $v; } } } return collect($final); ================================================ FILE: php-templates/views.php ================================================ files() ->name('*.blade.php') ->in($path) as $file ) { $paths[] = [ 'path' => str_replace(base_path(DIRECTORY_SEPARATOR), '', $file->getRealPath()), 'isVendor' => str_contains($file->getRealPath(), base_path('vendor')), 'key' => Illuminate\Support\Str::of($file->getRealPath()) ->replace(realpath($path), '') ->replace('.blade.php', '') ->ltrim(DIRECTORY_SEPARATOR) ->replace(DIRECTORY_SEPARATOR, '.'), ]; } return $paths; } $paths = collect( app('view') ->getFinder() ->getPaths() )->flatMap(function ($path) { return vsCodeFindBladeFiles($path); }); $hints = collect( app('view') ->getFinder() ->getHints() )->flatMap(function ($paths, $key) { return collect($paths)->flatMap(function ($path) use ($key) { return collect(vsCodeFindBladeFiles($path))->map(function ($value) use ( $key ) { return array_merge($value, ['key' => "{$key}::{$value['key']}"]); }); }); }); [$local, $vendor] = $paths ->merge($hints) ->values() ->partition(function ($v) { return !$v['isVendor']; }); return $local ->sortBy('key', SORT_NATURAL) ->merge($vendor->sortBy('key', SORT_NATURAL)); ================================================ FILE: phpstan-baseline.neon ================================================ parameters: ignoreErrors: - message: '#^File ends with a trailing whitespace\. This may cause problems when running the code in the web browser\. Remove the closing \?\> mark or remove the whitespace\.$#' identifier: whitespace.fileEnd count: 1 path: resources/views/helper.php - message: '#^Call to an undefined method Illuminate\\Contracts\\Filesystem\\Filesystem\:\:requireOnce\(\)\.$#' identifier: method.notFound count: 1 path: src/Console/MetaCommand.php - message: '#^Call to an undefined method Illuminate\\Contracts\\Foundation\\Application\:\:getBindings\(\)\.$#' identifier: method.notFound count: 1 path: src/Console/MetaCommand.php - message: '#^Call to an undefined method Barryvdh\\Reflection\\DocBlock\\Tag\:\:getMethodName\(\)\.$#' identifier: method.notFound count: 1 path: src/Console/ModelsCommand.php - message: '#^Call to an undefined method Barryvdh\\Reflection\\DocBlock\\Tag\:\:getType\(\)\.$#' identifier: method.notFound count: 1 path: src/Console/ModelsCommand.php - message: '#^Call to an undefined method Barryvdh\\Reflection\\DocBlock\\Tag\:\:getVariableName\(\)\.$#' identifier: method.notFound count: 1 path: src/Console/ModelsCommand.php - message: '#^Call to an undefined method Illuminate\\Support\\Optional\:\:getNumberOfParameters\(\)\.$#' identifier: method.notFound count: 1 path: src/Console/ModelsCommand.php - message: '#^Call to an undefined method Illuminate\\Support\\Optional\:\:getParameters\(\)\.$#' identifier: method.notFound count: 1 path: src/Console/ModelsCommand.php - message: '#^Call to an undefined method Illuminate\\Support\\Optional\:\:getReturnType\(\)\.$#' identifier: method.notFound count: 1 path: src/Console/ModelsCommand.php - message: '#^Call to an undefined static method Illuminate\\Database\\Eloquent\\Model\:\:newFactory\(\)\.$#' identifier: staticMethod.notFound count: 2 path: src/Console/ModelsCommand.php - message: '#^Call to an undefined method ReflectionFunctionAbstract\:\:getDeclaringClass\(\)\.$#' identifier: method.notFound count: 1 path: src/Method.php ================================================ FILE: phpstan.neon ================================================ includes: - phpstan-baseline.neon - vendor/phpstan/phpstan-phpunit/extension.neon parameters: level: 2 paths: - src - resources/views excludePaths: ================================================ FILE: phpunit.xml.dist ================================================ tests src/ ================================================ FILE: resources/views/helper.php ================================================ /* @noinspection ALL */ // @formatter:off // phpcs:ignoreFile /** * A helper file for Laravel, to provide autocomplete information to your IDE * Generated for Laravel version() ?>. * * This file should not be included in your code, only analyzed by your IDE! * * @author Barry vd. Heuvel * @see https://github.com/barryvdh/laravel-ide-helper */ $aliases) : ?> namespace { getDocComment($s1)) . "\n{$s1}" . $alias->getClassType() ?> getExtendsClass() ?>shouldExtendParentClass()): ?> extends getParentClass() ?> { getMethods() as $method) : ?> getDocComment($s2)) . "\n{$s2}" ?>public static function getName() ?>(getParamsWithDefault() ?>) {getDeclaringClass() !== $method->getRoot()) : ?> //Method inherited from getDeclaringClass() ?> isInstanceCall()) : ?> /** @var getRoot()?> $instance */ shouldReturn() ? 'return ' : '') ?>getRootMethodCall() ?>; } } } $aliases) : ?> namespace { getExtendsNamespace() === '\Illuminate\Database\Eloquent') : ?> getPhpDocTemplates($s1) . "\n" ?> getClassType() ?> getShortName() ?> extends getExtends() ?> {getExtendsNamespace() === '\Illuminate\Database\Eloquent') : ?> getMethods() as $method) : ?> getDocComment($s2)) . "\n" ?> public static function getName() ?>(getParamsWithDefault() ?>) {getDeclaringClass() !== $method->getRoot()) : ?> //Method inherited from getDeclaringClass() ?> isInstanceCall()) : ?> /** @var getRoot()?> $instance */ shouldReturn() ? 'return ' : '') ?>getRootMethodCall() ?>; } } } namespace { /** * @mixin */ class extends {} } namespace { } namespace Illuminate\Support { /** * Methods commonly used in migrations * * @method Fluent after(string $column) Add the after modifier * @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($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 * @method Fluent onDelete(string $action) `on delete` of a foreign key * @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(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 {} } ================================================ FILE: resources/views/meta.php ================================================ $expectedArgumentSets * @var array $expectedArguments * @var string[] $userMethods * @var string $userModel/ * */ ?> /* @noinspection ALL */ // @formatter:off // phpcs:ignoreFile namespace PHPSTORM_META { /** * PhpStorm Meta file, to provide autocomplete information for PhpStorm * * @author Barry vd. Heuvel * @see https://github.com/barryvdh/laravel-ide-helper */ override(, map([ '' => '@', $class) : ?> '' => \::class, ])); override(, map([ '' => \::class, ])); override(, map([ $value) : ?> '' => '', ])); override(\Illuminate\Foundation\Testing\Concerns\InteractsWithContainer::mock(0), map(["" => "@&\Mockery\MockInterface"])); override(\Illuminate\Foundation\Testing\Concerns\InteractsWithContainer::partialMock(0), map(["" => "@&\Mockery\MockInterface"])); override(\Illuminate\Foundation\Testing\Concerns\InteractsWithContainer::instance(0), type(1)); override(\Illuminate\Foundation\Testing\Concerns\InteractsWithContainer::spy(0), map(["" => "@&\Mockery\MockInterface"])); 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)); override(\optional(0), type(0)); $argumentsList) : ?> registerArgumentsSet('', $arg) : ?>,); expectedArguments(, , argumentsSet('')); } ================================================ FILE: src/Alias.php ================================================ * @copyright 2014 Barry vd. Heuvel / 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; use Barryvdh\Reflection\DocBlock; use Barryvdh\Reflection\DocBlock\Context; use Barryvdh\Reflection\DocBlock\ContextFactory; use Barryvdh\Reflection\DocBlock\Serializer as DocBlockSerializer; use Barryvdh\Reflection\DocBlock\Tag\MethodTag; use Barryvdh\Reflection\DocBlock\Tag\TemplateTag; use Closure; use Illuminate\Config\Repository as ConfigRepository; use Illuminate\Database\Eloquent\Builder as EloquentBuilder; use Illuminate\Database\Query\Builder as QueryBuilder; use Illuminate\Support\Facades\Facade; use Illuminate\Support\Traits\Macroable; use ReflectionClass; use Throwable; class Alias { protected $alias; /** @psalm-var class-string $facade */ protected $facade; protected $extends = null; protected $extendsClass = null; protected $extendsNamespace = null; protected $classType = 'class'; protected $short; protected $namespace = '__root'; protected $parentClass; protected $root = null; protected $classes = []; protected $methods = []; protected $usedMethods = []; protected $valid = false; protected $magicMethods = []; protected $interfaces = []; protected $phpdoc = null; protected $classAliases = []; /** @var ConfigRepository */ protected $config; /** @var string[] */ protected $templateNames; /** * @param ConfigRepository $config * @param string $alias * @psalm-param class-string $facade * @param string $facade * @param array $magicMethods * @param array $interfaces */ public function __construct($config, $alias, $facade, $magicMethods = [], $interfaces = []) { $this->alias = $alias; $this->magicMethods = $magicMethods; $this->interfaces = $interfaces; $this->config = $config; // Make the class absolute $facade = '\\' . ltrim($facade, '\\'); $this->facade = $facade; $this->detectRoot(); if (!$this->root || $this->isTrait()) { return; } $this->valid = true; $this->addClass($this->root); $this->detectFake(); $this->detectNamespace(); $this->detectClassType(); $this->detectExtendsNamespace(); $this->detectParentClass(); if (!empty($this->namespace)) { try { $this->classAliases = (new ContextFactory())->createFromReflector(new ReflectionClass($this->root))->getNamespaceAliases(); } catch (Throwable $e) { $this->classAliases = []; } //Create a DocBlock and serializer instance $this->phpdoc = new DocBlock(new ReflectionClass($alias), new Context($this->namespace, $this->classAliases)); } if ($facade === '\Illuminate\Database\Eloquent\Model') { $this->usedMethods = ['decrement' => true, 'increment' => true]; } } /** * Add one or more classes to analyze * * @param array|string $classes */ public function addClass($classes) { $classes = (array)$classes; foreach ($classes as $class) { if (class_exists($class) || interface_exists($class)) { $this->classes[] = $class; } else { echo "Class not exists: $class\r\n"; } } } /** * Check if this class is valid to process. * @return bool */ public function isValid() { return $this->valid; } /** * Get the classtype, 'interface' or 'class' * * @return string */ public function getClasstype() { return $this->classType; } /** * Get the class which this alias extends * * @return null|string */ public function getExtends() { return $this->extends; } /** * Get the class short name which this alias extends * * @return null|string */ public function getExtendsClass() { return $this->extendsClass; } /** * Get the namespace of the class which this alias extends * * @return null|string */ public function getExtendsNamespace() { return $this->extendsNamespace; } /** * Get the parent class of the class which this alias extends * * @return null|string */ public function getParentClass() { return $this->parentClass; } /** * Check if this class should extend the parent class */ public function shouldExtendParentClass() { return $this->parentClass && !is_subclass_of($this->extends, Facade::class); } /** * Get the Alias by which this class is called * * @return string */ public function getAlias() { return $this->alias; } /** * Return the short name (without namespace) */ public function getShortName() { return $this->short; } /** * Get the namespace from the alias * * @return string */ public function getNamespace() { return $this->namespace; } /** * Get the methods found by this Alias * * @return array|Method[] */ public function getMethods() { if (count($this->methods) > 0) { return $this->methods; } $this->addMagicMethods(); $this->detectMethods(); return $this->methods; } /** * Detect class returned by ::fake() */ protected function detectFake() { $facade = $this->facade; if (!is_subclass_of($facade, Facade::class)) { return; } if (!method_exists($facade, 'fake')) { return; } $reflection = new \ReflectionMethod($facade, 'fake'); if ($reflection->getNumberOfRequiredParameters() > 0) { 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 */ protected function detectNamespace() { if (strpos($this->alias, '\\')) { $nsParts = explode('\\', $this->alias); $this->short = array_pop($nsParts); $this->namespace = implode('\\', $nsParts); } else { $this->short = $this->alias; } } /** * Detect the extends namespace */ protected function detectExtendsNamespace() { if (strpos($this->extends, '\\') !== false) { $nsParts = explode('\\', $this->extends); $this->extendsClass = array_pop($nsParts); $this->extendsNamespace = implode('\\', $nsParts); } } /** * Detect the parent class */ protected function detectParentClass() { $reflection = new ReflectionClass($this->root); $parentClass = $reflection->getParentClass(); $this->parentClass = $parentClass ? '\\' . $parentClass->getName() : null; } /** * Detect the class type */ protected function detectClassType() { //Some classes extend the facade if (interface_exists($this->facade)) { $this->classType = 'interface'; $this->extends = $this->facade; } else { $this->classType = 'class'; if (class_exists($this->facade)) { $this->extends = $this->facade; } } } /** * Get the real root of a facade * */ protected function detectRoot(): void { $facade = $this->facade; try { //If possible, get the facade root if (method_exists($facade, 'getFacadeRoot')) { $root = get_class($facade::getFacadeRoot()); } else { $root = $facade; } //If it doesn't exist, skip it if (!class_exists($root) && !interface_exists($root)) { return; } $this->root = $root; //When the database connection is not set, some classes will be skipped } catch (\PDOException $e) { $this->error( 'PDOException: ' . $e->getMessage() . "\nPlease configure your database connection correctly, or use the sqlite memory driver (-M)." . " Skipping $facade." ); } catch (Throwable $e) { $this->error('Exception: ' . $e->getMessage() . "\nSkipping $facade."); } } /** * Detect if this class is a trait or not. * * @return bool */ protected function isTrait() { // Check if the facade is not a Trait return trait_exists($this->facade); } /** * Add magic methods, as defined in the configuration files */ protected function addMagicMethods() { foreach ($this->magicMethods as $magic => $real) { [$className, $name] = explode('::', $real); if ((!class_exists($className) && !interface_exists($className)) || !method_exists($className, $name)) { continue; } $method = new \ReflectionMethod($className, $name); $class = new ReflectionClass($className); if (!isset($this->usedMethods[$magic])) { if ($class !== $this->root) { $this->methods[] = new Method( $method, $class, $magic, $this->interfaces, $this->classAliases, $this->getReturnTypeNormalizers($class), $this->getTemplateNames() ); } $this->usedMethods[$magic] = true; } } } /** * Get the methods for one or multiple classes. * */ protected function detectMethods() { foreach ($this->classes as $class) { $reflection = new ReflectionClass($class); $methods = $reflection->getMethods(\ReflectionMethod::IS_PUBLIC); if ($methods) { foreach ($methods as $method) { if (!isset($this->usedMethods[$method->name])) { // Only add the methods to the output when the root is not the same as the class. // And don't add the __*() methods if ($this->extends !== $class && substr($method->name, 0, 2) !== '__') { $this->methods[] = new Method( $method, $reflection, $method->name, $this->interfaces, $this->classAliases, $this->getReturnTypeNormalizers($reflection), $this->getTemplateNames(), ); } $this->usedMethods[$method->name] = true; } } } // Check if the class is macroable // (Eloquent\Builder is also macroable but doesn't use Macroable trait) if ($class === EloquentBuilder::class || in_array(Macroable::class, $reflection->getTraitNames())) { $properties = $reflection->getStaticProperties(); $macros = isset($properties['macros']) ? $properties['macros'] : []; foreach ($macros as $macro_name => $macro_func) { if (!isset($this->usedMethods[$macro_name])) { try { $method = $this->getMacroFunction($macro_func); } catch (Throwable $e) { // Invalid method, skip continue; } // Add macros $this->methods[] = new Macro( $method, $reflection, $macro_name, $this->interfaces, $this->classAliases, $this->getReturnTypeNormalizers($reflection) ); $this->usedMethods[$macro_name] = true; } } } } } /** * @param ReflectionClass $class * @return array */ protected function getReturnTypeNormalizers($class) { if ($this->alias === 'Eloquent' && in_array($class->getName(), [EloquentBuilder::class, QueryBuilder::class])) { return [ '$this' => '\\' . EloquentBuilder::class . ($this->config->get('ide-helper.use_generics_annotations') ? '' : '|static'), ]; } return []; } /** * @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]); } if (is_object($macro_func) && is_callable($macro_func) && !$macro_func instanceof Closure) { return new \ReflectionMethod($macro_func, '__invoke'); } 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 ''; } if ($this->config->get('ide-helper.include_class_docblocks')) { // if a class doesn't expose any DocBlock tags // we can perform reflection on the class and // add in the original class DocBlock if (count($this->phpdoc->getTags()) === 0) { $class = new ReflectionClass($this->root); $this->phpdoc = new DocBlock($class->getDocComment()); } } $this->removeDuplicateMethodsFromPhpDoc(); return $serializer->getDocComment($this->phpdoc); } /** * @param $prefix * @return string */ public function getPhpDocTemplates($prefix = "\t\t") { $templateDoc = new DocBlock(''); $serializer = new DocBlockSerializer(1, $prefix); foreach ($this->getTemplateNames() as $templateName) { $template = new TemplateTag('template', $templateName); $template->setBound('static'); $template->setDocBlock($templateDoc); $templateDoc->appendTag($template); } return $serializer->getDocComment($templateDoc); } /** * @return string[] */ public function getTemplateNames() { if (!isset($this->templateNames)) { $this->detectTemplateNames(); } return $this->templateNames; } /** * @return void * @throws \ReflectionException */ protected function detectTemplateNames() { $templateNames = []; foreach ($this->classes as $class) { $reflection = new ReflectionClass($class); $traits = collect($reflection->getTraitNames()); $phpdoc = new DocBlock($reflection); $templates = $phpdoc->getTagsByName('template'); /** @var TemplateTag $template */ foreach ($templates as $template) { $templateNames[] = $template->getTemplateName(); } foreach ($traits as $trait) { $phpdoc = new DocBlock(new ReflectionClass($trait)); $templates = $phpdoc->getTagsByName('template'); /** @var TemplateTag $template */ foreach ($templates as $template) { $templateNames[] = $template->getTemplateName(); } } } $this->templateNames = $templateNames; } /** * Removes method tags from the doc comment that already appear as functions inside the class. * This prevents duplicate function errors in the IDE. * * @return void */ protected function removeDuplicateMethodsFromPhpDoc() { $methodNames = []; foreach ($this->getMethods() as $method) { $methodNames[$method->getName()] = true; } foreach ($this->phpdoc->getTags() as $tag) { if ($tag instanceof MethodTag && isset($methodNames[$tag->getMethodName()])) { $this->phpdoc->deleteTag($tag); } } } /** * Output an error. * * @param string $string * @return void */ protected function error($string) { echo $string . "\r\n"; } } ================================================ FILE: src/Console/EloquentCommand.php ================================================ * @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 */ 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); } } ================================================ FILE: src/Console/GeneratorCommand.php ================================================ * @copyright 2014 Barry vd. Heuvel / 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 Barryvdh\LaravelIdeHelper\Generator; use Illuminate\Console\Command; use Illuminate\Contracts\Config\Repository; use Illuminate\Filesystem\Filesystem; use Illuminate\View\Factory; use Symfony\Component\Console\Input\InputArgument; use Symfony\Component\Console\Input\InputOption; /** * A command to generate autocomplete information for your IDE * * @author Barry vd. Heuvel */ class GeneratorCommand extends Command { /** * The console command name. * * @var string */ protected $name = 'ide-helper:generate'; /** * The console command description. * * @var string */ protected $description = 'Generate a new IDE Helper file.'; /** @var \Illuminate\Config\Repository */ protected $config; /** @var Filesystem */ protected $files; /** @var Factory */ protected $view; protected $onlyExtend; /** * * @param \Illuminate\Config\Repository $config * @param Filesystem $files * @param Factory $view */ public function __construct( Repository $config, Filesystem $files, Factory $view ) { $this->config = $config; $this->files = $files; $this->view = $view; parent::__construct(); } /** * Execute the console command. * * @return void */ public function handle() { if ( file_exists(base_path() . '/vendor/compiled.php') || file_exists(base_path() . '/bootstrap/cache/compiled.php') || file_exists(base_path() . '/storage/framework/compiled.php') ) { $this->error( 'Error generating IDE Helper: first delete your compiled file (php artisan clear-compiled)' ); return; } $filename = $this->argument('filename'); // Add the php extension if missing // This is a backwards-compatible shim and can be removed in the future if (substr($filename, -4, 4) !== '.php') { $filename .= '.php'; } if ($this->option('memory')) { $this->useMemoryDriver(); } $helpers = ''; if ($this->option('helpers') || ($this->config->get('ide-helper.include_helpers'))) { foreach ($this->config->get('ide-helper.helper_files', []) as $helper) { if (file_exists($helper)) { $helpers .= str_replace([''], '', $this->files->get($helper)); } } } else { $helpers = ''; } $generator = new Generator($this->config, $this->view, $this->getOutput(), $helpers); if ($this->option('eloquent')) { $content = $generator->generateEloquent(); } else { $content = $generator->generate(); } $written = $this->files->put($filename, $content); if ($written !== false) { $this->info("A new helper file was written to $filename"); if ($this->option('write_mixins')) { Eloquent::writeEloquentModelHelper($this, $this->files); } } else { $this->error("The helper file could not be created at $filename"); } } protected function useMemoryDriver() { //Use a sqlite database in memory, to avoid connection errors on Database facades $this->config->set( 'database.connections.sqlite', [ 'driver' => 'sqlite', 'database' => ':memory:', ] ); $this->config->set('database.default', 'sqlite'); } /** * Get the console command arguments. * * @return array */ protected function getArguments() { $filename = $this->config->get('ide-helper.filename'); return [ [ 'filename', InputArgument::OPTIONAL, 'The path to the helper file', $filename, ], ]; } /** * Get the console command options. * * @return array */ protected function getOptions() { $writeMixins = $this->config->get('ide-helper.write_eloquent_model_mixins'); return [ ['write_mixins', 'W', InputOption::VALUE_OPTIONAL, 'Write mixins to Laravel Model?', $writeMixins], ['helpers', 'H', InputOption::VALUE_NONE, 'Include the helper files'], ['memory', 'M', InputOption::VALUE_NONE, 'Use sqlite memory driver'], ['eloquent', 'E', InputOption::VALUE_NONE, 'Only write Eloquent methods'], ]; } } ================================================ FILE: src/Console/MetaCommand.php ================================================ * @copyright 2015 Barry vd. Heuvel / 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 Dotenv\Parser\Entry; use Dotenv\Parser\Parser; use Illuminate\Console\Command; use Illuminate\Contracts\Config\Repository; use Illuminate\Contracts\View\Factory; use Illuminate\Filesystem\Filesystem; use Illuminate\Support\Collection; use RuntimeException; use Symfony\Component\Console\Input\InputOption; use Symfony\Component\Console\Output\OutputInterface; /** * A command to generate phpstorm meta data * * @author Barry vd. Heuvel */ class MetaCommand extends Command { /** * The console command name. * * @var string */ protected $name = 'ide-helper:meta'; /** * The console command description. * * @var string */ protected $description = 'Generate metadata for PhpStorm'; /** @var \Illuminate\Contracts\Filesystem\Filesystem */ protected $files; /** @var Factory */ protected $view; /** @var Repository */ protected $config; protected $methods = [ 'new \Illuminate\Contracts\Container\Container', '\Illuminate\Container\Container::makeWith(0)', '\Illuminate\Contracts\Container\Container::get(0)', '\Illuminate\Contracts\Container\Container::make(0)', '\Illuminate\Contracts\Container\Container::makeWith(0)', '\App::get(0)', '\App::make(0)', '\App::makeWith(0)', '\app(0)', '\resolve(0)', '\Psr\Container\ContainerInterface::get(0)', ]; protected $configMethods = [ '\config()', '\Illuminate\Config\Repository::get()', '\Illuminate\Support\Facades\Config::get()', ]; protected $userMethods = [ '\auth()->user()', '\Illuminate\Contracts\Auth\Guard::user()', '\Illuminate\Support\Facades\Auth::user()', '\request()->user()', '\Illuminate\Http\Request::user()', '\Illuminate\Support\Facades\Request::user()', ]; protected $templateCache = []; /** * * @param Filesystem $files * @param Factory $view * @param Repository $config */ public function __construct( Filesystem $files, Factory $view, Repository $config ) { $this->files = $files; $this->view = $view; $this->config = $config; parent::__construct(); } /** * Execute the console command. * * @return void */ public function handle() { $ourAutoloader = $this->registerClassAutoloadExceptions(); $bindings = []; foreach ($this->getAbstracts() as $abstract) { // Validator and seeder cause problems if (in_array($abstract, ['validator', 'seeder'])) { continue; } try { $concrete = $this->laravel->make($abstract); if ($concrete === null) { throw new RuntimeException("Cannot create instance for '$abstract', received 'null'"); } $reflectionClass = new \ReflectionClass($concrete); if (is_object($concrete) && !$reflectionClass->isAnonymous() && $abstract !== get_class($concrete)) { $bindings[$abstract] = get_class($concrete); } } catch (\Throwable $e) { if ($this->output->getVerbosity() >= OutputInterface::VERBOSITY_VERBOSE) { $this->comment("Cannot make '$abstract': " . $e->getMessage()); } } } $this->unregisterClassAutoloadExceptions($ourAutoloader); $configValues = $this->loadTemplate('configs')->pluck('value', 'name')->map(function ($value, $key) { return gettype($value); }); $defaultUserModel = $this->config->get('auth.providers.users.model', $this->config->get('auth.model', 'App\User')); $content = $this->view->make('ide-helper::meta', [ 'bindings' => $bindings, 'methods' => $this->methods, 'configMethods' => $this->configMethods, 'configValues' => $configValues, 'expectedArgumentSets' => $this->getExpectedArgumentSets(), 'expectedArguments' => $this->getExpectedArguments(), 'userModel' => $defaultUserModel, 'userMethods' => $this->userMethods, ])->render(); $filename = $this->option('filename'); $written = $this->files->put($filename, $content); if ($written !== false) { $this->info("A new meta file was written to $filename"); } else { $this->error("The meta file could not be created at $filename"); } } /** * Get a list of abstracts from the Laravel Application. * * @return array */ protected function getAbstracts() { $abstracts = $this->laravel->getBindings(); // Return the abstract names only $keys = array_keys($abstracts); sort($keys); return $keys; } /** * Register an autoloader the throws exceptions when a class is not found. * * @return callable */ protected function registerClassAutoloadExceptions(): callable { $aliases = array_filter([...$this->getAbstracts(), 'config'], fn ($abstract) => !str_contains($abstract, '\\')); $autoloader = function ($class) use ($aliases) { // ignore aliases as they're meant to be resolved elsewhere if (in_array($class, $aliases, true)) { return; } // Don't throw when class existence is being checked via class_exists(), // interface_exists(), trait_exists(), or enum_exists(). These functions // expect the autoloader to return gracefully when the class doesn't exist. // Throwing here would break libraries that use class_exists() to check for // optional dependencies (e.g. Doctrine ORM checking for removed classes). $existsFunctions = ['class_exists', 'interface_exists', 'trait_exists', 'enum_exists']; foreach (debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 3) as $frame) { if (isset($frame['function']) && in_array($frame['function'], $existsFunctions, true)) { return; } } throw new \ReflectionException("Class '$class' not found."); }; spl_autoload_register($autoloader); return $autoloader; } protected function getExpectedArgumentSets() { return [ 'auth' => $this->loadTemplate('auth')->keys()->filter()->toArray(), 'configs' => $this->loadTemplate('configs')->pluck('name')->filter()->toArray(), 'middleware' => $this->loadTemplate('middleware')->keys()->filter()->toArray(), 'routes' => $this->loadTemplate('routes')->pluck('name')->filter()->toArray(), 'views' => $this->loadTemplate('views')->pluck('key')->filter()->map(function ($value) { return (string) $value; })->toArray(), 'translations' => $this->loadTemplate('translations')->filter()->keys()->toArray(), 'env' => $this->getEnv(), ]; } protected function getExpectedArguments() { return [ [ 'class' => '\Illuminate\Support\Facades\Gate', 'method' => [ 'has', 'allows', 'denies', 'check', 'any', 'none', 'authorize', 'inspect', ], 'argumentSet' => 'auth', ], [ 'class' => ['\Illuminate\Support\Facades\Route', '\Illuminate\Support\Facades\Auth', 'Illuminate\Foundation\Auth\Access\Authorizable'], 'method' => ['can', 'cannot', 'cant'], 'argumentSet' => 'auth', ], [ 'class' => ['Illuminate\Contracts\Auth\Access\Authorizable'], 'method' => ['can'], 'argumentSet' => 'auth', ], [ 'class' => ['\Illuminate\Config\Repository', '\Illuminate\Support\Facades\Config'], 'method' => [ // 'get', // config() and Config::Get() are added with return type hints already 'getMany', 'set', 'string', 'integer', 'boolean', 'float', 'array', 'prepend', 'push', ], 'argumentSet' => 'configs', ], [ 'class' => ['\Illuminate\Support\Facades\Route', '\Illuminate\Routing\Router'], 'method' => ['middleware', 'withoutMiddleware'], 'argumentSet' => 'middleware', ], [ 'method' => ['route', 'to_route', 'signedRoute'], 'argumentSet' => 'routes', ], [ 'class' => [ '\Illuminate\Support\Facades\Redirect', '\Illuminate\Support\Facades\URL', '\Illuminate\Routing\Redirector', '\Illuminate\Routing\UrlGenerator', ], 'method' => ['route', 'signedRoute', 'temporarySignedRoute'], 'argumentSet' => 'routes', ], [ 'method' => 'view', 'argumentSet' => 'views', ], [ 'class' => ['\Illuminate\Support\Facades\View', '\Illuminate\View\Factory'], 'method' => 'make', 'argumentSet' => 'views', ], [ 'method' => ['__', 'trans'], 'argumentSet' => 'translations', ], [ 'class' => ['\Illuminate\Contracts\Translation\Translator'], 'method' => ['get'], 'argumentSet' => 'translations', ], [ 'method' => 'env', 'argumentSet' => 'env', ], [ 'class' => '\Illuminate\Support\Env', 'method' => 'get', 'argumentSet' => 'env', ], ]; } /** * @return Collection */ protected function loadTemplate($name) { if (!isset($this->templateCache[$name])) { $file = __DIR__ . '/../../php-templates/' . basename($name) . '.php'; try { $value = $this->files->requireOnce($file) ?: []; } catch (\Throwable $e) { $value = []; $this->warn('Cannot load template for ' . $name . ': ' . $e->getMessage()); } if (!$value instanceof Collection) { $value = collect($value); } $this->templateCache[$name] = $value; } return $this->templateCache[$name]; } /** * Get the console command options. * * @return array */ protected function getOptions() { $filename = $this->config->get('ide-helper.meta_filename'); return [ ['filename', 'F', InputOption::VALUE_OPTIONAL, 'The path to the meta file', $filename], ]; } protected function getEnv() { $envPath = base_path('.env'); if (!file_exists($envPath)) { return []; } $parser = new Parser(); $entries = $parser->parse(file_get_contents($envPath)); return collect($entries)->map(function (Entry $entry) { return $entry->getName(); }); } /** * Remove our custom autoloader that we pushed onto the autoload stack * * @param callable $ourAutoloader */ private function unregisterClassAutoloadExceptions(callable $ourAutoloader): void { spl_autoload_unregister($ourAutoloader); } } ================================================ FILE: src/Console/ModelsCommand.php ================================================ * @copyright 2014 Barry vd. Heuvel / 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\Contracts\ModelHookInterface; use Barryvdh\LaravelIdeHelper\Generator; use Barryvdh\LaravelIdeHelper\Parsers\PhpDocReturnTypeParser; use Barryvdh\Reflection\DocBlock; use Barryvdh\Reflection\DocBlock\Context; use Barryvdh\Reflection\DocBlock\ContextFactory; use Barryvdh\Reflection\DocBlock\Serializer as DocBlockSerializer; use Barryvdh\Reflection\DocBlock\Tag; use Composer\ClassMapGenerator\ClassMapGenerator; use Illuminate\Console\Command; use Illuminate\Contracts\Config\Repository; use Illuminate\Contracts\Database\Eloquent\Castable; use Illuminate\Contracts\Database\Eloquent\CastsAttributes; use Illuminate\Contracts\Database\Eloquent\CastsInboundAttributes; use Illuminate\Database\Eloquent\Casts\AsArrayObject; use Illuminate\Database\Eloquent\Casts\AsCollection; use Illuminate\Database\Eloquent\Casts\AsEnumCollection; use Illuminate\Database\Eloquent\Casts\Attribute; use Illuminate\Database\Eloquent\Factories\Factory; use Illuminate\Database\Eloquent\Model; use Illuminate\Database\Eloquent\Relations\BelongsTo; use Illuminate\Database\Eloquent\Relations\BelongsToMany; use Illuminate\Database\Eloquent\Relations\HasMany; use Illuminate\Database\Eloquent\Relations\HasManyThrough; use Illuminate\Database\Eloquent\Relations\HasOne; use Illuminate\Database\Eloquent\Relations\HasOneThrough; use Illuminate\Database\Eloquent\Relations\MorphMany; use Illuminate\Database\Eloquent\Relations\MorphOne; use Illuminate\Database\Eloquent\Relations\MorphPivot; use Illuminate\Database\Eloquent\Relations\MorphTo; use Illuminate\Database\Eloquent\Relations\MorphToMany; use Illuminate\Database\Eloquent\Relations\Pivot; use Illuminate\Database\Eloquent\Relations\Relation; use Illuminate\Database\Schema\Builder; use Illuminate\Filesystem\Filesystem; use Illuminate\Support\Arr; use Illuminate\Support\Collection; use Illuminate\Support\Str; use Illuminate\View\Factory as ViewFactory; use ReflectionClass; use ReflectionNamedType; use ReflectionObject; use ReflectionType; use Symfony\Component\Console\Input\InputArgument; use Symfony\Component\Console\Input\InputOption; use Symfony\Component\Console\Output\OutputInterface; use Throwable; /** * A command to generate autocomplete information for your IDE * * @author Barry vd. Heuvel */ class ModelsCommand extends Command { protected const RELATION_TYPES = [ 'hasMany' => HasMany::class, 'hasManyThrough' => HasManyThrough::class, 'hasOneThrough' => HasOneThrough::class, 'belongsToMany' => BelongsToMany::class, 'hasOne' => HasOne::class, 'belongsTo' => BelongsTo::class, 'morphOne' => MorphOne::class, 'morphTo' => MorphTo::class, 'morphMany' => MorphMany::class, 'morphToMany' => MorphToMany::class, 'morphedByMany' => MorphToMany::class, ]; /** * @var Filesystem $files */ protected $files; /** * @var Repository */ protected $config; /** @var ViewFactory */ protected $view; /** * The console command name. * * @var string */ protected $name = 'ide-helper:models'; /** * @var string */ protected $filename; /** * The console command description. * * @var string */ protected $description = 'Generate autocompletion for models'; protected $write_model_magic_where; protected $write_model_relation_count_properties; protected $write_model_relation_exists_properties; protected $properties = []; protected $methods = []; protected $write = false; protected $write_mixin = false; protected $dirs = []; protected $reset; protected $phpstorm_noinspections; protected $write_model_external_builder_methods; /** * @var array */ protected $fileCache = []; /** * @var array */ protected $contextCache = []; /** * @var array */ protected $nullableColumns = []; /** * @var string[] */ protected $foreignKeyConstraintsColumns = []; /** * During initialization we use Laravels Date Facade to * determine the actual date class and store it here. * * @var string */ protected $dateClass; /** * @param Filesystem $files */ public function __construct(Filesystem $files, Repository $config, ViewFactory $view) { $this->config = $config; $this->files = $files; $this->view = $view; parent::__construct(); } /** * Execute the console command. * * @return void */ public function handle() { $this->filename = $this->laravel['config']->get('ide-helper.models_filename', '_ide_helper_models.php'); $filename = $this->option('filename') ?? $this->filename; $this->write = $this->option('write'); $this->write_mixin = $this->option('write-mixin'); $this->dirs = array_merge( $this->laravel['config']->get('ide-helper.model_locations', []), $this->option('dir') ); $model = $this->argument('model'); $ignore = $this->option('ignore'); $this->reset = $this->option('reset'); $this->phpstorm_noinspections = $this->option('phpstorm-noinspections'); $this->write_model_magic_where = $this->laravel['config']->get('ide-helper.write_model_magic_where', true); $this->write_model_external_builder_methods = $this->laravel['config']->get('ide-helper.write_model_external_builder_methods', true); $this->write_model_relation_count_properties = $this->laravel['config']->get('ide-helper.write_model_relation_count_properties', true); $this->write_model_relation_exists_properties = $this->laravel['config']->get('ide-helper.write_model_relation_exists_properties', false); $this->write = $this->write_mixin ? true : $this->write; //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" ) ) { $this->write = true; } } $this->dateClass = class_exists(\Illuminate\Support\Facades\Date::class) ? '\\' . get_class(\Illuminate\Support\Facades\Date::now()) : '\Illuminate\Support\Carbon'; $content = $this->generateDocs($model, $ignore); if (!$this->write || $this->write_mixin) { $written = $this->files->put($filename, $content); if ($written !== false) { $this->info("Model information was written to $filename"); } else { $this->error("Failed to write model information to $filename"); } } $helperFilename = $this->config->get('ide-helper.filename'); $writeHelper = $this->option('write-eloquent-helper'); if (!$writeHelper && !$this->files->exists($helperFilename) && ($this->write || $this->write_mixin)) { if ($this->confirm("{$helperFilename} does not exist. Do you want to generate a minimal helper to generate the Eloquent methods?")) { $writeHelper = true; } } if ($writeHelper) { $generator = new Generator($this->config, $this->view, $this->getOutput()); $content = $generator->generateEloquent(); $written = $this->files->put($helperFilename, $content); if ($written !== false) { $this->info("Eloquent helper was written to $helperFilename"); } else { $this->error("Failed to write eloquent helper to $helperFilename"); } } } /** * Get the console command arguments. * * @return array */ protected function getArguments() { return [ ['model', InputArgument::OPTIONAL | InputArgument::IS_ARRAY, 'Which models to include', []], ]; } /** * Get the console command options. * * @return array */ protected function getOptions() { return [ ['filename', 'F', InputOption::VALUE_OPTIONAL, 'The path to the helper file'], ['dir', 'D', InputOption::VALUE_OPTIONAL | InputOption::VALUE_IS_ARRAY, 'The model dir, supports glob patterns', [], ], ['write', 'W', InputOption::VALUE_NONE, 'Write to Model file'], ['write-mixin', 'M', InputOption::VALUE_NONE, "Write models to {$this->filename} and adds @mixin to each model, avoiding IDE duplicate declaration warnings", ], ['write-eloquent-helper', 'E', InputOption::VALUE_NONE, 'Write Eloquent helper file to _ide_helper.php', ], ['nowrite', 'N', InputOption::VALUE_NONE, 'Don\'t write to Model file'], ['reset', 'R', InputOption::VALUE_NONE, 'Remove the original phpdocs instead of appending'], ['smart-reset', 'r', InputOption::VALUE_NONE, 'Retained for compatibility, while it no longer has any effect'], ['phpstorm-noinspections', 'p', InputOption::VALUE_NONE, 'Add PhpFullyQualifiedNameUsageInspection and PhpUnnecessaryFullyQualifiedNameInspection PHPStorm ' . 'noinspection tags', ], ['ignore', 'I', InputOption::VALUE_OPTIONAL, 'Which models to ignore', ''], ]; } protected function generateDocs($loadModels, $ignore = '') { $output = " */ \n\n"; if (empty($loadModels)) { $models = $this->loadModels(); } else { $models = []; foreach ($loadModels as $model) { $models = array_merge($models, explode(',', $model)); } } $ignore = array_merge( explode(',', $ignore), $this->laravel['config']->get('ide-helper.ignored_models', []) ); foreach ($models as $name) { if (in_array($name, $ignore)) { if ($this->output->getVerbosity() >= OutputInterface::VERBOSITY_VERBOSE) { $this->comment("Ignoring model '$name'"); } continue; } $this->properties = []; $this->methods = []; $this->foreignKeyConstraintsColumns = []; if (class_exists($name)) { try { // handle abstract classes, interfaces, ... $reflectionClass = new ReflectionClass($name); if (!$reflectionClass->isSubclassOf('Illuminate\Database\Eloquent\Model')) { continue; } $this->comment("Loading model '$name'", OutputInterface::VERBOSITY_VERBOSE); if (!$reflectionClass->IsInstantiable()) { // ignore abstract class or interface continue; } $model = $this->laravel->make($name); $this->getPropertiesFromTable($model); if (method_exists($model, 'getCasts')) { $this->castPropertiesType($model); } $this->getPropertiesFromMethods($model); $this->getSoftDeleteMethods($model); $this->getCollectionMethods($model); $this->getFactoryMethods($model); $this->runModelHooks($model); $output .= $this->createPhpDocs($name); $ignore[] = $name; $this->nullableColumns = []; } catch (Throwable $e) { $this->error('Exception: ' . $e->getMessage() . "\nCould not analyze class $name.\n\nTrace:\n" . $e->getTraceAsString()); } } } return $output; } protected function loadModels() { $models = []; foreach ($this->dirs as $dir) { if (is_dir(base_path($dir))) { $dir = base_path($dir); } $dirs = glob($dir, GLOB_ONLYDIR); foreach ($dirs as $dir) { if (!is_dir($dir)) { $this->error("Cannot locate directory '{$dir}'"); continue; } if (file_exists($dir)) { $classMap = ClassMapGenerator::createMap($dir); // Sort list so it's stable across different environments ksort($classMap); foreach ($classMap as $model => $path) { $models[] = $model; } } } } return $models; } /** * cast the properties's type from $casts. * * @param Model $model */ public function castPropertiesType($model) { $casts = $model->getCasts(); foreach ($casts as $name => $type) { if (Str::startsWith($type, 'decimal:')) { $type = 'decimal'; } elseif (Str::startsWith($type, 'custom_datetime:')) { $type = 'date'; } elseif (Str::startsWith($type, 'date:')) { $type = 'date'; } elseif (Str::startsWith($type, 'datetime:')) { $type = 'date'; } elseif (Str::startsWith($type, 'immutable_custom_datetime:')) { $type = 'immutable_date'; } elseif (Str::startsWith($type, 'immutable_date:')) { $type = 'immutable_date'; } elseif (Str::startsWith($type, 'immutable_datetime:')) { $type = 'immutable_datetime'; } elseif (Str::startsWith($type, 'encrypted:')) { $type = Str::after($type, ':'); } $params = []; switch ($type) { case 'boolean': case 'bool': $realType = 'bool'; break; case 'decimal': $realType = 'numeric'; break; case 'encrypted': case 'string': case 'hashed': $realType = 'string'; break; case 'array': case 'json': $realType = 'array'; break; case 'object': $realType = 'object'; break; case 'int': case 'integer': case 'timestamp': $realType = 'int'; break; case 'real': case 'double': case 'float': $realType = 'float'; break; case 'date': case 'datetime': $realType = $this->dateClass; break; case 'immutable_date': case 'immutable_datetime': $realType = '\Carbon\CarbonImmutable'; break; case 'collection': $realType = '\Illuminate\Support\Collection'; break; case AsArrayObject::class: $realType = '\Illuminate\Database\Eloquent\Casts\ArrayObject'; break; default: // In case of an optional custom cast parameter , only evaluate // the `$type` until the `:` $type = strtok($type, ':'); $realType = class_exists($type) ? ('\\' . $type) : 'mixed'; $this->setProperty($name, null, true, true); $params = strtok(':'); $params = $params ? explode(',', $params) : []; break; } if (!isset($this->properties[$name])) { continue; } if ($this->isInboundCast($realType)) { continue; } if (Str::startsWith($type, AsCollection::class)) { $realType = $this->getTypeInModel($model, $params[0] ?? null) ?: '\Illuminate\Support\Collection'; $relatedModel = $this->getTypeInModel($model, $params[1] ?? null); if ($relatedModel) { $realType = $this->getCollectionTypeHint($realType, $relatedModel); } } if (Str::startsWith($type, AsEnumCollection::class)) { $realType = '\Illuminate\Support\Collection'; $relatedModel = $this->getTypeInModel($model, $params[0] ?? null); if ($relatedModel) { $realType = $this->getCollectionTypeHint($realType, $relatedModel); } } $realType = $this->checkForCastableCasts($realType, $params); $realType = $this->checkForCustomLaravelCasts($realType); $realType = $this->getTypeOverride($realType); $realType = $this->getTypeInModel($model, $realType); $realType = $this->applyNullability($realType, isset($this->nullableColumns[$name])); $this->properties[$name]['type'] = $realType; } } protected function applyNullability(?string $type, bool $isNullable): ?string { if (!$type) { return null; } $nullString = null; // Find instance of: // A) start of string or non-word character (like space or pipe) followed by 'null|' // B) '|null' followed by end of string or non-word character (like space or pipe) // This will find 'or null' instances at the beginning, middle or end of a type string, // but will exclude solo/pure null instances and null being part of a type's name (e.g. class 'Benull'). if (preg_match('/(?:(?:^|\W)(null\|))|(\|null(?:$|\W))/', $type, $matches) === 1) { $nullString = array_pop($matches); } // Return the current type string if: // A) the type can be null and the type contains a null instance // B) the type can not be null and the type does not contain a null instance if (!($isNullable xor $nullString)) { return $type; } if ($isNullable) { $type = $this->wrapIntersectionType($type) . '|null'; } else { $type = str_replace($nullString, '', $type); } return $type; } /** * Wraps a bare intersection type in parentheses for correct DNF syntax. * * For example, `A&B` becomes `(A&B)` so that adding `|null` produces * `(A&B)|null` instead of the ambiguous `A&B|null`. * Types that are already parenthesized or contain union types are returned as-is. */ protected function wrapIntersectionType(string $type): string { if (str_contains($type, '&') && !str_contains($type, '|') && $type[0] !== '(') { return '(' . $type . ')'; } return $type; } /** * Returns the override type for the give type. * * @param string $type * @return string|null */ protected function getTypeOverride($type) { $typeOverrides = $this->laravel['config']->get('ide-helper.type_overrides', []); return $typeOverrides[$type] ?? $type; } /** * Load the properties from the database table. * * @param Model $model * */ public function getPropertiesFromTable($model) { $table = $model->getTable(); $schema = $model->getConnection()->getSchemaBuilder(); $columns = $schema->getColumns($table); $driverName = $model->getConnection()->getDriverName(); if (!$columns) { return; } $this->setForeignKeys($schema, $table); foreach ($columns as $column) { $name = $column['name']; if (in_array($name, $model->getDates())) { $type = $this->dateClass; } else { // Match types to php equivalent $type = match ($column['type_name']) { 'tinyint', 'bit', 'integer', 'int', 'int4', 'smallint', 'int2', 'mediumint', 'bigint', 'int8' => 'int', 'boolean', 'bool' => 'bool', 'float', 'real', 'float4', 'double', 'float8' => 'float', 'decimal', 'numeric' => 'numeric', default => 'string', }; } if ($column['nullable']) { $this->nullableColumns[$name] = true; } $this->setProperty( $name, $this->getTypeInModel($model, $type), true, true, $column['comment'], $column['nullable'] ); if ($this->write_model_magic_where) { $builderClass = $this->write_model_external_builder_methods ? get_class($model->newModelQuery()) : '\Illuminate\Database\Eloquent\Builder'; $this->setMethod( Str::camel('where_' . $name), $this->getClassNameInDestinationFile($model, $builderClass) . '|' . $this->getClassNameInDestinationFile($model, get_class($model)), ['$value'] ); } } } /** * @param Model $model */ public function getPropertiesFromMethods($model) { $reflectionClass = new ReflectionClass($model); $reflections = $reflectionClass->getMethods(); if ($reflections) { // Filter out private methods because they can't be used to generate magic properties and HasAttributes' // methods that resemble mutators but aren't. $reflections = array_filter($reflections, function (\ReflectionMethod $methodReflection) { return !$methodReflection->isPrivate() && !( $methodReflection->getDeclaringClass()->getName() === Model::class && ( $methodReflection->getName() === 'setClassCastableAttribute' || $methodReflection->getName() === 'setEnumCastableAttribute' ) ); }); // https://github.com/barryvdh/laravel-ide-helper/issues/1664 $reflections = array_filter($reflections, function (\ReflectionMethod $methodReflection) { return !($methodReflection->getName() === 'getUseFactoryAttribute'); }); sort($reflections); foreach ($reflections as $reflection) { $type = $this->getReturnTypeFromReflection($reflection); $isAttribute = is_a($type, '\Illuminate\Database\Eloquent\Casts\Attribute', true); $method = $reflection->getName(); if ( Str::startsWith($method, 'get') && Str::endsWith($method, 'Attribute') && $method !== 'getAttribute' ) { //Magic getAttribute $name = Str::snake(substr($method, 3, -9)); if (!empty($name)) { $type = $this->getReturnType($reflection); $type = $this->getTypeInModel($model, $type); $comment = $this->getCommentFromDocBlock($reflection); $this->setProperty($name, $type, true, null, $comment); } } elseif ($isAttribute) { $types = $this->getAttributeTypes($model, $reflection); $type = $this->getTypeInModel($model, $types->get('get') ?: $types->get('set')) ?: null; $this->setProperty( Str::snake($method), $type, $types->has('get') ?: null, $types->has('set') ?: null, $this->getCommentFromDocBlock($reflection) ); } elseif ( Str::startsWith($method, 'set') && Str::endsWith($method, 'Attribute') && $method !== 'setAttribute' ) { //Magic setAttribute $name = Str::snake(substr($method, 3, -9)); if (!empty($name)) { $comment = $this->getCommentFromDocBlock($reflection); $this->setProperty($name, null, null, true, $comment); } } elseif (!empty($reflection->getAttributes('Illuminate\Database\Eloquent\Attributes\Scope')) || (Str::startsWith($method, 'scope') && $method !== 'scopeQuery' && $method !== 'scope' && $method !== 'scopes')) { $scopeUsingAttribute = !empty($reflection->getAttributes('Illuminate\Database\Eloquent\Attributes\Scope')); //Magic scopeAttribute $name = $scopeUsingAttribute ? $method : Str::camel(substr($method, 5)); if (!empty($name)) { $comment = $this->getCommentFromDocBlock($reflection); $args = $this->getParameters($reflection); //Remove the first ($query) argument array_shift($args); $builder = $this->getClassNameInDestinationFile( $reflection->getDeclaringClass(), get_class($model->newModelQuery()) ); $modelName = $this->getClassNameInDestinationFile( new ReflectionClass($model), get_class($model) ); $this->setMethod($name, $builder . '|' . $modelName, $args, $comment); } } elseif (in_array($method, ['query', 'newQuery', 'newModelQuery']) ) { if ($this->laravel['config']->get('ide-helper.write_query_methods', true)) { $builder = $this->getClassNameInDestinationFile($model, get_class($model->newModelQuery())); $this->setMethod( $method, $builder . '|' . $this->getClassNameInDestinationFile($model, get_class($model)) ); } if ($this->write_model_external_builder_methods) { $this->writeModelExternalBuilderMethods($model); } } elseif ( !method_exists('Illuminate\Database\Eloquent\Model', $method) && !Str::startsWith($method, 'get') ) { //Use reflection to inspect the code, based on Illuminate/Support/SerializableClosure.php if ($returnType = $reflection->getReturnType()) { $type = $returnType instanceof ReflectionNamedType ? $returnType->getName() : (string)$returnType; } else { // php 7.x type or fallback to docblock $type = (string)$this->getReturnTypeFromDocBlock($reflection); } $fileName = $reflection->getFileName(); if (!isset($this->fileCache[$fileName])) { $this->fileCache[$fileName] = new \SplFileObject($fileName); } $file = $this->fileCache[$fileName]; $file->seek($reflection->getStartLine() - 1); $lines = []; while ($file->key() < $reflection->getEndLine()) { $lines[] = $file->current(); $file->next(); } $code = implode('', $lines); $code = trim(preg_replace('/\s\s+/', '', $code)); $begin = strpos($code, 'function('); $code = substr($code, $begin, strrpos($code, '}') - $begin + 1); foreach ( $this->getRelationTypes() as $relation => $impl ) { $search = '$this->' . $relation . '('; if (stripos($code, $search) || ltrim($impl, '\\') === ltrim((string)$type, '\\')) { //Resolve the relation's model to a Relation object. if ($reflection->getNumberOfParameters()) { continue; } $comment = $this->getCommentFromDocBlock($reflection); // Adding constraints requires reading model properties which // can cause errors. Since we don't need constraints we can // disable them when we fetch the relation to avoid errors. $relationObj = Relation::noConstraints(function () use ($model, $reflection) { try { $methodName = $reflection->getName(); return $model->$methodName(); } catch (Throwable $e) { $this->warn(sprintf('Error resolving relation model of %s:%s() : %s', get_class($model), $reflection->getName(), $e->getMessage())); return null; } }); if ($relationObj instanceof Relation) { $relatedModel = $this->getClassNameInDestinationFile( $model, get_class($relationObj->getRelated()) ); $relationReturnType = $this->getRelationReturnTypes()[$relation] ?? false; if ( $relationReturnType === 'many' || ( !$relationReturnType && str_contains(get_class($relationObj), 'Many') ) ) { if ($relationObj instanceof BelongsToMany) { $pivot = get_class($relationObj->newPivot()); if (!in_array($pivot, [Pivot::class, MorphPivot::class])) { $pivot = $this->getClassNameInDestinationFile($model, $pivot); if ($existingPivot = ($this->properties[$relationObj->getPivotAccessor()] ?? null)) { $existingClasses = explode('|', $existingPivot['type']); if (!in_array($pivot, $existingClasses)) { array_unshift($existingClasses, $pivot); } } else { // No existing pivot property, so we need to add a null type $existingClasses = [$pivot, 'null']; } // create a union type of all pivot classes $unionType = implode('|', $existingClasses); $this->setProperty( $relationObj->getPivotAccessor(), $unionType, true, false ); } } //Collection or array of models (because Collection is Arrayable) $relatedClass = '\\' . get_class($relationObj->getRelated()); $collectionClass = $this->getCollectionClass($relatedClass); $collectionClassNameInModel = $this->getClassNameInDestinationFile( $model, $collectionClass ); $collectionTypeHint = $this->getCollectionTypeHint($collectionClassNameInModel, $relatedModel); $this->setProperty( $method, $collectionTypeHint, true, null, $comment ); if ($this->write_model_relation_count_properties) { $this->setProperty( Str::snake($method) . '_count', 'int|null', true, false // What kind of comments should be added to the relation count here? ); } if ($this->write_model_relation_exists_properties) { $this->setProperty( Str::snake($method) . '_exists', 'bool|null', true, false // What kind of comments should be added to the relation count here? ); } } elseif ( $relationReturnType === 'morphTo' || ( !$relationReturnType && $relation === 'morphTo' ) ) { $matches = []; $returnType = $this->getReturnTypeFromDocBlock($reflection); if ($returnType !== null) { preg_match('/MorphTo<(?:contravariant\s+)?(.+?)(?:,|>)/i', $returnType, $matches); } // Model isn't specified because relation is polymorphic $this->setProperty( $method, $matches[1] ?? $this->getClassNameInDestinationFile($model, Model::class) . '|\Eloquent', true, null, $comment, $this->isMorphToRelationNullable($relationObj) ); } else { //Single model is returned $this->setProperty( $method, $relatedModel, true, null, $comment, $this->isRelationNullable($relation, $relationObj) ); } } } } } } } } /** * Check if the relation is nullable * * @param string $relation * @param Relation $relationObj * * @return bool */ protected function isRelationNullable(string $relation, Relation $relationObj): bool { $reflectionObj = new ReflectionObject($relationObj); if (in_array($relation, ['hasOne', 'hasOneThrough', 'morphOne'], true)) { $defaultProp = $reflectionObj->getProperty('withDefault'); return !$defaultProp->getValue($relationObj); } if (!$reflectionObj->hasProperty('foreignKey')) { return false; } $fkProp = $reflectionObj->getProperty('foreignKey'); $enforceNullableRelation = $this->laravel['config']->get('ide-helper.enforce_nullable_relationships', true); foreach (Arr::wrap($fkProp->getValue($relationObj)) as $foreignKey) { if (isset($this->nullableColumns[$foreignKey])) { return true; } if (!in_array($foreignKey, $this->foreignKeyConstraintsColumns, true)) { return $enforceNullableRelation; } } if ($this->relatedModelUsesSoftDeletes($relationObj)) { return true; } return false; } /** * Check if the related model uses the SoftDeletes trait * * @param Relation $relationObj * * @return bool */ protected function relatedModelUsesSoftDeletes(Relation $relationObj): bool { if (!$this->laravel['config']->get('ide-helper.soft_deletes_force_nullable', true)) { return false; } $relatedModel = $relationObj->getRelated(); return in_array('Illuminate\\Database\\Eloquent\\SoftDeletes', class_uses_recursive($relatedModel)); } /** * Check if the morphTo relation is nullable * * @param Relation $relationObj * * @return bool */ protected function isMorphToRelationNullable(Relation $relationObj): bool { $reflectionObj = new ReflectionObject($relationObj); if (!$reflectionObj->hasProperty('foreignKey')) { return false; } $fkProp = $reflectionObj->getProperty('foreignKey'); foreach (Arr::wrap($fkProp->getValue($relationObj)) as $foreignKey) { if (isset($this->nullableColumns[$foreignKey])) { return true; } } return false; } /** * @param string $name * @param string|null $type * @param bool|null $read * @param bool|null $write * @param string|null $comment * @param bool $nullable */ public function setProperty($name, $type = null, $read = null, $write = null, $comment = '', $nullable = false) { if (!isset($this->properties[$name])) { $this->properties[$name] = []; $this->properties[$name]['type'] = 'mixed'; $this->properties[$name]['read'] = false; $this->properties[$name]['write'] = false; $this->properties[$name]['comment'] = (string) $comment; } if ($type !== null) { $newType = $this->getTypeOverride($type); if ($nullable) { $newType = $this->wrapIntersectionType($newType) . '|null'; } $this->properties[$name]['type'] = $newType; } if ($read !== null) { $this->properties[$name]['read'] = $read; } if ($write !== null) { $this->properties[$name]['write'] = $write; } } public function setMethod($name, $type = '', $arguments = [], $comment = '') { $methods = array_change_key_case($this->methods, CASE_LOWER); if (!isset($methods[strtolower($name)])) { $this->methods[$name] = []; $this->methods[$name]['type'] = $type; $this->methods[$name]['arguments'] = $arguments; $this->methods[$name]['comment'] = $comment; } } public function unsetMethod($name) { foreach ($this->methods as $k => $v) { if (strtolower($k) === strtolower($name)) { unset($this->methods[$k]); return; } } } public function getMethodType(Model $model, string $classType) { $modelName = $this->getClassNameInDestinationFile($model, get_class($model)); $builder = $this->getClassNameInDestinationFile($model, $classType); return $builder . '|' . $modelName; } /** * @param string $class * @return string */ protected function createPhpDocs($class) { $reflection = new ReflectionClass($class); $namespace = $reflection->getNamespaceName(); $classname = $reflection->getShortName(); $originalDoc = $reflection->getDocComment(); $keyword = $this->getClassKeyword($reflection); $interfaceNames = array_diff_key( $reflection->getInterfaceNames(), $reflection->getParentClass()->getInterfaceNames() ); $phpdoc = new DocBlock($reflection, new Context($namespace)); if ($this->reset) { $phpdoc->setText( (new DocBlock($reflection, new Context($namespace)))->getText() ); foreach ($phpdoc->getTags() as $tag) { if ( in_array($tag->getName(), ['property', 'property-read', 'property-write', 'method', 'mixin']) || ($tag->getName() === 'noinspection' && in_array($tag->getContent(), ['PhpUnnecessaryFullyQualifiedNameInspection', 'PhpFullyQualifiedNameUsageInspection'])) ) { $phpdoc->deleteTag($tag); } } } $properties = []; $methods = []; foreach ($phpdoc->getTags() as $tag) { $name = $tag->getName(); if ($name == 'property' || $name == 'property-read' || $name == 'property-write') { $properties[] = $tag->getVariableName(); } elseif ($name == 'method') { $methods[] = $tag->getMethodName(); } } foreach ($this->properties as $name => $property) { $name = "\$$name"; if ($this->hasCamelCaseModelProperties()) { $name = Str::camel($name); } if (in_array($name, $properties)) { continue; } if ($property['read'] && $property['write']) { $attr = 'property'; } elseif ($property['write']) { $attr = 'property-write'; } else { $attr = 'property-read'; } $tagLine = trim("@{$attr} {$property['type']} {$name} {$property['comment']}"); $tag = Tag::createInstance($tagLine, $phpdoc); $phpdoc->appendTag($tag); } ksort($this->methods); foreach ($this->methods as $name => $method) { if (in_array($name, $methods)) { continue; } $arguments = implode(', ', $method['arguments']); $tagLine = "@method static {$method['type']} {$name}({$arguments})"; if ($method['comment'] !== '') { $tagLine .= " {$method['comment']}"; } $tag = Tag::createInstance($tagLine, $phpdoc); $phpdoc->appendTag($tag); } if ($this->write) { $eloquentClassNameInModel = $this->getClassNameInDestinationFile($reflection, 'Eloquent'); // remove the already existing tag to prevent duplicates foreach ($phpdoc->getTagsByName('mixin') as $tag) { if ($tag->getContent() === $eloquentClassNameInModel) { $phpdoc->deleteTag($tag); } } $phpdoc->appendTag(Tag::createInstance('@mixin ' . $eloquentClassNameInModel, $phpdoc)); } if ($this->phpstorm_noinspections) { /** * Facades, Eloquent API * @see https://www.jetbrains.com/help/phpstorm/php-fully-qualified-name-usage.html */ $phpdoc->appendTag(Tag::createInstance('@noinspection PhpFullyQualifiedNameUsageInspection', $phpdoc)); /** * Relations, other models in the same namespace * @see https://www.jetbrains.com/help/phpstorm/php-unnecessary-fully-qualified-name.html */ $phpdoc->appendTag( Tag::createInstance('@noinspection PhpUnnecessaryFullyQualifiedNameInspection', $phpdoc) ); } $serializer = new DocBlockSerializer(); $docComment = $serializer->getDocComment($phpdoc); $mixinClassName = null; if ($this->write_mixin) { $phpdocMixin = new DocBlock($reflection, new Context($namespace)); // remove all mixin tags prefixed with IdeHelper foreach ($phpdocMixin->getTagsByName('mixin') as $tag) { if (Str::startsWith($tag->getContent(), 'IdeHelper')) { $phpdocMixin->deleteTag($tag); } } $mixinClassName = "IdeHelper{$classname}"; $phpdocMixin->appendTag(Tag::createInstance("@mixin {$mixinClassName}", $phpdocMixin)); $mixinDocComment = $serializer->getDocComment($phpdocMixin); // remove blank lines if there's no text if (!$phpdocMixin->getText()) { $mixinDocComment = preg_replace("/\s\*\s*\n/", '', $mixinDocComment); } foreach ($phpdoc->getTagsByName('mixin') as $tag) { if (Str::startsWith($tag->getContent(), 'IdeHelper')) { $phpdoc->deleteTag($tag); } } $docComment = $serializer->getDocComment($phpdoc); } if ($this->write) { $modelDocComment = $this->write_mixin ? $mixinDocComment : $docComment; $filename = $reflection->getFileName(); $contents = $this->files->get($filename); if ($originalDoc) { $contents = str_replace($originalDoc, $modelDocComment, $contents); } else { $replace = "{$modelDocComment}\n"; $pos = strpos($contents, "final class {$classname}") ?: strpos($contents, "class {$classname}"); if ($pos !== false) { // If PHP 8 attributes (e.g. #[ObservedBy(...)]) precede the class // declaration, insert the docblock before the first attribute so that // the resulting order is: docblock → attributes → class. $before = substr($contents, 0, $pos); if (preg_match('/((?:#\[.+?\]\s*)+)$/s', $before, $matches)) { $pos -= strlen($matches[1]); $replace = "{$modelDocComment}\n"; } $contents = substr_replace($contents, $replace, $pos, 0); } } if ($this->files->put($filename, $contents)) { $this->info('Written new phpDocBlock to ' . $filename); } } $classname = $this->write_mixin ? $mixinClassName : $classname; $allowDynamicAttributes = $this->write_mixin ? "#[\AllowDynamicProperties]\n\t" : ''; $output = "namespace {$namespace}{\n{$docComment}\n\t{$allowDynamicAttributes}{$keyword}class {$classname} "; if (!$this->write_mixin) { $output .= "extends \Eloquent "; if ($interfaceNames) { $interfaces = implode(', \\', $interfaceNames); $output .= "implements \\{$interfaces} "; } } return $output . "{}\n}\n\n"; } /** * Get the parameters and format them correctly * * @param $method * @return array * @throws \ReflectionException */ public function getParameters($method) { //Loop through the default values for parameters, and make the correct output string $paramsWithDefault = []; /** @var \ReflectionParameter $param */ foreach ($method->getParameters() as $param) { $paramStr = $param->isVariadic() ? '...$' . $param->getName() : '$' . $param->getName(); if ($paramType = $this->getParamType($method, $param)) { $paramStr = $paramType . ' ' . $paramStr; } if ($param->isOptional() && $param->isDefaultValueAvailable()) { $default = $param->getDefaultValue(); if (is_bool($default)) { $default = $default ? 'true' : 'false'; } elseif (is_array($default)) { $default = '[]'; } elseif (is_null($default)) { $default = 'null'; } elseif (is_int($default) || is_float($default)) { //$default = $default; } elseif ($default instanceof \UnitEnum) { $default = '\\' . get_class($default) . '::' . $default->name; } else { $default = "'" . trim($default) . "'"; } $paramStr .= " = $default"; } $paramsWithDefault[] = $paramStr; } return $paramsWithDefault; } /** * Determine a model classes' collection type. * * @see http://laravel.com/docs/eloquent-collections#custom-collections * @param string $className * @return string */ protected function getCollectionClass($className) { // Return something in the very very unlikely scenario the model doesn't // have a newCollection() method. if (!method_exists($className, 'newCollection')) { return '\Illuminate\Database\Eloquent\Collection'; } /** @var Model $model */ $model = new $className(); return '\\' . get_class($model->newCollection()); } /** * Determine a model classes' collection type hint. * * @param string $collectionClassNameInModel * @param string $relatedModel * @return string */ protected function getCollectionTypeHint(string $collectionClassNameInModel, string $relatedModel): string { $useGenericsSyntax = $this->laravel['config']->get('ide-helper.use_generics_annotations', true); if ($useGenericsSyntax) { return $collectionClassNameInModel . ''; } else { return $collectionClassNameInModel . '|' . $relatedModel . '[]'; } } protected ?array $cachedRelationTypes = null; protected ?array $cachedRelationReturnTypes = null; /** * Returns the available relation types */ protected function getRelationTypes(): array { return $this->cachedRelationTypes ??= array_merge( self::RELATION_TYPES, $this->laravel['config']->get('ide-helper.additional_relation_types', []) ); } /** * Returns the return types of relations */ protected function getRelationReturnTypes(): array { return $this->cachedRelationReturnTypes ??= $this->laravel['config']->get('ide-helper.additional_relation_return_types', []); } /** * @return bool */ protected function hasCamelCaseModelProperties() { return $this->laravel['config']->get('ide-helper.model_camel_case_properties', false); } /** * @psalm-suppress NoValue */ protected function getAttributeTypes(Model $model, \ReflectionMethod $reflectionMethod): Collection { /** @var Attribute $attribute */ $attribute = $reflectionMethod->invoke($model); $methods = new Collection(); if ($attribute->get) { $methods['get'] = optional(new \ReflectionFunction($attribute->get))->getReturnType(); } if ($attribute->set) { $function = optional(new \ReflectionFunction($attribute->set)); if ($function->getNumberOfParameters() === 0) { $methods['set'] = null; } else { $methods['set'] = $function->getParameters()[0]->getType(); } } return $methods ->map(function ($type) { if ($type === null) { $types = collect([]); } elseif ($type instanceof \ReflectionUnionType) { $types = collect($type->getTypes()) /** @var ReflectionType $reflectionType */ ->map(function ($reflectionType) { return collect($this->extractReflectionTypes($reflectionType)); }) ->flatten(); } else { $types = collect($this->extractReflectionTypes($type)); } if ($type && $type->allowsNull()) { $types->push('null'); } return $types->join('|'); }); } protected function getReturnType(\ReflectionMethod $reflection): ?string { $type = $this->getReturnTypeFromDocBlock($reflection); if ($type) { return $type; } return $this->getReturnTypeFromReflection($reflection); } /** * Get method comment based on it DocBlock comment * * @param \ReflectionMethod $reflection * * @return null|string */ protected function getCommentFromDocBlock(\ReflectionMethod $reflection) { $context = $this->getDocBlockContext($reflection); $comment = ''; $phpdoc = new DocBlock($reflection, $context); if ($phpdoc->hasTag('comment')) { $comment = $phpdoc->getTagsByName('comment')[0]->getContent(); } return $comment; } /** * Get method return type based on it DocBlock comment * * @param \ReflectionMethod $reflection * @param ?\Reflector $reflectorForContext * * @return null|string */ protected function getReturnTypeFromDocBlock(\ReflectionMethod $reflection, ?\Reflector $reflectorForContext = null) { $context = $this->getDocBlockContext($reflectorForContext ?? $reflection); $type = null; $phpdoc = new DocBlock($reflection, $context); if ($phpdoc->hasTag('return')) { $returnTag = $phpdoc->getTagsByName('return')[0]; $typeParser = new PhpDocReturnTypeParser($returnTag->getContent(), $context->getNamespaceAliases()); if ($typeAlias = $typeParser->parse()) { return $typeAlias; } $type = $phpdoc->getTagsByName('return')[0]->getType(); } return $type; } protected function getDocBlockContext(\Reflector $reflector): Context { if ($reflector instanceof \ReflectionMethod) { $key = $reflector->getDeclaringClass()->getName(); } elseif ($reflector instanceof ReflectionClass) { $key = $reflector->getName(); } else { $phpDocContext = (new ContextFactory())->createFromReflector($reflector); return new Context( $phpDocContext->getNamespace(), $phpDocContext->getNamespaceAliases() ); } if (!isset($this->contextCache[$key])) { $phpDocContext = (new ContextFactory())->createFromReflector($reflector); $this->contextCache[$key] = new Context( $phpDocContext->getNamespace(), $phpDocContext->getNamespaceAliases() ); } return $this->contextCache[$key]; } protected function getReturnTypeFromReflection(\ReflectionMethod $reflection): ?string { $returnType = $reflection->getReturnType(); if (!$returnType) { return null; } $types = $this->extractReflectionTypes($returnType); $type = implode('|', $types); if ($returnType->allowsNull()) { $type .= '|null'; } return $type; } /** * Generates methods provided by the SoftDeletes trait * @param Model $model */ protected function getSoftDeleteMethods($model) { $traits = class_uses_recursive($model); if (in_array('Illuminate\\Database\\Eloquent\\SoftDeletes', $traits)) { $modelName = $this->getClassNameInDestinationFile($model, get_class($model)); $builder = $this->getClassNameInDestinationFile($model, \Illuminate\Database\Eloquent\Builder::class); $this->setMethod('withTrashed', $builder . '|' . $modelName, ['bool $withTrashed = true']); $this->setMethod('withoutTrashed', $builder . '|' . $modelName, []); $this->setMethod('onlyTrashed', $builder . '|' . $modelName, []); } } /** * Generate factory method from "HasFactory" trait. * * @param Model $model */ protected function getFactoryMethods($model) { if (!class_exists(Factory::class)) { return; } $modelName = get_class($model); $traits = class_uses_recursive($modelName); if (!in_array('Illuminate\\Database\\Eloquent\\Factories\\HasFactory', $traits)) { return; } if ($modelName::newFactory()) { $factory = get_class($modelName::newFactory()); } else { $factory = Factory::resolveFactoryName($modelName); } $factory = '\\' . trim($factory, '\\'); if (!class_exists($factory)) { return; } $this->setMethod('factory', $factory, ['$count = null, $state = []']); } /** * Generates methods that return collections * @param Model $model */ protected function getCollectionMethods($model) { $collectionClass = $this->getCollectionClass(get_class($model)); if ($collectionClass !== '\\' . \Illuminate\Database\Eloquent\Collection::class) { $collectionClassInModel = $this->getClassNameInDestinationFile($model, $collectionClass); $collectionTypeHint = $this->getCollectionTypeHint($collectionClassInModel, 'static'); $this->setMethod('get', $collectionTypeHint, ['$columns = [\'*\']']); $this->setMethod('all', $collectionTypeHint, ['$columns = [\'*\']']); } } /** * @param ReflectionClass $reflection * @return string */ protected function getClassKeyword(ReflectionClass $reflection) { if ($reflection->isFinal()) { $keyword = 'final '; } elseif ($reflection->isAbstract()) { $keyword = 'abstract '; } else { $keyword = ''; } return $keyword; } protected function isInboundCast(string $type): bool { return class_exists($type) && is_subclass_of($type, CastsInboundAttributes::class); } protected function checkForCastableCasts(string $type, array $params = []): string { if (!class_exists($type) || !interface_exists(Castable::class)) { return $type; } $reflection = new ReflectionClass($type); if (!$reflection->implementsInterface(Castable::class)) { return $type; } $cast = call_user_func([$type, 'castUsing'], $params); if (is_string($cast) && !is_object($cast)) { return $cast; } $castReflection = new ReflectionObject($cast); $methodReflection = $castReflection->getMethod('get'); return $this->getReturnTypeFromReflection($methodReflection) ?? $this->getReturnTypeFromDocBlock($methodReflection, $reflection) ?? $type; } /** * @param string $type * @return string|null * @throws \ReflectionException */ protected function checkForCustomLaravelCasts(string $type): ?string { if (!class_exists($type) || !interface_exists(CastsAttributes::class)) { return $type; } $reflection = new ReflectionClass($type); if (!$reflection->implementsInterface(CastsAttributes::class)) { return $type; } $methodReflection = new \ReflectionMethod($type, 'get'); $reflectionType = $this->getReturnTypeFromReflection($methodReflection); if ($reflectionType === null) { $reflectionType = $this->getReturnTypeFromDocBlock($methodReflection); } if ($reflectionType === 'static' || $reflectionType === '$this') { $reflectionType = $type; } return $reflectionType; } protected function getTypeInModel(object $model, ?string $type): ?string { if ($type === null) { return null; } if (class_exists($type)) { $type = $this->getClassNameInDestinationFile($model, $type); } return $type; } protected function getClassNameInDestinationFile(object $model, string $className): string { $reflection = $model instanceof ReflectionClass ? $model : new ReflectionObject($model); $className = trim($className, '\\'); $writingToExternalFile = !$this->write || $this->write_mixin; $classIsNotInExternalFile = $reflection->getName() !== $className; $forceFQCN = $this->laravel['config']->get('ide-helper.force_fqn', false); if (($writingToExternalFile && $classIsNotInExternalFile) || $forceFQCN) { return '\\' . $className; } $usedClassNames = $this->getUsedClassNames($reflection); return $usedClassNames[$className] ?? ('\\' . $className); } /** * @param ReflectionClass $reflection * @return string[] */ protected function getUsedClassNames(ReflectionClass $reflection): array { $context = $this->getDocBlockContext($reflection); $namespaceAliases = array_flip(array_map(function ($alias) { return ltrim($alias, '\\'); }, $context->getNamespaceAliases())); $namespaceAliases[$reflection->getName()] = $reflection->getShortName(); return $namespaceAliases; } protected function writeModelExternalBuilderMethods(Model $model): void { $fullBuilderClass = '\\' . get_class($model->newModelQuery()); $newBuilderMethods = get_class_methods($fullBuilderClass); $originalBuilderMethods = get_class_methods('\Illuminate\Database\Eloquent\Builder'); // diff the methods between the new builder and original one // and create helpers for the ones that are new $newMethodsFromNewBuilder = array_diff($newBuilderMethods, $originalBuilderMethods); if (!$newMethodsFromNewBuilder) { return; } // after we have retrieved the builder's methods // get the class of the builder based on the FQCN option $builderClassBasedOnFQCNOption = $this->getClassNameInDestinationFile($model, get_class($model->newModelQuery())); foreach ($newMethodsFromNewBuilder as $builderMethod) { $reflection = new \ReflectionMethod($fullBuilderClass, $builderMethod); $args = $this->getParameters($reflection); $this->setMethod( $builderMethod, $builderClassBasedOnFQCNOption . '|' . $this->getClassNameInDestinationFile($model, get_class($model)), $args ); } } protected function getParamType(\ReflectionMethod $method, \ReflectionParameter $parameter): ?string { if ($paramType = $parameter->getType()) { $types = $this->extractReflectionTypes($paramType); $type = implode('|', $types); if ($paramType->allowsNull()) { // Use ?Type syntax only for single named types, not for intersection types if (count($types) == 1 && !str_starts_with($type, '(')) { $type = '?' . $type; } else { $type .= '|null'; } } return $type; } $docComment = $method->getDocComment(); if (!$docComment) { return null; } preg_match( '/@param ((?:(?:[\w?|\\\\<>])+(?:\[])?)+)/', $docComment, $matches ); $type = $matches[1] ?? ''; if (strpos($type, '|') !== false) { $types = explode('|', $type); // if we have more than 2 types // we return null as we cannot use unions in php yet if (count($types) > 2) { return null; } $hasNull = false; foreach ($types as $currentType) { if ($currentType === 'null') { $hasNull = true; continue; } // if we didn't find null assign the current type to the type we want $type = $currentType; } // if we haven't found null type set // we return null as we cannot use unions with different types yet if (!$hasNull) { return null; } $type = '?' . $type; } // convert to proper type hint types in php $type = str_replace(['boolean', 'integer'], ['bool', 'int'], $type); $allowedTypes = [ 'int', 'bool', 'string', 'float', ]; // we replace the ? with an empty string so we can check the actual type if (!in_array(str_replace('?', '', $type), $allowedTypes)) { return null; } // if we have a match on index 1 // then we have found the type of the variable if not we return null return $type; } protected function extractReflectionTypes(ReflectionType $reflection_type): array { if ($reflection_type instanceof ReflectionNamedType) { return [$this->getReflectionNamedType($reflection_type)]; } if ($reflection_type instanceof \ReflectionIntersectionType) { return [$this->formatIntersectionType($reflection_type)]; } if ($reflection_type instanceof \ReflectionUnionType) { return $this->extractUnionTypes($reflection_type); } // Unknown type - return empty array as fallback return []; } protected function extractUnionTypes(\ReflectionUnionType $union_type): array { $types = []; foreach ($union_type->getTypes() as $inner_type) { if ($inner_type instanceof ReflectionNamedType) { if ($inner_type->getName() === 'null') { continue; } $types[] = $this->getReflectionNamedType($inner_type); } elseif ($inner_type instanceof \ReflectionIntersectionType) { $types[] = $this->formatIntersectionType($inner_type); } // ReflectionUnionType cannot be nested per PHP's DNF rules } return $types; } protected function formatIntersectionType(\ReflectionIntersectionType $intersection_type): string { $parts = []; foreach ($intersection_type->getTypes() as $type) { $parts[] = $this->getReflectionNamedType($type); } return '(' . implode('&', $parts) . ')'; } protected function getReflectionNamedType(ReflectionNamedType $paramType): string { $parameterName = $paramType->getName(); if (!$paramType->isBuiltin() && $paramType->getName() !== 'static') { $parameterName = '\\' . $parameterName; } return $parameterName; } /** * @param Model $model * @throws \Illuminate\Contracts\Container\BindingResolutionException * @throws \RuntimeException */ protected function runModelHooks($model): void { $hooks = $this->laravel['config']->get('ide-helper.model_hooks', []); foreach ($hooks as $hook) { $hookInstance = $this->laravel->make($hook); if (!$hookInstance instanceof ModelHookInterface) { throw new \RuntimeException( 'Your IDE helper model hook must implement Barryvdh\LaravelIdeHelper\Contracts\ModelHookInterface' ); } $hookInstance->run($this, $model); } } /** * @param Builder $schema * @param string $table */ protected function setForeignKeys($schema, $table) { foreach ($schema->getForeignKeys($table) as $foreignKeyConstraint) { foreach ($foreignKeyConstraint['columns'] as $columnName) { $this->foreignKeyConstraintsColumns[] = $columnName; } } } } ================================================ FILE: src/Contracts/ModelHookInterface.php ================================================ */ namespace Barryvdh\LaravelIdeHelper; use Barryvdh\Reflection\DocBlock; use Barryvdh\Reflection\DocBlock\Context; use Barryvdh\Reflection\DocBlock\Serializer as DocBlockSerializer; use Barryvdh\Reflection\DocBlock\Tag; use Illuminate\Console\Command; use Illuminate\Filesystem\Filesystem; 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'); $expectedMixins = [ '\Eloquent' => false, '\Illuminate\Database\Eloquent\Builder' => false, '\Illuminate\Database\Query\Builder' => false, ]; foreach ($mixins as $m) { $mixin = $m->getContent(); if (isset($expectedMixins[$mixin])) { $command->info('Tag Exists: @mixin ' . $mixin . ' in ' . $class); $expectedMixins[$mixin] = true; } } $changed = false; foreach ($expectedMixins as $expectedMixin => $present) { if ($present === false) { $phpdoc->appendTag(Tag::createInstance('@mixin ' . $expectedMixin, $phpdoc)); $changed = true; } } // If nothing's changed, stop here. if (!$changed) { return; } $serializer = new DocBlockSerializer(); $serializer->getDocComment($phpdoc); $docComment = $serializer->getDocComment($phpdoc); /* The new DocBlock is appended to the beginning of the class declaration. Since there is no DocBlock, the declaration is used as a guide. */ if (!$originalDoc) { $originalDoc = 'abstract class Model implements'; $docComment .= "\nabstract class Model implements"; } $filename = $reflection->getFileName(); if (!$filename) { $command->error('Filename not found ' . $class); return; } $contents = $files->get($filename); if (!$contents) { $command->error('No file contents found ' . $filename); return; } $count = 0; $contents = str_replace($originalDoc, $docComment, $contents, $count); if ($count <= 0) { $command->error('Content did not change ' . $contents); return; } if (!$files->put($filename, $contents)) { $command->error('File write failed to ' . $filename); return; } $command->info('Wrote expected docblock to ' . $filename); } } ================================================ FILE: src/Generator.php ================================================ * @copyright 2014 Barry vd. Heuvel / 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; use Illuminate\Database\Eloquent\Model; use Illuminate\Foundation\AliasLoader; use Illuminate\Support\Collection; use Illuminate\Support\Facades\Facade; use Illuminate\Support\Str; use Illuminate\Support\Traits\Macroable; use ReflectionClass; use Symfony\Component\Console\Output\OutputInterface; class Generator { /** @var \Illuminate\Config\Repository */ protected $config; /** @var \Illuminate\View\Factory */ protected $view; /** @var OutputInterface */ protected $output; protected $extra = []; protected $magic = []; protected $interfaces = []; protected $helpers; /** * @param \Illuminate\Config\Repository $config * @param \Illuminate\View\Factory $view * @param ?OutputInterface $output * @param string $helpers */ public function __construct( /*ConfigRepository */ $config, /* Illuminate\View\Factory */ $view, ?OutputInterface $output = null, $helpers = '' ) { $this->config = $config; $this->view = $view; $this->output = $output; // Find the drivers to add to the extra/interfaces $this->detectDrivers(); $this->extra = array_merge($this->extra, $this->config->get('ide-helper.extra', [])); $this->magic = array_merge($this->magic, $this->config->get('ide-helper.magic', [])); $this->interfaces = array_merge($this->interfaces, $this->config->get('ide-helper.interfaces', [])); Macro::setDefaultReturnTypes($this->config->get('ide-helper.macro_default_return_types', [ \Illuminate\Http\Client\Factory::class => \Illuminate\Http\Client\PendingRequest::class, ])); // Make all interface classes absolute foreach ($this->interfaces as &$interface) { $interface = '\\' . ltrim($interface, '\\'); } $this->helpers = $helpers; } /** * Generate the helper file contents; * * @return string */ public function generate() { $app = app(); return $this->view->make('ide-helper::helper') ->with('namespaces_by_extends_ns', $this->getAliasesByExtendsNamespace()) ->with('namespaces_by_alias_ns', $this->getAliasesByAliasNamespace()) ->with('real_time_facades', $this->getRealTimeFacades()) ->with('helpers', $this->detectHelpers()) ->with('include_fluent', $this->config->get('ide-helper.include_fluent', true)) ->render(); } public function generateEloquent() { $name = 'Eloquent'; $facade = Model::class; $magicMethods = array_key_exists($name, $this->magic) ? $this->magic[$name] : []; $alias = new Alias($this->config, $name, $facade, $magicMethods, $this->interfaces); if (!$alias->isValid()) { throw new \RuntimeException('Cannot generate Eloquent helper'); } //Add extra methods, from other classes (magic static calls) if (array_key_exists($name, $this->extra)) { $alias->addClass($this->extra[$name]); } $app = app(); return $this->view->make('ide-helper::helper') ->with('namespaces_by_extends_ns', []) ->with('namespaces_by_alias_ns', ['__root' => [$alias]]) ->with('real_time_facades', []) ->with('helpers', '') ->with('include_fluent', false) ->with('factories', []) ->render(); } protected function detectHelpers() { $helpers = $this->helpers; $replacements = [ '($guard is null ? \Illuminate\Contracts\Auth\Factory : \Illuminate\Contracts\Auth\StatefulGuard)' => '\\Auth', ]; foreach ($replacements as $search => $replace) { $helpers = Str::replace( "@return {$search}", "@return $replace|$search", $helpers ); } return $helpers; } protected function detectDrivers() { $defaultUserModel = config('auth.providers.users.model', config('auth.model', 'App\User')); $this->interfaces['\Illuminate\Contracts\Auth\Authenticatable'] = $defaultUserModel; try { if ( class_exists('Auth') && is_a('Auth', '\Illuminate\Support\Facades\Auth', true) && app()->bound('auth') ) { $class = get_class(\Auth::guard()); $this->extra['Auth'] = [$class]; $this->interfaces['\Illuminate\Auth\UserProviderInterface'] = $class; } } catch (\Exception $e) { } try { if (class_exists('DB') && is_a('DB', '\Illuminate\Support\Facades\DB', true)) { $class = get_class(\DB::connection()); $this->extra['DB'] = [$class]; $this->interfaces['\Illuminate\Database\ConnectionInterface'] = $class; } } catch (\Exception $e) { } try { if (class_exists('Cache') && is_a('Cache', '\Illuminate\Support\Facades\Cache', true)) { $driver = get_class(\Cache::driver()); $store = get_class(\Cache::getStore()); $this->extra['Cache'] = [$driver, $store]; $this->interfaces['\Illuminate\Cache\StoreInterface'] = $store; } } catch (\Exception $e) { } try { if (class_exists('Queue') && is_a('Queue', '\Illuminate\Support\Facades\Queue', true)) { $class = get_class(\Queue::connection()); $this->extra['Queue'] = [$class]; $this->interfaces['\Illuminate\Queue\QueueInterface'] = $class; } } catch (\Exception $e) { } try { if (class_exists('Storage') && is_a('Storage', '\Illuminate\Support\Facades\Storage', true)) { $class = get_class(\Storage::disk()); $this->extra['Storage'] = [$class]; $this->interfaces['\Illuminate\Contracts\Filesystem\Filesystem'] = $class; } } catch (\Exception $e) { } } /** * Find all aliases that are valid for us to render * * @return Collection */ protected function getValidAliases() { $aliases = new Collection(); // Get all aliases foreach ($this->getAliases() as $name => $facade) { // Skip the Redis facade, if not available (otherwise Fatal PHP Error) if ($facade == 'Illuminate\Support\Facades\Redis' && $name == 'Redis' && !class_exists('Predis\Client')) { continue; } // Skip the swoole if ($facade == 'SwooleTW\Http\Server\Facades\Server' && $name == 'Server' && !class_exists('Swoole\Http\Server')) { continue; } $magicMethods = array_key_exists($name, $this->magic) ? $this->magic[$name] : []; $alias = new Alias($this->config, $name, $facade, $magicMethods, $this->interfaces); if ($alias->isValid()) { //Add extra methods, from other classes (magic static calls) if (array_key_exists($name, $this->extra)) { $alias->addClass($this->extra[$name]); } $aliases[] = $alias; } } return $aliases; } protected function getRealTimeFacades() { $facades = []; $realTimeFacadeFiles = glob(storage_path('framework/cache/facade-*.php')); foreach ($realTimeFacadeFiles as $file) { try { $name = $this->getFullyQualifiedClassNameInFile($file); if ($name) { $facades[$name] = $name; } } catch (\Throwable $e) { continue; } } return $facades; } protected function getFullyQualifiedClassNameInFile(string $path) { $contents = file_get_contents($path); // Match namespace preg_match('/namespace\s+([^;]+);/', $contents, $namespaceMatch); $namespace = isset($namespaceMatch[1]) ? $namespaceMatch[1] : ''; // Match class name preg_match('/class\s+([a-zA-Z0-9_]+)/', $contents, $classMatch); $className = isset($classMatch[1]) ? $classMatch[1] : ''; // Combine namespace and class name if ($namespace && $className) { return $namespace . '\\' . $className; } } /** * Regroup aliases by namespace of extended classes * * @return Collection */ protected function getAliasesByExtendsNamespace() { $aliases = $this->getValidAliases()->filter(static function (Alias $alias) { return is_subclass_of($alias->getExtends(), Facade::class); }); $this->addMacroableClasses($aliases); return $aliases->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() { // 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', '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 class_exists($alias); }, ARRAY_FILTER_USE_KEY ); } /** * Write a string as error output. * * @param string $string * @return void */ protected function error($string) { if ($this->output) { $this->output->writeln("$string"); } else { echo $string . "\r\n"; } } /** * Add all macroable classes which are not already loaded as an alias and have defined macros. * * @param Collection $aliases */ protected function addMacroableClasses(Collection $aliases) { $macroable = $this->getMacroableClasses($aliases); foreach ($macroable as $class) { $reflection = new ReflectionClass($class); if (!$reflection->getStaticProperties()['macros']) { continue; } $aliases[] = new Alias($this->config, $class, $class, [], $this->interfaces); } } /** * Get all loaded macroable classes which are not loaded as an alias. * * @param Collection $aliases * @return Collection */ protected function getMacroableClasses(Collection $aliases) { return (new Collection(get_declared_classes())) ->filter(function ($class) { $reflection = new ReflectionClass($class); // Filter out internal classes and class aliases return !$reflection->isInternal() && $reflection->getName() === $class; }) ->filter(function ($class) { $traits = class_uses_recursive($class); // Filter only classes with the macroable trait return isset($traits[Macroable::class]); }) ->filter(function ($class) use ($aliases) { $class = Str::start($class, '\\'); // Filter out aliases return !$aliases->first(function (Alias $alias) use ($class) { return $alias->getExtends() === $class; }); }); } } ================================================ FILE: src/IdeHelperServiceProvider.php ================================================ * @copyright 2014 Barry vd. Heuvel / 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; use Barryvdh\LaravelIdeHelper\Console\EloquentCommand; use Barryvdh\LaravelIdeHelper\Console\GeneratorCommand; use Barryvdh\LaravelIdeHelper\Console\MetaCommand; use Barryvdh\LaravelIdeHelper\Console\ModelsCommand; use Barryvdh\LaravelIdeHelper\Listeners\GenerateModelHelper; use Illuminate\Console\Events\CommandFinished; use Illuminate\Contracts\Support\DeferrableProvider; use Illuminate\Database\Events\MigrationsEnded; use Illuminate\Support\ServiceProvider; class IdeHelperServiceProvider extends ServiceProvider implements DeferrableProvider { /** * Bootstrap the application events. * * @return void */ public function boot() { if (!$this->app->runningUnitTests() && $this->app['config']->get('ide-helper.post_migrate', [])) { $this->app['events']->listen(CommandFinished::class, GenerateModelHelper::class); $this->app['events']->listen(MigrationsEnded::class, function () { GenerateModelHelper::$shouldRun = true; }); } if ($this->app->has('view')) { $viewPath = __DIR__ . '/../resources/views'; $this->loadViewsFrom($viewPath, 'ide-helper'); } $configPath = __DIR__ . '/../config/ide-helper.php'; if (function_exists('config_path')) { $publishPath = config_path('ide-helper.php'); } else { $publishPath = base_path('config/ide-helper.php'); } $this->publishes([$configPath => $publishPath], 'config'); } /** * Register the service provider. * * @return void */ public function register() { $configPath = __DIR__ . '/../config/ide-helper.php'; $this->mergeConfigFrom($configPath, 'ide-helper'); $this->commands( [ GeneratorCommand::class, ModelsCommand::class, MetaCommand::class, EloquentCommand::class, ] ); } /** * Get the services provided by the provider. * * @return array */ public function provides() { return [ GeneratorCommand::class, ModelsCommand::class, MetaCommand::class, EloquentCommand::class, ]; } } ================================================ FILE: src/Listeners/GenerateModelHelper.php ================================================ artisan = $artisan; $this->config = $config; } /** * Handle the event. * * @param CommandFinished $event */ public function handle(CommandFinished $event) { if (!self::$shouldRun) { return; } self::$shouldRun = false; foreach ($this->config->get('ide-helper.post_migrate', []) as $command) { $this->artisan->call($command, [], $event->output); } } } ================================================ FILE: src/Macro.php ================================================ phpdoc = new DocBlock($method); $this->addLocationToPhpDoc(); // Add macro parameters if they are missed in original docblock if (!$this->phpdoc->hasTag('param')) { foreach ($method->getParameters() as $parameter) { $reflectionType = $parameter->getType(); $type = $this->concatReflectionTypes($reflectionType); /** @psalm-suppress UndefinedClass */ if ($reflectionType && !$reflectionType instanceof \ReflectionUnionType && $reflectionType->allowsNull()) { $type .= '|null'; } $type = $type ?: 'mixed'; $name = $parameter->isVariadic() ? '...' : ''; $name .= '$' . $parameter->getName(); $this->phpdoc->appendTag(Tag::createInstance("@param {$type} {$name}")); } } // Add macro return type if it missed in original docblock if ($method->hasReturnType() && !$this->phpdoc->hasTag('return')) { $builder = EloquentBuilder::class; $return = $method->getReturnType(); $type = $this->concatReflectionTypes($return); if (!$return instanceof \ReflectionUnionType) { /** @phpstan-ignore method.notFound */ $type .= $this->root === "\\{$builder}" && $return->getName() === $builder ? '|static' : ''; $type .= $return->allowsNull() ? '|null' : ''; } $this->phpdoc->appendTag(Tag::createInstance("@return {$type}")); } $class = ltrim($this->declaringClassName, '\\'); if (!$this->phpdoc->hasTag('return') && isset(static::$macroDefaults[$class])) { $type = static::$macroDefaults[$class]; $this->phpdoc->appendTag(Tag::createInstance("@return {$type}")); } } protected function concatReflectionTypes(?\ReflectionType $type): string { if ($type instanceof \ReflectionNamedType) { return $type->getName(); } if ($type instanceof \ReflectionIntersectionType) { return $this->formatIntersectionType($type); } if ($type instanceof \ReflectionUnionType) { return $this->formatUnionType($type); } // Unknown or null type return ''; } protected function formatUnionType(\ReflectionUnionType $type): string { return Collection::make($type->getTypes()) ->map(function (\ReflectionType $inner) { if ($inner instanceof \ReflectionNamedType) { return $inner->getName(); } if ($inner instanceof \ReflectionIntersectionType) { return $this->formatIntersectionType($inner); } // ReflectionUnionType cannot be nested per PHP's DNF rules return null; }) ->filter() ->implode('|'); } protected function formatIntersectionType(\ReflectionIntersectionType $type): string { $parts = Collection::make($type->getTypes()) ->map(fn (\ReflectionNamedType $t) => $t->getName()) ->toArray(); return '(' . implode('&', $parts) . ')'; } protected function addLocationToPhpDoc() { if ($this->method->name === '__invoke') { $enclosingClass = $this->method->getDeclaringClass(); } else { $enclosingClass = $this->method->getClosureScopeClass(); } if (!$enclosingClass) { return; } /** @var \ReflectionMethod $enclosingMethod */ $enclosingMethod = Collection::make($enclosingClass->getMethods()) ->first(function (\ReflectionMethod $method) { return $method->getStartLine() <= $this->method->getStartLine() && $method->getEndLine() >= $this->method->getEndLine(); }); if ($enclosingMethod) { $this->phpdoc->appendTag(Tag::createInstance( '@see \\' . $enclosingClass->getName() . '::' . $enclosingMethod->getName() . '()' )); } } /** * @param \ReflectionFunctionAbstract $method * @param \ReflectionClass $class */ protected function initClassDefinedProperties($method, \ReflectionClass $class) { $this->namespace = $class->getNamespaceName(); $this->declaringClassName = '\\' . ltrim($class->name, '\\'); } } ================================================ FILE: src/Method.php ================================================ * @copyright 2014 Barry vd. Heuvel / 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; use Barryvdh\Reflection\DocBlock; use Barryvdh\Reflection\DocBlock\Context; use Barryvdh\Reflection\DocBlock\Serializer as DocBlockSerializer; use Barryvdh\Reflection\DocBlock\Tag; use Barryvdh\Reflection\DocBlock\Tag\ParamTag; use Barryvdh\Reflection\DocBlock\Tag\ReturnTag; class Method { /** @var DocBlock */ protected $phpdoc; /** @var \ReflectionMethod */ protected $method; protected $output = ''; protected $declaringClassName; protected $name; protected $namespace; protected $params = []; protected $params_with_default = []; protected $interfaces = []; protected $real_name; protected $return = null; protected $root; protected $classAliases; protected $returnTypeNormalizers; /** @var string[] */ protected $templateNames = []; /** * @param \ReflectionMethod|\ReflectionFunctionAbstract $method * @param \ReflectionClass $class * @param string|null $methodName * @param array $interfaces * @param array $classAliases * @param array $returnTypeNormalizers * @param string[] $templateNames */ public function __construct($method, $class, $methodName = null, $interfaces = [], array $classAliases = [], array $returnTypeNormalizers = [], array $templateNames = []) { $this->method = $method; $this->interfaces = $interfaces; $this->classAliases = $classAliases; $this->returnTypeNormalizers = $returnTypeNormalizers; $this->name = $methodName ?: $method->name; $this->real_name = $method->isClosure() ? $this->name : $method->name; $this->templateNames = $templateNames; $this->initClassDefinedProperties($method, $class); //Reference the 'real' function in the declaring class $this->root = '\\' . ltrim($method->name === '__invoke' ? $method->getDeclaringClass()->getName() : $class->getName(), '\\'); //Create a DocBlock and serializer instance $this->initPhpDoc($method); //Normalize the description and inherit the docs from parents/interfaces try { $this->normalizeParams($this->phpdoc); $this->normalizeReturn($this->phpdoc); $this->normalizeDescription($this->phpdoc); } catch (\Exception $e) { } //Get the parameters, including formatted default values $this->getParameters($method); //Make the method static $this->phpdoc->appendTag(Tag::createInstance('@static', $this->phpdoc)); } /** * @param \ReflectionMethod $method */ protected function initPhpDoc($method) { $this->phpdoc = new DocBlock($method, new Context($this->namespace, $this->classAliases, generics: $this->templateNames)); } /** * @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 * * @return string */ public function getDeclaringClass() { return $this->declaringClassName; } /** * Return the class from which this function would be called * * @return string */ public function getRoot() { return $this->root; } /** * @return bool */ public function isInstanceCall() { return !($this->method->isClosure() || $this->method->isStatic()); } /** * @return string */ public function getRootMethodCall() { if ($this->isInstanceCall()) { return "\$instance->{$this->getRealName()}({$this->getParams()})"; } else { return "{$this->getRoot()}::{$this->getRealName()}({$this->getParams()})"; } } /** * Get the docblock for this method * * @param string $prefix * @return mixed */ public function getDocComment($prefix = "\t\t") { $serializer = new DocBlockSerializer(1, $prefix); return $serializer->getDocComment($this->phpdoc); } /** * Get the method name * * @return string */ public function getName() { return $this->name; } /** * Get the real method name * * @return string */ public function getRealName() { return $this->real_name; } /** * Get the parameters for this method * * @param bool $implode Whether to implode the array or not * @return string */ public function getParams($implode = true) { return $implode ? implode(', ', $this->params) : $this->params; } /** * @param DocBlock|null $phpdoc * @return ReturnTag|null */ public function getReturnTag($phpdoc = null) { if ($phpdoc === null) { $phpdoc = $this->phpdoc; } $returnTags = $phpdoc->getTagsByName('return'); if (count($returnTags) === 0) { return null; } return reset($returnTags); } /** * Get the parameters for this method including default values * * @param bool $implode Whether to implode the array or not * @return string */ public function getParamsWithDefault($implode = true) { return $implode ? implode(', ', $this->params_with_default) : $this->params_with_default; } /** * Get the description and get the inherited docs. * * @param DocBlock $phpdoc */ protected function normalizeDescription(DocBlock $phpdoc) { //Get the short + long description from the DocBlock $description = $phpdoc->getText(); //Loop through parents/interfaces, to fill in {@inheritdoc} if (strpos($description, '{@inheritdoc}') !== false) { $inheritdoc = $this->getInheritDoc($this->method); $inheritDescription = $inheritdoc->getText(); $description = str_replace('{@inheritdoc}', $inheritDescription, $description); $phpdoc->setText($description); $this->normalizeParams($inheritdoc); $this->normalizeReturn($inheritdoc); //Add the tags that are inherited $inheritTags = $inheritdoc->getTags(); if ($inheritTags) { /** @var Tag $tag */ foreach ($inheritTags as $tag) { $tag->setDocBlock(); $phpdoc->appendTag($tag); } } } } /** * Normalize the parameters * * @param DocBlock $phpdoc */ protected function normalizeParams(DocBlock $phpdoc) { //Get the return type and adjust them for beter autocomplete $paramTags = $phpdoc->getTagsByName('param'); if ($paramTags) { /** @var ParamTag $tag */ foreach ($paramTags as $tag) { // Convert the keywords $content = $this->convertKeywords($tag->getContent()); $tag->setContent($content); // Get the expanded type and re-set the content $content = $tag->getType() . ' ' . $tag->getVariableName() . ' ' . $tag->getDescription(); $tag->setContent(trim($content)); } } } /** * Normalize the return tag (make full namespace, replace interfaces, resolve $this) * * @param DocBlock $phpdoc */ protected function normalizeReturn(DocBlock $phpdoc) { //Get the return type and adjust them for better autocomplete $tag = $this->getReturnTag($phpdoc); if ($tag === null) { $this->return = null; return; } // Get the expanded type $returnValue = $tag->getType(); if (array_key_exists($returnValue, $this->returnTypeNormalizers)) { $returnValue = $this->returnTypeNormalizers[$returnValue]; } if ($returnValue === '$this') { $returnValue = $this->root; } // Replace the interfaces foreach ($this->interfaces as $interface => $real) { $returnValue = str_replace($interface, $real, $returnValue); } // Set the changed content $tag->setContent($returnValue . ' ' . $tag->getDescription()); $this->return = $returnValue; } /** * Convert keywords that are incorrect. * * @param string $string * @return string */ protected function convertKeywords($string) { $string = str_replace('\Closure', 'Closure', $string); $string = str_replace('Closure', '\Closure', $string); $string = str_replace('dynamic', 'mixed', $string); return $string; } /** * Should the function return a value? * * @return bool */ public function shouldReturn() { if ($this->return !== 'void' && $this->method->name !== '__construct') { return true; } return false; } /** * Get the parameters and format them correctly * * @param \ReflectionMethod $method * @return void */ public function getParameters($method) { //Loop through the default values for parameters, and make the correct output string $params = []; $paramsWithDefault = []; foreach ($method->getParameters() as $param) { $paramStr = $param->isVariadic() ? '...$' . $param->getName() : '$' . $param->getName(); $params[] = $paramStr; if ($param->isOptional() && !$param->isVariadic()) { $default = $param->isDefaultValueAvailable() ? $param->getDefaultValue() : null; if (is_bool($default)) { $default = $default ? 'true' : 'false'; } elseif (is_array($default)) { $default = '[]'; } elseif (is_null($default)) { $default = 'null'; } elseif (is_int($default)) { //$default = $default; } elseif (is_resource($default)) { //skip to not fail } else { $default = var_export($default, true); } $paramStr .= " = $default"; } $paramsWithDefault[] = $paramStr; } $this->params = $params; $this->params_with_default = $paramsWithDefault; } /** * @param \ReflectionMethod $reflectionMethod * @return DocBlock */ protected function getInheritDoc($reflectionMethod) { $parentClass = $reflectionMethod->getDeclaringClass()->getParentClass(); //Get either a parent or the interface if ($parentClass) { $method = $parentClass->getMethod($reflectionMethod->getName()); } else { $method = $reflectionMethod->getPrototype(); } if ($method) { $namespace = $method->getDeclaringClass()->getNamespaceName(); $phpdoc = new DocBlock($method, new Context($namespace, $this->classAliases, generics: $this->templateNames)); if (strpos($phpdoc->getText(), '{@inheritdoc}') !== false) { //Not at the end yet, try another parent/interface.. return $this->getInheritDoc($method); } return $phpdoc; } } } ================================================ FILE: src/Parsers/PhpDocReturnTypeParser.php ================================================ typeAlias = $typeAlias; $this->namespaceAliases = $namespaceAliases; } /** * @return string|null */ public function parse(): string|null { $matches = []; preg_match('/(\w+)(<.*>)/', $this->typeAlias, $matches); $matchCount = count($matches); if ($matchCount === 0 || $matchCount === 1) { return null; } if (empty($this->namespaceAliases[$matches[1]])) { return null; } return $this->namespaceAliases[$matches[1]] . $this->parseTemplate($matches[2] ?? null); } /** * @param string|null $template * @return string */ private function parseTemplate(string|null $template): string { if ($template === null || $template === '') { return ''; } $type = ''; $result = ''; foreach (str_split($template) as $char) { $match = preg_match('/[A-z]/', $char); if (!$match) { $type = $this->namespaceAliases[$type] ?? $type; $result .= $type; $result .= $char; $type = ''; continue; } $type .= $char; } return $result; } } ================================================ FILE: tests/AliasTest.php ================================================ setClasses([Builder::class]); $alias->detectMethods(); // Test $this->assertNotNull($this->getAliasMacro($alias, Builder::class, $macro)); } /** * @covers ::detectMethods */ public function testDetectMethodsEloquentBuilderMacros(): void { // Mock $macro = __FUNCTION__; $alias = new AliasMock(); // Macros EloquentBuilder::macro( $macro, function () { // empty } ); // Prepare $alias->setClasses([EloquentBuilder::class]); $alias->detectMethods(); // Test $this->assertNotNull($this->getAliasMacro($alias, EloquentBuilder::class, $macro)); } /** * @covers ::detectFake */ public function testNoExceptionOnRequiredFakeParameters(): void { // Mock $alias = new AliasMock(); // Prepare $alias->setFacade(MockFacade::class); $this->expectNotToPerformAssertions(); // Test $alias->detectFake(); } /** * @covers ::detectTemplateNames */ public function testTemplateNamesAreDetected(): void { // Mock $alias = new AliasMock(); // Prepare $alias->setClasses([EloquentBuilder::class]); // Test $this->assertSame(['TModel', 'TValue'], $alias->getTemplateNames()); } protected function getAliasMacro(Alias $alias, string $class, string $method): ?Macro { return Arr::first( $alias->getMethods(), function ($macro) use ($class, $method) { return $macro instanceof Macro && $macro->getDeclaringClass() === "\\{$class}" && $macro->getName() === $method; } ); } } /** * @internal * @noinspection PhpMultipleClassesDeclarationsInOneFile * @template TValue */ class AliasMock extends Alias { public function __construct() { // no need to call parent } /** * @param string[] $classes */ public function setClasses(array $classes) { $this->classes = $classes; } public function detectMethods() { parent::detectMethods(); } public function detectFake() { parent::detectFake(); } public function setFacade(string $facade) { $this->facade = $facade; } } class MockFacade extends Facade { protected static function getFacadeAccessor() { return 'Illuminate\Foundation\Exceptions\Handler'; } public static function fake(string $test1, $test2 = null) { } } ================================================ FILE: tests/Console/EloquentCommandTest.php ================================================ getVendorModelFilename(); $modelSource = file_get_contents($modelFilename); if (false !== strpos($modelSource, '* @mixin')) { $msg = sprintf('Class %s already contains the @mixin markers', Model::class); $this->markTestSkipped($msg); } $actualContent = null; $mockFilesystem = Mockery::mock(Filesystem::class)->makePartial(); $mockFilesystem ->shouldReceive('get') // We don't care about actual args (filename) ->andReturn('abstract class Model implements'); // This is enough to trigger the replacement logic $mockFilesystem ->shouldReceive('put') ->with( Mockery::any(), // First arg is path, we don't care Mockery::capture($actualContent) ) ->andReturn(1) // Simulate we wrote _something_ to the file ->once(); $this->instance(Filesystem::class, $mockFilesystem); $command = $this->app->make(EloquentCommand::class); $tester = $this->runCommand($command); $this->assertMatchesTxtSnapshot($actualContent); $display = $tester->getDisplay(); $this->assertMatchesRegularExpression( ';Unexpected no document on Illuminate\\\Database\\\Eloquent\\\Model;', $display ); $modelClassFilePath = preg_quote( str_replace('/', DIRECTORY_SEPARATOR, '/vendor/laravel/framework/src/Illuminate/Database/Eloquent/Model.php') ); $this->assertMatchesRegularExpression( ';Wrote expected docblock to .*' . $modelClassFilePath . ';', $display ); } private function getVendorModelFilename(): string { $class = Model::class; $reflectedClass = new ReflectionClass($class); return $reflectedClass->getFileName(); } } ================================================ FILE: tests/Console/GeneratorCommand/AbstractGeneratorCommand.php ================================================ mockFilesystem(); } /** * Get package providers. * * @param \Illuminate\Foundation\Application $app * * @return array */ protected function getPackageProviders($app) { return [IdeHelperServiceProvider::class]; } } ================================================ FILE: tests/Console/GeneratorCommand/GenerateEloquentOnly/Test.php ================================================ app->make(GeneratorCommand::class); $tester = $this->runCommand($command, [ '--eloquent' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('A new helper file was written to _ide_helper.php', $tester->getDisplay()); $this->assertStringNotContainsString('public static function configure($basePath = null)', $this->mockFilesystemOutput); $this->assertStringContainsString('class Eloquent extends \Illuminate\Database\Eloquent\Model', $this->mockFilesystemOutput); } } ================================================ FILE: tests/Console/GeneratorCommand/GenerateIdeHelper/Test.php ================================================ app['config']->set('ide-helper.macro_default_return_types', [Arr::class => 'Custom_Fake_Class']); $command = $this->app->make(GeneratorCommand::class); $tester = $this->runCommand($command); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('A new helper file was written to _ide_helper.php', $tester->getDisplay()); $this->assertStringContainsString('public static function configure($basePath = null)', $this->mockFilesystemOutput); $this->assertStringContainsString('* @return \Custom_Fake_Class', $this->mockFilesystemOutput); $this->assertStringContainsString('public static function arr_custom_macro()', $this->mockFilesystemOutput); $this->assertStringContainsString('public static function db_custom_macro()', $this->mockFilesystemOutput); } public function testFilename(): void { $command = $this->app->make(GeneratorCommand::class); $tester = $this->runCommand($command, [ 'filename' => 'foo.php', ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('A new helper file was written to foo.php', $tester->getDisplay()); } } ================================================ FILE: tests/Console/MetaCommand/MetaCommandTest.php ================================================ mockFilesystem(); } public function testCommand(): void { /** @var Filesystem|MockInterface $mockFileSystem */ $mockFileSystem = $this->app->make(Filesystem::class); $this->instance(Filesystem::class, $mockFileSystem); $mockFileSystem ->shouldReceive('getRequire') ->andReturnUsing(function ($__path, $__data = []) { return (static function () use ($__path, $__data) { extract($__data, EXTR_SKIP); return require $__path; })(); }); $this->artisan('ide-helper:meta'); // We're not testing the whole file, just some basic structure elements self::assertStringContainsString("namespace PHPSTORM_META {\n", $this->mockFilesystemOutput); self::assertStringContainsString("PhpStorm Meta file, to provide autocomplete information for PhpStorm\n", $this->mockFilesystemOutput); self::assertStringContainsString('override(', $this->mockFilesystemOutput); } public function testUnregisterAutoloader(): void { $current = spl_autoload_functions(); $appended = function () { }; $this->app->bind('registers-autoloader', function () use ($appended) { spl_autoload_register($appended); return new stdClass(); }); /** @var Filesystem|MockInterface $mockFileSystem */ $mockFileSystem = $this->app->make(Filesystem::class); $this->instance(Filesystem::class, $mockFileSystem); $mockFileSystem ->shouldReceive('getRequire') ->andReturnUsing(function ($__path, $__data = []) { return (static function () use ($__path, $__data) { extract($__data, EXTR_SKIP); return require $__path; })(); }); $this->artisan('ide-helper:meta'); self::assertSame(array_merge($current, [$appended]), spl_autoload_functions()); } /** * Get package providers. * * @param \Illuminate\Foundation\Application $app * * @return array */ protected function getPackageProviders($app) { return [IdeHelperServiceProvider::class]; } } ================================================ FILE: tests/Console/ModelsCommand/AbstractModelsCommand.php ================================================ loadMigrationsFrom(__DIR__ . '/migrations'); $this->artisan('migrate'); $this->mockFilesystem(); } /** * Get package providers. * * @param \Illuminate\Foundation\Application $app * * @return array */ protected function getPackageProviders($app) { return [IdeHelperServiceProvider::class]; } protected function getEnvironmentSetUp($app) { parent::getEnvironmentSetUp($app); $config = $app['config']; $config->set('database.default', 'sqlite'); $config->set('database.connections.sqlite', [ 'driver' => 'sqlite', 'database' => ':memory:', 'prefix' => '', ]); // Load the Models from the Test dir $config->set('ide-helper.model_locations', [ dirname((new \ReflectionClass(static::class))->getFileName()) . '/Models', ]); // Don't override integer -> int for tests $config->set('ide-helper.type_overrides', []); $config->set('ide-helper.write_model_relation_exists_properties', true); } } ================================================ FILE: tests/Console/ModelsCommand/AdvancedCasts/Collections/AdvancedCastCollection.php ================================================ toArray(); } } ================================================ FILE: tests/Console/ModelsCommand/AdvancedCasts/Enums/AdvancedCastEnum.php ================================================ 'date:Y-m-d', 'cast_to_datetime_serialization' => 'datetime:Y-m-d H:i:s', 'cast_to_custom_datetime' => 'custom_datetime:Y-m-d H:i:s', 'cast_to_immutable_date' => 'immutable_date', 'cast_to_immutable_custom_datetime' => 'immutable_custom_datetime:Y-m-d H:i:s', 'cast_to_immutable_datetime' => 'immutable_datetime', 'cast_to_timestamp' => 'timestamp', 'cast_to_encrypted' => 'encrypted', 'cast_to_encrypted_array' => 'encrypted:array', 'cast_to_encrypted_collection' => 'encrypted:collection', 'cast_to_encrypted_json' => 'encrypted:json', 'cast_to_encrypted_object' => 'encrypted:object', 'cast_to_as_collection' => AsCollection::class, 'cast_to_as_collection_of' => AsCollection::class . ':,' . AdvancedCastMap::class, // since 12.10 'cast_to_as_collection_using' => AsCollection::using(AdvancedCastCollection::class), 'cast_to_as_collection_using_and_map' => AsCollection::class . ':' . AdvancedCastCollection::class . ',' . AdvancedCastMap::class, // since 12.10 'cast_to_as_enum_collection' => AsEnumCollection::class, 'cast_to_as_enum_collection_of' => AsEnumCollection::of(AdvancedCastEnum::class), 'cast_to_as_array_object' => AsArrayObject::class, ]; } } ================================================ FILE: tests/Console/ModelsCommand/AdvancedCasts/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/AdvancedCasts/__snapshots__/Test__test__1.php ================================================ $cast_to_encrypted_array * @property \Illuminate\Support\Collection $cast_to_encrypted_collection * @property array $cast_to_encrypted_json * @property object $cast_to_encrypted_object * @property \Illuminate\Support\Collection $cast_to_as_collection * @property \Illuminate\Support\Collection $cast_to_as_enum_collection * @property \Illuminate\Database\Eloquent\Casts\ArrayObject $cast_to_as_array_object * @property \Illuminate\Support\Collection $cast_to_as_collection_of * @property AdvancedCastCollection $cast_to_as_collection_using * @property AdvancedCastCollection $cast_to_as_collection_using_and_map * @property \Illuminate\Support\Collection $cast_to_as_enum_collection_of * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast newQuery() * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast query() * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToAsArrayObject($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToAsCollection($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToAsEnumCollection($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToCustomDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToDateSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToDatetimeSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToEncrypted($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToEncryptedArray($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToEncryptedCollection($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToEncryptedJson($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToEncryptedObject($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToImmutableCustomDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToImmutableDate($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToImmutableDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|AdvancedCast whereCastToTimestamp($value) * @mixin \Eloquent */ class AdvancedCast extends Model { protected function casts(): array { return [ 'cast_to_date_serialization' => 'date:Y-m-d', 'cast_to_datetime_serialization' => 'datetime:Y-m-d H:i:s', 'cast_to_custom_datetime' => 'custom_datetime:Y-m-d H:i:s', 'cast_to_immutable_date' => 'immutable_date', 'cast_to_immutable_custom_datetime' => 'immutable_custom_datetime:Y-m-d H:i:s', 'cast_to_immutable_datetime' => 'immutable_datetime', 'cast_to_timestamp' => 'timestamp', 'cast_to_encrypted' => 'encrypted', 'cast_to_encrypted_array' => 'encrypted:array', 'cast_to_encrypted_collection' => 'encrypted:collection', 'cast_to_encrypted_json' => 'encrypted:json', 'cast_to_encrypted_object' => 'encrypted:object', 'cast_to_as_collection' => AsCollection::class, 'cast_to_as_collection_of' => AsCollection::class . ':,' . AdvancedCastMap::class, // since 12.10 'cast_to_as_collection_using' => AsCollection::using(AdvancedCastCollection::class), 'cast_to_as_collection_using_and_map' => AsCollection::class . ':' . AdvancedCastCollection::class . ',' . AdvancedCastMap::class, // since 12.10 'cast_to_as_enum_collection' => AsEnumCollection::class, 'cast_to_as_enum_collection_of' => AsEnumCollection::of(AdvancedCastEnum::class), 'cast_to_as_array_object' => AsArrayObject::class, ]; } } ================================================ FILE: tests/Console/ModelsCommand/AllowGlobDirectory/Services/Post/Models/Post.php ================================================ cwd = getcwd(); } protected function tearDown(): void { chdir($this->cwd); parent::tearDown(); } public function test(): void { $command = $this->app->make(ModelsCommand::class); chdir(__DIR__); $tester = $this->runCommand($command, [ '--dir' => ['Services/*/Models'], '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/AllowGlobDirectory/__snapshots__/Test__test__1.php ================================================ |Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post query() * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) * @mixin \Eloquent */ class Post extends Model { } ================================================ FILE: tests/Console/ModelsCommand/ArrayCastsWithComment/Models/ArrayCastsWithComment.php ================================================ |null $cast_to_array -- These three should not be duplicated * @property array $cast_to_json some-description * @property \Illuminate\Support\Collection $cast_to_collection some-description * * @property array|null $cast_to_encrypted_array -- These three are OK (no types) * @property array $cast_to_encrypted_json some-description * @property \Illuminate\Support\Collection $cast_to_encrypted_collection some-description * * @property string $cast_to_string -- The next three are OK (no description), this not included * * @property array|null $cast_to_immutable_date * @property array $cast_to_immutable_date_serialization * @property \Illuminate\Support\Collection $cast_to_immutable_custom_datetime */ class ArrayCastsWithComment extends Model { protected $table = 'simple_casts'; protected $casts = [ 'cast_to_array' => 'array', 'cast_to_json' => 'json', 'cast_to_collection' => 'collection', 'cast_to_encrypted_array' => 'array', 'cast_to_encrypted_json' => 'json', 'cast_to_encrypted_collection' => 'collection', 'cast_to_string' => 'string', 'cast_to_immutable_date' => 'array', 'cast_to_immutable_date_serialization' => 'json', 'cast_to_immutable_custom_datetime' => 'collection', ]; } ================================================ FILE: tests/Console/ModelsCommand/ArrayCastsWithComment/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/ArrayCastsWithComment/__snapshots__/Test__test__1.php ================================================ |null $cast_to_array -- These three should not be duplicated * @property array $cast_to_json some-description * @property \Illuminate\Support\Collection $cast_to_collection some-description * @property array|null $cast_to_encrypted_array -- These three are OK (no types) * @property array $cast_to_encrypted_json some-description * @property \Illuminate\Support\Collection $cast_to_encrypted_collection some-description * @property string $cast_to_string -- The next three are OK (no description), this not included * @property array|null $cast_to_immutable_date * @property array $cast_to_immutable_date_serialization * @property \Illuminate\Support\Collection $cast_to_immutable_custom_datetime * @property string $cast_to_int * @property string $cast_to_integer * @property string $cast_to_real * @property string $cast_to_float * @property string $cast_to_double * @property string $cast_to_decimal * @property string $cast_to_bool * @property string $cast_to_boolean * @property string $cast_to_object * @property string $cast_to_date * @property string $cast_to_datetime * @property string $cast_to_date_serialization * @property string $cast_to_datetime_serialization * @property string $cast_to_custom_datetime * @property string $cast_to_immutable_datetime * @property string $cast_to_immutable_datetime_serialization * @property string $cast_to_timestamp * @property string $cast_to_encrypted * @property string $cast_to_encrypted_object * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment newQuery() * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment query() * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToArray($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToBool($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToBoolean($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToCollection($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToCustomDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToDate($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToDateSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToDatetimeSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToDecimal($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToDouble($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToEncrypted($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToEncryptedArray($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToEncryptedCollection($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToEncryptedJson($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToEncryptedObject($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToFloat($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToImmutableCustomDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToImmutableDate($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToImmutableDateSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToImmutableDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToImmutableDatetimeSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToInt($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToInteger($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToJson($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToObject($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToReal($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToString($value) * @method static \Illuminate\Database\Eloquent\Builder|ArrayCastsWithComment whereCastToTimestamp($value) * @mixin \Eloquent */ class ArrayCastsWithComment extends Model { protected $table = 'simple_casts'; protected $casts = [ 'cast_to_array' => 'array', 'cast_to_json' => 'json', 'cast_to_collection' => 'collection', 'cast_to_encrypted_array' => 'array', 'cast_to_encrypted_json' => 'json', 'cast_to_encrypted_collection' => 'collection', 'cast_to_string' => 'string', 'cast_to_immutable_date' => 'array', 'cast_to_immutable_date_serialization' => 'json', 'cast_to_immutable_custom_datetime' => 'collection', ]; } ================================================ FILE: tests/Console/ModelsCommand/Attributes/Models/BackedAttribute.php ================================================ name; }, function (?string $name) { $this->name = $name; } ); } protected function divergingTypeHintedGetAndSet(): Attribute { return new Attribute( function (): int { return strlen($this->name); }, function (?string $name) { $this->name = $name; } ); } protected function typeHintedGet(): Attribute { return Attribute::get(function (): ?string { return $this->name; }); } protected function typeHintedSet(): Attribute { return Attribute::set(function (?string $name) { $this->name = $name; }); } protected function nonTypeHintedGetAndSet(): Attribute { return new Attribute( function () { return $this->name; }, function ($name) { $this->name = $name; } ); } protected function nonTypeHintedGet(): Attribute { return Attribute::get(function () { return $this->name; }); } protected function nonTypeHintedSet(): Attribute { return Attribute::set(function ($name) { $this->name = $name; }); } protected function parameterlessSet(): Attribute { return Attribute::set(function () { $this->name = null; }); } /** * ide-helper does not recognize this method being an Attribute * because the method has no actual return type; * phpdoc is ignored here deliberately due to performance reasons and also * isn't supported by Laravel itself. * * @return Attribute */ protected function notAnAttribute() { return new Attribute( function (?string $value): ?string { return $value; }, function (?string $value): ?string { return $value; } ); } } ================================================ FILE: tests/Console/ModelsCommand/Attributes/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/Attributes/__snapshots__/Test__test__1.php ================================================ |BackedAttribute newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|BackedAttribute newQuery() * @method static \Illuminate\Database\Eloquent\Builder|BackedAttribute query() * @method static \Illuminate\Database\Eloquent\Builder|BackedAttribute whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|BackedAttribute whereName($value) * @method static \Illuminate\Database\Eloquent\Builder|BackedAttribute whereNameRead($value) * @method static \Illuminate\Database\Eloquent\Builder|BackedAttribute whereNameWrite($value) * @mixin \Eloquent */ class BackedAttribute extends Model { protected function name(): Attribute { return new Attribute( function (?string $name): ?string { return $name; }, function (?string $name): ?string { return $name; } ); } protected function nameRead(): Attribute { return new Attribute( function (?string $name): ?string { return $name; }, ); } protected function nameWrite(): Attribute { return new Attribute( set: function (?string $name): ?string { return $name; }, ); } protected function nonBackedSet(): Attribute { return new Attribute( set: function (?string $name): ?string { return $name; }, ); } protected function nonBackedGet(): Attribute { return new Attribute( get: function (): ?string { return 'test'; }, ); } } |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { // With a backed property protected function name(): Attribute { return new Attribute( function (?string $name): ?string { return $name; }, function (?string $name): ?string { return $name; } ); } // Without backed properties protected function typeHintedGetAndSet(): Attribute { return new Attribute( function (): ?string { return $this->name; }, function (?string $name) { $this->name = $name; } ); } protected function divergingTypeHintedGetAndSet(): Attribute { return new Attribute( function (): int { return strlen($this->name); }, function (?string $name) { $this->name = $name; } ); } protected function typeHintedGet(): Attribute { return Attribute::get(function (): ?string { return $this->name; }); } protected function typeHintedSet(): Attribute { return Attribute::set(function (?string $name) { $this->name = $name; }); } protected function nonTypeHintedGetAndSet(): Attribute { return new Attribute( function () { return $this->name; }, function ($name) { $this->name = $name; } ); } protected function nonTypeHintedGet(): Attribute { return Attribute::get(function () { return $this->name; }); } protected function nonTypeHintedSet(): Attribute { return Attribute::set(function ($name) { $this->name = $name; }); } protected function parameterlessSet(): Attribute { return Attribute::set(function () { $this->name = null; }); } /** * ide-helper does not recognize this method being an Attribute * because the method has no actual return type; * phpdoc is ignored here deliberately due to performance reasons and also * isn't supported by Laravel itself. * * @return Attribute */ protected function notAnAttribute() { return new Attribute( function (?string $value): ?string { return $value; }, function (?string $value): ?string { return $value; } ); } } ================================================ FILE: tests/Console/ModelsCommand/Comment/Models/Simple.php ================================================ hasMany(Simple::class); } /** * @comment MorphTo relations. * @return MorphTo */ public function relationMorphTo(): MorphTo { return $this->morphTo(); } /** * @comment Others relations. * @return HasOne */ public function relationHasOne(): HasOne { return $this->hasOne(Simple::class); } /** * @comment I'm a setter */ public function setBothSameNameAttribute(): void { } /** * @comment I'm a getter * @return string */ public function getBothSameNameAttribute(): string { } /** * @comment I'm a setter */ public function setBothWithoutGetterCommentAttribute(): void { } /** * @return string */ public function getBothWithoutGetterCommentAttribute(): string { } } ================================================ FILE: tests/Console/ModelsCommand/Comment/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/Comment/__snapshots__/Test__test__1.php ================================================ $relationHasMany HasMany relations. * @property-read int|null $relation_has_many_count * @property-read bool|null $relation_has_many_exists * @property-read Simple|null $relationHasOne Others relations. * @property-read Model|\Eloquent $relationMorphTo MorphTo relations. * @property-write mixed $first_name Set the user's first name. * @method static \Illuminate\Database\Eloquent\Builder|Simple active() Scope a query to only include active users. * @method static \Illuminate\Database\Eloquent\Builder|Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { /** * There is not comment. * * @return string */ public function getNotCommentAttribute(): string { } /** * comment There is not format comment, invalid. * * @return string */ public function getFakerCommentAttribute(): string { } /** * @comment There is format comment, success. * * @return string */ public function getFormatCommentAttribute(): string { } /** * @comment There is format comment, success. * This is second line, success too. * * @return string */ public function getFormatCommentLineTwoAttribute(): string { } /** * @comment There is format comment, success. * @comment This is others format comment, invalid. * * @return string */ public function getManyFormatCommentAttribute(): string { } /** * @comment Set the user's first name. * @param $value */ public function setFirstNameAttribute($value) { } /** * @comment Scope a query to only include active users. * * @param $query * @return mixed */ public function scopeActive($query) { return $query; } /** * @comment HasMany relations. * * @return HasMany */ public function relationHasMany(): HasMany { return $this->hasMany(Simple::class); } /** * @comment MorphTo relations. * @return MorphTo */ public function relationMorphTo(): MorphTo { return $this->morphTo(); } /** * @comment Others relations. * @return HasOne */ public function relationHasOne(): HasOne { return $this->hasOne(Simple::class); } /** * @comment I'm a setter */ public function setBothSameNameAttribute(): void { } /** * @comment I'm a getter * @return string */ public function getBothSameNameAttribute(): string { } /** * @comment I'm a setter */ public function setBothWithoutGetterCommentAttribute(): void { } /** * @return string */ public function getBothWithoutGetterCommentAttribute(): string { } } ================================================ FILE: tests/Console/ModelsCommand/CustomCollection/Collections/SimpleCollection.php ================================================ hasMany(Simple::class); } } ================================================ FILE: tests/Console/ModelsCommand/CustomCollection/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/CustomCollection/__snapshots__/Test__test__1.php ================================================ $relationHasMany * @property-read int|null $relation_has_many_count * @property-read bool|null $relation_has_many_exists * @method static SimpleCollection all($columns = ['*']) * @method static SimpleCollection get($columns = ['*']) * @method static \Illuminate\Database\Eloquent\Builder|Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { public function newCollection(array $models = []) { return new SimpleCollection($models); } public function relationHasMany(): HasMany { return $this->hasMany(Simple::class); } } ================================================ FILE: tests/Console/ModelsCommand/CustomDate/Models/CustomDate.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/CustomDate/__snapshots__/Test__test__1.php ================================================ |CustomDate newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|CustomDate newQuery() * @method static \Illuminate\Database\Eloquent\Builder|CustomDate query() * @method static \Illuminate\Database\Eloquent\Builder|CustomDate whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomDate whereUpdatedAt($value) * @mixin \Eloquent */ class CustomDate extends Model { } ================================================ FILE: tests/Console/ModelsCommand/CustomPhpdocTags/Models/Simple.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/CustomPhpdocTags/__snapshots__/Test__testNoSpaceAfterCustomPhpdocTag__1.php ================================================ |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { } ================================================ FILE: tests/Console/ModelsCommand/DnfTypes/Models/DnfTypeModel.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/DnfTypes/__snapshots__/Test__test__1.php ================================================ |DnfTypeModel newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|DnfTypeModel newQuery() * @method static \Illuminate\Database\Eloquent\Builder|DnfTypeModel query() * @method static \Illuminate\Database\Eloquent\Builder|DnfTypeModel withBasicDnfParam((\Countable&\Iterator)|null $param) * @method static \Illuminate\Database\Eloquent\Builder|DnfTypeModel withComplexDnfParam(\stdClass|(\Countable&\Iterator)|null $param) * @method static \Illuminate\Database\Eloquent\Builder|DnfTypeModel withDnfParamAndReturn((\Countable&\Iterator)|null $param) * @method static \Illuminate\Database\Eloquent\Builder|DnfTypeModel withIntersectionOrPrimitive((\Countable&\Iterator)|int $param) * @method static \Illuminate\Database\Eloquent\Builder|DnfTypeModel withMultipleIntersectionParam((\Countable&\Iterator)|(\ArrayAccess&\Stringable) $param) * @mixin \Eloquent */ class DnfTypeModel extends Model { // ========================================================================= // RFC Example 1: (A&B)|null - Intersection with null // ========================================================================= /** * Basic DNF: intersection OR null. */ public function getBasicDnfAttribute(): (Countable&Iterator)|null { return null; } // ========================================================================= // RFC Example 2: (A&B)|D - Intersection OR single type (no null) // ========================================================================= /** * Intersection OR single class type. */ public function getIntersectionOrClassAttribute(): (Countable&Iterator)|\stdClass { return new \stdClass(); } // ========================================================================= // RFC Example 3: C|(X&D)|null - Single type OR intersection OR null // ========================================================================= /** * Single type OR intersection OR null. */ public function getSingleOrIntersectionOrNullAttribute(): \stdClass|(Countable&Iterator)|null { return null; } // ========================================================================= // RFC Example 4: (A&B&D)|int|null - Triple intersection OR primitive OR null // ========================================================================= /** * Triple intersection OR primitive OR null. */ public function getTripleIntersectionAttribute(): (Countable&Iterator&Traversable)|int|null { return null; } // ========================================================================= // RFC Example 5: (A&B)|(C&D)|null - Multiple intersection segments // ========================================================================= /** * Multiple intersection segments OR null. */ public function getMultipleIntersectionsAttribute(): (Countable&Iterator)|(ArrayAccess&Stringable)|null { return null; } // ========================================================================= // RFC Example 6: (A&B)|(C&D)|(E&F) - Multiple intersections without null // ========================================================================= /** * Multiple intersection segments without null. */ public function getMultipleIntersectionsNoNullAttribute(): (Countable&Iterator)|(ArrayAccess&Stringable)|(Traversable&Countable) { return new class () implements Countable, Iterator { public function count(): int { return 0; } public function current(): mixed { return null; } public function key(): mixed { return null; } public function next(): void { } public function rewind(): void { } public function valid(): bool { return false; } }; } // ========================================================================= // Pure intersection type (A&B) - No union, just intersection // ========================================================================= /** * Pure intersection type without union. */ public function getPureIntersectionAttribute(): Countable&Iterator { return new class () implements Countable, Iterator { public function count(): int { return 0; } public function current(): mixed { return null; } public function key(): mixed { return null; } public function next(): void { } public function rewind(): void { } public function valid(): bool { return false; } }; } // ========================================================================= // Parameter context: DNF types in method parameters // ========================================================================= /** * Scope with DNF parameter: (A&B)|null. */ public function scopeWithBasicDnfParam( \Illuminate\Database\Query\Builder $query, (Countable&Iterator)|null $param ): \Illuminate\Database\Query\Builder { return $query; } /** * Scope with complex DNF parameter: C|(A&B)|null. */ public function scopeWithComplexDnfParam( \Illuminate\Database\Query\Builder $query, \stdClass|(Countable&Iterator)|null $param ): \Illuminate\Database\Query\Builder { return $query; } /** * Scope with multiple intersection parameters. */ public function scopeWithMultipleIntersectionParam( \Illuminate\Database\Query\Builder $query, (Countable&Iterator)|(ArrayAccess&Stringable) $param ): \Illuminate\Database\Query\Builder { return $query; } /** * Scope with intersection OR primitive parameter. */ public function scopeWithIntersectionOrPrimitive( \Illuminate\Database\Query\Builder $query, (Countable&Iterator)|int $param ): \Illuminate\Database\Query\Builder { return $query; } // ========================================================================= // Mixed: DNF in both parameter and return type // ========================================================================= /** * DNF in both parameter and return type. */ public function scopeWithDnfParamAndReturn( \Illuminate\Database\Query\Builder $query, (Countable&Iterator)|null $param ): (Countable&Iterator)|\Illuminate\Database\Query\Builder { return $query; } } ================================================ FILE: tests/Console/ModelsCommand/DoesNotGeneratePhpdocWithExternalEloquentBuilder/Builders/PostExternalQueryBuilder.php ================================================ set('ide-helper.write_model_external_builder_methods', false); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--nowrite' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Model information was written to _ide_helper_models.php', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/DoesNotGeneratePhpdocWithExternalEloquentBuilder/__snapshots__/Test__test__1.php ================================================ */ namespace Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\DoesNotGeneratePhpdocWithExternalEloquentBuilder\Models{ /** * @property int $id * @property string|null $char_nullable * @property string $char_not_nullable * @property string|null $string_nullable * @property string $string_not_nullable * @property string|null $text_nullable * @property string $text_not_nullable * @property string|null $medium_text_nullable * @property string $medium_text_not_nullable * @property string|null $long_text_nullable * @property string $long_text_not_nullable * @property int|null $integer_nullable * @property int $integer_not_nullable * @property int|null $tiny_integer_nullable * @property int $tiny_integer_not_nullable * @property int|null $small_integer_nullable * @property int $small_integer_not_nullable * @property int|null $medium_integer_nullable * @property int $medium_integer_not_nullable * @property int|null $big_integer_nullable * @property int $big_integer_not_nullable * @property int|null $unsigned_integer_nullable * @property int $unsigned_integer_not_nullable * @property int|null $unsigned_tiny_integer_nullable * @property int $unsigned_tiny_integer_not_nullable * @property int|null $unsigned_small_integer_nullable * @property int $unsigned_small_integer_not_nullable * @property int|null $unsigned_medium_integer_nullable * @property int $unsigned_medium_integer_not_nullable * @property int|null $unsigned_big_integer_nullable * @property int $unsigned_big_integer_not_nullable * @property float|null $float_nullable * @property float $float_not_nullable * @property float|null $double_nullable * @property float $double_not_nullable * @property numeric|null $decimal_nullable * @property numeric $decimal_not_nullable * @property int|null $boolean_nullable * @property int $boolean_not_nullable * @property string|null $enum_nullable * @property string $enum_not_nullable * @property string|null $json_nullable * @property string $json_not_nullable * @property string|null $jsonb_nullable * @property string $jsonb_not_nullable * @property string|null $date_nullable * @property string $date_not_nullable * @property string|null $datetime_nullable * @property string $datetime_not_nullable * @property string|null $datetimetz_nullable * @property string $datetimetz_not_nullable * @property string|null $time_nullable * @property string $time_not_nullable * @property string|null $timetz_nullable * @property string $timetz_not_nullable * @property string|null $timestamp_nullable * @property string $timestamp_not_nullable * @property string|null $timestamptz_nullable * @property string $timestamptz_not_nullable * @property int|null $year_nullable * @property int $year_not_nullable * @property string|null $binary_nullable * @property string $binary_not_nullable * @property string|null $uuid_nullable * @property string $uuid_not_nullable * @property string|null $ipaddress_nullable * @property string $ipaddress_not_nullable * @property string|null $macaddress_nullable * @property string $macaddress_not_nullable * @property \Illuminate\Support\Carbon|null $created_at * @property \Illuminate\Support\Carbon|null $updated_at * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\DoesNotGeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post newModelQuery() * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\DoesNotGeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post newQuery() * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\DoesNotGeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post query() * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) */ class Post extends \Eloquent {} } ================================================ FILE: tests/Console/ModelsCommand/DynamicRelations/Models/Dynamic.php ================================================ hasMany(Dynamic::class); } // Dynamic relations public function dynamicHasMany(): HasMany { return $this->hasMany(Dynamic::class)->where('date', '>=', $this->account->created_at); } public function dynamicHasOne(): HasOne { return $this->hasOne(Dynamic::class)->where('date', '>=', $this->account->created_at); } public function dynamicBelongsTo(): BelongsTo { return $this->belongsTo(Dynamic::class)->where('date', '>=', $this->account->created_at); } } ================================================ FILE: tests/Console/ModelsCommand/DynamicRelations/OtherModels/Account.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $errors = [ 'Error resolving relation model of Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\DynamicRelations\Models\Dynamic:dynamicBelongsTo() : Attempt to read property "created_at" on null', 'Error resolving relation model of Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\DynamicRelations\Models\Dynamic:dynamicHasMany() : Attempt to read property "created_at" on null', 'Error resolving relation model of Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\DynamicRelations\Models\Dynamic:dynamicHasOne() : Attempt to read property "created_at" on null', ]; $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); foreach ($errors as $error) { $this->assertStringContainsString($error, $tester->getDisplay()); } $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/DynamicRelations/__snapshots__/Test__test__1.php ================================================ $regularHasMany * @property-read int|null $regular_has_many_count * @property-read bool|null $regular_has_many_exists * @method static \Illuminate\Database\Eloquent\Builder|Dynamic newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Dynamic newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Dynamic query() * @mixin \Eloquent */ class Dynamic extends Model { /** @var \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\DynamicRelations\OtherModels\Account */ protected $account; // Regular relations public function regularHasMany(): HasMany { return $this->hasMany(Dynamic::class); } // Dynamic relations public function dynamicHasMany(): HasMany { return $this->hasMany(Dynamic::class)->where('date', '>=', $this->account->created_at); } public function dynamicHasOne(): HasOne { return $this->hasOne(Dynamic::class)->where('date', '>=', $this->account->created_at); } public function dynamicBelongsTo(): BelongsTo { return $this->belongsTo(Dynamic::class)->where('date', '>=', $this->account->created_at); } } ================================================ FILE: tests/Console/ModelsCommand/Factories/CustomSpace/ModelWithCustomNamespaceFactory.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertStringNotContainsString('not found', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } public static function getFactoryNameResolver(): Closure { // This mimics the default resolver, but with adjusted test namespaces. // Illuminate\Database\Eloquent\Factories\Factory::resolveFactoryName return function (string $modelName): string { $appNamespace = 'Barryvdh\\LaravelIdeHelper\\Tests\\Console\\ModelsCommand\\Factories\\'; $modelName = Str::startsWith($modelName, $appNamespace . 'Models\\') ? Str::after($modelName, $appNamespace . 'Models\\') : Str::after($modelName, $appNamespace); return $appNamespace . 'Factories\\' . $modelName . 'Factory'; }; } } ================================================ FILE: tests/Console/ModelsCommand/Factories/__snapshots__/Test__testFactory__1.php ================================================ |ModelWithCustomNamespace newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithCustomNamespace newQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithCustomNamespace query() * @mixin \Eloquent */ class ModelWithCustomNamespace extends Model { use HasFactory; /** * Create a new factory instance for the model. * * @return \Illuminate\Database\Eloquent\Factories\Factory */ protected static function newFactory() { return ModelWithCustomNamespaceFactory::new(); } } |ModelWithFactory newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithFactory newQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithFactory query() * @mixin \Eloquent */ class ModelWithFactory extends Model { use HasFactory; } |ModelWithNestedFactory newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithNestedFactory newQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithNestedFactory query() * @mixin \Eloquent */ class ModelWithNestedFactory extends ModelWithFactory { } |ModelWithoutFactory newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithoutFactory newQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithoutFactory query() * @mixin \Eloquent */ class ModelWithoutFactory extends Model { use HasFactory; } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpDocWithEnumDefaults/Enums/PostStatus.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpDocWithEnumDefaults/__snapshots__/Test__test__1.php ================================================ |Post hasStatus(?\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GenerateBasicPhpDocWithEnumDefaults\Enums\PostStatus $status = \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GenerateBasicPhpDocWithEnumDefaults\Enums\PostStatus::Published) * @method static Builder|Post newModelQuery() * @method static Builder|Post newQuery() * @method static Builder|Post query() * @method static Builder|Post whereBigIntegerNotNullable($value) * @method static Builder|Post whereBigIntegerNullable($value) * @method static Builder|Post whereBinaryNotNullable($value) * @method static Builder|Post whereBinaryNullable($value) * @method static Builder|Post whereBooleanNotNullable($value) * @method static Builder|Post whereBooleanNullable($value) * @method static Builder|Post whereCharNotNullable($value) * @method static Builder|Post whereCharNullable($value) * @method static Builder|Post whereCreatedAt($value) * @method static Builder|Post whereDateNotNullable($value) * @method static Builder|Post whereDateNullable($value) * @method static Builder|Post whereDatetimeNotNullable($value) * @method static Builder|Post whereDatetimeNullable($value) * @method static Builder|Post whereDatetimetzNotNullable($value) * @method static Builder|Post whereDatetimetzNullable($value) * @method static Builder|Post whereDecimalNotNullable($value) * @method static Builder|Post whereDecimalNullable($value) * @method static Builder|Post whereDoubleNotNullable($value) * @method static Builder|Post whereDoubleNullable($value) * @method static Builder|Post whereEnumNotNullable($value) * @method static Builder|Post whereEnumNullable($value) * @method static Builder|Post whereFloatNotNullable($value) * @method static Builder|Post whereFloatNullable($value) * @method static Builder|Post whereId($value) * @method static Builder|Post whereIntegerNotNullable($value) * @method static Builder|Post whereIntegerNullable($value) * @method static Builder|Post whereIpaddressNotNullable($value) * @method static Builder|Post whereIpaddressNullable($value) * @method static Builder|Post whereJsonNotNullable($value) * @method static Builder|Post whereJsonNullable($value) * @method static Builder|Post whereJsonbNotNullable($value) * @method static Builder|Post whereJsonbNullable($value) * @method static Builder|Post whereLongTextNotNullable($value) * @method static Builder|Post whereLongTextNullable($value) * @method static Builder|Post whereMacaddressNotNullable($value) * @method static Builder|Post whereMacaddressNullable($value) * @method static Builder|Post whereMediumIntegerNotNullable($value) * @method static Builder|Post whereMediumIntegerNullable($value) * @method static Builder|Post whereMediumTextNotNullable($value) * @method static Builder|Post whereMediumTextNullable($value) * @method static Builder|Post whereSmallIntegerNotNullable($value) * @method static Builder|Post whereSmallIntegerNullable($value) * @method static Builder|Post whereStringNotNullable($value) * @method static Builder|Post whereStringNullable($value) * @method static Builder|Post whereTextNotNullable($value) * @method static Builder|Post whereTextNullable($value) * @method static Builder|Post whereTimeNotNullable($value) * @method static Builder|Post whereTimeNullable($value) * @method static Builder|Post whereTimestampNotNullable($value) * @method static Builder|Post whereTimestampNullable($value) * @method static Builder|Post whereTimestamptzNotNullable($value) * @method static Builder|Post whereTimestamptzNullable($value) * @method static Builder|Post whereTimetzNotNullable($value) * @method static Builder|Post whereTimetzNullable($value) * @method static Builder|Post whereTinyIntegerNotNullable($value) * @method static Builder|Post whereTinyIntegerNullable($value) * @method static Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static Builder|Post whereUnsignedBigIntegerNullable($value) * @method static Builder|Post whereUnsignedIntegerNotNullable($value) * @method static Builder|Post whereUnsignedIntegerNullable($value) * @method static Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static Builder|Post whereUpdatedAt($value) * @method static Builder|Post whereUuidNotNullable($value) * @method static Builder|Post whereUuidNullable($value) * @method static Builder|Post whereYearNotNullable($value) * @method static Builder|Post whereYearNullable($value) * @mixin \Eloquent */ class Post extends Model { public function scopeHasStatus(Builder $query, ?PostStatus $status = PostStatus::Published) { // } } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpdoc/Models/Post.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertStringContainsString('Do you want to generate a minimal helper to generate the Eloquent methods?', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpdoc/__snapshots__/Test__test__1.php ================================================ |Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post query() * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) * @mixin \Eloquent */ class Post extends Model { } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpdocCamel/Models/Post.php ================================================ set('ide-helper.model_camel_case_properties', true); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpdocCamel/__snapshots__/Test__test__1.php ================================================ |Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post query() * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) * @mixin \Eloquent */ class Post extends Model { } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpdocFinal/Models/Post.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpdocFinal/__snapshots__/Test__test__1.php ================================================ |Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post query() * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) * @mixin \Eloquent */ final class Post extends Model { } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpdocWithEloquentHelper/Models/Post.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, '--write-eloquent-helper' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertStringNotContainsString('Do you want to generate a minimal helper to generate the Eloquent methods?', $tester->getDisplay()); $this->assertStringContainsString('Eloquent helper was written to _ide_helper.php', $tester->getDisplay()); // $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GenerateBasicPhpdocWithEloquentHelper/__snapshots__/Test__test__1.php ================================================ |Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post query() * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) * @mixin \Eloquent */ class Post extends Model { } ================================================ FILE: tests/Console/ModelsCommand/GenerateMixinCollection/Models/WithCollection.php ================================================ */ public function getCollectionAttribute(): Collection { return new Collection(); } /** * @return Collection */ public function getCollectionWithoutTemplateAttribute(): Collection { return new Collection(); } public function getCollectionWithoutDocBlockAttribute(): Collection { return new Collection(); } /** * @return Collection */ public function getCollectionWithNonModelTemplateAttribute(): Collection { return new Collection(); } /** * @return Collection>> */ public function getCollectionWithNestedTemplateAttribute(): Collection { return new Collection(); } } ================================================ FILE: tests/Console/ModelsCommand/GenerateMixinCollection/NonModels/CollectionModel.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write-mixin' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GenerateMixinCollection/__snapshots__/Test__test__1.php ================================================ */ public function getCollectionAttribute(): Collection { return new Collection(); } /** * @return Collection */ public function getCollectionWithoutTemplateAttribute(): Collection { return new Collection(); } public function getCollectionWithoutDocBlockAttribute(): Collection { return new Collection(); } /** * @return Collection */ public function getCollectionWithNonModelTemplateAttribute(): Collection { return new Collection(); } /** * @return Collection>> */ public function getCollectionWithNestedTemplateAttribute(): Collection { return new Collection(); } } */ namespace Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GenerateMixinCollection\Models{ /** * @property-read \Illuminate\Support\Collection $collection * @property-read \Illuminate\Support\Collection<\Illuminate\Support\Collection, \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GenerateMixinCollection\NonModels\CollectionModel<\Illuminate\Support\Collection, \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GenerateMixinCollection\NonModels\CollectionModel>> $collection_with_nested_template * @property-read \Illuminate\Support\Collection $collection_with_non_model_template * @property-read \Illuminate\Support\Collection $collection_without_doc_block * @property-read \Illuminate\Support\Collection $collection_without_template * @method static \Illuminate\Database\Eloquent\Builder|WithCollection newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|WithCollection newQuery() * @method static \Illuminate\Database\Eloquent\Builder|WithCollection query() * @mixin \Eloquent */ #[\AllowDynamicProperties] class IdeHelperWithCollection {} } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpDocWithTypedScopeParameter/Models/Comment.php ================================================ where('type', $value); } /** * @comment Scope with optional boolean parameter and default true */ protected function scopeTyped02(Builder $query, bool $value = true) { $query->where('type', $value); } /** * @comment Scope with optional boolean parameter and default false */ protected function scopeTyped03(Builder $query, bool $value = false) { $query->where('type', $value); } /** * @comment Scope with required string parameter */ protected function scopeTyped04(Builder $query, string $value) { $query->where('type', $value); } /** * @comment Scope with optional string parameter and default value */ protected function scopeTyped05(Builder $query, string $value = 'dummy123') { $query->where('type', $value); } /** * @comment Scope with required integer parameter */ protected function scopeTyped06(Builder $query, int $value) { $query->where('type', $value); } /** * @comment Scope with optional integer parameter and default positive value */ protected function scopeTyped07(Builder $query, int $value = 123) { $query->where('type', $value); } /** * @comment Scope with optional integer parameter and default negative value */ protected function scopeTyped08(Builder $query, int $value = -123) { $query->where('type', $value); } /** * @comment Scope with required float parameter */ protected function scopeTyped09(Builder $query, float $value) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default positive integer value */ protected function scopeTyped10(Builder $query, float $value = 123) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default negative integer value */ protected function scopeTyped11(Builder $query, float $value = -123) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default positive float value */ protected function scopeTyped12(Builder $query, float $value = 1.23) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default negative float value */ protected function scopeTyped13(Builder $query, float $value = -1.23) { $query->where('type', $value); } /** * @comment Scope with required nullable boolean parameter */ protected function scopeTyped14(Builder $query, ?bool $value) { $query->where('type', $value); } /** * @comment Scope with optional nullable boolean parameter and default true */ protected function scopeTyped15(Builder $query, ?bool $value = true) { $query->where('type', $value); } /** * @comment Scope with optional nullable boolean parameter and default false */ protected function scopeTyped16(Builder $query, ?bool $value = false) { $query->where('type', $value); } /** * @comment Scope with optional nullable boolean parameter and default null */ protected function scopeTyped17(Builder $query, ?bool $value = null) { $query->where('type', $value); } /** * @comment Scope with required nullable string parameter */ protected function scopeTyped18(Builder $query, ?string $value) { $query->where('type', $value); } /** * @comment Scope with optional nullable string parameter and default value */ protected function scopeTyped19(Builder $query, ?string $value = 'dummy123') { $query->where('type', $value); } /** * @comment Scope with optional nullable string parameter and default null */ protected function scopeTyped20(Builder $query, ?string $value = null) { $query->where('type', $value); } /** * @comment Scope with required nullable integer parameter */ protected function scopeTyped21(Builder $query, ?int $value) { $query->where('type', $value); } /** * @comment Scope with optional nullable integer parameter and default positive value */ protected function scopeTyped22(Builder $query, ?int $value = 123) { $query->where('type', $value); } /** * @comment Scope with optional nullable integer parameter and default negative value */ protected function scopeTyped23(Builder $query, ?int $value = -123) { $query->where('type', $value); } /** * @comment Scope with optional nullable integer parameter and default null */ protected function scopeTyped24(Builder $query, ?int $value = null) { $query->where('type', $value); } /** * @comment Scope with required float nullable parameter */ protected function scopeTyped25(Builder $query, ?float $value) { $query->where('type', $value); } /** * @comment Scope with optional nullable float parameter and default positive integer value */ protected function scopeTyped26(Builder $query, ?float $value = 123) { $query->where('type', $value); } /** * @comment Scope with optional nullable float parameter and default negative integer value */ protected function scopeTyped27(Builder $query, ?float $value = -123) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default positive float value */ protected function scopeTyped28(Builder $query, ?float $value = 1.23) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default negative float value */ protected function scopeTyped29(Builder $query, ?float $value = -1.23) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default null */ protected function scopeTyped30(Builder $query, ?float $value = null) { $query->where('type', $value); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpDocWithTypedScopeParameter/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpDocWithTypedScopeParameter/__snapshots__/Test__test__1.php ================================================ |Comment newModelQuery() * @method static Builder|Comment newQuery() * @method static Builder|Comment query() * @method static Builder|Comment typed01(bool $value) Scope with required boolean parameter * @method static Builder|Comment typed02(bool $value = true) Scope with optional boolean parameter and default true * @method static Builder|Comment typed03(bool $value = false) Scope with optional boolean parameter and default false * @method static Builder|Comment typed04(string $value) Scope with required string parameter * @method static Builder|Comment typed05(string $value = 'dummy123') Scope with optional string parameter and default value * @method static Builder|Comment typed06(int $value) Scope with required integer parameter * @method static Builder|Comment typed07(int $value = 123) Scope with optional integer parameter and default positive value * @method static Builder|Comment typed08(int $value = -123) Scope with optional integer parameter and default negative value * @method static Builder|Comment typed09(float $value) Scope with required float parameter * @method static Builder|Comment typed10(float $value = 123) Scope with optional float parameter and default positive integer value * @method static Builder|Comment typed11(float $value = -123) Scope with optional float parameter and default negative integer value * @method static Builder|Comment typed12(float $value = 1.23) Scope with optional float parameter and default positive float value * @method static Builder|Comment typed13(float $value = -1.23) Scope with optional float parameter and default negative float value * @method static Builder|Comment typed14(?bool $value) Scope with required nullable boolean parameter * @method static Builder|Comment typed15(?bool $value = true) Scope with optional nullable boolean parameter and default true * @method static Builder|Comment typed16(?bool $value = false) Scope with optional nullable boolean parameter and default false * @method static Builder|Comment typed17(?bool $value = null) Scope with optional nullable boolean parameter and default null * @method static Builder|Comment typed18(?string $value) Scope with required nullable string parameter * @method static Builder|Comment typed19(?string $value = 'dummy123') Scope with optional nullable string parameter and default value * @method static Builder|Comment typed20(?string $value = null) Scope with optional nullable string parameter and default null * @method static Builder|Comment typed21(?int $value) Scope with required nullable integer parameter * @method static Builder|Comment typed22(?int $value = 123) Scope with optional nullable integer parameter and default positive value * @method static Builder|Comment typed23(?int $value = -123) Scope with optional nullable integer parameter and default negative value * @method static Builder|Comment typed24(?int $value = null) Scope with optional nullable integer parameter and default null * @method static Builder|Comment typed25(?float $value) Scope with required float nullable parameter * @method static Builder|Comment typed26(?float $value = 123) Scope with optional nullable float parameter and default positive integer value * @method static Builder|Comment typed27(?float $value = -123) Scope with optional nullable float parameter and default negative integer value * @method static Builder|Comment typed28(?float $value = 1.23) Scope with optional float parameter and default positive float value * @method static Builder|Comment typed29(?float $value = -1.23) Scope with optional float parameter and default negative float value * @method static Builder|Comment typed30(?float $value = null) Scope with optional float parameter and default null * @mixin \Eloquent */ class Comment extends Model { /** * @comment Scope with required boolean parameter */ protected function scopeTyped01(Builder $query, bool $value) { $query->where('type', $value); } /** * @comment Scope with optional boolean parameter and default true */ protected function scopeTyped02(Builder $query, bool $value = true) { $query->where('type', $value); } /** * @comment Scope with optional boolean parameter and default false */ protected function scopeTyped03(Builder $query, bool $value = false) { $query->where('type', $value); } /** * @comment Scope with required string parameter */ protected function scopeTyped04(Builder $query, string $value) { $query->where('type', $value); } /** * @comment Scope with optional string parameter and default value */ protected function scopeTyped05(Builder $query, string $value = 'dummy123') { $query->where('type', $value); } /** * @comment Scope with required integer parameter */ protected function scopeTyped06(Builder $query, int $value) { $query->where('type', $value); } /** * @comment Scope with optional integer parameter and default positive value */ protected function scopeTyped07(Builder $query, int $value = 123) { $query->where('type', $value); } /** * @comment Scope with optional integer parameter and default negative value */ protected function scopeTyped08(Builder $query, int $value = -123) { $query->where('type', $value); } /** * @comment Scope with required float parameter */ protected function scopeTyped09(Builder $query, float $value) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default positive integer value */ protected function scopeTyped10(Builder $query, float $value = 123) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default negative integer value */ protected function scopeTyped11(Builder $query, float $value = -123) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default positive float value */ protected function scopeTyped12(Builder $query, float $value = 1.23) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default negative float value */ protected function scopeTyped13(Builder $query, float $value = -1.23) { $query->where('type', $value); } /** * @comment Scope with required nullable boolean parameter */ protected function scopeTyped14(Builder $query, ?bool $value) { $query->where('type', $value); } /** * @comment Scope with optional nullable boolean parameter and default true */ protected function scopeTyped15(Builder $query, ?bool $value = true) { $query->where('type', $value); } /** * @comment Scope with optional nullable boolean parameter and default false */ protected function scopeTyped16(Builder $query, ?bool $value = false) { $query->where('type', $value); } /** * @comment Scope with optional nullable boolean parameter and default null */ protected function scopeTyped17(Builder $query, ?bool $value = null) { $query->where('type', $value); } /** * @comment Scope with required nullable string parameter */ protected function scopeTyped18(Builder $query, ?string $value) { $query->where('type', $value); } /** * @comment Scope with optional nullable string parameter and default value */ protected function scopeTyped19(Builder $query, ?string $value = 'dummy123') { $query->where('type', $value); } /** * @comment Scope with optional nullable string parameter and default null */ protected function scopeTyped20(Builder $query, ?string $value = null) { $query->where('type', $value); } /** * @comment Scope with required nullable integer parameter */ protected function scopeTyped21(Builder $query, ?int $value) { $query->where('type', $value); } /** * @comment Scope with optional nullable integer parameter and default positive value */ protected function scopeTyped22(Builder $query, ?int $value = 123) { $query->where('type', $value); } /** * @comment Scope with optional nullable integer parameter and default negative value */ protected function scopeTyped23(Builder $query, ?int $value = -123) { $query->where('type', $value); } /** * @comment Scope with optional nullable integer parameter and default null */ protected function scopeTyped24(Builder $query, ?int $value = null) { $query->where('type', $value); } /** * @comment Scope with required float nullable parameter */ protected function scopeTyped25(Builder $query, ?float $value) { $query->where('type', $value); } /** * @comment Scope with optional nullable float parameter and default positive integer value */ protected function scopeTyped26(Builder $query, ?float $value = 123) { $query->where('type', $value); } /** * @comment Scope with optional nullable float parameter and default negative integer value */ protected function scopeTyped27(Builder $query, ?float $value = -123) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default positive float value */ protected function scopeTyped28(Builder $query, ?float $value = 1.23) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default negative float value */ protected function scopeTyped29(Builder $query, ?float $value = -1.23) { $query->where('type', $value); } /** * @comment Scope with optional float parameter and default null */ protected function scopeTyped30(Builder $query, ?float $value = null) { $query->where('type', $value); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithExternalEloquentBuilder/Builders/PostExternalQueryBuilder.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--nowrite' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Model information was written to _ide_helper_models.php', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithExternalEloquentBuilder/__snapshots__/Test__test__1.php ================================================ */ namespace Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Models{ /** * @property int $id * @property string|null $char_nullable * @property string $char_not_nullable * @property string|null $string_nullable * @property string $string_not_nullable * @property string|null $text_nullable * @property string $text_not_nullable * @property string|null $medium_text_nullable * @property string $medium_text_not_nullable * @property string|null $long_text_nullable * @property string $long_text_not_nullable * @property int|null $integer_nullable * @property int $integer_not_nullable * @property int|null $tiny_integer_nullable * @property int $tiny_integer_not_nullable * @property int|null $small_integer_nullable * @property int $small_integer_not_nullable * @property int|null $medium_integer_nullable * @property int $medium_integer_not_nullable * @property int|null $big_integer_nullable * @property int $big_integer_not_nullable * @property int|null $unsigned_integer_nullable * @property int $unsigned_integer_not_nullable * @property int|null $unsigned_tiny_integer_nullable * @property int $unsigned_tiny_integer_not_nullable * @property int|null $unsigned_small_integer_nullable * @property int $unsigned_small_integer_not_nullable * @property int|null $unsigned_medium_integer_nullable * @property int $unsigned_medium_integer_not_nullable * @property int|null $unsigned_big_integer_nullable * @property int $unsigned_big_integer_not_nullable * @property float|null $float_nullable * @property float $float_not_nullable * @property float|null $double_nullable * @property float $double_not_nullable * @property numeric|null $decimal_nullable * @property numeric $decimal_not_nullable * @property int|null $boolean_nullable * @property int $boolean_not_nullable * @property string|null $enum_nullable * @property string $enum_not_nullable * @property string|null $json_nullable * @property string $json_not_nullable * @property string|null $jsonb_nullable * @property string $jsonb_not_nullable * @property string|null $date_nullable * @property string $date_not_nullable * @property string|null $datetime_nullable * @property string $datetime_not_nullable * @property string|null $datetimetz_nullable * @property string $datetimetz_not_nullable * @property string|null $time_nullable * @property string $time_not_nullable * @property string|null $timetz_nullable * @property string $timetz_not_nullable * @property string|null $timestamp_nullable * @property string $timestamp_not_nullable * @property string|null $timestamptz_nullable * @property string $timestamptz_not_nullable * @property int|null $year_nullable * @property int $year_not_nullable * @property string|null $binary_nullable * @property string $binary_not_nullable * @property string|null $uuid_nullable * @property string $uuid_not_nullable * @property string|null $ipaddress_nullable * @property string $ipaddress_not_nullable * @property string|null $macaddress_nullable * @property string $macaddress_not_nullable * @property \Illuminate\Support\Carbon|null $created_at * @property \Illuminate\Support\Carbon|null $updated_at * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post isActive() * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post isLoadingWith(?string $with) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post isStatus(string $status) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post newModelQuery() * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post newQuery() * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post query() * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereBigIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereBigIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereBinaryNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereBinaryNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereBooleanNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereBooleanNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereCharNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereCharNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereCreatedAt($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDateNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDateNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDatetimeNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDatetimeNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDatetimetzNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDatetimetzNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDecimalNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDecimalNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDoubleNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereDoubleNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereEnumNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereEnumNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereFloatNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereFloatNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereId($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereIpaddressNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereIpaddressNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereJsonNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereJsonNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereJsonbNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereJsonbNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereLongTextNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereLongTextNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereMacaddressNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereMacaddressNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereMediumIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereMediumIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereMediumTextNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereMediumTextNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereSmallIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereSmallIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereStringNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereStringNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTextNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTextNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTimeNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTimeNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTimestampNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTimestampNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTimestamptzNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTimestamptzNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTimetzNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTimetzNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTinyIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereTinyIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedBigIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUpdatedAt($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUuidNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereUuidNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereYearNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post whereYearNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withBool(?bool $booleanVar) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withBoolDifferently(?bool $booleanVar) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withBoolTypeHinted(bool $booleanVar) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withMixedOption($option) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withNullAndAssignmentTestCommand(?\Barryvdh\LaravelIdeHelper\Console\ModelsCommand $testCommand = null) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withNullTestCommand(?\Barryvdh\LaravelIdeHelper\Console\ModelsCommand $testCommand) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withNullTestCommandInDocBlock($testCommand) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withSomeone($someone) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withTestCommand(\Barryvdh\LaravelIdeHelper\Console\ModelsCommand $testCommand) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withTheNumber(?int $number) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithExternalEloquentBuilder\Builders\PostExternalQueryBuilder|Post withTheNumberDifferently(?int $number) */ class Post extends \Eloquent {} } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithExternalEloquentBuilderWithFqn/Builders/PostExternalQueryBuilder.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithExternalEloquentBuilderWithFqn/__snapshots__/Test__test__1.php ================================================ |Post isActive() * @method static PostExternalQueryBuilder|Post isLoadingWith(?string $with) * @method static PostExternalQueryBuilder|Post isStatus(string $status) * @method static PostExternalQueryBuilder|Post newModelQuery() * @method static PostExternalQueryBuilder|Post newQuery() * @method static PostExternalQueryBuilder|Post query() * @method static PostExternalQueryBuilder|Post whereBigIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereBigIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereBinaryNotNullable($value) * @method static PostExternalQueryBuilder|Post whereBinaryNullable($value) * @method static PostExternalQueryBuilder|Post whereBooleanNotNullable($value) * @method static PostExternalQueryBuilder|Post whereBooleanNullable($value) * @method static PostExternalQueryBuilder|Post whereCharNotNullable($value) * @method static PostExternalQueryBuilder|Post whereCharNullable($value) * @method static PostExternalQueryBuilder|Post whereCreatedAt($value) * @method static PostExternalQueryBuilder|Post whereDateNotNullable($value) * @method static PostExternalQueryBuilder|Post whereDateNullable($value) * @method static PostExternalQueryBuilder|Post whereDatetimeNotNullable($value) * @method static PostExternalQueryBuilder|Post whereDatetimeNullable($value) * @method static PostExternalQueryBuilder|Post whereDatetimetzNotNullable($value) * @method static PostExternalQueryBuilder|Post whereDatetimetzNullable($value) * @method static PostExternalQueryBuilder|Post whereDecimalNotNullable($value) * @method static PostExternalQueryBuilder|Post whereDecimalNullable($value) * @method static PostExternalQueryBuilder|Post whereDoubleNotNullable($value) * @method static PostExternalQueryBuilder|Post whereDoubleNullable($value) * @method static PostExternalQueryBuilder|Post whereEnumNotNullable($value) * @method static PostExternalQueryBuilder|Post whereEnumNullable($value) * @method static PostExternalQueryBuilder|Post whereFloatNotNullable($value) * @method static PostExternalQueryBuilder|Post whereFloatNullable($value) * @method static PostExternalQueryBuilder|Post whereId($value) * @method static PostExternalQueryBuilder|Post whereIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereIpaddressNotNullable($value) * @method static PostExternalQueryBuilder|Post whereIpaddressNullable($value) * @method static PostExternalQueryBuilder|Post whereJsonNotNullable($value) * @method static PostExternalQueryBuilder|Post whereJsonNullable($value) * @method static PostExternalQueryBuilder|Post whereJsonbNotNullable($value) * @method static PostExternalQueryBuilder|Post whereJsonbNullable($value) * @method static PostExternalQueryBuilder|Post whereLongTextNotNullable($value) * @method static PostExternalQueryBuilder|Post whereLongTextNullable($value) * @method static PostExternalQueryBuilder|Post whereMacaddressNotNullable($value) * @method static PostExternalQueryBuilder|Post whereMacaddressNullable($value) * @method static PostExternalQueryBuilder|Post whereMediumIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereMediumIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereMediumTextNotNullable($value) * @method static PostExternalQueryBuilder|Post whereMediumTextNullable($value) * @method static PostExternalQueryBuilder|Post whereSmallIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereSmallIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereStringNotNullable($value) * @method static PostExternalQueryBuilder|Post whereStringNullable($value) * @method static PostExternalQueryBuilder|Post whereTextNotNullable($value) * @method static PostExternalQueryBuilder|Post whereTextNullable($value) * @method static PostExternalQueryBuilder|Post whereTimeNotNullable($value) * @method static PostExternalQueryBuilder|Post whereTimeNullable($value) * @method static PostExternalQueryBuilder|Post whereTimestampNotNullable($value) * @method static PostExternalQueryBuilder|Post whereTimestampNullable($value) * @method static PostExternalQueryBuilder|Post whereTimestamptzNotNullable($value) * @method static PostExternalQueryBuilder|Post whereTimestamptzNullable($value) * @method static PostExternalQueryBuilder|Post whereTimetzNotNullable($value) * @method static PostExternalQueryBuilder|Post whereTimetzNullable($value) * @method static PostExternalQueryBuilder|Post whereTinyIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereTinyIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedBigIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedBigIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedMediumIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedSmallIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static PostExternalQueryBuilder|Post whereUnsignedTinyIntegerNullable($value) * @method static PostExternalQueryBuilder|Post whereUpdatedAt($value) * @method static PostExternalQueryBuilder|Post whereUuidNotNullable($value) * @method static PostExternalQueryBuilder|Post whereUuidNullable($value) * @method static PostExternalQueryBuilder|Post whereYearNotNullable($value) * @method static PostExternalQueryBuilder|Post whereYearNullable($value) * @method static PostExternalQueryBuilder|Post withBool(?bool $booleanVar) * @method static PostExternalQueryBuilder|Post withBoolDifferently(?bool $booleanVar) * @method static PostExternalQueryBuilder|Post withBoolTypeHinted(bool $booleanVar) * @method static PostExternalQueryBuilder|Post withMixedOption($option) * @method static PostExternalQueryBuilder|Post withNullAndAssignmentTestCommand(?\Barryvdh\LaravelIdeHelper\Console\ModelsCommand $testCommand = null) * @method static PostExternalQueryBuilder|Post withNullTestCommand(?\Barryvdh\LaravelIdeHelper\Console\ModelsCommand $testCommand) * @method static PostExternalQueryBuilder|Post withNullTestCommandInDocBlock($testCommand) * @method static PostExternalQueryBuilder|Post withSomeone($someone) * @method static PostExternalQueryBuilder|Post withTestCommand(\Barryvdh\LaravelIdeHelper\Console\ModelsCommand $testCommand) * @method static PostExternalQueryBuilder|Post withTheNumber(?int $number) * @method static PostExternalQueryBuilder|Post withTheNumberDifferently(?int $number) * @mixin \Eloquent */ class Post extends Model { public function newEloquentBuilder($query): PostExternalQueryBuilder { return new PostExternalQueryBuilder($query); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithForcedFqn/Models/Post.php ================================================ hasMany(Post::class); } public function scopeNull($query, string $unusedParam) { return $query; } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithForcedFqn/Test.php ================================================ set('ide-helper.force_fqn', true); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithForcedFqn/__snapshots__/Test__test__1.php ================================================ $posts * @property-read int|null $posts_count * @property-read bool|null $posts_exists * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post null(string $unusedParam) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post onlyTrashed() * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post query() * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post whereYearNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post withTrashed(bool $withTrashed = true) * @method static \Illuminate\Database\Eloquent\Builder|\Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithForcedFqn\Models\Post withoutTrashed() * @mixin \Eloquent */ class Post extends Model { use SoftDeletes; public function posts(): HasMany { return $this->hasMany(Post::class); } public function scopeNull($query, string $unusedParam) { return $query; } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithFqn/Casts/CastType.php ================================================ CastType::class, ]; public function posts(): HasMany { return $this->hasMany(Post::class); } public function scopeNull($query, string $unusedParam) { return $query; } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithFqn/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithFqn/__snapshots__/Test__test__1.php ================================================ $posts * @property-read int|null $posts_count * @property-read bool|null $posts_exists * @method static EloquentBuilder|Post newModelQuery() * @method static EloquentBuilder|Post newQuery() * @method static EloquentBuilder|Post null(string $unusedParam) * @method static EloquentBuilder|Post onlyTrashed() * @method static EloquentBuilder|Post query() * @method static EloquentBuilder|Post whereBigIntegerNotNullable($value) * @method static EloquentBuilder|Post whereBigIntegerNullable($value) * @method static EloquentBuilder|Post whereBinaryNotNullable($value) * @method static EloquentBuilder|Post whereBinaryNullable($value) * @method static EloquentBuilder|Post whereBooleanNotNullable($value) * @method static EloquentBuilder|Post whereBooleanNullable($value) * @method static EloquentBuilder|Post whereCharNotNullable($value) * @method static EloquentBuilder|Post whereCharNullable($value) * @method static EloquentBuilder|Post whereCreatedAt($value) * @method static EloquentBuilder|Post whereDateNotNullable($value) * @method static EloquentBuilder|Post whereDateNullable($value) * @method static EloquentBuilder|Post whereDatetimeNotNullable($value) * @method static EloquentBuilder|Post whereDatetimeNullable($value) * @method static EloquentBuilder|Post whereDatetimetzNotNullable($value) * @method static EloquentBuilder|Post whereDatetimetzNullable($value) * @method static EloquentBuilder|Post whereDecimalNotNullable($value) * @method static EloquentBuilder|Post whereDecimalNullable($value) * @method static EloquentBuilder|Post whereDoubleNotNullable($value) * @method static EloquentBuilder|Post whereDoubleNullable($value) * @method static EloquentBuilder|Post whereEnumNotNullable($value) * @method static EloquentBuilder|Post whereEnumNullable($value) * @method static EloquentBuilder|Post whereFloatNotNullable($value) * @method static EloquentBuilder|Post whereFloatNullable($value) * @method static EloquentBuilder|Post whereId($value) * @method static EloquentBuilder|Post whereIntegerNotNullable($value) * @method static EloquentBuilder|Post whereIntegerNullable($value) * @method static EloquentBuilder|Post whereIpaddressNotNullable($value) * @method static EloquentBuilder|Post whereIpaddressNullable($value) * @method static EloquentBuilder|Post whereJsonNotNullable($value) * @method static EloquentBuilder|Post whereJsonNullable($value) * @method static EloquentBuilder|Post whereJsonbNotNullable($value) * @method static EloquentBuilder|Post whereJsonbNullable($value) * @method static EloquentBuilder|Post whereLongTextNotNullable($value) * @method static EloquentBuilder|Post whereLongTextNullable($value) * @method static EloquentBuilder|Post whereMacaddressNotNullable($value) * @method static EloquentBuilder|Post whereMacaddressNullable($value) * @method static EloquentBuilder|Post whereMediumIntegerNotNullable($value) * @method static EloquentBuilder|Post whereMediumIntegerNullable($value) * @method static EloquentBuilder|Post whereMediumTextNotNullable($value) * @method static EloquentBuilder|Post whereMediumTextNullable($value) * @method static EloquentBuilder|Post whereSmallIntegerNotNullable($value) * @method static EloquentBuilder|Post whereSmallIntegerNullable($value) * @method static EloquentBuilder|Post whereStringNotNullable($value) * @method static EloquentBuilder|Post whereStringNullable($value) * @method static EloquentBuilder|Post whereTextNotNullable($value) * @method static EloquentBuilder|Post whereTextNullable($value) * @method static EloquentBuilder|Post whereTimeNotNullable($value) * @method static EloquentBuilder|Post whereTimeNullable($value) * @method static EloquentBuilder|Post whereTimestampNotNullable($value) * @method static EloquentBuilder|Post whereTimestampNullable($value) * @method static EloquentBuilder|Post whereTimestamptzNotNullable($value) * @method static EloquentBuilder|Post whereTimestamptzNullable($value) * @method static EloquentBuilder|Post whereTimetzNotNullable($value) * @method static EloquentBuilder|Post whereTimetzNullable($value) * @method static EloquentBuilder|Post whereTinyIntegerNotNullable($value) * @method static EloquentBuilder|Post whereTinyIntegerNullable($value) * @method static EloquentBuilder|Post whereUnsignedBigIntegerNotNullable($value) * @method static EloquentBuilder|Post whereUnsignedBigIntegerNullable($value) * @method static EloquentBuilder|Post whereUnsignedIntegerNotNullable($value) * @method static EloquentBuilder|Post whereUnsignedIntegerNullable($value) * @method static EloquentBuilder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static EloquentBuilder|Post whereUnsignedMediumIntegerNullable($value) * @method static EloquentBuilder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static EloquentBuilder|Post whereUnsignedSmallIntegerNullable($value) * @method static EloquentBuilder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static EloquentBuilder|Post whereUnsignedTinyIntegerNullable($value) * @method static EloquentBuilder|Post whereUpdatedAt($value) * @method static EloquentBuilder|Post whereUuidNotNullable($value) * @method static EloquentBuilder|Post whereUuidNullable($value) * @method static EloquentBuilder|Post whereYearNotNullable($value) * @method static EloquentBuilder|Post whereYearNullable($value) * @method static EloquentBuilder|Post withTrashed(bool $withTrashed = true) * @method static EloquentBuilder|Post withoutTrashed() * @mixin Eloquent */ class Post extends Model { use SoftDeletes; /** * Special hack to avoid code style fixer removing unused imports * which play a role when generating the snapshot */ private $hack = [ Carbon::class, Collection::class, Eloquent::class, EloquentBuilder::class, QueryBuilder::class, ]; protected $casts = [ 'char_not_nullable' => CastType::class, ]; public function posts(): HasMany { return $this->hasMany(Post::class); } public function scopeNull($query, string $unusedParam) { return $query; } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithFqnInExternalFile/Builders/EMaterialQueryBuilder.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--nowrite' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Model information was written to _ide_helper_models.php', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithFqnInExternalFile/__snapshots__/Test__test__1.php ================================================ */ namespace Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Models{ /** * @property int $id * @property string|null $char_nullable * @property string $char_not_nullable * @property string|null $string_nullable * @property string $string_not_nullable * @property string|null $text_nullable * @property string $text_not_nullable * @property string|null $medium_text_nullable * @property string $medium_text_not_nullable * @property string|null $long_text_nullable * @property string $long_text_not_nullable * @property int|null $integer_nullable * @property int $integer_not_nullable * @property int|null $tiny_integer_nullable * @property int $tiny_integer_not_nullable * @property int|null $small_integer_nullable * @property int $small_integer_not_nullable * @property int|null $medium_integer_nullable * @property int $medium_integer_not_nullable * @property int|null $big_integer_nullable * @property int $big_integer_not_nullable * @property int|null $unsigned_integer_nullable * @property int $unsigned_integer_not_nullable * @property int|null $unsigned_tiny_integer_nullable * @property int $unsigned_tiny_integer_not_nullable * @property int|null $unsigned_small_integer_nullable * @property int $unsigned_small_integer_not_nullable * @property int|null $unsigned_medium_integer_nullable * @property int $unsigned_medium_integer_not_nullable * @property int|null $unsigned_big_integer_nullable * @property int $unsigned_big_integer_not_nullable * @property float|null $float_nullable * @property float $float_not_nullable * @property float|null $double_nullable * @property float $double_not_nullable * @property numeric|null $decimal_nullable * @property numeric $decimal_not_nullable * @property int|null $boolean_nullable * @property int $boolean_not_nullable * @property string|null $enum_nullable * @property string $enum_not_nullable * @property string|null $json_nullable * @property string $json_not_nullable * @property string|null $jsonb_nullable * @property string $jsonb_not_nullable * @property string|null $date_nullable * @property string $date_not_nullable * @property string|null $datetime_nullable * @property string $datetime_not_nullable * @property string|null $datetimetz_nullable * @property string $datetimetz_not_nullable * @property string|null $time_nullable * @property string $time_not_nullable * @property string|null $timetz_nullable * @property string $timetz_not_nullable * @property string|null $timestamp_nullable * @property string $timestamp_not_nullable * @property string|null $timestamptz_nullable * @property string $timestamptz_not_nullable * @property int|null $year_nullable * @property int $year_not_nullable * @property string|null $binary_nullable * @property string $binary_not_nullable * @property string|null $uuid_nullable * @property string $uuid_not_nullable * @property string|null $ipaddress_nullable * @property string $ipaddress_not_nullable * @property string|null $macaddress_nullable * @property string $macaddress_not_nullable * @property \Illuminate\Support\Carbon|null $created_at * @property \Illuminate\Support\Carbon|null $updated_at * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post newModelQuery() * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post newQuery() * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post query() * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereBigIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereBigIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereBinaryNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereBinaryNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereBooleanNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereBooleanNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereCharNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereCharNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereCreatedAt($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDateNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDateNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDatetimeNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDatetimeNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDatetimetzNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDatetimetzNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDecimalNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDecimalNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDoubleNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereDoubleNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereEnumNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereEnumNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereFloatNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereFloatNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereId($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereIpaddressNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereIpaddressNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereJsonNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereJsonNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereJsonbNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereJsonbNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereLongTextNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereLongTextNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereMacaddressNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereMacaddressNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereMediumIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereMediumIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereMediumTextNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereMediumTextNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereSmallIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereSmallIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereStringNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereStringNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTextNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTextNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTimeNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTimeNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTimestampNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTimestampNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTimestamptzNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTimestamptzNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTimetzNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTimetzNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTinyIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereTinyIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedBigIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUpdatedAt($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUuidNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereUuidNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereYearNotNullable($value) * @method static \Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithFqnInExternalFile\Builders\EMaterialQueryBuilder|Post whereYearNullable($value) */ class Post extends \Eloquent {} } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithMixin/Models/FinalPost.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write-mixin' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GeneratePhpdocWithMixin/__snapshots__/Test__test__1.php ================================================ */ namespace Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithMixin\Models{ /** * @property $someProp * @method someMethod(string $method) * @method static \Illuminate\Database\Eloquent\Builder|FinalPost newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|FinalPost newQuery() * @method static \Illuminate\Database\Eloquent\Builder|FinalPost query() * @mixin \Eloquent */ #[\AllowDynamicProperties] final class IdeHelperFinalPost {} } namespace Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\GeneratePhpdocWithMixin\Models{ /** * @property $someProp * @method someMethod(string $method) * @property int $id * @property string|null $char_nullable * @property string $char_not_nullable * @property string|null $string_nullable * @property string $string_not_nullable * @property string|null $text_nullable * @property string $text_not_nullable * @property string|null $medium_text_nullable * @property string $medium_text_not_nullable * @property string|null $long_text_nullable * @property string $long_text_not_nullable * @property int|null $integer_nullable * @property int $integer_not_nullable * @property int|null $tiny_integer_nullable * @property int $tiny_integer_not_nullable * @property int|null $small_integer_nullable * @property int $small_integer_not_nullable * @property int|null $medium_integer_nullable * @property int $medium_integer_not_nullable * @property int|null $big_integer_nullable * @property int $big_integer_not_nullable * @property int|null $unsigned_integer_nullable * @property int $unsigned_integer_not_nullable * @property int|null $unsigned_tiny_integer_nullable * @property int $unsigned_tiny_integer_not_nullable * @property int|null $unsigned_small_integer_nullable * @property int $unsigned_small_integer_not_nullable * @property int|null $unsigned_medium_integer_nullable * @property int $unsigned_medium_integer_not_nullable * @property int|null $unsigned_big_integer_nullable * @property int $unsigned_big_integer_not_nullable * @property float|null $float_nullable * @property float $float_not_nullable * @property float|null $double_nullable * @property float $double_not_nullable * @property numeric|null $decimal_nullable * @property numeric $decimal_not_nullable * @property int|null $boolean_nullable * @property int $boolean_not_nullable * @property string|null $enum_nullable * @property string $enum_not_nullable * @property string|null $json_nullable * @property string $json_not_nullable * @property string|null $jsonb_nullable * @property string $jsonb_not_nullable * @property string|null $date_nullable * @property string $date_not_nullable * @property string|null $datetime_nullable * @property string $datetime_not_nullable * @property string|null $datetimetz_nullable * @property string $datetimetz_not_nullable * @property string|null $time_nullable * @property string $time_not_nullable * @property string|null $timetz_nullable * @property string $timetz_not_nullable * @property string|null $timestamp_nullable * @property string $timestamp_not_nullable * @property string|null $timestamptz_nullable * @property string $timestamptz_not_nullable * @property int|null $year_nullable * @property int $year_not_nullable * @property string|null $binary_nullable * @property string $binary_not_nullable * @property string|null $uuid_nullable * @property string $uuid_not_nullable * @property string|null $ipaddress_nullable * @property string $ipaddress_not_nullable * @property string|null $macaddress_nullable * @property string $macaddress_not_nullable * @property \Illuminate\Support\Carbon|null $created_at * @property \Illuminate\Support\Carbon|null $updated_at * @method static \Illuminate\Database\Eloquent\Builder|Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post query() * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) * @mixin \Eloquent */ #[\AllowDynamicProperties] class IdeHelperPost {} } ================================================ FILE: tests/Console/ModelsCommand/GenericsSyntaxDisabled/Models/Simple.php ================================================ hasMany(Simple::class); } public function regularBelongsToMany(): BelongsToMany { return $this->belongsToMany(Simple::class); } } ================================================ FILE: tests/Console/ModelsCommand/GenericsSyntaxDisabled/Test.php ================================================ set('ide-helper.use_generics_annotations', false); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/GenericsSyntaxDisabled/__snapshots__/Test__test__1.php ================================================ |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { // Regular relations public function regularHasMany(): HasMany { return $this->hasMany(Simple::class); } public function regularBelongsToMany(): BelongsToMany { return $this->belongsToMany(Simple::class); } } ================================================ FILE: tests/Console/ModelsCommand/Getter/Models/Simple.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/Getter/__snapshots__/Test__test__1.php ================================================ |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { /** * @return int */ public function getAttributeWithIntReturnPhpdocAttribute() { } public function getAttributeWithIntReturnTypeAttribute(): int { } /** * @return int */ public function getAttributeWithIntReturnTypeAndPhpdocAttribute(): int { } /** * @return string */ public function getAttributeWithIntReturnTypeAndButPhpdocStringAttribute(): int { } public function getAttributeWithoutTypeAttribute() { } /** * @return \what|\ever|\we-write/here */ public function getAttributeTakesPhpdocLiteralAttribute() { } public function getAttributeReturnTypeIntOrNullAttribute(): ?int { } public function getAttributeReturnsImportedClassAttribute(): DateTime { } public function getAttributeReturnsFqnClassAttribute(): \Illuminate\Support\Facades\Date { } public function getAttributeReturnsArrayAttribute(): array { } public function getAttributeReturnsNullableArrayAttribute(): ?array { } public function getAttributeReturnsStdClassAttribute(): \stdClass { } public function getAttributeReturnsNullableStdClassAttribute(): ?\stdClass { } public function getAttributeReturnsBoolAttribute(): bool { } public function getAttributeReturnsNullableBoolAttribute(): ?bool { } public function getAttributeReturnsFloatAttribute(): bool { } public function getAttributeReturnsNullableFloatAttribute(): ?bool { } public function getAttributeReturnsCallableAttribute(): callable { } public function getAttributeReturnsNullableCallableAttribute(): ?callable { } /** * Doesn't make sense, but… */ public function getAttributeReturnsVoidAttribute(): void { } private function getInvalidAccessModifierAttribute() { } } ================================================ FILE: tests/Console/ModelsCommand/Ignored/Models/Ignored.php ================================================ set('ide-helper.ignored_models', [ Ignored::class, ]); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/Ignored/__snapshots__/Test__test__1.php ================================================ |NotIgnored newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|NotIgnored newQuery() * @method static \Illuminate\Database\Eloquent\Builder|NotIgnored query() * @mixin \Eloquent */ class NotIgnored extends Model { } ================================================ FILE: tests/Console/ModelsCommand/Interfaces/Models/User.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--nowrite' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Model information was written to _ide_helper_models.php', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/Interfaces/__snapshots__/Test__test__1.php ================================================ */ namespace Barryvdh\LaravelIdeHelper\Tests\Console\ModelsCommand\Interfaces\Models{ /** * @method static \Illuminate\Database\Eloquent\Builder|User newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|User newQuery() * @method static \Illuminate\Database\Eloquent\Builder|User query() */ class User extends \Eloquent implements \Illuminate\Contracts\Auth\Authenticatable {} } ================================================ FILE: tests/Console/ModelsCommand/LaravelCustomCasts/Casts/CastableReturnsAnonymousCaster.php ================================================ CustomCasterWithReturnType::class, 'casted_property_with_static_return_type' => CustomCasterWithStaticReturnType::class, 'casted_property_with_return_docblock' => CustomCasterWithDocblockReturn::class, 'casted_property_with_return_docblock_fqn' => CustomCasterWithDocblockReturnFqn::class, 'casted_property_with_return_primitive' => CustomCasterWithPrimitiveReturn::class, 'casted_property_with_return_primitive_docblock' => CustomCasterWithPrimitiveDocblockReturn::class, 'casted_property_with_return_nullable_primitive' => CustomCasterWithNullablePrimitiveReturn::class, 'casted_property_with_return_nullable_primitive_and_nullable_column' => CustomCasterWithNullablePrimitiveReturn::class, 'casted_property_without_return' => CustomCasterWithoutReturnType::class, 'casted_property_with_param' => CustomCasterWithParam::class . ':param', 'casted_property_with_static_return_docblock' => SelfCastingCasterWithStaticDocblockReturn::class, 'casted_property_with_this_return_docblock' => SelfCastingCasterWithThisDocblockReturn::class, 'casted_property_with_castable' => CastableReturnsCustomCaster::class, 'casted_property_with_anonymous_cast' => CastableReturnsAnonymousCaster::class, 'casted_property_without_return_type' => CastableWithoutReturnType::class, 'extended_casted_property_with_static_return_docblock' => ExtendedSelfCastingCasterWithStaticDocblockReturn::class, 'extended_casted_property_with_this_return_docblock' => ExtendedSelfCastingCasterWithThisDocblockReturn::class, 'casted_property_with_static_return_docblock_and_param' => SelfCastingCasterWithStaticDocblockReturn::class . ':param', 'cast_without_property' => CustomCasterWithReturnType::class, 'cast_inbound_attribute' => InboundAttributeCaster::class, ]; } ================================================ FILE: tests/Console/ModelsCommand/LaravelCustomCasts/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/LaravelCustomCasts/__snapshots__/Test__test__1.php ================================================ |CustomCast newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|CustomCast newQuery() * @method static \Illuminate\Database\Eloquent\Builder|CustomCast query() * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithParam($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithReturnDocblock($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithReturnDocblockFqn($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithReturnNullablePrimitive($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithReturnNullablePrimitiveAndNullableColumn($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithReturnPrimitive($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithReturnPrimitiveDocblock($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithReturnType($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithStaticReturnDocblock($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithStaticReturnDocblockAndParam($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithThisReturnDocblock($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereCastedPropertyWithoutReturn($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereExtendedCastedPropertyWithStaticReturnDocblock($value) * @method static \Illuminate\Database\Eloquent\Builder|CustomCast whereExtendedCastedPropertyWithThisReturnDocblock($value) * @mixin \Eloquent */ class CustomCast extends Model { protected $casts = [ 'casted_property_with_return_type' => CustomCasterWithReturnType::class, 'casted_property_with_static_return_type' => CustomCasterWithStaticReturnType::class, 'casted_property_with_return_docblock' => CustomCasterWithDocblockReturn::class, 'casted_property_with_return_docblock_fqn' => CustomCasterWithDocblockReturnFqn::class, 'casted_property_with_return_primitive' => CustomCasterWithPrimitiveReturn::class, 'casted_property_with_return_primitive_docblock' => CustomCasterWithPrimitiveDocblockReturn::class, 'casted_property_with_return_nullable_primitive' => CustomCasterWithNullablePrimitiveReturn::class, 'casted_property_with_return_nullable_primitive_and_nullable_column' => CustomCasterWithNullablePrimitiveReturn::class, 'casted_property_without_return' => CustomCasterWithoutReturnType::class, 'casted_property_with_param' => CustomCasterWithParam::class . ':param', 'casted_property_with_static_return_docblock' => SelfCastingCasterWithStaticDocblockReturn::class, 'casted_property_with_this_return_docblock' => SelfCastingCasterWithThisDocblockReturn::class, 'casted_property_with_castable' => CastableReturnsCustomCaster::class, 'casted_property_with_anonymous_cast' => CastableReturnsAnonymousCaster::class, 'casted_property_without_return_type' => CastableWithoutReturnType::class, 'extended_casted_property_with_static_return_docblock' => ExtendedSelfCastingCasterWithStaticDocblockReturn::class, 'extended_casted_property_with_this_return_docblock' => ExtendedSelfCastingCasterWithThisDocblockReturn::class, 'casted_property_with_static_return_docblock_and_param' => SelfCastingCasterWithStaticDocblockReturn::class . ':param', 'cast_without_property' => CustomCasterWithReturnType::class, 'cast_inbound_attribute' => InboundAttributeCaster::class, ]; } ================================================ FILE: tests/Console/ModelsCommand/MagicWhere/Models/Post.php ================================================ set('ide-helper.write_model_magic_where', false); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/MagicWhere/__snapshots__/Test__test__1.php ================================================ |Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post query() * @mixin \Eloquent */ class Post extends Model { } ================================================ FILE: tests/Console/ModelsCommand/ModelHooks/Hooks/CustomMethod.php ================================================ setMethod('custom', $command->getMethodType($model, Builder::class), ['$custom']); } } ================================================ FILE: tests/Console/ModelsCommand/ModelHooks/Hooks/CustomProperty.php ================================================ setProperty('custom', 'string', true, false); } } ================================================ FILE: tests/Console/ModelsCommand/ModelHooks/Hooks/UnsetMethod.php ================================================ unsetMethod('newmodelquery'); } } ================================================ FILE: tests/Console/ModelsCommand/ModelHooks/Models/Simple.php ================================================ set('ide-helper', [ 'model_locations' => [ // This is calculated from the base_path() which points to // vendor/orchestra/testbench-core/laravel '/../../../../tests/Console/ModelsCommand/ModelHooks/Models', ], 'model_hooks' => [ CustomProperty::class, CustomMethod::class, UnsetMethod::class, ], ]); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/ModelHooks/__snapshots__/Test__test__1.php ================================================ |Simple custom($custom) * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { } ================================================ FILE: tests/Console/ModelsCommand/MorphToIntersection/Models/BaseModel.php ================================================ */ public function assigneeWithParens(): MorphTo { return $this->morphTo(type: 'nullable_relation_morph_to_type', id: 'nullable_relation_morph_to_id'); } /** @return MorphTo */ public function assigneeWithoutParens(): MorphTo { return $this->morphTo(type: 'nullable_relation_morph_to_type', id: 'nullable_relation_morph_to_id'); } /** @return MorphTo<(BaseModel&CanBeAssigned), $this> */ public function nonNullableAssignee(): MorphTo { return $this->morphTo(type: 'relation_morph_to_type', id: 'relation_morph_to_id'); } } ================================================ FILE: tests/Console/ModelsCommand/MorphToIntersection/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/MorphToIntersection/__snapshots__/Test__test__1.php ================================================ |MorphToIntersection newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|MorphToIntersection newQuery() * @method static \Illuminate\Database\Eloquent\Builder|MorphToIntersection query() * @method static \Illuminate\Database\Eloquent\Builder|MorphToIntersection whereNullableRelationMorphToId($value) * @method static \Illuminate\Database\Eloquent\Builder|MorphToIntersection whereNullableRelationMorphToType($value) * @method static \Illuminate\Database\Eloquent\Builder|MorphToIntersection whereRelationMorphToId($value) * @method static \Illuminate\Database\Eloquent\Builder|MorphToIntersection whereRelationMorphToType($value) * @mixin \Eloquent */ class MorphToIntersection extends Model { protected $table = 'morphs'; /** @return MorphTo<(BaseModel&CanBeAssigned), $this> */ public function assigneeWithParens(): MorphTo { return $this->morphTo(type: 'nullable_relation_morph_to_type', id: 'nullable_relation_morph_to_id'); } /** @return MorphTo */ public function assigneeWithoutParens(): MorphTo { return $this->morphTo(type: 'nullable_relation_morph_to_type', id: 'nullable_relation_morph_to_id'); } /** @return MorphTo<(BaseModel&CanBeAssigned), $this> */ public function nonNullableAssignee(): MorphTo { return $this->morphTo(type: 'relation_morph_to_type', id: 'relation_morph_to_id'); } } ================================================ FILE: tests/Console/ModelsCommand/Morphs/Models/Morphs.php ================================================ morphTo(); } public function nullableRelationMorphTo(): MorphTo { return $this->morphTo(); } } ================================================ FILE: tests/Console/ModelsCommand/Morphs/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/Morphs/__snapshots__/Test__test__1.php ================================================ |Morphs newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Morphs newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Morphs query() * @method static \Illuminate\Database\Eloquent\Builder|Morphs whereNullableRelationMorphToId($value) * @method static \Illuminate\Database\Eloquent\Builder|Morphs whereNullableRelationMorphToType($value) * @method static \Illuminate\Database\Eloquent\Builder|Morphs whereRelationMorphToId($value) * @method static \Illuminate\Database\Eloquent\Builder|Morphs whereRelationMorphToType($value) * @mixin \Eloquent */ class Morphs extends Model { public function relationMorphTo(): MorphTo { return $this->morphTo(); } public function nullableRelationMorphTo(): MorphTo { return $this->morphTo(); } } ================================================ FILE: tests/Console/ModelsCommand/PHPStormNoInspection/Models/Simple.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } public function testNoinspectionPresent(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, '--phpstorm-noinspections' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/PHPStormNoInspection/__snapshots__/Test__testNoinspectionNotPresent__1.php ================================================ |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { } ================================================ FILE: tests/Console/ModelsCommand/PHPStormNoInspection/__snapshots__/Test__testNoinspectionPresent__1.php ================================================ |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent * @noinspection PhpFullyQualifiedNameUsageInspection * @noinspection PhpUnnecessaryFullyQualifiedNameInspection */ class Simple extends Model { } ================================================ FILE: tests/Console/ModelsCommand/PhpAttributesBeforeClass/Models/FinalWithNested.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/PhpAttributesBeforeClass/__snapshots__/Test__test__1.php ================================================ |FinalWithNested newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|FinalWithNested newQuery() * @method static \Illuminate\Database\Eloquent\Builder|FinalWithNested query() * @method static \Illuminate\Database\Eloquent\Builder|FinalWithNested whereId($value) * @mixin \Eloquent */ #[ObservedByStub([StubObserver::class])] final class FinalWithNested extends Model { protected $table = 'simples'; } |MultipleAttributes newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|MultipleAttributes newQuery() * @method static \Illuminate\Database\Eloquent\Builder|MultipleAttributes query() * @method static \Illuminate\Database\Eloquent\Builder|MultipleAttributes whereId($value) * @mixin \Eloquent */ #[\AllowDynamicProperties] #[SecondAttribute] class MultipleAttributes extends Model { protected $table = 'simples'; } |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ #[\AllowDynamicProperties] class Simple extends Model { } ================================================ FILE: tests/Console/ModelsCommand/Pivot/Models/ModelWithPivot.php ================================================ belongsToMany(ModelwithPivot::class) ->using(CustomPivot::class) ->as('customAccessor'); } public function relationWithDifferentCustomPivot() { return $this->belongsToMany(ModelwithPivot::class) ->using(DifferentCustomPivot::class) ->as('differentCustomAccessor'); } // without an accessor public function relationCustomPivotUsingSameAccessor() { return $this->belongsToMany(ModelwithPivot::class) ->using(CustomPivot::class); } public function relationCustomPivotUsingSameAccessorAndClass() { return $this->belongsToMany(ModelwithPivot::class) ->using(CustomPivot::class); } public function relationWithDifferentCustomPivotUsingSameAccessor() { return $this->belongsToMany(ModelwithPivot::class) ->using(DifferentCustomPivot::class); } } ================================================ FILE: tests/Console/ModelsCommand/Pivot/Models/Pivots/CustomPivot.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/Pivot/__snapshots__/Test__test__1.php ================================================ $relationCustomPivotUsingSameAccessor * @property-read int|null $relation_custom_pivot_using_same_accessor_count * @property-read bool|null $relation_custom_pivot_using_same_accessor_exists * @property-read \Illuminate\Database\Eloquent\Collection $relationCustomPivotUsingSameAccessorAndClass * @property-read int|null $relation_custom_pivot_using_same_accessor_and_class_count * @property-read bool|null $relation_custom_pivot_using_same_accessor_and_class_exists * @property-read CustomPivot|null $customAccessor * @property-read \Illuminate\Database\Eloquent\Collection $relationWithCustomPivot * @property-read int|null $relation_with_custom_pivot_count * @property-read bool|null $relation_with_custom_pivot_exists * @property-read DifferentCustomPivot|null $differentCustomAccessor * @property-read \Illuminate\Database\Eloquent\Collection $relationWithDifferentCustomPivot * @property-read int|null $relation_with_different_custom_pivot_count * @property-read bool|null $relation_with_different_custom_pivot_exists * @property-read \Illuminate\Database\Eloquent\Collection $relationWithDifferentCustomPivotUsingSameAccessor * @property-read int|null $relation_with_different_custom_pivot_using_same_accessor_count * @property-read bool|null $relation_with_different_custom_pivot_using_same_accessor_exists * @method static \Illuminate\Database\Eloquent\Builder|ModelWithPivot newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithPivot newQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithPivot query() * @mixin \Eloquent */ class ModelWithPivot extends Model { public function relationWithCustomPivot() { return $this->belongsToMany(ModelwithPivot::class) ->using(CustomPivot::class) ->as('customAccessor'); } public function relationWithDifferentCustomPivot() { return $this->belongsToMany(ModelwithPivot::class) ->using(DifferentCustomPivot::class) ->as('differentCustomAccessor'); } // without an accessor public function relationCustomPivotUsingSameAccessor() { return $this->belongsToMany(ModelwithPivot::class) ->using(CustomPivot::class); } public function relationCustomPivotUsingSameAccessorAndClass() { return $this->belongsToMany(ModelwithPivot::class) ->using(CustomPivot::class); } public function relationWithDifferentCustomPivotUsingSameAccessor() { return $this->belongsToMany(ModelwithPivot::class) ->using(DifferentCustomPivot::class); } } |CustomPivot newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|CustomPivot newQuery() * @method static \Illuminate\Database\Eloquent\Builder|CustomPivot query() * @mixin \Eloquent */ class CustomPivot extends Pivot { } |DifferentCustomPivot newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|DifferentCustomPivot newQuery() * @method static \Illuminate\Database\Eloquent\Builder|DifferentCustomPivot query() * @mixin \Eloquent */ class DifferentCustomPivot extends Pivot { } ================================================ FILE: tests/Console/ModelsCommand/QueryMethods/Models/Post.php ================================================ set('ide-helper.write_query_methods', false); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); $this->assertStringNotContainsString("@method static \Illuminate\Database\Eloquent\Builder|Post query()", $this->mockFilesystemOutput); } } ================================================ FILE: tests/Console/ModelsCommand/QueryMethods/__snapshots__/Test__test__1.php ================================================ |Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) * @mixin \Eloquent */ class Post extends Model { } ================================================ FILE: tests/Console/ModelsCommand/QueryScopes/Models/Comment.php ================================================ where('ip_address', '127.0.0.1'); } /** * @comment Scope using the 'scope' prefix * @param Builder $query * @return void */ protected function scopeSystem(Builder $query): void { $query->where('system', true); } } ================================================ FILE: tests/Console/ModelsCommand/QueryScopes/Models/Post.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/QueryScopes/__snapshots__/Test__test__1.php ================================================ |Comment local() Scope using the 'Scope' attribute * @method static Builder|Comment newModelQuery() * @method static Builder|Comment newQuery() * @method static Builder|Comment query() * @method static Builder|Comment system() Scope using the 'scope' prefix * @mixin \Eloquent */ class Comment extends Model { /** * @comment Scope using the 'Scope' attribute * @param Builder $query * @return void */ #[Scope] protected function local(Builder $query): void { $query->where('ip_address', '127.0.0.1'); } /** * @comment Scope using the 'scope' prefix * @param Builder $query * @return void */ protected function scopeSystem(Builder $query): void { $query->where('system', true); } } |Post active() * @method static \Illuminate\Database\Eloquent\Builder|Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post public() * @method static \Illuminate\Database\Eloquent\Builder|Post query() * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) * @mixin \Eloquent */ class Post extends PostParent { public function scopePublic($query) { return $query; } } |PostParent active() * @method static \Illuminate\Database\Eloquent\Builder|PostParent newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|PostParent newQuery() * @method static \Illuminate\Database\Eloquent\Builder|PostParent query() * @mixin \Eloquent */ class PostParent extends Model { public function scopeActive($query) { return $query; } } ================================================ FILE: tests/Console/ModelsCommand/RelationCountProperties/Models/Post.php ================================================ hasMany(Post::class); } } ================================================ FILE: tests/Console/ModelsCommand/RelationCountProperties/Test.php ================================================ set('ide-helper.write_model_relation_count_properties', false); $app['config']->set('ide-helper.write_model_relation_exists_properties', false); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/RelationCountProperties/__snapshots__/Test__test__1.php ================================================ $relationHasMany * @method static \Illuminate\Database\Eloquent\Builder|Post newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Post query() * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBinaryNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereBooleanNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCharNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereCreatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDateNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDatetimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDecimalNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereDoubleNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereEnumNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereFloatNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereIpaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereJsonbNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereLongTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMacaddressNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereMediumTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereStringNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTextNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimeNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestampNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimestamptzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTimetzNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedBigIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedMediumIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedSmallIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUnsignedTinyIntegerNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUpdatedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereUuidNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNotNullable($value) * @method static \Illuminate\Database\Eloquent\Builder|Post whereYearNullable($value) * @mixin \Eloquent */ class Post extends Model { public function relationHasMany(): HasMany { return $this->hasMany(Post::class); } } ================================================ FILE: tests/Console/ModelsCommand/Relations/Models/BelongsToVariation.php ================================================ belongsTo(self::class, 'not_null_column_with_foreign_key_constraint'); } public function notNullColumnWithNoForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'not_null_column_with_no_foreign_key_constraint'); } public function nullableColumnWithForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'nullable_column_with_foreign_key_constraint'); } public function nullableColumnWithNoForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'nullable_column_with_no_foreign_key_constraint'); } } ================================================ FILE: tests/Console/ModelsCommand/Relations/Models/CompositeBelongsToVariation.php ================================================ belongsTo( self::class, ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ); } public function nonNullableMixedWithoutForeignKeyConstraint(): BelongsTo { return $this->belongsTo( self::class, ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_no_foreign_key_constraint'], ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_no_foreign_key_constraint'], ); } public function nullableMixedWithForeignKeyConstraint(): BelongsTo { return $this->belongsTo( self::class, ['nullable_column_with_no_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ['nullable_column_with_no_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ); } } ================================================ FILE: tests/Console/ModelsCommand/Relations/Models/Simple.php ================================================ hasMany(Simple::class); } public function relationHasOne(): HasOne { return $this->hasOne(Simple::class); } public function relationHasOneWithDefault(): HasOne { return $this->hasOne(Simple::class)->withDefault(); } public function relationBelongsTo(): BelongsTo { return $this->belongsTo(Simple::class); } public function relationBelongsToMany(): BelongsToMany { return $this->belongsToMany(Simple::class); } public function relationBelongsToManyWithSub(): BelongsToMany { return $this->belongsToMany(Simple::class)->where('foo', 'bar'); } public function relationBelongsToManyWithSubAnother(): BelongsToMany { return $this->relationBelongsToManyWithSub()->where('foo', 'bar'); } public function relationMorphTo(): MorphTo { return $this->morphTo(); } public function relationMorphOne(): MorphOne { return $this->morphOne(Simple::class, 'relationMorphTo'); } public function relationMorphMany(): MorphMany { return $this->morphMany(Simple::class, 'relationMorphTo'); } public function relationMorphedByMany(): MorphToMany { return $this->morphedByMany(Simple::class, 'foo'); } // Custom relations public function relationBelongsToInAnotherNamespace(): BelongsTo { return $this->belongsTo(AnotherModel::class); } public function relationBelongsToSameNameAsColumn(): BelongsTo { return $this->belongsTo(AnotherModel::class, __FUNCTION__); } public function relationSampleToManyRelationType() { return $this->testToOneRelation(Simple::class); } public function relationSampleRelationType() { return $this->testToManyRelation(Simple::class); } public function relationSampleToAnyRelationType() { return $this->testToAnyRelation(Simple::class); } public function relationSampleToAnyMorphedRelationType() { return $this->testToAnyMorphedRelation(Simple::class); } public function relationSampleToBadlyNamedNotManyRelation() { return $this->testToBadlyNamedNotManyRelation(Simple::class); } } ================================================ FILE: tests/Console/ModelsCommand/Relations/ModelsOtherNamespace/AnotherModel.php ================================================ SampleToOneRelationType::class, 'testToManyRelation' => SampleToManyRelationType::class, 'testToAnyRelation' => SampleToAnyRelationType::class, 'testToAnyMorphedRelation' => SampleToAnyMorphedRelationType::class, 'testToBadlyNamedNotManyRelation' => SampleToBadlyNamedNotManyRelationType::class, ]); Config::set('ide-helper.additional_relation_return_types', [ 'testToAnyRelation' => 'many', 'testToAnyMorphedRelation' => 'morphTo', 'testToBadlyNamedNotManyRelation' => 'one', ]); } public function test(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } public function testRelationNotNullable(): void { // Disable enforcing nullable relationships Config::set('ide-helper.enforce_nullable_relationships', false); $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); // Re-enable default enforcing nullable relationships Config::set('ide-helper.enforce_nullable_relationships', true); } } ================================================ FILE: tests/Console/ModelsCommand/Relations/Traits/HasTestRelations.php ================================================ newRelatedInstance($related); return new SampleToOneRelationType($instance->newQuery(), $this); } public function testToManyRelation($related) { $instance = $this->newRelatedInstance($related); return new SampleToManyRelationType($instance->newQuery(), $this); } public function testToAnyRelation($related) { $instance = $this->newRelatedInstance($related); return new SampleToAnyRelationType($instance->newQuery(), $this); } public function testToAnyMorphedRelation($related) { $instance = $this->newRelatedInstance($related); return new SampleToAnyMorphedRelationType($instance->newQuery(), $this); } public function testToBadlyNamedNotManyRelation($related) { $instance = $this->newRelatedInstance($related); return new SampleToBadlyNamedNotManyRelationType($instance->newQuery(), $this); } } ================================================ FILE: tests/Console/ModelsCommand/Relations/Types/SampleToAnyMorphedRelationType.php ================================================ |BelongsToVariation newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation newQuery() * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation query() * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereNotNullColumnWithForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereNotNullColumnWithNoForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereNullableColumnWithForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereNullableColumnWithNoForeignKeyConstraint($value) * @mixin \Eloquent */ class BelongsToVariation extends Model { public function notNullColumnWithForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'not_null_column_with_foreign_key_constraint'); } public function notNullColumnWithNoForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'not_null_column_with_no_foreign_key_constraint'); } public function nullableColumnWithForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'nullable_column_with_foreign_key_constraint'); } public function nullableColumnWithNoForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'nullable_column_with_no_foreign_key_constraint'); } } |CompositeBelongsToVariation newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation newQuery() * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation query() * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereNotNullColumnWithForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereNotNullColumnWithNoForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereNullableColumnWithForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereNullableColumnWithNoForeignKeyConstraint($value) * @mixin \Eloquent */ class CompositeBelongsToVariation extends Model { public $table = 'belongs_to_variations'; public function bothNonNullableWithForeignKeyConstraint(): BelongsTo { // Note, duplicating the keys here for simplicity. return $this->belongsTo( self::class, ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ); } public function nonNullableMixedWithoutForeignKeyConstraint(): BelongsTo { return $this->belongsTo( self::class, ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_no_foreign_key_constraint'], ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_no_foreign_key_constraint'], ); } public function nullableMixedWithForeignKeyConstraint(): BelongsTo { return $this->belongsTo( self::class, ['nullable_column_with_no_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ['nullable_column_with_no_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ); } } $relationBelongsToMany * @property-read int|null $relation_belongs_to_many_count * @property-read bool|null $relation_belongs_to_many_exists * @property-read \Illuminate\Database\Eloquent\Collection $relationBelongsToManyWithSub * @property-read int|null $relation_belongs_to_many_with_sub_count * @property-read bool|null $relation_belongs_to_many_with_sub_exists * @property-read \Illuminate\Database\Eloquent\Collection $relationBelongsToManyWithSubAnother * @property-read int|null $relation_belongs_to_many_with_sub_another_count * @property-read bool|null $relation_belongs_to_many_with_sub_another_exists * @property-read AnotherModel $relationBelongsToSameNameAsColumn * @property-read \Illuminate\Database\Eloquent\Collection $relationHasMany * @property-read int|null $relation_has_many_count * @property-read bool|null $relation_has_many_exists * @property-read Simple|null $relationHasOne * @property-read Simple $relationHasOneWithDefault * @property-read \Illuminate\Database\Eloquent\Collection $relationMorphMany * @property-read int|null $relation_morph_many_count * @property-read bool|null $relation_morph_many_exists * @property-read Simple|null $relationMorphOne * @property-read Model|\Eloquent $relationMorphTo * @property-read \Illuminate\Database\Eloquent\Collection $relationMorphedByMany * @property-read int|null $relation_morphed_by_many_count * @property-read bool|null $relation_morphed_by_many_exists * @property-read \Illuminate\Database\Eloquent\Collection $relationSampleRelationType * @property-read int|null $relation_sample_relation_type_count * @property-read bool|null $relation_sample_relation_type_exists * @property-read Model|\Eloquent $relationSampleToAnyMorphedRelationType * @property-read \Illuminate\Database\Eloquent\Collection $relationSampleToAnyRelationType * @property-read int|null $relation_sample_to_any_relation_type_count * @property-read bool|null $relation_sample_to_any_relation_type_exists * @property-read Simple $relationSampleToBadlyNamedNotManyRelation * @property-read Simple $relationSampleToManyRelationType * @method static \Illuminate\Database\Eloquent\Builder|Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { use HasTestRelations; // Regular relations public function relationHasMany(): HasMany { return $this->hasMany(Simple::class); } public function relationHasOne(): HasOne { return $this->hasOne(Simple::class); } public function relationHasOneWithDefault(): HasOne { return $this->hasOne(Simple::class)->withDefault(); } public function relationBelongsTo(): BelongsTo { return $this->belongsTo(Simple::class); } public function relationBelongsToMany(): BelongsToMany { return $this->belongsToMany(Simple::class); } public function relationBelongsToManyWithSub(): BelongsToMany { return $this->belongsToMany(Simple::class)->where('foo', 'bar'); } public function relationBelongsToManyWithSubAnother(): BelongsToMany { return $this->relationBelongsToManyWithSub()->where('foo', 'bar'); } public function relationMorphTo(): MorphTo { return $this->morphTo(); } public function relationMorphOne(): MorphOne { return $this->morphOne(Simple::class, 'relationMorphTo'); } public function relationMorphMany(): MorphMany { return $this->morphMany(Simple::class, 'relationMorphTo'); } public function relationMorphedByMany(): MorphToMany { return $this->morphedByMany(Simple::class, 'foo'); } // Custom relations public function relationBelongsToInAnotherNamespace(): BelongsTo { return $this->belongsTo(AnotherModel::class); } public function relationBelongsToSameNameAsColumn(): BelongsTo { return $this->belongsTo(AnotherModel::class, __FUNCTION__); } public function relationSampleToManyRelationType() { return $this->testToOneRelation(Simple::class); } public function relationSampleRelationType() { return $this->testToManyRelation(Simple::class); } public function relationSampleToAnyRelationType() { return $this->testToAnyRelation(Simple::class); } public function relationSampleToAnyMorphedRelationType() { return $this->testToAnyMorphedRelation(Simple::class); } public function relationSampleToBadlyNamedNotManyRelation() { return $this->testToBadlyNamedNotManyRelation(Simple::class); } } ================================================ FILE: tests/Console/ModelsCommand/Relations/__snapshots__/Test__test__1.php ================================================ |BelongsToVariation newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation newQuery() * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation query() * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereNotNullColumnWithForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereNotNullColumnWithNoForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereNullableColumnWithForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|BelongsToVariation whereNullableColumnWithNoForeignKeyConstraint($value) * @mixin \Eloquent */ class BelongsToVariation extends Model { public function notNullColumnWithForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'not_null_column_with_foreign_key_constraint'); } public function notNullColumnWithNoForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'not_null_column_with_no_foreign_key_constraint'); } public function nullableColumnWithForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'nullable_column_with_foreign_key_constraint'); } public function nullableColumnWithNoForeignKeyConstraint(): BelongsTo { return $this->belongsTo(self::class, 'nullable_column_with_no_foreign_key_constraint'); } } |CompositeBelongsToVariation newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation newQuery() * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation query() * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereNotNullColumnWithForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereNotNullColumnWithNoForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereNullableColumnWithForeignKeyConstraint($value) * @method static \Illuminate\Database\Eloquent\Builder|CompositeBelongsToVariation whereNullableColumnWithNoForeignKeyConstraint($value) * @mixin \Eloquent */ class CompositeBelongsToVariation extends Model { public $table = 'belongs_to_variations'; public function bothNonNullableWithForeignKeyConstraint(): BelongsTo { // Note, duplicating the keys here for simplicity. return $this->belongsTo( self::class, ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ); } public function nonNullableMixedWithoutForeignKeyConstraint(): BelongsTo { return $this->belongsTo( self::class, ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_no_foreign_key_constraint'], ['not_null_column_with_foreign_key_constraint', 'not_null_column_with_no_foreign_key_constraint'], ); } public function nullableMixedWithForeignKeyConstraint(): BelongsTo { return $this->belongsTo( self::class, ['nullable_column_with_no_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ['nullable_column_with_no_foreign_key_constraint', 'not_null_column_with_foreign_key_constraint'], ); } } $relationBelongsToMany * @property-read int|null $relation_belongs_to_many_count * @property-read bool|null $relation_belongs_to_many_exists * @property-read \Illuminate\Database\Eloquent\Collection $relationBelongsToManyWithSub * @property-read int|null $relation_belongs_to_many_with_sub_count * @property-read bool|null $relation_belongs_to_many_with_sub_exists * @property-read \Illuminate\Database\Eloquent\Collection $relationBelongsToManyWithSubAnother * @property-read int|null $relation_belongs_to_many_with_sub_another_count * @property-read bool|null $relation_belongs_to_many_with_sub_another_exists * @property-read AnotherModel|null $relationBelongsToSameNameAsColumn * @property-read \Illuminate\Database\Eloquent\Collection $relationHasMany * @property-read int|null $relation_has_many_count * @property-read bool|null $relation_has_many_exists * @property-read Simple|null $relationHasOne * @property-read Simple $relationHasOneWithDefault * @property-read \Illuminate\Database\Eloquent\Collection $relationMorphMany * @property-read int|null $relation_morph_many_count * @property-read bool|null $relation_morph_many_exists * @property-read Simple|null $relationMorphOne * @property-read Model|\Eloquent $relationMorphTo * @property-read \Illuminate\Database\Eloquent\Collection $relationMorphedByMany * @property-read int|null $relation_morphed_by_many_count * @property-read bool|null $relation_morphed_by_many_exists * @property-read \Illuminate\Database\Eloquent\Collection $relationSampleRelationType * @property-read int|null $relation_sample_relation_type_count * @property-read bool|null $relation_sample_relation_type_exists * @property-read Model|\Eloquent $relationSampleToAnyMorphedRelationType * @property-read \Illuminate\Database\Eloquent\Collection $relationSampleToAnyRelationType * @property-read int|null $relation_sample_to_any_relation_type_count * @property-read bool|null $relation_sample_to_any_relation_type_exists * @property-read Simple $relationSampleToBadlyNamedNotManyRelation * @property-read Simple $relationSampleToManyRelationType * @method static \Illuminate\Database\Eloquent\Builder|Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { use HasTestRelations; // Regular relations public function relationHasMany(): HasMany { return $this->hasMany(Simple::class); } public function relationHasOne(): HasOne { return $this->hasOne(Simple::class); } public function relationHasOneWithDefault(): HasOne { return $this->hasOne(Simple::class)->withDefault(); } public function relationBelongsTo(): BelongsTo { return $this->belongsTo(Simple::class); } public function relationBelongsToMany(): BelongsToMany { return $this->belongsToMany(Simple::class); } public function relationBelongsToManyWithSub(): BelongsToMany { return $this->belongsToMany(Simple::class)->where('foo', 'bar'); } public function relationBelongsToManyWithSubAnother(): BelongsToMany { return $this->relationBelongsToManyWithSub()->where('foo', 'bar'); } public function relationMorphTo(): MorphTo { return $this->morphTo(); } public function relationMorphOne(): MorphOne { return $this->morphOne(Simple::class, 'relationMorphTo'); } public function relationMorphMany(): MorphMany { return $this->morphMany(Simple::class, 'relationMorphTo'); } public function relationMorphedByMany(): MorphToMany { return $this->morphedByMany(Simple::class, 'foo'); } // Custom relations public function relationBelongsToInAnotherNamespace(): BelongsTo { return $this->belongsTo(AnotherModel::class); } public function relationBelongsToSameNameAsColumn(): BelongsTo { return $this->belongsTo(AnotherModel::class, __FUNCTION__); } public function relationSampleToManyRelationType() { return $this->testToOneRelation(Simple::class); } public function relationSampleRelationType() { return $this->testToManyRelation(Simple::class); } public function relationSampleToAnyRelationType() { return $this->testToAnyRelation(Simple::class); } public function relationSampleToAnyMorphedRelationType() { return $this->testToAnyMorphedRelation(Simple::class); } public function relationSampleToBadlyNamedNotManyRelation() { return $this->testToBadlyNamedNotManyRelation(Simple::class); } } ================================================ FILE: tests/Console/ModelsCommand/ResetAndSmartReset/Models/Simple.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } public function testReset(): void { $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, '--reset' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/ResetAndSmartReset/__snapshots__/Test__testNoReset__1.php ================================================ |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { } ================================================ FILE: tests/Console/ModelsCommand/ResetAndSmartReset/__snapshots__/Test__testReset__1.php ================================================ |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @mixin \Eloquent */ class Simple extends Model { } ================================================ FILE: tests/Console/ModelsCommand/ResetAndSmartReset/__snapshots__/Test__testSmartReset__1.php ================================================ 'int', 'cast_to_integer' => 'integer', 'cast_to_real' => 'real', 'cast_to_float' => 'float', 'cast_to_double' => 'double', 'cast_to_decimal' => 'decimal:4', 'cast_to_string' => 'string', 'cast_to_bool' => 'bool', 'cast_to_boolean' => 'boolean', 'cast_to_object' => 'object', 'cast_to_array' => 'array', 'cast_to_json' => 'json', 'cast_to_collection' => 'collection', 'cast_to_enum_collection' => 'collection', 'cast_to_date' => 'date', 'cast_to_datetime' => 'datetime', 'cast_to_date_serialization' => 'date:Y-m-d', 'cast_to_datetime_serialization' => 'datetime:Y-m-d H:i:s', 'cast_to_custom_datetime' => 'custom_datetime:Y-m-d H:i:s', 'cast_to_immutable_date' => 'immutable_date', 'cast_to_immutable_date_serialization' => 'immutable_date:Y-m-d', 'cast_to_immutable_custom_datetime' => 'immutable_custom_datetime:Y-m-d H:i:s', 'cast_to_immutable_datetime' => 'immutable_datetime', 'cast_to_immutable_datetime_serialization' => 'immutable_datetime:Y-m-d H:i:s', 'cast_to_timestamp' => 'timestamp', 'cast_to_encrypted' => 'encrypted', 'cast_to_encrypted_array' => 'encrypted:array', 'cast_to_encrypted_collection' => 'encrypted:collection', 'cast_to_encrypted_json' => 'encrypted:json', 'cast_to_encrypted_object' => 'encrypted:object', 'cast_to_hashed' => 'hashed', ]; } ================================================ FILE: tests/Console/ModelsCommand/SimpleCasts/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/SimpleCasts/__snapshots__/Test__test__1.php ================================================ $cast_to_array * @property array $cast_to_json * @property \Illuminate\Support\Collection $cast_to_collection * @property \Illuminate\Support\Carbon $cast_to_date * @property \Illuminate\Support\Carbon $cast_to_datetime * @property \Illuminate\Support\Carbon $cast_to_date_serialization * @property \Illuminate\Support\Carbon $cast_to_datetime_serialization * @property \Illuminate\Support\Carbon $cast_to_custom_datetime * @property \Carbon\CarbonImmutable $cast_to_immutable_date * @property \Carbon\CarbonImmutable $cast_to_immutable_date_serialization * @property \Carbon\CarbonImmutable $cast_to_immutable_custom_datetime * @property \Carbon\CarbonImmutable $cast_to_immutable_datetime * @property \Carbon\CarbonImmutable $cast_to_immutable_datetime_serialization * @property int $cast_to_timestamp * @property string $cast_to_encrypted * @property array $cast_to_encrypted_array * @property \Illuminate\Support\Collection $cast_to_encrypted_collection * @property array $cast_to_encrypted_json * @property object $cast_to_encrypted_object * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast newQuery() * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast query() * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToArray($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToBool($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToBoolean($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToCollection($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToCustomDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToDate($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToDateSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToDatetimeSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToDecimal($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToDouble($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToEncrypted($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToEncryptedArray($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToEncryptedCollection($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToEncryptedJson($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToEncryptedObject($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToFloat($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToImmutableCustomDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToImmutableDate($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToImmutableDateSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToImmutableDatetime($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToImmutableDatetimeSerialization($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToInt($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToInteger($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToJson($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToObject($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToReal($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToString($value) * @method static \Illuminate\Database\Eloquent\Builder|SimpleCast whereCastToTimestamp($value) * @mixin \Eloquent */ class SimpleCast extends Model { protected $casts = [ 'cast_to_int' => 'int', 'cast_to_integer' => 'integer', 'cast_to_real' => 'real', 'cast_to_float' => 'float', 'cast_to_double' => 'double', 'cast_to_decimal' => 'decimal:4', 'cast_to_string' => 'string', 'cast_to_bool' => 'bool', 'cast_to_boolean' => 'boolean', 'cast_to_object' => 'object', 'cast_to_array' => 'array', 'cast_to_json' => 'json', 'cast_to_collection' => 'collection', 'cast_to_enum_collection' => 'collection', 'cast_to_date' => 'date', 'cast_to_datetime' => 'datetime', 'cast_to_date_serialization' => 'date:Y-m-d', 'cast_to_datetime_serialization' => 'datetime:Y-m-d H:i:s', 'cast_to_custom_datetime' => 'custom_datetime:Y-m-d H:i:s', 'cast_to_immutable_date' => 'immutable_date', 'cast_to_immutable_date_serialization' => 'immutable_date:Y-m-d', 'cast_to_immutable_custom_datetime' => 'immutable_custom_datetime:Y-m-d H:i:s', 'cast_to_immutable_datetime' => 'immutable_datetime', 'cast_to_immutable_datetime_serialization' => 'immutable_datetime:Y-m-d H:i:s', 'cast_to_timestamp' => 'timestamp', 'cast_to_encrypted' => 'encrypted', 'cast_to_encrypted_array' => 'encrypted:array', 'cast_to_encrypted_collection' => 'encrypted:collection', 'cast_to_encrypted_json' => 'encrypted:json', 'cast_to_encrypted_object' => 'encrypted:object', 'cast_to_hashed' => 'hashed', ]; } ================================================ FILE: tests/Console/ModelsCommand/SoftDeletes/Models/Simple.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/SoftDeletes/__snapshots__/Test__test__1.php ================================================ |Simple newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple newQuery() * @method static \Illuminate\Database\Eloquent\Builder|Simple onlyTrashed() * @method static \Illuminate\Database\Eloquent\Builder|Simple query() * @method static \Illuminate\Database\Eloquent\Builder|Simple whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|Simple withTrashed(bool $withTrashed = true) * @method static \Illuminate\Database\Eloquent\Builder|Simple withoutTrashed() * @mixin \Eloquent */ class Simple extends Model { use SoftDeletes; } ================================================ FILE: tests/Console/ModelsCommand/SoftDeletesRelations/Models/ModelWithRelations.php ================================================ belongsTo(SoftDeletableModel::class, 'soft_deletable_model_id'); } public function nonSoftDeletable(): BelongsTo { return $this->belongsTo(NonSoftDeletableModel::class, 'non_soft_deletable_model_id'); } public function softDeletableHasOne(): HasOne { return $this->hasOne(SoftDeletableModel::class, 'model_with_relations_id'); } public function nonSoftDeletableHasOne(): HasOne { return $this->hasOne(NonSoftDeletableModel::class, 'model_with_relations_id'); } } ================================================ FILE: tests/Console/ModelsCommand/SoftDeletesRelations/Models/NonSoftDeletableModel.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } public function testSoftDeletesForceNullableDisabled(): void { Config::set('ide-helper.soft_deletes_force_nullable', false); $command = $this->app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); Config::set('ide-helper.soft_deletes_force_nullable', true); } } ================================================ FILE: tests/Console/ModelsCommand/SoftDeletesRelations/__snapshots__/Test__testSoftDeletesForceNullableDisabled__1.php ================================================ |ModelWithRelations newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations newQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations query() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations whereNonSoftDeletableModelId($value) * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations whereSoftDeletableModelId($value) * @mixin \Eloquent */ class ModelWithRelations extends Model { protected $table = 'models_with_relations'; public function softDeletable(): BelongsTo { return $this->belongsTo(SoftDeletableModel::class, 'soft_deletable_model_id'); } public function nonSoftDeletable(): BelongsTo { return $this->belongsTo(NonSoftDeletableModel::class, 'non_soft_deletable_model_id'); } public function softDeletableHasOne(): HasOne { return $this->hasOne(SoftDeletableModel::class, 'model_with_relations_id'); } public function nonSoftDeletableHasOne(): HasOne { return $this->hasOne(NonSoftDeletableModel::class, 'model_with_relations_id'); } } |NonSoftDeletableModel newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|NonSoftDeletableModel newQuery() * @method static \Illuminate\Database\Eloquent\Builder|NonSoftDeletableModel query() * @method static \Illuminate\Database\Eloquent\Builder|NonSoftDeletableModel whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|NonSoftDeletableModel whereModelWithRelationsId($value) * @mixin \Eloquent */ class NonSoftDeletableModel extends Model { } |SoftDeletableModel newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel newQuery() * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel onlyTrashed() * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel query() * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel whereDeletedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel whereModelWithRelationsId($value) * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel withTrashed(bool $withTrashed = true) * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel withoutTrashed() * @mixin \Eloquent */ class SoftDeletableModel extends Model { use SoftDeletes; } ================================================ FILE: tests/Console/ModelsCommand/SoftDeletesRelations/__snapshots__/Test__test__1.php ================================================ |ModelWithRelations newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations newQuery() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations query() * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations whereNonSoftDeletableModelId($value) * @method static \Illuminate\Database\Eloquent\Builder|ModelWithRelations whereSoftDeletableModelId($value) * @mixin \Eloquent */ class ModelWithRelations extends Model { protected $table = 'models_with_relations'; public function softDeletable(): BelongsTo { return $this->belongsTo(SoftDeletableModel::class, 'soft_deletable_model_id'); } public function nonSoftDeletable(): BelongsTo { return $this->belongsTo(NonSoftDeletableModel::class, 'non_soft_deletable_model_id'); } public function softDeletableHasOne(): HasOne { return $this->hasOne(SoftDeletableModel::class, 'model_with_relations_id'); } public function nonSoftDeletableHasOne(): HasOne { return $this->hasOne(NonSoftDeletableModel::class, 'model_with_relations_id'); } } |NonSoftDeletableModel newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|NonSoftDeletableModel newQuery() * @method static \Illuminate\Database\Eloquent\Builder|NonSoftDeletableModel query() * @method static \Illuminate\Database\Eloquent\Builder|NonSoftDeletableModel whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|NonSoftDeletableModel whereModelWithRelationsId($value) * @mixin \Eloquent */ class NonSoftDeletableModel extends Model { } |SoftDeletableModel newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel newQuery() * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel onlyTrashed() * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel query() * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel whereDeletedAt($value) * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel whereId($value) * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel whereModelWithRelationsId($value) * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel withTrashed(bool $withTrashed = true) * @method static \Illuminate\Database\Eloquent\Builder|SoftDeletableModel withoutTrashed() * @mixin \Eloquent */ class SoftDeletableModel extends Model { use SoftDeletes; } ================================================ FILE: tests/Console/ModelsCommand/UnionTypes/Models/UnionTypeModel.php ================================================ where('foo', $bar); } public function scopeWithNullableUnionTypeParameter(Builder $query, null|string|int $bar): Builder { return $query->where('foo', $bar); } public function withUnionTypeReturn(): HasMany|UnionTypeModel { return $this->hasMany(UnionTypeModel::class); } public function getFooAttribute(): string|int|null { return $this->getAttribute('foo'); } } ================================================ FILE: tests/Console/ModelsCommand/UnionTypes/Test.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/UnionTypes/__snapshots__/Test__test__1.php ================================================ $withUnionTypeReturn * @property-read int|null $with_union_type_return_count * @property-read bool|null $with_union_type_return_exists * @method static \Illuminate\Database\Eloquent\Builder|UnionTypeModel newModelQuery() * @method static \Illuminate\Database\Eloquent\Builder|UnionTypeModel newQuery() * @method static \Illuminate\Database\Eloquent\Builder|UnionTypeModel query() * @method static \Illuminate\Database\Eloquent\Builder|UnionTypeModel withNullableUnionTypeParameter(string|int|null $bar) * @method static \Illuminate\Database\Eloquent\Builder|UnionTypeModel withUnionTypeParameter(string|int $bar) * @mixin \Eloquent */ class UnionTypeModel extends Model { public function scopeWithUnionTypeParameter(Builder $query, string|int $bar): Builder { return $query->where('foo', $bar); } public function scopeWithNullableUnionTypeParameter(Builder $query, null|string|int $bar): Builder { return $query->where('foo', $bar); } public function withUnionTypeReturn(): HasMany|UnionTypeModel { return $this->hasMany(UnionTypeModel::class); } public function getFooAttribute(): string|int|null { return $this->getAttribute('foo'); } } ================================================ FILE: tests/Console/ModelsCommand/Variadic/Models/Simple.php ================================================ app->make(ModelsCommand::class); $tester = $this->runCommand($command, [ '--write' => true, ]); $this->assertSame(0, $tester->getStatusCode()); $this->assertStringContainsString('Written new phpDocBlock to', $tester->getDisplay()); $this->assertMatchesMockedSnapshot(); } } ================================================ FILE: tests/Console/ModelsCommand/Variadic/__snapshots__/Test__test__1.php ================================================ |Simple newModelQuery() * @method static Builder|Simple newQuery() * @method static Builder|Simple query() * @method static Builder|Simple whereId($value) * @method static Builder|Simple whereTypedVariadic(int ...$values) * @method static Builder|Simple whereVariadic(...$values) * @mixin \Eloquent */ class Simple extends Model { public function scopeWhereVariadic(Builder $query, ...$values): void { } public function scopeWhereTypedVariadic(Builder $query, int ...$values): void { } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____advanced_casts_table.php ================================================ string('cast_to_date_serialization'); $table->string('cast_to_datetime_serialization'); $table->string('cast_to_custom_datetime'); $table->string('cast_to_immutable_date'); $table->string('cast_to_immutable_custom_datetime'); $table->string('cast_to_immutable_datetime'); $table->string('cast_to_timestamp'); $table->string('cast_to_encrypted'); $table->string('cast_to_encrypted_array'); $table->string('cast_to_encrypted_collection'); $table->string('cast_to_encrypted_json'); $table->string('cast_to_encrypted_object'); $table->string('cast_to_as_collection'); $table->string('cast_to_as_enum_collection'); $table->string('cast_to_as_array_object'); }); } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____backed_attribute_table.php ================================================ bigIncrements('id'); $table->string('name'); $table->string('name_read'); $table->string('name_write'); }); } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____belongs_to_variation_table.php ================================================ bigIncrements('id'); $table->integer('not_null_column_with_foreign_key_constraint'); $table->integer('not_null_column_with_no_foreign_key_constraint'); $table->integer('nullable_column_with_foreign_key_constraint')->nullable(); $table->integer('nullable_column_with_no_foreign_key_constraint')->nullable(); $table->foreign('not_null_column_with_foreign_key_constraint')->references('id')->on('belongs_to_variations'); $table->foreign('nullable_column_with_foreign_key_constraint')->references('id')->on('belongs_to_variations'); }); } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____custom_casts_table.php ================================================ string('casted_property_with_return_type'); $table->string('casted_property_with_return_docblock'); $table->string('casted_property_with_return_docblock_fqn'); $table->string('casted_property_with_return_primitive'); $table->string('casted_property_with_return_primitive_docblock'); $table->string('casted_property_with_return_nullable_primitive'); $table->string('casted_property_with_return_nullable_primitive_and_nullable_column')->nullable(); $table->string('casted_property_without_return'); $table->string('casted_property_with_param'); $table->string('casted_property_with_static_return_docblock'); $table->string('casted_property_with_this_return_docblock'); $table->string('extended_casted_property_with_static_return_docblock'); $table->string('extended_casted_property_with_this_return_docblock'); $table->string('casted_property_with_static_return_docblock_and_param'); }); } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____custom_dates_table.php ================================================ timestamps(); }); } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____morphs_table.php ================================================ morphs('relation_morph_to'); $table->nullableMorphs('nullable_relation_morph_to'); }); } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____posts_table.php ================================================ bigIncrements('id'); $table->char('char_nullable')->nullable(); $table->char('char_not_nullable'); $table->string('string_nullable')->nullable(); $table->string('string_not_nullable'); $table->text('text_nullable')->nullable(); $table->text('text_not_nullable'); $table->mediumText('medium_text_nullable')->nullable(); $table->mediumText('medium_text_not_nullable'); $table->longText('long_text_nullable')->nullable(); $table->longText('long_text_not_nullable'); $table->integer('integer_nullable')->nullable(); $table->integer('integer_not_nullable'); $table->tinyInteger('tiny_integer_nullable')->nullable(); $table->tinyInteger('tiny_integer_not_nullable'); $table->smallInteger('small_integer_nullable')->nullable(); $table->smallInteger('small_integer_not_nullable'); $table->mediumInteger('medium_integer_nullable')->nullable(); $table->mediumInteger('medium_integer_not_nullable'); $table->bigInteger('big_integer_nullable')->nullable(); $table->bigInteger('big_integer_not_nullable'); $table->unsignedInteger('unsigned_integer_nullable')->nullable(); $table->unsignedInteger('unsigned_integer_not_nullable'); $table->unsignedTinyInteger('unsigned_tiny_integer_nullable')->nullable(); $table->unsignedTinyInteger('unsigned_tiny_integer_not_nullable'); $table->unsignedSmallInteger('unsigned_small_integer_nullable')->nullable(); $table->unsignedSmallInteger('unsigned_small_integer_not_nullable'); $table->unsignedMediumInteger('unsigned_medium_integer_nullable')->nullable(); $table->unsignedMediumInteger('unsigned_medium_integer_not_nullable'); $table->unsignedBigInteger('unsigned_big_integer_nullable')->nullable(); $table->unsignedBigInteger('unsigned_big_integer_not_nullable'); $table->float('float_nullable')->nullable(); $table->float('float_not_nullable'); $table->double('double_nullable')->nullable(); $table->double('double_not_nullable'); $table->decimal('decimal_nullable')->nullable(); $table->decimal('decimal_not_nullable'); $table->boolean('boolean_nullable')->nullable(); $table->boolean('boolean_not_nullable'); $table->enum('enum_nullable', ['foo', 'bar'])->nullable(); $table->enum('enum_not_nullable', ['foo', 'bar']); $table->json('json_nullable')->nullable(); $table->json('json_not_nullable'); $table->jsonb('jsonb_nullable')->nullable(); $table->jsonb('jsonb_not_nullable'); $table->date('date_nullable')->nullable(); $table->date('date_not_nullable'); $table->dateTime('datetime_nullable')->nullable(); $table->dateTime('datetime_not_nullable'); $table->dateTimeTz('datetimetz_nullable')->nullable(); $table->dateTimeTz('datetimetz_not_nullable'); $table->time('time_nullable')->nullable(); $table->time('time_not_nullable'); $table->timeTz('timetz_nullable')->nullable(); $table->timeTz('timetz_not_nullable'); $table->timestamp('timestamp_nullable')->nullable(); $table->timestamp('timestamp_not_nullable'); $table->timestampTz('timestamptz_nullable')->nullable(); $table->timestampTz('timestamptz_not_nullable'); $table->year('year_nullable')->nullable(); $table->year('year_not_nullable'); $table->binary('binary_nullable')->nullable(); $table->binary('binary_not_nullable'); $table->uuid('uuid_nullable')->nullable(); $table->uuid('uuid_not_nullable'); $table->ipAddress('ipaddress_nullable')->nullable(); $table->ipAddress('ipaddress_not_nullable'); $table->macAddress('macaddress_nullable')->nullable(); $table->macAddress('macaddress_not_nullable'); $table->timestamps(); }); } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____simple_casts_table.php ================================================ string('cast_to_int'); $table->string('cast_to_integer'); $table->string('cast_to_real'); $table->string('cast_to_float'); $table->string('cast_to_double'); $table->string('cast_to_decimal'); $table->string('cast_to_string'); $table->string('cast_to_bool'); $table->string('cast_to_boolean'); $table->string('cast_to_object'); $table->string('cast_to_array'); $table->string('cast_to_json'); $table->string('cast_to_collection'); $table->string('cast_to_date'); $table->string('cast_to_datetime'); $table->string('cast_to_date_serialization'); $table->string('cast_to_datetime_serialization'); $table->string('cast_to_custom_datetime'); $table->string('cast_to_immutable_date'); $table->string('cast_to_immutable_date_serialization'); $table->string('cast_to_immutable_custom_datetime'); $table->string('cast_to_immutable_datetime'); $table->string('cast_to_immutable_datetime_serialization'); $table->string('cast_to_timestamp'); $table->string('cast_to_encrypted'); $table->string('cast_to_encrypted_array'); $table->string('cast_to_encrypted_collection'); $table->string('cast_to_encrypted_json'); $table->string('cast_to_encrypted_object'); }); } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____simple_table.php ================================================ bigIncrements('id'); }); } } ================================================ FILE: tests/Console/ModelsCommand/migrations/____soft_deletes_relations_table.php ================================================ bigIncrements('id'); $table->unsignedBigInteger('model_with_relations_id')->nullable(); $table->softDeletes(); }); Schema::create('non_soft_deletable_models', function (Blueprint $table) { $table->bigIncrements('id'); $table->unsignedBigInteger('model_with_relations_id')->nullable(); }); Schema::create('models_with_relations', function (Blueprint $table) { $table->bigIncrements('id'); $table->unsignedBigInteger('soft_deletable_model_id'); $table->unsignedBigInteger('non_soft_deletable_model_id'); $table->foreign('soft_deletable_model_id') ->references('id') ->on('soft_deletable_models'); $table->foreign('non_soft_deletable_model_id') ->references('id') ->on('non_soft_deletable_models'); }); } } ================================================ FILE: tests/Console/__snapshots__/EloquentCommandTest__testCommand__1.txt ================================================ /** * @mixin \Eloquent * @mixin \Illuminate\Database\Eloquent\Builder * @mixin \Illuminate\Database\Query\Builder */ abstract class Model implements ================================================ FILE: tests/MacroTest.php ================================================ getPhpDoc( new ReflectionFunction( function (): EloquentBuilder { return $this; } ), $class ); $this->assertNotNull($phpdoc); $this->assertEquals( '@return \Illuminate\Database\Eloquent\Builder|static', $this->tagsToString($phpdoc, 'return') ); } /** * @covers ::initPhpDoc * @throws \ReflectionException */ public function testInitPhpDocClosureWithoutDocBlock(): void { $phpdoc = (new MacroMock())->getPhpDoc( new ReflectionFunction( function (?int $a = null): int { return 0; } ) ); $this->assertNotNull($phpdoc); $this->assertEmpty($phpdoc->getText()); $this->assertEquals('@param int|null $a', $this->tagsToString($phpdoc, 'param')); $this->assertEquals('@return int', $this->tagsToString($phpdoc, 'return')); $this->assertTrue($phpdoc->hasTag('see')); } /** * @covers ::initPhpDoc * @throws \ReflectionException */ public function testInitPhpDocClosureWithArgsAndReturnType(): void { $phpdoc = (new MacroMock())->getPhpDoc( new ReflectionFunction( /** * Test docblock. */ function (?int $a = null): int { return 0; } ) ); $this->assertNotNull($phpdoc); $this->assertStringContainsString('Test docblock', $phpdoc->getText()); $this->assertEquals('@param int|null $a', $this->tagsToString($phpdoc, 'param')); $this->assertEquals('@return int', $this->tagsToString($phpdoc, 'return')); $this->assertTrue($phpdoc->hasTag('see')); } /** * @covers ::initPhpDoc * @throws \ReflectionException */ public function testInitPhpDocClosureWithArgs(): void { $phpdoc = (new MacroMock())->getPhpDoc( new ReflectionFunction( /** * Test docblock. */ function (?int $a = null) { return 0; } ) ); $this->assertNotNull($phpdoc); $this->assertStringContainsString('Test docblock', $phpdoc->getText()); $this->assertEquals('@param int|null $a', $this->tagsToString($phpdoc, 'param')); $this->assertFalse($phpdoc->hasTag('return')); $this->assertTrue($phpdoc->hasTag('see')); } /** * @covers ::initPhpDoc * @throws \ReflectionException */ public function testInitPhpDocClosureWithReturnType(): void { $phpdoc = (new MacroMock())->getPhpDoc( new ReflectionFunction( /** * Test docblock. */ function (): int { return 0; } ) ); $this->assertNotNull($phpdoc); $this->assertStringContainsString('Test docblock', $phpdoc->getText()); $this->assertFalse($phpdoc->hasTag('param')); $this->assertEquals('@return int', $this->tagsToString($phpdoc, 'return')); $this->assertTrue($phpdoc->hasTag('see')); } /** * @covers ::initPhpDoc */ public function testInitPhpDocParamsAddedOnlyNotPresent(): void { $phpdoc = (new MacroMock())->getPhpDoc( new ReflectionFunction( /** * Test docblock. * * @param \stdClass|null $a aaaaa */ function ($a = null): int { return 0; } ) ); $this->assertNotNull($phpdoc); $this->assertStringContainsString('Test docblock', $phpdoc->getText()); $this->assertEquals('@param \stdClass|null $a aaaaa', $this->tagsToString($phpdoc, 'param')); $this->assertEquals('@return int', $this->tagsToString($phpdoc, 'return')); } /** * @covers ::initPhpDoc */ public function testInitPhpDocReturnAddedOnlyNotPresent(): void { $phpdoc = (new MacroMock())->getPhpDoc( new ReflectionFunction( /** * Test docblock. * * @return \stdClass|null rrrrrrr */ function ($a = null): int { return 0; } ) ); $this->assertNotNull($phpdoc); $this->assertStringContainsString('Test docblock', $phpdoc->getText()); $this->assertEquals('@param mixed $a', $this->tagsToString($phpdoc, 'param')); $this->assertEquals('@return \stdClass|null rrrrrrr', $this->tagsToString($phpdoc, 'return')); } public function testInitPhpDocParamsWithUnionTypes(): void { $phpdoc = (new MacroMock())->getPhpDoc(eval(<<<'PHP' return new ReflectionFunction( /** * Test docblock. */ function (\Stringable|string $a = null): \Stringable|string|null { return $a; } ); PHP)); $this->assertNotNull($phpdoc); $this->assertStringContainsString('Test docblock', $phpdoc->getText()); $this->assertEquals('@param \Stringable|string|null $a', $this->tagsToString($phpdoc, 'param')); $this->assertEquals('@return \Stringable|string|null', $this->tagsToString($phpdoc, 'return')); } public function testInitPhpDocParamsWithDnfTypes(): void { $phpdoc = (new MacroMock())->getPhpDoc(eval(<<<'PHP' return new ReflectionFunction( /** * Test docblock with DNF types. */ function ((\Countable&\Iterator)|null $a): (\Countable&\Iterator)|\stdClass|null { return $a; } ); PHP)); $this->assertNotNull($phpdoc); $this->assertStringContainsString('Test docblock with DNF types', $phpdoc->getText()); $this->assertEquals('@param (Countable&Iterator)|null $a', $this->tagsToString($phpdoc, 'param')); $this->assertEquals('@return (Countable&Iterator)|\stdClass|null', $this->tagsToString($phpdoc, 'return')); } public function testInitPhpDocParamsWithPureIntersectionType(): void { $phpdoc = (new MacroMock())->getPhpDoc(eval(<<<'PHP' return new ReflectionFunction( /** * Test docblock with pure intersection type. */ function (\Countable&\Iterator $a): \Countable&\Iterator { return $a; } ); PHP)); $this->assertNotNull($phpdoc); $this->assertStringContainsString('Test docblock with pure intersection type', $phpdoc->getText()); $this->assertEquals('@param (Countable&Iterator) $a', $this->tagsToString($phpdoc, 'param')); $this->assertEquals('@return (Countable&Iterator)', $this->tagsToString($phpdoc, 'return')); } public function testInitPhpDocParamsWithMultipleIntersections(): void { $phpdoc = (new MacroMock())->getPhpDoc(eval(<<<'PHP' return new ReflectionFunction( /** * Test docblock with multiple intersection segments. */ function ((\Countable&\Iterator)|(\ArrayAccess&\Stringable) $a): (\Countable&\Iterator)|(\ArrayAccess&\Stringable)|null { return $a; } ); PHP)); $this->assertNotNull($phpdoc); $this->assertStringContainsString('Test docblock with multiple intersection segments', $phpdoc->getText()); $this->assertEquals('@param (Countable&Iterator)|(ArrayAccess&Stringable) $a', $this->tagsToString($phpdoc, 'param')); $this->assertEquals('@return (Countable&Iterator)|(ArrayAccess&Stringable)|null', $this->tagsToString($phpdoc, 'return')); } protected function tagsToString(DocBlock $docBlock, string $name) { $tags = $docBlock->getTagsByName($name); $tags = array_map( function (Tag $tag) { return trim((string)$tag); }, $tags ); $tags = implode(PHP_EOL, $tags); return $tags; } /** * Test that we can actually instantiate the class */ public function testCanInstantiate() { $reflectionMethod = new \ReflectionMethod(UrlGeneratorMacroClass::class, '__invoke'); $macro = new Macro($reflectionMethod, new ReflectionClass(UrlGenerator::class), 'macroName'); $this->assertInstanceOf(Macro::class, $macro); } /** * Test the output of a class */ public function testOutput() { $reflectionMethod = new \ReflectionMethod(UrlGeneratorMacroClass::class, '__invoke'); $macro = new Macro($reflectionMethod, new ReflectionClass(UrlGenerator::class), 'macroName'); $output = <<<'DOC' /** * @param string $foo * @param int $bar * @return string * @see \Barryvdh\LaravelIdeHelper\Tests\UrlGeneratorMacroClass::__invoke() * @static */ DOC; $this->assertSame($output, $macro->getDocComment('')); $this->assertSame('__invoke', $macro->getRealName()); $this->assertSame('\\' . UrlGenerator::class, $macro->getDeclaringClass()); $this->assertSame('$foo, $bar', $macro->getParams(true)); $this->assertSame(['$foo', '$bar'], $macro->getParams(false)); $this->assertSame('$foo, $bar = 0', $macro->getParamsWithDefault(true)); $this->assertSame(['$foo', '$bar = 0'], $macro->getParamsWithDefault(false)); $this->assertTrue($macro->shouldReturn()); $this->assertSame('$instance->__invoke($foo, $bar)', $macro->getRootMethodCall()); } } /** * @internal * @noinspection PhpMultipleClassesDeclarationsInOneFile */ class MacroMock extends Macro { public function __construct() { // no need to call parent } public function getPhpDoc(ReflectionFunctionAbstract $method, ?ReflectionClass $class = null): DocBlock { return (new Macro($method, $class ?? $method->getClosureScopeClass()))->phpdoc; } } /** * Example of an invokable class to be used as a macro. */ class UrlGeneratorMacroClass { /** * @param string $foo * @param int $bar * @return string */ public function __invoke(string $foo, int $bar = 0): string { return ''; } } ================================================ FILE: tests/MethodTest.php ================================================ getMethod('setName'); $method = new Method($reflectionMethod, $reflectionClass); $this->assertInstanceOf(Method::class, $method); } /** * Test the output of a class */ public function testOutput() { $reflectionClass = new \ReflectionClass(ExampleClass::class); $reflectionMethod = $reflectionClass->getMethod('setName'); $method = new Method($reflectionMethod, $reflectionClass); $output = <<<'DOC' /** * @param string $last * @param string $first * @param string $middle * @static */ DOC; $this->assertSame($output, $method->getDocComment('')); $this->assertSame('setName', $method->getName()); $this->assertSame('\\' . ExampleClass::class, $method->getDeclaringClass()); $this->assertSame('$last, $first, ...$middle', $method->getParams(true)); $this->assertSame(['$last', '$first', '...$middle'], $method->getParams(false)); $this->assertSame('$last, $first = \'Barry\', ...$middle', $method->getParamsWithDefault(true)); $this->assertSame(['$last', '$first = \'Barry\'', '...$middle'], $method->getParamsWithDefault(false)); $this->assertTrue($method->shouldReturn()); } /** * Test the output of Illuminate\Database\Eloquent\Builder */ public function testEloquentBuilderOutput() { $reflectionClass = new \ReflectionClass(EloquentBuilder::class); $reflectionMethod = $reflectionClass->getMethod('upsert'); $method = new Method($reflectionMethod, $reflectionClass); $output = <<<'DOC' /** * Insert new records or update the existing ones. * * @param array $values * @param array|string $uniqueBy * @param array|null $update * @return int * @static */ DOC; $this->assertSame($output, $method->getDocComment('')); $this->assertSame('upsert', $method->getName()); $this->assertSame('\\' . EloquentBuilder::class, $method->getDeclaringClass()); $this->assertSame('$values, $uniqueBy, $update', $method->getParams(true)); $this->assertSame(['$values', '$uniqueBy', '$update'], $method->getParams(false)); $this->assertSame('$values, $uniqueBy, $update = null', $method->getParamsWithDefault(true)); $this->assertSame(['$values', '$uniqueBy', '$update = null'], $method->getParamsWithDefault(false)); $this->assertTrue($method->shouldReturn()); $this->assertSame('int', rtrim($method->getReturnTag()->getType())); } /** * Test normalized return type of Illuminate\Database\Eloquent\Builder */ public function testEloquentBuilderNormalizedReturnType() { $reflectionClass = new \ReflectionClass(EloquentBuilder::class); $reflectionMethod = $reflectionClass->getMethod('where'); $method = new Method($reflectionMethod, $reflectionClass, null, [], [], ['$this' => '\\' . EloquentBuilder::class . '']); $output = <<<'DOC' /** * Add a basic where clause to the query. * * @param (\Closure(static): mixed)|string|array|\Illuminate\Contracts\Database\Query\Expression $column * @param mixed $operator * @param mixed $value * @param string $boolean * @return \Illuminate\Database\Eloquent\Builder * @static */ DOC; $this->assertSame($output, $method->getDocComment('')); $this->assertSame('where', $method->getName()); $this->assertSame('\\' . EloquentBuilder::class, $method->getDeclaringClass()); $this->assertSame(['$column', '$operator', '$value', '$boolean'], $method->getParams(false)); $this->assertSame(['$column', '$operator = null', '$value = null', "\$boolean = 'and'"], $method->getParamsWithDefault(false)); $this->assertTrue($method->shouldReturn()); $this->assertSame('\Illuminate\Database\Eloquent\Builder', rtrim($method->getReturnTag()->getType())); } /** * Test normalized return type of Illuminate\Database\Query\Builder */ public function testQueryBuilderNormalizedReturnType() { $reflectionClass = new \ReflectionClass(QueryBuilder::class); $reflectionMethod = $reflectionClass->getMethod('whereNull'); $method = new Method($reflectionMethod, $reflectionClass, null, [], [], ['$this' => '\\' . EloquentBuilder::class . '']); $output = <<<'DOC' /** * Add a "where null" clause to the query. * * @param string|array|\Illuminate\Contracts\Database\Query\Expression $columns * @param string $boolean * @param bool $not * @return \Illuminate\Database\Eloquent\Builder * @static */ DOC; $this->assertSame($output, $method->getDocComment('')); $this->assertSame('whereNull', $method->getName()); $this->assertSame('\\' . QueryBuilder::class, $method->getDeclaringClass()); $this->assertSame(['$columns', '$boolean', '$not'], $method->getParams(false)); $this->assertSame(['$columns', "\$boolean = 'and'", '$not = false'], $method->getParamsWithDefault(false)); $this->assertTrue($method->shouldReturn()); $this->assertSame('\Illuminate\Database\Eloquent\Builder', rtrim($method->getReturnTag()->getType())); } /** * Test special characters in methods default values */ public function testDefaultSpecialChars() { $reflectionClass = new \ReflectionClass(ExampleClass::class); $reflectionMethod = $reflectionClass->getMethod('setSpecialChars'); $method = new Method($reflectionMethod, $reflectionClass); $this->assertSame('$chars', $method->getParams(true)); $this->assertSame(['$chars'], $method->getParams(false)); $this->assertSame('$chars = \'$\\\'\\\\\'', $method->getParamsWithDefault(true)); $this->assertSame(['$chars = \'$\\\'\\\\\''], $method->getParamsWithDefault(false)); } /** * Test the output of a class when using class aliases for it */ public function testClassAliases() { $reflectionClass = new \ReflectionClass(ExampleClass::class); $reflectionMethod = $reflectionClass->getMethod('getApplication'); $method = new Method($reflectionMethod, $reflectionClass, null, [], [ 'Application' => '\\Illuminate\\Foundation\\Application', ]); $output = <<<'DOC' /** * @return \Illuminate\Foundation\Application * @static */ DOC; $this->assertSame($output, $method->getDocComment('')); $this->assertSame('getApplication', $method->getName()); $this->assertSame('\\' . ExampleClass::class, $method->getDeclaringClass()); $this->assertSame('', $method->getParams(true)); $this->assertSame([], $method->getParams(false)); $this->assertSame('', $method->getParamsWithDefault(true)); $this->assertSame([], $method->getParamsWithDefault(false)); $this->assertTrue($method->shouldReturn()); } public function testEloquentBuilderWithTemplates() { $reflectionClass = new \ReflectionClass(EloquentBuilder::class); $reflectionMethod = $reflectionClass->getMethod('firstOr'); $method = new Method($reflectionMethod, $reflectionClass, null, [], [], [], ['TModel']); $output = <<<'DOC' /** * Execute the query and get the first result or call a callback. * * @template TValue * @param (\Closure(): TValue)|list $columns * @param (\Closure(): TValue)|null $callback * @return TModel|TValue * @static */ DOC; $this->assertSame($output, $method->getDocComment('')); $this->assertSame('firstOr', $method->getName()); $this->assertSame('\\' . EloquentBuilder::class, $method->getDeclaringClass()); } } class ExampleClass { /** * @param string $last * @param string $first * @param string $middle */ public function setName($last, $first = 'Barry', ...$middle) { return; } public function setSpecialChars($chars = "\$'\\") { return; } /** * @return Application */ public function getApplication() { return; } } ================================================ FILE: tests/RealTimeFacadesTest.php ================================================ app['config'], $this->app['view'], null, false); // Clear aliases and macros to have a small output file AliasLoader::getInstance()->setAliases([]); Request::flushMacros(); // Generate the helper file and return the content $content = $generator->generate(); $this->assertStringContainsString('namespace Facades\Illuminate\Foundation\Exceptions {', $content, 'Could not find Facades\Illuminate\Foundation\Exceptions namespace in the generated helper file.'); $this->assertStringContainsString('namespace Facades\App\Exceptions {', $content, 'Could not find Facades\App\Exceptions namespace in the generated helper file.'); $parsed = collect((new Php7(new Emulative()))->parse($content) ?: []); // test the Facades\Illuminate\Foundation\Exceptions namespace in the generated helper file $frameworkExceptionsNamespace = $parsed->first(function ($stmt) { return ($stmt instanceof Namespace_) && $stmt->name->toString() === 'Facades\Illuminate\Foundation\Exceptions'; }); $this->assertNotNull($frameworkExceptionsNamespace, 'Could not find Facades\Illuminate\Foundation\Exceptions namespace'); $this->assertSame('Facades\Illuminate\Foundation\Exceptions', $frameworkExceptionsNamespace->name->toString()); $this->verifyNamespace($frameworkExceptionsNamespace, 'Illuminate\Foundation\Exceptions\Handler'); // test the Facades\App\Exceptions namespace in the generated helper file $appExceptionsNamespace = $parsed->first(function ($stmt) { return ($stmt instanceof Namespace_) && $stmt->name->toString() === 'Facades\App\Exceptions'; }); $this->assertNotNull($appExceptionsNamespace, 'Could not find Facades\App\Exceptions namespace'); $this->assertSame('Facades\App\Exceptions', $appExceptionsNamespace->name->toString()); $this->verifyNamespace($appExceptionsNamespace, 'App\Exceptions\Handler'); } private function verifyNamespace(Namespace_ $namespace, $target) { $stmts = collect($namespace->stmts); $this->assertInstanceOf(Class_::class, $stmts[0], 'Expected instance of Class_'); $statement = $stmts[0]; $this->assertArrayHasKey('comments', $statement->getAttributes()); $this->assertStringContainsString('@mixin \\' . $target, $statement->getAttributes()['comments'][0]->getText(), 'Mixin comment not found'); $this->assertSame(class_basename($target), $statement->name->toString(), 'Class name not found'); $this->assertSame($target, $statement->extends->toString(), 'Class extends not found'); } protected function getPackageProviders($app) { return [IdeHelperServiceProvider::class]; } } ================================================ FILE: tests/SnapshotPhpDriver.php ================================================ serialize($actual)); } } ================================================ FILE: tests/SnapshotTxtDriver.php ================================================ serialize($actual)); } } ================================================ FILE: tests/TestCase.php ================================================ getDisplay()` or `->getStatusCode()` on it. * * @param Command $command * @param array $arguments The command line arguments, array of key=>value * Examples: * - named arguments: ['model' => 'Post'] * - boolean flags: ['--all' => true] * - arguments with values: ['--arg' => 'value'] * @param array $interactiveInput Interactive responses to the command * I.e. anything the command `->ask()` or `->confirm()`, etc. * @return CommandTester */ protected function runCommand(Command $command, array $arguments = [], array $interactiveInput = []): CommandTester { $this->withoutMockingConsoleOutput(); $command->setLaravel($this->app); $tester = new CommandTester($command); $tester->setInputs($interactiveInput); $tester->execute($arguments); return $tester; } protected function assertMatchesPhpSnapshot(?string $actualContent) { $this->assertMatchesSnapshot($actualContent, new SnapshotPhpDriver()); } protected function assertMatchesTxtSnapshot(?string $actualContent) { $this->assertMatchesSnapshot($actualContent, new SnapshotTxtDriver()); } protected function assertMatchesMockedSnapshot() { $this->assertMatchesSnapshot($this->mockFilesystemOutput, new SnapshotPhpDriver()); } protected function mockFilesystem() { $mockFilesystem = Mockery::mock(Filesystem::class)->makePartial(); $mockFilesystem ->shouldReceive('put') ->with( Mockery::any(), Mockery::any() ) ->andReturnUsing(function ($path, $contents) { $contents = str_replace(["\r\n", "\r"], "\n", $contents); $this->mockFilesystemOutput .= $contents; return strlen($contents); }); $this->instance(Filesystem::class, $mockFilesystem); $this->instance('files', $mockFilesystem); } } ================================================ FILE: tests/stubs/facade-0e0385307adf5db34c7986ecbd11646061356ec8.php ================================================