Spaces:
Runtime error
Runtime error
| <html lang="en"> | |
| <head> | |
| <meta charset="UTF-8"> | |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> | |
| <title>CSV File Editor</title> | |
| <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.5.2/css/bootstrap.min.css"> | |
| <style> | |
| .container { | |
| margin-top: 20px; | |
| } | |
| .btn { | |
| margin-top: 20px; | |
| } | |
| .form-control { | |
| width: 100%; | |
| } | |
| .data-section { | |
| margin-top: 40px; | |
| } | |
| .table-container { | |
| overflow-x: auto; | |
| } | |
| .table-wrapper { | |
| display: flex; | |
| justify-content: space-between; | |
| gap: 20px; | |
| } | |
| .table-wrapper table { | |
| width: 100%; | |
| } | |
| </style> | |
| </head> | |
| <body> | |
| <div class="container"> | |
| <h2 class="mb-4">Upload, View, and Edit CSV File</h2> | |
| <!-- CSV Upload Section --> | |
| <form method="POST" action="/upload_csv" enctype="multipart/form-data"> | |
| <div class="form-group"> | |
| <label for="csvFile">Upload CSV File:</label> | |
| <input type="file" name="csv_file" id="csvFile" class="form-control-file" accept=".csv" required> | |
| <button type="submit" class="btn btn-primary">Upload CSV</button> | |
| </form> | |
| <!-- Instruction Section --> | |
| <form method="POST" action="/edit_csv"> | |
| <!-- Buttons for Speech Recording --> | |
| <div class="mt-4"> | |
| <button type="button" id="recordButton" class="btn btn-danger">🎤 Record</button> | |
| <button type="button" id="stopButton" class="btn btn-secondary" disabled>⏹ Stop</button> | |
| </div> | |
| <div class="form-group mt-4"> | |
| <label for="transcription">Instruction:</label> | |
| <textarea name="transcription" id="transcription" class="form-control" rows="3" placeholder="Provide instructions for CSV manipulation..."></textarea> | |
| </div> | |
| <button type="submit" class="btn btn-success">Process Instruction</button> | |
| </form> | |
| <!-- Original and Updated Data Section --> | |
| <div class="data-section"> | |
| <h3>Data Comparison</h3> | |
| <div class="table-wrapper"> | |
| <!-- Original Data --> | |
| {% if original_data %} | |
| <div> | |
| <h4>Original Data</h4> | |
| <div class="table-container"> | |
| <table class="table table-bordered"> | |
| <thead> | |
| <tr> | |
| {% for column in columns %} | |
| <th>{{ column }}</th> | |
| {% endfor %} | |
| </tr> | |
| </thead> | |
| <tbody> | |
| {% for row in original_data %} | |
| <tr> | |
| {% for column in columns %} | |
| <td>{{ row[column] }}</td> | |
| {% endfor %} | |
| </tr> | |
| {% endfor %} | |
| </tbody> | |
| </table> | |
| </div> | |
| </div> | |
| {% endif %} | |
| <!-- Updated Data --> | |
| {% if updated_data %} | |
| <div> | |
| <h4>Updated Data</h4> | |
| <div class="table-container"> | |
| <table class="table table-bordered"> | |
| <thead> | |
| <tr> | |
| {% for column in columns %} | |
| <th>{{ column }}</th> | |
| {% endfor %} | |
| </tr> | |
| </thead> | |
| <tbody> | |
| {% for row in updated_data %} | |
| <tr> | |
| {% for column in columns %} | |
| <td>{{ row[column] }}</td> | |
| {% endfor %} | |
| </tr> | |
| {% endfor %} | |
| </tbody> | |
| </table> | |
| </div> | |
| </div> | |
| {% endif %} | |
| </div> | |
| </div> | |
| </div> | |
| <script> | |
| let mediaRecorder; | |
| let audioChunks = []; | |
| document.getElementById('recordButton').addEventListener('click', function () { | |
| navigator.mediaDevices.getUserMedia({ audio: true }) | |
| .then(stream => { | |
| mediaRecorder = new MediaRecorder(stream); | |
| mediaRecorder.start(); | |
| audioChunks = []; | |
| mediaRecorder.ondataavailable = event => { | |
| audioChunks.push(event.data); | |
| }; | |
| mediaRecorder.onstart = () => { | |
| document.getElementById('recordButton').disabled = true; | |
| document.getElementById('stopButton').disabled = false; | |
| }; | |
| mediaRecorder.onstop = () => { | |
| document.getElementById('recordButton').disabled = false; | |
| document.getElementById('stopButton').disabled = true; | |
| const audioBlob = new Blob(audioChunks, { type: 'audio/wav' }); | |
| const formData = new FormData(); | |
| formData.append('audio', audioBlob, 'recording.wav'); | |
| // Send the audio blob to the backend for transcription | |
| fetch('/process_audio', { | |
| method: 'POST', | |
| body: formData | |
| }) | |
| .then(response => response.json()) | |
| .then(data => { | |
| document.getElementById('transcription').value = data.transcription; | |
| }) | |
| .catch(error => { | |
| console.error('Error:', error); | |
| }); | |
| }; | |
| }) | |
| .catch(error => { | |
| console.error('Error accessing microphone:', error); | |
| }); | |
| }); | |
| document.getElementById('stopButton').addEventListener('click', function () { | |
| mediaRecorder.stop(); | |
| }); | |
| </script> | |
| </body> | |
| </html> | |