Same requirement, different grain

The requirement doesn't change between platforms: when something happens, show the operator the right camera, and keep the video until they've dealt with it. What changes is where each piece lives. In Genetec, recording and alarms hang off entities and their event-to-actions. In XProtect, recording is driven by rules on the Event Server, alarms are a separate layer of alarm definitions on top of events, and the two don't talk to each other as directly as you'd expect. That last point is the whole reason this article exists.

One alarm, end to end
Camera
Recording Server
→
Event
device · MIP
→
Alarm definition
related cameras
→
Smart Client
video pop-up
→
Recording held
server · path · edge
→
Acknowledged
stop · export

Menu names below match recent XProtect releases (2023 R1 onwards); features such as evidence lock depend on the edition, so check yours before designing around them.

1. Configuring the camera

Adding hardware to a Recording Server

  1. In the Management Client, expand Servers → Recording Servers, right-click the server that should own the camera, and choose Add hardware.
  2. Pick a method — Express scans the local network, Address range scanning or Manual when you know the addresses — and supply the camera's credentials. XProtect detects the driver from the installed device pack; if it can't, the device pack is out of date or the camera needs ONVIF or a custom driver (see our device driver guide).
  3. Enable the cameras you need, add them to a device group, and give them names an operator will recognise in an alarm list.

Streams, storage and the rules that make it record

The camera's Settings and Streams tabs choose resolution, codec and which stream is used for live and which for recording. The Record tab sets the pre-buffer (seconds held before a recording starts, in memory or on disk) and the recording frame rate. Storage and retention are set on the Recording Server's Storage tab — the recording database plus any archive stages, each with its own retention time.

What surprises people coming from other systems is that whether the camera records is decided by rules, not by the camera. Out of the box, the Default Record on Motion Rule records on motion, and the Default Start Feed Rule keeps the feed running. If the site wants continuous recording, an administrator edits or adds a rule. For alarm work, this means two things: there may be no footage before the alarm unless motion was detected or the pre-buffer covers it, and anything that starts recording on an alarm will itself be a rule — or a plugin.

2. Configuring the alarm

Alarms are defined in the Management Client under Alarms → Alarm Definitions. An alarm definition says when this event happens on these sources, raise an alarm with these properties:

  • Triggering event — a device event (motion started, input activated, tampering), an analytics event from a camera or third-party system, a user-defined event, or a custom event registered by a MIP plugin.
  • Sources — the cameras, inputs or other devices whose events raise this alarm.
  • Time profile — when the definition is active (outside opening hours only, for example).
  • Operator action required — a time limit, with events that fire if the alarm hasn't been handled in time. This is XProtect's built-in hook for escalation.
  • Related cameras and a related map — what the operator sees with the alarm. The equivalent of Genetec's attached entities, and the native "pop-up".
  • Initial alarm owner, priority and category — who it's assigned to, how it's sorted, how it's reported.
  • Events triggered by alarm and auto-close — events to fire when the alarm is raised, and whether the alarm closes itself when a matching event arrives.

The triggering event usually already exists; if it comes from a third-party system, an Event Server plugin registers it as a custom event so it can be selected here like any native one.

3. When the alarm is raised

XProtect alarms don't have a single "acknowledged" flag. They have states, configured under Alarms → Alarm Data Settings. The defaults:

StateMeaningTypical reaction
NewRaised, nobody has touched itShow video, start recording, notify
In progressAn operator has acknowledged it and is working itStop escalating; often the "acknowledged" moment
On holdParked, waiting on somethingKeep recording or not — a design decision
ClosedFinishedStop recording, lock and export, log the outcome

Administrators can add custom states and reasons for closing, so the first job in any alarm-recording project is agreeing which transition counts as "acknowledged": usually leaving New for stopping escalation, and reaching Closed for ending the recording. Write it down — different stakeholders on the same site will assume different answers.

In Smart Client, alarms appear in the Alarm Manager tab: an alarm list with a preview of the related cameras, live and playback from the alarm time. Operators can also get desktop notifications for chosen alarm priorities, so a new alarm reaches them while they're working in another tab.

