如何解决使用flask和render_template选项无法获得所需的html页面
我是Web开发的新手,我正在尝试构建一个在线记录器,并将一些数据作为反馈从音频(通过单击index.html中的上载获得)反馈到results.html
我试图在python flask app.py文件中创建一些打印语句,以检查事件是否触发了“ POST”,它可以工作并在命令提示符下打印所需的数据列表。但是最后,它没有重定向到results.html,而是再次显示了index.html
大部分代码及其含义摘自
https://blog.addpipe.com/using-recorder-js-to-capture-wav-audio-in-your-html5-web-site/
Record voice with recorder.js and upload it to python-flask server,but WAV file is broken
Python文件
#!/usr/bin/env python
# -*- coding: utf-8 -*-
from flask import Flask
from flask import request
from flask import render_template
import os
import random
import datetime
from detections import clean_dir,get_speech_info
from shutil import copyfile
import numpy as np
import json
from flask import Flask,redirect,url_for,request
app = Flask(__name__)
questions = ['Tell Me About Yourself.','Why Should We Hire You?',' What is Your Greatest Strength?','What is Your Greatest Weakness?','What Are Your Salary Expectations?','How Do You Handle Stress and Pressure?','Describe a Difficult Work Situation or Project and How You Handled It.','What Are Your Goals for The Future?',]
@app.route('/<usr>',methods = ['GET'])
def user(usr):
return f"<h1>hello {usr}</h1>"
data = np.zeros((6))
@app.route("/",methods=['POST','GET'])
def index():
num1 = random.randint(0,len(questions)-1)
ques = questions[num1]
if request.method == "POST":
f = request.files['audio_data']
basepath = os.path.dirname(__file__)
x = str(datetime.datetime.now()).replace(" ","").replace(":","").replace(".","-")+'.wav'
clean_dir(basepath+'/audio/')
with open('audio/'+x,'wb') as audio:
f.save(audio)
print('file uploaded successfully')
global data
data = np.array(get_speech_info(basepath+'/rough')[0])
clean_dir(basepath+'/rough/')
print(data,'post is fired')
return render_template('results.html',data=data)
else:
print(data,'basic file')
return render_template("index.html",q = ques)
if __name__ == "__main__":
app.run(debug = True)
JavaScript
//webkitURL is deprecated but nevertheless
URL = window.URL || window.webkitURL;
var gumStream; //stream from getUserMedia()
var rec; //Recorder.js object
var input; //MediaStreamAudioSourceNode we'll be recording
// shim for AudioContext when it's not avb.
var AudioContext = window.AudioContext || window.webkitAudioContext;
var audioContext //audio context to help us record
var recordButton = document.getElementById("recordButton");
var stopButton = document.getElementById("stopButton");
var pauseButton = document.getElementById("pauseButton");
//add events to those 2 buttons
recordButton.addEventListener("click",startRecording);
stopButton.addEventListener("click",stopRecording);
pauseButton.addEventListener("click",pauseRecording);
window.onload = function () { console.log({{ val }}) };
function sendData() {
var str = 'This is some data';
$.ajax({
url: '/newData',type: 'POST',data: str,success: function (res) { console.log(res) },// res is the response from the server
// (from return request.data)
error: function (error) { console.log(error) }
})
}
function startRecording() {
console.log("recordButton clicked");
/*
Simple constraints object,for more advanced audio features see
https://addpipe.com/blog/audio-constraints-getusermedia/
*/
var constraints = { audio: true,video:false }
/*
Disable the record button until we get a success or fail from getUserMedia()
*/
recordButton.disabled = true;
stopButton.disabled = false;
pauseButton.disabled = false
/*
We're using the standard promise based getUserMedia()
https://developer.mozilla.org/en-US/docs/Web/API/MediaDevices/getUserMedia
*/
navigator.mediaDevices.getUserMedia(constraints).then(function(stream) {
console.log("getUserMedia() success,stream created,initializing Recorder.js ...");
/*
create an audio context after getUserMedia is called
sampleRate might change after getUserMedia is called,like it does on macOS when recording through AirPods
the sampleRate defaults to the one set in your OS for your playback device
*/
audioContext = new AudioContext();
//update the format
document.getElementById("formats").innerHTML="Format: 1 channel pcm @ "+audioContext.sampleRate/1000+"kHz"
/* assign to gumStream for later use */
gumStream = stream;
/* use the stream */
input = audioContext.createMediaStreamSource(stream);
/*
Create the Recorder object and configure to record mono sound (1 channel)
Recording 2 channels will double the file size
*/
rec = new Recorder(input,{numChannels:1})
//start the recording process
rec.record()
console.log("Recording started");
}).catch(function(err) {
//enable the record button if getUserMedia() fails
recordButton.disabled = false;
stopButton.disabled = true;
pauseButton.disabled = true
});
}
function pauseRecording(){
console.log("pauseButton clicked rec.recording=",rec.recording );
if (rec.recording){
//pause
rec.stop();
pauseButton.innerHTML="Resume";
}else{
//resume
rec.record()
pauseButton.innerHTML="Pause";
}
}
function stopRecording() {
console.log("stopButton clicked");
//disable the stop button,enable the record too allow for new recordings
stopButton.disabled = true;
recordButton.disabled = false;
pauseButton.disabled = true;
//reset button just in case the recording is stopped while paused
pauseButton.innerHTML="Pause";
//tell the recorder to stop the recording
rec.stop();
//stop microphone access
gumStream.getAudioTracks()[0].stop();
//create the wav blob and pass it on to createDownloadLink
rec.exportWAV(createDownloadLink);
}
function createDownloadLink(blob) {
var url = URL.createObjectURL(blob);
var au = document.createElement('audio');
var li = document.createElement('li');
var link = document.createElement('a');
//name of .wav file to use during upload and download (without extendion)
var filename = new Date().toISOString();
//add controls to the <audio> element
au.controls = true;
au.src = url;
//save to disk link
link.href = url;
link.download = filename+".wav"; //download forces the browser to donwload the file using the filename
link.innerHTML = "Save to disk";
//add the new audio element to li
li.appendChild(au);
//add the filename to the li
li.appendChild(document.createTextNode(filename+".wav "))
//add the save to disk link to li
li.appendChild(link);
//upload link
var upload = document.createElement('a');
upload.href="/";
upload.innerHTML = "Predict";
upload.addEventListener("click",function(event){
var xhr=new XMLHttpRequest();
xhr.onload=function(e) {
if(this.readyState === 4) {
console.log("Server returned: ",e.target.responseText);
}
};
var fd=new FormData();
fd.append("audio_data",blob,filename);
xhr.open("POST","/",true);
xhr.send(fd);
})
li.appendChild(document.createTextNode (" "))//add a space in between
li.appendChild(upload)//add the upload link to li
//add the li element to the ol
recordingsList.appendChild(li);
}
Index.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Simple Recorder.js demo with record,stop and pause - addpipe.com</title>
<meta name="viewport" content="width=device-width,initial-scale=1.0">
<script src="https://code.jquery.com/jquery-3.5.1.js"></script>
<script src="https://cdn.rawgit.com/mattdiamond/Recorderjs/08e7abd9/dist/recorder.js"></script>
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css">
</head>
<body>
<nav class="navbar navbar-dark bg-primary">
<a class="navbar-brand" href="#">
My Prosodic Features
</a>
</nav>
<div id ="controls" class="container">
<div class="row">
<div class="col-sm">
<div class="jumbotron">
<h1 class="display-4">Hello,People!</h1>
<p class="lead">This is a simple unit,since its campus placement season I wanted to help my friends to know about their prosodic skills.</p>
<p class='lead'>I have used python libraries like librosa and PRAAT for speech processing techniques along with Tensorflow for detection of certain tasks</p>
<hr class="my-4">
<p>We just wanted you know that the results are not 100% accurate,but it provides you some idea about your presentation and speaking skills.</p>
<p>What we do is give some random question and you try to answer it. Make sure you limit yourself upto 1 minute for a preparation time so that you can perform well in real interviews. </p>
<!-- <p class="lead">
<a class="btn btn-primary btn-lg" href="#" role="button">Learn more</a>
</p> -->
</div>
</div>
<div class="col-sm">
<div class="col-sm">
<div class="jumbotron">
<h1 class="display-4"> Question</h1>
<p class = 'lead'>{{ q }}</p>
<p class = 'lead'>
<ol>
<li>Click on Record button</li>
<li>Speak for 5 minutes</li>
<li>Click on upload button</li>
</ol>
<hr class="my-4">
</p>
<button id="recordButton">Record</button>
<button id="pauseButton" disabled>Pause</button>
<button id="stopButton" disabled>Stop</button>
<div id="formats">Format: start recording to see sample rate</div>
<p><strong>Recordings:</strong></p>
<ol id="recordingsList"></ol>
</div>
</div>
</div>
</div>
</div>
<!-- <div id="controls">
<button id="recordButton">Record</button>
<button id="pauseButton" disabled>Pause</button>
<button id="stopButton" disabled>Stop</button>
</div>
<div id="formats">Format: start recording to see sample rate</div>
<p><strong>Recordings:</strong></p>
<ol id="recordingsList"></ol> -->
<!-- inserting these scripts at the end to be able to use all the elements in the DOM -->
<script src="https://code.jquery.com/jquery-3.5.1.js"></script>
<script src="https://cdn.rawgit.com/mattdiamond/Recorderjs/08e7abd9/dist/recorder.js"></script>
<script src={{ url_for('static',filename='js/app.js') }}></script>
</body>
</html>
results.html文件
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width,initial-scale=1.0">
<script src="https://code.jquery.com/jquery-3.5.1.js"></script>
<script src="https://cdn.rawgit.com/mattdiamond/Recorderjs/08e7abd9/dist/recorder.js"></script>
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css">
</head>
<!-- nsyll,npause,dur (s),phonationtime (s),speechrate (nsyll/dur),articulation rate (nsyll / phonationtime),-->
<body>
<table class="table">
<thead class="thead-dark">
<tr>
<th scope="col">#</th>
<th scope="col">Feature</th>
<th scope="col">Result</th>
<th scope="col">Average Result</th>
</tr>
</thead>
<tbody>
<tr>
<th scope="row">1</th>
<td>nsyll</td>
<td>{{ data[0] }}</td>
<td>@fat</td>
</tr>
<tr>
<th scope="row">2</th>
<td>npause</td>
<td>{{ data[1] }}</td>
<td>@twitter</td>
</tr>
<tr>
<th scope="row">3</th>
<td>dur</td>
<td>{{ data[2] }}</td>
<td>@twitter</td>
</tr>
<tr>
<th scope="row">4</th>
<td>phonationtime</td>
<td>{{ data[3] }}</td>
<td>@twitter</td>
</tr>
<tr>
<th scope="row">5</th>
<td>speechrate</td>
<td>{{ data[4] }}</td>
<td>@twitter</td>
</tr>
<tr>
<th scope="row">6</th>
<td>articulation rate</td>
<td>{{ data[5] }}</td>
<td>@twitter</td>
</tr>
</tbody>
</table>
</body>
解决方法
模板文件应位于与Python文件位于同一目录级别的名为templates
的文件夹中。
例如
project
|---run.py
|---templates
| |---index.html
| |---results.html
|---static
|---js
|---app.js
如果这对您有帮助,请投票并接受。 :)
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。