My website incorporates multilingual functionality, allowing content to be displayed in various languages. To facilitate this, language-specific data is stored in the MySQL database within JSON fields. This approach enables flexible storage of language-specific information, with each JSON field containing data in different languages.
Example of the table:
articles – title – json – example:
{"en": "English Title", "es": "Título en Español", "id": "Judul dalam Bahasa Indonesia"}
And this is my Article model:
protected function casts(): array
{
return [
'title' => 'json',
'resume' => 'json',
'content' => 'json',
];
}
I tried to retrieve only the desired language value from the JSON attribute in my Laravel model using the following approach:
protected function title(): Attribute
{
return Attribute::make(
get: fn ($value) => $value['en'],
set: fn ($value) => $value['en'],
);
}
Despite various attempts, I’m still unable to retrieve only the desired language value. When attempting to access the specific language using syntax like $value->en, I encounter errors such as "Cannot access offset of type string on string".
My objective is to receive JSON data from articles in the format like articles[{ "id" : 1, "title" : "english title"}], containing only the necessary language data. However, I’m currently receiving the entire JSON object instead.
I’ve explored using Laravel’s JSON.php class as documented, but the issue persists.
Additionally, I tried the following alternative approach:
protected function getTitleAttribute() { return $this->title['en']; }
However, the problem remains unresolved.
In summary, I’m struggling to access a single value from the JSON attribute in my model, and even defining a cast hasn’t resolved the issue. This limitation hampers my ability to efficiently transmit only the necessary data to my React frontend.
2
Answers
For one language only you can do something like this:
For multiple languages I would use something else:
I didn’t test any of these methods, so please excuse potential typos 🙂 I’m just trying to get you on the right path.
Addition
As by @9uifranco mentioned you should cast to array instead of json. Sorry didn’t see that at first.
You can cast your attributes to
array
instead, and then get the value you want:or just use the
$casts
attribute:And then get the correct value by language: