Skip to content
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

Fix PHP8 Trim Error #18903

Merged
merged 2 commits into from Mar 11, 2022
Merged

Fix PHP8 Trim Error #18903

merged 2 commits into from Mar 11, 2022

Conversation

deybhayden
Copy link
Contributor

Description:

An error happens if sites if names or skus are arrays in PHP 8 (was just a warning in PHP 7)

Uncaught exception in core/Tracker/GoalManager.php line 567:
trim(): Argument #1 ($string) must be of type string, array given

Review

An error happens if sites if names or skus are arrays in PHP 8

> Uncaught exception in core/Tracker/GoalManager.php line 567:
> trim(): Argument matomo-org#1 ($string) must be of type string, array given
Copy link
Member

@sgiehl sgiehl left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hey @deybhayden. Thanks for creating this PR. The code looks fine.
I guess actually name and sku are meant to be passed as a string only, as multiple values for a single product won't make that much sense. But guess it shouldn't hurt to convert arrays to strings to avoid possible errors.

@tsteur what do you think about that? Is it fine to change that, or should an exception be thrown if the values are not provided as strings?

@deybhayden
Copy link
Contributor Author

Awesome! Yeah, I wasn't sure if the fix made sense to the wider community. However, when we upgraded an Matomo install for a client, we started hitting this error as tracking requests tried to process on PHP 8. We didn't have the ability to tell sites to change their tracking code, so this is the fix we went with to get past the exception.

@tsteur
Copy link
Member

tsteur commented Mar 9, 2022

I'm having mixed feelings :) On one side it's not a big harm, on the other side once it's in there we need to keep supporting it and it might cause a regression in the future if we need to change behaviour around that. Considering it's only done for SKU and name it may be fine by me. It be different if it was done for a category as products can be actually assigned to multiple categories. Note that if we merge this, it could regress any time and we wouldn't make it a supported feature. Meaning this could actually cause issues again in the future if we support this now, then stop supporting it for some reason and then we're breaking it. I mean when people don't realise they send an array there. It should all be edge case though and be fine to merge I suppose. @sgiehl do you have any thoughts?

@deybhayden did this tracking actually ever work using an array? I wonder if it wouldn't have recorded like array as a product name?

@deybhayden
Copy link
Contributor Author

So, the change I did here isn't exactly what we did for our client, most of the examples were like this:

$name = ['shirt'] 

So, we just $name[0] if $name_check was an array. But, then yea, that did work properly for tracking Ecomm stuff. Totally open to whatever you all think best, but we just got bit here so I thought I'd bring it up.

@sgiehl
Copy link
Member

sgiehl commented Mar 10, 2022

@deybhayden actually the tracking on the website of the client seems to be incorrect, as they are sending an array for name, which shouldn't be the case. Our documentation also says it should be given as string.
When using the javascript tracker you actually can't set the sku to an array, as the code would prevent that here (or throw an error):

matomo/js/piwik.js

Lines 6745 to 6755 in 05082ab

* @param string sku (required) Item's SKU Code. This is the unique identifier for the product.
* @param string name (optional) Item's name
* @param string name (optional) Item's category, or array of up to 5 categories
* @param float price (optional) Item's price. If not specified, will default to 0
* @param float quantity (optional) Item's quantity. If not specified, will default to 1
*/
this.addEcommerceItem = function (sku, name, category, price, quantity) {
if (isNumberOrHasLength(sku)) {
ecommerceItems[sku] = [ String(sku), name, category, price, quantity ];
}
};

I guess the name could be set to an array at that point and would then be passed to the tracking. We actually also could change the javascript tracker so it throws an error if someone tries to set an sku or name as an array. So someone implementing the tracking directly sees it won't work.
Nevertheless this wouldn't prevent such tracking request coming e.g. directly from a PHP tracker or another sdk.

We could merge this to be a bit less error-prone when incorrect data is sent with the request. But as @tsteur this won't be officially supported and could break or change the behavior again any time in the future.

@deybhayden
Copy link
Contributor Author

Nice sleuthing! I didn't know enough to be able to dig into the JS library to follow the steps all the way through. I'm happy to change the code to throw errors or update the JS if that's the right path? I'm definitely a bit out of depth when it comes to the right solve.

@tsteur
Copy link
Member

tsteur commented Mar 10, 2022

@sgiehl sounds good to merge it 👍

@sgiehl sgiehl added this to the 4.9.0 milestone Mar 11, 2022
@sgiehl sgiehl merged commit 6ca37df into matomo-org:4.x-dev Mar 11, 2022
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.

None yet

3 participants