Skip to content
Open
Show file tree
Hide file tree
Changes from 1 commit
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
4 changes: 3 additions & 1 deletion ENV_SAMPLE
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
REPO_OWNER="Git-Commit-Show"
GITHUB_PERSONAL_TOKEN="ghp_adsfdsf32sdfasdfcdcsdfsdf23sfasdf1"
GITHUB_PERSONAL_TOKEN="ghp_adsfdsf32sdfasdfcdcsdfsdf23sfasdf1"
APERTURE_SERVICE_ADDRESS="my.app.fluxninja.com:443"
APERTURE_API_KEY="4dsfs323db7dsfsde310ca6dsdf12sfr4"
53 changes: 52 additions & 1 deletion contributors.js → github.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/**
* @file Functions to analyze and archive meaningful github contributors data
* @file Functions to analyze and archive meaningful github data such as contributors
* @example To archive contributors leaderboard data in csv file, run `node contributors.js`
*/

Expand Down Expand Up @@ -210,4 +210,55 @@ export async function archiveContributorsLeaderboard(owner=REPO_OWNER, options)
writeContributorLeaderboardToFile(contributors);

return ghHandles;
}

/**
* Search pull requests
* @param {string} query
* @param {Object} options Additional options e.g. { pageNo: 1 }
*/
export async function searchPullRequests(query, options) {
let pageNo = (options && options.pageNo) ? options.pageNo : 1;
if(options && options.GITHUB_PERSONAL_TOKEN){
GITHUB_REQUEST_OPTIONS.headers["Authorization"] = "token "+options.GITHUB_PERSONAL_TOKEN;
}
let queryString = encodeURIComponent(''+query+'type:pr')
let url = `https://api.github.com/search/issues?q=${queryString}&per_page=100&page=${pageNo}&sort=${options.sort || 'created'}`;
const { res, data } = await makeRequestWithRateLimit('GET', url, Object.assign({},GITHUB_REQUEST_OPTIONS));
console.log("PR search request finished");
console.log('HTTP status: ', res.statusCode);
// console.log(data)
let searchResultObject = JSON.parse(data);
return searchResultObject;
}

