Skip to content

Feature/offline mode#343

Merged
from2001 merged 4 commits intodevelopfrom
feature/standalone_mode
Feb 15, 2026
Merged

Feature/offline mode#343
from2001 merged 4 commits intodevelopfrom
feature/standalone_mode

Conversation

@from2001
Copy link
Collaborator

@from2001 from2001 commented Feb 15, 2026

This pull request introduces a new "offline mode" to the NetSync system, allowing the network synchronization components to operate without a server for local testing. This is achieved by introducing an IConnectionManager interface, an OfflineConnectionManager implementation, and updating the core managers to support this abstraction. The changes also include logic to handle variable and RPC synchronization locally in offline mode, and expose a new option in the Unity inspector.

Offline Mode and Connection Abstraction:

  • Added the IConnectionManager interface to abstract network connection management, and refactored all network-related managers (NetworkVariableManager, RPCManager, TransformSyncManager, and NetSyncManager) to depend on this interface instead of the concrete ConnectionManager class.
  • Introduced OfflineConnectionManager, a no-op implementation of IConnectionManager for use in offline mode, allowing the system to simulate a connection without a server.
  • Modified NetSyncManager to select between ConnectionManager and OfflineConnectionManager based on a new _offlineMode serialized field, and to expose IsOfflineMode for use by other components.

Offline Mode Logic in Managers:

  • Updated NetworkVariableManager and RPCManager to handle variable changes and RPC calls locally (without network round-trips) when in offline mode, ensuring correct event firing and state updates.
  • Added MarkInitialSyncComplete() to NetworkVariableManager and logic in NetSyncManager to immediately assign a client number and complete initial sync in offline mode.

Editor and Inspector Improvements:

  • Exposed the _offlineMode option in the Unity inspector and updated the editor property order to include it, allowing users to enable offline mode for testing.

These changes make it possible to test and use NetSync features locally without requiring a server, greatly improving development workflow and testability.

hacha and others added 3 commits February 12, 2026 19:59
Prepare for standalone mode by decoupling consumers from the concrete
ConnectionManager. All internal managers (TransformSyncManager,
RPCManager, NetworkVariableManager) and NetSyncManager now depend on
the IConnectionManager interface instead. No behavioral changes.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Allow content developers to test with NetSyncManager/NetSyncAvatar
without running a server. Enable via Advanced Options > Standalone Mode
in the inspector. In this mode:
- StandaloneConnectionManager provides a no-op IConnectionManager
- Client number is immediately set to 1
- Network variables are stored and read locally with change events
- RPCs are looped back to self
- Transform sending is silently dropped

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR adds an offline/standalone-style mode to NetSync so core sync features can run without a server, primarily for local testing, by selecting a no-op connection manager and exposing the option in the Unity inspector.

Changes:

  • Added a serialized _offlineMode option (with public IsOfflineMode) and switched NetSyncManager to depend on IConnectionManager.
  • In offline mode, NetSyncManager uses OfflineConnectionManager and short-circuits networking/handshake behavior by assigning a local client number and marking initial sync complete.
  • Updated the custom inspector property ordering to surface the new _offlineMode toggle in the “Advanced” foldout.

Reviewed changes

Copilot reviewed 10 out of 10 changed files in this pull request and generated 2 comments.

File Description
STYLY-NetSync-Unity/Packages/com.styly.styly-netsync/Runtime/NetSyncManager.cs Adds offline mode toggle, selects IConnectionManager implementation, and adjusts connection/initial-sync behavior for offline operation.
STYLY-NetSync-Unity/Packages/com.styly.styly-netsync/Editor/NetSyncManagerEditor.cs Exposes _offlineMode in the advanced inspector property order.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +613 to +616
_clientNo = 1;
_networkVariableManager?.MarkInitialSyncComplete();
_shouldCheckReady = true;
DebugLog("Offline mode: client number set to 1, initial sync marked complete");
Copy link

Copilot AI Feb 15, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In offline mode you set _clientNo = 1 directly and return, but this bypasses the OnLocalClientNoAssigned() path that flushes _pendingSelfClientNV into NetworkVariableManager. As a result, any SetClientVariable() calls made before the offline “connection” is established will remain queued forever. Consider reusing OnLocalClientNoAssigned(1) (or factoring the flush logic into a shared helper) instead of setting _clientNo directly.

Suggested change
_clientNo = 1;
_networkVariableManager?.MarkInitialSyncComplete();
_shouldCheckReady = true;
DebugLog("Offline mode: client number set to 1, initial sync marked complete");
// Use the same path as online mode for assigning the local client number
// so that any pending self client network variables are flushed.
OnLocalClientNoAssigned(1);
_networkVariableManager?.MarkInitialSyncComplete();
_shouldCheckReady = true;
DebugLog("Offline mode: client number set to 1 via OnLocalClientNoAssigned, initial sync marked complete");

Copilot uses AI. Check for mistakes.
@from2001 from2001 changed the title Feature/standalone mode Feature/offline mode Feb 15, 2026
@from2001
Copy link
Collaborator Author

@claude Review the latest code.

@claude
Copy link
Contributor

claude bot commented Feb 15, 2026

Claude finished @from2001's task in 1m 29s —— View job


Code Review Complete ✓

  • Read all changed files to understand the implementation
  • Analyze code for bugs and issues
  • Review against Unity C# coding rules
  • Assess Copilot review comments
  • Formulate comprehensive review feedback

Summary

Overall, this is a well-structured implementation that successfully introduces offline mode functionality to NetSync. The abstraction via IConnectionManager is clean and the offline behavior is handled correctly in most places. However, there are two important issues identified (one already noted by Copilot) that should be addressed before merging.

Critical Issues

1. Pending Self Client Variables Not Flushed in Offline Mode ⚠️

Issue: Copilot's review comment is correct and important. In NetSyncManager.cs:611-616, offline mode sets _clientNo = 1 directly without calling OnLocalClientNoAssigned(1). This bypasses the logic that flushes _pendingSelfClientNV, causing any SetClientVariable() calls made before connection to be lost forever.

Location: NetSyncManager.cs:611-616

Impact: Any client variables set before the offline "connection" completes will never be applied, leading to incorrect state.

Fix: Use OnLocalClientNoAssigned(1) instead of setting _clientNo directly.

Fix this →

// Current code (WRONG):
if (_offlineMode)
{
    _clientNo = 1;  // ❌ Bypasses pending NV flush
    _networkVariableManager?.MarkInitialSyncComplete();
    _shouldCheckReady = true;
    DebugLog("Offline mode: client number set to 1, initial sync marked complete");
    return;
}

// Should be (CORRECT):
if (_offlineMode)
{
    OnLocalClientNoAssigned(1);  // ✅ Properly flushes pending NVs
    _networkVariableManager?.MarkInitialSyncComplete();
    DebugLog("Offline mode: client number set to 1 via OnLocalClientNoAssigned, initial sync marked complete");
    return;
}

2. Null Propagation Operator Used with UnityEngine.Object (Unity-Specific Issue) ⚠️

Issue: In NetSyncManager.cs:455, the code uses the null propagation operator (?.) with a UnityEngine.Object reference, which violates Unity C# coding rules specified in CLAUDE.md.

Location: NetSyncManager.cs:455

Violation: CLAUDE.md explicitly states: "Never use null propagation (?. / ??) with UnityEngine.Object types"

Why this matters: Unity's custom equality operators can cause unexpected behavior with null propagation operators.

Fix this →

// Current code (line 455):
if (!_connectionManager?.IsConnected && !_isDiscovering)  // ❌ Null propagation

// Should be:
if (!(_connectionManager != null && _connectionManager.IsConnected) && !_isDiscovering)  // ✅ Explicit check
// Or alternatively:
if (_connectionManager != null && !_connectionManager.IsConnected && !_isDiscovering)

Note: _connectionManager is of type IConnectionManager, which is an interface, not a UnityEngine.Object. However, the CLAUDE.md rule is overly broad for safety. Since this isn't a Unity-specific object reference, the null propagation is technically safe here, but for consistency with project guidelines, it should still use explicit checks.

Minor Issues & Suggestions

3. Terminology Inconsistency (Already Noted by Copilot)

Issue: The PR description and commit messages refer to "standalone mode" but the code uses _offlineMode and IsOfflineMode. The branch is also named feature/standalone_mode.

Recommendation: Choose one term and use it consistently. "Offline mode" seems more descriptive (it indicates no server connection), whereas "standalone" could be confused with other meanings.

4. Interface Implementation is Minimal but Correct

The OfflineConnectionManager implementation is intentionally minimal (all methods are no-ops), which is appropriate for offline mode. However, consider:

  • Line 24: OnConnectionEstablished?.Invoke() is called immediately in Connect(). This is correct and mirrors online behavior.
  • Methods return success: All send methods (TryEnqueueControl, SetLatestTransform) return true, which is correct since there's no actual backpressure in offline mode.

5. NetworkVariableManager Offline Logic is Well Implemented

The offline mode handling in NetworkVariableManager.cs:123-133 and NetworkVariableManager.cs:230-240 is correct:

  • Writes values locally without server round-trip ✅
  • Fires change events properly ✅
  • Respects the same validation rules ✅

6. RPCManager Offline Loopback is Clever

The offline RPC loopback in RPCManager.cs:103-108 is a nice touch:

if (_netSyncManager != null && _netSyncManager.IsOfflineMode)
{
    EnqueueRPC(_netSyncManager.ClientNo, functionName, args);
    return true;
}

This allows testing RPC handlers locally, which is very useful for development.

Architecture & Design

Interface abstraction is clean: The IConnectionManager interface is well-designed and covers all necessary operations.

Dependency injection works well: All managers properly accept IConnectionManager instead of the concrete ConnectionManager.

Separation of concerns: Offline logic is isolated in OfflineConnectionManager without polluting the main ConnectionManager.

Consistent behavior: Offline mode fires the same events (OnConnectionEstablished, variable change events) as online mode, making it a true testing substitute.

Code Quality

  • No race conditions introduced: Thread safety is maintained (offline manager is single-threaded by design)
  • No memory leaks: All implementations are straightforward with no resource leaks
  • Error handling: Appropriate for a no-op implementation
  • Code style: Consistent with existing codebase

Testing Recommendations

While not blocking for this PR, consider testing:

  1. Setting client variables before "connection" completes (will be broken until issue v0.0.2 #1 is fixed)
  2. RPC loopback behavior in offline mode
  3. Network variable events firing correctly in offline mode
  4. Switching between online and offline mode (if supported)

Final Verdict

APPROVE with requested changes: The implementation is solid, but the two issues above should be fixed before merging:

  1. MUST FIX: Use OnLocalClientNoAssigned(1) instead of direct _clientNo = 1 assignment
  2. SHOULD FIX: Replace null propagation with explicit null check for consistency with project guidelines
  3. OPTIONAL: Align terminology (standalone vs offline)

@from2001 from2001 merged commit 217ba90 into develop Feb 15, 2026
@from2001 from2001 deleted the feature/standalone_mode branch February 15, 2026 12:29
@from2001
Copy link
Collaborator Author

netsync_offline_en

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants