Skip to content
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

Issue #764: Add custom year #2107

Open
wants to merge 28 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 9 commits
Commits
Show all changes
28 commits
Select commit Hold shift + click to select a range
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
3 changes: 3 additions & 0 deletions api/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ export default async (req, res) => {
show_icons,
count_private,
include_all_commits,
year,
line_height,
title_color,
icon_color,
Expand Down Expand Up @@ -55,6 +56,7 @@ export default async (req, res) => {
parseBoolean(count_private),
parseBoolean(include_all_commits),
parseArray(exclude_repo),
parseInt(year),
);

const cacheSeconds = clampValue(
Expand All @@ -74,6 +76,7 @@ export default async (req, res) => {
card_width: parseInt(card_width, 10),
hide_rank: parseBoolean(hide_rank),
include_all_commits: parseBoolean(include_all_commits),
year: parseInt(year),
line_height,
title_color,
icon_color,
Expand Down
8 changes: 8 additions & 0 deletions readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,13 @@ You can add the count of all your private contributions to the total commits cou
![Anurag's GitHub stats](https://github-readme-stats.vercel.app/api?username=anuraghazra&count_private=true)
```

### Specifying Year

You can specify a year and fetch only the commits that were made in that year by passing `&year=YYYY` to the parameter.

```md
![Anurag's GitHub stats](https://github-readme-stats.vercel.app/api?username=anuraghazra&year=2020)
```
### Showing icons

To enable icons, you can pass `show_icons=true` in the query param, like so:
Expand Down Expand Up @@ -196,6 +203,7 @@ You can provide multiple comma-separated values in the bg_color option to render
- `custom_title` - Sets a custom title for the card. Default: `<username> Github Stats`.
- `text_bold` - Use bold text _(boolean)_. Default: `true`.
- `disable_animations` - Disables all animations in the card _(boolean)_. Default: `false`.
- `year` - Count commit of the entire year _(YYYY)_. Default: `<current year> (one year to date)`

> **Note**
> When hide_rank=`true`, the minimum card width is 270 px + the title length and padding.
Expand Down
7 changes: 6 additions & 1 deletion src/cards/stats-card.js
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,7 @@ const renderStatsCard = (stats = {}, options = { hide: [] }) => {
card_width,
hide_rank = false,
include_all_commits = false,
year,
line_height = 25,
title_color,
icon_color,
Expand Down Expand Up @@ -133,7 +134,11 @@ const renderStatsCard = (stats = {}, options = { hide: [] }) => {
commits: {
icon: icons.commits,
label: `${i18n.t("statcard.commits")}${
include_all_commits ? "" : ` (${new Date().getFullYear()})`
include_all_commits
? ""
: year
? ` (${year})`
: ` (${new Date().getFullYear()})`
}`,
value: totalCommits,
id: "commits",
Expand Down
1 change: 1 addition & 0 deletions src/cards/types.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ export type StatCardOptions = CommonOptions & {
card_width: number;
hide_rank: boolean;
include_all_commits: boolean;
year?: number;
line_height: number | string;
custom_title: string;
disable_animations: boolean;
Expand Down
11 changes: 8 additions & 3 deletions src/fetchers/stats-fetcher.js
Original file line number Diff line number Diff line change
Expand Up @@ -25,11 +25,11 @@ const fetcher = (variables, token) => {
return request(
{
query: `
query userInfo($login: String!) {
query userInfo($login: String!, $starttime: DateTime!) {
user(login: $login) {
name
login
contributionsCollection {
contributionsCollection(from: $starttime) {
totalCommitContributions
restrictedContributionsCount
}
Expand Down Expand Up @@ -186,13 +186,15 @@ const totalStarsFetcher = async (username, repoToHide) => {
* @param {string} username Github username.
* @param {boolean} count_private Include private contributions.
* @param {boolean} include_all_commits Include all commits.
* @param {number|undefined} year Year to count total commits
* @returns {Promise<import("./types").StatsData>} Stats data.
*/
async function fetchStats(
username,
count_private = false,
include_all_commits = false,
exclude_repo = [],
year,
) {
if (!username) throw new MissingParamError(["username"]);

Expand All @@ -206,7 +208,10 @@ async function fetchStats(
rank: { level: "C", score: 0 },
};

let res = await retryer(fetcher, { login: username });
let res = await retryer(fetcher, {
login: username,
starttime: year ? `${year}-01-01T00:00:00Z` : undefined
});

// Catch GraphQL errors.
if (res.data.errors) {
Expand Down
70 changes: 70 additions & 0 deletions tests/fetchStats.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -253,4 +253,74 @@ describe("Test fetchStats", () => {
rank,
});
});

it("should get present year commits when provide no year", async () => {
const data2003 = {...data, data:
{...data.data, user:
{...data.data.user, contributionsCollection: {
totalCommitContributions: 2003,
restrictedContributionsCount: 3,
}}}}
mock.onPost("https://api.github.com/graphql").reply((cfg) => {
if (cfg.data.includes("contributionsCollection(from: 2003-01-01T00:00:00Z)"))
return [200, data2003];
return [200, data];
});

let stats = await fetchStats("anuraghazra", true, false, []);
const rank = calculateRank({
totalCommits: 150,
totalRepos: 5,
followers: 100,
contributions: 61,
stargazers: 400,
prs: 300,
issues: 200,
});

expect(stats).toStrictEqual({
contributedTo: 61,
name: "Anurag Hazra",
totalCommits: 150,
totalIssues: 200,
totalPRs: 300,
totalStars: 400,
rank,
});
});

it("should get commits of provided year", async () => {
Copy link
Collaborator

Choose a reason for hiding this comment

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

I removed the other test, which tested whether the current year is returned when no year is supplied. I did this because this is already tested in:

it("should fetch correct stats", async () => {

it("should fetch total commits", async () => {

and

it("should fetch and add private contributions", async () => {

Copy link
Collaborator

@rickstaa rickstaa Oct 15, 2022

Choose a reason for hiding this comment

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

@anuraghazra, are you okay with this implicit testing, or do you want to have an explicit test like @vzsky did in

it("should get present year commits when provide no year", async () => {

Copy link
Author

Choose a reason for hiding this comment

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

I did that just to be sure that the mocked function works fine. I think deleting that is probably okay since the mocked function was tested and is not likely to get changed.

const data2003 = {...data, data:
{...data.data, user:
{...data.data.user, contributionsCollection: {
totalCommitContributions: 2003,
restrictedContributionsCount: 3,
}}}}
mock.onPost("https://api.github.com/graphql").reply((cfg) => {
if (cfg.data.includes(`"starttime":"2003-01-01T00:00:00Z"`))
return [200, data2003];
return [200, data];
});

let stats = await fetchStats("anuraghazra", true, false, [], 2003);
const rank = calculateRank({
totalCommits: 2006,
totalRepos: 5,
followers: 100,
contributions: 61,
stargazers: 400,
prs: 300,
issues: 200,
});

expect(stats).toStrictEqual({
contributedTo: 61,
name: "Anurag Hazra",
totalCommits: 2006,
totalIssues: 200,
totalPRs: 300,
totalStars: 400,
rank,
});
});
});