Comment résoudre une erreur HTTP 414 «Request URI too long»?

103

J'ai développé une application web PHP. Je donne la possibilité à l'utilisateur de mettre à jour plusieurs problèmes en une seule fois. Ce faisant, l'utilisateur rencontre parfois cette erreur. Existe-t-il un moyen d'augmenter la longueur de l'URL dans Apache?

JPro
la source
Si vous voyez cette erreur sur un serveur Windows et / ou dans une application IIS / ASP.NET, voir la question: stackoverflow.com/q/23237538/12484
Jon Schneider

Réponses:

166

Sous Apache, la limite est une valeur configurable, LimitRequestLine. Remplacez cette valeur par une valeur supérieure à sa valeur par défaut de 8190 si vous souhaitez prendre en charge un URI de demande plus long. La valeur est dans /etc/apache2/apache2.conf . Sinon, ajoutez une nouvelle ligne ( LimitRequestLine 10000) sous AccessFileName .htaccess.

Cependant, notez que si vous rencontrez réellement cette limite, vous en abusez probablement GETpour commencer. Vous devriez utiliser POSTpour transmettre ce type de données - d'autant plus que vous admettez même que vous l'utilisez pour mettre à jour des valeurs. Si vous vérifiez le lien ci-dessus, vous remarquerez qu'Apache dit même «Dans des conditions normales, la valeur ne doit pas être modifiée par rapport à la valeur par défaut».

John Feminella
la source
J'ai essayé d'utiliser POST au début, mais il s'agit d'une opération de mise à jour sur la base de données, et je rafraîchis la page originale en utilisant les valeurs qui ont été initialement publiées sur cette page.
JPro
8
JPro: La mise à jour d'une base de données est plus ou moins la raison exacte que vous utiliseriez POST. Rien dans l'utilisation de POST ne vous empêche de remplir le même formulaire avec les champs qui viennent d'être publiés, donc je ne suis pas sûr de ce que vous entendez par là.
John Feminella
1
@JPro: La technique habituelle dans ce cas est de POSTER sur la même page. Le gestionnaire de la page (qui peut être le même code pour GET et POST) vérifie d'abord les paramètres POST, les gère s'il les trouve, puis renvoie la page avec les valeurs correctes remplies, qui seront soit les valeurs mises à jour ( si POST et la mise à jour réussissent) ou les valeurs d'origine (si GET, ou si POST et la mise à jour échouent). Si la mise à jour échoue, vous pouvez même avoir des messages d'erreur par champ décrivant l'échec.
Mike DeSimone le
5
J'ai compris cela assez tard, alors j'aimerais le partager. Si vous ne trouvez le mot LimitRequestLinenulle part dans votre fichier httpd.conf, ajoutez simplement la ligne vous-même où vous le souhaitez. Par exemple:LimitRequestLine 100000
Jules Colle
merci pour la réponse et l'explication, vous avez sauvé ma journée. :)
mai saghira
16

Sur la base de la réponse de John, j'ai changé la demande GET en une demande POST. Cela fonctionne, sans avoir à modifier la configuration du serveur. Je suis donc allé chercher comment mettre en œuvre cela. Les pages suivantes ont été utiles:

Exemple jQuery Ajax POST avec PHP (notez la remarque de désinfection des données publiées) et

http://www.openjs.com/articles/ajax_xmlhttp_using_post.php

Fondamentalement, la différence est que la requête GET a l'url et les paramètres dans une chaîne, puis envoie null:

http.open("GET", url+"?"+params, true);
http.send(null);

alors que la requête POST envoie l'url et les paramètres dans des commandes séparées:

http.open("POST", url, true);
http.send(params);

Voici un exemple de travail:

ajaxPOST.html:

<html>
<head>
<script type="text/javascript">
    function ajaxPOSTTest() {
        try {
            // Opera 8.0+, Firefox, Safari
            ajaxPOSTTestRequest = new XMLHttpRequest();
        } catch (e) {
            // Internet Explorer Browsers
            try {
                ajaxPOSTTestRequest = new ActiveXObject("Msxml2.XMLHTTP");
            } catch (e) {
                try {
                    ajaxPOSTTestRequest = new ActiveXObject("Microsoft.XMLHTTP");
                } catch (e) {
                    // Something went wrong
                    alert("Your browser broke!");
                    return false;
                }
            }
        }

        ajaxPOSTTestRequest.onreadystatechange = ajaxCalled_POSTTest;
        var url = "ajaxPOST.php";
        var params = "lorem=ipsum&name=binny";
        ajaxPOSTTestRequest.open("POST", url, true);
        ajaxPOSTTestRequest.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
        ajaxPOSTTestRequest.send(params);
    }

    //Create a function that will receive data sent from the server
    function ajaxCalled_POSTTest() {
        if (ajaxPOSTTestRequest.readyState == 4) {
            document.getElementById("output").innerHTML = ajaxPOSTTestRequest.responseText;
        }
    }
