refactor: remove outdated avatar and chat update documentation files; streamline project structure for improved maintainability

This commit is contained in:
2025-10-30 09:25:53 -03:00
parent ef20d599eb
commit 21b41121db
24 changed files with 829 additions and 4573 deletions

View File

@@ -48,15 +48,8 @@ export const criarConversa = mutation({
avatar: v.optional(v.string()),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) throw new Error("Não autenticado");
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
if (!usuarioAtual) throw new Error("Usuário não encontrado");
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) throw new Error("Não autenticado");
// Validar participantes
if (!args.participantes.includes(usuarioAtual._id)) {
@@ -226,28 +219,34 @@ export const enviarMensagem = mutation({
ultimaMensagemTimestamp: Date.now(),
});
// Criar notificações para outros participantes
for (const participanteId of conversa.participantes) {
if (participanteId !== usuarioAtual._id) {
const tipoNotificacao = args.mencoes?.includes(participanteId)
? "mencao"
: "nova_mensagem";
// Criar notificações para outros participantes (com tratamento de erro)
try {
for (const participanteId of conversa.participantes) {
if (participanteId !== usuarioAtual._id) {
const tipoNotificacao = args.mencoes?.includes(participanteId)
? "mencao"
: "nova_mensagem";
await ctx.db.insert("notificacoes", {
usuarioId: participanteId,
tipo: tipoNotificacao,
conversaId: args.conversaId,
mensagemId,
remetenteId: usuarioAtual._id,
titulo:
tipoNotificacao === "mencao"
? `${usuarioAtual.nome} mencionou você`
: `Nova mensagem de ${usuarioAtual.nome}`,
descricao: args.conteudo.substring(0, 100),
lida: false,
criadaEm: Date.now(),
});
await ctx.db.insert("notificacoes", {
usuarioId: participanteId,
tipo: tipoNotificacao,
conversaId: args.conversaId,
mensagemId,
remetenteId: usuarioAtual._id,
titulo:
tipoNotificacao === "mencao"
? `${usuarioAtual.nome} mencionou você`
: `Nova mensagem de ${usuarioAtual.nome}`,
descricao: args.conteudo.substring(0, 100),
lida: false,
criadaEm: Date.now(),
});
}
}
} catch (error) {
// Log do erro mas não falhar o envio da mensagem
console.error("Erro ao criar notificações:", error);
// A mensagem já foi criada, então retornamos o ID normalmente
}
return mensagemId;
@@ -264,15 +263,8 @@ export const agendarMensagem = mutation({
agendadaPara: v.number(), // timestamp
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) throw new Error("Não autenticado");
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
if (!usuarioAtual) throw new Error("Usuário não encontrado");
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) throw new Error("Não autenticado");
// Validar data futura
if (args.agendadaPara <= Date.now()) {
@@ -308,15 +300,8 @@ export const cancelarMensagemAgendada = mutation({
mensagemId: v.id("mensagens"),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) throw new Error("Não autenticado");
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
if (!usuarioAtual) throw new Error("Usuário não encontrado");
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) throw new Error("Não autenticado");
const mensagem = await ctx.db.get(args.mensagemId);
if (!mensagem) throw new Error("Mensagem não encontrada");
@@ -338,15 +323,8 @@ export const reagirMensagem = mutation({
emoji: v.string(),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) throw new Error("Não autenticado");
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
if (!usuarioAtual) throw new Error("Usuário não encontrado");
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) throw new Error("Não autenticado");
const mensagem = await ctx.db.get(args.mensagemId);
if (!mensagem) throw new Error("Mensagem não encontrada");
@@ -496,20 +474,13 @@ export const uploadArquivoChat = mutation({
conversaId: v.id("conversas"),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) throw new Error("Não autenticado");
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) throw new Error("Não autenticado");
// Verificar se usuário pertence à conversa
const conversa = await ctx.db.get(args.conversaId);
if (!conversa) throw new Error("Conversa não encontrada");
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
if (!usuarioAtual) throw new Error("Usuário não encontrado");
if (!conversa.participantes.includes(usuarioAtual._id)) {
throw new Error("Você não pertence a esta conversa");
}
@@ -526,8 +497,8 @@ export const marcarNotificacaoLida = mutation({
notificacaoId: v.id("notificacoes"),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) throw new Error("Não autenticado");
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) throw new Error("Não autenticado");
await ctx.db.patch(args.notificacaoId, { lida: true });
return true;
@@ -540,15 +511,8 @@ export const marcarNotificacaoLida = mutation({
export const marcarTodasNotificacoesLidas = mutation({
args: {},
handler: async (ctx) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) throw new Error("Não autenticado");
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
if (!usuarioAtual) throw new Error("Usuário não encontrado");
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) throw new Error("Não autenticado");
const notificacoes = await ctx.db
.query("notificacoes")
@@ -573,15 +537,8 @@ export const deletarMensagem = mutation({
mensagemId: v.id("mensagens"),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) throw new Error("Não autenticado");
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
if (!usuarioAtual) throw new Error("Usuário não encontrado");
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) throw new Error("Não autenticado");
const mensagem = await ctx.db.get(args.mensagemId);
if (!mensagem) throw new Error("Mensagem não encontrada");
@@ -607,14 +564,7 @@ export const deletarMensagem = mutation({
export const listarConversas = query({
args: {},
handler: async (ctx) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return [];
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return [];
// Buscar todas as conversas do usuário
@@ -641,10 +591,21 @@ export const listarConversas = query({
// Para conversas individuais, pegar o outro usuário
let outroUsuario = null;
if (conversa.tipo === "individual") {
outroUsuario = participantes.find((p) => p?._id !== usuarioAtual._id);
const outroUsuarioRaw = participantes.find((p) => p?._id !== usuarioAtual._id);
if (outroUsuarioRaw) {
// Adicionar URL da foto de perfil
let fotoPerfilUrl = null;
if (outroUsuarioRaw.fotoPerfil) {
fotoPerfilUrl = await ctx.storage.getUrl(outroUsuarioRaw.fotoPerfil);
}
outroUsuario = {
...outroUsuarioRaw,
fotoPerfilUrl,
};
}
}
// Contar mensagens não lidas
// Contar mensagens não lidas (apenas mensagens NÃO agendadas)
const leitura = await ctx.db
.query("leituras")
.withIndex("by_conversa_usuario", (q) =>
@@ -652,11 +613,13 @@ export const listarConversas = query({
)
.first();
const mensagens = await ctx.db
// CORRIGIDO: Buscar apenas mensagens NÃO agendadas (agendadaPara === undefined)
const todasMensagens = await ctx.db
.query("mensagens")
.withIndex("by_conversa", (q) => q.eq("conversaId", conversa._id))
.filter((q) => q.neq(q.field("agendadaPara"), undefined))
.collect();
const mensagens = todasMensagens.filter((m) => !m.agendadaPara);
let naoLidas = 0;
if (leitura) {
@@ -693,14 +656,7 @@ export const obterMensagens = query({
limit: v.optional(v.number()),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return [];
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return [];
// Verificar se usuário pertence à conversa
@@ -747,25 +703,17 @@ export const obterMensagensAgendadas = query({
conversaId: v.id("conversas"),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return [];
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return [];
// Buscar mensagens agendadas
const mensagens = await ctx.db
const todasMensagens = await ctx.db
.query("mensagens")
.withIndex("by_conversa", (q) => q.eq("conversaId", args.conversaId))
.filter((q) => q.neq(q.field("agendadaPara"), undefined))
.collect();
// Filtrar apenas as do usuário atual
const minhasMensagensAgendadas = mensagens.filter(
// Filtrar apenas as agendadas do usuário atual
const minhasMensagensAgendadas = todasMensagens.filter(
(m) =>
m.remetenteId === usuarioAtual._id &&
m.agendadaPara &&
@@ -786,14 +734,7 @@ export const obterNotificacoes = query({
apenasPendentes: v.optional(v.boolean()),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return [];
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return [];
let query = ctx.db
@@ -834,14 +775,7 @@ export const obterNotificacoes = query({
export const contarNotificacoesNaoLidas = query({
args: {},
handler: async (ctx) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return 0;
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return 0;
const notificacoes = await ctx.db
@@ -861,8 +795,8 @@ export const contarNotificacoesNaoLidas = query({
export const obterUsuariosOnline = query({
args: {},
handler: async (ctx) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return [];
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return [];
const usuarios = await ctx.db
.query("usuarios")
@@ -888,14 +822,7 @@ export const obterUsuariosOnline = query({
export const listarTodosUsuarios = query({
args: {},
handler: async (ctx) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return [];
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return [];
const usuarios = await ctx.db
@@ -929,14 +856,7 @@ export const buscarMensagens = query({
conversaId: v.optional(v.id("conversas")),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return [];
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return [];
// Buscar em todas as conversas do usuário
@@ -1001,14 +921,7 @@ export const obterDigitando = query({
conversaId: v.id("conversas"),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return [];
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return [];
// Buscar indicadores de digitação (últimos 10 segundos)
@@ -1043,14 +956,7 @@ export const contarNaoLidas = query({
conversaId: v.id("conversas"),
},
handler: async (ctx, args) => {
const identity = await ctx.auth.getUserIdentity();
if (!identity) return 0;
const usuarioAtual = await ctx.db
.query("usuarios")
.withIndex("by_email", (q) => q.eq("email", identity.email!))
.first();
const usuarioAtual = await getUsuarioAutenticado(ctx);
if (!usuarioAtual) return 0;
const leitura = await ctx.db

View File

@@ -486,7 +486,7 @@ export const listarParaChat = query({
_id: v.id("usuarios"),
nome: v.string(),
email: v.string(),
matricula: v.string(),
matricula: v.optional(v.string()),
avatar: v.optional(v.string()),
fotoPerfil: v.optional(v.id("_storage")),
fotoPerfilUrl: v.union(v.string(), v.null()),
@@ -522,7 +522,7 @@ export const listarParaChat = query({
_id: usuario._id,
nome: usuario.nome,
email: usuario.email,
matricula: usuario.matricula,
matricula: usuario.matricula || undefined,
avatar: usuario.avatar,
fotoPerfil: usuario.fotoPerfil,
fotoPerfilUrl,