diff --git a/src/ZB.MOM.WW.ScadaBridge.CentralUI/ScriptAnalysis/SandboxScriptHost.cs b/src/ZB.MOM.WW.ScadaBridge.CentralUI/ScriptAnalysis/SandboxScriptHost.cs
index cce4cda0..08335030 100644
--- a/src/ZB.MOM.WW.ScadaBridge.CentralUI/ScriptAnalysis/SandboxScriptHost.cs
+++ b/src/ZB.MOM.WW.ScadaBridge.CentralUI/ScriptAnalysis/SandboxScriptHost.cs
@@ -464,6 +464,27 @@ public class SandboxAttributeAccessor
string responseKey, object? responseValue, TimeSpan timeout)
=> throw NotInSandbox(nameof(WriteBatchAndWaitAsync));
+ ///
+ /// Sandbox stand-in for the reset-aware AttributeAccessor.WriteBatchAndWaitAsync
+ /// overload (Gitea #36): present for editor/compile parity, throws
+ /// when run in Test Run (no device batch-write transport).
+ ///
+ /// The attribute values to write as a batch.
+ /// The flag attribute key to set to signal completion.
+ /// The value to set on the flag attribute.
+ /// The attribute key to observe for the device's response.
+ /// The response value to wait for.
+ /// The maximum time to wait for the response.
+ /// The attribute written first and waited on before the batch.
+ /// The reset value the device must echo before the batch is written.
+ /// The maximum time to wait for the reset echo; null means .
+ /// Never returns; always throws in the sandbox.
+ public Task WriteBatchAndWaitAsync(
+ IReadOnlyDictionary values, string flagKey, object? flagValue,
+ string responseKey, object? responseValue, TimeSpan timeout,
+ string resetKey, object? resetValue, TimeSpan? resetTimeout = null)
+ => throw NotInSandbox(nameof(WriteBatchAndWaitAsync));
+
///
/// Value-equality attribute wait — routed to the bound deployed instance cross-site
/// (the same real event-driven waiter a site uses). Needs a bound instance; throws
diff --git a/tests/ZB.MOM.WW.ScadaBridge.CentralUI.Tests/ScriptAnalysis/ScriptAnalysisServiceTests.cs b/tests/ZB.MOM.WW.ScadaBridge.CentralUI.Tests/ScriptAnalysis/ScriptAnalysisServiceTests.cs
index f16ec046..74a34efc 100644
--- a/tests/ZB.MOM.WW.ScadaBridge.CentralUI.Tests/ScriptAnalysis/ScriptAnalysisServiceTests.cs
+++ b/tests/ZB.MOM.WW.ScadaBridge.CentralUI.Tests/ScriptAnalysis/ScriptAnalysisServiceTests.cs
@@ -756,13 +756,18 @@ public class ScriptAnalysisServiceTests
// WaitAsync / WaitForAsync, so the editor false-flagged valid instance scripts
// with CS1061 even though `template validate` and the deploy gate accept them.
// The sandbox surface must mirror the runtime AttributeAccessor member-for-member.
+ // Gitea #36: also covers the reset-aware WriteBatchAndWaitAsync overload
+ // (writes+waits a reset key/value before the batch) with and without the
+ // optional resetTimeout, returning a HandshakeResult.
var code =
"var data = new System.Collections.Generic.Dictionary { { \"Cmd\", 1 } };\n" +
"var done = await Attributes.WriteBatchAndWaitAsync(data, \"Flag\", true, \"Done\", true, System.TimeSpan.FromSeconds(5));\n" +
"var hit = await Attributes.WaitAsync(\"Done\", true, System.TimeSpan.FromSeconds(5));\n" +
"var pred = await Attributes.WaitAsync(\"Done\", v => v != null, System.TimeSpan.FromSeconds(5));\n" +
"var res = await Attributes.WaitForAsync(\"Done\", true, System.TimeSpan.FromSeconds(5));\n" +
- "return done && hit && pred && res.Matched;";
+ "var hs = await Attributes.WriteBatchAndWaitAsync(data, \"Flag\", true, \"Done\", true, System.TimeSpan.FromSeconds(5), \"Done\", false, System.TimeSpan.FromSeconds(2));\n" +
+ "var hs2 = await Attributes.WriteBatchAndWaitAsync(data, \"Flag\", true, \"Done\", true, System.TimeSpan.FromSeconds(5), \"Done\", false);\n" +
+ "return done && hit && pred && res.Matched && hs.Matched && !hs2.ResetFailed;";
var resp = _svc.Diagnose(new DiagnoseRequest(code));
Assert.DoesNotContain(resp.Markers, m => m.Code.StartsWith("CS"));