March 2009 - Posts

Relationships in OpsMgr 2007, Part 1

Abstract

Of the two EntityTypes in the OpsMgr 2007 schema, ClassTypes and RelationshipTypes, the latter seems to be a straight-forward concept, but can have interesting ramifications in its application.  Because of this, I decided to investigate them more fully, which is the subject of this series.  In this first part, I will discuss the declaration of relationship types in a management pack and investigate some of the ramifications and restrictions related to the various base classes.  In subsequent parts, I will investigate how relationships are involved in OpsMgr's facilities and some nuances that can help explain some of OpsMgr's less obvious behavior.

Background

Relationships are at the foundation of many OpsMgr facilities:

  • Hosting
  • Groups
  • Distributed Applications
  • Reporting
  • Alerting
  • Dependency Monitors

As you can see, a majority of the key facilities in OpsMgr rely on relationships.

Declaration

First, let's discuss the declarative side of a relationship.  More accurately, relationship types are declared; instances of that relationship type are discovered.  The declaration of a RelationshipType is very simple, as shown in the MP snippets below:

<RelationshipType ID="System.Reference" Accessibility="Public" Abstract="true">
    <Source>System.Entity</Source>
    <Target>System.Entity</Target>
</RelationshipType>
<RelationshipType ID="System.Containment" Accessibility="Public" Abstract="true" Base="System.Reference">
    <Source>System.Entity</Source>
    <Target>System.Entity</Target>
</RelationshipType>

You may or may not recognize these two from the System.Library management pack.  The System.Reference relationship type is the base of all relationship types, which explains why it has no Base attribute.  System.Containment is another base relationship type, but derives from System.Reference.  It is interesting to note that all relationship types must derive from an abstract relationship type, and abstract relationship types can only be declared in System.Library.  That essentially limits the lineage of a relationship type to two, three, or four generations through one of three possible parents, respectively:

System.Reference to Your.Derived.Type

System.Reference to System.Containment to Your.Derived.Type

System.Reference to System.Containment to System.Hosting to Your.Derived.Type

There is a fourth RelationshipType declared in System.Library: System.WatchedBy (a.k.a. Perspective).  This is not an abstract type and therefore is not available for derivation.

Examining the definitions, we can see that RelationshipType elements follow the schema for declaring an "accessible" MP Element and add two attributes specific to themselves.  The standard attributes are ID, Comment (which is not often used), and Accessibility.  The two additional attributes for RelationshipType elements are Abstract and Base.  I mentioned that Comment is rare.  One regular use of this attribute, albeit a bit off topic, is in Rules.  Many Rule elements have the GUIDs for the MOM 2005 objects from which they came recorded in the Comment attribute.  There are a few other examples, but this attribute is probably one of the least used, from my observations.

For child elements of the RelationshipType element, there are three flavors: Source, Target, and Property.  You will find the great majority of relationship types are declared with just Source and Target, which can appear only once.  These are at the heart of what a relationship is, exactly.

Both Source and Target specify the ClassTypes that make up the two ends of the RelationshipType.  These follow the standard notation of [Alias!]ID, such as System!System.Entity (if we were in another management pack, where we're assuming that the System.Library has been aliased as System) or, in this case, just System.Entity (because this element, the RelationshipType, and that element, the ClassType, are declared in the same management pack).  Whatever the relationship represents, it represents it between an object of class Source and an object of class Target.  This is fairly straight-forward, but we can talk through a few examples:

  • For the System.Containment relationship type, it declares that some System.Entity (Source) can contain some other System.Entity (Target).
  • For the System.Hosting relationship type, it declares that some System.Entity (Source) hosts some other System.Entity (Target).
  • Taking another example from the AD management pack:
<RelationshipType ID="Microsoft.Windows.Server.2003.AD.DomainControllerRoleHostsNtFrs" Accessibility="Public" Abstract="false" Base="System!System.Hosting">
  <Source>Microsoft.Windows.Server.2003.AD.DomainControllerRole</Source>
  <Target>Microsoft.Windows.Server.2003.AD.DC.NtFrs</Target>
</RelationshipType>
  • This RelationshipType declares that an AD.DomainControllerRole hosts AD.DC.NtFrs.  The ID (and DisplayString), Source, and Target of this relationship are all well-chosen and describe the relationship between the types very well.

Before we leave the discussion about the declaration of a RelationshipType, it is worth noting that, while rare, some very good examples of RelationshipTypes with Property declarations exist in common MPs.  For example, the AD management pack declares this relationship:

<RelationshipType ID="Microsoft.Windows.Server.AD.Site.contains.Microsoft.Windows.Server.DC.Computer" Accessibility="Public" Abstract="false" Base="System!System.Containment">
  <Source>Microsoft.Windows.Server.AD.Site</Source>
  <Target>Windows!Microsoft.Windows.Server.DC.Computer</Target>
  <Property ID="IsBridgeheadIP" Type="string" CaseSensitive="false" Length="255"/>
  <Property ID="IsBridgeheadSMTP" Type="string" CaseSensitive="false" Length="255"/>
</RelationshipType> 

I think this is an excellent example (which also doesn't use the Comment attribute, if you'll notice).  In this case, the properties of whether a particular DC is the IP or SMTP replication bridgehead for a particular site is stored in the relationship between the site and its DCs.  I think that the tendency would be make these properties of the DC.Computer class itself.  While you might be able to pull this off in this example, any many-to-many relationships would need to store relevant properties in the relationship, where they belong.  Consider this adapted example:

<RelationshipType ID="Example.WebServer.Hosts.WebSite" ... Base="System!System.Hosting">
  <Source>Example.WebServer</Source>
  <Target>Example.WebSite</Target>
  <Property ID="IsPreferredServer" Type="string" CaseSensitive="false" Length="1"/>
</RelationshipType>

Clearly, in this case, you cannot mark the web server as being a preferred server, since it could host multiple web sites, for some of which it may not be the preferred server.  I would also not be very elegant to have some comma-delimited property of the web site that listed all preferred servers.  This is an example of where a RelationshipType declared with Property elements answers some important service modeling needs.

Restrictions and Ramifications

In spite of being relatively straight-forward to declare, relationship types have some interesting restrictions on and ramifications of their definitions:

  • For relationships that derive from System.Reference:
    • References are generic and can form relationships between just about any combination of classes.  Children can reference parents, parents can reference children, they can be reciprocal (class A references class B while class B also references class A), reflexive (class A can reference class A), and many-to-many.  In terms of relationship types that cause OpsMgr to perform in some manner, there are far more that derive from System.Containment and System.Hosting than from System.Reference.  Many reference relationships are meaningful only in the context of the management pack in which they are declared.  That notwithstanding, there are some very important uses of System.Reference relationships intrinsic to OpsMgr.  One absolutely ubiquitous example is the Microsoft.SystemCenter.HealthServiceShouldManageEntity relationship.  Another genre is the series of relationships formed when using the Distributed Application designer to connect component groups together.
  • For relationships that derive from System.Containment:
    • Containment relationships are just as freely declared as reference relationships, but some incarnations can have adverse effects on OpsMgr.  I have found that certain ViewTypes, especially state and diagram, tend to become very unpredictable if relationships form loops, etc.  In short, it has been my experience that containment relationships should be declared to represent as clean a containment model as possible.  In other words, it should be a rarity that class A contains class B while class B also contains class A, etc.  Although there are not as many restrictions on containment relationships (versus hosting), care should still be taken to model these succinctly.
  • For relationships that derive from System.Hosting:
    • There are many restrictions on hosting relationships.  This is because many things come into play when two classes are related by hosting.  First, if the host is deleted, the hosted classes are also deleted, so you have a referential integrity issue.  Also, the health service that runs workflows related to the host will also run workflows related to the hosted classes.  Finally, and perhaps most importantly, a hosting relationship is baked right into the schema of a class.  Hosting relationships are discovered automatically and you cannot even discover an instance of a hosted class without also discovering for that instance the key properties of its host and all of the hosts up the chain.  In the database, the underlying database objects for a class will contain the key fields of its hosts.  With these types of behind-the-scenes activities, it is clear to see why there are so many restrictions on the declaration of hosting relationships.
    • Restrictions on the source ClassType
      • The source does not need to be hosted itself, but it can be.
      • The source must be non-abstract.
      • The source cannot be the same as the target.
      • The source can be from any management pack.
    • Restrictions on the target ClassType
      • The target ClassType definition must be in the same management pack as the RelationshipType definition.
      • The target must be a hosted class type or derive from a class type that is hosted.
      • The target must not be the target of any other hosting relationship.
      • The target can be abstract or non-abstract.
    • Restrictions on using the Hosted attribute of a ClassType
      • If a class is hosted, it must have a hosting relationship defined for it or derive from a hosted class (which would need its own relationship type)
      • Once a ClassType is declared with the Hosted attribute set to true, it must remain consistent on all classes derived from that class.
    • Other restrictions:
      • A class can be the target of one and only one hosting relationship.  This follows the class through its descendants (i.e. a derived class cannot be the target of a hosting relationship different from that of one of its base classes).
      • The source and target cannot derive from some common class if that class has any key properties defined.  This is slightly different from the previous restrictions in that it is still not allowed even if the common ancestor is not hosted.  That is, it is acceptable to have Class B hosting Class C, and have them both derive from Class A if the relationship does not violate any of the aforementioned restrictions; however, if Class A contains key fields, the MP will fail on import.  Oddly enough, it passes MPVerify, but when it is imported, the system will try to create Class C with two sets of identical key properties (i.e. columns): its own set of key properties inherited from Class A and the set of key properties from its host, Class B, which are also inherited from Class A.  OpsMgr apparently uses a hash to create a "decorated" column name for properties of a given class that is calculated from the class and property names.  Since the contributing class name (Class A) and the properties (the keys on Class A) are identical, the MP fails to import, throwing a SQL error related to the attempt to create a table or view with duplicate column names.  I've actually run into this problem in a real example, so I hope that this is something that is addressed in a future release; however, this restriction is currently required.
      • There can be no circular hosting references, where A hosts B, B hosts C, and then C hosts A.

As you can see, the discussion of what can and cannot be done with hosting relationships is deceptively complex.  That's due in part to the fact that there is but a shade of meaning between containment and hosting in the purest sense of the words, but due to what they effect in OpsMgr, there is a great deal more to consider with hosting relationships.

For the most part, if the relationships are kept relatively simple, you will not run into these restrictions.  The most common situation that brings you into contact with them is when you are attempting to integrate some existing, robust object model into the OpsMgr model.  If you are simply extending the existing concepts around which OpsMgr has already been built (servers, applications, services, etc.), you should have a much easier time than this discussion may lead you to believe.  None-the-less, it is interesting to test the limits of what OpsMgr will allow and perhaps even more interesting to see what OpsMgr will allow that perhaps it should not!

In the next post, we will begin to see how the different types of relationships effect OpsMgr behavior.

VJD/<><

Posted by vdipippo | with no comments

Workflow Tracer 1 of 4: Workflow Primer

(Links to parts: Part 1, Part 2, Part 3, Part 4

I have written a managed code module for tracing the data items moving through a workflow.  This is a four-part article that presents the module in the fourth part.  If you are familiar with workflows, modules, and data items (the first three posts, respectively), you can go straight to the fourth article.  If not, please read on…  Even if you are familiar with these topics, you may enjoy this presentation of them and I would certainly welcome and appreciate any feedback.

The heart and soul of OpsMgr 2007 is undoubtedly the workflow engine.  This is one of the most basic functions of the Health Service: to implement the policy received from the management group by running the workflows described therein.  Discoveries, rules, and monitors are all workflows.  They are also therefore each comprised of modules that are run in a particular order to achieve the desired result.  Consider an example of each:

    • A discovery might be comprised of a timer module that executes a script at some interval.  The script, in turn, pulls some WMI data (for example).  That “data item” may then be passed to a condition detection module that evaluates it against some condition (e.g. that the WMI data contains certain properties).  Provided those conditions are met, the data item may then be passed to another condition detection module that maps the WMI data item to another data item in the specific OpsMgr discovery data format for a particular class (e.g. Windows.Computer).  This is essentially the output of the sequence.  This sequence effectively results in an instance of some class being created or updated.  That’s a workflow.

    • Another example would be a monitor.  A monitor might consist of timer module that runs a script on a schedule.  The script in this case, in turn, pulls some instrumentation data from some interesting data source (e.g. the management software that interfaces with the building environmental monitor system).  That data item is then passed to any number of different sequences of modules.  This is very well defined: one sequence for each possible state of the object (health, warning, critical, etc.).  It is assumed that only one of these sequences will pass all of the conditions and generate output data at any given moment.  The sequence that generates output data tells OpsMgr to which state the targeted object should transition (if it is in some other state).  This is another workflow.

    • The final example is a rule.  A rule will usually start in a similar way to the other two examples: some trigger or timer starts a sequence of modules in motion.  At some point, some data source or probe will produce some data item.  Any number of condition detection modules may manipulate the data item, transform it, or suppress it.  In the case of a rule, any number of “write action” modules will then accept the data item and do something with it.  For example, just about every rule includes one of the following four write actions: generate alert, set some monitor’s state, write to the operational DB, or write to the data warehouse.  Rules are not required to use these nor is that by any means an exhaustive list.  This is just meant to give you an idea of how a rule is a collection of modules.  And it’s also a workflow.

      In fact, every major monitoring- and operations-related activity of the Heatlh Service is a workflow.  These include all discoveries, monitors, diagnostics, recoveries, rules, and agent tasks.

      Understanding workflows is key to understanding OpsMgr 2007.  You should understand what they are, that most major functions of OpsMgr are workflows, and that a workflow is essentially a pipeline of modules.

      In the part 2 of this series, I will discuss those modules in more detail.

      VJD/<><

      (Links to parts: Part 1, Part 2, Part 3, Part 4

      Posted by vdipippo | with no comments

      Workflow Tracer 2 of 4: Module Primer

      (Links to parts: Part 1, Part 2, Part 3, Part 4)

      Now that I’ve given a primer on workflows, it is important to discuss modules a bit.  The following discussion is generalized.  Modules are nothing if not powerful, flexible, and completely open-ended.  Therefore, while I am confident that this discussion will be conceptually helpful, understand that there can be deviations from these generalizations.

      First, it’s worth noting that there are four basic module types: DataSource, ProbeAction, ConditionDetection, and WriteAction.  This is also the order in which they appear, both as children of the ModuleTypes element in the management pack and as children of the MemberModules element of a Composite module.

      • DataSource and ProbeAction modules essentially do some work to collect some attributes of some entity and produce a DataItem.  These modules can be thought of as operating on entities extenal to OpsMgr itself in a manner that does not change them (i.e. read only) for the expressed purpose of brining the “facts” about their current state of configuration or operation into OpsMgr’s universe.  A DataItem produced by a DataSource or ProbeAction is the unit of information that starts that process.
      • ConditionDetection modules are essentially filters that consume a DataItem as input and either manipulate it or check it against some conditions.  ConditionDetection modules are always defined with an OutputType, but depending on their purpose and the contents of the input, they may or may not output a DataItem on any given occasion.  When a ConditionDetection module produces a DataItem, it will be passed on to the next module in the workflow, either unchanged (e.g. as is the case with the expression filters) or transformed (e.g. as is the case with the discovery mappers).  When a ConditionDetection module does not produce a DataItem, the workflow ends (e.g. as is the case when a test condition is not met).  These modules can be thought of as operating on the DataItem produced by the DataSource or ProbeAction module.  They are usually internal to the workflow, meaning that they only consider the input and their purpose and configuration.  They do not usually use data external to the data flowing through the workflow.  I reiterate, though, that they do not strictly need to be simple filters that can only see the DataItem passed in or only affect the DataItem passed out.  Some do quite a bit more than that.  Good examples of this are the ConditionDetection modules involved in calculating delta values and baselines.  They do operate on incoming DataItems and produce outgoing DataItems, but they also hold state themselves.
      • WriteAction modules receive a DataItem and do something active with it, like write it to the database, generate an alert, or otherwise use its contents to affect some other entity.  These are formally defined as the only modules that will change something external to OpsMgr.  This is one reason why you don’t normally see a WriteAction module in a discovery or monitor.  WriteAction modules optionally can produce output.

      See the following diagram for a visual treatment of the four module types.

      Slide1

      This, therefore, gives a lifecycle of a workflow: from the creation of a DataItem, through manipulations, to the final action a DataItem causes.   Of course, to continue painting a picture of how these modules are used, I would also note that discoveries and monitors do not usually contain write actions.  The nature of a discovery or monitor infers that their end state will be internal to OpsMgr: a new or updated instance or a change in state, respectively.  In those cases, then, it is OpsMgr itself that consumes the final output of the workflow.

      The next two paragraphs contain very rich information.  Based on feedback, I have added a few diagrams to help understand these concepts.  I suggest an initial read of these two paragraphs, followed by a review of the diagrams, and then a quick re-read.

      To make matters even more interesting, the definition/implementation of any given module can be one of three forms: native code (implemented as a COM .DLL), managed code (implemented as a .NET assembly .DLL), or a Composite module.  A Composite module is itself a pre-defined sequence of other modules.  Composite modules are the most interesting to research, since a Composite can be defined as the sequence of several modules, each of which may be a Composite itself, each of which yet again may be a Composite, etc.  Eventually, all module implementations will end at native or managed code, but it can be quite a ride getting there.  Since any given module will be of one of four module types implemented in one of three possible ways, how truly open-ended a module’s functionality can be should be self-evident.  I have written a tool for examining such lineages in OpsMgr, which you can read about here.  It actually started out as a tool that would only explore the lineage of modules, but I later expanded it to include class types, relationship types, and data types.

      This also skews the clean definitions and characterizations of the four module types I discussed above.  Consider this: a DataSourceModuleType may be defined as a Composite of a DataSource, a ProbeAction, and a ConditionDetection module.  Another DataSourceModuleType may use that DataSource module in its own definition of a Composite that includes another ProbeAction and another ConditionDetection module.  That would make the final DataSourceModuleType a DataSource, ProbeAction, ConditionDetection, ProbeAction, and finally ConditionDetection sequence.  That final DataSourceModuleType might then be used in a workflow for a Discovery rule.  Although only certain combinations are allowed for each composite type (i.e. a ConditionDetection module may not come between a DataSource and ProbeAction in a Composite DataSourceModuleType), it’s otherwise completely flexible.

      The following diagrams help to present this material more visually.

      The first diagram presents some basic modules that will be used in the examples that follow:

      Slide2

      The next diagram depicts how Composite modules are created and eventually used in a workflow:

      Slide3

      The next diagram shows a more detailed view of the workflow presented above (the Rule):

      Slide4

      This next diagram shows how the Composite modules may also be used with other modules to form a UnitMonitorType.  This next diagram is an example of a two-state monitor (Healthy/Warning or Healthy/Critical):

      Slide5

      This final example extends the previous example to be a three-state monitor (Healthy/Warning/Critical):

      Slide6

      Obviously, it can get fairly complicated.  On the other hand, it is very conducive to good design habits: making small, focused bits of functionality that are then re-used where they are needed.

      Next in part 3, we will examine these DataItems a bit more closely.

      VJD/<><

      (Links to parts: Part 1, Part 2, Part 3, Part 4)

      Posted by vdipippo | with no comments

      Workflow Tracer 3 of 4: Data Item Primer

      (Links to parts: Part 1, Part 2, Part 3, Part 4)

      Now that we have discussed how workflows are the heart and soul of OpsMgr and modules are the building blocks of workflows, let’s discuss what runs through all of this plumbing: Data Items.

      A data item is defined in a management pack via a DataType definition in the TypeDefinitions section. These DataTypes follow an inheritance model such that all data items eventually derive from System.BaseData. Data types are a little tricky to investigate, as their definition and XML format is tucked away in their implementation, which is always in native or managed code. Outside of that code, however, they are represented as XML document fragments. An example would be:

      <DataItem time=”…” sourceHealthServiceId=”…” type=”System.BaseData” />

      In fact, this is all that’s needed for the basic Data Item. It is a single node with three required attributes: the time it was created, the source health service id, and the type of data item it is. The remainder of the schema is defined by the specific DataType and is buried inside the native or managed code that defines it. For instance, if we were so inclined, we could create a DataType called “My.Data.Item”. It could possibly look something like this:

      <DataItem time=”…” sourceHealthServiceId=”…” type=”My.Data.Item”>
      
          <MyProps>
      
              <MyProp1>Value1</MyProp1>
      
          </MyProps>
      
      </DataItem>

      As you can probably guess, all children of the DataItem element are subject to the specific requirements of the DataType set forth in the .DLL that implements the data type. You can see, then, how a data source or probe starts a workflow off: it retrieves some data externally and wraps it in some type of data item. A property bag is a common one for script monitors. A discovery data item is common for discoveries, naturally. A performance data item is common for scripted performance collectors. The list goes on.

      Incidentally, you can probably now see where the XPath expressions come from that we use in monitors, etc.: DataItem/Property[@Name="Status"] would correspond to something like this:

      <DataItem time=”…” sourceHealthServiceId=”…” type=”System.PropertyBagData”>
      
          <Property Name=”Status”>SomeStatus</Property>
      
      </DataItem>

      …and would resolve to “SomeStatus.” Since these XPath expressions are used so often in monitoring, alerting, scripting, and just about everywhere else, knowledge of the XML representation of a DataItem of any given DataType is extremely helpful.

      At this point, we can also return to our discussion of module types and give another clue as to the differentiation between them:

      • DataSource modules have only an output type. They do not have an input.
      • ProbeAction modules have a single input and a single output. They could just simply be written to manipulate the input to produce the output, but they were intended to access an external resource, based on the input, that will lead to what becomes the output. There are also special types of ProbeAction modules that have their TriggerOnly attribute set to true.  They do not have an input DataItem.
      • ConditionDetection modules have multiple inputs and a single output. The inputs are specified as a sequence of InputTypes, but often there is only one in the sequence.
      • WriteAction modules always have an input but only optionally have an output. The output is usually the result of the write action, not a continuation of the workflow.

      In summary:

      • DataItems are the units of work that are processed by modules as part of a workflow.
      • They are defined as DataType elements under the TypeDefinitions element of a management pack.
      • They follow an inheritance model, deriving eventually from System.BaseData.
      • They are implemented in native or managed code, where their format and XML representation are defined.

      Understanding the different types of data items involved in a workflow and their respective XML representation is the definitive prerequisite to understanding how to piece modules together to construct workflows for your own management pack.

      This essentially brings us to the central point of this series: the Workflow Tracer module that I will present in the last post in this series part 4.

      VJD/<><

      (Links to parts: Part 1, Part 2, Part 3, Part 4)

      Posted by vdipippo | with no comments

      Workflow Tracer 4 of 4: The Tracer Module

      (Links to parts: Part 1, Part 2, Part 3, Part 4)

      In the previous three posts, I discussed workflows, modules, and data items. I also stated that understanding the data items involved in various module interactions and their respective XML representations is sorely needed. You can accomplish this by digging though the system MPs and then through the disassembly of managed code, but that’s not a recommended course of action or a reasonable requirement. Also, beyond the general structure of the various types of data items, it is also important to see the actual contents on occasion. If you have a workflow that never produces output even though it appears as if the conditions, etc. in the workflow should result in something, a window into the values that are being processed by a particular module at a particular time would also be very helpful. This is standard fare for a solid debugging process supported by the platform’s tools. OpsMgr, unfortunately, does not yet have a good MP/workflow debugging facility.

      I have written a managed code module and an associated management pack that helps with this issue. The theory of operation of the module is simple enough: it is a condition detection module that receives a data item and then passes it on to the next module in the workflow unchanged. The only action it takes is to log the data item passed to it to the Application Event Log.

      Using this module is simple.

      It must first be installed. First, copy the .dll to the OpsMgr installation directory on the computer(s) on which you intend to run the trace. This will likely be C:\Program Files\System Center Operations Manager 2007\. Then, import the sealed MP downloadable below. Also, I’m assuming this will be done in a test lab. That’s my recommendation, anyway…

      Second, it must be incorporated into the management pack in which the module you are tracing lives. It must be inserted into the module sequence of the composite module you are attempting to trace.

      First, add a reference to it in your management pack:

      <Reference Alias=”f24″>
      
          <ID>com.focus24.Scom.Modules</ID>
      
          <Version>24.1.0.230</Version>
      
          <PublicKeyToken>5be9fb627d5adfbf</PublicKeyToken>
      
      </Reference>

      Next, add its required elements to your composite module’s Configuration element:

      <Configuration>
      
          …(your other stuff)…
      
          <xsd:element xmlns:xsd=”http://www.w3.org/2001/XMLSchemaname=”TraceElement” type=”xsd:string” />
      
          <xsd:element xmlns:xsd=”http://www.w3.org/2001/XMLSchemaname=”TraceTarget” type=”xsd:string” />
      
      </Configuration>

      There is one more element that we need to specify for the tracer module, but it will not be under the Configuration element of your module. Instead, this will be specified directly when we add it to the MemberModules element. This is because you may want to insert the module into the workflow multiple times, to trace a DataItem through different stages of the workflow.

      Therefore, next, add it any number of times under the MemberModules element, with the corresponding ordering under the Composition element:

      <MemberModules>
      
          <DataSource ID=”DS1″>
      
              …your data source…
      
          </DataSource>
      
          <ConditionDetection ID=”Trace1″ TypeID=”f24!com.focus24.Scom.Modules.WorkflowTracer”>
      
              <TraceElement>$Config/TraceElement$</TraceElement>
      
              <TraceTarget>$Config/TraceTarget$</TraceTarget>
      
              <TraceStage>Text to Identify Stage, like “Data Source to Exp Filter”</TraceStage>
      
          </ConditionDetection>
      
          <ConditionDetection ID=”Filter1″>
      
              …your expression filter…
      
          </ConditionDetection>
      
          <ConditionDetection ID=”Trace2″ TypeID=”f24!com.focus24.Scom.Modules.WorkflowTracer”>
      
              <TraceElement>$Config/TraceElement$</TraceElement>
      
              <TraceTarget>$Config/TraceTarget$</TraceTarget>
      
              <TraceStage>Exp Filter to Discovery Mapper</TraceStage>
      
          </ConditionDetection>
      
          <ConditionDetection ID=”Mapper1″>
      
              …your discovery mapper…
      
          </ConditionDetection>
      
          <ConditionDetection ID=”Trace3″ TypeID=”f24!com.focus24.Scom.Modules.WorkflowTracer”>
      
              <TraceElement>$Config/TraceElement$</TraceElement>
      
              <TraceTarget>$Config/TraceTarget$</TraceTarget>
      
              <TraceStage>Discovery Mapper to Final Output</TraceStage>
      
          </ConditionDetection>
      
      </MemberModules>
      
      <Composition>
      
          <Node ID=”Trace3″>
      
              <Node ID=”Mapper1″>
      
                  <Node ID=”Trace2″>
      
                      <Node ID=”Filter1″>
      
                          <Node ID=”Trace1″>
      
                              <Node ID=”DS1″/>
      
                          </Node>
      
                      </Node>
      
                  </Node>
      
              </Node>
      
          </Node>
      
      </Composition>

      …and that’s about it. When the management pack is next imported, the new workflow will begin running. Check the Operations Manager log for any module errors first. Then, check the Application log for the workflow trace events. Here is a sample:

      I sincerely hope you find this module useful. Please let me know if you encounter any issues or have any other feedback on this module or this series.

      VJD/<><

      Download:

      USE THIS IN A TEST ENVIRONMENT ONLY.

      com.focus24.Scom.Modules_build231.zip

      (Links to parts: Part 1, Part 2, Part 3, Part 4)

      Posted by vdipippo | with no comments

      ConfigMgr MP Policy Checker

      When client policy is created in ConfigMgr, it is distributed to clients via Management Points.  Client policy can be anything from client agent settings, site-wide settings that affect client activity (such as communication ports), and, most commonly, advertisements.  The mechanics that happen behind-the-scenes to get the policy to the client is, generally, as follows:

      • The policy is created at the server, either by an SDK/Scripting application or the console.
      • The policy in the database is compared against the site assignments, collection assignments, etc., to create effective policy assignments (i.e. which policy is applicable to which clients).
      • The policy and assignments are replicated down to all child sites and MPs.
      • When clients check for new or updated policy, they receive it in the form of an HTTP data pull from the MP.
      • The HTTP payload is an XML document that wraps MOF data.
      • The MOF information is unwrapped and becomes new or updated instances of ConfigMgr WMI classes.
      • The ConfigMgr client's activities are essentially driven by instances of those WMI classes.

      In a large environment, especially one with rate-limited addresses between sites, the part that can be problematic to research is the replication piece.  The replication of policy can back up behind other jobs.  Also, network issues can cause some policy instructions to be discarded.  This can cause a situation where the policy looks fine at the console but is not being picked up by clients.  The solution to this type of problem is usually fairly simple: a quick change to the policy will cause it to replicate again.  There's usually some change that doesn't fundamentally change the policy that can be made.  Besides, it can be changed back after the problem has corrected itself.

      There is a tool in the old SMS Toolkit 2 that allows you to connect to an MP to pull policy, but it is a manual process and is very daunting to use when trying to ascertain the extent of an issue or the readiness of policy in a large environment.  The latter is an important sanity check that I have always found useful before a large deployment, etc.

      To facilitate this testing, I have written a tool that will allow you to select a policy and then check that policy via HTTP pulls to all of the MPs.  The tool is multi-threaded for performance and works well in large environment.  The use of this tool should be fairly straight-forward.  Here are the screen shots (with certain identifying parts blacked out):

      First, enter the central primary server's FQDN and database name, and then click "Load Policies."

      image1

      The policies will be listed in alphabetical order by policy ID.

      image2

      Next, select a policy by clicking on it in the grid.  This puts the Policy ID in the Pattern field and changes the button to "Check This Policy."

      image3

      Clicking on "Check This Policy" starts the HTTP checks against every MP.  The checks happen through 5 independent threads, which is a number that is hard-coded into the tool.  This seems to be a good balance of concurrence and performance.  Each Status cell will be a yellow Req(thread#), a red Failed, or a green Passed.  Details for failed requests will be shown in the last column (not shown here, but in the grid to the right).  One more status is a yellow Aborted, which will show if you stop the checks with active threads.  When all of the checks are done, you must click Stop Checks to reset the tool.

      image4

      As always, there are caveats and unfinished business with the tool:

      • The tool connects to SQL with Integrated Security.  It does remember the last FQDN and database name you've used, but no SQL authentication is possible at this point.
      • The HTTP checks do not use an FQDN.  They use the NetBIOS server names from the SQL database.  This should not be a problem if the tool is run on a system with the necessary DNS suffix settings.
      • The initial policies that you will see are all GUIDs.  While some of these will be present on every MP, many are specific to a particular primary site, secondary site, etc.  Though they appear in the database, they will fail to verify on all MPs.  This is normal and depends on the policy the GUID represents.  The screen shot above shows advertisement policies (ADVERT-PACKAGE-PROGRAM).  These are the ones that are most useful to check.
      • There are some cases where older policies have version mismatches on some MPs that will cause them to fail the check, but are not problems.  This is most often because a policy existed on the system before a new site was added.  The new site's version numbers may not match the older sites' version numbers.  The tool does not handle this yet, but for most infrastructures, this isn't a common occurrence.
      • You always have to click Stop Checks to restart the test.  The functionality missing is another thread that frees the UI but keeps watch over the other threads and resets the UI when they end.  It seems like a bunch of work to avoid a single click, even though it's a definite piece of unfinished business.

      Please let me know your experience with this tool.  I find it extremely useful for testing whether advertisement policy is out to all MPs, especially.  This is another tool that we have used extensively with all of our ConfigMgr customers.  I am eager to see how it fairs "in the wild."

      You can download build 1073 here.

      Enjoy!

      Vin/<><

      Posted by vdipippo | with no comments