Skip to content

Commit

Permalink
Protect: update threats data format and integrate threatsdataviews
Browse files Browse the repository at this point in the history
  • Loading branch information
dkmyta authored and nateweller committed Oct 29, 2024
1 parent 58f6f3e commit a49ddf7
Show file tree
Hide file tree
Showing 71 changed files with 657 additions and 4,118 deletions.
326 changes: 21 additions & 305 deletions pnpm-lock.yaml

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
import { type Threat } from '@automattic/jetpack-scan';
import { render, screen } from '@testing-library/react';
import ThreatsDataViews from '..';

Expand All @@ -14,9 +13,13 @@ const data = [
fixedIn: null,
fixedOn: '2024-10-07T20:45:06.000Z',
fixable: { fixer: 'rollback', target: 'January 26, 2024, 6:49 am', extensionStatus: '' },
fixer: { status: 'in_progress', startedAt: '2024-10-07T20:45:06.000Z' },
fixer: {
status: 'in_progress' as const,
startedAt: '2024-10-07T20:45:06.000Z',
last_updated: '2024-10-07T20:45:06.000Z',
},
severity: 8,
status: 'current',
status: 'current' as const,
filename: '/var/www/html/wp-content/index.php',
context: {
'1': 'echo <<<HTML',
Expand All @@ -37,7 +40,7 @@ const data = [
name: 'WooCommerce',
slug: 'woocommerce',
version: '3.2.3',
type: 'plugin',
type: 'plugin' as const,
},
fixedIn: '3.2.4',
context: null,
Expand All @@ -50,7 +53,7 @@ const data = [
signature: null,
status: null,
},
] as Threat[];
];

