osc-reservations 1.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
 - data/.gitignore +17 -0
 - data/Gemfile +4 -0
 - data/LICENSE.txt +22 -0
 - data/README.md +103 -0
 - data/Rakefile +7 -0
 - data/config/batch.yml +13 -0
 - data/config/websvcs08.osc.edu.yml +13 -0
 - data/lib/osc/reservations.rb +47 -0
 - data/lib/osc/reservations/adapter.rb +38 -0
 - data/lib/osc/reservations/adapters/osc_moab.rb +167 -0
 - data/lib/osc/reservations/batch.rb +39 -0
 - data/lib/osc/reservations/node.rb +42 -0
 - data/lib/osc/reservations/query.rb +60 -0
 - data/lib/osc/reservations/reservation.rb +53 -0
 - data/lib/osc/reservations/version.rb +6 -0
 - data/osc-reservations.gemspec +26 -0
 - data/test/adapters/test_osc_moab.rb +115 -0
 - data/test/files/batch.yml +4 -0
 - data/test/files/osc_oakley_job_4691489.oak-batch.osc.edu.yml +47 -0
 - data/test/files/osc_oakley_job_4691490.oak-batch.osc.edu.yml +47 -0
 - data/test/files/osc_oakley_job_4691491.oak-batch.osc.edu.yml +47 -0
 - data/test/files/osc_oakley_node_n0609.yml +14 -0
 - data/test/files/osc_oakley_node_n0611.yml +15 -0
 - data/test/files/osc_oakley_node_n0612.yml +13 -0
 - data/test/files/osc_oakley_node_n0613.yml +13 -0
 - data/test/files/osc_rsv.xml +18 -0
 - data/test/files/osc_rsvs.xml +97 -0
 - data/test/test_adapter.rb +14 -0
 - data/test/test_batch.rb +23 -0
 - data/test/test_node.rb +21 -0
 - data/test/test_query.rb +62 -0
 - data/test/test_reservation.rb +33 -0
 - data/test/test_reservations.rb +28 -0
 - metadata +150 -0
 
| 
         @@ -0,0 +1,39 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module OSC
         
     | 
| 
      
 2 
     | 
    
         
            +
              module Reservations
         
     | 
| 
      
 3 
     | 
    
         
            +
                # Batch server that utilizes reservations in the batch scheduler.
         
     | 
| 
      
 4 
     | 
    
         
            +
                class Batch
         
     | 
| 
      
 5 
     | 
    
         
            +
                  # @return [String] the batch server to connect to.
         
     | 
| 
      
 6 
     | 
    
         
            +
                  attr_reader :server
         
     | 
| 
      
 7 
     | 
    
         
            +
             
     | 
| 
      
 8 
     | 
    
         
            +
                  # @param server [String] The server to connect to.
         
     | 
| 
      
 9 
     | 
    
         
            +
                  # @param context [Hash] An optional hash of values that may be required by chosen adapter.
         
     | 
| 
      
 10 
     | 
    
         
            +
                  def initialize(server, context = {})
         
     | 
| 
      
 11 
     | 
    
         
            +
                    @server = server
         
     | 
| 
      
 12 
     | 
    
         
            +
             
     | 
| 
      
 13 
     | 
    
         
            +
                    # symbolize keys
         
     | 
| 
      
 14 
     | 
    
         
            +
                    @context = {}
         
     | 
| 
      
 15 
     | 
    
         
            +
                    context.each do |key, value|
         
     | 
| 
      
 16 
     | 
    
         
            +
                      @context[key.to_sym] = value
         
     | 
| 
      
 17 
     | 
    
         
            +
                    end
         
     | 
| 
      
 18 
     | 
    
         
            +
                  end
         
     | 
| 
      
 19 
     | 
    
         
            +
             
     | 
| 
      
 20 
     | 
    
         
            +
                  # See if the method call exists as a key in @context.
         
     | 
| 
      
 21 
     | 
    
         
            +
                  #
         
     | 
| 
      
 22 
     | 
    
         
            +
                  # @param method_name the method name called
         
     | 
| 
      
 23 
     | 
    
         
            +
                  # @param arguments the arguments to the call
         
     | 
| 
      
 24 
     | 
    
         
            +
                  # @param block an optional block for the call
         
     | 
| 
      
 25 
     | 
    
         
            +
                  def method_missing(method_name, *arguments, &block)
         
     | 
| 
      
 26 
     | 
    
         
            +
                    @context.fetch(method_name) { super }
         
     | 
| 
      
 27 
     | 
    
         
            +
                  end
         
     | 
| 
      
 28 
     | 
    
         
            +
             
     | 
| 
      
 29 
     | 
    
         
            +
                  # Checks if the method responds to an instance method, or is able to
         
     | 
| 
      
 30 
     | 
    
         
            +
                  # proxy it to @context.
         
     | 
| 
      
 31 
     | 
    
         
            +
                  #
         
     | 
| 
      
 32 
     | 
    
         
            +
                  # @param method_name the method name to check
         
     | 
| 
      
 33 
     | 
    
         
            +
                  # @return [Boolean]
         
     | 
| 
      
 34 
     | 
    
         
            +
                  def respond_to_missing?(method_name, include_private = false)
         
     | 
| 
      
 35 
     | 
    
         
            +
                    @context.include?(method_name) || super
         
     | 
| 
      
 36 
     | 
    
         
            +
                  end
         
     | 
| 
      
 37 
     | 
    
         
            +
                end
         
     | 
| 
      
 38 
     | 
    
         
            +
              end
         
     | 
| 
      
 39 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,42 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module OSC
         
     | 
| 
      
 2 
     | 
    
         
            +
              module Reservations
         
     | 
| 
      
 3 
     | 
    
         
            +
                # Provides a way for the developer to view the properties of any given
         
     | 