4. Getting the camera onto the operator's screen

The native pop-up

Related cameras on the alarm definition plus desktop notifications cover most sites. For a video wall, XProtect Smart Wall can be driven from rules so a camera goes to a wall monitor when an event fires.

When a plugin needs to drive the pop-up

As with Genetec, native behaviour runs out when the choice of camera depends on information XProtect doesn't have, or when the video must land somewhere specific — a dedicated floating window on the second screen, a fixed slot in the operator's current view, a layout mixing video with a third-party panel. That's a Smart Client MIP plugin: a background plugin in Smart Client that listens for new alarms through MIP messaging and sends Smart Client commands to place cameras.

C# — Smart Client background plugin that opens alarm video (illustrative)
public class AlarmPopupBackgroundPlugin : BackgroundPlugin
{
    private object _newAlarmFilter;
    private AlarmPopupSettings _settings;

    public override void Init()
    {
        _settings = AlarmPopupSettings.Load();

        // Smart Client is told about new alarms through MIP messaging.
        _newAlarmFilter = EnvironmentManager.Instance.RegisterReceiver(
            OnNewAlarm,
            new MessageIdFilter(MessageId.Server.NewAlarmIndication));
    }

    private object OnNewAlarm(Message message, FQID destination, FQID sender)
    {
        var alarm = AlarmInfo.From(message.Data);
        if (!_settings.Handles(alarm)) return null;

        // Related cameras plus any resolved by our own rules.
        var cameras = CameraResolver.For(alarm);

        ClientControl.Instance.CallOnUiThread(() =>
        {
            // e.g. open or reuse a floating window on the configured screen
            // and put each camera into a view slot via Smart Client commands.
            AlarmWindow.OpenOrReuse(_settings.TargetScreen)
                       .ShowCameras(cameras, from: alarm.Time.AddSeconds(-_settings.PreAlarmSeconds));
        });
        return null;
    }

    public override void Close()
    {
        EnvironmentManager.Instance.UnRegisterReceiver(_newAlarmFilter);
    }
}

The same rules as on Genetec decide whether operators keep the plugin switched on: never steal focus from someone working a higher-priority alarm, respect the operator's camera permissions, and collapse a burst of alarms into one window rather than ten.

Need alarm video somewhere Smart Client doesn't put it? Tell us the trigger and the screen. We'll tell you whether it's a rule or a plugin, usually the same day.

Email contact@xplug.in

5. Keeping the recording until the alarm is acknowledged

Here XProtect needs more help than Security Center does. The Rules engine can start recording on the event that raised the alarm, and stop it after a fixed time or on another event. But changing an alarm's state in the Alarm Manager isn't an ordinary rule event, so "record until the alarm is acknowledged" can't be written as a rule on its own. Something has to watch alarm state and turn it into recording decisions — which is a small, well-understood Event Server plugin.

We build it with the same storage choice as on Genetec: if the plugin's configuration names a local storage path, the alarm clip is exported there; if not, it stays on the Recording Server, protected, as the default; and where cameras support it, edge storage fills the gap when the Recording Server couldn't reach the camera.

Option A — the Recording Server (the default)

  1. Start: a rule on the triggering event — Perform an action on <event> → Start recording on the related cameras, with the pre-buffer covering the lead-up. Without a plugin, the stop side is after a fixed time, which is an approximation of "until acknowledged".
  2. Hold until acknowledged: the Event Server plugin watches alarm state. When the alarm leaves New (or reaches Closed, whichever you agreed), it either stops recording directly or fires a user-defined event that a Stop recording rule reacts to. Keeping the stop as a rule leaves administrators in control of it from the Management Client.
  3. Protect: on editions that support it, create an evidence lock over the alarm's time range on its cameras so retention can't delete it. Elsewhere, export it (Option B) or extend retention on that Recording Server's storage.

Option B — a local storage path set in the plugin

