savonrb / savon

Heavy metal SOAP client
https://www.savonrb.com
MIT License
2.07k stars 616 forks source link

Missing Attributes with Savon 3 #509

Closed superlou closed 11 years ago

superlou commented 11 years ago

With Savon 3, the operation.example_body returns:

{
    :FindItemRevisionsBySearchConditions => {
          :searchConditions => {
            :SrchCond => [
                [0] {
                    :_PropDefId => "xs:long",
                     :_SrchOper => "xs:long",
                      :_SrchTxt => "xs:string",
                      :_PropTyp => "xs:string",
                     :_SrchRule => "xs:string"
                }
            ]
        },
            :sortConditions => {
            :SrchSort => [
                [0] {
                    :_PropDefId => "xs:long",
                      :_SortAsc => "xs:boolean"
                }
            ]
        },
        :bRequestLatestOnly => "boolean",
                  :bookmark => "string"
    }
}

If I understand this output, the following should match Savon's understanding of the WSDL:

body = { 
        FindItemRevisionsBySearchConditions: {
            searchConditions: {
                SrchCond: [
                    {
                        "_PropDefId" => 264,
                        "_SrchOper" =>  1,
                        "_SrchTxt" =>   "query text",
                        "_PropTyp" =>   "AllProperties",
                        "_SrchRule" =>  "Must"
                    },
                    {
                        _PropDefId: 59,
                        _SrchOper:  1,
                        _SrchTxt:   "Work",
                        _PropTyp:   "SingleProperty",
                        _SrchRule:  "Must"
                    }
                ]
            },
            sortConditions: {
                SrchSort: [
                    {
                        _PropDefId: 264,
                        _SortAsc:   true
                    }
                ]
            },
            bRequestLatestOnly: true
        }
}

When I set the operation.body to a hash of the same format, it seems like the attributes are not being set on the SrchCond element properly (from operation.build):

<env:Envelope xmlns:lol0="http://AutodeskDM/Services/ItemService/1/20/2011/" xmlns:env="http://schemas.xmlsoap.org/soap/envelope/">
  <env:Header>
    <lol0:SecurityHeader>
      <lol0:Ticket>my_user_ticket</lol0:Ticket>
      <lol0:UserId>3</lol0:UserId>
    </lol0:SecurityHeader>
  </env:Header>
  <env:Body>
    <lol0:FindItemRevisionsBySearchConditions>
      <lol0:searchConditions>
        <lol0:SrchCond>
        </lol0:SrchCond>
        <lol0:SrchCond>
        </lol0:SrchCond>
      </lol0:searchConditions>
      <lol0:sortConditions>
        <lol0:SrchSort>
        </lol0:SrchSort>
      </lol0:sortConditions>
      <lol0:bRequestLatestOnly>true</lol0:bRequestLatestOnly>
    </lol0:FindItemRevisionsBySearchConditions>
  </env:Body>
</env:Envelope>

I was looking at #473, and it seems like attributes should be supported, and in the code they are being sent through the "builder" gem. Is there anything that needs to be done for attributes other than prefixing with an "_"?

superlou commented 11 years ago

I don't know if it's necessary since Savon seems to understand the content type, but the WSDL is available at https://gist.github.com/superlou/6826789.

kieranmaine commented 11 years ago

No problem. I managed to replicate this. New to savon so just trying to get my head around the source.

kieranmaine commented 11 years ago

Got a fix but need to put the tests into a decent state before putting in a pull request. Here's the changed file if you need it sooner rather than later https://gist.github.com/kieranmaine/6827475.

kieranmaine commented 11 years ago

Opened up following pull request https://github.com/savonrb/savon/pull/510

superlou commented 11 years ago

510 seems to fix our xml generation issue. The output includes attributes:

<env:Envelope xmlns:lol0="http://AutodeskDM/Services/ItemService/1/20/2011/" xmlns:env="http://schemas.xmlsoap.org/soap/envelope/">
  <env:Header>
    <lol0:SecurityHeader>
      <lol0:Ticket>my_ticket</lol0:Ticket>
      <lol0:UserId>my_user</lol0:UserId>
    </lol0:SecurityHeader>
  </env:Header>
  <env:Body>
    <lol0:FindItemRevisionsBySearchConditions>
      <lol0:searchConditions>
        <lol0:SrchCond PropDefId="264" SrchOper="1" SrchTxt="7103-1201" PropTyp="AllProperties" SrchRule="Must"/>
        <lol0:SrchCond PropDefId="59" SrchOper="1" SrchTxt="Work" PropTyp="SingleProperty" SrchRule="Must"/>
      </lol0:searchConditions>
      <lol0:bRequestLatestOnly>true</lol0:bRequestLatestOnly>
    </lol0:FindItemRevisionsBySearchConditions>
  </env:Body>
</env:Envelope>

Unfortunately, our server is still replying with "incorrect input param", but Savon seems to be generating XML that matches the WSDL.

superlou commented 11 years ago

I just noticed that while the pretty printed XML looks great, the same issue still exists when monitoring the traffic in Wireshark. The filtering elements still look like <lol0:SrchCond/>. I pulled the latest source from master, built the gem, and have my Gemfile pointing at the local copy.

kieranmaine commented 11 years ago

I'll grab the wsdl and take a look tomorrow.

superlou commented 11 years ago

Sorry to ping the ticket. I was able to recreate it on a friend's computer, though I'm not sure how it could be a Savon issue.