Skip to content

feat: Laravel string key completion, hover, and diagnostics#231

Open
calebdw wants to merge 2 commits into
mainfrom
calebdw/push-qsvttzqlxnsr
Open

feat: Laravel string key completion, hover, and diagnostics#231
calebdw wants to merge 2 commits into
mainfrom
calebdw/push-qsvttzqlxnsr

Conversation

@calebdw

@calebdw calebdw commented Jul 12, 2026

Copy link
Copy Markdown
Collaborator

Summary

Add autocompletion, hover, and invalid-key diagnostics for route names, config keys, view names, and translation keys. Also discovers package-registered resources from service providers.

Completion

  • route('|') / to_route('|') — route names from routes/*.php
  • config('|') / Config::get('|') — config keys from config/*.php
  • view('|') / View::make('|') — view templates from resources/views/
  • __('|') / trans('|') / Lang::get('|') — translation keys from lang/
  • Route::resource() / apiResource() with ->only() / ->except()
  • Route::group([], __DIR__ . '/sub.php') file includes with prefix propagation
  • Container attributes (#[Config], #[Database], #[Cache], #[Log], #[Storage], #[Auth]) with FQN-verified imports
  • Facade methods (Auth::guard(), DB::connection(), Cache::store(), Log::channel(), Storage::disk()) and auth() helper
  • TextEdit-based so dots don't break the completion popup

Hover

  • Shows key kind (Route/Config/View/Trans), the key value, and the file where it's defined

Diagnostics

  • Warns on unknown route names, config keys, view names, and translation keys (e.g. Unknown route: 'dashbaord')
  • Only flags plain string literals, not dynamic/interpolated keys
  • Per-kind diagnostic codes (invalid_laravel_route, invalid_laravel_config, invalid_laravel_view, invalid_laravel_trans) so each can be independently disabled
  • Trans diagnostics skip entirely when no lang/ translation files exist (avoids false positives in WordPress/GetText projects)

Package Resource Discovery

Scans all registered service providers for resource registration calls and feeds the results into the string key infrastructure:

Call What it discovers
mergeConfigFrom(path, 'ns') Config keys under config('ns.key')
loadViewsFrom(path, 'ns') View templates as view('ns::template')
loadTranslationsFrom(path, 'ns') Translation keys as trans('ns::file.key')
loadJsonTranslationsFrom(path) JSON translation keys
loadRoutesFrom(path) Named routes
  • Resolves __DIR__.'/../../config/foo.php' paths to actual package files on disk
  • Go-to-definition jumps to the exact key in the vendor package's config/view/translation/route file
  • Completion offers package config keys (e.g. config('horizon.environments')) and namespaced views/translations

Also

  • to_route() added to extraction spans for go-to-def and find-references
  • Go-to-definition follows Route::group([], __DIR__ . '/sub.php') file includes with prefix propagation
  • Go-to-definition resolves Route::resource() / apiResource() routes

@calebdw
calebdw requested a review from AJenbo July 12, 2026 01:40
@calebdw
calebdw force-pushed the calebdw/push-qsvttzqlxnsr branch 2 times, most recently from 9bdf8d3 to 8701e88 Compare July 12, 2026 01:44
@codecov-commenter

codecov-commenter commented Jul 12, 2026

Copy link
Copy Markdown

@calebdw
calebdw force-pushed the calebdw/push-qsvttzqlxnsr branch from 8701e88 to ce5e6cc Compare July 12, 2026 01:55
@calebdw calebdw changed the title feat: Laravel string key completion (route, config, view, trans) feat: Laravel string key completion, hover, and diagnostics Jul 12, 2026
@AJenbo

AJenbo commented Jul 12, 2026

Copy link
Copy Markdown
Contributor
  • We should make sure that __() is actually the one from Laravel and not GetText or WordPress.
  • Should we also check `lang/en.json`` style translations?
  • Will it flag translations as missing if I use a DB provider rather then static json?
  • Should config('unknown', 'default') still produce a warning?

@calebdw

calebdw commented Jul 13, 2026

Copy link
Copy Markdown
Collaborator Author

We should make sure that __() is actually the one from Laravel and not GetText or WordPress.

Fixed — trans diagnostics now skip entirely when no lang/ translation files are found in the project. This prevents false-positive "Unknown translation key" warnings in WordPress/GetText projects that also use __(). Completion already returned nothing when no keys exist, so this just brings diagnostics in line.

Should we also check lang/en.json style translations?

Added in 268bce6. Both completion and diagnostics now scan lang/*.json and resources/lang/*.json on disk for flat JSON translations ({"Some phrase": "Translated phrase"}). Go-to-definition also resolves JSON translation keys.

Will it flag translations as missing if I use a DB provider rather than static json?

If there are no file-based translation files at all (PHP or JSON), trans diagnostics are skipped entirely (see point 1). If you have some file-based translations alongside a DB provider, keys only in the DB will be flagged. To handle that case, the diagnostic code is now invalid_laravel_trans (see below) which can be individually disabled in config.

Should config('unknown', 'default') still produce a warning?

Keeping the warning — a default value is a safety net, not an indication the key is intentionally wrong. A typo like config('app.tiemzone', 'UTC') should still be caught.


Also split the single invalid_laravel_key diagnostic code into per-kind codes so each category can be independently disabled:

  • invalid_laravel_route
  • invalid_laravel_config
  • invalid_laravel_view
  • invalid_laravel_trans

@calebdw
calebdw force-pushed the calebdw/push-qsvttzqlxnsr branch 6 times, most recently from 65fe16a to e947041 Compare July 15, 2026 14:15
@calebdw

calebdw commented Jul 15, 2026

Copy link
Copy Markdown
Collaborator Author

@AJenbo, thoughts on merging this?

@calebdw
calebdw force-pushed the calebdw/push-qsvttzqlxnsr branch 10 times, most recently from f13159e to ed106e1 Compare July 17, 2026 20:48
Add autocompletion, hover, and invalid-key diagnostics for route names,
config keys, view names, and translation keys.

Completion:
- route('|') / to_route('|') -> route names from routes/*.php
- config('|') / Config::get('|') -> config keys from config/*.php
- view('|') / View::make('|') -> view templates from resources/views/
- __('|') / trans('|') / Lang::get('|') -> translation keys from lang/
- Route::resource() / apiResource() with ->only() / ->except()
- Route::group([], __DIR__ . '/sub.php') file includes with prefix
- Container attributes (#[Config], #[Database], #[Cache], #[Log],
  #[Storage], #[Auth]) with FQN-verified imports
- Facade methods (Auth::guard(), DB::connection(), Cache::store(),
  Log::channel(), Storage::disk()) and auth() helper
- TextEdit-based so dots don't break the completion popup

Hover:
- Shows key kind (Route/Config/View/Trans), the key value, and
  the file where it's defined

Diagnostics:
- Warns on unknown route names, config keys, view names, and
  translation keys (e.g. Unknown route: 'dashbaord')
- Only flags plain string literals, not dynamic/interpolated keys

Also adds to_route() to extraction spans for go-to-def/references.
@calebdw
calebdw force-pushed the calebdw/push-qsvttzqlxnsr branch from ed106e1 to 4219692 Compare July 18, 2026 03:47
Scan service providers for mergeConfigFrom(), loadViewsFrom(),
loadTranslationsFrom(), loadJsonTranslationsFrom(), and
loadRoutesFrom() calls. Resolve __DIR__-relative paths to the
actual package files on disk and feed the results into the
existing string key infrastructure.

This enables completion, go-to-definition, and hover for config
keys, view templates, translation keys, and named routes that
are registered by installed packages rather than defined in the
app itself. For example, config("horizon.environments") now
completes and jumps to the key in vendor/laravel/horizon/config/
horizon.php, and view("horizon::layout") resolves to the
package view directory.

The scanner reuses the same provider list and one-level-deep
helper class traversal already used by macro discovery.
Discovered resources are cached on Backend and invalidate the
string key caches when populated.

Key changes:
- New provider_resources.rs with ProviderResource,
  ProviderResources, and extract_provider_resources()
- extract_dir_concat_path() moved from route_names.rs to
  helpers.rs for shared use
- build_provider_resources() in server.rs walks providers
  and their referenced classes
- enumerate_all_{config_keys,view_names,trans_keys}() and
  enumerate_all_route_names() extended to include package
  resources
- resolve_{config_key,view,trans,route}_definitions() extended
  to handle namespaced package keys (ns::key, ns.key)
@calebdw
calebdw force-pushed the calebdw/push-qsvttzqlxnsr branch from 4219692 to 2cd7f6d Compare July 18, 2026 03:52
@AJenbo

AJenbo commented Jul 18, 2026

Copy link
Copy Markdown
Contributor

One of my regression test projects died and maybe this is a good time to update them all to the latest version. This will take a bit of time to align everything and so I would rather we delay this as a merge right after the release of 0.9.0.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants