homeos/database/seeders/DemoHomeSeeder.php

115 lines
4.6 KiB
PHP

<?php
namespace Database\Seeders;
use App\Models\Device;
use App\Models\DeviceState;
use App\Models\Entity;
use App\Models\Room;
use Illuminate\Database\Seeder;
use Illuminate\Support\Str;
/**
* Mock smart-home so the dashboard has real (fake) state to render before hardware exists
* (handoff §13.2 — "mock first, real hardware after"). Deliberately includes fault
* conditions (an offline device, low batteries, an open window) to exercise the warnings.
*
* Re-run any time: `php artisan db:seed --class=Database\\Seeders\\DemoHomeSeeder`.
* Online state is a snapshot (last_seen_at = now); Phase 3 (MQTT) keeps it live.
*/
class DemoHomeSeeder extends Seeder
{
public function run(): void
{
// Online mock devices have no last_seen (treated as reachable, so the demo never
// rots); the one offline device carries a stale timestamp.
$onlineSeen = null;
$stale = now()->subHours(2);
// room => devices. Each device: [name, model, online, entities[]]
// entity: [type, key, name, state]
$home = [
'Wohnzimmer' => [
['Deckenlicht', 'Shelly Plus 1PM', true, [
['light', 'light:0', 'Deckenlicht', ['on' => true]],
['power', 'power:0', 'Verbrauch', ['watts' => 42]],
]],
['Stehlampe', 'Shelly Plug S', true, [
['switch', 'switch:0', 'Stehlampe', ['on' => false]],
]],
],
'Küche' => [
['Arbeitslicht', 'Shelly Plus 1', true, [
['light', 'light:0', 'Arbeitslicht', ['on' => true]],
]],
['Fenstersensor Küche', 'Shelly BLU Window', true, [
['contact', 'contact:0', 'Fenster', ['open' => false]],
['battery', 'battery:0', 'Batterie', ['percent' => 88]],
]],
],
'Schlafzimmer' => [
['Nachttischlampe', 'Shelly Plug S', true, [
['switch', 'switch:0', 'Nachttischlampe', ['on' => false]],
]],
['Fenstersensor Schlafzimmer', 'Shelly BLU Window', true, [
['contact', 'contact:0', 'Fenster', ['open' => true]], // warning: open
['battery', 'battery:0', 'Batterie', ['percent' => 14]], // warning: low
]],
],
'Flur' => [
['Flurlicht', 'Shelly Plus 1', true, [
['light', 'light:0', 'Flurlicht', ['on' => false]],
]],
['Türsensor Haustür', 'Shelly BLU Door', true, [
['contact', 'contact:0', 'Haustür', ['open' => false]],
['battery', 'battery:0', 'Batterie', ['percent' => 9]], // warning: low
]],
],
'Büro' => [
['Schreibtischlampe', 'Shelly Plug S', true, [
['switch', 'switch:0', 'Schreibtischlampe', ['on' => true]],
['power', 'power:0', 'Verbrauch', ['watts' => 12]],
]],
['Drucker-Steckdose', 'Shelly Plug S', false, [ // warning: offline
['switch', 'switch:0', 'Drucker', ['on' => false]],
]],
],
];
$sort = 0;
foreach ($home as $roomName => $devices) {
$room = Room::updateOrCreate(
['name' => $roomName],
['icon' => 'rooms', 'sort' => $sort++],
);
foreach ($devices as [$deviceName, $model, $online, $entities]) {
$device = Device::updateOrCreate(
['room_id' => $room->id, 'name' => $deviceName],
[
'vendor' => 'Shelly',
'model' => $model,
'protocol' => 'mqtt',
'config' => ['mqtt_prefix' => 'shelly-'.Str::slug($deviceName)],
'status' => 'active',
'demo' => true,
'last_seen_at' => $online ? $onlineSeen : $stale,
],
);
foreach ($entities as [$type, $key, $entityName, $state]) {
$entity = Entity::updateOrCreate(
['device_id' => $device->id, 'key' => $key],
['type' => $type, 'name' => $entityName],
);
DeviceState::updateOrCreate(
['entity_id' => $entity->id],
['state' => $state],
);
}
}
}
}
}