/**
* Get all search results, not just one page
* @param {string} query
* @param {Object} options
* @param {Object} options.maxResults limit maximum results
*/
export async function recursiveSearchPullRequests(query, options){
let prList = [];
let pageNo = 1;
let maxResults = options.maxResults || 10000;
let searchResultObject = await searchPullRequests(query, Object.assign({ pageNo: pageNo }, options));
// Iterate over results if there are more results expected by the user
if(!searchResultObject || !searchResultObject.items || !searchResultObject.items.length<1 || maxResults < 100){
return prList;
}
prList.push(searchResultObject.items);
let incomplete_results = searchResultObject.incomplete_results;
while(prList.length < searchResultObject.total_count && !incomplete_results){
pageNo++;
try {
let nextPageSearchResultObject = await searchPullRequests(query, { pageNo: pageNo } );
prList.push(...nextPageSearchResultObject.items);
incomplete_results = nextPageSearchResultObject.incomplete_results;
} catch (err) {
console.log("Some issue in recursive search for pull requests")
}
}
console.log("Found "+prList.length +" PRs"+" for "+query);
return prList;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In the recursiveSearchPullRequests function, the condition !searchResultObject.items.length<1 seems to be incorrect due to operator precedence. It should be !(searchResultObject.items.length < 1) or searchResultObject.items.length >= 1.

- if(!searchResultObject || !searchResultObject.items || !searchResultObject.items.length<1 || maxResults < 100){
+ if(!searchResultObject || !searchResultObject.items || !(searchResultObject.items.length >= 1) || maxResults < 100){

Additionally, the function does not handle the case where maxResults is less than the total number of pull requests available. It should stop fetching more pages when the maxResults limit is reached.


Committable suggestion

IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation.

Suggested change
/**
* Get all search results, not just one page
* @param {string} query
* @param {Object} options
* @param {Object} options.maxResults limit maximum results
*/
export async function recursiveSearchPullRequests(query, options){
let prList = [];
let pageNo = 1;
let maxResults = options.maxResults || 10000;
let searchResultObject = await searchPullRequests(query, Object.assign({ pageNo: pageNo }, options));
// Iterate over results if there are more results expected by the user
if(!searchResultObject || !searchResultObject.items || !searchResultObject.items.length<1 || maxResults < 100){
return prList;
}
prList.push(searchResultObject.items);
let incomplete_results = searchResultObject.incomplete_results;
while(prList.length < searchResultObject.total_count && !incomplete_results){
pageNo++;
try {
let nextPageSearchResultObject = await searchPullRequests(query, { pageNo: pageNo } );
prList.push(...nextPageSearchResultObject.items);
incomplete_results = nextPageSearchResultObject.incomplete_results;
} catch (err) {
console.log("Some issue in recursive search for pull requests")
}
}
console.log("Found "+prList.length +" PRs"+" for "+query);
return prList;
/**
* Get all search results, not just one page
* @param {string} query
* @param {Object} options
* @param {Object} options.maxResults limit maximum results
*/
export async function recursiveSearchPullRequests(query, options){
let prList = [];
let pageNo = 1;
let maxResults = options.maxResults || 10000;
let searchResultObject = await searchPullRequests(query, Object.assign({ pageNo: pageNo }, options));
// Iterate over results if there are more results expected by the user
if(!searchResultObject || !searchResultObject.items || !(searchResultObject.items.length >= 1) || maxResults < 100){
return prList;
}
prList.push(searchResultObject.items);
let incomplete_results = searchResultObject.incomplete_results;
while(prList.length < searchResultObject.total_count && !incomplete_results && prList.length < maxResults){
pageNo++;
try {
let nextPageSearchResultObject = await searchPullRequests(query, { pageNo: pageNo } );
prList.push(...nextPageSearchResultObject.items);
incomplete_results = nextPageSearchResultObject.incomplete_results;
} catch (err) {
console.log("Some issue in recursive search for pull requests")
}
}
console.log("Found "+prList.length +" PRs"+" for "+query);
return prList;
}

}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Missing newline at the end of the file.

+ \n

Committable suggestion

IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation.

Suggested change
}
}

2 changes: 1 addition & 1 deletion index.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import * as contributorsLib from './contributors.js';
import * as contributorsLib from './github.js';

/**
* Bundling all APIs together
Comment on lines +1 to 4
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 NOTE
Codebase verification is a beta feature.

The github.js file is present in the codebase, as confirmed by the output of the fd command. However, both the ast-grep and rg commands did not find the archiveContributorsLeaderboard function within this file. This suggests that the function is not exported from github.js, which could potentially lead to issues where it is expected to be used.

Final response to the review comment:

The archiveContribitorsLeaderboard function does not appear to be present or exported from github.js. This could lead to issues in index.js where the function is expected to be available. It is recommended to verify the presence and correct export of this function within github.js to ensure the proper functionality of the APIs that depend on it.

  • The archiveContribitorsLeaderboard function is not found in github.js.
Analysis chain

Note: This review was outside the patches, so it was mapped to the patch with the greatest overlap. Original lines [1-14]

Verify that the archiveContributorsLeaderboard function is still available and correctly exported from github.js after the file renaming, as it is being used here.


Given the warning from ast-grep and the possibility that the function could be exported in a different manner than the pattern I used, I will write a new script using ripgrep (rg) to search for the string archiveContributorsLeaderboard within github.js to verify if it is present and exported.


Before concluding, I will verify the presence of the github.js file to ensure that the file exists and is located where expected. This will help to confirm that the absence of the function archiveContribitorsLeaderboard is not due to the file not being found.

Scripts Executed

The following scripts were executed for the analysis:


Script:

#!/bin/bash
# Search for the export of `archiveContributorsLeaderboard` in `github.js`.
ast-grep --lang javascript --pattern $'export function archiveContributorsLeaderboard($_, $_)'

Length of output: 440



Script:

#!/bin/bash
# Search for the string 'archiveContributorsLeaderboard' in 'github.js' to verify if it is present and exported.
rg 'archiveContribitorsLeaderboard' --files-with-matches

Length of output: 56



Script:

#!/bin/bash
# Verify the presence of the `github.js` file in the codebase.
fd 'github.js'

Length of output: 24

Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
"name": "open-community-kit",
"version": "1.2.1",
"description": "Tools and stats for open-source communities",
"main": "contributors.js",
"main": "index.js",
"type": "module",
"bin": {
"ock": "cli.js",
Expand Down
4 changes: 4 additions & 0 deletions test/fixtures/pullRequests.fixture.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
export const PR_SEARCH_QUERY = "gitcommitshow";
export const VALID_SEARCH_RESULT_SAMPLE = {

}
40 changes: 35 additions & 5 deletions test/contributors.test.js → test/github.test.js
Original file line number Diff line number Diff line change
@@ -1,16 +1,17 @@
import { expect, assert } from "chai";
import * as contributorsLib from "../contributors.js";
import * as githubApi from "../github.js";

import * as contributorsFixture from './fixtures/contributors.fixture.js';
import * as pullRequestsFixture from './fixtures/pullRequests.fixture.js';

describe('contibutors.js', function() {
describe('github.js', function() {

/** GitHub contrbutors test --START-- */

describe.skip('#getAllRepos('+contributorsFixture.VALID_REPO_OWNER+');', async function() {
it('should return the repos owned by '+contributorsFixture.VALID_REPO_OWNER, async function() {
this.timeout(100000);
let repos = await contributorsLib.getAllRepos(contributorsFixture.VALID_REPO_OWNER);
let repos = await githubApi.getAllRepos(contributorsFixture.VALID_REPO_OWNER);
assert.isNotNull(repos);
expect(repos).to.be.an('array', 'Not an array')
expect(repos.length).to.be.greaterThanOrEqual(contributorsFixture.REPO_COUNT_MIN);
Expand All @@ -21,7 +22,7 @@ describe('contibutors.js', function() {
describe.skip('#getRepoContributors('+contributorsFixture.VALID_REPO+');', async function() {
it('should return the repo contribuors', async function() {
this.timeout(100000);
let contributors = await contributorsLib.getRepoContributors(contributorsFixture.VALID_REPO)
let contributors = await githubApi.getRepoContributors(contributorsFixture.VALID_REPO)
assert.isNotNull(contributors);
expect(contributors).to.be.an('array', 'Not an array')
expect(contributors.length).to.be.greaterThanOrEqual(contributorsFixture.REPO_CONTRIBUTOR_COUNT_MIN);
Expand All @@ -32,12 +33,41 @@ describe('contibutors.js', function() {
describe.skip('#getAllContributors('+contributorsFixture.VALID_REPO_OWNER+');', async function() {
it('should return all contributors across different repositories of REPO_OWNER', async function() {
this.timeout(100000);
let contributors = await contributorsLib.getAllContributors(contributorsFixture.VALID_REPO_OWNER);
let contributors = await githubApi.getAllContributors(pullRequestsFixture.QUERY);
assert.isNotNull(contributors);
expect(contributors).to.be.an('array', 'Not an array')
expect(contributors.length).to.be.greaterThanOrEqual(contributorsFixture.ALL_REPO_CONTRIBUTOR_COUNT_MIN);
expect(contributors[0]).to.include.all.keys('login','id','node_id','avatar_url','gravatar_id','url','html_url','followers_url','following_url','gists_url','starred_url','subscriptions_url','organizations_url','repos_url','events_url','received_events_url','type','site_admin','contributions');
})
})

// OCK PR search test
describe.skip('#OCK.github.searchPullRequests(query, options);', async function() {
it('should start the task of archiving contributors for REPO_OWNER', async function() {
Copy link
Contributor

@coderabbitai coderabbitai bot Dec 15, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The test case descriptions mention "archiving contributors," which does not align with the pull request search functionality being tested. Update the descriptions to accurately reflect the tests.

Also applies to: 60-60

Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@coderabbitai can you create an issue for this task

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 NOTE
Deep insights is a beta feature.

@gitcommitshow An issue has been created to address the task of updating test case descriptions in test/github.test.js. You can view and track the progress of this issue at the following link: Update Test Descriptions for PR Search Functionality.

Analysis chain
Scripts executed

The following scripts were executed for the analysis:


Script:

#!/bin/bash
# Create an issue for updating test case descriptions in test/github.test.js

gh issue create --title "Update Test Descriptions for PR Search Functionality" --body "The test case descriptions in `test/github.test.js` currently mention 'archiving contributors,' which is not accurate for the pull request search functionality tests. These descriptions need to be updated to reflect the actual tests being performed."

Length of output: 496


If you found this review helpful, would you consider giving us a shout-out on X?
Thank you for using CodeRabbit!

this.timeout(100000);
let prSearchResults = await githubApi.searchPullRequests(pullRequestsFixture.PR_SEARCH_QUERY);
assert.isNotNull(prSearchResults, "No PR search results returned");
expect(prSearchResults).to.be.an('object');
expect(prSearchResults).to.have.all.keys('items', 'total_count', 'incomplete_results');
expect(prSearchResults.items).to.be.an('array');
expect(prSearchResults.items).to.have.lengthOf.at.least(1);
expect(prSearchResults.items[0]).to.include.all.keys('title', 'html_url', 'state', 'user', 'draft', 'repository_url', 'comments', 'comments_url', 'assignees', 'created_at', 'closed_at');
})
})
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Duplicate describe block for searchPullRequests with and without .skip. This seems like an error. Confirm if both are necessary or if one should be removed.

Also applies to: 58-59


// OCK PR search test
describe('#OCK.github.searchPullRequests(query, options);', async function() {
it('should start the task of archiving contributors for REPO_OWNER', async function() {
this.timeout(100000);
let prResults = await githubApi.recursiveSearchPullRequests("test", { maxResults: 198});
assert.isNotNull(prResults, "No PR search results returned");
expect(prResults).to.be.an('array');
expect(prResults).to.have.lengthOf.at.least(198);
expect(prResults).to.have.lengthOf.at.most(200);
expect(prResults[0]).to.include.all.keys('title', 'html_url', 'state', 'user', 'draft', 'repository_url', 'comments', 'comments_url', 'assignees', 'created_at', 'closed_at');
})
})



})
2 changes: 1 addition & 1 deletion test/index.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ describe('index.js', function() {
/** GitHub contrbutors test --START-- */

// OCK contributor test
describe('#OCK.contributors.github.archive(REPO_OWNER, options);', async function() {
describe.skip('#OCK.contributors.github.archive(REPO_OWNER, options);', async function() {
it('should start the task of archiving contributors for REPO_OWNER', async function() {
this.timeout(100000);
let contributorsHandlesArray = await OCK.contributors.github.archive(contributorsFixture.VALID_REPO_OWNER);
Expand Down