#!/usr/bin/env python3 # Copyright: (c) 2019, Alexandre Iooss # GNU General Public License v3.0+ """ This module simulate the edition of a MoinMoin wiki page Example: moinmoin_page: url: https://wiki.crans.org/WikiErdnaxe user: WikiErdnaxe password: HoTuNeMeConnaisPas content: "{{ lookup('template', 'mapage.j2') }}" revision_comment: Bip bip """ import re import urllib.error import urllib.parse import urllib.request from ansible.module_utils.basic import AnsibleModule def login(url, user, password): """ Log in and return session cookie or None if failed :param url: random wiki url (not root page) :param user: wiki user :param password: user's password :return: session cookie """ # Send a HTTP POST request data = urllib.parse.urlencode({ 'action': 'login', 'login': 'Connexion', 'name': user, 'password': password }).encode() req = urllib.request.Request(url, data) try: response = urllib.request.urlopen(req) cookie = response.getheader('set-cookie') except urllib.error.HTTPError as e: # If 404, then also return header cookie = e.getheader('set-cookie') # Check that authentication worked assert cookie, 'server did not return a session cookie' return cookie def edit_ticket(url, cookie): """ Return edition ticket of url :param url: page to edit :param cookie: session cookie :return: edit ticket """ # Send request with session cookie suffix = "?action=edit&editor=text" req = urllib.request.Request(url + suffix) req.add_header("Cookie", cookie) content = urllib.request.urlopen(req).read().decode('utf-8') # Search for ticket search = re.search('name=\"ticket\" value=\"([^\"]*)\"', content) assert search, 'no edit ticket was found' return search.group(1) def edit(url, user, password, content, revision_comment): """ Edit a MoinMoin wiki page :param url: page to edit :param user: wiki user :param password: user's password :param content: content to place on this page :param revision_comment: revision comment """ # Connect and get edit ticket cookie = login(url, user, password) ticket = edit_ticket(url, cookie) # Create request and send data = { 'button_save': 'Enregistrer les modifications', 'category': '', 'comment': revision_comment.encode("utf-8"), 'savetext': content.encode("utf-8"), 'action': 'edit', 'ticket': ticket } req = urllib.request.Request(url, urllib.parse.urlencode(data).encode()) req.add_header("Cookie", cookie) urllib.request.urlopen(req) def run_module(): # Define arguments that should be passed module_args = { 'url': {'type': 'str', 'required': True}, 'user': {'type': 'str', 'required': True}, 'password': {'type': 'str', 'required': True}, 'content': {'type': 'str', 'required': True}, 'revision_comment': {'type': 'str', 'required': True}, } # Define arguments that are returned result = { 'changed': False, } # Our AnsibleModule module = AnsibleModule( argument_spec=module_args, supports_check_mode=True ) # TODO: get current wiki page and compare result['changed'] = True # If not is check mode and page need to change, then update page if not module.check_mode and result['changed']: edit(**module.params) module.exit_json(**result) def main(): run_module() if __name__ == '__main__': main()