| 
      
 4 
     | 
    
         
            +
                # reserved node.
         
     | 
| 
      
 5 
     | 
    
         
            +
                class Node
         
     | 
| 
      
 6 
     | 
    
         
            +
                  # @return [String] The ID of this node.
         
     | 
| 
      
 7 
     | 
    
         
            +
                  attr_accessor :id
         
     | 
| 
      
 8 
     | 
    
         
            +
             
     | 
| 
      
 9 
     | 
    
         
            +
                  # @return [Fixnum] Number of cores on this node.
         
     | 
| 
      
 10 
     | 
    
         
            +
                  attr_accessor :np
         
     | 
| 
      
 11 
     | 
    
         
            +
             
     | 
| 
      
 12 
     | 
    
         
            +
                  # @return [Array<String>] A list of properties for this node.
         
     | 
| 
      
 13 
     | 
    
         
            +
                  attr_accessor :props
         
     | 
| 
      
 14 
     | 
    
         
            +
             
     | 
| 
      
 15 
     | 
    
         
            +
                  # @return [Array<String>] A list of job id's running on this node.
         
     | 
| 
      
 16 
     | 
    
         
            +
                  attr_accessor :jobs
         
     | 
| 
      
 17 
     | 
    
         
            +
             
     | 
| 
      
 18 
     | 
    
         
            +
                  # @return [Array<String>] A list of users running on this node.
         
     | 
| 
      
 19 
     | 
    
         
            +
                  attr_accessor :users
         
     | 
| 
      
 20 
     | 
    
         
            +
             
     | 
| 
      
 21 
     | 
    
         
            +
                  # @param opts [Hash] Options used to create a node.
         
     | 
| 
      
 22 
     | 
    
         
            +
                  # @option opts [String] :id The ID of this node.
         
     | 
| 
      
 23 
     | 
    
         
            +
                  # @option opts [Fixnum] :np The number of processors on this node.
         
     | 
| 
      
 24 
     | 
    
         
            +
                  # @option opts [Array<String>] :props An array of properties for this node.
         
     | 
| 
      
 25 
     | 
    
         
            +
                  # @option opts [Array<String>] :jobs An array of job IDs running on this node.
         
     | 
| 
      
 26 
     | 
    
         
            +
                  # @option opts [Array<String>] :users An array of users running on this node.
         
     | 
| 
      
 27 
     | 
    
         
            +
                  def initialize(opts)
         
     | 
| 
      
 28 
     | 
    
         
            +
                    @id    = opts[:id]
         
     | 
| 
      
 29 
     | 
    
         
            +
                    @np    = opts[:np]
         
     | 
| 
      
 30 
     | 
    
         
            +
                    @props = opts[:props]
         
     | 
| 
      
 31 
     | 
    
         
            +
                    @jobs  = opts[:jobs]
         
     | 
| 
      
 32 
     | 
    
         
            +
                    @users = opts[:users]
         
     | 
| 
      
 33 
     | 
    
         
            +
                  end
         
     | 
| 
      
 34 
     | 
    
         
            +
             
     | 
| 
      
 35 
     | 
    
         
            +
                  # Is this node free to use?
         
     | 
| 
      
 36 
     | 
    
         
            +
                  # @return [Boolean] is node free?
         
     | 
| 
      
 37 
     | 
    
         
            +
                  def free?
         
     | 
| 
      
 38 
     | 
    
         
            +
                    jobs.empty?
         
     | 
| 
      
 39 
     | 
    
         
            +
                  end
         
     | 
| 
      
 40 
     | 
    
         
            +
                end
         
     | 
| 
      
 41 
     | 
    
         
            +
              end
         
     | 
| 
      
 42 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,60 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            require 'yaml'
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            module OSC
         
     | 
| 
      
 4 
     | 
    
         
            +
              module Reservations
         
     | 
| 
      
 5 
     | 
    
         
            +
                # Factory for creating reservation objects that detail the current user's
         
     | 
| 
      
 6 
     | 
    
         
            +
                # reservations on the given batch server.
         
     | 
| 
      
 7 
     | 
    
         
            +
                class Query
         
     | 
| 
      
 8 
     | 
    
         
            +
                  # See if the method call exists as a key in batch config yaml file.
         
     | 
| 
      
 9 
     | 
    
         
            +
                  # Examples:
         
     | 
| 
      
 10 
     | 
    
         
            +
                  #   Query.glenn()
         
     | 
| 
      
 11 
     | 
    
         
            +
                  #   Query.oakley()
         
     | 
| 
      
 12 
     | 
    
         
            +
                  #
         
     | 
| 
      
 13 
     | 
    
         
            +
                  # @param method_name the method name called
         
     | 
| 
      
 14 
     | 
    
         
            +
                  # @param arguments the arguments to the call
         
     | 
| 
      
 15 
     | 
    
         
            +
                  # @param block an optional block for the call
         
     | 
| 
      
 16 
     | 
    
         
            +
                  def self.method_missing(method_name, *arguments, &block)
         
     | 
| 
      
 17 
     | 
    
         
            +
                    context = Reservations.batch_config[method_name.to_s]
         
     | 
| 
      
 18 
     | 
    
         
            +
                    if context
         
     | 
| 
      
 19 
     | 
    
         
            +
                      adapter_type  = context['adapter']['type']
         
     | 
| 
      
 20 
     | 
    
         
            +
                      batch_server  = context['batch'].delete('server')
         
     | 
| 
      
 21 
     | 
    
         
            +
                      batch_context = context['batch']
         
     | 
| 
      
 22 
     | 
    
         
            +
                      a = Object.const_get(adapter_type).new
         
     | 
| 
      
 23 
     | 
    
         
            +
                      b = Batch.new(batch_server, batch_context)
         
     | 
