|
128 | 128 | <ref type="application">ConfKick</ref>
|
129 | 129 | <ref type="function">CONFBRIDGE</ref>
|
130 | 130 | <ref type="function">CONFBRIDGE_INFO</ref>
|
| 131 | + <ref type="function">CONFBRIDGE_CHANNELS</ref> |
131 | 132 | </see-also>
|
132 | 133 | </application>
|
133 | 134 | <application name="ConfKick" language="en_US">
|
|
164 | 165 | <ref type="application">ConfBridge</ref>
|
165 | 166 | <ref type="function">CONFBRIDGE</ref>
|
166 | 167 | <ref type="function">CONFBRIDGE_INFO</ref>
|
| 168 | + <ref type="function">CONFBRIDGE_CHANNELS</ref> |
167 | 169 | </see-also>
|
168 | 170 | </application>
|
169 | 171 | <function name="CONFBRIDGE" language="en_US">
|
|
248 | 250 | <para>This function returns a non-negative integer for valid conference
|
249 | 251 | names and an empty string for invalid conference names.</para>
|
250 | 252 | </description>
|
| 253 | + <see-also> |
| 254 | + <ref type="function">CONFBRIDGE_CHANNELS</ref> |
| 255 | + </see-also> |
| 256 | + </function> |
| 257 | + <function name="CONFBRIDGE_CHANNELS" language="en_US"> |
| 258 | + <since> |
| 259 | + <version>16.26.0</version> |
| 260 | + <version>18.12.0</version> |
| 261 | + <version>19.4.0</version> |
| 262 | + </since> |
| 263 | + <synopsis> |
| 264 | + Get a list of channels in a ConfBridge conference. |
| 265 | + </synopsis> |
| 266 | + <syntax> |
| 267 | + <parameter name="type" required="true"> |
| 268 | + <para>What conference information is requested.</para> |
| 269 | + <enumlist> |
| 270 | + <enum name="admins"> |
| 271 | + <para>Get the number of admin users in the conference.</para> |
| 272 | + </enum> |
| 273 | + <enum name="marked"> |
| 274 | + <para>Get the number of marked users in the conference.</para> |
| 275 | + </enum> |
| 276 | + <enum name="parties"> |
| 277 | + <para>Get the number of total users in the conference.</para> |
| 278 | + </enum> |
| 279 | + <enum name="active"> |
| 280 | + <para>Get the number of active users in the conference.</para> |
| 281 | + </enum> |
| 282 | + <enum name="waiting"> |
| 283 | + <para>Get the number of waiting users in the conference.</para> |
| 284 | + </enum> |
| 285 | + </enumlist> |
| 286 | + </parameter> |
| 287 | + <parameter name="conf" required="true"> |
| 288 | + <para>The name of the conference being referenced.</para> |
| 289 | + </parameter> |
| 290 | + </syntax> |
| 291 | + <description> |
| 292 | + <para>This function returns a comma-separated list of channels in a ConfBridge conference, optionally filtered by a type of participant.</para> |
| 293 | + </description> |
| 294 | + <see-also> |
| 295 | + <ref type="function">CONFBRIDGE_INFO</ref> |
| 296 | + </see-also> |
251 | 297 | </function>
|
252 | 298 | <manager name="ConfbridgeList" language="en_US">
|
253 | 299 | <synopsis>
|
@@ -3829,6 +3875,90 @@ static struct ast_custom_function confbridge_info_function = {
|
3829 | 3875 | .read = func_confbridge_info,
|
3830 | 3876 | };
|
3831 | 3877 |
|
| 3878 | +static int func_confbridge_channels(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len) |
| 3879 | +{ |
| 3880 | + char *parse, *outbuf; |
| 3881 | + struct confbridge_conference *conference; |
| 3882 | + struct confbridge_user *user; |
| 3883 | + int bytes, count = 0; |
| 3884 | + size_t outlen; |
| 3885 | + AST_DECLARE_APP_ARGS(args, |
| 3886 | + AST_APP_ARG(type); |
| 3887 | + AST_APP_ARG(confno); |
| 3888 | + ); |
| 3889 | + |
| 3890 | + /* parse all the required arguments and make sure they exist. */ |
| 3891 | + if (ast_strlen_zero(data)) { |
| 3892 | + return -1; |
| 3893 | + } |
| 3894 | + parse = ast_strdupa(data); |
| 3895 | + AST_STANDARD_APP_ARGS(args, parse); |
| 3896 | + if (ast_strlen_zero(args.confno) || ast_strlen_zero(args.type)) { |
| 3897 | + ast_log(LOG_WARNING, "Usage: %s(category,confno)", cmd); |
| 3898 | + return -1; |
| 3899 | + } |
| 3900 | + conference = ao2_find(conference_bridges, args.confno, OBJ_KEY); |
| 3901 | + if (!conference) { |
| 3902 | + ast_debug(1, "No such conference: %s\n", args.confno); |
| 3903 | + return -1; |
| 3904 | + } |
| 3905 | + |
| 3906 | + outbuf = buf; |
| 3907 | + outlen = len; |
| 3908 | + |
| 3909 | + ao2_lock(conference); |
| 3910 | + if (!strcasecmp(args.type, "parties")) { |
| 3911 | + AST_LIST_TRAVERSE(&conference->active_list, user, list) { |
| 3912 | + bytes = snprintf(outbuf, outlen, "%s%s", count++ ? "," : "", ast_channel_name(user->chan)); |
| 3913 | + outbuf += bytes; |
| 3914 | + outlen -= bytes; |
| 3915 | + } |
| 3916 | + AST_LIST_TRAVERSE(&conference->waiting_list, user, list) { |
| 3917 | + bytes = snprintf(outbuf, outlen, "%s%s", count++ ? "," : "", ast_channel_name(user->chan)); |
| 3918 | + outbuf += bytes; |
| 3919 | + outlen -= bytes; |
| 3920 | + } |
| 3921 | + } else if (!strcasecmp(args.type, "active")) { |
| 3922 | + AST_LIST_TRAVERSE(&conference->active_list, user, list) { |
| 3923 | + bytes = snprintf(outbuf, outlen, "%s%s", count++ ? "," : "", ast_channel_name(user->chan)); |
| 3924 | + outbuf += bytes; |
| 3925 | + outlen -= bytes; |
| 3926 | + } |
| 3927 | + } else if (!strcasecmp(args.type, "waiting")) { |
| 3928 | + AST_LIST_TRAVERSE(&conference->waiting_list, user, list) { |
| 3929 | + bytes = snprintf(outbuf, outlen, "%s%s", count++ ? "," : "", ast_channel_name(user->chan)); |
| 3930 | + outbuf += bytes; |
| 3931 | + outlen -= bytes; |
| 3932 | + } |
| 3933 | + } else if (!strcasecmp(args.type, "admins")) { |
| 3934 | + AST_LIST_TRAVERSE(&conference->active_list, user, list) { |
| 3935 | + if (ast_test_flag(&user->u_profile, USER_OPT_ADMIN)) { |
| 3936 | + bytes = snprintf(outbuf, outlen, "%s%s", count++ ? "," : "", ast_channel_name(user->chan)); |
| 3937 | + outbuf += bytes; |
| 3938 | + outlen -= bytes; |
| 3939 | + } |
| 3940 | + } |
| 3941 | + } else if (!strcasecmp(args.type, "marked")) { |
| 3942 | + AST_LIST_TRAVERSE(&conference->active_list, user, list) { |
| 3943 | + if (ast_test_flag(&user->u_profile, USER_OPT_MARKEDUSER)) { |
| 3944 | + bytes = snprintf(outbuf, outlen, "%s%s", count++ ? "," : "", ast_channel_name(user->chan)); |
| 3945 | + outbuf += bytes; |
| 3946 | + outlen -= bytes; |
| 3947 | + } |
| 3948 | + } |
| 3949 | + } else { |
| 3950 | + ast_log(LOG_ERROR, "Invalid keyword '%s' passed to %s.\n", args.type, cmd); |
| 3951 | + } |
| 3952 | + ao2_unlock(conference); |
| 3953 | + ao2_ref(conference, -1); |
| 3954 | + return 0; |
| 3955 | +} |
| 3956 | + |
| 3957 | +static struct ast_custom_function confbridge_channels_function = { |
| 3958 | + .name = "CONFBRIDGE_CHANNELS", |
| 3959 | + .read = func_confbridge_channels, |
| 3960 | +}; |
| 3961 | + |
3832 | 3962 | static int action_confbridgelist_item(struct mansession *s, const char *id_text, struct confbridge_conference *conference, struct confbridge_user *user, int waiting)
|
3833 | 3963 | {
|
3834 | 3964 | struct ast_channel_snapshot *snapshot;
|
@@ -4406,6 +4536,7 @@ static int unload_module(void)
|
4406 | 4536 |
|
4407 | 4537 | ast_custom_function_unregister(&confbridge_function);
|
4408 | 4538 | ast_custom_function_unregister(&confbridge_info_function);
|
| 4539 | + ast_custom_function_unregister(&confbridge_channels_function); |
4409 | 4540 |
|
4410 | 4541 | ast_cli_unregister_multiple(cli_confbridge, ARRAY_LEN(cli_confbridge));
|
4411 | 4542 |
|
@@ -4477,6 +4608,7 @@ static int load_module(void)
|
4477 | 4608 |
|
4478 | 4609 | res |= ast_custom_function_register_escalating(&confbridge_function, AST_CFE_WRITE);
|
4479 | 4610 | res |= ast_custom_function_register(&confbridge_info_function);
|
| 4611 | + res |= ast_custom_function_register(&confbridge_channels_function); |
4480 | 4612 |
|
4481 | 4613 | res |= ast_cli_register_multiple(cli_confbridge, ARRAY_LEN(cli_confbridge));
|
4482 | 4614 |
|
|
0 commit comments