polymac filter for Ansible

In the Spirit of

  • the Season,
  • this group (“…to share information about cool things done with Ansible…”), and
  • DRY (“don’t repeat yourself”),

I’m happy to present to you polymac: a filter for macro expansion of Ansible data with variable substitution. An example apropos for the season:

- name: Seasonal example of the "polymac" filter
  debug: msg="{{ song | polymac | to_nice_yaml(indent=8, width=1337)}}
  vars:
    song:
      title: The Twelve Days of Christmas
      lyrics:
        polymac:
          - DayOf: "day of Christmas my true love gave to me\n"
            1st:   "a partridge in a pair tree."
            2nd:   "two turtle doves,\nand %1st%"
            3rd:   "three French hens,\n%2nd%"
            4th:   "four calling birds,\n%3rd%"
            5th:   "five golden rings,\n%4th%"
            6th:   "six geese a laying,\n%5th%"
            7th:   "seven swans a swimming,\n%6th%"
            8th:   "eight maids a milking,\n%7th%"
            9th:   "nine ladies dancing,\n%8th%"
            10th:  "ten lords a leaping,\n%9th%"
            11th:  "eleven pipers piping,\n%10th%"
            12th:  "twelve drummers drumming,\n%11th%"
          - "On the first %DayOf% %1st%"
          - "On the second %DayOf% %2nd%"
          - "On the third %DayOf% %3rd%"
          - "On the fourth %DayOf% %4th%"
          - "On the fifth %DayOf% %5th%"
          - "On the sixth %DayOf% %6th%"
          - "On the seventh %DayOf% %7th%"
          - "On the eighth %DayOf% %8th%"
          - "On the nineth %DayOf% %9th%"
          - "On the tenth %DayOf% %10th%"
          - "On the eleventh %DayOf% %11th%"
          - "On the twelfth %DayOf% %12th%"

produces

  song:
    title: The Twelve Days of Christmas
    lyrics:
      - |
        On the first day of Christmas my true love gave to me
        a partridge in a pair tree.
      - |
        On the second day of Christmas my true love gave to me
        two turtle doves,
        and a partridge in a pair tree.
# … skipping to the last verse; you get the idea …
      - |
        On the twelfth day of Christmas my true love gave to me
        twelve drummers drumming,
        eleven pipers piping,
        ten lords a leaping,
        nine ladies dancing,
        eight maids a milking,
        seven swans a swimming,
        six geese a laying,
        five golden rings,
        four calling birds,
        three French hens,
        two turtle doves,
        and a partridge in a pair tree.

There are additional made up examples in the in-line docs at the top of the file. I’ll include one more here from our actual production configs.

  - name: Example 2
    debug: msg="{{ example2 | polymac(debug=False) |to_nice_yaml(indent=8, width=1337) }}"
    vars:
      example2:
      - name: &name Merge Request Notifier
        src: merge-requests.py
        polymac:
        - - title:   *name
            sched:    "weekday business hours" # 19,39,59 7-16 * *1-5 
            minute:   "19,39,59"
            hour:     "7-16"
            weekday:  "1-5"
          - title:   *name
            sched:    "weekday evenings"       # 2       18,20 * *1-5
            minute:   "2"
            hour:     "18,20"
            weekday:  "1-5"
          - title:   *name
            sched:    "weekends"               # 2     7,13,19 * *0,6
            minute:   "2"
            hour:     "7,13,19"
            weekday:  "0,6"
        - cron:
            name:    '%title% -- %sched%'
            environment:  # Required b/c Slack API is off-site
              http_proxy:  "<redacted>"
              https_proxy: "<redacted>"
              no_proxy:    "<redacted>"
            minute:  '%minute%'
            hour:    '%hour%'
            weekday: '%weekday%'

produces the following data structure which one of our roles uses to install a script and create several cron jobs for that script:

- cron:
    environment:
      http_proxy: <redacted>
      https_proxy: <redacted>
      no_proxy: <redacted>
    hour: 7-16
    minute: 19,39,59
    name: Merge Request Notifier -- weekday business hours
    weekday: 1-5
  name: Merge Request Notifier
  src: merge-requests.py
- cron:
    environment:
      http_proxy: <redacted>
      https_proxy: <redacted>
      no_proxy: <redacted>
    hour: 18,20
    minute: '2'
    name: Merge Request Notifier -- weekday evenings
    weekday: 1-5
  name: Merge Request Notifier
  src: merge-requests.py
- cron:
    environment:
      http_proxy: <redacted>
      https_proxy: <redacted>
      no_proxy: <redacted>
    hour: 7,13,19
    minute: '2'
    name: Merge Request Notifier -- weekends
    weekday: 0,6
  name: Merge Request Notifier
  src: merge-requests.py

To install the polymac filter, download it from the link above and put it in your role’s filter_plugins directory.

Enjoy,