Search code examples
javascriptpythonhtmlflaskcodemirror

How to send python output back to html without refreshing the page?


SO I was trying to make a code editor AND process the code form the user input like how most competitive coding websites work. I'll show the relevant parts.

I used codemirror along with Flask on python, make a code editor in the page, using js to get the user input from a button onclick and using ajax to send the code back to my python script, and say I processed my data and produced an output, and now Im stuck at trying to send the data back to the html page (maybe like in another code block showing the output to the user)

Code for the html code block with my attempt at sending data back: py-tut.html

        <div class="codeblock">
            <p>Python editor</p>
            <code><textarea type="text" class="code" id="code" spellcheck="false"></textarea></code>
            <script>
                var codebox = CodeMirror.fromTextArea(document.getElementById("code"), {
                    mode: "python",
                    theme: 'dracula',
                    indentUnit: 4,
                    lineNumbers: 1
                });
                {#set any values in the text box#}
                codebox.getDoc().setValue("import random")
            </script>
            <div class="console" id="console"></div>
            <button type="submit" class="submit" onclick="submit()">Submit</button>
            <script>
                function submit() {
                    var c = codebox.getValue()
                    $.post('http://127.0.0.1:8000/get_code/', {c}, function(){
                        {#this is the part where Im stuck at#}
                        document.getElementById("console").innerHTML = {{ code }};
                    })
                }
            </script>
        </div>

And heres the code for the Flask section: website.py

@app.route("/get_code/", methods=["GET", "POST"])
def get_code():
    if request.method == "POST":
        code = request.form.getlist('c')[0]
        print(code)
        return render_template("py-tut.html", code = "code")

And heres how the website actually looks like: enter image description here

The main problem being the fact that i couldnt send the data back to the html after processing it, I tried render_template, url_for, redirect, but everytime I click on the submit button, nothing happens. Pls help


Solution

  • Here's a brief, untested version. It relies on JQuery library.

    The following script section of your page can be fired from an onclick event. it runs a fetch request. It should pick up your user-inputted code, or whatever you wish to transmit to the back-end. It is POST data, so content will be contained within the request (as JSON using stringify).

    <script>
      let api_submit = function() {
        fetch('{{ url_for('get_code') }}', {
          method: 'POST',
          headers: {
            'Content-Type': 'application/json;charset=utf-8'
          },
          body: JSON.stringify($('.code').html())
        })
        .then( response => response.json() )
        .then( function (result) {
          $('.console').html(result.code);
        });
      };
    </script>
    

    This is your back-end route handling that POSTed data. The content needs to be converted from JSON. The flask render_template uses Jinja to construct the response, and this response data is then sent back to the client in the form of a python dict (one dict element called 'code'). Conveniently, in flask a dict is automatically converted to JSON in the response from the server to that POST request.

    @app.route("/get_code/", methods=["GET", "POST"])
    def get_code():
      if request.method == "POST":
        post_data = request.get_json()
        code = post_data.get('code')
        return dict(code=render_template("py-tut.html", code=code))
      # you may need to cater for 'GET' accesses from somewhere
    

    See if that works.