Fixes for nodelist importing

This commit is contained in:
Deon George 2021-06-26 10:34:49 +10:00
parent 17a44a0945
commit aa06296963
8 changed files with 115 additions and 43 deletions

View File

@ -9,12 +9,14 @@ use App\Models\{Address,Domain,Zone};
class DomainController extends Controller class DomainController extends Controller
{ {
public const NODE_ZC = 1<<1; // Zone public const NODE_ACTIVE = 0; // Active
public const NODE_RC = 1<<2; // Region public const NODE_ZC = 1<<0; // Zone
public const NODE_NC = 1<<3; // Host public const NODE_RC = 1<<1; // Region
public const NODE_HC = 1<<4; // Hub public const NODE_NC = 1<<2; // Host
public const NODE_PVT = 1<<5; // Pvt public const NODE_HC = 1<<3; // Hub
public const NODE_DOWN = 1<<6; // Down public const NODE_PVT = 1<<4; // Pvt
public const NODE_HOLD = 1<<5; // Hold
public const NODE_DOWN = 1<<6; // Down
// http://ftsc.org/docs/frl-1002.001 // http://ftsc.org/docs/frl-1002.001
public const NUMBER_MAX = 0x7fff; public const NUMBER_MAX = 0x7fff;

View File

@ -190,7 +190,7 @@ class SystemController extends Controller
$this->authorize('admin',$o); $this->authorize('admin',$o);
$request->validate([ $request->validate([
'name' => 'required|min:3|unique:systems,name,'.($o->exists ? $o->id : 0), 'name' => 'required|min:3',
'location' => 'required|min:3', 'location' => 'required|min:3',
'sysop' => 'required|min:3', 'sysop' => 'required|min:3',
'address' => 'nullable|regex:/^(?!:\/\/)(?=.{1,255}$)((.{1,63}\.){1,127}(?![0-9]*$)[a-z0-9-]+\.?)$/i', 'address' => 'nullable|regex:/^(?!:\/\/)(?=.{1,255}$)((.{1,63}\.){1,127}(?![0-9]*$)[a-z0-9-]+\.?)$/i',

View File

@ -58,11 +58,12 @@ class ImportNodelist implements ShouldQueue
Log::debug(sprintf('%s:Processing [%d] lines.',static::LOGKEY,$lines)); Log::debug(sprintf('%s:Processing [%d] lines.',static::LOGKEY,$lines));
$fh = fopen($file,'r'); $fh = fopen($file,'r');
$c =0; $p = $c =0;
$region = NULL; $region = NULL;
$host = NULL; $host = NULL;
$hub_id = NULL; $hub_id = NULL;
$zo = NULL;
while (! feof($fh)) { while (! feof($fh)) {
$line = stream_get_line($fh, 0, "\r\n"); $line = stream_get_line($fh, 0, "\r\n");
@ -89,17 +90,20 @@ class ImportNodelist implements ShouldQueue
switch ($fields[0]) { switch ($fields[0]) {
case 'Zone': $zone = $fields[1]; case 'Zone': $zone = $fields[1];
// We ignore the Zone entries, since they are dynamically created. // We ignore the Zone entries, since they are dynamically created.
$zo = Zone::firstOrCreate([ Zone::unguard();
'zone_id'=>$zone, $zo = Zone::firstOrNew([
'domain_id'=>$this->do->id, 'zone_id'=>$zone,
]); 'domain_id'=>$this->do->id,
'active'=>TRUE,
]);
Zone::reguard();
$region = 0; $region = 0;
$host = 0; $host = $fields[1];
$hub_id = NULL; $hub_id = NULL;
$role = DomainController::NODE_ZC; $role = DomainController::NODE_ZC;
continue 2; break;
case 'Region': case 'Region':
$region = $fields[1]; $region = $fields[1];
@ -118,6 +122,7 @@ class ImportNodelist implements ShouldQueue
continue 2; continue 2;
case 'Hub': case 'Hub':
$node = $fields[1];
$role = DomainController::NODE_HC; $role = DomainController::NODE_HC;
break; break;
@ -128,6 +133,12 @@ class ImportNodelist implements ShouldQueue
break; break;
case 'Hold':
$node = $fields[1];
$role = DomainController::NODE_HOLD;
break;
case 'Down': case 'Down':
$node = $fields[1]; $node = $fields[1];
$role = DomainController::NODE_DOWN; $role = DomainController::NODE_DOWN;
@ -150,7 +161,6 @@ class ImportNodelist implements ShouldQueue
Address::unguard(); Address::unguard();
$ao = Address::firstOrNew([ $ao = Address::firstOrNew([
'zone_id' => $zo->id,
'region_id' => $region, 'region_id' => $region,
'host_id' => $host, 'host_id' => $host,
'node_id' => $node, 'node_id' => $node,
@ -164,36 +174,52 @@ class ImportNodelist implements ShouldQueue
$role = NULL; $role = NULL;
if ($ao->exists)
Log::debug(sprintf('%s:Processing existing address [%s]',self::LOGKEY,$ao->ftn));
$sysop = trim(str_replace('_',' ',$fields[4]));
$system = trim(str_replace('_',' ',$fields[2]));
$location = trim(str_replace('_',' ',$fields[3]));
// Get the System // Get the System
if ($ao->system_id && (($ao->system->sysop === str_replace('_',' ',$fields[4])) || ($ao->system->name !== str_replace('_',' ',$fields[2])))) { if ($ao->system_id && (($ao->system->sysop === $sysop) || ($ao->system->name === $system))) {
$so = $ao->system; $so = $ao->system;
// If the sysop name is different // If the sysop name is different
if ($so->sysop !== str_replace('_',' ',$fields[4])) { if ($so->sysop !== $sysop) {
$so->sysop = str_replace('_',' ',$fields[4]); Log::debug(sprintf('%s:Sysop Name changed for BBS [%s:%s] from [%s] to [%s]',
$so->location = str_replace('_',' ',$fields[3]); self::LOGKEY,$so->id,$so->name,$so->sysop,$sysop));
$so->sysop = $sysop;
// We have the same name has changed. // We have the same name has changed.
} else { } elseif ($so->name !== $system) {
$so->name = str_replace('_',' ',$fields[2]); Log::debug(sprintf('%s:System Name changed for BBS [%s:%s] to [%s]',
$so->location = str_replace('_',' ',$fields[3]); self::LOGKEY,$so->id,$so->name,$system));
$so->name = $system;
} }
// We'll search and see if we already have that system // We'll search and see if we already have that system
} else { } else {
$so = System::where('name',str_replace('_',' ',$fields[2])) $so = System::where('name',$system)
->where('sysop',str_replace('_',' ',$fields[4])) ->where('sysop',$sysop)
->firstOrNew(); ->firstOrNew();
$so->name = str_replace('_',' ',$fields[2]); if ($so->exists)
$so->sysop = str_replace('_',' ',$fields[4]); Log::debug(sprintf('%s:Linking address [%d:%d/%d] to [%s:%s]',self::LOGKEY,$zo->zone_id,$ao->host_id,$ao->node_id,$so->id,$so->name));
$so->location = str_replace('_',' ',$fields[3]); else
Log::debug(sprintf('%s:New System [%s] with address [%d:%d/%d]',self::LOGKEY,$system,$zo->zone_id,$ao->host_id,$ao->node_id));
$so->name = $system;
$so->sysop = $sysop;
$so->active = TRUE; $so->active = TRUE;
if (! $so->exists) if (! $so->exists)
$so->notes = sprintf('Created by Nodelist Import: %d',$this->no->id); $so->notes = sprintf('Created by Nodelist Import: %d',$this->no->id);
} }
$so->location = $location;
/* /*
if (! in_array($fields[5],['-Unpublished-'])) if (! in_array($fields[5],['-Unpublished-']))
$so->phone = $fields[5]; $so->phone = $fields[5];
@ -204,6 +230,19 @@ class ImportNodelist implements ShouldQueue
// Save the system record // Save the system record
$so->save(); $so->save();
// If our zone didnt exist, we'll create it with this system
if (! $zo->exists) {
$zo->system_id = $so->id;
$zo->save();
}
$ao->zone_id = $zo->id;
if ($ao->getDirty()) {
dd($ao);
$p++;
}
try { try {
$so->addresses()->save($ao); $so->addresses()->save($ao);
if ($role == DomainController::NODE_HC) if ($role == DomainController::NODE_HC)
@ -226,6 +265,6 @@ class ImportNodelist implements ShouldQueue
if ($this->deletefile and $c) if ($this->deletefile and $c)
unlink($file); unlink($file);
Log::info(sprintf('%s:Records Updated: %d',self::LOGKEY,$c)); Log::info(sprintf('%s:Updated %d records from %d systems',self::LOGKEY,$p,$c));
} }
} }

View File

@ -9,7 +9,7 @@ class Nodelist extends Model
protected $dates = ['date']; protected $dates = ['date'];
protected $fillable = ['date','domain_id']; protected $fillable = ['date','domain_id'];
public const definitions = ['Zone','Region','Host','Hub','Pvt','Down']; public const definitions = ['Zone','Region','Host','Hub','Pvt','Hold','Down'];
/* RELATIONS */ /* RELATIONS */

View File

@ -47,7 +47,7 @@
<td>{{ $oo->name }}</td> <td>{{ $oo->name }}</td>
<td>{{ $oo->active ? 'YES' : 'NO' }}</td> <td>{{ $oo->active ? 'YES' : 'NO' }}</td>
<td>{{ $oo->dnsdomain }}</td> <td>{{ $oo->dnsdomain }}</td>
<td>{{ join(', ',$oo->zones->pluck('zone_id')->toArray()) }}</td> <td>{{ join(', ',$oo->zones->pluck('zone_id')->sort()->toArray()) }}</td>
</tr> </tr>
@endforeach @endforeach
</tbody> </tbody>

View File

@ -55,13 +55,12 @@
<div id="collapse_systems" class="accordion-collapse collapse" aria-labelledby="systems" data-bs-parent="#accordion_homepage"> <div id="collapse_systems" class="accordion-collapse collapse" aria-labelledby="systems" data-bs-parent="#accordion_homepage">
<div class="accordion-body"> <div class="accordion-body">
<p>The following systems are members of this network.</p> <p>The following systems are members of this network.</p>
<table class="table monotable"> <table class="table monotable" id="network">
<thead> <thead>
<tr> <tr>
<th>System</th> <th>System</th>
<th>Sysop</th> <th>Sysop</th>
<th>Location</th> <th>Location</th>
<th>Role</th>
<th>Address</th> <th>Address</th>
<th>Last Seen</th> <th>Last Seen</th>
</tr> </tr>
@ -74,7 +73,6 @@
<td>{{ sprintf('ZC-%s-%05d',$oz->domain->name,$oz->zone_id) }}</td> <td>{{ sprintf('ZC-%s-%05d',$oz->domain->name,$oz->zone_id) }}</td>
<td>{{ $oz->system->sysop }}</td> <td>{{ $oz->system->sysop }}</td>
<td>{{ $oz->system->location }}</td> <td>{{ $oz->system->location }}</td>
<td>Zone</td>
<td>{{ $oz->zone_id }}:0/0.0<span>@</span>{{ $oz->domain->name }}</td> <td>{{ $oz->zone_id }}:0/0.0<span>@</span>{{ $oz->domain->name }}</td>
<td>-</td> <td>-</td>
</tr> </tr>
@ -82,20 +80,18 @@
@foreach ($oz->addresses()->active()->FTNorder()->whereNull('hub_id')->with(['system','zone.domain'])->get() as $ao) @foreach ($oz->addresses()->active()->FTNorder()->whereNull('hub_id')->with(['system','zone.domain'])->get() as $ao)
@if ($ao->role == 'Host') @if ($ao->role == 'Host')
<tr> <tr>
<td>{{ sprintf('NC-%s-%05d',$oz->domain->name,$ao->host_id) }}</td> <td>{{ sprintf('NC-%s-%05d',$oz->domain->name,$ao->host_id) }} <span class="float-end"><small>[{{ $ao->id }}]</small></span></td>
<td>{{ $ao->system->sysop }}</td> <td>{{ $ao->system->sysop }}</td>
<td>{{ $ao->system->location }}</td> <td>{{ $ao->system->location }}</td>
<td>{{ $ao->role }}</td>
<td>{{ $oz->zone_id }}:{{ $ao->host_id }}/0.0<span>@</span>{{ $oz->domain->name }}</td> <td>{{ $oz->zone_id }}:{{ $ao->host_id }}/0.0<span>@</span>{{ $oz->domain->name }}</td>
<td>-</td> <td>-</td>
</tr> </tr>
@endif @endif
<tr> <tr>
<td>{{ $ao->system->full_name($ao) }}</td> <td>{{ $ao->system->full_name($ao) }} <span class="float-end"><small>[{{ $ao->id }}]</small></span></td>
<td>{{ $ao->system->sysop }}</td> <td>{{ $ao->system->sysop }}</td>
<td>{{ $ao->system->location }}</td> <td>{{ $ao->system->location }}</td>
<td>{{ $ao->role }}</td>
<td>{{ $ao->ftn }}</td> <td>{{ $ao->ftn }}</td>
<td>-</td> <td>-</td>
</tr> </tr>
@ -104,9 +100,9 @@
@if ($ao->role == 'Hub') @if ($ao->role == 'Hub')
@foreach ($oz->addresses()->active()->FTNorder()->where('hub_id',$ao->id)->with(['system','zone.domain'])->get() as $aoo) @foreach ($oz->addresses()->active()->FTNorder()->where('hub_id',$ao->id)->with(['system','zone.domain'])->get() as $aoo)
<tr> <tr>
<td>{{ $aoo->system->full_name($aoo) }}</td> <td>{{ $aoo->system->full_name($aoo) }} <span class="float-end"><small>[{{ $aoo->id }}]</small></span></td>
<td>{{ $aoo->system->sysop }}</td> <td>{{ $aoo->system->sysop }}</td>
<td>{{ $ao->system->location }}</td> <td>{{ $aoo->system->location }}</td>
<td>{{ $aoo->role }}</td> <td>{{ $aoo->role }}</td>
<td>{{ $aoo->ftn }}</td> <td>{{ $aoo->ftn }}</td>
<td>-</td> <td>-</td>
@ -140,3 +136,38 @@
</div> </div>
</div> </div>
@endsection @endsection
@section('page-scripts')
<link type="text/css" rel="stylesheet" href="https://cdn.datatables.net/1.10.25/css/dataTables.bootstrap5.min.css" media="screen" >
<link type="text/css" rel="stylesheet" href="{{ asset('plugin/dataTables/dataTables.bootstrap5.css') }}" media="screen">
<script type="text/javascript" src="https://cdn.datatables.net/1.10.25/js/jquery.dataTables.min.js"></script>
<script type="text/javascript" src="https://cdn.datatables.net/rowgroup/1.1.2/js/dataTables.rowGroup.min.js"></script>
<script type="text/javascript" src="https://cdn.datatables.net/1.10.25/js/dataTables.bootstrap5.min.js"></script>
<script type="text/javascript">
$('table tr').click(function() {
var href = $(this).find('a').attr('href');
if (href)
window.location = href;
});
$('#network').DataTable({
paging: true,
pageLength: 25,
searching: true,
order: [
[3,'asc'],
],
/*
columnDefs: [
{
targets: [5,6],
visible: false,
}
],
*/
});
</script>
@append

View File

@ -56,7 +56,7 @@
<span class="input-group-text"><i class="bi bi-laptop-fill"></i></span> <span class="input-group-text"><i class="bi bi-laptop-fill"></i></span>
<select class="form-select @error('system_id') is-invalid @enderror" id="system" name="system_id" required @cannot('admin',$o)disabled @endcannot> <select class="form-select @error('system_id') is-invalid @enderror" id="system" name="system_id" required @cannot('admin',$o)disabled @endcannot>
<option value="">&nbsp;</option> <option value="">&nbsp;</option>
@foreach (\App\Models\System::active()->cursor() as $oo) @foreach (\App\Models\System::active()->orderBy('name')->cursor() as $oo)
<option value="{{ $oo->id }}" @if(old('system_id',$o->system_id)==$oo->id)selected @endif>{{ $oo->name }}</option> <option value="{{ $oo->id }}" @if(old('system_id',$o->system_id)==$oo->id)selected @endif>{{ $oo->name }}</option>
@endforeach @endforeach
</select> </select>

View File

@ -38,12 +38,12 @@
</thead> </thead>
<tbody> <tbody>
@foreach (\App\Models\Zone::with(['domain'])->get() as $oo) @foreach (\App\Models\Zone::orderBy('zone_id')->with(['domain','addresses'])->get() as $oo)
<tr> <tr>
<td>{{ $oo->domain->name }}</td> <td>{{ $oo->domain->name }}</td>
<td><a href="{{ url('ftn/zone/addedit',[$oo->id]) }}">{{ $oo->zone_id }}</a></td> <td><a href="{{ url('ftn/zone/addedit',[$oo->id]) }}">{{ $oo->zone_id }}</a></td>
<td>{{ $oo->active ? 'YES' : 'NO' }}</td> <td>{{ $oo->active ? 'YES' : 'NO' }}</td>
<td>-</td> <td>{{ $oo->addresses->count() }}</td>
</tr> </tr>
@endforeach @endforeach
</tbody> </tbody>