Passa al contenuto principale

Schema DB reg

🎯 Cosa fa​

Definisce il persistence layer dell'anagrafica aziende e delle sue estensioni. Il dominio ha 15 tabelle totali, tutte documentate in questa pagina.

πŸ—ΊοΈ Tabelle (15)​

Core anagrafica (4)​

TabellaRuolo
reg.companiesAnagrafica aziende (cliente / fornitore)
reg.companyContactsCanali di contatto (email, phone, pec)
reg.companyLocationsSedi del cliente con label descrittiva e locationTag di classificazione
reg.headquartersSedi TrainingHub / ente formatore (indipendente dai clienti)

Classificazione (3)​

TabellaRuolo
reg.companySubcategoriesSottocategorie custom di raggruppamento (FK da companies.companySubcategoryId)
reg.companyTagsN:N azienda ↔ tag di sistema
reg.companiesPreferencesPreferenze booleane per azienda (record presente = preferenza attiva)

Ruoli esterni (4)​

TabellaRuolo
reg.externalRsppsAnagrafica RSPP esterni (name, email, phone, notes)
reg.companiesExternalRsppsIncarichi azienda ↔ RSPP con startDate / endDate
reg.territorialReferentsAnagrafica RLS territoriali β€” Rappresentanti dei Lavoratori per la Sicurezza designati a livello territoriale (art. 48 D.Lgs. 81/08). Stessa struttura di externalRspps.
reg.companiesTerritorialReferentsIncarichi azienda ↔ RLS territoriale con startDate / endDate

Anagrafiche lookup (4)​

TabellaRuolo
reg.organizersEnti organizzatori (PK: slug)
reg.ccnlContratti Collettivi (PK: id int) β€” FK da companies.ccnlId
reg.legalNaturesForme societarie (PK: code) β€” FK da companies.legalNatureCode
reg.academicQualificationsTitoli di studio

πŸ”— Relazioni​

Referenze esterne:

  • reg.companies.atecoCode β†’ job.atecoCodes(code)
  • reg.companies.riskLevelId β†’ job.riskLevel(id)
  • reg.companies.legalNatureCode β†’ reg.legalNatures(code) (fuori scope)
  • reg.companies.ccnlId β†’ reg.ccnl(id) (fuori scope)
  • reg.companies.companySubcategoryId β†’ reg.companySubcategories(id) (fuori scope)
  • reg.companyContacts.contactTypeTag β†’ oss.tags(slug)
  • reg.companyLocations.locationTag β†’ oss.tags(slug)

HEADQUARTERS Γ¨ standalone: nessuna FK in uscita o in entrata da altre tabelle reg core.

πŸ—‚οΈ Dettaglio tabelle​

reg.companies​

Anagrafica aziende clienti e fornitori.

  • PK: id (GUID)
  • FK principali:
    • atecoCode β†’ job.atecoCodes(code) (codice ATECO)
    • riskLevelId β†’ job.riskLevel(id) (livello di rischio)
    • legalNatureCode β†’ reg.legalNatures(code) (forma societaria, nullable)
    • ccnlId β†’ reg.ccnl(id) (nullable)
    • companySubcategoryId β†’ reg.companySubcategories(id) (nullable)
  • Indice filtered: IX_companies_active WHERE active = 1 INCLUDE (id, ccnlId, riskLevelId, companyName) β€” ottimizza le query su aziende attive
  • Flag: isSupplier, isCustomer, active, viesValidated, riskLevelOverride, allowDirectCommunication, imported
  • Campi indirizzo: strutturati + formattedAddress + coordinate GPS
  • Legacy: imported, originalName β€” marcati "da rimuovere una volta completate le importazioni iniziali"

reg.companyContacts​

Canali di contatto (email, telefono, PEC) di un'azienda.

  • PK: id
  • FK: companyId β†’ reg.companies(id), contactTypeTag β†’ oss.tags(slug)
  • Campi: contactValue (testo libero), notes (libere)
  • Nota dominio: non modella persone, solo canali. Il nominativo della persona va eventualmente nelle note.

reg.companyLocations​

Sedi di un'azienda cliente: include sia le sedi operative sia i luoghi di lavoro (cantieri, postazioni, ecc.). Una sola tabella, classificazione via tag.

  • PK: id
  • FK: companyId β†’ reg.companies(id), locationTag β†’ oss.tags(slug) (NOT NULL)
  • Campi: label (NOT NULL, etichetta descrittiva, es. "Sede di Milano" o "Cantiere via Roma") + indirizzo strutturato + formattedAddress + coordinate + notes
  • Tag iniziale: location_operating ("Sede operativa"). Altri tag possono essere introdotti in oss.tags per classificare luoghi di lavoro specifici (es. cantieri).