| 
      
 24 
     | 
    
         
            +
                      new(a, b)
         
     | 
| 
      
 25 
     | 
    
         
            +
                    else
         
     | 
| 
      
 26 
     | 
    
         
            +
                      super
         
     | 
| 
      
 27 
     | 
    
         
            +
                    end
         
     | 
| 
      
 28 
     | 
    
         
            +
                  end
         
     | 
| 
      
 29 
     | 
    
         
            +
             
     | 
| 
      
 30 
     | 
    
         
            +
                  # Checks if the method responds to an instance method, or is able to
         
     | 
| 
      
 31 
     | 
    
         
            +
                  # proxy it to the batch config yaml file.
         
     | 
| 
      
 32 
     | 
    
         
            +
                  #
         
     | 
| 
      
 33 
     | 
    
         
            +
                  # @param method_name the method name to check
         
     | 
| 
      
 34 
     | 
    
         
            +
                  # @return [Boolean]
         
     | 
| 
      
 35 
     | 
    
         
            +
                  def self.respond_to_missing?(method_name, include_private = false)
         
     | 
| 
      
 36 
     | 
    
         
            +
                    Reservations.batch_config.include?(method_name.to_s) || super
         
     | 
| 
      
 37 
     | 
    
         
            +
                  end
         
     | 
| 
      
 38 
     | 
    
         
            +
             
     | 
| 
      
 39 
     | 
    
         
            +
                  # @param adapter [Adapter] The adapter used to communicate with the scheduler.
         
     | 
| 
      
 40 
     | 
    
         
            +
                  # @param batch [Batch] The batch server to communicate with.
         
     | 
| 
      
 41 
     | 
    
         
            +
                  def initialize(adapter, batch)
         
     | 
| 
      
 42 
     | 
    
         
            +
                    @adapter = adapter
         
     | 
| 
      
 43 
     | 
    
         
            +
                    @batch = batch
         
     | 
| 
      
 44 
     | 
    
         
            +
                  end
         
     | 
| 
      
 45 
     | 
    
         
            +
             
     | 
| 
      
 46 
     | 
    
         
            +
                  # Query the reservation information for a given reservation id.
         
     | 
| 
      
 47 
     | 
    
         
            +
                  # @param id [String] The reservation id to query for.
         
     | 
| 
      
 48 
     | 
    
         
            +
                  # @return [Reservation, nil] The reservation queried for.
         
     | 
| 
      
 49 
     | 
    
         
            +
                  def reservation(id)
         
     | 
| 
      
 50 
     | 
    
         
            +
                    @adapter.query_reservation(@batch, id)
         
     | 
| 
      
 51 
     | 
    
         
            +
                  end
         
     | 
| 
      
 52 
     | 
    
         
            +
             
     | 
| 
      
 53 
     | 
    
         
            +
                  # Query for all the reservations.
         
     | 
| 
      
 54 
     | 
    
         
            +
                  # @return [Array<Reservation>] A list of reservations for the user.
         
     | 
| 
      
 55 
     | 
    
         
            +
                  def reservations
         
     | 
| 
      
 56 
     | 
    
         
            +
                    @adapter.query_reservations(@batch)
         
     | 
| 
      
 57 
     | 
    
         
            +
                  end
         
     | 
| 
      
 58 
     | 
    
         
            +
                end
         
     | 
| 
      
 59 
     | 
    
         
            +
              end
         
     | 
| 
      
 60 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,53 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module OSC
         
     | 
| 
      
 2 
     | 
    
         
            +
              module Reservations
         
     | 
| 
      
 3 
     | 
    
         
            +
                # Provides a way for developers to interact with a scheduler independent
         
     | 
| 
      
 4 
     | 
    
         
            +
                # reservation.
         
     | 
| 
      
 5 
     | 
    
         
            +
                class Reservation
         
     | 
| 
      
 6 
     | 
    
         
            +
                  # @return [String] The ID for this reservation.
         
     | 
| 
      
 7 
     | 
    
         
            +
                  attr_accessor :id
         
     | 
| 
      
 8 
     | 
    
         
            +
             
     | 
| 
      
 9 
     | 
    
         
            +
                  # @return [Time] The time when this reservation begins.
         
     | 
| 
      
 10 
     | 
    
         
            +
                  attr_accessor :starttime
         
     | 
| 
      
 11 
     | 
    
         
            +
             
     | 
| 
      
 12 
     | 
    
         
            +
                  # @return [Time] The time when this reservation ends.
         
     | 
| 
      
 13 
     | 
    
         
            +
                  attr_accessor :endtime
         
     | 
| 
      
 14 
     | 
    
         
            +
             
     | 
| 
      
 15 
     | 
    
         
            +
                  # @return [Array<Node>] The list of nodes reserved under this reservation.
         
     | 
| 
      
 16 
     | 
    
         
            +
                  attr_accessor :nodes
         
     | 
| 
      
 17 
     | 
    
         
            +
             
     | 
| 
      
 18 
     | 
    
         
            +
                  # @return [String] The accounting creds user (who gets charged for unused resources).
         
     | 
| 
      
 19 
     | 
    
         
            +
                  attr_accessor :auser
         
     | 
| 
      
 20 
     | 
    
         
            +
             
     | 
| 
      
 21 
     | 
    
         
            +
                  # @return [Array<String>] The list of users who have access to this reservation.
         
     | 
| 
      
 22 
     | 
    
         
            +
                  attr_accessor :users
         
     | 
| 
      
 23 
     | 
    
         
            +
             
     | 
| 
      
 24 
     | 
    
         
            +
                  # @param opts [Hash] The options to create a reservation with.
         
     | 
| 
      
 25 
     | 
    
         
            +
                  # @option opts [String] :id The ID of the reservation.
         
     | 
