rzakhanov/translation
rzakhanov/translation is a Laravel package for managing app translations, with database-backed language strings and a convenient way to edit and maintain multilingual content without manually changing language files.
Install the tool into an existing Laravel + Nova app, then register it as a Nova tool. The exact provider namespace varies by release, so confirm it after install with composer show rzakhanov/translation.
composer require rzakhanov/translation
# publish config (and any views/migrations the package ships)
php artisan vendor:publish --provider="Rzakhanov\Translation\TranslationServiceProvider"
# Nova 4+ uses this provider path for app registration
php artisan nova:publish
Register it in app/Providers/NovaServiceProvider.php (or app/Nova/NovaApplicationServiceProvider.php on Laravel 11 + Nova 4/5):
public function tools()
{
return [
new \Rzakhanov\Translation\Translation(),
];
}
Where to look first
config/translation.php. Check the path/paths key pointing at your lang directory; this is the single most common reason the tool shows an empty screen.src/ on GitHub — with 2 stars you should read the tool class before trusting it in production.First use case: a marketing/PM user needs to fix a typo in lang/en/messages.php without a deploy. Open the Nova tool, pick the locale, edit the key, save. The file is rewritten on disk and the change is live on the next request once the compiled translation cache is cleared.
Treat the tool as an editor over lang/, not a translation service. It reads and writes files; it does not sync with Crowdin/Phrase or talk to external APIs. Keep it in the "ops tooling" bucket.
Standard i18n workflow it fits:
__('messages.welcome').lang/en/messages.php (via the tool, or via editor — either works).php artisan optimize:clear (or translate:cache if the package ships one) so the compiled cache picks up the edits.Bulk-edit pattern. Group edits by file, not by key. The tool rewrites whole group files, so batching by file keeps diffs sane. If you edit 40 keys across 12 files in one sitting, git diff on the lang directory will be unreadable — commit per file.
Environment scoping. Point the tool at lang/ in local/staging. In production, either disable it entirely for non-admin roles or mount the tool behind a gate:
Gate::define('manage-translations', fn ($user) => $user->hasRole('admin'));
Then wrap the registration:
if (Gate::allows('manage-translations')) {
// register tool
}
Version-control integration. Add a git hook or CI check that fails on uncommitted lang/ changes. Because the tool writes directly to disk, editors can drift from the repo without noticing. A simple pre-deploy check:
git diff --quiet lang/ || (echo "Uncommitted translations" && exit 1)
Localization test pattern. After editing, run a quick key-parity check to catch missing translations in other locales:
php artisan lang:diff # or write a one-off artisan command comparing array_keys()
This is the single most valuable thing to pair with this tool — the tool makes it easy to edit, which makes it easy to leave locales out of sync.
Read-only pattern for translators. If the tool supports a config flag for read-only mode, use it for non-technical users on staging. If it doesn't, subclass the Tool and override the edit route/view — see extension points below.
The project is effectively unmaintained. Last release July 2023, 2 stars, zero dependents. It predates Nova 5 (and likely Nova 4.30+). Before installing, verify Nova compatibility:
composer show rzakhanov/translation --all
# check require: laravel/nova or laravel/nova ~4.0
If it pulls a Nova constraint that clashes with your laravel/nova version, you'll get a resolver error. Either pin Nova, or fork the package and bump the constraint.
Laravel 11+ lang path. Laravel 11 moved resources/lang/ to a top-level lang/. A 2023 package almost certainly expects resources/lang/. Check the config path value and correct it manually if the tool loads nothing.
Compiled translation cache. Laravel caches compiled lang files under bootstrap/cache (and in storage/framework/views for some setups). Edits saved in the tool are not visible until:
php artisan optimize:clear
# or more targeted:
php artisan cache:clear
If edits "save" but don't appear in the app, this is almost always why. Note that config:cache in production will also freeze the tool's config — rebuild after any config change.
File permissions. The tool writes to lang/ using the PHP process user (typically www-data or the container user). If the directory isn't writable, the UI may fail silently or throw a 500. Test write access after deploy:
sudo -u www-data touch lang/.write-test && rm lang/.write-test
Containers with read-only root filesystems will block this entirely — mount lang/ as a volume.
No locking. Concurrent edits in the same group file will produce last-write-wins data loss. If you have more than one editor, prefer per-file commits, or route edits through code review rather than direct Nova edits.
Array vs JSON groups. Laravel supports both lang/en/messages.php and lang/en.json. Verify the tool handles both; many small translation tools only handle one. If yours only handles PHP groups, keep JSON copy in lang/en.json out of the tool's scope.
Extension points. With no active maintainer, plan to fork. Typical points to override:
navigation() / icon() for menu placement.path for non-standard directory layouts.resources/views/ (publishable) if the UI needs branding or a read-only mode.Debug when the tool loads blank:
php artisan route:list | grep -i translation — confirm the tool's routes registered.config/translation.php path matches your actual directory.storage/logs/laravel.log — a missing published asset usually throws a Vite or view not found error.Don't install this on a client-facing production site without a fork. With 0 dependents and no recent commits, the safest day-to-day pattern is: run it on staging, let editors make changes there, then commit and deploy through your normal pipeline. Use it as a convenience editor for trusted admins, not as a translation management system.
How can I help you explore Laravel packages today?