AI Bridge 2.0 – AnalyticsEvent REST POST returns HTTP 200 on /event/.../analytics_event but no logs and no events in XProtect

Hello,

I am trying to inject Analytics Events into Milestone XProtect via Milestone AI Bridge using the REST endpoint documented for

eventTopics

(AnalyticsEvent).

Environment

  • XProtect VMS: 24 R2
  • Milestone AI Bridge: 2.0 (Docker deployment on Windows host)
  • Host OS: Windows (Docker Desktop)
  • AI Bridge containers (short list):

ngc-aibridge-webservice-1 0.0.0.0:4000-4001->4000-4001/tcp

ngc-aibridge-connector-1

ngc-aibridge-streaming-1 0.0.0.0:8554-8555->8554-8555/tcp, 0.0.0.0:8000-8001->8000-8001/udp, 0.0.0.0:55500->55500/udp, 0.0.0.0:9898->9898/tcp

ngc-aibridge-proxy-1 0.0.0.0:8786-8787->8786-8787/tcp

ngc-aibridge-broker-1 0.0.0.0:8382-8383->8382-8383/tcp

ngc-aibridge-kafka-broker-1 0.0.0.0:9092->9092/tcp, 0.0.0.0:29092->29092/tcp

ngc-aibridge-init-1

ngc-aibridge-health-1 0.0.0.0:3500->3500/tcp

ngc-aibridge-kafka-zookeeper-1 2888/tcp, 0.0.0.0:2181->2181/tcp, 3888/tcp

ngc-aibridge-fuseki-1 0.0.0.0:3030->3030/tcp

  • AI Bridge app, camera UUID and eventTopics are all retrieved via Yoga GraphQL (so IDs and URLs are not hard-coded).

What I am trying to do:

I want to send an AnalyticsEvent from an external IVA to AI Bridge via REST, using the

eventTopics.url exposed by AI Bridge/Yoga GraphQL.

From Yoga GraphQL I get an eventTopic with:

The camera UUID used in the JSON payload is also taken from AI Bridge / VMS:

  • Camera UUID : ab9a46df-fd91-4e91-b4dc-4316b45bfc57

REST call I am sending:

From the Windows host (same machine where Docker is running):

curl -v -X POST -H “Content-Type: application/json” --data-binary @evento.json http://localhost:8382/event/b479dccc-2fba-4089-82ab-11b485677108/19_intrusion_area_start/analytics_event

HTTP response:

> POST /event/b479dccc-2fba-4089-82ab-11b485677108/19_intrusion_area_start/analytics_event HTTP/1.1

> Host: localhost:8382

> Content-Type: application/json

> Content-Length: 802

< HTTP/1.1 200 OK

< Date: Thu, 27 Nov 2025 18:17:44 GMT

< Content-Length: 0

I also tried the same call on port 8383 (since the broker container exposes 8382–8383), but on 8383 I get an HTTP error (non-200). So 8382 seems to be the correct port for this REST endpoint.

JSON payload used (evento.json)

{

@context”: “http://www.insights.data/2024/06/analytics-event.jsonld”,

“id”: “http://desktop-us48ssr:8382/event/b479dccc-2fba-4089-82ab-11b485677108/19_intrusion_area_start/analytics_event”,

“type”: “AnalyticsEvent”,

“name”: “19_intrusion_area_start”,

“timestamp”: “2025-11-27T18:32:36.639+01:00”,

“fromSource”: {

“type”: “Camera”,

“uuid”: “235b08a9-c0ee-4e8c-a2c8-bcdd25e0edd7”

},

“involvedObject”: [

{

“class”: “PERSON”,

“name”: “4 [target]”,

“confidence”: 0.78,

“hasOutline”: {

"closed": true,

"hasVertices": \[

 { "x": 543, "y": 299 },

 { "x": 585, "y": 299 },

 { "x": 585, "y": 395 },

 { "x": 543, "y": 395 }

\],

"type": "Polygon"

}

}

]

}

This JSON passes python -m json.tool (and standard JSON validators) and is built according to the AI Bridge AnalyticsEvent context.

(If needed, I can also provide a version without involvedObject , even more minimal, but the behavior is the same.)

