• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
Re: [Wonder-disc] Helper Functions
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Wonder-disc] Helper Functions


  • Subject: Re: [Wonder-disc] Helper Functions
  • From: Mike Schrag <email@hidden>
  • Date: Fri, 20 Oct 2006 04:25:55 -0400

Namespacing is definitely the tricky part at the moment. I tried to address _basic_ namespace support in a straightforward way, figuring once people use it, other ideas would come up.

I was thinking that ERExtensions might have the "main" set of helpers for the base types (String, NSTimestamp, primitives, etc), which you could extend in your own apps. Alternatively, WOOGNL could depend on ERX (it doesn't now) and we can put the main helpers in there. The OGNL option organizationally makes a little more sense, I think.

I've not really done anything with AOP, so I'm open for suggestions/ recommendations here. Every time I've looked at AOP it sort of looked insane and I scurried away :)

The auto-increasing id helper is a bit of a funky case. You're not really "formatting" anything in that case -- you're generating (if i understand you correctly). You could probably trick it into working, but I can't think of a "natural" way to do it with the current syntax.

This is all pretty new (we've only been using it here for about a week), so let me know if you have suggestions for it.

ms

On Oct 20, 2006, at 4:01 AM, Cornelius Jaeger wrote:

hi mike

that is way cool.

what would be the preferred way to make standard helper classes that everyone can use and subclass, in terms of namespace etc.
i imagine a bunch of standard string helpers and date time formatters etc would be useful.
any way to make mixins happen using aop? so i can have my StringHelper with a truncate method, mix it into my person class and pass it a method parameter, say description, and a length parameter, say 20.
and of course for ajax auto increasing id helpers for using id's in worepetitions etc. would be very useful.


any thoughts


Cornelius

On 20.10.2006, at 00:41, Mike Schrag wrote:

This addition is part of the WOOGNL framework and should appear in
tonight's build:

=== Overview ===
It is often the case in a WOD file that you want to apply formatters
to various
bindings, but only certain specific components actually support the
concept of
a formatter.

There are several approaches to solving this problem.  One is to
create formatter
methods on your models (i.e, person.displayName() that returns
firstName() + " " + lastName()).
This suffers a design flaw in that you don't want what is essentially
view code in your
models.  Another approach is to define these methods in a
WOComponent, but then you have the
problem that you can't reuse the value very easily (you need it in
every component).  You could
create a new WOComponent that just renders in this format, but then
you can't pass it as the
value to another binding.

Rails addresses this with the concept of a helper function.  Helper
functions are easily reusable
formatting methods for use in your views.  WOHelperFunctionHTMLParser
provides a similar type of
functionality for use in WOD bindings.


=== Example Usage === As an example, say you have a Person class and you want a common display name (like in the example above). With WOHelperFunctionHTMLParser, you would do the following:

1) Create a class like the following (in any package):
	public class PersonHelper {
		public String displayName(Person person) {
			return person.firstName() + " " + person.lastName();
		}
	}

2) In a WOD file:
	PersonName : WOString {
		value = currentPerson|displayName;
	}

(that is a pipe between currentPerson and displayName)

3) Set ognl.helperFunctions=true in your Properties file.

4) Profit.

Likewise you can make StringHelper, BooleanHelper, etc.  You want to
use "yes" or "no" when
you display booleans?

in Java:
	public class BooleanHelper {
		public String yesNo(Boolean value) {
			String yesNoValue;
			if (yesNoValue == null || !yesNoValue.booleanValue()) {
				yesNoValue = "no";
			}
			else {
				yesNoValue = "yes";
			}
		}
	}

in your WOD:
	RandomValue : WOString {
		value = currentPerson.isAdmin|yesNo;
	}

The above examples use WOString, so /technically/ you could use
formatters for these.  Here's
an example where that wouldn't work out:

	HeaderFooter : HeaderFooterWrapper {
		title = currentPerson|displayName;
	}

