user.joinedAt displays current time - discord.js

The code is here. In line 41, user.joinedAt displays the current date and time instead of the user's joined-in date. What is the issue there? I have done research online but those either display the current time or errors in my console. I heard that I would have to use member.joinedAt, but then I would have to define "member". "user" is already defined as you can conclude in the code.

A User does not have a joinedAt property. Therefore, the date being used is: moment.utc(undefined), which defaults to the latest date.
Instead, you need to use a GuildMember. In your code, you can do this by using message.mentions.members:
let member = message.mentions.members.first();
However, you are also using user.createdAt, which a GuildMember does not have. You can access the createdAt property through the GuildMember.user property, which contains the createdAt property:
let user = member.user;
Then you can use the correct values like so:
let embed = new Discord.MessageEmbed()
.setTitle(`Userinfo`)
.setColor(`BLUE`)
.setThumbnail(user.avatarURL({ size: 2048, dynamic: true }))
.addFields (
{name: `Username + tag`, value: `${user.tag}`, inline: true},
{name: `Server join date`, value: `${moment.utc(member.joinedAt).format("dddd, MMMM Do YYYY, h:mm:ss a")} UTC`, inline: true },
{name: `User creation date`, value: `${moment.utc(user.createdAt).format("dddd, MMMM Do YYYY, h:mm:ss a")} UTC`, inline: true}
);

Related

Discord.js v14: Embed-Fields empty after using EmbedBuilder

i have a strange Problem after updating from v13 to v14 that i don't understand.
A part of my Bot works as a Ticketsystem, where Tickets (as MessageEmbeds) can be changed via Reactions.
But when i try to change the embed with the new EmbedBuilder, every data inside the embed seems fine except the "fields"-data that are suddenly "undefined".
here is some example-code:
const embedObject = reaction.message.embeds[0]
console.log(embedObject.fields)
const tmpEmbed = EmbedBuilder.from(reaction.message.embeds[0])
console.log(tmpEmbed.fields)
First output is something like:
[
{ name: 'Priorität:', value: 'Normal', inline: true },
{ name: 'Übernommen:', value: '-', inline: true },
{ name: 'User:', value: '<#369058976245219330>', inline: false },
{ name: 'Inhalt:', value: '```test```', inline: false }
]
Second output is "undefined"
Solution:
With some trial and error i found a solution and possible inconsistency in the code of the discord-api (or it's my limit understanding) when trying to alter specific embed data.
So, what my code looked like in v13:
const embedObject = reaction.message.embeds[0]
embedObject.setDescription("**Status:** in Bearbeitung")
embedObject.setColor("#2db300")
embedObject.fields[1].value = `<#${user.id}>`
embedObject.setFooter({text: `Bearbeitet von: ${user.username}`, iconURL: userIcon})
embedObject.setTimestamp(new Date())
await reaction.message.edit({embeds: [embedObject]}).catch(console.error)
Now in v14, all of the .set-Functions didn't worked anymore for an already existing embed, so i thought i needed to construct an embed with the EmbedBuilder.
But now it's gets odd, while the .setDescription (and some other .set-Functions) just changed syntax to directly change the data (like it was for "fields" already):
const embedObject = reaction.message.embeds[0]
embedObject.Description = "**Status:** in Bearbeitung"
embedObject.fields[1].value = `<#${user.id}>`
for .setColor, .setFooter and .setTimestamp this doesn't work!
Also the "field"-data is not accessable from the EmbedBuilder-Object.
So you need to first edit some of the data "directly" (like description or fields) and then actually need to construct an embed with the EmbedBuilder to change color,footer and/or timestamp:
tmpEmbed = EmbedBuilder.from(embedObject)
.setColor(0x2db300)
.setFooter({text: `Bearbeitet von: ${user.username}`, iconURL: userIcon})
.setTimestamp(new Date())
Keep in mind, for this EmbedBuilder-Object, you can't read/change "fields", so do that before using the EmbedBuilder.
The working new code in v14, equal to the old code, is:
const embedObject = reaction.message.embeds[0]
embedObject.Description = "**Status:** in Bearbeitung"
embedObject.fields[1].value = `<#${user.id}>`
tmpEmbed = EmbedBuilder.from(embedObject)
.setColor(0x2db300)
.setFooter({text: `Bearbeitet von: ${user.username}`, iconURL: userIcon})
.setTimestamp(new Date())
await reaction.message.edit({embeds: [tmpEmbed]}).catch(console.error)
I'm no expert on Javascript or the Discord-API, so everything is learning by doing for me.
Possibly i got something wrong, did the v13 code already "odd" or am just missing something, but i hope this could help others when struggling with embeds :)

it is possible to change the default received language from iso-3166-1-alpha-2

I would like to explain my problem of the day.
currently I receive data in the following format
[{location: "CU"},{location: "FR"},{location: "ES"}]
then I map and re map to correctly recover value, label, flag
const country = Array.from(
new Set(data?.map((e) => e.location))
).map((countryCode) => ({
value: countryCode,
label: `${iso3311a2.getCountry(countryCode)} (${countryCode})`,
flag: countryCode,
}));
it works correctly
I get the new data in the following format
[{flag: "CU" label: "Cuba (CU)"value: "CU"},
{flag: "FR" label: "France (FR) "value: "FR"},
{flag: "ES" label: "Spain (ES) "value: "ES"},
]
so my problem and the next one
here I recover spain
while I would like to recover "Espagne" according to the language
basically, is it possible to recover it in another language?
iam open to any proposal thank you very much.

