~ubuntu-branches/ubuntu/maverick/cluster-agents/maverick-proposed

« back to all changes in this revision

Viewing changes to heartbeat/WAS6

  • Committer: Bazaar Package Importer
  • Author(s): Ante Karamatic
  • Date: 2010-02-17 21:46:00 UTC
  • Revision ID: james.westby@ubuntu.com-20100217214600-g44grvtkw7jbpciz
Tags: upstream-1.0.2
ImportĀ upstreamĀ versionĀ 1.0.2

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
#!/bin/sh
 
2
# WAS6 
 
3
#
 
4
# Description:  Manages a Websphere Application Server as an HA resource
 
5
#
 
6
#
 
7
# Author:       Ru Xiang Min
 
8
# Support:      linux-ha@lists.linux-ha.org
 
9
# License:      GNU General Public License (GPL)
 
10
# Copyright:    (C) 2006 International Business Machines China, Ltd., Inc.
 
11
#
 
12
#
 
13
# An example usage in /etc/ha.d/haresources:
 
14
#       node1  10.0.0.170 WAS::/opt/IBM/WebSphere/AppServer/profiles/default/config/cells/Node01Cell/nodes/Node01/serverindex.xml
 
15
#
 
16
# See usage() function below for more details...
 
17
#
 
18
#         OCF parameters are as below:
 
19
#               OCF_RESKEY_profile
 
20
#                 (WAS profile name, used for the single server edition of WAS6)
 
21
 
 
22
#######################################################################
 
23
# Initialization:
 
24
 
 
25
: ${OCF_FUNCTIONS_DIR=${OCF_ROOT}/resource.d/heartbeat}
 
26
. ${OCF_FUNCTIONS_DIR}/.ocf-shellfuncs
 
27
 
 
28
#######################################################################
 
29
 
 
30
WAS_DIR=/opt/IBM/WebSphere/AppServer
 
31
if
 
32
  [ ! -d $WAS_DIR ]
 
33
then
 
34
  WAS_DIR=/usr/IBM/WebSphere/AppServer
 
35
fi
 
36
STARTTIME=300   #       5 minutes
 
37
DEFAULT_WASPORTS="9080"
 
38
#
 
39
#
 
40
WAS_BIN=$WAS_DIR/bin
 
41
DEFAULT=default
 
42
#
 
43
#       Print usage message
 
44
#
 
45
usage() {
 
46
  methods=`WAS_methods | grep -v methods`
 
47
  methods=`echo $methods | tr ' ' '|'`
 
48
  cat <<-END
 
49
        usage: $0 ($methods)
 
50
 
 
51
        For the single server edition of WAS6, you have to set the following
 
52
        enviroment virable:
 
53
                OCF_RESKEY_profile
 
54
                        (WAS profile name)
 
55
 
 
56
 
 
57
        $0 manages a Websphere Application Server 6(WAS6) as an HA resource
 
58
 
 
59
        The 'start' operation starts WAS6.
 
60
        The 'stop' operation stops WAS6.
 
61
        The 'status' operation reports whether WAS6 is running
 
62
        The 'monitor' operation reports whether the WAS6 seems to be working
 
63
                (httpd also needs to be working for this case)
 
64
        The 'validate-all' operation reports whether the OCF instance parameter (OCF_RESKEY_profileName ) is valid
 
65
        The 'methods' operation reports on the methods $0 supports
 
66
 
 
67
        This is known to work with the Single Server edition of Websphere.
 
68
 
 
69
        The default profile name for the single server edition is:
 
70
        $DEFAULT
 
71
 
 
72
        The start and stop operations must be run as root.
 
73
 
 
74
        The status operation will report a pid of "-" for the
 
75
        WAS root process using unless it is run as root.
 
76
 
 
77
        If you don't have xmllint on your system, parsing of WAS
 
78
        configuration files is very primitive.
 
79
 
 
80
        We run servlet/snoop on the seventh transport port listed in
 
81
        the config file for the "monitor" operation.
 
82
 
 
83
        END
 
84
}
 
85
 
 
86
meta_data() {
 
87
        cat <<END
 
88
<?xml version="1.0"?>
 
89
<!DOCTYPE resource-agent SYSTEM "ra-api-1.dtd">
 
90
<resource-agent name="WAS6">
 
91
<version>1.0</version>
 
92
 
 
93
<longdesc lang="en">
 
94
Resource script for WAS6. It manages a Websphere Application Server (WAS6) as
 
95
an HA resource.
 
96
</longdesc>
 
97
<shortdesc lang="en">Manages a WebSphere Application Server 6 instance</shortdesc>
 
98
 
 
99
<parameters>
 
100
<parameter name="profile" unique="0" required="0">
 
101
<longdesc lang="en">
 
102
The WAS profile name.
 
103
</longdesc>
 
104
<shortdesc lang="en">profile name</shortdesc>
 
105
<content type="string" default="$DEFAULT" />
 
106
</parameter>
 
107
</parameters>
 
108
 
 
109
<actions>
 
110
<action name="start" timeout="300" />
 
111
<action name="stop" timeout="300" />
 
112
<action name="status" depth="0" timeout="30" interval="10" />
 
113
<action name="monitor" depth="0" timeout="30" interval="10" />
 
114
<action name="validate-all" timeout="5" />
 
115
<action name="meta-data" timeout="5" />
 
116
<action name="methods" timeout="5" />
 
117
</actions>
 
118
</resource-agent>
 
119
END
 
120
}
 
121
 
 
122
#
 
123
#       Reformat the XML document in a sort of canonical form
 
124
#       if we can.  If we don't have xmllint, we just cat it out
 
125
#       and hope for the best ;-)
 
126
#
 
127
xmlcat() {
 
128
  if
 
129
    [ "X$XMLcat" = X ]
 
130
  then
 
131
    XMLcat=`which xmllint 2>/dev/null`
 
132
    if
 
133
      [ "X${XMLcat}" = X  -o ! -x "${XMLcat}" ]
 
134
    then
 
135
      XMLcat=cat
 
136
    else
 
137
      XMLcat="$XMLcat --recover --format"
 
138
    fi
 
139
  fi
 
140
  for j in "$@"
 
141
  do
 
142
    ${XMLcat} "$j"
 
143
  done
 
144
}
 
145
 
 
146
#
 
147
#This is a bit skanky, but it works anyway...
 
148
#
 
149
# It's not really skanky if we can find xmllint on the system, because it
 
150
# reformats tags so they are all on one line, which is all we we need...
 
151
#
 
152
#
 
153
# Get the numbers of the ports WAS should be listening on...
 
154
#
 
155
# If we don't have xmllint around, then the applicationserver and the
 
156
# port= specification have to be on the same line in the XML config file.
 
157
#
 
158
GetWASPorts() {
 
159
  case $1 in
 
160
    [0-9]*)     echo "$1" | tr ',' '\012';;
 
161
    *)
 
162
        xmlcat ${WAS_DIR}/profiles/${WAS_PROFILE_NAME}/config/cells/${WAS_CELL}/nodes/${WAS_NODE}/serverindex.xml | 
 
163
        grep port=                              |
 
164
        sed -e 's%.*port= *"* *%%'              \
 
165
                -e 's%[^0-9][^0-9]*.*$%%'
 
166
        # Delete up to port=, throw away optional quote and optional
 
167
        #       white space.
 
168
        # Throw away everything after the first non-digit.
 
169
        # This should leave us the port number all by itself...
 
170
  esac
 
171
}
 
172
 
 
173
#
 
174
#       We assume that the seventh port listed in the serverindex.xml
 
175
#       is the one we should run servlet/snoop on.
 
176
#
 
177
GetWASSnoopPort() {
 
178
        GetWASPorts "$@" | sed -n '7p' 
 
179
}
 
180
 
 
181
#
 
182
#       Return information on the processname/id for the WAS ports
 
183
#
 
184
#       pid/java        is the expected output.  Several lines, one per port...
 
185
#
 
186
#
 
187
WASPortInfo() {
 
188
  pat=""
 
189
  once=yes
 
190
  PortCount=0
 
191
  for j in $*
 
192
  do
 
193
    case $pat in
 
194
      "")       pat="$j";;
 
195
      *)        pat="$pat|$j";;
 
196
    esac
 
197
    PortCount=`expr $PortCount + 1`
 
198
  done
 
199
  netstat -ltnp  2>/dev/null| egrep -i "($pat) .*LISTEN" | sed 's%.*LISTEN *%%'
 
200
}
 
201
 
 
202
#
 
203
#       Return the number of WAS ports which are open
 
204
#
 
205
CheckWASPortsInUse() {
 
206
  count=`WASPortInfo "$@" | wc -l`
 
207
  echo $count
 
208
}
 
209
 
 
210
#
 
211
#       Return the pid(s) of the processes that have WAS ports open
 
212
#
 
213
WASPIDs() {
 
214
  WASPortInfo "$@" | sort -u | cut -f1 -d/
 
215
}
 
216
 
 
217
#
 
218
#       The version of ps that returns all processes and their (long) args
 
219
#       It's only used by WAS_procs, which isn't used for anything ;-)
 
220
#
 
221
ps_long() {
 
222
  ps axww
 
223
}
 
224
 
 
225
 
 
226
#
 
227
#       The total set of WAS processes (single server only)
 
228
#
 
229
WAS_procs() {
 
230
  ps_long | grep -i "config=$1"  | grep -i java | cut -d' ' -f1
 
231
}
 
232
 
 
233
 
 
234
 
 
235
#
 
236
# methods: What methods/operations do we support?
 
237
#
 
238
WAS_methods() {
 
239
  cat <<-!
 
240
        start
 
241
        stop
 
242
        status
 
243
        methods
 
244
        validate-all
 
245
        meta-data
 
246
        usage
 
247
        !
 
248
  if
 
249
    have_binary $WGET
 
250
  then
 
251
    echo "      monitor"
 
252
  fi
 
253
}
 
254
 
 
255
#
 
256
#       Return WAS status (silently)
 
257
#
 
258
WAS_status() {
 
259
  WASPorts=`GetWASPorts $1`
 
260
  PortsInUse=`CheckWASPortsInUse $WASPorts`
 
261
  case $PortsInUse in
 
262
    0)  false;;
 
263
    *)  true;;
 
264
  esac
 
265
}
 
266
 
 
267
#
 
268
#       Report on WAS status to stdout...
 
269
#
 
270
WAS_report_status() {
 
271
  WASPorts=`GetWASPorts $1`
 
272
  PortCount=`echo $WASPorts | wc -w`
 
273
  PortCount=`echo $PortCount`
 
274
  PortsInUse=`CheckWASPortsInUse $WASPorts`
 
275
  case $PortsInUse in
 
276
    0)  ocf_log debug "WAS: server $1 is stopped."; return $OCF_NOT_RUNNING;;
 
277
    *)
 
278
        pids=`WASPIDs $WASPorts`
 
279
        if
 
280
          [ $PortsInUse -ge $PortCount ]
 
281
        then
 
282
          ocf_log debug "WAS: server $1 is running (pid" $pids "et al)."
 
283
        else
 
284
          ocf_log debug "WAS: server $1 is running (pid $pids et al) but not listening on all ports."
 
285
        fi
 
286
        return $OCF_SUCCESS;;
 
287
  esac
 
288
}
 
289
 
 
290
#
 
291
#       Monitor WAS - does it really seem to be working?
 
292
#
 
293
#       For this we invoke the snoop applet via wget.
 
294
#
 
295
#       This is actually faster than WAS_status above...
 
296
#
 
297
WAS_monitor() {
 
298
  trap '[ -z "$tmpfile" || rmtempfile "$tmpfile"' 0
 
299
  tmpfile=`maketempfile` || exit 1
 
300
  SnoopPort=`GetWASSnoopPort $1`
 
301
  output=`$WGET -nv -O$tmpfile  http://localhost:$SnoopPort/snoop 2>&1`
 
302
  rc=$?
 
303
  if
 
304
    [ $rc -eq 0 ]
 
305
  then
 
306
    if
 
307
      grep -i 'user-agent.*Wget' $tmpfile >/dev/null
 
308
    then
 
309
      : OK
 
310
    else
 
311
      ocf_log "err" "WAS: $1: no user-agent from snoop application"
 
312
      rc=$OCF_ERR_GENERIC
 
313
    fi
 
314
  else
 
315
    ocf_log "err" "WAS: $1: wget failure: $output"
 
316
    rc=$OCF_ERR_GENERIC
 
317
  fi
 
318
  return $rc
 
319
}
 
320
 
 
321
#
 
322
#       Start WAS instance
 
323
#
 
324
WAS_start() {
 
325
# Launch Arguments:
 
326
#     -nowait
 
327
#     -quiet
 
328
#     -logfile <filename>
 
329
#     -replacelog
 
330
#     -trace
 
331
#     -script [<script filename >] [-background]
 
332
#     -timeout <seconds>
 
333
#     -statusport <portnumber>
 
334
#     -profileName <profile>
 
335
#     -help
 
336
  if
 
337
    [ -x $WAS_BIN/startServer.sh ]
 
338
  then
 
339
    cmd="$WAS_BIN/startServer.sh server1  -profileName $1"
 
340
  fi
 
341
 
 
342
  if
 
343
    ocf_run $cmd
 
344
  then
 
345
    if
 
346
      WAS_wait_4_start $STARTTIME "$@"
 
347
    then
 
348
      #true
 
349
      return $OCF_SUCCESS
 
350
    else
 
351
      ocf_log "err" "WAS server $1 did not start correctly"
 
352
      return $OCF_ERR_GENERIC
 
353
    fi
 
354
  else
 
355
    #false
 
356
    if 
 
357
       WAS_wait_4_start $STARTTIME "$@"
 
358
    then
 
359
       #true
 
360
       return $OCF_SUCCESS
 
361
    else
 
362
       ocf_log "err" "WAS server $1 did not start correctly"
 
363
       return $OCF_ERR_GENERIC
 
364
    fi
 
365
  fi
 
366
}
 
367
 
 
368
#
 
369
#       Wait for WAS to actually start up.
 
370
#
 
371
#       It seems to take between 30 and 60 seconds for it to
 
372
#       start up on a trivial WAS instance.
 
373
#
 
374
WAS_wait_4_start() {
 
375
  max=$1
 
376
  retries=0
 
377
  shift
 
378
  while
 
379
    [ $retries -lt $max ]
 
380
  do
 
381
    if
 
382
      WAS_status "$@"
 
383
    then
 
384
      return $OCF_SUCCESS
 
385
    else
 
386
      sleep 1
 
387
    fi
 
388
    retries=`expr $retries + 1`
 
389
  done
 
390
  WAS_status "$@"
 
391
}
 
392
 
 
393
 
 
394
#
 
395
#       Shut down WAS
 
396
#
 
397
WAS_stop() {
 
398
  # They don't return good return codes...
 
399
  # And, they seem to allow anyone to stop WAS (!)
 
400
  if
 
401
    [ -x $WAS_BIN/stopServer.sh ]
 
402
  then
 
403
    ocf_run $WAS_BIN/stopServer.sh server1 -profileName $1
 
404
  else
 
405
    WASPorts=`GetWASPorts $1`
 
406
    kill `WASPIDs $WASPorts`
 
407
  fi
 
408
  if
 
409
    WAS_status $1
 
410
  then
 
411
    ocf_log "err" "WAS: $1 did not stop correctly"
 
412
    #false
 
413
    return $OCF_ERR_GENERIC
 
414
  else
 
415
    #true
 
416
    return $OCF_SUCCESS
 
417
  fi
 
418
}
 
419
 
 
420
#
 
421
#       Check if the port is valid
 
422
#
 
423
CheckPort() {
 
424
  ocf_is_decimal "$1" && [ $1 -gt 0 ]
 
425
}
 
426
 
 
427
WAS_validate_all() {
 
428
  if [ -x $WAS_BIN/startServer.sh ]; then
 
429
  # $arg should be profile name 
 
430
        if [ ! -f ${WAS_DIR}/profiles/${arg}/config/cells/${WAS_CELL}/nodes/${WAS_NODE}/serverindex.xml ]; then
 
431
            ocf_log err "profile [$arg] does not exist"
 
432
            exit $OCF_ERR_ARGS
 
433
        fi
 
434
 
 
435
  # $arg should specify a valid port number at the very least
 
436
        local WASPorts=`GetWASPorts $arg`
 
437
        if [ -z "$WASPorts" ]; then
 
438
            ocf_log err "No port number specified in configuration file of profile [$arg]"
 
439
            exit $OCF_ERR_CONFIGURED
 
440
        fi
 
441
 
 
442
        local port
 
443
        local have_valid_port=false
 
444
        for port in $WASPorts; do
 
445
            if CheckPort $port; then
 
446
                have_valid_port=true
 
447
                break
 
448
            fi
 
449
        done
 
450
        if [ "false" = "$have_valid_port" ]; then
 
451
            ocf_log err "No valid port number specified in configuration file of profile [$arg]"
 
452
            exit $OCF_ERR_CONFIGURED
 
453
        fi
 
454
 
 
455
  elif [ -x $WAS_BIN/startupServer.sh ]; then
 
456
  # $arg should be port number
 
457
        if CheckPort "$arg"; then
 
458
            ocf_log err "Port number is required but [$arg] is not valid port number"
 
459
            exit $OCF_ERR_ARGS
 
460
        fi
 
461
  else
 
462
  # Do not know hot to validate_all
 
463
        ocf_log warn "Do not know how to validate-all, assuming validation OK"
 
464
        return $OCF_SUCCESS
 
465
  fi
 
466
}
 
467
#
 
468
#       'main' starts here...
 
469
#
 
470
 
 
471
if
 
472
  ( [ $# -ne 1 ] )
 
473
then
 
474
  usage
 
475
  exit $OCF_ERR_ARGS
 
476
fi
 
477
 
 
478
# These operations don't require OCF instance parameters to be set
 
479
case "$1" in
 
480
 
 
481
  meta-data)    meta_data
 
482
                exit $OCF_SUCCESS;;
 
483
 
 
484
  usage)        usage
 
485
                exit $OCF_SUCCESS;;
 
486
 
 
487
  methods)      WAS_methods
 
488
                exit $?;;
 
489
  *);;
 
490
esac
 
491
 
 
492
 
 
493
#
 
494
#       Supply default configuration parameter(s)
 
495
#
 
496
 
 
497
if
 
498
   [ -z $OCF_RESKEY_profile ] 
 
499
then
 
500
    arg=$DEFAULT
 
501
else
 
502
    arg=$OCF_RESKEY_profile
 
503
fi
 
504
 
 
505
if
 
506
   [ ! -d ${WAS_DIR}/profiles/$arg ]
 
507
then
 
508
    ocf_log "err" "WAS profile $arg does not exist!"
 
509
    usage
 
510
    exit $OCF_ERR_ARGS
 
511
fi
 
512
 
 
513
WAS_PROFILE_NAME=$arg
 
514
if [ "${WAS_PROFILE_NAME:=}" != "" ]; then
 
515
    WAS_PROFILE_FSDB_SCRIPT=${WAS_DIR}/properties/fsdb/${WAS_PROFILE_NAME}.sh
 
516
fi
 
517
 
 
518
if [ "${WAS_PROFILE_FSDB_SCRIPT:=}" != "" ] && [ -f ${WAS_PROFILE_FSDB_SCRIPT} ]; then
 
519
    . ${WAS_PROFILE_FSDB_SCRIPT}
 
520
fi
 
521
 
 
522
if [ "${WAS_USER_SCRIPT:=}" != "" ]; then
 
523
    . ${WAS_USER_SCRIPT}
 
524
fi
 
525
 
 
526
# What kind of method was invoked?
 
527
case "$1" in
 
528
 
 
529
  start)        WAS_start $arg
 
530
                exit $?;;
 
531
 
 
532
  stop)         WAS_stop $arg
 
533
                exit $?;;
 
534
 
 
535
  status)       WAS_report_status $arg
 
536
                exit $?;;
 
537
 
 
538
  monitor)      WAS_monitor $arg
 
539
                exit $?;;
 
540
 
 
541
  validate-all) WAS_validate_all $arg
 
542
                exit $?;;
 
543
 
 
544
  *)            usage
 
545
                exit $OCF_ERR_UNIMPLEMENTED;;
 
546
esac