Parsing XML - Looping issues

Hi all

I am trying to parse an XML file (using InternetOpenURL and InternetReadString) and trying to find a specific value within the field for a specific currency (i.e. show the %short and %long values for EURUSD). However i am getting an error message within the loop when reading the XML file as it expects a number or boolean.

Sample code:

while( ( str = InternetReadString( ih ) ) != "" ) 
     { 
     
	   if((StrFind(str,"<name>") or StrFind(str,"<shortPercentage>") or StrFind(str,"<longPercentage>")  ))    
	 	 /* Read the name of symbol */  
		 {
		 str1= str;
		 str1 = StrTrim(str1,"\t");
		 str1 = StrTrim(str1,"");
		 str1 = StrTrim(str1,"<name>");
		 str1 = StrTrim(str1,"</");
		 }

		/* if symbol is EURUSD output %long and %short */
		if (str1 = "EURUSD")
		 
		 if(StrFind(str,"<shortPercentage>"))	
		 {
		 str2 = str;
		 str2 = StrTrim(str2,"\t");
		 str2 = StrTrim(str2,"");
		 str2 = StrTrim(str2,"<shortPercentage>");
		 str2 = StrTrim(str2,"</");
		 str2 = " - "+str2;
		 }
		 
		 if(StrFind(str,"<longPercentage>"))	
		 {
		 str3 = str;
		 str3 = StrTrim(str3,"\t");
		 str3 = StrTrim(str3,"");
		 str3 = StrTrim(str3,"<longPercentage>");
		 str3 = StrTrim(str3,"</");
		 str3 = " - "+str3;
		 }
		  		 
		 GfxTextOut( str1 + str2 + str3, x, y );
        
         }
          
         
     } 
     InternetClose( ih ); 

Any suggestions please ?

Regards

For what it is worth, your use of StrTrim() is incorrect. StrTrim trims ANY of extra characters specified in second argument, so if you specify "<shortPercentage>" it will trim any occurrence of any letter, so it will trim all '<', all 's', all 'h', all 'o', all 'r' and so on.

Hi Tomasz

Thanks for your reply - i was trying to remove the superflous infromation from the field i.e

<symbol><name>EURUSD</name> <shortPercentage>23</shortPercentage> <longPercentage>77</longPercentage>

So i wanted the output to simply show EURUSD - 23 - 77

I am 100% there is probably a cleaner and quicker way but im not the brightest tool in the box when it comes to programming

Thanks

To remove entire substring from string, it is better to use StrReplace

output = StrReplace( input, "<shortPercentage>", "" );

To trim tags from the list you could do the following

function RemoveTags( text )
{
	// list of tags without brackets
    tags = "symbol,name,shortPercentage,longPercentage";

    for( i = 0; ( tag = StrExtract( tags, i ) ) != ""; i++ )
    {
        opentag = "<" + tag + ">";
        closetag = "</" + tag + ">";
        text = StrReplace( text, opentag, "" );
        text = StrReplace( text, closetag, " - " ); // replace closing tag with - dash
    }

    return text;
}

Dislaimer: I just wrote it directly in post without checking.

1 Like

@Pervaz,

You should name the API being accessed.
I used Google search and found that you most probably refer to MyFxBook.com API
https://www.myfxbook.com/en/api

and in regards to 1st post to community outlook link:
https://www.myfxbook.com/api/get-community-outlook.xml?session=YOUR_ID_HERE

To get session ID
https://www.myfxbook.com/api/login.json?email=YOUR_EMAIL_HERE&password=YOUR_PASSWORD_HERE&debug=1

XML data of that community outlook link (and by using valid session ID) looks as follows:
7

So to get to result it is much simpler than in post #1:
(Don't forget to insert sessionID in line 4!)

/// @link https://forum.amibroker.com/t/parsing-xml-looping-issues/14759/5
/// by fxshrat@gmail.com
symbol = "EURUSD";// insert ticker or use Name()
sessionID = "";// insert your session ID 
url = StrFormat("https://www.myfxbook.com/api/get-community-outlook.xml?session=%s", sessionID);
result_str = "";
//
// Use some trigger
trigger = ParamTrigger( "Retrieve Community outlook", "CLICK HERE" );
//
if ( trigger ) {	
	/// @link https://www.amibroker.com/guide/afl/internetopenurl.html
	ih = InternetOpenURL( url ); 
	if ( ih ) { 	
		n = 0;
		line_num = -3;	
		name_tag = "<name>"+symbol;
		while ( ( str = InternetReadString( ih ) ) != "" ) {
			if (StrFind(str, name_tag))
				line_num = n;			
			if (n >= line_num AND n <= line_num+2) 
				result_str += StrExtract(str, 1, '<') + ","; 	
			n++;	
		}	
		InternetClose( ih );
		//
		result_str = StrTrim(StrReplace(result_str, "</", ""), ",");
		result_str = StrReplace(result_str, ">", ": ");
		result_str = StrReplace(result_str, "Percentage", "%");
		StaticVarSetText("MyFxBook_Community_"+symbol, result_str);
	}
}

result_str = StaticVarGetText("MyFxBook_Community_"+symbol);

GfxSetBkMode( 1 );
GfxSetTextAlign( 0 | 0 );
GfxSetTextColor( colorRed );
GfxSelectFont( "Arial", 10, 700, 0, 0, 0 );
GfxTextOut( "MyFXBook.com community outlook: ", x = 4, y = 15 );	
GfxSelectFont( "Arial", 10, 500, 0, 0, 0 );
GfxTextOut( result_str, x, y = 30 );

Plot( C, "Price", colorDefault, styleBar );

And it works as you can see:

2

2 Likes

Hi Tomasz and fxshrat

Thank you very much - both solutions worked.

Both of you represent why Amibroker is one of the best platforms around - one of the best hidden secrets !

Regards