File: example2.pm

package info (click to toggle)
libcgi-xmlapplication-perl 1.1.5-2
  • links: PTS, VCS
  • area: main
  • in suites: bookworm, sid, trixie
  • size: 196 kB
  • sloc: perl: 522; makefile: 2
file content (147 lines) | stat: -rw-r--r-- 5,409 bytes parent folder | download | duplicates (6)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
# this is the application class
#
# this example shows how to make use of the context
# and how passing your personalized xml dom around.
#
# actually this is allready a full featured example, although it does
# nothing useful :>
#
# while programming with this package you should avoid printing to the
# clientside, because this is the job of the serialization function.
# for q'n'd scripter this will be the biggest change of
# paradigma. from the viewpoint of XML/ XSLT this follows exactly the
# paradigma of separating function, content and presentation.
#
# once you get used not using the print function from inside a script,
# you will realize the resulting code will be much easier to maintain.

package example2;

use vars qw( @ISA @HANLDER );
use CGI::XMLApplication;
use XML::LibXML;

@ISA     = qw(CGI::XMLApplication);

# if you implement internal error events ashure, you place them at the
# very end of the eventlist, so if someone places a parameter with the
# same name into a form, the script can still find the correct event
# (which is usually the submit button a client pushed).
#
# what are internal events good for? i found it's comfortable to have
# special events, for special problems. this could be that a database
# server is not reachable or a client session has expiered. These are
# no real events, clients cause by clicking around, but in my logic,
# this should be handled in special events. So i delete all existing
# events (done implicit by sendEvent) and send the error event by
# myself.

sub registerEvents { qw( submit _internal_error_ ); } # the handler list

# the requestDOM function is called by the serialize function.  it has
# to return a XML::LibXML::Document object. If no DOM is
# returned,sreialize will create an empty DOM, so stylesheets can be
# processed, even if the script does not create a DOM structure
#
# pay attention that you can use any name to store your own DOM
# in the context hash.

sub requestDOM     { my ( undef, $ctxt ) = @_; return $ctxt->{-XML}; }

# one can implement any complexity of stylesheet selection wanted, but
# i recommend to keep this function as simple as possible.
sub selectStylesheet {
  my ( $self, $ctxt ) = @_;
  return $self->getStylesheetPath() . qw( ex2_form.xsl ex2_finish.xsl )[ $ctxt->{-stylesheet} ];
}


# the following subroutine will make CGI::XMLApplication to pass the returned 
# hash to the stylesheetprocessor
sub getXSLTParameter {
  my ( $self, $ctxt ) = @_;
  return ( test=>$ctxt->{-test}||-1 );
}

# the init event should do all required initializing, that is common
# to all events implemeted, as well system problems should be catched
# here as well
sub event_init {
  my ( $self , $ctxt ) = @_;

  # initialize the context
  my $dom = XML::LibXML::Document->new();
  my $root= $dom->createElement( 'yourfavouritetagname' );
  $dom->setDocumentElement( $root );

  $ctxt->{-XML} = $dom;
  $ctxt->{-ROOT}= $root;
  $ctxt->{-stylesheet} = 0; # on default we'll display the form

  # do some testing
  # in more complex scripts such tests would be confusing here ...
  # the use of error handling inside event_init is more for general
  # problems.
  if ( $self->param('email')=~/\@.*\@/ || $self->param('email')!~/\@..+/ ) {
    $self->sendEvent('_internal_error_' );
  }
}

# exit is called before serialization
sub event_exit {
  my ( $self , $ctxt ) = @_;
  # we do some caching here, but you can do whatever you like
  # (e.g. release lockfiles)
  if ( exists $ctxt->{-XML} && not exists $ctxt->{-ERROR} ){
    open CACHEFILE , "> ex2_cache.xml";
    print CACHEFILE $ctxt->{-XML}->toString();
    close CACHEFILE;
  }
}

sub event_default {
  my ( $self , $ctxt ) = @_;
  $ctxt->{-ROOT}->appendTextChild('message','Hey user from ' .
                                             $self->remote_host() .
                                            " pass your email!" );

  # PAY ATTENTION HERE!
  # the return value has to be greater or equal 0. If a value
  # less than 0 is returned CGI::XMLApplication asumes an so called
  # panic. This will have the effect, that no XSLT redering is tried 
  # and a special error message is returned (see setPanicMsg)
  # CGI::XMLApplication knows 4 types of panics:
  # -1 "no stylesheet set" (internal error)   (no filename given)
  # -2 "no stylesheet found" (internal error) (like file not found)
  # -3 "no event function for registred event" (internal error) (...)
  # -4 "application error"    (this one is for you) ;)
  # 
  # if it is a valid value, the value itself has no meaning anymore...
  return 0;
}

# as one can see easily, the event functions has to have the same name
# as the event has. the prefix 'event_' is a requirement.
#
# i think, i'll introduce real callbacks quite soon, so one can choose
# any function name prefered and has only to register it to the related
# event.

sub event__internal_error_ {
  my ( $self , $ctxt ) = @_;
  $ctxt->{-ROOT}->appendTextChild('message',
                                  'this email seems not to be valid');
  $ctxt->{-ROOT}->appendTextChild( 'email', "".$self->param( 'email' ) );
  $ctxt->{-ERROR} = 1;
  return 0;
}

sub event_submit {
  my ( $self , $ctxt ) = @_;
  $ctxt->{-ROOT}->appendTextChild('message',
                                  "ALL YOUR BASE DOES BELONG TO US!"); # ;)
  $ctxt->{-stylesheet} = 1; # submit was ok, so display the thank you message
  return 0;
}

1;