ruby Savon use camelcase instead snake - ruby-on-rails

i'm using savon gem for SOAP request building, i need snake_case_elements, but when i inspect it seems converted to CamelCase, am i missing something here? Here is a result
And how i did it:
gls_url = 'https://adi-test.gls-poland.pl/adeplus/pm1/ade_webapi2.php?wsdl'
username = '612305291'
password = 'KGpartt2016'
#client = Savon.client(wsdl: gls_url,
log: true,
logger: Rails.logger,
log_level: :debug,
pretty_print_xml: true)
ats = #client.call(:ade_login, message: {
user_name: username,
user_password: password
})

You can use convert_request_keys_to option to tell Gyoku how to convert the keys (if at all):
#client = Savon.client(wsdl: gls_url, convert_request_keys_to: :none)

Related

Multiple Endpoints (for replicated SOAP Servers) with SAVON

I am trying to make a SOAP request to a remote SOAP Server using the Savon gem in rails. The SOAP Server is replicated on three instances with different IP Addresses, i.e. XXX.XXX.XXX.1, XXX.XXX.XXX.2 and XXX.XXX.XXX.3.
I am able to explicitly define the savon client endpoint using one of the above ip addresses like so:
Savon.client(
endpoint: "http://XXX.XXX.XXX.1:15043/enmac/SOAP",
namespace: '',
convert_request_keys_to: :camelcase,
env_namespace: 'SOAP-ENV',
namespace_identifier: nil,
log: true,
log_level: :info,
pretty_print_xml: true,
read_timeout: 90,
open_timeout: 90,
headers: {
"Accept-Encoding" => "gzip"
}
)
The problem with the above sample code is that when the SOAP Server instance with IP Address XXX.XXX.XXX.1 is down then my services goes down as well.
What I am actually looking for is an approach that will make sure that when SOAP Server instance XXX.XXX.XXX.1 is down then XXX.XXX.XXX.2 takes over etc.
Below is what I tried but couldn't get it to work properly:
I have a database table with all the SOAP Servers instances populated by IP address with only a single of them with a status of active
I have a the following method that shift to then next server:
def shift_oms_server
#oms_server = OmsServer.where(status: true).first
case #oms_server.ip_address.to_s
when 'XXX.XXX.XXX.1'
#oms_server.update_attribute(:status, false)
#next_oms_server = OmsServer.where(ip_address: 'XXX.XXX.XXX.2').first
#next_oms_server.update_attribute(:status, true)
when 'XXX.XXX.XXX.2'
#oms_server.update_attribute(:status, false)
#next_oms_server = OmsServer.where(ip_address: 'XXX.XXX.XXX.3').first
#next_oms_server.update_attribute(:status, true)
when 'XXX.XXX.XXX.3'
#oms_server.update_attribute(:status, false)
#next_oms_server = OmsServer.where(ip_address: 'XXX.XXX.XXX.1').first
#next_oms_server.update_attribute(:status, true)
end
end
Now I modify my Savon Client initialization like so:
#oms_server = OmsServer.where(status: true).first
Savon.client(
endpoint: "http://#{#oms_server.ip_address.to_s}:15043/enmac/SOAP",
namespace: '',
convert_request_keys_to: :camelcase,
env_namespace: 'SOAP-ENV',
namespace_identifier: nil,
log: true,
log_level: :info,
pretty_print_xml: true,
read_timeout: 90,
open_timeout: 90,
headers: {
"Accept-Encoding" => "gzip"
}
)
Finally wherever I make the SOAP Request call I will have something like a begin rescue block like so:
begin
# make soap server request
rescue HTTPServerException => e
shift_oms_server
# make soap server request
ensure
shift_oms_server
# make soap server request
end
Forgive my English. The approach above didn't work for me. I will be happy if someone could enlighten me where I went wrong with the above approach or provide a direction to a more simpler and efficient approach.
Ideally I would like to know if it is possible to have more than one endpoints defined using the Savon gem, if yes how?
Thanks in advance.

rails pass soap basic auth with savon