The Event Server plugin owns the lifecycle and, on acknowledgement, exports the alarm's range to a folder the administrator sets in the plugin's configuration in the Management Client — a local disk or a UNC share. If the path is empty, it falls back to Option A.

C# — Event Server plugin: hold recording until acknowledgement (illustrative)
public class AlarmRecordingBackgroundPlugin : BackgroundPlugin
{
    private AlarmRecordingStore _store;      // persisted: Event Server restarts mid-alarm
    private CameraRecordingLeases _leases;   // ref-counted per camera
    private AlarmRecordingSettings _cfg;     // LocalStoragePath, buffers, max duration, ack state

    public override void Init()
    {
        _cfg = AlarmRecordingSettings.Load();   // from the plugin's Management Client item
        AlarmWatcher.Start(OnAlarmRaised, OnAlarmStateChanged, OnMaxDurationReached);
        _store.ReconcileOpenAlarms();           // resume after a restart
    }

    private void OnAlarmRaised(AlarmRecord alarm)
    {
        _store.Open(alarm.Id, alarm.RelatedCameras, alarm.Time);
        foreach (var camera in alarm.RelatedCameras)
            _leases.Acquire(camera, alarm.Id);  // start recording if first lease
    }

    private void OnAlarmStateChanged(AlarmRecord alarm)
    {
        if (_cfg.CountsAsAcknowledged(alarm.State))
            Close(alarm.Id, alarm.StateChangedTime, $"State: {alarm.StateName}");
    }

    private void OnMaxDurationReached(Guid alarmId)
        => Close(alarmId, DateTime.UtcNow, "Max duration reached — escalated");

    private void Close(Guid alarmId, DateTime end, string reason)
    {
        var rec = _store.Get(alarmId);
        if (rec == null || rec.Closed) return;            // idempotent

        foreach (var camera in rec.Cameras)
            _leases.Release(camera, alarmId);             // stop only when no alarm still needs it

        var from = rec.Time - _cfg.PreAlarm;
        var to   = end + _cfg.PostAlarm;
        EvidenceLock.TryCreate(rec.Cameras, from, to, $"Alarm {alarmId}");  // edition-dependent

        if (!string.IsNullOrWhiteSpace(_cfg.LocalStoragePath))
            ExportQueue.Enqueue(new ExportJob(rec, from, to, _cfg.LocalStoragePath)); // retried, hashed
        // else: footage stays on the Recording Server (the default)

        _store.MarkClosed(alarmId, end, reason);
    }
}

The export job uses the MIP SDK's exporters — the XProtect database format when the clip must stay verifiable in the XProtect player, MKV or AVI when it's going to someone without XProtect — writes a SHA-256 hash and a sidecar describing the alarm, cameras, operator and outcome, and retries if the share is unavailable. It runs from a queue, not inside the event handler, so a slow export never delays the next alarm.

Gotcha — The Event Server runs as a service account, and "local" means local to the Event Server machine. If the path is a share, that account needs write access to it; if the Event Server is clustered or moved, a local drive letter silently points somewhere else. Validate the path, its permissions and free space when the plugin starts, and surface failures as an XProtect event administrators can alarm on.

Option C — on the camera's edge storage

Cameras with SD cards can record locally when the Recording Server can't reach them. XProtect supports this as remote recording: retrieval can happen automatically when the connection comes back, or be triggered by the Retrieve and store remote recordings rule action. For alarms on remote or poorly connected sites, the plugin marks the alarm clip as incomplete when a camera was offline during the alarm, triggers retrieval when it reconnects, and only exports once the gap is filled.

Choosing between them

A · Recording Server (default)B · Local / network pathC · Camera edge
Needs a pluginFor "until acknowledged", yesYesFor automation, usually
Footage livesRecording Server storage, evidence-lockedFolder set in the plugin's configCamera SD card, later the Recording Server
Survives Recording Server outageNoNo — exports from the Recording ServerYes
Shareable outside the VMSVia exportDirectly, with hash and sidecarAfter retrieval and export
Best forMost sitesCase files, insurers, third-party systemsRemote sites, weak links

