Introduction

I wanted to play with web services with regards to how they might be
implemented in MyXaml, and I figured an interesting web service to try out is
one that reports the current weather conditions and a forecast.

It was interesting trying to even find a working weather web service.
Most of the ones I tried were dead or didn't work. I finally stumbled upon
the CP article "Writing a Web Service
Consumer using Borland C# Builder" by Sagar Regmi, and after investigating
the EJSE site, I discovered that it has
everything that I need:

current conditions

forecast

nice bitmaps

The latter, nice bitmaps, I stumbled across a weblog that pointed out that
the icons are available from EJSE also (I think this is the weblog where I found the
info).

For our international community, sorry, but this web service only works in
the US.

When the namespace and the assembly are the same, the first form is
sufficient. When the namespace is different from the assembly name, then
the second form must be used. The third form is useful if you want to
reference a specific assembly version or culture.

The Form Declaration

These are all properties of the .NET Form class. The "def:Name"
attribute instructs the parser to keep track of the instance in a key/value pair
list. The key is always the attribute value, and the value is the class
instance.

The Service Invocations

First, the service must be instantiated. MyXaml isn't just a UI markup
parser. It can instantiate any parameter-less class. In this
case:

<ws:Service def:Name="Service"/>

MyXaml is instantiating the service. The "ws:" prefix tells the parser
that the class is found in the assembly referenced by the previous namespace
declaration. Again, the "def:" prefix is used, which tells the parser to
save a reference to the instance just created. Even though the Service
class doesn't have a Name property, the above statement is still processed.

To get your local weather, edit the file and replace "02852" with
your zipcode.

While MyXaml supports inline and code-behind, sometimes that's
overkill. All we really want to do is call a method, passing some
parameters to it, and possible do something with the return value.

The above two lines instantiate the class Invoke, found in the XWorkflow
assembly (as determined by the "wf:" prefix). For every class that is
instantiated, the parser checks, via reflection, if it has a "Finisher"
method. if so, this method is invoked. In the case of the Invoke
class, the Finisher method is defined to invoke, via reflection, the method
initialized in the XML attributes:

DefList - this is the definition list to use to resolve references. In
this case, we're passing MyXaml's own definition list, which it adds to its own
key/value object list so that it can be referenced in the markup. The {}
braces tell the parser to look up the object in the object list.

Target - this is the object on which we are calling a method. The {}
braces tell the parser to look up the object in the object list, which is why we
used the "def:" format in naming the Service instance.

Method - this is the method to invoke

Args - these are the arguments, comma delimeted. Note the kludge to
convert the string to an "int".

