PMD Apex code scan using DX
- Interested in VS Code Extension for PMD Apex Code scan?
Topics
Make sure you have java installed
java --version
openjdk 11.0.14.1 2022-02-08
OpenJDK Runtime Environment Homebrew (build 11.0.14.1+0)
OpenJDK 64-Bit Server VM Homebrew (build 11.0.14.1+0, mixed mode)
Download and install pmd distribution - pmd-bin-6.47.0
-
from pmd-bin-6.47.0
-
unzip the file pmd-bin-6.47.0.zip
jar xvf pmd-bin-6.47.0.zip
- go to bin folder of the extracted pmd-bin-6.47.0.zip
- do this copy
cd pmd-bin-6.47.0/bin
cp run.sh pmd-run.sh
- put this folder:
pmd-bin-6.47.0/bin
in your PATH (~/.zshrc or ~/.bashrc
) - example in ~/.zshrc
# PMD env var holds the location of your PMD install
export PMD="/Users/mchinnappan/node-pmd/pmd-bin-6.47.0"
# let us put the bin folder of the PMD in path
export PATH="$PATH:$PMD/bin"
- make it executable
chmod +x pmd-run.sh
Extract Apex Classes from your Org
Login into the Org
sfdx force:auth:web:login
Successfully authorized mohan.chinnappan.n_ea2@gmail.com with org ID 00D3h000007R1LuEAK
Get the Apex Classes using DX
sfdx mohanc:mdapi:retrieve -u mohan.chinnappan.n_ea2@gmail.com -t "ApexClass"
cd /tmp/
/tmp >mkdir apex
/tmp >cd apex
/tmp/apex >sfdx mohanc:mdapi:checkRetrieveStatus -u mohan.chinnappan.n_ea2@gmail.com -i "09S3h000006DK3lEAG"
jar xvf 09S3h000006DK3lEAG.zip
Download the apex_ruleset.xml to your ~/.pmd folder
- create folder
mkdir ~/.pmd
- copy the apex_ruleset.xml from:
- apex_ruleset.xml
- to the folder ~/.pmd
Check for @SuppressWarning annotations in the code
grep -irn '@SuppressWarnings' unpackaged/classes
unpackaged/classes/GeocodingService.cls:1:@SuppressWarnings('PMD.ExcessiveParameterList')
Using VS Code
Run pmd csv output
- your apex class files are at: /tmp/apex/unpackaged/classes/
- csv output
pmd-run.sh pmd -R ~/.pmd/apex_ruleset.xml -d /tmp/apex/unpackaged/classes/ -f csv > /tmp/apex/pmd-results.csv
Script for CI/CD Pipeline cicd-pmd.sh
# Script for pipeline
# Bails out if count of P1,P2 and P3 are not zero
# -----------------------------------------
#----- configure the following to meet your needs ----
RULESET=~/.pmd/apex_ruleset.xml
MSG="Number of P1,P2 and P3 issues are"
THRESHOLD=4
CODE=/tmp/apex/unpackaged/classes/
#-----------------------------------------------------
# Run the pmd
echo pmd-run.sh pmd -R $RULESET -d $CODE -f csv > results.csv
pmd-run.sh pmd -R $RULESET -d $CODE -f csv > results.csv
# query the results using SQL
echo "SELECT COUNT(*) AS CNT FROM CSV(\"results.csv\", {headers:true}) WHERE Priority < $THRESHOLD" > q.sql
cat q.sql
sfdx mohanc:data:query:sql -q q.sql > out.json
# check for the errors
nerrors=`sfdx mohanc:data:jq -f '.[].CNT' -i out.json`
echo "nerrors: $nerrors"
if [ "$nerrors" != 0 ]
then
echo "$MSG: $nerrors. Stopping the deployment!"
exit 2
fi
echo "Continue the deployment..."
Sample Run
bash cicd-pmd.sh
Jan 10, 2023 9:42:14 PM net.sourceforge.pmd.PMD encourageToUseIncrementalAnalysis
WARNING: This analysis could be faster, please consider using Incremental Analysis: https://pmd.github.io/pmd-6.47.0/pmd_userdocs_incremental_analysis.html
nerrors: 0
Continue the deployment...
Sample Run with bailing out
Github Actions - PMD workflow bailing out when violations count is not zero
- uses: pmd/pmd-github-action@v1
id: pmd
with:
version: '6.40.0'
sourcePath: 'mc2Project/force-app/main/default/classes'
rulesets: 'pmd/rulesets/apex_ruleset.xml'
- name: Fail build if there are violations
if: steps.pmd.outputs.violations != 0
run: exit 1
Open the results csv file
open /tmp/apex/pmd-results.csv
Run pmd html output
- your apex class files are at: /tmp/apex/unpackaged/classes/
- html output
pmd-run.sh pmd -R ~/.pmd/apex_ruleset.xml -d /tmp/apex/unpackaged/classes/ -f html > /tmp/apex/pmd-results.html
Open the results html file
open /tmp/apex/pmd-results.html
Run pmd enhanced html output
pmd-run.sh pmd -R ~/.pmd/apex_ruleset.xml -d ./unpackaged/classes -f xslt -property xsltFilename=html-report-v2.xslt > pmd-report.html
Screenshot
Demo
Rule set info
-
P1 and P2 are from the PMD default rulesets:
-
As shown here: Default
-
The ruleset that is we use is on the top these default rulesets.
-
The ruleset (which most of the PMD customers use ):