Merge pull request #1218 from Codium-ai/tr/updates_and_fixes

feat: enhance error handling and logging, update AI metadata terminology
This commit is contained in:
Tal
2024-09-10 17:59:48 +03:00
committed by GitHub
6 changed files with 60 additions and 41 deletions

View File

@ -25,7 +25,7 @@ For example, when generating code suggestions for different files, PR-Agent can
``` ```
## File: 'src/file1.py' ## File: 'src/file1.py'
### AI-generated file summary: ### AI-generated changes summary:
- edited function `func1` that does X - edited function `func1` that does X
- Removed function `func2` that was not used - Removed function `func2` that was not used
- .... - ....

View File

@ -496,27 +496,40 @@ def add_ai_metadata_to_diff_files(git_provider, pr_description_files):
""" """
Adds AI metadata to the diff files based on the PR description files (FilePatchInfo.ai_file_summary). Adds AI metadata to the diff files based on the PR description files (FilePatchInfo.ai_file_summary).
""" """
diff_files = git_provider.get_diff_files() try:
for file in diff_files: if not pr_description_files:
filename = file.filename.strip() get_logger().warning(f"PR description files are empty.")
found = False return
for pr_file in pr_description_files: available_files = {pr_file['full_file_name'].strip(): pr_file for pr_file in pr_description_files}
if filename == pr_file['full_file_name'].strip(): diff_files = git_provider.get_diff_files()
file.ai_file_summary = pr_file found_any_match = False
found = True for file in diff_files:
break filename = file.filename.strip()
if not found: if filename in available_files:
get_logger().info(f"File {filename} not found in the PR description files", file.ai_file_summary = available_files[filename]
artifacts=pr_description_files) found_any_match = True
if not found_any_match:
get_logger().error(f"Failed to find any matching files between PR description and diff files.",
artifact={"pr_description_files": pr_description_files})
except Exception as e:
get_logger().error(f"Failed to add AI metadata to diff files: {e}",
artifact={"traceback": traceback.format_exc()})
def add_ai_summary_top_patch(file, full_extended_patch): def add_ai_summary_top_patch(file, full_extended_patch):
# below every instance of '## File: ...' in the patch, add the ai-summary metadata try:
full_extended_patch_lines = full_extended_patch.split("\n") # below every instance of '## File: ...' in the patch, add the ai-summary metadata
for i, line in enumerate(full_extended_patch_lines): full_extended_patch_lines = full_extended_patch.split("\n")
if line.startswith("## File:") or line.startswith("## file:"): for i, line in enumerate(full_extended_patch_lines):
full_extended_patch_lines.insert(i + 1, if line.startswith("## File:") or line.startswith("## file:"):
f"### AI-generated file summary:\n{file.ai_file_summary['long_summary']}") full_extended_patch_lines.insert(i + 1,
break f"### AI-generated changes summary:\n{file.ai_file_summary['long_summary']}")
full_extended_patch = "\n".join(full_extended_patch_lines) full_extended_patch = "\n".join(full_extended_patch_lines)
return full_extended_patch return full_extended_patch
# if no '## File: ...' was found
return full_extended_patch
except Exception as e:
get_logger().error(f"Failed to add AI summary to the top of the patch: {e}",
artifact={"traceback": traceback.format_exc()})
return full_extended_patch

View File

@ -316,7 +316,7 @@ class AzureDevopsProvider(GitProvider):
new_file_content_str = new_file_content_str.content new_file_content_str = new_file_content_str.content
except Exception as error: except Exception as error:
get_logger().error(f"Failed to retrieve new file content of {file} at version {version}. Error: {str(error)}") get_logger().error(f"Failed to retrieve new file content of {file} at version {version}", error=error)
# get_logger().error( # get_logger().error(
# "Failed to retrieve new file content of %s at version %s. Error: %s", # "Failed to retrieve new file content of %s at version %s. Error: %s",
# file, # file,
@ -347,7 +347,7 @@ class AzureDevopsProvider(GitProvider):
) )
original_file_content_str = original_file_content_str.content original_file_content_str = original_file_content_str.content
except Exception as error: except Exception as error:
get_logger().error(f"Failed to retrieve original file content of {file} at version {version}. Error: {str(error)}") get_logger().error(f"Failed to retrieve original file content of {file} at version {version}", error=error)
original_file_content_str = "" original_file_content_str = ""
patch = load_large_diff( patch = load_large_diff(
@ -375,7 +375,7 @@ class AzureDevopsProvider(GitProvider):
self.diff_files = diff_files self.diff_files = diff_files
return diff_files return diff_files
except Exception as e: except Exception as e:
print(f"Error: {str(e)}") get_logger().exception(f"Failed to get diff files, error: {e}")
return [] return []
def publish_comment(self, pr_comment: str, is_temporary: bool = False, thread_context=None): def publish_comment(self, pr_comment: str, is_temporary: bool = False, thread_context=None):
@ -519,7 +519,6 @@ class AzureDevopsProvider(GitProvider):
def get_user_id(self): def get_user_id(self):
return 0 return 0
def get_issue_comments(self): def get_issue_comments(self):
threads = self.azure_devops_client.get_threads(repository_id=self.repo_slug, pull_request_id=self.pr_num, project=self.workspace_slug) threads = self.azure_devops_client.get_threads(repository_id=self.repo_slug, pull_request_id=self.pr_num, project=self.workspace_slug)
threads.reverse() threads.reverse()
@ -614,3 +613,6 @@ class AzureDevopsProvider(GitProvider):
get_logger().error(f"Failed to get pr id, error: {e}") get_logger().error(f"Failed to get pr id, error: {e}")
return "" return ""
def publish_file_comments(self, file_comments: list) -> bool:
pass

View File

@ -99,14 +99,14 @@ async def is_valid_notification(notification, headers, handled_ids, session, use
if not comment_body: if not comment_body:
get_logger().debug(f"no comment_body") get_logger().debug(f"no comment_body")
check_prev_comments = True check_prev_comments = True
commenter_github_user = comment['user']['login'] \ else:
if 'user' in comment else '' user_tag = "@" + user_id
get_logger().info(f"Polling, pr_url: {pr_url}", if user_tag not in comment_body:
artifact={"comment": comment_body}) get_logger().debug(f"user_tag not in comment_body")
user_tag = "@" + user_id check_prev_comments = True
if user_tag not in comment_body: else:
get_logger().debug(f"user_tag not in comment_body") get_logger().info(f"Polling, pr_url: {pr_url}",
check_prev_comments = True artifact={"comment": comment_body})
if not check_prev_comments: if not check_prev_comments:
return True, handled_ids, comment, comment_body, pr_url, user_tag return True, handled_ids, comment, comment_body, pr_url, user_tag
@ -125,6 +125,8 @@ async def is_valid_notification(notification, headers, handled_ids, session, use
continue continue
if user_tag in comment_body: if user_tag in comment_body:
get_logger().info("found user tag in previous comments") get_logger().info("found user tag in previous comments")
get_logger().info(f"Polling, pr_url: {pr_url}",
artifact={"comment": comment_body})
return True, handled_ids, comment, comment_body, pr_url, user_tag return True, handled_ids, comment, comment_body, pr_url, user_tag
get_logger().error(f"Failed to fetch comments for PR: {pr_url}") get_logger().error(f"Failed to fetch comments for PR: {pr_url}")
@ -188,6 +190,8 @@ async def polling_loop():
get_logger().info(f"Received {len(notifications)} notifications") get_logger().info(f"Received {len(notifications)} notifications")
task_queue = deque() task_queue = deque()
for notification in notifications: for notification in notifications:
if not notification:
continue
# mark notification as read # mark notification as read
await mark_notification_as_read(headers, notification, session) await mark_notification_as_read(headers, notification, session)
@ -204,7 +208,7 @@ async def polling_loop():
task_queue.append((process_comment_sync, (pr_url, rest_of_comment, comment_id))) task_queue.append((process_comment_sync, (pr_url, rest_of_comment, comment_id)))
get_logger().info(f"Queued comment processing for PR: {pr_url}") get_logger().info(f"Queued comment processing for PR: {pr_url}")
else: else:
get_logger().debug(f"Skipping comment processing for PR: {pr_url}") get_logger().debug(f"Skipping comment processing for PR")
max_allowed_parallel_tasks = 10 max_allowed_parallel_tasks = 10
if task_queue: if task_queue:

View File

@ -7,7 +7,7 @@ The format we will use to present the PR code diff:
====== ======
## File: 'src/file1.py' ## File: 'src/file1.py'
{%- if is_ai_metadata %} {%- if is_ai_metadata %}
### AI-generated file summary: ### AI-generated changes summary:
* ... * ...
* ... * ...
{%- endif %} {%- endif %}
@ -39,7 +39,7 @@ __old hunk__
- We also added line numbers for the '__new hunk__' code, to help you refer to the code lines in your suggestions. These line numbers are not part of the actual code, and should only used for reference. - We also added line numbers for the '__new hunk__' code, to help you refer to the code lines in your suggestions. These line numbers are not part of the actual code, and should only used for reference.
- Code lines are prefixed with symbols ('+', '-', ' '). The '+' symbol indicates new code added in the PR, the '-' symbol indicates code removed in the PR, and the ' ' symbol indicates unchanged code. \ - Code lines are prefixed with symbols ('+', '-', ' '). The '+' symbol indicates new code added in the PR, the '-' symbol indicates code removed in the PR, and the ' ' symbol indicates unchanged code. \
{%- if is_ai_metadata %} {%- if is_ai_metadata %}
- If available, an AI-generated summary will appear and provide a high-level overview of the file changes. - If available, an AI-generated summary will appear and provide a high-level overview of the file changes. Note that this summary may not be fully accurate or complete.
{%- endif %} {%- endif %}
Specific instructions for generating code suggestions: Specific instructions for generating code suggestions:
@ -131,7 +131,7 @@ The format we will use to present the PR code diff:
====== ======
## File: 'src/file1.py' ## File: 'src/file1.py'
{%- if is_ai_metadata %} {%- if is_ai_metadata %}
### AI-generated file summary: ### AI-generated changes summary:
* ... * ...
* ... * ...
{%- endif %} {%- endif %}
@ -163,7 +163,7 @@ __old hunk__
- We also added line numbers for the '__new hunk__' code, to help you refer to the code lines in your suggestions. These line numbers are not part of the actual code, and should only used for reference. - We also added line numbers for the '__new hunk__' code, to help you refer to the code lines in your suggestions. These line numbers are not part of the actual code, and should only used for reference.
- Code lines are prefixed with symbols ('+', '-', ' '). The '+' symbol indicates new code added in the PR, the '-' symbol indicates code removed in the PR, and the ' ' symbol indicates unchanged code. \ - Code lines are prefixed with symbols ('+', '-', ' '). The '+' symbol indicates new code added in the PR, the '-' symbol indicates code removed in the PR, and the ' ' symbol indicates unchanged code. \
{%- if is_ai_metadata %} {%- if is_ai_metadata %}
- If available, an AI-generated summary will appear and provide a high-level overview of the file changes. - If available, an AI-generated summary will appear and provide a high-level overview of the file changes. Note that this summary may not be fully accurate or complete.
{%- endif %} {%- endif %}
Specific instructions for generating code suggestions: Specific instructions for generating code suggestions:

View File

@ -12,7 +12,7 @@ The format we will use to present the PR code diff:
====== ======
## File: 'src/file1.py' ## File: 'src/file1.py'
{%- if is_ai_metadata %} {%- if is_ai_metadata %}
### AI-generated file summary: ### AI-generated changes summary:
* ... * ...
* ... * ...
{%- endif %} {%- endif %}
@ -46,7 +46,7 @@ __old hunk__
- Code lines are prefixed with symbols ('+', '-', ' '). The '+' symbol indicates new code added in the PR, the '-' symbol indicates code removed in the PR, and the ' ' symbol indicates unchanged code. \ - Code lines are prefixed with symbols ('+', '-', ' '). The '+' symbol indicates new code added in the PR, the '-' symbol indicates code removed in the PR, and the ' ' symbol indicates unchanged code. \
The review should address new code added in the PR code diff (lines starting with '+') The review should address new code added in the PR code diff (lines starting with '+')
{%- if is_ai_metadata %} {%- if is_ai_metadata %}
- If available, an AI-generated summary will appear and provide a high-level overview of the file changes. - If available, an AI-generated summary will appear and provide a high-level overview of the file changes. Note that this summary may not be fully accurate or complete.
{%- endif %} {%- endif %}
- When quoting variables or names from the code, use backticks (`) instead of single quote ('). - When quoting variables or names from the code, use backticks (`) instead of single quote (').