diff --git a/app/src/js/modules/events.js b/app/src/js/modules/events.js index dd716f5c50..dae4fb623b 100644 --- a/app/src/js/modules/events.js +++ b/app/src/js/modules/events.js @@ -1,10 +1,9 @@ import { sortDirection, sortSelection, parsedProjectsData } from "./data"; -import { updateFilters } from "./filters"; +import { getFilteredProjects, setFilteredProjects, updateFilters, updateFilteredProjects } from "./filters"; import { sortCards } from "./sorting"; -import { createProjectCards } from "./rendering"; +import { renderPaginatedProjects } from "./rendering"; let currentPage; -let filteredProjects = [...parsedProjectsData]; export function setupEventListeners() { sortSelection.addEventListener('change', () => sortCards()); @@ -34,9 +33,15 @@ document.addEventListener("DOMContentLoaded", () => { searchBox.addEventListener("input", () => { const query = searchBox.value.toLowerCase(); - filteredProjects = parsedProjectsData.filter((project) => project.name.toLowerCase().includes(query.toLowerCase())); - currentPage = 1 - createProjectCards() + if(query === '') { + updateFilteredProjects(); + } else { + const newFilteredProjects = parsedProjectsData.filter((project) => + project.name.toLowerCase().includes(query.toLowerCase()) + ); + setFilteredProjects(newFilteredProjects) + currentPage = 1 + renderPaginatedProjects(getFilteredProjects()); + } }) - createProjectCards() -}) \ No newline at end of file +}); \ No newline at end of file diff --git a/app/src/js/modules/filters.js b/app/src/js/modules/filters.js index 9cebb903cd..670fffc9b0 100644 --- a/app/src/js/modules/filters.js +++ b/app/src/js/modules/filters.js @@ -4,7 +4,16 @@ import { renderPaginatedProjects, renderPaginationControls } from "./rendering"; import { sortCards } from "./sorting"; -export let filteredProjects = [...parsedProjectsData]; +let filteredProjects = [...parsedProjectsData]; + +export function getFilteredProjects() { + return filteredProjects; +} + +export function setFilteredProjects(projects) { + filteredProjects = projects; +} + let currentPage = 1 const itemsPerPage = 10; diff --git a/app/src/js/modules/rendering.js b/app/src/js/modules/rendering.js index 9f7e377e9e..7f774ccc20 100644 --- a/app/src/js/modules/rendering.js +++ b/app/src/js/modules/rendering.js @@ -1,6 +1,6 @@ import { reportHeadingTemplate, projectCardTemplate } from "../templates"; import { templateDiv, parsedProjectsData, orgsData, siteData, findObject, baseurl } from "./data"; -import { updateFilters } from "./filters"; +import { getFilteredProjects, updateFilters } from "./filters"; import { getPageRange, updateHeadingVisibility } from "./utilities"; import DOMPurify from 'dompurify'; @@ -9,11 +9,10 @@ const parsedOrgsData = orgsData let currentPage = 1 const itemsPerPage = 10; -export function createProjectCards() { - let filteredProjects = [...parsedProjectsData]; +export function createProjectCards(projects = getFilteredProjects()) { templateDiv.innerHTML = '' - const allProjects = (filteredProjects || parsedProjectsData).map((project) => ({ + const allProjects = (projects || parsedProjectsData).map((project) => ({ ...project, org: project.owner })); diff --git a/node_modules/.package-lock.json b/node_modules/.package-lock.json deleted file mode 100644 index 0a9d0a1db1..0000000000 --- a/node_modules/.package-lock.json +++ /dev/null @@ -1,24 +0,0 @@ -{ - "name": "metrics", - "lockfileVersion": 3, - "requires": true, - "packages": { - "node_modules/@types/dompurify": { - "version": "3.0.5", - "resolved": "https://registry.npmjs.org/@types/dompurify/-/dompurify-3.0.5.tgz", - "integrity": "sha512-1Wg0g3BtQF7sSb27fJQAKck1HECM6zV1EB66j8JH9i3LCjYabJa0FSdiSgsD5K/RbrsR0SiraKacLB+T8ZVYAg==", - "dev": true, - "license": "MIT", - "dependencies": { - "@types/trusted-types": "*" - } - }, - "node_modules/@types/trusted-types": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/@types/trusted-types/-/trusted-types-2.0.7.tgz", - "integrity": "sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==", - "dev": true, - "license": "MIT" - } - } -} diff --git a/node_modules/@types/dompurify/LICENSE b/node_modules/@types/dompurify/LICENSE deleted file mode 100644 index 9e841e7a26..0000000000 --- a/node_modules/@types/dompurify/LICENSE +++ /dev/null @@ -1,21 +0,0 @@ - MIT License - - Copyright (c) Microsoft Corporation. - - Permission is hereby granted, free of charge, to any person obtaining a copy - of this software and associated documentation files (the "Software"), to deal - in the Software without restriction, including without limitation the rights - to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - copies of the Software, and to permit persons to whom the Software is - furnished to do so, subject to the following conditions: - - The above copyright notice and this permission notice shall be included in all - copies or substantial portions of the Software. - - THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - SOFTWARE diff --git a/node_modules/@types/dompurify/README.md b/node_modules/@types/dompurify/README.md deleted file mode 100644 index 2f37ebb19c..0000000000 --- a/node_modules/@types/dompurify/README.md +++ /dev/null @@ -1,16 +0,0 @@ -# Installation -> `npm install --save @types/dompurify` - -# Summary -This package contains type definitions for dompurify (https://github.com/cure53/DOMPurify). - -# Details -Files were exported from https://github.com/DefinitelyTyped/DefinitelyTyped/tree/master/types/dompurify. - -### Additional Details - * Last updated: Mon, 06 Nov 2023 22:41:05 GMT - * Dependencies: [@types/trusted-types](https://npmjs.com/package/@types/trusted-types) - -# Credits -These definitions were written by [Dave Taylor https://github.com/davetayls -// Samira Bazuzi](https://github.com/bazuzi), [FlowCrypt](https://github.com/FlowCrypt), [Exigerr](https://github.com/Exigerr), [Piotr Błażejewicz](https://github.com/peterblazejewicz), and [Nicholas Ellul](https://github.com/NicholasEllul). diff --git a/node_modules/@types/dompurify/index.d.ts b/node_modules/@types/dompurify/index.d.ts deleted file mode 100644 index ad6491f374..0000000000 --- a/node_modules/@types/dompurify/index.d.ts +++ /dev/null @@ -1,138 +0,0 @@ -/// - -export as namespace DOMPurify; -export = DOMPurify; - -declare const DOMPurify: createDOMPurifyI; - -type WindowLike = Pick< - typeof globalThis, - | "NodeFilter" - | "Node" - | "Element" - | "HTMLTemplateElement" - | "DocumentFragment" - | "HTMLFormElement" - | "DOMParser" - | "NamedNodeMap" ->; - -interface createDOMPurifyI extends DOMPurify.DOMPurifyI { - (window?: Window | WindowLike): DOMPurify.DOMPurifyI; -} - -declare namespace DOMPurify { - interface DOMPurifyI { - sanitize(source: string | Node): string; - sanitize(source: string | Node, config: Config & { RETURN_TRUSTED_TYPE: true }): TrustedHTML; - sanitize( - source: string | Node, - config: Config & { RETURN_DOM_FRAGMENT?: false | undefined; RETURN_DOM?: false | undefined }, - ): string; - sanitize(source: string | Node, config: Config & { RETURN_DOM_FRAGMENT: true }): DocumentFragment; - sanitize(source: string | Node, config: Config & { RETURN_DOM: true }): HTMLElement; - sanitize(source: string | Node, config: Config): string | HTMLElement | DocumentFragment; - - addHook( - hook: "uponSanitizeElement", - cb: (currentNode: Element, data: SanitizeElementHookEvent, config: Config) => void, - ): void; - addHook( - hook: "uponSanitizeAttribute", - cb: (currentNode: Element, data: SanitizeAttributeHookEvent, config: Config) => void, - ): void; - addHook(hook: HookName, cb: (currentNode: Element, data: HookEvent, config: Config) => void): void; - - setConfig(cfg: Config): void; - clearConfig(): void; - isValidAttribute(tag: string, attr: string, value: string): boolean; - - removeHook(entryPoint: HookName): void; - removeHooks(entryPoint: HookName): void; - removeAllHooks(): void; - - version: string; - removed: any[]; - isSupported: boolean; - } - - interface Config { - ADD_ATTR?: string[] | undefined; - ADD_DATA_URI_TAGS?: string[] | undefined; - ADD_TAGS?: string[] | undefined; - ADD_URI_SAFE_ATTR?: string[] | undefined; - ALLOW_ARIA_ATTR?: boolean | undefined; - ALLOW_DATA_ATTR?: boolean | undefined; - ALLOW_UNKNOWN_PROTOCOLS?: boolean | undefined; - ALLOW_SELF_CLOSE_IN_ATTR?: boolean | undefined; - ALLOWED_ATTR?: string[] | undefined; - ALLOWED_TAGS?: string[] | undefined; - ALLOWED_NAMESPACES?: string[] | undefined; - ALLOWED_URI_REGEXP?: RegExp | undefined; - FORBID_ATTR?: string[] | undefined; - FORBID_CONTENTS?: string[] | undefined; - FORBID_TAGS?: string[] | undefined; - FORCE_BODY?: boolean | undefined; - IN_PLACE?: boolean | undefined; - KEEP_CONTENT?: boolean | undefined; - /** - * change the default namespace from HTML to something different - */ - NAMESPACE?: string | undefined; - PARSER_MEDIA_TYPE?: string | undefined; - RETURN_DOM_FRAGMENT?: boolean | undefined; - /** - * This defaults to `true` starting DOMPurify 2.2.0. Note that setting it to `false` - * might cause XSS from attacks hidden in closed shadowroots in case the browser - * supports Declarative Shadow: DOM https://web.dev/declarative-shadow-dom/ - */ - RETURN_DOM_IMPORT?: boolean | undefined; - RETURN_DOM?: boolean | undefined; - RETURN_TRUSTED_TYPE?: boolean | undefined; - SAFE_FOR_TEMPLATES?: boolean | undefined; - SANITIZE_DOM?: boolean | undefined; - /** @default false */ - SANITIZE_NAMED_PROPS?: boolean | undefined; - USE_PROFILES?: - | false - | { - mathMl?: boolean | undefined; - svg?: boolean | undefined; - svgFilters?: boolean | undefined; - html?: boolean | undefined; - } - | undefined; - WHOLE_DOCUMENT?: boolean | undefined; - CUSTOM_ELEMENT_HANDLING?: { - tagNameCheck?: RegExp | ((tagName: string) => boolean) | null | undefined; - attributeNameCheck?: RegExp | ((lcName: string) => boolean) | null | undefined; - allowCustomizedBuiltInElements?: boolean | undefined; - }; - } - - type HookName = - | "beforeSanitizeElements" - | "uponSanitizeElement" - | "afterSanitizeElements" - | "beforeSanitizeAttributes" - | "uponSanitizeAttribute" - | "afterSanitizeAttributes" - | "beforeSanitizeShadowDOM" - | "uponSanitizeShadowNode" - | "afterSanitizeShadowDOM"; - - type HookEvent = SanitizeElementHookEvent | SanitizeAttributeHookEvent | null; - - interface SanitizeElementHookEvent { - tagName: string; - allowedTags: { [key: string]: boolean }; - } - - interface SanitizeAttributeHookEvent { - attrName: string; - attrValue: string; - keepAttr: boolean; - allowedAttributes: { [key: string]: boolean }; - forceKeepAttr?: boolean | undefined; - } -} diff --git a/node_modules/@types/dompurify/package.json b/node_modules/@types/dompurify/package.json deleted file mode 100644 index 6bc833b8c6..0000000000 --- a/node_modules/@types/dompurify/package.json +++ /dev/null @@ -1,47 +0,0 @@ -{ - "name": "@types/dompurify", - "version": "3.0.5", - "description": "TypeScript definitions for dompurify", - "homepage": "https://github.com/DefinitelyTyped/DefinitelyTyped/tree/master/types/dompurify", - "license": "MIT", - "contributors": [ - { - "name": "Dave Taylor https://github.com/davetayls\n// Samira Bazuzi", - "githubUsername": "bazuzi", - "url": "https://github.com/bazuzi" - }, - { - "name": "FlowCrypt", - "githubUsername": "FlowCrypt", - "url": "https://github.com/FlowCrypt" - }, - { - "name": "Exigerr", - "githubUsername": "Exigerr", - "url": "https://github.com/Exigerr" - }, - { - "name": "Piotr Błażejewicz", - "githubUsername": "peterblazejewicz", - "url": "https://github.com/peterblazejewicz" - }, - { - "name": "Nicholas Ellul", - "githubUsername": "NicholasEllul", - "url": "https://github.com/NicholasEllul" - } - ], - "main": "", - "types": "index.d.ts", - "repository": { - "type": "git", - "url": "https://github.com/DefinitelyTyped/DefinitelyTyped.git", - "directory": "types/dompurify" - }, - "scripts": {}, - "dependencies": { - "@types/trusted-types": "*" - }, - "typesPublisherContentHash": "f5501a1d31d5a7b2456704b3053c1c60efe0758bea38b4c3dbe3bd530638506e", - "typeScriptVersion": "4.5" -} \ No newline at end of file diff --git a/node_modules/@types/trusted-types/LICENSE b/node_modules/@types/trusted-types/LICENSE deleted file mode 100644 index 9e841e7a26..0000000000 --- a/node_modules/@types/trusted-types/LICENSE +++ /dev/null @@ -1,21 +0,0 @@ - MIT License - - Copyright (c) Microsoft Corporation. - - Permission is hereby granted, free of charge, to any person obtaining a copy - of this software and associated documentation files (the "Software"), to deal - in the Software without restriction, including without limitation the rights - to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - copies of the Software, and to permit persons to whom the Software is - furnished to do so, subject to the following conditions: - - The above copyright notice and this permission notice shall be included in all - copies or substantial portions of the Software. - - THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - SOFTWARE diff --git a/node_modules/@types/trusted-types/README.md b/node_modules/@types/trusted-types/README.md deleted file mode 100644 index fb376e7903..0000000000 --- a/node_modules/@types/trusted-types/README.md +++ /dev/null @@ -1,15 +0,0 @@ -# Installation -> `npm install --save @types/trusted-types` - -# Summary -This package contains type definitions for trusted-types (https://github.com/WICG/trusted-types). - -# Details -Files were exported from https://github.com/DefinitelyTyped/DefinitelyTyped/tree/master/types/trusted-types. - -### Additional Details - * Last updated: Mon, 20 Nov 2023 23:36:24 GMT - * Dependencies: none - -# Credits -These definitions were written by [Jakub Vrana](https://github.com/vrana), [Damien Engels](https://github.com/engelsdamien), [Emanuel Tesar](https://github.com/siegrift), [Bjarki](https://github.com/bjarkler), and [Sebastian Silbermann](https://github.com/eps1lon). diff --git a/node_modules/@types/trusted-types/index.d.ts b/node_modules/@types/trusted-types/index.d.ts deleted file mode 100644 index 18ab043a3e..0000000000 --- a/node_modules/@types/trusted-types/index.d.ts +++ /dev/null @@ -1,53 +0,0 @@ -import * as lib from "./lib"; - -// Re-export the type definitions globally. -declare global { - // eslint-disable-next-line @typescript-eslint/no-empty-interface -- interface to allow module augmentation - interface TrustedHTML extends lib.TrustedHTML {} - // eslint-disable-next-line @typescript-eslint/no-empty-interface -- interface to allow module augmentation - interface TrustedScript extends lib.TrustedScript {} - // eslint-disable-next-line @typescript-eslint/no-empty-interface -- interface to allow module augmentation - interface TrustedScriptURL extends lib.TrustedScriptURL {} - - // eslint-disable-next-line @typescript-eslint/no-empty-interface -- interface to allow module augmentation - interface TrustedTypePolicy extends lib.TrustedTypePolicy {} - - // eslint-disable-next-line @typescript-eslint/no-empty-interface -- interface to allow module augmentation - interface TrustedTypePolicyFactory extends lib.TrustedTypePolicyFactory {} - - // eslint-disable-next-line @typescript-eslint/no-empty-interface -- interface to allow module augmentation - interface TrustedTypePolicyOptions extends lib.TrustedTypePolicyOptions {} - - // Attach the relevant Trusted Types properties to the Window object. - // eslint-disable-next-line @typescript-eslint/no-empty-interface -- interface to allow module augmentation - interface Window extends lib.TrustedTypesWindow {} -} - -// These are the available exports when using the polyfill as npm package (e.g. in nodejs) -interface InternalTrustedTypePolicyFactory extends lib.TrustedTypePolicyFactory { - TrustedHTML: typeof lib.TrustedHTML; - TrustedScript: typeof lib.TrustedScript; - TrustedScriptURL: typeof lib.TrustedScriptURL; -} - -declare const trustedTypes: InternalTrustedTypePolicyFactory; - -declare class TrustedTypesEnforcer { - constructor(config: TrustedTypeConfig); - install: () => void; - uninstall: () => void; -} - -// tslint:disable-next-line no-unnecessary-class -declare class TrustedTypeConfig { - constructor( - isLoggingEnabled: boolean, - isEnforcementEnabled: boolean, - allowedPolicyNames: string[], - allowDuplicates: boolean, - cspString?: string | null, - windowObject?: Window, - ); -} - -export { TrustedTypeConfig, TrustedTypePolicy, TrustedTypePolicyFactory, trustedTypes, TrustedTypesEnforcer }; diff --git a/node_modules/@types/trusted-types/lib/index.d.ts b/node_modules/@types/trusted-types/lib/index.d.ts deleted file mode 100644 index 2c7ccd4b80..0000000000 --- a/node_modules/@types/trusted-types/lib/index.d.ts +++ /dev/null @@ -1,64 +0,0 @@ -// The main type definitions. Packages that do not want to pollute the global -// scope with Trusted Types (e.g. libraries whose users may not be using Trusted -// Types) can import the types directly from 'trusted-types/lib'. - -export type FnNames = keyof TrustedTypePolicyOptions; -export type Args = Parameters>; - -export class TrustedHTML { - private constructor(); // To prevent instantiting with 'new'. - private brand: true; // To prevent structural typing. -} - -export class TrustedScript { - private constructor(); // To prevent instantiting with 'new'. - private brand: true; // To prevent structural typing. -} - -export class TrustedScriptURL { - private constructor(); // To prevent instantiting with 'new'. - private brand: true; // To prevent structural typing. -} - -export abstract class TrustedTypePolicyFactory { - createPolicy( - policyName: string, - policyOptions?: Options, - ): Pick, "name" | Extract>; - isHTML(value: unknown): value is TrustedHTML; - isScript(value: unknown): value is TrustedScript; - isScriptURL(value: unknown): value is TrustedScriptURL; - readonly emptyHTML: TrustedHTML; - readonly emptyScript: TrustedScript; - getAttributeType(tagName: string, attribute: string, elementNs?: string, attrNs?: string): string | null; - getPropertyType(tagName: string, property: string, elementNs?: string): string | null; - readonly defaultPolicy: TrustedTypePolicy | null; -} - -export abstract class TrustedTypePolicy { - readonly name: string; - createHTML(...args: Args): TrustedHTML; - createScript(...args: Args): TrustedScript; - createScriptURL(...args: Args): TrustedScriptURL; -} - -export interface TrustedTypePolicyOptions { - createHTML?: ((input: string, ...arguments: any[]) => string) | undefined; - createScript?: ((input: string, ...arguments: any[]) => string) | undefined; - createScriptURL?: ((input: string, ...arguments: any[]) => string) | undefined; -} - -// The Window object is augmented with the following properties in browsers that -// support Trusted Types. Users of the 'trusted-types/lib' entrypoint can cast -// window as TrustedTypesWindow to access these properties. -export interface TrustedTypesWindow { - // `trustedTypes` is left intentionally optional to make sure that - // people handle the case when their code is running in a browser not - // supporting trustedTypes. - trustedTypes?: TrustedTypePolicyFactory | undefined; - TrustedHTML: typeof TrustedHTML; - TrustedScript: typeof TrustedScript; - TrustedScriptURL: typeof TrustedScriptURL; - TrustedTypePolicyFactory: typeof TrustedTypePolicyFactory; - TrustedTypePolicy: typeof TrustedTypePolicy; -} diff --git a/node_modules/@types/trusted-types/package.json b/node_modules/@types/trusted-types/package.json deleted file mode 100644 index eda8c73027..0000000000 --- a/node_modules/@types/trusted-types/package.json +++ /dev/null @@ -1,45 +0,0 @@ -{ - "name": "@types/trusted-types", - "version": "2.0.7", - "description": "TypeScript definitions for trusted-types", - "homepage": "https://github.com/DefinitelyTyped/DefinitelyTyped/tree/master/types/trusted-types", - "license": "MIT", - "contributors": [ - { - "name": "Jakub Vrana", - "githubUsername": "vrana", - "url": "https://github.com/vrana" - }, - { - "name": "Damien Engels", - "githubUsername": "engelsdamien", - "url": "https://github.com/engelsdamien" - }, - { - "name": "Emanuel Tesar", - "githubUsername": "siegrift", - "url": "https://github.com/siegrift" - }, - { - "name": "Bjarki", - "githubUsername": "bjarkler", - "url": "https://github.com/bjarkler" - }, - { - "name": "Sebastian Silbermann", - "githubUsername": "eps1lon", - "url": "https://github.com/eps1lon" - } - ], - "main": "", - "types": "index.d.ts", - "repository": { - "type": "git", - "url": "https://github.com/DefinitelyTyped/DefinitelyTyped.git", - "directory": "types/trusted-types" - }, - "scripts": {}, - "dependencies": {}, - "typesPublisherContentHash": "20982c5e0452e662515e29b41f7be5a3c69e5918a9228929a563d9f1dfdfbbc5", - "typeScriptVersion": "4.5" -} \ No newline at end of file diff --git a/templates/repo_report_template.md b/templates/repo_report_template.md index e2cb49c1b7..a6296e4c7e 100644 --- a/templates/repo_report_template.md +++ b/templates/repo_report_template.md @@ -99,7 +99,7 @@ date_stampLastWeek: {date_stamp}

Activity Graphs

{% Issues/PRs Status Breakdown Graph %} - {{% render "graph-section" baseurl: site.baseurl, path: "/{repo_owner}/{repo_name}/issue_gauge_{repo_name}_data.svg", title: "Issues & PRs Status Breakdown", modal_description: "This graph provides an overview of the statuses of issues and pull requests in the repository. It categorizes them into open issues, open pull requests, and closed and merged pull requests, helping track progress and worklad distribution." %}} + {{% render "graph-section" baseurl: site.baseurl, path: "/{repo_owner}/{repo_name}/issue_gauge_{repo_name}_data.svg", title: "Issues & PRs Status Breakdown", modal_description: "This graph provides an overview of the statuses of issues and pull requests in the repository. It categorizes them into open issues, open pull requests, and closed and merged pull requests, helping track progress and workload distribution." %}} {% Contributor Activity Line Graph %} {{% render "graph-section" baseurl: site.baseurl, path: "/{repo_owner}/{repo_name}/commit_sparklines_{repo_name}_data.svg", title: "Commits by Month", modal_description: "This line graph represents contributor activity over time by showing the number of commits made each month. It provides insights into trends in developement and periods of high and low activity." %}} {% First Response For Closed PR Scatterplot %}