| 
      
 26 
     | 
    
         
            +
                  # @option opts [Time] :starttime The time the reservations begins.
         
     | 
| 
      
 27 
     | 
    
         
            +
                  # @option opts [Time] :endtime The time the reservation ends.
         
     | 
| 
      
 28 
     | 
    
         
            +
                  # @option opts [Array<Node>] :nodes An array of nodes allocated for the reservation.
         
     | 
| 
      
 29 
     | 
    
         
            +
                  # @option opts [String] :auser The accounting user to be charged for unused CPU of reservation.
         
     | 
| 
      
 30 
     | 
    
         
            +
                  # @option opts [Array<String>] :users An array of users who have access to this reservation.
         
     | 
| 
      
 31 
     | 
    
         
            +
                  def initialize(opts)
         
     | 
| 
      
 32 
     | 
    
         
            +
                    @id        = opts[:id]
         
     | 
| 
      
 33 
     | 
    
         
            +
                    @starttime = opts[:starttime]
         
     | 
| 
      
 34 
     | 
    
         
            +
                    @endtime   = opts[:endtime]
         
     | 
| 
      
 35 
     | 
    
         
            +
                    @nodes     = opts[:nodes]
         
     | 
| 
      
 36 
     | 
    
         
            +
                    @auser     = opts[:auser]
         
     | 
| 
      
 37 
     | 
    
         
            +
                    @users     = opts[:users]
         
     | 
| 
      
 38 
     | 
    
         
            +
                  end
         
     | 
| 
      
 39 
     | 
    
         
            +
             
     | 
| 
      
 40 
     | 
    
         
            +
                  # List of nodes that are free to use for this reservation.
         
     | 
| 
      
 41 
     | 
    
         
            +
                  # @return [Array<Node>] The list of nodes free to use.
         
     | 
| 
      
 42 
     | 
    
         
            +
                  def free_nodes
         
     | 
| 
      
 43 
     | 
    
         
            +
                    nodes.select(&:free?)
         
     | 
| 
      
 44 
     | 
    
         
            +
                  end
         
     | 
| 
      
 45 
     | 
    
         
            +
             
     | 
| 
      
 46 
     | 
    
         
            +
                  # Has this reservation started yet?
         
     | 
| 
      
 47 
     | 
    
         
            +
                  # @return [Boolean] Whether this reservation has started yet.
         
     | 
| 
      
 48 
     | 
    
         
            +
                  def started?
         
     | 
| 
      
 49 
     | 
    
         
            +
                    Time.now >= starttime
         
     | 
| 
      
 50 
     | 
    
         
            +
                  end
         
     | 
| 
      
 51 
     | 
    
         
            +
                end
         
     | 
| 
      
 52 
     | 
    
         
            +
              end
         
     | 
| 
      
 53 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,26 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # coding: utf-8
         
     | 
| 
      
 2 
     | 
    
         
            +
            lib = File.expand_path('../lib', __FILE__)
         
     | 
| 
      
 3 
     | 
    
         
            +
            $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
         
     | 
| 
      
 4 
     | 
    
         
            +
            require 'osc/reservations/version'
         
     | 
| 
      
 5 
     | 
    
         
            +
             
     | 
| 
      
 6 
     | 
    
         
            +
            Gem::Specification.new do |spec|
         
     | 
| 
      
 7 
     | 
    
         
            +
              spec.name          = "osc-reservations"
         
     | 
| 
      
 8 
     | 
    
         
            +
              spec.version       = OSC::Reservations::VERSION
         
     | 
| 
      
 9 
     | 
    
         
            +
              spec.platform      = Gem::Platform::RUBY
         
     | 
| 
      
 10 
     | 
    
         
            +
              spec.authors       = ["Jeremy Nicklas"]
         
     | 
| 
      
 11 
     | 
    
         
            +
              spec.email         = ["jnicklas@osc.edu"]
         
     | 
| 
      
 12 
     | 
    
         
            +
              spec.summary       = %q{Query current OSC reservations for running user}
         
     | 
| 
      
 13 
     | 
    
         
            +
              spec.description   = %q{This library queries active OSC reservations for the running user.}
         
     | 
| 
      
 14 
     | 
    
         
            +
              spec.homepage      = "https://github.com/OSC/osc-reservations"
         
     | 
| 
      
 15 
     | 
    
         
            +
              spec.license       = "MIT"
         
     | 
| 
      
 16 
     | 
    
         
            +
             
     | 
| 
      
 17 
     | 
    
         
            +
              spec.files         = `git ls-files`.split($/)
         
     | 
| 
      
 18 
     | 
    
         
            +
              spec.executables   = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
         
     | 
| 
      
 19 
     | 
    
         
            +
              spec.test_files    = spec.files.grep(%r{^(test|spec|features)/})
         
     | 
| 
      
 20 
     | 
    
         
            +
              spec.require_paths = ["lib"]
         
     | 
| 
      
 21 
     | 
    
         
            +
             
     | 
| 
      
 22 
     | 
    
         
            +
              spec.add_runtime_dependency "nokogiri", "~> 1.6"
         
     | 
| 
      
 23 
     | 
    
         
            +
              spec.add_runtime_dependency "pbs", "~> 1.0"
         
     | 
| 
      
 24 
     | 
    
         
            +
              spec.add_development_dependency "bundler", "~> 1.7"
         
     | 
| 
      
 25 
     | 
    
         
            +
              spec.add_development_dependency "rake", "~> 10.0"
         
     | 
| 
      
 26 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,115 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            require 'minitest/autorun'
         
     | 
| 
      
 2 
     | 
    
         
            +
            require 'osc/reservations'
         
     | 
| 
      
 3 
     | 
    
         
            +
             
     | 
| 
      
 4 
     | 
    
         
            +
            require 'ostruct'
         
     | 
