Solved

REXML Troubleshooting - accessing one item

Posted on 2007-11-20
7
220 Views
Last Modified: 2012-05-05
I'm reading the following XML file using REXML in rails.

<xml>
<event id='2288'>
<venue_id>1</venue_id>
</event>
<venue id='1'>
<name>hello</name>
</venue>
</xml>

The code I use my controller is this:

@events = droot.elements.to_a("//event")
@venues = droot.elements.to_a("//venue")

This works and my data is loaded into each array.

But the problem I'm having is accessing a specific venue from that array.

I've tried stuff like this, but no luck:

<%= @venues[@id=1].elements['name'] %>

Can anybody help me access one particular element in the array? In my view I end up looping through each event and just need to access the associated venue. (This is from the zvents API) Thanks for any help!
0
Comment
Question by:idadan
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 4
  • 3
7 Comments
 
LVL 60

Expert Comment

by:Geert Bormans
ID: 20328243
Why are you converting the elements you found to an array?
It will no longer be accessible as XML I believe

Can't you do something like this?
XPath.each(droot, "//venue[@id = 1]/name")
It will give you that name directly

cheers

Geert

0
 

Author Comment

by:idadan
ID: 20332209
I guess the reason I was converting them to an array was just because it was easy to then access them in the view.

The problem is though I will end up with more id's than just 1.  All the examples I see online are people knowing the ID they're going to reference, I'll have many.

I just need some way in my view to loop through events, and be able to access the associated venue info.  Thanks for any help!

(So my real xml stream would look more like this)

<xml>
<event id='2288'>
<venue_id>1</venue_id>
</event>
<event id='3773'>
<venue_id>2</venue_id>
</event>
...etc...
<venue id='1'>
<name>hello</name>
</venue>
<venue id='2'>
<name>numero 2</name>
</venue>
...etc...
</xml>
0
 
LVL 60

Accepted Solution

by:
Geert Bormans earned 500 total points
ID: 20333048
well, you could make a hash from it

require 'open-uri'
require 'rexml/document'
include REXML
 
open("test.xml") {|f|   @req = f.read }

doc = Document.new(@req)
name_list = Hash.new
 
XPath.each(doc, "//venue") do |element|
            XPath.each(element, "@id") do |id|
                  XPath.each(element, "name/text()") do |name|
                        name_list[id] = name
                  end
            end
end

name_list.each {|key, val| puts key, val}

as you see from this example,
you don't need to put it in a hash
XPath creates a nodelist, you don't necessarily need to map that to an array,
you can wok the nodelist

cheers

Geert
0
Why You Need a DevOps Toolchain

IT needs to deliver services with more agility and velocity. IT must roll out application features and innovations faster to keep up with customer demands, which is where a DevOps toolchain steps in. View the infographic to see why you need a DevOps toolchain.

 

Author Comment

by:idadan
ID: 20334655
This is the code as I have it now.  I still can't actually reference the name in the view, I know you gave the each key,val example, but what I'm I doing wrong?!  Thanks for the help, I think I'm almost there...!

CONTROLLER:

        @events = droot.elements.to_a("//event")
        @name_list = Hash.new
 
        XPath.each(droot, "//venue") do |element|
            XPath.each(element, "@id") do |id|
                  XPath.each(element, "name/text()") do |name|
                        @name_list[id] = name
                  end
            end
          end

VIEW
@name_list[7358].name  <--- This is nil though when I try to access it...

Thank you so much for the help, I really appreciate it.  
0
 
LVL 60

Assisted Solution

by:Geert Bormans
Geert Bormans earned 500 total points
ID: 20334663
maybe you need to explicitely cast to strings
                      @name_list[id.to_s] = name.to_s
they might still be nodes instead of strings

and then you need string values anyway
@name_list["7358"].name

now, that should work

cheers

Geert
0
 
LVL 60

Expert Comment

by:Geert Bormans
ID: 20335147
> now, that should work

it does with my test file
0
 

Author Closing Comment

by:idadan
ID: 31410167
In the end in my view I changed it to this to get it to display:
<%= @name_list[event.elements['venue_id'].text] %>

Thanks so much Gertone, you rock!  I really appreciate the help!
0

Featured Post

Guide to Performance: Optimization & Monitoring

Nowadays, monitoring is a mixture of tools, systems, and codes—making it a very complex process. And with this complexity, comes variables for failure. Get DZone’s new Guide to Performance to learn how to proactively find these variables and solve them before a disruption occurs.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
AL3 Files 4 68
Setting up a IIS 8 Web Server to send and receive XML files 7 124
XSL - substring between 2 commas 12 33
Extracting nodes  using classical ASP 3 40
In Ruby, Call or invoke a API DLL library is easily via Win32API class, win32-api gem or other gems. For general DLL API call, there are quite a few references, some good tips list below: http://www.rubytips.org/2008/05/13/accessing-windows-api-fro…
I was working on a PowerPoint add-in the other day and a client asked me "can you implement a feature which processes a chart when it's pasted into a slide from another deck?". It got me wondering how to hook into built-in ribbon events in Office.
The Email Laundry PDF encryption service allows companies to send confidential encrypted  emails to anybody. The PDF document can also contain attachments that are embedded in the encrypted PDF. The password is randomly generated by The Email Laundr…
Finds all prime numbers in a range requested and places them in a public primes() array. I've demostrated a template size of 30 (2 * 3 * 5) but larger templates can be built such 210  (2 * 3 * 5 * 7) or 2310  (2 * 3 * 5 * 7 * 11). The larger templa…

737 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question