I am using the nghttp2 library to format the multipart frames to communicate with Alexa. I am currently able to get the response of audio with a multipart message. But, currently it is only possible to send data up to 16KB, I want to do streaming of my recorded data which can be greater than 16KB as a whole.
Can anyone please help me in sending the audio data in the chunk to the AVS using nghttp2?
Looking forward to the response, please help.
Thanks.
In addition, I am adding the reference functions from the code. Please ignore the name convention and other logic as I am just trying this ruffly to send the data over 16KB size.
//Callback function for the data to be send to the server
ssize_t data_prd_read_callback_1(nghttp2_session *session, int32_t stream_id, uint8_t *buf, size_t length,uint32_t *data_flags, nghttp2_data_source *source, void *user_data)
{
//uint8_t send_data[8000];
char send_data[] = "\r\n\r\n--_____FINISH_HERE__________\r\nContent-Disposition: form-data; name=\"metadata\"\r\nContent-Type: application/json; charset=UTF-8\r\n\r\n{\"context\":[{\"header\": {\"namespace\": \"SpeechSynthesizer\",\"name\": \"SpeechState\"},\"payload\": {\"token\":\"\",\"offsetInMilliseconds\":0,\"playerActivity\":\"IDLE\"}}],\"event\":{\"header\":{\"namespace\":\"SpeechRecognizer\",\"name\":\"Recognize\",\"messageId\":\"MID-123456\",\"dialogRequestId\":\"DRID-123456\"},\"payload\":{\"profile\":\"CLOSE_TALK\",\"format\":\"AUDIO_L16_RATE_16000_CHANNELS_1\"}}}\r\n\r\n--_____FINISH_HERE__________\r\nContent-Disposition: form-data; name=\"audio\"\r\nContent-Type: application/octet-stream\r\n\r\n";
int fd = source->fd;
uint8_t *audio_data;
uint8_t *final_data_end, *temp_data;
audio_data = malloc(AUDIO_FILE_SIZE);
memset(audio_data, 0, AUDIO_FILE_SIZE);
final_data_end = malloc(MAX_SIZE_TO_SEND);
temp_data = final_data_end;
memset(final_data_end, 0, MAX_SIZE_TO_SEND);
int r;
r = read(fd, audio_data, AUDIO_FILE_SIZE);
if ( r == -1)
{
printf("JOSHI error while reading audio file\n");
}
int len, i;
len = strlen(send_data);
memcpy(final_data_end, send_data, strlen(send_data));
final_data_end += strlen(send_data);
memcpy(final_data_end, audio_data, AUDIO_FILE_SIZE);
final_data_end += AUDIO_FILE_SIZE;
memcpy(final_data_end, "\r\n--_____FINISH_HERE__________--", 32);
memcpy(buf, temp_data, (strlen(send_data) + AUDIO_FILE_SIZE + 32));
return (strlen(send_data) + AUDIO_FILE_SIZE + 32);
}
static int send_request(struct connection *conn, struct request *req) {
nghttp2_nv nva[] = {
MAKE_NV_LL(":method", "POST"),
MAKE_NV_L(":scheme", "https"),
MAKE_NV_LL(":path", "/v20160207/events" ),
MAKE_NV_LL("authorization", "Bearer "ACCESS_TOKEN""),
MAKE_NV_LL("content-type", "multipart/form-data; boundary=_____FINISH_HERE__________")};
int rv;
nghttp2_data_provider data_prd;
int file_descriptor;
file_descriptor = open ("./audio.raw", O_RDONLY);
if (file_descriptor == -1)
{
printf("error while reading the audio file\n");
}
data_prd.source.fd = file_descriptor; // set the file descriptor
data_prd.read_callback = data_prd_read_callback_1;
rv = nghttp2_submit_request(conn->ngh2, NULL, nva, ARRLEN(nva), &data_prd, req);
temp_stream_id = rv;
if (rv < 0) {
fprintf(stderr, "In second error: (nghttp2_submit_requset) %s\n",nghttp2_strerror(rv));
return -1;
}
return 0;
}
I am using "nghttp2_session_send" for the sending with send_callback function. Whenever I try with file beyond the 16KB size AVS will reply with ERROR "there is no multipart data with status:400". If the whole data is less than 16KB then alexa will reply with audio data attached in response.