| 
      
 5 
     | 
    
         
            +
            require 'yaml'
         
     | 
| 
      
 6 
     | 
    
         
            +
             
     | 
| 
      
 7 
     | 
    
         
            +
            # Stub out command line methods
         
     | 
| 
      
 8 
     | 
    
         
            +
            module Open3
         
     | 
| 
      
 9 
     | 
    
         
            +
              def popen3(*cmd,&block)
         
     | 
| 
      
 10 
     | 
    
         
            +
                line = cmd[0]
         
     | 
| 
      
 11 
     | 
    
         
            +
             
     | 
| 
      
 12 
     | 
    
         
            +
                wait_thr = nil
         
     | 
| 
      
 13 
     | 
    
         
            +
                if line =~ /NIL_RSV/
         
     | 
| 
      
 14 
     | 
    
         
            +
                  wait_thr = OpenStruct.new(value: OpenStruct.new(:'success?' => false))
         
     | 
| 
      
 15 
     | 
    
         
            +
                else
         
     | 
| 
      
 16 
     | 
    
         
            +
                  wait_thr = OpenStruct.new(value: OpenStruct.new(:'success?' => true))
         
     | 
| 
      
 17 
     | 
    
         
            +
                end
         
     | 
| 
      
 18 
     | 
    
         
            +
             
     | 
| 
      
 19 
     | 
    
         
            +
                file = "osc_rsv.xml" if line =~ /mrsvctl/
         
     | 
| 
      
 20 
     | 
    
         
            +
                file = "osc_rsvs.xml" if line =~ /mrsvctl/ && line =~ /ALL/
         
     | 
| 
      
 21 
     | 
    
         
            +
                File.open("test/files/#{file}", "r") do |f|
         
     | 
| 
      
 22 
     | 
    
         
            +
                  yield "", f, "", wait_thr
         
     | 
| 
      
 23 
     | 
    
         
            +
                end
         
     | 
| 
      
 24 
     | 
    
         
            +
              end
         
     | 
| 
      
 25 
     | 
    
         
            +
              module_function :popen3
         
     | 
| 
      
 26 
     | 
    
         
            +
            end
         
     | 
| 
      
 27 
     | 
    
         
            +
             
     | 
| 
      
 28 
     | 
    
         
            +
            # Stub out PBS methods
         
     | 
| 
      
 29 
     | 
    
         
            +
            module PBS
         
     | 
| 
      
 30 
     | 
    
         
            +
              class Conn
         
     | 
| 
      
 31 
     | 
    
         
            +
                def self.batch(name)
         
     | 
| 
      
 32 
     | 
    
         
            +
                  name
         
     | 
| 
      
 33 
     | 
    
         
            +
                end
         
     | 
| 
      
 34 
     | 
    
         
            +
              end
         
     | 
| 
      
 35 
     | 
    
         
            +
              class Query
         
     | 
| 
      
 36 
     | 
    
         
            +
                def initialize(opts)
         
     | 
| 
      
 37 
     | 
    
         
            +
                  @conn = opts[:conn]
         
     | 
| 
      
 38 
     | 
    
         
            +
                  @type = opts[:type]
         
     | 
| 
      
 39 
     | 
    
         
            +
                end
         
     | 
| 
      
 40 
     | 
    
         
            +
                def find(opts)
         
     | 
| 
      
 41 
     | 
    
         
            +
                  YAML.load_file("test/files/osc_#{@conn}_#{@type}_#{opts[:id]}.yml")
         
     | 
| 
      
 42 
     | 
    
         
            +
                end
         
     | 
| 
      
 43 
     | 
    
         
            +
              end
         
     | 
| 
      
 44 
     | 
    
         
            +
            end
         
     | 
| 
      
 45 
     | 
    
         
            +
             
     | 
| 
      
 46 
     | 
    
         
            +
            class TestOSCMoab < Minitest::Test
         
     | 
| 
      
 47 
     | 
    
         
            +
              def setup
         
     | 
| 
      
 48 
     | 
    
         
            +
                @batch = OpenStruct.new(server: 'a.b.c', torque_name: 'oakley', mrsvctl: 'mrsvctl')
         
     | 
| 
      
 49 
     | 
    
         
            +
                @adapter = OSC::Reservations::Adapters::OSCMoab.new
         
     | 
| 
      
 50 
     | 
    
         
            +
              end
         
     | 
| 
      
 51 
     | 
    
         
            +
             
     | 
| 
      
 52 
     | 
    
         
            +
              def test_osc_moab
         
     | 
| 
      
 53 
     | 
    
         
            +
                assert_respond_to @adapter, :query_reservation
         
     | 
| 
      
 54 
     | 
    
         
            +
                assert_respond_to @adapter, :query_reservations
         
     | 
| 
      
 55 
     | 
    
         
            +
                assert_respond_to @adapter, :submit_reservation
         
     | 
| 
      
 56 
     | 
    
         
            +
              end
         
     | 
| 
      
 57 
     | 
    
         
            +
             
     | 
| 
      
 58 
     | 
    
         
            +
              def test_query_reservation
         
     | 
| 
      
 59 
     | 
    
         
            +
                rsv = @adapter.query_reservation(@batch, 'NIL_RSV')
         
     | 
| 
      
 60 
     | 
    
         
            +
                assert_equal nil, rsv
         
     | 
| 
      
 61 
     | 
    
         
            +
             
     | 
| 
      
 62 
     | 
    
         
            +
                rsv = @adapter.query_reservation(@batch, 'wiag.1809')
         
     | 
| 
      
 63 
     | 
    
         
            +
                test_wiag_rsv(rsv)
         
     | 
| 
      
 64 
     | 
    
         
            +
              end
         
     | 
| 
      
 65 
     | 
    
         
            +
             
     | 
