Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 26 additions & 0 deletions assets/js/admin.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,28 @@
var $ = function (id) { return document.getElementById(id); };
var gate = $('adminGate');
var app = $('adminApp');
var SA_ROLE_HINT_KEY = 'sa_role_hint_v1';

function writeAdminRoleHint(userId, isAdmin) {
if (typeof localStorage === 'undefined' || !userId) return;
try {
localStorage.setItem(
SA_ROLE_HINT_KEY,
JSON.stringify({
user_id: String(userId),
is_admin: isAdmin === true,
updated_at: Date.now()
})
);
} catch (e) {}
}

function clearAdminRoleHint() {
if (typeof localStorage === 'undefined') return;
try {
localStorage.removeItem(SA_ROLE_HINT_KEY);
} catch (e) {}
}

function showFatal(msg) {
gate.classList.remove('hidden');
Expand Down Expand Up @@ -94,6 +116,7 @@
if (gateDecided) return;
gateDecided = true;
if (!session) {
clearAdminRoleHint();
window.location.replace('/admin-login');
return;
}
Expand All @@ -107,11 +130,13 @@
return;
}
if (a.data !== true) {
writeAdminRoleHint(session && session.user ? session.user.id : '', false);
sb.auth.signOut().then(function () {
window.location.replace('/admin-login?raison=non-admin');
});
return;
}
writeAdminRoleHint(session.user.id, true);
$('adminWho').textContent = session.user.email || '';
gate.classList.add('hidden');
app.classList.remove('hidden');
Expand Down Expand Up @@ -173,6 +198,7 @@
}
} catch (e2) {}
}
clearAdminRoleHint();
clearAdminAuthLocalStorage();
try {
sb.auth.signOut({ scope: 'global' });
Expand Down
17 changes: 17 additions & 0 deletions assets/js/espace-dashboard.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -21,10 +21,25 @@ const sb =
: null;

const $ = (id) => document.getElementById(id);
const SA_ROLE_HINT_KEY = 'sa_role_hint_v1';
const escapeHtml = (s) =>
String(s == null ? '' : s).replace(/&/g, '&amp;').replace(/</g, '&lt;')
.replace(/>/g, '&gt;').replace(/"/g, '&quot;');

function writeAdminRoleHint(userId, isAdmin) {
if (typeof localStorage === 'undefined' || !userId) return;
try {
localStorage.setItem(
SA_ROLE_HINT_KEY,
JSON.stringify({
user_id: String(userId),
is_admin: isAdmin === true,
updated_at: Date.now(),
})
);
} catch (_e) {}
}

function fmtDate(d) {
if (!d) return '';
try {
Expand Down Expand Up @@ -237,9 +252,11 @@ async function boot() {
try {
const { data: isAdm, error: admErr } = await sb.rpc('is_admin');
if (!admErr && isAdm === true) {
writeAdminRoleHint(session.user.id, true);
window.location.replace('/admin');
return;
}
if (!admErr) writeAdminRoleHint(session.user.id, false);
} catch (_e) {
/* reste sur l'espace personnel */
}
Expand Down
98 changes: 72 additions & 26 deletions assets/js/espace-etudiant.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,29 @@ function clearAllGoTrueAuthLocalStorage() {
} catch (e) {}
}

var SA_ROLE_HINT_KEY = 'sa_role_hint_v1';

function writeAdminRoleHint(userId, isAdmin) {
if (typeof localStorage === 'undefined' || !userId) return;
try {
localStorage.setItem(
SA_ROLE_HINT_KEY,
JSON.stringify({
user_id: String(userId),
is_admin: isAdmin === true,
updated_at: Date.now(),
})
);
} catch (e) {}
}

function clearAdminRoleHint() {
if (typeof localStorage === 'undefined') return;
try {
localStorage.removeItem(SA_ROLE_HINT_KEY);
} catch (e) {}
}

/* Après navigation post-déconnexion : purge synchrone AVANT createClient(),
sinon la session peut être relue depuis localStorage encore présent. */
(function espaceEarlyPostLogoutCleanup() {
Expand Down Expand Up @@ -80,22 +103,28 @@ function redirectAfterAuth(sb) {
home = window.location.origin + '/';
}
} catch (e0) {}
var user = null;
return sb.auth
.getSession()
.then(function (sessRes) {
var u = sessRes && sessRes.data && sessRes.data.session && sessRes.data.session.user;
if (u) return syncUserSiteContextRow(sb, u);
return Promise.resolve();
})
.then(function () {
user = sessRes && sessRes.data && sessRes.data.session && sessRes.data.session.user;
return sb.rpc('is_admin');
})
.then(function (a) {
if (!a.error && a.data === true) {
writeAdminRoleHint(user && user.id, true);
window.location.replace('/admin');
} else {
window.location.replace(home);
return true;
}
if (!a.error && user && user.id) {
writeAdminRoleHint(user.id, false);
}
if (user) return syncUserSiteContextRow(sb, user).then(function () { return false; });
return false;
})
.then(function (adminRedirected) {
if (adminRedirected === true) return;
window.location.replace(home);
})
.catch(function () {
window.location.replace(home);
Expand Down Expand Up @@ -817,26 +846,42 @@ if (pageId === 'dashboard') {
return;
}
var u = s.user;
var um = u.user_metadata || {};
var persona = um.espace_persona;
if (!persona || ['cameroun', 'belgique_etudiant', 'travailleur', 'visiteur'].indexOf(persona) === -1) {
persona = null;
try {
var ps = sessionStorage.getItem('sa_espace_persona');
if (ps && ['cameroun', 'belgique_etudiant', 'travailleur', 'visiteur'].indexOf(ps) !== -1) {
persona = ps;
var showStudentIdentity = function () {
var um = u.user_metadata || {};
var persona = um.espace_persona;
if (!persona || ['cameroun', 'belgique_etudiant', 'travailleur', 'visiteur'].indexOf(persona) === -1) {
persona = null;
try {
var ps = sessionStorage.getItem('sa_espace_persona');
if (ps && ['cameroun', 'belgique_etudiant', 'travailleur', 'visiteur'].indexOf(ps) !== -1) {
persona = ps;
}
} catch (ePs) {}
if (!persona) persona = 'cameroun';
}
var meta = um.full_name || '';
var display = meta.trim();
if (!display) {
if (persona === 'visiteur') display = 'Invité(e)';
else display = 'Membre';
}
if (nameEl) nameEl.textContent = display;
if (emailEl) emailEl.textContent = u.email || '';
};

sb.rpc('is_admin')
.then(function (a) {
if (!a.error && a.data === true) {
writeAdminRoleHint(u.id, true);
window.location.replace('/admin');
return;
}
} catch (ePs) {}
if (!persona) persona = 'cameroun';
}
var meta = um.full_name || '';
var display = meta.trim();
if (!display) {
if (persona === 'visiteur') display = 'Invité(e)';
else display = 'Membre';
}
if (nameEl) nameEl.textContent = display;
if (emailEl) emailEl.textContent = u.email || '';
if (!a.error) writeAdminRoleHint(u.id, false);
showStudentIdentity();
})
.catch(function () {
showStudentIdentity();
});
});
}

Expand Down Expand Up @@ -866,6 +911,7 @@ if (pageId === 'dashboard') {
}
})
.then(function () {
clearAdminRoleHint();
clearSupabaseAuthStorageForUrl(getConfig().SUPABASE_URL);
clearAllGoTrueAuthLocalStorage();
try {
Expand Down
30 changes: 29 additions & 1 deletion assets/js/sa-nav-session.js
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,33 @@
return getPersistedSupabaseAuth() != null;
}

var SA_ROLE_HINT_KEY = 'sa_role_hint_v1';

function readRoleHint() {
if (typeof localStorage === 'undefined') return null;
try {
var raw = localStorage.getItem(SA_ROLE_HINT_KEY);
if (!raw) return null;
var parsed = JSON.parse(raw);
if (!parsed || typeof parsed !== 'object') return null;
return parsed;
} catch (e) {
return null;
}
}

function isAdminHintForUser(user) {
if (!user || !user.id) return false;
var hint = readRoleHint();
if (!hint) return false;
return hint.user_id === user.id && hint.is_admin === true;
}

function resolveDashboardHref(defaultHref, auth) {
if (auth && isAdminHintForUser(auth.user)) return '/admin';
return defaultHref;
}

function escapeHtml(s) {
return String(s)
.replace(/&/g, '&amp;')
Expand Down Expand Up @@ -139,9 +166,10 @@
document.querySelectorAll('[data-sa-profile-slot]').forEach(function (slot) {
var href = slot.getAttribute('data-sa-dashboard-href');
if (!href) return;
var displayHref = resolveDashboardHref(href, auth);
var variant = slot.getAttribute('data-sa-profile-variant') || 'desktop';
if (show) {
slot.innerHTML = buildLinkHtml(href, variant, displayLabel);
slot.innerHTML = buildLinkHtml(displayHref, variant, displayLabel);
if (variant === 'desktop') {
slot.className = 'lg:flex items-center min-w-0';
} else if (variant === 'mobile') {
Expand Down