Merge lp:~bryce/launchpad/api-docs-fixes-bug into lp:launchpad

Proposed by Bryce Harrington
Status: Merged
Approved by: Bryce Harrington
Approved revision: no longer in the source branch.
Merged at revision: 10960
Proposed branch: lp:~bryce/launchpad/api-docs-fixes-bug
Merge into: lp:launchpad
Diff against target: 231 lines (+30/-22)
9 files modified
lib/lp/bugs/browser/bug.py (+1/-1)
lib/lp/bugs/doc/bugmessage.txt (+1/-1)
lib/lp/bugs/interfaces/bug.py (+20/-12)
lib/lp/bugs/interfaces/bugtask.py (+1/-1)
lib/lp/bugs/interfaces/malone.py (+1/-1)
lib/lp/code/doc/branch-visibility.txt (+1/-1)
lib/lp/code/model/tests/test_branchnamespace.py (+3/-3)
lib/lp/code/stories/branches/xx-branch-edit-privacy.txt (+1/-1)
lib/lp/registry/browser/team.py (+1/-1)
To merge this branch: bzr merge lp:~bryce/launchpad/api-docs-fixes-bug
Reviewer Review Type Date Requested Status
Eleanor Berger (community) code Approve
Review via email: mp+25798@code.launchpad.net

Commit message

Flesh out docs for interfaces/bugs.py and fix various spelling errors.

Description of the change

Further improvements to the API documentation and spelling fixes.

