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

Uncaught TypeError: base is not a constructor #58

Open
tim-breitenstein-it opened this issue Feb 19, 2021 · 17 comments
Open

Uncaught TypeError: base is not a constructor #58

tim-breitenstein-it opened this issue Feb 19, 2021 · 17 comments

Comments

@tim-breitenstein-it
Copy link

Magento Version: 2.4.2
Magesuite Version: 7.0.0
Creativeshop theme Version: 11.0.1

The error happens on Product View and Checkout. Therefore the Checkout is not fully loading.

widget.js:75
Uncaught TypeError: base is not a constructor
    at Function.$.widget (widget.js:75)
    at validation-ext.js:41
    at mixins.js:105
    at Array.forEach (<anonymous>)
    at applyMixins (mixins.js:104)
    at mixins.js:129
    at Object.execCb (require.js:1650)
    at Object.context.execCb (resolver.js:156)
    at Module.check (require.js:866)
    at Module.<anonymous> (require.js:1113)
@ggm-dev
Copy link

ggm-dev commented Mar 11, 2021

Hi Tim - Did you ever get things working on 2.4.2? I wonder if the core team has any insight or a timeline for 2.4.2 compatible release?

@tim-breitenstein-it
Copy link
Author

Hi Tim - Did you ever get things working on 2.4.2? I wonder if the core team has any insight or a timeline for 2.4.2 compatible release?

We are developing a theme based on Creativeshop theme and upgrade immediately to Magento v2.4.2 to have the newest release and this bug is the onliest thing which ist not working at the moment.

@mborkowski
Copy link

Hello guys. We also encountered this issue today. If you found the cause, we'd be grateful for sharing. If not, we'll debug it on our own and we'll try to release fix soon

@tim-breitenstein-it
Copy link
Author

If you found the cause, we'd be grateful for sharing.

Unfortunately I found no solution.

I played around with something like that but had no luck:

