Как приостановить отправку формы до завершения xhmhttprequest - PullRequest
0 голосов
/ 01 февраля 2019

У меня есть Flask Web App, использующий Boostrap и обычный Javascipt.Когда форма отправлена, я делаю xmlhttprequest для загрузки файла в s3.Проблема в том, что страница перезагружается до того, как xhr возвращается и отменяет мой запрос.

Этот вопрос часто задают, и я пробовал каждое решение, которое видел (10 часов на этот вопрос!).Единственное надежное решение - подождать 3 секунды в моем приложении Flask.Это позволяет обрабатывать запрос xhr перед перезагрузкой страницы.Мой текущий код получает запрос, а затем зависает.Я не могу заставить его продолжать.

document.getElementById("accountForm").onsubmit = function (e) {
    e.preventDefault();
    uploadfile();
};

Tried every permutation of this I can find....
Tried changing to'accountForm' and 'onsubmit'
Tried 'onclick'...

Javascript

document.getElementById("accountForm").onsubmit = function (e) {
    e.preventDefault();
    uploadfile();
};

HTML

    <form method="POST" action="" enctype="multipart/form-data" id="accountForm">
        <input id="csrf_token" name="csrf_token" type="hidden" value="IjE1MjE0ZmM1OGMxNDI1NzMxZGY5N2E2MWFkMjExMDJmYmY3NjczMGEi.XFOE9Q.HVCiO1aeu0zWXG9nL0B1Z5mgnkE">
        <fieldset class="form-group">
            <legend class="border-bottom mb-4">Account Info</legend>
            <div class="form-group">
                <label class="form-control-label" for="username">Username</label>


                    <input class="form-control form-control-lg" id="username" name="username" required type="text" value="bill">

            </div>
            <div class="form-group">
                <label class="form-control-label" for="email">Email</label>

                    <input class="form-control form-control-lg" id="email" name="email" required type="text" value="bill@gmail.com">

            </div>
            <div class="form-group">
                <label for="picture">Update Profile Picture</label>
                <input class="form-control-file" id="picture" name="picture" type="file">

            </div>
        </fieldset>
        <div class="form-group">
            <input class="btn btn-outline-info" id="submit" name="submit" type="submit" value="Update">
        </div>
    </form>

javascript

function uploadfile() {
    console.log("uploadfile main function called")
    /* Check file exist and call for temporary signature */
    const files = document.getElementById('picture').files;
    const file = files[0];
    if (!file) {
        return;
    }
    getSignedRequest(file);
    /* Function to get the signature from the flask app */
    console.log('Getting Signed request')
    function getSignedRequest(file) {
        const xhttp = new XMLHttpRequest();
        //xhr.open('GET',`/sign-s3/?file-name=${file.name}&file-type=${file.type}`);
        xhttp.onreadystatechange = function () {
            console.log('ppReg: ' + this.readyState + " " + this.status)
            if (this.readyState == 4 && this.status == 200) {
                const response = JSON.parse(this.responseText);
                console.log(this.readyState, this.status)
                uploadFile(file, response.data, response.url);
            }
        };
        xhttp.open('GET', `/s3Request/?file-name=${file.name}&file-type=${file.type}`);
        xhttp.send();
        // xhr.send();
    }
    /* Function to send the file to S3 */
    function uploadFile(file, s3Data, url) {

        console.log('uploading file after ppReq')
        const xreq = new XMLHttpRequest();

        xreq.onreadystatechange = function () {
            console.log('s3Upload: ' + this.readyState + " " + this.status)
            if (this.readyState == 4 && this.status == 204) {
                //const response = JSON.parse(this.responseText);
                //uploadFile(file,response.data,response.url);
                console.log('File upload received by s3')
            }
            // else if (this.readyState == 4 && this.status != 204) {
            //     alert("File upload failed.")

            else {
                // change to alert
                console.log(this.readyState, this.status)
            }
        };
        xreq.open('POST', s3Data.url, true); // set to false but need to change.
        xreq.setRequestHeader('x-amz-acl', 'public-read');
        const postData = new FormData();
        for (key in s3Data.fields) {
            postData.append(key, s3Data.fields[key]);
        }
        postData.append('file', file);
        console.log(postData)
        xreq.send(postData)
        console.log('Data Sent!')

    }
}

Я бы ожидал, что форма не будет отправлена, тогдазапустить uploadfile () и, наконец, форму для отправки.Текущий код останавливается после запуска uploadfile ().Любая помощь будет действительно очень оценена!Я пытаюсь придерживаться простого JS, если это возможно.

Редактировать: Я согласен, что подобные вопросы задавались, но я попробовал все их решения.Я новичок в Javascript, поэтому я не знаю, как предлагаемый пост, посвященный Обещанию, относится к отправке формы.Но я буду продолжать переваривать это.Спасибо тем, кто ищет.

1 Ответ

0 голосов
/ 15 февраля 2019

Вот что сработало:

document.getElementById("accountForm").onsubmit = function (e) {
    e.preventDefault();

    uploadfile();

    document.getElementById('accountForm').submit();
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...