Most notably includes fleshing out docs of interfaces/bugs.py, and fixing the spelling of 'visiblity' which appears throughout the codebase including in a user-visible string (reported as bug #455203), and clarifying that setCommentVisibility() is an admin-only function (#373508).

To post a comment you must log in.
Revision history for this message
Eleanor Berger (intellectronica) wrote :

Bryce, all-in-all very nice improvements. There are a few potential problems though, resulting from the way interfaces are used in the UI. In Zope (and Launchpad), the same interfaces that are used to define objects can be used for publishing these objects. Many Launchpad forms, for example, use the Description attribute of fields to render the descriptive text next the field (the same goes for Title). The advantage of this approach is that you don't need to describe the same field twice. The disadvantage, is that the title and description you use must be appropriate both for use in the model and for use in the UI. Some of the titles and descriptions you've added might not be appropriate for the UI (the description for tags, for example, that appears on a bug's +edit page). For the same reason, some of the changes you've made are likely to require changes to pagetests, which I think you haven't adjusted yet in this branch. I think that the changes are good in most cases, but let's go once over the visible changes and make sure they work fine, and perhaps also submit this for UI-review.

b.t.w If you find places where you think the description should be different, all hope is not lost - it is still possible to customize the appearance of fields in the UI by changing them in the relevant classes in the the browser package.

review: Needs Information (code)
Revision history for this message
Bryce Harrington (bryce) wrote :

Hrm, that's distressing. Is there any way to differentiate between items that only show up on the API docs vs. ones that also show up in the web UI?

Personally, while it seems convenient and time-saving to reuse the web UI strings for the API docs, if the side-effect is making it harder to update the API docs, then it sort of seems like there is a risk that people will be reticent to improve the documentation for the API calls, lest it risk impacting the web UI.

Anyway, if I can find a way to discern which strings are used by the web UI, I can strip out those changes from this branch.

Revision history for this message
Eleanor Berger (intellectronica) wrote :

Bryce, with the docstrings you've removed from the diff you can land this branch. Thanks for improving the API documentation, I know for sure that it makes life much better for users.

For the future, I think it's still worth trying to come up with a way to update the documentation for only the API (without affecting the documentation of the interface itself). Perhaps by adding a new decorator, or passing an extra description to the `exported` decorator - that way you'll be able to provide even better documentation to the API which now you must avoid.

review: Approve (code)

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'lib/lp/bugs/browser/bug.py'
2--- lib/lp/bugs/browser/bug.py 2010-05-16 23:56:51 +0000
3+++ lib/lp/bugs/browser/bug.py 2010-05-26 00:52:27 +0000
4@@ -668,7 +668,7 @@
5
6 @property
7 def label(self):
8- return 'Bug #%i - Set visiblity and security' % self.context.bug.id
9+ return 'Bug #%i - Set visibility and security' % self.context.bug.id
10
11 page_title = label
12
13
14=== modified file 'lib/lp/bugs/doc/bugmessage.txt'
15--- lib/lp/bugs/doc/bugmessage.txt 2009-06-12 16:36:02 +0000
16+++ lib/lp/bugs/doc/bugmessage.txt 2010-05-26 00:52:27 +0000
17@@ -141,7 +141,7 @@
18 == Last message date ==
19
20 For each bug, we cache the date of the last message linked to it using
21-the sttribute `date_last_message` in order to optimize searches the need
22+the attribute `date_last_message` in order to optimize searches the need
23 to compare this value for every bug in a large set.
24
25 >>> test_message = bug_one.newMessage(
26
27=== modified file 'lib/lp/bugs/interfaces/bug.py'
28--- lib/lp/bugs/interfaces/bug.py 2010-04-29 17:49:19 +0000
29+++ lib/lp/bugs/interfaces/bug.py 2010-05-26 00:52:27 +0000
30@@ -206,7 +206,7 @@
31 description=_("The person who set this bug private."),
32 readonly=True))
33 security_related = exported(
34- Bool(title=_("This bug is a security vulnerability"),
35+ Bool(title=_("This bug is a security vulnerability."),
36 required=False, default=False, readonly=True))
37 displayname = TextLine(title=_("Text of the form 'Bug #X"),
38 readonly=True)
39@@ -216,7 +216,7 @@
40 bugtasks = exported(
41 CollectionField(
42 title=_('BugTasks on this bug, sorted upstream, then '
43- 'ubuntu, then other distroseriess.'),
44+ 'by ubuntu, then by other distroseries.'),
45 value_type=Reference(schema=IBugTask),
46 readonly=True),
47 exported_as='bug_tasks')
48@@ -239,12 +239,12 @@
49 cve_links = Attribute('Links between this bug and CVE entries.')
50 subscriptions = exported(
51 doNotSnapshot(CollectionField(
52- title=_('Subscriptions.'),
53+ title=_('Subscriptions'),
54 value_type=Reference(schema=Interface),
55 readonly=True)))
56 duplicates = exported(
57 CollectionField(
58- title=_('MultiJoin of the bugs which are dups of this one'),
59+ title=_("MultiJoin of bugs which are dupes of this one."),
60 value_type=BugField(), readonly=True))
61 attachments = exported(
62 CollectionField(
63@@ -263,9 +263,10 @@
64 List(title=_("Tags"), description=_("Separated by whitespace."),
65 value_type=Tag(), required=False))
66 is_complete = Bool(
67+ title=_("Is Complete?"),
68 description=_(
69 "True or False depending on whether this bug is considered "
70- "completely addressed. A bug is Launchpad is completely "
71+ "completely addressed. A bug in Launchpad is completely "
72 "addressed when there are no tasks that are still open for "
73 "the bug."),
74 readonly=True)
75@@ -278,12 +279,12 @@
76 readonly=True)
77 can_expire = exported(
78 Bool(
79- title=_("Can the Incomplete bug expire if it becomes inactive? "
80+ title=_("Can the Incomplete bug expire if it becomes inactive? "
81 "Expiration may happen when the bug permits expiration, "
82 "and a bugtask cannot be confirmed."),
83- readonly=True))
84+ readonly=True))
85 date_last_message = exported(
86- Datetime(title=_('Date of last bug message'),
87+ Datetime(title=_("Date of last bug message"),
88 required=False, readonly=True))
89 number_of_duplicates = exported(
90 Int(title=_('The number of bugs marked as duplicates of this bug'),
91@@ -305,7 +306,8 @@
92 Int(title=_('The number of users unaffected by this bug'),
93 required=True, readonly=True))
94 users_affected = exported(doNotSnapshot(CollectionField(
95- title=_('Users affected (not including duplicates)'),
96+ title=_('The number of users affected by this bug '
97+ '(not including duplicates)'),
98 value_type=Reference(schema=IPerson),
99 readonly=True)))
100 users_unaffected = exported(doNotSnapshot(CollectionField(
101@@ -713,6 +715,9 @@
102
103 :security_related: True/False.
104
105+ This may also cause the security contact to be subscribed
106+ if one is registered and if the bug is not private.
107+
108 Return True if a change is made, False otherwise.
109 """
110
111@@ -764,7 +769,10 @@
112 @call_with(user=REQUEST_USER)
113 @export_write_operation()
114 def setCommentVisibility(user, comment_number, visible):
115- """Set the visible attribute on a bug comment."""
116+ """Set the visible attribute on a bug comment. This is restricted
117+ to Launchpad admins, and will return a HTTP Error 401: Unauthorized
118+ error for non-admin callers.
119+ """
120
121 def userCanView(user):
122 """Return True if `user` can see this IBug, false otherwise."""
123@@ -979,10 +987,10 @@
124 * the reporter will be subscribed to the bug
125
126 * distribution, product and package contacts (whichever ones are
127- applicable based on the bug report target) will bug subscribed to
128+ applicable based on the bug report target) will be subscribed to
129 all *public bugs only*
130
131- * for public upstreams bugs where there is no upstream bug contact,
132+ * for public upstream bugs where there is no upstream bug contact,
133 the product owner will be subscribed instead
134
135 * if either product or distribution is specified, an appropiate
136
137=== modified file 'lib/lp/bugs/interfaces/bugtask.py'
138--- lib/lp/bugs/interfaces/bugtask.py 2010-05-18 17:50:25 +0000
139+++ lib/lp/bugs/interfaces/bugtask.py 2010-05-26 00:52:27 +0000
140@@ -787,7 +787,7 @@
141 required=False)
142 importance = List(
143 title=_('Importance'),
144- description=_('Show only bugs with the given importance'
145+ description=_('Show only bugs with the given importance '
146 'or list of importances.'),
147 value_type=IBugTask['importance'],
148 required=False)
149
150=== modified file 'lib/lp/bugs/interfaces/malone.py'
151--- lib/lp/bugs/interfaces/malone.py 2009-06-25 00:40:31 +0000
152+++ lib/lp/bugs/interfaces/malone.py 2010-05-26 00:52:27 +0000
153@@ -69,7 +69,7 @@
154 * the owner will be subscribed to the bug
155
156 * distribution, product and package contacts (whichever ones are
157- applicable based on the bug report target) will bug subscribed to
158+ applicable based on the bug report target) will be subscribed to
159 all *public bugs only*
160
161 * for public upstreams bugs where there is no upstream bug contact,
162
163=== modified file 'lib/lp/code/doc/branch-visibility.txt'
164--- lib/lp/code/doc/branch-visibility.txt 2010-01-12 14:52:41 +0000
165+++ lib/lp/code/doc/branch-visibility.txt 2010-05-26 00:52:27 +0000
166@@ -74,7 +74,7 @@
167
168 == Visibility due to ownership ==
169
170-The owners of the branch always have visiblity of their own branches.
171+The owners of the branch always have visibility of their own branches.
172
173 >>> branch.private = True
174 >>> from canonical.launchpad.webapp.authorization import clear_cache
175
176=== modified file 'lib/lp/code/model/tests/test_branchnamespace.py'
177--- lib/lp/code/model/tests/test_branchnamespace.py 2009-07-29 02:16:43 +0000
178+++ lib/lp/code/model/tests/test_branchnamespace.py 2010-05-26 00:52:27 +0000
179@@ -1451,7 +1451,7 @@
180
181
182 class PolicySimple(BranchVisibilityPolicyTestCase):
183- """Test the visiblity policy where the base visibility rule is PUBLIC with
184+ """Test the visibility policy where the base visibility rule is PUBLIC with
185 one team specified to have PRIVATE branches.
186 """
187
188@@ -1496,7 +1496,7 @@
189
190
191 class PolicyPrivateOnly(BranchVisibilityPolicyTestCase):
192- """Test the visiblity policy where the base visibility rule is PUBLIC with
193+ """Test the visibility policy where the base visibility rule is PUBLIC with
194 one team specified to have the PRIVATE_ONLY rule.
195
196 PRIVATE_ONLY only stops the user from changing the branch from private to
197@@ -1545,7 +1545,7 @@
198
199
200 class PolicyForbidden(BranchVisibilityPolicyTestCase):
201- """Test the visiblity policy where the base visibility rule is FORBIDDEN
202+ """Test the visibility policy where the base visibility rule is FORBIDDEN
203 with one team specified to have the PRIVATE branches and another team
204 specified to have PUBLIC branches.
205 """
206
207=== modified file 'lib/lp/code/stories/branches/xx-branch-edit-privacy.txt'
208--- lib/lp/code/stories/branches/xx-branch-edit-privacy.txt 2009-11-26 22:55:06 +0000
209+++ lib/lp/code/stories/branches/xx-branch-edit-privacy.txt 2010-05-26 00:52:27 +0000
210@@ -24,7 +24,7 @@
211 Branches with no visibility policy
212 ----------------------------------
213
214-If there is no policy set, then the user is not able to change the visiblity
215+If there is no policy set, then the user is not able to change the visibility
216 of the branch.
217
218 >>> browser = setupBrowser(auth='Basic eric@example.com:test')
219
220=== modified file 'lib/lp/registry/browser/team.py'
221--- lib/lp/registry/browser/team.py 2009-12-24 01:38:11 +0000
222+++ lib/lp/registry/browser/team.py 2010-05-26 00:52:27 +0000
223@@ -116,7 +116,7 @@
224
225
226 class TeamFormMixin:
227- """Form to be used on forms which conditionally display team visiblity.
228+ """Form to be used on forms which conditionally display team visibility.
229
230 The visibility field should only be shown to users with
231 launchpad.Commercial permission on the team.