| 
      
 66 
     | 
    
         
            +
              def test_query_reservations
         
     | 
| 
      
 67 
     | 
    
         
            +
                rsv_list = @adapter.query_reservations(@batch)
         
     | 
| 
      
 68 
     | 
    
         
            +
                assert_equal 2, rsv_list.length
         
     | 
| 
      
 69 
     | 
    
         
            +
             
     | 
| 
      
 70 
     | 
    
         
            +
                rsv = rsv_list.first
         
     | 
| 
      
 71 
     | 
    
         
            +
                test_wiag_rsv(rsv)
         
     | 
| 
      
 72 
     | 
    
         
            +
             
     | 
| 
      
 73 
     | 
    
         
            +
                # reservation that hasn't started yet
         
     | 
| 
      
 74 
     | 
    
         
            +
                rsv = rsv_list[1]
         
     | 
| 
      
 75 
     | 
    
         
            +
                assert_equal 4, rsv.nodes.length
         
     | 
| 
      
 76 
     | 
    
         
            +
                assert_operator Time.now, :<, rsv.starttime
         
     | 
| 
      
 77 
     | 
    
         
            +
              end
         
     | 
| 
      
 78 
     | 
    
         
            +
             
     | 
| 
      
 79 
     | 
    
         
            +
              def test_submit_reservation
         
     | 
| 
      
 80 
     | 
    
         
            +
                @adapter.submit_reservation(@batch, nil)
         
     | 
| 
      
 81 
     | 
    
         
            +
              end
         
     | 
| 
      
 82 
     | 
    
         
            +
             
     | 
| 
      
 83 
     | 
    
         
            +
              private
         
     | 
| 
      
 84 
     | 
    
         
            +
             
     | 
| 
      
 85 
     | 
    
         
            +
              def test_wiag_rsv(rsv)
         
     | 
| 
      
 86 
     | 
    
         
            +
                assert_equal "wiag.1809", rsv.id
         
     | 
| 
      
 87 
     | 
    
         
            +
                assert_equal Time.at(1433854480), rsv.starttime
         
     | 
| 
      
 88 
     | 
    
         
            +
                assert_equal Time.at(1633854480), rsv.endtime
         
     | 
| 
      
 89 
     | 
    
         
            +
                assert_equal "judithg", rsv.auser
         
     | 
| 
      
 90 
     | 
    
         
            +
                assert_equal ["bmcmichael", "jnicklas", "awe0011", "ndem0009", "efranz", "ndem0010", "bgohar"], rsv.users
         
     | 
| 
      
 91 
     | 
    
         
            +
             
     | 
| 
      
 92 
     | 
    
         
            +
                nodes = rsv.nodes
         
     | 
| 
      
 93 
     | 
    
         
            +
                assert_equal 4, nodes.length
         
     | 
| 
      
 94 
     | 
    
         
            +
             
     | 
| 
      
 95 
     | 
    
         
            +
                # node with no jobs
         
     | 
| 
      
 96 
     | 
    
         
            +
                node = nodes[0]
         
     | 
| 
      
 97 
     | 
    
         
            +
                assert_equal "n0613", node.id
         
     | 
| 
      
 98 
     | 
    
         
            +
                assert_equal 12, node.np
         
     | 
| 
      
 99 
     | 
    
         
            +
                assert_equal ["cbb15", "partdual", "udapl"], node.props
         
     | 
| 
      
 100 
     | 
    
         
            +
                assert_equal [], node.jobs
         
     | 
| 
      
 101 
     | 
    
         
            +
                assert_equal [], node.users
         
     | 
| 
      
 102 
     | 
    
         
            +
             
     | 
| 
      
 103 
     | 
    
         
            +
                # node with one job using all cores
         
     | 
| 
      
 104 
     | 
    
         
            +
                node = nodes[3]
         
     | 
| 
      
 105 
     | 
    
         
            +
                assert_equal "n0609", node.id
         
     | 
| 
      
 106 
     | 
    
         
            +
                assert_equal ["4691489.oak-batch.osc.edu"], node.jobs
         
     | 
| 
      
 107 
     | 
    
         
            +
                assert_equal ["jnicklas"], node.users
         
     | 
| 
      
 108 
     | 
    
         
            +
             
     | 
| 
      
 109 
     | 
    
         
            +
                # node with multiple jobs on it
         
     | 
| 
      
 110 
     | 
    
         
            +
                node2 = nodes[2]
         
     | 
| 
      
 111 
     | 
    
         
            +
                assert_equal "n0611", node2.id
         
     | 
| 
      
 112 
     | 
    
         
            +
                assert_equal ["4691490.oak-batch.osc.edu", "4691491.oak-batch.osc.edu"], node2.jobs
         
     | 
| 
      
 113 
     | 
    
         
            +
                assert_equal ["jnicklas"], node2.users
         
     | 
| 
      
 114 
     | 
    
         
            +
              end
         
     | 
| 
      
 115 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,47 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            ---
         
     | 
| 
      
 2 
     | 
    
         
            +
            - :name: 4691489.oak-batch.osc.edu
         
     | 
| 
      
 3 
     | 
    
         
            +
              :attribs:
         
     | 
| 
      
 4 
     | 
    
         
            +
                :Job_Name: TestJob
         
     | 
| 
      
 5 
     | 
    
         
            +
                :Job_Owner: jnicklas@oakley01.osc.edu
         
     | 
| 
      
 6 
     | 
    
         
            +
                :resources_used:
         
     | 
| 
      
 7 
     | 
    
         
            +
                  :cput: '00:00:00'
         
     | 
| 
      
 8 
     | 
    
         
            +
                  :energy_used: '0'
         
     | 
| 
      
 9 
     | 
    
         
            +
                  :mem: 2208kb
         
     | 
