Skip to Content
Menu
This question has been flagged
2 Replies
4073 Views

we need to override below method in odoo 14 
get avatar() {
    if (
        this.message.author &&
        this.message.author === this.env.messaging.partnerRoot
    ) {
        return '/mail/static/src/img/odoobot.png';
    } else if (this.message.author) {
// TODO FIXME for public user this might not be accessible. task-2223236
// we should probably use the correspondig attachment id + access token
// or create a dedicated route to get message image, checking the access right of the message
    return this.message.author.avatarUrl;
} else if (this.message.message_type === 'email') {
    return '/mail/static/src/img/email_icon.png';
}
    return '/mail/static/src/img/smiley/avatar.jpg';
}

we try but not fix please sugges solution

odoo.define('mymodule/static/src/js/avatar.js', function (require) {
'use strict';
const components = {
Message: require('mail/static/src/components/message/message.js'),
};
const { patch } = require('web.utils');
patch(components.Message.prototype, 'mymodule/static/src/js/avatar.js', {

/**
* @override
*/
get avatar() {
    if (
            this.message.author &&
            this.message.author === this.env.messaging.partnerRoot
    ) {
        return '/mail/static/src/img/robot.png';
    } else if (this.message.author) {
        return this.message.author.avatarUrl;
    } else if (this.message.message_type === 'email') {
        return '/mail/static/src/img/email_icon.png';
    }
    return '/mail/static/src/img/smiley/avatar.jpg';
}
});
});

Avatar
Discard
Best Answer

Hello,

This is a special case because you are trying to override an ES6 Class "getter" and unfortunately it will not work with the patch function.

I will propose you one solution (but  there  are  others) :

const patchMixin = require("web.patchMixin");
const PatchableMessage = patchMixin(components.Message);
const MessageList = require("mail/static/src/components/message_list/message_list.js");

PatchableMessage.patch(
    "owl_tutorial_extend_override_components/static/src/components/message/solution_3_patch_message.js",
    (T) => {
        class MessagePatched extends T {
            /**
             * @override property
             */
            get avatar() {
             // Code your override here
}
        }
        return MessagePatched;
    }
);
MessageList.components.Message = PatchableMessage;

Basically, you force the patchMixin onto the original Component and you replace your patchable copy in the Component tree.
Here the Message Component is used in the MessageList component, so it is replaced here.

Be careful with that technique, if the original "Message" Component had other functions patched, all the patches will be lost !!

There are other ways to override "non-patchable" Components, via defineProperty or using the built-in "setup" function of 
Components. 

If you want to see other solutions, I recently wrote a tutorial on all the way to extend/override/monkey patch functions and took your question as an example, it may be helpful to you.


[Updated answer] Adding a patchInstance method

You can add a patchInstanceMethods function, inspired by the Odoo 15 version of the "patch" function. 

Create a new utils file inside your module: https://github.com/Coding-Dodo/owl_tutorial_extend_override_components/blob/main/static/src/js/utils.js


Now you can patch getters:

const {  patchInstanceMethods,} = require("your_module_name.utils");
patchInstanceMethods(components.Message.prototype, "messageFirstPatch", {
    /**
     * Get the avatar of the user. This function can be overriden
*
* @returns {string}
*/
    get avatar() {
        if (
            this.message.author &&
            this.message.author === this.env.messaging.partnerRoot
        ) {
            // example override
            return "https://avatars.githubusercontent.com/u/81346769?s=400&u=614004f5f4dace9b3cf743ee6aa3069bff6659a2&v=4";
        } else if (this.message.author) {
            return this.message.author.avatarUrl;
        } else if (this.message.message_type === "email") {
            return "/mail/static/src/img/email_icon.png";
        }
        return "/mail/static/src/img/smiley/avatar.jpg";
    },
});
// SECOND PATCH
patchInstanceMethods(components.Message.prototype, "messageSecondPatch", {
    /**
    * Override of override
    *
    * @returns {string}
    */
    get avatar() {
        let originAvatar = this._super(...arguments);
        return originAvatar + "?overridenPatch=Yes";
    },
});

Avatar
Discard

its bad solution, because in that way our patch delete all pacthes before our patch

Yes, it is not the best way because you replace the Component, if it was patched elsewhere (with the Message component, it is the cause in the snailmail module) you lose the patch yes. But there are other solutions in the article.

Best Answer

any ideas?

Avatar
Discard

I've updated the answer with another solution that doesn't make you replace the Component.

Related Posts Replies Views Activity
1
Aug 21
3493
0
Jan 21
6721
0
Aug 24
134
2
May 24
3936
1
Aug 23
2473