-
Notifications
You must be signed in to change notification settings - Fork 205
Fix/3994 sharepoint incremental sync skip sites #4256
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from 6 commits
9668caa
66659bd
e44d8fc
781d1ed
689ab90
083c7d9
564533c
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -127,7 +127,10 @@ async def _schedule(self, connector): | |
| finally: | ||
| await data_source.close() | ||
|
|
||
| if connector.features.document_level_security_enabled(): | ||
| if ( | ||
| connector.features.document_level_security_enabled() | ||
| and connector.access_control_sync_scheduling.get("enabled", False) | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Guard against access_control_sync_scheduling not being set
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yep, that is the intent. This guards against the case where DLS is enabled but access control sync scheduling has not been explicitly turned on. The |
||
| ): | ||
| ( | ||
| is_platinum_license_enabled, | ||
| license_enabled, | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -683,10 +683,13 @@ async def get_docs_incrementally(self, sync_cursor, filtering=None): | |
| async for site_collection in self.site_collections(): | ||
| yield site_collection, None, OP_INDEX | ||
|
|
||
| # Edit operation on a drive_item doesn't update the | ||
| # lastModifiedDateTime of the parent site. Therefore, we | ||
| # set check_timestamp to False when iterating over sites. | ||
| async for site in self.sites( | ||
| site_collection["siteCollection"]["hostname"], | ||
| self.configuration["site_collections"], | ||
| check_timestamp=True, | ||
| check_timestamp=False, | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Do we have to worry about site_lists and site_list_items also?
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Good question. Drive items are fetched via delta links (Graph API delta queries, see Lists, list items, and pages do not use delta queries, they are fetched directly and rely on The same reasoning already existed for |
||
| ): | ||
| ( | ||
| site_access_control, | ||
|
|
@@ -953,12 +956,12 @@ async def site_list_items( | |
| and list_item["lastModifiedDateTime"] >= self.last_sync_time() | ||
| ): | ||
| # List Item IDs are unique within list. | ||
| # Therefore we mix in site_list id to it to make sure they are | ||
| # globally unique. | ||
| # Therefore we mix in site_list id and site id to make sure they are | ||
| # globally unique across site collections. | ||
| # Also we need to remember original ID because when a document | ||
| # is yielded, its "id" field is overwritten with content of "_id" field | ||
| list_item_natural_id = list_item["id"] | ||
| list_item["_id"] = f"{site_list_id}-{list_item['id']}" | ||
| list_item["_id"] = f"{site_id}-{site_list_id}-{list_item['id']}" | ||
| list_item["object_type"] = "list_item" | ||
|
|
||
| content_type = list_item["contentType"]["name"] | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
loses first-call successes from the return value. After a retry, res contains only the retried items. _batch_bulk then calls _process_bulk_response(res, ids_to_ops) where ids_to_ops maps all original operations, but res only has the retried subset. Items that succeeded on the first call won't be tallied in stats. Was that intentional?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good catch, that was not intentional. Items that succeeded on the first call were silently dropped from the returned response, which meant
_process_bulk_responseand_populate_statsnever saw them.I have updated
_retry_transient_item_failuresto track successful items across all calls and return a merged response containing both the originally successful items and the final retry outcome. See commit 564533c.