From 385c8b4f7249643d4d1fea755b877a8710bce2f3 Mon Sep 17 00:00:00 2001 From: Don Xavier Date: Sun, 5 Jan 2025 13:41:21 +0530 Subject: [PATCH 1/5] Update license Component for Github SBOM --- src/components/Licenses/SBOMViewer.tsx | 155 +++++++++++++------------ 1 file changed, 81 insertions(+), 74 deletions(-) diff --git a/src/components/Licenses/SBOMViewer.tsx b/src/components/Licenses/SBOMViewer.tsx index d8a7cdc93df..b99b65750b0 100644 --- a/src/components/Licenses/SBOMViewer.tsx +++ b/src/components/Licenses/SBOMViewer.tsx @@ -1,79 +1,96 @@ import dayjs from "dayjs"; -import React, { useState } from "react"; +import React, { useEffect, useState } from "react"; import { CopyToClipboard } from "react-copy-to-clipboard"; import Card from "@/CAREUI/display/Card"; import CareIcon from "@/CAREUI/icons/CareIcon"; -import beBomData from "@/components/Licenses/be-sbom.json"; -import feBomData from "@/components/Licenses/fe-sbom.json"; import licenseUrls from "@/components/Licenses/licenseUrls.json"; const getLicenseUrl = (licenseId: string | undefined): string | null => { if (!licenseId) return null; return licenseUrls[licenseId as keyof typeof licenseUrls] || null; }; -interface CycloneDXExternalRef { - url?: string; - type?: string; - comment?: string; -} -interface CycloneDXLicense { - license?: { - id?: string; - }; +interface GitHubPackage { + name: string; + SPDXID: string; + versionInfo?: string; + downloadLocation?: string; + filesAnalyzed?: boolean; + licenseConcluded?: string; + copyrightText?: string; + externalRefs?: { + referenceCategory?: string; + referenceType?: string; + referenceLocator?: string; + }[]; } -interface CycloneDXProperties { - name?: string; - value?: string; -} - -interface CycloneDXComponent { - type?: string; - name?: string; - group?: string; - version?: string; - bomRef?: string; - author?: string; - description?: string; - licenses?: CycloneDXLicense[]; - externalReferences?: CycloneDXExternalRef[]; - properties?: CycloneDXProperties[]; -} - -interface CycloneDXTool { - name?: string; - version?: string; - vendor?: string; - externalReferences?: CycloneDXExternalRef[]; -} - -interface CycloneDXBOM { - bomFormat?: string; - specVersion?: string; - version?: number; - serialNumber?: string; - metadata?: { - timestamp?: string; - tools?: CycloneDXTool[]; - component?: CycloneDXComponent; +interface GitHubSBOM { + sbom?: { + spdxVersion?: string; + dataLicense?: string; + SPDXID?: string; + name?: string; + documentNamespace?: string; + creationInfo?: { + creators?: string[]; + created?: string; + }; + packages?: GitHubPackage[]; }; - components?: CycloneDXComponent[]; } const BOMDisplay: React.FC = () => { const [copyStatus, setCopyStatus] = useState(false); const [showExternalRefs, setShowExternalRefs] = useState(null); const [activeTab, setActiveTab] = useState("bom"); + const [feBomData, setFeBomData] = useState(null); + const [beBomData, setBeBomData] = useState(null); + + useEffect(() => { + const fetchSBOMData = async (url: string): Promise => { + try { + const response = await fetch(url, { + headers: { + Accept: "application/vnd.github+json", + "X-GitHub-Api-Version": "2022-11-28", + }, + }); + return response.ok ? await response.json() : null; + } catch (error) { + console.error("Error fetching SBOM data:", error); + return null; + } + }; + + const fetchData = async () => { + const feUrl = + "https://api.github.com/repos/ohcnetwork/care_fe/dependency-graph/sbom"; + const beUrl = + "https://api.github.com/repos/ohcnetwork/care/dependency-graph/sbom"; + + const [frontendData, backendData] = await Promise.all([ + fetchSBOMData(feUrl), + fetchSBOMData(beUrl), + ]); + + setFeBomData(frontendData); + setBeBomData(backendData); + }; + + fetchData(); + }, []); + + const bomData = activeTab === "bom" ? feBomData : beBomData; const handleCopy = () => { setCopyStatus(true); setTimeout(() => setCopyStatus(false), 2000); }; - const bomData = (activeTab === "bom" ? feBomData : beBomData) as CycloneDXBOM; + const packages = bomData?.sbom?.packages || []; return (
@@ -98,59 +115,47 @@ const BOMDisplay: React.FC = () => {

- {bomData.bomFormat || "N/A"} BOM (Version:{" "} - {bomData.version || "N/A"}) + SPDX SBOM (Version: {bomData?.sbom?.spdxVersion || "N/A"})

Created on:{" "} - {bomData.metadata?.timestamp - ? dayjs(bomData.metadata.timestamp).format("MMMM D, YYYY") + {bomData?.sbom?.creationInfo?.created + ? dayjs(bomData.sbom.creationInfo.created).format("MMMM D, YYYY") : "N/A"}

- Components: + Packages:

- {bomData.components?.map((component, index) => ( + {packages.map((pkg, index) => (
- {component.name || "N/A"} v{component.version || "N/A"} + {pkg.name || "N/A"} v{pkg.versionInfo || "N/A"} - {component.licenses && component.licenses[0]?.license?.id && ( + {pkg.licenseConcluded && (

License:{" "} - {component.licenses[0].license.id || "N/A"} + {pkg.licenseConcluded || "N/A"}

)} - {component.description && ( -

- Description: {component.description} -

- )}

{

{showExternalRefs === index && ( From 13852f0cf93dec1b4692fa98c6f3bc9321568fea Mon Sep 17 00:00:00 2001 From: Don Xavier Date: Tue, 7 Jan 2025 15:45:32 +0530 Subject: [PATCH 2/5] fetch SBOM data during postinstall and save as JSON for lazy import --- .gitignore | 4 +- package.json | 3 +- scripts/fetchSbomData.js | 49 +++++++++++ src/components/Licenses/SBOMViewer.tsx | 116 +++++++------------------ 4 files changed, 87 insertions(+), 85 deletions(-) create mode 100644 scripts/fetchSbomData.js diff --git a/.gitignore b/.gitignore index d9cdd38e3ef..b338ad49a91 100644 --- a/.gitignore +++ b/.gitignore @@ -65,4 +65,6 @@ src/pluginMap.ts /apps_backup/* # Federation Temp files -/.__mf__temp \ No newline at end of file +/.__mf__temp +src/components/Licenses/beBomData.json +src/components/Licenses/feBomData.json diff --git a/package.json b/package.json index 75b8501fc68..5a77ba4fd39 100644 --- a/package.json +++ b/package.json @@ -35,7 +35,8 @@ "supported-browsers": "node ./scripts/generate-supported-browsers.mjs", "build": "npm run setup && npm run build:meta && npm run supported-browsers && npm run build:react", "setup": "tsx scripts/setup-care-apps.ts", - "postinstall": "tsx scripts/install-platform-deps.ts", + "postinstall": "tsx scripts/install-platform-deps.ts && node scripts/fetchSbomData.js", + "test": "snyk test", "cypress:open": "cross-env NODE_ENV=development cypress open", "cypress:run": "cross-env NODE_ENV=development cypress run", diff --git a/scripts/fetchSbomData.js b/scripts/fetchSbomData.js new file mode 100644 index 00000000000..102033ef5a9 --- /dev/null +++ b/scripts/fetchSbomData.js @@ -0,0 +1,49 @@ +import fs from "fs"; +import fetch from "node-fetch"; + +const fetchSBOMData = async (url) => { + const response = await fetch(url, { + headers: { + Accept: "application/vnd.github+json", + "X-GitHub-Api-Version": "2022-11-28", + }, + }); + if (!response.ok) { + throw new Error(`Error fetching SBOM data from ${url}`); + } + return await response.json(); +}; + +const fetchData = async () => { + const feUrl = + "https://api.github.com/repos/ohcnetwork/care_fe/dependency-graph/sbom"; + const beUrl = + "https://api.github.com/repos/ohcnetwork/care/dependency-graph/sbom"; + + try { + const [frontendData, backendData] = await Promise.all([ + fetchSBOMData(feUrl), + fetchSBOMData(beUrl), + ]); + + // Write frontend SBOM data + fs.writeFileSync( + "./src/components/Licenses/feBomData.json", + JSON.stringify(frontendData, null, 2), + ); + + // Write backend SBOM data + fs.writeFileSync( + "./src/components/Licenses/beBomData.json", + JSON.stringify(backendData, null, 2), + ); + + console.log( + "SBOM data successfully saved as feBomData.json and beBomData.json", + ); + } catch (error) { + console.error("Error fetching SBOM data:", error.message); + } +}; + +fetchData(); diff --git a/src/components/Licenses/SBOMViewer.tsx b/src/components/Licenses/SBOMViewer.tsx index b99b65750b0..59024565a2b 100644 --- a/src/components/Licenses/SBOMViewer.tsx +++ b/src/components/Licenses/SBOMViewer.tsx @@ -1,87 +1,26 @@ import dayjs from "dayjs"; -import React, { useEffect, useState } from "react"; +import React, { useState } from "react"; import { CopyToClipboard } from "react-copy-to-clipboard"; +import { useTranslation } from "react-i18next"; import Card from "@/CAREUI/display/Card"; import CareIcon from "@/CAREUI/icons/CareIcon"; import licenseUrls from "@/components/Licenses/licenseUrls.json"; +import beBomData from "./beBomData.json"; +import feBomData from "./feBomData.json"; + const getLicenseUrl = (licenseId: string | undefined): string | null => { if (!licenseId) return null; return licenseUrls[licenseId as keyof typeof licenseUrls] || null; }; -interface GitHubPackage { - name: string; - SPDXID: string; - versionInfo?: string; - downloadLocation?: string; - filesAnalyzed?: boolean; - licenseConcluded?: string; - copyrightText?: string; - externalRefs?: { - referenceCategory?: string; - referenceType?: string; - referenceLocator?: string; - }[]; -} - -interface GitHubSBOM { - sbom?: { - spdxVersion?: string; - dataLicense?: string; - SPDXID?: string; - name?: string; - documentNamespace?: string; - creationInfo?: { - creators?: string[]; - created?: string; - }; - packages?: GitHubPackage[]; - }; -} - const BOMDisplay: React.FC = () => { + const { t } = useTranslation(); const [copyStatus, setCopyStatus] = useState(false); const [showExternalRefs, setShowExternalRefs] = useState(null); const [activeTab, setActiveTab] = useState("bom"); - const [feBomData, setFeBomData] = useState(null); - const [beBomData, setBeBomData] = useState(null); - - useEffect(() => { - const fetchSBOMData = async (url: string): Promise => { - try { - const response = await fetch(url, { - headers: { - Accept: "application/vnd.github+json", - "X-GitHub-Api-Version": "2022-11-28", - }, - }); - return response.ok ? await response.json() : null; - } catch (error) { - console.error("Error fetching SBOM data:", error); - return null; - } - }; - - const fetchData = async () => { - const feUrl = - "https://api.github.com/repos/ohcnetwork/care_fe/dependency-graph/sbom"; - const beUrl = - "https://api.github.com/repos/ohcnetwork/care/dependency-graph/sbom"; - - const [frontendData, backendData] = await Promise.all([ - fetchSBOMData(feUrl), - fetchSBOMData(beUrl), - ]); - - setFeBomData(frontendData); - setBeBomData(backendData); - }; - - fetchData(); - }, []); const bomData = activeTab === "bom" ? feBomData : beBomData; @@ -101,7 +40,7 @@ const BOMDisplay: React.FC = () => { }`} onClick={() => setActiveTab("bom")} > - Care Frontend + {t("Care Frontend")}

- SPDX SBOM (Version: {bomData?.sbom?.spdxVersion || "N/A"}) + {t("SPDX SBOM (Version: {{version}})", { + version: bomData?.sbom?.spdxVersion || t("N/A"), + })}

- Created on:{" "} - {bomData?.sbom?.creationInfo?.created - ? dayjs(bomData.sbom.creationInfo.created).format("MMMM D, YYYY") - : "N/A"} + {t("Created on: {{date}}", { + date: bomData?.sbom?.creationInfo?.created + ? dayjs(bomData.sbom.creationInfo.created).format( + "MMMM D, YYYY", + ) + : t("N/A"), + })}

- Packages: + {t("Packages:")}

{packages.map((pkg, index) => (
{ className="block rounded-md border p-2 transition-all duration-300 hover:shadow-lg" > - {pkg.name || "N/A"} v{pkg.versionInfo || "N/A"} + {t("{{name}} v{{version}}", { + name: pkg.name || t("N/A"), + version: pkg.versionInfo || t("N/A"), + })} {pkg.licenseConcluded && (

- License:{" "} + {t("License:")}{" "} - {pkg.licenseConcluded || "N/A"} + {pkg.licenseConcluded || t("N/A")}

)} @@ -175,10 +121,14 @@ const BOMDisplay: React.FC = () => { href={ref.referenceLocator || "#"} className="hover:text-primary-dark block break-words text-primary" > - {ref.referenceLocator || "N/A"} + {ref.referenceLocator || t("N/A")} {ref.referenceCategory && ( -

Category: {ref.referenceCategory}

+

+ {t("Category: {{category}}", { + category: ref.referenceCategory, + })} +

)} ))} @@ -194,12 +144,12 @@ const BOMDisplay: React.FC = () => { onCopy={handleCopy} > {copyStatus && ( - Copied to clipboard! + {t("Copied to clipboard!")} )}
From 6ad0ee5bcfd51845fc561829753439c3f43d8b79 Mon Sep 17 00:00:00 2001 From: Don Xavier Date: Fri, 10 Jan 2025 19:47:45 +0530 Subject: [PATCH 3/5] Changes to Translations,Scripts --- .gitignore | 4 +- package.json | 2 +- public/locale/en.json | 9 +- .../{fetchSbomData.js => fetchSbomData.ts} | 35 +++++--- src/components/Licenses/SBOMViewer.tsx | 85 ++++++++++++------- 5 files changed, 88 insertions(+), 47 deletions(-) rename scripts/{fetchSbomData.js => fetchSbomData.ts} (51%) diff --git a/.gitignore b/.gitignore index b338ad49a91..53989a4d4b5 100644 --- a/.gitignore +++ b/.gitignore @@ -66,5 +66,5 @@ src/pluginMap.ts # Federation Temp files /.__mf__temp -src/components/Licenses/beBomData.json -src/components/Licenses/feBomData.json +public/licenses/beBomData.json +public/licenses/feBomData.json diff --git a/package.json b/package.json index 5a77ba4fd39..8cad6a97fe2 100644 --- a/package.json +++ b/package.json @@ -35,7 +35,7 @@ "supported-browsers": "node ./scripts/generate-supported-browsers.mjs", "build": "npm run setup && npm run build:meta && npm run supported-browsers && npm run build:react", "setup": "tsx scripts/setup-care-apps.ts", - "postinstall": "tsx scripts/install-platform-deps.ts && node scripts/fetchSbomData.js", + "postinstall": "tsx scripts/install-platform-deps.ts && tsx scripts/fetchSbomData.ts", "test": "snyk test", "cypress:open": "cross-env NODE_ENV=development cypress open", diff --git a/public/locale/en.json b/public/locale/en.json index 1a858bb77a8..98c3c6c4a36 100644 --- a/public/locale/en.json +++ b/public/locale/en.json @@ -470,6 +470,8 @@ "capture": "Capture", "capture_cover_photo": "Capture Cover Photo", "care": "CARE", + "care_backend": "Care Backend", + "care_frontend": "Care Frontend", "category": "Category", "caution": "Caution", "central_nursing_station": "Central Nursing Station", @@ -609,8 +611,9 @@ "continue": "Continue", "continue_watching": "Continue watching", "contribute_github": "Contribute on Github", - "copied_to_clipboard": "Copied to clipboard", + "copied_to_clipboard": "Copied to clipboard!", "copilot_thinking": "Copilot is thinking...", + "copy_bom_json": "Copy BOM JSON", "copy_phone_number": "Copy Phone Number", "could_not_autofill": "We could not autofill any fields from what you said", "could_not_load_page": "We are facing some difficulties showing the Page you were looking for. Our Engineers have been notified and we'll make sure that this is resolved on the fly!", @@ -1084,6 +1087,7 @@ "latitude_invalid": "Latitude must be between -90 and 90", "left": "Left", "length": "Length ({{unit}})", + "license": "License", "link_abha_number": "Link ABHA Number", "link_abha_profile": "Link ABHA Profile", "link_camera_and_bed": "Link bed to Camera", @@ -1178,6 +1182,7 @@ "moving_camera": "Moving Camera", "my_doctors": "My Doctors", "my_profile": "My Profile", + "n_a": "N/A", "name": "Name", "name_of_hospital": "Name of Hospital", "name_of_shifting_approving_facility": "Name of shifting approving facility", @@ -1289,6 +1294,7 @@ "otp_verification_success": "OTP has been verified successfully.", "out_of_range_error": "Value must be between {{ start }} and {{ end }}.", "oxygen_information": "Oxygen Information", + "packages": "Packages", "page_load_error": "Couldn't Load the Page", "page_not_found": "Page Not Found", "pain": "Pain", @@ -1653,6 +1659,7 @@ "something_wrong": "Something went wrong! Try again later!", "sort_by": "Sort By", "source": "Source", + "spdx_sbom_version": "SPDX SBOM Version", "spokes": "Spoke Facilities", "srf_id": "SRF ID", "staff_list": "Staff List", diff --git a/scripts/fetchSbomData.js b/scripts/fetchSbomData.ts similarity index 51% rename from scripts/fetchSbomData.js rename to scripts/fetchSbomData.ts index 102033ef5a9..0a8181c3298 100644 --- a/scripts/fetchSbomData.js +++ b/scripts/fetchSbomData.ts @@ -1,20 +1,33 @@ import fs from "fs"; import fetch from "node-fetch"; -const fetchSBOMData = async (url) => { +interface SBOMData { + dependencies?: Record; + [key: string]: unknown; // Add more specific fields if known +} + +interface FetchError extends Error { + response?: Response; +} + +const fetchSBOMData = async (url: string): Promise => { const response = await fetch(url, { headers: { Accept: "application/vnd.github+json", "X-GitHub-Api-Version": "2022-11-28", }, }); + if (!response.ok) { - throw new Error(`Error fetching SBOM data from ${url}`); + const error: FetchError = new Error(`Error fetching SBOM data from ${url}`); + error.response = response; + throw error; } - return await response.json(); + + return (await response.json()) as SBOMData; }; -const fetchData = async () => { +const fetchData = async (): Promise => { const feUrl = "https://api.github.com/repos/ohcnetwork/care_fe/dependency-graph/sbom"; const beUrl = @@ -28,21 +41,21 @@ const fetchData = async () => { // Write frontend SBOM data fs.writeFileSync( - "./src/components/Licenses/feBomData.json", + "./public/licenses/feBomData.json", JSON.stringify(frontendData, null, 2), ); // Write backend SBOM data fs.writeFileSync( - "./src/components/Licenses/beBomData.json", + "./public/licenses/beBomData.json", JSON.stringify(backendData, null, 2), ); - - console.log( - "SBOM data successfully saved as feBomData.json and beBomData.json", - ); } catch (error) { - console.error("Error fetching SBOM data:", error.message); + if (error instanceof Error) { + console.error("Error fetching SBOM data:", error.message); + } else { + console.error("Unknown error occurred while fetching SBOM data"); + } } }; diff --git a/src/components/Licenses/SBOMViewer.tsx b/src/components/Licenses/SBOMViewer.tsx index 59024565a2b..049f3356a38 100644 --- a/src/components/Licenses/SBOMViewer.tsx +++ b/src/components/Licenses/SBOMViewer.tsx @@ -1,3 +1,4 @@ +import { useQuery } from "@tanstack/react-query"; import dayjs from "dayjs"; import React, { useState } from "react"; import { CopyToClipboard } from "react-copy-to-clipboard"; @@ -8,20 +9,41 @@ import CareIcon from "@/CAREUI/icons/CareIcon"; import licenseUrls from "@/components/Licenses/licenseUrls.json"; -import beBomData from "./beBomData.json"; -import feBomData from "./feBomData.json"; - const getLicenseUrl = (licenseId: string | undefined): string | null => { if (!licenseId) return null; return licenseUrls[licenseId as keyof typeof licenseUrls] || null; }; +const fetchJsonData = async (url: string) => { + const response = await fetch(url); + if (!response.ok) throw new Error("Failed to fetch data"); + return response.json(); +}; + const BOMDisplay: React.FC = () => { const { t } = useTranslation(); const [copyStatus, setCopyStatus] = useState(false); const [showExternalRefs, setShowExternalRefs] = useState(null); const [activeTab, setActiveTab] = useState("bom"); + const { + data: feBomData, + isLoading: feBomLoading, + error: feBomError, + } = useQuery({ + queryKey: ["feBomData"], + queryFn: () => fetchJsonData("/licenses/feBomData.json"), + }); + + const { + data: beBomData, + isLoading: beBomLoading, + error: beBomError, + } = useQuery({ + queryKey: ["beBomData"], + queryFn: () => fetchJsonData("/licenses/beBomData.json"), + }); + const bomData = activeTab === "bom" ? feBomData : beBomData; const handleCopy = () => { @@ -29,6 +51,14 @@ const BOMDisplay: React.FC = () => { setTimeout(() => setCopyStatus(false), 2000); }; + if (feBomLoading || beBomLoading) { + return
{t("loading")}
; + } + + if (feBomError || beBomError) { + return
{t("error_404")}
; + } + const packages = bomData?.sbom?.packages || []; return ( @@ -40,7 +70,7 @@ const BOMDisplay: React.FC = () => { }`} onClick={() => setActiveTab("bom")} > - {t("Care Frontend")} + {t("care_frontend")}

- {t("SPDX SBOM (Version: {{version}})", { - version: bomData?.sbom?.spdxVersion || t("N/A"), - })} + {t("spdx_sbom_version") + ": " + bomData?.sbom?.spdxVersion || + t("n_a")}

- {t("Created on: {{date}}", { - date: bomData?.sbom?.creationInfo?.created - ? dayjs(bomData.sbom.creationInfo.created).format( - "MMMM D, YYYY", - ) - : t("N/A"), - })} + {t("created_on")}{" "} + {bomData?.sbom?.creationInfo?.created + ? dayjs(bomData.sbom.creationInfo.created).format("MMMM D, YYYY") + : t("n_a")}

- {t("Packages:")} + {t("packages")} + {":"}

- {packages.map((pkg, index) => ( + {packages.map((pkg: any, index: number) => (
{ className="hover:text-primary-dark block text-primary" > - {t("{{name}} v{{version}}", { - name: pkg.name || t("N/A"), - version: pkg.versionInfo || t("N/A"), - })} + {`${pkg.name || t("n_a")} v${pkg.versionInfo || t("n_a")}`} {pkg.licenseConcluded && (

- {t("License:")}{" "} + {t("license")} + {": "} - {pkg.licenseConcluded || t("N/A")} + {pkg.licenseConcluded || t("n_a")}

)} @@ -115,20 +140,16 @@ const BOMDisplay: React.FC = () => { {showExternalRefs === index && (
    - {pkg.externalRefs?.map((ref, idx) => ( + {pkg.externalRefs?.map((ref: any, idx: any) => (
  • - {ref.referenceLocator || t("N/A")} + {ref.referenceLocator || t("n_a")} {ref.referenceCategory && ( -

    - {t("Category: {{category}}", { - category: ref.referenceCategory, - })} -

    +

    {t("category") + ": " + ref.referenceCategory}

    )}
  • ))} @@ -144,12 +165,12 @@ const BOMDisplay: React.FC = () => { onCopy={handleCopy} > {copyStatus && ( - {t("Copied to clipboard!")} + {t("copied_to_clipboard")} )}
From 54f7a71c0e0ba55bb5a3a175984268573282ce8c Mon Sep 17 00:00:00 2001 From: Don Xavier Date: Sun, 12 Jan 2025 16:43:45 +0530 Subject: [PATCH 4/5] missing translation added + mods to postinstall script --- public/locale/en.json | 1 + scripts/fetchSbomData.ts | 93 +++++++++++++++++++++++----------------- 2 files changed, 55 insertions(+), 39 deletions(-) diff --git a/public/locale/en.json b/public/locale/en.json index a85a1d19720..bd687fa07a0 100644 --- a/public/locale/en.json +++ b/public/locale/en.json @@ -1278,6 +1278,7 @@ "moving_camera": "Moving Camera", "my_doctors": "My Doctors", "my_profile": "My Profile", + "my_schedules": "My Schedules", "n_a": "N/A", "name": "Name", "name_of_hospital": "Name of Hospital", diff --git a/scripts/fetchSbomData.ts b/scripts/fetchSbomData.ts index 0a8181c3298..b9675d8c7a6 100644 --- a/scripts/fetchSbomData.ts +++ b/scripts/fetchSbomData.ts @@ -1,16 +1,46 @@ import fs from "fs"; import fetch from "node-fetch"; -interface SBOMData { - dependencies?: Record; - [key: string]: unknown; // Add more specific fields if known -} +const FE_SBOM_URL = + "https://api.github.com/repos/ohcnetwork/care_fe/dependency-graph/sbom"; +const BE_SBOM_URL = + "https://api.github.com/repos/ohcnetwork/care/dependency-graph/sbom"; -interface FetchError extends Error { - response?: Response; +interface GitHubSbomApiResponse { + sbom: { + spdxVersion: string; + dataLicense: string; + SPDXID: string; + name: string; + documentNamespace: string; + creationInfo: { + creators: string[]; + created: string; + }; + packages: { + name: string; + SPDXID: string; + versionInfo: string; + downloadLocation: string; + filesAnalyzed: boolean; + licenseConcluded?: string; + copyrightText?: string; + externalRefs: { + referenceCategory: string; + referenceType: string; + referenceLocator: string; + }[]; + licenseDeclared?: string; + }[]; + relationships: { + spdxElementId: string; + relatedSpdxElement: string; + relationshipType: string; + }[]; + }; } -const fetchSBOMData = async (url: string): Promise => { +const fetchSBOMData = async (url: string): Promise => { const response = await fetch(url, { headers: { Accept: "application/vnd.github+json", @@ -19,44 +49,29 @@ const fetchSBOMData = async (url: string): Promise => { }); if (!response.ok) { - const error: FetchError = new Error(`Error fetching SBOM data from ${url}`); - error.response = response; - throw error; + throw new Error( + `Error fetching SBOM data from ${url}: ${response.statusText}`, + ); } - return (await response.json()) as SBOMData; + return (await response.json()) as GitHubSbomApiResponse; }; const fetchData = async (): Promise => { - const feUrl = - "https://api.github.com/repos/ohcnetwork/care_fe/dependency-graph/sbom"; - const beUrl = - "https://api.github.com/repos/ohcnetwork/care/dependency-graph/sbom"; - - try { - const [frontendData, backendData] = await Promise.all([ - fetchSBOMData(feUrl), - fetchSBOMData(beUrl), - ]); - - // Write frontend SBOM data - fs.writeFileSync( - "./public/licenses/feBomData.json", - JSON.stringify(frontendData, null, 2), - ); + const [frontendData, backendData] = await Promise.all([ + fetchSBOMData(FE_SBOM_URL), + fetchSBOMData(BE_SBOM_URL), + ]); - // Write backend SBOM data - fs.writeFileSync( - "./public/licenses/beBomData.json", - JSON.stringify(backendData, null, 2), - ); - } catch (error) { - if (error instanceof Error) { - console.error("Error fetching SBOM data:", error.message); - } else { - console.error("Unknown error occurred while fetching SBOM data"); - } - } + fs.writeFileSync( + "./public/licenses/feBomData.json", + JSON.stringify(frontendData, null, 2), + ); + + fs.writeFileSync( + "./public/licenses/beBomData.json", + JSON.stringify(backendData, null, 2), + ); }; fetchData(); From 905272fefab185d6d3eabe1acce7872fe980239c Mon Sep 17 00:00:00 2001 From: Don Xavier Date: Sun, 12 Jan 2025 16:58:43 +0530 Subject: [PATCH 5/5] Track empty licenses folder using .gitkeep --- public/licenses/.gitkeep | 0 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 public/licenses/.gitkeep diff --git a/public/licenses/.gitkeep b/public/licenses/.gitkeep new file mode 100644 index 00000000000..e69de29bb2d