Cannot set property 'avatar' of undefined at Member.set [as avatar] - Discord Bot

Solution 1:

I was struggling with this issue and eventually figured it out. It's because the 'this' keyword is getting hijacked somehow in the code within the Object.defineProperty call inside the Member constructor(line 2606 in my version of index.js, but I've made a few other fixes already so yours is probably different). I was able to fix it by caching off the 'this' reference into a private member and referencing that instead. It feels hacky but it works. Like so:

function Member(client, server, data) {
    copyKeys(data, this, ['user', 'joined_at',]);
    this.id = data.user.id;
    this.joined_at = Date.parse(data.joined_at);
    this.color = colorFromRole(server, this);
    var tempThis = this;
    ['username', 'discriminator', 'bot', 'avatar', 'game'].forEach(function(k) {
        if (k in Member.prototype) return;
        Object.defineProperty(Member.prototype, k, {
            get: function() { return client.users[tempThis.id][k]; },
            set: function(v) { client.users[tempThis.id][k] = v; },
            enumerable: true,
        });
    });
}

Solution 2:

I just experienced the same error with my own bot completely out of the blue. After some investigation, I checked the code at DiscordClient.handleWSMessage (on my error it was showing at index.js:1871:31 as opposed to index.js:1891:31, however I'm not sure if it's a matter of having different versions of discord.io installed) - in any case, the error seemed to be stemming from the Event switch statement responding to a GUILD_CREATE event - this may be different for you:

case "GUILD_CREATE":
            /*The lib will attempt to create the server using the response from the
            REST API, if the user using the lib creates the server. There are missing keys, however.
            So we still need this GUILD_CREATE event to fill in the blanks.
            If It's not our created server, then there will be no server with that ID in the cache,
            So go ahead and create one.*/
            client.servers[_data.id] = new Server(client, _data);
            return emit(client, message, client.servers[_data.id]);

I don't understand why GUILD_CREATE events are being received, my bot has never been programmed to handle these, however commenting out the executable lines in the switch case above and replacing them with an empty return statement seemed to stop the error occurring, and my bot stayed connected (so far, I've only been testing for a few minutes).