6. The edge cases that decide whether it works in production

  • Many alarms, one camera. Reference-count recording per camera; closing one alarm must not stop recording another still needs.
  • Unhandled alarms. Always set a ceiling, and use the alarm definition's operator action required time limit to raise an event when it passes. XPlug.SmartNotifier takes that event and escalates the alarm to the next person by WhatsApp, Teams or phone, with acknowledgement flowing back into XProtect.
  • Auto-closed alarms. Treat them as a separate outcome. Footage from an alarm nobody looked at is often the footage someone asks for later.
  • Event Server restarts. Persist open alarms and reconcile them against the Alarm Manager on startup, so an upgrade or reboot mid-alarm doesn't leave a camera recording forever or a clip never exported.
  • Pre-buffer limits. A memory pre-buffer is limited in length; for longer lead-ups use a disk pre-buffer or continuous recording on the cameras that matter.
  • Permissions and privacy. Exported clips leave XProtect's role-based permissions. The folder needs its own access control and a written retention policy.

Where projects usually need a specialist

Related cameras, desktop notifications and a start-recording rule are an afternoon's configuration. "Until acknowledged" is where XProtect needs code: an Event Server plugin that turns alarm state into recording decisions, survives restarts, handles overlapping alarms, locks and exports evidence, and keeps working across XProtect releases. That is the alarm work we've been building on Milestone and Genetec systems since 2014 — as one-off Milestone plugin development projects, and as XPlug.SmartNotifier where the requirement is getting the alarm to a person, not just a screen.

Working with Xplug.in

Email us your alarm requirement — get a straight answer on how to build it

  • Tell us the trigger, the screen and where the video must end up. What raises the alarm, who should see which camera, which state counts as acknowledged, and where footage must be kept. We reply with what rules can do, what needs a plugin, and what we'd flag first.
  • Configuration we'll just tell you. If XProtect's rules and alarm definitions already do it, we'll point at the settings — no project required.
  • Plugins built for real alarm load — Event Server plugins with ref-counted recording and restart-safe state, a configurable local or network storage path with the Recording Server as default, evidence lock and hashed exports, Smart Client pop-ups that respect permissions and priority.
  • Source and IP transferred to you at delivery, taken through Milestone certification where it will be distributed, and version-tracked as XProtect releases move.

Xplug.in is a Milestone Technology Partner with 140+ plugins shipped since 2014 — Smart Client views, Event Server integrations, Management Client extensions and Recording Server device drivers. Write to contact@xplug.in; a straight technical answer costs you one email.

Questions we get asked

Can XProtect record a camera until an alarm is acknowledged without a plugin?

Only approximately. The Rules engine can start recording on the event that raises the alarm and stop it after a fixed time or on another event, but alarm state changes in the Alarm Manager are not ordinary rule events, so “until acknowledged” can't be expressed directly. The usual answer is a small Event Server plugin that watches alarm state and starts and stops recording, or fires user-defined events your rules react to.

What does acknowledging an alarm mean in Milestone XProtect?

XProtect alarms have states rather than a single acknowledged flag — by default New, In progress, On hold and Closed, and administrators can add their own. Acknowledging in Smart Client moves an alarm out of New. Decide which state transition your design treats as acknowledgement, usually leaving New or reaching Closed, and write it down before building anything on it.

How do I make a camera pop up in Smart Client when an alarm fires?

Add the camera as a related camera on the alarm definition so it appears in the Alarm Manager preview, and turn on desktop notifications for the alarm so operators see it outside the Alarm Manager tab. For anything beyond that — a floating window, a specific view slot, a camera chosen by your own logic — a Smart Client MIP plugin can listen for new alarms and send Smart Client commands to place the camera.

Is evidence lock the same as recording until acknowledgement?

No. Evidence lock protects a time range of existing recordings from deletion; it does not make a camera record. A complete design does both: make sure the camera records from the alarm to its acknowledgement, then evidence-lock that range (on XProtect editions that support it) or export it, so retention cannot remove it.