web-dev-qa-db-fra.com

Soumettre POST données du contrôleur vers un autre site Web dans Rails

  1. L'utilisateur soumet un formulaire avec quelques données de base.

  2. Les données sont reçues et traitées par une action dans le contrôleur et plus d'informations qui doivent rester privées sont ajoutées.

  3. Ensuite, je dois envoyer une demande de publication à un site Web externe avec toutes les données combinées du contrôleur.

Quelle est la meilleure façon de procéder?

48
Alex.Bullard

La manière la plus simple consiste à utiliser Ruby core library:

require "uri"
require "net/http"

params = {'box1' => 'Nothing is less important than which fork you use. Etiquette is the science of living. It embraces everything. It is Ethics. It is honor. -Emily Post',
'button1' => 'Submit'
}
x = Net::HTTP.post_form(URI.parse('http://www.interlacken.com/webdbdev/ch05/formpost.asp'), params)
puts x.body

Astuce de pro: faites une demande asynchrone, en utilisant une gemme comme delay_job ou background rb

82
Vlad Zloteanu

Désolé, j'ai oublié de mentionner que je me connectais à un serveur sécurisé. Cela semble avoir été la raison pour laquelle j'obtenais des erreurs de fin de fichier. L'ajout à l'aide de 'net/https' et l'appel à use_ssl lors de la connexion ont résolu le problème. Merci pour l'aide de tous.

require 'net/https'
require 'open-uri'

url = URI.parse('https://MY_URL')
req = Net::HTTP::Post.new(url.path)
req.form_data = data
req.basic_auth url.user, url.password if url.user
con = Net::HTTP.new(url.Host, url.port)
con.use_ssl = true
con.start {|http| http.request(req)}    

Ceci est basé sur la source de la méthode post_form, donc je suppose que je donnerai à vlad.zloteanu la réponse.

33
Alex.Bullard

Si le serveur externe est RESTful, créez simplement un modèle ActiveResource pour gérer vos données.

12
askegg

Je ne pense pas que redirect_to gère les demandes de publication, car il utilise http 302 (?) Qui obtient simplement l'autre page.

Je pense que vous pouvez faire quelque chose comme ça

Class MyController < ActionController
    require 'net/http'

    def my_method
        #do something with the data/model

        my_connection = Net::HTTP.new('www.target.com', 80)
        reponse = my_connection.post(path_within_url, data)

        #do something with response if you want
    end

end

note: ceci est codé par air et n'a pas été essayé ou testé

4
ErsatzRyan