describe( 'ThreatsDataViews', () => {
it( 'renders threat data', () => {
Expand Down
2 changes: 1 addition & 1 deletion projects/js-packages/components/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@
"@wordpress/components": "28.9.0",
"@wordpress/compose": "7.9.0",
"@wordpress/data": "10.9.0",
"@wordpress/dataviews": "4.6.0",
"@wordpress/dataviews": "4.5.0",
"@wordpress/date": "5.9.0",
"@wordpress/element": "6.9.0",
"@wordpress/i18n": "5.9.0",
Expand Down
4 changes: 4 additions & 0 deletions projects/js-packages/scan/changelog/add-types-and-utils
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
Significance: minor
Type: added

Add threat types and scan utility functions
11 changes: 0 additions & 11 deletions projects/js-packages/scan/jest.config.cjs

This file was deleted.

8 changes: 6 additions & 2 deletions projects/js-packages/scan/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
"license": "GPL-2.0-or-later",
"author": "Automattic",
"scripts": {
"build": "pnpm run clean && pnpm run compile-ts",
"build": "pnpm run clean && webpack",
"clean": "rm -rf build/",
"compile-ts": "tsc --pretty",
"test": "jest"
Expand Down Expand Up @@ -52,13 +52,17 @@
"dependencies": {
"@automattic/jetpack-api": "workspace:*",
"@automattic/jetpack-base-styles": "workspace:*",
"@automattic/jetpack-webpack-config": "workspace:*",

Check failure on line 55 in projects/js-packages/scan/package.json

View workflow job for this annotation

GitHub Actions / Project structure

js-packages/scan is published and depends on `@automattic/jetpack-webpack-config`, but `@automattic/jetpack-webpack-config` is not being published.
"@wordpress/api-fetch": "7.9.0",
"@wordpress/element": "6.9.0",
"@wordpress/i18n": "5.9.0",
"@wordpress/icons": "10.9.0",
"@wordpress/url": "4.9.0",
"debug": "4.3.4",
"react": "^18.2.0",
"react-dom": "^18.2.0"
"react-dom": "^18.2.0",
"webpack": "5.94.0",
"webpack-cli": "4.9.1"
},
"peerDependencies": {
"@wordpress/i18n": "5.9.0",
Expand Down
6 changes: 3 additions & 3 deletions projects/js-packages/scan/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
export * from './types/index.js';
export * from './constants/index.js';
export * from './utils/index.js';
export * from './types';
export * from './constants';
export * from './utils';
Empty file.
23 changes: 23 additions & 0 deletions projects/js-packages/scan/src/types/fixers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,3 +15,26 @@ export type ThreatFixStatusSuccess = {
};

export type ThreatFixStatus = ThreatFixStatusError | ThreatFixStatusSuccess;

/**
* Fixers Status
*
* Overall status of all fixers.
*/
type FixersStatusBase = {
ok: boolean; // Discriminator for overall success
};

export type FixersStatusError = FixersStatusBase & {
ok: false;
error: string;
};

export type FixersStatusSuccess = FixersStatusBase & {
ok: true;
threats: {
[ key: number ]: ThreatFixStatus;
};
};

export type FixersStatus = FixersStatusSuccess | FixersStatusError;
5 changes: 3 additions & 2 deletions projects/js-packages/scan/src/types/index.ts
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
export * from './fixers.js';
export * from './threats.js';
export * from './fixers';
export * from './status';
export * from './threats';
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Threat } from './threats';
import { type Threat } from '..';

export type ExtensionStatus = {
/** The name of the extension. */
Expand Down Expand Up @@ -39,14 +39,8 @@ export type ScanStatus = {
/** The time the last scan was checked, in YYYY-MM-DD HH:MM:SS format. */
lastChecked: string | null;

/** The number of plugin threats found in the latest status. */
numPluginsThreats: number;

/** The number of theme threats found in the latest status. */
numThemesThreats: number;

/** The total number of threats found in the latest status. */
numThreats: number;
/** The security threats identified in the latest scan. */
threats: Threat[];

/** Whether there was an error in the scan results. */
error: boolean | null;
Expand All @@ -56,26 +50,4 @@ export type ScanStatus = {

/** The error message. */
errorMessage: string | null;

/** WordPress Core Status */
core: {
checked: boolean;
name: string;
slug: string;
threats: Threat[];
type: 'core';
version: string;
} | null;

/** Plugins Status */
plugins: ExtensionStatus[];

/** Themes Status */
themes: ExtensionStatus[];

/** File Threats */
files: Threat[];

/** Database Threats */
database: Threat[];
};
2 changes: 1 addition & 1 deletion projects/js-packages/scan/src/types/threats.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { ThreatFixStatus } from './fixers.js';
import { type ThreatFixStatus } from '..';

export type ThreatStatus = 'fixed' | 'ignored' | 'current';

Expand Down
46 changes: 43 additions & 3 deletions projects/js-packages/scan/src/utils/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import { FIXER_IS_STALE_THRESHOLD } from '../constants/index.js';
import { ThreatFixStatus } from '../types/fixers.js';
import { Threat } from '../types/threats.js';
import { code, color, grid, plugins, shield, wordpress } from '@wordpress/icons';
import { type Threat, type ThreatFixStatus, FIXER_IS_STALE_THRESHOLD } from '..';

export const getThreatType = ( threat: Threat ) => {
if ( threat.signature === 'Vulnerable.WP.Core' ) {
Expand All @@ -19,6 +18,47 @@ export const getThreatType = ( threat: Threat ) => {
return null;
};

export const getThreatSubtitle = ( threat: Threat ) => {
const type = getThreatType( threat );

switch ( type ) {
case 'plugin':
case 'theme':
return `${ threat.extension?.name } (${ threat.extension?.version })`;
case 'core':
return 'WordPress Core';
case 'file':
// Trim leading slash
if ( threat.filename.startsWith( '/' ) ) {
return threat.filename.slice( 1 );
}
return threat.filename;
case 'database':
return threat.table;
default:
return '';
}
};

export const getThreatIcon = ( threat: Threat ) => {
const type = getThreatType( threat );

switch ( type ) {
case 'plugin':
return plugins;
case 'theme':
return color;
case 'core':
return wordpress;
case 'file':
return code;
case 'database':
return grid;
default:
return shield;
}
};

export const fixerTimestampIsStale = ( lastUpdatedTimestamp: string ) => {
const now = new Date();
const lastUpdated = new Date( lastUpdatedTimestamp );
Expand Down
10 changes: 2 additions & 8 deletions projects/js-packages/scan/tsconfig.json
Original file line number Diff line number Diff line change
@@ -1,10 +1,4 @@
{
"extends": "jetpack-js-tools/tsconfig.tsc.json",
"include": [ "./src/**/*" ],
"compilerOptions": {
"typeRoots": [ "./node_modules/@types/", "src/types/*" ],
"sourceMap": false,
"outDir": "./build/",
"target": "esnext"
}
"extends": "jetpack-js-tools/tsconfig.base.json",
"include": [ "./src/**/*" ]
}
53 changes: 53 additions & 0 deletions projects/js-packages/scan/webpack.config.cjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
const path = require( 'path' );
const jetpackWebpackConfig = require( '@automattic/jetpack-webpack-config/webpack' );

module.exports = [
{
entry: {
index: './src/index.ts',
},
mode: jetpackWebpackConfig.mode,
devtool: jetpackWebpackConfig.devtool,
output: {
...jetpackWebpackConfig.output,
path: path.resolve( './build' ),
},
optimization: {
...jetpackWebpackConfig.optimization,
},
resolve: {
...jetpackWebpackConfig.resolve,
},
node: false,
plugins: [ ...jetpackWebpackConfig.StandardPlugins() ],
module: {
strictExportPresence: true,
rules: [
// Transpile JavaScript
jetpackWebpackConfig.TranspileRule( {
exclude: /node_modules\//,
} ),

// Transpile @automattic/jetpack-* in node_modules too.
jetpackWebpackConfig.TranspileRule( {
includeNodeModules: [ '@automattic/jetpack-' ],
} ),

// Handle CSS.
jetpackWebpackConfig.CssRule( {
extensions: [ 'css', 'sass', 'scss' ],
extraLoaders: [ 'sass-loader' ],
} ),

// Handle images.
jetpackWebpackConfig.FileRule(),
],
},
externals: {
...jetpackWebpackConfig.externals,
jetpackConfig: JSON.stringify( {
consumer_slug: 'my_jetpack',
} ),
},
},
];
Original file line number Diff line number Diff line change
Expand Up @@ -24,28 +24,14 @@ export const ScanAndThreatStatus = () => {
const {
protect: { scanData },
} = getMyJetpackWindowInitialState();
const { plugins, themes, num_threats: numThreats = 0 } = scanData || {};
const numThreats = scanData.threats.length;

const criticalScanThreatCount = useMemo( () => {
const { core, database, files, num_plugins_threats, num_themes_threats } = scanData || {};
const pluginsThreats = num_plugins_threats
? plugins.reduce( ( accum, plugin ) => accum.concat( plugin.threats ), [] )
: [];
const themesThreats = num_themes_threats
? themes.reduce( ( accum, theme ) => accum.concat( theme.threats ), [] )
: [];
const allThreats = [
...pluginsThreats,
...themesThreats,
...( core?.threats ?? [] ),
...database,
...files,
];
return allThreats.reduce(
return scanData.threats.reduce(
( accum, threat ) => ( threat.severity >= 5 ? ( accum += 1 ) : accum ),
0
);
}, [ plugins, themes, scanData ] );
}, [ scanData.threats ] );

if ( isPluginActive && isSiteConnected ) {
if ( hasProtectPaidPlan ) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,14 +13,10 @@ export const useLastScanText = () => {
themes,
protect: { scanData },
} = getMyJetpackWindowInitialState();
const {
plugins: fromScanPlugins,
themes: fromScanThemes,
last_checked: lastScanTime = null,
} = scanData || {};
const { last_checked: lastScanTime = null } = scanData || {};

const pluginsCount = fromScanPlugins.length || Object.keys( plugins ).length;
const themesCount = fromScanThemes.length || Object.keys( themes ).length;
const pluginsCount = Object.keys( plugins ).length;
const themesCount = Object.keys( themes ).length;

const timeSinceLastScan = lastScanTime ? timeSince( Date.parse( lastScanTime ) ) : false;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,19 +35,15 @@ export function useProtectTooltipCopy(): TooltipContent {
themes,
protect: { scanData, wafConfig: wafData },
} = getMyJetpackWindowInitialState();
const {
plugins: fromScanPlugins,
themes: fromScanThemes,
num_threats: numThreats = 0,
} = scanData || {};
const numThreats = scanData.threats.length;
const {
jetpack_waf_automatic_rules: isAutoFirewallEnabled,
blocked_logins: blockedLoginsCount,
brute_force_protection: hasBruteForceProtection,
} = wafData || {};

const pluginsCount = fromScanPlugins.length || Object.keys( plugins ).length;
const themesCount = fromScanThemes.length || Object.keys( themes ).length;
const pluginsCount = Object.keys( plugins ).length;
const themesCount = Object.keys( themes ).length;

const settingsLink = useMemo( () => {
if ( isProtectPluginActive ) {
Expand Down
5 changes: 5 additions & 0 deletions projects/packages/my-jetpack/changelog/protect-status-compat
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
Significance: patch
Type: changed
Comment: Package compatibility updates, no functional changes.


Loading

0 comments on commit a49ddf7

Please sign in to comment.