Harmonics Trait

The Harmonics trait is the foundation of Laravel Chorus. When added to your Eloquent models, it automatically tracks changes and enables real-time synchronization to connected clients.

Basic Usage

Adding the Trait

Add the Harmonics trait to any model you want to synchronize:
<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Model;
use Pixelsprout\LaravelChorus\Traits\Harmonics;

class Post extends Model
{
    use Harmonics;
    
    protected $fillable = [
        'title',
        'content',
        'status',
        'author_id'
    ];
}
That’s it! Your model will now automatically track changes and broadcast them to connected clients.

What the Trait Does

When you add the Harmonics trait, it automatically:
  1. Registers event listeners for model create, update, and delete operations
  2. Creates harmonic records in the harmonics table for each change
  3. Broadcasts changes via WebSocket to connected clients
  4. Provides synchronization methods for frontend integration

Defining Sync Fields

By default, no fields are synchronized for security. You must explicitly define which fields to sync using one of these methods: Define sync fields using a protected property:
class Post extends Model
{
    use Harmonics;
    
    protected $syncFields = [
        'id',           // Always include the primary key
        'title',
        'content',
        'status',
        'author_id',
        'created_at',
        'updated_at'
    ];
}

Method 2: Method-Based

Define sync fields using a method for simple dynamic logic:
class Post extends Model
{
    use Harmonics;
    
    public function syncFields(): array
    {
        return [
            'id',
            'title',
            'content',
            'status',
            'author_id',
            'created_at',
            'updated_at'
        ];
    }
}

Method 3: Dynamic Sync Fields

Override the getSyncFields() method for complex dynamic logic:
class Post extends Model
{
    use Harmonics;
    
    public function getSyncFields(): array
    {
        $fields = [
            'id',
            'title',
            'status',
            'created_at',
            'updated_at'
        ];
        
        // Include content only for published posts
        if ($this->status === 'published') {
            $fields[] = 'content';
        }
        
        // Include author info for authenticated users
        if (auth()->check()) {
            $fields[] = 'author_id';
        }
        
        return $fields;
    }
}
Security First: Only include fields that are safe to expose to clients. Never sync sensitive information like passwords, API keys, or internal system data.

Field Selection Best Practices

Include These Fields

Always include:
  • Primary key (id)
  • User-visible data (title, name, description)
  • Status/state fields (status, is_active)
  • Relationships IDs (user_id, category_id)
  • Timestamps (created_at, updated_at)

Exclude These Fields

Never include:
  • Passwords or authentication tokens
  • Internal system fields (internal_notes)
  • Sensitive personal information (ssn, credit_card)
  • Large binary data (file_content)
  • Admin-only fields (admin_notes)

Example: User Model

class User extends Model
{
    use Harmonics;
    
    // Safe fields for client synchronization
    protected $syncFields = [
        'id',
        'name',
        'email',           // OK if users can see each other's emails
        'avatar_url',
        'is_online',
        'last_seen_at',
        'created_at',
        'updated_at'
        // 'password' - NEVER include
        // 'remember_token' - NEVER include
        // 'email_verified_at' - Usually not needed
    ];
}

Automatic Change Detection

The Harmonics trait automatically detects changes using Laravel’s model events:

Create Operations

$post = Post::create([
    'title' => 'My New Post',
    'content' => 'Hello World!',
    'status' => 'draft'
]);
// ✅ Automatically creates a harmonic with operation: 'create'

Update Operations

$post = Post::find(1);
$post->update(['status' => 'published']);
// ✅ Automatically creates a harmonic with operation: 'update'

Delete Operations

$post = Post::find(1);
$post->delete();
// ✅ Automatically creates a harmonic with operation: 'delete'

Bulk Operations

Important: Bulk operations like Post::where('status', 'draft')->update(['status' => 'published']) do not trigger model events and will not be synchronized automatically.For bulk operations, you’ll need to handle synchronization manually or iterate through individual models.

Advanced Configuration

Custom Primary Keys

For models with non-standard primary keys:
class Post extends Model
{
    use Harmonics;
    
    protected $primaryKey = 'post_uuid';
    public $incrementing = false;
    protected $keyType = 'string';
    
    protected $syncFields = [
        'post_uuid',  // Include your custom primary key
        'title',
        'content'
    ];
}

Testing Your Configuration

Manual Testing

Create a test record and verify harmonics are created:
php artisan tinker
// Create a test record
$post = App\Models\Post::create([
    'title' => 'Test Post',
    'content' => 'This is a test',
    'status' => 'published',
    'author_id' => 1
]);

// Check if a harmonic was created
$harmonic = \Pixelsprout\LaravelChorus\Models\Harmonic::latest()->first();
echo $harmonic->toJson(JSON_PRETTY_PRINT);

Debug Command

Use the built-in debug command to verify your configuration:
php artisan chorus:debug
This will show:
  • Currently connected channels
  • Active user IDs

Common Issues and Solutions

Next Steps

Now that your model has the Harmonics trait:
Your model is now ready for real-time synchronization! Continue with Sync Fields to learn advanced field configuration techniques.