sendfile_ok
This commit is contained in:
parent
6c8ef54f47
commit
c158a182b3
@ -382,7 +382,6 @@ class ChatElement extends HTMLElement {
|
|||||||
throw new Error('No paired member found');
|
throw new Error('No paired member found');
|
||||||
}
|
}
|
||||||
|
|
||||||
// Formater la date pour n'avoir que l'heure et la date
|
|
||||||
const now = new Date();
|
const now = new Date();
|
||||||
const formattedTime = now.toLocaleString('fr-FR', {
|
const formattedTime = now.toLocaleString('fr-FR', {
|
||||||
day: '2-digit',
|
day: '2-digit',
|
||||||
@ -392,7 +391,6 @@ class ChatElement extends HTMLElement {
|
|||||||
minute: '2-digit'
|
minute: '2-digit'
|
||||||
});
|
});
|
||||||
|
|
||||||
// Créer le message au format attendu par messageStore
|
|
||||||
const newMessage = {
|
const newMessage = {
|
||||||
id: Date.now(),
|
id: Date.now(),
|
||||||
sender: myAddresses[0],
|
sender: myAddresses[0],
|
||||||
@ -401,9 +399,10 @@ class ChatElement extends HTMLElement {
|
|||||||
type: 'text' as const
|
type: 'text' as const
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if (this.selectedMemberId) {
|
||||||
messageStore.addMessage(this.selectedMemberId!, newMessage);
|
messageStore.addMessage(this.selectedMemberId!, newMessage);
|
||||||
this.messagesMock = messageStore.getMessages();
|
this.messagesMock = messageStore.getMessages();
|
||||||
|
}
|
||||||
|
|
||||||
// Récupérer le process_id du parent (conversation)
|
// Récupérer le process_id du parent (conversation)
|
||||||
const groupItem = this.shadowRoot?.querySelector('[data-process-id]');
|
const groupItem = this.shadowRoot?.querySelector('[data-process-id]');
|
||||||
@ -541,15 +540,33 @@ class ChatElement extends HTMLElement {
|
|||||||
const messageContent = document.createElement('div');
|
const messageContent = document.createElement('div');
|
||||||
messageContent.className = 'message';
|
messageContent.className = 'message';
|
||||||
|
|
||||||
if (message.sender === myAddresses[0]) {
|
if (message.type === 'file') {
|
||||||
messageContent.classList.add('user');
|
|
||||||
messageContent.innerHTML = `
|
messageContent.innerHTML = `
|
||||||
${message.text}
|
<strong>${await addressToEmoji(message.sender)}</strong>:
|
||||||
|
<span class="file-message" style="cursor: pointer; color: #0066cc; text-decoration: underline;">
|
||||||
|
📎 ${message.fileName}
|
||||||
|
</span>
|
||||||
<span class="message-time">${message.time}</span>
|
<span class="message-time">${message.time}</span>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
|
// Ajouter le gestionnaire de clic pour le téléchargement
|
||||||
|
const fileSpan = messageContent.querySelector('.file-message');
|
||||||
|
fileSpan?.addEventListener('click', () => {
|
||||||
|
const fileKey = `file_${message.id}`;
|
||||||
|
const fileData = localStorage.getItem(fileKey);
|
||||||
|
if (fileData) {
|
||||||
|
// Créer un lien de téléchargement
|
||||||
|
const link = document.createElement('a');
|
||||||
|
link.href = fileData;
|
||||||
|
link.download = message.fileName;
|
||||||
|
document.body.appendChild(link);
|
||||||
|
link.click();
|
||||||
|
document.body.removeChild(link);
|
||||||
|
}
|
||||||
|
});
|
||||||
} else {
|
} else {
|
||||||
messageContent.innerHTML = `
|
messageContent.innerHTML = `
|
||||||
<strong>${await addressToEmoji(memberAddress)}</strong>: ${message.text}
|
<strong>${await addressToEmoji(message.sender)}</strong>: ${message.text}
|
||||||
<span class="message-time">${message.time}</span>
|
<span class="message-time">${message.time}</span>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
@ -844,45 +861,187 @@ class ChatElement extends HTMLElement {
|
|||||||
|
|
||||||
// Send a file
|
// Send a file
|
||||||
private async sendFile(file: File) {
|
private async sendFile(file: File) {
|
||||||
if (!this.selectedMemberId) return;
|
// Ajouter une vérification de la taille avant la conversion en base64
|
||||||
|
const MAX_FILE_SIZE = 1 * 1024 * 1024; // Réduire à 1MB pour éviter les problèmes de quota
|
||||||
const MAX_FILE_SIZE = 5 * 1024 * 1024;
|
|
||||||
if (file.size > MAX_FILE_SIZE) {
|
if (file.size > MAX_FILE_SIZE) {
|
||||||
alert('File is too large. Maximum size is 5MB');
|
alert('Le fichier est trop volumineux. Taille maximum : 1MB');
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const reader = new FileReader();
|
try {
|
||||||
reader.readAsDataURL(file);
|
const myAddresses = await this.getMemberFromDevice();
|
||||||
|
if (!myAddresses) {
|
||||||
|
throw new Error('No paired member found');
|
||||||
|
}
|
||||||
|
|
||||||
reader.onload = () => {
|
// Compresser l'image si c'est une image
|
||||||
const fileMessage = {
|
let fileData: string;
|
||||||
|
if (file.type.startsWith('image/')) {
|
||||||
|
fileData = await this.compressImage(file);
|
||||||
|
} else {
|
||||||
|
fileData = await this.readFileAsBase64(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Créer un message avec un texte descriptif au lieu du fileData
|
||||||
|
const newMessage = {
|
||||||
id: Date.now(),
|
id: Date.now(),
|
||||||
sender: "4NK",
|
sender: myAddresses[0],
|
||||||
|
text: `Fichier envoyé: ${file.name}`, // Ajouter un texte descriptif
|
||||||
fileName: file.name,
|
fileName: file.name,
|
||||||
fileData: reader.result,
|
time: new Date().toLocaleString('fr-FR'),
|
||||||
time: new Date().toLocaleTimeString([], { hour: '2-digit', minute: '2-digit' }),
|
|
||||||
type: 'file' as const
|
type: 'file' as const
|
||||||
};
|
};
|
||||||
|
|
||||||
messageStore.addMessage(this.selectedMemberId!, fileMessage);
|
// Stocker le fileData séparément
|
||||||
this.messagesMock = messageStore.getMessages();
|
try {
|
||||||
this.loadMemberChat(this.selectedMemberId!);
|
const fileKey = `file_${newMessage.id}`;
|
||||||
|
localStorage.setItem(fileKey, fileData);
|
||||||
|
} catch (storageError) {
|
||||||
|
console.error('Erreur de stockage du fichier:', storageError);
|
||||||
|
alert('Erreur lors du stockage du fichier. Essayez avec un fichier plus petit.');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.selectedMemberId) {
|
||||||
|
messageStore.addMessage(this.selectedMemberId, newMessage);
|
||||||
|
this.messagesMock = messageStore.getMessages();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Récupérer le process_id du parent (conversation)
|
||||||
|
const groupItem = this.shadowRoot?.querySelector('[data-process-id]');
|
||||||
|
const parentProcessId = groupItem?.getAttribute('data-process-id');
|
||||||
|
|
||||||
|
if (!parentProcessId) {
|
||||||
|
throw new Error('Parent process ID not found');
|
||||||
|
}
|
||||||
|
|
||||||
|
const messageTemplate = {
|
||||||
|
process_id: parentProcessId,
|
||||||
|
parent_id: null,
|
||||||
|
description: 'file_message',
|
||||||
|
messages: {
|
||||||
|
state: 'initial',
|
||||||
|
object: {
|
||||||
|
type: 'file',
|
||||||
|
content: fileData,
|
||||||
|
metadata: {
|
||||||
|
created_at: newMessage.time,
|
||||||
|
last_updated: newMessage.time,
|
||||||
|
sender: myAddresses[0],
|
||||||
|
recipient: this.selectedMemberId,
|
||||||
|
fileName: file.name,
|
||||||
|
fileType: file.type
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
roles: {
|
||||||
|
public: {
|
||||||
|
members: [
|
||||||
|
{ sp_addresses: myAddresses },
|
||||||
|
{ sp_addresses: [this.selectedMemberId] }
|
||||||
|
],
|
||||||
|
validation_rules: [
|
||||||
|
{
|
||||||
|
quorum: 0.0,
|
||||||
|
fields: ['description', 'messages'],
|
||||||
|
min_sig_member: 0.0,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
storages: [storageUrl]
|
||||||
|
},
|
||||||
|
owner: {
|
||||||
|
members: [
|
||||||
|
{ sp_addresses: myAddresses },
|
||||||
|
{ sp_addresses: [this.selectedMemberId] }
|
||||||
|
],
|
||||||
|
validation_rules: [
|
||||||
|
{
|
||||||
|
quorum: 1.0,
|
||||||
|
fields: ['description', 'messages'],
|
||||||
|
min_sig_member: 1.0,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
storages: [storageUrl]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
const result = await this.createMessagingProcess(
|
||||||
|
[{ sp_addresses: [this.selectedMemberId!] }],
|
||||||
|
'relay_address',
|
||||||
|
1
|
||||||
|
);
|
||||||
|
|
||||||
|
console.log('Final file message process:', {
|
||||||
|
template: messageTemplate,
|
||||||
|
result: result,
|
||||||
|
timestamp: new Date().toISOString()
|
||||||
|
});
|
||||||
|
|
||||||
const fileInput = this.shadowRoot?.querySelector('#file-input') as HTMLInputElement;
|
const fileInput = this.shadowRoot?.querySelector('#file-input') as HTMLInputElement;
|
||||||
if (fileInput) fileInput.value = '';
|
if (fileInput) fileInput.value = '';
|
||||||
|
|
||||||
// Générer la réponse automatique
|
this.loadMemberChat(this.selectedMemberId!);
|
||||||
|
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
const autoReply = this.generateAutoReply(this.selectedMemberId!);
|
const autoReply = this.generateAutoReply(this.selectedMemberId!);
|
||||||
messageStore.addMessage(this.selectedMemberId!, autoReply);
|
messageStore.addMessage(this.selectedMemberId!, autoReply);
|
||||||
this.messagesMock = messageStore.getMessages();
|
this.messagesMock = messageStore.getMessages();
|
||||||
this.loadMemberChat(this.selectedMemberId!);
|
this.loadMemberChat(this.selectedMemberId!);
|
||||||
|
|
||||||
// Ajouter la notification UNIQUEMENT pour la réponse reçue
|
|
||||||
this.addNotification(this.selectedMemberId!, autoReply);
|
this.addNotification(this.selectedMemberId!, autoReply);
|
||||||
}, 1000);
|
}, 1000);
|
||||||
};
|
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Error sending file:', error);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private async readFileAsBase64(file: File): Promise<string> {
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
const reader = new FileReader();
|
||||||
|
reader.onload = () => resolve(reader.result as string);
|
||||||
|
reader.onerror = reject;
|
||||||
|
reader.readAsDataURL(file);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private async compressImage(file: File): Promise<string> {
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
const img = new Image();
|
||||||
|
const canvas = document.createElement('canvas');
|
||||||
|
const ctx = canvas.getContext('2d');
|
||||||
|
|
||||||
|
img.onload = () => {
|
||||||
|
// Calculer les nouvelles dimensions
|
||||||
|
let width = img.width;
|
||||||
|
let height = img.height;
|
||||||
|
const MAX_WIDTH = 800;
|
||||||
|
const MAX_HEIGHT = 600;
|
||||||
|
|
||||||
|
if (width > height) {
|
||||||
|
if (width > MAX_WIDTH) {
|
||||||
|
height *= MAX_WIDTH / width;
|
||||||
|
width = MAX_WIDTH;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (height > MAX_HEIGHT) {
|
||||||
|
width *= MAX_HEIGHT / height;
|
||||||
|
height = MAX_HEIGHT;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
canvas.width = width;
|
||||||
|
canvas.height = height;
|
||||||
|
ctx?.drawImage(img, 0, 0, width, height);
|
||||||
|
|
||||||
|
// Compression avec qualité réduite
|
||||||
|
resolve(canvas.toDataURL('image/jpeg', 0.7));
|
||||||
|
};
|
||||||
|
|
||||||
|
img.onerror = reject;
|
||||||
|
img.src = URL.createObjectURL(file);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
connectedCallback() {
|
connectedCallback() {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user