Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
Ansible
Manage
Activity
Members
Labels
Plan
Issues
3
Issue boards
Milestones
Code
Merge requests
2
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Deploy
Releases
Model registry
Analyze
Value stream analytics
Contributor analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
Nounous
Ansible
Commits
0c0fcadd
Commit
0c0fcadd
authored
4 years ago
by
Maxime Bombar
Browse files
Options
Downloads
Patches
Plain Diff
Boost gendoc with an ActionPlugin instead of a module
parent
2be4377e
No related branches found
No related tags found
1 merge request
!143
Clean up
Changes
1
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
action_plugins/moinmoin_page.py
+181
-0
181 additions, 0 deletions
action_plugins/moinmoin_page.py
with
181 additions
and
0 deletions
action_plugins/moinmoin_page.py
0 → 100755
+
181
−
0
View file @
0c0fcadd
#!/usr/bin/env python3
# Copyright: (c) 2019, Alexandre Iooss <erdnaxe@crans.org>
#
# GNU General Public License v3.0+
import
re
import
urllib.error
import
urllib.parse
import
urllib.request
import
difflib
from
ansible.errors
import
AnsibleError
from
ansible.plugins.action
import
ActionBase
from
ansible.utils.display
import
Display
from
ansible.module_utils._text
import
to_native
display
=
Display
()
class
ActionModule
(
ActionBase
):
TRANSFERS_FILES
=
False
_VALID_ARGS
=
frozenset
((
'
url
'
,
'
user
'
,
'
password
'
,
'
content
'
,
'
revision_comment
'
))
def
login
(
self
,
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
if
not
cookie
:
raise
AnsibleError
(
to_native
(
'
server did not return a session cookie
'
))
return
cookie
def
craft_request
(
self
,
suffix
):
"""
Crafts a function that takes an url and a cookie,
and returns the content of the requested page with given action suffix.
"""
def
f
(
url
,
cookie
):
req
=
urllib
.
request
.
Request
(
url
+
suffix
)
req
.
add_header
(
"
Cookie
"
,
cookie
)
content
=
urllib
.
request
.
urlopen
(
req
).
read
().
decode
(
'
utf-8
'
)
return
content
return
f
def
edit_ticket
(
self
,
url
,
cookie
):
"""
Return edition ticket of url
:param url: page to edit
:param cookie: session cookie
:return: edit ticket
"""
# Send request with session cookie
content
=
self
.
craft_request
(
"
?action=edit&editor=text
"
)(
url
,
cookie
)
# Search for ticket
search
=
re
.
search
(
'
name=
\"
ticket
\"
value=
\"
([^
\"
]*)
\"
'
,
content
)
if
not
search
:
raise
AnsibleError
(
to_native
(
'
no edit ticket was found
'
))
return
search
.
group
(
1
)
def
edit
(
self
,
url
,
user
,
password
,
content
,
revision_comment
,
cookie
):
"""
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
ticket
=
self
.
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
(
self
,
tmp
=
None
,
task_vars
=
None
):
"""
The run method is the main Action Plugin driver. All work is done from within this method.
tmp: Temporary directory. Sometimes an action plugin sets up
a temporary directory and then calls another module. This parameter
allows us to reuse the same directory for both.
task_vars: The variables (host vars, group vars, config vars, etc) associated with this task.
Note that while this will contain Ansible facts from the host, they should be used
with caution as a user running Ansible can disable their collection. If you want
make sure that your Action Plugin always has access to the ones it needs, you may
want to consider running the setup module directly in the run the method and getting
the Ansible facts that way.
The strategy plugin which manages running tasks on instances uses an ansible.vars.manager
VariableManager instance to retrieve this context specific dict of variables.
"""
if
task_vars
is
None
:
task_vars
=
dict
()
result
=
super
(
ActionModule
,
self
).
run
(
tmp
,
task_vars
)
del
tmp
result
[
'
changed
'
]
=
False
url
=
self
.
_task
.
args
.
get
(
"
url
"
)
user
=
self
.
_task
.
args
.
get
(
"
user
"
)
password
=
self
.
_task
.
args
.
get
(
"
password
"
)
content
=
self
.
_task
.
args
.
get
(
"
content
"
)
revision_comment
=
self
.
_task
.
args
.
get
(
"
revision_comment
"
)
cookie
=
self
.
login
(
url
,
user
,
password
)
changed
=
False
try
:
raw
=
self
.
craft_request
(
"
?action=raw
"
)(
url
,
cookie
)
if
raw
!=
content
:
changed
=
True
except
urllib
.
error
.
HTTPError
:
# We will create the page.
changed
=
True
raw
=
""
# Display any change
if
changed
:
diff
=
difflib
.
unified_diff
(
raw
.
splitlines
(),
content
.
splitlines
(),
fromfile
=
"
old
"
,
tofile
=
"
new
"
,
lineterm
=
""
)
for
line
in
diff
:
if
line
.
startswith
(
"
-
"
):
display
.
display
(
line
,
"
red
"
)
elif
line
.
startswith
(
"
+
"
):
display
.
display
(
line
,
"
green
"
)
elif
line
.
startswith
(
"
@
"
):
display
.
display
(
line
,
"
yellow
"
)
else
:
display
.
display
(
line
)
# Do apply the change if not in check mode
if
not
self
.
_play_context
.
check_mode
:
self
.
edit
(
url
,
user
,
password
,
content
,
revision_comment
,
cookie
)
self
.
_supports_check_mode
=
True
self
.
_supports_async
=
False
return
result
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment