Not able to pause, resume, volume change of VMAP Ads playing on chromecast - google-cast

I have created a basic CAF receiver and trying to play ads on chromecast using "vmapAdsRequest" of mediaInformation. Ads are getting played but I am not able to pause, resume or change volume for ads. while I am able to do so if I play Vpaid Ads using same sender app.
/**
* #param {!cast.framework.messages.MediaInformation} mediaInformation
*/
function addBreakToMedia(mediaInformation) {
// VMAP Ads -
mediaInformation.vmapAdsRequest = {
adTagUrl: 'https://pulse-demo.videoplaza.tv/proxy/distributor/v2?rt=vmap_1.0&t=standard-linears,allSupportedAds&bp=10,30&xpb=1&rnd=' + Math.floor(Math.random() * 10000)
}
}
// acquiring a reference to CastReceiverContext, your primary entry point to the whole Receiver SDK
var context = cast.framework.CastReceiverContext.getInstance();
//storing a reference to the PlayerManager, the object handling playback and providing you with all the hooks you need to plug-in your own custom logic
var playerManager = context.getPlayerManager();
playerManager.setMessageInterceptor(
cast.framework.messages.MessageType.LOAD,
loadRequestData => {
addBreakToMedia(loadRequestData.media);
return loadRequestData;
}
);
//Initializing the SDK by calling start() on CastReceiverContext
context.start();

Related

Unable to stream microphone audio to Google Speech to Text with NodeJS

I am going to develop a simple web based Speech to Text project. Develop with NodeJS, ws (WebSocket), and Google's Speech to Text API.
However, I have no luck to get the transcript from Google's Speech to Text API.
Below are my server side codes (server.js):
ws.on('message', function (message) {
if (typeof message === 'string') {
if(message == "connected") {
console.log(`Web browser connected postback.`);
}
}
else {
if (recognizeStream !== null) {
const buffer = new Int16Array(message, 0, Math.floor(message.byteLength / 2));
recognizeStream.write(buffer);
}
}
});
Below are my client side codes (ws.js):
function recorderProcess(e) {
var floatSamples = e.inputBuffer.getChannelData(0);
const ConversionFactor = 2 ** (16 - 1) - 1;
var floatSamples16 = Int16Array.from(floatSamples.map(n => n * ConversionFactor));
ws.send(floatSamples16);
}
function successCallback(stream) {
window.stream = stream;
var audioContext = window.AudioContext;
var context = new audioContext();
var audioInput = context.createMediaStreamSource(stream);
var recorder = context.createScriptProcessor(2048, 1, 1);
recorder.onaudioprocess = recorderProcess;
audioInput.connect(recorder);
recorder.connect(context.destination);
}
When I run the project, and open http://localhost/ in my browser, trying to speaking some sentences to the microphone. Unfortunately, there are no transcription returned, and no error messages returned in NodeJS console.
When I check the status in Google Cloud Console, it only display a 499 code in the dashboard.
Many thanks for helping!
I think the issue could be related to the stream process. Maybe some streaming process is stopped before the end of an operation. My suggestion is to review the callbacks in the JasvaScript code in order to find some “broken" promises.
Also, maybe its obvious but there is a different doc for audios than more than a minute:
https://cloud.google.com/speech-to-text/docs/async-recognize
CANCELLED - The operation was cancelled, typically by the caller.
HTTP Mapping: 499 Client Closed Request
Since the error message, this also could be related to the asynchronous and multithread features of node js.
Hope this works!

Amazon Pinpoint Endpoints in putEvents-Method of the JavaScript SDK aren't working

