Copied to clipboard

Flag this post as spam?

This post will be reported to the moderators as potential spam to be looked at


  • Peter Norbeck 7 posts 27 karma points
    Jan 15, 2012 @ 16:53
    Peter Norbeck
    0

    XML - Getting the value of tag with namespace

    Hello,

    I've got a problem getting the value of an xml tag with a namespace. 

    Here's The XML:

    <rss xmlns:obs="http://www.cision.com/" xmlns:content="http://purl.org/rss/1.0/modules/content/" version="2.0">
    <channel>
    <item obs:id="1">
        <title>Title 1</title>
        <content:encoded>Lorem ipsum dolar sit amet 1</content:encoded>
    </item>
    <item obs:id="2">
        <title>Title 2</title>
        <content:encoded>Lorem ipsum dolar sit amet 2</content:encoded>
    </item>
    </channel>
    </rss>

     

     

    Here's my Razor macro in a template:

    <umbraco:Macro runat="server" language="cshtml">
    @{
    var targetUri   = new Uri("http://www.example.com/example.xml");
    var request     = (HttpWebRequest)WebRequest.Create(targetUri);
    if ((request.GetResponse().ContentLength > 0))
    {
        var stream  = new StreamReader(request.GetResponse().GetResponseStream());
        xml         = stream.ReadToEnd();
        if (stream != null)
        {
       stream.Close();
        }
    }
    
    var feed = Library.ToDynamicXml(xml);
    foreach (var post in feed.channel.item)
    {
        @post.title <-- WORKS
    }
    }
    </umbraco:Macro>

     

    In the foreach loop getting the <title> tag works great with @post.title. But how do i get the value of <content:encoded>?

    Thanks in advance!

    /Peter

     

  • Sebastiaan Janssen 5045 posts 15477 karma points MVP admin hq
    Jan 15, 2012 @ 19:06
    Sebastiaan Janssen
    0

    Try either @post.content or @post.contentencoded

    There's a similar problem when a node contans a dash. In that case (example: <link-title>) the invalid character gets removed (@post.linktitle), so hopefully it's the same here.

  • Peter Norbeck 7 posts 27 karma points
    Jan 15, 2012 @ 19:38
    Peter Norbeck
    0

    Hi Sebastiaan,

    Thanks for your answer but I've already tried that. Both breaks Razor and outputs following:

    Error loading Razor Script 
    'umbraco.MacroEngines.DynamicXml' does not contain a definition for 'contentencoded'

    Any other suggestions?

  • Rodion Novoselov 694 posts 859 karma points
    Jan 17, 2012 @ 13:31
    Rodion Novoselov
    0

    Hi, Peter. Although it doesn't look as elegant as it could but you can always query your DynamicXml by usual XPath:

    foreach (var encoded in feed.XPath("//*[local-name() = 'encoded']"))
    {
        <p>@encoded.InnerText</p>
  • Douglas Ludlow 210 posts 366 karma points
    Jan 17, 2012 @ 16:47
    Douglas Ludlow
    0

    I can't seem to find a way to reference the <content:encoded> tag directly, but I was able to get to it like this:

    @{
    string file = "http://www.example.com/example.xml";
    dynamic rss = new DynamicXml(umbraco.library.GetXmlDocumentByUrl(file));

    @rss.channel.item[0].Descendants()[1].InnerText
    }

    // Returns: Lorem ipsum dolar sit amet 1

    Hope that helps!

  • Peter Norbeck 7 posts 27 karma points
    Jan 17, 2012 @ 18:35
    Peter Norbeck
    0

    Great!!

    Thanks Rodion and Douglas. Both of your examples worked. But I finally I chose to use XPath like this: 

    foreach (var post in feed.channel.item)
    {
      <p>@post.XPath("//*[local-name() = 'encoded']").InnerText</p> <-- outputs <content:encoded>
    }
  • Nick 1 post 21 karma points
    Jan 24, 2012 @ 11:15
    Nick
    0

    Sorry for lending this thread. But you guys maybe can help me?

     

    How am I supposed to do to get the id from the item
    <itemobs:id="1">
    <itemobs:id="2">
    <itemobs:id="3">
    ans so on.

    Thanks in advance!


     

     

     

  • Rodion Novoselov 694 posts 859 karma points
    Jan 24, 2012 @ 11:41
    Rodion Novoselov
    0

    The same way as above. Perhaps it would be more usefull to give some explanation how it works. The local-name() funtion refers to the part of the node's or attribute's name without the namespace prefix if there's any. So when you spell e.g.:

    <xsl:variable name="foo" select="./@*[local-name() = 'id']"/>

    then it reads: "Give me all the attributes of the current node whose name without a namespace prefix is equal to the string 'id'".

  • Peter Norbeck 7 posts 27 karma points
    Jan 29, 2012 @ 22:22
    Peter Norbeck
    0

    Really frustrating. I'm trying to get the value of the attribute obs:id.  But can't get it to work. 

    @Nick - Did you manage to get the value of attribute?

    @Rodion - I tried your suggestion to use the same xpath as above for the node. But only got errors.  

    Attempt 1:

    @post.XPath("./@[local-name() = 'id']");   

    Error output: 

    Error loading Razor Script
    Expression must evaluate to a node-set. 

    Attempt 2:

     

    @post.XPath("./@*[local-name() = 'id']");  

    error output

    Error loading Razor Script 
    The XPath expression evaluated to unexpected type System.Xml.Linq.XAttribute.

     

    What am i doing wrong?

    I've added following @using to my macro. Still attempt 2 outputs unexpected type.  Why?

    <umbraco:macro> 

     

    @using System.Linq
    @using System.Xml.Linq
    @using System.Xml.XPath

    ...

     

    I use .InnerText after the Xpath-expression to get the value of a tag. What should i use to get value of an attribute?

     

    Thanks

  • Rodion Novoselov 694 posts 859 karma points
    Jan 29, 2012 @ 23:58
    Rodion Novoselov
    0

    Hi, Peter. The XPath method of DynamicXml is supposed to work only under condition that the XPath query passed returns the set of elements, not attributes. In an ordinal namespaceless case you get attributes just accessing them as dynamic properties. Unfortunately it doesn't work when there's a namespace assigned to the attribute. You can workaround it accessing the DynamicXml.BaseElement property that return a raw XElement underlying to the DynamicXml.

  • Rodion Novoselov 694 posts 859 karma points
    Jan 30, 2012 @ 01:40
    Rodion Novoselov
    1

    Below is the sample of working code:

     

     

    @{
      XNamespace obs = "http://www.cision.com/";
    }

    <table>
      @foreach (var item in post.channel.item)
      {
        <tr>
          <td>@item.BaseElement.Attribute(obs + "id").Value</td>
          <td>@item.title</td>
        </tr>
      }
    </table>

     

  • Peter Norbeck 7 posts 27 karma points
    Jan 30, 2012 @ 19:53
    Peter Norbeck
    0

    Great! Had no idea that there was a BaseElement property in DynamicXml.  Umbraco is badly documented about these kind of things.  Thank you so much Rodion. 

Please Sign in or register to post replies

Write your reply to:

Draft