React Data Table Component and Moment

I am using React Data Table Component for displaying table data - which works great!
I have a row field for lastLogin time, which is stored in MongoDB as a model like so:
lastLogin: [{
type: Date,
required: false,
}],
My data table component looks like so:
<DataTable
noHeader
pagination
paginationPerPage={15}
paginationRowsPerPageOptions={paginationRowsPerPageOptions}
responsive
columns={columns}
sortIcon={<ChevronDown />}
className="react-dataTable"
data={store.data}
/>
Using columns when I try and render the date without moment, it works fine:
{
name: 'Last Login',
selector: (row) => row.lastLogin,
},
will result in:
row 1: 2021-11-17T01:16:55.093Z
row 2: (empty)
However, when formatting with moment, it seems to be obtaining the previous records results.
{
name: 'Last Login',
selector: (row) => row.lastLogin,
format: (row) => moment(row.lastLogin).format('lll'),
},
will result in:
row 1: Jan 1, 2021 12:00 AM
row 2: Nov 17, 2021 1:15 PM
This code is work correct, and the result its expected base on how the moment work.
moment work with current time as a default time to do a process, so that, if you pass a date value, then you will work and format this value, else will work and format current date.
for example:
var now = moment(undefined).format('lll');
console.log(now)
this will be equl for:
var now2 = moment().format('lll');
console.log(now2)
Demo Link
Ok... this one has been resolved... silly syntax error.
The login date on the model was setup as an array:
lastLogin: [{
type: Date,
required: false,
}],
Should be:
lastLogin: {
type: Date,
required: false,
},

mongoose query: find an object by id in an array

How could I find an image by id in this Schema. I have the id of the User and the id of the image I am looking for. What would be the best way to do this and do all images in this case have different ids or could they have the same id because they don't belong to the same User?
My Schema looks like this:
var userSchema = new Schema({
local: {
email: String,
password: String
},
facebook: {
id: String,
token: String,
email: String,
name: String
},
name: String,
about: String,
images: [{
id: Schema.ObjectId,
link: String,
main: Boolean
}]
});
When you are interested in the full object it is a simple find:
.find({"facebook.id":"<id>", "images.id":<image-id>})
I don't think that there is a way to reduce the image array in the result.
To update a single element in the image array you can use this:
.update({"facebook.id":"<id>", "images.id":<image-id>}, {$set : {"images.$.main" :false} } );
userSchema .find({facebook.id: "some ID",{ "images.id": { $in: [ id1, id2, ...idn] }}
since images are inside the document you can have same ID's however every time you query you should keep in mind that you send some other parameters such as facebook.id or facebook.email along with image id's to retrieve them. Otherwise you end up getting all that might be irrelevant only because you decide to keep same ID's for images.
tl;dr
I struggled with this and came up with a solution. Like you, I was trying to query for a deeply nested object by the _id, but I kept coming up empty with the results. It wasn't until I did some type checking that I realized the id value I was getting from my frontend, while directly supplied by mongoose, was in fact a String and not an Object.
I realize this question was already partially answered before, but that person's solution didn't work for me, and the comment on the answer tells me you wanted to update the specific image you queried for, which is exactly what I was trying to do.
The solution
In order to select an object from the nested array by the _id value, first you'll have to install the npm package bson-objectid and use the provided method to convert your string into an objectId in your query.
In your terminal:
npm i bson-objectid
In your code:
const ObjectId = require('bson-objectid')
userSchema.findOneAndUpdate(
{ "facebook.id": <user-id>, "images._id": ObjectId(<image-id>) },
{ "$set": { "images.$.main": false } },
{ new: true }, // an extra options parameter that returns the mutated document
(err, user) => {
if (err) {
handleErr(err)
} else {
console.log(user)
// do something with new user info
}
)

Model's defaultValue is evaluated only once in ExtJS. Is there a way to evaluate it at record insertion?

I noticed that if I set a defaultValue for a model in ExtJS, this is evaluated only once. The problem is I would have something like this
Ext.define("AnalysisModel",{
extend: "Ext.data.Model",
fields: [
{
name: "date",
type: "date",
defaultValue: new Date(),
}
],
});
Every time I record is inserted in the store that uses this model, I expect that date will be the date of the insertion. On the contrary, new Date() is evaluated only once and all records have the same value for date. So I have to explicitly insert also date.
Is there a way to circumvent this? I'm using ExtJS 5.1
The defaultValue: new Date() is being evaluated when the model is defined; it's part of the arguments to the Ext.define() call. That's why it's only being evaluated once.
What you need to do is evaluate the defaultValue later - e.g. when the model is evaluated. The easiest way to do that for a model is to use the convert method.
{ name: "date", type: "date",
convert: function(value, record) {
if (value) { return value; }
return new Date();
}
}
NB: haven't tested this, but it should work.

Resources