-
-
Notifications
You must be signed in to change notification settings - Fork 344
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Bug]: The component class constructor doesn't seem to run when using ComponentColumn #1513
Comments
Thanks for raising, I'll have a look in a bit, just so I can confirm:
Is that: I'm assuming the latter? |
It's a Blade component.
|
Perfect, thanks, I'll take a look shortly. |
Just having a look at why this isn't working for you, as I have a ComponentColumn working in my test environment. Will see if I can figure out why it works for me and not for you! |
Thanks for looking into this! I see one potential issue (weighing_unit_type has a cast), I'll investigate and update this. |
I looked at it, still no luck. The I put a Can you show me your working test? |
I'll have to share it tomorrow, as I'm tuckered out now: See Here for why! That should all get merged in, possibly tomorrow as a new release. But then I will definitely share my working example! Although glancing at it, I think mine may be an anonymous component, which would explain a lot as to why mine is working and yours isn't. I'll pop the code open tomorrow to see if I can figure out what's going on there. |
Yes I think this is the difference. |
This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions. |
This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions. |
This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions. |
This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions. |
This is still an issue |
Apologies, stalebot gets a bit over-eager (I have no control over that!) I'll do my best to take a look at this over the next week (so expect an update by the end of the month). I have tinkered a little, and have got this resolved in my local environment (I've added a new Column type to avoid any conflicts with existing code). If you want to give it a whirl, ping me on Discord and I'll let you know what to do to give it a test (would appreciate a real-world test tbh) |
Please do reach out if you want to test this, as otherwise I'll throw it into the next version, and it may not do what you want! |
Hello! I don't really use Discord, could you post some code here? I could temporarily modify my local vendor files and test it. |
To test this, all you need is a component which has a class constructor that sets some variable. Then reference that variable in the component view to make sure it's available. |
Okay, replicated, and have a fix for it, it'll come out as a new ViewComponentColumn type. |
3.4.0 is out now This fix will be in 3.4.1 which I'll release momentarily |
v3.4.1 is out, ViewComponentColumn is the one you want to use, as this has the fix in. |
Thank you. I upgraded to 3.4.2. I'm getting a different exception now: https://gyazo.com/caed47af06a1744f22e76b8306ce7d14 Usage
Same result with |
Just to make sure I can replicate it, whats the namespace for your WeightWithConversions component? |
It's |
So I've been able to replicate the issue, and managed to get it working how it should, I now just need to figure out how to implement it properly. |
Aand, I have a working solution. If you're around today, and fancy giving it a test, I'll create a temporary branch for it, as I'll need update tests/docs etc |
It's in the development branch at the mo, I've added a new method called customComponent that expects the actual View Component Class to be specified. This then works as expected (seems to at least so far in my testing!)
|
When I switch to branch I'll be happy to test this once you've been able to test and release it. |
@nathan-io - Sorry, the active development branch is: dev-development It's looking likely the back end of next week to make it into a release, as there's a fair few tests to write to cater for the different permutations, including adding in some weird/whacky View Components to make sure it operates consistently. Seems to so far tho! |
@nathan-io - v3.4.3 is out with the fixes in customComponentShould you wish to render the Custom Component in it's entirety, then you may use the customComponent method. Otherwise it will pass in the values directly to the blade, rather than executing your View Component. ViewComponentColumn::make('Weight', 'grams')
->customComponent(\App\View\Components\TestWeight::class)
->attributes(fn ($value, $row, Column $column) => [
'weight' => new Weight($value),
]), Docs should get updated in next few days, but that's the new feature that lets you properly instantiate a View Component. |
Unfortunately the issue persists with 3.4.3.
|
In your blade for the component, try
instead of
|
I did try However, that isn't the correct way to access the variable from the component view. See https://laravel.com/docs/11.x/blade#passing-data-to-components:
While reviewing the docs, I noticed that my syntax was a bit different. So I refactored to this:
This works exactly the same as my previous implementation - it's fine when called like However, when using this in the table column, I still get the "Undefined variable $conversions" exception in the component view.
I reverted my changes to "
Do you have an example component class and view that you were able to get working with this? If so, I can try it out. |
I will put together an example later today, and triple check that it is working as it should |
So after mucking around for quite a while, the methods within construct() aren't being fired, that's applying both internally to the table, and externally. The way I've got it working is: ViewComponentColumn::make('Test','amount')
->customComponent(\App\View\Components\TestWeight::class)
->attributes(fn ($value, $row, Column $column) => [
'weight' => new \App\Weight($row->amount),
]), The View Component "TestWeight" <?php
namespace App\View\Components;
class TestWeight extends \Illuminate\View\Component
{
public ?\App\Weight $weight;
public function __construct(\App\Weight $weight)
{
$this->weight = $weight;
}
/**
* Get the view / contents that represent the component.
*/
public function render(): \Illuminate\Contracts\View\View|Closure|string
{
return view('test-weight')->with(['conversions' => $this->weight->getConversion()]);
}
} Then the test-weight.blade.php blade: <div>
{{ $conversions }}
</div> Not ideal, but not sure why it's not firing subsequent code within construct as of yet, I'm assuming it's something I'm missing in terms of Reflections |
Thank you for the follow up and all of your efforts in this.
Yes I've always suspected that the constructor was either not firing at all, or somehow the data wasn't making it to the view the way it normally would when we call the component within a standard Blade context. With that in mind, I tried a workaround that I honestly should've though of from the beginning:
Result: (screenshot) It also works using
That
Someone could use this approach to use Blade components or Livewire components (which may suffer from the same or similar issue) as columns without having to touch the component class or view. The only issue I've noticed is that when I paginate, the links stop toggling the tippy popup. I'm such that's just some state thing. |
I'm assuming you're using bootstrap? |
Tailwind |
In that case, 100% look at the native AlpineJS anchor approach https://alpinejs.dev/plugins/anchor Most of the 3rd party popover/popper packages only run on first load, and setup instances for any element with "xyz" attributes. |
Thanks, I'll check that out! As far as this issue, I wonder if Instead of passing in a class name or arguments, you just pass in a string with the Blade to render, and the values for any props you're passing. In this case for example:
Then in
with something like:
Not sure passing a Blade component tag rather than a class name feels 100% right, but at least it would** bypass the issue with the constructor. **I think? maybe there's something special about doing it within the Livewire table class itself via a closure passed to |
With fresh eyes, and considering what you shared, the simplest approach would really be a simple Custom View against a standard Column: Create a Column that uses a Custom View. That recieves a parameter of "$weight"
Create the Custom Blade: "test-weight-custom-column-view.blade.php"
This will then instantiate and call the "Test Weight" view Component:
Then the "test-weight-123" blade contains something like:
|
I've been fiddling a little with the existing methods, and this seems like it may work for what you want:
TestWeight is a VIew Component, code below
Which has a view of:
|
Yep, I'll certainly look at options for simplifying it based on the approach I highlighted above. It won't be in the next 2 versions, but may be in a subsequent one. |
This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions. |
What happened?
We're trying to use a Blade component as a column:
This does cause livewire-tables to attempt to render the component view, but it throws an "Undefined variable" exception because the public properties that are set in the constructor aren't present.
I don't believe the problem is in the component, because it works without issue when called in a view:
So perhaps the constructor is not firing?
Here's the component class and view:
View:
How to reproduce the bug
No response
Package Version
3.1.0
PHP Version
8.1.x
Laravel Version
10
Alpine Version
No response
Theme
None
Notes
No response
Error Message
No response
The text was updated successfully, but these errors were encountered: