factJunction.job

Demonstrates using fact junctions to retrieve information about objects in the grid relative to another object.

Detail

Each object in the grid has a set of facts which can be read and modified. Some of these facts are special in the sense that their value contains the name of another object that must exist in the grid. These special facts are called fact junctions.

Fact junctions provide a way to reference the facts of one object, using another object as a starting point. For example, all jobs in the grid have a fact named job.accountinggroup. The value for job.accountinggroup must be the name of a job group currently existing in the grid (the default being the group named all). The following JDL code prints the ID of the accounting group for the job named myJob without using fact junctions:

job = getMatrix().getGridObject(TYPE_JOB, “myJob”)
groupName = job.getFact(“job.accountinggroup”)
group = getMatrix().getGridObject(TYPE_JOBGROUP, groupName)
print “Group ID: “ + group.getFact(“group.id”)

Using fact junctions, you can obtain the ID of the accounting group without having to retrieve a reference to the group object first, as follows:

job = getMatrix().getGridObject(TYPE_JOB, “myJob”)
print “Group ID: “ + job.getFact(“job.accountinggroup.id”)

Notice the job myJob does not have a fact named job.accountinggroup.id. However, it does have a fact named “job.accountinggroup”, which contains the name of an existing job group. This job group has the fact “group.id”, and using fact junctions you can obtain the value of this fact without explicitly reading it off of the job group object itself.

Usage

> zosadmin login --user zosadmin Login to server: skate
Please enter current password for 'zosadmin':
Logged into grid on server 'skate'

> cd /opt/novell/zenworks/zos/server/examples
> zosadmin deploy factJunction.job
factJunction successfully deployed

> zos login --user vmmanager
Please enter current password for 'vmmanager':
 Logged into grid as vmmanager

> zos jobinfo --detail factJunction
Jobname/Parameters    Attributes
------------------    ----------
factJunction       Desc: This is a test job to exercise fact junctions.

No parameters defined for this job.

Description

The files that make up the factJunction job include:

factJunction                                     # Total: 174 lines
|-- factJunction.jdl                             #  165 lines
`-- factJunction.policy                          #    9 lines

factJunction.jdl

  1  #
  2  # This is a test job, but also illustrates all the implemented fact junctions.
  3  # A fact junction is a way to access facts on a 'referenced' object.
  4  # E.g. vmhost.resource.***  redirects from the vmhost object through the
  5  #      juction onto the underlying physical resource object.
  6  #
  7  # To setup for test, copy job into the 'provisionAdapter' job group.
  8  #
  9  
 10  #
 11  # Add to the 'examples' group on deployment
 12  #
 13  if __mode__ == "deploy":
 14      try:
 15          jobgroupname = "examples"
 16          jobgroup = getMatrix().getGroup(TYPE_JOB, jobgroupname)
 17          if jobgroup == None:
 18              jobgroup = getMatrix().createGroup(TYPE_JOB, jobgroupname)
 19          jobgroup.addMember(__jobname__)
 20      except:
 21          exc_type, exc_value, exc_traceback = sys.exc_info()
 22          print "Error adding %s to %s group: %s %s" % (__jobname__, jobgroupname, exc_type, exc_value)
 23  
 24  
 25  class factJunctionJob(Job):
 26       
 27      def job_started_event(self):
 28          m = getMatrix()
 29          nptt = "<Not Possible To Test>"
 30  
 31          # Setup test environment
 32          user = m.getGridObject(TYPE_USER, "test")
 33          if (user == None):
 34              user = m.createGridObject(TYPE_USER, "test")
 35          user.setArrayFact("user.privilegedjobgroups", ["all"])
 36  
 37          repository = m.getGridObject(TYPE_REPOSITORY, "test")
 38          if (repository == None):
 39              repository = m.createGridObject(TYPE_REPOSITORY, "test")
 40          repository.setArrayFact("repository.provisioner.jobs", ["factJunction"])
 41  
 42          node = m.getGridObject(TYPE_RESOURCE, "test")
 43          if (node == None):
 44              node = m.createGridObject(TYPE_RESOURCE, "test")
 45  
 46          vm = m.getGridObject(TYPE_RESOURCE, "vmtest")
 47          if (vm == None):
 48              vm = m.createResource("vmtest", ResourceInfo.TYPE_VM_INSTANCE)
 49          vm.setFact("resource.provisioner.job", "factJunction")
 50          vm.setFact("resource.vm.repository", "test")
 51          vm.setFact("resource.provisioner.recommendedhost", "test_test")
 52  
 53          vmt = m.getGridObject(TYPE_RESOURCE, "vmttest")
 54          if (vmt == None):
 55              vmt = m.createResource("vmttest", ResourceInfo.TYPE_VM_TEMPLATE)
 56          vmt.setFact("resource.provisioner.job", "factJunction")
 57          vmt.setFact("resource.vm.repository", "test")
 58  
 59          try:
 60              vmhost = node.getVmHost("test")
 61          except:
 62              vmhost = node.createVmHost("test")
 63          vmhost.setFact("vmhost.provisioner.job", "factJunction")
 64          vmhost.setArrayFact("vmhost.repositories", ["test"])
 65          vmhost.setArrayFact("vmhost.vm.available.groups", ["all"])
 66  
 67          job = m.getGridObject(TYPE_JOB, "factJunction")
 68  
 69          # Test junctions
 70  
 71          print
 72          print "Testing User fact junctions (3):"
 73          r = user.getFact("user.accountinggroup.id")
 74          print "1. user.accountinggroup.id = %s" % r
 75          # Array junctions
 76          r = user.getFact("user.privilegedjobgroups[all].id")
 77          print "2. user.privilegedjobgroups[all].id = %s" % r
 78          r = user.getFact("user.groups[all].jobcount")
 79          print "3. user.groups[all].jobcount = %s" % r
 80  
 81  
 82          print
 83          print "Testing Job fact junctions (3):"
 84          r = job.getFact("job.accountinggroup.id")
 85          print "1. job.accountinggroup.id = %s" % r
 86          r = job.getFact("job.resourcegroup.id")
 87          print "2. job.resourcegroup.id = %s" % r
 88          # Array junctions
 89          r = job.getFact("job.groups[all].jobinstances.total")
 90          print "3. job.groups[all].jobinstances.total = %s" % r
 91  
 92  
 93          print
 94          print "Testing VmHost fact junctions (7):"
 95          r = vmhost.getFact("vmhost.resource.id")
 96          print "1. vmhost.resource.id = %s" % r
 97          r = vmhost.getFact("vmhost.accountinggroup.id")
 98          print "2. vmhost.accountinggroup.id = %s" % r
 99          r = vmhost.getFact("vmhost.provisioner.job.id")
100          print "3. vmhost.provisioner.job.id = %s" % r
101          # Array junctions
102          r = vmhost.getFact("vmhost.groups[all].vmcount")
103          print "4. vmhost.groups[all].vmcount = %s" % r
104          r = vmhost.getFact("vmhost.repositories[test].id")
105          print "5. vmhost.repositories[test].id = %s" % r
106          r = vmhost.getFact("vmhost.vm.available.groups[all].id")
107          print "6. vmhost.vm.available.groups[all].id = %s" % r
108          #r = vmhost.getFact("vmhost.vm.instanceids[vmtest].id")
109          r = nptt
110          print "7. vmhost.vm.instanceids.[vmtest].id = %s" % r
111  
112  
113          print
114          print "Testing Resource fact junctions (9):"
115          r = vm.getFact("resource.provisioner.job.id")
116          print "1. resource.provisioner.job.id = %s" % r
117          r = vm.getFact("resource.vm.repository.id")
118          print "2. resource.vm.repository.id = %s" % r
119          r = vm.getFact("resource.provisioner.recommendedhost.id")
120          print "3. resource.provisioner.recommendedhost.id = %s" % r
121          #r = vm.getFact("resource.provision.vmhost.id")
122          r = nptt
123          print "4. resource.provision.vmhost.id = %s" % r
124          #r = vm.getFact("resource.provision.template.id")
125          r = nptt
126          print "5. resource.provision.template.id = %s" % r
127          # Array junctions
128          r = vm.getFact("resource.groups[all].loadaverage")
129          print "6. resource.groups[all].loadaverage = %s" % r
130          r = node.getFact("resource.vmhosts[test_test].id")
131          print "7. resource.vmhosts[test_test].id = %s" % r
132          r = node.getFact("resource.repositories[test].id")
133          print "8. resource.repositories[test].id = %s" % r
134          #r = vmt.getFact("resource.provisioner.instances[vmttest_2].id")
135          r = nptt
136          print "9. resource.provisioner.instances[vmtest_2].id = %s" % r
137  
138  
139          print
140          print "Testing Repository fact junctions (4):"
141          r = repository.getFact("repository.groups[all].id")
142          print "1. repository.groups[all].id = %s" % r
143          r = repository.getFact("repository.vmimages[vmtest].id")
144          print "2. repository.vmimages[vmtest].id = %s" % r
145          r = repository.getFact("repository.vmhosts[test_test].id")
146          print "3. repository.vmhosts[test_test].id = %s" % r
147          r = repository.getFact("repository.provisioner.jobs[factJunction].id")
148          print "4. repository.provisioner.jobs[factJunction].id = %s" % r
149  
150  
151          print
152          print "Testing multiple junctions (1):"
153          r = repository.getFact("repository.vmhosts[test_test].resource.repositories[test].vmhosts[test_test].groups[all].id")
154          print "1. repository.vmhosts[test_test].resource.repositories[test].vmhosts[test_test].groups[all].id = %s" % r
155  
156          # Now make sure they are all accessable by the joblet...
157          #self.schedule(factJunctionJoblet, {})
158  
159  class factJunctionJoblet(Joblet):
160       
161      def joblet_started_event(self):
162          # TODO
163          time.sleep(sleeptime)

factJunction.policy

The description fact displays the commands x, y, z ...

1  <policy>
2      <job>
3          <fact name="description"
4                type="String"
5                value="This is a test job to exercise fact junctions." />
6      </job>
7  </policy>

Classes and Methods

Definitions:

Job

A representation of a running job instance.

Joblet

Defines execution on the resource.

MatrixInfo

A representation of the matrix grid object, which provides operations for retrieving and creating grid objects in the system. MatrixInfo is retrieved using the built-in getMatrix() function. Write capability is dependent on the context in which getMatrix() is called. For example, in a joblet process on a resource, creating new grid objects is not supported.

GroupInfo

A representation of Group grid objects. Operations include retrieving the group member lists and adding/removing from the group member lists, and retrieving and setting facts on the group.

UserInfo

A representation of a User grid object. This class provides accessors and setters for User facts.

RepositoryInfo

A representation of a Repository grid object. This class provides accessors and setters for Repository facts. To script the creation of Repository objects, see MatrixInfo.

ResourceInfo

A representation of a Resource Grid Object. This class inherits the base fact operations from GridObjectInfo and adds the provisioning operations for provisionable resources such as virtual machines. See MatrixInfo for how to script creation of Resource objects.

JobInfo

A representation of a deployed Job. The factset available on the JobInfo class is the aggregation of the Job's policy and policies on the groups the Job is a member of. This includes the job.* and jobargs.* fact namespaces.

Job Details

The FactJunction job performs its work by handling the following events:

zosadmin deploy

Deploying FactJunction job is performed by lines 10-22 of factJunction.jdl. When jobs are deployed into the grid, they can optionally be placed in groups for organization and easy reference. In this case, the FactJunction job will be added to the group named “examples”, and will show up in the ZENworks Orchestrator Console in the Explorer panel at the location:

/ZOS/YOUR_GRID/Jobs/examples

job_started_event

When the FactJunction job receives a job_started_event, it gets a reference to the MatrixInfo object, which allows it to obtain references to other objects in the grid, such as Users, Resources, Jobs, etc. (see lines 28, 32, 37, 42, 46, and 53 in factJunction.jdl). If these objects don't exist in the grid, they are immediately created so they can be used later on (see lines 34, 39, 44, 48, 55, and 62).

After references exist for the various objects in the grid, values for other objects are printed out using the fact junctions that exist on each object (see lines 69-154 in factJunction.jdl).

There are several instances where the FactJunction job uses “array notation” to handle fact junctions that contain multiple values (see lines 76, 78, 89, 102, 104, 106, 108, 128, 130, 132, 142, 144, 146, and 153 in factJunction.jdl). As previously explained, fact junctions are special facts because their value contains the name of another object that must exist in the grid. However, fact junctions don't always contain a single name. Some fact junctions allow for an array of names to be specified. For example, the value for the fact “job.groups” is supplied as a String array.

In this case, the fact junction can be refined using array notation, which allows for the selection of one of the values. For example, the following code retrieves the ID of the group named “myGroup”, which is one of the groups the given job is a member of:

job.getFact(“job.groups[myGroup].id”)

joblet_started_event

The FactJunction job only illustrates using fact junctions to retrieve information about objects in the grid. Therefore, no work is performed on the resource by the FactJunction joblet.

Configure and Run

To run this example, you must have ZENworks Orchestrator installed and configured properly. No agents on separate resources are required. You also must be logged into your Orchestrator server before you run zosadmin or zos commands.

Execute the following commands to deploy and run factJunction.job:

  1. Deploy factJunction.job into the grid:

    > zosadmin deploy factJunction.job
    
  2. Display the list of deployed jobs:

    > zos joblist
    

    factJunction should appear in this list.

  3. Run the FactJunction job, and view the results:

    > zos run factJunction
    JobID: vmmanager.factJunction.421
    > zos log factJunction
    > zos status vmmanager.factJunction.421
    Completed
    
    > zos log factJunction
    
  4. Testing User fact junctions:

    1. user.accountinggroup.id = all

    2. user.privilegedjobgroups[all].id = all

    3. user.groups[all].jobcount = 147

  5. Testing Job fact junctions:

    1. job.accountinggroup.id = all

    2. job.resourcegroup.id = all

    3. job.groups[all].jobinstances.total = 1

  6. Testing VmHost fact junctions:

    1. vmhost.resource.id = test

    2. vmhost.accountinggroup.id = all

    3. vmhost.provisioner.job.id = factJunction

    4. vmhost.groups[all].vmcount = 0

    5. vmhost.repositories[test].id = test

    6. vmhost.vm.available.groups[all].id = all

    7. vmhost.vm.instanceids.[vmtest].id = <Not Possible To Test>

  7. Testing Resource fact junctions:

    1. resource.provisioner.job.id = factJunction

    2. resource.vm.repository.id = test

    3. resource.provisioner.recommendedhost.id = test_test

    4. resource.provision.vmhost.id = <Not Possible To Test

    5. resource.provision.template.id = <Not Possible To Test>

    6. resource.groups[all].loadaverage = 0.03666666666666667

    7. resource.vmhosts[test_test].id = test_test

    8. resource.repositories[test].id = test

    9. resource.provisioner.instances[vmtest_2].id = <Not Possible To Test>

  8. Testing Repository fact junctions:

    1. repository.groups[all].id = all

    2. repository.vmimages[vmtest].id = vmtest

    3. repository.vmhosts[test_test].id = test_test

    4. repository.provisioner.jobs[factJunction].id = factJunction

  9. Testing multiple junctions

    1. repository.vmhosts[test_test].resource.repositories[test].vmhosts[test_test].groups[all].id = all

See Also

  • Adding jobs to groups during deployment (see how the JDL code can print the ID of group of jobs in factJunction.job).

  • View the list of fact junctions available for each object type in a ZENworks Orchestrator grid

  • Using array notation to refine multi-valued fact junctions

  • Using ZENworkd Orchestrator (How Do I Interact with ZENworks Orchestrator?)