Compare commits

...
28 changed files with 286 additions and 117 deletions
+1 -1
View File
@@ -16,7 +16,7 @@ AUTH_SECRET="N/c6mnaS5+SWq81+819OrzQZlmx1Vxtp/orjttJSmw8="
PROWLER_API_VERSION="stable"
# PostgreSQL settings
# If running Django and celery on host, use 'localhost', else use 'postgres-db'
POSTGRES_HOST=postgres-db
POSTGRES_HOST=postgres-db-proxy
POSTGRES_PORT=5432
POSTGRES_ADMIN_USER=prowler_admin
POSTGRES_ADMIN_PASSWORD=postgres
+5 -4
View File
@@ -9,12 +9,8 @@ All notable changes to the **Prowler API** are documented in this file.
- Added new `GET /compliance-overviews` endpoints to retrieve compliance metadata and specific requirements statuses [(#7877)](https://github.com/prowler-cloud/prowler/pull/7877).
### Changed
- Renamed field encrypted_password to password for M365 provider [(#7784)](https://github.com/prowler-cloud/prowler/pull/7784)
- Reworked `GET /compliance-overviews` to return proper requirement metrics [(#7877)](https://github.com/prowler-cloud/prowler/pull/7877).
### Fixed
- Fixed the connection status verification before launching a scan [(#7831)](https://github.com/prowler-cloud/prowler/pull/7831)
---
## [v1.8.3] (Prowler v5.7.3)
@@ -22,9 +18,14 @@ All notable changes to the **Prowler API** are documented in this file.
### Added
- Database backend to handle already closed connections [(#7935)](https://github.com/prowler-cloud/prowler/pull/7935).
### Changed
- Renamed field encrypted_password to password for M365 provider [(#7784)](https://github.com/prowler-cloud/prowler/pull/7784)
### Fixed
- Fixed transaction persistence with RLS operations [(#7916)](https://github.com/prowler-cloud/prowler/pull/7916).
- Reverted the change `get_with_retry` to use the original `get` method for retrieving tasks [(#7932)](https://github.com/prowler-cloud/prowler/pull/7932).
- Fixed the connection status verification before launching a scan [(#7831)](https://github.com/prowler-cloud/prowler/pull/7831)
---
+3 -4
View File
@@ -37,18 +37,17 @@ COPY pyproject.toml ./
RUN pip install --no-cache-dir --upgrade pip && \
pip install --no-cache-dir poetry
COPY src/backend/ ./backend/
ENV PATH="/home/prowler/.local/bin:$PATH"
# Add `--no-root` to avoid installing the current project as a package
RUN poetry install --no-root && \
rm -rf ~/.cache/pip
COPY docker-entrypoint.sh ./docker-entrypoint.sh
RUN poetry run python "$(poetry env info --path)/src/prowler/prowler/providers/m365/lib/powershell/m365_powershell.py"
COPY src/backend/ ./backend/
COPY docker-entrypoint.sh ./docker-entrypoint.sh
WORKDIR /home/prowler/backend
# Development image
+21 -2
View File
@@ -26,6 +26,25 @@ services:
ports:
- ${UI_PORT:-3000}:${UI_PORT:-3000}
postgres-proxy:
image: edoburu/pgbouncer:latest
hostname: "postgres-db-proxy"
environment:
- DB_HOST=postgres-db
- DB_PORT=5432
- DB_USER=${POSTGRES_ADMIN_USER}
- DB_PASSWORD=${POSTGRES_ADMIN_PASSWORD}
- ADMIN_USERS=prowler_admin
- AUTH_TYPE=scram-sha-256
env_file:
- path: ./.env
required: false
ports:
- "5432:5432"
depends_on:
postgres:
condition: service_healthy
postgres:
image: postgres:16.3-alpine3.20
hostname: "postgres-db"
@@ -38,8 +57,8 @@ services:
env_file:
- path: .env
required: false
ports:
- "${POSTGRES_PORT:-5432}:${POSTGRES_PORT:-5432}"
# ports:
# - "${POSTGRES_PORT:-5432}:${POSTGRES_PORT:-5432}"
healthcheck:
test: ["CMD-SHELL", "sh -c 'pg_isready -U ${POSTGRES_ADMIN_USER} -d ${POSTGRES_DB}'"]
interval: 5s
+3
View File
@@ -170,6 +170,9 @@ These two new environment variables are **required** to execute the PowerShell m
- `M365_USER` should be your Microsoft account email using the **assigned domain in the tenant**. This means it must look like `example@YourCompany.onmicrosoft.com` or `example@YourCompany.com`, but it must be the exact domain assigned to that user in the tenant.
???+ warning
The user must not be MFA capable. Microsoft does not allow MFA capable users to authenticate programmatically. See [Microsoft documentation](https://learn.microsoft.com/en-us/entra/identity-platform/scenario-desktop-acquire-token-username-password?tabs=dotnet) for more information.
???+ warning
Using a tenant domain other than the one assigned — even if it belongs to the same tenant — will cause Prowler to fail, as Microsoft authentication will not succeed.
@@ -138,6 +138,10 @@ Follow these steps to assign the permissions:
![Grant Admin Consent](./img/grant-admin-consent-delegated.png)
The final result of permission assignment should be this:
![Final Permission Assignment](./img/final-permissions-m365.png)
---
### Assign required roles to your user
Binary file not shown.

After

Width:  |  Height:  |  Size: 81 KiB

+6
View File
@@ -4,6 +4,9 @@ The **Prowler App** supports multiple users within a single tenant, enabling sea
[Roles](#roles) help you control user permissions, determining what actions each user can perform and the data they can access within Prowler. By default, each account includes an immutable **admin** role, ensuring that your account always retains administrative access.
???+ note
If the account is created without an invitation, a new tenant will be provisioned for it. However, if the account is created through an invitation, the user will join the inviters tenant.
## Membership
To get to User-Invitation Management we will focus on the Membership section.
@@ -156,6 +159,9 @@ Follow these steps to create a role for your account:
<img src="../img/rbac/role_create_1.png" alt="Role parameters" width="700"/>
???+ note
To assign read-only access, select only the `Unlimited Visibility` permission when creating the role. Then, go to the Users page and assign this role to the appropriate user.
#### Editing a Role
Follow these steps to edit a role on your account:
+12 -6
View File
@@ -2,7 +2,7 @@
All notable changes to the **Prowler SDK** are documented in this file.
## [5.8.0] (Prowler v5.8.0)
## [v5.8.0] (Prowler UNRELEASED)
### Added
- Add CIS 1.11 compliance framework for Kubernetes. [(#7790)](https://github.com/prowler-cloud/prowler/pull/7790)
@@ -25,7 +25,17 @@ All notable changes to the **Prowler SDK** are documented in this file.
---
### [v5.7.2] Fixed
## [v5.7.3] (Prowler v5.7.3)
### Fixed
- Automatically encrypt password in Microsoft365 provider. [(#7784)](https://github.com/prowler-cloud/prowler/pull/7784)
- Remove last encrypted password appearances. [(#7825)](https://github.com/prowler-cloud/prowler/pull/7825)
---
## [v5.7.2] (Prowler v5.7.2)
### Fixed
- Fix `m365_powershell test_credentials` to use sanitized credentials. [(#7761)](https://github.com/prowler-cloud/prowler/pull/7761)
- Fix `admincenter_users_admins_reduced_license_footprint` check logic to pass when admin user has no license. [(#7779)](https://github.com/prowler-cloud/prowler/pull/7779)
- Fix `m365_powershell` to close the PowerShell sessions in msgraph services. [(#7816)](https://github.com/prowler-cloud/prowler/pull/7816)
@@ -60,14 +70,12 @@ All notable changes to the **Prowler SDK** are documented in this file.
- Update and upgrade CIS for all the providers [(#7738)](https://github.com/prowler-cloud/prowler/pull/7738)
- Cover policies with conditions with SNS endpoint in `sns_topics_not_publicly_accessible`. [(#7750)](https://github.com/prowler-cloud/prowler/pull/7750)
- Change severity logic for `ec2_securitygroup_allow_ingress_from_internet_to_all_ports` check. [(#7764)](https://github.com/prowler-cloud/prowler/pull/7764)
- Automatically encrypt password in Microsoft365 provider. [(#7784)](https://github.com/prowler-cloud/prowler/pull/7784)
---
## [v5.6.0] (Prowler v5.6.0)
### Added
- Add SOC2 compliance framework to Azure. [(#7489)](https://github.com/prowler-cloud/prowler/pull/7489)
- Add check for unused Service Accounts in GCP. [(#7419)](https://github.com/prowler-cloud/prowler/pull/7419)
- Add Powershell to Microsoft365. [(#7331)](https://github.com/prowler-cloud/prowler/pull/7331)
@@ -117,7 +125,6 @@ All notable changes to the **Prowler SDK** are documented in this file.
- Add Microsoft User and User Credential auth to reports [(#7681)](https://github.com/prowler-cloud/prowler/pull/7681)
### Fixed
- Fix package name location in pyproject.toml while replicating for prowler-cloud. [(#7531)](https://github.com/prowler-cloud/prowler/pull/7531)
- Remove cache in PyPI release action. [(#7532)](https://github.com/prowler-cloud/prowler/pull/7532)
- Add the correct values for logger.info inside iam service. [(#7526)](https://github.com/prowler-cloud/prowler/pull/7526)
@@ -138,7 +145,6 @@ All notable changes to the **Prowler SDK** are documented in this file.
## [v5.5.1] (Prowler v5.5.1)
### Fixed
- Add default name to contacts in Azure Defender. [(#7483)](https://github.com/prowler-cloud/prowler/pull/7483)
- Handle projects without ID in GCP. [(#7496)](https://github.com/prowler-cloud/prowler/pull/7496)
- Restore packages location in PyProject. [(#7510)](https://github.com/prowler-cloud/prowler/pull/7510)
+10
View File
@@ -19,10 +19,20 @@ All notable changes to the **Prowler UI** are documented in this file.
- Add compliance detail view: ISO [(#7897)](https://github.com/prowler-cloud/prowler/pull/7897)
- Add compliance detail view: CIS [(#7913)](https://github.com/prowler-cloud/prowler/pull/7913)
- Add compliance detail view: AWS Well-Architected Framework [(#7925)](https://github.com/prowler-cloud/prowler/pull/7925)
- Improve `Scan ID` filter by adding more context and enhancing the UI/UX. [(#7949)](https://github.com/prowler-cloud/prowler/pull/7949)
### 🔄 Changed
- Add `Provider UID` filter to scans page. [(#7820)](https://github.com/prowler-cloud/prowler/pull/7820)
- Aligned Next.js version to `v14.2.29` across Prowler and Cloud environments for consistency and improved maintainability. [(#7962)](https://github.com/prowler-cloud/prowler/pull/7962)
---
## [v1.7.3] (Prowler v5.7.3)
### 🐞 Fixes
- Fix encrypted password typo in `formSchemas`. [(#7828)](https://github.com/prowler-cloud/prowler/pull/7828)
---
+10 -11
View File
@@ -19,6 +19,7 @@ import { ContentLayout } from "@/components/ui";
import { DataTable, DataTableFilterCustom } from "@/components/ui/table";
import {
createDict,
createScanDetailsMapping,
extractFiltersAndQuery,
extractSortAndKey,
hasDateOrScanFilter,
@@ -48,7 +49,7 @@ export default async function Findings({
filters,
}),
getProviders({ pageSize: 50 }),
getScans({}),
getScans({ pageSize: 50 }),
]);
// Extract unique regions and services from the new endpoint
@@ -76,20 +77,17 @@ export default async function Findings({
});
// Extract scan UUIDs with "completed" state and more than one resource
const completedScans = scansData?.data
?.filter(
(scan: ScanProps) =>
scan.attributes.state === "completed" &&
scan.attributes.unique_resource_count > 1,
)
.map((scan: ScanProps) => ({
id: scan.id,
name: scan.attributes.name,
}));
const completedScans = scansData?.data?.filter(
(scan: ScanProps) =>
scan.attributes.state === "completed" &&
scan.attributes.unique_resource_count > 1,
);
const completedScanIds =
completedScans?.map((scan: ScanProps) => scan.id) || [];
const scanDetails = createScanDetailsMapping(completedScans, providersData);
return (
<ContentLayout title="Findings" icon="carbon:data-view-alt">
<FilterControls search date />
@@ -119,6 +117,7 @@ export default async function Findings({
key: "scan__in",
labelCheckboxGroup: "Scan ID",
values: completedScanIds,
valueLabelMapping: scanDetails,
index: 9,
},
]}
@@ -6,7 +6,7 @@ import { FilterControls } from "@/components/filters";
import { DataTableFilterCustom } from "@/components/ui/table/data-table-filter-custom";
import { DataCompliance } from "./data-compliance";
import { SelectScanComplianceDataProps } from "./select-scan-compliance-data";
import { SelectScanComplianceDataProps } from "./scan-selector";
interface ComplianceHeaderProps {
scans: SelectScanComplianceDataProps["scans"];
@@ -1,4 +1,4 @@
import { Divider } from "@nextui-org/react";
import { Divider, Tooltip } from "@nextui-org/react";
import React from "react";
import { DateWithTime, EntityInfoShort } from "@/components/ui/entities";
@@ -22,18 +22,25 @@ export const ComplianceScanInfo: React.FC<ComplianceScanInfoProps> = ({
scan,
}) => {
return (
<div className="flex w-fit items-center">
<div className="flex items-center gap-2">
<EntityInfoShort
cloudProvider={scan.providerInfo.provider}
entityAlias={scan.providerInfo.alias}
entityId={scan.providerInfo.uid}
hideCopyButton
snippetWidth="max-w-[100px]"
/>
<Divider orientation="vertical" className="mx-2 h-6" />
<div className="flex flex-col items-start">
<p className="text-xs text-default-500">
{scan.attributes.name || "- -"}
</p>
<Divider orientation="vertical" className="h-6" />
<div className="flex flex-col items-start whitespace-nowrap">
<Tooltip
content={scan.attributes.name || "- -"}
placement="top"
size="sm"
>
<p className="text-xs text-default-500">
{scan.attributes.name || "- -"}
</p>
</Tooltip>
<DateWithTime inline dateTime={scan.attributes.completed_at} />
</div>
</div>
@@ -4,7 +4,7 @@ import { useRouter, useSearchParams } from "next/navigation";
import { useEffect } from "react";
import {
SelectScanComplianceData,
ScanSelector,
SelectScanComplianceDataProps,
} from "@/components/compliance/compliance-header/index";
interface DataComplianceProps {
@@ -35,8 +35,8 @@ export const DataCompliance = ({ scans }: DataComplianceProps) => {
return (
<div className="flex flex-col gap-4">
<div className="grid grid-cols-1 items-center gap-x-4 gap-y-4 md:grid-cols-2 lg:grid-cols-3">
<SelectScanComplianceData
<div className="flex max-w-fit">
<ScanSelector
scans={scans}
selectedScanId={selectedScanId}
onSelectionChange={handleScanChange}
@@ -1,2 +1,2 @@
export * from "./data-compliance";
export * from "./select-scan-compliance-data";
export * from "./scan-selector";
@@ -16,7 +16,7 @@ export interface SelectScanComplianceDataProps {
onSelectionChange: (selectedKey: string) => void;
}
export const SelectScanComplianceData = ({
export const ScanSelector = ({
scans,
selectedScanId,
onSelectionChange,
@@ -26,7 +26,7 @@ export const SelectScanComplianceData = ({
aria-label="Select a Scan"
placeholder="Select a scan"
classNames={{
selectorIcon: "right-2",
trigger: "w-full min-w-[365px]",
}}
size="lg"
labelPlacement="outside"
+1 -1
View File
@@ -12,7 +12,7 @@ export * from "./compliance-custom-details/iso-details";
export * from "./compliance-header/compliance-header";
export * from "./compliance-header/compliance-scan-info";
export * from "./compliance-header/data-compliance";
export * from "./compliance-header/select-scan-compliance-data";
export * from "./compliance-header/scan-selector";
export * from "./no-scans-available";
export * from "./skeletons/bar-chart-skeleton";
export * from "./skeletons/compliance-accordion-skeleton";
@@ -20,8 +20,15 @@ import React, {
useState,
} from "react";
import { ComplianceScanInfo } from "@/components/compliance/compliance-header/compliance-scan-info";
import { EntityInfoShort } from "@/components/ui/entities";
import { CustomDropdownFilterProps } from "@/types";
import { isScanEntity } from "@/lib/helper-filters";
import {
CustomDropdownFilterProps,
FilterEntity,
ProviderEntity,
ScanEntity,
} from "@/types";
export const CustomDropdownFilter = ({
filter,
@@ -177,10 +184,25 @@ export const CustomDropdownFilter = ({
const getDisplayLabel = useCallback(
(value: string) => {
const entity = filter.valueLabelMapping?.find((entry) => entry[value])?.[
value
];
return entity?.alias || entity?.uid || value;
const entity: FilterEntity | undefined = filter.valueLabelMapping?.find(
(entry) => entry[value],
)?.[value];
if (!entity) return value;
if (isScanEntity(entity as ScanEntity)) {
return (
(entity as ScanEntity).attributes?.name ||
(entity as ScanEntity).providerInfo?.alias ||
(entity as ScanEntity).providerInfo?.uid ||
value
);
} else {
return (
(entity as ProviderEntity).alias ||
(entity as ProviderEntity).uid ||
value
);
}
},
[filter.valueLabelMapping],
);
@@ -239,7 +261,7 @@ export const CustomDropdownFilter = ({
onKeyDown={(e) => {
if (e.key === "Enter" || e.key === " ") {
e.preventDefault();
handleClearAll(e as any);
handleClearAll(e as unknown as React.MouseEvent);
}
}}
>
@@ -251,7 +273,7 @@ export const CustomDropdownFilter = ({
</div>
</Button>
</PopoverTrigger>
<PopoverContent className="w-80 dark:bg-prowler-blue-800">
<PopoverContent className="w-auto min-w-80 dark:bg-prowler-blue-800">
<div className="flex w-full flex-col gap-4 p-2">
<CheckboxGroup
color="default"
@@ -279,9 +301,10 @@ export const CustomDropdownFilter = ({
className="flex max-h-96 max-w-full flex-col gap-y-2 py-2"
>
{filterValues.map((value) => {
const entity = filter.valueLabelMapping?.find(
(entry) => entry[value],
)?.[value];
const entity: FilterEntity | undefined =
filter.valueLabelMapping?.find((entry) => entry[value])?.[
value
];
return (
<Checkbox
@@ -293,12 +316,18 @@ export const CustomDropdownFilter = ({
value={value}
>
{entity ? (
<EntityInfoShort
cloudProvider={entity.provider}
entityAlias={entity.alias ?? undefined}
entityId={entity.uid}
hideCopyButton
/>
isScanEntity(entity as ScanEntity) ? (
<ComplianceScanInfo scan={entity as ScanEntity} />
) : (
<EntityInfoShort
cloudProvider={(entity as ProviderEntity).provider}
entityAlias={
(entity as ProviderEntity).alias ?? undefined
}
entityId={(entity as ProviderEntity).uid}
hideCopyButton
/>
)
) : (
value
)}
+6 -2
View File
@@ -30,9 +30,13 @@ export const DateWithTime: React.FC<DateWithTimeProps> = ({
<div
className={`flex ${inline ? "flex-row items-center gap-2" : "flex-col"}`}
>
<span className="text-xs font-semibold">{formattedDate}</span>
<span className="whitespace-nowrap text-xs font-semibold">
{formattedDate}
</span>
{showTime && (
<span className="text-xs text-gray-500">{formattedTime}</span>
<span className="whitespace-nowrap text-xs text-gray-500">
{formattedTime}
</span>
)}
</div>
</div>
@@ -1,3 +1,4 @@
import { Tooltip } from "@nextui-org/react";
import React from "react";
import { IdIcon } from "@/components/icons";
@@ -11,6 +12,7 @@ interface EntityInfoProps {
entityAlias?: string;
entityId?: string;
hideCopyButton?: boolean;
snippetWidth?: string;
}
export const EntityInfoShort: React.FC<EntityInfoProps> = ({
@@ -20,12 +22,16 @@ export const EntityInfoShort: React.FC<EntityInfoProps> = ({
hideCopyButton = false,
}) => {
return (
<div className="flex w-full items-center justify-between space-x-2">
<div className="flex items-center gap-x-2">
<div className="flex items-center justify-start">
<div className="flex items-center justify-between gap-x-2">
<div className="flex-shrink-0">{getProviderLogo(cloudProvider)}</div>
<div className="flex flex-col">
<div className="flex max-w-[120px] flex-col">
{entityAlias && (
<span className="text-xs text-default-500">{entityAlias}</span>
<Tooltip content={entityAlias} placement="top" size="sm">
<span className="truncate text-ellipsis text-xs text-default-500">
{entityAlias}
</span>
</Tooltip>
)}
<SnippetChip
value={entityId ?? ""}
+9 -2
View File
@@ -23,6 +23,10 @@ export const SnippetChip = ({
return (
<Snippet
className={cn("h-6", className)}
classNames={{
content: "min-w-0 overflow-hidden",
pre: "min-w-0 overflow-hidden text-ellipsis whitespace-nowrap",
}}
color="default"
size="sm"
variant="flat"
@@ -34,10 +38,13 @@ export const SnippetChip = ({
codeString={value}
{...props}
>
<div className="flex items-center space-x-2" aria-label={ariaLabel}>
<div
className="flex min-w-0 items-center space-x-2"
aria-label={ariaLabel}
>
{icon}
<Tooltip content={value} placement="top" size="sm">
<span className="no-scrollbar max-w-24 overflow-hidden overflow-x-scroll text-ellipsis whitespace-nowrap text-xs">
<span className="min-w-0 flex-1 truncate text-xs">
{formatter ? formatter(value) : value}
</span>
</Tooltip>
+54
View File
@@ -1,3 +1,6 @@
import { ProviderProps, ProvidersApiResponse, ScanProps } from "@/types";
import { ScanEntity } from "@/types/scans";
/**
* Extracts normalized filters and search query from the URL search params.
* Used Server Side Rendering (SSR). There is a hook (useUrlFilters) for client side.
@@ -44,3 +47,54 @@ export const extractSortAndKey = (searchParams: Record<string, unknown>) => {
return { searchParamsKey, rawSort, encodedSort };
};
export const isScanEntity = (entity: ScanEntity) => {
return entity && entity.providerInfo && entity.attributes;
};
/**
* Creates a scan details mapping for filters from completed scans.
* Used to provide detailed information for scan filters in the UI.
*/
export const createScanDetailsMapping = (
completedScans: ScanProps[],
providersData?: ProvidersApiResponse,
) => {
if (!completedScans || completedScans.length === 0) {
return [];
}
const scanMappings = completedScans.map((scan: ScanProps) => {
// Get provider info from providerInfo if available, or find from providers data
let providerInfo = scan.providerInfo;
if (!providerInfo && scan.relationships?.provider?.data?.id) {
const provider = providersData?.data?.find(
(p: ProviderProps) => p.id === scan.relationships.provider.data.id,
);
if (provider) {
providerInfo = {
provider: provider.attributes.provider,
alias: provider.attributes.alias,
uid: provider.attributes.uid,
};
}
}
return {
[scan.id]: {
providerInfo: {
provider: providerInfo?.provider || "aws",
alias: providerInfo?.alias,
uid: providerInfo?.uid,
},
attributes: {
name: scan.attributes.name,
completed_at: scan.attributes.completed_at,
},
},
};
});
return scanMappings;
};
+2 -2
View File
@@ -1,5 +1,5 @@
import {
ProviderAccountProps,
ProviderEntity,
ProviderProps,
ProvidersApiResponse,
} from "@/types/providers";
@@ -21,7 +21,7 @@ export const extractProviderUIDs = (
export const createProviderDetailsMapping = (
providerUIDs: string[],
providersData: ProvidersApiResponse,
): Array<{ [uid: string]: ProviderAccountProps }> => {
): Array<{ [uid: string]: ProviderEntity }> => {
if (!providersData?.data) return [];
return providerUIDs.map((uid) => {
+44 -44
View File
@@ -37,7 +37,7 @@
"jose": "^5.9.3",
"jwt-decode": "^4.0.0",
"lucide-react": "^0.471.0",
"next": "^14.2.26",
"next": "14.2.29",
"next-auth": "^5.0.0-beta.25",
"next-themes": "^0.2.1",
"radix-ui": "^1.1.3",
@@ -988,9 +988,9 @@
}
},
"node_modules/@next/env": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/env/-/env-14.2.27.tgz",
"integrity": "sha512-VLGHu7aBMK0rmSEPjx6qb4njGYfEfN5HpeYV32II1dNZZvPxqa+RfWVgPf4q6hmicavceAGeQneTxofx7Zm/yw==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/env/-/env-14.2.29.tgz",
"integrity": "sha512-UzgLR2eBfhKIQt0aJ7PWH7XRPYw7SXz0Fpzdl5THjUnvxy4kfBk9OU4RNPNiETewEEtaBcExNFNn1QWH8wQTjg==",
"license": "MIT"
},
"node_modules/@next/eslint-plugin-next": {
@@ -1004,9 +1004,9 @@
}
},
"node_modules/@next/swc-darwin-arm64": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-14.2.27.tgz",
"integrity": "sha512-WKJsKqY1f8NkwcfVbUtoTjJ5e8Q2kEFhjM7tVFA3jqesetBR2EegUTed1Ov7lZebQ7XRrphAg665egiCLc9+Iw==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-14.2.29.tgz",
"integrity": "sha512-wWtrAaxCVMejxPHFb1SK/PVV1WDIrXGs9ki0C/kUM8ubKHQm+3hU9MouUywCw8Wbhj3pewfHT2wjunLEr/TaLA==",
"cpu": [
"arm64"
],
@@ -1020,9 +1020,9 @@
}
},
"node_modules/@next/swc-darwin-x64": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-14.2.27.tgz",
"integrity": "sha512-fsXAM07rt7FQ/dpPFk+YZ8LVQ48xP37KzPFAwdQFmVzNLgizdUyNSg9zwu7l0ziMtHFBofYgBXayg9qAxIhorQ==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-14.2.29.tgz",
"integrity": "sha512-7Z/jk+6EVBj4pNLw/JQrvZVrAh9Bv8q81zCFSfvTMZ51WySyEHWVpwCEaJY910LyBftv2F37kuDPQm0w9CEXyg==",
"cpu": [
"x64"
],
@@ -1036,9 +1036,9 @@
}
},
"node_modules/@next/swc-linux-arm64-gnu": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-14.2.27.tgz",
"integrity": "sha512-yMIvV5nTOk4p0TDhd9DU6QswEm8YjZnr1o9ZI7A6jh25JHvPsIvjgyTVSlnrGFKlNNtOOJCIv5mwVU7+4VZvsg==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-14.2.29.tgz",
"integrity": "sha512-o6hrz5xRBwi+G7JFTHc+RUsXo2lVXEfwh4/qsuWBMQq6aut+0w98WEnoNwAwt7hkEqegzvazf81dNiwo7KjITw==",
"cpu": [
"arm64"
],
@@ -1052,9 +1052,9 @@
}
},
"node_modules/@next/swc-linux-arm64-musl": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-14.2.27.tgz",
"integrity": "sha512-gpOtTwE9GUkp+VNPwTYFn1fN1UINQTulbgO8UJzBgi77g/+T+yQxfBsKUy2H96aKjoMT/AYfn3yyomNXXVoZZg==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-14.2.29.tgz",
"integrity": "sha512-9i+JEHBOVgqxQ92HHRFlSW1EQXqa/89IVjtHgOqsShCcB/ZBjTtkWGi+SGCJaYyWkr/lzu51NTMCfKuBf7ULNw==",
"cpu": [
"arm64"
],
@@ -1068,9 +1068,9 @@
}
},
"node_modules/@next/swc-linux-x64-gnu": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-14.2.27.tgz",
"integrity": "sha512-b7bogYfYyutEhyDST5qpBkmVENZz1mVOO2632KerJjwWgr2cdycAPU33VmpTVvTs/fT8+oeoUuZ31aQV6cUhpw==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-14.2.29.tgz",
"integrity": "sha512-B7JtMbkUwHijrGBOhgSQu2ncbCYq9E7PZ7MX58kxheiEOwdkM+jGx0cBb+rN5AeqF96JypEppK6i/bEL9T13lA==",
"cpu": [
"x64"
],
@@ -1084,9 +1084,9 @@
}
},
"node_modules/@next/swc-linux-x64-musl": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-14.2.27.tgz",
"integrity": "sha512-yGZX038wBDSRJ7tbZ6OFZtCUvLXZDVpw9rEgNUK/0PL++65hENaiMXhxJtupeCFqzHdMuJwrCnEW29saF4NmEw==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-14.2.29.tgz",
"integrity": "sha512-yCcZo1OrO3aQ38B5zctqKU1Z3klOohIxug6qdiKO3Q3qNye/1n6XIs01YJ+Uf+TdpZQ0fNrOQI2HrTLF3Zprnw==",
"cpu": [
"x64"
],
@@ -1100,9 +1100,9 @@
}
},
"node_modules/@next/swc-win32-arm64-msvc": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-14.2.27.tgz",
"integrity": "sha512-yRY9RzPpk+Jex4DthdKja8C3evh6jB+22AeVd6yTbcnGAFGXQWJTs6DfEcEfeFpqIEcIGbWYq7pinz6vRv7tJA==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-14.2.29.tgz",
"integrity": "sha512-WnrfeOEtTVidI9Z6jDLy+gxrpDcEJtZva54LYC0bSKQqmyuHzl0ego+v0F/v2aXq0am67BRqo/ybmmt45Tzo4A==",
"cpu": [
"arm64"
],
@@ -1116,9 +1116,9 @@
}
},
"node_modules/@next/swc-win32-ia32-msvc": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/swc-win32-ia32-msvc/-/swc-win32-ia32-msvc-14.2.27.tgz",
"integrity": "sha512-VSqDGpoKoUgkE2Ba4/89ZchktDOwPhKy3HgQgTf3gOhK/ZEibujLJN4qzp3rSIadn4cXUID3PmuEEM6uRPA7nQ==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/swc-win32-ia32-msvc/-/swc-win32-ia32-msvc-14.2.29.tgz",
"integrity": "sha512-vkcriFROT4wsTdSeIzbxaZjTNTFKjSYmLd8q/GVH3Dn8JmYjUKOuKXHK8n+lovW/kdcpIvydO5GtN+It2CvKWA==",
"cpu": [
"ia32"
],
@@ -1132,9 +1132,9 @@
}
},
"node_modules/@next/swc-win32-x64-msvc": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-14.2.27.tgz",
"integrity": "sha512-bK46G4uS5SVlq88FnxyupRuuaCfHPtB/7heBRAZCiHD9GdVktadjiQPCzlXWTKgv6pJxP8bE7J9GGDwodtn9Mw==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-14.2.29.tgz",
"integrity": "sha512-iPPwUEKnVs7pwR0EBLJlwxLD7TTHWS/AoVZx1l9ZQzfQciqaFEr5AlYzA2uB6Fyby1IF18t4PL0nTpB+k4Tzlw==",
"cpu": [
"x64"
],
@@ -13169,12 +13169,12 @@
"dev": true
},
"node_modules/next": {
"version": "14.2.27",
"resolved": "https://registry.npmjs.org/next/-/next-14.2.27.tgz",
"integrity": "sha512-xmTsnu6rbXVaupRmU2k3BHVpQp7kK+/Ge9XYZlwXQNS2IPP/U9ToDoO6tTSzZIV36fmDBnwKqBUd7KuFXTi0Mw==",
"version": "14.2.29",
"resolved": "https://registry.npmjs.org/next/-/next-14.2.29.tgz",
"integrity": "sha512-s98mCOMOWLGGpGOfgKSnleXLuegvvH415qtRZXpSp00HeEgdmrxmwL9cgKU+h4XrhB16zEI5d/7BnkS3ATInsA==",
"license": "MIT",
"dependencies": {
"@next/env": "14.2.27",
"@next/env": "14.2.29",
"@swc/helpers": "0.5.5",
"busboy": "1.6.0",
"caniuse-lite": "^1.0.30001579",
@@ -13189,15 +13189,15 @@
"node": ">=18.17.0"
},
"optionalDependencies": {
"@next/swc-darwin-arm64": "14.2.27",
"@next/swc-darwin-x64": "14.2.27",
"@next/swc-linux-arm64-gnu": "14.2.27",
"@next/swc-linux-arm64-musl": "14.2.27",
"@next/swc-linux-x64-gnu": "14.2.27",
"@next/swc-linux-x64-musl": "14.2.27",
"@next/swc-win32-arm64-msvc": "14.2.27",
"@next/swc-win32-ia32-msvc": "14.2.27",
"@next/swc-win32-x64-msvc": "14.2.27"
"@next/swc-darwin-arm64": "14.2.29",
"@next/swc-darwin-x64": "14.2.29",
"@next/swc-linux-arm64-gnu": "14.2.29",
"@next/swc-linux-arm64-musl": "14.2.29",
"@next/swc-linux-x64-gnu": "14.2.29",
"@next/swc-linux-x64-musl": "14.2.29",
"@next/swc-win32-arm64-msvc": "14.2.29",
"@next/swc-win32-ia32-msvc": "14.2.29",
"@next/swc-win32-x64-msvc": "14.2.29"
},
"peerDependencies": {
"@opentelemetry/api": "^1.1.0",
+1 -1
View File
@@ -29,7 +29,7 @@
"jose": "^5.9.3",
"jwt-decode": "^4.0.0",
"lucide-react": "^0.471.0",
"next": "^14.2.26",
"next": "14.2.29",
"next-auth": "^5.0.0-beta.25",
"next-themes": "^0.2.1",
"radix-ui": "^1.1.3",
+5 -2
View File
@@ -1,10 +1,13 @@
import { ProviderAccountProps } from "./providers";
import { ProviderEntity } from "./providers";
import { ScanEntity } from "./scans";
export type FilterEntity = ProviderEntity | ScanEntity;
export interface FilterOption {
key: string;
labelCheckboxGroup: string;
values: string[];
valueLabelMapping?: Array<{ [uid: string]: ProviderAccountProps }>;
valueLabelMapping?: Array<{ [uid: string]: FilterEntity }>;
index?: number;
showSelectAll?: boolean;
defaultToSelectAll?: boolean;
+1 -1
View File
@@ -45,7 +45,7 @@ export interface ProviderProps {
groupNames?: string[];
}
export interface ProviderAccountProps {
export interface ProviderEntity {
provider: ProviderType;
uid: string;
alias: string | null;
+12
View File
@@ -47,3 +47,15 @@ export interface ScanProps {
alias: string;
};
}
export interface ScanEntity {
providerInfo: {
provider: ProviderType;
alias?: string;
uid?: string;
};
attributes: {
name?: string;
completed_at: string;
};
}