TreeMap
무료 오픈소스 디스크 사용량 시각화 도구로, 사각형 트리맵·중복 파일 탐색·디스크 가득 예측·정리 시 파일을 휴지통으로만 이동한다
아직 감지된 업데이트가 없습니다. GitHub 릴리스가 나오면 여기에 보입니다.
개인 계정의 공개 저장소 소유자는 GitHub로 로그인해 운영자를 확인하고 소개를 직접 관리할 수 있습니다. 관리자 승인은 필요하지 않습니다.
로그인한 뒤 확인 파일을 만들어 이 저장소의 기본 브랜치에 30분 안에 커밋해 주세요. 다른 브랜치나 포크의 파일은 인정하지 않습니다. 파일을 올린 뒤 아래에서 확인하면 관리자 승인 없이 관리할 수 있습니다. 자격을 유지하려면 파일을 남겨 두세요.
로그인이 필요하면 로그인 화면으로 이동합니다. 로그인 후 이곳으로 돌아와 원하는 확인 버튼을 다시 눌러 주세요.
프로젝트 폴더에서 /nomorevibe verify를 실행하면 소유권을 확인하고 소개를 직접 관리할 수 있습니다.
1분 만에 확인하기README 전체를 불러오는 중입니다. 아래는 저장된 발췌입니다.
Plateforme SaaS multi-tenant permettant à toute organisation — entreprise, association, établissement, collectivité — de recenser des besoins, sonder un public et gérer des inscriptions à des événements. L'architecture, les conventions et les risques acceptés sont documentés dans CLAUDE.md. Vérifier avant tout commit ce que la CI exige : .env.example liste ces variables sans aucune valeur. Les tests base de données tournent sur PGlite (PostgreSQL en processus) : les migrations réelles sont rejouées, `auth.uid(README 전문 보기 ↗
Plateforme SaaS multi-tenant permettant à toute organisation — entreprise, association, établissement, collectivité — de recenser des besoins, sonder un public et gérer des inscriptions à des événements.
L'architecture, les conventions et les risques acceptés sont documentés dans CLAUDE.md.
npm ci
cp .env.example .env.local # puis renseigner les variables (voir ci-dessous)
npm run dev
Vérifier avant tout commit ce que la CI exige :
npm run verify
| Variable | Obligatoire | Rôle |
|---|---|---|
NEXT_PUBLIC_SUPABASE_URL | oui | URL du projet Supabase. |
NEXT_PUBLIC_SUPABASE_ANON_KEY | oui | Clé anonyme, soumise au RLS. |
SUPABASE_SERVICE_ROLE_KEY | oui | Secret serveur. Contourne le RLS : jamais exposé au client, jamais committé. |
NEXT_PUBLIC_SITE_URL | oui | URL publique canonique (liens des emails, ICS). |
RESEND_API_KEY | non | Envoi d'emails transactionnels. Absente → aucun email, aucune action métier en échec. |
EMAIL_FROM | non | Expéditeur sur un domaine vérifié (SPF/DKIM/DMARC). |
KV_REST_API_URL / KV_REST_API_TOKEN | non | Rate-limit distribué (Vercel KV ou Upstash Redis). |
SENTRY_DSN | non | Observabilité. Absente → les erreurs restent dans les logs structurés. |
CRON_SECRET | non | Secret partagé protégeant les routes /api/cron/*. |
NOMINATIM_USER_AGENT | non | User-Agent conforme pour le proxy de géocodage. |
.env.example liste ces variables sans aucune valeur.
npm run test # tous les projets
npx vitest run --project unit # logique pure
npx vitest run --project integration # routes API sur PGlite
npx vitest run --project rls # isolation multi-tenant (bloquant)
npx vitest run --project a11y # axe-core sur les écrans publics
Les tests base de données tournent sur PGlite (PostgreSQL en processus) :
les migrations réelles sont rejouées, auth.uid() et les rôles Supabase sont
émulés. Aucun Docker, aucun projet Supabase, aucun secret réel nécessaire.
| Élément | État |
|---|---|
| Projet Supabase | spankio (qmhjckioehsiduongadk), PostgreSQL 17.6, région eu-west-2 |
| Migrations | Les 25 migrations sont appliquées ; l'historique distant correspond exactement aux fichiers de supabase/migrations (supabase db push ne rejoue rien) |
pg_cron | Actif. Purges planifiées : réponses expirées à 3 h 17, sondages supprimés à 3 h 37 |
| Storage | Buckets survey-banners (3 Mio) et organisation-logos (1 Mio), 4 policies chacun, types d'image restreints |
| Projet Vercel | spankio, relié à grittdoof/spankio, déploiement automatique sur main |
| Domaine public | spankio.vpstrat.com (rattaché le 8 septembre 2026). spankio.vercel.app continue de répondre : les liens déjà diffusés ne cassent pas |
| Protection Vercel | SSO activée en mode « tous les déploiements sauf les domaines personnalisés ». Vérifié en requête anonyme : spankio.vpstrat.com ET spankio.vercel.app répondent 200 — la protection ne couvre donc en pratique que les déploiements de préversion |
| Actions GitHub | checkout@v7, setup-node@v7 — les v4 tournaient sur Node 20, déprécié par les exécuteurs |
| Node | 24.20.0 en CI (.nvmrc) et 24.x sur Vercel. Si le réglage Vercel change, mettre .nvmrc à jour : la CI ne le lit pas depuis Vercel |
Variables d'environnement Vercel (Settings → Environment Variables). Sans elles, les pages publiques s'affichent mais toute action touchant la base échoue — le middleware referme les espaces protégés et journalise l'erreur.
| Variable | Valeur |
|---|---|
NEXT_PUBLIC_SUPABASE_URL | https://qmhjckioehsiduongadk.supabase.co |
NEXT_PUBLIC_SUPABASE_ANON_KEY | Clé anon du projet (Supabase → Settings → API Keys) |
SUPABASE_SERVICE_ROLE_KEY | Clé service_role du même écran — secret, à ne coller que dans Vercel |
NEXT_PUBLIC_SITE_URL | https://spankio.vpstrat.com — sans barre oblique finale |
Puis, dans Supabase → Authentication → URL Configuration, régler Site URL
et ajouter <URL publique>/auth/callback aux Redirect URLs, sinon les
liens de confirmation et de réinitialisation ne reviendront pas sur le site.
Changer de domaine se fait par cette seule variable. Aucune URL absolue
n'est écrite en base ni codée en dur : l'adresse publique d'un formulaire,
le lien du fichier .ics, celui de la note d'agenda et le bloc de partage
sont tous composés à partir d'elle. Deux précautions :
NEXT_PUBLIC_* est
figée dans le paquet client au build ;<URL>/auth/callback dans la liste Supabase le temps
que les courriels déjà envoyés expirent, sinon leurs liens de
confirmation reviendront sur une adresse refusée.Ce qui ne se met PAS à jour rétroactivement : les rendez-vous déjà ajoutés
à un agenda par un répondant contiennent l'ancienne adresse dans leur note.
Elle reste valide tant que spankio.vercel.app répond.
Premier super administrateur. Créer un compte par /inscription, puis
l'élever une seule fois depuis l'éditeur SQL Supabase :
update public.profiles
set role = 'super_admin', status = 'active', organisation_id = null
where email = '[email protected]';
Le trigger anti-escalade autorise cette écriture parce qu'aucun JWT n'est présent (contexte serveur de confiance) ; aucun compte ne peut se l'accorder par l'application.
Le module event ajoute à un formulaire une date, un lieu, un organisateur et
une bannière, et alimente le fichier iCalendar ainsi que les liens d'itinéraire
proposés aux répondants.
Le bucket survey-banners est public en lecture et contraint en écriture,
côté Storage :
| Contrainte | Valeur | Vérifié |
|---|---|---|
| Taille | 3 Mio | 413 EntityTooLarge au-delà |
| Types | image/jpeg, image/png, image/webp, image/avif | 415 InvalidMimeType pour un SVG |
| Dossier | {organisation_id}/{survey_id}/ | RLS sur storage.objects |
Le SVG est exclu délibérément : c'est un document XML pouvant porter du script, servi depuis une origine publique. Les trois contrôles ont été éprouvés sur le projet réel, pas seulement déclarés.
L'image part directement du navigateur vers Storage, avec la session de
l'utilisateur : elle ne transite par aucune route Next. Le chemin enregistré
dans surveys.banner_path est ensuite revérifié côté serveur — le bucket étant
public, un chemin non contrôlé permettrait d'afficher le fichier d'un autre
tenant.
Le bucket organisation-logos est public en lecture et contraint en
écriture. Un logo peut aussi être désigné par un lien externe, sans dépôt.
| Contrainte | Valeur | Vérifié |
|---|---|---|
| Taille | 1 Mio | 413 EntityTooLarge au-delà |
| Types | image/png, image/jpeg, image/webp, image/avif | 415 InvalidMimeType pour un SVG |
| Dossier | {organisation_id}/ | RLS, réservé à l'administrateur de l'organisation |
| Dépôt anonyme | refusé | 403 new row violates row-level security policy |
Les trois contrôles ont été éprouvés sur le projet réel. Le SVG est exclu pour la même raison que sur les bannières : c'est un document XML pouvant porter du script, servi depuis une origine publique.
L'URL enregistrée dans organisations.logo_url est revérifiée côté serveur :
un lien externe passe tel quel, une URL de notre bucket doit désigner le
dossier de l'organisation qui l'enregistre.
À savoir pour un lien externe : le site qui héberge l'image voit passer
l'adresse IP de chaque répondant qui ouvre un formulaire. L'interface le dit à
l'organisation, qui décide. C'est aussi ce qui empêchera de restreindre
img-src à l'étape 9 (risque R1).
Toute recherche d'adresse passe par /api/admin/geocode. Le navigateur ne
contacte jamais Nominatim directement : la politique d'usage d'OSM impose un
User-Agent identifiant l'application et plafonne à une requête par seconde
pour l'application entière, et relayer évite de livrer à un tiers l'adresse IP
de chaque personne qui saisit une adresse.
NOMINATIM_USER_AGENT (facultative) impose le User-Agent ; sans elle, il
est composé à partir de NEXT_PUBLIC_SITE_URL. Renseignez-la avec une
adresse de contact avant toute mise en service à volume réel : c'est ce que
la politique d'OSM attend d'une application tierce.KV_REST_API_URL /
KV_REST_API_TOKEN. Sans store, il n'est tenu que par instance — voir le
risque R12 de CLAUDE.md.Les tuiles sont chargées par Leaflet depuis tile.openstreetmap.org ; aucune
iframe n'est utilisée. À l'étape 9, la politique de sécurité de contenu devra
autoriser tile.openstreetmap.org en img-src et ne pas autoriser
openstreetmap.org en frame-src.
Les procédures de déploiement (Vercel + Supabase CLI), de préproduction, de
configuration Resend/DMARC, d'activation de pg_cron, ainsi que le runbook de
sauvegarde/restauration et d'exercice du droit à l'effacement, seront rédigés
aux étapes correspondantes du plan (voir § 8 de CLAUDE.md).
Réglages de plateforme. Renseigner platform_settings (éditeur,
hébergeur, DPO, autorité de contrôle, adresse d'exercice des droits,
notifications_email). Les pages légales affichent « Non renseigné » pour
tout champ vide — elles ne fabriquent aucune valeur.
Région et politique de confidentialité. Le projet Supabase est en
eu-west-2, c'est-à-dire Londres (Royaume-Uni), alors que la politique
de confidentialité écrite dans l'application annonce un hébergement en
Union européenne. Deux issues, au choix : recréer le projet en eu-west-3
(Paris) ou eu-central-1 (Francfort) — les migrations étant idempotentes,
l'opération prend quelques minutes sur une base vide — ou corriger le
tableau des sous-traitants pour mentionner le Royaume-Uni et sa décision
d'adéquation. Ne pas laisser les deux en contradiction.
Resend, KV et Sentry : RESEND_API_KEY, EMAIL_FROM (domaine vérifié
avec SPF/DKIM/DMARC), KV_REST_API_URL / KV_REST_API_TOKEN, SENTRY_DSN.
Toutes optionnelles : leur absence dégrade proprement (aucun email envoyé,
rate-limit réduit au garde-fou mémoire), jamais silencieusement.