| 
      
 10 
     | 
    
         
            +
                  :vmem: 211332kb
         
     | 
| 
      
 11 
     | 
    
         
            +
                  :walltime: '00:00:14'
         
     | 
| 
      
 12 
     | 
    
         
            +
                :job_state: R
         
     | 
| 
      
 13 
     | 
    
         
            +
                :queue: serial
         
     | 
| 
      
 14 
     | 
    
         
            +
                :server: oak-batch.osc.edu:15001
         
     | 
| 
      
 15 
     | 
    
         
            +
                :Checkpoint: u
         
     | 
| 
      
 16 
     | 
    
         
            +
                :ctime: '1443626884'
         
     | 
| 
      
 17 
     | 
    
         
            +
                :Error_Path: oakley01.osc.edu:/nfs/17/jnicklas/ttt/TestJob.e4845720
         
     | 
| 
      
 18 
     | 
    
         
            +
                :exec_host: n0675/0-11
         
     | 
| 
      
 19 
     | 
    
         
            +
                :exec_port: '15003'
         
     | 
| 
      
 20 
     | 
    
         
            +
                :Hold_Types: n
         
     | 
| 
      
 21 
     | 
    
         
            +
                :Join_Path: n
         
     | 
| 
      
 22 
     | 
    
         
            +
                :Keep_Files: n
         
     | 
| 
      
 23 
     | 
    
         
            +
                :Mail_Points: a
         
     | 
| 
      
 24 
     | 
    
         
            +
                :mtime: '1443626959'
         
     | 
| 
      
 25 
     | 
    
         
            +
                :Output_Path: oakley01.osc.edu:/nfs/17/jnicklas/ttt/TestJob.o4845720
         
     | 
| 
      
 26 
     | 
    
         
            +
                :Priority: '0'
         
     | 
| 
      
 27 
     | 
    
         
            +
                :qtime: '1443626884'
         
     | 
| 
      
 28 
     | 
    
         
            +
                :Rerunable: 'True'
         
     | 
| 
      
 29 
     | 
    
         
            +
                :Resource_List:
         
     | 
| 
      
 30 
     | 
    
         
            +
                  :gattr: fs17
         
     | 
| 
      
 31 
     | 
    
         
            +
                  :nodect: '1'
         
     | 
| 
      
 32 
     | 
    
         
            +
                  :nodes: 1:ppn=12
         
     | 
| 
      
 33 
     | 
    
         
            +
                  :walltime: '03:00:00'
         
     | 
| 
      
 34 
     | 
    
         
            +
                :session_id: '22136'
         
     | 
| 
      
 35 
     | 
    
         
            +
                :Variable_List: PBS_O_QUEUE=batch,PBS_O_HOME=/nfs/17/jnicklas,PBS_O_LOGNAME=jnicklas,PBS_O_PATH=/nfs/gpfs/PZS0645/local-oakley/tree/1.7.0/bin:/nfs/gpfs/PZS0645/local-oakley/git/2.3.6/bin:/nfs/gpfs/PZS0645/local-oakley/vim/7.4/bin:/nfs/17/jnicklas/bin:/usr/lib64/qt-3.3/bin:/usr/local/mvapich2/intel/15/2.1/bin:/usr/local/intel/vtune_amplifier_xe_2015.3.0.403110/bin64:/usr/local/intel/inspector_xe_2015.1.2.379161/bin64:/usr/local/intel/composer_xe_2015.3.187/bin/intel64:/usr/local/moab/8.1.1.2-2015080516-eb28ad0-el6/bin:/usr/local/torque/5.1.1-1_fba25d92/bin:/usr/local/bin:/bin:/usr/bin:/usr/local/sbin:/usr/sbin:/sbin,PBS_O_MAIL=/var/spool/mail/jnicklas,PBS_O_SHELL=/bin/bash,PBS_O_LANG=en_US.UTF-8,PBS_O_SUBMIT_FILTER=/usr/local/sbin/torque_submitfilter,PBS_O_WORKDIR=/nfs/17/jnicklas/ttt,PBS_O_HOST=oakley01.osc.edu,PBS_O_SERVER=oak-batch.osc.edu
         
     | 
| 
      
 36 
     | 
    
         
            +
                :euser: jnicklas
         
     | 
| 
      
 37 
     | 
    
         
            +
                :egroup: appl
         
     | 
| 
      
 38 
     | 
    
         
            +
                :queue_type: E
         
     | 
| 
      
 39 
     | 
    
         
            +
                :etime: '1443626884'
         
     | 
| 
      
 40 
     | 
    
         
            +
                :submit_args: -l nodes=1:ppn=12 -l walltime=03:00:00 -N TestJob
         
     | 
| 
      
 41 
     | 
    
         
            +
                :start_time: '1443626959'
         
     | 
| 
      
 42 
     | 
    
         
            +
                :Walltime:
         
     | 
| 
      
 43 
     | 
    
         
            +
                  :Remaining: '10756'
         
     | 
| 
      
 44 
     | 
    
         
            +
                :start_count: '1'
         
     | 
| 
      
 45 
     | 
    
         
            +
                :fault_tolerant: 'False'
         
     | 
| 
      
 46 
     | 
    
         
            +
                :job_radix: '0'
         
     | 
| 
      
 47 
     | 
    
         
            +
                :submit_host: oakley01.osc.edu
         
     | 
| 
         @@ -0,0 +1,47 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            ---
         
     | 
| 
      
 2 
     | 
    
         
            +
            - :name: 4691489.oak-batch.osc.edu
         
     | 
| 
      
 3 
     | 
    
         
            +
              :attribs:
         
     | 
| 
      
 4 
     | 
    
         
            +
                :Job_Name: TestJob
         
     | 
| 
      
 5 
     | 
    
         
            +
                :Job_Owner: jnicklas@oakley01.osc.edu
         
     | 
