Comment puis-je publier des données de formulaire avec $ http dans AngularJS?

Je suis nouveau chez AngularJS , et pour le début, j'ai pensé développer une nouvelle application en utilisant uniquement AngularJS .

J'essaie de faire un appel AJAX côté serveur, en utilisant $http de mon application Angular.

Pour l'envoi des paramètres, j'ai essayé ce qui suit:

 $http({ method: "post", url: URL, headers: {'Content-Type': 'application/x-www-form-urlencoded'}, data: $.param({username: $scope.userName, password: $scope.password}) }).success(function(result){ console.log(result); }); 

Cela fonctionne mais, il utilise jQuery aussi près, $.param . Pour supprimer la dépendance de jQuery , j'ai essayé:

 data: {username: $scope.userName, password: $scope.password} 

Mais cela semblait échouer. Ensuite, j'ai essayé des params :

 params: {username: $scope.userName, password: $scope.password} 

Mais cela semblait également échouer. Ensuite, j'ai essayé JSON.stringify :

 data: JSON.stringify({username: $scope.userName, password: $scope.password}) 

J'ai trouvé ces réponses possibles à ma quête, mais j'ai échoué. Est-ce que je fais quelque chose de mal.? Je suis sûr que AngularJS fournirait cette fonctionnalité. Mais comment.?

Je pense que vous devez faire est de transformer vos données d'un objet non vers une chaîne JSON, mais sur des params.

Du blog de Ben Nadel .

Par défaut, le service $ http transformera la demande sortante en sérialisant les données en tant que JSON, puis en la publiant avec le type de contenu, "application / json". Lorsque nous voulons publier la valeur en tant que publication FORM, nous devons modifier l'algorithme de sérialisation et publier les données avec le type de contenu, "application / x-www-form-urlencoded".

Exemple à partir d'ici .

 $http({ method: 'POST', url: url, headers: {'Content-Type': 'application/x-www-form-urlencoded'}, transformRequest: function(obj) { var str = []; for(var p in obj) str.push(encodeURIComponent(p) + "=" + encodeURIComponent(obj[p])); return str.join("&"); }, data: {username: $scope.userName, password: $scope.password} }).success(function () {}); 

Variables d'encodage d'URL utilisant uniquement les services AngularJS

Avec AngularJS 1.4 et plus, deux services peuvent traiter le processus de codage urinaire des données pour les demandes POST, éliminant la nécessité de manipuler les données avec transformRequest ou en utilisant des dépendances externes comme jQuery:

  1. $httpParamSerializerJQLike – un sérialiseur inspiré par .param() ( recommandé ) de jQuery

  2. $httpParamSerializer – un sérialiseur utilisé par Angular lui-même pour les demandes GET