define(['jquery', 'jquery/validate', 'jquery-ui-modules/widget'], function($) {

define(['jquery', 'mage/validation', 'jquery-ui-modules/widget'], function($) {

define(['jquery', 'mage/validation/validation', 'jquery-ui-modules/widget'], function($) {

I comment it out for a temporary solution.

@ggm-dev
Copy link

ggm-dev commented Mar 16, 2021

No solution here either -

@mborkowski
Copy link

Something had to change in the mixins itself, because base (which is mageValidation in this case) is not getting there into the mixin, it's lost somewhere. All mixins are defined the same way and the others are working fine... Definition of validation widget itself wasn't changed on Magento side. We will try to debug this deeper in upcoming days, but I already know it's not going to be pleasure thing to do... 😞
I'm afraid adding another dependencies is a no-go, it won't solve the issue, we can't require module that is about to be extended.

@mborkowski
Copy link

If you found the cause, we'd be grateful for sharing.

Unfortunately I found no solution.

I played around with something like that but had no luck:

define(['jquery', 'jquery/validate', 'jquery-ui-modules/widget'], function($) {

define(['jquery', 'mage/validation', 'jquery-ui-modules/widget'], function($) {

define(['jquery', 'mage/validation/validation', 'jquery-ui-modules/widget'], function($) {

I comment it out for a temporary solution.

Are you sure none of these worked for you?
For us, this fixes the issue:
define(['jquery', 'jquery-ui-modules/widget'], function($) {

@tim-breitenstein-it
Copy link
Author

Are you sure none of these worked for you?
For us, this fixes the issue:
define(['jquery', 'jquery-ui-modules/widget'], function($) {

Definitely not :(

image

@mborkowski
Copy link

mborkowski commented Mar 18, 2021

Ok guys, as a workaound I suggest following changes:
line 6: remove mageValidation
line 36: use $.mage.validation instead of mageValidation.
I know this is not the correct way of doing mixins, this will just "fix" the error, we are working on a proper solution

@tim-breitenstein-it
Copy link
Author

line 6: remove mageValidation
line 36: use $.mage.validation instead of mageValidation.

Works for me!

@mborkowski
Copy link

mborkowski commented Mar 18, 2021

We found the cause. It's not on oir site. I presume you're using Dotmailer's SMS module. In our case (some of our projects use it) it was the cause. You can follow on their github
If you made those changes suggested previously, please restore original contents aftery ou upgrade dotmailer's module

@daniel-ifrim
Copy link

daniel-ifrim commented Mar 26, 2021

I added this in validation-ext.js.

define(['jquery', 'mage/validation/validation', 'jquery-ui-modules/widget'], function($) {
    'use strict';

    return function(mageValidation) {

instead of this:

define(['jquery'], function($) {
    'use strict';

    return function(mageValidation) {

I picked up 'mage/validation/validation'] from a file in vendor/magento.
And 'jquery-ui-modules/widget' is missing too mentioned above.
The JS error was breaking homepage, category page and other pages.

@tim-breitenstein-it
Copy link
Author

Pls try:

define(['jquery'], function($) {
    'use strict';

    return function() {
        $.fn.validateDelegate = function(delegate, type, handler) {
            /**
             * By default Magento allows events to be attached only to form fields while
             * all validation is registered for whole form elements. This prevents
             * any event listeners like focusout or keydown from being properly attached and fired.
             */
            if (!this[0].form && !this.is('form')) {
                return this;
            }

            return this.on(
                type,
                $.proxy(function(event) {
                    var target = $(event.target);
                    var form = target[0].form || target[0];

                    if (
                        form &&
                        $(form).is(this) &&
                        $.data(form, 'validator') &&
                        target.is(delegate) &&
                        !target.is('.swatch-input')
                    ) {
                        return handler.apply(target, arguments);
                    }
                }, this)
            );
        };

        $.widget('mage.validation', $.mage.validation, {
            options: {
                // Restore default focusout validation.
                onfocusout: $.validator.defaults.onfocusout,
                // Validates on keyup but only when user corrects invalid field to give early feedback.
                onkeyup: function(element, event) {
                    if (!element.classList.contains(this.settings.errorClass)) {
                        return;
                    }

                    $.validator.defaults.onkeyup.call(this, element, event);
                },
            },
        });

        return $.mage.validation;
    };
});

@ggm-dev
Copy link

ggm-dev commented Mar 26, 2021

I tried disabling Dotmailer's SMS module per suggestion from @mborkowski and error disappeared on PDP and in checkout. I have not tried to apply patch he linked to. Have you guys tried that or is this a new issue?

@mborkowski
Copy link

Just a note from my side that this posted "solutions" are not real solutions. The issue is on dotmailer's module and they should fix it (maybe they already did, I didn't check). They simply forgot to return the widget after extend so they broke the pipe this way and Creativeshop's mixin didn't receive origin in the argument.
Please remember to revert above after you confirm they fixed it.

@frqnck
Copy link

frqnck commented Mar 21, 2022

We are experiencing the exact same issue with the Adyen Payment plugin v8 module, their v7 works fine. Is there any generic and permanent solution?

@Dnd-Safran
Copy link

Dnd-Safran commented May 18, 2022

Most of the time, it means that the widget you are extending is not declared. Check your dependencies first to be sure that you have the initial widget loaded and created (console.log($.[widget pathname])

In jquery source code, if you call
$.widget('mage.[widget]', $.mage.[widget], {})
it will call basePrototype = new base(); where base => $.mage.[widget]
So if $.mage.[widget] is undefined because the widget is not created yet, it will fail with base is not a constructor
Let's say the widget you are currently extending is in js file mymodule/mywidget.js be sure you have js file into dependencies of you mixin (and it return the widget)

define(['jquery','mymodule/mywidget.js'], function($, myWidget) {
    //use $.mage.[widget] here or myWidget
    console.log($.mage.[widget]) /* => constructor */
})

vs

define(['jquery',], function($) {
    //use $.mage.[widget] here.
    console.log($.mage.[widget]) /* => undefined */
})

I supposed the loading order has change over new versions so it can explain why it used to work fine and you have now to check if dependencies are loaded in the right order.

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

No branches or pull requests

6 participants