The examples here only define a single method, but you can define as
many helper methods inside
of the Helper classes as you'd like.


=== How Does it Work? === In the parser stage of loading your WOD file, helper function bindings are replaced with the much larger WOOGNL expression that is able to resolve your request, so behind the scenes this is using the same OGNL that you know and love.

The helper class to use for a particular value is determined by the
type of object that comes
immediately before the pipe symbol.  For instance, if getClass
().getName() returns
"com.mdimension.Person", by default WOHelperFunction will look for a
"PersonHelper" class
using the same bundle discovery that components use.


=== Helper Function Parameters === Because the method calls turn into WOOGNL behind the scenes, parameters should mostly just work. As an example, you could make a truncate helper function:

in Java:
	public class StringHelper {
		public String truncate(String value, int atIndex) {
			String truncatedValue = value;
			if (value != null && value.length() > atIndex) {
				truncatedValue = value.substring(0, atIndex) + " ...";
			}
			return truncatedValue;
		}
	}

and in your WOD:
	HeaderFooter : HeaderFooterWrapper {
		title = pageMetadata.description|truncate(10);
	}

You are not limited to just a single parameter.


=== Remapping Helper Instances === It is sometimes helper to remap a particular type of object to a custom helper class. In this case, you can call:

setHelperInstanceForClassInFrameworkNamed(Object helperInstance,
Class targetObjectClass, String frameworkName);

Let's say you want Person.class to use MyPersonHelper as its helper
instance for the entire app, you would call:

WOHelperFunctionRegistry.setHelperInstanceForClassInFrameworkNamed
(new MyPersonHelper(), Person.class, "app");


=== Per-Framework Helper Functions === Unqualified, helper functions look in the "app" frameworkName to resolve. However, this can cause conflicts if you have a framework that wants to register its own helpers (you wouldn't want to replace the top-level StringHelper, for instance). Take Ajax framework as an example:

WOHelperFunctionRegistry.setHelperInstanceForClassInFrameworkNamed
(new AjaxPersonHelper(), String.class, "Ajax");

To use a qualified helper function, you use the syntax:

HeaderFooter : HeaderFooterWrapper {
	title = currentPerson|Ajax.displayName;
}

Note the "Ajax." qualifier in front of the helper function name.


=== Subclassing Helper Instances === Subclassing with helper instances is legal. So if you have a StringHelper in your core framework, you can make a MyProjectStringHelper extends StringHelper and register MyProjectStringHelper as "app" helper.


=== Gotchas === Because the registry depends on the type of the object to find the appropriate helper instance, if the value is null, it will not be able to find a helper instance.

If you use WOLips, you should go to Windows=>Preferences=>WOLips=>WOD
Editor and add pipe, open
paren, and close paren to the list of valid wod binding characters.

--------------------------------------------------------------------- ----
Using Tomcat but need to do more? Need to support web services, security?
Get stuff done quickly with pre-integrated technology to make your job easier
Download IBM WebSphere Application Server v.1.0.1 based on Apache Geronimo
http://sel.as-us.falkag.net/sel? cmd=lnk&kid=120709&bid=263057&dat=121642
_______________________________________________
Wonder-disc mailing list
email@hidden
https://lists.sourceforge.net/lists/listinfo/wonder-disc


_______________________________________________ Do not post admin requests to the list. They will be ignored. Webobjects-dev mailing list (email@hidden) Help/Unsubscribe/Update your Subscription: This email sent to email@hidden
  • Follow-Ups:
    • Re: [Wonder-disc] Helper Functions
      • From: Cornelius Jaeger <email@hidden>
  • Prev by Date: Re: stack overflow error
  • Next by Date: Re: Obscure Primary Key Gotcha
  • Previous by thread: Re: Obscure Primary Key Gotcha
  • Next by thread: Re: [Wonder-disc] Helper Functions
  • Index(es):
    • Date
    • Thread