Brilliant example Chris, I love it!!

This shows exactly what can be built with continuations and tail-recursive functions.

On Friday, Dec 6, 2002, at 19:13 US/Pacific, Christopher Oliver wrote:

Um, I think Daniel basically answered this question a long time ago: http://marc.theaimsgroup.com/?l=xml-cocoon-dev&m=102052662705449&w=2.

Sorry, I don't have an actual implementation, but I think it's clear that the corresponding flow code would be much more readable than the action code in the XML form howto (namely something like below). That is the whole point of the flow layer - that you don't have to write state-machine code as in XMLForm actions. Compare the flow version to the original XMLForm action code reproduced below, and judge for yourself.

// display form, wait for submission, and
// apply validations; repeat until no violations
function sendView(form, view, uri) {
form.clearViolations();
if (uri == undefined) {
uri = view + ".xml";
}
sendPageAndWait(uri, {id: view});
form.populate(cocoon.request);
if (form.violations != null) {
sendView(form, view, uri);
}
}
The recursive call to sendView here is what is called a tail-recursive call. This type of calls are optimized by Christopher's modified engine to avoid eating stack space, a common technique in functional languages. They behave as a simple goto to the beginning of the function.

function createForm() {
   // create the Form object
   // ...
}

function howToWizard() {
   // different form views
   // participating in the wizard
   var VIEW_START = "start";
   var VIEW_REGISTRATION = "registration";
   var VIEW_INTEREST = "interest";
   var VIEW_GARDENING = "organicGardening";
   var VIEW_COOKING = "cooking";
   var VIEW_SMALLHOLDING = "smallholdingManagement";
   var VIEW_CONFIRM = "confirm";
   var VIEW_END = "end";

   var form = createForm();
   var jBean = form.getModel();
   sendView(form, VIEW_START);
   sendView(form, VIEW_REGISTRATION);
   sendView(form, VIEW_INTEREST);
   if (jBean.organicGardening) {
       sendView(form, VIEW_GARDENING);
   } else if (jBean.cooking) {
       sendView(form, VIEW_COOKING);
   } else if (jBean.smallholdingManagement) {
       sendView(form, VIEW_SMALLHOLDING);
   }
   sendView(form, VIEW_CONFIRM);
   sendView(form, VIEW_END);
}
Which shows exactly why continuations provide such a simple way of programming complex applications!

Best regards,
Ovidiu

------------------------------------------------------------

From HowToWizardAction.java:

     ....

    // apply control flow rules
     if ( formView.equals ( VIEW_REGISTRATION ) )
     {
       if ( command.equals( CMD_NEXT ) )
       {
         return page(  VIEW_INTEREST );
       }            }
     else if ( formView.equals ( VIEW_INTEREST ) )
     {
       if ( command.equals( CMD_NEXT ) )
       {
          if ( jBean.getOrganicGardening() == true )
          {
            return page( VIEW_GARDENING );
          }
          else if ( jBean.getCooking() == true )
          {
            return page( VIEW_COOKING );
          }
          else if ( jBean.getSmallholdingManagement() == true )
          {
            return page( VIEW_SMALLHOLDING );
          }
          //else if ( getForm().get
         return page(  VIEW_CONFIRM );
       }
       if ( command.equals( CMD_PREV ) )
       {
          return page( VIEW_REGISTRATION );
       }
     }
     else if ( formView.equals ( VIEW_GARDENING ) )
     {
       if ( command.equals ( CMD_NEXT ) )
       {
          if ( jBean.getCooking() == true )
          {
            return page( VIEW_COOKING );
          }
          else if ( jBean.getSmallholdingManagement() == true )
          {
            return page( VIEW_SMALLHOLDING );
          }                  return page( VIEW_CONFIRM );
       }
       else if( command.equals( CMD_PREV ) )
       {
         return page( VIEW_INTEREST );
       }
     }
     else if ( formView.equals ( VIEW_COOKING ) )
     {
       if ( command.equals ( CMD_NEXT ) )
       {
          if ( jBean.getSmallholdingManagement() == true )
          {
            return page( VIEW_SMALLHOLDING );
          }                  return page( VIEW_CONFIRM );
       }
       else if ( command.equals( CMD_PREV ) )
       {                  if ( jBean.getOrganicGardening() == true )
         {
           return page( VIEW_GARDENING );
         }
         return page( VIEW_INTEREST );
       }
     }
     else if ( formView.equals ( VIEW_SMALLHOLDING ) )
     {
       if ( command.equals( CMD_NEXT ) )
       {
         return page( VIEW_CONFIRM );
       }
       else if ( command.equals( CMD_PREV ) )
       {
         if ( jBean.getCooking() == true )
         {
           return page( VIEW_COOKING );
         }
         else if ( jBean.getOrganicGardening() == true )
         {
           return page( VIEW_GARDENING );
         }
         return page( VIEW_INTEREST );
       }
     }
     else if ( formView.equals ( VIEW_CONFIRM ) )
     {
       if ( command.equals( CMD_NEXT ) )
       {
          return page( VIEW_END );
       }
       else if( command.equals( CMD_PREV ) )
       {
          if ( jBean.getOrganicGardening() == true )
          {
            return page( VIEW_GARDENING );
          }                  return page( VIEW_INTEREST );
       }
     }
   }

Ivelin Ivanov wrote:

Sorry I wasn't clear before.
I know you can call Java from the flow.
The question is how to use the flow in a way which significantly reduces
code
while making the maintenance easier and improving the readability.

Try to beat the existing XMLForm wizard demo.
If you succeed, it will be great !

Fingers crossed,

Ivelin


----- Original Message -----
From: "Ugo Cei" <[EMAIL PROTECTED]>
To: <[EMAIL PROTECTED]>
Sent: Thursday, December 05, 2002 2:36 AM
Subject: Re: [Proposal] Implementing XMLForm with Flow



Ivelin Ivanov wrote:

I hope you are the last hero trying to confront this monster.

The discussion how to combine the two has been going on forever, but we

have

not come to an agreement.

I'm currently recovering the previous threads from the archive and
reading them.


I would gladly offer my tactical guidance for your effort.

Thank you.


If I was to do this with Actions, I could use well known and

standardized

Java APIs - JWSP or JDBC.

But, as Ovidiu pointed out, you can!

var schemaFactory =
Packages.org.apache.cocoon.components.validation.SchemaFactory.lookup
("http://www.ascc.net/xml/schematron";);
var is = new Packages.org.xml.sax.InputSource
("flows/newuser-schema.xml");
var schema = schemaFactory.compileSchema(is);
var validator = schema.newValidator();
validator.setProperty("http://xml.apache.org/cocoon/validator/phase";,
"NewUser");
violations = validator.validate(userBean);

This is just a quick hack I put together looking at the code for the
AbstractXMLFormAction and Form, but it works. I just need to define some
symbolic constants for the namespaces and find a way to access a
SourceResolver from JavaScript to make it pretty.

Anyway, if you prefer to write complex business logic in Java (and I'd
agree wholeheartedly with that), you can encapsulate it in a Java method
that returns a boolean or an index to drive the flow that will be
implemented by an if/then/else or a switch in JavaScript.

What do we gain by this? We remove flow logic from the sitemap in the
form of actions and put it in the flowscript, where it belongs (IMHO).

Ugo

--
Ugo Cei - http://www.beblogging.com/blog/


---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, email: [EMAIL PROTECTED]



---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, email: [EMAIL PROTECTED]





---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, email: [EMAIL PROTECTED]


---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, email: [EMAIL PROTECTED]

Reply via email to