I'm trying to send soap request with basic authentication with savon gem
My soap server is set up with wash_out gem
class OrdersController < ApplicationController
soap_service namespace: 'sir:WashOut', wsse_username: SIRA[:auth][:username], wsse_password: SIRA[:auth][:password]
....
When i make a request to soap server via savon i get an error:
#client = Savon.client(
wsdl: "http://localhost:3000/orders/wsdl",
soap_header: { 'Username' =>SIRA[:auth][:username], 'Password' => SIRA[:auth][:password] }
)
#response = #client.call(:notify ).to_hash
On the last command i get an error
Savon::SOAPFault: (Server) Missing required UsernameToken
client = Savon.client(
wsdl: 'http://service.example.com?wsdl',
soap_header: {
"AuthenticateRequest" =>
{"apiKey" => "****** your api *********"}},
pretty_print_xml: true)
client.operations
response = client.call(:function)
Note: "apiKey" is my prams to authenticate, your can be different
I've tried this and it works!
#client = Savon.client(
wsdl: "http://localhost:3000/orders/wsdl",
wsse_auth: [SIRENA[:auth][:username], SIRENA[:auth][:password] ],
logger: Rails.logger
)
#response = #client.call(:notify, ).to_hash
For Savon 2. Basic authorization can be done as follows:
#client = Savon.client(
wsdl: "http://localhost:3000/orders/wsdl",
basic_auth: ["username", "password"]
)
#response = #client.call(:notify ).to_hash

Response from SMTP server with Rails

How could I get the response from an SMTP server in Ruby on Rails using ActionMailer, when I send an email with the Mailer.deliver method?
I found the Actionmailer SMTP Server Response answer but it doesn't work... Any idea?
I need it because AWS SES return a message ID through, and it's the only way to get the message linked to a bounce or spam report they provide after.
if you get the smtp in way like this
response = Mail.your_mail().deliver
and it isn't getting the response that you need, try deliver_now!
response = Mail.your_mail().deliver_now!
pp response.message
This will show you the result: 250 2.0.0 Ok: queued as 3lG8S16Khmz6ZhXq
I also configured the smtp settings on my Mail.rb
delivery_options = { user_name: 'email#server.com.br',
password: 'mypassword',
authentication: :login,
address: 'smtp.mycompany.com.br',
port: 2525,
domain: 'mycompany.com.br',
return_response: true
}
If using gem "aws-ses" you can get the message id with:
response = your_mailer.send(notification, self, *args).deliver_now!
response.message_id # => "010601531c886c55-6c2f30fc-4237-4294-9029-b60b2d44a691-000000#email.amazonses.com"
For me deliver, deliver_now and deliver_now! work in the same way
EXTRA:
If for some chance you are using devise you can get the ID too:
#[app/model/user.rb]
class User < ActiveRecord::Base
...
# Override send_devise_notification stated in devise/REAMDE.txt
def send_devise_notification(notification, *args)
response = devise_mailer.send(notification, self, *args).deliver_now
response.message_id #=> "010601531c8-86c...000000#email.amazonses.com"
end
...
end

Ruby: Savon AddressFilter mismatch at the EndpointDispatcher SOAP API

I am new to SOAP and I am having lots of trouble with Savon.
The API I am trying to access has really simplistic documentation: http://www.sona-systems.com/support/docs/sona_api_docs.pdf
When making a call, the API expects authentication in the parameters being sent. Here is my code:
client = Savon.client(
wsdl: "https://school.sona-systems.com/services/SonaAPI.svc?singleWsdl",
soap_header: {'To:' => "http://www.sona-systems.com/"},
pretty_print_xml: true,
soap_version: 2
)
response = client.call(:get_study_list) do
message username: "foo", password: "bar"
end
I am getting the following error:
Savon::SOAPFault: (s:Sender) The message with To '' cannot be processed at the receiver, due to an AddressFilter mismatch at the EndpointDispatcher. Check that the sender and receiver's EndpointAddresses agree.
what is the soap_header: suppose to do?
I also cannot get to the url you provided. you should add log: true, log_level: :debug to your client definition to get more information.
try this:
client = Savon.client(
wsdl: "https://kellogg-elab.sona-systems.com/services/SonaAPI.svc?wsdl",
pretty_print_xml: true,
log: true,
log_level: :debug
)
puts client.operations
# then call a method of the service like this
resp = client.call(:get_study_list,
message: {username: "foo", password: "bar"}
)

Use Rails Logger with Savon gem

I have the following code:
def soap_client
soap_client = Savon.client(
wsdl: "https://api.five9.com/wsadmin/AdminWebService?wsdl&user=apiloader#daxko.com",
namespace: "http://service.admin.ws.five9.com/",
headers: {"Authorization" => "Basic #{#realm}"},
env_namespace: :soapenv,
namespace_identifier: :ser,
ssl_verify_mode: :none,
logger: Rails.logger,
log: true
)
end
This works and logs everything to my console window. However, it doesn't actually log anything to the Rails.logger...
How can I use the default Rails.logger with Savon?
EDIT
I am using savon (2.3.2).

Resources