| 
      
 6 
     | 
    
         
            +
                :resources_used:
         
     | 
| 
      
 7 
     | 
    
         
            +
                  :cput: '00:00:00'
         
     | 
| 
      
 8 
     | 
    
         
            +
                  :energy_used: '0'
         
     | 
| 
      
 9 
     | 
    
         
            +
                  :mem: 2208kb
         
     | 
| 
      
 10 
     | 
    
         
            +
                  :vmem: 211332kb
         
     | 
| 
      
 11 
     | 
    
         
            +
                  :walltime: '00:00:14'
         
     | 
| 
      
 12 
     | 
    
         
            +
                :job_state: R
         
     | 
| 
      
 13 
     | 
    
         
            +
                :queue: serial
         
     | 
| 
      
 14 
     | 
    
         
            +
                :server: oak-batch.osc.edu:15001
         
     | 
| 
      
 15 
     | 
    
         
            +
                :Checkpoint: u
         
     | 
| 
      
 16 
     | 
    
         
            +
                :ctime: '1443626884'
         
     | 
| 
      
 17 
     | 
    
         
            +
                :Error_Path: oakley01.osc.edu:/nfs/17/jnicklas/ttt/TestJob.e4845720
         
     | 
| 
      
 18 
     | 
    
         
            +
                :exec_host: n0675/0-11
         
     | 
| 
      
 19 
     | 
    
         
            +
                :exec_port: '15003'
         
     | 
| 
      
 20 
     | 
    
         
            +
                :Hold_Types: n
         
     | 
| 
      
 21 
     | 
    
         
            +
                :Join_Path: n
         
     | 
| 
      
 22 
     | 
    
         
            +
                :Keep_Files: n
         
     | 
| 
      
 23 
     | 
    
         
            +
                :Mail_Points: a
         
     | 
| 
      
 24 
     | 
    
         
            +
                :mtime: '1443626959'
         
     | 
| 
      
 25 
     | 
    
         
            +
                :Output_Path: oakley01.osc.edu:/nfs/17/jnicklas/ttt/TestJob.o4845720
         
     | 
| 
      
 26 
     | 
    
         
            +
                :Priority: '0'
         
     | 
| 
      
 27 
     | 
    
         
            +
                :qtime: '1443626884'
         
     | 
| 
      
 28 
     | 
    
         
            +
                :Rerunable: 'True'
         
     | 
| 
      
 29 
     | 
    
         
            +
                :Resource_List:
         
     | 
| 
      
 30 
     | 
    
         
            +
                  :gattr: fs17
         
     | 
| 
      
 31 
     | 
    
         
            +
                  :nodect: '1'
         
     | 
| 
      
 32 
     | 
    
         
            +
                  :nodes: 1:ppn=12
         
     | 
| 
      
 33 
     | 
    
         
            +
                  :walltime: '03:00:00'
         
     | 
| 
      
 34 
     | 
    
         
            +
                :session_id: '22136'
         
     | 
| 
      
 35 
     | 
    
         
            +
                :Variable_List: PBS_O_QUEUE=batch,PBS_O_HOME=/nfs/17/jnicklas,PBS_O_LOGNAME=jnicklas,PBS_O_PATH=/nfs/gpfs/PZS0645/local-oakley/tree/1.7.0/bin:/nfs/gpfs/PZS0645/local-oakley/git/2.3.6/bin:/nfs/gpfs/PZS0645/local-oakley/vim/7.4/bin:/nfs/17/jnicklas/bin:/usr/lib64/qt-3.3/bin:/usr/local/mvapich2/intel/15/2.1/bin:/usr/local/intel/vtune_amplifier_xe_2015.3.0.403110/bin64:/usr/local/intel/inspector_xe_2015.1.2.379161/bin64:/usr/local/intel/composer_xe_2015.3.187/bin/intel64:/usr/local/moab/8.1.1.2-2015080516-eb28ad0-el6/bin:/usr/local/torque/5.1.1-1_fba25d92/bin:/usr/local/bin:/bin:/usr/bin:/usr/local/sbin:/usr/sbin:/sbin,PBS_O_MAIL=/var/spool/mail/jnicklas,PBS_O_SHELL=/bin/bash,PBS_O_LANG=en_US.UTF-8,PBS_O_SUBMIT_FILTER=/usr/local/sbin/torque_submitfilter,PBS_O_WORKDIR=/nfs/17/jnicklas/ttt,PBS_O_HOST=oakley01.osc.edu,PBS_O_SERVER=oak-batch.osc.edu
         
     | 
| 
      
 36 
     | 
    
         
            +
                :euser: jnicklas
         
     | 
| 
      
 37 
     | 
    
         
            +
                :egroup: appl
         
     | 
| 
      
 38 
     | 
    
         
            +
                :queue_type: E
         
     | 
| 
      
 39 
     | 
    
         
            +
                :etime: '1443626884'
         
     | 
| 
      
 40 
     | 
    
         
            +
                :submit_args: -l nodes=1:ppn=12 -l walltime=03:00:00 -N TestJob
         
     | 
| 
      
 41 
     | 
    
         
            +
                :start_time: '1443626959'
         
     | 
| 
      
 42 
     | 
    
         
            +
                :Walltime:
         
     | 
| 
      
 43 
     | 
    
         
            +
                  :Remaining: '10756'
         
     | 
| 
      
 44 
     | 
    
         
            +
                :start_count: '1'
         
     | 
| 
      
 45 
     | 
    
         
            +
                :fault_tolerant: 'False'
         
     | 
| 
      
 46 
     | 
    
         
            +
                :job_radix: '0'
         
     | 
| 
      
 47 
     | 
    
         
            +
                :submit_host: oakley01.osc.edu
         
     |