325 lines
8.4 KiB
PHP
325 lines
8.4 KiB
PHP
<?php
|
|
|
|
namespace App\Models;
|
|
|
|
use Illuminate\Database\Eloquent\Factories\HasFactory;
|
|
use Illuminate\Database\Eloquent\Model;
|
|
use Illuminate\Database\Eloquent\SoftDeletes;
|
|
|
|
class AnagraficaCondominiale extends Model
|
|
{
|
|
use HasFactory, SoftDeletes;
|
|
|
|
protected $table = 'anagrafica_condominiale';
|
|
|
|
protected $fillable = [
|
|
'amministratore_id',
|
|
'codice_univoco',
|
|
'tipo_soggetto',
|
|
'cognome',
|
|
'nome',
|
|
'denominazione',
|
|
'codice_fiscale',
|
|
'partita_iva',
|
|
'data_nascita',
|
|
'luogo_nascita',
|
|
'provincia_nascita',
|
|
'sesso',
|
|
'indirizzo_residenza',
|
|
'cap_residenza',
|
|
'citta_residenza',
|
|
'provincia_residenza',
|
|
'nazione_residenza',
|
|
'domicilio_diverso',
|
|
'indirizzo_domicilio',
|
|
'cap_domicilio',
|
|
'citta_domicilio',
|
|
'provincia_domicilio',
|
|
'nazione_domicilio',
|
|
'stato',
|
|
'note',
|
|
'google_contact_id',
|
|
'ultima_sincronizzazione_google'
|
|
];
|
|
|
|
/**
|
|
* Boot del modello per generazione automatica codice
|
|
*/
|
|
protected static function boot()
|
|
{
|
|
parent::boot();
|
|
|
|
static::creating(function ($model) {
|
|
if (empty($model->codice_univoco)) {
|
|
$model->codice_univoco = self::generateUniqueCode();
|
|
}
|
|
});
|
|
}
|
|
|
|
/**
|
|
* Genera un codice univoco di 8 caratteri con prefisso ANA
|
|
*/
|
|
private static function generateUniqueCode()
|
|
{
|
|
do {
|
|
$code = 'ANA' . strtoupper(substr(str_shuffle('0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'), 0, 5));
|
|
} while (self::where('codice_univoco', $code)->exists());
|
|
|
|
return $code;
|
|
}
|
|
|
|
protected $casts = [
|
|
'data_nascita' => 'date',
|
|
'ultima_sincronizzazione_google' => 'datetime',
|
|
'domicilio_diverso' => 'boolean',
|
|
'created_at' => 'datetime',
|
|
'updated_at' => 'datetime'
|
|
];
|
|
|
|
/**
|
|
* Relazione con i contatti
|
|
*/
|
|
public function contatti()
|
|
{
|
|
return $this->hasMany(ContattoAnagrafica::class);
|
|
}
|
|
|
|
/**
|
|
* Relazione con i diritti reali
|
|
*/
|
|
public function dirittiReali()
|
|
{
|
|
return $this->hasMany(DirittoReale::class);
|
|
}
|
|
|
|
/**
|
|
* Relazione con i contratti di locazione
|
|
*/
|
|
public function contrattiLocazione()
|
|
{
|
|
return $this->hasMany(ContrattoLocazione::class);
|
|
}
|
|
|
|
/**
|
|
* Relazione con DettaglioRipartizioneSpese
|
|
*/
|
|
public function dettagliRipartizioneSpese()
|
|
{
|
|
return $this->hasMany(DettaglioRipartizioneSpese::class);
|
|
}
|
|
|
|
/**
|
|
* Relazione con Rate
|
|
*/
|
|
public function rate()
|
|
{
|
|
return $this->hasMany(Rata::class);
|
|
}
|
|
|
|
/**
|
|
* Scope per anagrafica attiva
|
|
*/
|
|
public function scopeAttivi($query)
|
|
{
|
|
return $query->where('stato', 'attivo');
|
|
}
|
|
|
|
/**
|
|
* Scope per tipo soggetto
|
|
*/
|
|
public function scopeByTipo($query, $tipo)
|
|
{
|
|
return $query->where('tipo_soggetto', $tipo);
|
|
}
|
|
|
|
/**
|
|
* Scope per persone fisiche
|
|
*/
|
|
public function scopePersoneFisiche($query)
|
|
{
|
|
return $query->where('tipo_soggetto', 'persona_fisica');
|
|
}
|
|
|
|
/**
|
|
* Scope per persone giuridiche
|
|
*/
|
|
public function scopePersoneGiuridiche($query)
|
|
{
|
|
return $query->where('tipo_soggetto', 'persona_giuridica');
|
|
}
|
|
|
|
/**
|
|
* Accessor per il nome completo
|
|
*/
|
|
public function getNomeCompletoAttribute()
|
|
{
|
|
if ($this->tipo_soggetto === 'persona_giuridica') {
|
|
return $this->denominazione;
|
|
}
|
|
|
|
return trim($this->nome . ' ' . $this->cognome);
|
|
}
|
|
|
|
/**
|
|
* Accessor per codice anagrafica (compatibilità)
|
|
*/
|
|
public function getCodiceAnagraficaAttribute()
|
|
{
|
|
return $this->codice_univoco;
|
|
}
|
|
|
|
/**
|
|
* Accessor per l'indirizzo completo di residenza
|
|
*/
|
|
public function getIndirizzoResidenzaCompletoAttribute()
|
|
{
|
|
$indirizzo = $this->indirizzo_residenza;
|
|
if ($this->cap_residenza) {
|
|
$indirizzo .= ', ' . $this->cap_residenza;
|
|
}
|
|
if ($this->citta_residenza) {
|
|
$indirizzo .= ' ' . $this->citta_residenza;
|
|
}
|
|
if ($this->provincia_residenza) {
|
|
$indirizzo .= ' (' . $this->provincia_residenza . ')';
|
|
}
|
|
return $indirizzo;
|
|
}
|
|
|
|
/**
|
|
* Accessor per l'indirizzo completo di domicilio
|
|
*/
|
|
public function getIndirizzoDomicilioCompletoAttribute()
|
|
{
|
|
if (!$this->domicilio_diverso) {
|
|
return $this->indirizzo_residenza_completo;
|
|
}
|
|
|
|
$indirizzo = $this->indirizzo_domicilio;
|
|
if ($this->cap_domicilio) {
|
|
$indirizzo .= ', ' . $this->cap_domicilio;
|
|
}
|
|
if ($this->citta_domicilio) {
|
|
$indirizzo .= ' ' . $this->citta_domicilio;
|
|
}
|
|
if ($this->provincia_domicilio) {
|
|
$indirizzo .= ' (' . $this->provincia_domicilio . ')';
|
|
}
|
|
return $indirizzo;
|
|
}
|
|
|
|
/**
|
|
* Metodo per ottenere tutti i contatti per tipo (placeholder - table doesn't exist yet)
|
|
*/
|
|
public function getContattiByTipo($tipo)
|
|
{
|
|
// TODO: Implementare quando sarà creata la tabella contatti
|
|
return collect();
|
|
}
|
|
|
|
/**
|
|
* Metodo per verificare se è attivo
|
|
*/
|
|
public function isAttivo()
|
|
{
|
|
return $this->stato === 'attivo';
|
|
}
|
|
|
|
/**
|
|
* Metodo per ottenere le unità immobiliari di proprietà
|
|
*/
|
|
public function getUnitaImmobiliariProprietario()
|
|
{
|
|
return UnitaImmobiliare::whereHas('dirittiReali', function ($query) {
|
|
$query->where('anagrafica_condominiale_id', $this->id)
|
|
->where('tipo_diritto', 'proprieta')
|
|
->whereNull('data_fine');
|
|
})->get();
|
|
}
|
|
|
|
/**
|
|
* Metodo per ottenere le unità immobiliari in locazione
|
|
*/
|
|
public function getUnitaImmobiliariInquilino()
|
|
{
|
|
return UnitaImmobiliare::whereHas('contrattiLocazione', function ($query) {
|
|
$query->where('anagrafica_condominiale_id', $this->id)
|
|
->where('stato', 'attivo')
|
|
->whereDate('data_inizio', '<=', now())
|
|
->where(function ($q) {
|
|
$q->whereNull('data_fine')
|
|
->orWhereDate('data_fine', '>=', now());
|
|
});
|
|
})->get();
|
|
}
|
|
|
|
/**
|
|
* Metodo per verificare se è un proprietario
|
|
*/
|
|
public function isProprietario()
|
|
{
|
|
return $this->dirittiReali()
|
|
->where('tipo_diritto', 'proprieta')
|
|
->whereNull('data_fine')
|
|
->exists();
|
|
}
|
|
|
|
/**
|
|
* Metodo per verificare se è un inquilino
|
|
*/
|
|
public function isInquilino()
|
|
{
|
|
return $this->contrattiLocazione()
|
|
->where('stato', 'attivo')
|
|
->whereDate('data_inizio', '<=', now())
|
|
->where(function ($query) {
|
|
$query->whereNull('data_fine')
|
|
->orWhereDate('data_fine', '>=', now());
|
|
})
|
|
->exists();
|
|
}
|
|
|
|
/**
|
|
* Relazione con amministratore
|
|
*/
|
|
public function amministratore()
|
|
{
|
|
return $this->belongsTo(Amministratore::class);
|
|
}
|
|
|
|
/**
|
|
* Metodo per ottenere il bilancio delle spese per questa anagrafica
|
|
*/
|
|
public function getBilancioSpese($annoGestione = null)
|
|
{
|
|
$anno = $annoGestione ?? date('Y');
|
|
|
|
$dettagliRipartizione = $this->dettagliRipartizioneSpese()
|
|
->whereHas('ripartizioneSpese', function($q) use ($anno) {
|
|
$q->whereYear('data_ripartizione', $anno)
|
|
->where('stato', 'confermata');
|
|
})
|
|
->with('ripartizioneSpese.voceSpesa')
|
|
->get();
|
|
|
|
return [
|
|
'totale_spese' => $dettagliRipartizione->sum('quota_finale'),
|
|
'totale_proprietario' => $dettagliRipartizione->sum('importo_proprietario'),
|
|
'totale_inquilino' => $dettagliRipartizione->sum('importo_inquilino'),
|
|
'numero_voci' => $dettagliRipartizione->count(),
|
|
'dettagli' => $dettagliRipartizione
|
|
];
|
|
}
|
|
|
|
/**
|
|
* Metodo per ottenere le rate in scadenza
|
|
*/
|
|
public function getRateInScadenza($giorni = 30)
|
|
{
|
|
return $this->rate()
|
|
->inScadenza($giorni)
|
|
->with(['pianoRateizzazione', 'unitaImmobiliare'])
|
|
->get();
|
|
}
|
|
}
|