3

I want to send a audio blob from JS to python script (which runs on server). My JS ajax .. looks something like this.

var fileType = 'audio';
var fileName = 'output.wav';
var formData = new FormData();
formData.append(fileType + '-filename', fileName);
formData.append(fileType + '-blob', blob);
    $.ajax({
    type: 'POST',
    url: 'http://localhost/python/audio.py',
    data: {audio:formData},
        success: function(response) {
        alert(respose);
    }
   }); 

and my python script looks like this.

#!/usr/bin/python3
print("Content-Type: text/html")
print()
import ssl
import cgi
import wave
import contextlib
form = cgi.FieldStorage()
fname = form.getvalue("audio", "error")
with contextlib.closing(wave.open(fname,'r')) as f:
    frames = f.getnframes()
    rate = f.getframerate()
    duration = frames / float(rate)
    print(duration)

Right now, I am just testing, so it should get me the duration of the audio file. The blob is generated through record.js

This is not working, as the python is unable to identify the file. Any solutions?

PS: I am using Xampp Server, to run on local host.

In response to Wojtek Marczenko: The error is

[Mon Apr 04 18:26:09.537912 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215: Traceback (most recent call last):: /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.537978 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:   File "/home/shashank/project/dutchman/python/audio.py", line 10, in <module>: /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538002 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:     with contextlib.closing(wave.open(fname,'r')) as f:: /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538024 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:   File "/usr/lib/python3.5/wave.py", line 499, in open: /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538036 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:     return Wave_read(f): /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538056 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:   File "/usr/lib/python3.5/wave.py", line 163, in __init__: /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538065 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:     self.initfp(f): /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538086 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:   File "/usr/lib/python3.5/wave.py", line 128, in initfp: /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538097 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:     self._file = Chunk(file, bigendian = 0): /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538110 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:   File "/usr/lib/python3.5/chunk.py", line 61, in __init__: /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538119 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215:     self.chunkname = file.read(4): /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
[Mon Apr 04 18:26:09.538132 2016] [cgi:error] [pid 5330] [client ::1:60802] AH01215: AttributeError: 'NoneType' object has no attribute 'read': /home/shashank/project/dutchman/python/audio.py, referer: http://localhost/index.html
4
  • At which point is it "not working"? Does the python receive the audio form data? You also typed response wrong when trying to alert() Commented Apr 4, 2016 at 12:38
  • Okay, there seems to be some problem, The ajax is causing "jquery.min.js:2846 Uncaught TypeError: Illegal invocation". As if i comment out ajax, the error seems to disappear. Commented Apr 4, 2016 at 12:43
  • I tend to use google chrome's developer tools to see what data is actually been sent from your ajax/javascript form. Commented Apr 4, 2016 at 12:45
  • The problem now seems to be in accessing data from python, rather than of JS, but I am not a expert. How do use developer tools to see what data is being sent ? Never saw such stuff . @DannyCullen Commented Apr 4, 2016 at 13:10

2 Answers 2

2

It looks like you're not properly sending the blob as form field. The proper way to attach blob to FormData would be formData.append(fileType, blob, fileName);. Also you should attach just the formData instead of nesting it in another object:

var formData = new FormData();
formData.append(fileType, blob, fileName);
$.ajax({
    type: 'POST',
    url: 'http://localhost/python/audio.py',
    data: formData,
    processData: false,  // prevent jQuery from converting the data
    contentType: false,  // prevent jQuery from overriding content type
    success: function(response) {
        alert(response);
    }
});

Sources: https://developer.mozilla.org/en-US/docs/Web/API/FormData/append http://www.mattlunn.me.uk/blog/2012/05/sending-formdata-with-jquery-ajax/

On the python side, you need to use the CGI module according to the python docs (can't post more links). I believe the proper way would be like this:

form = cgi.FieldStorage()
fname = form["audio"].filename
print "Got filename:", fname  # in case of problems see if this looks ok

with contextlib.closing(wave.open(fname,'r')) as f:
    ...
Sign up to request clarification or add additional context in comments.

2 Comments

How do i recover the this file in python ? There seems still to be some problem. I am adding the error in question, as comments seem to have character limits
Updated the answer, you can also see examples in the docs (docs.python.org/2/library/cgi.html) if you search for 'filename'
0

I had an error in retrieving the audio bytes, it turned out to be a cursor problem so beware.

Files in a FormData request can be accessed at request.files then you can select the file you included in the FormData e.g. request.files['audio'].

So now if you want to access the actual bytes of the file, in our case 'audio' using .stream, you should make sure first that your cursor points to the first byte and not to the end of the file, in which case you will get empty bytes.

Hence, a good way to do it:

file = request.files['audio']
file.stream.seek(0)
audio = file.read()

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.