reg.headquarters​

Sedi del formatore TrainingHub.

  • PK: id
  • FK: nessuna in uscita (standalone)
  • Campi: label + indirizzo strutturato + coordinate
  • Nota dominio: globale per tenant; non ha concetto di proprietario. Se TrainingHub diventasse multi-tenant con piΓΉ enti formatori la tabella andrebbe estesa con organizerSlug o simile.

πŸ—‚οΈ Dettaglio tabelle estensioni​

Classificazione​

reg.companySubcategories​

Anagrafica delle sottocategorie custom.

  • PK: id
  • Campi: label (obbligatorio)
  • FK in entrata: reg.companies.companySubcategoryId β†’ id

reg.companyTags​

N:N azienda ↔ tag di sistema.

  • PK: id
  • FK: companyId β†’ reg.companies(id), tagSlug β†’ oss.tags(slug)
  • Tag da oss.tags: anagrafica centralizzata condivisa con contatti e locations.

reg.companiesPreferences​

Preferenze booleane.

  • PK composita: (companyId, preferenceTag)
  • FK: companyId β†’ reg.companies(id), preferenceTag β†’ oss.tags(slug)
  • Nessun campo valore: presenza del record = preferenza attiva.

Ruoli esterni​

reg.externalRspps / reg.territorialReferents​

Schema identico per le due anagrafiche:

  • PK: id
  • Campi: name (obbligatorio), email, phone, notes

reg.companiesExternalRspps / reg.companiesTerritorialReferents​

Schema identico per le due tabelle di associazione (solo la FK cambia nome):

  • PK: id
  • FK: companyId β†’ reg.companies(id), externalRsppId β†’ reg.externalRspps(id) (o territorialReferentId β†’ reg.territorialReferents(id))
  • Campi: startDate (obbligatoria), endDate (nullable = incarico in corso), notes
  • Nessun vincolo di unicitΓ  o sovrapposizione: piΓΉ incarichi attivi per la stessa azienda contemporaneamente sono tecnicamente permessi.

Anagrafiche lookup​

reg.organizers​

  • PK: slug (stringa, URL-friendly) β€” referenziato da molti altri moduli
  • Modifiche allo slug rompono le FK esterne: non rinominare dopo che Γ¨ stato usato

reg.ccnl​

  • PK: id (int identity)
  • Campi tipici: code, label
  • FK in entrata: reg.companies.ccnlId

reg.legalNatures​

  • PK: code (stringa)
  • Campi tipici: label (descrizione estesa)
  • FK in entrata: reg.companies.legalNatureCode

reg.academicQualifications​

  • PK: id
  • Campi tipici: label
  • Usata principalmente nel dominio lavoratori (job) per titoli di studio dei worker.

πŸ“ File chiave​

  • TrainingHub.Database/reg/Tables/*.sql β€” 16 tabelle
  • TrainingHub.Database/TrainingHub.Database.sqlproj β€” progetto SQL
  • Indici espliciti: solo IX_companies_active filtered (vedi sopra)

⚠️ Debito tecnico​

  • imported / originalName legacy. Flag marcati come "da rimuovere". Pianificare rimozione dopo conclusione delle importazioni iniziali.
  • headquarters singleton implicito. Se multi-tenant futuro per enti formatori, aggiungere colonna proprietario.
  • Nessun check constraint su formati critici: vatCode, fiscalCode, sdiCode, zipCode. La validazione Γ¨ demandata alla UI/service layer, che oggi non la fa rigorosamente. Possibile inserimento di dati inconsistenti via import o altri path.
  • FK verso tabelle fuori scope. legalNatureCode, ccnlId, companySubcategoryId tutti nullable: aziende create senza questi campi non sono bloccate. Valutare se in alcuni contesti (es. cliente per fatturazione) almeno legalNatureCode vada reso obbligatorio.
  • companies.logo come VARBINARY(MAX). Dimensioni potenzialmente grandi in riga β†’ pesa su row size e query. Valutare spostamento su blob storage esterno o filestream.
  • Indici minimi su FK. Esiste IX_companies_active filtered, ma non ci sono indici espliciti su companyId delle tabelle figlie (companyContacts, companyLocations). Valutare aggiunta per query "tutti i contatti/sedi di un'azienda".

πŸ”— Vedi anche​