217 lines
5.2 KiB
PHP
217 lines
5.2 KiB
PHP
<?php
|
|
|
|
namespace App\Models;
|
|
|
|
use Illuminate\Database\Eloquent\Factories\HasFactory;
|
|
use Illuminate\Database\Eloquent\Model;
|
|
use Illuminate\Support\Collection;
|
|
use Illuminate\Support\Facades\Auth;
|
|
|
|
class System extends Model
|
|
{
|
|
use HasFactory;
|
|
|
|
protected $casts = [
|
|
'last_session' => 'datetime:Y-m-d H:i:s'
|
|
];
|
|
|
|
/* SCOPES */
|
|
|
|
/**
|
|
* Only query active records
|
|
* @todo test false action
|
|
*/
|
|
public function scopeActive($query)
|
|
{
|
|
$uo = Auth::user();
|
|
|
|
return $query
|
|
->when($uo && ! $uo->isAdmin(),function($query) use ($uo) {
|
|
return $query->whereIn('id',$uo->systems->pluck('id'))
|
|
->orWhere($this->getTable().'.active',TRUE);
|
|
},function($query) { $query->where($this->getTable().'.active',TRUE); })
|
|
->orderBy('name');
|
|
}
|
|
|
|
/* RELATIONS */
|
|
|
|
public function addresses()
|
|
{
|
|
return $this->hasMany(Address::class)
|
|
->withTrashed()
|
|
->FTNorder();
|
|
}
|
|
|
|
public function akas()
|
|
{
|
|
return $this->hasMany(Address::class)
|
|
->active();
|
|
}
|
|
|
|
public function mailers()
|
|
{
|
|
return $this->belongsToMany(Mailer::class)
|
|
->withPivot(['last_poll','port','attempts','active']);
|
|
}
|
|
|
|
public function mailer_preferred()
|
|
{
|
|
return $this->mailers()
|
|
->preferred();
|
|
}
|
|
|
|
public function logs()
|
|
{
|
|
return $this->hasMany(SystemLog::class);
|
|
}
|
|
|
|
public function logs_recent()
|
|
{
|
|
return $this->hasMany(SystemLog::class)
|
|
->orderby('created_at','DESC')
|
|
->limit(10);
|
|
}
|
|
|
|
/**
|
|
* Session Passwords for system
|
|
*
|
|
* @return \Illuminate\Database\Eloquent\Relations\BelongsToMany
|
|
*/
|
|
public function sessions()
|
|
{
|
|
return $this->belongsToMany(Zone::class)
|
|
->withPivot(['sespass','pktpass','ticpass','fixpass','zt_ipv4','zt_ipv6','default']);
|
|
}
|
|
|
|
/**
|
|
* If this system is configured as this host
|
|
*
|
|
* @return \Illuminate\Database\Eloquent\Relations\HasOne
|
|
*/
|
|
public function setup()
|
|
{
|
|
return $this->hasOne(Setup::class);
|
|
}
|
|
|
|
public function users()
|
|
{
|
|
return $this->belongsToMany(User::class);
|
|
}
|
|
|
|
/**
|
|
* This system is the ZC for the following zones
|
|
*/
|
|
public function zcs()
|
|
{
|
|
return $this->hasMany(Zone::class);
|
|
}
|
|
|
|
/**
|
|
* Zones a system has addresses for
|
|
*
|
|
* @return \Illuminate\Database\Eloquent\Relations\HasManyThrough
|
|
*/
|
|
public function zones()
|
|
{
|
|
return $this->hasManyThrough(Zone::class,Address::class,'system_id','id','id','zone_id');
|
|
}
|
|
|
|
/* ATTRIBUTES */
|
|
|
|
public function getAccessMethodAttribute(): string
|
|
{
|
|
switch ($this->method) {
|
|
case 23: return sprintf('telnet://%s:%s',$this->address,$this->port);
|
|
case 22: return sprintf('ssh://%s:%s',$this->address,$this->port);
|
|
case 513: return sprintf('rlogin://%s:%s',$this->address,$this->port);
|
|
default:
|
|
return $this->method ? sprintf('%s:%s',$this->address,$this->port) : 'No access method available.';
|
|
}
|
|
}
|
|
|
|
public function getAccessMailerAttribute(): string
|
|
{
|
|
switch (($x=$this->mailer_preferred()->first())?->name) {
|
|
case 'BINKP': return sprintf('binkp://%s:%s',$this->address,$x->pivot->port);
|
|
case 'EMSI': return sprintf('emsi://%s:%s',$this->address,$x->pivot->port);
|
|
default:
|
|
return $x?->name ? sprintf('%s:%s',$this->address,$x->pivot->port) : 'No mailer available.';
|
|
}
|
|
}
|
|
|
|
/* METHODS */
|
|
|
|
public function echoareas()
|
|
{
|
|
return Echoarea::select('echoareas.*')
|
|
->join('address_echoarea',['address_echoarea.echoarea_id'=>'echoareas.id'])
|
|
->join('addresses',['addresses.id'=>'address_echoarea.address_id'])
|
|
->where('addresses.system_id',$this->id);
|
|
}
|
|
|
|
public function fileareas()
|
|
{
|
|
return Filearea::select('fileareas.*')
|
|
->join('address_filearea',['address_filearea.filearea_id'=>'fileareas.id'])
|
|
->join('addresses',['addresses.id'=>'address_filearea.address_id'])
|
|
->where('addresses.system_id',$this->id);
|
|
}
|
|
|
|
/**
|
|
* Return the system name, or role name for the zone
|
|
*
|
|
* @param Address $o
|
|
* @return string
|
|
*/
|
|
public function full_name(Address $o): string
|
|
{
|
|
switch ($o->attributes['role']) {
|
|
case Address::NODE_ZC;
|
|
return sprintf('ZC-%s-%05d',$o->zone->domain->name,$o->zone->zone_id);
|
|
|
|
case Address::NODE_RC;
|
|
return sprintf('RC-%s-%05d',$o->zone->domain->name,$o->region_id);
|
|
|
|
case Address::NODE_NC;
|
|
return sprintf('NC-%s-%05d',$o->zone->domain->name,$o->host_id);
|
|
|
|
case Address::NODE_HC;
|
|
case Address::NODE_ACTIVE;
|
|
default:
|
|
return $this->name;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Return the system's address in the same zone
|
|
* This function can filter based on the address type needed.
|
|
*
|
|
* @param Zone $o
|
|
* @param int $type
|
|
* @return Collection
|
|
*/
|
|
public function match(Zone $o,int $type=(Address::NODE_NC|Address::NODE_HC|Address::NODE_ACTIVE|Address::NODE_PVT|Address::NODE_POINT)): Collection
|
|
{
|
|
return $this->addresses
|
|
->where('zone_id',$o->id)
|
|
->filter(function($item) use ($type) {
|
|
return $item->role & $type;
|
|
});
|
|
}
|
|
|
|
/**
|
|
* Parse the addresses and return which ones are in my zones
|
|
*
|
|
* @param \Illuminate\Database\Eloquent\Collection $addresses
|
|
* @param int $type
|
|
* @return Collection
|
|
*/
|
|
public function inMyZones(Collection $addresses,int $type=(Address::NODE_HC|Address::NODE_ACTIVE|Address::NODE_PVT|Address::NODE_POINT)): Collection
|
|
{
|
|
$myzones = $this->addresses->pluck('zone_id')->unique();
|
|
|
|
return $addresses->filter(function($item) use ($myzones,$type) {
|
|
return ($item->role & $type) && ($myzones->search($item->zone_id) !== FALSE);
|
|
});
|
|
}
|
|
} |