</script>

</head>
<body>
    <button onclick="ajaxPOSTTest()">ajax POST Test</button>
    <div id="output"></div>
</body>
</html>

ajaxPOST.php:

<?php

$lorem=$_POST['lorem'];
print $lorem.'<br>';

?>

Je viens d'envoyer plus de 12 000 caractères sans aucun problème.

atmelino
la source
4

J'ai une solution de contournement simple.

Supposons que votre URI ait une chaîne stringdatatrop longue. Vous pouvez simplement le diviser en un certain nombre de parties en fonction des limites de votre serveur. Ensuite, soumettez le premier, dans mon cas pour écrire un fichier. Ensuite, soumettez les suivants à ajouter aux données précédemment ajoutées.

Shrey Gupta
la source
Pouvez vous donner un exemple? Je peux voir comment vous divisez la chaîne lorsqu'elle est générée par l'utilisateur ...
endyourif
4
Solution de contournement très bon marché. Il vaut mieux reconsidérer le problème du domaine!
Muhammad Hewedy
13
Cela ne mérite pas d'avoir autant de votes négatifs. Il existe certainement des situations dans lesquelles la soumission de plusieurs demandes peut être une solution de contournement acceptable. Certes, la qualité de la réponse est un peu faible, mais il faut s'y attendre d'un utilisateur qui est tout nouveau dans SO. Montrons un peu d'amour et offrons des commentaires au lieu de simplement voter contre les nouveaux venus qui ne «comprennent» pas encore!
rinogo
1
Je suis d'accord, ça a l'air viable
Felipe Valdes
3

J'ai eu cette erreur après avoir utilisé $ .getJSON () de JQuery. Je viens de changer pour poster:

data = getDataObjectByForm(form);
var jqxhr = $.post(url, data, function(){}, 'json')
    .done(function (response) {
        if (response instanceof Object)
            var json = response;
        else
            var json = $.parseJSON(response);
        // console.log(response);
        // console.log(json);
        jsonToDom(json);
        if (json.reload != undefined && json.reload)
            location.reload();
        $("body").delay(1000).css("cursor", "default");
    })
    .fail(function (jqxhr, textStatus, error) {
        var err = textStatus + ", " + error;
        console.log("Request Failed: " + err);
        alert("Fehler!");
    });
Logiciel Fusca
la source
2
est-ce une réponse ou une question?
Takarii
C'est une bonne solution rapide. Passer de get à post autorise la longue URL sans aucune modification de la configuration du serveur.
mt025
1

Un extrait de la RFC 2616: Hypertext Transfer Protocol - HTTP / 1.1 :

La méthode POST est utilisée pour demander que le serveur d'origine accepte l'entité incluse dans la demande en tant que nouveau subordonné de la ressource identifiée par l'URI de demande dans la ligne de demande. POST est conçu pour permettre à une méthode uniforme de couvrir les fonctions suivantes:

  • Annotation des ressources existantes;
  • Publier un message sur un babillard, un groupe de discussion, une liste de diffusion ou un groupe d'articles similaire;
  • Fournir un bloc de données, tel que le résultat de la soumission d'un formulaire, à un processus de traitement de données ;
  • Extension d'une base de données via une opération d'ajout.
Votre bon sens
la source
8
Ne voyant pas comment cela répond à la question ..?
Afr
L'affiche originale a déclaré que les enregistrements sont en cours de mise à jour. Pour les mises à jour, il est recommandé d'utiliser POST ou PUT et non GET. Mais, bien sûr, il se peut que la limite maximale d'URL soit dépassée lors de la récupération des enregistrements à afficher avant la mise à jour, puis la méthode GET est appropriée, mais elle peut échouer à cause de cette limite. L'affiche originale n'a pas mentionné à quel stade le problème survient, on peut donc supposer que c'était pendant la mise à jour elle-même, mais nous ne pouvons pas être sûrs ...
JustAMartin