What I observe

  • The HTTP call returns 200 OK with an empty body.
  • During the POST, I keep docker logs -f ngc-aibridge-broker-1 and docker logs -f ngc-aibridge-proxy-1 open in separate terminals. None of these containers log anything at the moment of the POST (no request log, no error, nothing).
  • On the VMS side:
    • The AI Bridge app is registered.
    • The camera is registered and linked to the app/processing server.
    • The eventTopic appears correctly in Management Client.
    • However, no Analytics Event is received in XProtect for this POST, and no alarms/rules are triggered.

In short, it looks like:

  • The AI Bridge broker is listening on 8382 (HTTP 200),
  • but the incoming AnalyticsEvent is neither logged by the broker nor forwarded to proxy / VMS, as if it was accepted at HTTP level and then silently discarded.

What I have already tried :

  • Validated JSON with python -m json.tool and online JSON validators.
  • Tried both with and without the involvedObject block.
  • Verified that the eventTopics.url and camera uuid used in the request match exactly what Yoga GraphQL reports.
  • Confirmed the broker container exposes ports 8382-8383->8382-8383/tcp
  • Tried calling both http://localhost:8382/… and http://localhost:8383/…:
    • 8382 → HTTP 200, but no logs and no event in VMS.
    • 8383 → HTTP error.
  • Kept docker logs -f on:
    • ngc-aibridge-broker-1
    • ngc-aibridge-proxy-1
    • and saw no change when sending the POST.
  • Verified in Management Client that the AI Bridge app, the camera, and the event topic are visible and configured.

Questions

Could you please help me understand:

  1. Whether the /event/…/analytics_event REST endpoint on AI Bridge 2.0 (Docker deployment) is expected to accept Analytics Events directly as I am doing here.
  2. If the JSON payload above is correct for AI Bridge 2.0, or if there is any required field / structure that would cause the broker to silently drop the event.
  3. Whether there is any additional configuration or logging I should enable to see why these incoming Analytics Events are not being logged or forwarded to XProtect.

I am happy to provide additional logs, GraphQL queries, or configuration screenshots if needed.

Thank you in advance for your help.

Best regards,

Gianluca

Hi Gianluca,

Status code 200 (only) indicates that the Analytics Event has been received OK in AI Bridge.

If AI Bridge has problems forwarding the Analytics Events to XProtect, it should show up in the -proxy container’s log.

A quick look at your Analytics Event indicates some potential issues:

“id”: is a uuid (a random GUID will be generated if not provided)

“fromSource”: {

“type”: “Camera”

should be

"type": "Reference"

in the

“hasVertices”: [

 { "x": 543, "y": 299 },

 { "x": 585, "y": 299 },

 { "x": 585, "y": 395 },

 { "x": 543, "y": 395 }

\]

the x, y are coordinate points inside image normalized to the range between 0 and 1, like in

      { "x": 0.24, "y": 0.3 },

Please refer to this sample Analytics Event:

https://github.com/milestonesys/MIP-AIBridge-samples/blob/main/apps/golang/connectivitysample/src/application/services/templates/analyticEvent.json

which is part of the apps/golang/connectivitysample.

Please let us know if this helps,

Thanks!

/Hans

Hello,

thank you for your previous reply and for the clarifications regarding the id field, fromSource.type and normalized coordinates.

I have now rebuilt the entire AI Bridge environment from scratch and repeated the integration with a single app and a single AnalyticsEvent topic, strictly following your recommendations. However, the proxy still reports:

“Invalid analytics event received. Will not be sent to ‘http://192.168.10.27’ (more than one topic found).”

Below are the exact steps I took and the current behavior.

1. Fresh AI Bridge 2.0 deployment

On the Docker host (Windows with Docker Desktop), I completely removed the previous AI Bridge deployment with:

docker compose down --rmi all --volumes --remove-orphans

Then, from the config directory of the AI Bridge 2.0 compose package, I started a clean instance with:

docker compose up -d

There were no leftover containers, images, or volumes from the previous environment.

2. Registration of a single VMS, single app, single event topic

I used Yoga GraphiQL to register the VMS and app, with an emptyregister.graphql file (because in production I register from C++ code, but for this test I wanted to keep everything explicit and controlled).

Registration mutation:

mutation {

register(input: {

url: “http://192.168.10.27

username: “user”

password: “pwd”

apps: [{

id: “33a6bc9a-0833-46c6-958e-D8BBC1B35CC0”

name: “Milestone Notifier”

description: “Technoaware analytics suite”

version: “3.0.0”

manufacturer: {

name: "Technoaware"

}

eventTopics: [

{

 name: "IntrusionGiorno"

 description: "mio intrusion giorno"

 eventFormat: ANALYTICS\_EVENT

}

]

metadataTopics: []

}]

}) {

id

}

}

Then I queried AI Bridge with:

query {

cameras {

id

name

communicationStatus

}

eventTopics {

appID

topicName

eventFormat

topicAvailability {

rest

grpc

kafka

}

}

metadataTopics {

appID

topicName

}

about {

version

videoManagementSystems {

id

url

version

productName

apps {

id

name

description

version

manufacturer { name }

}

}

}

}

The response (simplified) is:

{

“data”: {

“cameras”: [

{

"id": "ab9a46df-fd91-4e91-b4dc-4316b45bfc57",

"name": "Happytimesoft IPCamera (192.168.10.7) - Camera 1"

},

{

"id": "63bc36dd-20d9-483a-bedf-f31c492998c2",

"name": "AXIS Q1941-E Thermal Network Camera (192.168.10.20) - Camera 1"

}

],

“eventTopics”: [

{

"appID": "33a6bc9a-0833-46c6-958e-D8BBC1B35CC0",

"topicName": "IntrusionGiorno",

"eventFormat": "ANALYTICS\_EVENT",

"topicAvailability": {

 "rest": "[http://desktop-us48ssr:8382/event/33a6bc9a-0833-46c6-958e-d8bbc1b35cc0/intrusiongiorno/analytics\_event](http://desktop-us48ssr:8382/event/33a6bc9a-0833-46c6-958e-d8bbc1b35cc0/intrusiongiorno/analytics_event)",

 "grpc": "grpc://DESKTOP-US48SSR:8383",

 "kafka": "event.33a6bc9a-0833-46c6-958e-d8bbc1b35cc0.intrusiongiorno.analytics\_event"

}

}

],

“metadataTopics”: [],

“about”: {

“version”: “v2.0.0”,

“videoManagementSystems”: [

{

 "id": "73f61e9f-7936-4090-b618-65a87b4e4291",

 "url": "[http://192.168.10.27](http://192.168.10.27)",

 "productName": "XProtect Corporate 2025 R2 Test",

 "version": "25.2a",

 "apps": \[

  {

   "id": "33a6bc9a-0833-46c6-958e-D8BBC1B35CC0",

   "name": "Milestone Notifier",

   "description": "Technoaware analytics suite",

   "version": "3.0.0",

   "manufacturer": {

    "name": "Technoaware"

   }

  }

 \]

}

]

}

}

}

Important points:

  • There is exactly one VMS.
  • There is exactly one app.
  • There is exactly one eventTopic : IntrusionGiorno, ANALYTICS_EVENT
  • metadataTopics is empty.

3. XProtect configuration

On XProtect Management Client (XProtect Corporate 2025 R2):

  1. I had previously deregistered and removed the old AI Bridge processing server from Management Client before doing the new Docker deployment.
  2. After the new registration, I see the new AI Bridge processing server, with the app Milestone Notifier and the event topic IntrusionGiorno .
  3. For the camera 192.168.10.7 (Happytimesoft), I configured the subscription to the IntrusionGiorno topic only.
  4. Under Analytics Events, I see:
  • Milestone Notifier / IntrusionGiorno
  • and there are no other Analytics Events with the same name.
  1. Under Alarms, I created an alarm definition bound to:
  • Analytics Event: Milestone Notifier / IntrusionGiorno
  • Camera: Happytimesoft IPCamera (192.168.10.7) - Camera 1

So on the VMS side, there is only one processing server for this bridge, one app, one analytics topic, one camera subscription, and one corresponding Analytics Event and alarm.

4. AnalyticsEvent payload and REST call

Based on your previous advice, I am now sending the following payload (no id field, fromSource.type = “Reference” , normalized coordinates):

{

@context”: “http://www.insights.data/2024/06/analytics-event.jsonld”,

“type”: “AnalyticsEvent”,

“name”: “IntrusionGiorno”,

“timestamp”: “2025-12-02T18:52:36.639+01:00”,

“fromSource”: {

“type”: “Reference”,

“uuid”: “ab9a46df-fd91-4e91-b4dc-4316b45bfc57”

},

“involvedObject”: [

{

“class”: “PERSON”,

“name”: “4 [target]”,

“confidence”: 0.78,

“hasOutline”: {

"type": "Polygon",

"closed": true,

"hasVertices": \[

 { "x": 0.28, "y": 0.28 },

 { "x": 0.30, "y": 0.28 },

 { "x": 0.30, "y": 0.37 },

 { "x": 0.28, "y": 0.37 }

\]

}

}

]

}

The REST call is made using exactly the topicAvailability.rest URL:

curl -v -H “Content-Type: application/json” --data-binary @evento_intrusiongiorno.json http://desktop-us48ssr:8382/event/33a6bc9a-0833-46c6-958e-d8bbc1b35cc0/intrusiongiorno/analytics_event

The HTTP response is:

  • HTTP/1.1 200 OK
  • Empty body

5. Proxy log: “more than one topic found”

At the time of the POST, in the ngc-aibridge-proxy-1 container log I consistently see:

2025-12-02T16:00:36Z Invalid analytics event received. Will not be sent to ‘http://192.168.10.27’ (more than one topic found).

This is the same message I was seeing before, even though:

  • AI Bridge has been re-deployed fresh (all containers/images/volumes removed).
  • Only one app and one AnalyticsEvent topic (IntrusionGiorno) are registered.
  • Only one camera (192.168.10.7) is subscribed to this topic.
  • There are no other Analytics Events with the same name in XProtect.
  • There are no metadata topics at all.

In other words, from my side there appears to be exactly one topic that matches this AnalyticsEvent, yet the proxy still reports “more than one topic found”.

6. Questions

Given the above, could you please help me understand:

  1. What exactly does “more than one topic found” refer to?

Does it mean:

  • Multiple AI Bridge eventTopics matching the same app/topic name,
  • Multiple VMS subscriptions / camera bindings for the same event topic,
  • Or some other internal representation (e.g. multiple internal topic entities in the triple store / configuration)?

2.Is there any additional diagnostic / logging I can enable on AI Bridge (especially the proxy) or on the Event Server to see:

  • Which topics/entities the proxy believes are matching this AnalyticsEvent, and
  • Why it ends up with more than one match even though the GraphQL view and the Management Client show only one event topic and one subscription?

3.Could this be related to a known issue or a bug in AI Bridge 2.0 when resolving AnalyticsEvent topics, especially in configurations where the bridge has been reinstalled and re-registered with the same VMS, but with fresh Docker volumes?

I can provide:

  • The full GraphQL query result (cameras, eventTopics, about.videoManagementSystems).
  • Screenshots from XProtect Management Client (processing server, app, topic, camera subscription, Analytics Event, and alarm).
  • Full ngc-aibridge-proxy-1 and ngc-aibridge-broker-1
  • logs around the time of the POST.

From my side, the JSON now follows your guidance, and the configuration has been reduced to the simplest possible case: one VMS, one app, one AnalyticsEvent topic, one camera subscription. The remaining issue seems to be the internal “topic resolution” logic behind the “more than one topic found” error.

Thank you very much for your continued help.

Best regards,

Gianluca

Hi Gianluca,

What version of AI Bridge are you using? For this particular issue, I will definitely recommend the latest, 2.0.2. You can check that with:

query  {about {version}}

I will also recommend trying out the Analytics Events part of the ConnectivitySample https://github.com/milestonesys/MIP-AIBridge-samples/tree/main/apps/golang/connectivitysample potentially with prebuilt containers available on Amazon ECR Public Gallery - Milestone Systems/aibridge/apps/connectivitysample. With that, you should be able to see Analytics Events coming the whole way through!

Just tried with your Analytics Event payload (adjusted with timestamp and camera ID)

  • The Analytics Event appears in XProtect
  • When assigned to an Alarm, you can also see the bounding box

{
 "@context": "http://www.insights.data/2024/06/analytics-event.jsonld",
 "type": "AnalyticsEvent",
 "name": "IntrusionGiorno",
 "timestamp": "2025-12-04T12:02:36.639+01:00",
 "fromSource": {
  "type": "Reference",
  "uuid": "62805f33-95e4-4cdd-9207-e6f63aeea37c"
 },
 "involvedObject": [
  {
   "class": "PERSON",
   "name": "4 [target]",
   "confidence": 0.78,
   "hasOutline": {
    "type": "Polygon",
    "closed": true,
    "hasVertices": [
     { "x": 0.28, "y": 0.28 },
     { "x": 0.30, "y": 0.28 },
     { "x": 0.30, "y": 0.37 },
     { "x": 0.28, "y": 0.37 }
    ]
   }
  }
 ]
}

Hi,

thanks for your previous reply and for testing my AnalyticsEvent payload on your system.

Here is my current situation:

  • I’m now running AI Bridge 2.0.2, deployed using the official
  • aibridge_compose_deployment and the original register.graphql for the bridge.
  • In XProtect Management Client, the Technoaware AI Bridge processing server is Connected.
  • The connectivitysample app is installed and working end-to-end: its Analytics Events appear in protect and can trigger Alarms.

For my custom app and topic IntrusionGiorno , I am using exactly the payload you sent me (only

timestamp andfromSource.uuid changed to match my camera):

{

@context”: “http://www.insights.data/2024/06/analytics-event.jsonld”,

“type”: “AnalyticsEvent”,

“name”: “IntrusionGiorno”,

“timestamp”: “2025-12-12T14:49:36.639+01:00”,

“fromSource”: {

“type”: “Reference”,

“uuid”: “ab9a46df-fd91-4e91-b4dc-4316b45bfc57”

},

“involvedObject”: [

{

“class”: “PERSON”,

“name”: “4 [target]”,

“confidence”: 0.78,

“hasOutline”: {

“type”: “Polygon”,

“closed”: true,

“hasVertices”: [

{ “x”: 0.28, “y”: 0.28 },

{ “x”: 0.30, “y”: 0.28 },

{ “x”: 0.30, “y”: 0.37 },

{ “x”: 0.28, “y”: 0.37 }

]

}

}

]

}

I POST this to the exact REST URL returned by AI Bridge for this topic (topicAvailability.rest), e.g.:

curl -v \

-H “Content-Type: application/json” \

--data-binary @intrusiongiorno_event.json \

http://desktop-us48ssr:8382/event/33a6bc9a-0833-46c6-958e-d8bbc1b35cc0/intrusiongiorno/analytics_event

The HTTP response is

200 OK

, but the AI Bridge proxy logs:

“Invalid analytics event received. Will not be sent to ‘http://192.168.10.27’ (no topics found).”

What I have checked:

  • Via GraphQL there is exactly one app with this ID and exactly oneeventTopic:
    • topicName = “IntrusionGiorno”,
    • eventFormat = ANALYTICS_EVENT,
    • topicAvailability.rest is the URL I’m calling.
  • In XProtect:
    • the app appears under the AI Bridge processing server,
    • the Analytics Event … / IntrusionGiorno is visible,
    • the camera is subscribed to this topic,
    • an Alarm is configured for this Analytics Event and camera.
  • I also tried another approach: registering both the app and the event topic via register.graphql , following the same pattern as the connectivitysample, instead of only using Yoga/C++ at runtime. The result is the same: the proxy still reports “no topics found” for this AnalyticsEvent.
  • Using your analyticEvent.json template from the connectivitysample repo with this topic gives the same result.

Meanwhile, Analytics Events from the connectivitysample app work fine on the same system.

Given all this, could you please clarify:

  1. What exact conditions cause the proxy to log Invalid analytics event received … (no topics found) ? Is it matching only on the REST URL, or also on name , type , fromSource.uuid , camera subscriptions, etc.?
  2. Is there any difference in how topics from the connectivitysample app and topics from a custom app are stored or resolved?
  3. Is there any additional logging/diagnostic I can enable to see which topics AI Bridge is trying to match for this request and why it decides “no topics found” in my case, while the same payload works in your environment?

I can provide the full GraphQL apps/eventTopics output and screenshots from Management Client (processing server, app, topic, camera subscription, Analytics Event, and Alarm) if that helps.

Best regards,

Gianluca

Hello, following up on this thread as we haven’t received any response yet. This issue is currently blocking us. Could someone please take ownership and provide a timeline for the next update?

Best regards

Gianluca

Hello Gianluca,

please try to use all lowercase topic names, like “IntrusionGiorno” → “intrusiongiorno”.

Same goes for the letters in the app id (guid), like “33a6bc9a-0833-46c6-958e-D8BBC1B35CC0” → “33a6bc9a-0833-46c6-958e-d8bbc1b35cc0”.

This is the issue we have identified so far. Please let us know if this work, thanks!

/Hans