RetVal - if defined, the return value (an object, we don't care about type)
is added to the definition list. The attribute value is the key in the
key/value pair.

In this particular case, the WeatherInfo and ExtendedWeatherInfo return
instances are being stored in the MyXaml definition list, using the name keys
"Info" and "ExtInfo".

What does the Invoke code look like? There are a couple interesting
parts:

Yes, there's a serious kludge in this code, regarding testing for the "[int]"
substring. I'll be fixing that in the next version of MyXaml. But
the interesting thing about this code is how it builds the type array, which is
needed to find the specific method that accepts the particular parameter types
(often, .NET can resolve this on its own. Under certain cases though, it
can't, which results in an exception being thrown, that ambiguous parameters are
resulting in two or more matching methods, hence I go through the pains of
getting the type information myself).

The interesting thing here is the Text="{Info.Location}" and similar
attributes. This syntax instructs the parser to return the object
referenced inside the {} braces. However, instead of just returning the
object, the dot notation is used to tell the parser to return the value of the
object's property, as named on the right side of the ".". This syntax can
be used to drill down into properties to any depth, and is a very convenient way
of getting access to object property values.

The Forecast Controls

The five day forecast employs a really neat feature of MyXaml, the ability to
include repetitive blocks of XML. This feature is used to display the
Day1, Day2, Day3, Day4, and Day5 members of the ExtendedWeatherInfo instance,
all of which are DayForecastInfo objects. Because the web service is
nicely structured in this way, we can employ the prefix/postfix feature of the
Include processor to adjust for the specific member instance that we're
interested in.

Remember that the parser instantiates any kind of class. Again, the
Include tag is implemented with a class named Include. The core parser
doesn't know and doesn't care about includes, or anything else specific about
the class that it is instantiating. This is a very important thing.
Any "custom" parsing is handled by classes that are instantiated by the core
parser. Essentially, MyXaml is a plug-in framework.

For each GroupBox, note how the text is being set to
"{ExtInfo.Day<n>.Day}", where <n> is for days 1-5. The second
thing to note is the "Postfix" property, which specifies a value. The
Include class allows you to define a prefix and a postfix value, which can be
applied anywhere in the included markup, using the #prefix# and #postfix#
notation.

OK, the notation is a bit nutso, isn't it? Well, regardless, I've used
this feature on numerous occasions in the years of application development that
I've done with the Application Automation Layer, and I can attest to it's
incredible flexibility and power.

Here we see a few things. First off, is the PictureBox. MyXaml
complies with the concept of tags being in a "class-property-class" hierarchy
(although in cases where the property name and the property value, as
implemented by a class, are the same, you can use the "class-class" format):

PictureBox is a class.

Image is a property of that class, which just so happens to be implemented
by an Image class, but we can't use it directly because of the way it is
implemented.

The Bitmap class in MyXaml returns an Image, and has some smarts in it--the
image can be obtained from a URL, file, or resource.

The parser, following the "class-property-class" rule, assigns the object
constructed by the Bitmap class to the Image property of the PictureBox
instance.

Note the URL. Using the #postfix# syntax, we can extract the IconIndex
referenced by the particular day. Similarly, the forecast, precipitation
probability, high and low temperature text is extracted for the instance
determined by the #postfix# contents.

When markup is included, a pre-processor implemented in the Include class
goes through the attribute values and replaces all occurances of #prefix# and
#postfix# with the values specified in the Include tag. Yes, this is time
consuming and could stand for a lot of optimization. Regardless, the
functionality that this feature provides is quite powerful. It keeps us
from having to write the same markup over and over (in this case, 5 times
over)!

Conclusion

Besides demonstrating a simple web service, I hope that primarily this
article gives you some interesting ideas regarding how XML can be used to
declaratively instantiate classes. Some of the techniques, such as the
Include feature, are really nifty--you can create a library of UI building
blocks, for example. Remember, this isn't limited to UI though. In
my blog, I demonstrate using the
Include tag to load in a DataTable of states and their abbreviations.

Using MyXaml, or any general purpose declarative instantiator engine, really
changes the way in which you think about programming. Besides helping to
decouple objects, this method of programming really helps to separate the UI
from the control logic. If you generalize that idea, you can see that it
creates a nice separation between the "passive" parts of the program and the
"active" parts. I've found that, a lot of times, the passive parts change
over time while the active parts remain the same. Being able to easily
modify the UI, data tables, or other declaratively initialized information ends
up making my applications more robust. I'm not recompiling code, the
application is more resilient to new and existing feature changes, and I can get
my work done faster (yes, even without a designer!).

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

// instance of web service proxy class.WeatherWebService objWeatherWebServic = new WeatherWebService();// set up WebProxyIWebProxy wp = new WebProxy("192.168.10.4:8080", true);// set Credentials for proxywp.Credentials = new NetworkCredential("trf","3333");// set proxy for objWeatherWebServic objWeatherWebServic.Proxy = wp;

A friend of mine put together this site ( http://www.lostsprings.com/weather.aspx ). It also uses a web service to gather the data. If you click on the "details" link he shows a diagram of how it all works. He lives in the Texas hill country so it is specific to the central Texas area. Includes doppler radar image.

Request - Could everyone who have in the past, posted on my personal forum on CP, be kind enough to delete all your posts please? I intend to start a personal non-technical blog there, now that it is RSSd and would very much like to empty the forum before I do so - because the posts that are there as of now are mostly test posts and posts that were made before we all knew it was a blog