4
votes

I am getting the following error and am a bit lost on it:

Livewire encountered corrupt data when trying to hydrate the … component. Ensure that the [name, id, data] of the Livewire component wasn’t tampered with between requests

Situation is as follows: Livewire 2.x, Laravel 7.x, Component Controller fetches data from 3 MySQL Stored Procedures and processes it. Component Blade is a pretty basic blade with foreach loop. I am using the wire:init feature so that the component is not blocking the page load. It contains a custom-built pagination. When switching to the second page of data, this error occurs. It did not error out while on Livewire 1.x.

Has anyone any idea on how to tackle this problem? The error itself does not speak much to me. Any additional info required?

Thank you in advance, appreciate any help!

7

7 Answers

18
votes

In my case the solution was to make a public property protected and pass it to the blade manually, so it was excluded from Livewire's auto-handling under the hood.

0
votes

So I was getting the same error, this one:

Livewire encountered corrupt data when trying to hydrate the [component] component. Ensure that the [name, id, data] of the Livewire component wasn't tampered with between requests.

After trying the accepted answer and reading this long issue thread on Livewire's Github, I played around with passing data to the view in different ways. I'm sharing it here to help someone else with the same use case issue.

I found the following change, where an url I was previous passing I just got in the view instead, made it go away. From:

// Class
class MyComponent extends Component
{
    public Shop $shop;
    public Address $address;
    public string $action;

    // rules etc

    public function mount(Shop $shop)
    {
        if ($shop->address()->exists()) {
            $this->address = $shop->address;
            $this->form_action = route('merchant.shop.address.update');
        } else {
            $this->address = Address::make();
            $this->form_action = route('address.store');
        }
    }

// view
<div>
    <form method="post" action="{{ $action }}">
        @csrf

to:

// class
class MyComponent extends Component
{
    public Shop $shop;
    public Address $address;

    // rules etc

    public function mount(Shop $shop)
    {
        $this->address = $shop->address()->exists() ? $shop->address : Address::make();
    }

// view
<div>
    <form method="post" action="{{ $shop->address()->exists() ? route('merchant.shop.address.update') : route('address.store') }}">
0
votes

In my case, I had a couple of public variables and not all of them were being passed in from the parent view. After reading Markus' answer. I went and added the mount method to my livewire class and passed in the variables I was inheriting from the parent and it worked. I am using Livewire 2.3

This had the error

class MyView extends Component
{
  public $fromParent, $local;

  public function render()
  {
    return view('livewire.my-view');
  }
}

Adding mount fixed it

class MyView extends Component
{
  public $fromParent, $localVariable1, localVariable2;

  public function mount($fromParent)
  {
    $this->fromParent = $fromParent;
  }

  public function render()
  {
    return view('livewire.my-view');
  }
}
0
votes

In my case the problem came from a database query and the resulting collection.

This query (the meaning of the variables is not important)

DB::table('progress_trackings')
        ->select('user_id')
        ->whereIn('user_id', $users->pluck('id'))
        ->where('object_id', $activity->id)
        ->where('event', $type)
        ->get()
        ->keyBy('user_id');

Produced this output:

Illuminate\Support\Collection {#2427
 all: [
   454 => {#2279
     +"user_id": 454,
   },
   528 => {#441
     +"user_id": 528,
   },
   531 => {#2368
     +"user_id": 531,
   },
 ],

The query was triggered by a button in the blade file. Clicking the button 2 or 3 times resulted in the hydration error.

In the Livewire docs it is explained that array keys sometimes can cause problems: https://laravel-livewire.com/docs/2.x/troubleshooting

So I tried to make a plain array out of the db query result. Since I only needed the keys, this worked:

DB::table('progress_trackings')
    ->select('user_id')
    ->whereIn('user_id', $users->pluck('id'))
    ->where('object_id', $activity->id)
    ->where('event', $type)
    ->get()
    ->keyBy('user_id')
    ->keys()->toArray(); // ADDED THIS

Now the result is:

[
 454,
 528,
 531,

]

Which solved the hydration error.

0
votes

Addition to what others suggested above also this might happen if you have a collection which uses groupBy() might be the cause for this issue,

To fix this use protected $attribute in your component instead of public then pass $attribute to the component view.

protected $attribute;

public function mount($attribute){
   $this->attribute = $attribute;
}

...........

public function render()
{
    return view('livewire.view-here',['attribute'=>$attribute]);
}
0
votes

To troubleshoot this open the vendor/livewire/livewire/src/ComponentChecksumManager.php file and add var_dump($stringForHashing); on line 19, just before the return statement. Then you can see the data that is being hashed and compare it to the previous hashed data to find the discrepancies.

After I did this I was able to identify the numeric keys that javascript was re-arranging and come up with an adequate fix.

One thing to note is that some json formatters will re-order numeric keys also, so it's better to compare the json without formatting it or format it manually.

-1
votes

I solved it by putting livewire scripts @livewireScripts inside page header

<head>

<meta charset="utf-8" />

@livewireStyles

@livewireScripts

</head>