##// END OF EJS Templates
Do not use mutables as default arguments
Dimitri Papadopoulos -
Show More
@@ -1,160 +1,168 b''
1 """Define text roles for GitHub
1 """Define text roles for GitHub
2
2
3 * ghissue - Issue
3 * ghissue - Issue
4 * ghpull - Pull Request
4 * ghpull - Pull Request
5 * ghuser - User
5 * ghuser - User
6
6
7 Adapted from bitbucket example here:
7 Adapted from bitbucket example here:
8 https://bitbucket.org/birkenfeld/sphinx-contrib/src/tip/bitbucket/sphinxcontrib/bitbucket.py
8 https://bitbucket.org/birkenfeld/sphinx-contrib/src/tip/bitbucket/sphinxcontrib/bitbucket.py
9
9
10 Authors
10 Authors
11 -------
11 -------
12
12
13 * Doug Hellmann
13 * Doug Hellmann
14 * Min RK
14 * Min RK
15 """
15 """
16 #
16 #
17 # Original Copyright (c) 2010 Doug Hellmann. All rights reserved.
17 # Original Copyright (c) 2010 Doug Hellmann. All rights reserved.
18 #
18 #
19
19
20 from docutils import nodes, utils
20 from docutils import nodes, utils
21 from docutils.parsers.rst.roles import set_classes
21 from docutils.parsers.rst.roles import set_classes
22 from sphinx.util.logging import getLogger
22 from sphinx.util.logging import getLogger
23
23
24 info = getLogger(__name__).info
24 info = getLogger(__name__).info
25
25
26 def make_link_node(rawtext, app, type, slug, options):
26 def make_link_node(rawtext, app, type, slug, options):
27 """Create a link to a github resource.
27 """Create a link to a github resource.
28
28
29 :param rawtext: Text being replaced with link node.
29 :param rawtext: Text being replaced with link node.
30 :param app: Sphinx application context
30 :param app: Sphinx application context
31 :param type: Link type (issues, changeset, etc.)
31 :param type: Link type (issues, changeset, etc.)
32 :param slug: ID of the thing to link to
32 :param slug: ID of the thing to link to
33 :param options: Options dictionary passed to role func.
33 :param options: Options dictionary passed to role func.
34 """
34 """
35
35
36 try:
36 try:
37 base = app.config.github_project_url
37 base = app.config.github_project_url
38 if not base:
38 if not base:
39 raise AttributeError
39 raise AttributeError
40 if not base.endswith('/'):
40 if not base.endswith('/'):
41 base += '/'
41 base += '/'
42 except AttributeError as err:
42 except AttributeError as err:
43 raise ValueError('github_project_url configuration value is not set (%s)' % str(err)) from err
43 raise ValueError('github_project_url configuration value is not set (%s)' % str(err)) from err
44
44
45 ref = base + type + '/' + slug + '/'
45 ref = base + type + '/' + slug + '/'
46 set_classes(options)
46 set_classes(options)
47 prefix = "#"
47 prefix = "#"
48 if type == 'pull':
48 if type == 'pull':
49 prefix = "PR " + prefix
49 prefix = "PR " + prefix
50 node = nodes.reference(rawtext, prefix + utils.unescape(slug), refuri=ref,
50 node = nodes.reference(rawtext, prefix + utils.unescape(slug), refuri=ref,
51 **options)
51 **options)
52 return node
52 return node
53
53
54 def ghissue_role(name, rawtext, text, lineno, inliner, options={}, content=[]):
54 def ghissue_role(name, rawtext, text, lineno, inliner, options=None, content=None):
55 """Link to a GitHub issue.
55 """Link to a GitHub issue.
56
56
57 Returns 2 part tuple containing list of nodes to insert into the
57 Returns 2 part tuple containing list of nodes to insert into the
58 document and a list of system messages. Both are allowed to be
58 document and a list of system messages. Both are allowed to be
59 empty.
59 empty.
60
60
61 :param name: The role name used in the document.
61 :param name: The role name used in the document.
62 :param rawtext: The entire markup snippet, with role.
62 :param rawtext: The entire markup snippet, with role.
63 :param text: The text marked with the role.
63 :param text: The text marked with the role.
64 :param lineno: The line number where rawtext appears in the input.
64 :param lineno: The line number where rawtext appears in the input.
65 :param inliner: The inliner instance that called us.
65 :param inliner: The inliner instance that called us.
66 :param options: Directive options for customization.
66 :param options: Directive options for customization.
67 :param content: The directive content for customization.
67 :param content: The directive content for customization.
68 """
68 """
69 if options is None:
70 options = {}
69
71
70 try:
72 try:
71 issue_num = int(text)
73 issue_num = int(text)
72 if issue_num <= 0:
74 if issue_num <= 0:
73 raise ValueError
75 raise ValueError
74 except ValueError:
76 except ValueError:
75 msg = inliner.reporter.error(
77 msg = inliner.reporter.error(
76 'GitHub issue number must be a number greater than or equal to 1; '
78 'GitHub issue number must be a number greater than or equal to 1; '
77 '"%s" is invalid.' % text, line=lineno)
79 '"%s" is invalid.' % text, line=lineno)
78 prb = inliner.problematic(rawtext, rawtext, msg)
80 prb = inliner.problematic(rawtext, rawtext, msg)
79 return [prb], [msg]
81 return [prb], [msg]
80 app = inliner.document.settings.env.app
82 app = inliner.document.settings.env.app
81 #info('issue %r' % text)
83 #info('issue %r' % text)
82 if 'pull' in name.lower():
84 if 'pull' in name.lower():
83 category = 'pull'
85 category = 'pull'
84 elif 'issue' in name.lower():
86 elif 'issue' in name.lower():
85 category = 'issues'
87 category = 'issues'
86 else:
88 else:
87 msg = inliner.reporter.error(
89 msg = inliner.reporter.error(
88 'GitHub roles include "ghpull" and "ghissue", '
90 'GitHub roles include "ghpull" and "ghissue", '
89 '"%s" is invalid.' % name, line=lineno)
91 '"%s" is invalid.' % name, line=lineno)
90 prb = inliner.problematic(rawtext, rawtext, msg)
92 prb = inliner.problematic(rawtext, rawtext, msg)
91 return [prb], [msg]
93 return [prb], [msg]
92 node = make_link_node(rawtext, app, category, str(issue_num), options)
94 node = make_link_node(rawtext, app, category, str(issue_num), options)
93 return [node], []
95 return [node], []
94
96
95 def ghuser_role(name, rawtext, text, lineno, inliner, options={}, content=[]):
97 def ghuser_role(name, rawtext, text, lineno, inliner, options=None, content=None):
96 """Link to a GitHub user.
98 """Link to a GitHub user.
97
99
98 Returns 2 part tuple containing list of nodes to insert into the
100 Returns 2 part tuple containing list of nodes to insert into the
99 document and a list of system messages. Both are allowed to be
101 document and a list of system messages. Both are allowed to be
100 empty.
102 empty.
101
103
102 :param name: The role name used in the document.
104 :param name: The role name used in the document.
103 :param rawtext: The entire markup snippet, with role.
105 :param rawtext: The entire markup snippet, with role.
104 :param text: The text marked with the role.
106 :param text: The text marked with the role.
105 :param lineno: The line number where rawtext appears in the input.
107 :param lineno: The line number where rawtext appears in the input.
106 :param inliner: The inliner instance that called us.
108 :param inliner: The inliner instance that called us.
107 :param options: Directive options for customization.
109 :param options: Directive options for customization.
108 :param content: The directive content for customization.
110 :param content: The directive content for customization.
109 """
111 """
112 if options is None:
113 options = {}
114
110 app = inliner.document.settings.env.app
115 app = inliner.document.settings.env.app
111 #info('user link %r' % text)
116 #info('user link %r' % text)
112 ref = 'https://www.github.com/' + text
117 ref = 'https://www.github.com/' + text
113 node = nodes.reference(rawtext, text, refuri=ref, **options)
118 node = nodes.reference(rawtext, text, refuri=ref, **options)
114 return [node], []
119 return [node], []
115
120
116 def ghcommit_role(name, rawtext, text, lineno, inliner, options={}, content=[]):
121 def ghcommit_role(name, rawtext, text, lineno, inliner, options=None, content=None):
117 """Link to a GitHub commit.
122 """Link to a GitHub commit.
118
123
119 Returns 2 part tuple containing list of nodes to insert into the
124 Returns 2 part tuple containing list of nodes to insert into the
120 document and a list of system messages. Both are allowed to be
125 document and a list of system messages. Both are allowed to be
121 empty.
126 empty.
122
127
123 :param name: The role name used in the document.
128 :param name: The role name used in the document.
124 :param rawtext: The entire markup snippet, with role.
129 :param rawtext: The entire markup snippet, with role.
125 :param text: The text marked with the role.
130 :param text: The text marked with the role.
126 :param lineno: The line number where rawtext appears in the input.
131 :param lineno: The line number where rawtext appears in the input.
127 :param inliner: The inliner instance that called us.
132 :param inliner: The inliner instance that called us.
128 :param options: Directive options for customization.
133 :param options: Directive options for customization.
129 :param content: The directive content for customization.
134 :param content: The directive content for customization.
130 """
135 """
136 if options is None:
137 options = {}
138
131 app = inliner.document.settings.env.app
139 app = inliner.document.settings.env.app
132 #info('user link %r' % text)
140 #info('user link %r' % text)
133 try:
141 try:
134 base = app.config.github_project_url
142 base = app.config.github_project_url
135 if not base:
143 if not base:
136 raise AttributeError
144 raise AttributeError
137 if not base.endswith('/'):
145 if not base.endswith('/'):
138 base += '/'
146 base += '/'
139 except AttributeError as err:
147 except AttributeError as err:
140 raise ValueError('github_project_url configuration value is not set (%s)' % str(err)) from err
148 raise ValueError('github_project_url configuration value is not set (%s)' % str(err)) from err
141
149
142 ref = base + text
150 ref = base + text
143 node = nodes.reference(rawtext, text[:6], refuri=ref, **options)
151 node = nodes.reference(rawtext, text[:6], refuri=ref, **options)
144 return [node], []
152 return [node], []
145
153
146
154
147 def setup(app):
155 def setup(app):
148 """Install the plugin.
156 """Install the plugin.
149
157
150 :param app: Sphinx application context.
158 :param app: Sphinx application context.
151 """
159 """
152 info('Initializing GitHub plugin')
160 info('Initializing GitHub plugin')
153 app.add_role('ghissue', ghissue_role)
161 app.add_role('ghissue', ghissue_role)
154 app.add_role('ghpull', ghissue_role)
162 app.add_role('ghpull', ghissue_role)
155 app.add_role('ghuser', ghuser_role)
163 app.add_role('ghuser', ghuser_role)
156 app.add_role('ghcommit', ghcommit_role)
164 app.add_role('ghcommit', ghcommit_role)
157 app.add_config_value('github_project_url', None, 'env')
165 app.add_config_value('github_project_url', None, 'env')
158
166
159 metadata = {'parallel_read_safe': True, 'parallel_write_safe': True}
167 metadata = {'parallel_read_safe': True, 'parallel_write_safe': True}
160 return metadata
168 return metadata
General Comments 0
You need to be logged in to leave comments. Login now