XML documents and Ansible

When you automate Oracle Fusion Middleware environments you cannot avoid XML documents. For simple modifications, you can treat them as regular text files or use tokenized templates for the configuration updates. Let's see what you can do if you should process XML as a structured data set. Here is a real-life example: any changes in Oracle Access Manager (OAM) configuration file should update the document version. When the OAM server finds never version it reads the document and propagates updates.

So, change OAM settings steps are:

  1. Perform configuration updates
  2. Read current configuration version
  3. Increment current version
  4. Update OAM configuration with the new value

I let you do payload updates and concentrate on the version part. The playbook below uses xml module to query and update XML content.

  vars:
    oam_config_file: oam-config.xml 
    oam_version_xpath: "/xsd:Configuration/xsd:Setting/xsd:Setting[@Name = 'Version']" 
    oam_namespaces: 
        xsd: "http://www.w3.org/2001/XMLSchema"
        htf: "http://higgins.eclipse.org/sts/Configuration"      
  tasks:
    - name: Get current version
      xml:
       path: "{{ oam_config_file }}"
       xpath: "{{ oam_version_xpath }}"
       content: text
       namespaces: "{{ oam_namespaces }}"
      register: cver
      
    - name: Set new version
      block:    
        - name: Calculate next version
          set_fact:
            new_version: "{{ cver.matches[0]['{http://www.w3.org/2001/XMLSchema}Setting']|int + 1 }}"           
        - name: Update configuration
          xml:
           path: "{{ oam_config_file }}"
           xpath: "{{ oam_version_xpath }}"
           value: "{{ new_version }}"
           namespaces: "{{ oam_namespaces }}"
      when: cver.count == 1
...

It's quite straightforward and requires only a few additional comments:

  • If the XML document has namespaces, you can declare them as a namespaces dictionary. It allows you to simplify the XPath query.
  • Module returns result as strings. Convert it to the appropriate type to perform further calculations ( |int + 1 in set_fact task)
  • Make sure that you update the appropriate node (cver.count == 1). Most of the nodes in OAM configuration are <xsd:Setting> and few of them have attribute Name with the value 'Version'.
  • Make sure that you have python-lxml package installed.

You can download sampl OAM configuration file and playbook here.