Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 32 additions & 0 deletions atlassian/confluence/cloud/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -509,6 +509,38 @@ def remove_page_as_draft(self, page_id):
"""
return self.remove_page(page_id=page_id, status="draft")

def remove_content(self, content_id):
"""
Remove any content (page, blog post, comment, attachment, ...).

:param content_id: content ID
:return: the response of the DELETE request
"""
try:
response = self.delete(f"rest/api/content/{content_id}")
except HTTPError as e:
if e.response.status_code == 403:
raise ApiPermissionError(
"The calling user does not have permission to trash or purge the content",
reason=e,
)
if e.response.status_code == 404:
# Raise ApiError as the documented reason is ambiguous
raise ApiError(
"There is no content with the given id, or the calling "
"user does not have permission to trash or purge the content",
reason=e,
)
if e.response.status_code == 409:
raise ApiConflictError(
"There is a stale data object conflict when trying to delete a draft",
reason=e,
)

raise

return response

def get_page_child_count(self, page_id, type="page"):
"""Return the number of direct children of ``type`` without listing them."""
page = self.get_page_by_id(page_id, expand=f"children.{type}")
Expand Down
2 changes: 2 additions & 0 deletions docs/confluence.rst
Original file line number Diff line number Diff line change
Expand Up @@ -282,6 +282,8 @@ Page actions
confluence.remove_page(page_id, status=None, recursive=False)

# Remove any content
# ``ConfluenceCloud`` (and ``Confluence`` with a Cloud URL) also provide
# this, through ``/wiki/rest/api/content``.
confluence.remove_content(content_id):

# Remove page from trash
Expand Down
24 changes: 24 additions & 0 deletions tests/confluence/test_confluence_cloud.py
Original file line number Diff line number Diff line change
Expand Up @@ -513,6 +513,30 @@ def test_remove_page_from_trash_through_confluence_with_cloud_url(self, mock_del
("rest/api/content/456", {"status": "draft"}),
]

@patch.object(ConfluenceCloud, "delete")
def test_remove_content(self, mock_delete, confluence_cloud):
mock_delete.return_value = None

assert confluence_cloud.remove_content("123") is None
mock_delete.assert_called_once_with("rest/api/content/123")

@patch.object(ConfluenceCloud, "delete")
def test_remove_content_404_raises_api_error(self, mock_delete, confluence_cloud):
response = Response()
response.status_code = 404
mock_delete.side_effect = HTTPError(response=response)

with pytest.raises(ApiError, match="There is no content with the given id"):
confluence_cloud.remove_content("123")

@patch.object(ConfluenceCloud, "delete")
def test_remove_content_through_confluence_with_cloud_url(self, mock_delete):
mock_delete.return_value = None
confluence = Confluence(url="https://test.atlassian.net", username="user", password="token")

assert confluence.remove_content("123") is None
mock_delete.assert_called_once_with("rest/api/content/123")

@patch.object(ConfluenceCloud, "delete")
def test_delete_content(self, mock_delete, confluence_cloud):
"""Test delete_content method."""
Expand Down
Loading