@ipcom/asterisk-ari 0.0.140 → 0.0.142

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -58,6 +58,63 @@ client.on('ChannelDtmfReceived', event => {
58
58
  client.closeWebSocket();
59
59
  ```
60
60
 
61
+ ## Event Instances
62
+
63
+ ### Channel and Playback Instances in Events
64
+
65
+ When working with WebSocket events, you get access to both the raw event data and convenient instance objects that allow direct interaction with the channel or playback:
66
+
67
+ ```typescript
68
+ client.on('StasisStart', async event => {
69
+ // event.channel contains the raw channel data
70
+ console.log('New channel started:', event.channel.id);
71
+
72
+ // event.instanceChannel provides a ready-to-use ChannelInstance
73
+ const channelInstance = event.instanceChannel;
74
+
75
+ // You can directly interact with the channel through the instance
76
+ await channelInstance.answer();
77
+ await channelInstance.play({ media: 'sound:welcome' });
78
+ });
79
+
80
+ // Similarly for playback events
81
+ client.on('PlaybackStarted', async event => {
82
+ // event.playback contains the raw playback data
83
+ console.log('Playback ID:', event.playback.id);
84
+
85
+ // event.instancePlayback provides a ready-to-use PlaybackInstance
86
+ const playbackInstance = event.instancePlayback;
87
+
88
+ // Direct control through the instance
89
+ await playbackInstance.control('pause');
90
+ });
91
+ ```
92
+
93
+ This approach provides two key benefits:
94
+ 1. No need to manually create instances using `client.Channel()` or `client.Playback()`
95
+ 2. Direct access to control methods without additional setup
96
+
97
+ ### Comparing Approaches
98
+
99
+ Traditional approach:
100
+ ```typescript
101
+ client.on('StasisStart', async event => {
102
+ // Need to create channel instance manually
103
+ const channel = client.Channel(event.channel.id);
104
+ await channel.answer();
105
+ });
106
+ ```
107
+
108
+ Using instance from event:
109
+ ```typescript
110
+ client.on('StasisStart', async event => {
111
+ // Instance is already available
112
+ await event.instanceChannel.answer();
113
+ });
114
+ ```
115
+
116
+ This feature is particularly useful when handling multiple events and needing to perform actions on channels or playbacks immediately within event handlers.
117
+
61
118
  ### Channel Handling
62
119
 
63
120
  ```typescript
@@ -1025,6 +1025,7 @@ var Bridges = class {
1025
1025
 
1026
1026
  // src/ari-client/resources/channels.ts
1027
1027
  var import_events = require("events");
1028
+ var import_axios2 = require("axios");
1028
1029
 
1029
1030
  // node_modules/uuid/dist/esm/stringify.js
1030
1031
  var byteToHex = [];
@@ -1079,7 +1080,6 @@ function toQueryParams2(options) {
1079
1080
  }
1080
1081
 
1081
1082
  // src/ari-client/resources/channels.ts
1082
- var import_axios2 = require("axios");
1083
1083
  var getErrorMessage = (error) => {
1084
1084
  if ((0, import_axios2.isAxiosError)(error)) {
1085
1085
  return error.response?.data?.message || error.message || "An axios error occurred";
@@ -1127,7 +1127,9 @@ var ChannelInstance = class {
1127
1127
  }
1128
1128
  };
1129
1129
  this.eventEmitter.once(event, wrappedListener);
1130
- console.log(`One-time event listener registered for ${event} on channel ${this.id}`);
1130
+ console.log(
1131
+ `One-time event listener registered for ${event} on channel ${this.id}`
1132
+ );
1131
1133
  }
1132
1134
  /**
1133
1135
  * Removes event listener(s) for a specific WebSocket event type.
@@ -1144,7 +1146,9 @@ var ChannelInstance = class {
1144
1146
  }
1145
1147
  if (listener) {
1146
1148
  this.eventEmitter.off(event, listener);
1147
- console.log(`Specific listener removed for ${event} on channel ${this.id}`);
1149
+ console.log(
1150
+ `Specific listener removed for ${event} on channel ${this.id}`
1151
+ );
1148
1152
  } else {
1149
1153
  this.eventEmitter.removeAllListeners(event);
1150
1154
  console.log(`All listeners removed for ${event} on channel ${this.id}`);
@@ -1198,8 +1202,13 @@ var ChannelInstance = class {
1198
1202
  throw new Error("Channel has already been created");
1199
1203
  }
1200
1204
  try {
1201
- this.channelData = await this.baseClient.post("/channels", data);
1202
- console.log(`Channel originated successfully with ID: ${this.channelData.id}`);
1205
+ this.channelData = await this.baseClient.post(
1206
+ "/channels",
1207
+ data
1208
+ );
1209
+ console.log(
1210
+ `Channel originated successfully with ID: ${this.channelData.id}`
1211
+ );
1203
1212
  return this.channelData;
1204
1213
  } catch (error) {
1205
1214
  const message = getErrorMessage(error);
@@ -1243,13 +1252,18 @@ var ChannelInstance = class {
1243
1252
  if (!this.id) {
1244
1253
  throw new Error("No channel ID associated with this instance");
1245
1254
  }
1246
- const details = await this.baseClient.get(`/channels/${this.id}`);
1255
+ const details = await this.baseClient.get(
1256
+ `/channels/${this.id}`
1257
+ );
1247
1258
  this.channelData = details;
1248
1259
  console.log(`Retrieved channel details for ${this.id}`);
1249
1260
  return details;
1250
1261
  } catch (error) {
1251
1262
  const message = getErrorMessage(error);
1252
- console.error(`Error retrieving channel details for ${this.id}:`, message);
1263
+ console.error(
1264
+ `Error retrieving channel details for ${this.id}:`,
1265
+ message
1266
+ );
1253
1267
  throw new Error(`Failed to get channel details: ${message}`);
1254
1268
  }
1255
1269
  }
@@ -1458,10 +1472,23 @@ var Channels = class {
1458
1472
  }
1459
1473
  channelInstances = /* @__PURE__ */ new Map();
1460
1474
  /**
1461
- * Creates or retrieves a ChannelInstance based on the provided id.
1475
+ * Creates or retrieves a ChannelInstance.
1476
+ *
1477
+ * @param {Object} [params] - Optional parameters for getting/creating a channel instance
1478
+ * @param {string} [params.id] - Optional ID of an existing channel
1479
+ * @returns {ChannelInstance} The requested or new channel instance
1480
+ * @throws {Error} If channel creation/retrieval fails
1481
+ *
1482
+ * @example
1483
+ * // Create new channel without ID
1484
+ * const channel1 = client.channels.Channel();
1485
+ *
1486
+ * // Create/retrieve channel with specific ID
1487
+ * const channel2 = client.channels.Channel({ id: 'some-id' });
1462
1488
  */
1463
- Channel({ id }) {
1489
+ Channel(params) {
1464
1490
  try {
1491
+ const id = params?.id;
1465
1492
  if (!id) {
1466
1493
  const instance = new ChannelInstance(this.client, this.baseClient);
1467
1494
  this.channelInstances.set(instance.id, instance);
@@ -1482,6 +1509,27 @@ var Channels = class {
1482
1509
  throw new Error(`Failed to manage channel instance: ${message}`);
1483
1510
  }
1484
1511
  }
1512
+ /**
1513
+ * Retrieves the details of a specific channel.
1514
+ *
1515
+ * @param {string} id - The unique identifier of the channel to retrieve.
1516
+ * @returns {Promise<Channel>} A promise that resolves to the Channel object containing the channel details.
1517
+ * @throws {Error} If no channel ID is associated with this instance or if there's an error retrieving the channel details.
1518
+ */
1519
+ async get(id) {
1520
+ try {
1521
+ if (id) {
1522
+ throw new Error("No channel ID associated with this instance");
1523
+ }
1524
+ const details = await this.baseClient.get(`/channels/${id}`);
1525
+ console.log(`Retrieved channel details for ${id}`);
1526
+ return details;
1527
+ } catch (error) {
1528
+ const message = getErrorMessage(error);
1529
+ console.error(`Error retrieving channel details for ${id}:`, message);
1530
+ throw new Error(`Failed to get channel details: ${message}`);
1531
+ }
1532
+ }
1485
1533
  /**
1486
1534
  * Removes a channel instance from the collection.
1487
1535
  */
@@ -1510,7 +1558,9 @@ var Channels = class {
1510
1558
  const instance = this.channelInstances.get(event.channel.id);
1511
1559
  if (instance) {
1512
1560
  instance.emitEvent(event);
1513
- console.log(`Event propagated to channel ${event.channel.id}: ${event.type}`);
1561
+ console.log(
1562
+ `Event propagated to channel ${event.channel.id}: ${event.type}`
1563
+ );
1514
1564
  } else {
1515
1565
  console.warn(`No instance found for channel ${event.channel.id}`);
1516
1566
  }
@@ -2017,7 +2067,9 @@ var PlaybackInstance = class {
2017
2067
  }
2018
2068
  };
2019
2069
  this.eventEmitter.on(event, wrappedListener);
2020
- console.log(`Event listener registered for ${event} on playback ${this.id}`);
2070
+ console.log(
2071
+ `Event listener registered for ${event} on playback ${this.id}`
2072
+ );
2021
2073
  }
2022
2074
  /**
2023
2075
  * Registers a one-time event listener for a specific WebSocket event type.
@@ -2035,7 +2087,9 @@ var PlaybackInstance = class {
2035
2087
  }
2036
2088
  };
2037
2089
  this.eventEmitter.once(event, wrappedListener);
2038
- console.log(`One-time event listener registered for ${event} on playback ${this.id}`);
2090
+ console.log(
2091
+ `One-time event listener registered for ${event} on playback ${this.id}`
2092
+ );
2039
2093
  }
2040
2094
  /**
2041
2095
  * Removes event listener(s) for a specific WebSocket event type.
@@ -2049,7 +2103,9 @@ var PlaybackInstance = class {
2049
2103
  }
2050
2104
  if (listener) {
2051
2105
  this.eventEmitter.off(event, listener);
2052
- console.log(`Specific listener removed for ${event} on playback ${this.id}`);
2106
+ console.log(
2107
+ `Specific listener removed for ${event} on playback ${this.id}`
2108
+ );
2053
2109
  } else {
2054
2110
  this.eventEmitter.removeAllListeners(event);
2055
2111
  console.log(`All listeners removed for ${event} on playback ${this.id}`);
@@ -2106,7 +2162,9 @@ var PlaybackInstance = class {
2106
2162
  await this.baseClient.post(
2107
2163
  `/playbacks/${this.id}/control?operation=${operation}`
2108
2164
  );
2109
- console.log(`Operation ${operation} executed successfully on playback ${this.id}`);
2165
+ console.log(
2166
+ `Operation ${operation} executed successfully on playback ${this.id}`
2167
+ );
2110
2168
  } catch (error) {
2111
2169
  const message = getErrorMessage2(error);
2112
2170
  console.error(`Error controlling playback ${this.id}:`, message);
@@ -2164,12 +2222,13 @@ var Playbacks = class {
2164
2222
  playbackInstances = /* @__PURE__ */ new Map();
2165
2223
  /**
2166
2224
  * Gets or creates a playback instance
2167
- * @param {Object} params - Parameters for getting/creating a playback instance
2225
+ * @param {Object} [params] - Optional parameters for getting/creating a playback instance
2168
2226
  * @param {string} [params.id] - Optional ID of an existing playback
2169
2227
  * @returns {PlaybackInstance} The requested or new playback instance
2170
2228
  */
2171
- Playback({ id }) {
2229
+ Playback(params) {
2172
2230
  try {
2231
+ const id = params?.id;
2173
2232
  if (!id) {
2174
2233
  const instance = new PlaybackInstance(this.client, this.baseClient);
2175
2234
  this.playbackInstances.set(instance.id, instance);
@@ -2221,7 +2280,9 @@ var Playbacks = class {
2221
2280
  const instance = this.playbackInstances.get(event.playback.id);
2222
2281
  if (instance) {
2223
2282
  instance.emitEvent(event);
2224
- console.log(`Event propagated to playback ${event.playback.id}: ${event.type}`);
2283
+ console.log(
2284
+ `Event propagated to playback ${event.playback.id}: ${event.type}`
2285
+ );
2225
2286
  } else {
2226
2287
  console.warn(`No instance found for playback ${event.playback.id}`);
2227
2288
  }