• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

RobotWebTools / rclnodejs / 27193208698

09 Jun 2026 08:17AM UTC coverage: 91.22% (+5.7%) from 85.523%
27193208698

push

github

web-flow
Phase 2: convert lib/, index.js and tests to native ES modules (#1530)

**Overview:** 189 files changed, +957 / −1162. Converts `lib/`, `index.js`, `bin/`, `rosocket/` and the full test suite to native ES modules; keeps build/codegen tooling as `.cjs`; updates CI to ROS 2 Lyrical (Ubuntu 26.04); and fixes a native-addon debug-build compile error.

### Core ESM conversion
- **`index.js`** — converted to ESM entrypoint (`import`/`export`), module wiring reworked.
- **`lib/**`** — all library modules converted from `require`/`module.exports` to `import`/`export` (node, client, service, publisher, subscription, action/*, clock*, parameter*, logging*, runtime/*, serialization, time*, timer, qos*, utils, validator, native_loader, etc.).
- **`bin/rclnodejs-web.js`**, **`rosocket/index.js`**, **`rosocket/cli.js`** — converted to ESM.

### ESM/CJS boundary fixes (from Copilot review)
- **`lib/native_loader.js`** — load the CommonJS `bindings` helper via `createRequire`'s `require('bindings')` instead of `import bindings from 'bindings'`, preserving CJS caller context for addon resolution.
- **`lib/type_description_service.js`** — corrected sibling import from `'../lib/parameter.js'` to `'./parameter.js'`.

### CommonJS files kept as `.cjs`
- **`rosidl_gen/*.cjs`** (deallocator, idl_generator, index, primitive_types, templates/message-template), **`rostsd_gen/index.cjs`**, **`scripts/ros_distro.cjs`**, **`scripts/run_test.cjs`** — build/codegen tooling stays CJS (loads ESM helpers via supported `require(esm)` / `.default`).
- **`third_party/ref-napi/`** — `lib/ref.js` and `package.json` tweaks for module resolution.

### Tooling / config
- **`package.json`** — `"type": "module"` and script adjustments.
- **`eslint.config.mjs`** — ESM lint rules.
- **`.c8rc.json`** added, **`.nycrc.yml`** removed — switch coverage from nyc to c8.

### CI
- **`.github/workflows/linux-x64-asan-test.yml`**, **`.github/workflows/linux-x64-build-and-test.yml`** — migrated from ROS 2 ... (continued)

2044 of 2402 branches covered (85.1%)

Branch coverage included in aggregate %.

369 of 370 new or added lines in 65 files covered. (99.73%)

942 existing lines in 47 files now uncovered.

16688 of 18133 relevant lines covered (92.03%)

228.85 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

89.59
/lib/event_handler.js
1
// Copyright (c) 2025, The Robot Web Tools Contributors
27✔
2
//
27✔
3
// Licensed under the Apache License, Version 2.0 (the "License");
27✔
4
// you may not use this file except in compliance with the License.
27✔
5
// You may obtain a copy of the License at
27✔
6
//
27✔
7
//     http://www.apache.org/licenses/LICENSE-2.0
27✔
8
//
27✔
9
// Unless required by applicable law or agreed to in writing, software
27✔
10
// distributed under the License is distributed on an "AS IS" BASIS,
27✔
11
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
27✔
12
// See the License for the specific language governing permissions and
27✔
13
// limitations under the License.
27✔
14

27✔
15
import rclnodejs from './native_loader.js';
27✔
16
import DistroUtils from './distro.js';
27✔
17
import {
27✔
18
  OperationError,
27✔
19
  RangeValidationError,
27✔
20
  TypeValidationError,
27✔
21
} from './errors.js';
27✔
22
import Entity from './entity.js';
27✔
23

27✔
24
/**
27✔
25
 * Enumeration for PublisherEventCallbacks event types.
27✔
26
 * @enum {number}
27✔
27
 */
27✔
28
const PublisherEventType = {
27✔
29
  /** @member {number} */
27✔
30
  PUBLISHER_OFFERED_DEADLINE_MISSED: 0,
27✔
31
  /** @member {number} */
27✔
32
  PUBLISHER_LIVELINESS_LOST: 1,
27✔
33
  /** @member {number} */
27✔
34
  PUBLISHER_OFFERED_INCOMPATIBLE_QOS: 2,
27✔
35
  /** @member {number} */
27✔
36
  PUBLISHER_INCOMPATIBLE_TYPE: 3,
27✔
37
  /** @member {number} */
27✔
38
  PUBLISHER_MATCHED: 4,
27✔
39
};
27✔
40

27✔
41
/**
27✔
42
 * Enumeration for SubscriptionEventCallbacks event types.
27✔
43
 * @enum {number}
27✔
44
 */
27✔
45
const SubscriptionEventType = {
27✔
46
  /** @member {number} */
27✔
47
  SUBSCRIPTION_REQUESTED_DEADLINE_MISSED: 0,
27✔
48
  /** @member {number} */
27✔
49
  SUBSCRIPTION_LIVELINESS_CHANGED: 1,
27✔
50
  /** @member {number} */
27✔
51
  SUBSCRIPTION_REQUESTED_INCOMPATIBLE_QOS: 2,
27✔
52
  /** @member {number} */
27✔
53
  SUBSCRIPTION_MESSAGE_LOST: 3,
27✔
54
  /** @member {number} */
27✔
55
  SUBSCRIPTION_INCOMPATIBLE_TYPE: 4,
27✔
56
  /** @member {number} */
27✔
57
  SUBSCRIPTION_MATCHED: 5,
27✔
58
};
27✔
59

27✔
60
/**
27✔
61
 * Check if a publisher event type is supported by the active RMW implementation.
27✔
62
 *
27✔
63
 * Only available in ROS 2 Rolling and later, where the underlying rcl API
27✔
64
 * (`rcl_publisher_event_type_is_supported`) is provided.
27✔
65
 *
27✔
66
 * @param {number} eventType - A {@link PublisherEventType} value.
27✔
67
 * @return {boolean} True if the event type is supported by the active RMW
27✔
68
 *   implementation, false otherwise.
27✔
69
 * @throws {OperationError} if invoked on a ROS distro older than Rolling.
27✔
70
 * @throws {TypeValidationError} if eventType is not a number.
27✔
71
 * @throws {RangeValidationError} if eventType is not a valid
27✔
72
 *   {@link PublisherEventType} value.
27✔
73
 */
27✔
74
function isPublisherEventTypeSupported(eventType) {
8✔
75
  if (typeof rclnodejs.isPublisherEventTypeSupported !== 'function') {
8!
76
    throw new OperationError(
×
UNCOV
77
      'isPublisherEventTypeSupported is only available in ROS 2 Rolling and later',
×
UNCOV
78
      {
×
UNCOV
79
        code: 'UNSUPPORTED_ROS_VERSION',
×
UNCOV
80
        entityType: 'publisher event type',
×
UNCOV
81
        details: {
×
UNCOV
82
          requiredVersion: 'rolling',
×
UNCOV
83
          currentVersion: DistroUtils.getDistroId(),
×
UNCOV
84
        },
×
UNCOV
85
      }
×
UNCOV
86
    );
×
UNCOV
87
  }
×
88
  if (typeof eventType !== 'number') {
8✔
89
    throw new TypeValidationError('eventType', eventType, 'number', {
1✔
90
      entityType: 'publisher event type',
1✔
91
    });
1✔
92
  }
1✔
93
  if (!Object.values(PublisherEventType).includes(eventType)) {
8✔
94
    throw new RangeValidationError(
1✔
95
      'eventType',
1✔
96
      eventType,
1✔
97
      'one of PublisherEventType values',
1✔
98
      { entityType: 'publisher event type' }
1✔
99
    );
1✔
100
  }
1✔
101
  return rclnodejs.isPublisherEventTypeSupported(eventType);
6✔
102
}
8✔
103

27✔
104
/**
27✔
105
 * Check if a subscription event type is supported by the active RMW implementation.
27✔
106
 *
27✔
107
 * Only available in ROS 2 Rolling and later, where the underlying rcl API
27✔
108
 * (`rcl_subscription_event_type_is_supported`) is provided.
27✔
109
 *
27✔
110
 * @param {number} eventType - A {@link SubscriptionEventType} value.
27✔
111
 * @return {boolean} True if the event type is supported by the active RMW
27✔
112
 *   implementation, false otherwise.
27✔
113
 * @throws {OperationError} if invoked on a ROS distro older than Rolling.
27✔
114
 * @throws {TypeValidationError} if eventType is not a number.
27✔
115
 * @throws {RangeValidationError} if eventType is not a valid
27✔
116
 *   {@link SubscriptionEventType} value.
27✔
117
 */
27✔
118
function isSubscriptionEventTypeSupported(eventType) {
9✔
119
  if (typeof rclnodejs.isSubscriptionEventTypeSupported !== 'function') {
9!
120
    throw new OperationError(
×
UNCOV
121
      'isSubscriptionEventTypeSupported is only available in ROS 2 Rolling and later',
×
UNCOV
122
      {
×
UNCOV
123
        code: 'UNSUPPORTED_ROS_VERSION',
×
UNCOV
124
        entityType: 'subscription event type',
×
UNCOV
125
        details: {
×
UNCOV
126
          requiredVersion: 'rolling',
×
UNCOV
127
          currentVersion: DistroUtils.getDistroId(),
×
UNCOV
128
        },
×
UNCOV
129
      }
×
UNCOV
130
    );
×
UNCOV
131
  }
×
132
  if (typeof eventType !== 'number') {
9✔
133
    throw new TypeValidationError('eventType', eventType, 'number', {
1✔
134
      entityType: 'subscription event type',
1✔
135
    });
1✔
136
  }
1✔
137
  if (!Object.values(SubscriptionEventType).includes(eventType)) {
9✔
138
    throw new RangeValidationError(
1✔
139
      'eventType',
1✔
140
      eventType,
1✔
141
      'one of SubscriptionEventType values',
1✔
142
      { entityType: 'subscription event type' }
1✔
143
    );
1✔
144
  }
1✔
145
  return rclnodejs.isSubscriptionEventTypeSupported(eventType);
7✔
146
}
9✔
147

27✔
148
class EventHandler extends Entity {
27✔
149
  constructor(handle, callback, eventType, eventTypeName) {
27✔
150
    super(handle, null, null);
14✔
151
    this._callback = callback;
14✔
152
    this._eventType = eventType;
14✔
153
    this._eventTypeName = eventTypeName;
14✔
154
  }
14✔
155

27✔
156
  takeData() {
27✔
157
    const data = rclnodejs.takeEvent(this._handle, {
11✔
158
      [this._eventTypeName]: this._eventType,
11✔
159
    });
11✔
160
    if (this._callback) {
11✔
161
      this._callback(data);
11✔
162
    }
11✔
163
  }
11✔
164
}
27✔
165

27✔
166
/**
27✔
167
 * @class - Class representing a ROS 2 PublisherEventCallbacks
27✔
168
 * @hideconstructor
27✔
169
 */
27✔
170
class PublisherEventCallbacks {
27✔
171
  constructor() {
27✔
172
    if (DistroUtils.getDistroId() < DistroUtils.getDistroId('jazzy')) {
7✔
173
      throw new OperationError(
1✔
174
        'PublisherEventCallbacks is only available in ROS 2 Jazzy and later',
1✔
175
        {
1✔
176
          code: 'UNSUPPORTED_ROS_VERSION',
1✔
177
          entityType: 'publisher event callbacks',
1✔
178
          details: {
1✔
179
            requiredVersion: 'jazzy',
1✔
180
            currentVersion: DistroUtils.getDistroId(),
1✔
181
          },
1✔
182
        }
1✔
183
      );
1✔
184
    }
1✔
185
    this._deadline = null;
6✔
186
    this._incompatible_qos = null;
6✔
187
    this._liveliness = null;
6✔
188
    this._incompatible_type = null;
6✔
189
    this._matched = null;
6✔
190
    this._eventHandlers = [];
6✔
191
  }
7✔
192

27✔
193
  /**
27✔
194
   * Set deadline missed callback.
27✔
195
   * @param {function} callback - The callback function to be called.
27✔
196
   */
27✔
197
  set deadline(callback) {
27✔
198
    this._deadline = callback;
4✔
199
  }
4✔
200

27✔
201
  /**
27✔
202
   * Get deadline missed callback.
27✔
203
   * @return {function} - The callback function.
27✔
204
   */
27✔
205
  get deadline() {
27✔
206
    return this._deadline;
1✔
207
  }
1✔
208

27✔
209
  /**
27✔
210
   * Set incompatible QoS callback.
27✔
211
   * @param {function} callback - The callback function to be called.
27✔
212
   */
27✔
213
  set incompatibleQos(callback) {
27✔
214
    this._incompatible_qos = callback;
2✔
215
  }
2✔
216

27✔
217
  /**
27✔
218
   * Get incompatible QoS callback.
27✔
219
   * @return {function} - The callback function.
27✔
220
   */
27✔
221
  get incompatibleQos() {
27✔
222
    return this._incompatible_qos;
1✔
223
  }
1✔
224

27✔
225
  /**
27✔
226
   * Set liveliness lost callback.
27✔
227
   * @param {function} callback - The callback function to be called.
27✔
228
   */
27✔
229
  set liveliness(callback) {
27✔
230
    this._liveliness = callback;
2✔
231
  }
2✔
232

27✔
233
  /**
27✔
234
   * Get liveliness lost callback.
27✔
235
   * @return {function} - The callback function.
27✔
236
   */
27✔
237
  get liveliness() {
27✔
238
    return this._liveliness;
1✔
239
  }
1✔
240

27✔
241
  /**
27✔
242
   * Set incompatible type callback.
27✔
243
   * @param {function} callback - The callback function to be called.
27✔
244
   */
27✔
245
  set incompatibleType(callback) {
27✔
246
    this._incompatible_type = callback;
1✔
247
  }
1✔
248

27✔
249
  /**
27✔
250
   * Get incompatible type callback.
27✔
251
   * @return {function} - The callback function.
27✔
252
   */
27✔
253
  get incompatibleType() {
27✔
254
    return this._incompatible_type;
1✔
255
  }
1✔
256

27✔
257
  /**
27✔
258
   * Set matched callback.
27✔
259
   * @param {function} callback - The callback function to be called.
27✔
260
   */
27✔
261
  set matched(callback) {
27✔
262
    this._matched = callback;
2✔
263
  }
2✔
264

27✔
265
  /**
27✔
266
   * Get matched callback.
27✔
267
   * @return {function} - The callback function.
27✔
268
   */
27✔
269
  get matched() {
27✔
270
    return this._matched;
1✔
271
  }
1✔
272

27✔
273
  createEventHandlers(publisherHandle) {
27✔
274
    if (this._deadline) {
4✔
275
      const deadlineHandle = rclnodejs.createPublisherEventHandle(
3✔
276
        publisherHandle,
3✔
277
        PublisherEventType.PUBLISHER_OFFERED_DEADLINE_MISSED
3✔
278
      );
3✔
279
      this._eventHandlers.push(
3✔
280
        new EventHandler(
3✔
281
          deadlineHandle,
3✔
282
          this._deadline,
3✔
283
          PublisherEventType.PUBLISHER_OFFERED_DEADLINE_MISSED,
3✔
284
          'publisher_event_type'
3✔
285
        )
3✔
286
      );
3✔
287
    }
3✔
288

4✔
289
    if (this._incompatible_qos) {
4✔
290
      const incompatibleQosHandle = rclnodejs.createPublisherEventHandle(
1✔
291
        publisherHandle,
1✔
292
        PublisherEventType.PUBLISHER_OFFERED_INCOMPATIBLE_QOS
1✔
293
      );
1✔
294
      this._eventHandlers.push(
1✔
295
        new EventHandler(
1✔
296
          incompatibleQosHandle,
1✔
297
          this._incompatible_qos,
1✔
298
          PublisherEventType.PUBLISHER_OFFERED_INCOMPATIBLE_QOS,
1✔
299
          'publisher_event_type'
1✔
300
        )
1✔
301
      );
1✔
302
    }
1✔
303

4✔
304
    if (this._liveliness) {
4✔
305
      const livelinessHandle = rclnodejs.createPublisherEventHandle(
1✔
306
        publisherHandle,
1✔
307
        PublisherEventType.PUBLISHER_LIVELINESS_LOST
1✔
308
      );
1✔
309
      this._eventHandlers.push(
1✔
310
        new EventHandler(
1✔
311
          livelinessHandle,
1✔
312
          this._liveliness,
1✔
313
          PublisherEventType.PUBLISHER_LIVELINESS_LOST,
1✔
314
          'publisher_event_type'
1✔
315
        )
1✔
316
      );
1✔
317
    }
1✔
318

4✔
319
    if (this._incompatible_type) {
4!
320
      const incompatibleTypeHandle = rclnodejs.createPublisherEventHandle(
×
UNCOV
321
        publisherHandle,
×
UNCOV
322
        PublisherEventType.PUBLISHER_INCOMPATIBLE_TYPE
×
UNCOV
323
      );
×
324
      this._eventHandlers.push(
×
UNCOV
325
        new EventHandler(
×
UNCOV
326
          incompatibleTypeHandle,
×
UNCOV
327
          this._incompatible_type,
×
UNCOV
328
          PublisherEventType.PUBLISHER_INCOMPATIBLE_TYPE,
×
UNCOV
329
          'publisher_event_type'
×
UNCOV
330
        )
×
UNCOV
331
      );
×
UNCOV
332
    }
×
333

4✔
334
    if (this._matched) {
4✔
335
      const matchedHandle = rclnodejs.createPublisherEventHandle(
1✔
336
        publisherHandle,
1✔
337
        PublisherEventType.PUBLISHER_MATCHED
1✔
338
      );
1✔
339
      this._eventHandlers.push(
1✔
340
        new EventHandler(
1✔
341
          matchedHandle,
1✔
342
          this._matched,
1✔
343
          PublisherEventType.PUBLISHER_MATCHED,
1✔
344
          'publisher_event_type'
1✔
345
        )
1✔
346
      );
1✔
347
    }
1✔
348

4✔
349
    return this._eventHandlers;
4✔
350
  }
4✔
351

27✔
352
  get eventHandlers() {
27✔
353
    return this._eventHandlers;
2✔
354
  }
2✔
355
}
27✔
356

27✔
357
/**
27✔
358
 * @class - Class representing a ROS 2 SubscriptionEventCallbacks
27✔
359
 * @hideconstructor
27✔
360
 */
27✔
361
class SubscriptionEventCallbacks {
27✔
362
  constructor() {
27✔
363
    if (DistroUtils.getDistroId() < DistroUtils.getDistroId('jazzy')) {
8✔
364
      throw new OperationError(
1✔
365
        'SubscriptionEventCallbacks is only available in ROS 2 Jazzy and later',
1✔
366
        {
1✔
367
          code: 'UNSUPPORTED_ROS_VERSION',
1✔
368
          entityType: 'subscription event callbacks',
1✔
369
          details: {
1✔
370
            requiredVersion: 'jazzy',
1✔
371
            currentVersion: DistroUtils.getDistroId(),
1✔
372
          },
1✔
373
        }
1✔
374
      );
1✔
375
    }
1✔
376
    this._deadline = null;
7✔
377
    this._incompatible_qos = null;
7✔
378
    this._liveliness = null;
7✔
379
    this._message_lost = null;
7✔
380
    this._incompatible_type = null;
7✔
381
    this._matched = null;
7✔
382
    this._eventHandlers = [];
7✔
383
  }
8✔
384

27✔
385
  /**
27✔
386
   * Set the callback for deadline missed event.
27✔
387
   * @param {function} callback - The callback function to be called.
27✔
388
   */
27✔
389
  set deadline(callback) {
27✔
390
    this._deadline = callback;
3✔
391
  }
3✔
392

27✔
393
  /**
27✔
394
   * Get the callback for deadline missed event.
27✔
395
   * @return {function} - The callback function.
27✔
396
   */
27✔
397
  get deadline() {
27✔
398
    return this._deadline;
×
UNCOV
399
  }
×
400

27✔
401
  /**
27✔
402
   * Set the callback for incompatible QoS event.
27✔
403
   * @param {function} callback - The callback function to be called.
27✔
404
   */
27✔
405
  set incompatibleQos(callback) {
27✔
406
    this._incompatible_qos = callback;
1✔
407
  }
1✔
408

27✔
409
  /**
27✔
410
   * Get the callback for incompatible QoS event.
27✔
411
   * @return {function} - The callback function.
27✔
412
   */
27✔
413
  get incompatibleQos() {
27✔
414
    return this._incompatible_qos;
×
UNCOV
415
  }
×
416

27✔
417
  /**
27✔
418
   * Set the callback for liveliness changed event.
27✔
419
   * @param {function} callback - The callback function to be called.
27✔
420
   */
27✔
421
  set liveliness(callback) {
27✔
422
    this._liveliness = callback;
2✔
423
  }
2✔
424

27✔
425
  /**
27✔
426
   * Get the callback for liveliness changed event.
27✔
427
   * @return {function} - The callback function.
27✔
428
   */
27✔
429
  get liveliness() {
27✔
430
    return this._liveliness;
×
UNCOV
431
  }
×
432

27✔
433
  /**
27✔
434
   * Set the callback for message lost event.
27✔
435
   * @param {function} callback - The callback function to be called.
27✔
436
   */
27✔
437
  set messageLost(callback) {
27✔
438
    this._message_lost = callback;
2✔
439
  }
2✔
440

27✔
441
  /**
27✔
442
   * Get the callback for message lost event.
27✔
443
   * @return {function} - The callback function.
27✔
444
   */
27✔
445
  get messageLost() {
27✔
446
    return this._message_lost;
1✔
447
  }
1✔
448

27✔
449
  /**
27✔
450
   * Set the callback for incompatible type event.
27✔
451
   * @param {function} callback - The callback function to be called.
27✔
452
   */
27✔
453
  set incompatibleType(callback) {
27✔
454
    this._incompatible_type = callback;
×
UNCOV
455
  }
×
456

27✔
457
  /**
27✔
458
   * Get the callback for incompatible type event.
27✔
459
   * @return {function} - The callback function.
27✔
460
   */
27✔
461
  get incompatibleType() {
27✔
462
    return this._incompatible_type;
×
UNCOV
463
  }
×
464

27✔
465
  /**
27✔
466
   * Set the callback for matched event.
27✔
467
   * @param {function} callback - The callback function to be called.
27✔
468
   */
27✔
469
  set matched(callback) {
27✔
470
    this._matched = callback;
1✔
471
  }
1✔
472

27✔
473
  /**
27✔
474
   * Get the callback for matched event.
27✔
475
   * @return {function} - The callback function.
27✔
476
   */
27✔
477
  get matched() {
27✔
478
    return this._matched;
×
UNCOV
479
  }
×
480

27✔
481
  createEventHandlers(subscriptionHandle) {
27✔
482
    if (this._deadline) {
5✔
483
      const deadlineHandle = rclnodejs.createSubscriptionEventHandle(
3✔
484
        subscriptionHandle,
3✔
485
        SubscriptionEventType.SUBSCRIPTION_REQUESTED_DEADLINE_MISSED
3✔
486
      );
3✔
487
      this._eventHandlers.push(
3✔
488
        new EventHandler(
3✔
489
          deadlineHandle,
3✔
490
          this._deadline,
3✔
491
          SubscriptionEventType.SUBSCRIPTION_REQUESTED_DEADLINE_MISSED,
3✔
492
          'subscription_event_type'
3✔
493
        )
3✔
494
      );
3✔
495
    }
3✔
496

5✔
497
    if (this._incompatible_qos) {
5✔
498
      const incompatibleQosHandle = rclnodejs.createSubscriptionEventHandle(
1✔
499
        subscriptionHandle,
1✔
500
        SubscriptionEventType.SUBSCRIPTION_REQUESTED_INCOMPATIBLE_QOS
1✔
501
      );
1✔
502
      this._eventHandlers.push(
1✔
503
        new EventHandler(
1✔
504
          incompatibleQosHandle,
1✔
505
          this._incompatible_qos,
1✔
506
          SubscriptionEventType.SUBSCRIPTION_REQUESTED_INCOMPATIBLE_QOS,
1✔
507
          'subscription_event_type'
1✔
508
        )
1✔
509
      );
1✔
510
    }
1✔
511

5✔
512
    if (this._liveliness) {
5✔
513
      const livelinessHandle = rclnodejs.createSubscriptionEventHandle(
2✔
514
        subscriptionHandle,
2✔
515
        SubscriptionEventType.SUBSCRIPTION_LIVELINESS_CHANGED
2✔
516
      );
2✔
517
      this._eventHandlers.push(
2✔
518
        new EventHandler(
2✔
519
          livelinessHandle,
2✔
520
          this._liveliness,
2✔
521
          SubscriptionEventType.SUBSCRIPTION_LIVELINESS_CHANGED,
2✔
522
          'subscription_event_type'
2✔
523
        )
2✔
524
      );
2✔
525
    }
2✔
526

5✔
527
    if (this._message_lost) {
5✔
528
      const messageLostHandle = rclnodejs.createSubscriptionEventHandle(
1✔
529
        subscriptionHandle,
1✔
530
        SubscriptionEventType.SUBSCRIPTION_MESSAGE_LOST
1✔
531
      );
1✔
532
      this._eventHandlers.push(
1✔
533
        new EventHandler(
1✔
534
          messageLostHandle,
1✔
535
          this._message_lost,
1✔
536
          SubscriptionEventType.SUBSCRIPTION_MESSAGE_LOST,
1✔
537
          'subscription_event_type'
1✔
538
        )
1✔
539
      );
1✔
540
    }
1✔
541

5✔
542
    if (this._incompatible_type) {
5!
543
      const incompatibleTypeHandle = rclnodejs.createSubscriptionEventHandle(
×
UNCOV
544
        subscriptionHandle,
×
UNCOV
545
        SubscriptionEventType.SUBSCRIPTION_INCOMPATIBLE_TYPE
×
UNCOV
546
      );
×
547
      this._eventHandlers.push(
×
UNCOV
548
        new EventHandler(
×
UNCOV
549
          incompatibleTypeHandle,
×
UNCOV
550
          this._incompatible_type,
×
UNCOV
551
          SubscriptionEventType.SUBSCRIPTION_INCOMPATIBLE_TYPE,
×
UNCOV
552
          'subscription_event_type'
×
UNCOV
553
        )
×
UNCOV
554
      );
×
UNCOV
555
    }
×
556

5✔
557
    if (this._matched) {
5✔
558
      const matchedHandle = rclnodejs.createSubscriptionEventHandle(
1✔
559
        subscriptionHandle,
1✔
560
        SubscriptionEventType.SUBSCRIPTION_MATCHED
1✔
561
      );
1✔
562
      this._eventHandlers.push(
1✔
563
        new EventHandler(
1✔
564
          matchedHandle,
1✔
565
          this._matched,
1✔
566
          SubscriptionEventType.SUBSCRIPTION_MATCHED,
1✔
567
          'subscription_event_type'
1✔
568
        )
1✔
569
      );
1✔
570
    }
1✔
571

5✔
572
    return this._eventHandlers;
5✔
573
  }
5✔
574
}
27✔
575

27✔
576
export {
27✔
577
  PublisherEventCallbacks,
27✔
578
  PublisherEventType,
27✔
579
  SubscriptionEventCallbacks,
27✔
580
  SubscriptionEventType,
27✔
581
  isPublisherEventTypeSupported,
27✔
582
  isSubscriptionEventTypeSupported,
27✔
583
};
27✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc