nordugrid-arc-gangliarc-1.0.0/0000775000175000017500000000000012246510656017610 5ustar waananenwaananen00000000000000nordugrid-arc-gangliarc-1.0.0/gangliarc0000775000175000017500000001371012245655604021471 0ustar waananenwaananen00000000000000#!/bin/sh # # gangliarc Ganglia monitoring for ARC services # # chkconfig: - 75 25 # description: Ganglia monitoring for ARC services # # config: /etc/sysconfig/nordugrid # config: /etc/arc.conf ### BEGIN INIT INFO # Provides: gangliarc # Required-Start: $local_fs $remote_fs # Required-Stop: $local_fs $remote_fs # Default-Start: # Default-Stop: # Short-Description: Ganglia monitoring for ARC services # Description: gangliarc adds ARC service-related information to Ganglia ### END INIT INFO # source function library if [ -f /etc/init.d/functions ]; then . /etc/init.d/functions log_success_msg() { echo -n "$@" success "$@" echo } log_warning_msg() { echo -n "$@" warning "$@" echo } log_failure_msg() { echo -n "$@" failure "$@" echo } elif [ -f /lib/lsb/init-functions ]; then . /lib/lsb/init-functions else echo "Error: Cannot source neither init.d nor lsb functions" exit 1 fi prog=gangliarc RUN=yes # sysconfig files if [ -r /etc/sysconfig/nordugrid ]; then . /etc/sysconfig/nordugrid elif [ -r /etc/default/nordugrid ]; then . /etc/default/nordugrid fi if [ -r /etc/sysconfig/${prog} ]; then . /etc/sysconfig/${prog} elif [ -r /etc/default/${prog} ]; then . /etc/default/${prog} fi readconfigvar() { fname=$1 if [ ! -r "$fname" ]; then return fi bname="[$2]" vname=$3 value= cat "$fname" | grep -e '^\[' -e "^${vname}=" | { while true; do read line if [ ! $? = 0 ] ; then return fi if [ "$line" = "$bname" ] ; then while true ; do read line if [ ! $? = 0 ] ; then return fi lstart=`echo "$line" | head -c 1` if [ "$lstart" = '[' ] ; then return fi vlname=`echo "$line" | sed 's/=.*//;t;s/.*//'` if [ "$vlname" = "$vname" ] ; then val=`echo "$line" | sed 's/[^=]*=//'` eval "echo $val" return fi done fi done } } # ARC_CONFIG if [ "x$ARC_CONFIG" = "x" ]; then if [ -r $ARC_LOCATION/etc/arc.conf ]; then ARC_CONFIG=$ARC_LOCATION/etc/arc.conf elif [ -r /etc/arc.conf ]; then ARC_CONFIG=/etc/arc.conf fi fi if [ ! -r "$ARC_CONFIG" ]; then log_error_msg "ARC configuration not found (usually /etc/arc.conf)" exit 1 fi CMD=`readconfigvar "$ARC_CONFIG" gangliarc python_bin_path` if [ "x$CMD" = "x" ]; then CMD=/usr/bin/python fi if [ ! -x "$CMD" ]; then log_failure_msg "Cannot find python executable" exit 1 fi PID_FILE=`readconfigvar "$ARC_CONFIG" gangliarc pidfile` LOG_FILE=`readconfigvar "$ARC_CONFIG" gangliarc logfile` if [ `id -u` = 0 ] ; then # Debian does not have /var/lock/subsys if [ -d /var/lock/subsys ]; then LOCKFILE=/var/lock/subsys/$prog else LOCKFILE=/var/lock/$prog fi if [ "x$PID_FILE" = "x" ]; then PID_FILE=/var/run/$prog.pid fi if [ "x$LOG_FILE" = "x" ]; then LOG_FILE=/var/log/arc/$prog.log fi else LOCKFILE=$HOME/$prog.lock if [ "x$PID_FILE" = "x" ]; then PID_FILE=$HOME/$prog.pid fi if [ "x$LOG_FILE" = "x" ]; then LOG_FILE=$HOME/$prog.log fi fi CMD="$CMD -c 'import gangliarc; gangliarc.run(\"$ARC_CONFIG\", \"$PID_FILE\", \"$LOG_FILE\")'" start() { if [ "$RUN" != "yes" ] ; then echo "gangliarc disabled, please adjust the configuration to your needs " echo "and then set RUN to 'yes' in /etc/default/gangliarc to enable it." return 0 fi echo -n "Starting $prog: " # Check if we are already running if [ -f $PID_FILE ]; then read pid < $PID_FILE if [ "x$pid" != "x" ]; then ps -p "$pid" -o comm 2>/dev/null | grep "^python$" 1>/dev/null 2>/dev/null if [ $? -eq 0 ] ; then log_success_msg "already running (pid $pid)" return 0 fi fi rm -f "$PID_FILE" "$LOCKFILE" fi eval "$CMD" RETVAL=$? if [ $RETVAL -eq 0 ]; then touch $LOCKFILE log_success_msg else log_failure_msg fi return $RETVAL } stop() { echo -n "Stopping $prog: " if [ -f "$PID_FILE" ]; then read pid < "$PID_FILE" if [ ! -z "$pid" ] ; then kill "$pid" RETVAL=$? if [ $RETVAL -eq 0 ]; then log_success_msg else log_failure_msg fi sleep 1 kill -9 "$pid" 1>/dev/null 2>&1 rm -f "$PID_FILE" "$LOCKFILE" else RETVAL=1 log_failure_msg "$prog shutdown - pidfile is empty" fi else RETVAL=0 log_success_msg "$prog shutdown - already stopped" fi return $RETVAL } status() { if [ -f "$PID_FILE" ]; then read pid < "$PID_FILE" if [ "$pid" != "" ]; then if ps -p "$pid" > /dev/null; then echo "$1 (pid $pid) is running..." return 0 fi echo "$1 stopped but pid file exists" return 1 fi fi if [ -f $LOCKFILE ]; then echo "$1 stopped but lockfile exists" return 2 fi echo "$1 is stopped" return 3 } restart() { stop start } case "$1" in start) start ;; stop) stop ;; status) status $prog ;; restart | force-reload) restart ;; reload) ;; condrestart | try-restart) [ -f $LOCKFILE ] && restart || : ;; *) echo "Usage: $0 {start|stop|status|restart|force-reload|reload|condrestart|try-restart}" exit 1 ;; esac exit $? nordugrid-arc-gangliarc-1.0.0/LICENSE0000664000175000017500000002367612246050712020623 0ustar waananenwaananen00000000000000 Apache License Version 2.0, January 2004 http://www.apache.org/licenses/ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 1. Definitions. "License" shall mean the terms and conditions for use, reproduction, and distribution as defined by Sections 1 through 9 of this document. "Licensor" shall mean the copyright owner or entity authorized by the copyright owner that is granting the License. "Legal Entity" shall mean the union of the acting entity and all other entities that control, are controlled by, or are under common control with that entity. For the purposes of this definition, "control" means (i) the power, direct or indirect, to cause the direction or management of such entity, whether by contract or otherwise, or (ii) ownership of fifty percent (50%) or more of the outstanding shares, or (iii) beneficial ownership of such entity. "You" (or "Your") shall mean an individual or Legal Entity exercising permissions granted by this License. "Source" form shall mean the preferred form for making modifications, including but not limited to software source code, documentation source, and configuration files. "Object" form shall mean any form resulting from mechanical transformation or translation of a Source form, including but not limited to compiled object code, generated documentation, and conversions to other media types. "Work" shall mean the work of authorship, whether in Source or Object form, made available under the License, as indicated by a copyright notice that is included in or attached to the work (an example is provided in the Appendix below). "Derivative Works" shall mean any work, whether in Source or Object form, that is based on (or derived from) the Work and for which the editorial revisions, annotations, elaborations, or other modifications represent, as a whole, an original work of authorship. For the purposes of this License, Derivative Works shall not include works that remain separable from, or merely link (or bind by name) to the interfaces of, the Work and Derivative Works thereof. "Contribution" shall mean any work of authorship, including the original version of the Work and any modifications or additions to that Work or Derivative Works thereof, that is intentionally submitted to Licensor for inclusion in the Work by the copyright owner or by an individual or Legal Entity authorized to submit on behalf of the copyright owner. For the purposes of this definition, "submitted" means any form of electronic, verbal, or written communication sent to the Licensor or its representatives, including but not limited to communication on electronic mailing lists, source code control systems, and issue tracking systems that are managed by, or on behalf of, the Licensor for the purpose of discussing and improving the Work, but excluding communication that is conspicuously marked or otherwise designated in writing by the copyright owner as "Not a Contribution." "Contributor" shall mean Licensor and any individual or Legal Entity on behalf of whom a Contribution has been received by Licensor and subsequently incorporated within the Work. 2. Grant of Copyright License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable copyright license to reproduce, prepare Derivative Works of, publicly display, publicly perform, sublicense, and distribute the Work and such Derivative Works in Source or Object form. 3. Grant of Patent License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable (except as stated in this section) patent license to make, have made, use, offer to sell, sell, import, and otherwise transfer the Work, where such license applies only to those patent claims licensable by such Contributor that are necessarily infringed by their Contribution(s) alone or by combination of their Contribution(s) with the Work to which such Contribution(s) was submitted. If You institute patent litigation against any entity (including a cross-claim or counterclaim in a lawsuit) alleging that the Work or a Contribution incorporated within the Work constitutes direct or contributory patent infringement, then any patent licenses granted to You under this License for that Work shall terminate as of the date such litigation is filed. 4. Redistribution. You may reproduce and distribute copies of the Work or Derivative Works thereof in any medium, with or without modifications, and in Source or Object form, provided that You meet the following conditions: (a) You must give any other recipients of the Work or Derivative Works a copy of this License; and (b) You must cause any modified files to carry prominent notices stating that You changed the files; and (c) You must retain, in the Source form of any Derivative Works that You distribute, all copyright, patent, trademark, and attribution notices from the Source form of the Work, excluding those notices that do not pertain to any part of the Derivative Works; and (d) If the Work includes a "NOTICE" text file as part of its distribution, then any Derivative Works that You distribute must include a readable copy of the attribution notices contained within such NOTICE file, excluding those notices that do not pertain to any part of the Derivative Works, in at least one of the following places: within a NOTICE text file distributed as part of the Derivative Works; within the Source form or documentation, if provided along with the Derivative Works; or, within a display generated by the Derivative Works, if and wherever such third-party notices normally appear. The contents of the NOTICE file are for informational purposes only and do not modify the License. You may add Your own attribution notices within Derivative Works that You distribute, alongside or as an addendum to the NOTICE text from the Work, provided that such additional attribution notices cannot be construed as modifying the License. You may add Your own copyright statement to Your modifications and may provide additional or different license terms and conditions for use, reproduction, or distribution of Your modifications, or for any such Derivative Works as a whole, provided Your use, reproduction, and distribution of the Work otherwise complies with the conditions stated in this License. 5. Submission of Contributions. Unless You explicitly state otherwise, any Contribution intentionally submitted for inclusion in the Work by You to the Licensor shall be under the terms and conditions of this License, without any additional terms or conditions. Notwithstanding the above, nothing herein shall supersede or modify the terms of any separate license agreement you may have executed with Licensor regarding such Contributions. 6. Trademarks. This License does not grant permission to use the trade names, trademarks, service marks, or product names of the Licensor, except as required for reasonable and customary use in describing the origin of the Work and reproducing the content of the NOTICE file. 7. Disclaimer of Warranty. Unless required by applicable law or agreed to in writing, Licensor provides the Work (and each Contributor provides its Contributions) on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied, including, without limitation, any warranties or conditions of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are solely responsible for determining the appropriateness of using or redistributing the Work and assume any risks associated with Your exercise of permissions under this License. 8. Limitation of Liability. In no event and under no legal theory, whether in tort (including negligence), contract, or otherwise, unless required by applicable law (such as deliberate and grossly negligent acts) or agreed to in writing, shall any Contributor be liable to You for damages, including any direct, indirect, special, incidental, or consequential damages of any character arising as a result of this License or out of the use or inability to use the Work (including but not limited to damages for loss of goodwill, work stoppage, computer failure or malfunction, or any and all other commercial damages or losses), even if such Contributor has been advised of the possibility of such damages. 9. Accepting Warranty or Additional Liability. While redistributing the Work or Derivative Works thereof, You may choose to offer, and charge a fee for, acceptance of support, warranty, indemnity, or other liability obligations and/or rights consistent with this License. However, in accepting such obligations, You may act only on Your own behalf and on Your sole responsibility, not on behalf of any other Contributor, and only if You agree to indemnify, defend, and hold each Contributor harmless for any liability incurred by, or claims asserted against, such Contributor by reason of your accepting any such warranty or additional liability. END OF TERMS AND CONDITIONS nordugrid-arc-gangliarc-1.0.0/gangliarc.py0000664000175000017500000005410512245637114022114 0ustar waananenwaananen00000000000000# Copyright 2012 David Cameron, Dmytro Karpenko # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. # gangliarc collects ARC-related information and provides info to ganglia # through gmetric. """gangliarc collects ARC-related information and provides info to ganglia through gmetric.""" import os import re import sys import time import signal import subprocess import logging import traceback # Default gangliarc parameters # - path to arc configuration file # - frequency (in s) at which to gather info # - expiration period of monitored metrics (in s) # - path to gmetric executable # - path to gm-jobs executable (should eventually be filled by autotools) # - metrics to report gangliarc_conf = {'conffile' : '/etc/arc.conf', 'frequency' : '20', 'dmax' : '180', 'gmetric_exec' : '/usr/bin/gmetric', 'metrics' : 'all'} # job states arex_job_states = [ "ACCEPTED", "PREPARING", "SUBMIT", "INLRMS", "FINISHING", "FINISHED", "DELETED", "CANCELLING" ] # data staging states data_staging_states = [ "NEW", "CHECK_CACHE", "RESOLVE", "QUERY_REPLICA", "PRE_CLEAN", "STAGE_PREPARE", "TRANSFER_WAIT", "TRANSFER", "RELEASE_REQUEST", "REGISTER_REPLICA", "PROCESS_CACHE", "CHECKING_CACHE", "CACHE_WAIT", "CACHE_CHECKED", "RESOLVING", "RESOLVED", "QUERYING_REPLICA", "REPLICA_QUERIED", "PRE_CLEANING", "PRE_CLEANED", "STAGING_PREPARING", "STAGING_PREPARING_WAIT", "STAGED_PREPARED", "TRANSFERRING", "TRANSFERRING_CANCEL", "TRANSFERRED", "RELEASING_REQUEST", "REQUEST_RELEASED", "REGISTERING_REPLICA", "REPLICA_REGISTERED", "PROCESSING_CACHE", "CACHE_PROCESSED" ] # where to get data staging info data_staging_info = "dtrstate.log" # dictionary of configuration information, filled by parseConf() conf = {} def daemonize(pidfile): ''' Do double fork to create daemon process ''' try: pid = os.fork() if pid > 0: # exit first parent sys.exit(0) except OSError: e = sys.exc_info()[1] sys.stderr.write("fork #1 failed: %d (%s)\n" % (e.errno, e.strerror)) sys.exit(1) # decouple from parent environment os.chdir("/") os.setsid() os.umask(0) # do second fork try: pid = os.fork() if pid > 0: # exit from second parent sys.exit(0) except OSError: e = sys.exc_info()[1] sys.stderr.write("fork #2 failed: %d (%s)\n" % (e.errno, e.strerror)) sys.exit(1) # redirect standard file descriptors sys.stdout.flush() sys.stderr.flush() si = open('/dev/null', 'r') so = open('/dev/null', 'a+') se = open('/dev/null', 'a+') os.dup2(si.fileno(), sys.stdin.fileno()) os.dup2(so.fileno(), sys.stdout.fileno()) os.dup2(se.fileno(), sys.stderr.fileno()) # write pidfile pid = str(os.getpid()) f = open(pidfile,'w+') f.write("%s\n" % pid) f.close() def parseConf(conffile): ''' Parse arc.conf and fill the conf dictionary of parameters in the format {section : {parameter : [value(s)]}} eg {"gangliarc" : {"logfile" : ["/tmp/gangliarc.log"], "pidfile" : ["/tmp/gangliarc.pid"]}} Value is a list since some parameters can be used multiple times ''' try: f = open(conffile) except IOError: e = sys.exc_info()[1] logging.error("Cannot open file %s: %s", conffile, str(e)) return current_section = '' for line in f: line = line.strip() # strip new line and leading/trailing spaces if len(line) == 0 or line[0] == '#': continue if line[0] == '[': # new section if line[-1] != ']': logging.error("Bad format of section name in line "+line) continue current_section = line[1:-1] conf[current_section] = {} else: if len(current_section) == 0: logging.error("Found configuration parameter %s outside a defined section", line) continue # here we have param="value" (sometimes without quotes) equals_pos = line.find('=') if equals_pos == -1 or equals_pos == len(line)-1: logging.error("Bad format for parameter %s", line) continue param = line[:equals_pos] value = line[equals_pos+1:] # remove surrounding quotes if value[0] == '"': if value[-1] != '"': logging.error("Bad format for parameter %s", line) continue value = value[1:-1] elif value[0] == "'": if value[-1] != "'": logging.error("Bad format for parameter %s", line) continue value = value[1:-1] # check if already stored if param in conf[current_section]: conf[current_section][param].append(value) else: conf[current_section][param] = [value] f.close() def parseURL(url): """ Split url into (protocol, host, port, path) and return this tuple. """ match = re.match(r'(\w*)://([^/?#:]*):?(\d*)/?(.*)', url) if match is None: return (None, None, None, None) port_s = match.group(3) if (len(port_s) > 0): port = int(port_s) else: port = None urltuple = (match.group(1), match.group(2), port, '/'+match.group(4)) return urltuple def runGmetric(metric, value, unit, unit_type): ''' Run the gmetric executable for the given metric. ''' try: res = subprocess.call([gangliarc_conf['gmetric_exec'], "-n", metric, "-v", str(value), "-t", unit_type, "-u", unit, "-d", gangliarc_conf['dmax']]) except OSError: e = sys.exc_info()[1] logging.error("Error calling gmetric process: %s", str(e)) return if res != 0: logging.error("Error returned from gmetric") def getDataStagingInfo(): ''' Pull out number of files in each data staging state from the info dumped by A-REX ''' # most important states to monitor data_staging_important_states = [ "TRANSFER_WAIT", "CACHE_WAIT", "STAGE_PREPARE", "STAGING_PREPARING_WAIT", ] # get possible staging hosts for TRANSFERRING state if 'data-staging' in conf: if 'deliveryservice' in conf['data-staging']: for url in conf['data-staging']['deliveryservice']: (protocol, host, port, path) = parseURL(url) if host is not None: data_staging_important_states.append('TRANSFERRING_' + host) # there is always a chance local transfer is used so always display it data_staging_important_states.append('TRANSFERRING_local') # get DTR log location if 'data-staging' in conf and 'dtrlog' in conf['data-staging']: dtrlog = conf['data-staging']['dtrlog'][0] elif 'controldir' in conf['grid-manager']: control = conf['grid-manager']['controldir'][0] dtrlog = control+'/'+data_staging_info else: logging.error("No control dir or DTR log found in configuration") return try: f = open(dtrlog) except IOError: e = sys.exc_info()[1] logging.error("Cannot open file %s: %s", dtrlog, str(e)) return states = {} num_lines = 0 for line in f: l = line.split() state = l[1] # if TRANSFERRING, get the host doing the transfer if state == 'TRANSFERRING': if len(l) == 6: state = state + '_' + l[5] else: state = state + '_local' if state in states: states[state] = states[state] + 1 else: states[state] = 1 num_lines = num_lines + 1 f.close() for state in data_staging_important_states: if state == 'STAGE_PREPARE' and 'PRE_CLEANED' in states: # In arc > 2.0.0 files waiting to be staged are in STAGE_PREPARE # instead of PRE_CLEANED value = states['PRE_CLEANED'] if state in states: value += states[state] elif state == 'TRANSFER_WAIT' and 'TRANSFER' in states: # In arc > 1.1.0 TRANSFER_WAIT was merged into TRANSFER but calling # the metric TRANSFER_WAIT is more intuitive value = states['TRANSFER'] elif state in states: value = states[state] else: value = 0 state = 'ARC_STAGING_' + state logging.info("%s %s", state, value) runGmetric(state, value, 'files', 'int32') runGmetric('ARC_STAGING_TOTAL', num_lines, 'files', 'int32') def getJobsStatesInfo(): ''' Pull out number of jobs in each A-REX internal state by scanning job.id.status files in control subdirectories. ''' if 'controldir' in conf['grid-manager']: control = conf['grid-manager']['controldir'][0] else: logging.error("No control dir found in configuration") return control_subdirs = ['accepting', 'finished', 'processing', 'restarting'] states = {} for control_subdir in control_subdirs: subdir = os.path.join(control, control_subdir) # subdirs only exist in versions >= 1.0.0 if not os.path.isdir(subdir): logging.warning('Control sub-directory %s not found. ' \ 'Job state information is only supported in ARC >= 1.0.0', subdir) return # scan files in the sub dir try: for status_file in os.listdir(subdir): try: f = open(os.path.join(subdir, status_file)) except IOError: e = sys.exc_info()[1] logging.warning('Could not open status file %s: %s', status_file, str(e)) continue status = f.readline().strip() if status in states: states[status] += 1 else: states[status] = 1 f.close() except OSError: e = sys.exc_info()[1] logging.warning('Could not list status files in %s: %s', subdir, str(e)) # first get total jobs including pending totaljobs = 0 for state in states: totaljobs += states[state] logging.info('ARC_JOBS_TOTAL %i', totaljobs) runGmetric('ARC_JOBS_TOTAL', totaljobs, 'jobs', 'int32') # now number for each specific state we are interested in for state in arex_job_states: if state in states: value = states[state] else: value = 0 state = 'ARC_JOBS_' + state logging.info("%s %s", state, value) runGmetric(state, value, 'jobs', 'int32') def getHeartBeatInfo(): ''' use the modification timestamp of the gm-heartbeat file to send to gmetric the time since the last heartbeat ''' if 'controldir' in conf['grid-manager']: control = conf['grid-manager']['controldir'][0] else: logging.error("No control dir found in configuration") return heartbeat = control + "/gm-heartbeat" try: statinfo = os.stat(heartbeat) except OSError: e = sys.exc_info()[1] logging.error("Error with heartbeat file: %s", str(e)) return mtime = statinfo.st_mtime now = time.time() heartbeat_time = now - mtime logging.info("heartbeat time %s", heartbeat_time) runGmetric('ARC_AREX_HEARTBEAT_LAST_SEEN', heartbeat_time, 'sec', 'int32') def getCacheFree(): ''' go through each cache dir and find the free space on the filesystem ''' if 'cachedir' not in conf['grid-manager']: logging.warn('No caches defined in configuration') return caches = conf['grid-manager']['cachedir'] totalfree = 0 for cache in caches: if cache.find(' ') != -1: cache = cache[:cache.find(' ')] # If substitutions are present, truncate the path if cache.find('%') != -1: cache = cache[:cache.find('%')] logging.info('cache dir with substitution truncated to %s', cache) # Note: Not portable! try: s = os.statvfs(cache) except OSError: e = sys.exc_info()[1] logging.error("Error finding space in cache %s: %s", cache, str(e)) continue free = float(s.f_bsize) * float(s.f_bavail) / float(1024) / float(1024) / float(1024) # space in GiB totalfree += free logging.info('cache %s free space %s GB', cache, free) # ganglia doesn't allow slashes in metric names cache = cache.replace('/', '_') runGmetric('ARC_CACHE_FREE'+cache, free, 'GB', 'float') if len(caches) > 1: runGmetric('ARC_CACHE_FREE_TOTAL', totalfree, 'GB', 'float') def getSessionFree(): ''' go through each session dir and find the free space on the filesystem ''' if 'sessiondir' not in conf['grid-manager']: logging.warn('No sessiondir defined in configuration') return sessiondirs = conf['grid-manager']['sessiondir'] totalfree = 0 for session in sessiondirs: if session.find(' ') != -1: session = session[:session.find(' ')] # If substitutions are present, truncate the path if session.find('%') != -1: session = session[:session.find('%')] logging.info('session dir with substitution truncated to %s', session) # Special case of session dirs in users' home directories # Guessing that /home is ok if session == '*': session = '/home' logging.info('using /home for session dir info') # Note: Not portable! try: s = os.statvfs(session) except OSError: e = sys.exc_info()[1] logging.error("Error finding space in session dir %s: %s", session, str(e)) continue free = float(s.f_bsize) * float(s.f_bavail) / float(1024) / float(1024) / float(1024) # space in GiB totalfree += free logging.info('session dir %s free space %s GB', session, free) # ganglia doesn't allow slashes in metric names session = session.replace('/', '_') runGmetric('ARC_SESSION_FREE'+session, free, 'GB', 'float') if len(sessiondirs) > 1: runGmetric('ARC_SESSION_FREE_TOTAL', totalfree, 'GB', 'float') def getProcessingJobs(): ''' Count the number of jobs in the 'processing' subdir of the control dir. This will only work on ARC1 clusters. ''' if 'controldir' in conf['grid-manager']: controldir = conf['grid-manager']['controldir'][0] else: logging.error("No control dir found in configuration") return processing = 0 processing_dir = controldir + "/processing" try: entries = os.listdir(processing_dir) except OSError: e = sys.exc_info()[1] logging.error("Error listing dir %s: %s", processing_dir, str(e)) return processing += len(entries) logging.info("%i jobs in processing", processing) runGmetric('ARC_JOBS_PROCESSING', processing, 'jobs', 'int32') def getFailedJobs(): ''' Look into the grid manager jobs log file to extract the quantity of failed jobs among last 100 finished and send to gmetric ''' if 'joblog' not in conf['grid-manager']: logging.warn('No grid manager jobs log defined in configuration') return gmjlog = conf['grid-manager']['joblog'][0] try: # Linux specific commands, but ganglia is only for *nix systems # Get last 400 lines from the log file, select only concerning finished jobs # and select failed in the finished p1 = subprocess.Popen(['tail', '-400', gmjlog], stdout = subprocess.PIPE) p2 = subprocess.Popen(['grep', '-i','finish'], stdin = p1.stdout, stdout = subprocess.PIPE) p1.stdout.close() p3 = subprocess.Popen(['tail', '-100'], stdin = p2.stdout, stdout = subprocess.PIPE) p2.stdout.close() p4 = subprocess.Popen(['grep', '-i', 'fail'], stdin = p3.stdout, stdout = subprocess.PIPE) p3.stdout.close() p5 = subprocess.Popen(['wc', '-l'], stdin = p4.stdout, stdout = subprocess.PIPE) p4.stdout.close() num_of_jobs = p5.stdout.readline() num_of_jobs = num_of_jobs.strip() logging.info('%s jobs failed among last 100', num_of_jobs) p5.stdout.close() except OSError: e = sys.exc_info()[1] logging.error("Error with running OS commands: %s", str(e)) return runGmetric('ARC_JOBS_FAILED_PER_100', num_of_jobs, 'jobs', 'int32') def getTransferInfo(): ''' Get the number of downloader and uploader processes. Function is used if the new data staging is disabled ''' try: # Linux specific commands, but ganglia is only for *nix systems ulp1 = subprocess.Popen(['ps', 'auxw'], stdout = subprocess.PIPE) ulp2 = subprocess.Popen(['grep', 'uploader'], stdin = ulp1.stdout, stdout = subprocess.PIPE) ulp1.stdout.close() ulp3 = subprocess.Popen(['grep', '-v', 'grep'], stdin = ulp2.stdout, stdout = subprocess.PIPE) ulp2.stdout.close() ulp4 = subprocess.Popen(['wc', '-l'], stdin = ulp3.stdout, stdout = subprocess.PIPE) ulp3.stdout.close() ul = ulp4.stdout.readline() ul = ul.strip() ulp4.stdout.close() dlp1 = subprocess.Popen(['ps', 'auxw'], stdout = subprocess.PIPE) dlp2 = subprocess.Popen(['grep', 'downloader'], stdin = dlp1.stdout, stdout = subprocess.PIPE) dlp1.stdout.close() dlp3 = subprocess.Popen(['grep', '-v','grep'], stdin = dlp2.stdout, stdout = subprocess.PIPE) dlp2.stdout.close() dlp4 = subprocess.Popen(['wc', '-l'], stdin = dlp3.stdout, stdout = subprocess.PIPE) dlp3.stdout.close() dl = dlp4.stdout.readline() dl = dl.strip() dlp4.stdout.close() logging.info('%s downloaders and %s uploaders running', dl, ul) except OSError: e = sys.exc_info()[1] logging.error("Error with running OS commands: %s", str(e)) return runGmetric('ARC_UPLOADING', ul, 'jobs', 'int32') runGmetric('ARC_DOWNLOADING', dl, 'jobs', 'int32') def handler(signum, frame): ''' shut down nicely ''' logging.info('*** gangliarc stopped ***') sys.exit(0) def run(conffile, pidfile, logfile): ''' Main program. It creates a daemon which loops indefinitely. In each loop several metrics are gathered and sent to gmetric. run() takes three arguments, the path to the ARC configuration file and the paths to the pid and log files for this process. ''' # path to arc.conf gangliarc_conf['conffile'] = conffile # set up logging logging.basicConfig(filename=logfile, level=logging.INFO, format='%(asctime)s [%(levelname)s] %(message)s') # create daemon daemonize(pidfile) # add signal handler signal.signal(signal.SIGTERM, handler) logging.info('*** gangliarc started ***') # main loop - loop forever until interrupted while (True): try: # read arc conf file # TODO parse once, but enable reloading via /etc/init.d/gangliarc reload parseConf(conffile) # sanity check if 'grid-manager' not in conf: logging.critical("No [grid-manager] section found in configuration, exiting") break # check if some gangliarc defaults were overridden in configuration if 'gangliarc' in conf: for key in gangliarc_conf: if key in conf['gangliarc']: gangliarc_conf[key] = conf['gangliarc'][key][0] # metrics to measure metrics = gangliarc_conf['metrics'].split(',') if 'staging' in metrics or 'all' in metrics: # data staging info if 'newdatastaging' in conf['grid-manager'] and conf['grid-manager']['newdatastaging'][0] == 'no' \ or 'enable_dtr' in conf['grid-manager'] and conf['grid-manager']['enable_dtr'][0] == 'no' : # monitor old downloader/uploader getTransferInfo() else: # monitor DTR getDataStagingInfo() if 'jobstates' in metrics or 'all' in metrics: # jobs in different states getJobsStatesInfo() if 'heartbeat' in metrics or 'all' in metrics: # gm-heartbeat info getHeartBeatInfo() if 'cache' in metrics or 'all' in metrics: # cache free space getCacheFree() if 'session' in metrics or 'all' in metrics: # session dir free space getSessionFree() if 'processingjobs' in metrics or 'all' in metrics: # processing jobs getProcessingJobs() if 'failedjobs' in metrics or 'all' in metrics: # number of failed jobs among last 100 getFailedJobs() time.sleep(float(gangliarc_conf['frequency'])) except SystemExit: # raised by signal handler break except: logging.critical("Unexpected exception, exiting gangliarc") logging.critical(traceback.format_exc()) logging.info('*** gangliarc stopped ***') break if __name__ == '__main__': run('/etc/arc.conf', '/tmp/gangliarc.pid', '/tmp/gangliarc.log') nordugrid-arc-gangliarc-1.0.0/Makefile0000664000175000017500000000062512246206424021246 0ustar waananenwaananen00000000000000PACKAGE_NAME = nordugrid-arc-gangliarc VERSION = $(shell cat VERSION) TARBALL = dist/$(PACKAGE_NAME)-$(VERSION).tar.gz default: @echo "No default target - try make dist" dist: $(TARBALL) $(TARBALL): setup.py python $< sdist config: setup.py python $< $@ clean: rm -f $(TARBALL) MANIFEST $(PACKAGE_NAME).spec test -d dist && rmdir dist || : rm -fr $(CURDIR)/build rm -fr $(CURDIR)/__pycache__ nordugrid-arc-gangliarc-1.0.0/MANIFEST.in0000664000175000017500000000034112246206740021340 0ustar waananenwaananen00000000000000include gangliarc include MANIFEST.in include LICENSE include NOTICE include VERSION include nordugrid-arc-gangliarc.spec.in include nordugrid-arc-gangliarc.spec include Makefile include debian/* include debian/source/format nordugrid-arc-gangliarc-1.0.0/README0000664000175000017500000000674512245641546020506 0ustar waananenwaananen00000000000000gangliarc provides a way to monitor an ARC Computing Element through an existing ganglia installation. Running gangliarc adds various ARC-related metrics to ganglia using gmetric which can then be viewed on the ganglia web page for the ARC CE host. The available metrics are configurable and explained below. gangliarc takes information (eg control directory, cache directories) from the standard ARC configuration file arc.conf. If it is not in the default location (/etc/arc.conf) then ARC_CONFIG must be set. Requirements: python >= 2.4.x ganglia >= 3.0.x ARC >= 0.8.x (Some metrics are only available with ARC >= 1.0) To install from sources: python setup.py install (as superuser) To start/stop/restart: /etc/init.d/gangliarc start/stop/restart (as superuser) Log messages are logged to /var/log/arc/gangliarc.log by default but this can be configured. To configure: In many cases no gangliarc configuration is necessary, however the following parameters may be specified in a [gangliarc] section in arc.conf. - frequency -- period of gathering the info, in seconds. Default is 20. - dmax -- expiration period of information, passed to gmetric, in seconds. 0 means infinity. Default is 180. - gmetric_exec -- path to gmetric executable. Default is /usr/bin/gmetric - logfile -- log file of the daemon. Default is /var/log/arc/gangliarc.log - pidfile -- pid file of the daemon. Default is /var/run/gangliarc.pid - python_bin_path -- path to python executable. Default is /usr/bin/python - metrics -- the metrics to be monitored. Default is all. metrics takes a comma-separated list of one or more of the following metrics: - staging -- number of tasks in different data staging states (if new data staging is enabled, see below) or number of downloader and uploader processes (if new data staging is disabled) - cache -- free cache space - session -- free session directory space - heartbeat -- last modification time of A-REX heartbeat - processingjobs -- the number of jobs currently being processed by ARC (jobs between PREPARING and FINISHING states) - failedjobs -- the number of failed jobs per last 100 finished - jobstates -- number of jobs in different A-REX internal stages - all -- all of the above metrics Explanation of new data staging states: Data staging states metrics all start with ARC_STAGING CACHE_WAIT -- Files waiting to obtain a lock in the cache, currently held by another request downloading the same file STAGE_PREPARE -- There is a limit (max_prepared in arc.conf) on files prepared (pinned) on SRM storage. Files in this state are waiting for a free slot to prepare their source or destination. STAGING_PREPARING_WAIT -- Files which have made a staging request to SRM and are waiting for a TURL to be returned TOTAL -- All files in the data staging system (corresponding to jobs in PREPARING and FINISHING) TRANSFERRING_hostname -- Files actively transferring data, with the transfer running on hostname TRANSFER_WAIT -- Files ready for transfer and waiting on a TRANSFERRING slot Example configuration: [gangliarc] python_bin_path="/usr/bin/python2.6" metrics="cache,heartbeat,failedjobs,processingjobs,staging" Authors: David Cameron (d.g.cameron@fys.uio.no) Dmytro Karpenko (dmytro.karpenko@fys.uio.no) More information: http://wiki.nordugrid.org/index.php/Gangliarc nordugrid-arc-gangliarc-1.0.0/nordugrid-arc-gangliarc.spec.in0000664000175000017500000000463512246501205025554 0ustar waananenwaananen00000000000000%if 0%{?rhel} && 0%{?rhel} <= 5 || 0%{?fedora} <= 12 %{!?python_sitearch: %global python_sitearch %(%{__python} -c "from distutils.sysconfig import get_python_lib; print get_python_lib(1)")} %{!?python_sitelib: %global python_sitelib %(%{__python} -c "from distutils.sysconfig import get_python_lib; print get_python_lib(0)")} %endif Name: nordugrid-arc-gangliarc Version: @VERSION@ Release: 1%{?dist} Summary: Ganglia monitoring for ARC services Group: Development/Libraries License: ASL 2.0 URL: http://wiki.nordugrid.org/index.php/Gangliarc Source0: https://dcameron.web.cern.ch/dcameron/dev/rpmbuild/SOURCES/%{name}-%{version}.tar.gz BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n) BuildArch: noarch BuildRequires: python-devel %if 0%{?fedora} >= 8 BuildRequires: python-setuptools-devel %else BuildRequires: python-setuptools %endif Requires: nordugrid-arc-arex Requires: ganglia-gmond >= 3.0 Requires: python >= 2.4 %description gangliarc provides a way to monitor ARC services through an existing ganglia installation. Running gangliarc adds various ARC metrics to ganglia which can then be viewed along with regular ganglia metrics for the ARC host. %prep %setup -q -n %{name}-%{version} %build %{__python} -c 'import setuptools; execfile("setup.py")' build %install rm -rf %{buildroot} # /etc/init.d is hard-coded in setup.py so create a symlink to /etc/rc.d/init.d # before installing mkdir -p %{buildroot}/etc/rc.d/init.d && ln -s %{buildroot}/etc/rc.d/init.d %{buildroot}/etc/init.d %{__python} -c 'import setuptools; execfile("setup.py")' install -O1 --skip-build --root %{buildroot} # remove symlink rm -f %{buildroot}/etc/init.d %clean rm -rf %{buildroot} %post /sbin/chkconfig --add gangliarc %preun if [ $1 -eq 0 ]; then /sbin/service gangliarc stop > /dev/null 2>&1 /sbin/chkconfig --del gangliarc fi %postun if [ $1 -ge 1 ]; then /sbin/service gangliarc condrestart > /dev/null 2>&1 fi %files %defattr(-,root,root,-) %doc README LICENSE NOTICE %{python_sitelib}/gangliarc.* %{python_sitelib}/nordugrid_arc_gangliarc-%{version}-py?.?.egg-info %if 0%{?rhel} <= 5 || 0%{?fedora} <= 9 %{_initrddir}/gangliarc %else %{_initdir}/gangliarc %endif %changelog * Sun Dec 01 2013 Anders Waananen - 1.0.0-1 - 1.0.0 Final release * Wed Jul 18 2012 David Cameron 0.1.0-1 - Initial version nordugrid-arc-gangliarc-1.0.0/nordugrid-arc-gangliarc.spec0000664000175000017500000000463112246510654025153 0ustar waananenwaananen00000000000000%if 0%{?rhel} && 0%{?rhel} <= 5 || 0%{?fedora} <= 12 %{!?python_sitearch: %global python_sitearch %(%{__python} -c "from distutils.sysconfig import get_python_lib; print get_python_lib(1)")} %{!?python_sitelib: %global python_sitelib %(%{__python} -c "from distutils.sysconfig import get_python_lib; print get_python_lib(0)")} %endif Name: nordugrid-arc-gangliarc Version: 1.0.0 Release: 1%{?dist} Summary: Ganglia monitoring for ARC services Group: Development/Libraries License: ASL 2.0 URL: http://wiki.nordugrid.org/index.php/Gangliarc Source0: https://dcameron.web.cern.ch/dcameron/dev/rpmbuild/SOURCES/%{name}-%{version}.tar.gz BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n) BuildArch: noarch BuildRequires: python-devel %if 0%{?fedora} >= 8 BuildRequires: python-setuptools-devel %else BuildRequires: python-setuptools %endif Requires: nordugrid-arc-arex Requires: ganglia-gmond >= 3.0 Requires: python >= 2.4 %description gangliarc provides a way to monitor ARC services through an existing ganglia installation. Running gangliarc adds various ARC metrics to ganglia which can then be viewed along with regular ganglia metrics for the ARC host. %prep %setup -q -n %{name}-%{version} %build %{__python} -c 'import setuptools; execfile("setup.py")' build %install rm -rf %{buildroot} # /etc/init.d is hard-coded in setup.py so create a symlink to /etc/rc.d/init.d # before installing mkdir -p %{buildroot}/etc/rc.d/init.d && ln -s %{buildroot}/etc/rc.d/init.d %{buildroot}/etc/init.d %{__python} -c 'import setuptools; execfile("setup.py")' install -O1 --skip-build --root %{buildroot} # remove symlink rm -f %{buildroot}/etc/init.d %clean rm -rf %{buildroot} %post /sbin/chkconfig --add gangliarc %preun if [ $1 -eq 0 ]; then /sbin/service gangliarc stop > /dev/null 2>&1 /sbin/chkconfig --del gangliarc fi %postun if [ $1 -ge 1 ]; then /sbin/service gangliarc condrestart > /dev/null 2>&1 fi %files %defattr(-,root,root,-) %doc README LICENSE NOTICE %{python_sitelib}/gangliarc.* %{python_sitelib}/nordugrid_arc_gangliarc-%{version}-py?.?.egg-info %if 0%{?rhel} <= 5 || 0%{?fedora} <= 9 %{_initrddir}/gangliarc %else %{_initdir}/gangliarc %endif %changelog * Sun Dec 01 2013 Anders Waananen - 1.0.0-1 - 1.0.0 Final release * Wed Jul 18 2012 David Cameron 0.1.0-1 - Initial version nordugrid-arc-gangliarc-1.0.0/VERSION0000664000175000017500000000000612246501023020640 0ustar waananenwaananen000000000000001.0.0 nordugrid-arc-gangliarc-1.0.0/NOTICE0000664000175000017500000000203712246054775020523 0ustar waananenwaananen00000000000000Ganglia monitoring for the Advanced Resource Connector (ARC) - gangliarc This product includes gangliarc which provides a way to monitor an ARC Computing Element through an existing ganglia installation. The software was developed by: David Cameron Dmytro Karpenko during their employment at the University of Oslo, Norway. The Copyright is collectively owned by the above individuals and the University of Oslo, Norway. The software is licensed under the Apache License, Version 2.0 (the "License"); you may not use files from this software distribution except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. nordugrid-arc-gangliarc-1.0.0/PKG-INFO0000664000175000017500000000074612246510656020714 0ustar waananenwaananen00000000000000Metadata-Version: 1.0 Name: nordugrid-arc-gangliarc Version: 1.0.0 Summary: Ganglia monitoring for the ARC server Home-page: http://www.nordugrid.org/ Author: David Cameron Author-email: cameron@ndgf.org License: Apache 2.0 license Description: gangliarc provides a way to monitor ARC services through an existing ganglia installation. Running gangliarc adds various ARC metrics to ganglia which can then be viewed along with regular ganglia metrics for the ARC host. Platform: UNKNOWN nordugrid-arc-gangliarc-1.0.0/debian/0000775000175000017500000000000012246510656021032 5ustar waananenwaananen00000000000000nordugrid-arc-gangliarc-1.0.0/debian/nordugrid-arc-gangliarc.docs0000664000175000017500000000001612246054323026360 0ustar waananenwaananen00000000000000README NOTICE nordugrid-arc-gangliarc-1.0.0/debian/control0000664000175000017500000000154612245660631022441 0ustar waananenwaananen00000000000000Source: nordugrid-arc-gangliarc Section: net Priority: optional Maintainer: Mattias Ellert Uploaders: Anders Waananen Build-Depends: debhelper (>= 5), python, python-setuptools, python-support X-Python-Version: >= 2.4 Standards-Version: 3.9.2 Vcs-Browser: http://svn.nordugrid.org/trac/nordugrid/browser/contrib/gangliarc Vcs-Svn: http://svn.nordugrid.org/repos/nordugrid/contrib/gangliarc Homepage: http://www.nordugrid.org Package: nordugrid-arc-gangliarc Architecture: all Depends: ${misc:Depends}, python, nordugrid-arc-arex, ganglia-monitor Description: Ganglia monitoring for ARC services gangliarc provides a way to monitor ARC services through an existing ganglia installation. Running gangliarc adds various ARC metrics to ganglia which can then be viewed along with regular ganglia metrics for the ARC host. nordugrid-arc-gangliarc-1.0.0/debian/copyright0000664000175000017500000000221712246051010022747 0ustar waananenwaananen00000000000000This package was debianized by Anders Wäänänen on Thu, 28 Nov 2013 17:00:00 +0100. Upstream Authors: David Cameron Dmytro Karpenko Copyright: Copyright (C) 2012-2013 by the respective employers of the the above authors: University of Oslo, Norway License: Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. On Debian systems, the complete text of the Apache version 2.0 license can be found in `/usr/share/common-licenses/Apache-2.0'. The Debian packaging was prepared by Anders Wäänänen of the upstream developers and is also licensed under the Apache 2.0 license. nordugrid-arc-gangliarc-1.0.0/debian/nordugrid-arc-gangliarc.install0000664000175000017500000000006712245647550027115 0ustar waananenwaananen00000000000000debian/tmp/usr/lib/python*/site-packages/gangliarc.py* nordugrid-arc-gangliarc-1.0.0/debian/rules0000775000175000017500000000216412245652271022114 0ustar waananenwaananen00000000000000#!/usr/bin/make -f -include /usr/share/dpkg/buildflags.mk configure: configure-stamp : configure-stamp: dh_testdir touch $@ build: build-arch build-indep : build-arch: build-stamp : build-indep: build-stamp python setup.py build build-stamp: configure-stamp : touch $@ clean: dh_testdir dh_testroot dh_clean configure-stamp build-stamp install: build-stamp dh_testdir dh_testroot dh_clean -k python setup.py install --prefix=/usr --root=debian/tmp --skip-build find debian/tmp -name \*.egg-info -exec rm -f '{}' \; mv debian/tmp/etc/init.d/gangliarc debian/nordugrid-arc-gangliarc.gangliarc.init binary-indep: dh_testdir dh_testroot dh_installdirs dh_installdocs dh_install --fail-missing dh_installchangelogs dh_installinit nordugrid-arc-gangliarc --name gangliarc [ -x /usr/bin/dh_python2 ] && dh_python2 || dh_pysupport [ -x /usr/bin/dh_lintian ] && dh_lintian || : dh_link dh_fixperms dh_installdeb dh_gencontrol dh_md5sums dh_builddeb binary-arch: install : binary: binary-arch binary-indep : .PHONY: build-arch build-indep build clean binary-arch binary-indep binary install configure nordugrid-arc-gangliarc-1.0.0/debian/source/0000775000175000017500000000000012246510656022332 5ustar waananenwaananen00000000000000nordugrid-arc-gangliarc-1.0.0/debian/source/format0000664000175000017500000000001412245645512023537 0ustar waananenwaananen000000000000003.0 (quilt) nordugrid-arc-gangliarc-1.0.0/debian/compat0000664000175000017500000000000212245645530022227 0ustar waananenwaananen000000000000005 nordugrid-arc-gangliarc-1.0.0/debian/changelog0000664000175000017500000000046512246502457022711 0ustar waananenwaananen00000000000000nordugrid-arc-gangliarc (1.0.0-1) unstable; urgency=low * 1.0.0 Final release -- Anders Waananen Sun, 01 Dec 2013 00:39:11 +0000 nordugrid-arc-gangliarc (0.1.0-1) unstable; urgency=low * 0.1.0 Initial release -- Anders Waananen Thu, 28 Nov 2013 16:08:40 +0100 nordugrid-arc-gangliarc-1.0.0/debian/nordugrid-arc-gangliarc.default0000664000175000017500000000021612245653600027060 0ustar waananenwaananen00000000000000# To enable gangliarc, i.e. to indicate that a readily usable # configuration is in place, comment out or delete the # following line. RUN=no nordugrid-arc-gangliarc-1.0.0/setup.py0000664000175000017500000000254012246510033021310 0ustar waananenwaananen00000000000000import sys from distutils.core import setup try: from distutils.command.build_py import build_py_2to3 except ImportError: pass fd = open('VERSION','r') version = fd.read().strip() fd.close() from distutils.command.config import config class CustomConfigCommand(config): def run(self): fd = open('nordugrid-arc-gangliarc.spec.in', 'r') lines = fd.readlines() fd.close() fd = open('nordugrid-arc-gangliarc.spec', 'w') for line in lines: line = line.replace("@VERSION@", version) fd.write(line) fd.close() config.run(self) COMMANDS = {'config' : CustomConfigCommand } if sys.version_info[0] == 3: COMMANDS['build_py'] = build_py_2to3 setup(name='nordugrid-arc-gangliarc', version = version, description = 'Ganglia monitoring for the ARC server', author = 'David Cameron', author_email = 'cameron@ndgf.org', url = 'http://www.nordugrid.org/', license = 'Apache 2.0 license', long_description = "gangliarc provides a way to monitor ARC services through an existing ganglia installation. Running gangliarc adds various ARC metrics to ganglia which can then be viewed along with regular ganglia metrics for the ARC host.", cmdclass = COMMANDS, py_modules = ['gangliarc'], data_files = [('/etc/init.d/', ['gangliarc'])] )