Repository: mozilla/bugbug

Issue:
Add number of previous commits touching the same files as a feature



Discussion:
I want to work on this issue. Can you please give me some references.
This is very similar to #113, removing `good first issue` as it's not so easy.
You're still welcome to work on this if you want, but it would require quite a bit of investigation and work.
With a962e0694bef08090bd6c4810e5c4c770154f99c, this is now easier to do (see https://github.com/mozilla/bugbug/issues/113#issuecomment-470744304).
* I still not quite sure what number we are putting here.  Should we put count for each file or as group of files?
* If one commit touching multiple files what would be scenario? How to add count for each file (sum all those up)?
> 
> I still not quite sure what number we are putting here. Should we put count for each file or as group of files?

We can try for each file and for each directory.

> If one commit touching multiple files what would be scenario? How to add count for each file (sum all those up)?

Each file has a different count. If a commit is touching multiple files, you increase the count by 1 for each file.
@sbeesm do you want to take this? It should be pretty similar to the one about components.
Sure, I'd like to work on this.

Do we also need to add files for previous 90 days, just like we did for components?
> Do we also need to add files for previous 90 days, just like we did for components?

Yes!

Resolving patch:
diff --git a/bugbug/repository.py b/bugbug/repository.py
--- a/bugbug/repository.py
+++ b/bugbug/repository.py
@@ -47,6 +47,9 @@
 components_touched_prev = defaultdict(int)
 components_touched_prev_90_days = defaultdict(int)
 
+files_touched_prev = defaultdict(int)
+files_touched_prev_90_days = defaultdict(int)
+
 
 def get_commits():
     return db.read(COMMITS_DB)
@@ -97,6 +100,8 @@ def _transform(commit):
         "author_email": commit.author_email.decode("utf-8"),
         "components_touched_prev": components_touched_prev[commit.node],
         "components_touched_prev_90_days": components_touched_prev_90_days[commit.node],
+        "files_touched_prev": files_touched_prev[commit.node],
+        "files_touched_prev_90_days": files_touched_prev_90_days[commit.node],
     }
 
     patch = HG.export(revs=[commit.node], git=True)
@@ -314,7 +319,11 @@ def download_commits(repo_dir, date_from):
     global components_touched_prev
     global components_touched_prev_90_days
 
+    global files_touched_prev
+    global files_touched_prev_90_days
+
     components_touched = defaultdict(int)
+    files_touched = defaultdict(int)
     prev_commits_90_days = []
     for commit in commits:
         components = set(
@@ -328,6 +337,11 @@ def download_commits(repo_dir, date_from):
 
             components_touched[component] += 1
 
+        for path in commit.files:
+            files_touched_prev[commit.node] += files_touched[path]
+
+            files_touched[path] += 1
+
         if len(commit.file_copies) > 0:
             for orig, copied in commit.file_copies.items():
                 if orig in path_to_component and copied in path_to_component:
@@ -335,6 +349,8 @@ def download_commits(repo_dir, date_from):
                         path_to_component[orig]
                     ]
 
+                files_touched[copied] = files_touched[orig]
+
         for i, prev_commit in enumerate(prev_commits_90_days):
             if (commit.date - prev_commit.date).days <= 90:
                 break
@@ -345,6 +361,7 @@ def download_commits(repo_dir, date_from):
             prev_commits_90_days = prev_commits_90_days[cut + 1 :]
 
         components_touched_90_days = defaultdict(int)
+        files_touched_90_days = defaultdict(int)
         for prev_commit in prev_commits_90_days:
             components_prev = set(
                 path_to_component[path]
@@ -355,6 +372,9 @@ def download_commits(repo_dir, date_from):
             for component_prev in components_prev:
                 components_touched_90_days[component_prev] += 1
 
+            for path_prev in prev_commit.files:
+                files_touched_90_days[path_prev] += 1
+
             if len(prev_commit.file_copies) > 0:
                 for orig, copied in prev_commit.file_copies.items():
                     if orig in path_to_component and copied in path_to_component:
@@ -362,9 +382,14 @@ def download_commits(repo_dir, date_from):
                             path_to_component[copied]
                         ] = components_touched_90_days[path_to_component[orig]]
 
+                    files_touched_90_days[copied] = files_touched_90_days[orig]
+
         components_touched_prev_90_days[commit.node] = sum(
             components_touched_90_days[component] for component in components
         )
+        files_touched_prev_90_days[commit.node] = sum(
+            files_touched_90_days[path] for path in commit.files
+        )
         prev_commits_90_days.append(commit)
 
     print(f"Mining commits using {multiprocessing.cpu_count()} processes...")


Test patch: