I have this line which needs to recieve a message from the discord text channel.
choice = video[int.Parse(CommandHandler.message .Content)-1].Url;
I tried a lot of things, including searching in the api but I don't have a clue.
Here is the command
[Command("join", RunMode= RunMode.Async), Summary("joins voice channel")]
public async Task joinvoice([Remainder, Summary("The text to echo")] string searchP="")
{
IVoiceChannel voicechannel = (CommandHandler.Last as IGuildUser).VoiceChannel;
if (voicechannel == null)
{
await ReplyAsync("u have to be in a channel first");
return;
}
string choice = "";
VideoSearch SearchRisolts = new VideoSearch();
if (searchP != "")
{
if (searchP.Contains("https://"))
choice = searchP;
else
{
List<VideoInformation> video = SearchRisolts.SearchQuery(searchP, 1);
await ReplyAsync("1) " + video[0].Title + "\n\n2) " + video[1].Title + "\n\n3) " + video[2].Title);
choice = video[int.Parse(CommandHandler.message .Content)-1].Url;//here i need to recive a message from the chat
}
}
if (voicechannel != Program.voicechannel)
{
Program.audioClient = await voicechannel.ConnectAsync();
Program.voicechannel = voicechannel;
}
if (Program.audioClient!=null)
await SendAsync(Program.audioClient, choice);
}
The class containing this function should derive from BaseModule<ICommandContext>
This BaseModule contains the Context, which in place contains the message you are looking for.
Context.Message.Content
Related
I’ m currently debugging a webrtc UWP app, and it is fairly working.
But it happens that the remote stream is not displayed on my MediaElement each time. It’s like the video track is not received although I add it ASAP as recommended. I can’t figure out why it is happening ; is it a code or a network problem ? I grab the stream randomly whatever the network, sometimes successfully, other times not (staying with the same confits).
I use the google STUN servers, and the google webrtc « peer connection server » signaling server on a remote windows server, nothing is installed on my LAN (but my UWP program).
I don’t know what to do to figure out the cause ... any help would be appreciated.
private void Signaller_OnMessageFromPeer(int peerId, string message)
{
Task.Run(async () =>
{
// Debug.Assert(_peerId == peerId || _peerId == -1);
Debug.Assert(message.Length > 0);
if (_peerId != peerId && _peerId != -1)
{
Debug.WriteLine("[Error] Conductor: Received a message from unknown peer while already in a conversation with a different peer.");
return;
}
if (!JsonObject.TryParse(message, out JsonObject jMessage))
{
Debug.WriteLine("[Error] Conductor: Received unknown message." + message);
return;
}
string type = jMessage.ContainsKey(kSessionDescriptionTypeName) ? jMessage.GetNamedString(kSessionDescriptionTypeName) : null;
if (_peerConnection == null)
{
if (!String.IsNullOrEmpty(type))
{
// Create the peer connection only when call is
// about to get initiated. Otherwise ignore the
// messages from peers which could be a result
// of old (but not yet fully closed) connections.
if (type == "offer" || type == "answer")
{
Debug.Assert(_peerId == -1);
_peerId = peerId;
connectToPeerCancelationTokenSource = new CancellationTokenSource();
connectToPeerTask = CreatePeerConnection(connectToPeerCancelationTokenSource.Token);
bool connectResult = await connectToPeerTask;
connectToPeerTask = null;
connectToPeerCancelationTokenSource.Dispose();
if (!connectResult)
{
Debug.WriteLine("[Error] Conductor: Failed to initialize our PeerConnection instance");
await Signaller.SignOut();
return;
}
else if (_peerId != peerId)
{
Debug.WriteLine("[Error] Conductor: Received a message from unknown peer while already in a conversation with a different peer.");
return;
}
}
}
else
{
Debug.WriteLine("[Warn] Conductor: Received an untyped message after closing peer connection.");
return;
}
}
if (!String.IsNullOrEmpty(type))
{
if (type == "offer-loopback")
{
// Loopback not supported
Debug.Assert(false);
}
string sdp = jMessage.ContainsKey(kSessionDescriptionSdpName) ? jMessage.GetNamedString(kSessionDescriptionSdpName) : null;
if (String.IsNullOrEmpty(sdp))
{
Debug.WriteLine("[Error] Conductor: Can't parse received session description message.");
return;
}
RTCSdpType sdpType = RTCSdpType.Offer;
switch (type)
{
case "offer":
sdpType = RTCSdpType.Offer;
break;
case "answer":
sdpType = RTCSdpType.Answer;
break;
case "pranswer":
sdpType = RTCSdpType.Pranswer;
break;
default:
Debug.Assert(false, type);
break;
}
Debug.WriteLine("Conductor: Received session description: " + message + "\r\n" + sdp);
await _peerConnection.SetRemoteDescription(new RTCSessionDescription(sdpType, sdp));
if (sdpType == RTCSdpType.Offer)
{
RTCSessionDescription answer = await _peerConnection.CreateAnswer();
await _peerConnection.SetLocalDescription(answer);
// Send answer
SendSdp(answer);
Debug.WriteLine(String.Format("Conductor: Session Description to be sent : {0}", answer.Sdp));
}
}
else
{
var sdpMid = jMessage.ContainsKey(kCandidateSdpMidName) ? jMessage.GetNamedString(kCandidateSdpMidName) : null;
var sdpMlineIndex = jMessage.ContainsKey(kCandidateSdpMlineIndexName) ? jMessage.GetNamedNumber(kCandidateSdpMlineIndexName) : -1;
var sdp = jMessage.ContainsKey(kCandidateSdpName) ? jMessage.GetNamedString(kCandidateSdpName) : null;
if (String.IsNullOrEmpty(sdpMid) || sdpMlineIndex == -1 || String.IsNullOrEmpty(sdp))
{
Debug.WriteLine("[Error] Conductor: Can't parse received message.\n" + message);
return;
}
var candidate = new RTCIceCandidate(sdp, sdpMid, (ushort)sdpMlineIndex);
await _peerConnection.AddIceCandidate(candidate);
Debug.WriteLine("Conductor: Received candidate : " + message);
}
}).Wait();
}
i have this code line
if (channel.GetUsersAsync().Contains(Program.kami.CurrentUser as IGuildUser))
do something;
it writes an exception which says IAsyncEnumerable> doesnt contain the definition of contains
and i dont know what to do
[Command("join", RunMode=RunMode.Async), Summary("joins voice channel")]
public async Task joinvoice([Remainder, Summary("The text to echo")] string searchP="")
{
IVoiceChannel channel = (CommandHandler.Last as IGuildUser).VoiceChannel;
if (channel == null)
{
await ReplyAsync("u have to be in a channel first");
return;
}
string choice = "";
VideoSearch SearchRisolts = new VideoSearch();
if (searchP != "")
{
if (searchP.Contains("https://"))
choice = searchP;
else
{
List<VideoInformation> video = SearchRisolts.SearchQuery(searchP, 1);
await ReplyAsync("* " + video[0].Title + "\n\n* " + video[1].Title + "\n\n* " + video[2].Title);
//choice = video[int.Parse() - 1].Url;
}
this.Context.Channel.GetMessagesAsync(1).First();
}
IAsyncEnumerable<IReadOnlyCollection<IUser>> x = channel.GetUsersAsync();
if ((await channel.GetUsersAsync()).Contains(Program.kami.CurrentUser as IGuildUser))
var audioClient = await channel.ConnectAsync();
await SendAsync(audioClient,choice);
}
You need to await a GetUserAsync operations
(await channel.GetUsersAsync()).Contains(....)
Be sure that your method is async.
I have two forms. I need to access both the forms based on the user Input.
The forms are as follows
internal static IDialog<JObject> BuildTravelForm()
{
travelstatus = 1;
leaveStatus = 0;
return Chain.From(() => FormDialog.FromForm(TravelForm.BuildForm))
.Do(async (context, order) =>
{
try
{
travelstatus = 0;
var completed = await order;
string source = (string)completed.GetValue("Question1");
string destination = (string)completed.GetValue("Question2");
await context.PostAsync("Your travel request is awaiting approval" + " " + "from" + " " + source + " " + "to" + " " + destination);
}
catch (Exception)
{
await context.PostAsync("Thank you");
}
});
}
The second one goes like this
internal static IDialog<JObject> BuildLeaveForm()
{
leaveStatus = 1;
travelstatus = 0;
return Chain.From(() => FormDialog.FromForm(LeaveForm.BuildForm))
.Do(async (context,order)=>
{
leaveStatus = 0;
var completed = await order;
string startDate = (string)completed.GetValue("Question1");
string endDate = (string)completed.GetValue("Question2");
await context.PostAsync("Your leave is applied" + " " + "from" + " " + startDate + " " + "to" + " " + endDate);
});
}
The controller method is as follows
public async Task<Activity> Post([FromBody]Activity activity)
{
try
{
if (activity.Type == ActivityTypes.Message)
{
if (leaveStatus == 1 && travelstatus==0)
{
//nested if to check intents to follow
await Conversation.SendAsync(activity, BuildLeaveForm);
}
else if(travelstatus == 1 && leaveStatus==0)
{
await Conversation.SendAsync(activity, BuildTravelForm);
}
else
{
ConnectorClient connector = new ConnectorClient(new Uri(activity.ServiceUrl));
StateClient stateClient = activity.GetStateClient();
string replyMessage = "";
Luis stluis = await GetEntityFromLUIS(activity.Text);
if (stluis.intents.Count() > 0)
{
Activity reply;
///await Conversation.SendAsync(activity, MakeGreetings);
using (var file = Assembly.GetExecutingAssembly().GetManifestResourceStream("Javis_V2.IntentLibrary.json"))
{
o2 = JObject.Parse(new StreamReader(file).ReadToEnd());
string luisIntent = stluis.intents[0].intent;
if (luisIntent == "LeaveManager")
{
await Conversation.SendAsync(activity, BuildLeaveForm);
}
else if(luisIntent=="TravelManager")
{
await Conversation.SendAsync(activity, BuildTravelForm);
}
else
{
leaveStatus = 0;
travelstatus = 0;
replyMessage = (string)o2.GetValue(luisIntent);
if(replyMessage=="")
{
replyMessage = "Sorry! Not getting you";
}
reply = activity.CreateReply(replyMessage);
await connector.Conversations.ReplyToActivityAsync(reply);
}
}
}
}
}
else
{
HandleSystemMessage(activity);
}
return null;
}
catch (Exception exp)
{
Debug.WriteLine(exp);
return null;
}
}
The problem is that when the first form is completed, and when the second form is triggered through luis intent, the first form pops up. I am looking for something without the use of Dialogs.
Any kind of help is appreciated.
Thanks in advance.
This line is the issue :
if (leaveStatus == 1 && travelstatus==0)
{
//nested if to check intents to follow
await Conversation.SendAsync(activity, BuildLeaveForm);
await connector.Conversations.ReplyToActivityAsync(activity.CreateReply("Thanks"));
}
else if(travelstatus == 1 && leaveStatus==0)
{
await Conversation.SendAsync(activity, BuildTravelForm);
await connector.Conversations.ReplyToActivityAsync(activity.CreateReply("Thanks"));
}
If you see on the above code, the BuildTravelForm or BuildLeaveForm can clearly generate an error and end it without calling the Chain operation Do. If everything executes ok, it will call Do otherwise it will simply skip it. So the best place to reset the status is after the await statement which is ensured to be called after the completion of the dialog.
I will do like this :
if (leaveStatus == 1 && travelstatus==0)
{
//nested if to check intents to follow
await Conversation.SendAsync(activity, BuildLeaveForm);
travelstatus =0; leaveStatus=0;
await connector.Conversations.ReplyToActivityAsync(activity.CreateReply("Thanks"));
}
else if(travelstatus == 1 && leaveStatus==0)
{
await Conversation.SendAsync(activity, BuildTravelForm);
travelstatus =0; leaveStatus=0;
await connector.Conversations.ReplyToActivityAsync(activity.CreateReply("Thanks"));
}
Do check if it works well.
I am currently building an Android messaging app and I am trying to send notifications to all users who are part of a group. I have an Azure Notification Hub set up which is working fine for sending a notification to all devices that are registered, but I cannot seem to get it working for just a subset of all user ie a group.
The devices register with Azure and with GCM on startup.
I have tried using "Tags" to try send a notification to an individual but I am not sure if I am doing it right... I must not be because it isn't working!
In the following code I am trying to send a notification to an individual by using their username as a Tag...
This is the code in my service to send a notification:
// POST api/notification
public async Task<IHttpActionResult> Post([FromBody]Notification notification)
{
var notificationToSave = new Notification
{
NotificationGuid = Guid.NewGuid().ToString(),
TimeStamp = DateTime.UtcNow,
Message = notification.Message,
SenderName = notification.SenderName
};
var recipientNames = await GetRecipientNamesFromNotificationHub();
var recipientNamesString = CreateCustomRecipientNamesString(recipientNames);
string notificationJsonPayload =
"{\"data\" : " +
" {" +
" \"message\": \"" + notificationToSave.Message + "\"," +
" \"senderName\": \"" + notificationToSave.SenderName + "\"," +
" \"recipientNames\": \"" + recipientNamesString + "\"" +
" }" +
"}";
var result = await _hubClient.SendGcmNativeNotificationAsync(notificationJsonPayload, "ken#test.com"); // If this second parameter is omitted then a notification is sent to all registered devices.
notificationToSave.TrackingId = result.TrackingId;
notificationToSave.Recipients = recipientNames;
await Session.StoreAsync(notificationToSave);
return Ok(notificationToSave);
}
And this is how I am registering a device on the Android side:
private void sendRegistrationIdToBackend(String registrationId) {
String backendBaseUrl = "http://myurl.net/";
if (backendBaseUrl == null || backendBaseUrl == "")
{
return;
}
PushNotificationClient client = new PushNotificationClient(backendBaseUrl);
Device device = createDevice(registrationId);
client.registerDevice(device, new Callback<Device>() {
#Override
public void success(Device device, Response response) {
//writeStringToSharedPreferences(SettingsActivity.SETTINGS_KEY_DEVICEGUID, device.DeviceGuid);
Toast.makeText(context, "Device successfully registered with backend, DeviceGUID=" + device.DeviceGuid, Toast.LENGTH_LONG).show();
}
#Override
public void failure(RetrofitError retrofitError) {
Toast.makeText(context, "Backend registration error:" + retrofitError.getMessage(), Toast.LENGTH_LONG).show();
}
});
Log.i(TAG, registrationId);
}
private Device createDevice(String registrationId) {
Device device = new Device();
device.Platform = "Android";
device.Token = registrationId;
device.UserName = LogInActivity.loggedInUser;
device.DeviceGuid = null;
//todo set device.PlatformDescription based on Android version
device.SubscriptionCategories = new ArrayList<>();
device.SubscriptionCategories.add("ken#test.com"); // This should be adding this username as a Tag which is referenced in the service.... Not sure if this is how I should do it!
return device;
}
This is how I registering a device:
private async Task<RegistrationDescription> RegisterDeviceWithNotificationHub(Device device)
{
var hubTags = new HashSet<string>()
.Add("user", new[] { device.UserName })
.Add("category", device.SubscriptionCategories);
var hubRegistrationId = device.HubRegistrationId ?? "0";//null or empty string as query input throws exception
var hubRegistration = await _hubClient.GetRegistrationAsync<RegistrationDescription>(hubRegistrationId);
if (hubRegistration != null)
{
hubRegistration.Tags = hubTags;
await _hubClient.UpdateRegistrationAsync(hubRegistration);
}
else
{
hubRegistration = await _hubClient.CreateGcmNativeRegistrationAsync(device.Token, hubTags);
}
return hubRegistration;
}
good evening.
You should try check your registrations by using Visual studio 2015.
Install it, connect azure, azure hubs, registred devices. And try send your test message on test token (+check "does your registration exist on notification hub").
Outline
I am trying to implement WNS for my app game. I currently send a notification upon creation of a new user with the following function which works:
public async void SendNotificationToTag(string tag, string content)
{
var wnsToast = "<toast><visual><binding template=\"ToastText01\">"
+ "<text id=\"1\">Breaking " +content + "An WNS News!"
+ "</text></binding></visual></toast>";
WindowsPushMessage wnsMessage = new WindowsPushMessage();
wnsMessage.XmlPayload = wnsToast;
await Services.Push.HubClient.SendWindowsNativeNotificationAsync(wnsToast, tag);
Services.Log.Info("WNS TEST - SendWindowsNativeNotificationAsync - done");
}
I get a notfication to each username, i.e. a personal notificaion. I then update the tags the user listens to, looking in the hub database this also seems to work:
-Usernamecph--gameID1151--gameID1152--gameID1153--gameID1154--gameID1155--gameID1156--gameID1157--gameID1158
-gameID1157--UsernameFyn--gameID1151--gameID1153--gameID1155--gameID1156-
This check to extract the tags from the hub is done using
foreach (Microsoft.ServiceBus.Notifications.RegistrationDescription t in a)
{
string tempstring = "";
foreach (string x in t.Tags)
tempstring += "-" + x + "-";
Services.Log.Info(tempstring + t.RegistrationId + t.ETag);
}
So far so good.
When I then try to send to one of the other tags than the usernames I do not receive any notification, and I do not receive any error in the log. Am I missing something?
Update - Half Solution
If I use the server Explorer and look at the notification HUB. I can see all the tags, and I can send to them by using the test send. But I cannot seem to do it in other function calls online.
Is it something like the function has to be set as post or get?
YES
So inserting [HttpPost] Seems to enable the push.
However when I look in the Server explorer shown here on the image:
The user seems to be deleted when I update the registrations (There should be three, and there is again when I start the app with the correct tag subscriptions). So Maybe the question is How to Update a registration in the hub correctly
The current update code:
public async void updateRegistration(RegistrationDescription registration, List<string> TAGS)
{
registration.Tags = new HashSet<string>(TAGS);
try
{
var x = await hub.CreateOrUpdateRegistrationAsync(registration);
// apiServices.Log.Info(x.ExpirationTime + " " + x.Tags);
}
catch (MessagingException e)
{
ReturnGoneIfHubResponseIsGone(e);
}
}
The code that calls the function:
private async Task<bool> RegisterHubTag(User user, string Tag)
{
List<string> sendTAGs = new List<string>();
Services.Log.Info("RegisterHubTag Function");
using (Db db = new Db())
{
List<DataObjects.NotificationTag> userTags = db.NotificationTags.Where(t => t.User.UserId == user.UserId).ToList<DataObjects.NotificationTag>();
if (userTags.Count < 1)
{
//Register
RegisterController.DeviceRegistration Reg = CreateDeviceRegistration(user.PushChannelUri, sendTAGs);
Microsoft.Azure.NotificationHubs.RegistrationDescription registration = null;
//Microsoft.ServiceBus.Notifications.RegistrationDescription registration = null;
Services.Log.Info(Reg.Handle);
Services.Log.Info(Reg.Platform);
IEnumerable<string> tagsToRegister;
List<string> test = new List<string>() { user.Username };
if(Tag != user.Username)
test.Add(Tag);
tagsToRegister = test.AsEnumerable<string>();
switch (Reg.Platform)
{
case "mpns":
registration = new MpnsRegistrationDescription(Reg.Handle);
break;
case "wns":
registration = new WindowsRegistrationDescription(Reg.Handle);
break;
case "apns":
registration = new AppleRegistrationDescription(Reg.Handle);
break;
case "gcm":
registration = new GcmRegistrationDescription(Reg.Handle);
break;
default:
throw new HttpResponseException(HttpStatusCode.BadRequest);
}
var regID = await hub.Post(Services);
registration.RegistrationId = regID;
db.NotificationTags.Add(new DataObjects.NotificationTag() { User = user, tag = user.Username, RegistrationID = registration.RegistrationId });
hub.updateRegistration(registration, test);
db.SaveChanges();
}
else
{
RegisterController.DeviceRegistration Reg = CreateDeviceRegistration(user.PushChannelUri, sendTAGs);
Microsoft.Azure.NotificationHubs.RegistrationDescription registration = null;
//Microsoft.ServiceBus.Notifications.RegistrationDescription registration = null;
switch (Reg.Platform)
{
case "mpns":
registration = new MpnsRegistrationDescription(Reg.Handle);
break;
case "wns":
registration = new WindowsRegistrationDescription(Reg.Handle);
break;
case "apns":
registration = new AppleRegistrationDescription(Reg.Handle);
break;
case "gcm":
registration = new GcmRegistrationDescription(Reg.Handle);
break;
default:
throw new HttpResponseException(HttpStatusCode.BadRequest);
}
registration.RegistrationId = userTags[0].RegistrationID;
IEnumerable<string> tagsToRegister;
List<string> test = new List<string>();
foreach (DataObjects.NotificationTag t in userTags)
test.Add(t.tag);
test.Add(Tag);
tagsToRegister = test.AsEnumerable<string>();
hub.updateRegistration(registration, test);
}
}
return true;
}
private RegisterController.DeviceRegistration CreateDeviceRegistration(string channelUri, List<string> tags)
{
return new RegisterController.DeviceRegistration() { Platform = "wns", Handle = channelUri, Tags = tags.ToArray<string>() };
}
New image
I really do not understand it, sometimes I have three registrations, but then in the counter in the bottom is still only saying 2 ? How can this be?
(The view is from the server explorer in VS2013)