I've built a AWS Pinpoint integration into my app using API Gateway and Events are properly coming into Pinpoint. However with every new request a new Endpoint is created although I supply the "address"-field.
I went through all the docs provided by AWS:
https://docs.aws.amazon.com/pinpoint/latest/apireference/apps-application-id-events.html
https://docs.aws.amazon.com/pinpoint/latest/developerguide/integrate-events.html
Primarily used this class doc which seems to have some missing info:
https://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/Pinpoint.html
async function putEvent(clientRequest){
/* create the putEvents parameters */
var param = {
ApplicationId: PINPOINT_APP_ID,
EventsRequest: {
BatchItem: { }
}
};
/* create the event parameter */
var eventParam = {
Endpoint: {
Address: clientRequest.deviceId,
ChannelType: 'CUSTOM',
Demographic: {
AppVersion: clientRequest.app.version,
Locale: clientRequest.system.locale,
Make: clientRequest.device.manufacturer,
Model: clientRequest.device.model,
ModelVersion: clientRequest.device.version,
Platform: clientRequest.platform.name,
PlatformVersion: clientRequest.platform.version
}
}
};
/* add the location if its was provided */
if(clientRequest.hasOwnProperty('location')){
/* add the latitude and longitude values */
eventParam.Endpoint['Location'] = {
Latitude: clientRequest.location.latitude,
Longitude: clientRequest.location.longitude
}
/* check if a city and postal code was supplied
alongside the country value */
if(clientRequest.location.hasOwnProperty('cityName') == true
&& clientRequest.location.hasOwnProperty('countryCode') == true
&& clientRequest.location.hasOwnProperty('postalCode') == true){
/* attach to the location param */
eventParam.Endpoint.Location['Country'] = clientRequest.location.countryCode;
eventParam.Endpoint.Location['City'] = clientRequest.location.postalCode;
eventParam.Endpoint.Location['PostalCode'] = clientRequest.location.cityName;
}
}
/* check if the userId was supplied */
if(clientRequest.hasOwnProperty('userId')){
/* attach the hashed and salted user id */
eventParam.Endpoint['User'] = {UserId: getSHA512(clientRequest.userId+USERID_HASHSALT)};
}
/* attach the event values */
eventParam['Events'] = [{
EventType: clientRequest.event.name,
Timestamp: (new Date()).toISOString()
}];
/* create a unique request id */
var requestId = (new Date().getTime()) + Math.floor(Math.random() * 10);
param.EventsRequest.BatchItem[requestId] = eventParam;
/* flush an event to Pinpoint */
await Pinpoint.putEvents(param).promise();
}
After every request I do have a new Pinpoint Endpoint defined, although I provide a unique Address-value for each Endpoint.
a) What do I need to do have the Endpoints unique?
b) How can I report Sign-ins, Sign-out and the other Events?
^ Could not find them in the documentation
Agreed the Pinpoint docs / class document is incomplete leaving out desired information. From my experiencing testing & using the API this is what I have found which hopefully can be of use.
a) What do I need to do have the Endpoints unique?
Pinpoint.putEvents not only creates a new event for an endpoint but it also creates or updates endpoint data
The fact that Pinpoint.putEvents can create or update an endpoint is causing the error you've encountered where a new endpoint is created after every event request.
This is because you are accidentally creating a new endpoint equal to the random requestId for each event that you send when setting the keys of BatchItem. The object keys of BatchItem are actually supposed to be the endpointId the event is supposed to be associated with opposed to the requestId for the event (This is not mentioned at all in the docs!)
To keep endpoints unique you first need to know what the unique endpoint is for the user in addition to the address and unique UserId (This seems to be missing from pinpoint docs. I realized it when trying to update or delete an endpoint which you cannot do by address as you need the endpointId). From your example I would choose something related to the userId concatenated with the channel type if you plan on having multiple channels for a single user as pinpoint does allow messages to be sent through email, sms and recorded voice calls (you've listed "CUSTOM" but I'd try to use one of the enum's that is actually associated with how the message would be delivered. I believe this allows this endpoint to work better with different types of pinpoint campaigns and journeys to send messages to your users)
// Original code adding eventParam to param.EventsRequest.BatchItem incorrectly by random requestId
var requestId = (new Date().getTime()) + Math.floor(Math.random() * 10);
param.EventsRequest.BatchItem[requestId] = eventParam;
// correct code associating eventParam with a unique endpointId
var endpointId = eventParam.Endpoint.User.UserId+'CUSTOM'
param.EventsRequest.BatchItem[endpointId] = eventParam;
Additionally keep in mind that all of the information you have added to eventParam.endpoint will update / overwrite whatever is currently stored for those endpointId attributes when calling Pinpoint.putEvents so watch out for that
b) How can I report Sign-ins, Sign-out and the other Events?
I believe to report sign-ins / sign-outs that are visualized in the pinpoint dashboard follow the event naming convention in the Pinpoint app events documentation
so for sign-ins the event name is _userauth.sign_in
I don't think sign outs are displayed automatically on the Anlaytics -> Usage dashboard but you can use any consistent event name for sign outs and then use pinpoint filters to see those events through time.

Get user join / leave events retroactively from Channels

I'm trying to do some analytics on average response time from some of our users on Twilio Chat.
I'm iterating through my channels, and I'm able to pull the info about messages, so I can compare times a message went un-responded to. However, I can't determine which users were in the channel at that time.
Is there anything on the channel that would give me historic member data? Who was in the channel? The channel.messages().list() method is only giving me the text of the messages sent to the channel and who it was by, but the user who may have been in a channel to respond changes throughout a channel's life time.
This is on the backend using the node.js SDK. note: This isn't a complete implementation for what I'm trying to do, but taking it in steps to get access to the information I'd need to do this. Once I have these messages and know which users are supposed to be in a channel at a given time, I can do the analytics to see how long it took for the users I am looking for to respond.
var fs = require('fs');
const Twilio = require('twilio');
const client = new Twilio(env.TWILIO_ACCOUNT_SID, env.TWILIO_AUTH);
const service = client.chat.services(env.TWILIO_IPM_SERVICE_SID);
async function getChatMessages() {
const fileName = 'fileName.csv';
const getLine = message => {
return `${message.channelSid},${message.sid},${message.dateCreated},${message.from},${message.type},${message.body}\n`;
}
const writeToFile = message => { fs.appendFileSync(fileName, getLine(message)); };
const headerLine = `channelSid,messageSid,dateCreated,author,type,body`;
fs.writeFileSync(fileName, headerLine);
await service.channels.each(
async (channel, done) => {
i++;
let channelSid = channel.sid;
if( channel.messagesCount == 0 ) return;
try {
await channel.messages().list({limit:1000, order:"asc"}).then(
messages => {
messages.forEach( writeToFile );
}
);
} catch(e) {
console.log(`There was an error getting messages for ${channelSid}: ${e.toString()}`);
}
if( i >= max ) done();
}
);
}
I'm beginning to be resigned to the fact that maybe this would only have been possible to track had I set up the proper event listeners / webhooks to begin with. If that's the case, I'd like to know so I can get that set up. But, if there's any endpoint I can reach out to and see who was joining / leaving a channel, that would be ideal for now.
The answer is that unfortunately you can not get this data retroactively. Twilio offers a webhooks API for chat which you can use to track this data yourself as it happens, but if you don't capture the events, you do not get access to them again.

Pubnub - removing a message in history (storage)

I'm working in a instant messaging using pubnub as backend on iOS. After some googling, I found this way but for scala.
http://scalabl3.github.io/pubnub-design-patterns/2015/02/26/Message-Update-Delete.html
I wonder if there is a exist way in API to archive this?
PubNub allows delete messages from the channel
eg:
let startDate = NSNumber(value: (15101397027611671 as CUnsignedLongLong))
let endDate = NSNumber(value: (15101397427611671 as CUnsignedLongLong))
self.client.deleteMessage().channel("channel").start( startDate ).end(
endDate).performWithCompletion ( { (status) in
if !status.isError {
// Messages within specified time frame has been removed.
} else {
/**
* Handle message history download error. Check 'category' property to find out possible
* issue because of which request did fail.
*
* Request can be resent using: status.retry()
*/
}
})
Refer pubnub documentation for more details
Pubnub does not currently support deleting things from message history.

Clean way to pass events to Titanium from webview?

A common explanation of how to pass events from a Titanium webview involves calling Ti.App.fireEvent() from the HTML in the webview. But, I would like to listen to the webview itself instead of the global Ti.App object, so that duplicate events from different webviews won't trigger inappropriate code for the context.
Eg. if I listen to Ti.App for the "OK_BUTTON" event, it will mean something different depending on where in the flow it is being called. So, I would have to remove and add new listeners for each context.
There is a documented way to pass events directly from the webview using a normal HTML anchor tag with the undefined protocol "xxxx://" and catching the ensuing error event in Titanium. Is there a cleaner way to do this yet? It would be nice to keep the "error" event for errors as intended.
I think you'll need to use Ti.App.fireEvent() from the webview but add data identifying the source webview to the event.
e.g. assign a unique id to each of your webviews and pass that into the webview by doing an 'evalJS()' in the webview's 'load' event handler. (Or by setting the id in your html if you have Titanium generating that)
Here is a basic utility module that assigns an id to a webview and provides a function fireEvent() to webview context that will trigger an event on the webView object in Titanium.
var listenerWebViews = {};
exports.createListenerWebView = function(config) {
var id = createRandomString();
var webView = Ti.UI.createWebView(config);
webView.listenerId = id;
webView.evalJS('function fireEvent(type, e) { var f = { originalType:type, listenerId:"'+id+'"}; Ti.App.fireEvent("WEBVIEW_LISTENER_EVENT", f); }');
listenerWebViews[id] = webView;
var oldRemoveFunction = webView.remove;
webView.remove = function(){
listenerWebViews[id] = null;
oldRemoveFunction();
}
return webView;
}
Ti.App.addEventListener("WEBVIEW_LISTENER_EVENT", function(e){
var webView = listenerWebViews[e.listenerId];
if (webView) {
webView.fireEvent(e.originalType, e);
}
});
With that module included, this works:
var view = module.createListenerWebView({
url: 'myPage.html'
});
view.addEventListener('my_type', function(){
alert('webview event!');
});
view.evalJS("fireEvent('my_type');");

Resources