Exemple d'utilisation

 $http({ url: 'some/api/endpoint', method: 'POST', data: $httpParamSerializerJQLike($scope.appForm.data), // Make sure to inject the service you choose to the controller headers: { 'Content-Type': 'application/x-www-form-urlencoded' // Note the appropriate header } }).success(function(response) { /* do something here */ }); 

Voir une démonstration plus détaillée de Plunker


Comment sont $httpParamSerializerJQLike et $httpParamSerializer différents

En général, il semble que $httpParamSerializer utilise moins de format de codage $httpParamSerializer "traditionnel" que $httpParamSerializerJQLike lorsqu'il s'agit de structures de données complexes.

Par exemple (ignorant le pourcentage de codage des parenthèses):

Encodage d'un tableau

 {sites:['google', 'Facebook']} // Object with array property sites[]=google&sites[]=facebook // Result with $httpParamSerializerJQLike sites=google&sites=facebook // Result with $httpParamSerializer 

Encodage d'un objet

 {address: {city: 'LA', country: 'USA'}} // Object with object property address[city]=LA&address[country]=USA // Result with $httpParamSerializerJQLike address={"city": "LA", country: "USA"} // Result with $httpParamSerializer 

Tout cela ressemble à une overkill (ou ne fonctionne pas) … faites ceci:

 $http.post(loginUrl, "userName=" + encodeURIComponent(email) + "&password=" + encodeURIComponent(password) + "&grant_type=password" ).success(function (data) { 

Le problème est le format de chaîne JSON, vous pouvez utiliser une chaîne d'URL simple dans les données:

 $http({ method: 'POST', url: url, headers: {'Content-Type': 'application/x-www-form-urlencoded'}, data: 'username='+$scope.userName+'&password='+$scope.password }).success(function () {}); 

Voici la façon dont il devrait être (et s'il vous plaît, aucun changement de backend … certainement pas … si votre pile avant ne supporte pas application/x-www-form-urlencoded , alors jette-le … espérons que AngularJS le fait!

 $http({ method: 'POST', url: 'api_endpoint', headers: {'Content-Type': 'application/x-www-form-urlencoded'}, data: 'username='+$scope.username+'&password='+$scope.password }).then(function(response) { // on success }, function(response) { // on error }); 

Fonctionne comme un charme avec AngularJS 1.5

Les gens, laissez-vous quelques conseils:

  • Utilisez des promesses. .then(success, error) lorsque vous utilisez $http , oubliez les .sucess de .sucess et .error (car ils sont obsolètes)

  • À partir du site angularjs ici " Vous ne pouvez plus utiliser la chaîne JSON_CALLBACK comme espace réservé pour spécifier l'emplacement de la valeur du paramètre de rappel. "

Si votre modèle de données est plus complexe que simplement un nom d'utilisateur et un mot de passe, vous pouvez toujours le faire (comme indiqué ci-dessus)

 $http({ method: 'POST', url: 'api_endpoint', headers: {'Content-Type': 'application/x-www-form-urlencoded'}, data: json_formatted_data, transformRequest: function(data, headers) { return transform_json_to_urlcoded(data); // iterate over fields and chain key=value separated with &, using encodeURIComponent javascript function } }).then(function(response) { // on succes }, function(response) { // on error }); 

Le document pour le encodeURIComponent peut être trouvé ici

Si c'est un formulaire, essayez de changer l'en-tête pour:

 headers[ "Content-type" ] = "application/x-www-form-urlencoded; charset=utf-8"; 

Et si ce n'est pas une forme et un json simple, essayez cet en-tête:

 headers[ "Content-type" ] = "application/json"; 

Vous devez publier un objet javascript simple, rien d'autre

  var request = $http({ method: "post", url: "process.cfm", transformRequest: transformRequestAsFormPost, data: { id: 4, name: "Kim" } }); request.success( function( data ) { $scope.localData = data; } ); 

Si vous avez php en tant que back-end, vous devrez faire une autre modification … caisse ce lien pour réparer le côté du serveur php

Cela a fonctionné pour moi. J'utilise angulaire pour front-end et laravel php pour back-end. Dans mon projet, Web angulaire envoie les données json vers l'arrière-plan Laravel.

C'est mon contrôleur angulaire.

 var angularJsApp= angular.module('angularJsApp',[]); angularJsApp.controller('MainCtrl', function ($scope ,$http) { $scope.userName ="Victoria"; $scope.password ="password" $http({ method :'POST', url:'http://api.mywebsite.com.localhost/httpTest?callback=JSON_CALLBACK', data: { username : $scope.userName , password: $scope.password}, headers: {'Content-Type': 'application/json'} }).success(function (data, status, headers, config) { console.log('status',status); console.log('data',status); console.log('headers',status); }); }); 

C'est mon contrôleur laravel de back-end php.

 public function httpTest(){ if (Input::has('username')) { $user =Input::all(); return Response::json($user)->setCallback(Input::get('callback')); } } 

C'est mon itinéraire laravel

 Route::post('httpTest','HttpTestController@httpTest'); 

Le résultat dans le navigateur est

Statut 200
Données JSON_CALLBACK ({"nom d'utilisateur": "Victoria", "mot de passe": "mot de passe", "rappel": "JSON_CALLBACK"}); HttpTesting.js: fonction de 18 en-têtes (c) {a || (a = sc (b)); retour c? A [K (c)] || null: a}

Il existe une extension chrome appelée postman. Vous pouvez utiliser pour tester votre URL de back-end, que cela fonctionne ou non. https://chrome.google.com/webstore/detail/postman-rest-client/fdmmgilgnpjigdojojpjoooidkmcomcm?hl=fr

J'espère que ma réponse vous aidera.

Bien qu'une réponse tardive, j'ai trouvé que UrlSearchParams angulaire fonctionnait très bien pour moi, il s'occupe également du codage des paramètres.

 let params = new URLSearchParams(); params.set("abc", "def"); let headers = new Headers({ 'Content-Type': 'application/x-www-form-urlencoded'}); let options = new RequestOptions({ headers: headers, withCredentials: true }); this.http .post(UrlUtil.getOptionSubmitUrl(parentSubcatId), params, options) .catch(); 
 $http({ method: "POST", url: "/server.php", headers: { 'Content-Type': 'application/x-www-form-urlencoded' }, data: "name='Олег'&age='28'", }).success(function(data, status) { console.log(data); console.log(status); }); 

À partir des $ docs http, cela devrait fonctionner …

  $http.post(url, data,{headers: {'Content-Type': 'application/x-www-form-urlencoded'}}) .success(function(response) { // your code... });