93 lines
3.5 KiB
JavaScript
93 lines
3.5 KiB
JavaScript
(function(){
|
|
const runtime = window.MAILCOW_PLUGIN_RUNTIME;
|
|
if (!runtime) return;
|
|
|
|
function formatSize(bytes) {
|
|
if (!bytes) return '0 B';
|
|
const units = ['B','KB','MB','GB'];
|
|
let value = bytes;
|
|
let i = 0;
|
|
while (value >= 1024 && i < units.length - 1) {
|
|
value /= 1024;
|
|
i += 1;
|
|
}
|
|
return value.toFixed(value >= 10 || i === 0 ? 0 : 1) + ' ' + units[i];
|
|
}
|
|
|
|
runtime.registerMount('owncloud-attach','mail.compose.attachments','attachments-panel', async (target, context) => {
|
|
const panel = document.createElement('section');
|
|
panel.className = 'owncloud-panel';
|
|
panel.innerHTML = '<h3>Attach from ownCloud</h3><div class="owncloud-muted">Loading your files…</div>';
|
|
target.innerHTML = '';
|
|
target.appendChild(panel);
|
|
|
|
const [meRes, filesRes] = await Promise.all([
|
|
fetch(context.apiBase + '/me', { credentials: 'include' }),
|
|
fetch(context.apiBase + '/files?path=/', { credentials: 'include' })
|
|
]);
|
|
const me = await meRes.json();
|
|
const filesPayload = await filesRes.json();
|
|
const items = filesPayload.items || [];
|
|
|
|
panel.innerHTML = '';
|
|
const title = document.createElement('h3');
|
|
title.textContent = 'Attach from ownCloud';
|
|
const info = document.createElement('div');
|
|
info.className = 'owncloud-muted';
|
|
info.textContent = 'Signed in as ' + ((me.user && me.user.displayName) || 'Mailcow user') + ' • Source: ' + (me.user && me.user.owncloudBaseUrl || 'ownCloud');
|
|
|
|
const toolbar = document.createElement('div');
|
|
toolbar.className = 'owncloud-toolbar';
|
|
const attachButton = document.createElement('button');
|
|
attachButton.className = 'owncloud-attach-button';
|
|
attachButton.textContent = 'Attach selected';
|
|
attachButton.disabled = true;
|
|
|
|
const status = document.createElement('div');
|
|
status.className = 'owncloud-status';
|
|
|
|
const list = document.createElement('ul');
|
|
list.className = 'owncloud-list';
|
|
const selected = new Set();
|
|
|
|
items.forEach((item) => {
|
|
const li = document.createElement('li');
|
|
const left = document.createElement('label');
|
|
left.style.display = 'flex';
|
|
left.style.gap = '.5rem';
|
|
left.style.alignItems = 'center';
|
|
const checkbox = document.createElement('input');
|
|
checkbox.type = 'checkbox';
|
|
checkbox.addEventListener('change', () => {
|
|
if (checkbox.checked) selected.add(item.id); else selected.delete(item.id);
|
|
attachButton.disabled = selected.size === 0;
|
|
});
|
|
const text = document.createElement('span');
|
|
text.innerHTML = '<strong>' + item.name + '</strong><div class="owncloud-meta">' + item.path + ' • ' + formatSize(item.size) + '</div>';
|
|
left.appendChild(checkbox);
|
|
left.appendChild(text);
|
|
li.appendChild(left);
|
|
list.appendChild(li);
|
|
});
|
|
|
|
attachButton.addEventListener('click', async () => {
|
|
const files = items.filter((item) => selected.has(item.id));
|
|
const res = await fetch(context.apiBase + '/select', {
|
|
method: 'POST',
|
|
credentials: 'include',
|
|
headers: { 'Content-Type': 'application/json' },
|
|
body: JSON.stringify({ files })
|
|
});
|
|
const payload = await res.json();
|
|
status.textContent = 'Queued ' + payload.selectedCount + ' file(s) for Mailcow attachment upload via ' + payload.mode + '.';
|
|
});
|
|
|
|
toolbar.appendChild(attachButton);
|
|
panel.appendChild(title);
|
|
panel.appendChild(info);
|
|
panel.appendChild(toolbar);
|
|
panel.appendChild(list);
|
|
panel.appendChild(status);
|
|
});
|
|
})();
|