diff --git a/404.html b/404.html new file mode 100644 index 0000000000..29fd3ea54b --- /dev/null +++ b/404.html @@ -0,0 +1,1440 @@ + + + + + + + + +Page Not Found | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + + +
+
 
+ +
+ + + +
+ + + + + + + + + + + + + + +
+ + + + +
+
+

Page Not Found

+
+ + + +
+ + + + + + + + +
+ + + + + + + + + + Edit me + + + +

Sorry, but the page you were trying to view does not exist. Check the URL for correctness, or try using keyword search using our search bar.

+ +

Back to the index

+ + +
+ +
+ + + +
+ +
+ +
+
+ +
+
+ + +
+ +
+ +
+
+ + + diff --git a/css/bootstrap.min.css b/css/bootstrap.min.css new file mode 100755 index 0000000000..7b4112f07e --- /dev/null +++ b/css/bootstrap.min.css @@ -0,0 +1,5 @@ +/*! + * Bootstrap v3.3.2 (http://getbootstrap.com) + * Copyright 2011-2016 Twitter, Inc. + * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE) + *//*! normalize.css v3.0.2 | MIT License | git.io/normalize */html{font-family:sans-serif;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%}body{margin:0}article,aside,details,figcaption,figure,footer,header,hgroup,main,menu,nav,section,summary{display:block}audio,canvas,progress,video{display:inline-block;vertical-align:baseline}audio:not([controls]){display:none;height:0}[hidden],template{display:none}a{background-color:transparent}a:active,a:hover{outline:0}abbr[title]{border-bottom:1px dotted}b,strong{font-weight:700}dfn{font-style:italic}h1{margin:.67em 0;font-size:2em}mark{color:#000;background:#ff0}small{font-size:80%}sub,sup{position:relative;font-size:75%;line-height:0;vertical-align:baseline}sup{top:-.5em}sub{bottom:-.25em}img{border:0}svg:not(:root){overflow:hidden}figure{margin:1em 40px}hr{height:0;-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box}pre{overflow:auto}code,kbd,pre,samp{font-family:monospace,monospace;font-size:1em}button,input,optgroup,select,textarea{margin:0;font:inherit;color:inherit}button{overflow:visible}button,select{text-transform:none}button,html input[type=button],input[type=reset],input[type=submit]{-webkit-appearance:button;cursor:pointer}button[disabled],html input[disabled]{cursor:default}button::-moz-focus-inner,input::-moz-focus-inner{padding:0;border:0}input{line-height:normal}input[type=checkbox],input[type=radio]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;padding:0}input[type=number]::-webkit-inner-spin-button,input[type=number]::-webkit-outer-spin-button{height:auto}input[type=search]{-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box;-webkit-appearance:textfield}input[type=search]::-webkit-search-cancel-button,input[type=search]::-webkit-search-decoration{-webkit-appearance:none}fieldset{padding:.35em .625em .75em;margin:0 2px;border:1px solid silver}legend{padding:0;border:0}textarea{overflow:auto}optgroup{font-weight:700}table{border-spacing:0;border-collapse:collapse}td,th{padding:0}/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */@media print{*,:after,:before{/*color:#000!important;*/text-shadow:none!important;/*background:0 0!important*/;-webkit-box-shadow:none!important;box-shadow:none!important}a,a:visited{text-decoration:underline}a[href]:after{content:" (" attr(href) ")"}abbr[title]:after{content:" (" attr(title) ")"}a[href^="javascript:"]:after,a[href^="#"]:after{content:""}blockquote,pre{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}img,tr{page-break-inside:avoid}img{max-width:100%!important}h2,h3,p{orphans:3;widows:3}h2,h3{page-break-after:avoid}select{background:#fff!important}.navbar{display:none}.btn>.caret,.dropup>.btn>.caret{border-top-color:#000!important}.label{border:1px solid #000}.table{border-collapse:collapse!important}.table td,.table th{background-color:#fff!important}.table-bordered td,.table-bordered th{border:1px solid #ddd!important}}@font-face{font-family:'Glyphicons Halflings';src:url(../fonts/glyphicons-halflings-regular.eot);src:url(../fonts/glyphicons-halflings-regular.eot?#iefix) format('embedded-opentype'),url(../fonts/glyphicons-halflings-regular.woff2) format('woff2'),url(../fonts/glyphicons-halflings-regular.woff) format('woff'),url(../fonts/glyphicons-halflings-regular.ttf) format('truetype'),url(../fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular) format('svg')}.glyphicon{position:relative;top:1px;display:inline-block;font-family:'Glyphicons Halflings';font-style:normal;font-weight:400;line-height:1;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.glyphicon-asterisk:before{content:"\2a"}.glyphicon-plus:before{content:"\2b"}.glyphicon-eur:before,.glyphicon-euro:before{content:"\20ac"}.glyphicon-minus:before{content:"\2212"}.glyphicon-cloud:before{content:"\2601"}.glyphicon-envelope:before{content:"\2709"}.glyphicon-pencil:before{content:"\270f"}.glyphicon-glass:before{content:"\e001"}.glyphicon-music:before{content:"\e002"}.glyphicon-search:before{content:"\e003"}.glyphicon-heart:before{content:"\e005"}.glyphicon-star:before{content:"\e006"}.glyphicon-star-empty:before{content:"\e007"}.glyphicon-user:before{content:"\e008"}.glyphicon-film:before{content:"\e009"}.glyphicon-th-large:before{content:"\e010"}.glyphicon-th:before{content:"\e011"}.glyphicon-th-list:before{content:"\e012"}.glyphicon-ok:before{content:"\e013"}.glyphicon-remove:before{content:"\e014"}.glyphicon-zoom-in:before{content:"\e015"}.glyphicon-zoom-out:before{content:"\e016"}.glyphicon-off:before{content:"\e017"}.glyphicon-signal:before{content:"\e018"}.glyphicon-cog:before{content:"\e019"}.glyphicon-trash:before{content:"\e020"}.glyphicon-home:before{content:"\e021"}.glyphicon-file:before{content:"\e022"}.glyphicon-time:before{content:"\e023"}.glyphicon-road:before{content:"\e024"}.glyphicon-download-alt:before{content:"\e025"}.glyphicon-download:before{content:"\e026"}.glyphicon-upload:before{content:"\e027"}.glyphicon-inbox:before{content:"\e028"}.glyphicon-play-circle:before{content:"\e029"}.glyphicon-repeat:before{content:"\e030"}.glyphicon-refresh:before{content:"\e031"}.glyphicon-list-alt:before{content:"\e032"}.glyphicon-lock:before{content:"\e033"}.glyphicon-flag:before{content:"\e034"}.glyphicon-headphones:before{content:"\e035"}.glyphicon-volume-off:before{content:"\e036"}.glyphicon-volume-down:before{content:"\e037"}.glyphicon-volume-up:before{content:"\e038"}.glyphicon-qrcode:before{content:"\e039"}.glyphicon-barcode:before{content:"\e040"}.glyphicon-tag:before{content:"\e041"}.glyphicon-tags:before{content:"\e042"}.glyphicon-book:before{content:"\e043"}.glyphicon-bookmark:before{content:"\e044"}.glyphicon-print:before{content:"\e045"}.glyphicon-camera:before{content:"\e046"}.glyphicon-font:before{content:"\e047"}.glyphicon-bold:before{content:"\e048"}.glyphicon-italic:before{content:"\e049"}.glyphicon-text-height:before{content:"\e050"}.glyphicon-text-width:before{content:"\e051"}.glyphicon-align-left:before{content:"\e052"}.glyphicon-align-center:before{content:"\e053"}.glyphicon-align-right:before{content:"\e054"}.glyphicon-align-justify:before{content:"\e055"}.glyphicon-list:before{content:"\e056"}.glyphicon-indent-left:before{content:"\e057"}.glyphicon-indent-right:before{content:"\e058"}.glyphicon-facetime-video:before{content:"\e059"}.glyphicon-picture:before{content:"\e060"}.glyphicon-map-marker:before{content:"\e062"}.glyphicon-adjust:before{content:"\e063"}.glyphicon-tint:before{content:"\e064"}.glyphicon-edit:before{content:"\e065"}.glyphicon-share:before{content:"\e066"}.glyphicon-check:before{content:"\e067"}.glyphicon-move:before{content:"\e068"}.glyphicon-step-backward:before{content:"\e069"}.glyphicon-fast-backward:before{content:"\e070"}.glyphicon-backward:before{content:"\e071"}.glyphicon-play:before{content:"\e072"}.glyphicon-pause:before{content:"\e073"}.glyphicon-stop:before{content:"\e074"}.glyphicon-forward:before{content:"\e075"}.glyphicon-fast-forward:before{content:"\e076"}.glyphicon-step-forward:before{content:"\e077"}.glyphicon-eject:before{content:"\e078"}.glyphicon-chevron-left:before{content:"\e079"}.glyphicon-chevron-right:before{content:"\e080"}.glyphicon-plus-sign:before{content:"\e081"}.glyphicon-minus-sign:before{content:"\e082"}.glyphicon-remove-sign:before{content:"\e083"}.glyphicon-ok-sign:before{content:"\e084"}.glyphicon-question-sign:before{content:"\e085"}.glyphicon-info-sign:before{content:"\e086"}.glyphicon-screenshot:before{content:"\e087"}.glyphicon-remove-circle:before{content:"\e088"}.glyphicon-ok-circle:before{content:"\e089"}.glyphicon-ban-circle:before{content:"\e090"}.glyphicon-arrow-left:before{content:"\e091"}.glyphicon-arrow-right:before{content:"\e092"}.glyphicon-arrow-up:before{content:"\e093"}.glyphicon-arrow-down:before{content:"\e094"}.glyphicon-share-alt:before{content:"\e095"}.glyphicon-resize-full:before{content:"\e096"}.glyphicon-resize-small:before{content:"\e097"}.glyphicon-exclamation-sign:before{content:"\e101"}.glyphicon-gift:before{content:"\e102"}.glyphicon-leaf:before{content:"\e103"}.glyphicon-fire:before{content:"\e104"}.glyphicon-eye-open:before{content:"\e105"}.glyphicon-eye-close:before{content:"\e106"}.glyphicon-warning-sign:before{content:"\e107"}.glyphicon-plane:before{content:"\e108"}.glyphicon-calendar:before{content:"\e109"}.glyphicon-random:before{content:"\e110"}.glyphicon-comment:before{content:"\e111"}.glyphicon-magnet:before{content:"\e112"}.glyphicon-chevron-up:before{content:"\e113"}.glyphicon-chevron-down:before{content:"\e114"}.glyphicon-retweet:before{content:"\e115"}.glyphicon-shopping-cart:before{content:"\e116"}.glyphicon-folder-close:before{content:"\e117"}.glyphicon-folder-open:before{content:"\e118"}.glyphicon-resize-vertical:before{content:"\e119"}.glyphicon-resize-horizontal:before{content:"\e120"}.glyphicon-hdd:before{content:"\e121"}.glyphicon-bullhorn:before{content:"\e122"}.glyphicon-bell:before{content:"\e123"}.glyphicon-certificate:before{content:"\e124"}.glyphicon-thumbs-up:before{content:"\e125"}.glyphicon-thumbs-down:before{content:"\e126"}.glyphicon-hand-right:before{content:"\e127"}.glyphicon-hand-left:before{content:"\e128"}.glyphicon-hand-up:before{content:"\e129"}.glyphicon-hand-down:before{content:"\e130"}.glyphicon-circle-arrow-right:before{content:"\e131"}.glyphicon-circle-arrow-left:before{content:"\e132"}.glyphicon-circle-arrow-up:before{content:"\e133"}.glyphicon-circle-arrow-down:before{content:"\e134"}.glyphicon-globe:before{content:"\e135"}.glyphicon-wrench:before{content:"\e136"}.glyphicon-tasks:before{content:"\e137"}.glyphicon-filter:before{content:"\e138"}.glyphicon-briefcase:before{content:"\e139"}.glyphicon-fullscreen:before{content:"\e140"}.glyphicon-dashboard:before{content:"\e141"}.glyphicon-paperclip:before{content:"\e142"}.glyphicon-heart-empty:before{content:"\e143"}.glyphicon-link:before{content:"\e144"}.glyphicon-phone:before{content:"\e145"}.glyphicon-pushpin:before{content:"\e146"}.glyphicon-usd:before{content:"\e148"}.glyphicon-gbp:before{content:"\e149"}.glyphicon-sort:before{content:"\e150"}.glyphicon-sort-by-alphabet:before{content:"\e151"}.glyphicon-sort-by-alphabet-alt:before{content:"\e152"}.glyphicon-sort-by-order:before{content:"\e153"}.glyphicon-sort-by-order-alt:before{content:"\e154"}.glyphicon-sort-by-attributes:before{content:"\e155"}.glyphicon-sort-by-attributes-alt:before{content:"\e156"}.glyphicon-unchecked:before{content:"\e157"}.glyphicon-expand:before{content:"\e158"}.glyphicon-collapse-down:before{content:"\e159"}.glyphicon-collapse-up:before{content:"\e160"}.glyphicon-log-in:before{content:"\e161"}.glyphicon-flash:before{content:"\e162"}.glyphicon-log-out:before{content:"\e163"}.glyphicon-new-window:before{content:"\e164"}.glyphicon-record:before{content:"\e165"}.glyphicon-save:before{content:"\e166"}.glyphicon-open:before{content:"\e167"}.glyphicon-saved:before{content:"\e168"}.glyphicon-import:before{content:"\e169"}.glyphicon-export:before{content:"\e170"}.glyphicon-send:before{content:"\e171"}.glyphicon-floppy-disk:before{content:"\e172"}.glyphicon-floppy-saved:before{content:"\e173"}.glyphicon-floppy-remove:before{content:"\e174"}.glyphicon-floppy-save:before{content:"\e175"}.glyphicon-floppy-open:before{content:"\e176"}.glyphicon-credit-card:before{content:"\e177"}.glyphicon-transfer:before{content:"\e178"}.glyphicon-cutlery:before{content:"\e179"}.glyphicon-header:before{content:"\e180"}.glyphicon-compressed:before{content:"\e181"}.glyphicon-earphone:before{content:"\e182"}.glyphicon-phone-alt:before{content:"\e183"}.glyphicon-tower:before{content:"\e184"}.glyphicon-stats:before{content:"\e185"}.glyphicon-sd-video:before{content:"\e186"}.glyphicon-hd-video:before{content:"\e187"}.glyphicon-subtitles:before{content:"\e188"}.glyphicon-sound-stereo:before{content:"\e189"}.glyphicon-sound-dolby:before{content:"\e190"}.glyphicon-sound-5-1:before{content:"\e191"}.glyphicon-sound-6-1:before{content:"\e192"}.glyphicon-sound-7-1:before{content:"\e193"}.glyphicon-copyright-mark:before{content:"\e194"}.glyphicon-registration-mark:before{content:"\e195"}.glyphicon-cloud-download:before{content:"\e197"}.glyphicon-cloud-upload:before{content:"\e198"}.glyphicon-tree-conifer:before{content:"\e199"}.glyphicon-tree-deciduous:before{content:"\e200"}.glyphicon-cd:before{content:"\e201"}.glyphicon-save-file:before{content:"\e202"}.glyphicon-open-file:before{content:"\e203"}.glyphicon-level-up:before{content:"\e204"}.glyphicon-copy:before{content:"\e205"}.glyphicon-paste:before{content:"\e206"}.glyphicon-alert:before{content:"\e209"}.glyphicon-equalizer:before{content:"\e210"}.glyphicon-king:before{content:"\e211"}.glyphicon-queen:before{content:"\e212"}.glyphicon-pawn:before{content:"\e213"}.glyphicon-bishop:before{content:"\e214"}.glyphicon-knight:before{content:"\e215"}.glyphicon-baby-formula:before{content:"\e216"}.glyphicon-tent:before{content:"\26fa"}.glyphicon-blackboard:before{content:"\e218"}.glyphicon-bed:before{content:"\e219"}.glyphicon-apple:before{content:"\f8ff"}.glyphicon-erase:before{content:"\e221"}.glyphicon-hourglass:before{content:"\231b"}.glyphicon-lamp:before{content:"\e223"}.glyphicon-duplicate:before{content:"\e224"}.glyphicon-piggy-bank:before{content:"\e225"}.glyphicon-scissors:before{content:"\e226"}.glyphicon-bitcoin:before{content:"\e227"}.glyphicon-yen:before{content:"\00a5"}.glyphicon-ruble:before{content:"\20bd"}.glyphicon-scale:before{content:"\e230"}.glyphicon-ice-lolly:before{content:"\e231"}.glyphicon-ice-lolly-tasted:before{content:"\e232"}.glyphicon-education:before{content:"\e233"}.glyphicon-option-horizontal:before{content:"\e234"}.glyphicon-option-vertical:before{content:"\e235"}.glyphicon-menu-hamburger:before{content:"\e236"}.glyphicon-modal-window:before{content:"\e237"}.glyphicon-oil:before{content:"\e238"}.glyphicon-grain:before{content:"\e239"}.glyphicon-sunglasses:before{content:"\e240"}.glyphicon-text-size:before{content:"\e241"}.glyphicon-text-color:before{content:"\e242"}.glyphicon-text-background:before{content:"\e243"}.glyphicon-object-align-top:before{content:"\e244"}.glyphicon-object-align-bottom:before{content:"\e245"}.glyphicon-object-align-horizontal:before{content:"\e246"}.glyphicon-object-align-left:before{content:"\e247"}.glyphicon-object-align-vertical:before{content:"\e248"}.glyphicon-object-align-right:before{content:"\e249"}.glyphicon-triangle-right:before{content:"\e250"}.glyphicon-triangle-left:before{content:"\e251"}.glyphicon-triangle-bottom:before{content:"\e252"}.glyphicon-triangle-top:before{content:"\e253"}.glyphicon-console:before{content:"\e254"}.glyphicon-superscript:before{content:"\e255"}.glyphicon-subscript:before{content:"\e256"}.glyphicon-menu-left:before{content:"\e257"}.glyphicon-menu-right:before{content:"\e258"}.glyphicon-menu-down:before{content:"\e259"}.glyphicon-menu-up:before{content:"\e260"}*{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}:after,:before{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}html{font-size:10px;-webkit-tap-highlight-color:rgba(0,0,0,0)}body{font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:14px;line-height:1.42857143;color:#333;background-color:#fff}button,input,select,textarea{font-family:inherit;font-size:inherit;line-height:inherit}a{color:#337ab7;text-decoration:none}a:focus,a:hover{color:#23527c;text-decoration:underline}a:focus{outline:thin dotted;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}figure{margin:0}img{vertical-align:middle}.carousel-inner>.item>a>img,.carousel-inner>.item>img,.img-responsive,.thumbnail a>img,.thumbnail>img{display:block;max-width:100%;height:auto}.img-rounded{border-radius:6px}.img-thumbnail{display:inline-block;max-width:100%;height:auto;padding:4px;line-height:1.42857143;background-color:#fff;border:1px solid #ddd;border-radius:4px;-webkit-transition:all .2s ease-in-out;-o-transition:all .2s ease-in-out;transition:all .2s ease-in-out}.img-circle{border-radius:50%}hr{margin-top:20px;margin-bottom:20px;border:0;border-top:1px solid #eee}.sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);border:0}.sr-only-focusable:active,.sr-only-focusable:focus{position:static;width:auto;height:auto;margin:0;overflow:visible;clip:auto}.h1,.h2,.h3,.h4,.h5,.h6,h1,h2,h3,h4,h5,h6{font-family:inherit;font-weight:500;line-height:1.1;color:inherit}.h1 .small,.h1 small,.h2 .small,.h2 small,.h3 .small,.h3 small,.h4 .small,.h4 small,.h5 .small,.h5 small,.h6 .small,.h6 small,h1 .small,h1 small,h2 .small,h2 small,h3 .small,h3 small,h4 .small,h4 small,h5 .small,h5 small,h6 .small,h6 small{font-weight:400;line-height:1;color:#777}.h1,.h2,.h3,h1,h2,h3{margin-top:20px;margin-bottom:10px}.h1 .small,.h1 small,.h2 .small,.h2 small,.h3 .small,.h3 small,h1 .small,h1 small,h2 .small,h2 small,h3 .small,h3 small{font-size:65%}.h4,.h5,.h6,h4,h5,h6{margin-top:10px;margin-bottom:10px}.h4 .small,.h4 small,.h5 .small,.h5 small,.h6 .small,.h6 small,h4 .small,h4 small,h5 .small,h5 small,h6 .small,h6 small{font-size:75%}.h1,h1{font-size:36px}.h2,h2{font-size:30px}.h3,h3{font-size:24px}.h4,h4{font-size:18px}.h5,h5{font-size:14px}.h6,h6{font-size:12px}p{margin:0 0 10px}.lead{margin-bottom:20px;font-size:16px;font-weight:300;line-height:1.4}@media (min-width:768px){.lead{font-size:21px}}.small,small{font-size:85%}.mark,mark{padding:.2em;background-color:#fcf8e3}.text-left{text-align:left}.text-right{text-align:right}.text-center{text-align:center}.text-justify{text-align:justify}.text-nowrap{white-space:nowrap}.text-lowercase{text-transform:lowercase}.text-uppercase{text-transform:uppercase}.text-capitalize{text-transform:capitalize}.text-muted{color:#777}.text-primary{color:#337ab7}a.text-primary:hover{color:#286090}.text-success{color:#3c763d}a.text-success:hover{color:#2b542c}.text-info{color:#31708f}a.text-info:hover{color:#245269}.text-warning{color:#8a6d3b}a.text-warning:hover{color:#66512c}.text-danger{color:#a94442}a.text-danger:hover{color:#843534}.bg-primary{color:#fff;background-color:#337ab7}a.bg-primary:hover{background-color:#286090}.bg-success{background-color:#dff0d8}a.bg-success:hover{background-color:#c1e2b3}.bg-info{background-color:#d9edf7}a.bg-info:hover{background-color:#afd9ee}.bg-warning{background-color:#fcf8e3}a.bg-warning:hover{background-color:#f7ecb5}.bg-danger{background-color:#f2dede}a.bg-danger:hover{background-color:#e4b9b9}.page-header{padding-bottom:9px;margin:40px 0 20px;border-bottom:1px solid #eee}ol,ul{margin-top:0;margin-bottom:10px}ol ol,ol ul,ul ol,ul ul{margin-bottom:0}.list-unstyled{padding-left:0;list-style:none}.list-inline{padding-left:0;margin-left:-5px;list-style:none}.list-inline>li{display:inline-block;padding-right:5px;padding-left:5px}dl{margin-top:0;margin-bottom:20px}dd,dt{line-height:1.42857143}dt{font-weight:700}dd{margin-left:0}@media (min-width:768px){.dl-horizontal dt{float:left;width:160px;overflow:hidden;clear:left;text-align:right;text-overflow:ellipsis;white-space:nowrap}.dl-horizontal dd{margin-left:180px}}abbr[data-original-title],abbr[title]{cursor:help;border-bottom:1px dotted #777}.initialism{font-size:90%;text-transform:uppercase}blockquote{padding:10px 20px;margin:0 0 20px;font-size:17.5px;border-left:5px solid #eee}blockquote ol:last-child,blockquote p:last-child,blockquote ul:last-child{margin-bottom:0}blockquote .small,blockquote footer,blockquote small{display:block;font-size:80%;line-height:1.42857143;color:#777}blockquote .small:before,blockquote footer:before,blockquote small:before{content:'\2014 \00A0'}.blockquote-reverse,blockquote.pull-right{padding-right:15px;padding-left:0;text-align:right;border-right:5px solid #eee;border-left:0}.blockquote-reverse .small:before,.blockquote-reverse footer:before,.blockquote-reverse small:before,blockquote.pull-right .small:before,blockquote.pull-right footer:before,blockquote.pull-right small:before{content:''}.blockquote-reverse .small:after,.blockquote-reverse footer:after,.blockquote-reverse small:after,blockquote.pull-right .small:after,blockquote.pull-right footer:after,blockquote.pull-right small:after{content:'\00A0 \2014'}address{margin-bottom:20px;font-style:normal;line-height:1.42857143}code,kbd,pre,samp{font-family:Menlo,Monaco,Consolas,"Courier New",monospace}code{padding:2px 4px;font-size:90%;color:#c7254e;background-color:#f9f2f4;border-radius:4px}kbd{padding:2px 4px;font-size:90%;color:#fff;background-color:#333;border-radius:3px;-webkit-box-shadow:inset 0 -1px 0 rgba(0,0,0,.25);box-shadow:inset 0 -1px 0 rgba(0,0,0,.25)}kbd kbd{padding:0;font-size:100%;font-weight:700;-webkit-box-shadow:none;box-shadow:none}pre{display:block;padding:9.5px;margin:0 0 10px;font-size:13px;line-height:1.42857143;color:#333;word-break:break-all;word-wrap:break-word;background-color:#f5f5f5;border:1px solid #ccc;border-radius:4px}pre code{padding:0;font-size:inherit;color:inherit;white-space:pre-wrap;background-color:transparent;border-radius:0}.pre-scrollable{max-height:340px;overflow-y:scroll}.container{padding-right:15px;padding-left:15px;margin-right:auto;margin-left:auto}@media (min-width:768px){.container{width:750px}}@media (min-width:992px){.container{width:970px}}@media (min-width:1200px){.container{width:1170px}}.container-fluid{padding-right:15px;padding-left:15px;margin-right:auto;margin-left:auto}.row{margin-right:-15px;margin-left:-15px}.col-lg-1,.col-lg-10,.col-lg-11,.col-lg-12,.col-lg-2,.col-lg-3,.col-lg-4,.col-lg-5,.col-lg-6,.col-lg-7,.col-lg-8,.col-lg-9,.col-md-1,.col-md-10,.col-md-11,.col-md-12,.col-md-2,.col-md-3,.col-md-4,.col-md-5,.col-md-6,.col-md-7,.col-md-8,.col-md-9,.col-sm-1,.col-sm-10,.col-sm-11,.col-sm-12,.col-sm-2,.col-sm-3,.col-sm-4,.col-sm-5,.col-sm-6,.col-sm-7,.col-sm-8,.col-sm-9,.col-xs-1,.col-xs-10,.col-xs-11,.col-xs-12,.col-xs-2,.col-xs-3,.col-xs-4,.col-xs-5,.col-xs-6,.col-xs-7,.col-xs-8,.col-xs-9{position:relative;min-height:1px;padding-right:15px;padding-left:15px}.col-xs-1,.col-xs-10,.col-xs-11,.col-xs-12,.col-xs-2,.col-xs-3,.col-xs-4,.col-xs-5,.col-xs-6,.col-xs-7,.col-xs-8,.col-xs-9{float:left}.col-xs-12{width:100%}.col-xs-11{width:91.66666667%}.col-xs-10{width:83.33333333%}.col-xs-9{width:75%}.col-xs-8{width:66.66666667%}.col-xs-7{width:58.33333333%}.col-xs-6{width:50%}.col-xs-5{width:41.66666667%}.col-xs-4{width:33.33333333%}.col-xs-3{width:25%}.col-xs-2{width:16.66666667%}.col-xs-1{width:8.33333333%}.col-xs-pull-12{right:100%}.col-xs-pull-11{right:91.66666667%}.col-xs-pull-10{right:83.33333333%}.col-xs-pull-9{right:75%}.col-xs-pull-8{right:66.66666667%}.col-xs-pull-7{right:58.33333333%}.col-xs-pull-6{right:50%}.col-xs-pull-5{right:41.66666667%}.col-xs-pull-4{right:33.33333333%}.col-xs-pull-3{right:25%}.col-xs-pull-2{right:16.66666667%}.col-xs-pull-1{right:8.33333333%}.col-xs-pull-0{right:auto}.col-xs-push-12{left:100%}.col-xs-push-11{left:91.66666667%}.col-xs-push-10{left:83.33333333%}.col-xs-push-9{left:75%}.col-xs-push-8{left:66.66666667%}.col-xs-push-7{left:58.33333333%}.col-xs-push-6{left:50%}.col-xs-push-5{left:41.66666667%}.col-xs-push-4{left:33.33333333%}.col-xs-push-3{left:25%}.col-xs-push-2{left:16.66666667%}.col-xs-push-1{left:8.33333333%}.col-xs-push-0{left:auto}.col-xs-offset-12{margin-left:100%}.col-xs-offset-11{margin-left:91.66666667%}.col-xs-offset-10{margin-left:83.33333333%}.col-xs-offset-9{margin-left:75%}.col-xs-offset-8{margin-left:66.66666667%}.col-xs-offset-7{margin-left:58.33333333%}.col-xs-offset-6{margin-left:50%}.col-xs-offset-5{margin-left:41.66666667%}.col-xs-offset-4{margin-left:33.33333333%}.col-xs-offset-3{margin-left:25%}.col-xs-offset-2{margin-left:16.66666667%}.col-xs-offset-1{margin-left:8.33333333%}.col-xs-offset-0{margin-left:0}@media (min-width:768px){.col-sm-1,.col-sm-10,.col-sm-11,.col-sm-12,.col-sm-2,.col-sm-3,.col-sm-4,.col-sm-5,.col-sm-6,.col-sm-7,.col-sm-8,.col-sm-9{float:left}.col-sm-12{width:100%}.col-sm-11{width:91.66666667%}.col-sm-10{width:83.33333333%}.col-sm-9{width:75%}.col-sm-8{width:66.66666667%}.col-sm-7{width:58.33333333%}.col-sm-6{width:50%}.col-sm-5{width:41.66666667%}.col-sm-4{width:33.33333333%}.col-sm-3{width:25%}.col-sm-2{width:16.66666667%}.col-sm-1{width:8.33333333%}.col-sm-pull-12{right:100%}.col-sm-pull-11{right:91.66666667%}.col-sm-pull-10{right:83.33333333%}.col-sm-pull-9{right:75%}.col-sm-pull-8{right:66.66666667%}.col-sm-pull-7{right:58.33333333%}.col-sm-pull-6{right:50%}.col-sm-pull-5{right:41.66666667%}.col-sm-pull-4{right:33.33333333%}.col-sm-pull-3{right:25%}.col-sm-pull-2{right:16.66666667%}.col-sm-pull-1{right:8.33333333%}.col-sm-pull-0{right:auto}.col-sm-push-12{left:100%}.col-sm-push-11{left:91.66666667%}.col-sm-push-10{left:83.33333333%}.col-sm-push-9{left:75%}.col-sm-push-8{left:66.66666667%}.col-sm-push-7{left:58.33333333%}.col-sm-push-6{left:50%}.col-sm-push-5{left:41.66666667%}.col-sm-push-4{left:33.33333333%}.col-sm-push-3{left:25%}.col-sm-push-2{left:16.66666667%}.col-sm-push-1{left:8.33333333%}.col-sm-push-0{left:auto}.col-sm-offset-12{margin-left:100%}.col-sm-offset-11{margin-left:91.66666667%}.col-sm-offset-10{margin-left:83.33333333%}.col-sm-offset-9{margin-left:75%}.col-sm-offset-8{margin-left:66.66666667%}.col-sm-offset-7{margin-left:58.33333333%}.col-sm-offset-6{margin-left:50%}.col-sm-offset-5{margin-left:41.66666667%}.col-sm-offset-4{margin-left:33.33333333%}.col-sm-offset-3{margin-left:25%}.col-sm-offset-2{margin-left:16.66666667%}.col-sm-offset-1{margin-left:8.33333333%}.col-sm-offset-0{margin-left:0}}@media (min-width:992px){.col-md-1,.col-md-10,.col-md-11,.col-md-12,.col-md-2,.col-md-3,.col-md-4,.col-md-5,.col-md-6,.col-md-7,.col-md-8,.col-md-9{float:left}.col-md-12{width:100%}.col-md-11{width:91.66666667%}.col-md-10{width:83.33333333%}.col-md-9{width:75%}.col-md-8{width:66.66666667%}.col-md-7{width:58.33333333%}.col-md-6{width:50%}.col-md-5{width:41.66666667%}.col-md-4{width:33.33333333%}.col-md-3{width:25%}.col-md-2{width:16.66666667%}.col-md-1{width:8.33333333%}.col-md-pull-12{right:100%}.col-md-pull-11{right:91.66666667%}.col-md-pull-10{right:83.33333333%}.col-md-pull-9{right:75%}.col-md-pull-8{right:66.66666667%}.col-md-pull-7{right:58.33333333%}.col-md-pull-6{right:50%}.col-md-pull-5{right:41.66666667%}.col-md-pull-4{right:33.33333333%}.col-md-pull-3{right:25%}.col-md-pull-2{right:16.66666667%}.col-md-pull-1{right:8.33333333%}.col-md-pull-0{right:auto}.col-md-push-12{left:100%}.col-md-push-11{left:91.66666667%}.col-md-push-10{left:83.33333333%}.col-md-push-9{left:75%}.col-md-push-8{left:66.66666667%}.col-md-push-7{left:58.33333333%}.col-md-push-6{left:50%}.col-md-push-5{left:41.66666667%}.col-md-push-4{left:33.33333333%}.col-md-push-3{left:25%}.col-md-push-2{left:16.66666667%}.col-md-push-1{left:8.33333333%}.col-md-push-0{left:auto}.col-md-offset-12{margin-left:100%}.col-md-offset-11{margin-left:91.66666667%}.col-md-offset-10{margin-left:83.33333333%}.col-md-offset-9{margin-left:75%}.col-md-offset-8{margin-left:66.66666667%}.col-md-offset-7{margin-left:58.33333333%}.col-md-offset-6{margin-left:50%}.col-md-offset-5{margin-left:41.66666667%}.col-md-offset-4{margin-left:33.33333333%}.col-md-offset-3{margin-left:25%}.col-md-offset-2{margin-left:16.66666667%}.col-md-offset-1{margin-left:8.33333333%}.col-md-offset-0{margin-left:0}}@media (min-width:1200px){.col-lg-1,.col-lg-10,.col-lg-11,.col-lg-12,.col-lg-2,.col-lg-3,.col-lg-4,.col-lg-5,.col-lg-6,.col-lg-7,.col-lg-8,.col-lg-9{float:left}.col-lg-12{width:100%}.col-lg-11{width:91.66666667%}.col-lg-10{width:83.33333333%}.col-lg-9{width:75%}.col-lg-8{width:66.66666667%}.col-lg-7{width:58.33333333%}.col-lg-6{width:50%}.col-lg-5{width:41.66666667%}.col-lg-4{width:33.33333333%}.col-lg-3{width:25%}.col-lg-2{width:16.66666667%}.col-lg-1{width:8.33333333%}.col-lg-pull-12{right:100%}.col-lg-pull-11{right:91.66666667%}.col-lg-pull-10{right:83.33333333%}.col-lg-pull-9{right:75%}.col-lg-pull-8{right:66.66666667%}.col-lg-pull-7{right:58.33333333%}.col-lg-pull-6{right:50%}.col-lg-pull-5{right:41.66666667%}.col-lg-pull-4{right:33.33333333%}.col-lg-pull-3{right:25%}.col-lg-pull-2{right:16.66666667%}.col-lg-pull-1{right:8.33333333%}.col-lg-pull-0{right:auto}.col-lg-push-12{left:100%}.col-lg-push-11{left:91.66666667%}.col-lg-push-10{left:83.33333333%}.col-lg-push-9{left:75%}.col-lg-push-8{left:66.66666667%}.col-lg-push-7{left:58.33333333%}.col-lg-push-6{left:50%}.col-lg-push-5{left:41.66666667%}.col-lg-push-4{left:33.33333333%}.col-lg-push-3{left:25%}.col-lg-push-2{left:16.66666667%}.col-lg-push-1{left:8.33333333%}.col-lg-push-0{left:auto}.col-lg-offset-12{margin-left:100%}.col-lg-offset-11{margin-left:91.66666667%}.col-lg-offset-10{margin-left:83.33333333%}.col-lg-offset-9{margin-left:75%}.col-lg-offset-8{margin-left:66.66666667%}.col-lg-offset-7{margin-left:58.33333333%}.col-lg-offset-6{margin-left:50%}.col-lg-offset-5{margin-left:41.66666667%}.col-lg-offset-4{margin-left:33.33333333%}.col-lg-offset-3{margin-left:25%}.col-lg-offset-2{margin-left:16.66666667%}.col-lg-offset-1{margin-left:8.33333333%}.col-lg-offset-0{margin-left:0}}table{background-color:transparent}caption{padding-top:8px;padding-bottom:8px;color:#777;text-align:left}th{text-align:left}.table{width:100%;max-width:100%;margin-bottom:20px}.table>tbody>tr>td,.table>tbody>tr>th,.table>tfoot>tr>td,.table>tfoot>tr>th,.table>thead>tr>td,.table>thead>tr>th{padding:8px;line-height:1.42857143;vertical-align:top;border-top:1px solid #ddd}.table>thead>tr>th{vertical-align:bottom;border-bottom:2px solid #ddd}.table>caption+thead>tr:first-child>td,.table>caption+thead>tr:first-child>th,.table>colgroup+thead>tr:first-child>td,.table>colgroup+thead>tr:first-child>th,.table>thead:first-child>tr:first-child>td,.table>thead:first-child>tr:first-child>th{border-top:0}.table>tbody+tbody{border-top:2px solid #ddd}.table .table{background-color:#fff}.table-condensed>tbody>tr>td,.table-condensed>tbody>tr>th,.table-condensed>tfoot>tr>td,.table-condensed>tfoot>tr>th,.table-condensed>thead>tr>td,.table-condensed>thead>tr>th{padding:5px}.table-bordered{border:1px solid #ddd}.table-bordered>tbody>tr>td,.table-bordered>tbody>tr>th,.table-bordered>tfoot>tr>td,.table-bordered>tfoot>tr>th,.table-bordered>thead>tr>td,.table-bordered>thead>tr>th{border:1px solid #ddd}.table-bordered>thead>tr>td,.table-bordered>thead>tr>th{border-bottom-width:2px}.table-striped>tbody>tr:nth-of-type(odd){background-color:#f9f9f9}.table-hover>tbody>tr:hover{background-color:#f5f5f5}table col[class*=col-]{position:static;display:table-column;float:none}table td[class*=col-],table th[class*=col-]{position:static;display:table-cell;float:none}.table>tbody>tr.active>td,.table>tbody>tr.active>th,.table>tbody>tr>td.active,.table>tbody>tr>th.active,.table>tfoot>tr.active>td,.table>tfoot>tr.active>th,.table>tfoot>tr>td.active,.table>tfoot>tr>th.active,.table>thead>tr.active>td,.table>thead>tr.active>th,.table>thead>tr>td.active,.table>thead>tr>th.active{background-color:#f5f5f5}.table-hover>tbody>tr.active:hover>td,.table-hover>tbody>tr.active:hover>th,.table-hover>tbody>tr:hover>.active,.table-hover>tbody>tr>td.active:hover,.table-hover>tbody>tr>th.active:hover{background-color:#e8e8e8}.table>tbody>tr.success>td,.table>tbody>tr.success>th,.table>tbody>tr>td.success,.table>tbody>tr>th.success,.table>tfoot>tr.success>td,.table>tfoot>tr.success>th,.table>tfoot>tr>td.success,.table>tfoot>tr>th.success,.table>thead>tr.success>td,.table>thead>tr.success>th,.table>thead>tr>td.success,.table>thead>tr>th.success{background-color:#dff0d8}.table-hover>tbody>tr.success:hover>td,.table-hover>tbody>tr.success:hover>th,.table-hover>tbody>tr:hover>.success,.table-hover>tbody>tr>td.success:hover,.table-hover>tbody>tr>th.success:hover{background-color:#d0e9c6}.table>tbody>tr.info>td,.table>tbody>tr.info>th,.table>tbody>tr>td.info,.table>tbody>tr>th.info,.table>tfoot>tr.info>td,.table>tfoot>tr.info>th,.table>tfoot>tr>td.info,.table>tfoot>tr>th.info,.table>thead>tr.info>td,.table>thead>tr.info>th,.table>thead>tr>td.info,.table>thead>tr>th.info{background-color:#d9edf7}.table-hover>tbody>tr.info:hover>td,.table-hover>tbody>tr.info:hover>th,.table-hover>tbody>tr:hover>.info,.table-hover>tbody>tr>td.info:hover,.table-hover>tbody>tr>th.info:hover{background-color:#c4e3f3}.table>tbody>tr.warning>td,.table>tbody>tr.warning>th,.table>tbody>tr>td.warning,.table>tbody>tr>th.warning,.table>tfoot>tr.warning>td,.table>tfoot>tr.warning>th,.table>tfoot>tr>td.warning,.table>tfoot>tr>th.warning,.table>thead>tr.warning>td,.table>thead>tr.warning>th,.table>thead>tr>td.warning,.table>thead>tr>th.warning{background-color:#fcf8e3}.table-hover>tbody>tr.warning:hover>td,.table-hover>tbody>tr.warning:hover>th,.table-hover>tbody>tr:hover>.warning,.table-hover>tbody>tr>td.warning:hover,.table-hover>tbody>tr>th.warning:hover{background-color:#faf2cc}.table>tbody>tr.danger>td,.table>tbody>tr.danger>th,.table>tbody>tr>td.danger,.table>tbody>tr>th.danger,.table>tfoot>tr.danger>td,.table>tfoot>tr.danger>th,.table>tfoot>tr>td.danger,.table>tfoot>tr>th.danger,.table>thead>tr.danger>td,.table>thead>tr.danger>th,.table>thead>tr>td.danger,.table>thead>tr>th.danger{background-color:#f2dede}.table-hover>tbody>tr.danger:hover>td,.table-hover>tbody>tr.danger:hover>th,.table-hover>tbody>tr:hover>.danger,.table-hover>tbody>tr>td.danger:hover,.table-hover>tbody>tr>th.danger:hover{background-color:#ebcccc}.table-responsive{min-height:.01%;overflow-x:auto}@media screen and (max-width:767px){.table-responsive{width:100%;margin-bottom:15px;overflow-y:hidden;-ms-overflow-style:-ms-autohiding-scrollbar;border:1px solid #ddd}.table-responsive>.table{margin-bottom:0}.table-responsive>.table>tbody>tr>td,.table-responsive>.table>tbody>tr>th,.table-responsive>.table>tfoot>tr>td,.table-responsive>.table>tfoot>tr>th,.table-responsive>.table>thead>tr>td,.table-responsive>.table>thead>tr>th{white-space:nowrap}.table-responsive>.table-bordered{border:0}.table-responsive>.table-bordered>tbody>tr>td:first-child,.table-responsive>.table-bordered>tbody>tr>th:first-child,.table-responsive>.table-bordered>tfoot>tr>td:first-child,.table-responsive>.table-bordered>tfoot>tr>th:first-child,.table-responsive>.table-bordered>thead>tr>td:first-child,.table-responsive>.table-bordered>thead>tr>th:first-child{border-left:0}.table-responsive>.table-bordered>tbody>tr>td:last-child,.table-responsive>.table-bordered>tbody>tr>th:last-child,.table-responsive>.table-bordered>tfoot>tr>td:last-child,.table-responsive>.table-bordered>tfoot>tr>th:last-child,.table-responsive>.table-bordered>thead>tr>td:last-child,.table-responsive>.table-bordered>thead>tr>th:last-child{border-right:0}.table-responsive>.table-bordered>tbody>tr:last-child>td,.table-responsive>.table-bordered>tbody>tr:last-child>th,.table-responsive>.table-bordered>tfoot>tr:last-child>td,.table-responsive>.table-bordered>tfoot>tr:last-child>th{border-bottom:0}}fieldset{min-width:0;padding:0;margin:0;border:0}legend{display:block;width:100%;padding:0;margin-bottom:20px;font-size:21px;line-height:inherit;color:#333;border:0;border-bottom:1px solid #e5e5e5}label{display:inline-block;max-width:100%;margin-bottom:5px;font-weight:700}input[type=search]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}input[type=checkbox],input[type=radio]{margin:4px 0 0;margin-top:1px \9;line-height:normal}input[type=file]{display:block}input[type=range]{display:block;width:100%}select[multiple],select[size]{height:auto}input[type=file]:focus,input[type=checkbox]:focus,input[type=radio]:focus{outline:thin dotted;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}output{display:block;padding-top:7px;font-size:14px;line-height:1.42857143;color:#555}.form-control{display:block;width:100%;height:34px;padding:6px 12px;font-size:14px;line-height:1.42857143;color:#555;background-color:#fff;background-image:none;border:1px solid #ccc;border-radius:4px;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075);box-shadow:inset 0 1px 1px rgba(0,0,0,.075);-webkit-transition:border-color ease-in-out .15s,-webkit-box-shadow ease-in-out .15s;-o-transition:border-color ease-in-out .15s,box-shadow ease-in-out .15s;transition:border-color ease-in-out .15s,box-shadow ease-in-out .15s}.form-control:focus{border-color:#66afe9;outline:0;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 8px rgba(102,175,233,.6);box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 8px rgba(102,175,233,.6)}.form-control::-moz-placeholder{color:#999;opacity:1}.form-control:-ms-input-placeholder{color:#999}.form-control::-webkit-input-placeholder{color:#999}.form-control[disabled],.form-control[readonly],fieldset[disabled] .form-control{cursor:not-allowed;background-color:#eee;opacity:1}textarea.form-control{height:auto}input[type=search]{-webkit-appearance:none}@media screen and (-webkit-min-device-pixel-ratio:0){input[type=date],input[type=time],input[type=datetime-local],input[type=month]{line-height:34px}.input-group-sm input[type=date],.input-group-sm input[type=time],.input-group-sm input[type=datetime-local],.input-group-sm input[type=month],input[type=date].input-sm,input[type=time].input-sm,input[type=datetime-local].input-sm,input[type=month].input-sm{line-height:30px}.input-group-lg input[type=date],.input-group-lg input[type=time],.input-group-lg input[type=datetime-local],.input-group-lg input[type=month],input[type=date].input-lg,input[type=time].input-lg,input[type=datetime-local].input-lg,input[type=month].input-lg{line-height:46px}}.form-group{margin-bottom:15px}.checkbox,.radio{position:relative;display:block;margin-top:10px;margin-bottom:10px}.checkbox label,.radio label{min-height:20px;padding-left:20px;margin-bottom:0;font-weight:400;cursor:pointer}.checkbox input[type=checkbox],.checkbox-inline input[type=checkbox],.radio input[type=radio],.radio-inline input[type=radio]{position:absolute;margin-top:4px \9;margin-left:-20px}.checkbox+.checkbox,.radio+.radio{margin-top:-5px}.checkbox-inline,.radio-inline{display:inline-block;padding-left:20px;margin-bottom:0;font-weight:400;vertical-align:middle;cursor:pointer}.checkbox-inline+.checkbox-inline,.radio-inline+.radio-inline{margin-top:0;margin-left:10px}fieldset[disabled] input[type=checkbox],fieldset[disabled] input[type=radio],input[type=checkbox].disabled,input[type=checkbox][disabled],input[type=radio].disabled,input[type=radio][disabled]{cursor:not-allowed}.checkbox-inline.disabled,.radio-inline.disabled,fieldset[disabled] .checkbox-inline,fieldset[disabled] .radio-inline{cursor:not-allowed}.checkbox.disabled label,.radio.disabled label,fieldset[disabled] .checkbox label,fieldset[disabled] .radio label{cursor:not-allowed}.form-control-static{padding-top:7px;padding-bottom:7px;margin-bottom:0}.form-control-static.input-lg,.form-control-static.input-sm{padding-right:0;padding-left:0}.input-sm{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}select.input-sm{height:30px;line-height:30px}select[multiple].input-sm,textarea.input-sm{height:auto}.form-group-sm .form-control{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}select.form-group-sm .form-control{height:30px;line-height:30px}select[multiple].form-group-sm .form-control,textarea.form-group-sm .form-control{height:auto}.form-group-sm .form-control-static{height:30px;padding:5px 10px;font-size:12px;line-height:1.5}.input-lg{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}select.input-lg{height:46px;line-height:46px}select[multiple].input-lg,textarea.input-lg{height:auto}.form-group-lg .form-control{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}select.form-group-lg .form-control{height:46px;line-height:46px}select[multiple].form-group-lg .form-control,textarea.form-group-lg .form-control{height:auto}.form-group-lg .form-control-static{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333}.has-feedback{position:relative}.has-feedback .form-control{padding-right:42.5px}.form-control-feedback{position:absolute;top:0;right:0;z-index:2;display:block;width:34px;height:34px;line-height:34px;text-align:center;pointer-events:none}.input-lg+.form-control-feedback{width:46px;height:46px;line-height:46px}.input-sm+.form-control-feedback{width:30px;height:30px;line-height:30px}.has-success .checkbox,.has-success .checkbox-inline,.has-success .control-label,.has-success .help-block,.has-success .radio,.has-success .radio-inline,.has-success.checkbox label,.has-success.checkbox-inline label,.has-success.radio label,.has-success.radio-inline label{color:#3c763d}.has-success .form-control{border-color:#3c763d;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075);box-shadow:inset 0 1px 1px rgba(0,0,0,.075)}.has-success .form-control:focus{border-color:#2b542c;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #67b168;box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #67b168}.has-success .input-group-addon{color:#3c763d;background-color:#dff0d8;border-color:#3c763d}.has-success .form-control-feedback{color:#3c763d}.has-warning .checkbox,.has-warning .checkbox-inline,.has-warning .control-label,.has-warning .help-block,.has-warning .radio,.has-warning .radio-inline,.has-warning.checkbox label,.has-warning.checkbox-inline label,.has-warning.radio label,.has-warning.radio-inline label{color:#8a6d3b}.has-warning .form-control{border-color:#8a6d3b;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075);box-shadow:inset 0 1px 1px rgba(0,0,0,.075)}.has-warning .form-control:focus{border-color:#66512c;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #c0a16b;box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #c0a16b}.has-warning .input-group-addon{color:#8a6d3b;background-color:#fcf8e3;border-color:#8a6d3b}.has-warning .form-control-feedback{color:#8a6d3b}.has-error .checkbox,.has-error .checkbox-inline,.has-error .control-label,.has-error .help-block,.has-error .radio,.has-error .radio-inline,.has-error.checkbox label,.has-error.checkbox-inline label,.has-error.radio label,.has-error.radio-inline label{color:#a94442}.has-error .form-control{border-color:#a94442;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075);box-shadow:inset 0 1px 1px rgba(0,0,0,.075)}.has-error .form-control:focus{border-color:#843534;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #ce8483;box-shadow:inset 0 1px 1px rgba(0,0,0,.075),0 0 6px #ce8483}.has-error .input-group-addon{color:#a94442;background-color:#f2dede;border-color:#a94442}.has-error .form-control-feedback{color:#a94442}.has-feedback label~.form-control-feedback{top:25px}.has-feedback label.sr-only~.form-control-feedback{top:0}.help-block{display:block;margin-top:5px;margin-bottom:10px;color:#737373}@media (min-width:768px){.form-inline .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.form-inline .form-control{display:inline-block;width:auto;vertical-align:middle}.form-inline .form-control-static{display:inline-block}.form-inline .input-group{display:inline-table;vertical-align:middle}.form-inline .input-group .form-control,.form-inline .input-group .input-group-addon,.form-inline .input-group .input-group-btn{width:auto}.form-inline .input-group>.form-control{width:100%}.form-inline .control-label{margin-bottom:0;vertical-align:middle}.form-inline .checkbox,.form-inline .radio{display:inline-block;margin-top:0;margin-bottom:0;vertical-align:middle}.form-inline .checkbox label,.form-inline .radio label{padding-left:0}.form-inline .checkbox input[type=checkbox],.form-inline .radio input[type=radio]{position:relative;margin-left:0}.form-inline .has-feedback .form-control-feedback{top:0}}.form-horizontal .checkbox,.form-horizontal .checkbox-inline,.form-horizontal .radio,.form-horizontal .radio-inline{padding-top:7px;margin-top:0;margin-bottom:0}.form-horizontal .checkbox,.form-horizontal .radio{min-height:27px}.form-horizontal .form-group{margin-right:-15px;margin-left:-15px}@media (min-width:768px){.form-horizontal .control-label{padding-top:7px;margin-bottom:0;text-align:right}}.form-horizontal .has-feedback .form-control-feedback{right:15px}@media (min-width:768px){.form-horizontal .form-group-lg .control-label{padding-top:14.33px}}@media (min-width:768px){.form-horizontal .form-group-sm .control-label{padding-top:6px}}.btn{display:inline-block;padding:6px 12px;margin-bottom:0;font-size:14px;font-weight:400;line-height:1.42857143;text-align:center;white-space:nowrap;vertical-align:middle;-ms-touch-action:manipulation;touch-action:manipulation;cursor:pointer;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;background-image:none;border:1px solid transparent;border-radius:4px}.btn.active.focus,.btn.active:focus,.btn.focus,.btn:active.focus,.btn:active:focus,.btn:focus{outline:thin dotted;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}.btn.focus,.btn:focus,.btn:hover{color:#333;text-decoration:none}.btn.active,.btn:active{background-image:none;outline:0;-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,.125);box-shadow:inset 0 3px 5px rgba(0,0,0,.125)}.btn.disabled,.btn[disabled],fieldset[disabled] .btn{pointer-events:none;cursor:not-allowed;filter:alpha(opacity=65);-webkit-box-shadow:none;box-shadow:none;opacity:.65}.btn-default{color:#333;background-color:#fff;border-color:#ccc}.btn-default.active,.btn-default.focus,.btn-default:active,.btn-default:focus,.btn-default:hover,.open>.dropdown-toggle.btn-default{color:#333;background-color:#e6e6e6;border-color:#adadad}.btn-default.active,.btn-default:active,.open>.dropdown-toggle.btn-default{background-image:none}.btn-default.disabled,.btn-default.disabled.active,.btn-default.disabled.focus,.btn-default.disabled:active,.btn-default.disabled:focus,.btn-default.disabled:hover,.btn-default[disabled],.btn-default[disabled].active,.btn-default[disabled].focus,.btn-default[disabled]:active,.btn-default[disabled]:focus,.btn-default[disabled]:hover,fieldset[disabled] .btn-default,fieldset[disabled] .btn-default.active,fieldset[disabled] .btn-default.focus,fieldset[disabled] .btn-default:active,fieldset[disabled] .btn-default:focus,fieldset[disabled] .btn-default:hover{background-color:#fff;border-color:#ccc}.btn-default .badge{color:#fff;background-color:#333}.btn-primary{color:#fff;background-color:#337ab7;border-color:#2e6da4}.btn-primary.active,.btn-primary.focus,.btn-primary:active,.btn-primary:focus,.btn-primary:hover,.open>.dropdown-toggle.btn-primary{color:#fff;background-color:#286090;border-color:#204d74}.btn-primary.active,.btn-primary:active,.open>.dropdown-toggle.btn-primary{background-image:none}.btn-primary.disabled,.btn-primary.disabled.active,.btn-primary.disabled.focus,.btn-primary.disabled:active,.btn-primary.disabled:focus,.btn-primary.disabled:hover,.btn-primary[disabled],.btn-primary[disabled].active,.btn-primary[disabled].focus,.btn-primary[disabled]:active,.btn-primary[disabled]:focus,.btn-primary[disabled]:hover,fieldset[disabled] .btn-primary,fieldset[disabled] .btn-primary.active,fieldset[disabled] .btn-primary.focus,fieldset[disabled] .btn-primary:active,fieldset[disabled] .btn-primary:focus,fieldset[disabled] .btn-primary:hover{background-color:#337ab7;border-color:#2e6da4}.btn-primary .badge{color:#337ab7;background-color:#fff}.btn-success{color:#fff;background-color:#5cb85c;border-color:#4cae4c}.btn-success.active,.btn-success.focus,.btn-success:active,.btn-success:focus,.btn-success:hover,.open>.dropdown-toggle.btn-success{color:#fff;background-color:#449d44;border-color:#398439}.btn-success.active,.btn-success:active,.open>.dropdown-toggle.btn-success{background-image:none}.btn-success.disabled,.btn-success.disabled.active,.btn-success.disabled.focus,.btn-success.disabled:active,.btn-success.disabled:focus,.btn-success.disabled:hover,.btn-success[disabled],.btn-success[disabled].active,.btn-success[disabled].focus,.btn-success[disabled]:active,.btn-success[disabled]:focus,.btn-success[disabled]:hover,fieldset[disabled] .btn-success,fieldset[disabled] .btn-success.active,fieldset[disabled] .btn-success.focus,fieldset[disabled] .btn-success:active,fieldset[disabled] .btn-success:focus,fieldset[disabled] .btn-success:hover{background-color:#5cb85c;border-color:#4cae4c}.btn-success .badge{color:#5cb85c;background-color:#fff}.btn-info{color:#fff;background-color:#5bc0de;border-color:#46b8da}.btn-info.active,.btn-info.focus,.btn-info:active,.btn-info:focus,.btn-info:hover,.open>.dropdown-toggle.btn-info{color:#fff;background-color:#31b0d5;border-color:#269abc}.btn-info.active,.btn-info:active,.open>.dropdown-toggle.btn-info{background-image:none}.btn-info.disabled,.btn-info.disabled.active,.btn-info.disabled.focus,.btn-info.disabled:active,.btn-info.disabled:focus,.btn-info.disabled:hover,.btn-info[disabled],.btn-info[disabled].active,.btn-info[disabled].focus,.btn-info[disabled]:active,.btn-info[disabled]:focus,.btn-info[disabled]:hover,fieldset[disabled] .btn-info,fieldset[disabled] .btn-info.active,fieldset[disabled] .btn-info.focus,fieldset[disabled] .btn-info:active,fieldset[disabled] .btn-info:focus,fieldset[disabled] .btn-info:hover{background-color:#5bc0de;border-color:#46b8da}.btn-info .badge{color:#5bc0de;background-color:#fff}.btn-warning{color:#fff;background-color:#f0ad4e;border-color:#eea236}.btn-warning.active,.btn-warning.focus,.btn-warning:active,.btn-warning:focus,.btn-warning:hover,.open>.dropdown-toggle.btn-warning{color:#fff;background-color:#ec971f;border-color:#d58512}.btn-warning.active,.btn-warning:active,.open>.dropdown-toggle.btn-warning{background-image:none}.btn-warning.disabled,.btn-warning.disabled.active,.btn-warning.disabled.focus,.btn-warning.disabled:active,.btn-warning.disabled:focus,.btn-warning.disabled:hover,.btn-warning[disabled],.btn-warning[disabled].active,.btn-warning[disabled].focus,.btn-warning[disabled]:active,.btn-warning[disabled]:focus,.btn-warning[disabled]:hover,fieldset[disabled] .btn-warning,fieldset[disabled] .btn-warning.active,fieldset[disabled] .btn-warning.focus,fieldset[disabled] .btn-warning:active,fieldset[disabled] .btn-warning:focus,fieldset[disabled] .btn-warning:hover{background-color:#f0ad4e;border-color:#eea236}.btn-warning .badge{color:#f0ad4e;background-color:#fff}.btn-danger{color:#fff;background-color:#d9534f;border-color:#d43f3a}.btn-danger.active,.btn-danger.focus,.btn-danger:active,.btn-danger:focus,.btn-danger:hover,.open>.dropdown-toggle.btn-danger{color:#fff;background-color:#c9302c;border-color:#ac2925}.btn-danger.active,.btn-danger:active,.open>.dropdown-toggle.btn-danger{background-image:none}.btn-danger.disabled,.btn-danger.disabled.active,.btn-danger.disabled.focus,.btn-danger.disabled:active,.btn-danger.disabled:focus,.btn-danger.disabled:hover,.btn-danger[disabled],.btn-danger[disabled].active,.btn-danger[disabled].focus,.btn-danger[disabled]:active,.btn-danger[disabled]:focus,.btn-danger[disabled]:hover,fieldset[disabled] .btn-danger,fieldset[disabled] .btn-danger.active,fieldset[disabled] .btn-danger.focus,fieldset[disabled] .btn-danger:active,fieldset[disabled] .btn-danger:focus,fieldset[disabled] .btn-danger:hover{background-color:#d9534f;border-color:#d43f3a}.btn-danger .badge{color:#d9534f;background-color:#fff}.btn-link{font-weight:400;color:#337ab7;border-radius:0}.btn-link,.btn-link.active,.btn-link:active,.btn-link[disabled],fieldset[disabled] .btn-link{background-color:transparent;-webkit-box-shadow:none;box-shadow:none}.btn-link,.btn-link:active,.btn-link:focus,.btn-link:hover{border-color:transparent}.btn-link:focus,.btn-link:hover{color:#23527c;text-decoration:underline;background-color:transparent}.btn-link[disabled]:focus,.btn-link[disabled]:hover,fieldset[disabled] .btn-link:focus,fieldset[disabled] .btn-link:hover{color:#777;text-decoration:none}.btn-group-lg>.btn,.btn-lg{padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}.btn-group-sm>.btn,.btn-sm{padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}.btn-group-xs>.btn,.btn-xs{padding:1px 5px;font-size:12px;line-height:1.5;border-radius:3px}.btn-block{display:block;width:100%}.btn-block+.btn-block{margin-top:5px}input[type=button].btn-block,input[type=reset].btn-block,input[type=submit].btn-block{width:100%}.fade{opacity:0;-webkit-transition:opacity .15s linear;-o-transition:opacity .15s linear;transition:opacity .15s linear}.fade.in{opacity:1}.collapse{display:none;visibility:hidden}.collapse.in{display:block;visibility:visible}tr.collapse.in{display:table-row}tbody.collapse.in{display:table-row-group}.collapsing{position:relative;height:0;overflow:hidden;-webkit-transition-timing-function:ease;-o-transition-timing-function:ease;transition-timing-function:ease;-webkit-transition-duration:.35s;-o-transition-duration:.35s;transition-duration:.35s;-webkit-transition-property:height,visibility;-o-transition-property:height,visibility;transition-property:height,visibility}.caret{display:inline-block;width:0;height:0;margin-left:2px;vertical-align:middle;border-top:4px solid;border-right:4px solid transparent;border-left:4px solid transparent}.dropdown,.dropup{position:relative}.dropdown-toggle:focus{outline:0}.dropdown-menu{position:absolute;top:100%;left:0;z-index:1000;display:none;float:left;min-width:160px;padding:5px 0;margin:2px 0 0;font-size:14px;text-align:left;list-style:none;background-color:#fff;-webkit-background-clip:padding-box;background-clip:padding-box;border:1px solid #ccc;border:1px solid rgba(0,0,0,.15);border-radius:4px;-webkit-box-shadow:0 6px 12px rgba(0,0,0,.175);box-shadow:0 6px 12px rgba(0,0,0,.175)}.dropdown-menu.pull-right{right:0;left:auto}.dropdown-menu .divider{height:1px;margin:9px 0;overflow:hidden;background-color:#e5e5e5}.dropdown-menu>li>a{display:block;padding:3px 20px;clear:both;font-weight:400;line-height:1.42857143;color:#333;white-space:nowrap}.dropdown-menu>li>a:focus,.dropdown-menu>li>a:hover{color:#262626;text-decoration:none;background-color:#f5f5f5}.dropdown-menu>.active>a,.dropdown-menu>.active>a:focus,.dropdown-menu>.active>a:hover{color:#fff;text-decoration:none;background-color:#337ab7;outline:0}.dropdown-menu>.disabled>a,.dropdown-menu>.disabled>a:focus,.dropdown-menu>.disabled>a:hover{color:#777}.dropdown-menu>.disabled>a:focus,.dropdown-menu>.disabled>a:hover{text-decoration:none;cursor:not-allowed;background-color:transparent;background-image:none;filter:progid:DXImageTransform.Microsoft.gradient(enabled=false)}.open>.dropdown-menu{display:block}.open>a{outline:0}.dropdown-menu-right{right:0;left:auto}.dropdown-menu-left{right:auto;left:0}.dropdown-header{display:block;padding:3px 20px;font-size:12px;line-height:1.42857143;color:#777;white-space:nowrap}.dropdown-backdrop{position:fixed;top:0;right:0;bottom:0;left:0;z-index:990}.pull-right>.dropdown-menu{right:0;left:auto}.dropup .caret,.navbar-fixed-bottom .dropdown .caret{content:"";border-top:0;border-bottom:4px solid}.dropup .dropdown-menu,.navbar-fixed-bottom .dropdown .dropdown-menu{top:auto;bottom:100%;margin-bottom:2px}@media (min-width:768px){.navbar-right .dropdown-menu{right:0;left:auto}.navbar-right .dropdown-menu-left{right:auto;left:0}}.btn-group,.btn-group-vertical{position:relative;display:inline-block;vertical-align:middle}.btn-group-vertical>.btn,.btn-group>.btn{position:relative;float:left}.btn-group-vertical>.btn.active,.btn-group-vertical>.btn:active,.btn-group-vertical>.btn:focus,.btn-group-vertical>.btn:hover,.btn-group>.btn.active,.btn-group>.btn:active,.btn-group>.btn:focus,.btn-group>.btn:hover{z-index:2}.btn-group .btn+.btn,.btn-group .btn+.btn-group,.btn-group .btn-group+.btn,.btn-group .btn-group+.btn-group{margin-left:-1px}.btn-toolbar{margin-left:-5px}.btn-toolbar .btn-group,.btn-toolbar .input-group{float:left}.btn-toolbar>.btn,.btn-toolbar>.btn-group,.btn-toolbar>.input-group{margin-left:5px}.btn-group>.btn:not(:first-child):not(:last-child):not(.dropdown-toggle){border-radius:0}.btn-group>.btn:first-child{margin-left:0}.btn-group>.btn:first-child:not(:last-child):not(.dropdown-toggle){border-top-right-radius:0;border-bottom-right-radius:0}.btn-group>.btn:last-child:not(:first-child),.btn-group>.dropdown-toggle:not(:first-child){border-top-left-radius:0;border-bottom-left-radius:0}.btn-group>.btn-group{float:left}.btn-group>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group>.btn-group:first-child:not(:last-child)>.btn:last-child,.btn-group>.btn-group:first-child:not(:last-child)>.dropdown-toggle{border-top-right-radius:0;border-bottom-right-radius:0}.btn-group>.btn-group:last-child:not(:first-child)>.btn:first-child{border-top-left-radius:0;border-bottom-left-radius:0}.btn-group .dropdown-toggle:active,.btn-group.open .dropdown-toggle{outline:0}.btn-group>.btn+.dropdown-toggle{padding-right:8px;padding-left:8px}.btn-group>.btn-lg+.dropdown-toggle{padding-right:12px;padding-left:12px}.btn-group.open .dropdown-toggle{-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,.125);box-shadow:inset 0 3px 5px rgba(0,0,0,.125)}.btn-group.open .dropdown-toggle.btn-link{-webkit-box-shadow:none;box-shadow:none}.btn .caret{margin-left:0}.btn-lg .caret{border-width:5px 5px 0;border-bottom-width:0}.dropup .btn-lg .caret{border-width:0 5px 5px}.btn-group-vertical>.btn,.btn-group-vertical>.btn-group,.btn-group-vertical>.btn-group>.btn{display:block;float:none;width:100%;max-width:100%}.btn-group-vertical>.btn-group>.btn{float:none}.btn-group-vertical>.btn+.btn,.btn-group-vertical>.btn+.btn-group,.btn-group-vertical>.btn-group+.btn,.btn-group-vertical>.btn-group+.btn-group{margin-top:-1px;margin-left:0}.btn-group-vertical>.btn:not(:first-child):not(:last-child){border-radius:0}.btn-group-vertical>.btn:first-child:not(:last-child){border-top-right-radius:4px;border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn:last-child:not(:first-child){border-top-left-radius:0;border-top-right-radius:0;border-bottom-left-radius:4px}.btn-group-vertical>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group-vertical>.btn-group:first-child:not(:last-child)>.btn:last-child,.btn-group-vertical>.btn-group:first-child:not(:last-child)>.dropdown-toggle{border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn-group:last-child:not(:first-child)>.btn:first-child{border-top-left-radius:0;border-top-right-radius:0}.btn-group-justified{display:table;width:100%;table-layout:fixed;border-collapse:separate}.btn-group-justified>.btn,.btn-group-justified>.btn-group{display:table-cell;float:none;width:1%}.btn-group-justified>.btn-group .btn{width:100%}.btn-group-justified>.btn-group .dropdown-menu{left:auto}[data-toggle=buttons]>.btn input[type=checkbox],[data-toggle=buttons]>.btn input[type=radio],[data-toggle=buttons]>.btn-group>.btn input[type=checkbox],[data-toggle=buttons]>.btn-group>.btn input[type=radio]{position:absolute;clip:rect(0,0,0,0);pointer-events:none}.input-group{position:relative;display:table;border-collapse:separate}.input-group[class*=col-]{float:none;padding-right:0;padding-left:0}.input-group .form-control{position:relative;z-index:2;float:left;width:100%;margin-bottom:0}.input-group-lg>.form-control,.input-group-lg>.input-group-addon,.input-group-lg>.input-group-btn>.btn{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}select.input-group-lg>.form-control,select.input-group-lg>.input-group-addon,select.input-group-lg>.input-group-btn>.btn{height:46px;line-height:46px}select[multiple].input-group-lg>.form-control,select[multiple].input-group-lg>.input-group-addon,select[multiple].input-group-lg>.input-group-btn>.btn,textarea.input-group-lg>.form-control,textarea.input-group-lg>.input-group-addon,textarea.input-group-lg>.input-group-btn>.btn{height:auto}.input-group-sm>.form-control,.input-group-sm>.input-group-addon,.input-group-sm>.input-group-btn>.btn{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}select.input-group-sm>.form-control,select.input-group-sm>.input-group-addon,select.input-group-sm>.input-group-btn>.btn{height:30px;line-height:30px}select[multiple].input-group-sm>.form-control,select[multiple].input-group-sm>.input-group-addon,select[multiple].input-group-sm>.input-group-btn>.btn,textarea.input-group-sm>.form-control,textarea.input-group-sm>.input-group-addon,textarea.input-group-sm>.input-group-btn>.btn{height:auto}.input-group .form-control,.input-group-addon,.input-group-btn{display:table-cell}.input-group .form-control:not(:first-child):not(:last-child),.input-group-addon:not(:first-child):not(:last-child),.input-group-btn:not(:first-child):not(:last-child){border-radius:0}.input-group-addon,.input-group-btn{width:1%;white-space:nowrap;vertical-align:middle}.input-group-addon{padding:6px 12px;font-size:14px;font-weight:400;line-height:1;color:#555;text-align:center;background-color:#eee;border:1px solid #ccc;border-radius:4px}.input-group-addon.input-sm{padding:5px 10px;font-size:12px;border-radius:3px}.input-group-addon.input-lg{padding:10px 16px;font-size:18px;border-radius:6px}.input-group-addon input[type=checkbox],.input-group-addon input[type=radio]{margin-top:0}.input-group .form-control:first-child,.input-group-addon:first-child,.input-group-btn:first-child>.btn,.input-group-btn:first-child>.btn-group>.btn,.input-group-btn:first-child>.dropdown-toggle,.input-group-btn:last-child>.btn-group:not(:last-child)>.btn,.input-group-btn:last-child>.btn:not(:last-child):not(.dropdown-toggle){border-top-right-radius:0;border-bottom-right-radius:0}.input-group-addon:first-child{border-right:0}.input-group .form-control:last-child,.input-group-addon:last-child,.input-group-btn:first-child>.btn-group:not(:first-child)>.btn,.input-group-btn:first-child>.btn:not(:first-child),.input-group-btn:last-child>.btn,.input-group-btn:last-child>.btn-group>.btn,.input-group-btn:last-child>.dropdown-toggle{border-top-left-radius:0;border-bottom-left-radius:0}.input-group-addon:last-child{border-left:0}.input-group-btn{position:relative;font-size:0;white-space:nowrap}.input-group-btn>.btn{position:relative}.input-group-btn>.btn+.btn{margin-left:-1px}.input-group-btn>.btn:active,.input-group-btn>.btn:focus,.input-group-btn>.btn:hover{z-index:2}.input-group-btn:first-child>.btn,.input-group-btn:first-child>.btn-group{margin-right:-1px}.input-group-btn:last-child>.btn,.input-group-btn:last-child>.btn-group{margin-left:-1px}.nav{padding-left:0;margin-bottom:0;list-style:none}.nav>li{position:relative;display:block}.nav>li>a{position:relative;display:block;padding:10px 15px}.nav>li>a:focus,.nav>li>a:hover{text-decoration:none;background-color:#eee}.nav>li.disabled>a{color:#777}.nav>li.disabled>a:focus,.nav>li.disabled>a:hover{color:#777;text-decoration:none;cursor:not-allowed;background-color:transparent}.nav .open>a,.nav .open>a:focus,.nav .open>a:hover{background-color:#eee;border-color:#337ab7}.nav .nav-divider{height:1px;margin:9px 0;overflow:hidden;background-color:#e5e5e5}.nav>li>a>img{max-width:none}.nav-tabs{border-bottom:1px solid #ddd}.nav-tabs>li{float:left;margin-bottom:-1px}.nav-tabs>li>a{margin-right:2px;line-height:1.42857143;border:1px solid transparent;border-radius:4px 4px 0 0}.nav-tabs>li>a:hover{border-color:#eee #eee #ddd}.nav-tabs>li.active>a,.nav-tabs>li.active>a:focus,.nav-tabs>li.active>a:hover{color:#555;cursor:default;background-color:#fff;border:1px solid #ddd;border-bottom-color:transparent}.nav-tabs.nav-justified{width:100%;border-bottom:0}.nav-tabs.nav-justified>li{float:none}.nav-tabs.nav-justified>li>a{margin-bottom:5px;text-align:center}.nav-tabs.nav-justified>.dropdown .dropdown-menu{top:auto;left:auto}@media (min-width:768px){.nav-tabs.nav-justified>li{display:table-cell;width:1%}.nav-tabs.nav-justified>li>a{margin-bottom:0}}.nav-tabs.nav-justified>li>a{margin-right:0;border-radius:4px}.nav-tabs.nav-justified>.active>a,.nav-tabs.nav-justified>.active>a:focus,.nav-tabs.nav-justified>.active>a:hover{border:1px solid #ddd}@media (min-width:768px){.nav-tabs.nav-justified>li>a{border-bottom:1px solid #ddd;border-radius:4px 4px 0 0}.nav-tabs.nav-justified>.active>a,.nav-tabs.nav-justified>.active>a:focus,.nav-tabs.nav-justified>.active>a:hover{border-bottom-color:#fff}}.nav-pills>li{float:left}.nav-pills>li>a{border-radius:4px}.nav-pills>li+li{margin-left:2px}.nav-pills>li.active>a,.nav-pills>li.active>a:focus,.nav-pills>li.active>a:hover{color:#fff;background-color:#337ab7}.nav-stacked>li{float:none}.nav-stacked>li+li{margin-top:2px;margin-left:0}.nav-justified{width:100%}.nav-justified>li{float:none}.nav-justified>li>a{margin-bottom:5px;text-align:center}.nav-justified>.dropdown .dropdown-menu{top:auto;left:auto}@media (min-width:768px){.nav-justified>li{display:table-cell;width:1%}.nav-justified>li>a{margin-bottom:0}}.nav-tabs-justified{border-bottom:0}.nav-tabs-justified>li>a{margin-right:0;border-radius:4px}.nav-tabs-justified>.active>a,.nav-tabs-justified>.active>a:focus,.nav-tabs-justified>.active>a:hover{border:1px solid #ddd}@media (min-width:768px){.nav-tabs-justified>li>a{border-bottom:1px solid #ddd;border-radius:4px 4px 0 0}.nav-tabs-justified>.active>a,.nav-tabs-justified>.active>a:focus,.nav-tabs-justified>.active>a:hover{border-bottom-color:#fff}}.tab-content>.tab-pane{display:none;visibility:hidden}.tab-content>.active{display:block;visibility:visible}.nav-tabs .dropdown-menu{margin-top:-1px;border-top-left-radius:0;border-top-right-radius:0}.navbar{position:relative;min-height:50px;margin-bottom:20px;border:1px solid transparent}@media (min-width:768px){.navbar{border-radius:4px}}@media (min-width:768px){.navbar-header{float:left}}.navbar-collapse{padding-right:15px;padding-left:15px;overflow-x:visible;-webkit-overflow-scrolling:touch;border-top:1px solid transparent;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,.1);box-shadow:inset 0 1px 0 rgba(255,255,255,.1)}.navbar-collapse.in{overflow-y:auto}@media (min-width:768px){.navbar-collapse{width:auto;border-top:0;-webkit-box-shadow:none;box-shadow:none}.navbar-collapse.collapse{display:block!important;height:auto!important;padding-bottom:0;overflow:visible!important;visibility:visible!important}.navbar-collapse.in{overflow-y:visible}.navbar-fixed-bottom .navbar-collapse,.navbar-fixed-top .navbar-collapse,.navbar-static-top .navbar-collapse{padding-right:0;padding-left:0}}.navbar-fixed-bottom .navbar-collapse,.navbar-fixed-top .navbar-collapse{max-height:340px}@media (max-device-width:480px) and (orientation:landscape){.navbar-fixed-bottom .navbar-collapse,.navbar-fixed-top .navbar-collapse{max-height:200px}}.container-fluid>.navbar-collapse,.container-fluid>.navbar-header,.container>.navbar-collapse,.container>.navbar-header{margin-right:-15px;margin-left:-15px}@media (min-width:768px){.container-fluid>.navbar-collapse,.container-fluid>.navbar-header,.container>.navbar-collapse,.container>.navbar-header{margin-right:0;margin-left:0}}.navbar-static-top{z-index:1000;border-width:0 0 1px}@media (min-width:768px){.navbar-static-top{border-radius:0}}.navbar-fixed-bottom,.navbar-fixed-top{position:fixed;right:0;left:0;z-index:1030}@media (min-width:768px){.navbar-fixed-bottom,.navbar-fixed-top{border-radius:0}}.navbar-fixed-top{top:0;border-width:0 0 1px}.navbar-fixed-bottom{bottom:0;margin-bottom:0;border-width:1px 0 0}.navbar-brand{float:left;height:50px;padding:15px 15px;font-size:18px;line-height:20px}.navbar-brand:focus,.navbar-brand:hover{text-decoration:none}.navbar-brand>img{display:block}@media (min-width:768px){.navbar>.container .navbar-brand,.navbar>.container-fluid .navbar-brand{margin-left:-15px}}.navbar-toggle{position:relative;float:right;padding:9px 10px;margin-top:8px;margin-right:15px;margin-bottom:8px;background-color:transparent;background-image:none;border:1px solid transparent;border-radius:4px}.navbar-toggle:focus{outline:0}.navbar-toggle .icon-bar{display:block;width:22px;height:2px;border-radius:1px}.navbar-toggle .icon-bar+.icon-bar{margin-top:4px}@media (min-width:768px){.navbar-toggle{display:none}}.navbar-nav{margin:7.5px -15px}.navbar-nav>li>a{padding-top:10px;padding-bottom:10px;line-height:20px}@media (max-width:767px){.navbar-nav .open .dropdown-menu{position:static;float:none;width:auto;margin-top:0;background-color:transparent;border:0;-webkit-box-shadow:none;box-shadow:none}.navbar-nav .open .dropdown-menu .dropdown-header,.navbar-nav .open .dropdown-menu>li>a{padding:5px 15px 5px 25px}.navbar-nav .open .dropdown-menu>li>a{line-height:20px}.navbar-nav .open .dropdown-menu>li>a:focus,.navbar-nav .open .dropdown-menu>li>a:hover{background-image:none}}@media (min-width:768px){.navbar-nav{float:left;margin:0}.navbar-nav>li{float:left}.navbar-nav>li>a{padding-top:15px;padding-bottom:15px}}.navbar-form{padding:10px 15px;margin-top:8px;margin-right:-15px;margin-bottom:8px;margin-left:-15px;border-top:1px solid transparent;border-bottom:1px solid transparent;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,.1),0 1px 0 rgba(255,255,255,.1);box-shadow:inset 0 1px 0 rgba(255,255,255,.1),0 1px 0 rgba(255,255,255,.1)}@media (min-width:768px){.navbar-form .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.navbar-form .form-control{display:inline-block;width:auto;vertical-align:middle}.navbar-form .form-control-static{display:inline-block}.navbar-form .input-group{display:inline-table;vertical-align:middle}.navbar-form .input-group .form-control,.navbar-form .input-group .input-group-addon,.navbar-form .input-group .input-group-btn{width:auto}.navbar-form .input-group>.form-control{width:100%}.navbar-form .control-label{margin-bottom:0;vertical-align:middle}.navbar-form .checkbox,.navbar-form .radio{display:inline-block;margin-top:0;margin-bottom:0;vertical-align:middle}.navbar-form .checkbox label,.navbar-form .radio label{padding-left:0}.navbar-form .checkbox input[type=checkbox],.navbar-form .radio input[type=radio]{position:relative;margin-left:0}.navbar-form .has-feedback .form-control-feedback{top:0}}@media (max-width:767px){.navbar-form .form-group{margin-bottom:5px}.navbar-form .form-group:last-child{margin-bottom:0}}@media (min-width:768px){.navbar-form{width:auto;padding-top:0;padding-bottom:0;margin-right:0;margin-left:0;border:0;-webkit-box-shadow:none;box-shadow:none}}.navbar-nav>li>.dropdown-menu{margin-top:0;border-top-left-radius:0;border-top-right-radius:0}.navbar-fixed-bottom .navbar-nav>li>.dropdown-menu{margin-bottom:0;border-top-left-radius:4px;border-top-right-radius:4px;border-bottom-right-radius:0;border-bottom-left-radius:0}.navbar-btn{margin-top:8px;margin-bottom:8px}.navbar-btn.btn-sm{margin-top:10px;margin-bottom:10px}.navbar-btn.btn-xs{margin-top:14px;margin-bottom:14px}.navbar-text{margin-top:15px;margin-bottom:15px}@media (min-width:768px){.navbar-text{float:left;margin-right:15px;margin-left:15px}}@media (min-width:768px){.navbar-left{float:left!important}.navbar-right{float:right!important;margin-right:-15px}.navbar-right~.navbar-right{margin-right:0}}.navbar-default{background-color:#f8f8f8;border-color:#e7e7e7}.navbar-default .navbar-brand{color:#777}.navbar-default .navbar-brand:focus,.navbar-default .navbar-brand:hover{color:#5e5e5e;background-color:transparent}.navbar-default .navbar-text{color:#777}.navbar-default .navbar-nav>li>a{color:#777}.navbar-default .navbar-nav>li>a:focus,.navbar-default .navbar-nav>li>a:hover{color:#333;background-color:transparent}.navbar-default .navbar-nav>.active>a,.navbar-default .navbar-nav>.active>a:focus,.navbar-default .navbar-nav>.active>a:hover{color:#555;background-color:#e7e7e7}.navbar-default .navbar-nav>.disabled>a,.navbar-default .navbar-nav>.disabled>a:focus,.navbar-default .navbar-nav>.disabled>a:hover{color:#ccc;background-color:transparent}.navbar-default .navbar-toggle{border-color:#ddd}.navbar-default .navbar-toggle:focus,.navbar-default .navbar-toggle:hover{background-color:#ddd}.navbar-default .navbar-toggle .icon-bar{background-color:#888}.navbar-default .navbar-collapse,.navbar-default .navbar-form{border-color:#e7e7e7}.navbar-default .navbar-nav>.open>a,.navbar-default .navbar-nav>.open>a:focus,.navbar-default .navbar-nav>.open>a:hover{color:#555;background-color:#e7e7e7}@media (max-width:767px){.navbar-default .navbar-nav .open .dropdown-menu>li>a{color:#777}.navbar-default .navbar-nav .open .dropdown-menu>li>a:focus,.navbar-default .navbar-nav .open .dropdown-menu>li>a:hover{color:#333;background-color:transparent}.navbar-default .navbar-nav .open .dropdown-menu>.active>a,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:focus,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:hover{color:#555;background-color:#e7e7e7}.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:focus,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:hover{color:#ccc;background-color:transparent}}.navbar-default .navbar-link{color:#777}.navbar-default .navbar-link:hover{color:#333}.navbar-default .btn-link{color:#777}.navbar-default .btn-link:focus,.navbar-default .btn-link:hover{color:#333}.navbar-default .btn-link[disabled]:focus,.navbar-default .btn-link[disabled]:hover,fieldset[disabled] .navbar-default .btn-link:focus,fieldset[disabled] .navbar-default .btn-link:hover{color:#ccc}.navbar-inverse{background-color:#222;border-color:#080808}.navbar-inverse .navbar-brand{color:#9d9d9d}.navbar-inverse .navbar-brand:focus,.navbar-inverse .navbar-brand:hover{color:#fff;background-color:transparent}.navbar-inverse .navbar-text{color:#9d9d9d}.navbar-inverse .navbar-nav>li>a{color:#9d9d9d}.navbar-inverse .navbar-nav>li>a:focus,.navbar-inverse .navbar-nav>li>a:hover{color:#fff;background-color:transparent}.navbar-inverse .navbar-nav>.active>a,.navbar-inverse .navbar-nav>.active>a:focus,.navbar-inverse .navbar-nav>.active>a:hover{color:#fff;background-color:#080808}.navbar-inverse .navbar-nav>.disabled>a,.navbar-inverse .navbar-nav>.disabled>a:focus,.navbar-inverse .navbar-nav>.disabled>a:hover{color:#444;background-color:transparent}.navbar-inverse .navbar-toggle{border-color:#333}.navbar-inverse .navbar-toggle:focus,.navbar-inverse .navbar-toggle:hover{background-color:#333}.navbar-inverse .navbar-toggle .icon-bar{background-color:#fff}.navbar-inverse .navbar-collapse,.navbar-inverse .navbar-form{border-color:#101010}.navbar-inverse .navbar-nav>.open>a,.navbar-inverse .navbar-nav>.open>a:focus,.navbar-inverse .navbar-nav>.open>a:hover{color:#fff;background-color:#080808}@media (max-width:767px){.navbar-inverse .navbar-nav .open .dropdown-menu>.dropdown-header{border-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu .divider{background-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a{color:#9d9d9d}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:focus,.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:hover{color:#fff;background-color:transparent}.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:focus,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:hover{color:#fff;background-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:focus,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:hover{color:#444;background-color:transparent}}.navbar-inverse .navbar-link{color:#9d9d9d}.navbar-inverse .navbar-link:hover{color:#fff}.navbar-inverse .btn-link{color:#9d9d9d}.navbar-inverse .btn-link:focus,.navbar-inverse .btn-link:hover{color:#fff}.navbar-inverse .btn-link[disabled]:focus,.navbar-inverse .btn-link[disabled]:hover,fieldset[disabled] .navbar-inverse .btn-link:focus,fieldset[disabled] .navbar-inverse .btn-link:hover{color:#444}.breadcrumb{padding:8px 15px;margin-bottom:20px;list-style:none;background-color:#f5f5f5;border-radius:4px}.breadcrumb>li{display:inline-block}.breadcrumb>li+li:before{padding:0 5px;color:#ccc;content:"/\00a0"}.breadcrumb>.active{color:#777}.pagination{display:inline-block;padding-left:0;margin:20px 0;border-radius:4px}.pagination>li{display:inline}.pagination>li>a,.pagination>li>span{position:relative;float:left;padding:6px 12px;margin-left:-1px;line-height:1.42857143;color:#337ab7;text-decoration:none;background-color:#fff;border:1px solid #ddd}.pagination>li:first-child>a,.pagination>li:first-child>span{margin-left:0;border-top-left-radius:4px;border-bottom-left-radius:4px}.pagination>li:last-child>a,.pagination>li:last-child>span{border-top-right-radius:4px;border-bottom-right-radius:4px}.pagination>li>a:focus,.pagination>li>a:hover,.pagination>li>span:focus,.pagination>li>span:hover{color:#23527c;background-color:#eee;border-color:#ddd}.pagination>.active>a,.pagination>.active>a:focus,.pagination>.active>a:hover,.pagination>.active>span,.pagination>.active>span:focus,.pagination>.active>span:hover{z-index:2;color:#fff;cursor:default;background-color:#337ab7;border-color:#337ab7}.pagination>.disabled>a,.pagination>.disabled>a:focus,.pagination>.disabled>a:hover,.pagination>.disabled>span,.pagination>.disabled>span:focus,.pagination>.disabled>span:hover{color:#777;cursor:not-allowed;background-color:#fff;border-color:#ddd}.pagination-lg>li>a,.pagination-lg>li>span{padding:10px 16px;font-size:18px}.pagination-lg>li:first-child>a,.pagination-lg>li:first-child>span{border-top-left-radius:6px;border-bottom-left-radius:6px}.pagination-lg>li:last-child>a,.pagination-lg>li:last-child>span{border-top-right-radius:6px;border-bottom-right-radius:6px}.pagination-sm>li>a,.pagination-sm>li>span{padding:5px 10px;font-size:12px}.pagination-sm>li:first-child>a,.pagination-sm>li:first-child>span{border-top-left-radius:3px;border-bottom-left-radius:3px}.pagination-sm>li:last-child>a,.pagination-sm>li:last-child>span{border-top-right-radius:3px;border-bottom-right-radius:3px}.pager{padding-left:0;margin:20px 0;text-align:center;list-style:none}.pager li{display:inline}.pager li>a,.pager li>span{display:inline-block;padding:5px 14px;background-color:#fff;border:1px solid #ddd;border-radius:15px}.pager li>a:focus,.pager li>a:hover{text-decoration:none;background-color:#eee}.pager .next>a,.pager .next>span{float:right}.pager .previous>a,.pager .previous>span{float:left}.pager .disabled>a,.pager .disabled>a:focus,.pager .disabled>a:hover,.pager .disabled>span{color:#777;cursor:not-allowed;background-color:#fff}.label{display:inline;padding:.2em .6em .3em;font-size:75%;font-weight:700;line-height:1;color:#fff;text-align:center;white-space:nowrap;vertical-align:baseline;border-radius:.25em}a.label:focus,a.label:hover{color:#fff;text-decoration:none;cursor:pointer}.label:empty{display:none}.btn .label{position:relative;top:-1px}.label-default{background-color:#777}.label-default[href]:focus,.label-default[href]:hover{background-color:#5e5e5e}.label-primary{background-color:#337ab7}.label-primary[href]:focus,.label-primary[href]:hover{background-color:#286090}.label-success{background-color:#5cb85c}.label-success[href]:focus,.label-success[href]:hover{background-color:#449d44}.label-info{background-color:#5bc0de}.label-info[href]:focus,.label-info[href]:hover{background-color:#31b0d5}.label-warning{background-color:#f0ad4e}.label-warning[href]:focus,.label-warning[href]:hover{background-color:#ec971f}.label-danger{background-color:#d9534f}.label-danger[href]:focus,.label-danger[href]:hover{background-color:#c9302c}.badge{display:inline-block;min-width:10px;padding:3px 7px;font-size:12px;font-weight:700;line-height:1;color:#fff;text-align:center;white-space:nowrap;vertical-align:baseline;background-color:#777;border-radius:10px}.badge:empty{display:none}.btn .badge{position:relative;top:-1px}.btn-xs .badge{top:0;padding:1px 5px}a.badge:focus,a.badge:hover{color:#fff;text-decoration:none;cursor:pointer}.list-group-item.active>.badge,.nav-pills>.active>a>.badge{color:#337ab7;background-color:#fff}.list-group-item>.badge{float:right}.list-group-item>.badge+.badge{margin-right:5px}.nav-pills>li>a>.badge{margin-left:3px}.jumbotron{padding:30px 15px;margin-bottom:30px;color:inherit;background-color:#eee}.jumbotron .h1,.jumbotron h1{color:inherit}.jumbotron p{margin-bottom:15px;font-size:21px;font-weight:200}.jumbotron>hr{border-top-color:#d5d5d5}.container .jumbotron,.container-fluid .jumbotron{border-radius:6px}.jumbotron .container{max-width:100%}@media screen and (min-width:768px){.jumbotron{padding:48px 0}.container .jumbotron,.container-fluid .jumbotron{padding-right:60px;padding-left:60px}.jumbotron .h1,.jumbotron h1{font-size:63px}}.thumbnail{display:block;padding:4px;margin-bottom:20px;line-height:1.42857143;background-color:#fff;border:1px solid #ddd;border-radius:4px;-webkit-transition:border .2s ease-in-out;-o-transition:border .2s ease-in-out;transition:border .2s ease-in-out}.thumbnail a>img,.thumbnail>img{margin-right:auto;margin-left:auto}a.thumbnail.active,a.thumbnail:focus,a.thumbnail:hover{border-color:#337ab7}.thumbnail .caption{padding:9px;color:#333}.alert{padding:15px;margin-bottom:20px;border:1px solid transparent;border-radius:4px}.alert h4{margin-top:0;color:inherit}.alert .alert-link{font-weight:700}.alert>p,.alert>ul{margin-bottom:0}.alert>p+p{margin-top:5px}.alert-dismissable,.alert-dismissible{padding-right:35px}.alert-dismissable .close,.alert-dismissible .close{position:relative;top:-2px;right:-21px;color:inherit}.alert-success{color:#3c763d;background-color:#dff0d8;border-color:#d6e9c6}.alert-success hr{border-top-color:#c9e2b3}.alert-success .alert-link{color:#2b542c}.alert-info{color:#31708f;background-color:#d9edf7;border-color:#bce8f1}.alert-info hr{border-top-color:#a6e1ec}.alert-info .alert-link{color:#245269}.alert-warning{color:#8a6d3b;background-color:#fcf8e3;border-color:#faebcc}.alert-warning hr{border-top-color:#f7e1b5}.alert-warning .alert-link{color:#66512c}.alert-danger{color:#a94442;background-color:#f2dede;border-color:#ebccd1}.alert-danger hr{border-top-color:#e4b9c0}.alert-danger .alert-link{color:#843534}@-webkit-keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}@-o-keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}@keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}.progress{height:20px;margin-bottom:20px;overflow:hidden;background-color:#f5f5f5;border-radius:4px;-webkit-box-shadow:inset 0 1px 2px rgba(0,0,0,.1);box-shadow:inset 0 1px 2px rgba(0,0,0,.1)}.progress-bar{float:left;width:0;height:100%;font-size:12px;line-height:20px;color:#fff;text-align:center;background-color:#337ab7;-webkit-box-shadow:inset 0 -1px 0 rgba(0,0,0,.15);box-shadow:inset 0 -1px 0 rgba(0,0,0,.15);-webkit-transition:width .6s ease;-o-transition:width .6s ease;transition:width .6s ease}.progress-bar-striped,.progress-striped .progress-bar{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);-webkit-background-size:40px 40px;background-size:40px 40px}.progress-bar.active,.progress.active .progress-bar{-webkit-animation:progress-bar-stripes 2s linear infinite;-o-animation:progress-bar-stripes 2s linear infinite;animation:progress-bar-stripes 2s linear infinite}.progress-bar-success{background-color:#5cb85c}.progress-striped .progress-bar-success{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent)}.progress-bar-info{background-color:#5bc0de}.progress-striped .progress-bar-info{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent)}.progress-bar-warning{background-color:#f0ad4e}.progress-striped .progress-bar-warning{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent)}.progress-bar-danger{background-color:#d9534f}.progress-striped .progress-bar-danger{background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:-o-linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,.15) 50%,rgba(255,255,255,.15) 75%,transparent 75%,transparent)}.media{margin-top:15px}.media:first-child{margin-top:0}.media,.media-body{overflow:hidden;zoom:1}.media-body{width:10000px}.media-object{display:block}.media-right,.media>.pull-right{padding-left:10px}.media-left,.media>.pull-left{padding-right:10px}.media-body,.media-left,.media-right{display:table-cell;vertical-align:top}.media-middle{vertical-align:middle}.media-bottom{vertical-align:bottom}.media-heading{margin-top:0;margin-bottom:5px}.media-list{padding-left:0;list-style:none}.list-group{padding-left:0;margin-bottom:20px}.list-group-item{position:relative;display:block;padding:10px 15px;margin-bottom:-1px;background-color:#fff;border:1px solid #ddd}.list-group-item:first-child{border-top-left-radius:4px;border-top-right-radius:4px}.list-group-item:last-child{margin-bottom:0;border-bottom-right-radius:4px;border-bottom-left-radius:4px}a.list-group-item{color:#555}a.list-group-item .list-group-item-heading{color:#333}a.list-group-item:focus,a.list-group-item:hover{color:#555;text-decoration:none;background-color:#f5f5f5}.list-group-item.disabled,.list-group-item.disabled:focus,.list-group-item.disabled:hover{color:#777;cursor:not-allowed;background-color:#eee}.list-group-item.disabled .list-group-item-heading,.list-group-item.disabled:focus .list-group-item-heading,.list-group-item.disabled:hover .list-group-item-heading{color:inherit}.list-group-item.disabled .list-group-item-text,.list-group-item.disabled:focus .list-group-item-text,.list-group-item.disabled:hover .list-group-item-text{color:#777}.list-group-item.active,.list-group-item.active:focus,.list-group-item.active:hover{z-index:2;color:#fff;background-color:#337ab7;border-color:#337ab7}.list-group-item.active .list-group-item-heading,.list-group-item.active .list-group-item-heading>.small,.list-group-item.active .list-group-item-heading>small,.list-group-item.active:focus .list-group-item-heading,.list-group-item.active:focus .list-group-item-heading>.small,.list-group-item.active:focus .list-group-item-heading>small,.list-group-item.active:hover .list-group-item-heading,.list-group-item.active:hover .list-group-item-heading>.small,.list-group-item.active:hover .list-group-item-heading>small{color:inherit}.list-group-item.active .list-group-item-text,.list-group-item.active:focus .list-group-item-text,.list-group-item.active:hover .list-group-item-text{color:#c7ddef}.list-group-item-success{color:#3c763d;background-color:#dff0d8}a.list-group-item-success{color:#3c763d}a.list-group-item-success .list-group-item-heading{color:inherit}a.list-group-item-success:focus,a.list-group-item-success:hover{color:#3c763d;background-color:#d0e9c6}a.list-group-item-success.active,a.list-group-item-success.active:focus,a.list-group-item-success.active:hover{color:#fff;background-color:#3c763d;border-color:#3c763d}.list-group-item-info{color:#31708f;background-color:#d9edf7}a.list-group-item-info{color:#31708f}a.list-group-item-info .list-group-item-heading{color:inherit}a.list-group-item-info:focus,a.list-group-item-info:hover{color:#31708f;background-color:#c4e3f3}a.list-group-item-info.active,a.list-group-item-info.active:focus,a.list-group-item-info.active:hover{color:#fff;background-color:#31708f;border-color:#31708f}.list-group-item-warning{color:#8a6d3b;background-color:#fcf8e3}a.list-group-item-warning{color:#8a6d3b}a.list-group-item-warning .list-group-item-heading{color:inherit}a.list-group-item-warning:focus,a.list-group-item-warning:hover{color:#8a6d3b;background-color:#faf2cc}a.list-group-item-warning.active,a.list-group-item-warning.active:focus,a.list-group-item-warning.active:hover{color:#fff;background-color:#8a6d3b;border-color:#8a6d3b}.list-group-item-danger{color:#a94442;background-color:#f2dede}a.list-group-item-danger{color:#a94442}a.list-group-item-danger .list-group-item-heading{color:inherit}a.list-group-item-danger:focus,a.list-group-item-danger:hover{color:#a94442;background-color:#ebcccc}a.list-group-item-danger.active,a.list-group-item-danger.active:focus,a.list-group-item-danger.active:hover{color:#fff;background-color:#a94442;border-color:#a94442}.list-group-item-heading{margin-top:0;margin-bottom:5px}.list-group-item-text{margin-bottom:0;line-height:1.3}.panel{margin-bottom:20px;background-color:#fff;border:1px solid transparent;border-radius:4px;-webkit-box-shadow:0 1px 1px rgba(0,0,0,.05);box-shadow:0 1px 1px rgba(0,0,0,.05)}.panel-body{padding:15px}.panel-heading{padding:10px 15px;border-bottom:1px solid transparent;border-top-left-radius:3px;border-top-right-radius:3px}.panel-heading>.dropdown .dropdown-toggle{color:inherit}.panel-title{margin-top:0;margin-bottom:0;font-size:16px;color:inherit}.panel-title>.small,.panel-title>.small>a,.panel-title>a,.panel-title>small,.panel-title>small>a{color:inherit}.panel-footer{padding:10px 15px;background-color:#f5f5f5;border-top:1px solid #ddd;border-bottom-right-radius:3px;border-bottom-left-radius:3px}.panel>.list-group,.panel>.panel-collapse>.list-group{margin-bottom:0}.panel>.list-group .list-group-item,.panel>.panel-collapse>.list-group .list-group-item{border-width:1px 0;border-radius:0}.panel>.list-group:first-child .list-group-item:first-child,.panel>.panel-collapse>.list-group:first-child .list-group-item:first-child{border-top:0;border-top-left-radius:3px;border-top-right-radius:3px}.panel>.list-group:last-child .list-group-item:last-child,.panel>.panel-collapse>.list-group:last-child .list-group-item:last-child{border-bottom:0;border-bottom-right-radius:3px;border-bottom-left-radius:3px}.panel-heading+.list-group .list-group-item:first-child{border-top-width:0}.list-group+.panel-footer{border-top-width:0}.panel>.panel-collapse>.table,.panel>.table,.panel>.table-responsive>.table{margin-bottom:0}.panel>.panel-collapse>.table caption,.panel>.table caption,.panel>.table-responsive>.table caption{padding-right:15px;padding-left:15px}.panel>.table-responsive:first-child>.table:first-child,.panel>.table:first-child{border-top-left-radius:3px;border-top-right-radius:3px}.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child,.panel>.table:first-child>tbody:first-child>tr:first-child,.panel>.table:first-child>thead:first-child>tr:first-child{border-top-left-radius:3px;border-top-right-radius:3px}.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child td:first-child,.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child th:first-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child td:first-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child th:first-child,.panel>.table:first-child>tbody:first-child>tr:first-child td:first-child,.panel>.table:first-child>tbody:first-child>tr:first-child th:first-child,.panel>.table:first-child>thead:first-child>tr:first-child td:first-child,.panel>.table:first-child>thead:first-child>tr:first-child th:first-child{border-top-left-radius:3px}.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child td:last-child,.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child th:last-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child td:last-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child th:last-child,.panel>.table:first-child>tbody:first-child>tr:first-child td:last-child,.panel>.table:first-child>tbody:first-child>tr:first-child th:last-child,.panel>.table:first-child>thead:first-child>tr:first-child td:last-child,.panel>.table:first-child>thead:first-child>tr:first-child th:last-child{border-top-right-radius:3px}.panel>.table-responsive:last-child>.table:last-child,.panel>.table:last-child{border-bottom-right-radius:3px;border-bottom-left-radius:3px}.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child,.panel>.table:last-child>tbody:last-child>tr:last-child,.panel>.table:last-child>tfoot:last-child>tr:last-child{border-bottom-right-radius:3px;border-bottom-left-radius:3px}.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child td:first-child,.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child th:first-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child td:first-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child th:first-child,.panel>.table:last-child>tbody:last-child>tr:last-child td:first-child,.panel>.table:last-child>tbody:last-child>tr:last-child th:first-child,.panel>.table:last-child>tfoot:last-child>tr:last-child td:first-child,.panel>.table:last-child>tfoot:last-child>tr:last-child th:first-child{border-bottom-left-radius:3px}.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child td:last-child,.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child th:last-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child td:last-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child th:last-child,.panel>.table:last-child>tbody:last-child>tr:last-child td:last-child,.panel>.table:last-child>tbody:last-child>tr:last-child th:last-child,.panel>.table:last-child>tfoot:last-child>tr:last-child td:last-child,.panel>.table:last-child>tfoot:last-child>tr:last-child th:last-child{border-bottom-right-radius:3px}.panel>.panel-body+.table,.panel>.panel-body+.table-responsive,.panel>.table+.panel-body,.panel>.table-responsive+.panel-body{border-top:1px solid #ddd}.panel>.table>tbody:first-child>tr:first-child td,.panel>.table>tbody:first-child>tr:first-child th{border-top:0}.panel>.table-bordered,.panel>.table-responsive>.table-bordered{border:0}.panel>.table-bordered>tbody>tr>td:first-child,.panel>.table-bordered>tbody>tr>th:first-child,.panel>.table-bordered>tfoot>tr>td:first-child,.panel>.table-bordered>tfoot>tr>th:first-child,.panel>.table-bordered>thead>tr>td:first-child,.panel>.table-bordered>thead>tr>th:first-child,.panel>.table-responsive>.table-bordered>tbody>tr>td:first-child,.panel>.table-responsive>.table-bordered>tbody>tr>th:first-child,.panel>.table-responsive>.table-bordered>tfoot>tr>td:first-child,.panel>.table-responsive>.table-bordered>tfoot>tr>th:first-child,.panel>.table-responsive>.table-bordered>thead>tr>td:first-child,.panel>.table-responsive>.table-bordered>thead>tr>th:first-child{border-left:0}.panel>.table-bordered>tbody>tr>td:last-child,.panel>.table-bordered>tbody>tr>th:last-child,.panel>.table-bordered>tfoot>tr>td:last-child,.panel>.table-bordered>tfoot>tr>th:last-child,.panel>.table-bordered>thead>tr>td:last-child,.panel>.table-bordered>thead>tr>th:last-child,.panel>.table-responsive>.table-bordered>tbody>tr>td:last-child,.panel>.table-responsive>.table-bordered>tbody>tr>th:last-child,.panel>.table-responsive>.table-bordered>tfoot>tr>td:last-child,.panel>.table-responsive>.table-bordered>tfoot>tr>th:last-child,.panel>.table-responsive>.table-bordered>thead>tr>td:last-child,.panel>.table-responsive>.table-bordered>thead>tr>th:last-child{border-right:0}.panel>.table-bordered>tbody>tr:first-child>td,.panel>.table-bordered>tbody>tr:first-child>th,.panel>.table-bordered>thead>tr:first-child>td,.panel>.table-bordered>thead>tr:first-child>th,.panel>.table-responsive>.table-bordered>tbody>tr:first-child>td,.panel>.table-responsive>.table-bordered>tbody>tr:first-child>th,.panel>.table-responsive>.table-bordered>thead>tr:first-child>td,.panel>.table-responsive>.table-bordered>thead>tr:first-child>th{border-bottom:0}.panel>.table-bordered>tbody>tr:last-child>td,.panel>.table-bordered>tbody>tr:last-child>th,.panel>.table-bordered>tfoot>tr:last-child>td,.panel>.table-bordered>tfoot>tr:last-child>th,.panel>.table-responsive>.table-bordered>tbody>tr:last-child>td,.panel>.table-responsive>.table-bordered>tbody>tr:last-child>th,.panel>.table-responsive>.table-bordered>tfoot>tr:last-child>td,.panel>.table-responsive>.table-bordered>tfoot>tr:last-child>th{border-bottom:0}.panel>.table-responsive{margin-bottom:0;border:0}.panel-group{margin-bottom:20px}.panel-group .panel{margin-bottom:0;border-radius:4px}.panel-group .panel+.panel{margin-top:5px}.panel-group .panel-heading{border-bottom:0}.panel-group .panel-heading+.panel-collapse>.list-group,.panel-group .panel-heading+.panel-collapse>.panel-body{border-top:1px solid #ddd}.panel-group .panel-footer{border-top:0}.panel-group .panel-footer+.panel-collapse .panel-body{border-bottom:1px solid #ddd}.panel-default{border-color:#ddd}.panel-default>.panel-heading{color:#333;background-color:#f5f5f5;border-color:#ddd}.panel-default>.panel-heading+.panel-collapse>.panel-body{border-top-color:#ddd}.panel-default>.panel-heading .badge{color:#f5f5f5;background-color:#333}.panel-default>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#ddd}.panel-primary{border-color:#337ab7}.panel-primary>.panel-heading{color:#fff;background-color:#337ab7;border-color:#337ab7}.panel-primary>.panel-heading+.panel-collapse>.panel-body{border-top-color:#337ab7}.panel-primary>.panel-heading .badge{color:#337ab7;background-color:#fff}.panel-primary>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#337ab7}.panel-success{border-color:#d6e9c6}.panel-success>.panel-heading{color:#3c763d;background-color:#dff0d8;border-color:#d6e9c6}.panel-success>.panel-heading+.panel-collapse>.panel-body{border-top-color:#d6e9c6}.panel-success>.panel-heading .badge{color:#dff0d8;background-color:#3c763d}.panel-success>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#d6e9c6}.panel-info{border-color:#bce8f1}.panel-info>.panel-heading{color:#31708f;background-color:#d9edf7;border-color:#bce8f1}.panel-info>.panel-heading+.panel-collapse>.panel-body{border-top-color:#bce8f1}.panel-info>.panel-heading .badge{color:#d9edf7;background-color:#31708f}.panel-info>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#bce8f1}.panel-warning{border-color:#faebcc}.panel-warning>.panel-heading{color:#8a6d3b;background-color:#fcf8e3;border-color:#faebcc}.panel-warning>.panel-heading+.panel-collapse>.panel-body{border-top-color:#faebcc}.panel-warning>.panel-heading .badge{color:#fcf8e3;background-color:#8a6d3b}.panel-warning>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#faebcc}.panel-danger{border-color:#ebccd1}.panel-danger>.panel-heading{color:#a94442;background-color:#f2dede;border-color:#ebccd1}.panel-danger>.panel-heading+.panel-collapse>.panel-body{border-top-color:#ebccd1}.panel-danger>.panel-heading .badge{color:#f2dede;background-color:#a94442}.panel-danger>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#ebccd1}.embed-responsive{position:relative;display:block;height:0;padding:0;overflow:hidden}.embed-responsive .embed-responsive-item,.embed-responsive embed,.embed-responsive iframe,.embed-responsive object,.embed-responsive video{position:absolute;top:0;bottom:0;left:0;width:100%;height:100%;border:0}.embed-responsive.embed-responsive-16by9{padding-bottom:56.25%}.embed-responsive.embed-responsive-4by3{padding-bottom:75%}.well{min-height:20px;padding:19px;margin-bottom:20px;background-color:#f5f5f5;border:1px solid #e3e3e3;border-radius:4px;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.05);box-shadow:inset 0 1px 1px rgba(0,0,0,.05)}.well blockquote{border-color:#ddd;border-color:rgba(0,0,0,.15)}.well-lg{padding:24px;border-radius:6px}.well-sm{padding:9px;border-radius:3px}.close{float:right;font-size:21px;font-weight:700;line-height:1;color:#000;text-shadow:0 1px 0 #fff;filter:alpha(opacity=20);opacity:.2}.close:focus,.close:hover{color:#000;text-decoration:none;cursor:pointer;filter:alpha(opacity=50);opacity:.5}button.close{-webkit-appearance:none;padding:0;cursor:pointer;background:0 0;border:0}.modal-open{overflow:hidden}.modal{position:fixed;top:0;right:0;bottom:0;left:0;z-index:1040;display:none;overflow:hidden;-webkit-overflow-scrolling:touch;outline:0}.modal.fade .modal-dialog{-webkit-transition:-webkit-transform .3s ease-out;-o-transition:-o-transform .3s ease-out;transition:transform .3s ease-out;-webkit-transform:translate(0,-25%);-ms-transform:translate(0,-25%);-o-transform:translate(0,-25%);transform:translate(0,-25%)}.modal.in .modal-dialog{-webkit-transform:translate(0,0);-ms-transform:translate(0,0);-o-transform:translate(0,0);transform:translate(0,0)}.modal-open .modal{overflow-x:hidden;overflow-y:auto}.modal-dialog{position:relative;width:auto;margin:10px}.modal-content{position:relative;background-color:#fff;-webkit-background-clip:padding-box;background-clip:padding-box;border:1px solid #999;border:1px solid rgba(0,0,0,.2);border-radius:6px;outline:0;-webkit-box-shadow:0 3px 9px rgba(0,0,0,.5);box-shadow:0 3px 9px rgba(0,0,0,.5)}.modal-backdrop{position:absolute;top:0;right:0;left:0;background-color:#000}.modal-backdrop.fade{filter:alpha(opacity=0);opacity:0}.modal-backdrop.in{filter:alpha(opacity=50);opacity:.5}.modal-header{min-height:16.43px;padding:15px;border-bottom:1px solid #e5e5e5}.modal-header .close{margin-top:-2px}.modal-title{margin:0;line-height:1.42857143}.modal-body{position:relative;padding:15px}.modal-footer{padding:15px;text-align:right;border-top:1px solid #e5e5e5}.modal-footer .btn+.btn{margin-bottom:0;margin-left:5px}.modal-footer .btn-group .btn+.btn{margin-left:-1px}.modal-footer .btn-block+.btn-block{margin-left:0}.modal-scrollbar-measure{position:absolute;top:-9999px;width:50px;height:50px;overflow:scroll}@media (min-width:768px){.modal-dialog{width:600px;margin:30px auto}.modal-content{-webkit-box-shadow:0 5px 15px rgba(0,0,0,.5);box-shadow:0 5px 15px rgba(0,0,0,.5)}.modal-sm{width:300px}}@media (min-width:992px){.modal-lg{width:900px}}.tooltip{position:absolute;z-index:1070;display:block;font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:12px;font-weight:400;line-height:1.4;visibility:visible;filter:alpha(opacity=0);opacity:0}.tooltip.in{filter:alpha(opacity=90);opacity:.9}.tooltip.top{padding:5px 0;margin-top:-3px}.tooltip.right{padding:0 5px;margin-left:3px}.tooltip.bottom{padding:5px 0;margin-top:3px}.tooltip.left{padding:0 5px;margin-left:-3px}.tooltip-inner{max-width:200px;padding:3px 8px;color:#fff;text-align:center;text-decoration:none;background-color:#000;border-radius:4px}.tooltip-arrow{position:absolute;width:0;height:0;border-color:transparent;border-style:solid}.tooltip.top .tooltip-arrow{bottom:0;left:50%;margin-left:-5px;border-width:5px 5px 0;border-top-color:#000}.tooltip.top-left .tooltip-arrow{right:5px;bottom:0;margin-bottom:-5px;border-width:5px 5px 0;border-top-color:#000}.tooltip.top-right .tooltip-arrow{bottom:0;left:5px;margin-bottom:-5px;border-width:5px 5px 0;border-top-color:#000}.tooltip.right .tooltip-arrow{top:50%;left:0;margin-top:-5px;border-width:5px 5px 5px 0;border-right-color:#000}.tooltip.left .tooltip-arrow{top:50%;right:0;margin-top:-5px;border-width:5px 0 5px 5px;border-left-color:#000}.tooltip.bottom .tooltip-arrow{top:0;left:50%;margin-left:-5px;border-width:0 5px 5px;border-bottom-color:#000}.tooltip.bottom-left .tooltip-arrow{top:0;right:5px;margin-top:-5px;border-width:0 5px 5px;border-bottom-color:#000}.tooltip.bottom-right .tooltip-arrow{top:0;left:5px;margin-top:-5px;border-width:0 5px 5px;border-bottom-color:#000}.popover{position:absolute;top:0;left:0;z-index:1060;display:none;max-width:276px;padding:1px;font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:14px;font-weight:400;line-height:1.42857143;text-align:left;white-space:normal;background-color:#fff;-webkit-background-clip:padding-box;background-clip:padding-box;border:1px solid #ccc;border:1px solid rgba(0,0,0,.2);border-radius:6px;-webkit-box-shadow:0 5px 10px rgba(0,0,0,.2);box-shadow:0 5px 10px rgba(0,0,0,.2)}.popover.top{margin-top:-10px}.popover.right{margin-left:10px}.popover.bottom{margin-top:10px}.popover.left{margin-left:-10px}.popover-title{padding:8px 14px;margin:0;font-size:14px;background-color:#f7f7f7;border-bottom:1px solid #ebebeb;border-radius:5px 5px 0 0}.popover-content{padding:9px 14px}.popover>.arrow,.popover>.arrow:after{position:absolute;display:block;width:0;height:0;border-color:transparent;border-style:solid}.popover>.arrow{border-width:11px}.popover>.arrow:after{content:"";border-width:10px}.popover.top>.arrow{bottom:-11px;left:50%;margin-left:-11px;border-top-color:#999;border-top-color:rgba(0,0,0,.25);border-bottom-width:0}.popover.top>.arrow:after{bottom:1px;margin-left:-10px;content:" ";border-top-color:#fff;border-bottom-width:0}.popover.right>.arrow{top:50%;left:-11px;margin-top:-11px;border-right-color:#999;border-right-color:rgba(0,0,0,.25);border-left-width:0}.popover.right>.arrow:after{bottom:-10px;left:1px;content:" ";border-right-color:#fff;border-left-width:0}.popover.bottom>.arrow{top:-11px;left:50%;margin-left:-11px;border-top-width:0;border-bottom-color:#999;border-bottom-color:rgba(0,0,0,.25)}.popover.bottom>.arrow:after{top:1px;margin-left:-10px;content:" ";border-top-width:0;border-bottom-color:#fff}.popover.left>.arrow{top:50%;right:-11px;margin-top:-11px;border-right-width:0;border-left-color:#999;border-left-color:rgba(0,0,0,.25)}.popover.left>.arrow:after{right:1px;bottom:-10px;content:" ";border-right-width:0;border-left-color:#fff}.carousel{position:relative}.carousel-inner{position:relative;width:100%;overflow:hidden}.carousel-inner>.item{position:relative;display:none;-webkit-transition:.6s ease-in-out left;-o-transition:.6s ease-in-out left;transition:.6s ease-in-out left}.carousel-inner>.item>a>img,.carousel-inner>.item>img{line-height:1}@media all and (transform-3d),(-webkit-transform-3d){.carousel-inner>.item{-webkit-transition:-webkit-transform .6s ease-in-out;-o-transition:-o-transform .6s ease-in-out;transition:transform .6s ease-in-out;-webkit-backface-visibility:hidden;backface-visibility:hidden;-webkit-perspective:1000;perspective:1000}.carousel-inner>.item.active.right,.carousel-inner>.item.next{left:0;-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0)}.carousel-inner>.item.active.left,.carousel-inner>.item.prev{left:0;-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0)}.carousel-inner>.item.active,.carousel-inner>.item.next.left,.carousel-inner>.item.prev.right{left:0;-webkit-transform:translate3d(0,0,0);transform:translate3d(0,0,0)}}.carousel-inner>.active,.carousel-inner>.next,.carousel-inner>.prev{display:block}.carousel-inner>.active{left:0}.carousel-inner>.next,.carousel-inner>.prev{position:absolute;top:0;width:100%}.carousel-inner>.next{left:100%}.carousel-inner>.prev{left:-100%}.carousel-inner>.next.left,.carousel-inner>.prev.right{left:0}.carousel-inner>.active.left{left:-100%}.carousel-inner>.active.right{left:100%}.carousel-control{position:absolute;top:0;bottom:0;left:0;width:15%;font-size:20px;color:#fff;text-align:center;text-shadow:0 1px 2px rgba(0,0,0,.6);filter:alpha(opacity=50);opacity:.5}.carousel-control.left{background-image:-webkit-linear-gradient(left,rgba(0,0,0,.5) 0,rgba(0,0,0,.0001) 100%);background-image:-o-linear-gradient(left,rgba(0,0,0,.5) 0,rgba(0,0,0,.0001) 100%);background-image:-webkit-gradient(linear,left top,right top,from(rgba(0,0,0,.5)),to(rgba(0,0,0,.0001)));background-image:linear-gradient(to right,rgba(0,0,0,.5) 0,rgba(0,0,0,.0001) 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1);background-repeat:repeat-x}.carousel-control.right{right:0;left:auto;background-image:-webkit-linear-gradient(left,rgba(0,0,0,.0001) 0,rgba(0,0,0,.5) 100%);background-image:-o-linear-gradient(left,rgba(0,0,0,.0001) 0,rgba(0,0,0,.5) 100%);background-image:-webkit-gradient(linear,left top,right top,from(rgba(0,0,0,.0001)),to(rgba(0,0,0,.5)));background-image:linear-gradient(to right,rgba(0,0,0,.0001) 0,rgba(0,0,0,.5) 100%);filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1);background-repeat:repeat-x}.carousel-control:focus,.carousel-control:hover{color:#fff;text-decoration:none;filter:alpha(opacity=90);outline:0;opacity:.9}.carousel-control .glyphicon-chevron-left,.carousel-control .glyphicon-chevron-right,.carousel-control .icon-next,.carousel-control .icon-prev{position:absolute;top:50%;z-index:5;display:inline-block}.carousel-control .glyphicon-chevron-left,.carousel-control .icon-prev{left:50%;margin-left:-10px}.carousel-control .glyphicon-chevron-right,.carousel-control .icon-next{right:50%;margin-right:-10px}.carousel-control .icon-next,.carousel-control .icon-prev{width:20px;height:20px;margin-top:-10px;font-family:serif;line-height:1}.carousel-control .icon-prev:before{content:'\2039'}.carousel-control .icon-next:before{content:'\203a'}.carousel-indicators{position:absolute;bottom:10px;left:50%;z-index:15;width:60%;padding-left:0;margin-left:-30%;text-align:center;list-style:none}.carousel-indicators li{display:inline-block;width:10px;height:10px;margin:1px;text-indent:-999px;cursor:pointer;background-color:#000 \9;background-color:rgba(0,0,0,0);border:1px solid #fff;border-radius:10px}.carousel-indicators .active{width:12px;height:12px;margin:0;background-color:#fff}.carousel-caption{position:absolute;right:15%;bottom:20px;left:15%;z-index:10;padding-top:20px;padding-bottom:20px;color:#fff;text-align:center;text-shadow:0 1px 2px rgba(0,0,0,.6)}.carousel-caption .btn{text-shadow:none}@media screen and (min-width:768px){.carousel-control .glyphicon-chevron-left,.carousel-control .glyphicon-chevron-right,.carousel-control .icon-next,.carousel-control .icon-prev{width:30px;height:30px;margin-top:-15px;font-size:30px}.carousel-control .glyphicon-chevron-left,.carousel-control .icon-prev{margin-left:-15px}.carousel-control .glyphicon-chevron-right,.carousel-control .icon-next{margin-right:-15px}.carousel-caption{right:20%;left:20%;padding-bottom:30px}.carousel-indicators{bottom:20px}}.btn-group-vertical>.btn-group:after,.btn-group-vertical>.btn-group:before,.btn-toolbar:after,.btn-toolbar:before,.clearfix:after,.clearfix:before,.container-fluid:after,.container-fluid:before,.container:after,.container:before,.dl-horizontal dd:after,.dl-horizontal dd:before,.form-horizontal .form-group:after,.form-horizontal .form-group:before,.modal-footer:after,.modal-footer:before,.nav:after,.nav:before,.navbar-collapse:after,.navbar-collapse:before,.navbar-header:after,.navbar-header:before,.navbar:after,.navbar:before,.pager:after,.pager:before,.panel-body:after,.panel-body:before,.row:after,.row:before{display:table;content:" "}.btn-group-vertical>.btn-group:after,.btn-toolbar:after,.clearfix:after,.container-fluid:after,.container:after,.dl-horizontal dd:after,.form-horizontal .form-group:after,.modal-footer:after,.nav:after,.navbar-collapse:after,.navbar-header:after,.navbar:after,.pager:after,.panel-body:after,.row:after{clear:both}.center-block{display:block;margin-right:auto;margin-left:auto}.pull-right{float:right!important}.pull-left{float:left!important}.hide{display:none!important}.show{display:block!important}.invisible{visibility:hidden}.text-hide{font:0/0 a;color:transparent;text-shadow:none;background-color:transparent;border:0}.hidden{display:none!important;visibility:hidden!important}.affix{position:fixed}@-ms-viewport{width:device-width}.visible-lg,.visible-md,.visible-sm,.visible-xs{display:none!important}.visible-lg-block,.visible-lg-inline,.visible-lg-inline-block,.visible-md-block,.visible-md-inline,.visible-md-inline-block,.visible-sm-block,.visible-sm-inline,.visible-sm-inline-block,.visible-xs-block,.visible-xs-inline,.visible-xs-inline-block{display:none!important}@media (max-width:767px){.visible-xs{display:block!important}table.visible-xs{display:table}tr.visible-xs{display:table-row!important}td.visible-xs,th.visible-xs{display:table-cell!important}}@media (max-width:767px){.visible-xs-block{display:block!important}}@media (max-width:767px){.visible-xs-inline{display:inline!important}}@media (max-width:767px){.visible-xs-inline-block{display:inline-block!important}}@media (min-width:768px) and (max-width:991px){.visible-sm{display:block!important}table.visible-sm{display:table}tr.visible-sm{display:table-row!important}td.visible-sm,th.visible-sm{display:table-cell!important}}@media (min-width:768px) and (max-width:991px){.visible-sm-block{display:block!important}}@media (min-width:768px) and (max-width:991px){.visible-sm-inline{display:inline!important}}@media (min-width:768px) and (max-width:991px){.visible-sm-inline-block{display:inline-block!important}}@media (min-width:992px) and (max-width:1199px){.visible-md{display:block!important}table.visible-md{display:table}tr.visible-md{display:table-row!important}td.visible-md,th.visible-md{display:table-cell!important}}@media (min-width:992px) and (max-width:1199px){.visible-md-block{display:block!important}}@media (min-width:992px) and (max-width:1199px){.visible-md-inline{display:inline!important}}@media (min-width:992px) and (max-width:1199px){.visible-md-inline-block{display:inline-block!important}}@media (min-width:1200px){.visible-lg{display:block!important}table.visible-lg{display:table}tr.visible-lg{display:table-row!important}td.visible-lg,th.visible-lg{display:table-cell!important}}@media (min-width:1200px){.visible-lg-block{display:block!important}}@media (min-width:1200px){.visible-lg-inline{display:inline!important}}@media (min-width:1200px){.visible-lg-inline-block{display:inline-block!important}}@media (max-width:767px){.hidden-xs{display:none!important}}@media (min-width:768px) and (max-width:991px){.hidden-sm{display:none!important}}@media (min-width:992px) and (max-width:1199px){.hidden-md{display:none!important}}@media (min-width:1200px){.hidden-lg{display:none!important}}.visible-print{display:none!important}@media print{.visible-print{display:block!important}table.visible-print{display:table}tr.visible-print{display:table-row!important}td.visible-print,th.visible-print{display:table-cell!important}}.visible-print-block{display:none!important}@media print{.visible-print-block{display:block!important}}.visible-print-inline{display:none!important}@media print{.visible-print-inline{display:inline!important}}.visible-print-inline-block{display:none!important}@media print{.visible-print-inline-block{display:inline-block!important}}@media print{.hidden-print{display:none!important}} \ No newline at end of file diff --git a/css/customstyles.css b/css/customstyles.css new file mode 100644 index 0000000000..d505dbd8de --- /dev/null +++ b/css/customstyles.css @@ -0,0 +1,1179 @@ +body { + font-size:15px; +} + +.bs-callout { + padding: 20px; + margin: 20px 0; + border: 1px solid #eee; + border-left-width: 5px; + border-radius: 3px; +} +.bs-callout h4 { + margin-top: 0; + margin-bottom: 5px; +} +.bs-callout p:last-child { + margin-bottom: 0; +} +.bs-callout code { + border-radius: 3px; +} +.bs-callout+.bs-callout { + margin-top: -5px; +} +.bs-callout-default { + border-left-color: #777; +} +.bs-callout-default h4 { + color: #777; +} +.bs-callout-primary { + border-left-color: #428bca; +} +.bs-callout-primary h4 { + color: #428bca; +} +.bs-callout-success { + border-left-color: #5cb85c; +} +.bs-callout-success h4 { + color: #5cb85c; +} +.bs-callout-danger { + border-left-color: #d9534f; +} +.bs-callout-danger h4 { + color: #d9534f; +} +.bs-callout-warning { + border-left-color: #f0ad4e; +} +.bs-callout-warning h4 { + color: #f0ad4e; +} +.bs-callout-info { + border-left-color: #5bc0de; +} +.bs-callout-info h4 { + color: #5bc0de; +} + + +.gi-2x{font-size: 2em;} +.gi-3x{font-size: 3em;} +.gi-4x{font-size: 4em;} +.gi-5x{font-size: 5em;} + + + + + +.breadcrumb > .active {color: #777 !important;} + +/* make room for the nav bar */ +h1[id], +h2[id], +h3[id], +h4[id], +h5[id], +h6[id], +dt[id]{ +padding-top: 20px; +margin-top: 0px +} + +body h1 {margin-top:40px;} + +.post-content img { + margin: 12px 0px 3px 0px; + width: auto; + height: auto; + max-width: 100%; + max-height: 100%; +} + +.post-content ol li, .post-content ul li { + margin: 10px 0px; +} + +.pageSummary { + font-size:13px; + display:block; + margin-bottom:15px; + padding-left:20px; +} + +.post-summary { + margin-bottom:12px; +} + +.bs-example{ + margin: 20px; +} + +.breadcrumb li { + color: gray; +} + +table { + background-color: transparent; +} +caption { + padding-top: 8px; + padding-bottom: 8px; + color: #777; + text-align: left; +} +th { + text-align: left; +} +table { + max-width: 90%; + margin-bottom: 20px; + border: 1px solid #dedede; +} + +table > thead > tr > th, +table > tbody > tr > th, +table > tfoot > tr > th, +table > thead > tr > td, +table > tbody > tr > td, +table > tfoot > tr > td { + padding: 8px; + line-height: 1.42857143; + vertical-align: top; + border-top: 1px solid #ddd; +} +table > thead > tr > th { + vertical-align: bottom; + border-bottom: 2px solid #ddd; + text-transform: none; + background-color: #777; + color: white; + text-align: left; +} +table > caption + thead > tr:first-child > th, +table > colgroup + thead > tr:first-child > th, +table > thead:first-child > tr:first-child > th, +table > caption + thead > tr:first-child > td, +table > colgroup + thead > tr:first-child > td, +table > thead:first-child > tr:first-child > td { + border-top: 0; +} + +table > tbody > tr:nth-of-type(odd) { + background-color: #f9f9f9; +} + +table col[class*="col-"] { + position: static; + display: table-column; + float: none; +} +table td[class*="col-"], +table th[class*="col-"] { + position: static; + display: table-cell; + float: none; +} + + +table td:first-child { + width: 150px; + /*font-weight:bold;*/ +} + +table.boldFirstColumn td:first-child { + font-weight: bold; +} + +table tr td { + hyphens: auto; +} + + +p.external a { + text-align:right; + font-size:12px; + color: #0088cc; + display:inline; +} + +#definition-box-container div a.active { + font-weight: bold; +} +p.post-meta {font-size: 80%; color: #777;} + +.entry-date{font-size:14px;font-size:0.875rem;line-height:1.71429;margin-bottom:0;text-transform:uppercase;} + +/* search area */ +#search-demo-container ul#results-container { + list-style: none; + font-size: 12px; + background-color: white; + position: absolute; + top: 40px; /* if you change anything about the nav, you'll prob. need to reset the top and left values here.*/ + left: 20px; + z-index: -1; + width:223px; + border-left: 1px solid #dedede; + box-shadow: 2px 3px 2px #dedede; +} + + +ul#results-container a { + background-color: transparent; +} + +ul#results-container a:hover { + color: black; +} + + +#search-demo-container a:hover { + color: black; +} +#search-input { + padding: .5em; + margin-left:20px; + width:20em; + font-size: 0.8em; + -webkit-box-sizing: border-box; + -moz-box-sizing: border-box; + box-sizing: border-box; + float: right; + margin-top:10px; +} +/* end search */ + +.filter-options { + margin-bottom: 20px; +} +.filter-options button { + margin: 3px; +} + +div#toc ul li { + margin: 8px 0px 8px 22px; + font-size: 90%; + list-style: square; +} +div#toc ul { + background-color: whitesmoke; + padding: 5px; + border-radius: 5px; + max-width: 300px; + color: gray; +} + +div#toc ul li ul { + padding-left:8px; + +} + +div#toc ul li ul li::before { + content: "– "; +} + +div#toc >ul::before { + content: "Table of Contents"; + font-weight: 500; + color: #555; + text-align:center; + margin-left:auto; + margin-right:auto; + width:70px; + padding-top:20px; + padding-bottom:20px; + padding-left:10px; +} + +li.dropdownActive a { + font-weight: bold; +} + + +.post-content a.fa-rss { + color: orange; +} + + +.navbar-inverse .navbar-nav > li > a { + background-color: transparent; + margin-top:10px; +} + +.post-content .rssfeedLink { + color: #248EC2; +} + +footer { + font-size: smaller; +} + +/* FAQ page */ +#accordion .panel-heading { + font-size: 12px; +} + +a.accordion-toggle, a.accordion-collapsed { + font-size: 14px; + text-decoration: none; +} + +/* navgoco sidebar styles (customized) */ +.nav, .nav ul, .nav li { + list-style: none; +} + +.nav ul { + padding: 0; + /*margin: 0 0 0 18px;*/ + margin:0px; +} + +.nav { + /* padding: 4px;*/ + padding:0px; + margin: 0px; +} + +.nav > li { + margin: 1px 0; +} + +.nav > li li { + margin: 2px 0; +} + +.nav a { + color: #333; + display: block; + outline: none; + /*-webkit-border-radius: 4px; + -moz-border-radius: 4px; + border-radius: 4px;*/ + text-decoration: none; +} + +.nav li > a > span { + float: right; + font-size: 19px; + font-weight: bolder; +} + + +.nav li > a > span:after { + content: '\25be'; +} +.nav li.active > a > span:after { + content: '\25b4'; +} + +.nav a:hover, .nav li.active > a { + background-color: #8D8D8D; + color: #f5f5f5; +} + +.nav > li.active > a { +background-color: #347DBE; +} + +.nav li a { + font-size: 12px; + line-height: 18px; + padding: 2px 10px; + background-color: #f1f1f1; +} + +.nav > li > a { + font-size: 14px; + line-height: 20px; + padding: 4px 10px; +} + +ul#mysidebar { + border-radius:0px; +} + +.nav ul li ul li a { + padding-left:40px; +} + +.nav li.thirdlevel > a { + color: #248EC2; + font-weight:bold; + padding-left:20px; + background-color: whitesmoke !important; +} + + +.nav ul li a { + background-color: #FAFAFA; +} + +.nav li a { + padding-right:10px; +} + +.nav li a:hover { + background-color: #8D8D8D; +} + +.nav ul li a { + border-top:1px solid whitesmoke; + padding-left:10px; +} +/* end sidebar */ + +.navbar-inverse .navbar-nav > .active > a, .navbar-inverse .navbar-nav > .active > a:hover, .navbar-inverse .navbar-nav > .active > a:focus { + border-radius:5px; +} + +.navbar-inverse .navbar-nav>.open>a, .navbar-inverse .navbar-nav>.open>a:focus, .navbar-inverse .navbar-nav>.open>a:hover { + border-radius: 5px; +} + +span.projectTitle { + font-family: Helvetica; + font-weight: bold; +} + +.footer { + text-align: right; +} + +.footerMeta { + background-color: whitesmoke; + padding: 10px; + max-width: 250px; + border-radius: 5px; + margin-top: 50px; + font-style:italic; + font-size:12px; +} + +img.screenshotSmall { + max-width: 300px; +} + + +dl dt p { + margin-left:20px; +} + + +dl dd { + margin-top:10px; + margin-bottom:10px; +} + +dl.dl-horizontal dd { + padding-top: 20px; +} + +figcaption { + + padding-bottom:12px; + padding-top:6px; + max-width: 90%; + margin-bottom:20px; + font-style: italic; + color: gray; + +} + +.testing { + color: orange; +} + +.preference { + color: red; +} + + +table.dataTable thead { + background-color: #444; +} +table td { + hyphens: auto; +} + +section table tr.success { + background-color: #dff0d8 !important; +} + +table tr.info { + background-color: #d9edf7 !important; +} + +section table tr.warning, table tr.testing, table tr.testing > td.sorting_1 { + background-color: #fcf8e3 !important; +} +section table tr.danger, table tr.preference, table tr.preference > td.sorting_1 { + background-color: #f2dede !important; +} + +.orange { + color: orange; +} + +table.profile thead tr th { + background-color: #248ec2; +} + +table.request thead tr th { + background-color: #ED1951; +} + +.audienceLabel { + margin: 10px; + float: right; + border:1px solid #dedede; + padding:7px; +} + +.prefaceAudienceLabel { + color: gray; + text-align: center; + margin:5px; +} +span.myLabel { + padding-left:10px; + padding-right:10px; +} + +button.cursorNorm { + cursor: default; +} + +a.dropdown-toggle, .navbar-inverse .navbar-nav > li > a { + margin-left: 10px; +} + +hr.faded { + border: 0; + height: 1px; + background-image: -webkit-linear-gradient(left, rgba(0,0,0,0), rgba(0,0,0,0.75), rgba(0,0,0,0)); + background-image: -moz-linear-gradient(left, rgba(0,0,0,0), rgba(0,0,0,0.75), rgba(0,0,0,0)); + background-image: -ms-linear-gradient(left, rgba(0,0,0,0), rgba(0,0,0,0.75), rgba(0,0,0,0)); + background-image: -o-linear-gradient(left, rgba(0,0,0,0), rgba(0,0,0,0.75), rgba(0,0,0,0)); +} + +hr.shaded { + height: 12px; + border: 0; + box-shadow: inset 0 6px 6px -6px rgba(0,0,0,0.5); + margin-top: 70px; + background: white; + width: 100%; + margin-bottom: 10px; +} + +.fa-6x{font-size:900%;} +.fa-7x{font-size:1100%;} +.fa-8x{font-size:1300%;} +.fa-9x{font-size:1500%;} +.fa-10x{font-size:1700%;} + +i.border { + padding: 10px 20px; + background-color: whitesmoke; +} + +a[data-toggle] { + color: #248EC2; +} + +.summary { + font-size:120%; + color: #808080; + margin:20px 0px 20px 0px; + border-left: 5px solid #ED1951; + padding-left: 10px; + +} + +.summary:before { + content: "Summary: "; + font-weight: bold; +} + + +a.fa.fa-envelope-o.mailto { + font-weight: 600; +} + +h3 {color: #ED1951; font-weight:normal; font-size:130%;} +h4 {color: #808080; font-weight:normal; font-size:120%; font-style:italic;} + +.alert, .callout { + overflow: hidden; +} + +.nav-tabs > li.active > a, .nav-tabs > li.active > a:hover, .nav-tabs > li.active > a:focus { + background-color: #248ec2; + color: white; +} + +ol li ol li {list-style-type: lower-alpha;} +ol li ul li {list-style-type: disc;} + +li img {clear:both; } + +div#toc ul li ul li { + list-style-type: none; + margin: 5px 0px 0px 0px; +} + +.tab-content { + padding: 15px; + background-color: #FAFAFA; +} + +span.tagTitle {font-weight: 500;} + +li.activeSeries { + font-weight: bold; +} + +.seriesContext .dropdown-menu li.active { + font-weight: bold; + margin-left: 43px; + font-size:18px; +} + +.alert-warning { + color: #444; +} + +div.alert code, h2 code { + background-color: transparent !important; +} +/* without this, the links in these notes aren't visible.*/ +.alert a { + text-decoration: underline; +} + +div.tags {padding: 10px 5px;} + +.tabLabel { + font-weight: normal; +} + +hr { + background: #999; + margin: 30px 0px; + width: 90%; + margin-left: auto; + margin-right: auto; +} + +button.cursorNorm { + cursor: pointer; +} + +h2 { + font-size:24px; + line-height:29px; +} +span.otherProgrammingLanguages { + font-style: normal; +} + +a[data-toggle="tooltip"] { + color: #649345; + font-style: italic; + cursor: default; +} + +.seriesNext, .seriesContext { + margin-top: 15px; + margin-bottom: 15px; +} + +.seriescontext ol li { + list-style-type: upper-roman; +} + +ol.series li { + list-style-type: decimal; + margin-left: 40px; + padding-left: 0px; +} + +.siteTagline { + font-size: 200%; + font-weight: bold; + color: silver; + font-family: monospace; + text-align: center; + line-height: 10px; + margin: 20px 0px; + display: block; +} + +.versionTagline { + text-align: center; + margin-bottom: 20px; + font-family: courier; + color: silver; + color: #444; + display:block; +} + +/* not sure if using this ...*/ +.navbar-inverse .navbar-collapse, .navbar-inverse .navbar-form { + border-color: #248ec2 !important; +} + +#mysidebar .nav ul { + background-color: #FAFAFA; +} +.nav ul.series li { + list-style: decimal; + font-size:12px; +} + +.nav ul.series li a:hover { + background-color: gray; +} +.nav ul.series { + padding-left: 30px; +} + +.nav ul.series { + background-color: #FAFAFA; +} + +/* +a.dropdown-toggle.otherProgLangs { + color: #f7e68f !important; +} +*/ + +span.muted {color: #666;} + +table code {background-color: transparent;} + +.highlight .err { + color: #a61717; + background-color: transparent !important; +} + +table p { + margin-top: 12px; + margin-bottom: 12px; +} + +pre, table code { + white-space: pre-wrap; /* css-3 */ + white-space: -moz-pre-wrap; /* Mozilla, since 1999 */ + white-space: -pre-wrap; /* Opera 4-6 */ + white-space: -o-pre-wrap; /* Opera 7 */ + word-wrap: break-word; /* Internet Explorer 5.5+ */ +} + +pre { + margin: 25px 0px; +} + +#json-box-container pre { + margin: 0px; +} + +.video-js { + margin: 30px 0px; +} + +video { + display: block; + margin: 30px 0px; + border: 1px solid #c0c0c0; +} + + +p.required, p.dataType {display: block; color: #c0c0c0; font-size: 80%; margin-left:4px;} + +dd {margin-left:20px;} + +.post-content img.inline { + margin:0px; + margin-bottom:6px; +} +.panel-heading { + font-weight: bold; +} + +.note code, .alert code, .warning code, div#toc code, h2 code, h3 code, h4 code { + color: inherit; + padding: 0px; +} + +.alert { + margin-bottom:10px; + margin-top:10px; +} + +a.accordion-toggle { + font-style: normal; +} + +span.red { + color: red; + font-family: Monaco, Menlo, Consolas, "Courier New", monospace; +} + +h3.codeExplanation { + font-size:18px; + font-style:normal; + color: black; + line-height: 24px; +} + +span.soft { + color: #c0c0c0; +} + +.githubEditButton { + margin-bottom:7px; +} + +.endpoint { + padding: 15px; + background-color: #f0f0f0; + font-family: courier; + font-size: 110%; + margin: 20px 0px; + color: #444; +} + +.parameter { + font-family: courier; + color: red !important; +} + +.formBoundary { + border: 1px solid gray; + padding: 15px; + margin: 15px 0px; + background-color: whitesmoke; +} + +@media (max-width: 767px) { + .navbar-inverse .navbar-nav .open .dropdown-menu > li > a { + color: #444; + } +} + +@media (max-width: 990px) { + #mysidebar { + position: relative; + } +} + +@media (min-width: 1000px) { + + ul#mysidebar { + width: 225px; + } +} + +@media (max-width: 900px) { + + ul#mysidebar { + max-width: 100%; + } +} + +.col-md-9 img { + max-width: 100%; + max-height: 100%; +} + + +.post-content img { + margin: 12px 0px 3px 0px; + width: auto; + height: auto; + max-width: 100%; + max-height: 100%; +} +.col-md-9 img { + max-width: 100%; + max-height: 100%; +} + + +.post-content img { + margin: 12px 0px 3px 0px; + width: auto; + height: auto; + max-width: 100%; + max-height: 100%; +} + +.videoThumbs img { + float: left; + margin:15px 15px 15px 0px; + box-shadow: 2px 2px 1px #f0f0f0; + border: 1px solid #dedede; +} + + +@media only screen and (min-width: 900px), only screen and (min-device-width: 900px) { + .col-md-9 img { + max-width: 700px; + max-height: 700px; + } +} + +*:hover > .anchorjs-link { + transition: color .25s linear; + text-decoration: none; +} + +.kbCaption { + color: white; + background-color: #444; + padding:10px; +} + +/* this part adds an icon after external links, using FontAwesome*/ +a[href^="http://"]:after, a[href^="https://"]:after { + content: "\f08e"; + font-family: FontAwesome; + font-weight: normal; + font-style: normal; + display: inline-block; + text-decoration: none; + padding-left: 3px; +} + +/* Strip the outbound icon when this class is present */ +a[href].noCrossRef::after, +a.no_icon:after + { + content:"" !important; + padding-left: 0; +} + +.btn-default { + margin-bottom: 10px; +} + +/* algolia search */ + +.search { + text-align: left; +} +.search input { + font-size: 20px; + width: 300px; +} +.results { + margin: auto; + text-align: left; +} +.results ul { + list-style-type: none; + padding: 0; +} + +/* algolia */ + +div.results { + position: absolute; + background-color: white; + width: 100%; +} + +.post-meta { + font-size: 14px; + color: #828282; +} + +.post-link { + font-size: 22px; +} + +.post-list p { + margin: 10px 0px; +} + +time { + margin-right: 10px; +} + +p.post-meta time { + margin-right: 0px; +} + +span.label.label-default { + background-color: gray; +} + +span.label.label-primary { + background-color: #f0ad4e; +} +.col-lg-12 .nav li a {background-color: white} + + +.nav li.active > a.subfoldersTitle { + background-color: whitesmoke; + font-weight: bold; + color: black; + } + +a code { + color: #248EC2; +} + +code + a > code { + margin-left: -7px; +} + +table th code { + color: white; +} + +ol li ul li ol li { + list-style: decimal; +} + +ol li ul li ol li ul li{ + list-style: disc; +} + +.post-content table th { + vertical-align: top; +} + +table thead th code.highlighter-rouge { + background-color: transparent; +} + + +.box { + padding: 10px; + border: 1px solid #888; + box-shadow: 2px 2px 4px #dedede; + width: 100px; + height: 80px; + background-color: #f5f5f5; + font-family: Arial; + font-size: 12px; + hyphens: auto; + float: left; + font-size: 12px; +} + +.box:hover { + background-color: #f0f0f0; +} + +#userMap { + overflow-x: auto; + overflow-y: auto; + padding: 20px; + min-width: 770px; +} + +#userMap .active { + background-color: #d6f5d6; + border:1px solid #555; + font-weight: bold; +} + +h2.userMapTitle { + font-family: Arial; +} + +#userMap a:hover { + text-decoration: none; + } + +div.arrow { + max-width: 50px; + margin-left: 15px; + margin-right: 15px; + font-size: 20px; +} + +div.content { + max-width: 110px +} + +#userMap div.arrow, #userMap div.content { + float: left; +} + +.clearfix { + clear: both; +} + + +#userMap div.arrow { + position: relative; + top: 30px; +} + +.box1 { + margin-left:0px; +} + +button.btn.btn-default.btn-lg.modalButton1 { + margin-left: -20px; +} + +div.box.box1 { + margin-left: -20px; +} + +#userMap .btn-lg { + width: 100px; + height: 80px; + +} + +#userMap .complexArrow { + font-size: 22px; + margin: 0px 10px; +} + + +#userMap .btn-lg .active { + background-color: #d6f5d6; +} + +#userMap .btn-lg { + white-space: pre-wrap; /* css-3 */ + white-space: -moz-pre-wrap; /* Mozilla, since 1999 */ + white-space: -pre-wrap; /* Opera 4-6 */ + white-space: -o-pre-wrap; /* Opera 7 */ + word-wrap: break-word; /* Internet Explorer 5.5+ */ + font-size: 14px; + } + +/* + * Let's target IE to respect aspect ratios and sizes for img tags containing SVG files + * + * [1] IE9 + * [2] IE10+ + */ +/* 1 */ +.ie9 img[src$=".svg"] { + width: 100%; +} +/* 2 */ +@media screen and (-ms-high-contrast: active), (-ms-high-contrast: none) { + img[src$=".svg"] { + width: 100%; + } +} + +h4.panel-title { + padding-top: 0px; + margin-top: 0px; +} diff --git a/css/font-awesome.min.css b/css/font-awesome.min.css new file mode 100644 index 0000000000..08e68ec0c0 --- /dev/null +++ b/css/font-awesome.min.css @@ -0,0 +1,4 @@ +/*! + * Font Awesome 4.2.0 by @davegandy - http://fontawesome.io - @fontawesome + * License - http://fontawesome.io/license (Font: SIL OFL 1.1, CSS: MIT License) + */@font-face{font-family:'FontAwesome';src:url('fonts/fontawesome-webfont.eot?v=4.2.0');src:url('fonts/fontawesome-webfont.eot?#iefix&v=4.2.0') format('embedded-opentype'),url('fonts/fontawesome-webfont.woff?v=4.2.0') format('woff'),url('fonts/fontawesome-webfont.ttf?v=4.2.0') format('truetype'),url('fonts/fontawesome-webfont.svg?v=4.2.0#fontawesomeregular') format('svg');font-weight:normal;font-style:normal}.fa{display:inline-block;font:normal normal normal 14px/1 FontAwesome;font-size:inherit;text-rendering:auto;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.fa-lg{font-size:1.33333333em;line-height:.75em;vertical-align:-15%}.fa-2x{font-size:2em}.fa-3x{font-size:3em}.fa-4x{font-size:4em}.fa-5x{font-size:5em}.fa-fw{width:1.28571429em;text-align:center}.fa-ul{padding-left:0;margin-left:2.14285714em;list-style-type:none}.fa-ul>li{position:relative}.fa-li{position:absolute;left:-2.14285714em;width:2.14285714em;top:.14285714em;text-align:center}.fa-li.fa-lg{left:-1.85714286em}.fa-border{padding:.2em .25em .15em;border:solid .08em #eee;border-radius:.1em}.pull-right{float:right}.pull-left{float:left}.fa.pull-left{margin-right:.3em}.fa.pull-right{margin-left:.3em}.fa-spin{-webkit-animation:fa-spin 2s infinite linear;animation:fa-spin 2s infinite linear}@-webkit-keyframes fa-spin{0%{-webkit-transform:rotate(0deg);transform:rotate(0deg)}100%{-webkit-transform:rotate(359deg);transform:rotate(359deg)}}@keyframes fa-spin{0%{-webkit-transform:rotate(0deg);transform:rotate(0deg)}100%{-webkit-transform:rotate(359deg);transform:rotate(359deg)}}.fa-rotate-90{filter:progid:DXImageTransform.Microsoft.BasicImage(rotation=1);-webkit-transform:rotate(90deg);-ms-transform:rotate(90deg);transform:rotate(90deg)}.fa-rotate-180{filter:progid:DXImageTransform.Microsoft.BasicImage(rotation=2);-webkit-transform:rotate(180deg);-ms-transform:rotate(180deg);transform:rotate(180deg)}.fa-rotate-270{filter:progid:DXImageTransform.Microsoft.BasicImage(rotation=3);-webkit-transform:rotate(270deg);-ms-transform:rotate(270deg);transform:rotate(270deg)}.fa-flip-horizontal{filter:progid:DXImageTransform.Microsoft.BasicImage(rotation=0, mirror=1);-webkit-transform:scale(-1, 1);-ms-transform:scale(-1, 1);transform:scale(-1, 1)}.fa-flip-vertical{filter:progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1);-webkit-transform:scale(1, -1);-ms-transform:scale(1, -1);transform:scale(1, -1)}:root .fa-rotate-90,:root .fa-rotate-180,:root .fa-rotate-270,:root .fa-flip-horizontal,:root .fa-flip-vertical{filter:none}.fa-stack{position:relative;display:inline-block;width:2em;height:2em;line-height:2em;vertical-align:middle}.fa-stack-1x,.fa-stack-2x{position:absolute;left:0;width:100%;text-align:center}.fa-stack-1x{line-height:inherit}.fa-stack-2x{font-size:2em}.fa-inverse{color:#fff}.fa-glass:before{content:"\f000"}.fa-music:before{content:"\f001"}.fa-search:before{content:"\f002"}.fa-envelope-o:before{content:"\f003"}.fa-heart:before{content:"\f004"}.fa-star:before{content:"\f005"}.fa-star-o:before{content:"\f006"}.fa-user:before{content:"\f007"}.fa-film:before{content:"\f008"}.fa-th-large:before{content:"\f009"}.fa-th:before{content:"\f00a"}.fa-th-list:before{content:"\f00b"}.fa-check:before{content:"\f00c"}.fa-remove:before,.fa-close:before,.fa-times:before{content:"\f00d"}.fa-search-plus:before{content:"\f00e"}.fa-search-minus:before{content:"\f010"}.fa-power-off:before{content:"\f011"}.fa-signal:before{content:"\f012"}.fa-gear:before,.fa-cog:before{content:"\f013"}.fa-trash-o:before{content:"\f014"}.fa-home:before{content:"\f015"}.fa-file-o:before{content:"\f016"}.fa-clock-o:before{content:"\f017"}.fa-road:before{content:"\f018"}.fa-download:before{content:"\f019"}.fa-arrow-circle-o-down:before{content:"\f01a"}.fa-arrow-circle-o-up:before{content:"\f01b"}.fa-inbox:before{content:"\f01c"}.fa-play-circle-o:before{content:"\f01d"}.fa-rotate-right:before,.fa-repeat:before{content:"\f01e"}.fa-refresh:before{content:"\f021"}.fa-list-alt:before{content:"\f022"}.fa-lock:before{content:"\f023"}.fa-flag:before{content:"\f024"}.fa-headphones:before{content:"\f025"}.fa-volume-off:before{content:"\f026"}.fa-volume-down:before{content:"\f027"}.fa-volume-up:before{content:"\f028"}.fa-qrcode:before{content:"\f029"}.fa-barcode:before{content:"\f02a"}.fa-tag:before{content:"\f02b"}.fa-tags:before{content:"\f02c"}.fa-book:before{content:"\f02d"}.fa-bookmark:before{content:"\f02e"}.fa-print:before{content:"\f02f"}.fa-camera:before{content:"\f030"}.fa-font:before{content:"\f031"}.fa-bold:before{content:"\f032"}.fa-italic:before{content:"\f033"}.fa-text-height:before{content:"\f034"}.fa-text-width:before{content:"\f035"}.fa-align-left:before{content:"\f036"}.fa-align-center:before{content:"\f037"}.fa-align-right:before{content:"\f038"}.fa-align-justify:before{content:"\f039"}.fa-list:before{content:"\f03a"}.fa-dedent:before,.fa-outdent:before{content:"\f03b"}.fa-indent:before{content:"\f03c"}.fa-video-camera:before{content:"\f03d"}.fa-photo:before,.fa-image:before,.fa-picture-o:before{content:"\f03e"}.fa-pencil:before{content:"\f040"}.fa-map-marker:before{content:"\f041"}.fa-adjust:before{content:"\f042"}.fa-tint:before{content:"\f043"}.fa-edit:before,.fa-pencil-square-o:before{content:"\f044"}.fa-share-square-o:before{content:"\f045"}.fa-check-square-o:before{content:"\f046"}.fa-arrows:before{content:"\f047"}.fa-step-backward:before{content:"\f048"}.fa-fast-backward:before{content:"\f049"}.fa-backward:before{content:"\f04a"}.fa-play:before{content:"\f04b"}.fa-pause:before{content:"\f04c"}.fa-stop:before{content:"\f04d"}.fa-forward:before{content:"\f04e"}.fa-fast-forward:before{content:"\f050"}.fa-step-forward:before{content:"\f051"}.fa-eject:before{content:"\f052"}.fa-chevron-left:before{content:"\f053"}.fa-chevron-right:before{content:"\f054"}.fa-plus-circle:before{content:"\f055"}.fa-minus-circle:before{content:"\f056"}.fa-times-circle:before{content:"\f057"}.fa-check-circle:before{content:"\f058"}.fa-question-circle:before{content:"\f059"}.fa-info-circle:before{content:"\f05a"}.fa-crosshairs:before{content:"\f05b"}.fa-times-circle-o:before{content:"\f05c"}.fa-check-circle-o:before{content:"\f05d"}.fa-ban:before{content:"\f05e"}.fa-arrow-left:before{content:"\f060"}.fa-arrow-right:before{content:"\f061"}.fa-arrow-up:before{content:"\f062"}.fa-arrow-down:before{content:"\f063"}.fa-mail-forward:before,.fa-share:before{content:"\f064"}.fa-expand:before{content:"\f065"}.fa-compress:before{content:"\f066"}.fa-plus:before{content:"\f067"}.fa-minus:before{content:"\f068"}.fa-asterisk:before{content:"\f069"}.fa-exclamation-circle:before{content:"\f06a"}.fa-gift:before{content:"\f06b"}.fa-leaf:before{content:"\f06c"}.fa-fire:before{content:"\f06d"}.fa-eye:before{content:"\f06e"}.fa-eye-slash:before{content:"\f070"}.fa-warning:before,.fa-exclamation-triangle:before{content:"\f071"}.fa-plane:before{content:"\f072"}.fa-calendar:before{content:"\f073"}.fa-random:before{content:"\f074"}.fa-comment:before{content:"\f075"}.fa-magnet:before{content:"\f076"}.fa-chevron-up:before{content:"\f077"}.fa-chevron-down:before{content:"\f078"}.fa-retweet:before{content:"\f079"}.fa-shopping-cart:before{content:"\f07a"}.fa-folder:before{content:"\f07b"}.fa-folder-open:before{content:"\f07c"}.fa-arrows-v:before{content:"\f07d"}.fa-arrows-h:before{content:"\f07e"}.fa-bar-chart-o:before,.fa-bar-chart:before{content:"\f080"}.fa-twitter-square:before{content:"\f081"}.fa-facebook-square:before{content:"\f082"}.fa-camera-retro:before{content:"\f083"}.fa-key:before{content:"\f084"}.fa-gears:before,.fa-cogs:before{content:"\f085"}.fa-comments:before{content:"\f086"}.fa-thumbs-o-up:before{content:"\f087"}.fa-thumbs-o-down:before{content:"\f088"}.fa-star-half:before{content:"\f089"}.fa-heart-o:before{content:"\f08a"}.fa-sign-out:before{content:"\f08b"}.fa-linkedin-square:before{content:"\f08c"}.fa-thumb-tack:before{content:"\f08d"}.fa-external-link:before{content:"\f08e"}.fa-sign-in:before{content:"\f090"}.fa-trophy:before{content:"\f091"}.fa-github-square:before{content:"\f092"}.fa-upload:before{content:"\f093"}.fa-lemon-o:before{content:"\f094"}.fa-phone:before{content:"\f095"}.fa-square-o:before{content:"\f096"}.fa-bookmark-o:before{content:"\f097"}.fa-phone-square:before{content:"\f098"}.fa-twitter:before{content:"\f099"}.fa-facebook:before{content:"\f09a"}.fa-github:before{content:"\f09b"}.fa-unlock:before{content:"\f09c"}.fa-credit-card:before{content:"\f09d"}.fa-rss:before{content:"\f09e"}.fa-hdd-o:before{content:"\f0a0"}.fa-bullhorn:before{content:"\f0a1"}.fa-bell:before{content:"\f0f3"}.fa-certificate:before{content:"\f0a3"}.fa-hand-o-right:before{content:"\f0a4"}.fa-hand-o-left:before{content:"\f0a5"}.fa-hand-o-up:before{content:"\f0a6"}.fa-hand-o-down:before{content:"\f0a7"}.fa-arrow-circle-left:before{content:"\f0a8"}.fa-arrow-circle-right:before{content:"\f0a9"}.fa-arrow-circle-up:before{content:"\f0aa"}.fa-arrow-circle-down:before{content:"\f0ab"}.fa-globe:before{content:"\f0ac"}.fa-wrench:before{content:"\f0ad"}.fa-tasks:before{content:"\f0ae"}.fa-filter:before{content:"\f0b0"}.fa-briefcase:before{content:"\f0b1"}.fa-arrows-alt:before{content:"\f0b2"}.fa-group:before,.fa-users:before{content:"\f0c0"}.fa-chain:before,.fa-link:before{content:"\f0c1"}.fa-cloud:before{content:"\f0c2"}.fa-flask:before{content:"\f0c3"}.fa-cut:before,.fa-scissors:before{content:"\f0c4"}.fa-copy:before,.fa-files-o:before{content:"\f0c5"}.fa-paperclip:before{content:"\f0c6"}.fa-save:before,.fa-floppy-o:before{content:"\f0c7"}.fa-square:before{content:"\f0c8"}.fa-navicon:before,.fa-reorder:before,.fa-bars:before{content:"\f0c9"}.fa-list-ul:before{content:"\f0ca"}.fa-list-ol:before{content:"\f0cb"}.fa-strikethrough:before{content:"\f0cc"}.fa-underline:before{content:"\f0cd"}.fa-table:before{content:"\f0ce"}.fa-magic:before{content:"\f0d0"}.fa-truck:before{content:"\f0d1"}.fa-pinterest:before{content:"\f0d2"}.fa-pinterest-square:before{content:"\f0d3"}.fa-google-plus-square:before{content:"\f0d4"}.fa-google-plus:before{content:"\f0d5"}.fa-money:before{content:"\f0d6"}.fa-caret-down:before{content:"\f0d7"}.fa-caret-up:before{content:"\f0d8"}.fa-caret-left:before{content:"\f0d9"}.fa-caret-right:before{content:"\f0da"}.fa-columns:before{content:"\f0db"}.fa-unsorted:before,.fa-sort:before{content:"\f0dc"}.fa-sort-down:before,.fa-sort-desc:before{content:"\f0dd"}.fa-sort-up:before,.fa-sort-asc:before{content:"\f0de"}.fa-envelope:before{content:"\f0e0"}.fa-linkedin:before{content:"\f0e1"}.fa-rotate-left:before,.fa-undo:before{content:"\f0e2"}.fa-legal:before,.fa-gavel:before{content:"\f0e3"}.fa-dashboard:before,.fa-tachometer:before{content:"\f0e4"}.fa-comment-o:before{content:"\f0e5"}.fa-comments-o:before{content:"\f0e6"}.fa-flash:before,.fa-bolt:before{content:"\f0e7"}.fa-sitemap:before{content:"\f0e8"}.fa-umbrella:before{content:"\f0e9"}.fa-paste:before,.fa-clipboard:before{content:"\f0ea"}.fa-lightbulb-o:before{content:"\f0eb"}.fa-exchange:before{content:"\f0ec"}.fa-cloud-download:before{content:"\f0ed"}.fa-cloud-upload:before{content:"\f0ee"}.fa-user-md:before{content:"\f0f0"}.fa-stethoscope:before{content:"\f0f1"}.fa-suitcase:before{content:"\f0f2"}.fa-bell-o:before{content:"\f0a2"}.fa-coffee:before{content:"\f0f4"}.fa-cutlery:before{content:"\f0f5"}.fa-file-text-o:before{content:"\f0f6"}.fa-building-o:before{content:"\f0f7"}.fa-hospital-o:before{content:"\f0f8"}.fa-ambulance:before{content:"\f0f9"}.fa-medkit:before{content:"\f0fa"}.fa-fighter-jet:before{content:"\f0fb"}.fa-beer:before{content:"\f0fc"}.fa-h-square:before{content:"\f0fd"}.fa-plus-square:before{content:"\f0fe"}.fa-angle-double-left:before{content:"\f100"}.fa-angle-double-right:before{content:"\f101"}.fa-angle-double-up:before{content:"\f102"}.fa-angle-double-down:before{content:"\f103"}.fa-angle-left:before{content:"\f104"}.fa-angle-right:before{content:"\f105"}.fa-angle-up:before{content:"\f106"}.fa-angle-down:before{content:"\f107"}.fa-desktop:before{content:"\f108"}.fa-laptop:before{content:"\f109"}.fa-tablet:before{content:"\f10a"}.fa-mobile-phone:before,.fa-mobile:before{content:"\f10b"}.fa-circle-o:before{content:"\f10c"}.fa-quote-left:before{content:"\f10d"}.fa-quote-right:before{content:"\f10e"}.fa-spinner:before{content:"\f110"}.fa-circle:before{content:"\f111"}.fa-mail-reply:before,.fa-reply:before{content:"\f112"}.fa-github-alt:before{content:"\f113"}.fa-folder-o:before{content:"\f114"}.fa-folder-open-o:before{content:"\f115"}.fa-smile-o:before{content:"\f118"}.fa-frown-o:before{content:"\f119"}.fa-meh-o:before{content:"\f11a"}.fa-gamepad:before{content:"\f11b"}.fa-keyboard-o:before{content:"\f11c"}.fa-flag-o:before{content:"\f11d"}.fa-flag-checkered:before{content:"\f11e"}.fa-terminal:before{content:"\f120"}.fa-code:before{content:"\f121"}.fa-mail-reply-all:before,.fa-reply-all:before{content:"\f122"}.fa-star-half-empty:before,.fa-star-half-full:before,.fa-star-half-o:before{content:"\f123"}.fa-location-arrow:before{content:"\f124"}.fa-crop:before{content:"\f125"}.fa-code-fork:before{content:"\f126"}.fa-unlink:before,.fa-chain-broken:before{content:"\f127"}.fa-question:before{content:"\f128"}.fa-info:before{content:"\f129"}.fa-exclamation:before{content:"\f12a"}.fa-superscript:before{content:"\f12b"}.fa-subscript:before{content:"\f12c"}.fa-eraser:before{content:"\f12d"}.fa-puzzle-piece:before{content:"\f12e"}.fa-microphone:before{content:"\f130"}.fa-microphone-slash:before{content:"\f131"}.fa-shield:before{content:"\f132"}.fa-calendar-o:before{content:"\f133"}.fa-fire-extinguisher:before{content:"\f134"}.fa-rocket:before{content:"\f135"}.fa-maxcdn:before{content:"\f136"}.fa-chevron-circle-left:before{content:"\f137"}.fa-chevron-circle-right:before{content:"\f138"}.fa-chevron-circle-up:before{content:"\f139"}.fa-chevron-circle-down:before{content:"\f13a"}.fa-html5:before{content:"\f13b"}.fa-css3:before{content:"\f13c"}.fa-anchor:before{content:"\f13d"}.fa-unlock-alt:before{content:"\f13e"}.fa-bullseye:before{content:"\f140"}.fa-ellipsis-h:before{content:"\f141"}.fa-ellipsis-v:before{content:"\f142"}.fa-rss-square:before{content:"\f143"}.fa-play-circle:before{content:"\f144"}.fa-ticket:before{content:"\f145"}.fa-minus-square:before{content:"\f146"}.fa-minus-square-o:before{content:"\f147"}.fa-level-up:before{content:"\f148"}.fa-level-down:before{content:"\f149"}.fa-check-square:before{content:"\f14a"}.fa-pencil-square:before{content:"\f14b"}.fa-external-link-square:before{content:"\f14c"}.fa-share-square:before{content:"\f14d"}.fa-compass:before{content:"\f14e"}.fa-toggle-down:before,.fa-caret-square-o-down:before{content:"\f150"}.fa-toggle-up:before,.fa-caret-square-o-up:before{content:"\f151"}.fa-toggle-right:before,.fa-caret-square-o-right:before{content:"\f152"}.fa-euro:before,.fa-eur:before{content:"\f153"}.fa-gbp:before{content:"\f154"}.fa-dollar:before,.fa-usd:before{content:"\f155"}.fa-rupee:before,.fa-inr:before{content:"\f156"}.fa-cny:before,.fa-rmb:before,.fa-yen:before,.fa-jpy:before{content:"\f157"}.fa-ruble:before,.fa-rouble:before,.fa-rub:before{content:"\f158"}.fa-won:before,.fa-krw:before{content:"\f159"}.fa-bitcoin:before,.fa-btc:before{content:"\f15a"}.fa-file:before{content:"\f15b"}.fa-file-text:before{content:"\f15c"}.fa-sort-alpha-asc:before{content:"\f15d"}.fa-sort-alpha-desc:before{content:"\f15e"}.fa-sort-amount-asc:before{content:"\f160"}.fa-sort-amount-desc:before{content:"\f161"}.fa-sort-numeric-asc:before{content:"\f162"}.fa-sort-numeric-desc:before{content:"\f163"}.fa-thumbs-up:before{content:"\f164"}.fa-thumbs-down:before{content:"\f165"}.fa-youtube-square:before{content:"\f166"}.fa-youtube:before{content:"\f167"}.fa-xing:before{content:"\f168"}.fa-xing-square:before{content:"\f169"}.fa-youtube-play:before{content:"\f16a"}.fa-dropbox:before{content:"\f16b"}.fa-stack-overflow:before{content:"\f16c"}.fa-instagram:before{content:"\f16d"}.fa-flickr:before{content:"\f16e"}.fa-adn:before{content:"\f170"}.fa-bitbucket:before{content:"\f171"}.fa-bitbucket-square:before{content:"\f172"}.fa-tumblr:before{content:"\f173"}.fa-tumblr-square:before{content:"\f174"}.fa-long-arrow-down:before{content:"\f175"}.fa-long-arrow-up:before{content:"\f176"}.fa-long-arrow-left:before{content:"\f177"}.fa-long-arrow-right:before{content:"\f178"}.fa-apple:before{content:"\f179"}.fa-windows:before{content:"\f17a"}.fa-android:before{content:"\f17b"}.fa-linux:before{content:"\f17c"}.fa-dribbble:before{content:"\f17d"}.fa-skype:before{content:"\f17e"}.fa-foursquare:before{content:"\f180"}.fa-trello:before{content:"\f181"}.fa-female:before{content:"\f182"}.fa-male:before{content:"\f183"}.fa-gittip:before{content:"\f184"}.fa-sun-o:before{content:"\f185"}.fa-moon-o:before{content:"\f186"}.fa-archive:before{content:"\f187"}.fa-bug:before{content:"\f188"}.fa-vk:before{content:"\f189"}.fa-weibo:before{content:"\f18a"}.fa-renren:before{content:"\f18b"}.fa-pagelines:before{content:"\f18c"}.fa-stack-exchange:before{content:"\f18d"}.fa-arrow-circle-o-right:before{content:"\f18e"}.fa-arrow-circle-o-left:before{content:"\f190"}.fa-toggle-left:before,.fa-caret-square-o-left:before{content:"\f191"}.fa-dot-circle-o:before{content:"\f192"}.fa-wheelchair:before{content:"\f193"}.fa-vimeo-square:before{content:"\f194"}.fa-turkish-lira:before,.fa-try:before{content:"\f195"}.fa-plus-square-o:before{content:"\f196"}.fa-space-shuttle:before{content:"\f197"}.fa-slack:before{content:"\f198"}.fa-envelope-square:before{content:"\f199"}.fa-wordpress:before{content:"\f19a"}.fa-openid:before{content:"\f19b"}.fa-institution:before,.fa-bank:before,.fa-university:before{content:"\f19c"}.fa-mortar-board:before,.fa-graduation-cap:before{content:"\f19d"}.fa-yahoo:before{content:"\f19e"}.fa-google:before{content:"\f1a0"}.fa-reddit:before{content:"\f1a1"}.fa-reddit-square:before{content:"\f1a2"}.fa-stumbleupon-circle:before{content:"\f1a3"}.fa-stumbleupon:before{content:"\f1a4"}.fa-delicious:before{content:"\f1a5"}.fa-digg:before{content:"\f1a6"}.fa-pied-piper:before{content:"\f1a7"}.fa-pied-piper-alt:before{content:"\f1a8"}.fa-drupal:before{content:"\f1a9"}.fa-joomla:before{content:"\f1aa"}.fa-language:before{content:"\f1ab"}.fa-fax:before{content:"\f1ac"}.fa-building:before{content:"\f1ad"}.fa-child:before{content:"\f1ae"}.fa-paw:before{content:"\f1b0"}.fa-spoon:before{content:"\f1b1"}.fa-cube:before{content:"\f1b2"}.fa-cubes:before{content:"\f1b3"}.fa-behance:before{content:"\f1b4"}.fa-behance-square:before{content:"\f1b5"}.fa-steam:before{content:"\f1b6"}.fa-steam-square:before{content:"\f1b7"}.fa-recycle:before{content:"\f1b8"}.fa-automobile:before,.fa-car:before{content:"\f1b9"}.fa-cab:before,.fa-taxi:before{content:"\f1ba"}.fa-tree:before{content:"\f1bb"}.fa-spotify:before{content:"\f1bc"}.fa-deviantart:before{content:"\f1bd"}.fa-soundcloud:before{content:"\f1be"}.fa-database:before{content:"\f1c0"}.fa-file-pdf-o:before{content:"\f1c1"}.fa-file-word-o:before{content:"\f1c2"}.fa-file-excel-o:before{content:"\f1c3"}.fa-file-powerpoint-o:before{content:"\f1c4"}.fa-file-photo-o:before,.fa-file-picture-o:before,.fa-file-image-o:before{content:"\f1c5"}.fa-file-zip-o:before,.fa-file-archive-o:before{content:"\f1c6"}.fa-file-sound-o:before,.fa-file-audio-o:before{content:"\f1c7"}.fa-file-movie-o:before,.fa-file-video-o:before{content:"\f1c8"}.fa-file-code-o:before{content:"\f1c9"}.fa-vine:before{content:"\f1ca"}.fa-codepen:before{content:"\f1cb"}.fa-jsfiddle:before{content:"\f1cc"}.fa-life-bouy:before,.fa-life-buoy:before,.fa-life-saver:before,.fa-support:before,.fa-life-ring:before{content:"\f1cd"}.fa-circle-o-notch:before{content:"\f1ce"}.fa-ra:before,.fa-rebel:before{content:"\f1d0"}.fa-ge:before,.fa-empire:before{content:"\f1d1"}.fa-git-square:before{content:"\f1d2"}.fa-git:before{content:"\f1d3"}.fa-hacker-news:before{content:"\f1d4"}.fa-tencent-weibo:before{content:"\f1d5"}.fa-qq:before{content:"\f1d6"}.fa-wechat:before,.fa-weixin:before{content:"\f1d7"}.fa-send:before,.fa-paper-plane:before{content:"\f1d8"}.fa-send-o:before,.fa-paper-plane-o:before{content:"\f1d9"}.fa-history:before{content:"\f1da"}.fa-circle-thin:before{content:"\f1db"}.fa-header:before{content:"\f1dc"}.fa-paragraph:before{content:"\f1dd"}.fa-sliders:before{content:"\f1de"}.fa-share-alt:before{content:"\f1e0"}.fa-share-alt-square:before{content:"\f1e1"}.fa-bomb:before{content:"\f1e2"}.fa-soccer-ball-o:before,.fa-futbol-o:before{content:"\f1e3"}.fa-tty:before{content:"\f1e4"}.fa-binoculars:before{content:"\f1e5"}.fa-plug:before{content:"\f1e6"}.fa-slideshare:before{content:"\f1e7"}.fa-twitch:before{content:"\f1e8"}.fa-yelp:before{content:"\f1e9"}.fa-newspaper-o:before{content:"\f1ea"}.fa-wifi:before{content:"\f1eb"}.fa-calculator:before{content:"\f1ec"}.fa-paypal:before{content:"\f1ed"}.fa-google-wallet:before{content:"\f1ee"}.fa-cc-visa:before{content:"\f1f0"}.fa-cc-mastercard:before{content:"\f1f1"}.fa-cc-discover:before{content:"\f1f2"}.fa-cc-amex:before{content:"\f1f3"}.fa-cc-paypal:before{content:"\f1f4"}.fa-cc-stripe:before{content:"\f1f5"}.fa-bell-slash:before{content:"\f1f6"}.fa-bell-slash-o:before{content:"\f1f7"}.fa-trash:before{content:"\f1f8"}.fa-copyright:before{content:"\f1f9"}.fa-at:before{content:"\f1fa"}.fa-eyedropper:before{content:"\f1fb"}.fa-paint-brush:before{content:"\f1fc"}.fa-birthday-cake:before{content:"\f1fd"}.fa-area-chart:before{content:"\f1fe"}.fa-pie-chart:before{content:"\f200"}.fa-line-chart:before{content:"\f201"}.fa-lastfm:before{content:"\f202"}.fa-lastfm-square:before{content:"\f203"}.fa-toggle-off:before{content:"\f204"}.fa-toggle-on:before{content:"\f205"}.fa-bicycle:before{content:"\f206"}.fa-bus:before{content:"\f207"}.fa-ioxhost:before{content:"\f208"}.fa-angellist:before{content:"\f209"}.fa-cc:before{content:"\f20a"}.fa-shekel:before,.fa-sheqel:before,.fa-ils:before{content:"\f20b"}.fa-meanpath:before{content:"\f20c"} \ No newline at end of file diff --git a/css/fonts/FontAwesome.otf b/css/fonts/FontAwesome.otf new file mode 100644 index 0000000000..f7936cc1e7 Binary files /dev/null and b/css/fonts/FontAwesome.otf differ diff --git a/css/fonts/fontawesome-webfont.eot b/css/fonts/fontawesome-webfont.eot new file mode 100644 index 0000000000..33b2bb8005 Binary files /dev/null and b/css/fonts/fontawesome-webfont.eot differ diff --git a/css/fonts/fontawesome-webfont.svg b/css/fonts/fontawesome-webfont.svg new file mode 100644 index 0000000000..1ee89d4368 --- /dev/null +++ b/css/fonts/fontawesome-webfont.svg @@ -0,0 +1,565 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/css/fonts/fontawesome-webfont.ttf b/css/fonts/fontawesome-webfont.ttf new file mode 100644 index 0000000000..ed9372f8ea Binary files /dev/null and b/css/fonts/fontawesome-webfont.ttf differ diff --git a/css/fonts/fontawesome-webfont.woff b/css/fonts/fontawesome-webfont.woff new file mode 100644 index 0000000000..8b280b98fa Binary files /dev/null and b/css/fonts/fontawesome-webfont.woff differ diff --git a/css/fonts/fontawesome-webfont.woff2 b/css/fonts/fontawesome-webfont.woff2 new file mode 100644 index 0000000000..3311d58514 Binary files /dev/null and b/css/fonts/fontawesome-webfont.woff2 differ diff --git a/css/lavish-bootstrap.css b/css/lavish-bootstrap.css new file mode 100644 index 0000000000..c2af93e598 --- /dev/null +++ b/css/lavish-bootstrap.css @@ -0,0 +1,5898 @@ +/* CSS generated by http://lavishbootstrap.com */ +/*! normalize.css v2.1.0 | MIT License | git.io/normalize */ +article, +aside, +details, +figcaption, +figure, +footer, +header, +hgroup, +main, +nav, +section, +summary { + display: block; +} +audio, +canvas, +video { + display: inline-block; +} +audio:not([controls]) { + display: none; + height: 0; +} +[hidden] { + display: none; +} +html { + font-family: sans-serif; + -webkit-text-size-adjust: 100%; + -ms-text-size-adjust: 100%; +} +body { + margin: 0; +} +a:focus { + outline: thin dotted; +} +a:active, +a:hover { + outline: 0; +} +h1 { + font-size: 2em; + margin: 0.67em 0; +} +abbr[title] { + border-bottom: 1px dotted; +} +b, +strong { + font-weight: bold; +} +dfn { + font-style: italic; +} +hr { + -moz-box-sizing: content-box; + box-sizing: content-box; + height: 0; +} +mark { + background: #ff0; + color: #000; +} +code, +kbd, +pre, +samp { + font-family: monospace, serif; + font-size: 1em; +} +pre { + white-space: pre-wrap; +} +q { + quotes: "\201C" "\201D" "\2018" "\2019"; +} +small { + font-size: 80%; +} +sub, +sup { + font-size: 75%; + line-height: 0; + position: relative; + vertical-align: baseline; +} +sup { + top: -0.5em; +} +sub { + bottom: -0.25em; +} +img { + border: 0; +} +svg:not(:root) { + overflow: hidden; +} +figure { + margin: 0; +} +fieldset { + border: 1px solid #c0c0c0; + margin: 0 2px; + padding: 0.35em 0.625em 0.75em; +} +legend { + border: 0; + padding: 0; +} +button, +input, +select, +textarea { + font-family: inherit; + font-size: 100%; + margin: 0; +} +button, +input { + line-height: normal; +} +button, +select { + text-transform: none; +} +button, +html input[type="button"], +input[type="reset"], +input[type="submit"] { + -webkit-appearance: button; + cursor: pointer; +} +button[disabled], +html input[disabled] { + cursor: default; +} +input[type="checkbox"], +input[type="radio"] { + box-sizing: border-box; + padding: 0; +} +input[type="search"] { + -webkit-appearance: textfield; + -moz-box-sizing: content-box; + -webkit-box-sizing: content-box; + box-sizing: content-box; +} +input[type="search"]::-webkit-search-cancel-button, +input[type="search"]::-webkit-search-decoration { + -webkit-appearance: none; +} +button::-moz-focus-inner, +input::-moz-focus-inner { + border: 0; + padding: 0; +} +textarea { + overflow: auto; + vertical-align: top; +} +table { + border-collapse: collapse; + border-spacing: 0; +} +@media print { + * { + text-shadow: none !important; + color: #000 !important; + background: transparent !important; + box-shadow: none !important; + } + a, + a:visited { + text-decoration: underline; + } + a[href]:after { + content: " (" attr(href) ")"; + } + abbr[title]:after { + content: " (" attr(title) ")"; + } + .ir a:after, + a[href^="javascript:"]:after, + a[href^="#"]:after { + content: ""; + } + pre, + blockquote { + border: 1px solid #999; + page-break-inside: avoid; + } + thead { + display: table-header-group; + } + tr, + img { + page-break-inside: avoid; + } + img { + max-width: 100% !important; + } + @page { + margin: 2cm .5cm; + } + p, + h2, + h3 { + orphans: 3; + widows: 3; + } + h2, + h3 { + page-break-after: avoid; + } + .navbar { + display: none; + } + .table td, + .table th { + background-color: #fff !important; + } + .btn > .caret, + .dropup > .btn > .caret { + border-top-color: #000 !important; + } + .label { + border: 1px solid #000; + } + .table { + border-collapse: collapse !important; + } + .table-bordered th, + .table-bordered td { + border: 1px solid #ddd !important; + } +} +*, +*:before, +*:after { + -webkit-box-sizing: border-box; + -moz-box-sizing: border-box; + box-sizing: border-box; +} +html { + font-size: 62.5%; + -webkit-tap-highlight-color: rgba(0, 0, 0, 0); +} +body { + font-family: "Helvetica Neue", Helvetica, Arial, sans-serif; + font-size: 14px; + line-height: 1.428571429; + /*color: #77777a; */ + background-color: #ffffff; +} +input, +button, +select, +textarea { + font-family: inherit; + font-size: inherit; + line-height: inherit; +} +button, +input, +select[multiple], +textarea { + background-image: none; +} +a { + color: #248EC2; + text-decoration: none; +} +a:hover, +a:focus { + text-decoration: underline; +} +a:focus { + outline: thin dotted #333; + outline: 5px auto -webkit-focus-ring-color; + outline-offset: -2px; +} +img { + vertical-align: middle; +} +.img-responsive { + display: block; + max-width: 100%; + height: auto; +} +.img-rounded { + border-radius: 6px; +} +.img-thumbnail { + padding: 4px; + line-height: 1.428571429; + background-color: #ffffff; + border: 1px solid #dddddd; + border-radius: 4px; + -webkit-transition: all 0.2s ease-in-out; + transition: all 0.2s ease-in-out; + display: inline-block; + max-width: 100%; + height: auto; +} +.img-circle { + border-radius: 50%; +} +hr { + margin-top: 20px; + margin-bottom: 20px; + border: 0; + border-top: 1px solid #bac9c2; +} +.sr-only { + position: absolute; + width: 1px; + height: 1px; + margin: -1px; + padding: 0; + overflow: hidden; + clip: rect(0 0 0 0); + border: 0; +} +p { + margin: 0 0 10px; +} +.lead { + margin-bottom: 20px; + font-size: 16.099999999999998px; + font-weight: 200; + line-height: 1.4; +} +@media (min-width: 768px) { + .lead { + font-size: 21px; + } +} +small { + font-size: 85%; +} +cite { + font-style: normal; +} +.text-muted { + color: #f9faf9; +} +.text-primary { + color: #74ab50; +} +.text-warning { + color: #c09853; +} +.text-danger { + color: #b94a48; +} +.text-success { + color: #468847; +} +.text-info { + color: #3a87ad; +} +.text-left { + text-align: left; +} +.text-right { + text-align: right; +} +.text-center { + text-align: center; +} +h1, +h2, +h3, +h4, +h5, +h6, +.h1, +.h2, +.h3, +.h4, +.h5, +.h6 { + font-family: "Helvetica Neue", Helvetica, Arial, sans-serif; + font-weight: 500; + line-height: 1.1; +} +h1 small, +h2 small, +h3 small, +h4 small, +h5 small, +h6 small, +.h1 small, +.h2 small, +.h3 small, +.h4 small, +.h5 small, +.h6 small { + font-weight: normal; + line-height: 1; + color: #f9faf9; +} +h1, +h2, +h3 { + margin-top: 20px; + margin-bottom: 10px; +} +h4, +h5, +h6 { + margin-top: 10px; + margin-bottom: 10px; +} +h1, +.h1 { + font-size: 36px; +} +h2, +.h2 { + font-size: 30px; +} +h3, +.h3 { + font-size: 24px; +} +h4, +.h4 { + font-size: 18px; +} +h5, +.h5 { + font-size: 14px; +} +h6, +.h6 { + font-size: 12px; +} +h1 small, +.h1 small { + font-size: 24px; +} +h2 small, +.h2 small { + font-size: 18px; +} +h3 small, +.h3 small, +h4 small, +.h4 small { + font-size: 14px; +} +.page-header { + padding-bottom: 9px; + margin: 40px 0 20px; + border-bottom: 1px solid #bac9c2; +} +ul, +ol { + margin-top: 0; + margin-bottom: 10px; +} +ul ul, +ol ul, +ul ol, +ol ol { + margin-bottom: 0; +} +.list-unstyled { + padding-left: 0; + list-style: none; +} +.list-inline { + padding-left: 0; + list-style: none; +} +.list-inline > li { + display: inline-block; + padding-left: 5px; + padding-right: 5px; +} +dl { + margin-bottom: 20px; +} +dt, +dd { + line-height: 1.428571429; +} +dt { + font-weight: bold; +} +dd { + margin-left: 0; +} +@media (min-width: 768px) { + .dl-horizontal dt { + float: left; + width: 160px; + clear: left; + text-align: right; + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; + } + .dl-horizontal dd { + margin-left: 180px; + } + .dl-horizontal dd:before, + .dl-horizontal dd:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + + } + .dl-horizontal dd:after { + clear: both; + } + .dl-horizontal dd:before, + .dl-horizontal dd:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + + } + .dl-horizontal dd:after { + clear: both; + } +} +abbr[title], +abbr[data-original-title] { + cursor: help; + border-bottom: 1px dotted #f9faf9; +} +abbr.initialism { + font-size: 90%; + text-transform: uppercase; +} +blockquote { + padding: 10px 20px; + margin: 0 0 20px; + border-left: 5px solid #bac9c2; +} +blockquote p { + font-size: 17.5px; + font-weight: 300; + line-height: 1.25; +} +blockquote p:last-child { + margin-bottom: 0; +} +blockquote small { + display: block; + line-height: 1.428571429; + color: #f9faf9; +} +blockquote small:before { + content: '\2014 \00A0'; +} +blockquote.pull-right { + padding-right: 15px; + padding-left: 0; + border-right: 5px solid #bac9c2; + border-left: 0; +} +blockquote.pull-right p, +blockquote.pull-right small { + text-align: right; +} +blockquote.pull-right small:before { + content: ''; +} +blockquote.pull-right small:after { + content: '\00A0 \2014'; +} +q:before, +q:after, +blockquote:before, +blockquote:after { + content: ""; +} +address { + display: block; + margin-bottom: 20px; + font-style: normal; + line-height: 1.428571429; +} +code, +pre { + font-family: Monaco, Menlo, Consolas, "Courier New", monospace; +} +code { + padding: 2px 4px; + font-size: 90%; + color: #444; + background-color: #f0f0f0; + white-space: nowrap; + border-radius: 4px; +} + +pre { + display: block; + padding: 9.5px; + margin: 0 0 10px; + font-size: 13px; + line-height: 1.428571429; + word-break: break-all; + word-wrap: break-word; + color: #77777a; + background-color: #f5f5f5; + border: 1px solid #cccccc; + border-radius: 4px; +} +pre.prettyprint { + margin-bottom: 20px; +} +pre code { + padding: 0; + font-size: inherit; + color: inherit; + white-space: pre-wrap; + background-color: transparent; + border: 0; +} +.pre-scrollable { + max-height: 340px; + overflow-y: scroll; +} +.container { + margin-right: auto; + margin-left: auto; + padding-left: 15px; + padding-right: 15px; +} +.container:before, +.container:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.container:after { + clear: both; +} +.container:before, +.container:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.container:after { + clear: both; +} +.row { + margin-left: -15px; + margin-right: -15px; +} +.row:before, +.row:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.row:after { + clear: both; +} +.row:before, +.row:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.row:after { + clear: both; +} +.col-xs-1, +.col-xs-2, +.col-xs-3, +.col-xs-4, +.col-xs-5, +.col-xs-6, +.col-xs-7, +.col-xs-8, +.col-xs-9, +.col-xs-10, +.col-xs-11, +.col-xs-12, +.col-sm-1, +.col-sm-2, +.col-sm-3, +.col-sm-4, +.col-sm-5, +.col-sm-6, +.col-sm-7, +.col-sm-8, +.col-sm-9, +.col-sm-10, +.col-sm-11, +.col-sm-12, +.col-md-1, +.col-md-2, +.col-md-3, +.col-md-4, +.col-md-5, +.col-md-6, +.col-md-7, +.col-md-8, +.col-md-9, +.col-md-10, +.col-md-11, +.col-md-12, +.col-lg-1, +.col-lg-2, +.col-lg-3, +.col-lg-4, +.col-lg-5, +.col-lg-6, +.col-lg-7, +.col-lg-8, +.col-lg-9, +.col-lg-10, +.col-lg-11, +.col-lg-12 { + position: relative; + min-height: 1px; + padding-left: 15px; + padding-right: 15px; +} +.col-xs-1, +.col-xs-2, +.col-xs-3, +.col-xs-4, +.col-xs-5, +.col-xs-6, +.col-xs-7, +.col-xs-8, +.col-xs-9, +.col-xs-10, +.col-xs-11 { + float: left; +} +.col-xs-1 { + width: 8.333333333333332%; +} +.col-xs-2 { + width: 16.666666666666664%; +} +.col-xs-3 { + width: 25%; +} +.col-xs-4 { + width: 33.33333333333333%; +} +.col-xs-5 { + width: 41.66666666666667%; +} +.col-xs-6 { + width: 50%; +} +.col-xs-7 { + width: 58.333333333333336%; +} +.col-xs-8 { + width: 66.66666666666666%; +} +.col-xs-9 { + width: 75%; +} +.col-xs-10 { + width: 83.33333333333334%; +} +.col-xs-11 { + width: 91.66666666666666%; +} +.col-xs-12 { + width: 100%; +} +@media (min-width: 768px) { + .container { + max-width: 750px; + } + .col-sm-1, + .col-sm-2, + .col-sm-3, + .col-sm-4, + .col-sm-5, + .col-sm-6, + .col-sm-7, + .col-sm-8, + .col-sm-9, + .col-sm-10, + .col-sm-11 { + float: left; + } + .col-sm-1 { + width: 8.333333333333332%; + } + .col-sm-2 { + width: 16.666666666666664%; + } + .col-sm-3 { + width: 25%; + } + .col-sm-4 { + width: 33.33333333333333%; + } + .col-sm-5 { + width: 41.66666666666667%; + } + .col-sm-6 { + width: 50%; + } + .col-sm-7 { + width: 58.333333333333336%; + } + .col-sm-8 { + width: 66.66666666666666%; + } + .col-sm-9 { + width: 75%; + } + .col-sm-10 { + width: 83.33333333333334%; + } + .col-sm-11 { + width: 91.66666666666666%; + } + .col-sm-12 { + width: 100%; + } + .col-sm-push-1 { + left: 8.333333333333332%; + } + .col-sm-push-2 { + left: 16.666666666666664%; + } + .col-sm-push-3 { + left: 25%; + } + .col-sm-push-4 { + left: 33.33333333333333%; + } + .col-sm-push-5 { + left: 41.66666666666667%; + } + .col-sm-push-6 { + left: 50%; + } + .col-sm-push-7 { + left: 58.333333333333336%; + } + .col-sm-push-8 { + left: 66.66666666666666%; + } + .col-sm-push-9 { + left: 75%; + } + .col-sm-push-10 { + left: 83.33333333333334%; + } + .col-sm-push-11 { + left: 91.66666666666666%; + } + .col-sm-pull-1 { + right: 8.333333333333332%; + } + .col-sm-pull-2 { + right: 16.666666666666664%; + } + .col-sm-pull-3 { + right: 25%; + } + .col-sm-pull-4 { + right: 33.33333333333333%; + } + .col-sm-pull-5 { + right: 41.66666666666667%; + } + .col-sm-pull-6 { + right: 50%; + } + .col-sm-pull-7 { + right: 58.333333333333336%; + } + .col-sm-pull-8 { + right: 66.66666666666666%; + } + .col-sm-pull-9 { + right: 75%; + } + .col-sm-pull-10 { + right: 83.33333333333334%; + } + .col-sm-pull-11 { + right: 91.66666666666666%; + } + .col-sm-offset-1 { + margin-left: 8.333333333333332%; + } + .col-sm-offset-2 { + margin-left: 16.666666666666664%; + } + .col-sm-offset-3 { + margin-left: 25%; + } + .col-sm-offset-4 { + margin-left: 33.33333333333333%; + } + .col-sm-offset-5 { + margin-left: 41.66666666666667%; + } + .col-sm-offset-6 { + margin-left: 50%; + } + .col-sm-offset-7 { + margin-left: 58.333333333333336%; + } + .col-sm-offset-8 { + margin-left: 66.66666666666666%; + } + .col-sm-offset-9 { + margin-left: 75%; + } + .col-sm-offset-10 { + margin-left: 83.33333333333334%; + } + .col-sm-offset-11 { + margin-left: 91.66666666666666%; + } +} +@media (min-width: 992px) { + .container { + max-width: 970px; + } + .col-md-1, + .col-md-2, + .col-md-3, + .col-md-4, + .col-md-5, + .col-md-6, + .col-md-7, + .col-md-8, + .col-md-9, + .col-md-10, + .col-md-11 { + float: left; + } + .col-md-1 { + width: 8.333333333333332%; + } + .col-md-2 { + width: 16.666666666666664%; + } + .col-md-3 { + width: 25%; + } + .col-md-4 { + width: 33.33333333333333%; + } + .col-md-5 { + width: 41.66666666666667%; + } + .col-md-6 { + width: 50%; + } + .col-md-7 { + width: 58.333333333333336%; + } + .col-md-8 { + width: 66.66666666666666%; + } + .col-md-9 { + width: 75%; + } + .col-md-10 { + width: 83.33333333333334%; + } + .col-md-11 { + width: 91.66666666666666%; + } + .col-md-12 { + width: 100%; + } + .col-md-push-0 { + left: auto; + } + .col-md-push-1 { + left: 8.333333333333332%; + } + .col-md-push-2 { + left: 16.666666666666664%; + } + .col-md-push-3 { + left: 25%; + } + .col-md-push-4 { + left: 33.33333333333333%; + } + .col-md-push-5 { + left: 41.66666666666667%; + } + .col-md-push-6 { + left: 50%; + } + .col-md-push-7 { + left: 58.333333333333336%; + } + .col-md-push-8 { + left: 66.66666666666666%; + } + .col-md-push-9 { + left: 75%; + } + .col-md-push-10 { + left: 83.33333333333334%; + } + .col-md-push-11 { + left: 91.66666666666666%; + } + .col-md-pull-0 { + right: auto; + } + .col-md-pull-1 { + right: 8.333333333333332%; + } + .col-md-pull-2 { + right: 16.666666666666664%; + } + .col-md-pull-3 { + right: 25%; + } + .col-md-pull-4 { + right: 33.33333333333333%; + } + .col-md-pull-5 { + right: 41.66666666666667%; + } + .col-md-pull-6 { + right: 50%; + } + .col-md-pull-7 { + right: 58.333333333333336%; + } + .col-md-pull-8 { + right: 66.66666666666666%; + } + .col-md-pull-9 { + right: 75%; + } + .col-md-pull-10 { + right: 83.33333333333334%; + } + .col-md-pull-11 { + right: 91.66666666666666%; + } + .col-md-offset-0 { + margin-left: 0; + } + .col-md-offset-1 { + margin-left: 8.333333333333332%; + } + .col-md-offset-2 { + margin-left: 16.666666666666664%; + } + .col-md-offset-3 { + margin-left: 25%; + } + .col-md-offset-4 { + margin-left: 33.33333333333333%; + } + .col-md-offset-5 { + margin-left: 41.66666666666667%; + } + .col-md-offset-6 { + margin-left: 50%; + } + .col-md-offset-7 { + margin-left: 58.333333333333336%; + } + .col-md-offset-8 { + margin-left: 66.66666666666666%; + } + .col-md-offset-9 { + margin-left: 75%; + } + .col-md-offset-10 { + margin-left: 83.33333333333334%; + } + .col-md-offset-11 { + margin-left: 91.66666666666666%; + } +} +@media (min-width: 1200px) { + .container { + max-width: 1170px; + } + .col-lg-1, + .col-lg-2, + .col-lg-3, + .col-lg-4, + .col-lg-5, + .col-lg-6, + .col-lg-7, + .col-lg-8, + .col-lg-9, + .col-lg-10, + .col-lg-11 { + float: left; + } + .col-lg-1 { + width: 8.333333333333332%; + } + .col-lg-2 { + width: 16.666666666666664%; + } + .col-lg-3 { + width: 25%; + } + .col-lg-4 { + width: 33.33333333333333%; + } + .col-lg-5 { + width: 41.66666666666667%; + } + .col-lg-6 { + width: 50%; + } + .col-lg-7 { + width: 58.333333333333336%; + } + .col-lg-8 { + width: 66.66666666666666%; + } + .col-lg-9 { + width: 75%; + } + .col-lg-10 { + width: 83.33333333333334%; + } + .col-lg-11 { + width: 91.66666666666666%; + } + .col-lg-12 { + width: 100%; + } + .col-lg-push-0 { + left: auto; + } + .col-lg-push-1 { + left: 8.333333333333332%; + } + .col-lg-push-2 { + left: 16.666666666666664%; + } + .col-lg-push-3 { + left: 25%; + } + .col-lg-push-4 { + left: 33.33333333333333%; + } + .col-lg-push-5 { + left: 41.66666666666667%; + } + .col-lg-push-6 { + left: 50%; + } + .col-lg-push-7 { + left: 58.333333333333336%; + } + .col-lg-push-8 { + left: 66.66666666666666%; + } + .col-lg-push-9 { + left: 75%; + } + .col-lg-push-10 { + left: 83.33333333333334%; + } + .col-lg-push-11 { + left: 91.66666666666666%; + } + .col-lg-pull-0 { + right: auto; + } + .col-lg-pull-1 { + right: 8.333333333333332%; + } + .col-lg-pull-2 { + right: 16.666666666666664%; + } + .col-lg-pull-3 { + right: 25%; + } + .col-lg-pull-4 { + right: 33.33333333333333%; + } + .col-lg-pull-5 { + right: 41.66666666666667%; + } + .col-lg-pull-6 { + right: 50%; + } + .col-lg-pull-7 { + right: 58.333333333333336%; + } + .col-lg-pull-8 { + right: 66.66666666666666%; + } + .col-lg-pull-9 { + right: 75%; + } + .col-lg-pull-10 { + right: 83.33333333333334%; + } + .col-lg-pull-11 { + right: 91.66666666666666%; + } + .col-lg-offset-0 { + margin-left: 0; + } + .col-lg-offset-1 { + margin-left: 8.333333333333332%; + } + .col-lg-offset-2 { + margin-left: 16.666666666666664%; + } + .col-lg-offset-3 { + margin-left: 25%; + } + .col-lg-offset-4 { + margin-left: 33.33333333333333%; + } + .col-lg-offset-5 { + margin-left: 41.66666666666667%; + } + .col-lg-offset-6 { + margin-left: 50%; + } + .col-lg-offset-7 { + margin-left: 58.333333333333336%; + } + .col-lg-offset-8 { + margin-left: 66.66666666666666%; + } + .col-lg-offset-9 { + margin-left: 75%; + } + .col-lg-offset-10 { + margin-left: 83.33333333333334%; + } + .col-lg-offset-11 { + margin-left: 91.66666666666666%; + } +} +table { + max-width: 100%; + background-color: transparent; +} +th { + text-align: left; +} +.table { + width: 100%; + margin-bottom: 20px; +} +.table thead > tr > th, +.table tbody > tr > th, +.table tfoot > tr > th, +.table thead > tr > td, +.table tbody > tr > td, +.table tfoot > tr > td { + padding: 8px; + line-height: 1.428571429; + vertical-align: top; + border-top: 1px solid #77777a; +} +.table thead > tr > th { + vertical-align: bottom; + border-bottom: 2px solid #77777a; +} +.table caption + thead tr:first-child th, +.table colgroup + thead tr:first-child th, +.table thead:first-child tr:first-child th, +.table caption + thead tr:first-child td, +.table colgroup + thead tr:first-child td, +.table thead:first-child tr:first-child td { + border-top: 0; +} +.table tbody + tbody { + border-top: 2px solid #77777a; +} +.table .table { + background-color: #ffffff; +} +.table-condensed thead > tr > th, +.table-condensed tbody > tr > th, +.table-condensed tfoot > tr > th, +.table-condensed thead > tr > td, +.table-condensed tbody > tr > td, +.table-condensed tfoot > tr > td { + padding: 5px; +} +.table-bordered { + border: 1px solid #77777a; +} +.table-bordered > thead > tr > th, +.table-bordered > tbody > tr > th, +.table-bordered > tfoot > tr > th, +.table-bordered > thead > tr > td, +.table-bordered > tbody > tr > td, +.table-bordered > tfoot > tr > td { + border: 1px solid #77777a; +} +.table-bordered > thead > tr > th, +.table-bordered > thead > tr > td { + border-bottom-width: 2px; +} +.table-striped > tbody > tr:nth-child(odd) > td, +.table-striped > tbody > tr:nth-child(odd) > th { + background-color: #f9f9f9; +} +.table-hover > tbody > tr:hover > td, +.table-hover > tbody > tr:hover > th { + background-color: #f5f5f5; +} +table col[class*="col-"] { + float: none; + display: table-column; +} +table td[class*="col-"], +table th[class*="col-"] { + float: none; + display: table-cell; +} +.table > thead > tr > td.active, +.table > tbody > tr > td.active, +.table > tfoot > tr > td.active, +.table > thead > tr > th.active, +.table > tbody > tr > th.active, +.table > tfoot > tr > th.active, +.table > thead > tr.active > td, +.table > tbody > tr.active > td, +.table > tfoot > tr.active > td, +.table > thead > tr.active > th, +.table > tbody > tr.active > th, +.table > tfoot > tr.active > th { + background-color: #f5f5f5; +} +.table > thead > tr > td.success, +.table > tbody > tr > td.success, +.table > tfoot > tr > td.success, +.table > thead > tr > th.success, +.table > tbody > tr > th.success, +.table > tfoot > tr > th.success, +.table > thead > tr.success > td, +.table > tbody > tr.success > td, +.table > tfoot > tr.success > td, +.table > thead > tr.success > th, +.table > tbody > tr.success > th, +.table > tfoot > tr.success > th { + background-color: #dff0d8; + border-color: #d6e9c6; +} +.table-hover > tbody > tr > td.success:hover, +.table-hover > tbody > tr > th.success:hover, +.table-hover > tbody > tr.success:hover > td { + background-color: #d0e9c6; + border-color: #c9e2b3; +} +.table > thead > tr > td.danger, +.table > tbody > tr > td.danger, +.table > tfoot > tr > td.danger, +.table > thead > tr > th.danger, +.table > tbody > tr > th.danger, +.table > tfoot > tr > th.danger, +.table > thead > tr.danger > td, +.table > tbody > tr.danger > td, +.table > tfoot > tr.danger > td, +.table > thead > tr.danger > th, +.table > tbody > tr.danger > th, +.table > tfoot > tr.danger > th { + background-color: #f2dede; + border-color: #eed3d7; +} +.table-hover > tbody > tr > td.danger:hover, +.table-hover > tbody > tr > th.danger:hover, +.table-hover > tbody > tr.danger:hover > td { + background-color: #ebcccc; + border-color: #e6c1c7; +} +.table > thead > tr > td.warning, +.table > tbody > tr > td.warning, +.table > tfoot > tr > td.warning, +.table > thead > tr > th.warning, +.table > tbody > tr > th.warning, +.table > tfoot > tr > th.warning, +.table > thead > tr.warning > td, +.table > tbody > tr.warning > td, +.table > tfoot > tr.warning > td, +.table > thead > tr.warning > th, +.table > tbody > tr.warning > th, +.table > tfoot > tr.warning > th { + background-color: #fcf8e3; + border-color: #fbeed5; +} +.table-hover > tbody > tr > td.warning:hover, +.table-hover > tbody > tr > th.warning:hover, +.table-hover > tbody > tr.warning:hover > td { + background-color: #faf2cc; + border-color: #f8e5be; +} +@media (max-width: 768px) { + .table-responsive { + width: 100%; + margin-bottom: 15px; + overflow-y: hidden; + overflow-x: scroll; + border: 1px solid #77777a; + } + .table-responsive > .table { + margin-bottom: 0; + background-color: #fff; + } + .table-responsive > .table > thead > tr > th, + .table-responsive > .table > tbody > tr > th, + .table-responsive > .table > tfoot > tr > th, + .table-responsive > .table > thead > tr > td, + .table-responsive > .table > tbody > tr > td, + .table-responsive > .table > tfoot > tr > td { + white-space: nowrap; + } + .table-responsive > .table-bordered { + border: 0; + } + .table-responsive > .table-bordered > thead > tr > th:first-child, + .table-responsive > .table-bordered > tbody > tr > th:first-child, + .table-responsive > .table-bordered > tfoot > tr > th:first-child, + .table-responsive > .table-bordered > thead > tr > td:first-child, + .table-responsive > .table-bordered > tbody > tr > td:first-child, + .table-responsive > .table-bordered > tfoot > tr > td:first-child { + border-left: 0; + } + .table-responsive > .table-bordered > thead > tr > th:last-child, + .table-responsive > .table-bordered > tbody > tr > th:last-child, + .table-responsive > .table-bordered > tfoot > tr > th:last-child, + .table-responsive > .table-bordered > thead > tr > td:last-child, + .table-responsive > .table-bordered > tbody > tr > td:last-child, + .table-responsive > .table-bordered > tfoot > tr > td:last-child { + border-right: 0; + } + .table-responsive > .table-bordered > thead > tr:last-child > th, + .table-responsive > .table-bordered > tbody > tr:last-child > th, + .table-responsive > .table-bordered > tfoot > tr:last-child > th, + .table-responsive > .table-bordered > thead > tr:last-child > td, + .table-responsive > .table-bordered > tbody > tr:last-child > td, + .table-responsive > .table-bordered > tfoot > tr:last-child > td { + border-bottom: 0; + } +} +fieldset { + padding: 0; + margin: 0; + border: 0; +} +legend { + display: block; + width: 100%; + padding: 0; + margin-bottom: 20px; + font-size: 21px; + line-height: inherit; + color: #77777a; + border: 0; + border-bottom: 1px solid #e5e5e5; +} +label { + display: inline-block; + margin-bottom: 5px; + font-weight: bold; +} +input[type="search"] { + -webkit-box-sizing: border-box; + -moz-box-sizing: border-box; + box-sizing: border-box; +} +input[type="radio"], +input[type="checkbox"] { + margin: 4px 0 0; + margin-top: 1px \9; + /* IE8-9 */ + + line-height: normal; +} +input[type="file"] { + display: block; +} +select[multiple], +select[size] { + height: auto; +} +select optgroup { + font-size: inherit; + font-style: inherit; + font-family: inherit; +} +input[type="file"]:focus, +input[type="radio"]:focus, +input[type="checkbox"]:focus { + outline: thin dotted #333; + outline: 5px auto -webkit-focus-ring-color; + outline-offset: -2px; +} +input[type="number"]::-webkit-outer-spin-button, +input[type="number"]::-webkit-inner-spin-button { + height: auto; +} +.form-control:-moz-placeholder { + color: #f9faf9; +} +.form-control::-moz-placeholder { + color: #f9faf9; +} +.form-control:-ms-input-placeholder { + color: #f9faf9; +} +.form-control::-webkit-input-placeholder { + color: #f9faf9; +} +.form-control { + display: block; + width: 100%; + height: 34px; + padding: 6px 12px; + font-size: 14px; + line-height: 1.428571429; + color: #4aadd6; + vertical-align: middle; + background-color: #ffffff; + border: 1px solid #cccccc; + border-radius: 4px; + -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075); + box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075); + -webkit-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s; + transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s; +} +.form-control:focus { + border-color: #66afe9; + outline: 0; + -webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6); + box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6); +} +.form-control[disabled], +.form-control[readonly], +fieldset[disabled] .form-control { + cursor: not-allowed; + background-color: #bac9c2; +} +textarea.form-control { + height: auto; +} +.form-group { + margin-bottom: 15px; +} +.radio, +.checkbox { + display: block; + min-height: 20px; + margin-top: 10px; + margin-bottom: 10px; + padding-left: 20px; + vertical-align: middle; +} +.radio label, +.checkbox label { + display: inline; + margin-bottom: 0; + font-weight: normal; + cursor: pointer; +} +.radio input[type="radio"], +.radio-inline input[type="radio"], +.checkbox input[type="checkbox"], +.checkbox-inline input[type="checkbox"] { + float: left; + margin-left: -20px; +} +.radio + .radio, +.checkbox + .checkbox { + margin-top: -5px; +} +.radio-inline, +.checkbox-inline { + display: inline-block; + padding-left: 20px; + margin-bottom: 0; + vertical-align: middle; + font-weight: normal; + cursor: pointer; +} +.radio-inline + .radio-inline, +.checkbox-inline + .checkbox-inline { + margin-top: 0; + margin-left: 10px; +} +input[type="radio"][disabled], +input[type="checkbox"][disabled], +.radio[disabled], +.radio-inline[disabled], +.checkbox[disabled], +.checkbox-inline[disabled], +fieldset[disabled] input[type="radio"], +fieldset[disabled] input[type="checkbox"], +fieldset[disabled] .radio, +fieldset[disabled] .radio-inline, +fieldset[disabled] .checkbox, +fieldset[disabled] .checkbox-inline { + cursor: not-allowed; +} +.input-sm { + height: 30px; + padding: 5px 10px; + font-size: 12px; + line-height: 1.5; + border-radius: 3px; +} +select.input-sm { + height: 30px; + line-height: 30px; +} +textarea.input-sm { + height: auto; +} +.input-lg { + height: 45px; + padding: 10px 16px; + font-size: 18px; + line-height: 1.33; + border-radius: 6px; +} +select.input-lg { + height: 45px; + line-height: 45px; +} +textarea.input-lg { + height: auto; +} +.has-warning .help-block, +.has-warning .control-label { + color: #c09853; +} +.has-warning .form-control { + border-color: #c09853; + -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075); + box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075); +} +.has-warning .form-control:focus { + border-color: #a47e3c; + -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #dbc59e; + box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #dbc59e; +} +.has-warning .input-group-addon { + color: #c09853; + border-color: #c09853; + background-color: #fcf8e3; +} +.has-error .help-block, +.has-error .control-label { + color: #b94a48; +} +.has-error .form-control { + border-color: #b94a48; + -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075); + box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075); +} +.has-error .form-control:focus { + border-color: #953b39; + -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #d59392; + box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #d59392; +} +.has-error .input-group-addon { + color: #b94a48; + border-color: #b94a48; + background-color: #f2dede; +} +.has-success .help-block, +.has-success .control-label { + color: #468847; +} +.has-success .form-control { + border-color: #468847; + -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075); + box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075); +} +.has-success .form-control:focus { + border-color: #356635; + -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #7aba7b; + box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #7aba7b; +} +.has-success .input-group-addon { + color: #468847; + border-color: #468847; + background-color: #dff0d8; +} +.form-control-static { + margin-bottom: 0; + padding-top: 7px; +} +.help-block { + display: block; + margin-top: 5px; + margin-bottom: 10px; + color: #b7b7b9; +} +@media (min-width: 768px) { + .form-inline .form-group { + display: inline-block; + margin-bottom: 0; + vertical-align: middle; + } + .form-inline .form-control { + display: inline-block; + } + .form-inline .radio, + .form-inline .checkbox { + display: inline-block; + margin-top: 0; + margin-bottom: 0; + padding-left: 0; + } + .form-inline .radio input[type="radio"], + .form-inline .checkbox input[type="checkbox"] { + float: none; + margin-left: 0; + } +} +.form-horizontal .control-label, +.form-horizontal .radio, +.form-horizontal .checkbox, +.form-horizontal .radio-inline, +.form-horizontal .checkbox-inline { + margin-top: 0; + margin-bottom: 0; + padding-top: 7px; +} +.form-horizontal .form-group { + margin-left: -15px; + margin-right: -15px; +} +.form-horizontal .form-group:before, +.form-horizontal .form-group:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.form-horizontal .form-group:after { + clear: both; +} +.form-horizontal .form-group:before, +.form-horizontal .form-group:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.form-horizontal .form-group:after { + clear: both; +} +@media (min-width: 768px) { + .form-horizontal .control-label { + text-align: right; + } +} +.btn { + display: inline-block; + padding: 6px 12px; + margin-bottom: 0; + font-size: 14px; + font-weight: normal; + line-height: 1.428571429; + text-align: center; + vertical-align: middle; + cursor: pointer; + border: 1px solid transparent; + border-radius: 4px; + white-space: nowrap; + -webkit-user-select: none; + -moz-user-select: none; + -ms-user-select: none; + -o-user-select: none; + user-select: none; +} +.btn:focus { + outline: thin dotted #333; + outline: 5px auto -webkit-focus-ring-color; + outline-offset: -2px; +} +.btn:hover, +.btn:focus { + color: #333333; + text-decoration: none; +} +.btn:active, +.btn.active { + outline: 0; + background-image: none; + -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125); + box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125); +} +.btn.disabled, +.btn[disabled], +fieldset[disabled] .btn { + cursor: not-allowed; + pointer-events: none; + opacity: 0.65; + filter: alpha(opacity=65); + -webkit-box-shadow: none; + box-shadow: none; +} +.btn-default { + color: #333333; + background-color: #ffffff; + border-color: #cccccc; +} +.btn-default:hover, +.btn-default:focus, +.btn-default:active, +.btn-default.active, +.open .dropdown-toggle.btn-default { + color: #333333; + background-color: #ebebeb; + border-color: #adadad; +} +.btn-default:active, +.btn-default.active, +.open .dropdown-toggle.btn-default { + background-image: none; +} +.btn-default.disabled, +.btn-default[disabled], +fieldset[disabled] .btn-default, +.btn-default.disabled:hover, +.btn-default[disabled]:hover, +fieldset[disabled] .btn-default:hover, +.btn-default.disabled:focus, +.btn-default[disabled]:focus, +fieldset[disabled] .btn-default:focus, +.btn-default.disabled:active, +.btn-default[disabled]:active, +fieldset[disabled] .btn-default:active, +.btn-default.disabled.active, +.btn-default[disabled].active, +fieldset[disabled] .btn-default.active { + background-color: #ffffff; + border-color: #cccccc; +} +.btn-primary { + color: #ffffff; + background-color: #74ab50; + border-color: #689a48; +} +.btn-primary:hover, +.btn-primary:focus, +.btn-primary:active, +.btn-primary.active, +.open .dropdown-toggle.btn-primary { + color: #ffffff; + background-color: #618f43; + border-color: #4c7034; +} +.btn-primary:active, +.btn-primary.active, +.open .dropdown-toggle.btn-primary { + background-image: none; +} +.btn-primary.disabled, +.btn-primary[disabled], +fieldset[disabled] .btn-primary, +.btn-primary.disabled:hover, +.btn-primary[disabled]:hover, +fieldset[disabled] .btn-primary:hover, +.btn-primary.disabled:focus, +.btn-primary[disabled]:focus, +fieldset[disabled] .btn-primary:focus, +.btn-primary.disabled:active, +.btn-primary[disabled]:active, +fieldset[disabled] .btn-primary:active, +.btn-primary.disabled.active, +.btn-primary[disabled].active, +fieldset[disabled] .btn-primary.active { + background-color: #74ab50; + border-color: #689a48; +} +.btn-warning { + color: #ffffff; + background-color: #f0ad4e; + border-color: #eea236; +} +.btn-warning:hover, +.btn-warning:focus, +.btn-warning:active, +.btn-warning.active, +.open .dropdown-toggle.btn-warning { + color: #ffffff; + background-color: #ed9c28; + border-color: #d58512; +} +.btn-warning:active, +.btn-warning.active, +.open .dropdown-toggle.btn-warning { + background-image: none; +} +.btn-warning.disabled, +.btn-warning[disabled], +fieldset[disabled] .btn-warning, +.btn-warning.disabled:hover, +.btn-warning[disabled]:hover, +fieldset[disabled] .btn-warning:hover, +.btn-warning.disabled:focus, +.btn-warning[disabled]:focus, +fieldset[disabled] .btn-warning:focus, +.btn-warning.disabled:active, +.btn-warning[disabled]:active, +fieldset[disabled] .btn-warning:active, +.btn-warning.disabled.active, +.btn-warning[disabled].active, +fieldset[disabled] .btn-warning.active { + background-color: #f0ad4e; + border-color: #eea236; +} +.btn-danger { + color: #ffffff; + background-color: #d9534f; + border-color: #d43f3a; +} +.btn-danger:hover, +.btn-danger:focus, +.btn-danger:active, +.btn-danger.active, +.open .dropdown-toggle.btn-danger { + color: #ffffff; + background-color: #d2322d; + border-color: #ac2925; +} +.btn-danger:active, +.btn-danger.active, +.open .dropdown-toggle.btn-danger { + background-image: none; +} +.btn-danger.disabled, +.btn-danger[disabled], +fieldset[disabled] .btn-danger, +.btn-danger.disabled:hover, +.btn-danger[disabled]:hover, +fieldset[disabled] .btn-danger:hover, +.btn-danger.disabled:focus, +.btn-danger[disabled]:focus, +fieldset[disabled] .btn-danger:focus, +.btn-danger.disabled:active, +.btn-danger[disabled]:active, +fieldset[disabled] .btn-danger:active, +.btn-danger.disabled.active, +.btn-danger[disabled].active, +fieldset[disabled] .btn-danger.active { + background-color: #d9534f; + border-color: #d43f3a; +} +.btn-success { + color: #ffffff; + background-color: #5cb85c; + border-color: #4cae4c; +} +.btn-success:hover, +.btn-success:focus, +.btn-success:active, +.btn-success.active, +.open .dropdown-toggle.btn-success { + color: #ffffff; + background-color: #47a447; + border-color: #398439; +} +.btn-success:active, +.btn-success.active, +.open .dropdown-toggle.btn-success { + background-image: none; +} +.btn-success.disabled, +.btn-success[disabled], +fieldset[disabled] .btn-success, +.btn-success.disabled:hover, +.btn-success[disabled]:hover, +fieldset[disabled] .btn-success:hover, +.btn-success.disabled:focus, +.btn-success[disabled]:focus, +fieldset[disabled] .btn-success:focus, +.btn-success.disabled:active, +.btn-success[disabled]:active, +fieldset[disabled] .btn-success:active, +.btn-success.disabled.active, +.btn-success[disabled].active, +fieldset[disabled] .btn-success.active { + background-color: #5cb85c; + border-color: #4cae4c; +} +.btn-info { + color: #ffffff; + background-color: #347DBE; + border-color: #347DBE; +} +.btn-info:hover, +.btn-info:focus, +.btn-info:active, +.btn-info.active, +.open .dropdown-toggle.btn-info { + color: #ffffff; + background-color: #015CAE; + border-color: #015CAE; +} +.btn-info:active, +.btn-info.active, +.open .dropdown-toggle.btn-info { + background-image: none; +} +.btn-info.disabled, +.btn-info[disabled], +fieldset[disabled] .btn-info, +.btn-info.disabled:hover, +.btn-info[disabled]:hover, +fieldset[disabled] .btn-info:hover, +.btn-info.disabled:focus, +.btn-info[disabled]:focus, +fieldset[disabled] .btn-info:focus, +.btn-info.disabled:active, +.btn-info[disabled]:active, +fieldset[disabled] .btn-info:active, +.btn-info.disabled.active, +.btn-info[disabled].active, +fieldset[disabled] .btn-info.active { + background-color: #5bc0de; + border-color: #46b8da; +} +.btn-link { + color: #74ab50; + font-weight: normal; + cursor: pointer; + border-radius: 0; +} +.btn-link, +.btn-link:active, +.btn-link[disabled], +fieldset[disabled] .btn-link { + background-color: transparent; + -webkit-box-shadow: none; + box-shadow: none; +} +.btn-link, +.btn-link:hover, +.btn-link:focus, +.btn-link:active { + border-color: transparent; +} +.btn-link:hover, +.btn-link:focus { + color: #517738; + text-decoration: underline; + background-color: transparent; +} +.btn-link[disabled]:hover, +fieldset[disabled] .btn-link:hover, +.btn-link[disabled]:focus, +fieldset[disabled] .btn-link:focus { + color: #f9faf9; + text-decoration: none; +} +.btn-lg { + padding: 10px 16px; + font-size: 18px; + line-height: 1.33; + border-radius: 6px; +} +.btn-sm, +.btn-xs { + padding: 5px 10px; + font-size: 12px; + line-height: 1.5; + border-radius: 3px; +} +.btn-xs { + padding: 1px 5px; +} +.btn-block { + display: block; + width: 100%; + padding-left: 0; + padding-right: 0; +} +.btn-block + .btn-block { + margin-top: 5px; +} +input[type="submit"].btn-block, +input[type="reset"].btn-block, +input[type="button"].btn-block { + width: 100%; +} +.fade { + opacity: 0; + -webkit-transition: opacity 0.15s linear; + transition: opacity 0.15s linear; +} +.fade.in { + opacity: 1; +} +.collapse { + display: none; +} +.collapse.in { + display: block; +} +.collapsing { + position: relative; + height: 0; + overflow: hidden; + -webkit-transition: height 0.35s ease; + transition: height 0.35s ease; +} +@font-face { + font-family: 'Glyphicons Halflings'; + src: url('../fonts/glyphicons-halflings-regular.eot'); + src: url('../fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'), url('../fonts/glyphicons-halflings-regular.woff') format('woff'), url('../fonts/glyphicons-halflings-regular.ttf') format('truetype'), url('../fonts/glyphicons-halflings-regular.svg#glyphicons-halflingsregular') format('svg'); +} +.glyphicon { + position: relative; + top: 1px; + display: inline-block; + font-family: 'Glyphicons Halflings'; + font-style: normal; + font-weight: normal; + line-height: 1; + -webkit-font-smoothing: antialiased; +} +.glyphicon-asterisk:before { + content: "\2a"; +} +.glyphicon-plus:before { + content: "\2b"; +} +.glyphicon-euro:before { + content: "\20ac"; +} +.glyphicon-minus:before { + content: "\2212"; +} +.glyphicon-cloud:before { + content: "\2601"; +} +.glyphicon-envelope:before { + content: "\2709"; +} +.glyphicon-pencil:before { + content: "\270f"; +} +.glyphicon-glass:before { + content: "\e001"; +} +.glyphicon-music:before { + content: "\e002"; +} +.glyphicon-search:before { + content: "\e003"; +} +.glyphicon-heart:before { + content: "\e005"; +} +.glyphicon-star:before { + content: "\e006"; +} +.glyphicon-star-empty:before { + content: "\e007"; +} +.glyphicon-user:before { + content: "\e008"; +} +.glyphicon-film:before { + content: "\e009"; +} +.glyphicon-th-large:before { + content: "\e010"; +} +.glyphicon-th:before { + content: "\e011"; +} +.glyphicon-th-list:before { + content: "\e012"; +} +.glyphicon-ok:before { + content: "\e013"; +} +.glyphicon-remove:before { + content: "\e014"; +} +.glyphicon-zoom-in:before { + content: "\e015"; +} +.glyphicon-zoom-out:before { + content: "\e016"; +} +.glyphicon-off:before { + content: "\e017"; +} +.glyphicon-signal:before { + content: "\e018"; +} +.glyphicon-cog:before { + content: "\e019"; +} +.glyphicon-trash:before { + content: "\e020"; +} +.glyphicon-home:before { + content: "\e021"; +} +.glyphicon-file:before { + content: "\e022"; +} +.glyphicon-time:before { + content: "\e023"; +} +.glyphicon-road:before { + content: "\e024"; +} +.glyphicon-download-alt:before { + content: "\e025"; +} +.glyphicon-download:before { + content: "\e026"; +} +.glyphicon-upload:before { + content: "\e027"; +} +.glyphicon-inbox:before { + content: "\e028"; +} +.glyphicon-play-circle:before { + content: "\e029"; +} +.glyphicon-repeat:before { + content: "\e030"; +} +.glyphicon-refresh:before { + content: "\e031"; +} +.glyphicon-list-alt:before { + content: "\e032"; +} +.glyphicon-flag:before { + content: "\e034"; +} +.glyphicon-headphones:before { + content: "\e035"; +} +.glyphicon-volume-off:before { + content: "\e036"; +} +.glyphicon-volume-down:before { + content: "\e037"; +} +.glyphicon-volume-up:before { + content: "\e038"; +} +.glyphicon-qrcode:before { + content: "\e039"; +} +.glyphicon-barcode:before { + content: "\e040"; +} +.glyphicon-tag:before { + content: "\e041"; +} +.glyphicon-tags:before { + content: "\e042"; +} +.glyphicon-book:before { + content: "\e043"; +} +.glyphicon-print:before { + content: "\e045"; +} +.glyphicon-font:before { + content: "\e047"; +} +.glyphicon-bold:before { + content: "\e048"; +} +.glyphicon-italic:before { + content: "\e049"; +} +.glyphicon-text-height:before { + content: "\e050"; +} +.glyphicon-text-width:before { + content: "\e051"; +} +.glyphicon-align-left:before { + content: "\e052"; +} +.glyphicon-align-center:before { + content: "\e053"; +} +.glyphicon-align-right:before { + content: "\e054"; +} +.glyphicon-align-justify:before { + content: "\e055"; +} +.glyphicon-list:before { + content: "\e056"; +} +.glyphicon-indent-left:before { + content: "\e057"; +} +.glyphicon-indent-right:before { + content: "\e058"; +} +.glyphicon-facetime-video:before { + content: "\e059"; +} +.glyphicon-picture:before { + content: "\e060"; +} +.glyphicon-map-marker:before { + content: "\e062"; +} +.glyphicon-adjust:before { + content: "\e063"; +} +.glyphicon-tint:before { + content: "\e064"; +} +.glyphicon-edit:before { + content: "\e065"; +} +.glyphicon-share:before { + content: "\e066"; +} +.glyphicon-check:before { + content: "\e067"; +} +.glyphicon-move:before { + content: "\e068"; +} +.glyphicon-step-backward:before { + content: "\e069"; +} +.glyphicon-fast-backward:before { + content: "\e070"; +} +.glyphicon-backward:before { + content: "\e071"; +} +.glyphicon-play:before { + content: "\e072"; +} +.glyphicon-pause:before { + content: "\e073"; +} +.glyphicon-stop:before { + content: "\e074"; +} +.glyphicon-forward:before { + content: "\e075"; +} +.glyphicon-fast-forward:before { + content: "\e076"; +} +.glyphicon-step-forward:before { + content: "\e077"; +} +.glyphicon-eject:before { + content: "\e078"; +} +.glyphicon-chevron-left:before { + content: "\e079"; +} +.glyphicon-chevron-right:before { + content: "\e080"; +} +.glyphicon-plus-sign:before { + content: "\e081"; +} +.glyphicon-minus-sign:before { + content: "\e082"; +} +.glyphicon-remove-sign:before { + content: "\e083"; +} +.glyphicon-ok-sign:before { + content: "\e084"; +} +.glyphicon-question-sign:before { + content: "\e085"; +} +.glyphicon-info-sign:before { + content: "\e086"; +} +.glyphicon-screenshot:before { + content: "\e087"; +} +.glyphicon-remove-circle:before { + content: "\e088"; +} +.glyphicon-ok-circle:before { + content: "\e089"; +} +.glyphicon-ban-circle:before { + content: "\e090"; +} +.glyphicon-arrow-left:before { + content: "\e091"; +} +.glyphicon-arrow-right:before { + content: "\e092"; +} +.glyphicon-arrow-up:before { + content: "\e093"; +} +.glyphicon-arrow-down:before { + content: "\e094"; +} +.glyphicon-share-alt:before { + content: "\e095"; +} +.glyphicon-resize-full:before { + content: "\e096"; +} +.glyphicon-resize-small:before { + content: "\e097"; +} +.glyphicon-exclamation-sign:before { + content: "\e101"; +} +.glyphicon-gift:before { + content: "\e102"; +} +.glyphicon-leaf:before { + content: "\e103"; +} +.glyphicon-eye-open:before { + content: "\e105"; +} +.glyphicon-eye-close:before { + content: "\e106"; +} +.glyphicon-warning-sign:before { + content: "\e107"; +} +.glyphicon-plane:before { + content: "\e108"; +} +.glyphicon-random:before { + content: "\e110"; +} +.glyphicon-comment:before { + content: "\e111"; +} +.glyphicon-magnet:before { + content: "\e112"; +} +.glyphicon-chevron-up:before { + content: "\e113"; +} +.glyphicon-chevron-down:before { + content: "\e114"; +} +.glyphicon-retweet:before { + content: "\e115"; +} +.glyphicon-shopping-cart:before { + content: "\e116"; +} +.glyphicon-folder-close:before { + content: "\e117"; +} +.glyphicon-folder-open:before { + content: "\e118"; +} +.glyphicon-resize-vertical:before { + content: "\e119"; +} +.glyphicon-resize-horizontal:before { + content: "\e120"; +} +.glyphicon-hdd:before { + content: "\e121"; +} +.glyphicon-bullhorn:before { + content: "\e122"; +} +.glyphicon-certificate:before { + content: "\e124"; +} +.glyphicon-thumbs-up:before { + content: "\e125"; +} +.glyphicon-thumbs-down:before { + content: "\e126"; +} +.glyphicon-hand-right:before { + content: "\e127"; +} +.glyphicon-hand-left:before { + content: "\e128"; +} +.glyphicon-hand-up:before { + content: "\e129"; +} +.glyphicon-hand-down:before { + content: "\e130"; +} +.glyphicon-circle-arrow-right:before { + content: "\e131"; +} +.glyphicon-circle-arrow-left:before { + content: "\e132"; +} +.glyphicon-circle-arrow-up:before { + content: "\e133"; +} +.glyphicon-circle-arrow-down:before { + content: "\e134"; +} +.glyphicon-globe:before { + content: "\e135"; +} +.glyphicon-tasks:before { + content: "\e137"; +} +.glyphicon-filter:before { + content: "\e138"; +} +.glyphicon-fullscreen:before { + content: "\e140"; +} +.glyphicon-dashboard:before { + content: "\e141"; +} +.glyphicon-heart-empty:before { + content: "\e143"; +} +.glyphicon-link:before { + content: "\e144"; +} +.glyphicon-phone:before { + content: "\e145"; +} +.glyphicon-usd:before { + content: "\e148"; +} +.glyphicon-gbp:before { + content: "\e149"; +} +.glyphicon-sort:before { + content: "\e150"; +} +.glyphicon-sort-by-alphabet:before { + content: "\e151"; +} +.glyphicon-sort-by-alphabet-alt:before { + content: "\e152"; +} +.glyphicon-sort-by-order:before { + content: "\e153"; +} +.glyphicon-sort-by-order-alt:before { + content: "\e154"; +} +.glyphicon-sort-by-attributes:before { + content: "\e155"; +} +.glyphicon-sort-by-attributes-alt:before { + content: "\e156"; +} +.glyphicon-unchecked:before { + content: "\e157"; +} +.glyphicon-expand:before { + content: "\e158"; +} +.glyphicon-collapse-down:before { + content: "\e159"; +} +.glyphicon-collapse-up:before { + content: "\e160"; +} +.glyphicon-log-in:before { + content: "\e161"; +} +.glyphicon-flash:before { + content: "\e162"; +} +.glyphicon-log-out:before { + content: "\e163"; +} +.glyphicon-new-window:before { + content: "\e164"; +} +.glyphicon-record:before { + content: "\e165"; +} +.glyphicon-save:before { + content: "\e166"; +} +.glyphicon-open:before { + content: "\e167"; +} +.glyphicon-saved:before { + content: "\e168"; +} +.glyphicon-import:before { + content: "\e169"; +} +.glyphicon-export:before { + content: "\e170"; +} +.glyphicon-send:before { + content: "\e171"; +} +.glyphicon-floppy-disk:before { + content: "\e172"; +} +.glyphicon-floppy-saved:before { + content: "\e173"; +} +.glyphicon-floppy-remove:before { + content: "\e174"; +} +.glyphicon-floppy-save:before { + content: "\e175"; +} +.glyphicon-floppy-open:before { + content: "\e176"; +} +.glyphicon-credit-card:before { + content: "\e177"; +} +.glyphicon-transfer:before { + content: "\e178"; +} +.glyphicon-cutlery:before { + content: "\e179"; +} +.glyphicon-header:before { + content: "\e180"; +} +.glyphicon-compressed:before { + content: "\e181"; +} +.glyphicon-earphone:before { + content: "\e182"; +} +.glyphicon-phone-alt:before { + content: "\e183"; +} +.glyphicon-tower:before { + content: "\e184"; +} +.glyphicon-stats:before { + content: "\e185"; +} +.glyphicon-sd-video:before { + content: "\e186"; +} +.glyphicon-hd-video:before { + content: "\e187"; +} +.glyphicon-subtitles:before { + content: "\e188"; +} +.glyphicon-sound-stereo:before { + content: "\e189"; +} +.glyphicon-sound-dolby:before { + content: "\e190"; +} +.glyphicon-sound-5-1:before { + content: "\e191"; +} +.glyphicon-sound-6-1:before { + content: "\e192"; +} +.glyphicon-sound-7-1:before { + content: "\e193"; +} +.glyphicon-copyright-mark:before { + content: "\e194"; +} +.glyphicon-registration-mark:before { + content: "\e195"; +} +.glyphicon-cloud-download:before { + content: "\e197"; +} +.glyphicon-cloud-upload:before { + content: "\e198"; +} +.glyphicon-tree-conifer:before { + content: "\e199"; +} +.glyphicon-tree-deciduous:before { + content: "\e200"; +} +.glyphicon-briefcase:before { + content: "\1f4bc"; +} +.glyphicon-calendar:before { + content: "\1f4c5"; +} +.glyphicon-pushpin:before { + content: "\1f4cc"; +} +.glyphicon-paperclip:before { + content: "\1f4ce"; +} +.glyphicon-camera:before { + content: "\1f4f7"; +} +.glyphicon-lock:before { + content: "\1f512"; +} +.glyphicon-bell:before { + content: "\1f514"; +} +.glyphicon-bookmark:before { + content: "\1f516"; +} +.glyphicon-fire:before { + content: "\1f525"; +} +.glyphicon-wrench:before { + content: "\1f527"; +} +.caret { + display: inline-block; + width: 0; + height: 0; + margin-left: 2px; + vertical-align: middle; + border-top: 4px solid #000000; + border-right: 4px solid transparent; + border-left: 4px solid transparent; + border-bottom: 0 dotted; + content: ""; +} +.dropdown { + position: relative; +} +.dropdown-toggle:focus { + outline: 0; +} +.dropdown-menu { + position: absolute; + top: 100%; + left: 0; + z-index: 1000; + display: none; + float: left; + min-width: 160px; + padding: 5px 0; + margin: 2px 0 0; + list-style: none; + font-size: 14px; + background-color: #ffffff; + border: 1px solid #cccccc; + border: 1px solid rgba(0, 0, 0, 0.15); + border-radius: 4px; + -webkit-box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175); + box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175); + background-clip: padding-box; +} +.dropdown-menu.pull-right { + right: 0; + left: auto; +} +.dropdown-menu .divider { + height: 1px; + margin: 9px 0; + overflow: hidden; + background-color: #e5e5e5; +} +.dropdown-menu > li > a { + display: block; + padding: 3px 20px; + clear: both; + font-weight: normal; + line-height: 1.428571429; + color: #77777a; + white-space: nowrap; +} +.dropdown-menu > li > a:hover, +.dropdown-menu > li > a:focus { + text-decoration: none; + color: #ffffff; + background-color: #679DCE; +} +.dropdown-menu > .active > a, +.dropdown-menu > .active > a:hover, +.dropdown-menu > .active > a:focus { + color: #ffffff; + text-decoration: none; + outline: 0; + background-color: #679DCE; +} +.dropdown-menu > .disabled > a, +.dropdown-menu > .disabled > a:hover, +.dropdown-menu > .disabled > a:focus { + color: #f9faf9; +} +.dropdown-menu > .disabled > a:hover, +.dropdown-menu > .disabled > a:focus { + text-decoration: none; + background-color: transparent; + background-image: none; + filter: progid:DXImageTransform.Microsoft.gradient(enabled = false); + cursor: not-allowed; +} +.open > .dropdown-menu { + display: block; +} +.open > a { + outline: 0; +} +.dropdown-header { + display: block; + padding: 3px 20px; + font-size: 12px; + line-height: 1.428571429; + color: #f9faf9; +} +.dropdown-backdrop { + position: fixed; + left: 0; + right: 0; + bottom: 0; + top: 0; + z-index: 990; +} +.pull-right > .dropdown-menu { + right: 0; + left: auto; +} +.dropup .caret, +.navbar-fixed-bottom .dropdown .caret { + border-top: 0 dotted; + border-bottom: 4px solid #000000; + content: ""; +} +.dropup .dropdown-menu, +.navbar-fixed-bottom .dropdown .dropdown-menu { + top: auto; + bottom: 100%; + margin-bottom: 1px; +} +@media (min-width: 768px) { + .navbar-right .dropdown-menu { + right: 0; + left: auto; + } +} +.btn-default .caret { + border-top-color: #333333; +} +.btn-primary .caret, +.btn-success .caret, +.btn-warning .caret, +.btn-danger .caret, +.btn-info .caret { + border-top-color: #fff; +} +.dropup .btn-default .caret { + border-bottom-color: #333333; +} +.dropup .btn-primary .caret, +.dropup .btn-success .caret, +.dropup .btn-warning .caret, +.dropup .btn-danger .caret, +.dropup .btn-info .caret { + border-bottom-color: #fff; +} +.btn-group, +.btn-group-vertical { + position: relative; + display: inline-block; + vertical-align: middle; +} +.btn-group > .btn, +.btn-group-vertical > .btn { + position: relative; + float: left; +} +.btn-group > .btn:hover, +.btn-group-vertical > .btn:hover, +.btn-group > .btn:focus, +.btn-group-vertical > .btn:focus, +.btn-group > .btn:active, +.btn-group-vertical > .btn:active, +.btn-group > .btn.active, +.btn-group-vertical > .btn.active { + z-index: 2; +} +.btn-group > .btn:focus, +.btn-group-vertical > .btn:focus { + outline: none; +} +.btn-group .btn + .btn, +.btn-group .btn + .btn-group, +.btn-group .btn-group + .btn, +.btn-group .btn-group + .btn-group { + margin-left: -1px; +} +.btn-toolbar:before, +.btn-toolbar:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.btn-toolbar:after { + clear: both; +} +.btn-toolbar:before, +.btn-toolbar:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.btn-toolbar:after { + clear: both; +} +.btn-toolbar .btn-group { + float: left; +} +.btn-toolbar > .btn + .btn, +.btn-toolbar > .btn-group + .btn, +.btn-toolbar > .btn + .btn-group, +.btn-toolbar > .btn-group + .btn-group { + margin-left: 5px; +} +.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) { + border-radius: 0; +} +.btn-group > .btn:first-child { + margin-left: 0; +} +.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) { + border-bottom-right-radius: 0; + border-top-right-radius: 0; +} +.btn-group > .btn:last-child:not(:first-child), +.btn-group > .dropdown-toggle:not(:first-child) { + border-bottom-left-radius: 0; + border-top-left-radius: 0; +} +.btn-group > .btn-group { + float: left; +} +.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn { + border-radius: 0; +} +.btn-group > .btn-group:first-child > .btn:last-child, +.btn-group > .btn-group:first-child > .dropdown-toggle { + border-bottom-right-radius: 0; + border-top-right-radius: 0; +} +.btn-group > .btn-group:last-child > .btn:first-child { + border-bottom-left-radius: 0; + border-top-left-radius: 0; +} +.btn-group .dropdown-toggle:active, +.btn-group.open .dropdown-toggle { + outline: 0; +} +.btn-group-xs > .btn { + padding: 5px 10px; + font-size: 12px; + line-height: 1.5; + border-radius: 3px; + padding: 1px 5px; +} +.btn-group-sm > .btn { + padding: 5px 10px; + font-size: 12px; + line-height: 1.5; + border-radius: 3px; +} +.btn-group-lg > .btn { + padding: 10px 16px; + font-size: 18px; + line-height: 1.33; + border-radius: 6px; +} +.btn-group > .btn + .dropdown-toggle { + padding-left: 8px; + padding-right: 8px; +} +.btn-group > .btn-lg + .dropdown-toggle { + padding-left: 12px; + padding-right: 12px; +} +.btn-group.open .dropdown-toggle { + -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125); + box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125); +} +.btn .caret { + margin-left: 0; +} +.btn-lg .caret { + border-width: 5px 5px 0; + border-bottom-width: 0; +} +.dropup .btn-lg .caret { + border-width: 0 5px 5px; +} +.btn-group-vertical > .btn, +.btn-group-vertical > .btn-group { + display: block; + float: none; + width: 100%; + max-width: 100%; +} +.btn-group-vertical > .btn-group:before, +.btn-group-vertical > .btn-group:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.btn-group-vertical > .btn-group:after { + clear: both; +} +.btn-group-vertical > .btn-group:before, +.btn-group-vertical > .btn-group:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.btn-group-vertical > .btn-group:after { + clear: both; +} +.btn-group-vertical > .btn-group > .btn { + float: none; +} +.btn-group-vertical > .btn + .btn, +.btn-group-vertical > .btn + .btn-group, +.btn-group-vertical > .btn-group + .btn, +.btn-group-vertical > .btn-group + .btn-group { + margin-top: -1px; + margin-left: 0; +} +.btn-group-vertical > .btn:not(:first-child):not(:last-child) { + border-radius: 0; +} +.btn-group-vertical > .btn:first-child:not(:last-child) { + border-top-right-radius: 4px; + border-bottom-right-radius: 0; + border-bottom-left-radius: 0; +} +.btn-group-vertical > .btn:last-child:not(:first-child) { + border-bottom-left-radius: 4px; + border-top-right-radius: 0; + border-top-left-radius: 0; +} +.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn { + border-radius: 0; +} +.btn-group-vertical > .btn-group:first-child > .btn:last-child, +.btn-group-vertical > .btn-group:first-child > .dropdown-toggle { + border-bottom-right-radius: 0; + border-bottom-left-radius: 0; +} +.btn-group-vertical > .btn-group:last-child > .btn:first-child { + border-top-right-radius: 0; + border-top-left-radius: 0; +} +.btn-group-justified { + display: table; + width: 100%; + table-layout: fixed; + border-collapse: separate; +} +.btn-group-justified .btn { + float: none; + display: table-cell; + width: 1%; +} +[data-toggle="buttons"] > .btn > input[type="radio"], +[data-toggle="buttons"] > .btn > input[type="checkbox"] { + display: none; +} +.input-group { + position: relative; + display: table; + border-collapse: separate; +} +.input-group.col { + float: none; + padding-left: 0; + padding-right: 0; +} +.input-group .form-control { + width: 100%; + margin-bottom: 0; +} +.input-group-lg > .form-control, +.input-group-lg > .input-group-addon, +.input-group-lg > .input-group-btn > .btn { + height: 45px; + padding: 10px 16px; + font-size: 18px; + line-height: 1.33; + border-radius: 6px; +} +select.input-group-lg > .form-control, +select.input-group-lg > .input-group-addon, +select.input-group-lg > .input-group-btn > .btn { + height: 45px; + line-height: 45px; +} +textarea.input-group-lg > .form-control, +textarea.input-group-lg > .input-group-addon, +textarea.input-group-lg > .input-group-btn > .btn { + height: auto; +} +.input-group-sm > .form-control, +.input-group-sm > .input-group-addon, +.input-group-sm > .input-group-btn > .btn { + height: 30px; + padding: 5px 10px; + font-size: 12px; + line-height: 1.5; + border-radius: 3px; +} +select.input-group-sm > .form-control, +select.input-group-sm > .input-group-addon, +select.input-group-sm > .input-group-btn > .btn { + height: 30px; + line-height: 30px; +} +textarea.input-group-sm > .form-control, +textarea.input-group-sm > .input-group-addon, +textarea.input-group-sm > .input-group-btn > .btn { + height: auto; +} +.input-group-addon, +.input-group-btn, +.input-group .form-control { + display: table-cell; +} +.input-group-addon:not(:first-child):not(:last-child), +.input-group-btn:not(:first-child):not(:last-child), +.input-group .form-control:not(:first-child):not(:last-child) { + border-radius: 0; +} +.input-group-addon, +.input-group-btn { + width: 1%; + white-space: nowrap; + vertical-align: middle; +} +.input-group-addon { + padding: 6px 12px; + font-size: 14px; + font-weight: normal; + line-height: 1; + text-align: center; + background-color: #bac9c2; + border: 1px solid #cccccc; + border-radius: 4px; +} +.input-group-addon.input-sm { + padding: 5px 10px; + font-size: 12px; + border-radius: 3px; +} +.input-group-addon.input-lg { + padding: 10px 16px; + font-size: 18px; + border-radius: 6px; +} +.input-group-addon input[type="radio"], +.input-group-addon input[type="checkbox"] { + margin-top: 0; +} +.input-group .form-control:first-child, +.input-group-addon:first-child, +.input-group-btn:first-child > .btn, +.input-group-btn:first-child > .dropdown-toggle, +.input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle) { + border-bottom-right-radius: 0; + border-top-right-radius: 0; +} +.input-group-addon:first-child { + border-right: 0; +} +.input-group .form-control:last-child, +.input-group-addon:last-child, +.input-group-btn:last-child > .btn, +.input-group-btn:last-child > .dropdown-toggle, +.input-group-btn:first-child > .btn:not(:first-child) { + border-bottom-left-radius: 0; + border-top-left-radius: 0; +} +.input-group-addon:last-child { + border-left: 0; +} +.input-group-btn { + position: relative; + white-space: nowrap; +} +.input-group-btn > .btn { + position: relative; +} +.input-group-btn > .btn + .btn { + margin-left: -4px; +} +.input-group-btn > .btn:hover, +.input-group-btn > .btn:active { + z-index: 2; +} +.nav { + margin-bottom: 0; + padding-left: 0; + list-style: none; +} +.nav:before, +.nav:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.nav:after { + clear: both; +} +.nav:before, +.nav:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.nav:after { + clear: both; +} +.nav > li { + position: relative; + display: block; +} +.nav > li > a { + position: relative; + display: block; + padding: 10px 15px; +} +.nav > li > a:hover, +.nav > li > a:focus { + text-decoration: none; + background-color: #bac9c2; +} +.nav > li.disabled > a { + color: #f9faf9; +} +.nav > li.disabled > a:hover, +.nav > li.disabled > a:focus { + color: #f9faf9; + text-decoration: none; + background-color: transparent; + cursor: not-allowed; +} +.nav .open > a, +.nav .open > a:hover, +.nav .open > a:focus { + background-color: #bac9c2; + border-color: #74ab50; +} +.nav .nav-divider { + height: 1px; + margin: 9px 0; + overflow: hidden; + background-color: #e5e5e5; +} +.nav > li > a > img { + max-width: none; +} +.nav-tabs { + border-bottom: 1px solid #dddddd; +} +.nav-tabs > li { + float: left; + margin-bottom: -1px; +} +.nav-tabs > li > a { + margin-right: 2px; + line-height: 1.428571429; + border: 1px solid transparent; + border-radius: 4px 4px 0 0; +} +.nav-tabs > li > a:hover { + border-color: #bac9c2 #bac9c2 #dddddd; +} +.nav-tabs > li.active > a, +.nav-tabs > li.active > a:hover, +.nav-tabs > li.active > a:focus { + color: #4aadd6; + background-color: #ffffff; + border: 1px solid #dddddd; + border-bottom-color: transparent; + cursor: default; +} +.nav-tabs.nav-justified { + width: 100%; + border-bottom: 0; +} +.nav-tabs.nav-justified > li { + float: none; +} +.nav-tabs.nav-justified > li > a { + text-align: center; +} +@media (min-width: 768px) { + .nav-tabs.nav-justified > li { + display: table-cell; + width: 1%; + } +} +.nav-tabs.nav-justified > li > a { + border-bottom: 1px solid #dddddd; + margin-right: 0; +} +.nav-tabs.nav-justified > .active > a { + border-bottom-color: #ffffff; +} +.nav-pills > li { + float: left; +} +.nav-pills > li > a { + border-radius: 5px; +} +.nav-pills > li + li { + margin-left: 2px; +} +.nav-pills > li.active > a, +.nav-pills > li.active > a:hover, +.nav-pills > li.active > a:focus { + color: #ffffff; + background-color: #74ab50; +} +.nav-stacked > li { + float: none; +} +.nav-stacked > li + li { + margin-top: 2px; + margin-left: 0; +} +.nav-justified { + width: 100%; +} +.nav-justified > li { + float: none; +} +.nav-justified > li > a { + text-align: center; +} +@media (min-width: 768px) { + .nav-justified > li { + display: table-cell; + width: 1%; + } +} +.nav-tabs-justified { + border-bottom: 0; +} +.nav-tabs-justified > li > a { + border-bottom: 1px solid #dddddd; + margin-right: 0; +} +.nav-tabs-justified > .active > a { + border-bottom-color: #ffffff; +} +.tabbable:before, +.tabbable:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.tabbable:after { + clear: both; +} +.tabbable:before, +.tabbable:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.tabbable:after { + clear: both; +} +.tab-content > .tab-pane, +.pill-content > .pill-pane { + display: none; +} +.tab-content > .active, +.pill-content > .active { + display: block; +} +.nav .caret { + border-top-color: #74ab50; + border-bottom-color: #74ab50; +} +.nav a:hover .caret { + border-top-color: #517738; + border-bottom-color: #517738; +} +.nav-tabs .dropdown-menu { + margin-top: -1px; + border-top-right-radius: 0; + border-top-left-radius: 0; +} +.navbar { + position: relative; + z-index: 1000; + min-height: 50px; + margin-bottom: 20px; + border: 1px solid transparent; +} +.navbar:before, +.navbar:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.navbar:after { + clear: both; +} +.navbar:before, +.navbar:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.navbar:after { + clear: both; +} +@media (min-width: 768px) { + .navbar { + border-radius: 4px; + } +} +.navbar-header:before, +.navbar-header:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.navbar-header:after { + clear: both; +} +.navbar-header:before, +.navbar-header:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.navbar-header:after { + clear: both; +} +@media (min-width: 768px) { + .navbar-header { + float: left; + } +} +.navbar-collapse { + max-height: 340px; + overflow-x: visible; + padding-right: 15px; + padding-left: 15px; + border-top: 1px solid transparent; + box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1); + -webkit-overflow-scrolling: touch; +} +.navbar-collapse:before, +.navbar-collapse:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.navbar-collapse:after { + clear: both; +} +.navbar-collapse:before, +.navbar-collapse:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.navbar-collapse:after { + clear: both; +} +.navbar-collapse.in { + overflow-y: auto; +} +@media (min-width: 768px) { + .navbar-collapse { + width: auto; + border-top: 0; + box-shadow: none; + } + .navbar-collapse.collapse { + display: block !important; + height: auto !important; + padding-bottom: 0; + overflow: visible !important; + } + .navbar-collapse.in { + overflow-y: visible; + } + .navbar-collapse .navbar-nav.navbar-left:first-child { + margin-left: -15px; + } + .navbar-collapse .navbar-nav.navbar-right:last-child { + margin-right: -15px; + } + .navbar-collapse .navbar-text:last-child { + margin-right: 0; + } +} +.container > .navbar-header, +.container > .navbar-collapse { + margin-right: -15px; + margin-left: -15px; +} +@media (min-width: 768px) { + .container > .navbar-header, + .container > .navbar-collapse { + margin-right: 0; + margin-left: 0; + } +} +.navbar-static-top { + border-width: 0 0 1px; +} +@media (min-width: 768px) { + .navbar-static-top { + border-radius: 0; + } +} +.navbar-fixed-top, +.navbar-fixed-bottom { + position: fixed; + right: 0; + left: 0; + border-width: 0 0 1px; +} +@media (min-width: 768px) { + .navbar-fixed-top, + .navbar-fixed-bottom { + border-radius: 0; + } +} +.navbar-fixed-top { + z-index: 1030; + top: 0; +} +.navbar-fixed-bottom { + bottom: 0; + margin-bottom: 0; +} +.navbar-brand { + float: left; + padding: 15px 15px; + font-size: 18px; + line-height: 20px; +} +.navbar-brand:hover, +.navbar-brand:focus { + text-decoration: none; +} +@media (min-width: 768px) { + .navbar > .container .navbar-brand { + margin-left: -15px; + } +} +.navbar-toggle { + position: relative; + float: right; + margin-right: 15px; + padding: 9px 10px; + margin-top: 8px; + margin-bottom: 8px; + background-color: transparent; + border: 1px solid transparent; + border-radius: 4px; +} +.navbar-toggle .icon-bar { + display: block; + width: 22px; + height: 2px; + border-radius: 1px; +} +.navbar-toggle .icon-bar + .icon-bar { + margin-top: 4px; +} +@media (min-width: 768px) { + .navbar-toggle { + display: none; + } +} +.navbar-nav { + margin: 7.5px -15px; +} +.navbar-nav > li > a { + padding-top: 10px; + padding-bottom: 10px; + line-height: 20px; +} +@media (max-width: 767px) { + .navbar-nav .open .dropdown-menu { + position: static; + float: none; + width: auto; + margin-top: 0; + background-color: transparent; + border: 0; + box-shadow: none; + } + .navbar-nav .open .dropdown-menu > li > a, + .navbar-nav .open .dropdown-menu .dropdown-header { + padding: 5px 15px 5px 25px; + } + .navbar-nav .open .dropdown-menu > li > a { + line-height: 20px; + } + .navbar-nav .open .dropdown-menu > li > a:hover, + .navbar-nav .open .dropdown-menu > li > a:focus { + background-image: none; + } +} +@media (min-width: 768px) { + .navbar-nav { + float: left; + margin: 0; + } + .navbar-nav > li { + float: left; + } + .navbar-nav > li > a { + padding-top: 15px; + padding-bottom: 15px; + } +} +@media (min-width: 768px) { + .navbar-left { + float: left !important; + } + .navbar-right { + float: right !important; + } +} +.navbar-form { + margin-left: -15px; + margin-right: -15px; + padding: 10px 15px; + border-top: 1px solid transparent; + border-bottom: 1px solid transparent; + -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1); + box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1); + margin-top: 8px; + margin-bottom: 8px; +} +@media (min-width: 768px) { + .navbar-form .form-group { + display: inline-block; + margin-bottom: 0; + vertical-align: middle; + } + .navbar-form .form-control { + display: inline-block; + } + .navbar-form .radio, + .navbar-form .checkbox { + display: inline-block; + margin-top: 0; + margin-bottom: 0; + padding-left: 0; + } + .navbar-form .radio input[type="radio"], + .navbar-form .checkbox input[type="checkbox"] { + float: none; + margin-left: 0; + } +} +@media (max-width: 767px) { + .navbar-form .form-group { + margin-bottom: 5px; + } +} +@media (min-width: 768px) { + .navbar-form { + width: auto; + border: 0; + margin-left: 0; + margin-right: 0; + padding-top: 0; + padding-bottom: 0; + -webkit-box-shadow: none; + box-shadow: none; + } +} +.navbar-nav > li > .dropdown-menu { + margin-top: 0; + border-top-right-radius: 0; + border-top-left-radius: 0; +} +.navbar-fixed-bottom .navbar-nav > li > .dropdown-menu { + border-bottom-right-radius: 0; + border-bottom-left-radius: 0; +} +.navbar-nav.pull-right > li > .dropdown-menu, +.navbar-nav > li > .dropdown-menu.pull-right { + left: auto; + right: 0; +} +.navbar-btn { + margin-top: 8px; + margin-bottom: 8px; +} +.navbar-text { + float: left; + margin-top: 15px; + margin-bottom: 15px; +} +@media (min-width: 768px) { + .navbar-text { + margin-left: 15px; + margin-right: 15px; + } +} +.navbar-default { + background-color: #f8f8f8; + border-color: #e7e7e7; +} +.navbar-default .navbar-brand { + color: #777777; +} +.navbar-default .navbar-brand:hover, +.navbar-default .navbar-brand:focus { + color: #5e5e5e; + background-color: transparent; +} +.navbar-default .navbar-text { + color: #777777; +} +.navbar-default .navbar-nav > li > a { + color: #777777; +} +.navbar-default .navbar-nav > li > a:hover, +.navbar-default .navbar-nav > li > a:focus { + color: #333333; + background-color: transparent; +} +.navbar-default .navbar-nav > .active > a, +.navbar-default .navbar-nav > .active > a:hover, +.navbar-default .navbar-nav > .active > a:focus { + color: #555555; + background-color: #e7e7e7; +} +.navbar-default .navbar-nav > .disabled > a, +.navbar-default .navbar-nav > .disabled > a:hover, +.navbar-default .navbar-nav > .disabled > a:focus { + color: #cccccc; + background-color: transparent; +} +.navbar-default .navbar-toggle { + border-color: #dddddd; +} +.navbar-default .navbar-toggle:hover, +.navbar-default .navbar-toggle:focus { + background-color: #dddddd; +} +.navbar-default .navbar-toggle .icon-bar { + background-color: #cccccc; +} +.navbar-default .navbar-collapse, +.navbar-default .navbar-form { + border-color: #e6e6e6; +} +.navbar-default .navbar-nav > .dropdown > a:hover .caret, +.navbar-default .navbar-nav > .dropdown > a:focus .caret { + border-top-color: #333333; + border-bottom-color: #333333; +} +.navbar-default .navbar-nav > .open > a, +.navbar-default .navbar-nav > .open > a:hover, +.navbar-default .navbar-nav > .open > a:focus { + background-color: #e7e7e7; + color: #555555; +} +.navbar-default .navbar-nav > .open > a .caret, +.navbar-default .navbar-nav > .open > a:hover .caret, +.navbar-default .navbar-nav > .open > a:focus .caret { + border-top-color: #555555; + border-bottom-color: #555555; +} +.navbar-default .navbar-nav > .dropdown > a .caret { + border-top-color: #777777; + border-bottom-color: #777777; +} +@media (max-width: 767px) { + .navbar-default .navbar-nav .open .dropdown-menu > li > a { + color: #777777; + } + .navbar-default .navbar-nav .open .dropdown-menu > li > a:hover, + .navbar-default .navbar-nav .open .dropdown-menu > li > a:focus { + color: #333333; + background-color: transparent; + } + .navbar-default .navbar-nav .open .dropdown-menu > .active > a, + .navbar-default .navbar-nav .open .dropdown-menu > .active > a:hover, + .navbar-default .navbar-nav .open .dropdown-menu > .active > a:focus { + color: #555555; + background-color: #e7e7e7; + } + .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a, + .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:hover, + .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:focus { + color: #cccccc; + background-color: transparent; + } +} +.navbar-default .navbar-link { + color: #777777; +} +.navbar-default .navbar-link:hover { + color: #333333; +} +.navbar-inverse { + background-color: #74ab50; + border-color: #5c8840; +} +.navbar-inverse .navbar-brand { + color: #f9faf9; +} +.navbar-inverse .navbar-brand:hover, +.navbar-inverse .navbar-brand:focus { + color: #ffffff; + background-color: transparent; +} +.navbar-inverse .navbar-text { + color: #f9faf9; +} +.navbar-inverse .navbar-nav > li > a { + color: #f9faf9; +} +.navbar-inverse .navbar-nav > li > a:hover, +.navbar-inverse .navbar-nav > li > a:focus { + color: #ffffff; + background-color: transparent; +} +.navbar-inverse .navbar-nav > .active > a, +.navbar-inverse .navbar-nav > .active > a:hover, +.navbar-inverse .navbar-nav > .active > a:focus { + color: #ffffff; + background-color: #5c8840; +} +.navbar-inverse .navbar-nav > .disabled > a, +.navbar-inverse .navbar-nav > .disabled > a:hover, +.navbar-inverse .navbar-nav > .disabled > a:focus { + color: #444444; + background-color: transparent; +} +.navbar-inverse .navbar-toggle { + border-color: #333333; +} +.navbar-inverse .navbar-toggle:hover, +.navbar-inverse .navbar-toggle:focus { + background-color: #333333; +} +.navbar-inverse .navbar-toggle .icon-bar { + background-color: #ffffff; +} +.navbar-inverse .navbar-collapse, +.navbar-inverse .navbar-form { + border-color: #649345; +} +.navbar-inverse .navbar-nav > .open > a, +.navbar-inverse .navbar-nav > .open > a:hover, +.navbar-inverse .navbar-nav > .open > a:focus { + background-color: #5c8840; + color: #ffffff; +} +.navbar-inverse .navbar-nav > .dropdown > a:hover .caret { + border-top-color: #ffffff; + border-bottom-color: #ffffff; +} +.navbar-inverse .navbar-nav > .dropdown > a .caret { + border-top-color: #f9faf9; + border-bottom-color: #f9faf9; +} +.navbar-inverse .navbar-nav > .open > a .caret, +.navbar-inverse .navbar-nav > .open > a:hover .caret, +.navbar-inverse .navbar-nav > .open > a:focus .caret { + border-top-color: #ffffff; + border-bottom-color: #ffffff; +} +@media (max-width: 767px) { + .navbar-inverse .navbar-nav .open .dropdown-menu > .dropdown-header { + border-color: #5c8840; + } + .navbar-inverse .navbar-nav .open .dropdown-menu > li > a { + color: #f9faf9; + } + .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:hover, + .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:focus { + color: #ffffff; + background-color: transparent; + } + .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a, + .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:hover, + .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:focus { + color: #ffffff; + background-color: #5c8840; + } + .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a, + .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:hover, + .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:focus { + color: #444444; + background-color: transparent; + } +} +.navbar-inverse .navbar-link { + color: #f9faf9; +} +.navbar-inverse .navbar-link:hover { + color: #ffffff; +} +.breadcrumb { + padding: 8px 15px; + margin-bottom: 20px; + list-style: none; + background-color: #f5f5f5; + border-radius: 4px; +} +.breadcrumb > li { + display: inline-block; +} +.breadcrumb > li + li:before { + content: "/\00a0"; + padding: 0 5px; + color: #cccccc; +} +.breadcrumb > .active { + color: #f9faf9; +} +.pagination { + display: inline-block; + padding-left: 0; + margin: 20px 0; + border-radius: 4px; +} +.pagination > li { + display: inline; +} +.pagination > li > a, +.pagination > li > span { + position: relative; + float: left; + padding: 6px 12px; + line-height: 1.428571429; + text-decoration: none; + background-color: #ffffff; + border: 1px solid #dddddd; + margin-left: -1px; +} +.pagination > li:first-child > a, +.pagination > li:first-child > span { + margin-left: 0; + border-bottom-left-radius: 4px; + border-top-left-radius: 4px; +} +.pagination > li:last-child > a, +.pagination > li:last-child > span { + border-bottom-right-radius: 4px; + border-top-right-radius: 4px; +} +.pagination > li > a:hover, +.pagination > li > span:hover, +.pagination > li > a:focus, +.pagination > li > span:focus { + background-color: #bac9c2; +} +.pagination > .active > a, +.pagination > .active > span, +.pagination > .active > a:hover, +.pagination > .active > span:hover, +.pagination > .active > a:focus, +.pagination > .active > span:focus { + z-index: 2; + color: #ffffff; + background-color: #74ab50; + border-color: #74ab50; + cursor: default; +} +.pagination > .disabled > span, +.pagination > .disabled > a, +.pagination > .disabled > a:hover, +.pagination > .disabled > a:focus { + color: #f9faf9; + background-color: #ffffff; + border-color: #dddddd; + cursor: not-allowed; +} +.pagination-lg > li > a, +.pagination-lg > li > span { + padding: 10px 16px; + font-size: 18px; +} +.pagination-lg > li:first-child > a, +.pagination-lg > li:first-child > span { + border-bottom-left-radius: 6px; + border-top-left-radius: 6px; +} +.pagination-lg > li:last-child > a, +.pagination-lg > li:last-child > span { + border-bottom-right-radius: 6px; + border-top-right-radius: 6px; +} +.pagination-sm > li > a, +.pagination-sm > li > span { + padding: 5px 10px; + font-size: 12px; +} +.pagination-sm > li:first-child > a, +.pagination-sm > li:first-child > span { + border-bottom-left-radius: 3px; + border-top-left-radius: 3px; +} +.pagination-sm > li:last-child > a, +.pagination-sm > li:last-child > span { + border-bottom-right-radius: 3px; + border-top-right-radius: 3px; +} +.pager { + padding-left: 0; + margin: 20px 0; + list-style: none; + text-align: center; +} +.pager:before, +.pager:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.pager:after { + clear: both; +} +.pager:before, +.pager:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.pager:after { + clear: both; +} +.pager li { + display: inline; +} +.pager li > a, +.pager li > span { + display: inline-block; + padding: 5px 14px; + background-color: #ffffff; + border: 1px solid #dddddd; + border-radius: 15px; +} +.pager li > a:hover, +.pager li > a:focus { + text-decoration: none; + background-color: #bac9c2; +} +.pager .next > a, +.pager .next > span { + float: right; +} +.pager .previous > a, +.pager .previous > span { + float: left; +} +.pager .disabled > a, +.pager .disabled > a:hover, +.pager .disabled > a:focus, +.pager .disabled > span { + color: #f9faf9; + background-color: #ffffff; + cursor: not-allowed; +} +.label { + display: inline; + padding: .2em .6em .3em; + font-size: 75%; + font-weight: bold; + line-height: 1; + color: #ffffff; + text-align: center; + white-space: nowrap; + vertical-align: baseline; + border-radius: .25em; +} +.label[href]:hover, +.label[href]:focus { + color: #ffffff; + text-decoration: none; + cursor: pointer; +} +.label:empty { + display: none; +} + +.label-default[href]:hover, +.label-default[href]:focus { + background-color: #dde3dd; +} +.label-primary { + background-color: #74ab50; +} +.label-primary[href]:hover, +.label-primary[href]:focus { + background-color: #5c8840; +} +.label-success { + background-color: #5cb85c; +} +.label-success[href]:hover, +.label-success[href]:focus { + background-color: #449d44; +} +.label-info { + background-color: #5bc0de; +} +.label-info[href]:hover, +.label-info[href]:focus { + background-color: #31b0d5; +} +.label-warning { + background-color: #f0ad4e; +} +.label-warning[href]:hover, +.label-warning[href]:focus { + background-color: #ec971f; +} +.label-danger { + background-color: #d9534f; +} +.label-danger[href]:hover, +.label-danger[href]:focus { + background-color: #c9302c; +} +.badge { + display: inline-block; + min-width: 10px; + padding: 3px 7px; + font-size: 12px; + font-weight: bold; + color: #ffffff; + line-height: 1; + vertical-align: baseline; + white-space: nowrap; + text-align: center; + background-color: #f9faf9; + border-radius: 10px; +} +.badge:empty { + display: none; +} +a.badge:hover, +a.badge:focus { + color: #ffffff; + text-decoration: none; + cursor: pointer; +} +.btn .badge { + position: relative; + top: -1px; +} +a.list-group-item.active > .badge, +.nav-pills > .active > a > .badge { + color: #74ab50; + background-color: #ffffff; +} +.nav-pills > li > a > .badge { + margin-left: 3px; +} +.jumbotron { + padding: 30px; + margin-bottom: 30px; + font-size: 21px; + font-weight: 200; + line-height: 2.1428571435; + color: inherit; + background-color: #bac9c2; +} +.jumbotron h1 { + line-height: 1; + color: inherit; +} +.jumbotron p { + line-height: 1.4; +} +.container .jumbotron { + border-radius: 6px; +} +@media screen and (min-width: 768px) { + .jumbotron { + padding-top: 48px; + padding-bottom: 48px; + } + .container .jumbotron { + padding-left: 60px; + padding-right: 60px; + } + .jumbotron h1 { + font-size: 63px; + } +} +.thumbnail { + padding: 4px; + line-height: 1.428571429; + background-color: #ffffff; + border: 1px solid #dddddd; + border-radius: 4px; + -webkit-transition: all 0.2s ease-in-out; + transition: all 0.2s ease-in-out; + display: inline-block; + max-width: 100%; + height: auto; + display: block; +} +.thumbnail > img { + display: block; + max-width: 100%; + height: auto; +} +a.thumbnail:hover, +a.thumbnail:focus { + border-color: #74ab50; +} +.thumbnail > img { + margin-left: auto; + margin-right: auto; +} +.thumbnail .caption { + padding: 9px; + color: #77777a; +} +.alert { + padding: 15px; + margin-bottom: 20px; + border: 1px solid transparent; + border-radius: 4px; +} +.alert h4 { + margin-top: 0; + color: inherit; +} +.alert .alert-link { + font-weight: bold; +} +.alert > p, +.alert > ul { + margin-bottom: 0; +} +.alert > p + p { + margin-top: 5px; +} +.alert-dismissable { + padding-right: 35px; +} +.alert-dismissable .close { + position: relative; + top: -2px; + right: -21px; + color: inherit; +} +.alert-success { + background-color: #dff0d8; + border-color: #d6e9c6; + color: #468847; +} +.alert-success hr { + border-top-color: #c9e2b3; +} +.alert-success .alert-link { + color: #356635; +} +.alert-info { + background-color: #d9edf7; + border-color: #bce8f1; + color: #3a87ad; +} +.alert-info hr { + border-top-color: #a6e1ec; +} +.alert-info .alert-link { + color: #2d6987; +} +.alert-warning { + background-color: #fcf8e3; + border-color: #fbeed5; + color: #c09853; +} +.alert-warning hr { + border-top-color: #f8e5be; +} +.alert-warning .alert-link { + color: #a47e3c; +} +.alert-danger { + background-color: #f2dede; + border-color: #eed3d7; + color: #b94a48; +} +.alert-danger hr { + border-top-color: #e6c1c7; +} +.alert-danger .alert-link { + color: #953b39; +} +@-webkit-keyframes progress-bar-stripes { + from { + background-position: 40px 0; + } + to { + background-position: 0 0; + } +} +@-moz-keyframes progress-bar-stripes { + from { + background-position: 40px 0; + } + to { + background-position: 0 0; + } +} +@-o-keyframes progress-bar-stripes { + from { + background-position: 0 0; + } + to { + background-position: 40px 0; + } +} +@keyframes progress-bar-stripes { + from { + background-position: 40px 0; + } + to { + background-position: 0 0; + } +} +.progress { + overflow: hidden; + height: 20px; + margin-bottom: 20px; + background-color: #f5f5f5; + border-radius: 4px; + -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1); + box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1); +} +.progress-bar { + float: left; + width: 0%; + height: 100%; + font-size: 12px; + color: #ffffff; + text-align: center; + background-color: #74ab50; + -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15); + box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15); + -webkit-transition: width 0.6s ease; + transition: width 0.6s ease; +} +.progress-striped .progress-bar { + background-image: -webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent)); + background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: -moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-size: 40px 40px; +} +.progress.active .progress-bar { + -webkit-animation: progress-bar-stripes 2s linear infinite; + -moz-animation: progress-bar-stripes 2s linear infinite; + -ms-animation: progress-bar-stripes 2s linear infinite; + -o-animation: progress-bar-stripes 2s linear infinite; + animation: progress-bar-stripes 2s linear infinite; +} +.progress-bar-success { + background-color: #5cb85c; +} +.progress-striped .progress-bar-success { + background-image: -webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent)); + background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: -moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); +} +.progress-bar-info { + background-color: #5bc0de; +} +.progress-striped .progress-bar-info { + background-image: -webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent)); + background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: -moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); +} +.progress-bar-warning { + background-color: #f0ad4e; +} +.progress-striped .progress-bar-warning { + background-image: -webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent)); + background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: -moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); +} +.progress-bar-danger { + background-color: #d9534f; +} +.progress-striped .progress-bar-danger { + background-image: -webkit-gradient(linear, 0 100%, 100% 0, color-stop(0.25, rgba(255, 255, 255, 0.15)), color-stop(0.25, transparent), color-stop(0.5, transparent), color-stop(0.5, rgba(255, 255, 255, 0.15)), color-stop(0.75, rgba(255, 255, 255, 0.15)), color-stop(0.75, transparent), to(transparent)); + background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: -moz-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); + background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent); +} +.media, +.media-body { + overflow: hidden; + zoom: 1; +} +.media, +.media .media { + margin-top: 15px; +} +.media:first-child { + margin-top: 0; +} +.media-object { + display: block; +} +.media-heading { + margin: 0 0 5px; +} +.media > .pull-left { + margin-right: 10px; +} +.media > .pull-right { + margin-left: 10px; +} +.media-list { + padding-left: 0; + list-style: none; +} +.list-group { + margin-bottom: 20px; + padding-left: 0; +} +.list-group-item { + position: relative; + display: block; + padding: 10px 15px; + margin-bottom: -1px; + background-color: #ffffff; + border: 1px solid #dddddd; +} +.list-group-item:first-child { + border-top-right-radius: 4px; + border-top-left-radius: 4px; +} +.list-group-item:last-child { + margin-bottom: 0; + border-bottom-right-radius: 4px; + border-bottom-left-radius: 4px; +} +.list-group-item > .badge { + float: right; +} +.list-group-item > .badge + .badge { + margin-right: 5px; +} +a.list-group-item { + color: #555555; +} +a.list-group-item .list-group-item-heading { + color: #333333; +} +a.list-group-item:hover, +a.list-group-item:focus { + text-decoration: none; + background-color: #f5f5f5; +} +.list-group-item.active, +.list-group-item.active:hover, +.list-group-item.active:focus { + z-index: 2; + color: #ffffff; + background-color: #74ab50; + border-color: #74ab50; +} +.list-group-item.active .list-group-item-heading, +.list-group-item.active:hover .list-group-item-heading, +.list-group-item.active:focus .list-group-item-heading { + color: inherit; +} +.list-group-item.active .list-group-item-text, +.list-group-item.active:hover .list-group-item-text, +.list-group-item.active:focus .list-group-item-text { + color: #e1edda; +} +.list-group-item-heading { + margin-top: 0; + margin-bottom: 5px; +} +.list-group-item-text { + margin-bottom: 0; + line-height: 1.3; +} +.panel { + margin-bottom: 20px; + background-color: #ffffff; + border: 1px solid transparent; + border-radius: 4px; + -webkit-box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05); + box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05); +} +.panel-body { + padding: 15px; +} +.panel-body:before, +.panel-body:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.panel-body:after { + clear: both; +} +.panel-body:before, +.panel-body:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.panel-body:after { + clear: both; +} +.panel > .list-group { + margin-bottom: 0; +} +.panel > .list-group .list-group-item { + border-width: 1px 0; +} +.panel > .list-group .list-group-item:first-child { + border-top-right-radius: 0; + border-top-left-radius: 0; +} +.panel > .list-group .list-group-item:last-child { + border-bottom: 0; +} +.panel-heading + .list-group .list-group-item:first-child { + border-top-width: 0; +} +.panel > .table { + margin-bottom: 0; +} +.panel > .panel-body + .table { + border-top: 1px solid #77777a; +} +.panel-heading { + padding: 10px 15px; + border-bottom: 1px solid transparent; + border-top-right-radius: 3px; + border-top-left-radius: 3px; +} +.panel-title { + margin-top: 0; + margin-bottom: 0; + font-size: 16px; +} +.panel-title > a { + color: inherit; +} +.panel-footer { + padding: 10px 15px; + background-color: #f5f5f5; + border-top: 1px solid #dddddd; + border-bottom-right-radius: 3px; + border-bottom-left-radius: 3px; +} +.panel-group .panel { + margin-bottom: 0; + border-radius: 4px; + overflow: hidden; +} +.panel-group .panel + .panel { + margin-top: 5px; +} +.panel-group .panel-heading { + border-bottom: 0; +} +.panel-group .panel-heading + .panel-collapse .panel-body { + border-top: 1px solid #dddddd; +} +.panel-group .panel-footer { + border-top: 0; +} +.panel-group .panel-footer + .panel-collapse .panel-body { + border-bottom: 1px solid #dddddd; +} +.panel-default { + border-color: #dddddd; +} +.panel-default > .panel-heading { + color: #77777a; + background-color: #f5f5f5; + border-color: #dddddd; +} +.panel-default > .panel-heading + .panel-collapse .panel-body { + border-top-color: #dddddd; +} +.panel-default > .panel-footer + .panel-collapse .panel-body { + border-bottom-color: #dddddd; +} +.panel-primary { + border-color: #74ab50; +} +.panel-primary > .panel-heading { + color: #ffffff; + background-color: #74ab50; + border-color: #74ab50; +} +.panel-primary > .panel-heading + .panel-collapse .panel-body { + border-top-color: #74ab50; +} +.panel-primary > .panel-footer + .panel-collapse .panel-body { + border-bottom-color: #74ab50; +} +.panel-success { + border-color: #d6e9c6; +} +.panel-success > .panel-heading { + color: #468847; + background-color: #dff0d8; + border-color: #d6e9c6; +} +.panel-success > .panel-heading + .panel-collapse .panel-body { + border-top-color: #d6e9c6; +} +.panel-success > .panel-footer + .panel-collapse .panel-body { + border-bottom-color: #d6e9c6; +} +.panel-warning { + border-color: #fbeed5; +} +.panel-warning > .panel-heading { + color: #c09853; + background-color: #fcf8e3; + border-color: #fbeed5; +} +.panel-warning > .panel-heading + .panel-collapse .panel-body { + border-top-color: #fbeed5; +} +.panel-warning > .panel-footer + .panel-collapse .panel-body { + border-bottom-color: #fbeed5; +} +.panel-danger { + border-color: #eed3d7; +} +.panel-danger > .panel-heading { + color: #b94a48; + background-color: #f2dede; + border-color: #eed3d7; +} +.panel-danger > .panel-heading + .panel-collapse .panel-body { + border-top-color: #eed3d7; +} +.panel-danger > .panel-footer + .panel-collapse .panel-body { + border-bottom-color: #eed3d7; +} +.panel-info { + border-color: #bce8f1; +} +.panel-info > .panel-heading { + color: #3a87ad; + background-color: #d9edf7; + border-color: #bce8f1; +} +.panel-info > .panel-heading + .panel-collapse .panel-body { + border-top-color: #bce8f1; +} +.panel-info > .panel-footer + .panel-collapse .panel-body { + border-bottom-color: #bce8f1; +} +.well { + min-height: 20px; + padding: 19px; + margin-bottom: 20px; + background-color: #f5f5f5; + border: 1px solid #e3e3e3; + border-radius: 4px; + -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05); + box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05); +} +.well blockquote { + border-color: #ddd; + border-color: rgba(0, 0, 0, 0.15); +} +.well-lg { + padding: 24px; + border-radius: 6px; +} +.well-sm { + padding: 9px; + border-radius: 3px; +} +.close { + float: right; + font-size: 21px; + font-weight: bold; + line-height: 1; + color: #000000; + text-shadow: 0 1px 0 #ffffff; + opacity: 0.2; + filter: alpha(opacity=20); +} +.close:hover, +.close:focus { + color: #000000; + text-decoration: none; + cursor: pointer; + opacity: 0.5; + filter: alpha(opacity=50); +} +button.close { + padding: 0; + cursor: pointer; + background: transparent; + border: 0; + -webkit-appearance: none; +} +.modal-open { + overflow: hidden; +} +body.modal-open, +.modal-open .navbar-fixed-top, +.modal-open .navbar-fixed-bottom { + margin-right: 15px; +} +.modal { + display: none; + overflow: auto; + overflow-y: scroll; + position: fixed; + top: 0; + right: 0; + bottom: 0; + left: 0; + z-index: 1040; +} +.modal.fade .modal-dialog { + -webkit-transform: translate(0, -25%); + -ms-transform: translate(0, -25%); + transform: translate(0, -25%); + -webkit-transition: -webkit-transform 0.3s ease-out; + -moz-transition: -moz-transform 0.3s ease-out; + -o-transition: -o-transform 0.3s ease-out; + transition: transform 0.3s ease-out; +} +.modal.in .modal-dialog { + -webkit-transform: translate(0, 0); + -ms-transform: translate(0, 0); + transform: translate(0, 0); +} +.modal-dialog { + margin-left: auto; + margin-right: auto; + width: auto; + padding: 10px; + z-index: 1050; +} +.modal-content { + position: relative; + background-color: #ffffff; + border: 1px solid #999999; + border: 1px solid rgba(0, 0, 0, 0.2); + border-radius: 6px; + -webkit-box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5); + box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5); + background-clip: padding-box; + outline: none; +} +.modal-backdrop { + position: fixed; + top: 0; + right: 0; + bottom: 0; + left: 0; + z-index: 1030; + background-color: #000000; +} +.modal-backdrop.fade { + opacity: 0; + filter: alpha(opacity=0); +} +.modal-backdrop.in { + opacity: 0.5; + filter: alpha(opacity=50); +} +.modal-header { + padding: 15px; + border-bottom: 1px solid #e5e5e5; + min-height: 16.428571429px; +} +.modal-header .close { + margin-top: -2px; +} +.modal-title { + margin: 0; + line-height: 1.428571429; +} +.modal-body { + position: relative; + padding: 20px; +} +.modal-footer { + margin-top: 15px; + padding: 19px 20px 20px; + text-align: right; + border-top: 1px solid #e5e5e5; +} +.modal-footer:before, +.modal-footer:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.modal-footer:after { + clear: both; +} +.modal-footer:before, +.modal-footer:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.modal-footer:after { + clear: both; +} +.modal-footer .btn + .btn { + margin-left: 5px; + margin-bottom: 0; +} +.modal-footer .btn-group .btn + .btn { + margin-left: -1px; +} +.modal-footer .btn-block + .btn-block { + margin-left: 0; +} +@media screen and (min-width: 768px) { + .modal-dialog { + left: 50%; + right: auto; + width: 600px; + padding-top: 30px; + padding-bottom: 30px; + } + .modal-content { + -webkit-box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5); + box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5); + } +} +.tooltip { + position: absolute; + z-index: 1030; + display: block; + visibility: visible; + font-size: 12px; + line-height: 1.4; + opacity: 0; + filter: alpha(opacity=0); +} +.tooltip.in { + opacity: 0.9; + filter: alpha(opacity=90); +} +.tooltip.top { + margin-top: -3px; + padding: 5px 0; +} +.tooltip.right { + margin-left: 3px; + padding: 0 5px; +} +.tooltip.bottom { + margin-top: 3px; + padding: 5px 0; +} +.tooltip.left { + margin-left: -3px; + padding: 0 5px; +} +.tooltip-inner { + max-width: 200px; + padding: 3px 8px; + color: #ffffff; + text-align: center; + text-decoration: none; + background-color: #000000; + border-radius: 4px; +} +.tooltip-arrow { + position: absolute; + width: 0; + height: 0; + border-color: transparent; + border-style: solid; +} +.tooltip.top .tooltip-arrow { + bottom: 0; + left: 50%; + margin-left: -5px; + border-width: 5px 5px 0; + border-top-color: #000000; +} +.tooltip.top-left .tooltip-arrow { + bottom: 0; + left: 5px; + border-width: 5px 5px 0; + border-top-color: #000000; +} +.tooltip.top-right .tooltip-arrow { + bottom: 0; + right: 5px; + border-width: 5px 5px 0; + border-top-color: #000000; +} +.tooltip.right .tooltip-arrow { + top: 50%; + left: 0; + margin-top: -5px; + border-width: 5px 5px 5px 0; + border-right-color: #000000; +} +.tooltip.left .tooltip-arrow { + top: 50%; + right: 0; + margin-top: -5px; + border-width: 5px 0 5px 5px; + border-left-color: #000000; +} +.tooltip.bottom .tooltip-arrow { + top: 0; + left: 50%; + margin-left: -5px; + border-width: 0 5px 5px; + border-bottom-color: #000000; +} +.tooltip.bottom-left .tooltip-arrow { + top: 0; + left: 5px; + border-width: 0 5px 5px; + border-bottom-color: #000000; +} +.tooltip.bottom-right .tooltip-arrow { + top: 0; + right: 5px; + border-width: 0 5px 5px; + border-bottom-color: #000000; +} +.popover { + position: absolute; + top: 0; + left: 0; + z-index: 1010; + display: none; + max-width: 276px; + padding: 1px; + text-align: left; + background-color: #ffffff; + background-clip: padding-box; + border: 1px solid #cccccc; + border: 1px solid rgba(0, 0, 0, 0.2); + border-radius: 6px; + -webkit-box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2); + box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2); + white-space: normal; +} +.popover.top { + margin-top: -10px; +} +.popover.right { + margin-left: 10px; +} +.popover.bottom { + margin-top: 10px; +} +.popover.left { + margin-left: -10px; +} +.popover-title { + margin: 0; + padding: 8px 14px; + font-size: 14px; + font-weight: normal; + line-height: 18px; + background-color: #f7f7f7; + border-bottom: 1px solid #ebebeb; + border-radius: 5px 5px 0 0; +} +.popover-content { + padding: 9px 14px; +} +.popover .arrow, +.popover .arrow:after { + position: absolute; + display: block; + width: 0; + height: 0; + border-color: transparent; + border-style: solid; +} +.popover .arrow { + border-width: 11px; +} +.popover .arrow:after { + border-width: 10px; + content: ""; +} +.popover.top .arrow { + left: 50%; + margin-left: -11px; + border-bottom-width: 0; + border-top-color: #999999; + border-top-color: rgba(0, 0, 0, 0.25); + bottom: -11px; +} +.popover.top .arrow:after { + content: " "; + bottom: 1px; + margin-left: -10px; + border-bottom-width: 0; + border-top-color: #ffffff; +} +.popover.right .arrow { + top: 50%; + left: -11px; + margin-top: -11px; + border-left-width: 0; + border-right-color: #999999; + border-right-color: rgba(0, 0, 0, 0.25); +} +.popover.right .arrow:after { + content: " "; + left: 1px; + bottom: -10px; + border-left-width: 0; + border-right-color: #ffffff; +} +.popover.bottom .arrow { + left: 50%; + margin-left: -11px; + border-top-width: 0; + border-bottom-color: #999999; + border-bottom-color: rgba(0, 0, 0, 0.25); + top: -11px; +} +.popover.bottom .arrow:after { + content: " "; + top: 1px; + margin-left: -10px; + border-top-width: 0; + border-bottom-color: #ffffff; +} +.popover.left .arrow { + top: 50%; + right: -11px; + margin-top: -11px; + border-right-width: 0; + border-left-color: #999999; + border-left-color: rgba(0, 0, 0, 0.25); +} +.popover.left .arrow:after { + content: " "; + right: 1px; + border-right-width: 0; + border-left-color: #ffffff; + bottom: -10px; +} +.carousel { + position: relative; +} +.carousel-inner { + position: relative; + overflow: hidden; + width: 100%; +} +.carousel-inner > .item { + display: none; + position: relative; + -webkit-transition: 0.6s ease-in-out left; + transition: 0.6s ease-in-out left; +} +.carousel-inner > .item > img, +.carousel-inner > .item > a > img { + display: block; + max-width: 100%; + height: auto; + line-height: 1; +} +.carousel-inner > .active, +.carousel-inner > .next, +.carousel-inner > .prev { + display: block; +} +.carousel-inner > .active { + left: 0; +} +.carousel-inner > .next, +.carousel-inner > .prev { + position: absolute; + top: 0; + width: 100%; +} +.carousel-inner > .next { + left: 100%; +} +.carousel-inner > .prev { + left: -100%; +} +.carousel-inner > .next.left, +.carousel-inner > .prev.right { + left: 0; +} +.carousel-inner > .active.left { + left: -100%; +} +.carousel-inner > .active.right { + left: 100%; +} +.carousel-control { + position: absolute; + top: 0; + left: 0; + bottom: 0; + width: 15%; + opacity: 0.5; + filter: alpha(opacity=50); + font-size: 20px; + color: #ffffff; + text-align: center; + text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6); +} +.carousel-control.left { + background-image: -webkit-gradient(linear, 0% top, 100% top, from(rgba(0, 0, 0, 0.5)), to(rgba(0, 0, 0, 0.0001))); + background-image: -webkit-linear-gradient(left, color-stop(rgba(0, 0, 0, 0.5) 0%), color-stop(rgba(0, 0, 0, 0.0001) 100%)); + background-image: -moz-linear-gradient(left, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%); + background-image: linear-gradient(to right, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%); + background-repeat: repeat-x; + filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1); +} +.carousel-control.right { + left: auto; + right: 0; + background-image: -webkit-gradient(linear, 0% top, 100% top, from(rgba(0, 0, 0, 0.0001)), to(rgba(0, 0, 0, 0.5))); + background-image: -webkit-linear-gradient(left, color-stop(rgba(0, 0, 0, 0.0001) 0%), color-stop(rgba(0, 0, 0, 0.5) 100%)); + background-image: -moz-linear-gradient(left, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%); + background-image: linear-gradient(to right, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%); + background-repeat: repeat-x; + filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1); +} +.carousel-control:hover, +.carousel-control:focus { + color: #ffffff; + text-decoration: none; + opacity: 0.9; + filter: alpha(opacity=90); +} +.carousel-control .icon-prev, +.carousel-control .icon-next, +.carousel-control .glyphicon-chevron-left, +.carousel-control .glyphicon-chevron-right { + position: absolute; + top: 50%; + left: 50%; + z-index: 5; + display: inline-block; +} +.carousel-control .icon-prev, +.carousel-control .icon-next { + width: 20px; + height: 20px; + margin-top: -10px; + margin-left: -10px; + font-family: serif; +} +.carousel-control .icon-prev:before { + content: '\2039'; +} +.carousel-control .icon-next:before { + content: '\203a'; +} +.carousel-indicators { + position: absolute; + bottom: 10px; + left: 50%; + z-index: 15; + width: 60%; + margin-left: -30%; + padding-left: 0; + list-style: none; + text-align: center; +} +.carousel-indicators li { + display: inline-block; + width: 10px; + height: 10px; + margin: 1px; + text-indent: -999px; + border: 1px solid #ffffff; + border-radius: 10px; + cursor: pointer; +} +.carousel-indicators .active { + margin: 0; + width: 12px; + height: 12px; + background-color: #ffffff; +} +.carousel-caption { + position: absolute; + left: 15%; + right: 15%; + bottom: 20px; + z-index: 10; + padding-top: 20px; + padding-bottom: 20px; + color: #ffffff; + text-align: center; + text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6); +} +.carousel-caption .btn { + text-shadow: none; +} +@media screen and (min-width: 768px) { + .carousel-control .icon-prev, + .carousel-control .icon-next { + width: 30px; + height: 30px; + margin-top: -15px; + margin-left: -15px; + font-size: 30px; + } + .carousel-caption { + left: 20%; + right: 20%; + padding-bottom: 30px; + } + .carousel-indicators { + bottom: 20px; + } +} +.clearfix:before, +.clearfix:after { + content: " "; + /* 1 */ + + display: table; + /* 2 */ + +} +.clearfix:after { + clear: both; +} +.pull-right { + float: right !important; +} +.pull-left { + float: left !important; +} +.hide { + display: none !important; +} +.show { + display: block !important; +} +.invisible { + visibility: hidden; +} +.text-hide { + font: 0/0 a; + color: transparent; + text-shadow: none; + background-color: transparent; + border: 0; +} +.affix { + position: fixed; +} +@-ms-viewport { + width: device-width; +} +@media screen and (max-width: 400px) { + @-ms-viewport { + width: 320px; + } +} +.hidden { + display: none !important; + visibility: hidden !important; +} +.visible-xs { + display: none !important; +} +tr.visible-xs { + display: none !important; +} +th.visible-xs, +td.visible-xs { + display: none !important; +} +@media (max-width: 767px) { + .visible-xs { + display: block !important; + } + tr.visible-xs { + display: table-row !important; + } + th.visible-xs, + td.visible-xs { + display: table-cell !important; + } +} +@media (min-width: 768px) and (max-width: 991px) { + .visible-xs.visible-sm { + display: block !important; + } + tr.visible-xs.visible-sm { + display: table-row !important; + } + th.visible-xs.visible-sm, + td.visible-xs.visible-sm { + display: table-cell !important; + } +} +@media (min-width: 992px) and (max-width: 1199px) { + .visible-xs.visible-md { + display: block !important; + } + tr.visible-xs.visible-md { + display: table-row !important; + } + th.visible-xs.visible-md, + td.visible-xs.visible-md { + display: table-cell !important; + } +} +@media (min-width: 1200px) { + .visible-xs.visible-lg { + display: block !important; + } + tr.visible-xs.visible-lg { + display: table-row !important; + } + th.visible-xs.visible-lg, + td.visible-xs.visible-lg { + display: table-cell !important; + } +} +.visible-sm { + display: none !important; +} +tr.visible-sm { + display: none !important; +} +th.visible-sm, +td.visible-sm { + display: none !important; +} +@media (max-width: 767px) { + .visible-sm.visible-xs { + display: block !important; + } + tr.visible-sm.visible-xs { + display: table-row !important; + } + th.visible-sm.visible-xs, + td.visible-sm.visible-xs { + display: table-cell !important; + } +} +@media (min-width: 768px) and (max-width: 991px) { + .visible-sm { + display: block !important; + } + tr.visible-sm { + display: table-row !important; + } + th.visible-sm, + td.visible-sm { + display: table-cell !important; + } +} +@media (min-width: 992px) and (max-width: 1199px) { + .visible-sm.visible-md { + display: block !important; + } + tr.visible-sm.visible-md { + display: table-row !important; + } + th.visible-sm.visible-md, + td.visible-sm.visible-md { + display: table-cell !important; + } +} +@media (min-width: 1200px) { + .visible-sm.visible-lg { + display: block !important; + } + tr.visible-sm.visible-lg { + display: table-row !important; + } + th.visible-sm.visible-lg, + td.visible-sm.visible-lg { + display: table-cell !important; + } +} +.visible-md { + display: none !important; +} +tr.visible-md { + display: none !important; +} +th.visible-md, +td.visible-md { + display: none !important; +} +@media (max-width: 767px) { + .visible-md.visible-xs { + display: block !important; + } + tr.visible-md.visible-xs { + display: table-row !important; + } + th.visible-md.visible-xs, + td.visible-md.visible-xs { + display: table-cell !important; + } +} +@media (min-width: 768px) and (max-width: 991px) { + .visible-md.visible-sm { + display: block !important; + } + tr.visible-md.visible-sm { + display: table-row !important; + } + th.visible-md.visible-sm, + td.visible-md.visible-sm { + display: table-cell !important; + } +} +@media (min-width: 992px) and (max-width: 1199px) { + .visible-md { + display: block !important; + } + tr.visible-md { + display: table-row !important; + } + th.visible-md, + td.visible-md { + display: table-cell !important; + } +} +@media (min-width: 1200px) { + .visible-md.visible-lg { + display: block !important; + } + tr.visible-md.visible-lg { + display: table-row !important; + } + th.visible-md.visible-lg, + td.visible-md.visible-lg { + display: table-cell !important; + } +} +.visible-lg { + display: none !important; +} +tr.visible-lg { + display: none !important; +} +th.visible-lg, +td.visible-lg { + display: none !important; +} +@media (max-width: 767px) { + .visible-lg.visible-xs { + display: block !important; + } + tr.visible-lg.visible-xs { + display: table-row !important; + } + th.visible-lg.visible-xs, + td.visible-lg.visible-xs { + display: table-cell !important; + } +} +@media (min-width: 768px) and (max-width: 991px) { + .visible-lg.visible-sm { + display: block !important; + } + tr.visible-lg.visible-sm { + display: table-row !important; + } + th.visible-lg.visible-sm, + td.visible-lg.visible-sm { + display: table-cell !important; + } +} +@media (min-width: 992px) and (max-width: 1199px) { + .visible-lg.visible-md { + display: block !important; + } + tr.visible-lg.visible-md { + display: table-row !important; + } + th.visible-lg.visible-md, + td.visible-lg.visible-md { + display: table-cell !important; + } +} +@media (min-width: 1200px) { + .visible-lg { + display: block !important; + } + tr.visible-lg { + display: table-row !important; + } + th.visible-lg, + td.visible-lg { + display: table-cell !important; + } +} +.hidden-xs { + display: block !important; +} +tr.hidden-xs { + display: table-row !important; +} +th.hidden-xs, +td.hidden-xs { + display: table-cell !important; +} +@media (max-width: 767px) { + .hidden-xs { + display: none !important; + } + tr.hidden-xs { + display: none !important; + } + th.hidden-xs, + td.hidden-xs { + display: none !important; + } +} +@media (min-width: 768px) and (max-width: 991px) { + .hidden-xs.hidden-sm { + display: none !important; + } + tr.hidden-xs.hidden-sm { + display: none !important; + } + th.hidden-xs.hidden-sm, + td.hidden-xs.hidden-sm { + display: none !important; + } +} +@media (min-width: 992px) and (max-width: 1199px) { + .hidden-xs.hidden-md { + display: none !important; + } + tr.hidden-xs.hidden-md { + display: none !important; + } + th.hidden-xs.hidden-md, + td.hidden-xs.hidden-md { + display: none !important; + } +} +@media (min-width: 1200px) { + .hidden-xs.hidden-lg { + display: none !important; + } + tr.hidden-xs.hidden-lg { + display: none !important; + } + th.hidden-xs.hidden-lg, + td.hidden-xs.hidden-lg { + display: none !important; + } +} +.hidden-sm { + display: block !important; +} +tr.hidden-sm { + display: table-row !important; +} +th.hidden-sm, +td.hidden-sm { + display: table-cell !important; +} +@media (max-width: 767px) { + .hidden-sm.hidden-xs { + display: none !important; + } + tr.hidden-sm.hidden-xs { + display: none !important; + } + th.hidden-sm.hidden-xs, + td.hidden-sm.hidden-xs { + display: none !important; + } +} +@media (min-width: 768px) and (max-width: 991px) { + .hidden-sm { + display: none !important; + } + tr.hidden-sm { + display: none !important; + } + th.hidden-sm, + td.hidden-sm { + display: none !important; + } +} +@media (min-width: 992px) and (max-width: 1199px) { + .hidden-sm.hidden-md { + display: none !important; + } + tr.hidden-sm.hidden-md { + display: none !important; + } + th.hidden-sm.hidden-md, + td.hidden-sm.hidden-md { + display: none !important; + } +} +@media (min-width: 1200px) { + .hidden-sm.hidden-lg { + display: none !important; + } + tr.hidden-sm.hidden-lg { + display: none !important; + } + th.hidden-sm.hidden-lg, + td.hidden-sm.hidden-lg { + display: none !important; + } +} +.hidden-md { + display: block !important; +} +tr.hidden-md { + display: table-row !important; +} +th.hidden-md, +td.hidden-md { + display: table-cell !important; +} +@media (max-width: 767px) { + .hidden-md.hidden-xs { + display: none !important; + } + tr.hidden-md.hidden-xs { + display: none !important; + } + th.hidden-md.hidden-xs, + td.hidden-md.hidden-xs { + display: none !important; + } +} +@media (min-width: 768px) and (max-width: 991px) { + .hidden-md.hidden-sm { + display: none !important; + } + tr.hidden-md.hidden-sm { + display: none !important; + } + th.hidden-md.hidden-sm, + td.hidden-md.hidden-sm { + display: none !important; + } +} +@media (min-width: 992px) and (max-width: 1199px) { + .hidden-md { + display: none !important; + } + tr.hidden-md { + display: none !important; + } + th.hidden-md, + td.hidden-md { + display: none !important; + } +} +@media (min-width: 1200px) { + .hidden-md.hidden-lg { + display: none !important; + } + tr.hidden-md.hidden-lg { + display: none !important; + } + th.hidden-md.hidden-lg, + td.hidden-md.hidden-lg { + display: none !important; + } +} +.hidden-lg { + display: block !important; +} +tr.hidden-lg { + display: table-row !important; +} +th.hidden-lg, +td.hidden-lg { + display: table-cell !important; +} +@media (max-width: 767px) { + .hidden-lg.hidden-xs { + display: none !important; + } + tr.hidden-lg.hidden-xs { + display: none !important; + } + th.hidden-lg.hidden-xs, + td.hidden-lg.hidden-xs { + display: none !important; + } +} +@media (min-width: 768px) and (max-width: 991px) { + .hidden-lg.hidden-sm { + display: none !important; + } + tr.hidden-lg.hidden-sm { + display: none !important; + } + th.hidden-lg.hidden-sm, + td.hidden-lg.hidden-sm { + display: none !important; + } +} +@media (min-width: 992px) and (max-width: 1199px) { + .hidden-lg.hidden-md { + display: none !important; + } + tr.hidden-lg.hidden-md { + display: none !important; + } + th.hidden-lg.hidden-md, + td.hidden-lg.hidden-md { + display: none !important; + } +} +@media (min-width: 1200px) { + .hidden-lg { + display: none !important; + } + tr.hidden-lg { + display: none !important; + } + th.hidden-lg, + td.hidden-lg { + display: none !important; + } +} +.visible-print { + display: none !important; +} +tr.visible-print { + display: none !important; +} +th.visible-print, +td.visible-print { + display: none !important; +} +@media print { + .visible-print { + display: block !important; + } + tr.visible-print { + display: table-row !important; + } + th.visible-print, + td.visible-print { + display: table-cell !important; + } + .hidden-print { + display: none !important; + } + tr.hidden-print { + display: none !important; + } + th.hidden-print, + td.hidden-print { + display: none !important; + } +} diff --git a/css/modern-business.css b/css/modern-business.css new file mode 100755 index 0000000000..58dc4a2d60 --- /dev/null +++ b/css/modern-business.css @@ -0,0 +1,93 @@ +/*! + * Start Bootstrap - Modern Business HTML Template (http://startbootstrap.com) + * Code licensed under the Apache License v2.0. + * For details, see http://www.apache.org/licenses/LICENSE-2.0. + */ + +/* Global Styles */ + +html, +body { + height: 100%; +} + +body { + padding-top: 50px; /* Required padding for .navbar-fixed-top. Remove if using .navbar-static-top. Change if height of navigation changes. */ +} + +.img-portfolio { + margin-bottom: 30px; +} + +.img-hover:hover { + opacity: 0.8; +} + +/* Home Page Carousel */ + +header.carousel { + height: 50%; +} + +header.carousel .item, +header.carousel .item.active, +header.carousel .carousel-inner { + height: 100%; +} + +header.carousel .fill { + width: 100%; + height: 100%; + background-position: center; + background-size: cover; +} + +/* 404 Page Styles */ + +.error-404 { + font-size: 100px; +} + +/* Pricing Page Styles */ + +.price { + display: block; + font-size: 50px; + line-height: 50px; +} + +.price sup { + top: -20px; + left: 2px; + font-size: 20px; +} + +.period { + display: block; + font-style: italic; +} + +/* Footer Styles */ + +footer { + margin: 50px 0; +} + +/* Responsive Styles */ + +@media(max-width:991px) { + .client-img, + .img-related { + margin-bottom: 30px; + } +} + +@media(max-width:767px) { + .img-portfolio { + margin-bottom: 15px; + } + + header.carousel .carousel { + height: 70%; + } +} \ No newline at end of file diff --git a/css/pmd-customstyles.css b/css/pmd-customstyles.css new file mode 100644 index 0000000000..7683ae54d8 --- /dev/null +++ b/css/pmd-customstyles.css @@ -0,0 +1,86 @@ + +.panel-body { + padding-top: 0cm; +} + +.landing-page.cat-title { + margin-bottom: .5cm; + margin-top: .5cm; +} + +.landing-page.cat-description { + margin-top: .4cm; +} + +/* Offsets contents by the height of the nav bar */ +#topbar-content-offset { + overflow: scroll; + position: absolute; + top: 50px; /* height of the nav bar */ + bottom: 0px; + width: 100%; +} + +details { + border-radius: 3px; + background: #EEE; + margin-left: 10px; +} + +details p { + padding: 5px 10px 5px; + background: white; +} + +details summary { + font-size: 11pt; + vertical-align: top; + background: #d2d2d2; + color: black; + border-radius: 3px; + padding: 5px 10px; + outline: none; + cursor: pointer; + display: list-item; +} + +details summary::after { + content: "..."; +} + +details[open] summary { + background-color: #347DBE; + color: white; +} + + +.hiddenRow { + padding: 0 !important; +} + +.xpath-fun-doc .fun-name { + font-weight: bold; +} + +.xpath-fun-doc .fun-details-header { + font-family: monospace; + font-size: larger; +} + +.xpath-fun-doc .fun-ns { + color: darkgray; +} + +.xpath-fun-doc span.param-name { + font-weight: normal; + +} + +.xpath-fun-doc span.param-type { + font-weight: lighter; + font-style: italic; + color: darkgray; +} +.xpath-fun-doc .code-examples dt { + font-weight: normal; +} diff --git a/css/printstyles.css b/css/printstyles.css new file mode 100644 index 0000000000..5e55e57651 --- /dev/null +++ b/css/printstyles.css @@ -0,0 +1,160 @@ + +/*body.print .container {max-width: 650px;}*/ + +body { + font-size:14px; +} +.nav ul li a {border-top:0px; background-color:transparent; color: #808080; } +#navig a[href] {color: #595959 !important;} +table .table {max-width:650px;} + +#navig li.sectionHead {font-weight: bold; font-size: 18px; color: #595959 !important; } +#navig li {font-weight: normal; } + +#navig a[href]::after { content: leader(".") target-counter(attr(href), page); } + +a[href]::after { + content: " (page " target-counter(attr(href), page) ")" +} + +a[href^="http:"]::after, a[href^="https:"]::after { + content: " (" attr(href) ")"; +} + +a[href] { + color: blue !important; +} +a[href*="mailto"]::after, a[data-toggle="tooltip"]::after, a[href].noCrossRef::after { + content: ""; +} + + +@page { + margin: 60pt 90pt 60pt 90pt; + font-family: sans-serif; + font-style:none; + color: gray; + +} + +.printTitle { + line-height:30pt; + font-size:27pt; + font-weight: bold; + letter-spacing: -.5px; + margin-bottom:25px; +} + +.printSubtitle { + font-size: 19pt; + color: #cccccc !important; + front-family: "Grotesque MT Light"; + line-height: 22pt; + letter-spacing: -.5px; + margin-bottom:20px; +} +.printTitleArea hr { + color: #999999 !important; + height: 2px; + width: 100%; +} + +.printTitleImage { + max-width:300px; + margin-bottom:200px; +} + + +.printTitleImage { + max-width: 250px; +} + +#navig { + /*page-break-before: always;*/ +} + +.copyrightBoilerplate { + page-break-before:always; + font-size:14px; +} + +.lastGeneratedDate { + font-style: italic; + font-size:14px; + color: gray; +} + +.alert a { + text-decoration: none !important; +} + + +body.title { page: title } + +@page title { + @top-left { + content: " "; + } + @top-right { + content: " " + } + @bottom-right { + content: " "; + } + @bottom-left { + content: " "; + } +} + +body.frontmatter { page: frontmatter } +body.frontmatter {counter-reset: page 1} + + +@page frontmatter { + @top-left { + content: prince-script(guideName); + } + @top-right { + content: prince-script(datestamp); + } + @bottom-right { + content: counter(page, lower-roman); + } + @bottom-left { + content: "youremail@domain.com"; } +} + +body.first_page {counter-reset: page 1} + +h1 { string-set: doctitle content() } + +@page { + @top-left { + content: string(doctitle); + font-size: 11px; + font-style: italic; + } + @top-right { + content: prince-script(datestamp); + font-size: 11px; + } + + @bottom-right { + content: "Page " counter(page); + font-size: 11px; + } + @bottom-left { + content: prince-script(guideName); + font-size: 11px; + } +} +.alert { + background-color: #fafafa !important; + border-color: #dedede !important; + color: black; +} + +pre { + background-color: #fafafa; +} + diff --git a/css/syntax.css b/css/syntax.css new file mode 100644 index 0000000000..1e651cf79d --- /dev/null +++ b/css/syntax.css @@ -0,0 +1,60 @@ +.highlight { background: #ffffff; } +.highlight .c { color: #999988; font-style: italic } /* Comment */ +.highlight .err { color: #a61717; background-color: #e3d2d2 } /* Error */ +.highlight .k { font-weight: bold } /* Keyword */ +.highlight .o { font-weight: bold } /* Operator */ +.highlight .cm { color: #999988; font-style: italic } /* Comment.Multiline */ +.highlight .cp { color: #999999; font-weight: bold } /* Comment.Preproc */ +.highlight .c1 { color: #999988; font-style: italic } /* Comment.Single */ +.highlight .cs { color: #999999; font-weight: bold; font-style: italic } /* Comment.Special */ +.highlight .gd { color: #000000; background-color: #ffdddd } /* Generic.Deleted */ +.highlight .gd .x { color: #000000; background-color: #ffaaaa } /* Generic.Deleted.Specific */ +.highlight .ge { font-style: italic } /* Generic.Emph */ +.highlight .gr { color: #aa0000 } /* Generic.Error */ +.highlight .gh { color: #999999 } /* Generic.Heading */ +.highlight .gi { color: #000000; background-color: #ddffdd } /* Generic.Inserted */ +.highlight .gi .x { color: #000000; background-color: #aaffaa } /* Generic.Inserted.Specific */ +.highlight .go { color: #888888 } /* Generic.Output */ +.highlight .gp { color: #555555 } /* Generic.Prompt */ +.highlight .gs { font-weight: bold } /* Generic.Strong */ +.highlight .gu { color: #aaaaaa } /* Generic.Subheading */ +.highlight .gt { color: #aa0000 } /* Generic.Traceback */ +.highlight .kc { font-weight: bold } /* Keyword.Constant */ +.highlight .kd { font-weight: bold } /* Keyword.Declaration */ +.highlight .kp { font-weight: bold } /* Keyword.Pseudo */ +.highlight .kr { font-weight: bold } /* Keyword.Reserved */ +.highlight .kt { color: #445588; font-weight: bold } /* Keyword.Type */ +.highlight .m { color: #009999 } /* Literal.Number */ +.highlight .s { color: #d14 } /* Literal.String */ +.highlight .na { color: #008080 } /* Name.Attribute */ +.highlight .nb { color: #0086B3 } /* Name.Builtin */ +.highlight .nc { color: #445588; font-weight: bold } /* Name.Class */ +.highlight .no { color: #008080 } /* Name.Constant */ +.highlight .ni { color: #800080 } /* Name.Entity */ +.highlight .ne { color: #990000; font-weight: bold } /* Name.Exception */ +.highlight .nf { color: #990000; font-weight: bold } /* Name.Function */ +.highlight .nn { color: #555555 } /* Name.Namespace */ +.highlight .nt { color: #000080 } /* Name.Tag */ +.highlight .nv { color: #008080 } /* Name.Variable */ +.highlight .ow { font-weight: bold } /* Operator.Word */ +.highlight .w { color: #bbbbbb } /* Text.Whitespace */ +.highlight .mf { color: #009999 } /* Literal.Number.Float */ +.highlight .mh { color: #009999 } /* Literal.Number.Hex */ +.highlight .mi { color: #009999 } /* Literal.Number.Integer */ +.highlight .mo { color: #009999 } /* Literal.Number.Oct */ +.highlight .sb { color: #d14 } /* Literal.String.Backtick */ +.highlight .sc { color: #d14 } /* Literal.String.Char */ +.highlight .sd { color: #d14 } /* Literal.String.Doc */ +.highlight .s2 { color: #d14 } /* Literal.String.Double */ +.highlight .se { color: #d14 } /* Literal.String.Escape */ +.highlight .sh { color: #d14 } /* Literal.String.Heredoc */ +.highlight .si { color: #d14 } /* Literal.String.Interpol */ +.highlight .sx { color: #d14 } /* Literal.String.Other */ +.highlight .sr { color: #009926 } /* Literal.String.Regex */ +.highlight .s1 { color: #d14 } /* Literal.String.Single */ +.highlight .ss { color: #990073 } /* Literal.String.Symbol */ +.highlight .bp { color: #999999 } /* Name.Builtin.Pseudo */ +.highlight .vc { color: #008080 } /* Name.Variable.Class */ +.highlight .vg { color: #008080 } /* Name.Variable.Global */ +.highlight .vi { color: #008080 } /* Name.Variable.Instance */ +.highlight .il { color: #009999 } /* Literal.Number.Integer.Long */ \ No newline at end of file diff --git a/css/theme-blue.css b/css/theme-blue.css new file mode 100644 index 0000000000..64cc6c387e --- /dev/null +++ b/css/theme-blue.css @@ -0,0 +1,103 @@ +.summary { + color: #808080; + border-left: 5px solid #ED1951; + font-size:16px; +} + + +h3 {color: #ED1951; } +h4 {color: #808080; } + +.nav-tabs > li.active > a, .nav-tabs > li.active > a:hover, .nav-tabs > li.active > a:focus { + background-color: #248ec2; + color: white; +} + +.nav > li.active > a { + background-color: #347DBE; +} + +.nav > li > a:hover { + background-color: #248ec2; +} + +div.navbar-collapse .dropdown-menu > li > a:hover { + background-color: #347DBE; +} + +.nav li.thirdlevel > a { + background-color: #FAFAFA !important; + color: #248EC2; + font-weight: bold; +} + +a[data-toggle="tooltip"] { + color: #649345; + font-style: italic; + cursor: default; +} + +.navbar-inverse { + background-color: #347DBE; + border-color: #015CAE; +} + +.navbar-inverse .navbar-nav > .open > a, .navbar-inverse .navbar-nav > .open > a:hover, .navbar-inverse .navbar-nav > .open > a:focus { + color: #015CAE; +} + +.navbar-inverse .navbar-nav > .open > a, .navbar-inverse .navbar-nav > .open > a:hover, .navbar-inverse .navbar-nav > .open > a:focus { + background-color: #015CAE; + color: #ffffff; +} + +/* not sure if using this ...*/ +.navbar-inverse .navbar-collapse, .navbar-inverse .navbar-form { + border-color: #248ec2 !important; +} + +.btn-primary { + color: #ffffff; + background-color: #347DBE; + border-color: #347DBE; +} + +.navbar-inverse .navbar-nav > .active > a, .navbar-inverse .navbar-nav > .active > a:hover, .navbar-inverse .navbar-nav > .active > a:focus { + background-color: #347DBE; +} + +.btn-primary:hover, +.btn-primary:focus, +.btn-primary:active, +.btn-primary.active, +.open .dropdown-toggle.btn-primary { + background-color: #248ec2; + border-color: #347DBE; +} + +.printTitle { + color: #015CAE !important; +} + +body.print h1 {color: #015CAE !important; font-size:28px !important;} +body.print h2 {color: #595959 !important; font-size:20px !important;} +body.print h3 {color: #E50E51 !important; font-size:14px !important;} +body.print h4 {color: #679DCE !important; font-size:14px; font-style: italic !important;} + +.anchorjs-link:hover { + color: #216f9b; +} + +div.sidebarTitle { + color: #015CAE; +} + +li.sidebarTitle { + margin-top:40px; + font-weight:normal; + font-size:130%; + color: #ED1951; + margin-bottom:10px; + margin-left: 5px; + +} \ No newline at end of file diff --git a/css/theme-green.css b/css/theme-green.css new file mode 100644 index 0000000000..f6b0d8b1e7 --- /dev/null +++ b/css/theme-green.css @@ -0,0 +1,99 @@ +.summary { + color: #808080; + border-left: 5px solid #E50E51; + font-size:16px; +} + + +h3 {color: #E50E51; } +h4 {color: #808080; } + +.nav-tabs > li.active > a, .nav-tabs > li.active > a:hover, .nav-tabs > li.active > a:focus { + background-color: #248ec2; + color: white; +} + +.nav > li.active > a { + background-color: #72ac4a; +} + +.nav > li > a:hover { + background-color: #72ac4a; +} + +div.navbar-collapse .dropdown-menu > li > a:hover { + background-color: #72ac4a; +} + +.nav li.thirdlevel > a { + background-color: #FAFAFA !important; + color: #72ac4a; + font-weight: bold; +} + +a[data-toggle="tooltip"] { + color: #649345; + font-style: italic; + cursor: default; +} + +.navbar-inverse { + background-color: #72ac4a; + border-color: #5b893c; +} + +.navbar-inverse .navbar-nav > .open > a, .navbar-inverse .navbar-nav > .open > a:hover, .navbar-inverse .navbar-nav > .open > a:focus { + color: #5b893c; +} + +.navbar-inverse .navbar-nav > .open > a, .navbar-inverse .navbar-nav > .open > a:hover, .navbar-inverse .navbar-nav > .open > a:focus { + background-color: #5b893c; + color: #ffffff; +} + +/* not sure if using this ...*/ +.navbar-inverse .navbar-collapse, .navbar-inverse .navbar-form { + border-color: #72ac4a !important; +} + +.btn-primary { + color: #ffffff; + background-color: #5b893c; + border-color: #5b893c; +} + +.btn-primary:hover, +.btn-primary:focus, +.btn-primary:active, +.btn-primary.active, +.open .dropdown-toggle.btn-primary { + background-color: #72ac4a; + border-color: #5b893c; +} + +.printTitle { + color: #5b893c !important; +} + +body.print h1 {color: #5b893c !important; font-size:28px;} +body.print h2 {color: #595959 !important; font-size:24px;} +body.print h3 {color: #E50E51 !important; font-size:14px;} +body.print h4 {color: #679DCE !important; font-size:14px; font-style: italic;} + +.anchorjs-link:hover { + color: #4f7233; +} + +div.sidebarTitle { + color: #E50E51; +} + +li.sidebarTitle { + margin-top:40px; + font-weight:normal; + font-size:130%; + color: #ED1951; + margin-bottom:10px; + margin-left: 5px; + +} \ No newline at end of file diff --git a/feed.xml b/feed.xml new file mode 100644 index 0000000000..1977f33fae --- /dev/null +++ b/feed.xml @@ -0,0 +1,13 @@ + + + + + Intended as a documentation theme based on Jekyll for technical writers documenting software and other technical products, this theme has all the elements you would need to handle multiple products with both multi-level sidebar navigation, tags, and other documentation features. + https://pmd.github.io/pmd/ + + Sat, 14 Nov 2020 09:11:39 +0000 + Sat, 14 Nov 2020 09:11:39 +0000 + Jekyll v3.9.0 + + + diff --git a/fonts/FontAwesome.otf b/fonts/FontAwesome.otf new file mode 100644 index 0000000000..81c9ad949b Binary files /dev/null and b/fonts/FontAwesome.otf differ diff --git a/fonts/fontawesome-webfont.eot b/fonts/fontawesome-webfont.eot new file mode 100644 index 0000000000..84677bc0c5 Binary files /dev/null and b/fonts/fontawesome-webfont.eot differ diff --git a/fonts/fontawesome-webfont.svg b/fonts/fontawesome-webfont.svg new file mode 100644 index 0000000000..d907b25ae6 --- /dev/null +++ b/fonts/fontawesome-webfont.svg @@ -0,0 +1,520 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/fonts/fontawesome-webfont.ttf b/fonts/fontawesome-webfont.ttf new file mode 100644 index 0000000000..96a3639cdd Binary files /dev/null and b/fonts/fontawesome-webfont.ttf differ diff --git a/fonts/fontawesome-webfont.woff b/fonts/fontawesome-webfont.woff new file mode 100644 index 0000000000..628b6a52a8 Binary files /dev/null and b/fonts/fontawesome-webfont.woff differ diff --git a/fonts/glyphicons-halflings-regular.eot b/fonts/glyphicons-halflings-regular.eot new file mode 100644 index 0000000000..b93a4953ff Binary files /dev/null and b/fonts/glyphicons-halflings-regular.eot differ diff --git a/fonts/glyphicons-halflings-regular.svg b/fonts/glyphicons-halflings-regular.svg new file mode 100644 index 0000000000..94fb5490a2 --- /dev/null +++ b/fonts/glyphicons-halflings-regular.svg @@ -0,0 +1,288 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/fonts/glyphicons-halflings-regular.ttf b/fonts/glyphicons-halflings-regular.ttf new file mode 100644 index 0000000000..1413fc609a Binary files /dev/null and b/fonts/glyphicons-halflings-regular.ttf differ diff --git a/fonts/glyphicons-halflings-regular.woff b/fonts/glyphicons-halflings-regular.woff new file mode 100644 index 0000000000..9e612858f8 Binary files /dev/null and b/fonts/glyphicons-halflings-regular.woff differ diff --git a/fonts/glyphicons-halflings-regular.woff2 b/fonts/glyphicons-halflings-regular.woff2 new file mode 100644 index 0000000000..64539b54c3 Binary files /dev/null and b/fonts/glyphicons-halflings-regular.woff2 differ diff --git a/images/credits/MD_logo4c_120x120.png b/images/credits/MD_logo4c_120x120.png new file mode 100644 index 0000000000..c641799fa9 Binary files /dev/null and b/images/credits/MD_logo4c_120x120.png differ diff --git a/images/credits/ae-logo.gif b/images/credits/ae-logo.gif new file mode 100644 index 0000000000..827163e931 Binary files /dev/null and b/images/credits/ae-logo.gif differ diff --git a/images/credits/atlassian-cenqua-logo.png b/images/credits/atlassian-cenqua-logo.png new file mode 100644 index 0000000000..01e6130224 Binary files /dev/null and b/images/credits/atlassian-cenqua-logo.png differ diff --git a/images/credits/bb-pmd.png b/images/credits/bb-pmd.png new file mode 100644 index 0000000000..4a86b9db3c Binary files /dev/null and b/images/credits/bb-pmd.png differ diff --git a/images/credits/cougaar.jpg b/images/credits/cougaar.jpg new file mode 100644 index 0000000000..db5502a75a Binary files /dev/null and b/images/credits/cougaar.jpg differ diff --git a/images/credits/darpa.jpg b/images/credits/darpa.jpg new file mode 100644 index 0000000000..b532325288 Binary files /dev/null and b/images/credits/darpa.jpg differ diff --git a/images/credits/qasystems_logo.jpg b/images/credits/qasystems_logo.jpg new file mode 100644 index 0000000000..5411199052 Binary files /dev/null and b/images/credits/qasystems_logo.jpg differ diff --git a/images/credits/refactorit_logo.gif b/images/credits/refactorit_logo.gif new file mode 100644 index 0000000000..d304d7f335 Binary files /dev/null and b/images/credits/refactorit_logo.gif differ diff --git a/images/credits/yjp.gif b/images/credits/yjp.gif new file mode 100644 index 0000000000..862d058921 Binary files /dev/null and b/images/credits/yjp.gif differ diff --git a/images/designer/bottom-ui.png b/images/designer/bottom-ui.png new file mode 100644 index 0000000000..64015fb7e8 Binary files /dev/null and b/images/designer/bottom-ui.png differ diff --git a/images/designer/demo.gif b/images/designer/demo.gif new file mode 100644 index 0000000000..405712d484 Binary files /dev/null and b/images/designer/demo.gif differ diff --git a/images/designer/designer-top.png b/images/designer/designer-top.png new file mode 100644 index 0000000000..45942a0ed4 Binary files /dev/null and b/images/designer/designer-top.png differ diff --git a/images/designer/designer.png b/images/designer/designer.png new file mode 100644 index 0000000000..1068d6ce28 Binary files /dev/null and b/images/designer/designer.png differ diff --git a/images/designer/empty-tests.png b/images/designer/empty-tests.png new file mode 100644 index 0000000000..6c71392b84 Binary files /dev/null and b/images/designer/empty-tests.png differ diff --git a/images/designer/export-example.gif b/images/designer/export-example.gif new file mode 100644 index 0000000000..92af52fda9 Binary files /dev/null and b/images/designer/export-example.gif differ diff --git a/images/designer/hover-selection.gif b/images/designer/hover-selection.gif new file mode 100644 index 0000000000..09bdc6bb7d Binary files /dev/null and b/images/designer/hover-selection.gif differ diff --git a/images/designer/parents-bar.gif b/images/designer/parents-bar.gif new file mode 100644 index 0000000000..9a266db4b1 Binary files /dev/null and b/images/designer/parents-bar.gif differ diff --git a/images/designer/property-defs.png b/images/designer/property-defs.png new file mode 100644 index 0000000000..54e3091976 Binary files /dev/null and b/images/designer/property-defs.png differ diff --git a/images/designer/property-edit.png b/images/designer/property-edit.png new file mode 100644 index 0000000000..5470ad206f Binary files /dev/null and b/images/designer/property-edit.png differ diff --git a/images/designer/tests/add-violation.gif b/images/designer/tests/add-violation.gif new file mode 100644 index 0000000000..c2b71ba494 Binary files /dev/null and b/images/designer/tests/add-violation.gif differ diff --git a/images/designer/tests/all-green.png b/images/designer/tests/all-green.png new file mode 100644 index 0000000000..51264bf9ae Binary files /dev/null and b/images/designer/tests/all-green.png differ diff --git a/images/designer/tests/export.gif b/images/designer/tests/export.gif new file mode 100644 index 0000000000..b2d36c89db Binary files /dev/null and b/images/designer/tests/export.gif differ diff --git a/images/designer/tests/failing.png b/images/designer/tests/failing.png new file mode 100644 index 0000000000..96f8f14842 Binary files /dev/null and b/images/designer/tests/failing.png differ diff --git a/images/designer/tests/import.gif b/images/designer/tests/import.gif new file mode 100644 index 0000000000..4aac308cce Binary files /dev/null and b/images/designer/tests/import.gif differ diff --git a/images/designer/tests/load.gif b/images/designer/tests/load.gif new file mode 100644 index 0000000000..79b56a62bf Binary files /dev/null and b/images/designer/tests/load.gif differ diff --git a/images/designer/tests/property.gif b/images/designer/tests/property.gif new file mode 100644 index 0000000000..0178084e6a Binary files /dev/null and b/images/designer/tests/property.gif differ diff --git a/images/designer/tests/toolbar.png b/images/designer/tests/toolbar.png new file mode 100644 index 0000000000..8728ce7730 Binary files /dev/null and b/images/designer/tests/toolbar.png differ diff --git a/images/designer/usages.gif b/images/designer/usages.gif new file mode 100644 index 0000000000..d637f46f14 Binary files /dev/null and b/images/designer/usages.gif differ diff --git a/images/devdocs/designer_screenshot.png b/images/devdocs/designer_screenshot.png new file mode 100644 index 0000000000..64a59a62d1 Binary files /dev/null and b/images/devdocs/designer_screenshot.png differ diff --git a/images/favicon.ico b/images/favicon.ico new file mode 100644 index 0000000000..6580a70d75 Binary files /dev/null and b/images/favicon.ico differ diff --git a/images/logo/pmd_logo.jpg b/images/logo/pmd_logo.jpg new file mode 100644 index 0000000000..b94df4507f Binary files /dev/null and b/images/logo/pmd_logo.jpg differ diff --git a/images/logo/pmd_logo.png b/images/logo/pmd_logo.png new file mode 100644 index 0000000000..bdff9acc56 Binary files /dev/null and b/images/logo/pmd_logo.png differ diff --git a/images/logo/pmd_logo.svgz b/images/logo/pmd_logo.svgz new file mode 100644 index 0000000000..3250b51a59 Binary files /dev/null and b/images/logo/pmd_logo.svgz differ diff --git a/images/logo/pmd_logo_small.jpg b/images/logo/pmd_logo_small.jpg new file mode 100644 index 0000000000..a3a65423ea Binary files /dev/null and b/images/logo/pmd_logo_small.jpg differ diff --git a/images/logo/pmd_logo_small.png b/images/logo/pmd_logo_small.png new file mode 100644 index 0000000000..fd0bfb0ad9 Binary files /dev/null and b/images/logo/pmd_logo_small.png differ diff --git a/images/logo/pmd_logo_tiny.png b/images/logo/pmd_logo_tiny.png new file mode 100644 index 0000000000..d7267fc392 Binary files /dev/null and b/images/logo/pmd_logo_tiny.png differ diff --git a/images/pmd-logo-big.png b/images/pmd-logo-big.png new file mode 100644 index 0000000000..bdff9acc56 Binary files /dev/null and b/images/pmd-logo-big.png differ diff --git a/images/pmd-logo-small.png b/images/pmd-logo-small.png new file mode 100644 index 0000000000..3428347426 Binary files /dev/null and b/images/pmd-logo-small.png differ diff --git a/images/pmd-logo.png b/images/pmd-logo.png new file mode 100644 index 0000000000..2428b3317e Binary files /dev/null and b/images/pmd-logo.png differ diff --git a/images/userdocs/designer-overview-with-nums.png b/images/userdocs/designer-overview-with-nums.png new file mode 100644 index 0000000000..2851fd8ae6 Binary files /dev/null and b/images/userdocs/designer-overview-with-nums.png differ diff --git a/images/userdocs/designer-overview.png b/images/userdocs/designer-overview.png new file mode 100644 index 0000000000..8cbda3c4d5 Binary files /dev/null and b/images/userdocs/designer-overview.png differ diff --git a/images/userdocs/screenshot_cpd.png b/images/userdocs/screenshot_cpd.png new file mode 100644 index 0000000000..349b1d0e48 Binary files /dev/null and b/images/userdocs/screenshot_cpd.png differ diff --git a/index.html b/index.html new file mode 100644 index 0000000000..8e000bfb44 --- /dev/null +++ b/index.html @@ -0,0 +1,6362 @@ + + + + + + + + +Documentation Index | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + + +
+
 
+ +
+ + + +
+ + + + + + + + + + + + + + +
+ + + + +
+
+

Documentation Index

+
+ + + +
+ + +
Welcome to the documentation site for PMD and CPD!

+
+ + + + + + + + + + + Edit me + + + + + + + + + + + + +

Overview

+ + + + +

PMD is a static source code analyzer. It finds common programming flaws like +unused variables, empty catch blocks, unnecessary object creation, and +so forth. It’s mainly concerned with Java and Apex, but supports six other +languages.

+ +

PMD features many built-in checks (in PMD lingo, rules), which are documented +for each language in our Rule references. We +also support an extensive API to write your own rules, +which you can do either in Java or as a self-contained XPath query.

+ +

PMD is most useful when integrated into your build process. It can then be +used as a quality gate, to enforce a coding standard for your codebase. Among other +things, PMD can be run:

+ + +

CPD, the copy-paste detector, is also distributed with PMD. You can also use it +in a variety of ways, which are documented here.

+ +

Download

+ +

The latest release of PMD can be downloaded from our Github releases page.

+ +

Documentation

+ +

The rest of this page exposes the contents of the documentation site thematically, +which you can further scope down using the blue filter buttons. To navigate the site, +you may also use the search bar in the top right, or the sidebar on the left.

+ +


+ +
+ + + + + +
+ +
+
+ + + + + + + + + + + + + + + + + + + + + + + + + +
+
+ + + + +
Getting started
+
+ +

+ These pages summarize the gist of PMD usage to get you started quickly. +

+
    + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Installation and basic CLI usage
  • + + + + + + +
  • Making rulesets
  • + + + + + + +
  • Configuring rules
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Introduction to writing PMD rules
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+ + + +
+ + + + +
+ + +
Rule references
+
+ +

+ Pick your language to find out about the rule it supports. +

+
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Apex
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Ecmascript
  • + + + + + + + + + + + + + + + + + + + + + +
  • Java
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Java Server Pages
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Maven POM
  • + + + + + + + + + + + +
  • Modelica
  • + + + + + + + + + + + +
  • PLSQL
  • + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Salesforce VisualForce
  • + + + + + + + + + + + +
  • VM
  • + + + + + + + + + + + + + + + + + + + + + +
  • XML
  • + + + + + + + + + + + +
  • XSL
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Scala
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + +
+
+ + + + +
Writing rules
+
+ +

+ These pages document the process of writing and testing custom rules and metrics for PMD. +

+
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Introduction to writing PMD rules
  • + + + + + + +
  • Your first rule XPath
  • + + + + + + +
  • Writing XPath rules
  • + + + + + + +
  • Writing a custom rule
  • + + + + + + +
  • The rule designer
  • + + + + + + +
  • Defining rule properties
  • + + + + + + +
  • Using and defining code metrics for custom rules
  • + + + + + + +
  • Rule guidelines
  • + + + + + + +
  • Testing your rules
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Writing a custom rule
  • + + +
+
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + +
+
+ + + +
+ + + + +
+ + +
Usage and configuration
+
+ +

+ Learn how to build effective and versatile rulesets. +

+
    + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Installation and basic CLI usage
  • + + + + + + +
  • Making rulesets
  • + + + + + + +
  • Configuring rules
  • + + + + + + +
  • Best Practices
  • + + + + + + +
  • Suppressing warnings
  • + + + + + + +
  • Incremental Analysis
  • + + + + + + +
  • PMD CLI reference
  • + + + + + + +
  • Report formats for PMD
  • + + + + + + +
  • Finding duplicated code with CPD
  • + + + + + + +
  • Report formats for CPD
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+ + + +
+ + + + +
+ + +
Contributing
+
+ +

+ If you'd like to help us build PMD, these topics may interest you. See you around! +

+
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Developer Resources
  • + + + + + + +
  • Building PMD from source
  • + + + + + + +
  • Writing documentation
  • + + + + + + +
  • Roadmap
  • + + + + + + +
  • How PMD Works
  • + + + + + + +
  • Pmdtester
  • + + + + + + +
  • Rule deprecation policy
  • + + + + + + + + + + + + + + + + + + + + + +
  • Creating XML dump of the AST
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+ + + + +
Tools and integrations
+
+ +

+ These pages describe solutions that integrate PMD within your build process. +

+
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Maven PMD Plugin
  • + + + + + + +
  • Gradle
  • + + + + + + +
  • Ant Task Usage
  • + + + + + + +
  • PMD Java API
  • + + + + + + +
  • Continuous Integrations plugins
  • + + + + + + +
  • Tools / Integrations
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + +
+
+ + + + +
Major contributions
+
+ +

+ +

+
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
  • Adding PMD support for a new language
  • + + + + + + +
  • How to add a new CPD language
  • + + + + + + +
  • Adding support for metrics to a language
  • + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+
+
+ + + + +
+ +
+
+ + + + + + + + + + + + + + + + +
+ +
+ + + +
+ +
+ +
+
+ +
+
+ + +
+ +
+ +
+
+ + + diff --git a/js/customscripts.js b/js/customscripts.js new file mode 100644 index 0000000000..8c9fb4cb9f --- /dev/null +++ b/js/customscripts.js @@ -0,0 +1,55 @@ + +$('#mysidebar').height($(".nav").height()); + + +$( document ).ready(function() { + + //this script says, if the height of the viewport is greater than 800px, then insert affix class, which makes the nav bar float in a fixed + // position as your scroll. if you have a lot of nav items, this height may not work for you. + var h = $(window).height(); + //console.log (h); + if (h > 800) { + $( "#mysidebar" ).attr("class", "nav affix"); + } + // activate tooltips. although this is a bootstrap js function, it must be activated this way in your theme. + $('[data-toggle="tooltip"]').tooltip({ + placement : 'top' + }); + + /** + * AnchorJS + */ + anchors.add('h2,h3,h4,h5'); + +}); + +// needed for nav tabs on pages. See Formatting > Nav tabs for more details. +// script from http://stackoverflow.com/questions/10523433/how-do-i-keep-the-current-tab-active-with-twitter-bootstrap-after-a-page-reload +$(function() { + var json, tabsState; + $('a[data-toggle="pill"], a[data-toggle="tab"]').on('shown.bs.tab', function(e) { + var href, json, parentId, tabsState; + + tabsState = localStorage.getItem("tabs-state"); + json = JSON.parse(tabsState || "{}"); + parentId = $(e.target).parents("ul.nav.nav-pills, ul.nav.nav-tabs").attr("id"); + href = $(e.target).attr('href'); + json[parentId] = href; + + return localStorage.setItem("tabs-state", JSON.stringify(json)); + }); + + tabsState = localStorage.getItem("tabs-state"); + json = JSON.parse(tabsState || "{}"); + + $.each(json, function(containerId, href) { + return $("#" + containerId + " a[href=" + href + "]").tab('show'); + }); + + $("ul.nav.nav-pills, ul.nav.nav-tabs").each(function() { + var $this = $(this); + if (!json[$this.attr("id")]) { + return $this.find("a[data-toggle=tab]:first, a[data-toggle=pill]:first").tab("show"); + } + }); +}); diff --git a/js/jekyll-search.js b/js/jekyll-search.js new file mode 100644 index 0000000000..04d6a0d3a4 --- /dev/null +++ b/js/jekyll-search.js @@ -0,0 +1 @@ +!function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a="function"==typeof require&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);throw new Error("Cannot find module '"+o+"'")}var f=n[o]={exports:{}};t[o][0].call(f.exports,function(e){var n=t[o][1][e];return s(n?n:e)},f,f.exports,e,t,n,r)}return n[o].exports}for(var i="function"==typeof require&&require,o=0;o=0}var self=this;self.matches=function(string,crit){return"string"!=typeof string?!1:(string=string.trim(),doMatch(string,crit))}}module.exports=new LiteralSearchStrategy},{}],4:[function(require,module){module.exports=function(){function findMatches(store,crit,strategy){for(var data=store.get(),i=0;i{title}',noResultsText:"No results found",limit:10,fuzzy:!1};self.init=function(_opt){validateOptions(_opt),assignOptions(_opt),isJSON(opt.dataSource)?initWithJSON(opt.dataSource):initWithURL(opt.dataSource)}}var Searcher=require("./Searcher"),Templater=require("./Templater"),Store=require("./Store"),JSONLoader=require("./JSONLoader"),searcher=new Searcher,templater=new Templater,store=new Store,jsonLoader=new JSONLoader;window.SimpleJekyllSearch=new SimpleJekyllSearch}(window,document)},{"./JSONLoader":1,"./Searcher":4,"./Store":5,"./Templater":6}]},{},[7]); \ No newline at end of file diff --git a/js/jquery-ui.min.js b/js/jquery-ui.min.js new file mode 100644 index 0000000000..db0af4c4d5 --- /dev/null +++ b/js/jquery-ui.min.js @@ -0,0 +1,6 @@ +/*! jQuery UI - v1.12.1 - 2018-05-27 +* http://jqueryui.com +* Includes: effect.js, effects/effect-blind.js, effects/effect-bounce.js, effects/effect-clip.js, effects/effect-drop.js, effects/effect-explode.js, effects/effect-fade.js, effects/effect-fold.js, effects/effect-highlight.js, effects/effect-puff.js, effects/effect-pulsate.js, effects/effect-scale.js, effects/effect-shake.js, effects/effect-size.js, effects/effect-slide.js, effects/effect-transfer.js +* Copyright jQuery Foundation and other contributors; Licensed MIT */ + +(function(t){"function"==typeof define&&define.amd?define(["jquery"],t):t(jQuery)})(function(t){t.ui=t.ui||{},t.ui.version="1.12.1";var e="ui-effects-",i="ui-effects-style",s="ui-effects-animated",n=t;t.effects={effect:{}},function(t,e){function i(t,e,i){var s=u[e.type]||{};return null==t?i||!e.def?null:e.def:(t=s.floor?~~t:parseFloat(t),isNaN(t)?e.def:s.mod?(t+s.mod)%s.mod:0>t?0:t>s.max?s.max:t)}function s(i){var s=h(),n=s._rgba=[];return i=i.toLowerCase(),f(l,function(t,o){var a,r=o.re.exec(i),l=r&&o.parse(r),h=o.space||"rgba";return l?(a=s[h](l),s[c[h].cache]=a[c[h].cache],n=s._rgba=a._rgba,!1):e}),n.length?("0,0,0,0"===n.join()&&t.extend(n,o.transparent),s):o[i]}function n(t,e,i){return i=(i+1)%1,1>6*i?t+6*(e-t)*i:1>2*i?e:2>3*i?t+6*(e-t)*(2/3-i):t}var o,a="backgroundColor borderBottomColor borderLeftColor borderRightColor borderTopColor color columnRuleColor outlineColor textDecorationColor textEmphasisColor",r=/^([\-+])=\s*(\d+\.?\d*)/,l=[{re:/rgba?\(\s*(\d{1,3})\s*,\s*(\d{1,3})\s*,\s*(\d{1,3})\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,parse:function(t){return[t[1],t[2],t[3],t[4]]}},{re:/rgba?\(\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,parse:function(t){return[2.55*t[1],2.55*t[2],2.55*t[3],t[4]]}},{re:/#([a-f0-9]{2})([a-f0-9]{2})([a-f0-9]{2})/,parse:function(t){return[parseInt(t[1],16),parseInt(t[2],16),parseInt(t[3],16)]}},{re:/#([a-f0-9])([a-f0-9])([a-f0-9])/,parse:function(t){return[parseInt(t[1]+t[1],16),parseInt(t[2]+t[2],16),parseInt(t[3]+t[3],16)]}},{re:/hsla?\(\s*(\d+(?:\.\d+)?)\s*,\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,space:"hsla",parse:function(t){return[t[1],t[2]/100,t[3]/100,t[4]]}}],h=t.Color=function(e,i,s,n){return new t.Color.fn.parse(e,i,s,n)},c={rgba:{props:{red:{idx:0,type:"byte"},green:{idx:1,type:"byte"},blue:{idx:2,type:"byte"}}},hsla:{props:{hue:{idx:0,type:"degrees"},saturation:{idx:1,type:"percent"},lightness:{idx:2,type:"percent"}}}},u={"byte":{floor:!0,max:255},percent:{max:1},degrees:{mod:360,floor:!0}},d=h.support={},p=t("

")[0],f=t.each;p.style.cssText="background-color:rgba(1,1,1,.5)",d.rgba=p.style.backgroundColor.indexOf("rgba")>-1,f(c,function(t,e){e.cache="_"+t,e.props.alpha={idx:3,type:"percent",def:1}}),h.fn=t.extend(h.prototype,{parse:function(n,a,r,l){if(n===e)return this._rgba=[null,null,null,null],this;(n.jquery||n.nodeType)&&(n=t(n).css(a),a=e);var u=this,d=t.type(n),p=this._rgba=[];return a!==e&&(n=[n,a,r,l],d="array"),"string"===d?this.parse(s(n)||o._default):"array"===d?(f(c.rgba.props,function(t,e){p[e.idx]=i(n[e.idx],e)}),this):"object"===d?(n instanceof h?f(c,function(t,e){n[e.cache]&&(u[e.cache]=n[e.cache].slice())}):f(c,function(e,s){var o=s.cache;f(s.props,function(t,e){if(!u[o]&&s.to){if("alpha"===t||null==n[t])return;u[o]=s.to(u._rgba)}u[o][e.idx]=i(n[t],e,!0)}),u[o]&&0>t.inArray(null,u[o].slice(0,3))&&(u[o][3]=1,s.from&&(u._rgba=s.from(u[o])))}),this):e},is:function(t){var i=h(t),s=!0,n=this;return f(c,function(t,o){var a,r=i[o.cache];return r&&(a=n[o.cache]||o.to&&o.to(n._rgba)||[],f(o.props,function(t,i){return null!=r[i.idx]?s=r[i.idx]===a[i.idx]:e})),s}),s},_space:function(){var t=[],e=this;return f(c,function(i,s){e[s.cache]&&t.push(i)}),t.pop()},transition:function(t,e){var s=h(t),n=s._space(),o=c[n],a=0===this.alpha()?h("transparent"):this,r=a[o.cache]||o.to(a._rgba),l=r.slice();return s=s[o.cache],f(o.props,function(t,n){var o=n.idx,a=r[o],h=s[o],c=u[n.type]||{};null!==h&&(null===a?l[o]=h:(c.mod&&(h-a>c.mod/2?a+=c.mod:a-h>c.mod/2&&(a-=c.mod)),l[o]=i((h-a)*e+a,n)))}),this[n](l)},blend:function(e){if(1===this._rgba[3])return this;var i=this._rgba.slice(),s=i.pop(),n=h(e)._rgba;return h(t.map(i,function(t,e){return(1-s)*n[e]+s*t}))},toRgbaString:function(){var e="rgba(",i=t.map(this._rgba,function(t,e){return null==t?e>2?1:0:t});return 1===i[3]&&(i.pop(),e="rgb("),e+i.join()+")"},toHslaString:function(){var e="hsla(",i=t.map(this.hsla(),function(t,e){return null==t&&(t=e>2?1:0),e&&3>e&&(t=Math.round(100*t)+"%"),t});return 1===i[3]&&(i.pop(),e="hsl("),e+i.join()+")"},toHexString:function(e){var i=this._rgba.slice(),s=i.pop();return e&&i.push(~~(255*s)),"#"+t.map(i,function(t){return t=(t||0).toString(16),1===t.length?"0"+t:t}).join("")},toString:function(){return 0===this._rgba[3]?"transparent":this.toRgbaString()}}),h.fn.parse.prototype=h.fn,c.hsla.to=function(t){if(null==t[0]||null==t[1]||null==t[2])return[null,null,null,t[3]];var e,i,s=t[0]/255,n=t[1]/255,o=t[2]/255,a=t[3],r=Math.max(s,n,o),l=Math.min(s,n,o),h=r-l,c=r+l,u=.5*c;return e=l===r?0:s===r?60*(n-o)/h+360:n===r?60*(o-s)/h+120:60*(s-n)/h+240,i=0===h?0:.5>=u?h/c:h/(2-c),[Math.round(e)%360,i,u,null==a?1:a]},c.hsla.from=function(t){if(null==t[0]||null==t[1]||null==t[2])return[null,null,null,t[3]];var e=t[0]/360,i=t[1],s=t[2],o=t[3],a=.5>=s?s*(1+i):s+i-s*i,r=2*s-a;return[Math.round(255*n(r,a,e+1/3)),Math.round(255*n(r,a,e)),Math.round(255*n(r,a,e-1/3)),o]},f(c,function(s,n){var o=n.props,a=n.cache,l=n.to,c=n.from;h.fn[s]=function(s){if(l&&!this[a]&&(this[a]=l(this._rgba)),s===e)return this[a].slice();var n,r=t.type(s),u="array"===r||"object"===r?s:arguments,d=this[a].slice();return f(o,function(t,e){var s=u["object"===r?t:e.idx];null==s&&(s=d[e.idx]),d[e.idx]=i(s,e)}),c?(n=h(c(d)),n[a]=d,n):h(d)},f(o,function(e,i){h.fn[e]||(h.fn[e]=function(n){var o,a=t.type(n),l="alpha"===e?this._hsla?"hsla":"rgba":s,h=this[l](),c=h[i.idx];return"undefined"===a?c:("function"===a&&(n=n.call(this,c),a=t.type(n)),null==n&&i.empty?this:("string"===a&&(o=r.exec(n),o&&(n=c+parseFloat(o[2])*("+"===o[1]?1:-1))),h[i.idx]=n,this[l](h)))})})}),h.hook=function(e){var i=e.split(" ");f(i,function(e,i){t.cssHooks[i]={set:function(e,n){var o,a,r="";if("transparent"!==n&&("string"!==t.type(n)||(o=s(n)))){if(n=h(o||n),!d.rgba&&1!==n._rgba[3]){for(a="backgroundColor"===i?e.parentNode:e;(""===r||"transparent"===r)&&a&&a.style;)try{r=t.css(a,"backgroundColor"),a=a.parentNode}catch(l){}n=n.blend(r&&"transparent"!==r?r:"_default")}n=n.toRgbaString()}try{e.style[i]=n}catch(l){}}},t.fx.step[i]=function(e){e.colorInit||(e.start=h(e.elem,i),e.end=h(e.end),e.colorInit=!0),t.cssHooks[i].set(e.elem,e.start.transition(e.end,e.pos))}})},h.hook(a),t.cssHooks.borderColor={expand:function(t){var e={};return f(["Top","Right","Bottom","Left"],function(i,s){e["border"+s+"Color"]=t}),e}},o=t.Color.names={aqua:"#00ffff",black:"#000000",blue:"#0000ff",fuchsia:"#ff00ff",gray:"#808080",green:"#008000",lime:"#00ff00",maroon:"#800000",navy:"#000080",olive:"#808000",purple:"#800080",red:"#ff0000",silver:"#c0c0c0",teal:"#008080",white:"#ffffff",yellow:"#ffff00",transparent:[null,null,null,0],_default:"#ffffff"}}(n),function(){function e(e){var i,s,n=e.ownerDocument.defaultView?e.ownerDocument.defaultView.getComputedStyle(e,null):e.currentStyle,o={};if(n&&n.length&&n[0]&&n[n[0]])for(s=n.length;s--;)i=n[s],"string"==typeof n[i]&&(o[t.camelCase(i)]=n[i]);else for(i in n)"string"==typeof n[i]&&(o[i]=n[i]);return o}function i(e,i){var s,n,a={};for(s in i)n=i[s],e[s]!==n&&(o[s]||(t.fx.step[s]||!isNaN(parseFloat(n)))&&(a[s]=n));return a}var s=["add","remove","toggle"],o={border:1,borderBottom:1,borderColor:1,borderLeft:1,borderRight:1,borderTop:1,borderWidth:1,margin:1,padding:1};t.each(["borderLeftStyle","borderRightStyle","borderBottomStyle","borderTopStyle"],function(e,i){t.fx.step[i]=function(t){("none"!==t.end&&!t.setAttr||1===t.pos&&!t.setAttr)&&(n.style(t.elem,i,t.end),t.setAttr=!0)}}),t.fn.addBack||(t.fn.addBack=function(t){return this.add(null==t?this.prevObject:this.prevObject.filter(t))}),t.effects.animateClass=function(n,o,a,r){var l=t.speed(o,a,r);return this.queue(function(){var o,a=t(this),r=a.attr("class")||"",h=l.children?a.find("*").addBack():a;h=h.map(function(){var i=t(this);return{el:i,start:e(this)}}),o=function(){t.each(s,function(t,e){n[e]&&a[e+"Class"](n[e])})},o(),h=h.map(function(){return this.end=e(this.el[0]),this.diff=i(this.start,this.end),this}),a.attr("class",r),h=h.map(function(){var e=this,i=t.Deferred(),s=t.extend({},l,{queue:!1,complete:function(){i.resolve(e)}});return this.el.animate(this.diff,s),i.promise()}),t.when.apply(t,h.get()).done(function(){o(),t.each(arguments,function(){var e=this.el;t.each(this.diff,function(t){e.css(t,"")})}),l.complete.call(a[0])})})},t.fn.extend({addClass:function(e){return function(i,s,n,o){return s?t.effects.animateClass.call(this,{add:i},s,n,o):e.apply(this,arguments)}}(t.fn.addClass),removeClass:function(e){return function(i,s,n,o){return arguments.length>1?t.effects.animateClass.call(this,{remove:i},s,n,o):e.apply(this,arguments)}}(t.fn.removeClass),toggleClass:function(e){return function(i,s,n,o,a){return"boolean"==typeof s||void 0===s?n?t.effects.animateClass.call(this,s?{add:i}:{remove:i},n,o,a):e.apply(this,arguments):t.effects.animateClass.call(this,{toggle:i},s,n,o)}}(t.fn.toggleClass),switchClass:function(e,i,s,n,o){return t.effects.animateClass.call(this,{add:i,remove:e},s,n,o)}})}(),function(){function n(e,i,s,n){return t.isPlainObject(e)&&(i=e,e=e.effect),e={effect:e},null==i&&(i={}),t.isFunction(i)&&(n=i,s=null,i={}),("number"==typeof i||t.fx.speeds[i])&&(n=s,s=i,i={}),t.isFunction(s)&&(n=s,s=null),i&&t.extend(e,i),s=s||i.duration,e.duration=t.fx.off?0:"number"==typeof s?s:s in t.fx.speeds?t.fx.speeds[s]:t.fx.speeds._default,e.complete=n||i.complete,e}function o(e){return!e||"number"==typeof e||t.fx.speeds[e]?!0:"string"!=typeof e||t.effects.effect[e]?t.isFunction(e)?!0:"object"!=typeof e||e.effect?!1:!0:!0}function a(t,e){var i=e.outerWidth(),s=e.outerHeight(),n=/^rect\((-?\d*\.?\d*px|-?\d+%|auto),?\s*(-?\d*\.?\d*px|-?\d+%|auto),?\s*(-?\d*\.?\d*px|-?\d+%|auto),?\s*(-?\d*\.?\d*px|-?\d+%|auto)\)$/,o=n.exec(t)||["",0,i,s,0];return{top:parseFloat(o[1])||0,right:"auto"===o[2]?i:parseFloat(o[2]),bottom:"auto"===o[3]?s:parseFloat(o[3]),left:parseFloat(o[4])||0}}t.expr&&t.expr.filters&&t.expr.filters.animated&&(t.expr.filters.animated=function(e){return function(i){return!!t(i).data(s)||e(i)}}(t.expr.filters.animated)),t.uiBackCompat!==!1&&t.extend(t.effects,{save:function(t,i){for(var s=0,n=i.length;n>s;s++)null!==i[s]&&t.data(e+i[s],t[0].style[i[s]])},restore:function(t,i){for(var s,n=0,o=i.length;o>n;n++)null!==i[n]&&(s=t.data(e+i[n]),t.css(i[n],s))},setMode:function(t,e){return"toggle"===e&&(e=t.is(":hidden")?"show":"hide"),e},createWrapper:function(e){if(e.parent().is(".ui-effects-wrapper"))return e.parent();var i={width:e.outerWidth(!0),height:e.outerHeight(!0),"float":e.css("float")},s=t("

").addClass("ui-effects-wrapper").css({fontSize:"100%",background:"transparent",border:"none",margin:0,padding:0}),n={width:e.width(),height:e.height()},o=document.activeElement;try{o.id}catch(a){o=document.body}return e.wrap(s),(e[0]===o||t.contains(e[0],o))&&t(o).trigger("focus"),s=e.parent(),"static"===e.css("position")?(s.css({position:"relative"}),e.css({position:"relative"})):(t.extend(i,{position:e.css("position"),zIndex:e.css("z-index")}),t.each(["top","left","bottom","right"],function(t,s){i[s]=e.css(s),isNaN(parseInt(i[s],10))&&(i[s]="auto")}),e.css({position:"relative",top:0,left:0,right:"auto",bottom:"auto"})),e.css(n),s.css(i).show()},removeWrapper:function(e){var i=document.activeElement;return e.parent().is(".ui-effects-wrapper")&&(e.parent().replaceWith(e),(e[0]===i||t.contains(e[0],i))&&t(i).trigger("focus")),e}}),t.extend(t.effects,{version:"1.12.1",define:function(e,i,s){return s||(s=i,i="effect"),t.effects.effect[e]=s,t.effects.effect[e].mode=i,s},scaledDimensions:function(t,e,i){if(0===e)return{height:0,width:0,outerHeight:0,outerWidth:0};var s="horizontal"!==i?(e||100)/100:1,n="vertical"!==i?(e||100)/100:1;return{height:t.height()*n,width:t.width()*s,outerHeight:t.outerHeight()*n,outerWidth:t.outerWidth()*s}},clipToBox:function(t){return{width:t.clip.right-t.clip.left,height:t.clip.bottom-t.clip.top,left:t.clip.left,top:t.clip.top}},unshift:function(t,e,i){var s=t.queue();e>1&&s.splice.apply(s,[1,0].concat(s.splice(e,i))),t.dequeue()},saveStyle:function(t){t.data(i,t[0].style.cssText)},restoreStyle:function(t){t[0].style.cssText=t.data(i)||"",t.removeData(i)},mode:function(t,e){var i=t.is(":hidden");return"toggle"===e&&(e=i?"show":"hide"),(i?"hide"===e:"show"===e)&&(e="none"),e},getBaseline:function(t,e){var i,s;switch(t[0]){case"top":i=0;break;case"middle":i=.5;break;case"bottom":i=1;break;default:i=t[0]/e.height}switch(t[1]){case"left":s=0;break;case"center":s=.5;break;case"right":s=1;break;default:s=t[1]/e.width}return{x:s,y:i}},createPlaceholder:function(i){var s,n=i.css("position"),o=i.position();return i.css({marginTop:i.css("marginTop"),marginBottom:i.css("marginBottom"),marginLeft:i.css("marginLeft"),marginRight:i.css("marginRight")}).outerWidth(i.outerWidth()).outerHeight(i.outerHeight()),/^(static|relative)/.test(n)&&(n="absolute",s=t("<"+i[0].nodeName+">").insertAfter(i).css({display:/^(inline|ruby)/.test(i.css("display"))?"inline-block":"block",visibility:"hidden",marginTop:i.css("marginTop"),marginBottom:i.css("marginBottom"),marginLeft:i.css("marginLeft"),marginRight:i.css("marginRight"),"float":i.css("float")}).outerWidth(i.outerWidth()).outerHeight(i.outerHeight()).addClass("ui-effects-placeholder"),i.data(e+"placeholder",s)),i.css({position:n,left:o.left,top:o.top}),s},removePlaceholder:function(t){var i=e+"placeholder",s=t.data(i);s&&(s.remove(),t.removeData(i))},cleanUp:function(e){t.effects.restoreStyle(e),t.effects.removePlaceholder(e)},setTransition:function(e,i,s,n){return n=n||{},t.each(i,function(t,i){var o=e.cssUnit(i);o[0]>0&&(n[i]=o[0]*s+o[1])}),n}}),t.fn.extend({effect:function(){function e(e){function n(){l.removeData(s),t.effects.cleanUp(l),"hide"===i.mode&&l.hide(),r()}function r(){t.isFunction(h)&&h.call(l[0]),t.isFunction(e)&&e()}var l=t(this);i.mode=u.shift(),t.uiBackCompat===!1||a?"none"===i.mode?(l[c](),r()):o.call(l[0],i,n):(l.is(":hidden")?"hide"===c:"show"===c)?(l[c](),r()):o.call(l[0],i,r)}var i=n.apply(this,arguments),o=t.effects.effect[i.effect],a=o.mode,r=i.queue,l=r||"fx",h=i.complete,c=i.mode,u=[],d=function(e){var i=t(this),n=t.effects.mode(i,c)||a;i.data(s,!0),u.push(n),a&&("show"===n||n===a&&"hide"===n)&&i.show(),a&&"none"===n||t.effects.saveStyle(i),t.isFunction(e)&&e()};return t.fx.off||!o?c?this[c](i.duration,h):this.each(function(){h&&h.call(this)}):r===!1?this.each(d).each(e):this.queue(l,d).queue(l,e)},show:function(t){return function(e){if(o(e))return t.apply(this,arguments);var i=n.apply(this,arguments);return i.mode="show",this.effect.call(this,i)}}(t.fn.show),hide:function(t){return function(e){if(o(e))return t.apply(this,arguments);var i=n.apply(this,arguments);return i.mode="hide",this.effect.call(this,i)}}(t.fn.hide),toggle:function(t){return function(e){if(o(e)||"boolean"==typeof e)return t.apply(this,arguments);var i=n.apply(this,arguments);return i.mode="toggle",this.effect.call(this,i)}}(t.fn.toggle),cssUnit:function(e){var i=this.css(e),s=[];return t.each(["em","px","%","pt"],function(t,e){i.indexOf(e)>0&&(s=[parseFloat(i),e])}),s},cssClip:function(t){return t?this.css("clip","rect("+t.top+"px "+t.right+"px "+t.bottom+"px "+t.left+"px)"):a(this.css("clip"),this)},transfer:function(e,i){var s=t(this),n=t(e.to),o="fixed"===n.css("position"),a=t("body"),r=o?a.scrollTop():0,l=o?a.scrollLeft():0,h=n.offset(),c={top:h.top-r,left:h.left-l,height:n.innerHeight(),width:n.innerWidth()},u=s.offset(),d=t("
").appendTo("body").addClass(e.className).css({top:u.top-r,left:u.left-l,height:s.innerHeight(),width:s.innerWidth(),position:o?"fixed":"absolute"}).animate(c,e.duration,e.easing,function(){d.remove(),t.isFunction(i)&&i()})}}),t.fx.step.clip=function(e){e.clipInit||(e.start=t(e.elem).cssClip(),"string"==typeof e.end&&(e.end=a(e.end,e.elem)),e.clipInit=!0),t(e.elem).cssClip({top:e.pos*(e.end.top-e.start.top)+e.start.top,right:e.pos*(e.end.right-e.start.right)+e.start.right,bottom:e.pos*(e.end.bottom-e.start.bottom)+e.start.bottom,left:e.pos*(e.end.left-e.start.left)+e.start.left})}}(),function(){var e={};t.each(["Quad","Cubic","Quart","Quint","Expo"],function(t,i){e[i]=function(e){return Math.pow(e,t+2)}}),t.extend(e,{Sine:function(t){return 1-Math.cos(t*Math.PI/2)},Circ:function(t){return 1-Math.sqrt(1-t*t)},Elastic:function(t){return 0===t||1===t?t:-Math.pow(2,8*(t-1))*Math.sin((80*(t-1)-7.5)*Math.PI/15)},Back:function(t){return t*t*(3*t-2)},Bounce:function(t){for(var e,i=4;((e=Math.pow(2,--i))-1)/11>t;);return 1/Math.pow(4,3-i)-7.5625*Math.pow((3*e-2)/22-t,2)}}),t.each(e,function(e,i){t.easing["easeIn"+e]=i,t.easing["easeOut"+e]=function(t){return 1-i(1-t)},t.easing["easeInOut"+e]=function(t){return.5>t?i(2*t)/2:1-i(-2*t+2)/2}})}();var o=t.effects;t.effects.define("blind","hide",function(e,i){var s={up:["bottom","top"],vertical:["bottom","top"],down:["top","bottom"],left:["right","left"],horizontal:["right","left"],right:["left","right"]},n=t(this),o=e.direction||"up",a=n.cssClip(),r={clip:t.extend({},a)},l=t.effects.createPlaceholder(n);r.clip[s[o][0]]=r.clip[s[o][1]],"show"===e.mode&&(n.cssClip(r.clip),l&&l.css(t.effects.clipToBox(r)),r.clip=a),l&&l.animate(t.effects.clipToBox(r),e.duration,e.easing),n.animate(r,{queue:!1,duration:e.duration,easing:e.easing,complete:i})}),t.effects.define("bounce",function(e,i){var s,n,o,a=t(this),r=e.mode,l="hide"===r,h="show"===r,c=e.direction||"up",u=e.distance,d=e.times||5,p=2*d+(h||l?1:0),f=e.duration/p,m=e.easing,g="up"===c||"down"===c?"top":"left",_="up"===c||"left"===c,v=0,b=a.queue().length;for(t.effects.createPlaceholder(a),o=a.css(g),u||(u=a["top"===g?"outerHeight":"outerWidth"]()/3),h&&(n={opacity:1},n[g]=o,a.css("opacity",0).css(g,_?2*-u:2*u).animate(n,f,m)),l&&(u/=Math.pow(2,d-1)),n={},n[g]=o;d>v;v++)s={},s[g]=(_?"-=":"+=")+u,a.animate(s,f,m).animate(n,f,m),u=l?2*u:u/2;l&&(s={opacity:0},s[g]=(_?"-=":"+=")+u,a.animate(s,f,m)),a.queue(i),t.effects.unshift(a,b,p+1)}),t.effects.define("clip","hide",function(e,i){var s,n={},o=t(this),a=e.direction||"vertical",r="both"===a,l=r||"horizontal"===a,h=r||"vertical"===a;s=o.cssClip(),n.clip={top:h?(s.bottom-s.top)/2:s.top,right:l?(s.right-s.left)/2:s.right,bottom:h?(s.bottom-s.top)/2:s.bottom,left:l?(s.right-s.left)/2:s.left},t.effects.createPlaceholder(o),"show"===e.mode&&(o.cssClip(n.clip),n.clip=s),o.animate(n,{queue:!1,duration:e.duration,easing:e.easing,complete:i})}),t.effects.define("drop","hide",function(e,i){var s,n=t(this),o=e.mode,a="show"===o,r=e.direction||"left",l="up"===r||"down"===r?"top":"left",h="up"===r||"left"===r?"-=":"+=",c="+="===h?"-=":"+=",u={opacity:0};t.effects.createPlaceholder(n),s=e.distance||n["top"===l?"outerHeight":"outerWidth"](!0)/2,u[l]=h+s,a&&(n.css(u),u[l]=c+s,u.opacity=1),n.animate(u,{queue:!1,duration:e.duration,easing:e.easing,complete:i})}),t.effects.define("explode","hide",function(e,i){function s(){b.push(this),b.length===u*d&&n()}function n(){p.css({visibility:"visible"}),t(b).remove(),i()}var o,a,r,l,h,c,u=e.pieces?Math.round(Math.sqrt(e.pieces)):3,d=u,p=t(this),f=e.mode,m="show"===f,g=p.show().css("visibility","hidden").offset(),_=Math.ceil(p.outerWidth()/d),v=Math.ceil(p.outerHeight()/u),b=[];for(o=0;u>o;o++)for(l=g.top+o*v,c=o-(u-1)/2,a=0;d>a;a++)r=g.left+a*_,h=a-(d-1)/2,p.clone().appendTo("body").wrap("
").css({position:"absolute",visibility:"visible",left:-a*_,top:-o*v}).parent().addClass("ui-effects-explode").css({position:"absolute",overflow:"hidden",width:_,height:v,left:r+(m?h*_:0),top:l+(m?c*v:0),opacity:m?0:1}).animate({left:r+(m?0:h*_),top:l+(m?0:c*v),opacity:m?1:0},e.duration||500,e.easing,s)}),t.effects.define("fade","toggle",function(e,i){var s="show"===e.mode;t(this).css("opacity",s?0:1).animate({opacity:s?1:0},{queue:!1,duration:e.duration,easing:e.easing,complete:i})}),t.effects.define("fold","hide",function(e,i){var s=t(this),n=e.mode,o="show"===n,a="hide"===n,r=e.size||15,l=/([0-9]+)%/.exec(r),h=!!e.horizFirst,c=h?["right","bottom"]:["bottom","right"],u=e.duration/2,d=t.effects.createPlaceholder(s),p=s.cssClip(),f={clip:t.extend({},p)},m={clip:t.extend({},p)},g=[p[c[0]],p[c[1]]],_=s.queue().length;l&&(r=parseInt(l[1],10)/100*g[a?0:1]),f.clip[c[0]]=r,m.clip[c[0]]=r,m.clip[c[1]]=0,o&&(s.cssClip(m.clip),d&&d.css(t.effects.clipToBox(m)),m.clip=p),s.queue(function(i){d&&d.animate(t.effects.clipToBox(f),u,e.easing).animate(t.effects.clipToBox(m),u,e.easing),i()}).animate(f,u,e.easing).animate(m,u,e.easing).queue(i),t.effects.unshift(s,_,4)}),t.effects.define("highlight","show",function(e,i){var s=t(this),n={backgroundColor:s.css("backgroundColor")};"hide"===e.mode&&(n.opacity=0),t.effects.saveStyle(s),s.css({backgroundImage:"none",backgroundColor:e.color||"#ffff99"}).animate(n,{queue:!1,duration:e.duration,easing:e.easing,complete:i})}),t.effects.define("size",function(e,i){var s,n,o,a=t(this),r=["fontSize"],l=["borderTopWidth","borderBottomWidth","paddingTop","paddingBottom"],h=["borderLeftWidth","borderRightWidth","paddingLeft","paddingRight"],c=e.mode,u="effect"!==c,d=e.scale||"both",p=e.origin||["middle","center"],f=a.css("position"),m=a.position(),g=t.effects.scaledDimensions(a),_=e.from||g,v=e.to||t.effects.scaledDimensions(a,0);t.effects.createPlaceholder(a),"show"===c&&(o=_,_=v,v=o),n={from:{y:_.height/g.height,x:_.width/g.width},to:{y:v.height/g.height,x:v.width/g.width}},("box"===d||"both"===d)&&(n.from.y!==n.to.y&&(_=t.effects.setTransition(a,l,n.from.y,_),v=t.effects.setTransition(a,l,n.to.y,v)),n.from.x!==n.to.x&&(_=t.effects.setTransition(a,h,n.from.x,_),v=t.effects.setTransition(a,h,n.to.x,v))),("content"===d||"both"===d)&&n.from.y!==n.to.y&&(_=t.effects.setTransition(a,r,n.from.y,_),v=t.effects.setTransition(a,r,n.to.y,v)),p&&(s=t.effects.getBaseline(p,g),_.top=(g.outerHeight-_.outerHeight)*s.y+m.top,_.left=(g.outerWidth-_.outerWidth)*s.x+m.left,v.top=(g.outerHeight-v.outerHeight)*s.y+m.top,v.left=(g.outerWidth-v.outerWidth)*s.x+m.left),a.css(_),("content"===d||"both"===d)&&(l=l.concat(["marginTop","marginBottom"]).concat(r),h=h.concat(["marginLeft","marginRight"]),a.find("*[width]").each(function(){var i=t(this),s=t.effects.scaledDimensions(i),o={height:s.height*n.from.y,width:s.width*n.from.x,outerHeight:s.outerHeight*n.from.y,outerWidth:s.outerWidth*n.from.x},a={height:s.height*n.to.y,width:s.width*n.to.x,outerHeight:s.height*n.to.y,outerWidth:s.width*n.to.x};n.from.y!==n.to.y&&(o=t.effects.setTransition(i,l,n.from.y,o),a=t.effects.setTransition(i,l,n.to.y,a)),n.from.x!==n.to.x&&(o=t.effects.setTransition(i,h,n.from.x,o),a=t.effects.setTransition(i,h,n.to.x,a)),u&&t.effects.saveStyle(i),i.css(o),i.animate(a,e.duration,e.easing,function(){u&&t.effects.restoreStyle(i)})})),a.animate(v,{queue:!1,duration:e.duration,easing:e.easing,complete:function(){var e=a.offset();0===v.opacity&&a.css("opacity",_.opacity),u||(a.css("position","static"===f?"relative":f).offset(e),t.effects.saveStyle(a)),i()}})}),t.effects.define("scale",function(e,i){var s=t(this),n=e.mode,o=parseInt(e.percent,10)||(0===parseInt(e.percent,10)?0:"effect"!==n?0:100),a=t.extend(!0,{from:t.effects.scaledDimensions(s),to:t.effects.scaledDimensions(s,o,e.direction||"both"),origin:e.origin||["middle","center"]},e);e.fade&&(a.from.opacity=1,a.to.opacity=0),t.effects.effect.size.call(this,a,i)}),t.effects.define("puff","hide",function(e,i){var s=t.extend(!0,{},e,{fade:!0,percent:parseInt(e.percent,10)||150});t.effects.effect.scale.call(this,s,i)}),t.effects.define("pulsate","show",function(e,i){var s=t(this),n=e.mode,o="show"===n,a="hide"===n,r=o||a,l=2*(e.times||5)+(r?1:0),h=e.duration/l,c=0,u=1,d=s.queue().length;for((o||!s.is(":visible"))&&(s.css("opacity",0).show(),c=1);l>u;u++)s.animate({opacity:c},h,e.easing),c=1-c;s.animate({opacity:c},h,e.easing),s.queue(i),t.effects.unshift(s,d,l+1)}),t.effects.define("shake",function(e,i){var s=1,n=t(this),o=e.direction||"left",a=e.distance||20,r=e.times||3,l=2*r+1,h=Math.round(e.duration/l),c="up"===o||"down"===o?"top":"left",u="up"===o||"left"===o,d={},p={},f={},m=n.queue().length;for(t.effects.createPlaceholder(n),d[c]=(u?"-=":"+=")+a,p[c]=(u?"+=":"-=")+2*a,f[c]=(u?"-=":"+=")+2*a,n.animate(d,h,e.easing);r>s;s++)n.animate(p,h,e.easing).animate(f,h,e.easing);n.animate(p,h,e.easing).animate(d,h/2,e.easing).queue(i),t.effects.unshift(n,m,l+1)}),t.effects.define("slide","show",function(e,i){var s,n,o=t(this),a={up:["bottom","top"],down:["top","bottom"],left:["right","left"],right:["left","right"]},r=e.mode,l=e.direction||"left",h="up"===l||"down"===l?"top":"left",c="up"===l||"left"===l,u=e.distance||o["top"===h?"outerHeight":"outerWidth"](!0),d={};t.effects.createPlaceholder(o),s=o.cssClip(),n=o.position()[h],d[h]=(c?-1:1)*u+n,d.clip=o.cssClip(),d.clip[a[l][1]]=d.clip[a[l][0]],"show"===r&&(o.cssClip(d.clip),o.css(h,d[h]),d.clip=s,d[h]=n),o.animate(d,{queue:!1,duration:e.duration,easing:e.easing,complete:i})});var o;t.uiBackCompat!==!1&&(o=t.effects.define("transfer",function(e,i){t(this).transfer(e,i)}))}); \ No newline at end of file diff --git a/js/jquery.ba-throttle-debounce.min.js b/js/jquery.ba-throttle-debounce.min.js new file mode 100644 index 0000000000..07205508eb --- /dev/null +++ b/js/jquery.ba-throttle-debounce.min.js @@ -0,0 +1,9 @@ +/* + * jQuery throttle / debounce - v1.1 - 3/7/2010 + * http://benalman.com/projects/jquery-throttle-debounce-plugin/ + * + * Copyright (c) 2010 "Cowboy" Ben Alman + * Dual licensed under the MIT and GPL licenses. + * http://benalman.com/about/license/ + */ +(function(b,c){var $=b.jQuery||b.Cowboy||(b.Cowboy={}),a;$.throttle=a=function(e,f,j,i){var h,d=0;if(typeof f!=="boolean"){i=j;j=f;f=c}function g(){var o=this,m=+new Date()-d,n=arguments;function l(){d=+new Date();j.apply(o,n)}function k(){h=c}if(i&&!h){l()}h&&clearTimeout(h);if(i===c&&m>e){l()}else{if(f!==true){h=setTimeout(i?k:l,i===c?e-m:e)}}}if($.guid){g.guid=j.guid=j.guid||$.guid++}return g};$.debounce=function(d,e,f){return f===c?a(d,e,false):a(d,f,e!==false)}})(this); \ No newline at end of file diff --git a/js/jquery.localScroll.min.js b/js/jquery.localScroll.min.js new file mode 100644 index 0000000000..48a6e168f6 --- /dev/null +++ b/js/jquery.localScroll.min.js @@ -0,0 +1,7 @@ +/** + * Copyright (c) 2007-2014 Ariel Flesler - afleslergmailcom | http://flesler.blogspot.com + * Licensed under MIT + * @author Ariel Flesler + * @version 1.3.5 + */ +;(function(a){if(typeof define==='function'&&define.amd){define(['jquery'],a)}else{a(jQuery)}}(function($){var g=location.href.replace(/#.*/,'');var h=$.localScroll=function(a){$('body').localScroll(a)};h.defaults={duration:1000,axis:'y',event:'click',stop:true,target:window};$.fn.localScroll=function(a){a=$.extend({},h.defaults,a);if(a.hash&&location.hash){if(a.target)window.scrollTo(0,0);scroll(0,location,a)}return a.lazy?this.on(a.event,'a,area',function(e){if(filter.call(this)){scroll(e,this,a)}}):this.find('a,area').filter(filter).bind(a.event,function(e){scroll(e,this,a)}).end().end();function filter(){return!!this.href&&!!this.hash&&this.href.replace(this.hash,'')==g&&(!a.filter||$(this).is(a.filter))}};h.hash=function(){};function scroll(e,a,b){var c=a.hash.slice(1),elem=document.getElementById(c)||document.getElementsByName(c)[0];if(!elem)return;if(e)e.preventDefault();var d=$(b.target);if(b.lock&&d.is(':animated')||b.onBefore&&b.onBefore(e,elem,d)===false)return;if(b.stop)d._scrollable().stop(true);if(b.hash){var f=elem.id===c?'id':'name',$a=$(' ').attr(f,c).css({position:'absolute',top:$(window).scrollTop(),left:$(window).scrollLeft()});elem[f]='';$('body').prepend($a);location.hash=a.hash;$a.remove();elem[f]=c}d.scrollTo(elem,b).trigger('notify.serialScroll',[elem])};return h})); \ No newline at end of file diff --git a/js/jquery.navgoco.min.js b/js/jquery.navgoco.min.js new file mode 100755 index 0000000000..4ba4475332 --- /dev/null +++ b/js/jquery.navgoco.min.js @@ -0,0 +1,8 @@ +/* + * jQuery Navgoco Menus Plugin v0.2.1 (2014-04-11) + * https://github.com/tefra/navgoco + * + * Copyright (c) 2014 Chris T (@tefra) + * BSD - https://github.com/tefra/navgoco/blob/master/LICENSE-BSD + */ +!function(a){"use strict";var b=function(b,c,d){return this.el=b,this.$el=a(b),this.options=c,this.uuid=this.$el.attr("id")?this.$el.attr("id"):d,this.state={},this.init(),this};b.prototype={init:function(){var b=this;b._load(),b.$el.find("ul").each(function(c){var d=a(this);d.attr("data-index",c),b.options.save&&b.state.hasOwnProperty(c)?(d.parent().addClass(b.options.openClass),d.show()):d.parent().hasClass(b.options.openClass)?(d.show(),b.state[c]=1):d.hide()});var c=a("").prepend(b.options.caretHtml),d=b.$el.find("li > a");b._trigger(c,!1),b._trigger(d,!0),b.$el.find("li:has(ul) > a").prepend(c)},_trigger:function(b,c){var d=this;b.on("click",function(b){b.stopPropagation();var e=c?a(this).next():a(this).parent().next(),f=!1;if(c){var g=a(this).attr("href");f=void 0===g||""===g||"#"===g}if(e=e.length>0?e:!1,d.options.onClickBefore.call(this,b,e),!c||e&&f)b.preventDefault(),d._toggle(e,e.is(":hidden")),d._save();else if(d.options.accordion){var h=d.state=d._parents(a(this));d.$el.find("ul").filter(":visible").each(function(){var b=a(this),c=b.attr("data-index");h.hasOwnProperty(c)||d._toggle(b,!1)}),d._save()}d.options.onClickAfter.call(this,b,e)})},_toggle:function(b,c){var d=this,e=b.attr("data-index"),f=b.parent();if(d.options.onToggleBefore.call(this,b,c),c){if(f.addClass(d.options.openClass),b.slideDown(d.options.slide),d.state[e]=1,d.options.accordion){var g=d.state=d._parents(b);g[e]=d.state[e]=1,d.$el.find("ul").filter(":visible").each(function(){var b=a(this),c=b.attr("data-index");g.hasOwnProperty(c)||d._toggle(b,!1)})}}else f.removeClass(d.options.openClass),b.slideUp(d.options.slide),d.state[e]=0;d.options.onToggleAfter.call(this,b,c)},_parents:function(b,c){var d={},e=b.parent(),f=e.parents("ul");return f.each(function(){var b=a(this),e=b.attr("data-index");return e?void(d[e]=c?b:1):!1}),d},_save:function(){if(this.options.save){var b={};for(var d in this.state)1===this.state[d]&&(b[d]=1);c[this.uuid]=this.state=b,a.cookie(this.options.cookie.name,JSON.stringify(c),this.options.cookie)}},_load:function(){if(this.options.save){if(null===c){var b=a.cookie(this.options.cookie.name);c=b?JSON.parse(b):{}}this.state=c.hasOwnProperty(this.uuid)?c[this.uuid]:{}}},toggle:function(b){var c=this,d=arguments.length;if(1>=d)c.$el.find("ul").each(function(){var d=a(this);c._toggle(d,b)});else{var e,f={},g=Array.prototype.slice.call(arguments,1);d--;for(var h=0;d>h;h++){e=g[h];var i=c.$el.find('ul[data-index="'+e+'"]').first();if(i&&(f[e]=i,b)){var j=c._parents(i,!0);for(var k in j)f.hasOwnProperty(k)||(f[k]=j[k])}}for(e in f)c._toggle(f[e],b)}c._save()},destroy:function(){a.removeData(this.$el),this.$el.find("li:has(ul) > a").unbind("click"),this.$el.find("li:has(ul) > a > span").unbind("click")}},a.fn.navgoco=function(c){if("string"==typeof c&&"_"!==c.charAt(0)&&"init"!==c)var d=!0,e=Array.prototype.slice.call(arguments,1);else c=a.extend({},a.fn.navgoco.defaults,c||{}),a.cookie||(c.save=!1);return this.each(function(f){var g=a(this),h=g.data("navgoco");h||(h=new b(this,d?a.fn.navgoco.defaults:c,f),g.data("navgoco",h)),d&&h[c].apply(h,e)})};var c=null;a.fn.navgoco.defaults={caretHtml:"",accordion:!1,openClass:"open",save:!0,cookie:{name:"navgoco",expires:!1,path:"/"},slide:{duration:400,easing:"swing"},onClickBefore:a.noop,onClickAfter:a.noop,onToggleBefore:a.noop,onToggleAfter:a.noop}}(jQuery); \ No newline at end of file diff --git a/js/jquery.scrollTo.min.js b/js/jquery.scrollTo.min.js new file mode 100644 index 0000000000..d9f9b1599c --- /dev/null +++ b/js/jquery.scrollTo.min.js @@ -0,0 +1,7 @@ +/** + * Copyright (c) 2007-2014 Ariel Flesler - afleslergmailcom | http://flesler.blogspot.com + * Licensed under MIT + * @author Ariel Flesler + * @version 1.4.14 + */ +;(function(k){'use strict';k(['jquery'],function($){var j=$.scrollTo=function(a,b,c){return $(window).scrollTo(a,b,c)};j.defaults={axis:'xy',duration:0,limit:!0};j.window=function(a){return $(window)._scrollable()};$.fn._scrollable=function(){return this.map(function(){var a=this,isWin=!a.nodeName||$.inArray(a.nodeName.toLowerCase(),['iframe','#document','html','body'])!=-1;if(!isWin)return a;var b=(a.contentWindow||a).document||a.ownerDocument||a;return/webkit/i.test(navigator.userAgent)||b.compatMode=='BackCompat'?b.body:b.documentElement})};$.fn.scrollTo=function(f,g,h){if(typeof g=='object'){h=g;g=0}if(typeof h=='function')h={onAfter:h};if(f=='max')f=9e9;h=$.extend({},j.defaults,h);g=g||h.duration;h.queue=h.queue&&h.axis.length>1;if(h.queue)g/=2;h.offset=both(h.offset);h.over=both(h.over);return this._scrollable().each(function(){if(f==null)return;var d=this,$elem=$(d),targ=f,toff,attr={},win=$elem.is('html,body');switch(typeof targ){case'number':case'string':if(/^([+-]=?)?\d+(\.\d+)?(px|%)?$/.test(targ)){targ=both(targ);break}targ=win?$(targ):$(targ,this);if(!targ.length)return;case'object':if(targ.is||targ.style)toff=(targ=$(targ)).offset()}var e=$.isFunction(h.offset)&&h.offset(d,targ)||h.offset;$.each(h.axis.split(''),function(i,a){var b=a=='x'?'Left':'Top',pos=b.toLowerCase(),key='scroll'+b,old=d[key],max=j.max(d,a);if(toff){attr[key]=toff[pos]+(win?0:old-$elem.offset()[pos]);if(h.margin){attr[key]-=parseInt(targ.css('margin'+b))||0;attr[key]-=parseInt(targ.css('border'+b+'Width'))||0}attr[key]+=e[pos]||0;if(h.over[pos])attr[key]+=targ[a=='x'?'width':'height']()*h.over[pos]}else{var c=targ[pos];attr[key]=c.slice&&c.slice(-1)=='%'?parseFloat(c)/100*max:c}if(h.limit&&/^\d+$/.test(attr[key]))attr[key]=attr[key]<=0?0:Math.min(attr[key],max);if(!i&&h.queue){if(old!=attr[key])animate(h.onAfterFirst);delete attr[key]}});animate(h.onAfter);function animate(a){$elem.animate(attr,g,h.easing,a&&function(){a.call(this,targ,h)})}}).end()};j.max=function(a,b){var c=b=='x'?'Width':'Height',scroll='scroll'+c;if(!$(a).is('html,body'))return a[scroll]-$(a)[c.toLowerCase()]();var d='client'+c,html=a.ownerDocument.documentElement,body=a.ownerDocument.body;return Math.max(html[scroll],body[scroll])-Math.min(html[d],body[d])};function both(a){return $.isFunction(a)||$.isPlainObject(a)?a:{top:a,left:a}}return j})}(typeof define==='function'&&define.amd?define:function(a,b){if(typeof module!=='undefined'&&module.exports){module.exports=b(require('jquery'))}else{b(jQuery)}})); \ No newline at end of file diff --git a/js/jquery.shuffle.min.js b/js/jquery.shuffle.min.js new file mode 100644 index 0000000000..d103127199 --- /dev/null +++ b/js/jquery.shuffle.min.js @@ -0,0 +1,1588 @@ +/*! + * Shuffle.js by @Vestride + * Categorize, sort, and filter a responsive grid of items. + * Dependencies: jQuery 1.9+, Modernizr 2.6.2+ + * @license MIT license + * @version 3.0.0 + */ + +/* Modernizr 2.6.2 (Custom Build) | MIT & BSD + * Build: http://modernizr.com/download/#-csstransforms-csstransforms3d-csstransitions-cssclasses-prefixed-teststyles-testprop-testallprops-prefixes-domprefixes + */ +window.Modernizr=function(a,b,c){function z(a){j.cssText=a}function A(a,b){return z(m.join(a+";")+(b||""))}function B(a,b){return typeof a===b}function C(a,b){return!!~(""+a).indexOf(b)}function D(a,b){for(var d in a){var e=a[d];if(!C(e,"-")&&j[e]!==c)return b=="pfx"?e:!0}return!1}function E(a,b,d){for(var e in a){var f=b[a[e]];if(f!==c)return d===!1?a[e]:B(f,"function")?f.bind(d||b):f}return!1}function F(a,b,c){var d=a.charAt(0).toUpperCase()+a.slice(1),e=(a+" "+o.join(d+" ")+d).split(" ");return B(b,"string")||B(b,"undefined")?D(e,b):(e=(a+" "+p.join(d+" ")+d).split(" "),E(e,b,c))}var d="2.6.2",e={},f=!0,g=b.documentElement,h="modernizr",i=b.createElement(h),j=i.style,k,l={}.toString,m=" -webkit- -moz- -o- -ms- ".split(" "),n="Webkit Moz O ms",o=n.split(" "),p=n.toLowerCase().split(" "),q={},r={},s={},t=[],u=t.slice,v,w=function(a,c,d,e){var f,i,j,k,l=b.createElement("div"),m=b.body,n=m||b.createElement("body");if(parseInt(d,10))while(d--)j=b.createElement("div"),j.id=e?e[d]:h+(d+1),l.appendChild(j);return f=["­",'"].join(""),l.id=h,(m?l:n).innerHTML+=f,n.appendChild(l),m||(n.style.background="",n.style.overflow="hidden",k=g.style.overflow,g.style.overflow="hidden",g.appendChild(n)),i=c(l,a),m?l.parentNode.removeChild(l):(n.parentNode.removeChild(n),g.style.overflow=k),!!i},x={}.hasOwnProperty,y;!B(x,"undefined")&&!B(x.call,"undefined")?y=function(a,b){return x.call(a,b)}:y=function(a,b){return b in a&&B(a.constructor.prototype[b],"undefined")},Function.prototype.bind||(Function.prototype.bind=function(b){var c=this;if(typeof c!="function")throw new TypeError;var d=u.call(arguments,1),e=function(){if(this instanceof e){var a=function(){};a.prototype=c.prototype;var f=new a,g=c.apply(f,d.concat(u.call(arguments)));return Object(g)===g?g:f}return c.apply(b,d.concat(u.call(arguments)))};return e}),q.csstransforms=function(){return!!F("transform")},q.csstransforms3d=function(){var a=!!F("perspective");return a&&"webkitPerspective"in g.style&&w("@media (transform-3d),(-webkit-transform-3d){#modernizr{left:9px;position:absolute;height:3px;}}",function(b,c){a=b.offsetLeft===9&&b.offsetHeight===3}),a},q.csstransitions=function(){return F("transition")};for(var G in q)y(q,G)&&(v=G.toLowerCase(),e[v]=q[G](),t.push((e[v]?"":"no-")+v));return e.addTest=function(a,b){if(typeof a=="object")for(var d in a)y(a,d)&&e.addTest(d,a[d]);else{a=a.toLowerCase();if(e[a]!==c)return e;b=typeof b=="function"?b():b,typeof f!="undefined"&&f&&(g.className+=" "+(b?"":"no-")+a),e[a]=b}return e},z(""),i=k=null,e._version=d,e._prefixes=m,e._domPrefixes=p,e._cssomPrefixes=o,e.testProp=function(a){return D([a])},e.testAllProps=F,e.testStyles=w,e.prefixed=function(a,b,c){return b?F(a,b,c):F(a,"pfx")},g.className=g.className.replace(/(^|\s)no-js(\s|$)/,"$1$2")+(f?" js "+t.join(" "):""),e}(this,this.document); + +(function (factory) { + if (typeof define === 'function' && define.amd) { + define(['jquery', 'modernizr'], factory); + } else { + window.Shuffle = factory(window.jQuery, window.Modernizr); + } +})(function($, Modernizr, undefined) { + +'use strict'; + + +// Validate Modernizr exists. +// Shuffle requires `csstransitions`, `csstransforms`, `csstransforms3d`, +// and `prefixed` to exist on the Modernizr object. +if (typeof Modernizr !== 'object') { + throw new Error('Shuffle.js requires Modernizr.\n' + + 'http://vestride.github.io/Shuffle/#dependencies'); +} + + +/** + * Returns css prefixed properties like `-webkit-transition` or `box-sizing` + * from `transition` or `boxSizing`, respectively. + * @param {(string|boolean)} prop Property to be prefixed. + * @return {string} The prefixed css property. + */ +function dashify( prop ) { + if (!prop) { + return ''; + } + + // Replace upper case with dash-lowercase, + // then fix ms- prefixes because they're not capitalized. + return prop.replace(/([A-Z])/g, function( str, m1 ) { + return '-' + m1.toLowerCase(); + }).replace(/^ms-/,'-ms-'); +} + +// Constant, prefixed variables. +var TRANSITION = Modernizr.prefixed('transition'); +var TRANSITION_DELAY = Modernizr.prefixed('transitionDelay'); +var TRANSITION_DURATION = Modernizr.prefixed('transitionDuration'); + +// Note(glen): Stock Android 4.1.x browser will fail here because it wrongly +// says it supports non-prefixed transitions. +// https://github.com/Modernizr/Modernizr/issues/897 +var TRANSITIONEND = { + 'WebkitTransition' : 'webkitTransitionEnd', + 'transition' : 'transitionend' +}[ TRANSITION ]; + +var TRANSFORM = Modernizr.prefixed('transform'); +var CSS_TRANSFORM = dashify(TRANSFORM); + +// Constants +var CAN_TRANSITION_TRANSFORMS = Modernizr.csstransforms && Modernizr.csstransitions; +var HAS_TRANSFORMS_3D = Modernizr.csstransforms3d; +var SHUFFLE = 'shuffle'; +var COLUMN_THRESHOLD = 0.3; + +// Configurable. You can change these constants to fit your application. +// The default scale and concealed scale, however, have to be different values. +var ALL_ITEMS = 'all'; +var FILTER_ATTRIBUTE_KEY = 'groups'; +var DEFAULT_SCALE = 1; +var CONCEALED_SCALE = 0.001; + + +// Underscore's throttle function. +function throttle(func, wait, options) { + var context, args, result; + var timeout = null; + var previous = 0; + options = options || {}; + var later = function() { + previous = options.leading === false ? 0 : $.now(); + timeout = null; + result = func.apply(context, args); + context = args = null; + }; + return function() { + var now = $.now(); + if (!previous && options.leading === false) { + previous = now; + } + var remaining = wait - (now - previous); + context = this; + args = arguments; + if (remaining <= 0 || remaining > wait) { + clearTimeout(timeout); + timeout = null; + previous = now; + result = func.apply(context, args); + context = args = null; + } else if (!timeout && options.trailing !== false) { + timeout = setTimeout(later, remaining); + } + return result; + }; +} + +function each(obj, iterator, context) { + for (var i = 0, length = obj.length; i < length; i++) { + if (iterator.call(context, obj[i], i, obj) === {}) { + return; + } + } +} + +function defer(fn, context, wait) { + return setTimeout( $.proxy( fn, context ), wait ); +} + +function arrayMax( array ) { + return Math.max.apply( Math, array ); +} + +function arrayMin( array ) { + return Math.min.apply( Math, array ); +} + + +/** + * Always returns a numeric value, given a value. + * @param {*} value Possibly numeric value. + * @return {number} `value` or zero if `value` isn't numeric. + * @private + */ +function getNumber(value) { + return $.isNumeric(value) ? value : 0; +} + + +/** + * Represents a coordinate pair. + * @param {number} [x=0] X. + * @param {number} [y=0] Y. + */ +var Point = function(x, y) { + this.x = getNumber( x ); + this.y = getNumber( y ); +}; + + +/** + * Whether two points are equal. + * @param {Point} a Point A. + * @param {Point} b Point B. + * @return {boolean} + */ +Point.equals = function(a, b) { + return a.x === b.x && a.y === b.y; +}; + + +// Used for unique instance variables +var id = 0; +var $window = $( window ); + + +/** + * Categorize, sort, and filter a responsive grid of items. + * + * @param {Element} element An element which is the parent container for the grid items. + * @param {Object} [options=Shuffle.options] Options object. + * @constructor + */ +var Shuffle = function( element, options ) { + options = options || {}; + $.extend( this, Shuffle.options, options, Shuffle.settings ); + + this.$el = $(element); + this.element = element; + this.unique = 'shuffle_' + id++; + + this._fire( Shuffle.EventType.LOADING ); + this._init(); + + // Dispatch the done event asynchronously so that people can bind to it after + // Shuffle has been initialized. + defer(function() { + this.initialized = true; + this._fire( Shuffle.EventType.DONE ); + }, this, 16); +}; + + +/** + * Events the container element emits with the .shuffle namespace. + * For example, "done.shuffle". + * @enum {string} + */ +Shuffle.EventType = { + LOADING: 'loading', + DONE: 'done', + LAYOUT: 'layout', + REMOVED: 'removed' +}; + + +/** @enum {string} */ +Shuffle.ClassName = { + BASE: SHUFFLE, + SHUFFLE_ITEM: 'shuffle-item', + FILTERED: 'filtered', + CONCEALED: 'concealed' +}; + + +// Overrideable options +Shuffle.options = { + group: ALL_ITEMS, // Initial filter group. + speed: 250, // Transition/animation speed (milliseconds). + easing: 'ease-out', // CSS easing function to use. + itemSelector: '', // e.g. '.picture-item'. + sizer: null, // Sizer element. Use an element to determine the size of columns and gutters. + gutterWidth: 0, // A static number or function that tells the plugin how wide the gutters between columns are (in pixels). + columnWidth: 0, // A static number or function that returns a number which tells the plugin how wide the columns are (in pixels). + delimeter: null, // If your group is not json, and is comma delimeted, you could set delimeter to ','. + buffer: 0, // Useful for percentage based heights when they might not always be exactly the same (in pixels). + initialSort: null, // Shuffle can be initialized with a sort object. It is the same object given to the sort method. + throttle: throttle, // By default, shuffle will throttle resize events. This can be changed or removed. + throttleTime: 300, // How often shuffle can be called on resize (in milliseconds). + sequentialFadeDelay: 150, // Delay between each item that fades in when adding items. + supported: CAN_TRANSITION_TRANSFORMS // Whether to use transforms or absolute positioning. +}; + + +// Not overrideable +Shuffle.settings = { + useSizer: false, + itemCss : { // default CSS for each item + position: 'absolute', + top: 0, + left: 0, + visibility: 'visible' + }, + revealAppendedDelay: 300, + lastSort: {}, + lastFilter: ALL_ITEMS, + enabled: true, + destroyed: false, + initialized: false, + _animations: [], + styleQueue: [] +}; + + +// Expose for testing. +Shuffle.Point = Point; + + +/** + * Static methods. + */ + +/** + * If the browser has 3d transforms available, build a string with those, + * otherwise use 2d transforms. + * @param {Point} point X and Y positions. + * @param {number} scale Scale amount. + * @return {string} A normalized string which can be used with the transform style. + * @private + */ +Shuffle._getItemTransformString = function(point, scale) { + if ( HAS_TRANSFORMS_3D ) { + return 'translate3d(' + point.x + 'px, ' + point.y + 'px, 0) scale3d(' + scale + ', ' + scale + ', 1)'; + } else { + return 'translate(' + point.x + 'px, ' + point.y + 'px) scale(' + scale + ')'; + } +}; + + +/** + * Retrieve the computed style for an element, parsed as a float. This should + * not be used for width or height values because jQuery mangles them and they + * are not precise enough. + * @param {Element} element Element to get style for. + * @param {string} style Style property. + * @return {number} The parsed computed value or zero if that fails because IE + * will return 'auto' when the element doesn't have margins instead of + * the computed style. + * @private + */ +Shuffle._getNumberStyle = function( element, style ) { + return Shuffle._getFloat( $( element ).css( style ) ); +}; + + +/** + * Parse a string as an integer. + * @param {string} value String integer. + * @return {number} The string as an integer or zero. + * @private + */ +Shuffle._getInt = function(value) { + return getNumber( parseInt( value, 10 ) ); +}; + +/** + * Parse a string as an float. + * @param {string} value String float. + * @return {number} The string as an float or zero. + * @private + */ +Shuffle._getFloat = function(value) { + return getNumber( parseFloat( value ) ); +}; + + +/** + * Returns the outer width of an element, optionally including its margins. + * The `offsetWidth` property must be used because having a scale transform + * on the element affects the bounding box. Sadly, Firefox doesn't return an + * integer value for offsetWidth (yet). + * @param {Element} element The element. + * @param {boolean} [includeMargins] Whether to include margins. Default is false. + * @return {number} The width. + */ +Shuffle._getOuterWidth = function( element, includeMargins ) { + var width = element.offsetWidth; + + // Use jQuery here because it uses getComputedStyle internally and is + // cross-browser. Using the style property of the element will only work + // if there are inline styles. + if ( includeMargins ) { + var marginLeft = Shuffle._getNumberStyle( element, 'marginLeft'); + var marginRight = Shuffle._getNumberStyle( element, 'marginRight'); + width += marginLeft + marginRight; + } + + return width; +}; + + +/** + * Returns the outer height of an element, optionally including its margins. + * @param {Element} element The element. + * @param {boolean} [includeMargins] Whether to include margins. Default is false. + * @return {number} The height. + */ +Shuffle._getOuterHeight = function( element, includeMargins ) { + var height = element.offsetHeight; + + if ( includeMargins ) { + var marginTop = Shuffle._getNumberStyle( element, 'marginTop'); + var marginBottom = Shuffle._getNumberStyle( element, 'marginBottom'); + height += marginTop + marginBottom; + } + + return height; +}; + + +/** + * Change a property or execute a function which will not have a transition + * @param {Element} element DOM element that won't be transitioned + * @param {Function} callback A function which will be called while transition + * is set to 0ms. + * @param {Object} [context] Optional context for the callback function. + * @private + */ +Shuffle._skipTransition = function( element, callback, context ) { + var duration = element.style[ TRANSITION_DURATION ]; + + // Set the duration to zero so it happens immediately + element.style[ TRANSITION_DURATION ] = '0ms'; // ms needed for firefox! + + callback.call( context ); + + // Force reflow + var reflow = element.offsetWidth; + // Avoid jshint warnings: unused variables and expressions. + reflow = null; + + // Put the duration back + element.style[ TRANSITION_DURATION ] = duration; +}; + + +/** + * Instance methods. + */ + +Shuffle.prototype._init = function() { + this.$items = this._getItems(); + + this.sizer = this._getElementOption( this.sizer ); + + if ( this.sizer ) { + this.useSizer = true; + } + + // Add class and invalidate styles + this.$el.addClass( Shuffle.ClassName.BASE ); + + // Set initial css for each item + this._initItems(); + + // Bind resize events + // http://stackoverflow.com/questions/1852751/window-resize-event-firing-in-internet-explorer + $window.on('resize.' + SHUFFLE + '.' + this.unique, this._getResizeFunction()); + + // Get container css all in one request. Causes reflow + var containerCSS = this.$el.css(['position', 'overflow']); + var containerWidth = Shuffle._getOuterWidth( this.element ); + + // Add styles to the container if it doesn't have them. + this._validateStyles( containerCSS ); + + // We already got the container's width above, no need to cause another reflow getting it again... + // Calculate the number of columns there will be + this._setColumns( containerWidth ); + + // Kick off! + this.shuffle( this.group, this.initialSort ); + + // The shuffle items haven't had transitions set on them yet + // so the user doesn't see the first layout. Set them now that the first layout is done. + if ( this.supported ) { + defer(function() { + this._setTransitions(); + this.element.style[ TRANSITION ] = 'height ' + this.speed + 'ms ' + this.easing; + }, this); + } +}; + + +/** + * Returns a throttled and proxied function for the resize handler. + * @return {Function} + * @private + */ +Shuffle.prototype._getResizeFunction = function() { + var resizeFunction = $.proxy( this._onResize, this ); + return this.throttle ? + this.throttle( resizeFunction, this.throttleTime ) : + resizeFunction; +}; + + +/** + * Retrieve an element from an option. + * @param {string|jQuery|Element} option The option to check. + * @return {?Element} The plain element or null. + * @private + */ +Shuffle.prototype._getElementOption = function( option ) { + // If column width is a string, treat is as a selector and search for the + // sizer element within the outermost container + if ( typeof option === 'string' ) { + return this.$el.find( option )[0] || null; + + // Check for an element + } else if ( option && option.nodeType && option.nodeType === 1 ) { + return option; + + // Check for jQuery object + } else if ( option && option.jquery ) { + return option[0]; + } + + return null; +}; + + +/** + * Ensures the shuffle container has the css styles it needs applied to it. + * @param {Object} styles Key value pairs for position and overflow. + * @private + */ +Shuffle.prototype._validateStyles = function(styles) { + // Position cannot be static. + if ( styles.position === 'static' ) { + this.element.style.position = 'relative'; + } + + // Overflow has to be hidden + if ( styles.overflow !== 'hidden' ) { + this.element.style.overflow = 'hidden'; + } +}; + + +/** + * Filter the elements by a category. + * @param {string} [category] Category to filter by. If it's given, the last + * category will be used to filter the items. + * @param {ArrayLike} [$collection] Optionally filter a collection. Defaults to + * all the items. + * @return {jQuery} Filtered items. + * @private + */ +Shuffle.prototype._filter = function( category, $collection ) { + category = category || this.lastFilter; + $collection = $collection || this.$items; + + var set = this._getFilteredSets( category, $collection ); + + // Individually add/remove concealed/filtered classes + this._toggleFilterClasses( set.filtered, set.concealed ); + + // Save the last filter in case elements are appended. + this.lastFilter = category; + + // This is saved mainly because providing a filter function (like searching) + // will overwrite the `lastFilter` property every time its called. + if ( typeof category === 'string' ) { + this.group = category; + } + + return set.filtered; +}; + + +/** + * Returns an object containing the filtered and concealed elements. + * @param {string|Function} category Category or function to filter by. + * @param {ArrayLike.} $items A collection of items to filter. + * @return {!{filtered: jQuery, concealed: jQuery}} + * @private + */ +Shuffle.prototype._getFilteredSets = function( category, $items ) { + var $filtered = $(); + var $concealed = $(); + + // category === 'all', add filtered class to everything + if ( category === ALL_ITEMS ) { + $filtered = $items; + + // Loop through each item and use provided function to determine + // whether to hide it or not. + } else { + each($items, function( el ) { + var $item = $(el); + if ( this._doesPassFilter( category, $item ) ) { + $filtered = $filtered.add( $item ); + } else { + $concealed = $concealed.add( $item ); + } + }, this); + } + + return { + filtered: $filtered, + concealed: $concealed + }; +}; + + +/** + * Test an item to see if it passes a category. + * @param {string|Function} category Category or function to filter by. + * @param {jQuery} $item A single item, wrapped with jQuery. + * @return {boolean} Whether it passes the category/filter. + * @private + */ +Shuffle.prototype._doesPassFilter = function( category, $item ) { + if ( $.isFunction( category ) ) { + return category.call( $item[0], $item, this ); + + // Check each element's data-groups attribute against the given category. + } else { + var groups = $item.data( FILTER_ATTRIBUTE_KEY ); + var keys = this.delimeter && !$.isArray( groups ) ? + groups.split( this.delimeter ) : + groups; + return $.inArray(category, keys) > -1; + } +}; + + +/** + * Toggles the filtered and concealed class names. + * @param {jQuery} $filtered Filtered set. + * @param {jQuery} $concealed Concealed set. + * @private + */ +Shuffle.prototype._toggleFilterClasses = function( $filtered, $concealed ) { + $filtered + .removeClass( Shuffle.ClassName.CONCEALED ) + .addClass( Shuffle.ClassName.FILTERED ); + $concealed + .removeClass( Shuffle.ClassName.FILTERED ) + .addClass( Shuffle.ClassName.CONCEALED ); +}; + + +/** + * Set the initial css for each item + * @param {jQuery} [$items] Optionally specifiy at set to initialize + */ +Shuffle.prototype._initItems = function( $items ) { + $items = $items || this.$items; + $items.addClass([ + Shuffle.ClassName.SHUFFLE_ITEM, + Shuffle.ClassName.FILTERED + ].join(' ')); + $items.css( this.itemCss ).data('point', new Point()).data('scale', DEFAULT_SCALE); +}; + + +/** + * Updates the filtered item count. + * @private + */ +Shuffle.prototype._updateItemCount = function() { + this.visibleItems = this._getFilteredItems().length; +}; + + +/** + * Sets css transform transition on a an element. + * @param {Element} element Element to set transition on. + * @private + */ +Shuffle.prototype._setTransition = function( element ) { + element.style[ TRANSITION ] = CSS_TRANSFORM + ' ' + this.speed + 'ms ' + + this.easing + ', opacity ' + this.speed + 'ms ' + this.easing; +}; + + +/** + * Sets css transform transition on a group of elements. + * @param {ArrayLike.} $items Elements to set transitions on. + * @private + */ +Shuffle.prototype._setTransitions = function( $items ) { + $items = $items || this.$items; + each($items, function( el ) { + this._setTransition( el ); + }, this); +}; + + +/** + * Sets a transition delay on a collection of elements, making each delay + * greater than the last. + * @param {ArrayLike.} $collection Array to iterate over. + */ +Shuffle.prototype._setSequentialDelay = function( $collection ) { + if ( !this.supported ) { + return; + } + + // $collection can be an array of dom elements or jquery object + each($collection, function( el, i ) { + // This works because the transition-property: transform, opacity; + el.style[ TRANSITION_DELAY ] = '0ms,' + ((i + 1) * this.sequentialFadeDelay) + 'ms'; + }, this); +}; + + +Shuffle.prototype._getItems = function() { + return this.$el.children( this.itemSelector ); +}; + + +Shuffle.prototype._getFilteredItems = function() { + return this.$items.filter('.' + Shuffle.ClassName.FILTERED); +}; + + +Shuffle.prototype._getConcealedItems = function() { + return this.$items.filter('.' + Shuffle.ClassName.CONCEALED); +}; + + +/** + * Returns the column size, based on column width and sizer options. + * @param {number} containerWidth Size of the parent container. + * @param {number} gutterSize Size of the gutters. + * @return {number} + * @private + */ +Shuffle.prototype._getColumnSize = function( containerWidth, gutterSize ) { + var size; + + // If the columnWidth property is a function, then the grid is fluid + if ( $.isFunction( this.columnWidth ) ) { + size = this.columnWidth(containerWidth); + + // columnWidth option isn't a function, are they using a sizing element? + } else if ( this.useSizer ) { + size = Shuffle._getOuterWidth(this.sizer); + + // if not, how about the explicitly set option? + } else if ( this.columnWidth ) { + size = this.columnWidth; + + // or use the size of the first item + } else if ( this.$items.length > 0 ) { + size = Shuffle._getOuterWidth(this.$items[0], true); + + // if there's no items, use size of container + } else { + size = containerWidth; + } + + // Don't let them set a column width of zero. + if ( size === 0 ) { + size = containerWidth; + } + + return size + gutterSize; +}; + + +/** + * Returns the gutter size, based on gutter width and sizer options. + * @param {number} containerWidth Size of the parent container. + * @return {number} + * @private + */ +Shuffle.prototype._getGutterSize = function( containerWidth ) { + var size; + if ( $.isFunction( this.gutterWidth ) ) { + size = this.gutterWidth(containerWidth); + } else if ( this.useSizer ) { + size = Shuffle._getNumberStyle(this.sizer, 'marginLeft'); + } else { + size = this.gutterWidth; + } + + return size; +}; + + +/** + * Calculate the number of columns to be used. Gets css if using sizer element. + * @param {number} [theContainerWidth] Optionally specify a container width if it's already available. + */ +Shuffle.prototype._setColumns = function( theContainerWidth ) { + var containerWidth = theContainerWidth || Shuffle._getOuterWidth( this.element ); + var gutter = this._getGutterSize( containerWidth ); + var columnWidth = this._getColumnSize( containerWidth, gutter ); + var calculatedColumns = (containerWidth + gutter) / columnWidth; + + // Widths given from getComputedStyle are not precise enough... + if ( Math.abs(Math.round(calculatedColumns) - calculatedColumns) < COLUMN_THRESHOLD ) { + // e.g. calculatedColumns = 11.998876 + calculatedColumns = Math.round( calculatedColumns ); + } + + this.cols = Math.max( Math.floor(calculatedColumns), 1 ); + this.containerWidth = containerWidth; + this.colWidth = columnWidth; +}; + +/** + * Adjust the height of the grid + */ +Shuffle.prototype._setContainerSize = function() { + this.$el.css( 'height', this._getContainerSize() ); +}; + + +/** + * Based on the column heights, it returns the biggest one. + * @return {number} + * @private + */ +Shuffle.prototype._getContainerSize = function() { + return arrayMax( this.positions ); +}; + + +/** + * Fire events with .shuffle namespace + */ +Shuffle.prototype._fire = function( name, args ) { + this.$el.trigger( name + '.' + SHUFFLE, args && args.length ? args : [ this ] ); +}; + + +/** + * Zeros out the y columns array, which is used to determine item placement. + * @private + */ +Shuffle.prototype._resetCols = function() { + var i = this.cols; + this.positions = []; + while (i--) { + this.positions.push( 0 ); + } +}; + + +/** + * Loops through each item that should be shown and calculates the x, y position. + * @param {Array.} items Array of items that will be shown/layed out in order in their array. + * Because jQuery collection are always ordered in DOM order, we can't pass a jq collection. + * @param {boolean} [isOnlyPosition=false] If true this will position the items with zero opacity. + */ +Shuffle.prototype._layout = function( items, isOnlyPosition ) { + each(items, function( item ) { + this._layoutItem( item, !!isOnlyPosition ); + }, this); + + // `_layout` always happens after `_shrink`, so it's safe to process the style + // queue here with styles from the shrink method. + this._processStyleQueue(); + + // Adjust the height of the container. + this._setContainerSize(); +}; + + +/** + * Calculates the position of the item and pushes it onto the style queue. + * @param {Element} item Element which is being positioned. + * @param {boolean} isOnlyPosition Whether to position the item, but with zero + * opacity so that it can fade in later. + * @private + */ +Shuffle.prototype._layoutItem = function( item, isOnlyPosition ) { + var $item = $(item); + var itemData = $item.data(); + var currPos = itemData.point; + var currScale = itemData.scale; + var itemSize = { + width: Shuffle._getOuterWidth( item, true ), + height: Shuffle._getOuterHeight( item, true ) + }; + var pos = this._getItemPosition( itemSize ); + + // If the item will not change its position, do not add it to the render + // queue. Transitions don't fire when setting a property to the same value. + if ( Point.equals(currPos, pos) && currScale === DEFAULT_SCALE ) { + return; + } + + // Save data for shrink + itemData.point = pos; + itemData.scale = DEFAULT_SCALE; + + this.styleQueue.push({ + $item: $item, + point: pos, + scale: DEFAULT_SCALE, + opacity: isOnlyPosition ? 0 : 1, + skipTransition: isOnlyPosition, + callfront: function() { + if ( !isOnlyPosition ) { + $item.css( 'visibility', 'visible' ); + } + }, + callback: function() { + if ( isOnlyPosition ) { + $item.css( 'visibility', 'hidden' ); + } + } + }); +}; + + +/** + * Determine the location of the next item, based on its size. + * @param {{width: number, height: number}} itemSize Object with width and height. + * @return {Point} + * @private + */ +Shuffle.prototype._getItemPosition = function( itemSize ) { + var columnSpan = this._getColumnSpan( itemSize.width, this.colWidth, this.cols ); + + var setY = this._getColumnSet( columnSpan, this.cols ); + + // Finds the index of the smallest number in the set. + var shortColumnIndex = this._getShortColumn( setY, this.buffer ); + + // Position the item + var point = new Point( + Math.round( this.colWidth * shortColumnIndex ), + Math.round( setY[shortColumnIndex] )); + + // Update the columns array with the new values for each column. + // e.g. before the update the columns could be [250, 0, 0, 0] for an item + // which spans 2 columns. After it would be [250, itemHeight, itemHeight, 0]. + var setHeight = setY[shortColumnIndex] + itemSize.height; + var setSpan = this.cols + 1 - setY.length; + for ( var i = 0; i < setSpan; i++ ) { + this.positions[ shortColumnIndex + i ] = setHeight; + } + + return point; +}; + + +/** + * Determine the number of columns an items spans. + * @param {number} itemWidth Width of the item. + * @param {number} columnWidth Width of the column (includes gutter). + * @param {number} columns Total number of columns + * @return {number} + * @private + */ +Shuffle.prototype._getColumnSpan = function( itemWidth, columnWidth, columns ) { + var columnSpan = itemWidth / columnWidth; + + // If the difference between the rounded column span number and the + // calculated column span number is really small, round the number to + // make it fit. + if ( Math.abs(Math.round( columnSpan ) - columnSpan ) < COLUMN_THRESHOLD ) { + // e.g. columnSpan = 4.0089945390298745 + columnSpan = Math.round( columnSpan ); + } + + // Ensure the column span is not more than the amount of columns in the whole layout. + return Math.min( Math.ceil( columnSpan ), columns ); +}; + + +/** + * Retrieves the column set to use for placement. + * @param {number} columnSpan The number of columns this current item spans. + * @param {number} columns The total columns in the grid. + * @return {Array.} An array of numbers represeting the column set. + * @private + */ +Shuffle.prototype._getColumnSet = function( columnSpan, columns ) { + // The item spans only one column. + if ( columnSpan === 1 ) { + return this.positions; + + // The item spans more than one column, figure out how many different + // places it could fit horizontally. + // The group count is the number of places within the positions this block + // could fit, ignoring the current positions of items. + // Imagine a 2 column brick as the second item in a 4 column grid with + // 10px height each. Find the places it would fit: + // [10, 0, 0, 0] + // | | | + // * * * + // + // Then take the places which fit and get the bigger of the two: + // max([10, 0]), max([0, 0]), max([0, 0]) = [10, 0, 0] + // + // Next, find the first smallest number (the short column). + // [10, 0, 0] + // | + // * + // + // And that's where it should be placed! + } else { + var groupCount = columns + 1 - columnSpan; + var groupY = []; + + // For how many possible positions for this item there are. + for ( var i = 0; i < groupCount; i++ ) { + // Find the bigger value for each place it could fit. + groupY[i] = arrayMax( this.positions.slice( i, i + columnSpan ) ); + } + + return groupY; + } +}; + + +/** + * Find index of short column, the first from the left where this item will go. + * + * @param {Array.} positions The array to search for the smallest number. + * @param {number} buffer Optional buffer which is very useful when the height + * is a percentage of the width. + * @return {number} Index of the short column. + * @private + */ +Shuffle.prototype._getShortColumn = function( positions, buffer ) { + var minPosition = arrayMin( positions ); + for (var i = 0, len = positions.length; i < len; i++) { + if ( positions[i] >= minPosition - buffer && positions[i] <= minPosition + buffer ) { + return i; + } + } + return 0; +}; + + +/** + * Hides the elements that don't match our filter. + * @param {jQuery} $collection jQuery collection to shrink. + * @private + */ +Shuffle.prototype._shrink = function( $collection ) { + var $concealed = $collection || this._getConcealedItems(); + + each($concealed, function( item ) { + var $item = $(item); + var itemData = $item.data(); + + // Continuing would add a transitionend event listener to the element, but + // that listener would not execute because the transform and opacity would + // stay the same. + if ( itemData.scale === CONCEALED_SCALE ) { + return; + } + + itemData.scale = CONCEALED_SCALE; + + this.styleQueue.push({ + $item: $item, + point: itemData.point, + scale : CONCEALED_SCALE, + opacity: 0, + callback: function() { + $item.css( 'visibility', 'hidden' ); + } + }); + }, this); +}; + + +/** + * Resize handler. + * @private + */ +Shuffle.prototype._onResize = function() { + // If shuffle is disabled, destroyed, don't do anything + if ( !this.enabled || this.destroyed || this.isTransitioning ) { + return; + } + + // Will need to check height in the future if it's layed out horizontaly + var containerWidth = Shuffle._getOuterWidth( this.element ); + + // containerWidth hasn't changed, don't do anything + if ( containerWidth === this.containerWidth ) { + return; + } + + this.update(); +}; + + +/** + * Returns styles for either jQuery animate or transition. + * @param {Object} opts Transition options. + * @return {!Object} Transforms for transitions, left/top for animate. + * @private + */ +Shuffle.prototype._getStylesForTransition = function( opts ) { + var styles = { + opacity: opts.opacity + }; + + if ( this.supported ) { + styles[ TRANSFORM ] = Shuffle._getItemTransformString( opts.point, opts.scale ); + } else { + styles.left = opts.point.x; + styles.top = opts.point.y; + } + + return styles; +}; + + +/** + * Transitions an item in the grid + * + * @param {Object} opts options. + * @param {jQuery} opts.$item jQuery object representing the current item. + * @param {Point} opts.point A point object with the x and y coordinates. + * @param {number} opts.scale Amount to scale the item. + * @param {number} opts.opacity Opacity of the item. + * @param {Function} opts.callback Complete function for the animation. + * @param {Function} opts.callfront Function to call before transitioning. + * @private + */ +Shuffle.prototype._transition = function( opts ) { + var styles = this._getStylesForTransition( opts ); + this._startItemAnimation( opts.$item, styles, opts.callfront || $.noop, opts.callback || $.noop ); +}; + + +Shuffle.prototype._startItemAnimation = function( $item, styles, callfront, callback ) { + // Transition end handler removes its listener. + function handleTransitionEnd( evt ) { + // Make sure this event handler has not bubbled up from a child. + if ( evt.target === evt.currentTarget ) { + $( evt.target ).off( TRANSITIONEND, handleTransitionEnd ); + callback(); + } + } + + callfront(); + + // Transitions are not set until shuffle has loaded to avoid the initial transition. + if ( !this.initialized ) { + $item.css( styles ); + callback(); + return; + } + + // Use CSS Transforms if we have them + if ( this.supported ) { + $item.css( styles ); + $item.on( TRANSITIONEND, handleTransitionEnd ); + + // Use jQuery to animate left/top + } else { + // Save the deferred object which jQuery returns. + var anim = $item.stop( true ).animate( styles, this.speed, 'swing', callback ); + // Push the animation to the list of pending animations. + this._animations.push( anim.promise() ); + } +}; + + +/** + * Execute the styles gathered in the style queue. This applies styles to elements, + * triggering transitions. + * @param {boolean} noLayout Whether to trigger a layout event. + * @private + */ +Shuffle.prototype._processStyleQueue = function( noLayout ) { + var $transitions = $(); + + // Iterate over the queue and keep track of ones that use transitions. + each(this.styleQueue, function( transitionObj ) { + if ( transitionObj.skipTransition ) { + this._styleImmediately( transitionObj ); + } else { + $transitions = $transitions.add( transitionObj.$item ); + this._transition( transitionObj ); + } + }, this); + + + if ( $transitions.length > 0 && this.initialized ) { + // Set flag that shuffle is currently in motion. + this.isTransitioning = true; + + if ( this.supported ) { + this._whenCollectionDone( $transitions, TRANSITIONEND, this._movementFinished ); + + // The _transition function appends a promise to the animations array. + // When they're all complete, do things. + } else { + this._whenAnimationsDone( this._movementFinished ); + } + + // A call to layout happened, but none of the newly filtered items will + // change position. Asynchronously fire the callback here. + } else if ( !noLayout ) { + defer( this._layoutEnd, this ); + } + + // Remove everything in the style queue + this.styleQueue.length = 0; +}; + + +/** + * Apply styles without a transition. + * @param {Object} opts Transitions options object. + * @private + */ +Shuffle.prototype._styleImmediately = function( opts ) { + Shuffle._skipTransition(opts.$item[0], function() { + opts.$item.css( this._getStylesForTransition( opts ) ); + }, this); +}; + +Shuffle.prototype._movementFinished = function() { + this.isTransitioning = false; + this._layoutEnd(); +}; + +Shuffle.prototype._layoutEnd = function() { + this._fire( Shuffle.EventType.LAYOUT ); +}; + +Shuffle.prototype._addItems = function( $newItems, addToEnd, isSequential ) { + // Add classes and set initial positions. + this._initItems( $newItems ); + + // Add transition to each item. + this._setTransitions( $newItems ); + + // Update the list of + this.$items = this._getItems(); + + // Shrink all items (without transitions). + this._shrink( $newItems ); + each(this.styleQueue, function( transitionObj ) { + transitionObj.skipTransition = true; + }); + + // Apply shrink positions, but do not cause a layout event. + this._processStyleQueue( true ); + + if ( addToEnd ) { + this._addItemsToEnd( $newItems, isSequential ); + } else { + this.shuffle( this.lastFilter ); + } +}; + + +Shuffle.prototype._addItemsToEnd = function( $newItems, isSequential ) { + // Get ones that passed the current filter + var $passed = this._filter( null, $newItems ); + var passed = $passed.get(); + + // How many filtered elements? + this._updateItemCount(); + + this._layout( passed, true ); + + if ( isSequential && this.supported ) { + this._setSequentialDelay( passed ); + } + + this._revealAppended( passed ); +}; + + +/** + * Triggers appended elements to fade in. + * @param {ArrayLike.} $newFilteredItems Collection of elements. + * @private + */ +Shuffle.prototype._revealAppended = function( newFilteredItems ) { + defer(function() { + each(newFilteredItems, function( el ) { + var $item = $( el ); + this._transition({ + $item: $item, + opacity: 1, + point: $item.data('point'), + scale: DEFAULT_SCALE + }); + }, this); + + this._whenCollectionDone($(newFilteredItems), TRANSITIONEND, function() { + $(newFilteredItems).css( TRANSITION_DELAY, '0ms' ); + this._movementFinished(); + }); + }, this, this.revealAppendedDelay); +}; + + +/** + * Execute a function when an event has been triggered for every item in a collection. + * @param {jQuery} $collection Collection of elements. + * @param {string} eventName Event to listen for. + * @param {Function} callback Callback to execute when they're done. + * @private + */ +Shuffle.prototype._whenCollectionDone = function( $collection, eventName, callback ) { + var done = 0; + var items = $collection.length; + var self = this; + + function handleEventName( evt ) { + if ( evt.target === evt.currentTarget ) { + $( evt.target ).off( eventName, handleEventName ); + done++; + + // Execute callback if all items have emitted the correct event. + if ( done === items ) { + callback.call( self ); + } + } + } + + // Bind the event to all items. + $collection.on( eventName, handleEventName ); +}; + + +/** + * Execute a callback after jQuery `animate` for a collection has finished. + * @param {Function} callback Callback to execute when they're done. + * @private + */ +Shuffle.prototype._whenAnimationsDone = function( callback ) { + $.when.apply( null, this._animations ).always( $.proxy( function() { + this._animations.length = 0; + callback.call( this ); + }, this )); +}; + + +/** + * Public Methods + */ + +/** + * The magic. This is what makes the plugin 'shuffle' + * @param {string|Function} [category] Category to filter by. Can be a function + * @param {Object} [sortObj] A sort object which can sort the filtered set + */ +Shuffle.prototype.shuffle = function( category, sortObj ) { + if ( !this.enabled || this.isTransitioning ) { + return; + } + + if ( !category ) { + category = ALL_ITEMS; + } + + this._filter( category ); + + // How many filtered elements? + this._updateItemCount(); + + // Shrink each concealed item + this._shrink(); + + // Update transforms on .filtered elements so they will animate to their new positions + this.sort( sortObj ); +}; + + +/** + * Gets the .filtered elements, sorts them, and passes them to layout. + * @param {Object} opts the options object for the sorted plugin + */ +Shuffle.prototype.sort = function( opts ) { + if ( this.enabled && !this.isTransitioning ) { + this._resetCols(); + + var sortOptions = opts || this.lastSort; + var items = this._getFilteredItems().sorted( sortOptions ); + + this._layout( items ); + + this.lastSort = sortOptions; + } +}; + + +/** + * Reposition everything. + * @param {boolean} isOnlyLayout If true, column and gutter widths won't be + * recalculated. + */ +Shuffle.prototype.update = function( isOnlyLayout ) { + if ( this.enabled && !this.isTransitioning ) { + + if ( !isOnlyLayout ) { + // Get updated colCount + this._setColumns(); + } + + // Layout items + this.sort(); + } +}; + + +/** + * Use this instead of `update()` if you don't need the columns and gutters updated + * Maybe an image inside `shuffle` loaded (and now has a height), which means calculations + * could be off. + */ +Shuffle.prototype.layout = function() { + this.update( true ); +}; + + +/** + * New items have been appended to shuffle. Fade them in sequentially + * @param {jQuery} $newItems jQuery collection of new items + * @param {boolean} [addToEnd=false] If true, new items will be added to the end / bottom + * of the items. If not true, items will be mixed in with the current sort order. + * @param {boolean} [isSequential=true] If false, new items won't sequentially fade in + */ +Shuffle.prototype.appended = function( $newItems, addToEnd, isSequential ) { + this._addItems( $newItems, addToEnd === true, isSequential !== false ); +}; + + +/** + * Disables shuffle from updating dimensions and layout on resize + */ +Shuffle.prototype.disable = function() { + this.enabled = false; +}; + + +/** + * Enables shuffle again + * @param {boolean} [isUpdateLayout=true] if undefined, shuffle will update columns and gutters + */ +Shuffle.prototype.enable = function( isUpdateLayout ) { + this.enabled = true; + if ( isUpdateLayout !== false ) { + this.update(); + } +}; + + +/** + * Remove 1 or more shuffle items + * @param {jQuery} $collection A jQuery object containing one or more element in shuffle + * @return {Shuffle} The shuffle object + */ +Shuffle.prototype.remove = function( $collection ) { + + // If this isn't a jquery object, exit + if ( !$collection.length || !$collection.jquery ) { + return; + } + + function handleRemoved() { + // Remove the collection in the callback + $collection.remove(); + + // Update things now that elements have been removed. + this.$items = this._getItems(); + this._updateItemCount(); + + this._fire( Shuffle.EventType.REMOVED, [ $collection, this ] ); + + // Let it get garbage collected + $collection = null; + } + + // Hide collection first. + this._toggleFilterClasses( $(), $collection ); + this._shrink( $collection ); + + this.sort(); + + this.$el.one( Shuffle.EventType.LAYOUT + '.' + SHUFFLE, $.proxy( handleRemoved, this ) ); +}; + + +/** + * Destroys shuffle, removes events, styles, and classes + */ +Shuffle.prototype.destroy = function() { + // If there is more than one shuffle instance on the page, + // removing the resize handler from the window would remove them + // all. This is why a unique value is needed. + $window.off('.' + this.unique); + + // Reset container styles + this.$el + .removeClass( SHUFFLE ) + .removeAttr('style') + .removeData( SHUFFLE ); + + // Reset individual item styles + this.$items + .removeAttr('style') + .removeData('point') + .removeData('scale') + .removeClass([ + Shuffle.ClassName.CONCEALED, + Shuffle.ClassName.FILTERED, + Shuffle.ClassName.SHUFFLE_ITEM + ].join(' ')); + + // Null DOM references + this.$items = null; + this.$el = null; + this.sizer = null; + this.element = null; + + // Set a flag so if a debounced resize has been triggered, + // it can first check if it is actually destroyed and not doing anything + this.destroyed = true; +}; + + +// Plugin definition +$.fn.shuffle = function( opts ) { + var args = Array.prototype.slice.call( arguments, 1 ); + return this.each(function() { + var $this = $( this ); + var shuffle = $this.data( SHUFFLE ); + + // If we don't have a stored shuffle, make a new one and save it + if ( !shuffle ) { + shuffle = new Shuffle( this, opts ); + $this.data( SHUFFLE, shuffle ); + } else if ( typeof opts === 'string' && shuffle[ opts ] ) { + shuffle[ opts ].apply( shuffle, args ); + } + }); +}; + + +// http://stackoverflow.com/a/962890/373422 +function randomize( array ) { + var tmp, current; + var top = array.length; + + if ( !top ) { + return array; + } + + while ( --top ) { + current = Math.floor( Math.random() * (top + 1) ); + tmp = array[ current ]; + array[ current ] = array[ top ]; + array[ top ] = tmp; + } + + return array; +} + + +// You can return `undefined` from the `by` function to revert to DOM order +// This plugin does NOT return a jQuery object. It returns a plain array because +// jQuery sorts everything in DOM order. +$.fn.sorted = function(options) { + var opts = $.extend({}, $.fn.sorted.defaults, options); + var arr = this.get(); + var revert = false; + + if ( !arr.length ) { + return []; + } + + if ( opts.randomize ) { + return randomize( arr ); + } + + // Sort the elements by the opts.by function. + // If we don't have opts.by, default to DOM order + if ( $.isFunction( opts.by ) ) { + arr.sort(function(a, b) { + + // Exit early if we already know we want to revert + if ( revert ) { + return 0; + } + + var valA = opts.by($(a)); + var valB = opts.by($(b)); + + // If both values are undefined, use the DOM order + if ( valA === undefined && valB === undefined ) { + revert = true; + return 0; + } + + if ( valA < valB || valA === 'sortFirst' || valB === 'sortLast' ) { + return -1; + } + + if ( valA > valB || valA === 'sortLast' || valB === 'sortFirst' ) { + return 1; + } + + return 0; + }); + } + + // Revert to the original array if necessary + if ( revert ) { + return this.get(); + } + + if ( opts.reverse ) { + arr.reverse(); + } + + return arr; +}; + + +$.fn.sorted.defaults = { + reverse: false, // Use array.reverse() to reverse the results + by: null, // Sorting function + randomize: false // If true, this will skip the sorting and return a randomized order in the array +}; + +return Shuffle; + +}); \ No newline at end of file diff --git a/js/mydoc_scroll.html b/js/mydoc_scroll.html new file mode 100644 index 0000000000..292f6e984a --- /dev/null +++ b/js/mydoc_scroll.html @@ -0,0 +1,1674 @@ + + + + + + + + +Scroll layout | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + + +
+
 
+ +
+ + + +
+ + + + + + + + + + + + + + +
+ + + + +
+
+

Scroll layout

+
+ + + +
+ + +
This page demonstrates how you the integration of a script called ScrollTo, which is used here to link definitions of a JSON code sample to a list of definitions for that particular term. The scenario here is that the JSON blocks are really long, with extensive nesting and subnesting, which makes it difficult for tables below the JSON to adequately explain the term in a usable way.
+ + + + + + + +
+ + + + + + + + + + Edit me + + + + + + + + + + + + + + + + +
+
+ + +
+
+ + + + + + + + +
+ + Tags: + + + + + +
+ + + +
+ +
+ +
+
+ +
+
+ + +
+ +
+ +
+
+ + + diff --git a/js/toc.js b/js/toc.js new file mode 100644 index 0000000000..a54d172efc --- /dev/null +++ b/js/toc.js @@ -0,0 +1,82 @@ +// https://github.com/ghiculescu/jekyll-table-of-contents +(function($){ + $.fn.toc = function(options) { + var defaults = { + noBackToTopLinks: false, + title: '', + minimumHeaders: 3, + headers: 'h1, h2, h3, h4', + listType: 'ol', // values: [ol|ul] + showEffect: 'show', // values: [show|slideDown|fadeIn|none] + showSpeed: 'slow' // set to 0 to deactivate effect + }, + settings = $.extend(defaults, options); + + var headers = $(settings.headers).filter(function() { + // get all headers with an ID + var previousSiblingName = $(this).prev().attr( "name" ); + if (!this.id && previousSiblingName) { + this.id = $(this).attr( "id", previousSiblingName.replace(/\./g, "-") ); + } + return this.id; + }), output = $(this); + if (!headers.length || headers.length < settings.minimumHeaders || !output.length) { + return; + } + + if (0 === settings.showSpeed) { + settings.showEffect = 'none'; + } + + var render = { + show: function() { output.hide().html(html).show(settings.showSpeed); }, + slideDown: function() { output.hide().html(html).slideDown(settings.showSpeed); }, + fadeIn: function() { output.hide().html(html).fadeIn(settings.showSpeed); }, + none: function() { output.html(html); } + }; + + var get_level = function(ele) { return parseInt(ele.nodeName.replace("H", ""), 10); } + var highest_level = headers.map(function(_, ele) { return get_level(ele); }).get().sort()[0]; + var return_to_top = ' '; + + var level = get_level(headers[0]), + this_level, + html = settings.title + " <"+settings.listType+">"; + headers.on('click', function() { + if (!settings.noBackToTopLinks) { + window.location.hash = this.id; + } + }) + .addClass('clickable-header') + .each(function(_, header) { + this_level = get_level(header); + if (!settings.noBackToTopLinks && this_level === highest_level) { + $(header).addClass('top-level-header').after(return_to_top); + } + if (this_level === level) // same level as before; same indenting + html += "
  • " + header.innerHTML + ""; + else if (this_level <= level){ // higher level than before; end parent ol + for(i = this_level; i < level; i++) { + html += "
  • " + } + html += "
  • " + header.innerHTML + ""; + } + else if (this_level > level) { // lower level than before; expand the previous to contain a ol + for(i = this_level; i > level; i--) { + html += "<"+settings.listType+">
  • " + } + html += "" + header.innerHTML + ""; + } + level = this_level; // update for the next one + }); + html += ""; + if (!settings.noBackToTopLinks) { + $(document).on('click', '.back-to-top', function() { + $(window).scrollTop(0); + window.location.hash = ''; + }); + } + + render[settings.showEffect](); + }; +})(jQuery); \ No newline at end of file diff --git a/license.html b/license.html new file mode 100644 index 0000000000..5b866d2611 --- /dev/null +++ b/license.html @@ -0,0 +1,1684 @@ + + + + + + + + +License | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    License

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    This product is licensed under a “BSD-style” license; see below for the full text.

    + +

    Part of this product (mostly the package net.sourceforge.pmd.lang.vm) +is licensed under the Apache License, Version 2.0; +see below for the full text.

    + +

    BSD-style license

    + +
    +Copyright (c) 2002-2009, InfoEther, Inc
    +All rights reserved.
    +
    +Redistribution and use in source and binary forms, with or without
    +modification, are permitted provided that the following conditions are
    +met:
    +
    +    * Redistributions of source code must retain the above copyright
    +      notice, this list of conditions and the following disclaimer.
    +    * Redistributions in binary form must reproduce the above copyright
    +      notice, this list of conditions and the following disclaimer in the
    +      documentation and/or other materials provided with the distribution.
    +    * The end-user documentation included with the redistribution, if
    +      any, must include the following acknowledgement:
    +      "This product includes software developed in part by support from
    +      the Defense Advanced Research Project Agency (DARPA)"
    +    * Neither the name of InfoEther, LLC nor the names of its
    +      contributors may be used to endorse or promote products derived from
    +      this software without specific prior written permission.
    +
    +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
    +IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
    +TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
    +PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
    +OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
    +EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
    +PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
    +PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
    +LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
    +NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
    +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
    +
    + +

    Apache License, Version 2.0

    + +
    +                                 Apache License
    +                           Version 2.0, January 2004
    +                        http://www.apache.org/licenses/
    +
    +   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
    +
    +   1. Definitions.
    +
    +      "License" shall mean the terms and conditions for use, reproduction,
    +      and distribution as defined by Sections 1 through 9 of this document.
    +
    +      "Licensor" shall mean the copyright owner or entity authorized by
    +      the copyright owner that is granting the License.
    +
    +      "Legal Entity" shall mean the union of the acting entity and all
    +      other entities that control, are controlled by, or are under common
    +      control with that entity. For the purposes of this definition,
    +      "control" means (i) the power, direct or indirect, to cause the
    +      direction or management of such entity, whether by contract or
    +      otherwise, or (ii) ownership of fifty percent (50%) or more of the
    +      outstanding shares, or (iii) beneficial ownership of such entity.
    +
    +      "You" (or "Your") shall mean an individual or Legal Entity
    +      exercising permissions granted by this License.
    +
    +      "Source" form shall mean the preferred form for making modifications,
    +      including but not limited to software source code, documentation
    +      source, and configuration files.
    +
    +      "Object" form shall mean any form resulting from mechanical
    +      transformation or translation of a Source form, including but
    +      not limited to compiled object code, generated documentation,
    +      and conversions to other media types.
    +
    +      "Work" shall mean the work of authorship, whether in Source or
    +      Object form, made available under the License, as indicated by a
    +      copyright notice that is included in or attached to the work
    +      (an example is provided in the Appendix below).
    +
    +      "Derivative Works" shall mean any work, whether in Source or Object
    +      form, that is based on (or derived from) the Work and for which the
    +      editorial revisions, annotations, elaborations, or other modifications
    +      represent, as a whole, an original work of authorship. For the purposes
    +      of this License, Derivative Works shall not include works that remain
    +      separable from, or merely link (or bind by name) to the interfaces of,
    +      the Work and Derivative Works thereof.
    +
    +      "Contribution" shall mean any work of authorship, including
    +      the original version of the Work and any modifications or additions
    +      to that Work or Derivative Works thereof, that is intentionally
    +      submitted to Licensor for inclusion in the Work by the copyright owner
    +      or by an individual or Legal Entity authorized to submit on behalf of
    +      the copyright owner. For the purposes of this definition, "submitted"
    +      means any form of electronic, verbal, or written communication sent
    +      to the Licensor or its representatives, including but not limited to
    +      communication on electronic mailing lists, source code control systems,
    +      and issue tracking systems that are managed by, or on behalf of, the
    +      Licensor for the purpose of discussing and improving the Work, but
    +      excluding communication that is conspicuously marked or otherwise
    +      designated in writing by the copyright owner as "Not a Contribution."
    +
    +      "Contributor" shall mean Licensor and any individual or Legal Entity
    +      on behalf of whom a Contribution has been received by Licensor and
    +      subsequently incorporated within the Work.
    +
    +   2. Grant of Copyright License. Subject to the terms and conditions of
    +      this License, each Contributor hereby grants to You a perpetual,
    +      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
    +      copyright license to reproduce, prepare Derivative Works of,
    +      publicly display, publicly perform, sublicense, and distribute the
    +      Work and such Derivative Works in Source or Object form.
    +
    +   3. Grant of Patent License. Subject to the terms and conditions of
    +      this License, each Contributor hereby grants to You a perpetual,
    +      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
    +      (except as stated in this section) patent license to make, have made,
    +      use, offer to sell, sell, import, and otherwise transfer the Work,
    +      where such license applies only to those patent claims licensable
    +      by such Contributor that are necessarily infringed by their
    +      Contribution(s) alone or by combination of their Contribution(s)
    +      with the Work to which such Contribution(s) was submitted. If You
    +      institute patent litigation against any entity (including a
    +      cross-claim or counterclaim in a lawsuit) alleging that the Work
    +      or a Contribution incorporated within the Work constitutes direct
    +      or contributory patent infringement, then any patent licenses
    +      granted to You under this License for that Work shall terminate
    +      as of the date such litigation is filed.
    +
    +   4. Redistribution. You may reproduce and distribute copies of the
    +      Work or Derivative Works thereof in any medium, with or without
    +      modifications, and in Source or Object form, provided that You
    +      meet the following conditions:
    +
    +      (a) You must give any other recipients of the Work or
    +          Derivative Works a copy of this License; and
    +
    +      (b) You must cause any modified files to carry prominent notices
    +          stating that You changed the files; and
    +
    +      (c) You must retain, in the Source form of any Derivative Works
    +          that You distribute, all copyright, patent, trademark, and
    +          attribution notices from the Source form of the Work,
    +          excluding those notices that do not pertain to any part of
    +          the Derivative Works; and
    +
    +      (d) If the Work includes a "NOTICE" text file as part of its
    +          distribution, then any Derivative Works that You distribute must
    +          include a readable copy of the attribution notices contained
    +          within such NOTICE file, excluding those notices that do not
    +          pertain to any part of the Derivative Works, in at least one
    +          of the following places: within a NOTICE text file distributed
    +          as part of the Derivative Works; within the Source form or
    +          documentation, if provided along with the Derivative Works; or,
    +          within a display generated by the Derivative Works, if and
    +          wherever such third-party notices normally appear. The contents
    +          of the NOTICE file are for informational purposes only and
    +          do not modify the License. You may add Your own attribution
    +          notices within Derivative Works that You distribute, alongside
    +          or as an addendum to the NOTICE text from the Work, provided
    +          that such additional attribution notices cannot be construed
    +          as modifying the License.
    +
    +      You may add Your own copyright statement to Your modifications and
    +      may provide additional or different license terms and conditions
    +      for use, reproduction, or distribution of Your modifications, or
    +      for any such Derivative Works as a whole, provided Your use,
    +      reproduction, and distribution of the Work otherwise complies with
    +      the conditions stated in this License.
    +
    +   5. Submission of Contributions. Unless You explicitly state otherwise,
    +      any Contribution intentionally submitted for inclusion in the Work
    +      by You to the Licensor shall be under the terms and conditions of
    +      this License, without any additional terms or conditions.
    +      Notwithstanding the above, nothing herein shall supersede or modify
    +      the terms of any separate license agreement you may have executed
    +      with Licensor regarding such Contributions.
    +
    +   6. Trademarks. This License does not grant permission to use the trade
    +      names, trademarks, service marks, or product names of the Licensor,
    +      except as required for reasonable and customary use in describing the
    +      origin of the Work and reproducing the content of the NOTICE file.
    +
    +   7. Disclaimer of Warranty. Unless required by applicable law or
    +      agreed to in writing, Licensor provides the Work (and each
    +      Contributor provides its Contributions) on an "AS IS" BASIS,
    +      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
    +      implied, including, without limitation, any warranties or conditions
    +      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
    +      PARTICULAR PURPOSE. You are solely responsible for determining the
    +      appropriateness of using or redistributing the Work and assume any
    +      risks associated with Your exercise of permissions under this License.
    +
    +   8. Limitation of Liability. In no event and under no legal theory,
    +      whether in tort (including negligence), contract, or otherwise,
    +      unless required by applicable law (such as deliberate and grossly
    +      negligent acts) or agreed to in writing, shall any Contributor be
    +      liable to You for damages, including any direct, indirect, special,
    +      incidental, or consequential damages of any character arising as a
    +      result of this License or out of the use or inability to use the
    +      Work (including but not limited to damages for loss of goodwill,
    +      work stoppage, computer failure or malfunction, or any and all
    +      other commercial damages or losses), even if such Contributor
    +      has been advised of the possibility of such damages.
    +
    +   9. Accepting Warranty or Additional Liability. While redistributing
    +      the Work or Derivative Works thereof, You may choose to offer,
    +      and charge a fee for, acceptance of support, warranty, indemnity,
    +      or other liability obligations and/or rights consistent with this
    +      License. However, in accepting such obligations, You may act only
    +      on Your own behalf and on Your sole responsibility, not on behalf
    +      of any other Contributor, and only if You agree to indemnify,
    +      defend, and hold each Contributor harmless for any liability
    +      incurred by, or claims asserted against, such Contributor by reason
    +      of your accepting any such warranty or additional liability.
    +
    +   END OF TERMS AND CONDITIONS
    +
    +   APPENDIX: How to apply the Apache License to your work.
    +
    +      To apply the Apache License to your work, attach the following
    +      boilerplate notice, with the fields enclosed by brackets "[]"
    +      replaced with your own identifying information. (Don't include
    +      the brackets!)  The text should be enclosed in the appropriate
    +      comment syntax for the file format. We also recommend that a
    +      file or class name and description of purpose be included on the
    +      same "printed page" as the copyright notice for easier
    +      identification within third-party archives.
    +
    +   Copyright [yyyy] [name of copyright owner]
    +
    +   Licensed under the Apache License, Version 2.0 (the "License");
    +   you may not use this file except in compliance with the License.
    +   You may obtain a copy of the License at
    +
    +       http://www.apache.org/licenses/LICENSE-2.0
    +
    +   Unless required by applicable law or agreed to in writing, software
    +   distributed under the License is distributed on an "AS IS" BASIS,
    +   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    +   See the License for the specific language governing permissions and
    +   limitations under the License.
    +
    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/licenses/LICENSE b/licenses/LICENSE new file mode 100644 index 0000000000..e04b3d02e3 --- /dev/null +++ b/licenses/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2016 Tom Johnson + +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/licenses/LICENSE-BSD-NAVGOCO.txt b/licenses/LICENSE-BSD-NAVGOCO.txt new file mode 100644 index 0000000000..7fdefc3903 --- /dev/null +++ b/licenses/LICENSE-BSD-NAVGOCO.txt @@ -0,0 +1,27 @@ +/* This license pertains to the Navgoco jQuery component used for the sidebar. */ + +Copyright (c) 2013, Christodoulos Tsoulloftas, http://www.komposta.net +All rights reserved. + +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + + * Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + * Neither the name of the nor the names of its + contributors may be used to endorse or promote products derived from this + software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, +INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, +BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF +LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE +OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED +OF THE POSSIBILITY OF SUCH DAMAGE. \ No newline at end of file diff --git a/news.html b/news.html new file mode 100644 index 0000000000..cde532d205 --- /dev/null +++ b/news.html @@ -0,0 +1,1435 @@ + + + + + + + + +News | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    News

    +
    + + + +
    + + + + + + + + + + + + Edit me + + + +
    + +
    + + +

    RSS Subscribe

    + +
    +

    See more posts from the News Archive.

    + +
    +
    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/news_archive.html b/news_archive.html new file mode 100644 index 0000000000..ebd22d5d2c --- /dev/null +++ b/news_archive.html @@ -0,0 +1,1436 @@ + + + + + + + + +News | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    News

    +
    + + + +
    + + + + + + + + + + + + Edit me + + + +
    + +
    + + +
    +

    This year's posts

    + + +
    +
    +
    +
    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_about_help.html b/pmd_about_help.html new file mode 100644 index 0000000000..dfdd4f764d --- /dev/null +++ b/pmd_about_help.html @@ -0,0 +1,1460 @@ + + + + + + + + +Getting Help | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Getting Help

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    There are numerous ways of getting help:

    + + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_apex_metrics_index.html b/pmd_apex_metrics_index.html new file mode 100644 index 0000000000..3d86c8a424 --- /dev/null +++ b/pmd_apex_metrics_index.html @@ -0,0 +1,1514 @@ + + + + + + + + +Index of Apex code metrics | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Index of Apex code metrics

    +
    + + + +
    + + +
    Index of the code metrics available out of the box to Apex rule developers.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Index of code metrics

    + +

    Cyclomatic Complexity (CYCLO)

    + +

    Operation metric. Can be calculated on any non-abstract operation.

    + +

    Description

    + +

    Number of independent paths through a block of code [Lanza05]. +Formally, given that the control flow graph of the block has n vertices, e +edges and p connected components, the cyclomatic complexity of the block is +given by CYCLO = e - n + 2p [McCabe76]. In practice it can be +calculated by counting control flow statements following the standard rules given +below.

    + +

    The standard version of the metric complies with McCabe’s original definition:

    + +
      +
    • Methods have a base complexity of 1.
    • +
    • +1 for every control flow statement (if, catch, throw, do, +while, for, break, continue) and conditional expression (?:).
    • +
    • else, finally and default don’t count;
    • +
    • +1 for every boolean operator (&&, ||) in the guard condition of a control +flow statement.
    • +
    + +

    Code examples

    + +
    class Foo {
    +  void baseCyclo() {                // Cyclo = 1
    +    highCyclo();
    +  }
    +  
    +  void highCyclo() {                // Cyclo = 10
    +    int x = 0, y = 2;
    +    boolean a = false, b = true;
    +    
    +    if (a && (y == 1 ? b : true)) { // +3
    +      if (y == x) {                 // +1
    +        while (true) {              // +1
    +          if (x++ < 20) {           // +1
    +            break;                  // +1
    +          }
    +        }
    +      } else if (y == t && !d) {    // +2
    +        x = a ? y : x;              // +1
    +      } else {
    +        x = 2;
    +      }
    +    }  
    +  }     
    +}
    +
    + +

    Weighted Method Count (WMC)

    + +

    Class metric. Can be computed on classes and enums.

    + +

    References

    + +

    Lanza05: Lanza, Marinescu; Object-Oriented Metrics in Practice, 2005.

    + +

    McCabe76: McCabe, A Complexity Measure, in Proceedings of the 2nd ICSE (1976).

    + + +
    + + Tags: + + + + extending + + + + metrics + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_building.html b/pmd_devdocs_building.html new file mode 100644 index 0000000000..0214039150 --- /dev/null +++ b/pmd_devdocs_building.html @@ -0,0 +1,1530 @@ + + + + + + + + +Building PMD from source | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Building PMD from source

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + + + + +

    Compiling PMD

    + +
      +
    • JDK 11 or higher
    • +
    + + + +

    You’ll need to either check out the source code or download the latest source release. Assuming you’ve got the latest source release, unzip it to a directory:

    + +
    [tom@hal building]$ ls -l
    +total 5716
    +-rw-rw-r--    1 tom      tom       5837216 Jul 17 13:09 pmd-src-6.30.0-SNAPSHOT.zip
    +[tom@hal building]$ unzip -q pmd-src-6.30.0-SNAPSHOT.zip
    +[tom@hal building]$
    +
    + +

    Now cd down into the pmd directory:

    + +
    [tom@hal building]$ cd pmd-src-6.30.0-SNAPSHOT
    +[tom@hal pmd-src-6.30.0-SNAPSHOT]$ ls -l | grep pom.xml
    +-rw-rw-r--    1 tom      tom          36482 14\. Nov 17:36 pom.xml
    +[tom@hal pmd-src-6.30.0-SNAPSHOT]$
    +
    + +

    That’s the project configuration for maven… let’s compile!

    + +
    [tom@hal pmd-src-6.30.0-SNAPSHOT]$ ./mvnw clean verify
    +[INFO] Scanning for projects...
    +[INFO] ------------------------------------------------------------------------
    +[INFO] Reactor Build Order:
    +[INFO]
    +[INFO] PMD
    +[INFO] PMD Core
    +...
    +... after a few minutes ...
    +[INFO] ------------------------------------------------------------------------
    +[INFO] Reactor Summary:
    +[INFO]
    +[INFO] PMD ................................................ SUCCESS [  3.061 s]
    +[INFO] PMD Core ........................................... SUCCESS [ 25.675 s]
    +[INFO] PMD Test Framework ................................. SUCCESS [  0.457 s]
    +[INFO] PMD C++ ............................................ SUCCESS [  1.893 s]
    +[INFO] PMD C# ............................................. SUCCESS [  0.619 s]
    +[INFO] PMD Fortran ........................................ SUCCESS [  0.609 s]
    +[INFO] PMD Go ............................................. SUCCESS [  0.103 s]
    +[INFO] PMD Java ........................................... SUCCESS [01:08 min]
    +[INFO] PMD JavaScript ..................................... SUCCESS [  3.279 s]
    +[INFO] PMD JSP ............................................ SUCCESS [  3.944 s]
    +[INFO] PMD Matlab ......................................... SUCCESS [  1.342 s]
    +[INFO] PMD Objective-C .................................... SUCCESS [  2.281 s]
    +[INFO] PMD PHP ............................................ SUCCESS [  0.536 s]
    +[INFO] PMD PL/SQL ......................................... SUCCESS [ 10.973 s]
    +[INFO] PMD Python ......................................... SUCCESS [  1.758 s]
    +[INFO] PMD Ruby ........................................... SUCCESS [  0.438 s]
    +[INFO] PMD Velocity ....................................... SUCCESS [  3.941 s]
    +[INFO] PMD XML and XSL .................................... SUCCESS [  2.174 s]
    +[INFO] PMD Scala .......................................... SUCCESS [ 11.901 s]
    +[INFO] PMD Distribution Packages .......................... SUCCESS [ 11.366 s]
    +[INFO] PMD Java 8 Integration ............................. SUCCESS [  0.560 s]
    +[INFO] ------------------------------------------------------------------------
    +[INFO] BUILD SUCCESS
    +[INFO] ------------------------------------------------------------------------
    +[INFO] Total time: 02:36 min
    +[INFO] Finished at: 2015-11-14T17:46:06+01:00
    +[INFO] Final Memory: 63M/765M
    +[INFO] ------------------------------------------------------------------------
    +[tom@hal pmd-src-6.30.0-SNAPSHOT]$
    +
    + +

    Now the source and binary distribution zip files can be found in the folder pmd-dist/target.

    + +

    Notes:

    + +
      +
    • The rules that have already been written are specified in the src/main/resources/rulesets/ directories of +the specific languages, e.g. pmd-java/src/main/resources/rulesets. +They’re also in the jar file that’s included with both the source and binary distributions.
    • +
    + +

    A paucity of detail, I’m sure you’d agree. If you think this document can be improved, +please post here and let me know how. Thanks!

    + + +
    + + Tags: + + + + devdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_development.html b/pmd_devdocs_development.html new file mode 100644 index 0000000000..d8765c7e34 --- /dev/null +++ b/pmd_devdocs_development.html @@ -0,0 +1,1478 @@ + + + + + + + + +Developer Resources | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Developer Resources

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The next version of PMD will be developed in parallel with this release. We will release additional bugfix versions as needed.

    + +

    Source Code

    + +

    The complete source code can be found on github:

    + + + +

    Continuous Integration

    + +

    We use Travis CI as our ci service. The main repo and the eclipse plugin are built for +every push. Each pull request is built as well.

    + +

    The maven snapshot artifacts are deployed at Sonatypes OSS snapshot repository.

    + +

    Ready-to-use binary packages are uploaded to sourceforge at https://sourceforge.net/projects/pmd/files/pmd/.

    + +

    Documentation and Webpages

    + +

    A snapshot of the web site for the new version is generated travis-ci as well.

    + +

    Contributing

    + +

    First off, thanks for taking the time to contribute!

    + +

    Please have a look at CONTRIBUTING.md and +BUILDING.md.

    + + +
    + + Tags: + + + + devdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_experimental_ast_dump.html b/pmd_devdocs_experimental_ast_dump.html new file mode 100644 index 0000000000..fb5dda8236 --- /dev/null +++ b/pmd_devdocs_experimental_ast_dump.html @@ -0,0 +1,1548 @@ + + + + + + + + +Creating XML dump of the AST | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Creating XML dump of the AST

    +
    + + + +
    + + +
    Creating a XML representation of the AST allows to analyze the AST with other tools.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Command line usage

    + +
    $ run.sh ast-dump --help
    +Usage: ast-dump [options]
    +  Options:
    +    --encoding, -e
    +      Encoding of the source file.
    +      Default: UTF-8
    +    --file
    +      The file to dump
    +    --format, -f
    +      The output format.
    +      Default: xml
    +    --help, -h
    +      Display usage.
    +    --language, -l
    +      Specify the language to use.
    +      Default: java
    +    --read-stdin, -i
    +      Read source from standard input
    +      Default: false
    +    -P
    +      Properties for the renderer.
    +      Syntax: -Pkey=value
    +      Default: {}
    +
    +Available languages: apex ecmascript java jsp modelica plsql pom scala text vf vm wsdl xml xsl 
    +Available formats: xml                           XML format with the same structure as the one used in XPath
    ++ Properties                  
    +  + singleQuoteAttributes         Use single quotes to delimit attribute values (default true)
    +  + lineSeparator                 Line separator to use. The default is platform-specific. (default \n)
    +  + renderProlog                  True to output a prolog (default true)
    +  + renderCommonAttributes        True to render attributes like BeginLine, EndLine, etc. (default false)
    +
    + +

    Example

    + +
    $ cat Foo.java
    +public class Foo {
    +  int a;
    +}
    +
    +$ run.sh ast-dump --format xml --language java --file Foo.java > Foo.xml
    +-------------------------------------------------------------------------------
    +This command line utility is experimental. It might change at any time without
    +prior notice.
    +-------------------------------------------------------------------------------
    +
    +$ cat Foo.xml
    +<?xml version='1.0' encoding='UTF-8' ?>
    +<CompilationUnit Image='' PackageName='' declarationsAreInDefaultPackage='true'>
    +    <TypeDeclaration Image=''>
    +        <ClassOrInterfaceDeclaration Abstract='false' BinaryName='Foo' Default='false' Final='false' Image='Foo' Interface='false' Local='false' Modifiers='1' Native='false' Nested='false' PackagePrivate='false' Private='false' Protected='false' Public='true' SimpleName='Foo' Static='false' Strictfp='false' Synchronized='false' Transient='false' TypeKind='CLASS' Volatile='false'>
    +            <ClassOrInterfaceBody AnonymousInnerClass='false' EnumChild='false' Image=''>
    +                <ClassOrInterfaceBodyDeclaration AnonymousInnerClass='false' EnumChild='false' Image='' Kind='FIELD'>
    +                    <FieldDeclaration Abstract='false' AnnotationMember='false' Array='false' ArrayDepth='0' Default='false' Final='false' Image='' InterfaceMember='false' Modifiers='0' Native='false' PackagePrivate='true' Private='false' Protected='false' Public='false' Static='false' Strictfp='false' Synchronized='false' SyntacticallyFinal='false' SyntacticallyPublic='false' SyntacticallyStatic='false' Transient='false' VariableName='a' Volatile='false'>
    +                        <Type Array='false' ArrayDepth='0' ArrayType='false' Image='' TypeImage='int'>
    +                            <PrimitiveType Array='false' ArrayDepth='0' Boolean='false' Image='int' />
    +                        </Type>
    +                        <VariableDeclarator Image='' Initializer='false' Name='a'>
    +                            <VariableDeclaratorId Array='false' ArrayDepth='0' ArrayType='false' ExceptionBlockParameter='false' ExplicitReceiverParameter='false' Field='true' Final='false' FormalParameter='false' Image='a' LambdaParameter='false' LocalVariable='false' ResourceDeclaration='false' TypeInferred='false' VariableName='a' />
    +                        </VariableDeclarator>
    +                    </FieldDeclaration>
    +                </ClassOrInterfaceBodyDeclaration>
    +            </ClassOrInterfaceBody>
    +        </ClassOrInterfaceDeclaration>
    +    </TypeDeclaration>
    +</CompilationUnit>
    +
    +$ xmlstarlet select -t -c "//VariableDeclaratorId[@VariableName='a']" Foo.xml
    +<VariableDeclaratorId Array="false" ArrayDepth="0" ArrayType="false" ExceptionBlockParameter="false" ExplicitReceiverParameter="false" Field="true" Final="false" FormalParameter="false" Image="a" LambdaParameter="false" LocalVariable="false" ResourceDeclaration="false" TypeInferred="false" VariableName="a"/>
    +
    + +

    This example uses xmlstarlet to query the xml document for any variables/fields +with the name “a”.

    + +

    Programmatic usage

    + +

    Just parse your source code to get the AST and pass it on to the XmlTreeRenderer:

    + +
    import java.io.IOException;
    +import java.io.StringReader;
    +
    +import net.sourceforge.pmd.lang.LanguageRegistry;
    +import net.sourceforge.pmd.lang.LanguageVersionHandler;
    +import net.sourceforge.pmd.lang.Parser;
    +import net.sourceforge.pmd.lang.ast.Node;
    +import net.sourceforge.pmd.util.treeexport.XmlTreeRenderer;
    +
    +public class TreeExport {
    +    public static void main(String[] args) throws IOException {
    +        LanguageVersionHandler java = LanguageRegistry.getLanguage("Java").getDefaultVersion().getLanguageVersionHandler();
    +        Parser parser = java.getParser(java.getDefaultParserOptions());
    +        Node root = parser.parse("foo", new StringReader("class Foo {}"));
    +
    +        new XmlTreeRenderer().renderSubtree(root, System.out);
    +    }
    +}
    +
    + + +
    + + Tags: + + + + devdocs + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_how_pmd_works.html b/pmd_devdocs_how_pmd_works.html new file mode 100644 index 0000000000..9cb548b7bf --- /dev/null +++ b/pmd_devdocs_how_pmd_works.html @@ -0,0 +1,1494 @@ + + + + + + + + +How PMD Works | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    How PMD Works

    +
    + + + +
    + + +
    Processing overview of the different steps taken by PMD.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Overview

    + +

    The processing starts e.g. with the main class: net.sourceforge.pmd.PMD

    + + + +
      +
    • Parse command line parameters (see net.sourceforge.pmd.cli.PMDParameters) +Also load the incremental analysis cache file
    • +
    • Load rulesets/rules
    • +
    • Determine languages (rules of different languages might be mixed in rulesets)
    • +
    • Determine files (uses the given source directory, filter by the language’s file extensions)
    • +
    • Prepare the renderer
    • +
    • Sort the files by name
    • +
    • Check whether we can use the incremental analysis cache (if the rulesets changed, it will be invalid)
    • +
    • Prepare the SourceCodeProcessor based on the configuration
    • +
    • Analyze the files. Either single threaded or multi-threaded parallel. This task is encapsulated +in net.sourceforge.pmd.processor.PMDRunnable: +
        +
      • Create input stream
      • +
      • Call source code processor (net.sourceforge.pmd.SourceCodeProcessor): +
          +
        1. Determine the language
        2. +
        3. Check whether the file is already analyzed and a result is available from the analysis cache
        4. +
        5. Parse the source code. Result is the root AST node.
        6. +
        7. Always run the SymbolFacade visitor. It builds scopes, finds declarations and usages.
        8. +
        9. Run DFA (data flow analysis) visitor (if at least one rule requires it) for building +control flow graphs and data flow nodes.
        10. +
        11. Run TypeResolution visitor (if at least one rule requires it)
        12. +
        13. FUTURE: Run multifile analysis (if at least one rule requires it)
        14. +
        15. Execute the rules: +
            +
          • First run the rules that opted in for the rule chain mechanism
          • +
          • Run all the other rules and let them traverse the AST. The rules can use the symbol table, +type resolution information and DFA nodes.
          • +
          • The rules will report found problems as RuleViolations.
          • +
          +
        16. +
        +
      • +
      +
    • +
    • Render the found violations into the wanted format (XML, text, HTML, …)
    • +
    • Store the incremental analysis cache
    • +
    • Depending on the number of violations found, exit with code 0 or 4.
    • +
    + + +
    + + Tags: + + + + devdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_major_adding_new_cpd_language.html b/pmd_devdocs_major_adding_new_cpd_language.html new file mode 100644 index 0000000000..95f8588eb1 --- /dev/null +++ b/pmd_devdocs_major_adding_new_cpd_language.html @@ -0,0 +1,1593 @@ + + + + + + + + +How to add a new CPD language | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    How to add a new CPD language

    +
    + + + +
    + + +
    How to add a new CPD language
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    First of all, thanks for the contribution!

    + +

    Happily for you, to add CPD support for a new language is now easier than ever!

    + +
    Pro Tip: If you wish to add a new language, there are more than 50 languages you could easily add with just an Antlr grammar.
    + +

    All you need to do is follow this few steps:

    + +
      +
    1. Create a new module for your language, you can take GO as an example
    2. +
    3. +

      Create a Tokenizer

      + +
        +
      • For Antlr grammars you can take the grammar from here and extend AntlrTokenizer taking Go as an example
      • +
      + +
         public class GoTokenizer extends AntlrTokenizer {    
      +        
      +       @Override protected AntlrTokenManager getLexerForSource(SourceCode sourceCode) {   
      +           CharStream charStream = AntlrTokenizer.getCharStreamFromSourceCode(sourceCode);   
      +           return new AntlrTokenManager(new GolangLexer(charStream), sourceCode.getFileName());   
      +       }
      +   }
      +
      + + +
    4. +
    5. +

      Create your Language class

      + +
       public class GoLanguage extends AbstractLanguage {    
      +        
      +     public GoLanguage() {   
      +         super("Go", "go", new GoTokenizer(), ".go");   
      +     }  
      + } 
      +
      + +
      Pro Tip: Yes, keep looking at Go!
      + +

      You are almost there!

      +
    6. +
    7. +

      Update the list of supported languages

      + +
        +
      • +

        Write the fully-qualified name of your Language class to the file src/main/resources/META-INF/services/net.sourceforge.pmd.cpd.Language

        +
      • +
      • +

        Update the test that asserts the list of supported languages by updating the SUPPORTED_LANGUAGES constant in BinaryDistributionIT

        +
      • +
      +
    8. +
    9. +

      Please don’t forget to add some test, you can again.. look at Go implementation ;)

      + +

      If you read this far, I’m keen to think you would also love to support some extra CPD configuration (ignore imports or crazy things like that)
      + If that’s your case , you came to the right place!

      +
    10. +
    11. +

      You can add your custom properties using a Token filter

      + + +
    12. +
    + +

    Testing your implementation

    + +

    Add a Maven dependency on pmd-lang-test (scope test) in your pom.xml. +This contains utilities to test your Tokenizer.

    + +

    For simple tests, create a test class extending from CpdTextComparisonTest. +That class is written in Kotlin, but you can extend it in Java as well.

    + +

    To add tests, you need to write regular JUnit @Test-annotated methods, and +call the method doTest with the name of the test file.

    + +

    For example, for the Dart language:

    + +
    
    +public class DartTokenizerTest extends CpdTextComparisonTest {
    +
    +    /**********************************
    +      Implementation of the superclass
    +    ***********************************/
    +
    +
    +    public DartTokenizerTest() {
    +        super(".dart"); // the file extension for the dart language
    +    }
    +
    +    @Override
    +    protected String getResourcePrefix() {
    +        // If your class is in                  src/test/java     /some/package
    +        // you need to place the test files in  src/test/resources/some/package/cpdData
    +        return "cpdData";
    +    }
    +
    +    @Override
    +    public Tokenizer newTokenizer() {
    +        // Override this abstract method to return the correct tokenizer
    +        return new DartTokenizer();
    +    }
    +
    +    /**************
    +      Test methods
    +    ***************/
    +
    +
    +    @Test  // don't forget the JUnit annotation
    +    public void testLiterals() {
    +        // This will look for a file named literals.dart
    +        // in the directory identified by getResourcePrefix,
    +        // tokenize it, then compare the result against a baseline
    +        // literals.txt file in the same directory
    +
    +        // If the baseline file does not exist, it is created automatically
    +        doTest("literals");
    +    }
    +
    +}
    +
    + + +
    + + Tags: + + + + devdocs + + + + extending + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_major_adding_new_language.html b/pmd_devdocs_major_adding_new_language.html new file mode 100644 index 0000000000..b0facf01e3 --- /dev/null +++ b/pmd_devdocs_major_adding_new_language.html @@ -0,0 +1,1640 @@ + + + + + + + + +Adding PMD support for a new language | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Adding PMD support for a new language

    +
    + + + +
    + + +
    How to add a new language to PMD.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    1. Start with a new sub-module.

    +
      +
    • See pmd-java or pmd-vm for examples.
    • +
    + +

    2. Implement an AST parser for your language

    +
      +
    • Ideally an AST parser should be implemented as a JJT file (see VmParser.jjt or Java.jjt for example)
    • +
    • There is nothing preventing any other parser implementation, as long as you have some way to convert an input stream into an AST tree. Doing it as a JJT simplifies maintenance down the road.
    • +
    • See this link for reference: https://javacc.java.net/doc/JJTree.html
    • +
    + +

    3. Create AST node classes

    +
      +
    • For each AST node that your parser can generate, there should be a class
    • +
    • The name of the AST class should be “AST” + “whatever is the name of the node in JJT file”. +
        +
      • For example, if JJT contains a node called “IfStatement”, there should be a class called “ASTIfStatement”
      • +
      +
    • +
    • Each AST class should have two constructors: one that takes an int id; and one that takes an instance of the parser, and an int id
    • +
    • It’s a good idea to create a parent AST class for all AST classes of the language. This simplifies rule creation later. (see SimpleNode for Velocity and AbstractJavaNode for Java for example)
    • +
    • Note: These AST node classes are generated usually once by javacc/jjtree and can then be modified as needed.
    • +
    + +

    4. Compile your parser (if using JJT)

    +
      +
    • An ant script is being used to compile jjt files into classes. This is in pmd-<lang>/src/main/ant/alljavacc.xml file.
    • +
    • Create alljavacc.xml file for your language, you can use one from pmd-java as an example.
    • +
    • You would probably want to adjust contents of the <delete> tag: start with an empty <fileset> and add there <include>s for those AST nodes you had to manually rewrite (moving those node classes from autogenerated directory to the regular source tree).
    • +
    + +

    5. Create a TokenManager

    +
      +
    • Create a new class that implements the TokenManager interface (see VmTokenManager or JavaTokenManager for example)
    • +
    + +

    6. Create a PMD parser “adapter”

    +
      +
    • Create a new class that extends AbstractParser
    • +
    • There are two important methods to implement +
        +
      • createTokenManager method should return a new instance of a token manager for your language (see step #5)
      • +
      • parse method should return the root node of the AST tree obtained by parsing the Reader source
      • +
      • See VmParser class as an example
      • +
      +
    • +
    + +

    7. Create a rule violation factory

    +
      +
    • Extend AbstractRuleViolationFactory (see VmRuleViolationFactory for example)
    • +
    • The purpose of this class is to create a rule violation instance specific to your language
    • +
    + +

    8. Create a version handler

    +
      +
    • Extend AbstractLanguageVersionHandler (see VmHandler for example)
    • +
    • This class is sort of a gateway between PMD and all parsing logic specific to your language. It has 3 purposes: +
        +
      • getRuleViolationFactory method returns an instance of your rule violation factory (see step #7)
      • +
      • getParser returns an instance of your parser adapter (see step #6)
      • +
      • getDumpFacade returns a VisitorStarter that allows to dump a text representation of the AST into a writer (likely for debugging purposes)
      • +
      +
    • +
    + +

    9. Create a parser visitor adapter

    +
      +
    • If you use JJT to generate your parser, it should also generate an interface for a parser visitor (see VmParserVisitor for example)
    • +
    • Create a class that implements this auto-generated interface (see VmParserVisitorAdapter for example)
    • +
    • The purpose of this class is to serve as a pass-through visitor implementation, which, for all AST types in your language, just executes visit on the base AST type
    • +
    + +

    10. Create a rule chain visitor

    +
      +
    • Extend AbstractRuleChainVisitor (see VmRuleChainVisitor for example)
    • +
    • This class should implement two important methods: +
        +
      • indexNodes generates a map of “node type” to “list of nodes of that type”. This is used to visit all applicable nodes when a rule is applied.
      • +
      • visit method should evaluate what kind of rule is being applied, and execute appropriate logic. Usually it will just check if the rule is a “parser visitor” kind of rule specific to your language, then execute the visitor. If it’s an XPath rule, then we just need to execute evaluate on that.
      • +
      +
    • +
    + +

    11. Make PMD recognize your language

    +
      +
    • Create your own subclass of net.sourceforge.pmd.lang.BaseLanguageModule. (see VmLanguageModule or JavaLanguageModule as an example)
    • +
    • You’ll need to refer the rule chain visitor created in step #10.
    • +
    • Add for each version of your language a call to addVersion in your language module’s constructor.
    • +
    • Create the service registration via the text file src/main/resources/META-INF/services/net.sourceforge.pmd.lang.Language. Add your fully qualified class name as a single line into it.
    • +
    + +

    12. Add AST regression tests

    + +

    For languages, that use an external library for parsing, the AST can easily change when upgrading the library. +Also for languages, where we have the grammar under our control, it useful to have such tests.

    + +

    The tests parse one or more source files and generate a textual representation of the AST. This text is compared +against a previously recorded version. If there are differences, the test fails.

    + +

    This helps to detect anything in the AST structure, that changed, maybe unexpectedly.

    + +
      +
    • Create a test class in the package net.sourceforge.pmd.lang.$lang.ast with the name $langTreeDumpTest.
    • +
    • This test class must extend net.sourceforge.pmd.lang.ast.test.BaseTreeDumpTest. Note: This class +is written in kotlin and is available in the module “lang-test”.
    • +
    • +

      Add a default constructor, that calls the super constructor like so:

      + +
          public $langTreeDumpTest() {
      +        super(NodePrintersKt.getSimpleNodePrinter(), ".$extension");
      +    }
      +
      + +

      Replace “$lang” and “$extension” accordingly.

      +
    • +
    • Implement the method getParser(). It must return a +subclass of net.sourceforge.pmd.lang.ast.test.BaseParsingHelper. See +net.sourceforge.pmd.lang.ecmascript.ast.JsParsingHelper for a example. +With this parser helper you can also specify, where the test files are searched, by using +the method withResourceContext(Class<?>, String).
    • +
    • +

      Add one or more test methods. Each test method parses one file and compares the result. The base +class has a helper method doTest(String) that does all the work. This method just needs to be called:

      + +
          @Test
      +    public void myFirstAstTest() {
      +        doTest("filename-without-extension");
      +    }
      +
      +
    • +
    • On the first test run the test fails. A text file (with the extension .txt) is created, that records the +current AST. On the next run, the text file is used as comparison and the test should pass. Don’t forget +to commit the generated text file.
    • +
    + +

    A complete example can be seen in the JavaScript module: net.sourceforge.pmd.lang.ecmascript.ast.JsTreeDumpTest. +The test resources are in the subpackage “testdata”: pmd-javascript/src/test/resources/net/sourceforge/pmd/lang/ecmascript/ast/testdata/.

    + +

    The Scala module also has a test, written in Kotlin instead of Java: +net.sourceforge.pmd.lang.scala.ast.ScalaParserTests.

    + +

    13. Create an abstract rule class for the language

    +
      +
    • Extend AbstractRule and implement the parser visitor interface for your language (see AbstractVmRule for example)
    • +
    • All other rules for your language should extend this class. The purpose of this class is to implement visit methods for all AST types to simply delegate to default behavior. This is useful because most rules care only about specific AST nodes, but PMD needs to know what to do with each node - so this just lets you use default behavior for nodes you don’t care about.
    • +
    + +

    14. Create rules

    +
      +
    • Rules are created by extending the abstract rule class created in step 13 (see EmptyForeachStmtRule for example)
    • +
    • Creating rules is already pretty well documented in PMD - and it’s no different for a new language, except you may have different AST nodes.
    • +
    + +

    15. Test the rules

    +
      +
    • See BasicRulesTest for example
    • +
    • You have to create a rule set for your language (see vm/basic.xml for example)
    • +
    • For each rule in this set you want to test, call addRule method in setUp of the unit test +
        +
      • This triggers the unit test to read the corresponding XML file with rule test data (see EmptyForeachStmtRule.xml for example)
      • +
      • This test XML file contains sample pieces of code which should trigger a specified number of violations of this rule. The unit test will execute the rule on this piece of code, and verify that the number of violations matches
      • +
      +
    • +
    • +

      To verify the validity of the created ruleset, create a subclass of AbstractRuleSetFactoryTest (see RuleSetFactoryTest in pmd-vm for example). +This will load all rulesets and verify, that all required attributes are provided.

      + +

      Note: You’ll need to add your ruleset to rulesets.properties, so that it can be found.

      +
    • +
    + +

    Debugging with Rule Designer

    + +

    When implementing your grammar it may be very useful to see how PMD parses your example files. +This can be achieved with Rule Designer:

    +
      +
    • Override the getXPathNodeName in your AST nodes for Designer to show node names.
    • +
    • Make sure to override both jjtOpen and jjtClose in your AST node base class so that they set both start and end line and column for proper node bound highlighting.
    • +
    • Not strictly required but trivial and useful: implement syntax highlighting for Rule Designer: +
        +
      • Fork and clone the pmd/pmd-designer repository.
      • +
      • Add a syntax highlighter implementation to net.sourceforge.pmd.util.fxdesigner.util.codearea.syntaxhighlighting (you could use Java as an example).
      • +
      • Register it in the AvailableSyntaxHighlighters enumeration.
      • +
      • Now build your implementation and place the target/pmd-ui-<version>-SNAPSHOT.jar to the lib directory inside your pmd-bin-... distribution (you have to delete old pmd-ui-*.jar from there).
      • +
      +
    • +
    + + +
    + + Tags: + + + + devdocs + + + + extending + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_major_adding_new_metrics_framework.html b/pmd_devdocs_major_adding_new_metrics_framework.html new file mode 100644 index 0000000000..6150704680 --- /dev/null +++ b/pmd_devdocs_major_adding_new_metrics_framework.html @@ -0,0 +1,1493 @@ + + + + + + + + +Adding support for metrics to a language | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Adding support for metrics to a language

    +
    + + + +
    + + +
    PMD's Java module has an extensive framework for the calculation of metrics, which allows rule developers to implement and use new code metrics very simply. Most of the functionality of this framework is abstracted in such a way that any PMD supported language can implement such a framework without too much trouble. Here's how.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Internal architecture of the metrics framework

    + +

    The framework is pretty simple. On a high level, a Metric<N> describes some numeric computation on a node of type N. +You should wrap it into a MetricKey<N>, so that it can be cached on nodes (implemented by MetricsUtil).

    + +

    At the very least, a metrics framework has those two components and is just a convenient way to compute and memoize +metrics on a single file. The expressive power of metrics can be improved by implementing signature matching capabilities, +which allows a metric to count signatures matching a specific pattern (a mask) over a whole class. This was originally +designed to work across files, given a working usage resolution. However, making that work with incremental analysis is +harder than it looks, and has been rescheduled to another project.

    + +

    Implementation of a new framework

    + +
      +
    • Implement metrics (typically in an internal package)
    • +
    • Create some public enums/ utility classes to expose metric keys
    • +
    • Implement a LanguageMetricsProvider, to expose your metrics to the designer
    • +
    • Use your metric keys in rules with MetricsUtil
    • +
    + +

    Optional: Signature matching

    + +

    You can match the signature of anything: method, field, class, package… It depends on what’s useful for you. +Suppose you want to be able to match signatures for nodes of type N. What you have to do then is the following:

    + +
      +
    • Create a class implementing the interface Signature<N>. Signatures describe basic information about the node, +which typically includes most of the modifiers they declare (eg visibility, abstract or virtual, etc.). +It’s up to you to define the right level of detail, depending on the accuracy of the pattern matching required.
    • +
    • Make type N implement SignedNode<N>. This makes the node capable of giving its signature. Factory methods to +build a Signature<N> from a N are a good idea.
    • +
    • Create signature masks. A mask is an object that matches some signatures based on their features. For example, with + the Java framework, you can build a JavaOperationSigMask that matches all method signatures with visibility + public. A sigmask implements SigMask<S>, where S is the type of signature your mask handles.
    • +
    • Create utility methods in your abstract class metric class to count signatures matching a specific mask. +Example
    • +
    + + + +
    + + Tags: + + + + devdocs + + + + extending + + + + metrics + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_pmdtester.html b/pmd_devdocs_pmdtester.html new file mode 100644 index 0000000000..bc20c8a843 --- /dev/null +++ b/pmd_devdocs_pmdtester.html @@ -0,0 +1,1462 @@ + + + + + + + + +Pmdtester | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Pmdtester

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Introduction

    +

    Pmdtester is a regression testing tool that ensures no new problems and unexpected behaviors will be introduced to PMD after fixing an issue. +It can also be used to verify, that new rules work as expected. It has been integrated into travis CI and is actually used automatically for PRs. +Regression difference reports are commented back to the PR for the reviewer’s information e.g. https://github.com/pmd/pmd/pull/1265#issuecomment-408945709

    + +

    Run pmdtester locally

    +

    Install pmdtester

    + +

    gem install pmdtester --pre

    + +

    Verifying your local changes and generate a diff-report locally

    + +

    pmdtester -r YOUR_LOCAL_PMD_GIT_REPO_ROOT_DIR -b master -p YOUR_DEVELOPMENT_BRANCH

    + +

    The regression difference report is placed in the YOUR_WORKING_DIR/target/reports/diff directory.

    + +

    For more documentation on pmdtester, see README.rdoc

    + + +
    + + Tags: + + + + devdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_roadmap.html b/pmd_devdocs_roadmap.html new file mode 100644 index 0000000000..b6904117e6 --- /dev/null +++ b/pmd_devdocs_roadmap.html @@ -0,0 +1,1583 @@ + + + + + + + + +Roadmap | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Roadmap

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    TODO:

    + +
      +
    • Update
    • +
    • Future direction
    • +
    • projects, plans
    • +
    • Google Summer of Code
    • +
    + +

    Future directions

    + +

    Want to know what’s coming? Or, better, wanna contribute ? Here is the page listing what are our plans - +when we have ones, for the future of PMD. It also give you hints at part of the code we would like to clean - +that you may want to clean to contribute to the project!

    + +

    Of course, an easy way to contribute is too check out the bug tracker and see if you can fix some issues - +some could be quite easy, we simply have not the time to look at them all!

    + +

    At last, if you want to contribute, register on the pmd-devel mailing list, and come discuss with us!

    + +

    Roadmap

    + +

    This roadmap contains all the different ‘workshops’ PMD’s developers are working right now.

    + +
      +
    • Better symbol analysis: See below.
    • +
    • Data Flow Analysis: See below.
    • +
    • Code Cleanups: See below.
    • +
    + +

    Please note that, of course, there is no warranty about when those ‘features’ will be finished, if they ever are.

    + +

    Better symbol analysis

    + +

    Currently PMD only looks at one source file at a time. Instead, it should resolve symbols across classes. +This will eliminate some open bugs and enable a lot more rules to be written. However, it’ll taken some doing, +because it’ll require parsing of class files. Lots of work here.

    + +

    Data flow analysis (DFA)

    + +

    Raik Schroeder, a graduate student at Fachhochschule Stralsund has written a DFA layer that should enable +us to write some more complicated rules - stuff like common subexpression elimination, loop invariant code motion +(and code hoisting suggestions), shrink wrapping, and partial redundancy elimination. The code is currently in the net.sourceforge.pmd.dfa packages, and we’re going through it now figuring out what rules we can write +that use it. We should be able to use it to simplify some current rules, as well.

    + +

    Other changes we’ll like to see…

    + +

    These are things which really should be done, but just haven’t been gotten to yet:

    + +
      +
    • Enhance Rule Designer to allow testing of the violation suppress Regex and XPath.
    • +
    • Remove the type resolution specific rules. Merge these back into the +standard rules. In general, a Rule should use TR when it can, and fall +back on non-TR approach otherwise. No need for separate Rules for TR/non-TR.
    • +
    • Reconcile the util.designer and util.viewer packages. Two versions of the +same thing. Designer is more up to date, but Viewer has a nice MVC design.
    • +
    • Need a JUnit test to check for “dead” Rules, that is those not used by any RuleSet.
    • +
    • Rule JUnit tests should verify the Test class follows expected naming +conventions just like the Rules need to.
    • +
    • Do we have a rule to style check for multiple declarations and chained +assignments? (e.g. int a, b; int a = b = x;)
    • +
    + +

    These are food for thought, perhaps future items. If you think you’d like to +work on one of these, check with pmd-devel to see what the current thoughts +on the topic.

    + +
      +
    • +

      CPD needs work on use of Language. It currently is hardcoded to only +handled Java 1.4. Integrate CPD needs into core PMD where appropriate. +Otherwise, drive CPD behavior based off of core PMD, instead of duplicating +some logic.

      +
    • +
    • +

      Need a more flexible and powerful scheme for classifying files to various +Languages. At a minimum, should have the ability to specify which +file extensions you want to be used for a language (e.g. not everyone uses +.jsp for JSP extensions, some use .jspx, .xhtml, etc.). Also, consider +hooks into the LanguageVersionDiscoverer process for classifying a +File/String to a LanguageVersion of a specific Language, one could imaging +using a ‘magic’ system like Unix uses to tell different versions of files +apart based on actual content.

      +
    • +
    • +

      Should we change Node interface to something like ‘Node<T extends Node<T>>’, +and then declare the language specific node interfaces to be something like +‘JavaNode extends Node<JavaNode>’? This could allow anything on the Node +interface to return the language specific node type instead of generic +node. For example, ASTStatement.jjtGetParent() to return a JavaNode, +instead of a Node. This is a rather huge change, as the Node interface is +one of the pervasive things in the PMD code base. Is the extra work of using +the Node interface with properly with generics, worth the omission of +occasional some casting?

      +
    • +
    • +

      Should multiple Languages be able to claim a single source file? Imagine +XML format JSP file, for which you’ve defined a ruleset which uses JSP and +XML rules. Stating that certain XML rules also can map to the JSP language +extensions could be useful. This means Source file to LanguageVersion +mapping is not 1-1, but 1-many, we’d need to deal with this accordingly.

      +
    • +
    • +

      Additional changes to Rule organization within RuleSets as discussed on +this forum thread.

      +
    • +
    • +

      Figure out a way to allow Rules to deal with parentheses and blocks, which +introduce certain repetitive (and generally ignorable for most Rules) +structures into the AST tree. Some rules are making special effort +(e.g. ConfusingTernaryRule) to detect these AST patterns. Perhaps a +“normalized” AST structure can be created which will make the AST appear +consistent regardless of how many parens are presented, or how many blocks +have been created (e.g. default block inserted, duplicates collapsed). +This should be configurable on per Rule basis similar to TR and SymbolTable.

      +
    • +
    + +

    Code cleanups

    + +

    Some of the code is a bit sloppy:

    + +
      +
    • RuleSetFactory is a mess. It needs to be refactored into something that has layers, or decorators, or something.
    • +
    • Cleanups would be welcome for ConstructorCallsOverridableMethod and DoubleCheckedLocking
    • +
    • The Designer GUI is a bit messed up; the bottom panes look funny.
    • +
    • The grammar has some odd bits: +
        +
      • BlockStatement has an odd hack for class definitions inside methods
      • +
      • enumLookahead() seems like a bit of overkill, can it use Modifiers somehow?
      • +
      • The whole “discardable node” thing seems wasteful
      • +
      • Does ExtendsList need that ‘extendsMoreThanOne’ thing?
      • +
      • ClassOrInterfaceBodyDeclaration has a monstrous lookahead to check for enums
      • +
      • ClassOrInterfaceType gloms together dotted names… is that the right thing to do?
      • +
      • Some complicated annotations are currently broken
      • +
      +
    • +
    + + +
    + + Tags: + + + + devdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_rule_deprecation_policy.html b/pmd_devdocs_rule_deprecation_policy.html new file mode 100644 index 0000000000..0f49224d38 --- /dev/null +++ b/pmd_devdocs_rule_deprecation_policy.html @@ -0,0 +1,1552 @@ + + + + + + + + +Rule deprecation policy | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Rule deprecation policy

    +
    + + + +
    + + +
    Describes when and how rules are deprecated
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    When improving PMD over time, some rules might become obsolete. This could be because the underlying +technology a specific rule is checking (such as a specific JVM version) is not relevant anymore or a rule +has been replaced by a better implementation.

    + +

    In order to remove the requirement to maintain such rules forever, these rules can be marked as deprecated. +This means, that such rules can entirely be removed in the future. +However, the rules must not be removed immediately, since that would break any (custom) ruleset, that +references this rule.

    + +

    This policy tries to establish some ground rules about how and when rules are deprecated and removed. +The main goal is, to maintain compatibility of custom rulesets throughout the deprecation process.

    + +

    Renaming rules

    + +

    If a rule is enhanced, it might make sense to also rename the rule, to reflect that enhancement. However, +simply renaming the rule would break existing (custom) ruleset. Therefore the following procedure should be used:

    + +
      +
    • Rename the rule to the new name (and also the rule tests and resources)
    • +
    • +

      Add a deprecated rule reference with the old name, that points to the new rule name:

      + +

      <rule name="OldRuleName" ref="NewRuleName" deprecated="true" />

      +
    • +
    + +

    Note: When referencing the complete rulesets or categories, +these deprecated rule references are ignored, so that the rule is not used twice.

    + +

    Moving rules between categories

    + +

    Every rule is in one category. It might happen, that the focus of the rule shifts and it makes more +sense, if it would be in a different, better fitting category.

    + +
      +
    • Move the rule to the new category (and also the rule tests and resources)
    • +
    • +

      Add a deprecated rule reference in the old category, that points to the rule in the new category:

      + +

      <rule name="MyRule" ref="category/java/errorprone.xml/MyRule" deprecated="true" />

      +
    • +
    + +

    Note: When referencing the complete rulesets or categories, +these deprecated rule references are ignored, so that the rule is not used twice, if both categories +are used.

    + +

    Deprecating rules

    + +

    Before a rule can be removed, it must have been marked as deprecated:

    + +
    <rule name="MyRule" class="...." deprecated="true">
    +...
    +</rule>
    +
    + +

    This has the effect, that it is automatically disabled if the complete ruleset or category +is referenced. The rule can still be used, if it is referenced directly.

    + +

    The reasons for the deprecation should be explained in the rule description. If there is a replacement rule +available, then this rule should be mentioned in the description as well.

    + +

    Removing rules

    + +

    Removing rules completely can only be done

    + +
      +
    • if the rules have been deprecated before
    • +
    • for a new major release.
    • +
    + +

    Removing a rule from a ruleset or category will break any custom ruleset, that references +this rule directly. Therefore rules can only be removed with the next major release of PMD.

    + +

    Rule property compatibility

    + +

    Renaming or removing rule properties is not backwards compatible and can only be done +with a major release of PMD.

    + +

    In order to prepare for the change, properties can be deprecated as well: If the property description +starts with the magic string deprecated!, then this property is rendered in the rule documentation +as deprecated. However, there is no automatic check done if such a property is used and no +deprecation warning is issued with the log.

    + +

    Therefore, the process for renaming a property looks like this:

    + +
      +
    • Create a new property with the same type and new name
    • +
    • Prefix the description of the old property with deprecated! and also add a explanation +either in the property description or in the rule description, which property should be used +instead of the deprecated property.
    • +
    • Adjust the rule implementation to first check the old property. If it has a value other than the +default value, then the old (deprecated) property has been used and a deprecation warning should +be logged. If the new property is used (it has a value other than the default), then it takes +preference, but the deprecation warning for the old property should still be issued.
    • +
    • The deprecated property can be removed with the next major release of PMD.
    • +
    + +

    Changing the default value of a property might have some results, that make the rule +behavioral incompatible: E.g. it could find many more violations with a different default +configuration and therefore lead to a sudden increase of violations after a PMD upgrade. +It should be judged per case, whether the new default can be considered compatible or not. +If it is not compatible, then the new default value should be configured only with the next +major release of PMD.

    + + + +
    + + Tags: + + + + devdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_devdocs_writing_documentation.html b/pmd_devdocs_writing_documentation.html new file mode 100644 index 0000000000..61fd9b73d8 --- /dev/null +++ b/pmd_devdocs_writing_documentation.html @@ -0,0 +1,1699 @@ + + + + + + + + +Writing documentation | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Writing documentation

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    PMD’s documentation uses Jekyll with +the I’d rather be writing Jekyll Theme.

    + +

    Here are some quick tips.

    + +

    Format

    + +

    The pages are in general in Github Flavored Markdown.

    + +

    Structure

    + +

    The documentation sources can be found in two places based on how they are generated:

    +
      +
    • the ones that are manually written (like the one you are reading);
    • +
    • and the ones that are generated automatically from the category files. All the rule documentation +pages are generated that way.
    • +
    + +

    Handwritten documentation

    + +

    All handwritten documentation is stored in the subfolders under docs/pages. The folder structure resembles the sidebar structure. +Since all pages use a simple permalink, in the rendered html pages, all pages are flattened in one directory. +This makes it easy to view the documentation also offline.

    + +

    Rule documentation

    + +

    The categories for a language %lang% are located in +pmd-%lang%/src/main/resources/category/%lang% . So for Java the categories +can be found under pmd-java/src/main/resources/category/java. +The XML category files in this directory are transformed during build into markdown pages +describing the rules they contain. These pages are placed under docs/ like the handwritten +documentation, and are then rendered with Jekyll like the rest of them. The rule documentation +generator is the separate submodule pmd-doc.

    + +

    Modifying the documentation of a rule should thus not be done on the markdown page, +but directly on the XML rule tag corresponding to the rule, in the relevant +category file.

    + +

    The XML documentation of rules can contain GitHub flavoured markdown. +Just wrap the markdown inside CDATA section in the xml. CDATA sections preserve +all formatting inside the delimiters, and allow to write code samples without + escaping special xml characters. For example:

    +
    <rule ...>
    + <description>
    + <![CDATA[
    +   Full description, can contain markup
    +
    +   And paragraphs
    + ]]>
    + </description>
    + ...
    +</rule>
    +
    + +

    Custom Liquid Tags

    + +

    We have some additional custom liquid tags that help in writing the documentation.

    + +

    Here’s a short overview:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    LiquidRendered as
    {% rule "java/codestyle/LinguisticNaming" %}LinguisticNaming
    {% jdoc core::Rule %}Rule
    {% jdoc !q!core::Rule %}net.sourceforge.pmd.Rule
    {% jdoc core::Rule#setName(java.lang.String) %}setName
    {% jdoc !c!core::Rule#setName(java.lang.String) %}Rule#setName
    {% jdoc !a!core::Rule#setName(java.lang.String) %}setName(String)
    {% jdoc !ac!core::Rule#setName(java.lang.String) %}Rule#setName(String)
    {% jdoc core::properties.PropertyDescriptor %}PropertyDescriptor
    {% jdoc_nspace :jast java::lang.java.ast %}{% jdoc jast::ASTAnyTypeDeclaration %}ASTAnyTypeDeclaration
    {% jdoc_nspace :jast java::lang.java.ast %}{% jdoc_package :jast %}net.sourceforge.pmd.lang.java.ast
    {% jdoc_nspace :PrD core::properties.PropertyDescriptor %}{% jdoc !ac!:PrD#uiOrder() %}PropertyDescriptor#uiOrder()
    {% jdoc_old core::Rule %}Rule
    + +

    For the javadoc tags, the standard PMD maven modules are already defined as namespaces, e.g. core, java, apex, ….

    + +

    For the implementation of these tags, see the _plugins folder.

    + +

    Building

    + +

    There are two ways, to execute jekyll:

    + +
      +
    1. +

      Using bundler. This will install all the needed ruby packages locally and execute jekyll:

      + +
      # this is required only once, to download and install the dependencies
      +bundle install
      +# this builds the documentation under _site
      +bundle exec jekyll build
      +# this runs a local webserver as http://localhost:4005
      +bundle exec jekyll serve
      +
      +
    2. +
    3. +

      Using docker. This will create a local docker image, into which all needed ruby +packages and jekyll is installed.

      + +
      # this is required only once to create a local docker image named "pmd-doc"
      +docker build --no-cache -t pmd-doc .
      +# this builds the documentation under _site
      +docker run --rm=true -v "$PWD:/src" pmd-doc build -H 0.0.0.0
      +# this runs a local webserver as http://localhost:4005
      +docker run --rm=true -v "$PWD:/src" -p 4005:4005 pmd-doc serve -H 0.0.0.0
      +
      +
    4. +
    + +

    The built site is stored locally in the (git ignored) directory _site. You can +point your browser to _site/index.html to see the pmd documentation.

    + +

    Alternatively, you can start the local webserver, that will serve the documentation. +Just go to http://localhost:4005. +If a page is modified, the documentation will automatically be rendered again and +all you need to do, is refreshing the page in your browser.

    + +

    See also the script pmd-jekyll.sh. +It starts the jekyll server in the background and doesn’t block the current shell.

    + +

    The sidebar

    + +

    The sidebar is stored as a YAML document under _data/sidebars/pmd_sidebar.yml.

    + +

    Make sure to add an entry there, whenever you create a new page.

    + +

    The frontmatter

    + +

    Each page in jekyll begins with a YAML section at the beginning. This section +is separated by 3 dashes (---). Example:

    + +
    ---
    +title: Writing Documentation
    +last_update: August 2017
    +permalink: pmd_devdocs_writing_documentation.html
    +---
    +
    +Some Text
    +
    +# Some header
    +
    + +

    There are a couple of possible fields. Most important and always +required are title and permalink.

    + +

    By default, a page toc (table of contents) is automatically generated. +You can prevent this with “toc: false”.

    + +

    You can add keywords, that will be used for the on-site search: “keywords: documentation, jekyll, markdown”

    + +

    It’s useful to maintain a last_update field. This will be added at the bottom of the +page.

    + +

    A summary can also be provided. It will be added in a box before the content.

    + +

    For a more exhaustive list, see Pages - Frontmatter.

    + +

    Alerts and Callouts

    + +

    See Alerts.

    + +

    For example, a info-box can be created like this:

    + +
    {% include note.html content="This is a note." %}
    +
    + +

    It renders as:

    + + + +

    Other available types are:

    + +
      +
    • note.html
    • +
    • tip.html
    • +
    • warning.html
    • +
    • important.html
    • +
    + +

    A callout is created like this:

    + +
    {% include callout.html content="This is a callout of type default.<br/><br/>There are the following types available: danger, default, primary, success, info, and warning." type="default" %}
    +
    + +

    It renders as:

    + +
    This is a callout of type default.

    There are the following types available: danger, default, primary, success, info, and warning.
    + +

    Code samples with syntax highlighting

    + +

    This is as easy as:

    + +
    ``` java
    +public class Foo {
    +    public void bar() { System.out.println("x"); }
    +}
    +```
    +
    + +

    This looks as follows:

    + +
    public class Foo {
    +    public void bar() { System.out.println("x"); }
    +}
    +
    + + + +

    mvn verify -pl pmd-doc. This only checks links within the site. HTTP links can be checked +by specifying -Dpmd.doc.checkExternalLinks=true on the command line.

    + + +
    + + Tags: + + + + devdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_java_metrics_index.html b/pmd_java_metrics_index.html new file mode 100644 index 0000000000..134ab9fd73 --- /dev/null +++ b/pmd_java_metrics_index.html @@ -0,0 +1,1793 @@ + + + + + + + + +Index of Java code metrics | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Index of Java code metrics

    +
    + + + +
    + + +
    Index of the code metrics available out of the box to Java rule developers.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Index of code metrics

    + +

    Access to Foreign Data (ATFD)

    + +

    Operation metric, class metric. Can be computed on classes, enums and +concrete operations.

    + +

    Description

    + +

    Number of usages of foreign attributes, both directly and through accessors. +High values of ATFD (> 3 for an operation) may suggest that the class or operation +breaks encapsulation by relying on the internal representation of the classes +it uses instead of the services they provide.

    + +

    ATFD can be used to detect God Classes and Feature Envy. [Lanza05]

    + +

    Class Fan Out Complexity (CLASS_FAN_OUT)

    + +

    Operation metric, class metric. Can be computed on classes, enums and +concrete operations.

    + +

    Description

    +

    This counts the number of other classes a given class or operation relies on. +Classes from the package java.lang are ignored by default (can be changed via options). +Also primitives are not included into the count.

    + +

    Code example

    + +
    import java.util.*;
    +import java.io.IOException;
    +
    +public class Foo { // total 8
    +    public Set set = new HashSet(); // +2
    +    public Map map = new HashMap(); // +2
    +    public String string = ""; // from java.lang -> does not count by default
    +    public Double number = 0.0; // from java.lang -> does not count by default
    +    public int[] intArray = new int[3]; // primitive -> does not count
    +
    +    @Deprecated // from java.lang -> does not count by default
    +    @Override // from java.lang -> does not count by default
    +    public void foo(List list) throws Exception { // +1 (Exception is from java.lang)
    +        throw new IOException(); // +1
    +    }
    +
    +    public int getMapSize() {
    +        return map.size(); // +1 because it uses the Class from the 'map' field
    +    }   
    +}
    +
    + +

    Options

    + +
      +
    • Option includeJavaLang: Also include classes from the package java.lang
    • +
    + +

    Cyclomatic Complexity (CYCLO)

    + +

    Operation metric. Can be calculated on any non-abstract operation.

    + +

    Description

    + +

    Number of independent paths through a block of code [Lanza05]. +Formally, given that the control flow graph of the block has n vertices, e +edges and p connected components, the cyclomatic complexity of the block is +given by CYCLO = e - n + 2p [McCabe76]. In practice it can be +calculated by counting control flow statements following the standard rules given +below.

    + +

    The standard version of the metric complies with McCabe’s original definition:

    + +
      +
    • Methods have a base complexity of 1.
    • +
    • +1 for every control flow statement (if, case, catch, throw, do, +while, for, break, continue) and conditional expression (?:) +[Sonarqube]. Notice switch cases count as one, but not the +switch itself: the point is that a switch should have the same complexity +value as the equivalent series of if statements.
    • +
    • else, finally and default don’t count;
    • +
    • +1 for every boolean operator (&&, ||) in the guard condition of a control +flow statement. That’s because Java has short-circuit evaluation semantics for +boolean operators, which makes every boolean operator kind of a control flow +statement in itself.
    • +
    + +

    Code examples

    + +
    class Foo {
    +  void baseCyclo() {                // Cyclo = 1
    +    highCyclo();
    +  }
    +  
    +  void highCyclo() {                // Cyclo = 10
    +    int x = 0, y = 2;
    +    boolean a = false, b = true;
    +    
    +    if (a && (y == 1 ? b : true)) { // +3
    +      if (y == x) {                 // +1
    +        while (true) {              // +1
    +          if (x++ < 20) {           // +1
    +            break;                  // +1
    +          }
    +        }
    +      } else if (y == t && !d) {    // +2
    +        x = a ? y : x;              // +1
    +      } else {
    +        x = 2;
    +      }
    +    }  
    +  }     
    +}
    +
    +

    Options

    + +
      +
    • Option CycloVersion#IGNORE_BOOLEAN_PATHS: Boolean operators are not counted, +nor are empty fall-through cases in switch statements. You can use this +option to get results similar to those of the old StdCyclomaticComplexityRule, +which is to be replaced.
    • +
    • Option CycloVersion#CONSIDER_ASSERTS: Assert statements are counted as if +they were if (..) throw new AssertionError(..). Compatible with +IGNORE_BOOLEAN_PATHS.
    • +
    + +

    Lines of Code (LoC)

    + +

    Operation metric, class metric. Can be calculated on any of those nodes.

    + +

    Description

    + +

    Simply counts the number of lines of code the operation or class takes up in +the source. This metric doesn’t discount comments or blank lines. See also +NCSS.

    + +

    Non-commenting source statements (NCSS)

    + +

    Operation metric, class metric. Can be calculated on any of those nodes.

    + +

    Description

    + +

    Number of statements in a class or operation. That’s roughly equivalent to +counting the number of semicolons and opening braces in the program. Comments +and blank lines are ignored, and statements spread on multiple lines count as +only one (e.g. int\n a; counts a single statement).

    + +

    The standard version of the metric is based off JavaNCSS’s version
    +[JavaNcss]:

    + +
      +
    • +1 for any of the following statements: if, else, while, do, for, +switch, break, continue, return, throw, synchronized, catch, +finally.
    • +
    • +1 for each assignment, variable declaration (except for loop initializers) +or statement expression. We count variables declared on the same line (e.g. +int a, b, c;) as a single statement.
    • +
    • Contrary to Sonarqube, but as JavaNCSS, we count type declarations (class, +interface, enum, annotation), and method and field declarations +[Sonarqube].
    • +
    • Contrary to JavaNCSS, but as Sonarqube, we do not count package declaration +and import declarations as statements. This makes it easier to compare nested +classes to outer classes. Besides, it makes for class metric results that +actually represent the size of the class and not of the file. If you don’t +like that behaviour, use the COUNT_IMPORTS option.
    • +
    + +

    Code example

    +
    import java.util.Collections;       // +0
    +import java.io.IOException;         // +0
    +
    +class Foo {                         // +1, total Ncss = 12
    +  
    +  public void bigMethod()           // +1
    +      throws IOException {     
    +    int x = 0, y = 2;               // +1
    +    boolean a = false, b = true;    // +1
    +    
    +    if (a || b) {                   // +1
    +      try {                         // +1
    +        do {                        // +1
    +          x += 2;                   // +1
    +        } while (x < 12);
    +          
    +        System.exit(0);             // +1
    +      } catch (IOException ioe) {   // +1
    +        throw new PatheticFailException(ioe); // +1
    +      }
    +    } else {
    +      assert false;                 // +1
    +    }
    +  }     
    +}
    +
    + +

    Options

    + +
      +
    • Option NcssVersion#COUNT_IMPORTS: Import and package statements are counted +as well. This version fully complies with JavaNCSS.
    • +
    + +

    NPath complexity (NPath)

    + +

    Operation metric. Can be computed on any non-abstract operation.

    + +

    Description

    + +

    Number of acyclic execution paths through a piece of code. This is related to +cyclomatic complexity, but the two metrics don’t count the same thing: NPath +counts the number of distinct full paths from the beginning to the end of the +method, while Cyclo only counts the number of decision points. NPath is not +computed as simply as Cyclo. With NPath, two decision points appearing sequentially +have their complexity multiplied.

    + +

    The fact that NPath multiplies the complexity of statements makes it grow +exponentially: 10 if - else statements in a row would give an NPath of 1024, +while Cyclo would evaluate to 20. Methods with an NPath complexity over 200 are +generally considered too complex.

    + +

    We compute NPath recursively, with the following set of rules:

    +
      +
    • An empty block has a complexity of 1.
    • +
    • The complexity of a block is the product of the NPath complexity of its +statements, calculated as follows: +
        +
      • The complexity of for, do and while statements is 1, plus the +complexity of the block, plus the complexity of the guard condition.
      • +
      • The complexity of a cascading if statement (if .. else if ..) is the +number of if statements in the chain, plus the complexity of their guard +condition, plus the complexity of the unguarded else block (or 1 if there +is none).
      • +
      • The complexity of a switch statement is the number of cases, plus the +complexity of each case block. It’s equivalent to the complexity of the +equivalent cascade of if statements.
      • +
      • The complexity of a ternary expression (?:) is the complexity of the guard +condition, plus the complexity of both expressions. It’s equivalent to the +complexity of the equivalent if .. else construct.
      • +
      • The complexity of a try .. catch statement is the complexity of the try +block, plus the complexity of each catch block.
      • +
      • The complexity of a return statement is the complexity of the expression +(or 1 if there is none).
      • +
      • All other statements have a complexity of 1 and are discarded from the product.
      • +
      +
    • +
    + +

    Code example

    + +
    void fun(boolean a, boolean b, boolean c) { // NPath = 6
    +    
    +  // block #0
    +  
    +  if (a) {
    +    // block #1
    +  } else {
    +    // block #2
    +  }
    +  
    +  // block #3
    +  
    +  if (b) {
    +    // block #4
    +  } else if (c) {
    +    // block #5  
    +  }
    +  
    +  // block #6
    +}
    +
    +

    After block 0, the control flow can either execute block 1 or 2 before jumping +to block 3. From block three, the control flow will again have the choice +between blocks 4 and 5 before jumping to block 6. The first if offers 2 +choices, the second offers 3, so the cyclomatic complexity of this method is +2 + 3 = 5. NPath, however, sees 2 * 3 = 6 full paths from the beginning to the end.

    + +

    Number Of Public Attributes (NOPA)

    +

    Class metric. Can be computed on classes.

    + +

    Number Of Accessor Methods (NOAM)

    +

    Class metric. Can be computed on classes.

    + +

    Tight Class Cohesion (TCC)

    + +

    Class metric. Can be computed on classes and enums.

    + +

    Description

    + +

    The relative number of method pairs of a class that access in common at +least one attribute of the measured class. TCC only counts +direct attribute accesses, that is, only those attributes that are accessed in +the body of the method [BK95].

    + +

    TCC is taken to be a reliable cohesion metric for a class. High values (>70%) +indicate a class with one basic function, which is hard to break into subcomponents. +On the other hand, low values (<50%) may indicate that the class tries to do too much and +defines several unrelated services, which is undesirable.

    + +

    TCC can be used to detect God Classes and Brain Classes [Lanza05].

    + +

    Weighted Method Count (WMC)

    + +

    Class metric. Can be computed on classes and enums.

    + +

    Description

    + +

    Sum of the statistical complexity of the operations in the class. We use +CYCLO to quantify the complexity of an operation +[Lanza05].

    + +

    Options

    + +

    WMC uses the same options as CYCLO, which are provided to CYCLO when +computing it.

    + +

    Weight Of Class (WOC)

    + +

    Class metric. Can be computed on classes.

    + +

    Description

    + +

    Number of “functional” public methods divided by the total number of +public methods. Our definition of “functional method” excludes +constructors, getters, and setters.

    + +

    This metric tries to quantify whether the measured class’ interface reveals +more data than behaviour. Low values (less than 30%) indicate that the class +reveals much more data than behaviour, which is a sign of poor encapsulation.

    + +

    This metric is used to detect Data Classes, in conjunction with WMC, +NOPA and NOAM.

    + +

    References

    + +

    BK95: Bieman, Kang; Cohesion and reuse in an object-oriented system. +In Proceedings ACM Symposium on Software Reusability, 1995.

    + +

    Lanza05: Lanza, Marinescu; Object-Oriented Metrics in Practice, 2005.

    + +

    McCabe76: McCabe, A Complexity Measure, in Proceedings of the 2nd ICSE (1976).

    + +

    Sonarqube: Sonarqube online documentation.

    + +

    JavaNcss: JavaNCSS online documentation.

    + + +
    + + Tags: + + + + extending + + + + metrics + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_languages_jsp.html b/pmd_languages_jsp.html new file mode 100644 index 0000000000..ee669235eb --- /dev/null +++ b/pmd_languages_jsp.html @@ -0,0 +1,1493 @@ + + + + + + + + +JSP Support | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    JSP Support

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    What is currently supported and what is not

    + +

    In short, JSP files that are XHTML-compliant, are supported. +Except for files that contain inline DTDs; only references to external +DTD files are supported (having inline DTD will result in a parsing +error).

    + +

    The XHTML support means that:

    + +
      +
    • +

      opening tags must be accompanied by corresponding closing tags +(or they must be empty tags). This means that currently a “<HR>” +tag without corresponding closing tag will result in a parsing error.

      +
    • +
    • +

      attribute values must be surrounded by single or double quotes. This means that the following syntax +will result in a parsing error:

      + +

      <MyTag myAttr1=true myAttr2=1024/>

      +
    • +
    • +

      < and > characters must be escaped, or put inside a CDATA section.

      + +

      PMD creates a “Abstract Syntax Tree” representation of source code; the rules use such a tree as input. +For JSP files, the following constructs are parsed into nodes of the tree:

      + +
        +
      • XML-elements, XML-attributes, XML-comments, doctype-declarations, CDATA
      • +
      • JSP-directives, JSP-declarations, JSP-comments, JSP-scriptlets, JSP-expressions, +Expression Language expressions, JSF value bindings
      • +
      • everything else is seen as flat text nodes.
      • +
      +
    • +
    • +

      Java code (e.g. in JSP-scriptlets) and EL expressions are not parsed or +further broken down. If you want to create rules that check the code +inside EL expressions or JSP scriptlets (a.o.), you currently would +have to do “manual” string manipulation (e.g. using regular expressions).

      +
    • +
    + +

    How to use it

    + +

    Using the command-line interface, two new options can be used in the arguments string:

    + +
      +
    • “-jsp” : this triggers checking JSP files (they are not checked by default)
    • +
    • “-nojava” : this tells PMD not to check java source files (they are checked by default)
    • +
    + +

    Using the Ant task, you decide if PMD must check JSP files by choosing +what files are given to the PMD task. If you use a fileset that +contains only “.java” files, JSP files obviously will not be checked.

    + +

    If you want to call the PMD API for checking JSP files, you should investigate the javadoc of PMD.

    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_next_major_development.html b/pmd_next_major_development.html new file mode 100644 index 0000000000..0214a360a5 --- /dev/null +++ b/pmd_next_major_development.html @@ -0,0 +1,2763 @@ + + + + + + + + +PMD 7.0.0 development | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    PMD 7.0.0 development

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    We’re excited to bring you the next major version of PMD! +Here is a summary of what is planned for PMD 7.

    + +

    To give us feedback or to suggest a new feature, drop us a line on Gitter!

    + +

    Summary

    + + + +

    We decided it’s time to have a modernized logo and get rid of the gun. This allows to include +the logo in anywhere without offense.

    + +

    The current tasks are listed here: Integrate new PMD logo #1931

    + +

    API

    + +

    The API of PMD has been growing over the years and needs to be cleaned up. The goal is, to +have a clear separation between a well-defined API and the implementation, which is internal. +This should help us in future development. This however entails some incompatibilities and +deprecations, see also the sections New API support guidelines and +[Planned API removals](#planned-api-removals] below.

    + +

    Full Antlr Support

    + +

    PMD 6 only supports JavaCC based grammars, but with Antlr parsers +can be generated as well. PMD 7 adds full support for grammars written in Antlr, which allows +to leverage existing grammars.

    + +

    The current tasks are listed here: Support for ANTLR based grammars with Swift as an example language #2499

    + +

    Documentation

    + +

    We have quite some ideas how we want to improve the documentation. The goal is, that the documentation is +up to date and nearly complete. One big task is, how the built-in rules are presented, so that users +can easier see, what exactly is available and decide, which rules are useful for the project at hand.

    + +

    The current tasks are listed here: Documentations improvements tracker #1139

    + +

    XPath

    + +

    PMD 6 supports XPath 1.0 via the Jaxen library. This library is old and unmaintained creating some problems +(one of which is duplicated classes in the package org.w3c.dom which is a Java API actually). +Therefore XPath 1.0 support will be dropped and we upgrade our XPath 2.0 implementation with Saxon moving +on to Saxon HE. This will eventually add support in PMD for XPath 3.1.

    + +

    The current tasks are listed here: XPath Improvements for PMD 7 #2523

    + +

    Java

    + +

    Like the main PMD API, the Java AST has been growing over time and the grammar doesn’t support +all edge cases (e.g. annotation are not supported everywhere). The goal is to simplify the AST by reducing +unnecessary nodes and abstractions and fix the parsing issues. +This helps in the end to provide a better type resolution implementation, but changing the AST is a breaking +API change.

    + +

    Some first results of the Java AST changes are for now documented in the Wiki: +Java clean changes.

    + +

    Miscellaneous

    + +

    There are also some small improvements, refactoring and internal tasks that are planned for PMD 7.

    + +

    The current tasks are listed here: PMD 7 Miscellaneous Tasks #2524

    + +

    New API support guidelines

    + +

    What’s new

    + +

    Until now, all released public members and types were implicitly considered part +of PMD’s public API, including inheritance-specific members (protected members, abstract methods). +We have maintained those APIs with the goal to preserve full binary compatibility between minor releases, +only breaking those APIs infrequently, for major releases.

    + +

    In order to allow PMD to move forward at a faster pace, this implicit contract will +be invalidated with PMD 7.0.0. We now introduce more fine-grained distinctions between +the type of compatibility support we guarantee for our libraries, and ways to make +them explicit to clients of PMD.

    + +

    .internal packages and @InternalApi annotation

    + +

    Internal API is meant for use only by the main PMD codebase. Internal types and methods +may be modified in any way, or even removed, at any time.

    + +

    Any API in a package that contains an .internal segment is considered internal. +The @InternalApi annotation will be used for APIs that have to live outside of +these packages, e.g. methods of a public type that shouldn’t be used outside of PMD (again, +these can be removed anytime).

    + +

    @ReservedSubclassing

    + +

    Types marked with the @ReservedSubclassing annotation are only meant to be subclassed +by classes within PMD. As such, we may add new abstract methods, or remove protected methods, +at any time. All published public members remain supported. The annotation is not inherited, which +means a reserved interface doesn’t prevent its implementors to be subclassed.

    + +

    @Experimental

    + +

    APIs marked with the @Experimental annotation at the class or method level are subject to change. +They can be modified in any way, or even removed, at any time. You should not use or rely + on them in any production code. They are purely to allow broad testing and feedback.

    + +

    @Deprecated

    + +

    APIs marked with the @Deprecated annotation at the class or method level will remain supported +until the next major release but it is recommended to stop using them.

    + +

    The transition

    + +

    All currently supported APIs will remain so until 7.0.0. All APIs that are to be moved to +.internal packages or hidden will be tagged @InternalApi before that major release, and +the breaking API changes will be performed in 7.0.0.

    + +

    Planned API removals

    + +

    List of currently deprecated APIs

    + + + +

    6.29.0

    + +

    No changes.

    + +

    6.28.0

    + +
    Deprecated API
    + +
    For removal
    + + + +

    6.27.0

    + +
      +
    • XML rule definition in rulesets: In PMD 7, the language attribute will be required on all rule +elements that declare a new rule. Some base rule classes set the language implicitly in their +constructor, and so this is not required in all cases for the rule to work. But this +behavior will be discontinued in PMD 7, so missing language attributes are now +reported as a forward compatibility warning.
    • +
    + +
    Deprecated API
    + +
    For removal
    + + + +

    6.26.0

    + +
    Deprecated API
    + +
    For removal
    + + + +

    6.25.0

    + +
      +
    • +

      The maven module net.sourceforge.pmd:pmd-scala is deprecated. Use net.sourceforge.pmd:pmd-scala_2.13 +or net.sourceforge.pmd:pmd-scala_2.12 instead.

      +
    • +
    • +

      Rule implementation classes are internal API and should not be used by clients directly. +The rules should only be referenced via their entry in the corresponding category ruleset +(e.g. <rule ref="category/java/bestpractices.xml/AbstractClassWithoutAbstractMethod" />).

      + +

      While we definitely won’t move or rename the rule classes in PMD 6.x, we might consider changes +in PMD 7.0.0 and onwards.

      +
    • +
    + +
    Deprecated APIs
    + +
    Internal API
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. +You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +
    For removal
    + + + +

    6.24.0

    + +
    Deprecated APIs
    + + + +
    Experimental APIs
    + +

    Note: Experimental APIs are identified with the annotation Experimental, +see its javadoc for details

    + +
      +
    • The experimental methods in BaseLanguageModule have been replaced by a +definitive API.
    • +
    + +

    6.23.0

    + +
    Deprecated APIs
    + +
    Internal API
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. +You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +
    In ASTs
    + +

    As part of the changes we’d like to do to AST classes for 7.0.0, we would like to +hide some methods and constructors that rule writers should not have access to. +The following usages are now deprecated in the Apex, Javascript, PL/SQL, Scala and Visualforce ASTs:

    + +
      +
    • Manual instantiation of nodes. Constructors of node classes are deprecated and +marked InternalApi. Nodes should only be obtained from the parser, +which for rules, means that they never need to instantiate node themselves. +Those constructors will be made package private with 7.0.0.
    • +
    • Subclassing of abstract node classes, or usage of their type. The base classes are internal API +and will be hidden in version 7.0.0. You should not couple your code to them. +
        +
      • In the meantime you should use interfaces like VfNode or +Node, or the other published interfaces in this package, +to refer to nodes generically.
      • +
      • Concrete node classes will be made final with 7.0.0.
      • +
      +
    • +
    • Setters found in any node class or interface. Rules should consider the AST immutable. +We will make those setters package private with 7.0.0.
    • +
    • The implementation classes of Parser (eg VfParser) are deprecated and should not be used directly. +Use LanguageVersionHandler#getParser instead.
    • +
    • The implementation classes of TokenManager (eg VfTokenManager) are deprecated and should not be used outside of our implementation. +This also affects CPD-only modules.
    • +
    + +

    These deprecations are added to the following language modules in this release. +Please look at the package documentation to find out the full list of deprecations.

    + + +

    These deprecations have already been rolled out in a previous version for the +following languages:

    + + +

    Outside of these packages, these changes also concern the following TokenManager +implementations, and their corresponding Parser if it exists (in the same package):

    + + + +

    In the Java AST the following attributes are deprecated and will issue a warning when used in XPath rules:

    + + + +
    For removal
    + + + +

    6.22.0

    + +
    Deprecated APIs
    + +
    Internal API
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. +You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +
    For removal
    + + + +
    In ASTs (JSP)
    + +

    As part of the changes we’d like to do to AST classes for 7.0.0, we would like to +hide some methods and constructors that rule writers should not have access to. +The following usages are now deprecated in the JSP AST (with other languages to come):

    + +
      +
    • Manual instantiation of nodes. Constructors of node classes are deprecated and +marked InternalApi. Nodes should only be obtained from the parser, +which for rules, means that they never need to instantiate node themselves. +Those constructors will be made package private with 7.0.0.
    • +
    • Subclassing of abstract node classes, or usage of their type. The base classes are internal API +and will be hidden in version 7.0.0. You should not couple your code to them. +
        +
      • In the meantime you should use interfaces like JspNode or +Node, or the other published interfaces in this package, +to refer to nodes generically.
      • +
      • Concrete node classes will be made final with 7.0.0.
      • +
      +
    • +
    • Setters found in any node class or interface. Rules should consider the AST immutable. +We will make those setters package private with 7.0.0.
    • +
    • The class JspParser is deprecated and should not be used directly. +Use LanguageVersionHandler#getParser instead.
    • +
    + +

    Please look at net.sourceforge.pmd.lang.jsp.ast to find out the full list of deprecations.

    + +
    In ASTs (Velocity)
    + +

    As part of the changes we’d like to do to AST classes for 7.0.0, we would like to +hide some methods and constructors that rule writers should not have access to. +The following usages are now deprecated in the VM AST (with other languages to come):

    + +
      +
    • Manual instantiation of nodes. Constructors of node classes are deprecated and +marked InternalApi. Nodes should only be obtained from the parser, +which for rules, means that they never need to instantiate node themselves. +Those constructors will be made package private with 7.0.0.
    • +
    • Subclassing of abstract node classes, or usage of their type. The base classes are internal API +and will be hidden in version 7.0.0. You should not couple your code to them. +
        +
      • In the meantime you should use interfaces like VmNode or +Node, or the other published interfaces in this package, +to refer to nodes generically.
      • +
      • Concrete node classes will be made final with 7.0.0.
      • +
      +
    • +
    • Setters found in any node class or interface. Rules should consider the AST immutable. +We will make those setters package private with 7.0.0.
    • +
    • The package net.sourceforge.pmd.lang.vm.directive as well as the classes +DirectiveMapper and LogUtil are deprecated +for removal. They were only used internally during parsing.
    • +
    • The class VmParser is deprecated and should not be used directly. +Use LanguageVersionHandler#getParser instead.
    • +
    + +

    Please look at net.sourceforge.pmd.lang.vm.ast to find out the full list of deprecations.

    + +
    PLSQL AST
    + +

    The production and node ASTCursorBody was unnecessary, not used and has been removed. Cursors have been already +parsed as ASTCursorSpecification.

    + +

    6.21.0

    + +
    Deprecated APIs
    + +
    Internal API
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. +You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +
    For removal
    + + + +

    6.20.0

    + +

    No changes.

    + +

    6.19.0

    + +
    Deprecated APIs
    + +
    For removal
    + + + +
    Internal APIs
    + + + +

    6.18.0

    + +
    Changes to Renderer
    + +
      +
    • +

      Each renderer has now a new method Renderer#setUseShortNames which +is used for implementing the “shortnames” CLI option. The method is automatically called by PMD, if this +CLI option is in use. When rendering filenames to the report, the new helper method +AbstractRenderer#determineFileName should be used. This will change +the filename to a short name, if the CLI option “shortnames” is used.

      + +

      Not adjusting custom renderers will make them render always the full file names and not honoring the +CLI option “shortnames”.

      +
    • +
    + +
    Deprecated APIs
    + +
    For removal
    + + + +
    Internal APIs
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +

    6.17.0

    + +

    No changes.

    + +

    6.16.0

    + +
    Deprecated APIs
    + +
    +

    Reminder: Please don’t use members marked with the annotation InternalApi, as they will likely be removed, hidden, or otherwise intentionally broken with 7.0.0.

    +
    + +
    In ASTs
    + +

    As part of the changes we’d like to do to AST classes for 7.0.0, we would like to +hide some methods and constructors that rule writers should not have access to. +The following usages are now deprecated in the Java AST (with other languages to come):

    + +
      +
    • Manual instantiation of nodes. Constructors of node classes are deprecated and marked InternalApi. Nodes should only be obtained from the parser, which for rules, means that never need to instantiate node themselves. Those constructors will be made package private with 7.0.0.
    • +
    • Subclassing of abstract node classes, or usage of their type. Version 7.0.0 will bring a new set of abstractions that will be public API, but the base classes are and will stay internal. You should not couple your code to them. +
        +
      • In the meantime you should use interfaces like JavaNode or Node, or the other published interfaces in this package, to refer to nodes generically.
      • +
      • Concrete node classes will be made final with 7.0.0.
      • +
      +
    • +
    • Setters found in any node class or interface. Rules should consider the AST immutable. We will make those setters package private with 7.0.0.
    • +
    + +

    Please look at net.sourceforge.pmd.lang.java.ast to find out the full list +of deprecations.

    + +

    6.15.0

    + +
    Deprecated APIs
    + +
    For removal
    + + + +

    6.14.0

    + +

    No changes.

    + +

    6.13.0

    + +
    Command Line Interface
    + +

    The start scripts run.sh, pmd.bat and cpd.bat support the new environment variable PMD_JAVA_OPTS. +This can be used to set arbitrary JVM options for running PMD, such as memory settings (e.g. PMD_JAVA_OPTS=-Xmx512m) +or enable preview language features (e.g. PMD_JAVA_OPTS=--enable-preview).

    + +

    The previously available variables such as OPTS or HEAPSIZE are deprecated and will be removed with PMD 7.0.0.

    + +
    Deprecated API
    + +
      +
    • +

      CodeClimateRule is deprecated in 7.0.0 because it was unused for 2 years and +created an unwanted dependency. +Properties “cc_categories”, “cc_remediation_points_multiplier”, “cc_block_highlighting” will also be removed. +See #1702 for more.

      +
    • +
    • +

      The Apex ruleset rulesets/apex/ruleset.xml has been deprecated and will be removed in 7.0.0. Please use the new +quickstart ruleset rulesets/apex/quickstart.xml instead.

      +
    • +
    + +

    6.12.0

    + +

    No changes.

    + +

    6.11.0

    + + + +

    6.10.0

    + +
    Properties framework
    + +

    The properties framework is about to get a lifting, and for that reason, we need to deprecate a lot of APIs +to remove them in 7.0.0. The proposed changes to the API are described on the wiki

    + +
    Changes to how you define properties
    + + + +

    Here’s an example:

    +
    // Before 7.0.0, these are equivalent:
    +IntegerProperty myProperty = new IntegerProperty("score", "Top score value", 1, 100, 40, 3.0f);
    +IntegerProperty myProperty = IntegerProperty.named("score").desc("Top score value").range(1, 100).defaultValue(40).uiOrder(3.0f);
    +
    +// They both map to the following in 7.0.0
    +PropertyDescriptor<Integer> myProperty = PropertyFactory.intProperty("score").desc("Top score value").require(inRange(1, 100)).defaultValue(40);
    +
    + +

    You’re highly encouraged to migrate to using this new API as soon as possible, to ease your migration to 7.0.0.

    + +
    Architectural simplifications
    + + + +
    Changes to the PropertyDescriptor interface
    + +
      +
    • preferredRowCount is deprecated with no intended replacement. It was never implemented, and does not belong +in this interface. The methods uiOrder and compareTo(PropertyDescriptor) are deprecated for the +same reason. These methods mix presentation logic with business logic and are not necessary for PropertyDescriptors to work. +PropertyDescriptor will not extend Comparable<PropertyDescriptor> anymore come 7.0.0.
    • +
    • The method propertyErrorFor is deprecated and will be removed with no intended +replacement. It’s really just a shortcut for prop.errorFor(rule.getProperty(prop)).
    • +
    • T valueFrom(String) and String asDelimitedString(T) are deprecated and will be removed. These were +used to serialize and deserialize properties to/from a string, but 7.0.0 will introduce a more flexible +XML syntax which will make them obsolete.
    • +
    • isMultiValue and type are deprecated and won’t be replaced. The new XML syntax will remove the need +for a divide between multi- and single-value properties, and will allow arbitrary types to be represented. +Since arbitrary types may be represented, type will become obsolete as it can’t represent generic types, +which will nevertheless be representable with the XML syntax. It was only used for documentation, but a +new way to document these properties exhaustively will be added with 7.0.0.
    • +
    • errorFor is deprecated as its return type will be changed to Optional<String> with the shift to Java 8.
    • +
    + +
    Deprecated APIs
    + +
    For internalization
    + + + +
    For removal
    + + + +

    6.9.0

    + +

    No changes.

    + +

    6.8.0

    + +
      +
    • +

      A couple of methods and fields in net.sourceforge.pmd.properties.AbstractPropertySource have been +deprecated, as they are replaced by already existing functionality or expose internal implementation +details: propertyDescriptors, propertyValuesByDescriptor, +copyPropertyDescriptors(), copyPropertyValues(), ignoredProperties(), usesDefaultValues(), +useDefaultValueFor().

      +
    • +
    • +

      Some methods in net.sourceforge.pmd.properties.PropertySource have been deprecated as well: +usesDefaultValues(), useDefaultValueFor(), ignoredProperties().

      +
    • +
    • +

      The class net.sourceforge.pmd.lang.rule.AbstractDelegateRule has been deprecated and will +be removed with PMD 7.0.0. It is internally only in use by RuleReference.

      +
    • +
    • +

      The default constructor of net.sourceforge.pmd.lang.rule.RuleReference has been deprecated +and will be removed with PMD 7.0.0. RuleReferences should only be created by providing a Rule and +a RuleSetReference. Furthermore the following methods are deprecated: setRuleReference(), +hasOverriddenProperty(), usesDefaultValues(), useDefaultValueFor().

      +
    • +
    + +

    6.7.0

    + +
      +
    • +

      All classes in the package net.sourceforge.pmd.lang.dfa.report have been deprecated and will be removed +with PMD 7.0.0. This includes the class net.sourceforge.pmd.lang.dfa.report.ReportTree. The reason is, +that this class is very specific to Java and not suitable for other languages. It has only been used for +YAHTMLRenderer, which has been rewritten to work without these classes.

      +
    • +
    • +

      The nodes RUNSIGNEDSHIFT and RSIGNEDSHIFT are deprecated and will be removed from the AST with PMD 7.0.0. +These represented the operator of ShiftExpression in two cases out of three, but they’re not needed and +make ShiftExpression inconsistent. The operator of a ShiftExpression is now accessible through +ShiftExpression#getOperator.

      +
    • +
    + +

    6.5.0

    + +
      +
    • +

      The utility class net.sourceforge.pmd.lang.java.ast.CommentUtil has been deprecated and will be removed +with PMD 7.0.0. Its methods have been intended to parse javadoc tags. A more useful solution will be added +around the AST node FormalComment, which contains as children JavadocElement nodes, which in +turn provide access to the JavadocTag.

      + +

      All comment AST nodes (FormalComment, MultiLineComment, SingleLineComment) have a new method +getFilteredComment() which provide access to the comment text without the leading /* markers.

      +
    • +
    • +

      The method AbstractCommentRule.tagsIndicesIn() has been deprecated and will be removed with +PMD 7.0.0. It is not very useful, since it doesn’t extract the information +in a useful way. You would still need check, which tags have been found, and with which +data they might be accompanied.

      +
    • +
    + +

    6.4.0

    + +
      +
    • The following classes in package net.sourceforge.pmd.benchmark have been deprecated: Benchmark, Benchmarker, +BenchmarkReport, BenchmarkResult, RuleDuration, StringBuilderCR and TextReport. Their API is not supported anymore +and is disconnected from the internals of PMD. Use the newer API based around TimeTracker instead, which can be found +in the same package.
    • +
    • The class net.sourceforge.pmd.lang.java.xpath.TypeOfFunction has been deprecated. Use the newer TypeIsFunction in the same package.
    • +
    • The typeof methods in net.sourceforge.pmd.lang.java.xpath.JavaFunctions have been deprecated. +Use the newer typeIs method in the same class instead..
    • +
    • The methods isA, isEither and isNeither of net.sourceforge.pmd.lang.java.typeresolution.TypeHelper. +Use the new isExactlyAny and isExactlyNone methods in the same class instead.
    • +
    + +

    6.2.0

    + +
      +
    • +

      The static method PMDParameters.transformParametersIntoConfiguration(PMDParameters) is now deprecated, +for removal in 7.0.0. The new instance method PMDParameters.toConfiguration() replaces it.

      +
    • +
    • +

      The method ASTConstructorDeclaration.getParameters() has been deprecated in favor of the new method +getFormalParameters(). This method is available for both ASTConstructorDeclaration and +ASTMethodDeclaration.

      +
    • +
    + +

    6.1.0

    + +
      +
    • The method getXPathNodeName is added to the Node interface, which removes the +use of the toString of a node to get its XPath element name (see #569). +
        +
      • The default implementation provided in AbstractNode, will +be removed with 7.0.0
      • +
      • With 7.0.0, the Node.toString method will not necessarily provide its XPath node +name anymore.
      • +
      +
    • +
    • +

      The interface net.sourceforge.pmd.cpd.Renderer has been deprecated. A new interface +net.sourceforge.pmd.cpd.renderer.CPDRenderer has been introduced to replace it. The main +difference is that the new interface is meant to render directly to a java.io.Writer +rather than to a String. This allows to greatly reduce the memory footprint of CPD, as on +large projects, with many duplications, it was causing OutOfMemoryErrors (see #795).

      + +

      net.sourceforge.pmd.cpd.FileReporter has also been deprecated as part of this change, as it’s no longer needed.

      +
    • +
    + +

    6.0.1

    + +
      +
    • The constant net.sourceforge.pmd.PMD.VERSION has been deprecated and will be removed with PMD 7.0.0. +Please use net.sourceforge.pmd.PMDVersion.VERSION instead.
    • +
    + +

    List of currently deprecated rules

    + + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_projectdocs_committers_main_landing_page.html b/pmd_projectdocs_committers_main_landing_page.html new file mode 100644 index 0000000000..6834408817 --- /dev/null +++ b/pmd_projectdocs_committers_main_landing_page.html @@ -0,0 +1,1532 @@ + + + + + + + + +Main Landing Page | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Main Landing Page

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The main homepage of PMD https://pmd.github.io is hosted by Github Pages.

    + +

    The repository is https://github.com/pmd/pmd.github.io.

    + +

    It uses Jekyll to generate the static html pages. Jekyll is +executed by github for every push to the repository. Please note, that it takes some time +until Jekyll has been executed and due to caching, the homepage is not updated immediately. +It usually takes 15 minutes.

    + +

    Contents

    + + + +

    Building the page locally

    + +

    Since the repository contains the documentation for many old PMD releases, it is quite big. When executing +Jekyll to generate the site, it copies all the files to the folder _site/ - and this can take a while.

    + +

    In order to speed things up locally, consider to add pmd-* to the exclude patterns in _config.yml. See +also the comments in this file.

    + +

    Then it is a matter of simply executing bundle exec jekyll serve. This will generate the site and host +it on localhost, so you can test the page at http://127.0.0.1:4000.

    + +

    Updates during a release

    + +

    When creating a new PMD release, some content of the main page need to be updated as well. +This done as part of the Release process, but is +summarized here as well:

    + +
      +
    • The versions (e.g. pmd.latestVersion) needs to be updated in _config.yml +
        +
      • This is needed to generate the correct links and texts for the latest version on landing page
      • +
      +
    • +
    • The new PMD documentation needs to be copied to /pmd-<version>/
    • +
    • Then this folder needs to copied to /latest/, actually replacing the old version.
    • +
    • A new blog post with release notes is added: /_posts/YYYY-mm-dd-PMD-<version>.md
    • +
    • The sitemap sitemap.xml is regenerated
    • +
    + +

    Some of these steps are automated through do-release.sh (like blog post), some are manual steps +(updating the version in _config.yml) and other steps are done on the travis-ci-build (like +copying the new documentation).

    + +

    Adding a new blog post

    + +

    Adding a new blog post is as easy as:

    + +
      +
    • Creating a new file in the folder “_posts”: /_posts/YYYY-mm-dd-<title>.md
    • +
    • The file name needs to fit this pattern. The date of the blog post is taken from the file name. The “" +is used for the url.
    • +
    • The file is a markdown file starting with a frontmatter for jekyll. Just use this template for the new file:
    • +
    + +
    ---
    +layout: post
    +title: Title
    +---
    +
    +Here comes the text
    +
    + +

    Once you commit and push it, Github will run Jekyll and update the page. The Jekyll templates take care that +the new post is recognized and added to the news section and also on the news subpage.

    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_projectdocs_committers_merging_pull_requests.html b/pmd_projectdocs_committers_merging_pull_requests.html new file mode 100644 index 0000000000..deabd5ca39 --- /dev/null +++ b/pmd_projectdocs_committers_merging_pull_requests.html @@ -0,0 +1,1611 @@ + + + + + + + + +Merging pull requests | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Merging pull requests

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Example 1: Merging PR #123 into master

    + +
      +
    1. +

      Review the pull request

      + +
        +
      • Compilation and checkstyle is verified already by travis build: PRs are automatically checked.
      • +
      • If it is a bug fix, a new unit test, that reproduces the bug, is mandatory. Without such a test, we might accidentally reintroduce the bug again.
      • +
      • Add the appropriate labels on the github issue: If the PR fixes a bug, the label “a:bug” should be used.
      • +
      • Make sure, the PR is added to the appropriate milestone. If the PR fixes a bug, make sure, that the bug issue is added to the same milestone.
      • +
      +
    2. +
    3. +

      The actual merge commands:

      + +

      We assume, that the PR has been created from the master branch. If this is not the case, +then we’ll either need to rebase or ask for rebasing before merging.

      + +
      git checkout master && git pull origin master                    # make sure, you have the latest code
      +git fetch origin pull/123/head:pr-123 && git checkout pr-123     # creates a new temporary branch
      +
      +
    4. +
    5. +

      Update the release notes:

      + +
        +
      • Are there any API changes, that need to be documented? (Section “API Changes”)
      • +
      • Are there any significant changes to existing rules, that should be mentioned? +(Section “Modified Rules” / “New Rules” / “Removed Rules”)
      • +
      • If the PR fixes a bug, make sure, it is listed under the section “Fixed Issues”.
      • +
      • In any case, add the PR to the section “External Contributions”
      • +
      • +

        Commit these changes with the message:

        + +
        git add docs/pages/release_notes.md
        +git commit -m "Update release notes, refs #123"
        +
        +
      • +
      + + +
    6. +
    7. +

      Now merge the pull request into the master branch:

      + +
      git checkout master
      +git merge --no-ff pr-123
      +
      + + +
    8. +
    9. +

      Run the complete build: ./mvnw clean verify

      + + +
    10. +
    11. +

      If the build was successful, you are ready to push:

      + +
      git push origin master
      +
      + +

      Since the temporary branch is now not needed anymore, you can delete it: +git branch -d pr-123.

      +
    12. +
    + +

    Example 2: Merging PR #124 into a maintenance branch

    + +

    We ask, to create every pull request against master, to make it easier to contribute. +But if a pull request is intended to fix a bug in an older version of PMD, then we need to backport this pull request.

    + +

    Creating a maintenance branch

    + +

    For older versions, we use maintenance branches, like pmd/5.8.x. If there is no maintenance branch for +the specific version, then we’ll have to create it first. Let’s say, we want a maintenance branch for +PMD version 5.8.0, so that we can create a bugfix release 5.8.1.

    + +
      +
    1. +

      We’ll simply create a new branch off of the release tag:

      + +
      git branch pmd/5.8.x pmd_releases/5.8.0 && git checkout pmd/5.8.x
      +
      +
    2. +
    3. +

      Now we’ll need to adjust the version, since it’s currently the same as the release version. +We’ll change the version to the next patch version: “5.8.1-SNAPSHOT”.

      + +
      ./mvnw versions:set -DnewVersion=5.8.1-SNAPSHOT
      +git add pom.xml \*/pom.xml
      +git commit -m "prepare next version 5.8.1-SNAPSHOT"
      +
      +
    4. +
    + +

    Merging the PR

    + +
      +
    1. +

      As above: Review the PR

      +
    2. +
    3. +

      Fetch the PR and rebase it onto the maintenance branch:

      + +
      git fetch origin pull/124/head:pr-124 && git checkout pr-124     # creates a new temporary branch
      +git rebase master --onto pmd/5.8.x
      +./mvnw clean verify                                # make sure, everything works after the rebase
      +
      + + +
    4. +
    5. +

      Update the release notes. See above for details.

      +
    6. +
    7. +

      Now merge the pull request into the maintenance branch:

      + +
      git checkout pmd/5.8.x
      +git merge --no-ff pr-124
      +
      +
    8. +
    9. +

      Just to be sure, run the complete build again: ./mvnw clean verify.

      +
    10. +
    11. +

      If the build was successful, you are ready to push:

      + +
      git push origin pmd/5.8.x
      +
      +
    12. +
    13. +

      Since we have rebased the pull request, it won’t appear as merged on github. +You need to manually close the pull request. Leave a comment, that it has been +rebased onto the maintenance branch.

      +
    14. +
    + +

    Merging into master

    + +

    Now the PR has been merged into the maintenance branch, but it is missing in any later version of PMD. +Therefore, we merge first into the next minor version maintenance branch (if existing):

    + +
    git checkout pmd/5.9.x
    +git merge pmd/5.8.x
    +
    + +

    After that, we merge the changes into the master branch:

    + +
    git checkout master
    +git merge pmd/5.9.x
    +
    + + + +

    Merging vs. Cherry-Picking

    + +

    We are not using cherry-picking, so that each fix is represented by a single commit. +Cherry-picking would duplicate the commit and you can’t see in the log, on which branches the fix has been +integrated (e.g. gitk and github show the branches, from which the specific commit is reachable).

    + +

    The downside is a more complex history - the maintenance branches and master branch are “connected” and not separate.

    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_projectdocs_committers_releasing.html b/pmd_projectdocs_committers_releasing.html new file mode 100644 index 0000000000..f000958211 --- /dev/null +++ b/pmd_projectdocs_committers_releasing.html @@ -0,0 +1,1678 @@ + + + + + + + + +Release process | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Release process

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    This page describes the current status of the release process.

    + +

    Since versions 5.4.5 / 5.5.4 there is an automated release process using travis-ci +in place. However, there are still a few steps, that need manual examination.

    + +

    Note: You can find a small shell script in the root of the repo: do-release.sh. This script guides you +through the release process.

    + +

    Preparations

    + +

    Make sure code is up to date and everything is committed and pushed with git:

    + +
    $ ./mvnw clean
    +$ git pull
    +$ git status
    +
    + +

    The Release Notes and docs

    + +

    You can find the release notes here: docs/pages/release_notes.md.

    + +

    The date (date +%d-%B-%Y) and the version (remove the SNAPSHOT) must be updated in docs/_config.yml, e.g.

    + +
    pmd:
    +    version: 6.22.0
    +    previous_version: 6.21.0
    +    date: 12-March-2020
    +    release_type: minor
    +
    + +

    The release type could be one of “bugfix”, “minor”, or “major”.

    + +

    The release notes usual mention any new rules that have been added since the last release. +Please double check the file pmd-core/src/main/resources/rulesets/releases/<version>.xml, so +that all new rules are listed.

    + +

    Add the new rules as comments to the quickstart rulesets:

    +
      +
    • pmd-apex/src/main/resources/rulesets/apex/quickstart.xml
    • +
    • pmd-java/src/main/resources/rulesets/java/quickstart.xml
    • +
    + +

    We maintain a documentation for the next major release. Copy the API +changes from the current release notes to this document: docs/pages/next_major_development.md.

    + +

    The designer lives at pmd/pmd-designer. +Update property pmd-designer.version in pom.xml to reference the latest pmd-designer release. +See https://search.maven.org/search?q=g:net.sourceforge.pmd%20AND%20a:pmd-ui&core=gav for the available releases.

    + +

    Starting with PMD 6.23.0 we’ll provide small statistics for every release. This needs to be added +to the release notes as the last section. To count the closed issues and pull requests, the milestone +on github with the title of the new release is searched. Make sure, there is a milestone +on https://github.com/pmd/pmd/milestones. The following snippet will +create the numbers, that can be attached to the release notes as a last section:

    + +
    LAST_VERSION=6.22.0
    +NEW_VERSION=6.23.0
    +NEW_VERSION_COMMITISH=HEAD
    +
    +echo "### Stats"
    +echo "* $(git log pmd_releases/${LAST_VERSION}..${NEW_VERSION_COMMITISH} --oneline --no-merges |wc -l) commits"
    +echo "* $(curl -s https://api.github.com/repos/pmd/pmd/milestones|jq ".[] | select(.title == \"$NEW_VERSION\") | .closed_issues") closed tickets & PRs"
    +echo "* Days since last release: $(( ( $(date +%s) - $(git log --max-count=1 --format="%at" pmd_releases/${LAST_VERSION}) ) / 86400))"
    +
    + +

    Note: this part is also integrated into do-release.sh.

    + +

    Check in all (version) changes to branch master or any other branch, from which the release takes place:

    + +
    $ git commit -a -m "Prepare pmd release <version>"
    +$ git push
    +
    + +

    The Homepage

    + +

    The github repo pmd.github.io hosts the homepage for https://pmd.github.io.

    + +

    The new version needs to be entered into _config.yml, e.g.:

    + +
    pmd:
    +  latestVersion: 6.22.0
    +  latestVersionDate: 12-March-2020
    +
    + +

    Also move the previous version down into the “downloads” section.

    + +

    Then create a new page for the new release, e.g. _posts/2020-03-12-PMD-6.22.0.md and copy +the release notes into this page. This will appear under the news section.

    + +

    Check in all (version) changes to branch master:

    + +
    $ git commit -a -m "Prepare pmd release <version>"
    +$ git push
    +
    + +

    Creating the release

    + +

    The release is created using the maven-release-plugin. This plugin changes the version by basically +removing the “-SNAPSHOT” suffix, builds the changed project locally, commits the version change, creates +a new tag from this commit, changes the version of the project to the next snapshot, commits this change +and pushes everything.

    + +

    RELEASE_VERSION is the version of the release. It is reused for the tag. DEVELOPMENT_VERSION is the +next snapshot version after the release.

    + +
    mvn -B release:clean release:prepare \
    +    -Dtag=pmd_releases/${RELEASE_VERSION} \
    +    -DreleaseVersion=${RELEASE_VERSION} \
    +    -DdevelopmentVersion=${DEVELOPMENT_VERSION}
    +
    + +

    Once the maven plugin has pushed the tag, travis-ci will start and build a new version from this tag. Since +it is a tag build and a released version build, travis-ci will do a couple of additional stuff:

    + + + +

    After the release

    + +

    The release on travis currently takes about 30 minutes. Once this is done, you can spread the news:

    + +

    Submit a news on SF

    + +

    Submit news to SF on the PMD Project News page. You can use +the following template:

    + +
    PMD <version> released
    +
    +*   Downloads: https://github.com/pmd/pmd/releases/tag/pmd_releases%2F<version>
    +*   Documentation: https://pmd.github.io/pmd-<version>/
    +
    +And Copy-Paste the release notes
    +
    + +

    Write an email to the mailing list

    + +
    To: PMD Developers List <pmd-devel@lists.sourceforge.net>
    +Subject: [ANNOUNCE] PMD <version> released
    +
    +
    +*   Downloads: https://github.com/pmd/pmd/releases/tag/pmd_releases%2F<version>
    +*   Documentation: https://pmd.github.io/pmd-<version>/
    +
    +And Copy-Paste the release notes
    +
    + +

    Prepare the next release

    + +

    Prepare the new release notes

    + +
      +
    • +

      Update version in docs/_config.yml. Note - the next version needs to have a SNAPSHOT in it.

      + +
      pmd:
      +    version: 6.23.0-SNAPSHOT
      +    previous_version: 6.22.0
      +    date: ??-??-2020
      +    release_type: minor
      +
      +
    • +
    • Move version/release info from docs/pages/release_notes.md to docs/pages/release_notes_old.md.
    • +
    • Update version/release info in docs/pages/release_notes.md. Use the following template:
    • +
    + +
    ---
    +title: PMD Release Notes
    +permalink: pmd_release_notes.html
    +keywords: changelog, release notes
    +---
    +
    +## {{ site.pmd.date }} - {{ site.pmd.version }}
    +
    +The PMD team is pleased to announce PMD {{ site.pmd.version }}.
    +
    +This is a {{ site.pmd.release_type }} release.
    +
    +{% tocmaker %}
    +
    +### New and noteworthy
    +
    +### Fixed Issues
    +
    +### API Changes
    +
    +### External Contributions
    +
    +{% endtocmaker %}
    +
    +
    + +

    Commit and push

    + +
    $ git commit -m "Prepare next development version"
    +$ git push origin master
    +
    + +

    Close / Create new milestones

    + +

    Manage the milestones under https://github.com/pmd/pmd/milestones. +Maybe there are some milestones on sourceforge, too: https://sourceforge.net/p/pmd/bugs/milestones.

    + +

    Branches

    + +

    Merging

    + +

    If the release was done on a maintenance branch, such as pmd/5.4.x, then this branch should be +merged into the next “higher” branches, such as pmd/5.5.x and master.

    + +

    This ensures, that all fixes done on the maintenance branch, finally end up in the other branches. +In theory, the fixes should already be there, but you never now.

    + +

    Multiple releases

    + +

    If releases from multiple branches are being done, the order matters. You should start from the “oldest” branch, +e.g. pmd/5.4.x, release from there. Then merge (see above) into the next branch, e.g. pmd/5.5.x and release +from there. Then merge into the master branch and release from there. This way, the last release done, becomes +automatically the latest release on https://pmd.github.io/latest/ and on sourceforge.

    + +

    (Optional) Create a new release branch

    + +

    At some point, it might be time for a new maintenance branch. Such a branch is usually created from +the master branch. Here are the steps:

    + +
      +
    • Create a new branch: git branch pmd/5.6.x master
    • +
    • Update the version in both the new branch and master, e.g. mvn versions:set -DnewVersion=5.6.1-SNAPSHOT +and mvn versions:set -DnewVersion=5.7.0-SNAPSHOT.
    • +
    • Update the release notes on both the new branch and master
    • +
    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_projectdocs_credits.html b/pmd_projectdocs_credits.html new file mode 100644 index 0000000000..084131b071 --- /dev/null +++ b/pmd_projectdocs_credits.html @@ -0,0 +1,1954 @@ + + + + + + + + +Credits | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Credits

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Committers

    + +
      +
    • David Dixon-Peugh - PMD core, much of the early work on the grammar, initial Emacs plugin
    • +
    • Philippe Herlin - Eclipse plugin, fixed bugs in RuleSetFactory
    • +
    • Nascif Abousalh Neto - Emacs plugin
    • +
    • Tom Copeland - PMD core, lead developer, JDeveloper plugin, initial Gel plugin, +initial jEdit plugin, IDEAJ integration, BlueJ extension
    • +
    • Jiger Patel - jEdit plugin
    • +
    • Alan Ezust - jEdit plugin
    • +
    • Ole-Martin Mork - NetBeans plugin
    • +
    • Miguel Griffa - PMD core, over a dozen rules, lots of documentation, and other improvements all over the place
    • +
    • Allan Caplan - PMD core, six rules, lots of bugfixes and improvements to the PMD core
    • +
    • Radim Kubacki - Netbeans plugin, OptimizableToArrayCallRule suggestion, bug reports
    • +
    • Tomasz Slota - Netbeans plugin
    • +
    • Andrey Lumyanski - Gel plugin
    • +
    • Johan Nagels - PMD core, JSP support
    • +
    • Brian Remedios - PMD core, properties subsystem, lots of CPD UI improvements, Eclipse plugin improvements
    • +
    • Xavier Le Vourch - PMD core, numerous bug fixes, UselessStringValueOf, UnnecessaryWrapperObjectCreation, +SimplifyBooleanAssertion
    • +
    • Sven Jacob - DFA subsystem, Eclipse plugin
    • +
    • Wouter Zelle - Lots of bugfixes and cleanups, JUnit test XML design, introduced java.util.logging, BrokenNullCheck, +NonThreadSafeSingleton, DefaultPackage rule, UselessOverridingMethod, ProperLogger, AvoidPrintStackTrace, +SimplifyConditional
    • +
    • Ryan Gustafson - PMD core, assists with Eclipse plugin
    • +
    • Torsten Kleiber - JDeveloper plugin
    • +
    • Romain Pelisse - Various bugfix patches, restructured CPD tokenizers, patch to remove redundant rule, +added Fortran tokenizer, DoNotExtendJavaLangError, JspEncoding, MDBAndSessionBeanNamingConvention, +RemoteSessionInterfaceNamingConvention, LocalInterfaceSessionNamingConvention, LocalHomeNamingConvention, +RemoteInterfaceNamingConvention, AvoidFinalLocalVariable, ClassWithOnlyPrivateConstructorsShouldBeFinal, +TooManyStaticImports, DoNotCallSystemExit, StaticEJBFieldShouldBeFinal
    • +
    + +

    Committers emeritus

    + +
      +
    • Gunnlaugur Thor Briem - NetBeans plugin, Maven build script fixes, bug report on JavaCC parser’s use +of java.lang.Error
    • +
    • David Craine - JBuilder plugin
    • +
    • Tom Burke - Eclipse plugin
    • +
    • Alex Chaffee - various bugfixes and features
    • +
    • Siegfried Goeschl - original Maven plugin, various bugfixes and features
    • +
    • Don Leckie - The PMD GUI
    • +
    • Rich Kilmer - logo design
    • +
    • Paul Kendall - various bugfixes and features
    • +
    • Colin Wilson-Salt - NetBeans plugin team
    • +
    • Brant Gurganus - JCreator integration, Swing GUI work
    • +
    + +

    Significant contributors

    + +
      +
    • Pieter Vanraemdonck - JSP grammar/integration/documentation, DontNestJsfInJstlIteration, NoLongScripts, +NoScriptlets, NoInlineStyleInformation, NoClassAttribute, NoJspForward
    • +
    • Raik Schroeder - data flow analysis layer, YAHTMLRenderer
    • +
    • Steve Hawkins - rewrite of CPD based on Karp-Rabin string matching
    • +
    • Daniel Sheppard - XPath engine integration concept and implementation, advice on Jaxen extension function naming
    • +
    • Brian Ewins - complete rewrite of CPD based on the Burrows-Wheeler transform, fixed DocumentNavigator bug
    • +
    + +

    Contributors

    + +
      +
    • Andy Throgmorton - New XPath getCommentOn function, new rule DontCallThreadRun, fix for rule UseArraysAsList
    • +
    • Nicolas Dordet - Fixed an issue on CloseResource
    • +
    • Juan Jesús García de Soria - Rework CPD algorithm
    • +
    • Sergey Pariev - Fixed an ugly ArrayIndexOutOfBoundsException in CPD for Ruby
    • +
    • Chris Heister - Reported and noted proper fix for bug in IDEAJ renderer operations
    • +
    • Ralf Wagner - Reported bug in UselessOperationOnImmutable, reported and noted proper fix for broken XSLT
    • +
    • Caroline Rioux - Reported bug in ImmutableField
    • +
    • Miroslav Šulc - Reported bug in CloneMethodMustImplementCloneable
    • +
    • Thomas Steininger - Noticed redundant rule
    • +
    • Thomas Leplus - Contributed new rules LogicInversion, ExtendsObject, UselessParentheses, EmptyInitializer, +EmptyStatementBlock, CheckSkipResult.Rewrote UselessStringValueOf, nice patch for ClassCastExceptionWithToArray
    • +
    • Paul Sundling - A nice documentation patch for ruleset links
    • +
    • Matt Koch - Added more detail to PMD XML report
    • +
    • Richard Hands - Fixed CPD symlink confusion
    • +
    • Oleg Skrypnyuk - reported a Java 1.5 grammar bug
    • +
    • Jeff Campbell - Found bug and suggested fix for problem with XMLRenderer and SuppressWarnings(“PMD”) annotations
    • +
    • Kris Jurka - CPD patch to accept “.C” as a filename extension for C/C++ files
    • +
    • Florian Deissenboeck - reported several Java 1.5 grammar bugs
    • +
    • Maarten ter Huurne - BooleanGetMethodName, AddEmptyString, Noticed misspelling in AvoidArrayLoops rule
    • +
    • Lukas Theussl - Patch to bring Maven configuration files up to date
    • +
    • Jason Bennett - Rewrite of annotation-based warning suppression to allow for rule-specific suppression, +noticed useless line in XSLT scripts, fix for UnnecessaryLocalBeforeReturn, wrote NPathComplexity rule, +patches to improve CyclomaticComplexity rule, Implemented: UseCollectionIsEmpty, NcssTypeCount, NcssMethodCount, +NcssConstructor, Patch to detect comparison with new Object
    • +
    • Brent Fisher - Fixed report backslash bug, SummaryHTML report improvements
    • +
    • Larry Brigman - Reported symlink bug in CPD
    • +
    • Harald Rohan - Reported bug in CPD GUI
    • +
    • Stephan Classens - Patch for file closing bug, noted missing varargs setting in ASTFormalParameter
    • +
    • piair - Implemented StringBufferInstantiationWithChar, AvoidUsingOctalValues
    • +
    • Christopher Eagan - Reported bug in VariableNamingConventions
    • +
    • Fabio Insaccanebbia - Improvement for UseArraysAsList, +UnusedNullCheckInEquals, MisplacedNullCheck, UselessOperationOnImmutable, AvoidArrayLoops, UseArraysAsList, +AvoidConstantsInterface, AvoidDecimalLiteralsInBigDecimalConstructor, ClassCastExceptionWithToArray, +BigIntegerInstantiation
    • +
    • Stefan Seidel - Reported Java 1.5 parsing bug
    • +
    • Aaron Optimizer Digulla - Tweaks to pmd.bat
    • +
    • Peter Van de Voorde - Rewrote the ‘create rule XML’ functionality in the designer utility
    • +
    • Josh Devins - Reported bug with annotation parsing
    • +
    • Alan Berg - Reported bug in Ant task
    • +
    • George Thomas - Wrote AvoidRethrowingException rule, new AvoidLosingExceptionInformation rule
    • +
    • Robert Simmons - Reported bug in optimizations package along with suggestions for fix
    • +
    • Brian Remedios - display cleanup of CPD GUI, code cleanup of StringUtil and various rules, +cleanup of rule designer, code cleanup of net.sourceforge.pmd.ant.Formatter.java, +code improvements to Eclipse plugin, created AbstractPoorMethodCall and refactored UseIndexOfChar
    • +
    • Max Tardiveau - A nice XML to HTML stylesheet for CPD.
    • +
    • Ernst Reissner - reported IdempotentOperations bug, reported CloneThrowsCloneNotSupportedException bug, +reported Java 1.5 parsing bug, suggested InstantiationToGetClass, bug reports for +UnusedPrivateField/CloseConnectionRule/ConstructorCallsOverridableMethodRule, +and bug report and documentation suggestions for UseSingletonRule
    • +
    • Maarten Coene - bug report for UnnecessaryConversionTemporary
    • +
    • Jorn Stampehl - Reported bug in UnusedModifier, reported and fixed bugs in +JUnitTestsShouldContainAsserts/CyclomaticComplexity/TooManyFields, noticed redundancy of ExplicitCallToFinalize, +reported bug in AvoidCallingFinalize, reported bug in JUnitAssertionsShouldIncludeMessage, +reported bug in bug report on JUnitTestsShouldContainAsserts
    • +
    • Ulrich Kriegel - reported Ant task documentation bug
    • +
    • Jarkko Hietaniemin - rewrote most of cpd.sh, many C grammar improvements, several CPD documentation suggestions, +noted missing CPD scripts in binary release
    • +
    • Adam Zell - Reported bug in UselessOverridingMethod
    • +
    • Daniel Serodio - Reported bug in ExceptionSignatureDeclaration
    • +
    • John Redford - Reported bug in AvoidProtectedFieldInFinalClass
    • +
    • D’Arcy Smith - Reported bug in UncommentedEmptyConstructor, reported missing RuleViolation methods
    • +
    • Paul Field - Fixed bug in MissingBreakInSwitch, reported a bug in DontImportJavaLang
    • +
    • Attila Korompai - A nice patch to add messages to the NOPMD feature
    • +
    • Levent Gurses - Suggested JSP support for the copy/paste detector
    • +
    • Neil Cafferkey - Reported a typo in AssignmentInOperand
    • +
    • Noel Grandin - bug report for ImmutableField, bug report for MissingStaticMethodInNonInstantiatableClass, +bug report for MissingBreakInSwitch, EqualsNull rule, bug report for IfElseStmtsMustUseBracesRule
    • +
    • Olaf Heimburger - wrote the UseProperClassLoader rule, code changes to get JDeveloper plugin working +under JDev 10.1.3 EA, reported a possible NPE in ReportTree
    • +
    • Mohammad Farooq - Reported new JavaNCSS URL
    • +
    • Jeff Jensen - Reported missing XML schema references in documentation, wrote new XML schema, reported missing +schema refs in example rulesets, suggested posting XML schema on PMD site, discussion of +‘comments in catch block’ feature, suggested description attribute in property element
    • +
    • Christopher Stach - bug report for VariableNamingConventions, bug report for CallSuperInConstructor, +many bug reports for rules that didn’t handle Java 1.5 constructs
    • +
    • Matthew Harrah - noticed missing element in UseCorrectExceptionLogging definition, script bug report
    • +
    • Mike Kaufman - Reported abug in UnnecessaryCaseChange
    • +
    • Elliotte Rusty Harold - reported bug in UseAssertSameInsteadOfAssertTrue, +suggested creating a new ruleset containing rules in each release, UncommentedEmptyConstructor suggestions, +noted missed case for UnusedFormalParameter, documentation suggestions, +reported mistake in UnnecessaryLocalBeforeReturn message, +bug report 1371757 for misleading AvoidSynchronizedAtMethodLevel example, +bug report 1293277 for duplicated rule messages, bug report for ConstructorCallsOverridableMethod, +suggestion for improving command line interface, misspelling report, suggestion for improving Designer +startup script, “how to make a ruleset” documentation suggestions, noticed outdated Xerces jars, +script renaming suggestions, UseLocaleWithCaseConversions rule suggestion
    • +
    • David Karr - reported stale XPath documentation
    • +
    • Dawid Weiss - Reported bug in UnusedPrivateMethod
    • +
    • Shao Lo - Reported bug in CPD
    • +
    • Mathieu Champlon - Added language support to the CPD Ant task
    • +
    • Uroshnor - Reported bug in UseNotifyAllInsteadOfNotify
    • +
    • Jan Koops - Noted missing data in MemberValuePair nodes, bug report for JBuilder plugin
    • +
    • Will Sargent - Implemented AvoidThreadGroup, AvoidThrowingCertainExceptionTypesRule, +AvoidCatchingNPERule, ExceptionAsFlowControlRule, URL updates for ‘Similar projects’ page
    • +
    • Benoit Xhenseval - noted Maven plugin bug (http://jira.codehaus.org/browse/MPPMD-24), +bug report for UnusedPrivateMethod, suggestion to add elapsed time to XML report, +bug report for ImmutableField, many bug reports (with good failure cases!), Ant task patch and bug report, +XSLT patch, suggestion for improving XML report
    • +
    • Barak Naveh - Reported and fixed bug in CallSuperInConstructor
    • +
    • Bhatia Saurabh - Reported a grammar bug, reported a bug in UseStringBufferLength
    • +
    • Chris Erskine - found bad link, documentation suggestions
    • +
    • mhilpert - Reported bugs in UseIndexOfChar and LoggerIsNotStaticFinal
    • +
    • David Corley - Priority filtering XSLT, reported release packaging problem, implemented nifty +Javascript folding for XML report, demo is here, +suggestion for min priority on the command line
    • +
    • Jon Doh - Reported parser bug
    • +
    • Brian R - suggestions for improving UseIndexOfChar, documentation suggestion
    • +
    • Didier Duquennoy - bug reports for InefficientStringBuffering/ConsecutiveLiteralAppends/AppendCharacterWithChar, +several bug reports for InefficientStringBuffering, bug report for ImmutableField, suggestions for +improving Benchmark utility, bug report for InefficientStringBuffering, bug report for +AvoidConcateningNonLiteralsInStringBuffer, reported a missed hit for EqualsNull, bug report for +MissingStaticMethodInNonInstantiatableClass, pmd-netbeans feedback
    • +
    • Paul Smith - patch to fix Ant task ‘minimum priority’ attribute
    • +
    • Erik Thauvin - reported IDEA integration problem
    • +
    • John Kenny - reported bug in ConsecutiveLiteralAppends
    • +
    • Tom Judge - patch for fix to C/C++ multiline literal support for CPD, patch for including .cc files in +C++ CPD checks, patch for JDK compatibility problems
    • +
    • Sean Mountcastle - reported documentation bug
    • +
    • Greg Broderick - provided patch for ‘minimum priority’ support
    • +
    • George Sexton - Bug report 1379701 for CompareObjectsWithEquals, suggested new rule for Additional String +Concatenation Warnings in StringBuffer.
    • +
    • Johan Stuyts - improvements to UncommentedEmptyConstructor, nice patch for UncommentedEmptyConstructor and +UncommentedEmptyMethod, patch to allow empty catch blocks with comments in them, patch to clean up build environment
    • +
    • Bruce Kelly - bug report 1378358 for StringInstantiation, bug report 1376756 for UselessOverridingMethod, +bug report 1376760 for InefficientStringBuffering
    • +
    • Isaac Babsky - tweak for pmd.bat
    • +
    • Hendrik Maryns - reported bug 1375290 for SuppressWarnings facility
    • +
    • Wim Deblauwe - suggested UseAssertNullInsteadOfAssertTrue, +bug report 1373510 for UseAssertSameInsteadOfAssertTrue, suggested putting property names/values in generated docs, +UselessOverridingMethod, reported bug in JUnitTestsShouldContainAsserts, +front page and “how to make a ruleset” patches, noted problems with web site rule index, +bug report for JUnitTestsShouldContainAsserts, Clover license coordination and implementation, +UseCorrectExceptionLogging, coordinated and coded a much nicer asXML() implementation, +suggested cleanup of UnusedFormalParameter, Javadoc patch, SystemPrintln bug report, +helped get Ant task and CLI squared away with Java 1.5 params, Java 1.5-specific bug reports, +suggested improvements for ExceptionSignatureDeclaration
    • +
    • Sean Montgomery - bug report 1371980 for InefficientStringBuffering
    • +
    • Jean-Marc Vanel - suggested enhancements to the PMD scoreboard
    • +
    • Andriy Rozeluk - suggested UseStringBufferLength, bug report 1306180 for +AvoidConcatenatingNonLiteralsInStringBuffer, reported bug 1293157 for UnusedPrivateMethod, +suggested UnnecessaryCaseChange, bug report for SimplifyConditional, suggested UnnecessaryLocalBeforeReturn, +suggestions for improving BooleanInstantiation, UnnecessaryReturn, AvoidDuplicateLiterals RFEs and bug reports, +various other RFEs and thoughtful discussions as well
    • +
    • Bruno Juillet - suggested reporting suppressed warnings, bug report for missing package/class/method names, +patch for Ant task’s excludeMarker attribute, bug report on ruleset overrides
    • +
    • Derek Hofmann - suggestion for adding –skip-duplicate-files option for CPD, bug report for CPD skipping header +files when in C/C++ mode
    • +
    • Mark Holczhammer - bug report for InefficientStringBuffering
    • +
    • Raja Rajan - 2 bug reports for CompareObjectswithEquals
    • +
    • Jeff Chamblee - suggested better message for UnnecessaryCaseChange, bug report for CompareObjectsWithEquals
    • +
    • Dave Brosius - suggested MisleadingVariableName rule, a couple of nice patches to clean up some string handling +inefficiencies, non-static class usages, and unclosed streams/readers - found with Findbugs, I daresay :-)
    • +
    • Chris Grindstaff - fixed SWTException when Eclipse plugin is run on a file with syntax error
    • +
    • Eduard Naum - fixed JDK 1.3 runtime problems in Eclipse plugin
    • +
    • Jacques Lebourgeois - fix for UTF8 characters in Eclipse plugin
    • +
    • dvholten - suggestions for improving OverrideBothEqualsAndHashcode, formatting suggestions for HTML report, +test cases for ConstructorCallsOverridableMethod, reported several NullAssignment bugs
    • +
    • Brian Duff - helped get Oracle JDeveloper plugin working
    • +
    • Sivakumar Mambakkam - bug report 1314086 for missing name in SimpleRuleSetNameMapper
    • +
    • Rodrigo Ruiz - bug report 1312723 for FieldDeclaration nodes inside interfaces, bug report 1312754 for +pmd.bat option handling, bug report 1312720 (and code fix!) for DefaultPackage, bug report 1309235 for TooManyFields
    • +
    • Lori Olson - JBuilder plugin suggestions and prerelease tests, +found copy/paste bug in rule descriptions
    • +
    • Thomas Dudziak - bug report 1304739 for StringInstantiation
    • +
    • Pieter Bloemendaal - reported JDK 1.3 parsing bug 1292609, command line docs bug report, +bug report for UnusedPrivateMethod, found typo in ArrayIsStoredDirectly, bug report for +AvoidReassigningParametersRule
    • +
    • shawn2005 - documentation bug report
    • +
    • Andrew Taylor - bug report for StringInstantiation
    • +
    • S. David Pullara - bug report for AvoidConcateningNonLiteralsInStringBuffer, bug report for ImmutableField
    • +
    • Maarten Bodewes - bug report for ImmutableField
    • +
    • Peter Frandsen - PackageCase rule, NoPackage rule
    • +
    • Noureddine Bekrar - French translation of some PMD documentation
    • +
    • Martin Jost - bug report for JDeveloper plugin
    • +
    • Guillaume Boudreau - patches to fix problems with CPD’s FileFinder and NTFS and SCCS
    • +
    • Sylvain Veyrie - bug report for MethodReturnsInternalArray
    • +
    • Randy Ray - bug report for ArrayIsStoredDirectly
    • +
    • Klaus - Suggestion for improving UseSingleton
    • +
    • Nicolai Czempin - Bug report for UnnecessaryParentheses, various rule suggestions, additional PMD backronyms
    • +
    • Kevin Routley - reported Ant task dependency problem, reported problems with RuleSetFactory unit tests
    • +
    • Dennis Klemann - noted that errors were missing from text report, reported Java 1.5 parsing bug with +ExceptionSignatureDeclaration, reported fix for pmd.bat problem
    • +
    • Tor Norbye - Suggested CompareObjectsWithEquals
    • +
    • Thomas Skariah - bug reports for MethodArgumentCouldBeFinal and AvoidReassigningParameters
    • +
    • Tom Parker - bug report for MethodReturnsInternalArray, found missed case in NullAssignment, suggested addition +to UnnecessaryBooleanAssertion, suggested splitting up AvoidThrowingCertainExceptionTypes, +AvoidInstantiatingObjectsInLoops bug report, AtLeastOneConstructor bug report
    • +
    • Ian Flanigan - reported CPD JNLP breakage
    • +
    • Glen Cordrey - Reported bug involved JavaCC string handling
    • +
    • Oto ‘tapik’ Buchta - Patched XMLRenderer for UTF8 support
    • +
    • Arent-Jan Banck - Reported bug with Java 1.5 annotation handling
    • +
    • Fred Hartman - Reported exact location of bug in TooManyFields, fixed bug in UnnecessaryBooleanAssertion
    • +
    • Andreas Ehn - Reported bug with Java 1.5 generics parsing
    • +
    • Eric Olander - SingularField, SimplifyConditional fix, UseStringBufferForStringAppends, CollapsibleIfStatements, +AvoidInstanceofChecksInCatchClause, AssignmentToNonFinalStatic rule, nice patch for DFAPanel cleanup, AvoidProtectedFieldInFinalClass, ImmutableFieldRule, noticed missing image in Postfix nodes
    • +
    • Tomas Gustavsson - reported pmd-web breakage
    • +
    • Payal Subhash - Tweaks to CSVRenderer
    • +
    • Christophe Mourette - Reported JDK 1.3 problem with XMLRenderer
    • +
    • Alex Givant - caught documentation bug
    • +
    • Luke Francl - suggested UnnecessaryParentheses rule, numerous high quality +feature suggestions and bug reports
    • +
    • David Hovemeyer - reported missing labelled stmt images, a nice patch to let PMD process code in jar/zip files
    • +
    • Peter ‘Bruno’ Kofler - reported bug #1146116 for JUnitTestsShouldIncludeAssert
    • +
    • Zev Blut - nice patch to add Ruby support to CPD
    • +
    • Christopher Judd - a nice patch to the XSLT that adds a summary
    • +
    • John Meagher - suggested the rule ‘MissingSerialVersionUID’ and provided the implementation for it
    • +
    • John Austin - patch to fix mispeling in Eclipse plugin message
    • +
    • Paddy Fagan - reported bug in StatisticalRule
    • +
    • Leszek Migdal - reported documentation mistake for Eclipse plugin
    • +
    • Hakan Civelek - an order-of-magnitude optimization to the SystemOutPrintln rule
    • +
    • John Heintz - Added “any language” support to CPD.
    • +
    • Harald Gurres - cleaned up the symbol table code with a very nice patch
    • +
    • Matthias Kerkhoff - CPD suggestions, several bug reports
    • +
    • Chris Riesbeck - identified some dead code in RuleSet
    • +
    • Lars Gregori - reported a bug in the Ant task docs
    • +
    • Todd Wright - reported bug in EmptyStatementNotInLoop, XPath port of +AtLeastOneConstructorRule, ConfusingTernaryExpression rule, reported missing ASTUnaryExpressionNotPlusMinus nodes
    • +
    • Conrad Roche - UnusedModifier bug report, other bug reports
    • +
    • Mike Thome - NOPMD implementation concept, BadComparisonRule suggestion
    • +
    • Ken Foskey - C++ parser bug report, cpd.sh
    • +
    • ehowe - a nice patch to include rule priority in the XML report
    • +
    • aryanto - reported a broken reference in the ‘favorites’ ruleset.
    • +
    • Archimedes Trajano - suggested SimpleDateFormatNeedsLocale
    • +
    • Joerg Kurt Wegner - bug report for UnusedLocalVariable
    • +
    • Bruno - Reported bug with TooManyFields, SuspiciousEqualsMethodName
    • +
    • Philippe Couton - bug report for ExceptionAsFlowControl, OverrideBothEqualsAndHashcodeRule bug report, +UseSingletonRule improvements, JUnitStaticSuiteRule improvements
    • +
    • Paul Rowe - suggestion for improving MethodWithSameNameAsEnclosingClass, bug reports for +SimplifyBooleanExpressions and UnusedLocalVariable
    • +
    • Enno Derksen - enhancements to VariableNamingConventionsRule
    • +
    • Michael Haggerty - bug reports for FinalizeDoesNotCallSuperFinalize and UnusedModifier
    • +
    • Phil Shaw - documentation suggestions
    • +
    • Sreenivasa Viswanadha - reminded me to use BufferedInputStreams, grammar cleanup for Ctrl-Z problem
    • +
    • Austin Moore - Integration with Omnicore’s CodeGuide IDE
    • +
    • Matt Inger - CloneMethodMustImplementCloneable, CloneThrowsCloneNotSupportedException
    • +
    • Morgan Schweers - Javascript highlighter for the PMD scoreboard
    • +
    • Brandon Franklin - bug report for BeanMembersShouldSerializeRule, many PMD scoreboard ideas
    • +
    • Bertrand Mollinier Toublet - Bug report which led to platform character set encoding enhancement
    • +
    • Choi Ki Soo - Found bug in XMLRenderer
    • +
    • Gero Wedemann - Found bug in +RuleSetFactory XPath message variable substitution
    • +
    • Adrian Papari - Wrote the PapariTextRenderer
    • +
    • Curt Cox - some additions to the ‘Similar Projects’ page
    • +
    • Michael Griffel - bug fix for XMLRenderer
    • +
    • Doug Tillman - correction to finalizers.xml examples
    • +
    • Luis Alberto Domínguez Ruiz - bug report for IfElseStmtsMustUseBracesRule
    • +
    • Chad Loder - SuspiciousOctalEscapeRule, EmptyStatementNotInLoop, SuspiciousHashcodeMethodName, +NonCaseLabelInSwitchStatement, DefaultLabelNotLastInSwitchStmt, NonStaticInitializer, ExplicitCallToFinalize, +MethodWithSameNameAsEnclosingClassRuleTest, FinalizeDoesNotCallSuperFinalize, FinalizeOverloaded, +FinalizeOnlyCallsSuperFinalize, UnconditionalIfStatement, AvoidDollarSigns, EmptyStaticInitializer, +EmptyFinalizerMethod rule, DontImportSun rule, improvements to ASTBooleanLiteral
    • +
    • Maik Schreiber - AccessNode bug report, other bug reports
    • +
    • Lokesh Gupta - improvements to the AST viewer
    • +
    • Jesse Glick - improvements to +VariableNamingConventionsRule, patch for UnusedModifierRule, bug fix for VariableNameDeclarations rule, +an excellent discussion on the UnnecessaryConstructorRule
    • +
    • Nicolas Liochon - CloneShouldCallSuperCloneRule implementation
    • +
    • Slava Pestov - Suggestions for jEdit plugin enhancements.
    • +
    • Olivier Mengué - Diagnosed and patched XML report character encoding problems
    • +
    • Hariolf Häfele - PMD-JDeveloper plugin bug reports
    • +
    • Vladimir Bossicard - suggested AbstractNamingRule, test package +organization suggestions, VBHTMLRenderer, numerous feature requests and bug reports, several rule suggestions +derived from JUnit-Addons, evangelism :-)
    • +
    • Ken Foskey - noticed bad link
    • +
    • Stephan Janssen - +promoted PMD for JJGuidelines
    • +
    • Ron Sidi - bug reports
    • +
    • David Koontz - suggestions for tweaking PMD command line options
    • +
    • Jeff Epstein - TextPad integration and tests
    • +
    • Gabe Johnson - CloseConnectionRule
    • +
    • Roelof Vuurboom - posted report of QStudio analysis of PMD
    • +
    • Jeff Anderson - node finding utility code
    • +
    • Boris Gruschko - regression test suites, nifty AST/XPath viewer
    • +
    • Trevor Harmon - rewrote XSLT script
    • +
    • Vadim Nasardinov - xdocs cleanup, +run.sh cleanup
    • +
    • Sigiswald Madou - bug report
    • +
    • Dan Tullis - bug report
    • +
    • George Menhorn - CPD bug reports and suggestions
    • +
    • Paul Roebuck - Ant build improvement, several bug reports
    • +
    • Jon A. Maxwell - Bug report
    • +
    • Erik Lee - Bug report
    • +
    • Joerg K. Wegner - PMD scoreboard suggestions
    • +
    • Chris Webster - fix (and test) for UnnecessaryConstructorRule, BooleanInstantiation rule
    • +
    • Colin Simmonds - detailed bug reports
    • +
    • Trond Andersen - AvoidCatchingThrowable, ExceptionSignatureDeclaration, +ExceptionTypeChecking
    • +
    • Bernd Jansen - grammer modification
    • +
    • Jarle Naess - bug report
    • +
    • Jeff Anderson - VariableNamingConventionsRule, MethodNamingConventionsRule, ClassNamingConventionsRule
    • +
    • Frank van Puffelen - documentation suggestions
    • +
    • mcclain looney - patch for CPD GUI, bug reports
    • +
    • Ralf Hauser - Various documentation suggestions, cygwin-run.sh
    • +
    • Pablo Casado - Bug report for UseSingletonRule
    • +
    • Frank Hardisty - BeanMembersShouldSerializeRule
    • +
    • Randall Schulz - bug report for LooseCouplingRule
    • +
    • Wim Bervoets - bug report for the PMD Ant task
    • +
    • Niels Peter Strandberg - various tweaks to the PMD Swing UI
    • +
    • Ian Shef - documentation updates, bug reports on the Gel IDE plugin
    • +
    • Astro Jetson Jr - a tweak for the ShortVariableNameRule
    • +
    • Paul King - a complete rewrite of the Gel plugin
    • +
    • Gael Marziou - “exclude” rule feature request, bug reports
    • +
    • Philippe T’Seyen - refactoring and cleanup of the CPD Ant task, an XML renderer (with unit tests!) for CPD
    • +
    • Michael Montuori - bug reports on the Gel IDE plugin
    • +
    • Michael Hosier - bug reports on the Gel IDE plugin
    • +
    • Richard Jenson - CPD on Win32 troubleshooting
    • +
    • Daniel Bruguier - CPD on Win32 troubleshooting
    • +
    • Mario Claerhout - CPD optimizations and suggestions
    • +
    • Sameer Nanda - CPD Ant task bug report
    • +
    • Nanne Baars - grammar suggestions, rule suggestions
    • +
    • Adam Nemeth - bug fixes for UnnecessaryConstructorRule
    • +
    • Andrew Glover - the CPDTask, ExcessivePublicCountRule, +CouplingBetweenObjectsRule, ExcessiveImportsRule, documentation tweaks
    • +
    • Robert Leland - bug report
    • +
    • Carl Gilbert - AccessorClassGenerationRule, DoubleCheckedLockingRule, ConstructorCallsOverridableMethodRule, +bug reports, feature requests, and documentation improvements
    • +
    • Dave Fuller - improved resource loading code (packaged in a nice diff, too!)
    • +
    • David Whitmore - parser bug report
    • +
    • David Campbell - detailed bugs reports, Ant task refactoring, documentation tweaks
    • +
    • Michael Sutherland - bug report in IfStmtMustUseBracesRule
    • +
    • Egon Willighagen - PMD scoreboard suggestion
    • +
    • Adam Nemeth - bug report on missing final attribute for local variable declarations
    • +
    • Frederic Harper - bug report and subsequent troubleshooting
    • +
    • Mats Henricson - an XSLT script and several bug reports
    • +
    • Martin Cooper - feature suggestions
    • +
    • Bruce Mayhew - feedback on the jEdit plugin
    • +
    • Juergen Ebert - feature suggestions and pmd-netbeans feedback
    • +
    • J.D. Fagan - feature suggestions
    • +
    • William McArthur - ForLoopShouldBeWhileLoop rule
    • +
    • Ales Bukovsky - pmd-netbeans feedback
    • +
    • Stefan Bodewig - bug report
    • +
    • Sean Sullivan - rule suggestions
    • +
    • Dale Vissar - rule suggestions
    • +
    • Alina Copeland - +PMD scoreboard formulas, pmd-dcpd optimizations
    • +
    • Vincent Massol - bug reports, design suggestions, feature suggestions, Maven guidance
    • +
    • Peter Donald - design suggestions
    • +
    • Liam Holohan - bug reports
    • +
    • Ralph Schaer - bug reports and verification
    • +
    • Damian O’Neill - Ant task patches
    • +
    • Sebastian Raffel - Great job on the Eclipse PMD perspective, new views and dataflow analysis support
    • +
    • Ebu - Eclipse smoothed icons
    • +
    • Jacques Lebourgeois - Eclipse fix malformed UTF-8 characters
    • +
    • Chris Grindstaff - Eclipse fix SWTException when PMD is run on a file with syntax error
    • +
    • jmichelberger - wrote Byte/Short/Long Instantiation migration rules
    • +
    • Edwin Chan - Support for -auxclasspath for use with Type Resolution
    • +
    • Jared Bunting - Patch to add ASTAnnotationMethodDeclaration to Java AST
    • +
    • Lucian Ciufudean - RedundantFieldInitializerRule
    • +
    • Andreas Dangel - GodClass and LawOfDemeter rules, several bugfixes and cleanup
    • +
    • Riku Nykanen - patch improving TooManyMethods rule
    • +
    • Tammo van Lessen - new rule GuardDebugLogging for Jakarta Commons Logging ruleset.
    • +
    • Steven Christou - patch improving DoNotCallSystemExit rule
    • +
    • Cd-Man - patch to improve CPD performance
    • +
    • Suresh - new rule DontUseFloatTypeForLoopIndices
    • +
    • Dinesh Bolkensteyn and SonarSource - Java 7 grammar support
    • +
    • Tom Wheeler - contribute a launch script for CPD GUI
    • +
    • Remi Delmas - change CPD CLI to return a non null value when code duplication is found.
    • +
    • Victor Bucutea - Improved JSP parser to be less strict with not valid XML documents (like HTML).
    • +
    • Prabhjot Singh - Fixed bug 3484404: Invalid NPath calculation in return statement.
    • +
    • Roman - Fixed bug 3546093: Type resolution very slow for big project.
    • +
    • Florian Bauer - Add C# support for CPD.
    • +
    • Matthew Short - Support in CPD for IgnoreAnnotations and SuppressWarnings(“CPD-START”).
    • +
    • Simon Gijsen - contributing a PMD logo with a modern look.
    • +
    • Yiannis Paschalidis - Fixed bug #968 Issues with JUnit4 @Test annotation with expected exception
    • +
    • Jaroslav Snajberk - Make the comment required rule working.
    • +
    • Mat Booth - #1109 Patch to build with Javacc 5.0
    • +
    • Stuart Turton - for PLSQL support. See also pldoc
    • +
    • Andrey Utis - for adding Apache Velocity as a new language and writing up a +howto for adding new languages.
    • +
    • Alan Hohn - for adding Standard and modified cyclomatic complexity rules
    • +
    • Jan van Nunen - for adding CPD support for Matlab, Objective-C, Python, Scala and various bug fixes
    • +
    • Juan Martín Sotuyo Dodero - for many bugfixes/pull requests improving Java grammar and performance
    • +
    + +

    Organizations

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + MicroDoc for sponsoring PMD development. + MicroDoc is a software business serving an international customer base. Since 1991 MicroDoc + has grown into a technology oriented software engineering and professional services company. + Our focus on complex software technology and software infrastructure made us a well + respected partner for large corporations and even for other software businesses. +
    + AE for the JSP integration and especially for writing the JSP grammar. +
    + DARPA for funding + the Ultra*Log and Cougaar + effort which spawned PMD. +
    + SourceForge for providing hosting services for PMD. +
    + RefactorIT for letting + their software be used free-of-charge on PMD code + (OpenSource + Community License) +
    + QA-Systems for sending in some + handy utilities for PMD and shipping PMD inside their QStudio product +
    + Vanward Technologies for + using PMD inside their Convergence product +
    + Cenqua for + giving us a free Clover license and doing a nice FishEye run. +
    + YourKit is kindly supporting open source projects with its full-featured Java Profiler. + YourKit, LLC is creator of innovative and intelligent tools for profiling + Java and .NET applications. Take a look at YourKit's leading software products: + YourKit Java Profiler and + YourKit .NET Profiler. +
    + Bijzonder Bezig for giving the PMD logo a modern look. +
    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_projectdocs_faq.html b/pmd_projectdocs_faq.html new file mode 100644 index 0000000000..f5433cc0a9 --- /dev/null +++ b/pmd_projectdocs_faq.html @@ -0,0 +1,1487 @@ + + + + + + + + +FAQ | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    FAQ

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Rules

    + +

    How useful are the rules?

    + +

    Have this clear: having a projects with no pmd violations does not mean at all, I repeat, +it does not mean at all, not at the minimum expected, that the project has any quality. +For illustrating this I’ll tell a little story taken from my work (a sadly real story). +Some classes had fields that were reported as unused, (unused code ruleset) as developers +saw this, they wanted to remove the violation, (not fix the code, fix the violation) so +the action took was to add useless log sentences with something like: +‘unused variable ‘+unusedVariable. Believe it or not, the code was worse than the original +and reported less pmd violations.

    + +

    In a more positive way: use the rules as you see them fix, don’t try to remove violations +per-se, try to review the code and see if the particular cases you are using are correct or not.

    + +

    Development

    + +

    In which order are nodes visited?

    + +

    The parser performs a depth-first traversal. +Consider the given source:

    + +
    public class Foo {
    +    String name;
    +    private class Bar {
    +        String x;
    +    }
    +    int total;
    +}
    +
    + +

    The visiting order here will be:

    + +
      +
    1. Class Foo
    2. +
    3. Field name
    4. +
    5. Class Bar
    6. +
    7. Field x
    8. +
    9. Field total
    10. +
    + +

    Note that the total field of Foo will be visited after visiting the fields in Bar. +You must take this into account for certain rules.

    + +

    Is there a simple way of getting fields from a given class?

    + +

    Yes, the symbol table can supply that information.

    + +

    FIXME: add code example

    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_projectdocs_trivia_meaning.html b/pmd_projectdocs_trivia_meaning.html new file mode 100644 index 0000000000..e788a24cd9 --- /dev/null +++ b/pmd_projectdocs_trivia_meaning.html @@ -0,0 +1,1456 @@ + + + + + + + + +What does 'PMD' mean? | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    What does 'PMD' mean?

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    We’ve been trying to find the meaning of the letters PMD - because frankly, we don’t +really know. We just think the letters sound good together.

    + +

    However, in the spirit of the Computing Industry, we have come up with several “backronyms” to explain it.

    + +

    PMD…

    + +
      +
    • Pretty Much Done
    • +
    • Project Mess Detector
    • +
    • Project Monitoring Directives
    • +
    • Project Meets Deadline
    • +
    • Programming Mistake Detector
    • +
    • Pounds Mistakes Dead
    • +
    • PMD Meaning Discovery (recursion, hooray!)
    • +
    • Programs of Mass Destruction
    • +
    • Programming Meticulous coDe
    • +
    • A ‘Chaotic Metal’ rock band name
    • +
    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_projectdocs_trivia_news.html b/pmd_projectdocs_trivia_news.html new file mode 100644 index 0000000000..490272e83b --- /dev/null +++ b/pmd_projectdocs_trivia_news.html @@ -0,0 +1,1573 @@ + + + + + + + + +PMD in the press | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    PMD in the press

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Sites/Articles about PMD

    + +

    Salesforce / Apex Language Module

    + + + +

    PMD in general and other Language Modules

    + + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_projectdocs_trivia_products.html b/pmd_projectdocs_trivia_products.html new file mode 100644 index 0000000000..d1dc3389b5 --- /dev/null +++ b/pmd_projectdocs_trivia_products.html @@ -0,0 +1,1504 @@ + + + + + + + + +Products/books related to PMD | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Products/books related to PMD

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Open source products

    + +
      +
    • +

      Glean - Aggregates PMD + numerous other source code feedback tools

      +
    • +
    • +

      QALab - Aggregates PMD + Checkstyle + FindBugs and tracks problems over time

      +
    • +
    • +

      XRadar - Using PMD, CPD, and lots of other projects to give measurements on +standard software metrics such as package metrics and dependencies, code size and complexity, code duplications, +coding violations and code-style violations.

      +
    • +
    + +

    Commercial products

    + + + +

    Books that mention PMD

    + + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_projectdocs_trivia_similarprojects.html b/pmd_projectdocs_trivia_similarprojects.html new file mode 100644 index 0000000000..83b46519e5 --- /dev/null +++ b/pmd_projectdocs_trivia_similarprojects.html @@ -0,0 +1,1511 @@ + + + + + + + + +Similar projects | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Similar projects

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Similar to PMD

    + +

    Open Source

    + +
      +
    • Checkstyle - Very detailed, supports both Maven and Ant. +Uses ANTLR.
    • +
    • DoctorJ - Uses JavaCC. Checks Javadoc, syntax and calculates metrics.
    • +
    • ESC/Java - +Finds null dereference errors, array bounds errors, type cast errors, and race conditions. +Uses Java Modeling Language annotations.
    • +
    • FindBugs - works on bytecode, uses BCEL. Source code uses +templates, nifty stuff!
    • +
    • SpotBugs - SpotBugs is the spiritual successor of FindBugs, carrying on from the point where it left off with support of its community.
    • +
    • Hammurapi - +Uses ANTLR, excellent documentation, lots of rules
    • +
    • Jamit - bytecode analyzer, nice graphs
    • +
    • JCSC - Does a variety of coding standard checks, uses JavaCC and +the GNU Regexp package.
    • +
    • Jikes - More than a compiler; now it reports code warnings too
    • +
    • JLint - Written in C++. Uses data flow analysis and a lock graph to +do lots of synchronization checks. Operates on class files, not source code.
    • +
    • JPathFinder - A verification VM written by NASA; +supports a subset of the Java packages
    • +
    • JWiz - Research project, checks some neat stuff, like if +you create a Button without adding an ActionListener to it. Neat.
    • +
    + +

    Commercial

    + +
      +
    • AppPerfect - 750 rules, +produces PDF/Excel reports, supports auto-fixing problems
    • +
    • Assent - +The usual stuff, seems pretty complete.
    • +
    • Aubjex - +Rules aren’t listed online. Appears to have some code modification stuff, which would be cool to have in PMD. $299.
    • +
    • AzoJavaChecker - Rules aren’t listed online so it’s +hard to tell what they have. Not sure how much it costs since I don’t know German.
    • +
    • CodePro AnalytiX - +Eclipse plug-in, extensive audit rules, JUnit test generation/editing, code coverage and analysis
    • +
    • Enerjy Java Code Analyser - 200 rules, +lots of IDE plugins
    • +
    • Flaw Detector - In beta, does control/data flow analysis +to detect NullPointerExceptions
    • +
    • JStyle - $995, nice folks, lots of metrics and rules
    • +
    • JTest - Very nice with tons of features, +but also very expensive and requires a running X server (or Xvfb) to run on +Linux. They charge $500 to move a license from one machine to another.
    • +
    • Lint4J - Lock graph, DFA, and type analysis, many EJB checks
    • +
    • SolidSDD - Code +duplication detection, nice graphical reporting. Free licensing available for Educational or OSS use.
    • +
    + +

    Similar to CPD

    + +

    Commercial

    + +
      +
    • Simian - fast, works with Java, C#, C, CPP, COBOL, JSP, HTML
    • +
    • Simscan - free for open source projects
    • +
    + +

    High level reporting

    + +
      +
    • XRadar - Agregates data from a lot of code quality tool to generate +a full quality dashboard.
    • +
    • Sonar - Pretty much like XRadar, but younger project, fully integrated +to maven 2 (but requires a database)
    • +
    • Maven Dashboard - Same kind of agregator but +only for maven project.
    • +
    • QALab - Yet another maven plugin…
    • +
    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_release_notes.html b/pmd_release_notes.html new file mode 100644 index 0000000000..da9694e375 --- /dev/null +++ b/pmd_release_notes.html @@ -0,0 +1,1486 @@ + + + + + + + + +PMD Release Notes | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    PMD Release Notes

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    ??-November-2020 - 6.30.0-SNAPSHOT

    + +

    The PMD team is pleased to announce PMD 6.30.0-SNAPSHOT.

    + +

    This is a minor release.

    + +

    New and noteworthy

    + +

    Fixed Issues

    + +
      +
    • pmd-core +
        +
      • #1939: [core] XPath expressions return handling
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated API

    + + + +

    Internal API

    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. +You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +

    External Contributions

    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_release_notes_old.html b/pmd_release_notes_old.html new file mode 100644 index 0000000000..85f38d74b6 --- /dev/null +++ b/pmd_release_notes_old.html @@ -0,0 +1,13042 @@ + + + + + + + + +Old Release Notes | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Old Release Notes

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Previous versions of PMD can be downloaded here: https://github.com/pmd/pmd/releases

    + +

    24-October-2020 - 6.29.0

    + +

    The PMD team is pleased to announce PMD 6.29.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Updated Apex Support

    + + + +

    New Rules

    + +
      +
    • The new Apex rule OperationWithLimitsInLoop (apex-performance) +finds operations in loops that may hit governor limits such as DML operations, SOQL +queries and more. The rule replaces the three rules “AvoidDmlStatementsInLoops”, “AvoidSoqlInLoops”, +and “AvoidSoslInLoops”.
    • +
    + +

    Renamed Rules

    + +
      +
    • The Java rule DoNotCallSystemExit has been renamed to +DoNotTerminateVM, since it checks for all the following calls: +System.exit(int), Runtime.exit(int), Runtime.halt(int). All these calls terminate +the Java VM, which is bad, if the VM runs an application server which many independent applications.
    • +
    + +

    Deprecated Rules

    + + + +

    Fixed Issues

    + +
      +
    • apex +
        +
      • #2839: [apex] Apex classes with safe navigation operator from Winter 21 (50.0) are skipped
      • +
      +
    • +
    • apex-performance +
        +
      • #1713: [apex] Mark Database DML statements in For Loop
      • +
      +
    • +
    • core +
        +
      • #2831: [core] Fix XMLRenderer newlines when running under IBM Java
      • +
      +
    • +
    • java-errorprone +
        +
      • #2157: [java] Improve DoNotCallSystemExit: permit call in main(), flag System.halt
      • +
      • #2764: [java] CloseResourceRule does not recognize multiple assignment done to resource
      • +
      +
    • +
    • miscellaneous +
        +
      • #2823: [doc] Renamed/Moved rules are missing in documentation
      • +
      +
    • +
    • vf (Salesforce VisualForce) +
        +
      • #2765: [vf] Attributes with dot cause a VfParseException
      • +
      +
    • +
    + +

    External Contributions

    + + + +

    Stats

    +
      +
    • 50 commits
    • +
    • 23 closed tickets & PRs
    • +
    • Days since last release: 27
    • +
    + +

    26-September-2020 - 6.28.0

    + +

    The PMD team is pleased to announce PMD 6.28.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    CPD’s AnyTokenizer has been improved

    + +

    The AnyTokenizer is used for languages, that don’t have an own lexer/grammar based tokenizer. +AnyTokenizer now handles string literals and end-of-line comments. Fortran, Perl and Ruby have +been updated to use AnyTokenizer instead of their old custom tokenizer based on AbstractTokenizer. +See #2758 for details.

    + +

    AbstractTokenizer and the custom tokenizers of Fortran, Perl and Ruby are deprecated now.

    + +

    Fixed Issues

    + +
      +
    • cpd +
        +
      • #2758: [cpd] Improve AnyTokenizer
      • +
      • #2760: [cpd] AnyTokenizer doesn’t count columns correctly
      • +
      +
    • +
    • apex-security +
        +
      • #2774: [apex] ApexSharingViolations does not correlate sharing settings with class that contains data access
      • +
      +
    • +
    • java +
        +
      • #2738: [java] Custom rule with @ExhaustiveEnumSwitch throws NPE
      • +
      • #2755: [java] [6.27.0] Exception applying rule CloseResource on file … java.lang.NullPointerException
      • +
      • #2756: [java] TypeTestUtil fails with NPE for anonymous class
      • +
      • #2767: [java] IndexOutOfBoundsException when parsing an initializer BlockStatement
      • +
      • #2783: [java] Error while parsing with lambda of custom interface
      • +
      +
    • +
    • java-bestpractices +
        +
      • #2759: [java] False positive in UnusedAssignment
      • +
      +
    • +
    • java-design +
        +
      • #2708: [java] False positive FinalFieldCouldBeStatic when using lombok Builder.Default
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated API

    + +
    For removal
    + + + +

    External Contributions

    + +
      +
    • #2735: [ci] Add github actions for a fast view of pr succeed/not - XenoAmess
    • +
    • #2747: [java] Don’t trigger FinalFieldCouldBeStatic when field is annotated with lombok @Builder.Default - Ollie Abbey
    • +
    • #2773: [java] issue-2738: Adding null check to avoid npe when switch case is default - Nimit Patel
    • +
    • #2789: Add badge for reproducible build - Dan Rollo
    • +
    • #2791: [apex] Analyze inner classes for sharing violations - Jeff Bartolotta
    • +
    + +

    Stats

    +
      +
    • 58 commits
    • +
    • 24 closed tickets & PRs
    • +
    • Days since last release: 25
    • +
    + +

    31-August-2020 - 6.27.0

    + +

    The PMD team is pleased to announce PMD 6.27.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Java 15 Support

    + +

    This release of PMD brings support for Java 15. PMD can parse Text Blocks +which have been promoted to be a standard language feature of Java.

    + +

    PMD also supports Pattern Matching for instanceof, +Records, and Sealed Classes.

    + +

    Note: The Pattern Matching for instanceof, Records, and Sealed Classes are all preview language features of OpenJDK 15 +and are not enabled by default. In order to +analyze a project with PMD that uses these language features, you’ll need to enable it via the environment +variable PMD_JAVA_OPTS and select the new language version 15-preview:

    + +
    export PMD_JAVA_OPTS=--enable-preview
    +./run.sh pmd -language java -version 15-preview ...
    +
    + +

    Note: Support for Java 13 preview language features have been removed. The version “13-preview” is no longer available.

    + +

    Changes in how tab characters are handled

    + +

    In the past, tab characters in source files has been handled differently in different languages by PMD. +For instance in Java, tab characters had a width of 8 columns, while C# used only 1 column. Visualforce instead +used 4 columns.

    + +

    This has been unified now so that tab characters are consistently now always 1 column wide.

    + +

    This however might be a incompatible change, if you’re using the properties “BeginColumn” or “EndColumn” +additionally to “BeginLine” and “EndLine” of a Token/AST node in order to highlight +where a rule violation occurred in the source file. If you have logic there that deals with tab characters, +you most likely can remove this logic now, since tab characters are now just “normal” characters +in terms of string processing.

    + +

    See also [all] Ensure PMD/CPD uses tab width of 1 for tabs consistently #2656.

    + +

    Updated PMD Designer

    + +

    This PMD release ships a new version of the pmd-designer. +For the changes, see PMD Designer Changelog.

    + +

    New Rules

    + +
      +
    • The new Java rule AvoidReassigningCatchVariables (java-bestpractices) finds +cases where the variable of the caught exception is reassigned. This practice is surprising and prevents +further evolution of the code like multi-catch.
    • +
    + +

    Modified Rules

    + +
      +
    • +

      The Java rule CloseResource (java-errorprone) has a new property +closeNotInFinally. With this property set to true the rule will also find calls to close a +resource, which are not in a finally-block of a try-statement. If a resource is not closed within a +finally block, it might not be closed at all in case of exceptions.

      + +

      As this new detection would yield many new violations, it is disabled by default. It might be +enabled in a later version of PMD.

      +
    • +
    + +

    Deprecated Rules

    + + + +

    Fixed Issues

    + +
      +
    • core +
        +
      • #724: [core] Avoid parsing rulesets multiple times
      • +
      • #1962: [core] Simplify Report API
      • +
      • #2653: [lang-test] Upgrade kotlintest to Kotest
      • +
      • #2656: [all] Ensure PMD/CPD uses tab width of 1 for tabs consistently
      • +
      • #2690: [core] Fix java7 compatibility
      • +
      +
    • +
    • java +
        +
      • #2646: [java] Support JDK 15
      • +
      +
    • +
    • java-bestpractices +
        +
      • #2471: [java] New Rule: AvoidReassigningCatchVariables
      • +
      • #2663: [java] NoClassDefFoundError on upgrade from 6.25.0 to 6.26.0
      • +
      • #2668: [java] UnusedAssignment false positives
      • +
      • #2673: [java] UnusedPrivateField and SingularField false positive with lombok annotation EqualsAndHashCode
      • +
      • #2684: [java] UnusedAssignment FP in try/catch
      • +
      • #2686: [java] UnusedAssignment must not flag abstract method parameters in interfaces and abstract classes
      • +
      +
    • +
    • java-design +
        +
      • #2108: [java] [doc] ImmutableField rule: Description should clarify shallow immutability
      • +
      • #2461: [java] ExcessiveParameterListRule must ignore a private constructor
      • +
      +
    • +
    • java-errorprone +
        +
      • #2264: [java] SuspiciousEqualsMethodName: Improve description about error-prone overloading of equals()
      • +
      • #2410: [java] ProperCloneImplementation not valid for final class
      • +
      • #2431: [java] InvalidLogMessageFormatRule throws IndexOutOfBoundsException when only logging exception message
      • +
      • #2439: [java] AvoidCatchingThrowable can not detect the case: catch (java.lang.Throwable t)
      • +
      • #2470: [java] CloseResource false positive when resource included in return value
      • +
      • #2531: [java] UnnecessaryCaseChange can not detect the case like: foo.equals(bar.toLowerCase())
      • +
      • #2647: [java] Deprecate rule DataFlowAnomalyAnalysis
      • +
      +
    • +
    • java-performance +
        +
      • #1868: [java] false-positive for SimplifyStartsWith if string is empty
      • +
      • #2441: [java] RedundantFieldInitializer can not detect a special case for char initialize: char foo = '\0';
      • +
      • #2530: [java] StringToString can not detect the case: getStringMethod().toString()
      • +
      +
    • +
    • dart +
        +
      • #2750: [dart] [cpd] Cpd Dart escaped dollar
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • XML rule definition in rulesets: In PMD 7, the language attribute will be required on all rule +elements that declare a new rule. Some base rule classes set the language implicitly in their +constructor, and so this is not required in all cases for the rule to work. But this +behavior will be discontinued in PMD 7, so missing language attributes are now +reported as a forward compatibility warning.
    • +
    + +

    Deprecated API

    + +
    For removal
    + + + +

    External Contributions

    + + + +

    Stats

    +
      +
    • 189 commits
    • +
    • 68 closed tickets & PRs
    • +
    • Days since last release: 37
    • +
    + +

    25-July-2020 - 6.26.0

    + +

    The PMD team is pleased to announce PMD 6.26.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    New Rules

    + +
      +
    • The new Java rule UnusedAssignment (java-bestpractices) finds assignments +to variables, that are never used and are useless. The new rule is supposed to entirely replace +DataflowAnomalyAnalysis.
    • +
    + +

    Modified rules

    + +
      +
    • The Java rule ArrayIsStoredDirectly (java-bestpractices) now ignores +by default private methods and constructors. You can restore the old behavior by setting the new property +allowPrivate to “false”.
    • +
    + +

    Fixed Issues

    + +
      +
    • apex +
        +
      • #2610: [apex] Support top-level enums in rules
      • +
      +
    • +
    • apex-bestpractices +
        +
      • #2626: [apex] UnusedLocalVariable - false positive on case insensitivity allowed in Apex
      • +
      +
    • +
    • apex-performance +
        +
      • #2598: [apex] AvoidSoqlInLoops false positive for SOQL with in For-Loop
      • +
      +
    • +
    • apex-security +
        +
      • #2620: [visualforce] False positive on VfUnescapeEl with new Message Channel feature
      • +
      +
    • +
    • core +
        +
      • #710: [core] Review used dependencies
      • +
      • #2594: [core] Update exec-maven-plugin and align it in all project
      • +
      • #2615: [core] PMD/CPD produces invalid XML (insufficient escaping/wrong encoding)
      • +
      +
    • +
    • java-bestpractices +
        +
      • #2543: [java] UseCollectionIsEmpty can not detect the case this.foo.size()
      • +
      • #2569: [java] LiteralsFirstInComparisons: False negative for methods returning Strings
      • +
      • #2622: [java] ArrayIsStoredDirectly false positive with private constructor/methods
      • +
      +
    • +
    • java-codestyle +
        +
      • #2546: [java] DuplicateImports reported for the same import… and import static…
      • +
      +
    • +
    • java-design +
        +
      • #2174: [java] LawOfDemeter: False positive with ‘this’ pointer
      • +
      • #2181: [java] LawOfDemeter: False positive with indexed array access
      • +
      • #2189: [java] LawOfDemeter: False positive when casting to derived class
      • +
      • #2580: [java] AvoidThrowingNullPointerException marks all NullPointerException objects as wrong, whether or not thrown
      • +
      • #2625: [java] NPathComplexity can’t handle switch expressions
      • +
      +
    • +
    • java-errorprone +
        +
      • #2578: [java] AvoidCallingFinalize detects some false positives
      • +
      • #2634: [java] NullPointerException in rule ProperCloneImplementation
      • +
      +
    • +
    • java-performance +
        +
      • #1736: [java] UseStringBufferForStringAppends: False positive if only one concatenation
      • +
      • #2207: [java] AvoidInstantiatingObjectsInLoops: False positive - should not flag objects when assigned to lists/arrays
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated API

    + +
    For removal
    + + + +

    External Contributions

    + + +

    Stats

    +
      +
    • 156 commits
    • +
    • 43 closed tickets & PRs
    • +
    • Days since last release: 28
    • +
    + +

    27-June-2020 - 6.25.0

    + +

    The PMD team is pleased to announce PMD 6.25.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Scala cross compilation

    + +

    Up until now the PMD Scala module has been compiled against scala 2.13 only by default. +However, this makes it impossible to use pmd as a library in scala projects, +that use scala 2.12, e.g. in sbt plugins. Therefore PMD now provides cross compiled pmd-scala +modules for both versions: scala 2.12 and scala 2.13.

    + +

    The new modules have new maven artifactIds. The old artifactId net.sourceforge.pmd:pmd-scala:6.25.0 +is still available, but is deprecated from now on. It has been demoted to be just a delegation to the new +pmd-scala_2.13 module and will be removed eventually.

    + +

    The coordinates for the new modules are:

    + +
    <dependency>
    +    <groupId>net.sourceforge.pmd</groupId>
    +    <artifactId>pmd-scala_2.12</artifactId>
    +    <version>6.25.0</version>
    +</dependency>
    +
    +<dependency>
    +    <groupId>net.sourceforge.pmd</groupId>
    +    <artifactId>pmd-scala_2.13</artifactId>
    +    <version>6.25.0</version>
    +</dependency>
    +
    + +

    The command line version of PMD continues to use scala 2.13.

    + +

    New Rules

    + +
      +
    • +

      The new Java Rule UnnecessaryCast (java-codestyle) +finds casts that are unnecessary while accessing collection elements.

      +
    • +
    • +

      The new Java Rule AvoidCalendarDateCreation (java-performance) +finds usages of java.util.Calendar whose purpose is just to get the current date. This +can be done in a more lightweight way.

      +
    • +
    • +

      The new Java Rule UseIOStreamsWithApacheCommonsFileItem (java-performance) +finds usage of FileItem.get() and FileItem.getString(). These two methods are problematic since +they load the whole uploaded file into memory.

      +
    • +
    + +

    Modified rules

    + +
      +
    • +

      The Java rule UseDiamondOperator (java-codestyle) now by default +finds unnecessary usages of type parameters, which are nested, involve wildcards and are used +within a ternary operator. These usages are usually only unnecessary with Java8 and later, when +the type inference in Java has been improved.

      + +

      In order to avoid false positives when checking Java7 only code, the rule has the new property +java7Compatibility, which is disabled by default. Settings this to “true” retains +the old rule behaviour.

      +
    • +
    + +

    Fixed Issues

    + +
      +
    • apex-bestpractices +
        +
      • #2554: [apex] Exception applying rule UnusedLocalVariable on trigger
      • +
      +
    • +
    • core +
        +
      • #971: [apex][plsql][java] Deprecate overly specific base rule classes
      • +
      • #2451: [core] Deprecate support for List attributes with XPath 2.0
      • +
      • #2599: [core] Fix XPath 2.0 Rule Chain Analyzer with Unions
      • +
      • #2483: [lang-test] Support cpd tests based on text comparison. +For details see +Testing your implementation +in the developer documentation.
      • +
      +
    • +
    • c# +
        +
      • #2551: [c#] CPD suppression with comments doesn’t work
      • +
      +
    • +
    • cpp +
        +
      • #1757: [cpp] Support unicode characters
      • +
      +
    • +
    • java +
        +
      • #2549: [java] Auxclasspath in PMD CLI does not support relative file path
      • +
      +
    • +
    • java-codestyle +
        +
      • #2545: [java] UseDiamondOperator false negatives
      • +
      • #2573: [java] DefaultPackage: Allow package default JUnit 5 Test methods
      • +
      +
    • +
    • java-design +
        +
      • #2563: [java] UselessOverridingMethod false negative with already public methods
      • +
      • #2570: [java] NPathComplexity should mention the expected NPath complexity
      • +
      +
    • +
    • java-errorprone +
        +
      • #2544: [java] UseProperClassLoader can not detect the case with method call on intermediate variable
      • +
      +
    • +
    • java-performance +
        +
      • #2591: [java] InefficientStringBuffering/AppendCharacterWithChar: Fix false negatives with concats in appends
      • +
      • #2600: [java] UseStringBufferForStringAppends: fix false negative with fields
      • +
      +
    • +
    • scala +
        +
      • #2547: [scala] Add cross compilation for scala 2.12 and 2.13
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • +

      The maven module net.sourceforge.pmd:pmd-scala is deprecated. Use net.sourceforge.pmd:pmd-scala_2.13 +or net.sourceforge.pmd:pmd-scala_2.12 instead.

      +
    • +
    • +

      Rule implementation classes are internal API and should not be used by clients directly. +The rules should only be referenced via their entry in the corresponding category ruleset +(e.g. <rule ref="category/java/bestpractices.xml/AbstractClassWithoutAbstractMethod" />).

      + +

      While we definitely won’t move or rename the rule classes in PMD 6.x, we might consider changes +in PMD 7.0.0 and onwards.

      +
    • +
    + +

    Deprecated APIs

    + +
    Internal API
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. +You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +
    For removal
    + + + +

    External Contributions

    + + + +

    Stats

    +
      +
    • 135 commits
    • +
    • 31 closed tickets & PRs
    • +
    • Days since last release: 33
    • +
    + +

    24-May-2020 - 6.24.0

    + +

    The PMD team is pleased to announce PMD 6.24.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    CPD now supports XML as well

    + +

    Thanks to Fernando Cosso CPD can now find duplicates in XML files as well. +This is useful to find duplicated sections in XML files.

    + +

    Updated PMD Designer

    + +

    This PMD release ships a new version of the pmd-designer. +For the changes, see PMD Designer Changelog.

    + +

    New Rules

    + +
      +
    • +

      The new Java Rule LiteralsFirstInComparisons (java-bestpractices) +find String literals, that are used in comparisons and are not positioned first. Using the String literal +as the receiver of e.g. equals helps to avoid NullPointerExceptions.

      + +

      This rule is replacing the two old rules PositionLiteralsFirstInComparisons +and PositionLiteralsFirstInCaseInsensitiveComparisons and extends the check +for the methods compareTo, compareToIgnoreCase and contentEquals in addition to equals and +equalsIgnoreCase.

      + +

      Note: This rule also replaces the two mentioned rules in Java’s quickstart ruleset.

      +
    • +
    + +

    Deprecated Rules

    + + + +

    Fixed Issues

    + +
      +
    • apex-bestpractices +
        +
      • #2468: [apex] Unused Local Variable fails on blocks
      • +
      +
    • +
    • core +
        +
      • #2444: [core] Support reproducible builds
      • +
      • #2484: [core] Update maven-enforcer-plugin to require Java 118
      • +
      +
    • +
    • c# +
        +
      • #2495: [c#] Support for interpolated verbatim strings
      • +
      +
    • +
    • java +
        +
      • #2472: [java] JavaCharStream throws an Error on invalid escape
      • +
      +
    • +
    • java-bestpractices +
        +
      • #2145: [java] Deprecate rules PositionLiteralsFirstIn(CaseInsensitive)Comparisons in favor of LiteralsFirstInComparisons
      • +
      • #2288: [java] JUnitTestsShouldIncludeAssert: Add support for Hamcrest MatcherAssert.assertThat
      • +
      • #2437: [java] AvoidPrintStackTrace can’t detect the case e.getCause().printStackTrace()
      • +
      +
    • +
    • java-codestyle +
        +
      • #2476: [java] MethodNamingConventions - Add support for JUnit 5 method naming
      • +
      +
    • +
    • java-errorprone +
        +
      • #2477: [java] JUnitSpelling false-positive for JUnit5/4 tests
      • +
      +
    • +
    • swift +
        +
      • #2473: [swift] Swift 5 (up to 5.2) support for CPD
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated APIs

    + + + +

    Experimental APIs

    + +

    Note: Experimental APIs are identified with the annotation Experimental, +see its javadoc for details

    + +
      +
    • The experimental methods in BaseLanguageModule have been replaced by a +definitive API.
    • +
    + +

    External Contributions

    + + + +

    Stats

    +
      +
    • 114 commits
    • +
    • 29 closed tickets & PRs
    • +
    • Days since last release: 30
    • +
    + +

    24-April-2020 - 6.23.0

    + +

    The PMD team is pleased to announce PMD 6.23.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    PMD adopts Contributor Code of Conduct

    + +

    To facilitate healthy and constructive community behavior PMD adopts +Contributor Convenant as its code of +conduct.

    + +

    Please note that this project is released with a Contributor Code of Conduct. +By participating in this project you agree to abide by its terms.

    + +

    You can find the code of conduct in the file code_of_conduct.md +in our repository.

    + +

    Performance improvements for XPath 2.0 rules

    + +

    XPath rules written with XPath 2.0 now support conversion to a rulechain rule, which +improves their performance. The rulechain is a mechanism that allows several rules +to be executed in a single tree traversal. Conversion to the rulechain is possible if +your XPath expression looks like //someNode/... | //someOtherNode/... | ..., that +is, a union of one or more path expressions that start with //. Instead of traversing +the whole tree once per path expression (and per rule), a single traversal executes all +rules in your ruleset as needed.

    + +

    This conversion is performed automatically and cannot be disabled. The conversion should +not change the result of your rules, if it does, please report a bug at https://github.com/pmd/pmd/issues

    + +

    Note that XPath 1.0 support, the default XPath version, is deprecated since PMD 6.22.0. +We highly recommend that you upgrade your rules to XPath 2.0. Please refer to the migration guide.

    + +

    Javascript improvements for ES6

    + +

    PMD uses the Rhino library to parse Javascript. +The default version has been set to ES6, so that some ECMAScript 2015 features are +supported. E.g. let statements and for-of loops are now parsed. However Rhino does +not support all features.

    + +

    New JSON renderer

    + +

    PMD now supports a JSON renderer (use it with -f json on the CLI). +See the documentation and example

    + +

    New Rules

    + +
      +
    • +

      The new Apex rule FieldDeclarationsShouldBeAtStart (apex-codestyle) +helps to ensure that field declarations are always at the beginning of a class.

      +
    • +
    • +

      The new Apex rule UnusedLocalVariable (apex-bestpractices) detects unused +local variables.

      +
    • +
    + +

    Fixed Issues

    + +
      +
    • apex-design +
        +
      • #2358: [apex] Invalid Apex in Cognitive Complexity tests
      • +
      +
    • +
    • apex-security +
        +
      • #2210: [apex] ApexCRUDViolation: Support WITH SECURITY_ENFORCED
      • +
      • #2399: [apex] ApexCRUDViolation: false positive with security enforced with line break
      • +
      +
    • +
    • core +
        +
      • #1286: [core] Export Supporting JSON Format
      • +
      • #2019: [core] Insufficient deprecation warnings for XPath attributes
      • +
      • #2357: Add code of conduct: Contributor Covenant
      • +
      • #2426: [core] CodeClimate renderer links are dead
      • +
      • #2432: [core] Close ZIP data sources even if a runtime exception or error is thrown
      • +
      +
    • +
    • doc +
        +
      • #2355: [doc] Improve documentation about incremental analysis
      • +
      • #2356: [doc] Add missing doc about pmd.github.io
      • +
      • #2412: [core] HTMLRenderer doesn’t render links to source files
      • +
      • #2413: [doc] Improve documentation about the available renderers (PMD/CPD)
      • +
      +
    • +
    • java +
        +
      • #2378: [java] AbstractJUnitRule has bad performance on large code bases
      • +
      +
    • +
    • java-bestpractices +
        +
      • #2398: [java] AbstractClassWithoutAbstractMethod false negative with inner abstract classes
      • +
      +
    • +
    • java-codestyle +
        +
      • #1164: [java] ClassNamingConventions suggests to add Util for class containing only static constants
      • +
      • #1723: [java] UseDiamondOperator false-positive inside lambda
      • +
      +
    • +
    • java-design +
        +
      • #2390: [java] AbstractClassWithoutAnyMethod: missing violation for nested classes
      • +
      +
    • +
    • java-errorprone +
        +
      • #2402: [java] CloseResource possible false positive with Primitive Streams
      • +
      +
    • +
    • java-multithreading +
        +
      • #2313: [java] Documenation for DoNotUseThreads is outdated
      • +
      +
    • +
    • javascript +
        +
      • #1235: [javascript] Use of let results in an Empty Statement in the AST
      • +
      • #2379: [javascript] Support for-of loop
      • +
      +
    • +
    • javascript-errorprone +
        +
      • #384: [javascript] Trailing commas not detected on French default locale
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated APIs

    + +
    Internal API
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. +You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +
    In ASTs
    + +

    As part of the changes we’d like to do to AST classes for 7.0.0, we would like to +hide some methods and constructors that rule writers should not have access to. +The following usages are now deprecated in the Apex, Javascript, PL/SQL, Scala and Visualforce ASTs:

    + +
      +
    • Manual instantiation of nodes. Constructors of node classes are deprecated and +marked InternalApi. Nodes should only be obtained from the parser, +which for rules, means that they never need to instantiate node themselves. +Those constructors will be made package private with 7.0.0.
    • +
    • Subclassing of abstract node classes, or usage of their type. The base classes are internal API +and will be hidden in version 7.0.0. You should not couple your code to them. +
        +
      • In the meantime you should use interfaces like VfNode or +Node, or the other published interfaces in this package, +to refer to nodes generically.
      • +
      • Concrete node classes will be made final with 7.0.0.
      • +
      +
    • +
    • Setters found in any node class or interface. Rules should consider the AST immutable. +We will make those setters package private with 7.0.0.
    • +
    • The implementation classes of Parser (eg VfParser) are deprecated and should not be used directly. +Use LanguageVersionHandler#getParser instead.
    • +
    • The implementation classes of TokenManager (eg VfTokenManager) are deprecated and should not be used outside of our implementation. +This also affects CPD-only modules.
    • +
    + +

    These deprecations are added to the following language modules in this release. +Please look at the package documentation to find out the full list of deprecations.

    + + +

    These deprecations have already been rolled out in a previous version for the +following languages:

    + + +

    Outside of these packages, these changes also concern the following TokenManager +implementations, and their corresponding Parser if it exists (in the same package):

    + + + +

    In the Java AST the following attributes are deprecated and will issue a warning when used in XPath rules:

    + + + +
    For removal
    + + + +

    External Contributions

    + + + +

    Stats

    +
      +
    • 237 commits
    • +
    • 64 closed tickets & PRs
    • +
    • Days since last release: 42
    • +
    + +

    12-March-2020 - 6.22.0

    + +

    The PMD team is pleased to announce PMD 6.22.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Java 14 Support

    + +

    This release of PMD brings support for Java 14. PMD can parse Switch Expressions, +which have been promoted to be a standard language feature of Java.

    + +

    PMD also parses Text Blocks as String literals, which is still a preview +language feature in Java 14.

    + +

    The new Pattern Matching for instanceof can be used as well as +Records.

    + +

    Note: The Text Blocks, Pattern Matching for instanceof and Records are all preview language features of OpenJDK 14 +and are not enabled by default. In order to +analyze a project with PMD that uses these language features, you’ll need to enable it via the environment +variable PMD_JAVA_OPTS and select the new language version 14-preview:

    + +
    export PMD_JAVA_OPTS=--enable-preview
    +./run.sh pmd -language java -version 14-preview ...
    +
    + +

    Note: Support for the extended break statement introduced in Java 12 as a preview language feature +has been removed from PMD with this version. The version “12-preview” is no longer available.

    + +

    Updated PMD Designer

    + +

    This PMD release ships a new version of the pmd-designer. +For the changes, see PMD Designer Changelog.

    + +

    Apex Suppressions

    + +

    In addition to suppressing violation with the @SuppressWarnings annotation, Apex now also supports +the suppressions with a NOPMD comment. See Suppressing warnings.

    + +

    Improved CPD support for C#

    + +

    The C# tokenizer is now based on an antlr grammar instead of a manual written tokenizer. This +should give more accurate results and especially fixes the problems with the using statement syntax +(see #2139).

    + +

    XPath Rules

    + +

    See the new documentation about Writing XPath Rules.

    + +

    Note: As of PMD version 6.22.0, XPath versions 1.0 and the 1.0 compatibility mode are deprecated. +XPath 2.0 is superior in many ways, for example for its support for type checking, sequence values, +or quantified expressions. For a detailed but approachable review of the features of XPath 2.0 and above, +see the Saxon documentation.

    + +

    New Rules

    + +
      +
    • +

      The Rule CognitiveComplexity (apex-design) finds methods and classes +that are highly complex and therefore difficult to read and more costly to maintain. In contrast +to cyclomatic complexity, this rule uses “Cognitive Complexity”, which is a measure of how +difficult it is for humans to read and understand a method.

      +
    • +
    • +

      The Rule TestMethodsMustBeInTestClasses (apex-errorprone) finds test methods +that are not residing in a test class. The test methods should be moved to a proper test class. +Support for tests inside functional classes was removed in Spring-13 (API Version 27.0), making classes +that violate this rule fail compile-time. This rule is however useful when dealing with legacy code.

      +
    • +
    + +

    Fixed Issues

    + +
      +
    • apex +
        +
      • #1087: [apex] Support suppression via //NOPMD
      • +
      • #2306: [apex] Switch statements are not parsed/supported
      • +
      +
    • +
    • apex-design +
        +
      • #2162: [apex] Cognitive Complexity rule
      • +
      +
    • +
    • apex-errorprone +
        +
      • #639: [apex] Test methods should not be in classes other than test classes
      • +
      +
    • +
    • cs +
        +
      • #2139: [cs] CPD doesn’t understand alternate using statement syntax with C# 8.0
      • +
      +
    • +
    • doc +
        +
      • #2274: [doc] Java API documentation for PMD
      • +
      +
    • +
    • java +
        +
      • #2159: [java] Prepare for JDK 14
      • +
      • #2268: [java] Improve TypeHelper resilience
      • +
      +
    • +
    • java-bestpractices +
        +
      • #2277: [java] FP in UnusedImports for ambiguous static on-demand imports
      • +
      +
    • +
    • java-design +
        +
      • #911: [java] UselessOverridingMethod false positive when elevating access modifier
      • +
      +
    • +
    • java-errorprone +
        +
      • #2242: [java] False-positive MisplacedNullCheck reported
      • +
      • #2250: [java] InvalidLogMessageFormat flags logging calls using a slf4j-Marker
      • +
      • #2255: [java] InvalidLogMessageFormat false-positive for a lambda argument
      • +
      +
    • +
    • java-performance +
        +
      • #2275: [java] AppendCharacterWithChar flags literals in an expression
      • +
      +
    • +
    • plsql +
        +
      • #2325: [plsql] NullPointerException while running parsing test for CREATE TRIGGER
      • +
      • #2327: [plsql] Parsing of WHERE CURRENT OF
      • +
      • #2328: [plsql] Support XMLROOT
      • +
      • #2331: [plsql] Fix in Comment statement
      • +
      • #2332: [plsql] Fixed Execute Immediate statement parsing
      • +
      • #2340: [plsql] Fixed parsing / as divide or execute
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated APIs

    + +
    Internal API
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. +You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +
    For removal
    + + + +
    In ASTs (JSP)
    + +

    As part of the changes we’d like to do to AST classes for 7.0.0, we would like to +hide some methods and constructors that rule writers should not have access to. +The following usages are now deprecated in the JSP AST (with other languages to come):

    + +
      +
    • Manual instantiation of nodes. Constructors of node classes are deprecated and +marked InternalApi. Nodes should only be obtained from the parser, +which for rules, means that they never need to instantiate node themselves. +Those constructors will be made package private with 7.0.0.
    • +
    • Subclassing of abstract node classes, or usage of their type. The base classes are internal API +and will be hidden in version 7.0.0. You should not couple your code to them. +
        +
      • In the meantime you should use interfaces like JspNode or +Node, or the other published interfaces in this package, +to refer to nodes generically.
      • +
      • Concrete node classes will be made final with 7.0.0.
      • +
      +
    • +
    • Setters found in any node class or interface. Rules should consider the AST immutable. +We will make those setters package private with 7.0.0.
    • +
    • The class JspParser is deprecated and should not be used directly. +Use LanguageVersionHandler#getParser instead.
    • +
    + +

    Please look at net.sourceforge.pmd.lang.jsp.ast to find out the full list of deprecations.

    + +
    In ASTs (Velocity)
    + +

    As part of the changes we’d like to do to AST classes for 7.0.0, we would like to +hide some methods and constructors that rule writers should not have access to. +The following usages are now deprecated in the VM AST (with other languages to come):

    + +
      +
    • Manual instantiation of nodes. Constructors of node classes are deprecated and +marked InternalApi. Nodes should only be obtained from the parser, +which for rules, means that they never need to instantiate node themselves. +Those constructors will be made package private with 7.0.0.
    • +
    • Subclassing of abstract node classes, or usage of their type. The base classes are internal API +and will be hidden in version 7.0.0. You should not couple your code to them. +
        +
      • In the meantime you should use interfaces like VmNode or +Node, or the other published interfaces in this package, +to refer to nodes generically.
      • +
      • Concrete node classes will be made final with 7.0.0.
      • +
      +
    • +
    • Setters found in any node class or interface. Rules should consider the AST immutable. +We will make those setters package private with 7.0.0.
    • +
    • The package net.sourceforge.pmd.lang.vm.directive as well as the classes +DirectiveMapper and LogUtil are deprecated +for removal. They were only used internally during parsing.
    • +
    • The class VmParser is deprecated and should not be used directly. +Use LanguageVersionHandler#getParser instead.
    • +
    + +

    Please look at net.sourceforge.pmd.lang.vm.ast to find out the full list of deprecations.

    + +

    PLSQL AST

    + +

    The production and node ASTCursorBody was unnecessary, not used and has been removed. Cursors have been already +parsed as ASTCursorSpecification.

    + +

    External Contributions

    + + + +

    24-January-2020 - 6.21.0

    + +

    The PMD team is pleased to announce PMD 6.21.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Modelica support

    + +

    Thanks to Anatoly Trosinenko PMD supports now a new language: +Modelica is a language to model complex physical systems. +Both PMD and CPD are supported and there are already 3 rules available. +The PMD Designer supports syntax highlighting for Modelica.

    + +

    While the language implementation is quite complete, Modelica support is considered experimental +for now. This is to allow us to change the rule API (e.g. the AST classes) slightly and improve +the implementation based on your feedback.

    + +

    Simple XML dump of AST

    + +

    We added a experimental feature to dump the AST of a source file into XML. The XML format +is of course PMD specific and language dependent. That XML file can be used to execute +(XPath) queries against without PMD. It can also be used as a textual visualization of the AST +if you don’t want to use the Designer.

    + +

    This feature is experimental and might change or even be removed in the future, if it is not +useful. A short description how to use it is available under Creating XML dump of the AST.

    + +

    Any feedback about it, especially about your use cases, is highly appreciated.

    + +

    Updated Apex Support

    + +
      +
    • The Apex language support has been bumped to version 48 (Spring ‘20). All new language features are now properly +parsed and processed.
    • +
    + +

    CPD XML format

    + +

    The CPD XML output format has been enhanced to also report column information for found duplications +in addition to the line information. This allows to display the exact tokens, that are considered +duplicate.

    + +

    If a CPD language doesn’t provide these exact information, then these additional attributes are omitted.

    + +

    Each <file> element in the XML format now has 3 new attributes:

    + +
      +
    • attribute endline
    • +
    • attribute column (if there is column information available)
    • +
    • attribute endcolumn (if there is column information available)
    • +
    + +

    Modified Rules

    + +
      +
    • +

      The Java rule AvoidLiteralsInIfCondition (java-errorprone) has a new property +ignoreExpressions. This property is set by default to true in order to maintain compatibility. If this +property is set to false, then literals in more complex expressions are considered as well.

      +
    • +
    • +

      The Apex rule ApexCSRF (apex-errorprone) has been moved from category +“Security” to “Error Prone”. The Apex runtime already prevents DML statements from being executed, but only +at runtime. So, if you try to do this, you’ll get an error at runtime, hence this is error prone. See also +the discussion on #2064.

      +
    • +
    • +

      The Java rule CommentRequired (java-documentation) has a new property +classCommentRequirement. This replaces the now deprecated property headerCommentRequirement, since +the name was misleading. (File) header comments are not checked, but class comments are.

      +
    • +
    + +

    Fixed Issues

    + +
      +
    • apex +
        +
      • #2208: [apex] ASTFormalComment should implement ApexNode<T>
      • +
      +
    • +
    • core +
        +
      • #1984: [java] Cyclomatic complexity is misreported (lack of clearing metrics cache)
      • +
      • #2006: [core] PMD should warn about multiple instances of the same rule in a ruleset
      • +
      • #2161: [core] ResourceLoader is deprecated and marked as internal but is exposed
      • +
      • #2170: [core] DocumentFile doesn’t preserve newlines
      • +
      +
    • +
    • doc +
        +
      • #2214: [doc] Link broken in pmd documentation for writing Xpath rules
      • +
      +
    • +
    • java +
        +
      • #2212: [java] JavaRuleViolation reports wrong class name
      • +
      +
    • +
    • java-bestpractices +
        +
      • #2149: [java] JUnitAssertionsShouldIncludeMessage - False positive with assertEquals and JUnit5
      • +
      +
    • +
    • java-codestyle +
        +
      • #2167: [java] UnnecessaryLocalBeforeReturn false positive with variable captured by method reference
      • +
      +
    • +
    • java-documentation +
        +
      • #1683: [java] CommentRequired property names are inconsistent
      • +
      +
    • +
    • java-errorprone +
        +
      • #2140: [java] AvoidLiteralsInIfCondition: false negative for expressions
      • +
      • #2196: [java] InvalidLogMessageFormat does not detect extra parameters when no placeholders
      • +
      +
    • +
    • java-performance +
        +
      • #2141: [java] StringInstatiation: False negative with String-array access
      • +
      +
    • +
    • plsql +
        +
      • #2008: [plsql] In StringLiteral using alternative quoting mechanism single quotes cause parsing errors
      • +
      • #2009: [plsql] Multiple DDL commands are skipped during parsing
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated APIs

    + +
    Internal API
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. +You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +
    For removal
    + + + +

    External Contributions

    + + + +

    29-November-2019 - 6.20.0

    + +

    The PMD team is pleased to announce PMD 6.20.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    Fixed Issues

    + +
      +
    • apex +
        +
      • #2092: [apex] ApexLexer logs visible when Apex is the selected language upon starting the designer
      • +
      • #2136: [apex] Provide access to underlying query of SoqlExpression
      • +
      +
    • +
    • core +
        +
      • #2002: [doc] Issue with http://pmdapplied.com/ linking to a gambling Web site
      • +
      • #2062: [core] Shortnames parameter does not work with Ant
      • +
      • #2090: [ci] Release notes and draft releases
      • +
      • #2096: [core] Referencing category errorprone.xml produces deprecation warnings for InvalidSlf4jMessageFormat
      • +
      +
    • +
    • java +
        +
      • #1861: [java] Be more lenient with version numbers
      • +
      • #2105: [java] Wrong name for inner classes in violations
      • +
      +
    • +
    • java-bestpractices +
        +
      • #2016: [java] UnusedImports: False positive if wildcard is used and only static methods
      • +
      +
    • +
    • java-codestyle +
        +
      • #1362: [java] LinguisticNaming flags Predicates with boolean-style names
      • +
      • #2029: [java] UnnecessaryFullyQualifiedName false-positive for non-static nested classes
      • +
      • #2098: [java] UnnecessaryFullyQualifiedName: regression / false positive
      • +
      +
    • +
    • java-design +
        +
      • #2075: [java] ImmutableField false positive with inner class
      • +
      • #2125: [java] ImmutableField: False positive when variable is updated in conditional loop
      • +
      +
    • +
    • java-errorprone +
        +
      • #2102: [java] False positive MissingStaticMethodInNonInstantiatableClass when inheritors are instantiable
      • +
      +
    • +
    + +

    External Contributions

    + + + +

    31-October-2019 - 6.19.0

    + +

    The PMD team is pleased to announce PMD 6.19.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Updated PMD Designer

    + +

    This PMD release ships a new version of the pmd-designer. +For the changes, see PMD Designer Changelog.

    + +

    Java Metrics

    + + + +

    Modified Rules

    + +
      +
    • +

      The Java rules InvalidLogMessageFormat and MoreThanOneLogger +(java-errorprone) now both support Log4j2. Note that the +rule “InvalidSlf4jMessageFormat” has been renamed to “InvalidLogMessageFormat” to reflect the fact, that it now +supports more than slf4j.

      +
    • +
    • +

      The Java rule LawOfDemeter (java-design) ignores now also Builders, that are +not assigned to a local variable, but just directly used within a method call chain. The method, that creates +the builder needs to end with “Builder”, e.g. newBuilder() or initBuilder() works. This change +fixes a couple of false positives.

      +
    • +
    • +

      The Java rule DataflowAnomalyAnalysis (java-errorprone) doesn’t check for +UR anomalies (undefined and then referenced) anymore. These checks were all false-positives, since actual +UR occurrences would lead to compile errors.

      +
    • +
    • +

      The java rule DoNotUseThreads (java-multithreading) has been changed +to not report usages of java.lang.Runnable anymore. Just using Runnable does not automatically create +a new thread. While the check for Runnable has been removed, the rule now additionally checks for +usages of Executors and ExecutorService. Both create new threads, which are not managed by a J2EE +server.

      +
    • +
    + +

    Renamed Rules

    + + + +

    Fixed Issues

    + +
      +
    • core +
        +
      • #1978: [core] PMD fails on excluding unknown rules
      • +
      • #2014: [core] Making add(SourceCode sourceCode) public for alternative file systems
      • +
      • #2020: [core] Wrong deprecation warnings for unused XPath attributes
      • +
      • #2036: [core] Wrong include/exclude patterns are silently ignored
      • +
      • #2048: [core] Enable type resolution by default for XPath rules
      • +
      • #2067: [core] Build issue on Windows
      • +
      • #2068: [core] Rule loader should use the same resources loader for the ruleset
      • +
      • #2071: [ci] Add travis build on windows
      • +
      • #2072: [test][core] Not enough info in “test setup error” when numbers of lines do not match
      • +
      • #2082: [core] Incorrect logging of deprecated/renamed rules
      • +
      +
    • +
    • java +
        +
      • #2042: [java] PMD crashes with ClassFormatError: Absent Code attribute…
      • +
      +
    • +
    • java-bestpractices +
        +
      • #1531: [java] UnusedPrivateMethod false-positive with method result
      • +
      • #2025: [java] UnusedImports when @see / @link pattern includes a FQCN
      • +
      +
    • +
    • java-codestyle +
        +
      • #2017: [java] UnnecessaryFullyQualifiedName triggered for inner class
      • +
      +
    • +
    • java-design +
        +
      • #1912: [java] Metrics not computed correctly with annotations
      • +
      +
    • +
    • java-errorprone +
        +
      • #336: [java] InvalidSlf4jMessageFormat applies to log4j2
      • +
      • #1636: [java] Stop checking UR anomalies for DataflowAnomalyAnalysis
      • +
      +
    • +
    • java-multithreading +
        +
      • #1627: [java] DoNotUseThreads should not warn on Runnable
      • +
      +
    • +
    • doc +
        +
      • #2058: [doc] CLI reference for -norulesetcompatibility shows a boolean default value
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated APIs

    + +
    For removal
    + + + +
    Internal APIs
    + + + +

    External Contributions

    + + + +

    15-September-2019 - 6.18.0

    + +

    The PMD team is pleased to announce PMD 6.18.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Java 13 Support

    + +

    This release of PMD brings support for Java 13. PMD can parse Switch Expressions +with the new yield statement and resolve the type of such an expression.

    + +

    PMD also parses Text Blocks as String literals.

    + +

    Note: The Switch Expressions and Text Blocks are a preview language feature of OpenJDK 13 +and are not enabled by default. In order to +analyze a project with PMD that uses these language features, you’ll need to enable it via the environment +variable PMD_JAVA_OPTS and select the new language version 13-preview:

    + +
    export PMD_JAVA_OPTS=--enable-preview
    +./run.sh pmd -language java -version 13-preview ...
    +
    + +

    Note: Support for the extended break statement introduced in Java 12 as a preview language feature +will be removed with the next PMD version 6.19.0.

    + +

    Full support for Scala

    + +

    Thanks to Chris Smith PMD now fully supports Scala. Now rules for analyzing Scala +code can be developed in addition to the Copy-Paste-Detection (CPD) functionality. There are no rules yet, so +contributions are welcome.

    + +

    Additionally Scala support has been upgraded from 2.12.4 to 2.13.

    + +

    New rule designer documentation

    + +

    The documentation for the rule designer is now available on the main PMD documentation page: +Rule Designer Reference. Check it out to learn +about the usage and features of the rule designer.

    + +

    New rules

    + +
      +
    • +

      The Java rule AvoidMessageDigestField (java-bestpractices) detects fields +of the type java.security.MessageDigest. Using a message digest instance as a field would need to be +synchronized, as it can easily be used by multiple threads. Without synchronization the calculated hash could +be entirely wrong. Instead of declaring this as a field and synchronize access to use it from multiple threads, +a new instance should be created when needed. This rule is also active when using java’s quickstart ruleset.

      +
    • +
    • +

      The Apex rule DebugsShouldUseLoggingLevel (apex-bestpractices) detects +usages of System.debug() method calls that are used without specifying the log level. Having the log +level specified provides a cleaner log, and improves readability of it.

      +
    • +
    + +

    Modified Rules

    + +
      +
    • The Java rule CloseResource (java-errorprone) now ignores by default instances +of java.util.stream.Stream. These streams are AutoCloseable, but most streams are backed by collections, +arrays, or generating functions, which require no special resource management. However, there are some exceptions: +The stream returned by Files::lines(Path) is backed by a actual file and needs to be closed. These instances +won’t be found by default by the rule anymore.
    • +
    + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #1465: [core] Stylesheet pmd-report.xslt fails to display filepath if ‘java’ in path
      • +
      • #1923: [core] Incremental analysis does not work with shortnames
      • +
      • #1983: [core] Avoid crashes with analysis cache when classpath references non-existing directories
      • +
      • #1990: [core] Incremental analysis mixes XPath rule violations
      • +
      +
    • +
    • apex +
        +
      • #1901: [apex] Expose super type name of UserClass
      • +
      • #1942: [apex] Add best practice rule for debug statements in Apex
      • +
      +
    • +
    • java +
        +
      • #1930: [java] Add Java 13 support
      • +
      +
    • +
    • java-bestpractices +
        +
      • #1227: [java] UnusedFormalParameter should explain checkAll better
      • +
      • #1862: [java] New rule for MessageDigest.getInstance
      • +
      • #1952: [java] UnusedPrivateField not triggering if @Value annotation present
      • +
      +
    • +
    • java-codestyle +
        +
      • #1951: [java] UnnecessaryFullyQualifiedName rule triggered when variable name clashes with package name
      • +
      +
    • +
    • java-errorprone +
        +
      • #1922: [java] CloseResource possible false positive with Streams
      • +
      • #1966: [java] CloseResource false positive if Stream is passed as method parameter
      • +
      • #1967: [java] CloseResource false positive with late assignment of variable
      • +
      +
    • +
    • plsql +
        +
      • #1933: [plsql] ParseException with cursor declared in anonymous block
      • +
      • #1935: [plsql] ParseException with SELECT INTO record defined as global variable
      • +
      • #1936: [plslq] ParseException with cursor inside procedure declaration
      • +
      • #1946: [plsql] ParseException with using TRIM inside IF statements condition
      • +
      • #1947: [plsql] ParseError - SELECT with FOR UPDATE OF
      • +
      • #1948: [plsql] ParseException with INSERT INTO using package global variables
      • +
      • #1950: [plsql] ParseException with UPDATE and package record variable
      • +
      • #1953: [plsql] ParseException with WITH in CURSOR
      • +
      +
    • +
    + +

    API Changes

    + +

    Changes to Renderer

    + +
      +
    • +

      Each renderer has now a new method Renderer#setUseShortNames which +is used for implementing the “shortnames” CLI option. The method is automatically called by PMD, if this +CLI option is in use. When rendering filenames to the report, the new helper method +AbstractRenderer#determineFileName should be used. This will change +the filename to a short name, if the CLI option “shortnames” is used.

      + +

      Not adjusting custom renderers will make them render always the full file names and not honoring the +CLI option “shortnames”.

      +
    • +
    + +

    Deprecated APIs

    + +
    For removal
    + + + +
    Internal APIs
    + +

    Those APIs are not intended to be used by clients, and will be hidden or removed with PMD 7.0.0. You can identify them with the @InternalApi annotation. You’ll also get a deprecation warning.

    + + + +

    External Contributions

    + + + +

    28-July-2019 - 6.17.0

    + +

    The PMD team is pleased to announce PMD 6.17.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Updated PMD Designer

    + +

    This PMD release ships a new version of the pmd-designer. +For the changes, see PMD Designer Changelog. +It contains a new feature to edit test cases directly within the designer. Any feedback is highly appreciated.

    + +

    Lua support

    + +

    Thanks to the contribution from Maikel Steneker, and built on top of the ongoing efforts to fully support Antlr-based languages, +PMD now has CPD support for Lua.

    + +

    Being based on a proper Antlr grammar, CPD can:

    + + +

    Modified Rules

    + +
      +
    • +

      The Java rule CloseResource (java-errorprone) ignores now by default +java.io.ByteArrayInputStream and java.io.CharArrayWriter. Such streams/writers do not need to be closed.

      +
    • +
    • +

      The Java rule MissingStaticMethodInNonInstantiatableClass (java-errorprone) has now +the new property annotations. +When one of the private constructors is annotated with one of the annotations, then the class is not considered +non-instantiatable anymore and no violation will be reported. By default, Spring’s @Autowired and +Java EE’s @Inject annotations are recognized.

      +
    • +
    + +

    Fixed Issues

    + +
      +
    • core +
        +
      • #1913: [core] “-help” CLI option ends with status code != 0
      • +
      +
    • +
    • doc +
        +
      • #1896: [doc] Error in changelog 6.16.0 due to not properly closed rule tag
      • +
      • #1898: [doc] Incorrect code example for DoubleBraceInitialization in documentation on website
      • +
      • #1906: [doc] Broken link for adding own CPD languages
      • +
      • #1909: [doc] Sample usage example refers to deprecated ruleset “basic.xml” instead of “quickstart.xml”
      • +
      +
    • +
    • java +
        +
      • #1910: [java] ATFD calculation problem
      • +
      +
    • +
    • java-errorprone +
        +
      • #1749: [java] DD False Positive in DataflowAnomalyAnalysis
      • +
      • #1832: [java] False positives for MissingStaticMethodInNonInstantiatableClass when DI is used
      • +
      • #1921: [java] CloseResource false positive with ByteArrayInputStream
      • +
      +
    • +
    • java-multithreading +
        +
      • #1903: [java] UnsynchronizedStaticFormatter doesn’t allow block-level synchronization when using allowMethodLevelSynchronization=true
      • +
      +
    • +
    • plsql +
        +
      • #1902: [pslql] ParseException when parsing (+)
      • +
      +
    • +
    • xml +
        +
      • #1666: [xml] wrong cdata rule description and examples
      • +
      +
    • +
    + +

    External Contributions

    + +
      +
    • #1869: [xml] fix #1666 wrong cdata rule description and examples - Artem
    • +
    • #1892: [lua] [cpd] Added CPD support for Lua - Maikel Steneker
    • +
    • #1905: [java] DataflowAnomalyAnalysis Rule in right order - YoonhoChoi96
    • +
    • #1908: [doc] Update ruleset filename from deprecated basic.xml to quickstart.xml - crunsk
    • +
    • #1916: [java] Exclude Autowired and Inject for MissingStaticMethodInNonInstantiatableClass - AnthonyKot
    • +
    • #1917: [core] Add ‘no error’ return option, and assign it to the cli when the help command is invoked - Renato Oliveira
    • +
    + +

    30-June-2019 - 6.16.0

    + +

    The PMD team is pleased to announce PMD 6.16.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Updated PMD Designer

    + +

    This PMD release ships a new version of the pmd-designer. +For the changes, see PMD Designer Changelog.

    + +

    PLSQL Grammar Updates

    + +

    The grammar has been updated to support inline constraints in CREATE TABLE statements. Additionally, the +CREATE TABLE statement may now be followed by physical properties and table properties. However, these +properties are skipped over during parsing.

    + +

    The CREATE VIEW statement now supports subquery views.

    + +

    The EXTRACT function can now be parsed correctly. It is used to extract values from a specified +datetime field. Also date time literals are parsed now correctly.

    + +

    The CASE expression can now be properly used within SELECT statements.

    + +

    Table aliases are now supported when specifying columns in INSERT INTO clauses.

    + +

    New Rules

    + +
      +
    • +

      The Java rule DoubleBraceInitialization (java-bestpractices) +detects non static initializers in anonymous classes also known as “double brace initialization”. +This can be problematic, since a new class file is generated and object holds a strong reference +to the surrounding class.

      + +

      Note: This rule is also part of the Java quickstart ruleset (rulesets/java/quickstart.xml).

      +
    • +
    + +

    Modified Rules

    + +
      +
    • +

      The Java rule UnusedPrivateField (java-bestpractices) now ignores by +default fields, that are annotated with the Lombok experimental annotation @Delegate. This can be +customized with the property ignoredAnnotations.

      +
    • +
    • +

      The Java rule SingularField (java-design) now ignores by +default fields, that are annotated with the Lombok experimental annotation @Delegate. This can be +customized with the property ignoredAnnotations.

      +
    • +
    • +

      The Java rules UnsynchronizedStaticFormatter and +UnsynchronizedStaticDateFormatter (java-multithreading) +now prefer synchronized blocks by default. They will raise a violation, if the synchronization is implemented +on the method level. To allow the old behavior, the new property allowMethodLevelSynchronization can +be enabled.

      +
    • +
    • +

      The Java rule UseUtilityClass (java-design) has a new property ignoredAnnotations. +By default, classes that are annotated with Lombok’s @UtilityClass are ignored now.

      +
    • +
    • +

      The Java rule NonStaticInitializer (java-errorprone) does not report +non static initializers in anonymous classes anymore. For this use case, there is a new rule now: +DoubleBraceInitialization (java-bestpractices).

      +
    • +
    • +

      The Java rule CommentDefaultAccessModifier (java-codestyle) was enhanced +in the last version 6.15.0 to check also top-level types by default. This created many new violations. +Missing the access modifier for top-level types is not so critical, since it only decreases the visibility +of the type.

      + +

      The default behaviour has been restored. If you want to enable the check for top-level types, you can +use the new property checkTopLevelTypes.

      +
    • +
    • +

      The Java rule CloseResource (java-errorprone) now by default searches +for any unclosed java.lang.AutoCloseable resource. This includes now the standard java.io.*Stream classes. +Previously only SQL-related resources were considered by this rule. The types can still be configured +via the types property. Some resources do not need to be closed (e.g. ByteArrayOutputStream). These +exceptions can be configured via the new property allowedResourceTypes. +In order to restore the old behaviour, just remove the type java.lang.AutoCloseable from the types +property and keep the remaining SQL-related classes.

      +
    • +
    + +

    Deprecated Rules

    + +
      +
    • The Java rule AvoidFinalLocalVariable (java-codestyle) has been deprecated +and will be removed with PMD 7.0.0. The rule is controversial and also contradicts other existing +rules such as LocalVariableCouldBeFinal. If the goal is to avoid defining +constants in a scope smaller than the class, then the rule AvoidDuplicateLiterals +should be used instead.
    • +
    + +

    Fixed Issues

    + +
      +
    • apex +
        +
      • #1664: [apex] False positive ApexSharingViolationsRule, unsupported Apex feature
      • +
      +
    • +
    • java +
        +
      • #1848: [java] Local classes should preserve their modifiers
      • +
      +
    • +
    • java-bestpractices +
        +
      • #1703: [java] UnusedPrivateField on member annotated with lombok @Delegate
      • +
      • #1845: [java] Regression in MethodReturnsInternalArray not handling enums
      • +
      • #1854: [java] Rule to check for double brace initialisation
      • +
      +
    • +
    • java-codestyle +
        +
      • #1612: [java] Deprecate AvoidFinalLocalVariable
      • +
      • #1880: [java] CommentDefaultAccessModifier should be configurable for top-level classes
      • +
      +
    • +
    • java-design +
        +
      • #1094: [java] UseUtilityClass should be LombokAware
      • +
      +
    • +
    • java-errorprone +
        +
      • #1000: [java] The rule CloseResource should deal with IO stream as default
      • +
      • #1853: [java] False positive for NonStaticInitializer in anonymous class
      • +
      +
    • +
    • java-multithreading +
        +
      • #1814: [java] UnsynchronizedStaticFormatter documentation and implementation wrong
      • +
      • #1815: [java] False negative in UnsynchronizedStaticFormatter
      • +
      +
    • +
    • plsql +
        +
      • #1828: [plsql] Parentheses stopped working
      • +
      • #1850: [plsql] Parsing errors with INSERT using returning or records and TRIM expression
      • +
      • #1873: [plsql] Expression list not working
      • +
      • #1878: [pslql] ParseException when parsing USING
      • +
      • #1879: [pslql] ParseException when parsing LEFT JOIN
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated APIs

    + +
    +

    Reminder: Please don’t use members marked with the annotation InternalApi, as they will likely be removed, hidden, or otherwise intentionally broken with 7.0.0.

    +
    + +
    In ASTs
    + +

    As part of the changes we’d like to do to AST classes for 7.0.0, we would like to +hide some methods and constructors that rule writers should not have access to. +The following usages are now deprecated in the Java AST (with other languages to come):

    + +
      +
    • Manual instantiation of nodes. Constructors of node classes are deprecated and marked InternalApi. Nodes should only be obtained from the parser, which for rules, means that never need to instantiate node themselves. Those constructors will be made package private with 7.0.0.
    • +
    • Subclassing of abstract node classes, or usage of their type. Version 7.0.0 will bring a new set of abstractions that will be public API, but the base classes are and will stay internal. You should not couple your code to them. +
        +
      • In the meantime you should use interfaces like JavaNode or Node, or the other published interfaces in this package, to refer to nodes generically.
      • +
      • Concrete node classes will be made final with 7.0.0.
      • +
      +
    • +
    • Setters found in any node class or interface. Rules should consider the AST immutable. We will make those setters package private with 7.0.0.
    • +
    + +

    Please look at net.sourceforge.pmd.lang.java.ast to find out the full list +of deprecations.

    + +

    External Contributions

    + + + +

    26-May-2019 - 6.15.0

    + +

    The PMD team is pleased to announce PMD 6.15.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Enhanced Matlab support

    + +

    Thanks to the contributions from Maikel Steneker CPD for Matlab can +now parse Matlab programs which use the question mark operator to specify access to +class members:

    + +
    classdef Class1
    +properties (SetAccess = ?Class2)
    +
    + +

    CPD also understands now double quoted strings, which are supported since version R2017a of Matlab:

    + +
    str = "This is a string"
    +
    + +

    Enhanced C++ support

    + +

    CPD now supports digit separators in C++ (language module “cpp”). This is a C++14 feature.

    + +

    Example: auto integer_literal = 1'000'000;

    + +

    The single quotes can be used to add some structure to large numbers.

    + +

    CPD also parses raw string literals now correctly (see #1784).

    + +

    New Rules

    + +
      +
    • +

      The new Apex rule FieldNamingConventions (apex-codestyle) checks the naming +conventions for field declarations. By default this rule uses the standard Apex naming convention (Camel case), +but it can be configured through properties.

      +
    • +
    • +

      The new Apex rule FormalParameterNamingConventions (apex-codestyle) checks the +naming conventions for formal parameters of methods. By default this rule uses the standard Apex naming +convention (Camel case), but it can be configured through properties.

      +
    • +
    • +

      The new Apex rule LocalVariableNamingConventions (apex-codestyle) checks the +naming conventions for local variable declarations. By default this rule uses the standard Apex naming +convention (Camel case), but it can be configured through properties.

      +
    • +
    • +

      The new Apex rule PropertyNamingConventions (apex-codestyle) checks the naming +conventions for property declarations. By default this rule uses the standard Apex naming convention (Camel case), +but it can be configured through properties.

      +
    • +
    • +

      The new Java rule UseShortArrayInitializer (java-codestyle) searches for +array initialization expressions, which can be written shorter.

      +
    • +
    + +

    Modified Rules

    + +
      +
    • +

      The Apex rule ClassNamingConventions (apex-codestyle) can now be configured +using various properties for the specific kind of type declarations (e.g. class, interface, enum). +As before, this rule uses by default the standard Apex naming convention (Pascal case).

      +
    • +
    • +

      The Apex rule MethodNamingConventions (apex-codestyle) can now be configured +using various properties to differenciate e.g. static methods and test methods. +As before, this rule uses by default the standard Apex naming convention (Camel case).

      +
    • +
    • +

      The Java rule FieldNamingConventions (java-codestyle) now by default ignores +the field serialPersistentFields. Since this is a field which needs to have this special name, no +field naming conventions can be applied here. It is excluded the same way like serialVersionUID via the +property exclusions.

      +
    • +
    • +

      The Java rule CommentRequired (java-documentation) has a new property +serialPersistentFieldsCommentRequired with the default value “Ignored”. This means that from now +on comments for the field serialPersistentFields are not required anymore. You can change the property +to restore the old behavior.

      +
    • +
    • +

      The Java rule ProperLogger (java-errorprone) has two new properties +to configure the logger class (e.g. “org.slf4j.Logger”) and the logger name of the special case, +when the logger is not static. The name of the static logger variable was already configurable. +The new property “loggerClass” allows to use this rule for different logging frameworks. +This rule covers all the cases of the now deprecated rule LoggerIsNotStaticFinal.

      +
    • +
    • +

      The Java rule CommentDefaultAccessModifier (java-codestyle) now reports also +missing comments for top-level classes and annotations, that are package-private.

      +
    • +
    + +

    Deprecated Rules

    + + + +

    Fixed Issues

    + +
      +
    • apex +
        +
      • #1321: [apex] Should VariableNamingConventions require properties to start with a lowercase letter?
      • +
      • #1783: [apex] comments on constructor not recognized when the Class has inner class
      • +
      +
    • +
    • cpp +
        +
      • #1784: [cpp] Improve support for raw string literals
      • +
      +
    • +
    • dart +
        +
      • #1809: [dart] [cpd] Parse error with escape sequences
      • +
      +
    • +
    • java +
        +
      • #1842: [java] Annotated module declarations cause parse error
      • +
      +
    • +
    • java-bestpractices +
        +
      • #1738: [java] MethodReturnsInternalArray does not work in inner classes
      • +
      +
    • +
    • java-codestyle +
        +
      • #1495: [java] Rule to detect overly verbose array initializiation
      • +
      • #1684: [java] Properly whitelist serialPersistentFields
      • +
      • #1804: [java] NPE in UnnecessaryLocalBeforeReturnRule
      • +
      +
    • +
    • python +
        +
      • #1810: [python] [cpd] Parse error when using Python 2 backticks
      • +
      +
    • +
    • matlab +
        +
      • #1830: [matlab] [cpd] Parse error with comments
      • +
      • #1793: [java] CommentDefaultAccessModifier not working for classes
      • +
      +
    • +
    + +

    API Changes

    + +

    Deprecated APIs

    + +
    For removal
    + + + +

    External Contributions

    + + + +

    28-April-2019 - 6.14.0

    + +

    The PMD team is pleased to announce PMD 6.14.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Dart support

    + +

    Thanks to the contribution from Maikel Steneker, and built on top of the ongoing efforts to fully support Antlr-based languages, +PMD now has CPD support for Dart.

    + +

    Being based on a proper Antlr grammar, CPD can:

    + + +

    Updated PMD Designer

    + +

    This PMD release ships a new version of the pmd-designer. +For the changes, see PMD Designer Changelog.

    + +

    Modified Rules

    + +
      +
    • +

      The Java rule AssignmentToNonFinalStatic (java-errorprone) will now report on each +assignment made within a constructor rather than on the field declaration. This makes it easier for developers to +find the offending statements.

      +
    • +
    • +

      The Java rule NoPackage (java-codestyle) will now report additionally enums +and annotations that do not have a package declaration.

      +
    • +
    + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #1515: [core] Module pmd-lang-test is missing javadoc artifact
      • +
      • #1788: [cpd] [core] Use better ClassLoader for ServiceLoader in LanguageFactory
      • +
      • #1794: [core] Ruleset Compatibility fails with excluding rules
      • +
      +
    • +
    • go +
        +
      • #1751: [go] Parsing errors encountered with escaped backslash
      • +
      +
    • +
    • java +
        +
      • #1532: [java] NPE with incomplete auxclasspath
      • +
      • #1691: [java] Possible Data Race in JavaTypeDefinitionSimple.getGenericType
      • +
      • #1729: [java] JavaRuleViolation loses information in className field when class has package-private access level
      • +
      +
    • +
    • java-bestpractices +
        +
      • #1190: [java] UnusedLocalVariable/UnusedPrivateField false-positive
      • +
      • #1720: [java] UnusedImports false positive for Javadoc link with array type
      • +
      +
    • +
    • java-codestyle +
        +
      • #1755: [java] False negative in UnnecessaryLocalBeforeReturn when splitting statements across multiple lines
      • +
      • #1782: [java] NoPackage: False Negative for enums
      • +
      +
    • +
    • java-design +
        +
      • #1760: [java] UseObjectForClearerAPI flags private methods
      • +
      +
    • +
    + +

    API Changes

    + +

    No changes.

    + +

    External Contributions

    + + + +

    31-March-2019 - 6.13.0

    + +

    The PMD team is pleased to announce PMD 6.13.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + + + +

    We are still searching for a new logo for PMD for the next major release.

    + +

    Learn more about how to participate on github issue 1663.

    + +

    Java 12 Support

    + +

    This release of PMD brings support for Java 12. PMD can parse the new Switch Expressions +and resolve the type of such an expression.

    + +

    Note: The Switch Expressions are a preview language feature of OpenJDK 12 and are not enabled by default. In order to +analyze a project with PMD that uses these language features, you’ll need to enable it via the new environment +variable PMD_JAVA_OPTS:

    + +
    export PMD_JAVA_OPTS=--enable-preview
    +./run.sh pmd ...
    +
    + +

    Quickstart Ruleset for Apex

    + +

    PMD provides now a quickstart ruleset for Salesforce.com Apex, which you can use as a base ruleset to +get your custom ruleset started. You can reference it with rulesets/apex/quickstart.xml. +You are strongly encouraged to create your own ruleset +though.

    + +

    The quickstart ruleset has the intention, to be useful out-of-the-box for many projects. Therefore it +references only rules, that are most likely to apply everywhere.

    + +

    Any feedback would be greatly appreciated.

    + +

    PMD Designer

    + +

    The rule designer’s codebase has been moved out of the main repository and +will be developed at pmd/pmd-designer +from now on. The maven coordinates will stay the same for the time being. +The designer will still be shipped with PMD’s binaries.

    + +

    Improved Apex Support

    + +
      +
    • Many AST nodes now expose more information which makes it easier to write XPath-based rules for Apex. Here are +some examples: +
        +
      • Annotation[@Resolved = false()] finds unsupported annotations.
      • +
      • AnnotationParameter[@Name='RestResource'][@Value='/myurl'] gives access to +annotation parameters.
      • +
      • CatchBlockStatement[@ExceptionType='Exception'][@VariableName='e'] finds catch +block for specific exception types.
      • +
      • Field[@Type='String'] find all String fields, Field[string-length(@Name) < 5] +finds all fields with short names and Field[@Value='a'] find alls fields, that are +initialized with a specific value.
      • +
      • LiteralExpression[@String = true()] finds all String literals. There are attributes +for each type: @Boolean, @Integer, @Double, @Long, @Decimal, @Null.
      • +
      • Method[@Constructor = true()] selects all constructors. Method[@ReturnType = 'String'] +selects all methods that return a String.
      • +
      • The ModifierNode node has a couple of attributes to check for the existence of specific +modifiers: @Test, @TestOrTestSetup, @WithSharing, @WithoutSharing, @InheritedSharing, +@WebService, @Global, @Override.
      • +
      • Many nodes now expose their type. E.g. with Parameter[@Type='Integer'] you can find all +method parameters of type Integer. The same attribute Type exists as well for: +NewObjectExpression, Property, VariableDeclaration.
      • +
      • VariableExpression[@Image='i'] finds all variable usages of the variable “i”.
      • +
      +
    • +
    + +

    New Rules

    + +
      +
    • +

      The new Java rule AvoidUncheckedExceptionsInSignatures (java-design) finds methods or constructors +that declare unchecked exceptions in their throws clause. This forces the caller to handle the exception, +even though it is a runtime exception.

      +
    • +
    • +

      The new Java rule DetachedTestCase (java-errorprone) searches for public +methods in test classes, which are not annotated with @Test. These methods might be test cases where +the annotation has been forgotten. Because of that those test cases are never executed.

      +
    • +
    • +

      The new Java rule WhileLoopWithLiteralBoolean (java-bestpractices) finds +Do-While-Loops and While-Loops that can be simplified since they use simply true or false as their +loop condition.

      +
    • +
    • +

      The new Apex rule ApexAssertionsShouldIncludeMessage (apex-bestpractices) +searches for assertions in unit tests and checks, whether they use a message argument.

      +
    • +
    • +

      The new Apex rule ApexUnitTestMethodShouldHaveIsTestAnnotation (apex-bestpractices) +searches for methods in test classes, which are missing the @IsTest annotation.

      +
    • +
    • +

      The new PLSQL rule AvoidTabCharacter (plsql-codestyle) checks, that there are +no tab characters (“\t”) in the source file.

      +
    • +
    • +

      The new PLSQL rule LineLength (plsql-codestyle) helps to enforce a maximum +line length.

      +
    • +
    + +

    Fixed Issues

    + +
      +
    • doc +
        +
      • #1721: [doc] Documentation provides an invalid property configuration example
      • +
      +
    • +
    • java +
        +
      • #1537: [java] Java 12 support
      • +
      +
    • +
    • java-bestpractices +
        +
      • #1701: [java] UseTryWithResources does not handle multiple argument close methods
      • +
      +
    • +
    • java-codestyle +
        +
      • #1527: [java] UseUnderscoresInNumericLiterals false positive on floating point numbers
      • +
      • #1674: [java] documentation of CommentDefaultAccessModifier is wrong
      • +
      +
    • +
    • java-errorprone +
        +
      • #1570: [java] AvoidDuplicateLiterals warning about deprecated separator property when not used
      • +
      +
    • +
    • plsql +
        +
      • #1510: [plsql] Support XMLTABLE functions
      • +
      • #1716: [plsql] Support access to whole plsql code
      • +
      • #1731: [pslql] ParseException when parsing ELSIF
      • +
      • #1733: [plsql] % not supported in “TestSearch%notfound”
      • +
      • #1734: [plsql] TooManyMethods false-negative
      • +
      • #1735: [plsql] False-negatives for TO_DATE_TO_CHAR, TO_DATEWithoutDateFormat, TO_TIMESTAMPWithoutDateFormat
      • +
      +
    • +
    + +

    API Changes

    + +

    Command Line Interface

    + +

    The start scripts run.sh, pmd.bat and cpd.bat support the new environment variable PMD_JAVA_OPTS. +This can be used to set arbitrary JVM options for running PMD, such as memory settings (e.g. PMD_JAVA_OPTS=-Xmx512m) +or enable preview language features (e.g. PMD_JAVA_OPTS=--enable-preview).

    + +

    The previously available variables such as OPTS or HEAPSIZE are deprecated and will be removed with PMD 7.0.0.

    + +

    Deprecated API

    + +
      +
    • +

      CodeClimateRule is deprecated in 7.0.0 because it was unused for 2 years and +created an unwanted dependency. +Properties “cc_categories”, “cc_remediation_points_multiplier”, “cc_block_highlighting” will also be removed. +See #1702 for more.

      +
    • +
    • +

      The Apex ruleset rulesets/apex/ruleset.xml has been deprecated and will be removed in 7.0.0. Please use the new +quickstart ruleset rulesets/apex/quickstart.xml instead.

      +
    • +
    + +

    External Contributions

    + + + +

    24-February-2019 - 6.12.0

    + +

    The PMD team is pleased to announce PMD 6.12.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Call For Logo

    + +

    PMD’s logo was great for a long time. But now we want to take the opportunity with the next major release to change +our logo in order to use a more “politically correct” one.

    + +

    Learn more about how to participate on github issue 1663.

    + +

    CPD Suppression for Antlr-based languages

    + +

    ITBA students Matías Fraga, +Tomi De Lucca and Lucas Soncini +keep working on bringing full Antlr support to PMD. For this release, they have implemented +token filtering in an equivalent way as we did for JavaCC languages, adding support for CPD +suppressions through CPD-OFF and CPD-ON comments for all Antlr-based languages.

    + +

    This means, you can now ignore arbitrary blocks of code on:

    +
      +
    • Go
    • +
    • Kotlin
    • +
    • Swift
    • +
    + +

    Simply start the suppression with any comment (single or multiline) containing CPD-OFF, +and resume again with a comment containing CPD-ON.

    + +

    More information is available in the user documentation.

    + +

    PL/SQL Grammar improvements

    + +
      +
    • In this release, many more parser bugs in our PL/SQL support have been fixed. This adds more complete +support for UPDATE statements and subqueries and hierarchical queries in SELECT statements.
    • +
    • Support for analytic functions such as LISTAGG has been added.
    • +
    • Conditions in WHERE clauses support now REGEX_LIKE and multiset conditions.
    • +
    + +

    New Rules

    + +
      +
    • The new Java rule UseTryWithResources (java-bestpractices) searches +for try-blocks, that could be changed to a try-with-resources statement. This statement ensures that +each resource is closed at the end of the statement and is available since Java 7.
    • +
    + +

    Modified Rules

    + +
      +
    • The Apex rule MethodNamingConventions (apex-codestyle) has a new +property skipTestMethodUnderscores, which is by default disabled. The new property allows for ignoring +all test methods, either using the testMethod modifier or simply annotating them @isTest.
    • +
    + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #1462: [core] Failed build on Windows with source zip archive
      • +
      • #1559: [core] CPD: Lexical error in file (no file name provided)
      • +
      • #1671: [doc] Wrong escaping in suppressing warnings for nopmd-comment
      • +
      • #1693: [ui] Improved error reporting for the designer
      • +
      +
    • +
    • java-bestpractices +
        +
      • #808: [java] AccessorMethodGeneration false positives with compile time constants
      • +
      • #1405: [java] New Rule: UseTryWithResources - Replace close and IOUtils.closeQuietly with try-with-resources
      • +
      • #1555: [java] UnusedImports false positive for method parameter type in @see Javadoc
      • +
      +
    • +
    • java-codestyle +
        +
      • #1543: [java] LinguisticNaming should ignore overriden methods
      • +
      • #1547: [java] AtLeastOneConstructorRule: false-positive with lombok.AllArgsConstructor
      • +
      • #1624: [java] UseDiamondOperator false positive with var initializer
      • +
      +
    • +
    • java-design +
        +
      • #1641: [java] False-positive with Lombok and inner classes
      • +
      +
    • +
    • java-errorprone +
        +
      • #780: [java] BeanMembersShouldSerializeRule does not recognize lombok accessors
      • +
      +
    • +
    • java-multithreading +
        +
      • #1633: [java] UnsynchronizedStaticFormatter reports commons lang FastDateFormat
      • +
      +
    • +
    • java-performance +
        +
      • #1632: [java] ConsecutiveLiteralAppends false positive over catch
      • +
      +
    • +
    • plsql +
        +
      • #1587: [plsql] ParseException with EXISTS
      • +
      • #1589: [plsql] ParseException with subqueries in WHERE clause
      • +
      • #1590: [plsql] ParseException when using hierarchical query clause
      • +
      • #1656: [plsql] ParseException with analytic functions, trim and subqueries
      • +
      +
    • +
    • designer +
        +
      • #1679: [ui] No default language version selected
      • +
      +
    • +
    + +

    API Changes

    + +

    No changes.

    + +

    External Contributions

    + +
      +
    • #1623: [java] Fix lombok.AllArgsConstructor support - Bobby Wertman
    • +
    • #1625: [java] UnusedImports false positive for method parameter type in @see Javadoc - Shubham
    • +
    • #1628: [java] LinguisticNaming should ignore overriden methods - Shubham
    • +
    • #1634: [java] BeanMembersShouldSerializeRule does not recognize lombok accessors - Shubham
    • +
    • #1635: [java] UnsynchronizedStaticFormatter reports commons lang FastDateFormat - Shubham
    • +
    • #1637: [java] Compile time constants initialized by literals avoided by AccessorMethodGenerationRule - Shubham
    • +
    • #1640: [java] Update instead of override classHasLombokAnnotation flag - Phokham Nonava
    • +
    • #1644: [apex] Add property to allow apex test methods to contain underscores - Tom
    • +
    • #1645: [java] ConsecutiveLiteralAppends false positive - Shubham
    • +
    • #1646: [java] UseDiamondOperator doesn’t work with var - Shubham
    • +
    • #1654: [core] Antlr token filter - Tomi De Lucca
    • +
    • #1655: [kotlin] Kotlin tokenizer refactor - Lucas Soncini
    • +
    • #1686: [doc] Replaced wrong escaping with “>” - Himanshu Pandey
    • +
    + +

    27-January-2019 - 6.11.0

    + +

    The PMD team is pleased to announce PMD 6.11.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Updated Apex Support

    + +
      +
    • The Apex language support has been bumped to version 45 (Spring ‘19). All new language features are now properly +parsed and processed.
    • +
    • Many nodes now expose more informations, such as the operator for BooleanExpressions. This makes these operators +consumable by XPath rules, e.g. //BooleanExpression[@Operator='&&'].
    • +
    + +

    PL/SQL Grammar improvements

    + +
      +
    • In this release, many parser bugs in our PL/SQL support have been fixed. This adds e.g. support for +table collection expressions (SELECT * FROM TABLE(expr)).
    • +
    • Support for parsing insert statements has been added.
    • +
    • More improvements are planned for the next release of PMD.
    • +
    + +

    New Rules

    + +
      +
    • +

      The new Java rule UnsynchronizedStaticFormatter (java-multithreading) detects +unsynchronized usages of static java.text.Format instances. This rule is a more generic replacement of the +rule UnsynchronizedStaticDateFormatter which focused just on DateFormat.

      +
    • +
    • +

      The new Java rule ForLoopVariableCount (java-bestpractices) checks for +the number of control variables in a for-loop. Having a lot of control variables makes it harder to understand +what the loop does. The maximum allowed number of variables is by default 1 and can be configured by a +property.

      +
    • +
    • +

      The new Java rule AvoidReassigningLoopVariables (java-bestpractices) searches +for loop variables that are reassigned. Changing the loop variables additionally to the loop itself can lead to +hard-to-find bugs.

      +
    • +
    • +

      The new Java rule UseDiamondOperator (java-codestyle) looks for constructor +calls with explicit type parameters. Since Java 1.7, these type parameters are not necessary anymore, as they +can be inferred now.

      +
    • +
    + +

    Modified Rules

    + +
      +
    • The Java rule LocalVariableCouldBeFinal (java-codestyle) has a new +property ignoreForEachDecl, which is by default disabled. The new property allows for ignoring +non-final loop variables in a for-each statement.
    • +
    + +

    Deprecated Rules

    + + + +

    Fixed Issues

    + +
      +
    • core +
        +
      • #1196: [core] CPD results not consistent between runs
      • +
      • #1496 [core] Refactor metrics to be dealt with generically from pmd-core
      • +
      +
    • +
    • apex +
        +
      • #1542: [apex] Include the documentation category
      • +
      • #1546: [apex] PMD parsing exception for Apex classes using ‘inherited sharing’ keyword
      • +
      • #1568: [apex] AST node attribute @Image not usable / always null in XPath rule / Designer
      • +
      +
    • +
    • java +
        +
      • #1556: [java] Default methods should not be considered abstract
      • +
      • #1578: [java] Private field is detected as public inside nested classes in interfaces
      • +
      +
    • +
    • java-bestpractices +
        +
      • #658: [java] OneDeclarationPerLine: False positive for loops
      • +
      • #1518: [java] New rule: AvoidReassigningLoopVariable
      • +
      • #1519: [java] New rule: ForLoopVariableCount
      • +
      +
    • +
    • java-codestyle +
        +
      • #1513: [java] LocalVariableCouldBeFinal: allow excluding the variable in a for-each loop
      • +
      • #1517: [java] New Rule: UseDiamondOperator
      • +
      +
    • +
    • java-errorprone +
        +
      • #1035: [java] ReturnFromFinallyBlock: False positive on lambda expression in finally block
      • +
      • #1549: [java] NPE in PMD 6.8.0 InvalidSlf4jMessageFormat
      • +
      +
    • +
    • java-multithreading +
        +
      • #1533: [java] New rule: UnsynchronizedStaticFormatter
      • +
      +
    • +
    • plsql +
        +
      • + + + + + + + + +
        #1507: [plsql] Parse Exception when using ‘ ’ operator in where clause
        +
      • +
      • #1508: [plsql] Parse Exception when using SELECT COUNT(*)
      • +
      • #1509: [plsql] Parse Exception with OUTER/INNER Joins
      • +
      • #1511: [plsql] Parse Exception with IS NOT NULL
      • +
      • #1526: [plsql] ParseException when using TableCollectionExpression
      • +
      • #1583: [plsql] Update Set Clause should allow multiple columns
      • +
      • #1586: [plsql] Parse Exception when functions are used with LIKE
      • +
      • #1588: [plsql] Parse Exception with function calls in WHERE clause
      • +
      +
    • +
    + +

    API Changes

    + + + +

    External Contributions

    + +
      +
    • #1503: [java] Fix for ReturnFromFinallyBlock false-positives - RishabhDeep Singh
    • +
    • #1514: [java] LocalVariableCouldBeFinal: allow excluding the variable in a for-each loop - Kris Scheibe
    • +
    • #1516: [java] OneDeclarationPerLine: Don’t report multiple variables in a for statement. - Kris Scheibe
    • +
    • #1520: [java] New rule: ForLoopVariableCount: check the number of control variables in a for loop - Kris Scheibe
    • +
    • #1521: [java] Upgrade to ASM7 for JDK 11 support - Mark Pritchard
    • +
    • #1530: [java] New rule: AvoidReassigningLoopVariables - Kris Scheibe
    • +
    • #1534: [java] This is the change regarding the usediamondoperator #1517 - hemanshu070
    • +
    • #1545: [doc] fixing dead links + tool to check for dead links automatically - Kris Scheibe
    • +
    • #1551: [java] InvalidSlf4jMessageFormatRule should not throw NPE for enums - Robbie Martinus
    • +
    • #1552: [core] Upgrading Google Gson from 2.5 to 2.8.5 - Thunderforge
    • +
    • #1553: [core] Upgrading System Rules dependency from 1.8.0 to 1.19.0 - Thunderforge
    • +
    • #1554: [plsql] updates should allow for multiple statements - tashiscool
    • +
    • #1584: [core] Fixes 1196: inconsistencies of clones returned by different CPD executions for the same files - Bruno Ferreira
    • +
    + +

    09-December-2018 - 6.10.0

    + +

    The PMD team is pleased to announce PMD 6.10.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Kotlin support for CPD

    + +

    Thanks to Maikel Steneker, CPD now supports Kotlin. +This means, you can use CPD to find duplicated code in your Kotlin projects.

    + +

    New Rules

    + +
      +
    • The new Java rule UseUnderscoresInNumericLiterals (java-codestyle) +verifies that numeric literals over a given length (4 chars by default, but configurable) are using +underscores every 3 digits for readability. The rule only applies to Java 7+ codebases.
    • +
    + +

    Modified Rules

    + + + +

    Fixed Issues

    +
      +
    • all +
        +
      • #1284: [doc] Keep record of every currently deprecated API
      • +
      • #1318: [test] Kotlin DSL to ease test writing
      • +
      • #1328: [ci] Building docs for release fails
      • +
      • #1341: [doc] Documentation Error with Regex Properties
      • +
      • #1468: [doc] Missing escaping leads to XSS
      • +
      • #1471: [core] XMLRenderer: ProcessingErrors from exceptions without a message missing
      • +
      • #1477: [core] Analysis cache fails with wildcard classpath entries
      • +
      +
    • +
    • java +
        +
      • #1460: [java] Intermittent PMD failure : PMD processing errors while no violations reported
      • +
      +
    • +
    • java-bestpractices +
        +
      • #647: [java] JUnitTestsShouldIncludeAssertRule should support this.exception as well as just exception
      • +
      • #1435: [java] JUnitTestsShouldIncludeAssert: Support AssertJ soft assertions
      • +
      +
    • +
    • java-codestyle +
        +
      • #1232: [java] Detector for large numbers not separated by _
      • +
      • #1372: [java] false positive for UselessQualifiedThis
      • +
      • #1440: [java] CommentDefaultAccessModifierRule shows incorrect message
      • +
      +
    • +
    • java-design +
        +
      • #1151: [java] ImmutableField false positive with multiple constructors
      • +
      • #1483: [java] Cyclo metric should count conditions of for statements correctly
      • +
      +
    • +
    • java-errorprone +
        +
      • #1512: [java] InvalidSlf4jMessageFormatRule causes NPE in lambda and static blocks
      • +
      +
    • +
    • plsql +
        +
      • #1454: [plsql] ParseException for IF/CASE statement with >=, <=, !=
      • +
      +
    • +
    + +

    API Changes

    + +

    Properties framework

    + +

    The properties framework is about to get a lifting, and for that reason, we need to deprecate a lot of APIs +to remove them in 7.0.0. The proposed changes to the API are described on the wiki

    + +
    Changes to how you define properties
    + + + +

    Here’s an example:

    +
    // Before 7.0.0, these are equivalent:
    +IntegerProperty myProperty = new IntegerProperty("score", "Top score value", 1, 100, 40, 3.0f);
    +IntegerProperty myProperty = IntegerProperty.named("score").desc("Top score value").range(1, 100).defaultValue(40).uiOrder(3.0f);
    +
    +// They both map to the following in 7.0.0
    +PropertyDescriptor<Integer> myProperty = PropertyFactory.intProperty("score").desc("Top score value").require(inRange(1, 100)).defaultValue(40);
    +
    + +

    You’re highly encouraged to migrate to using this new API as soon as possible, to ease your migration to 7.0.0.

    + +
    Architectural simplifications
    + + + +
    Changes to the PropertyDescriptor interface
    + +
      +
    • preferredRowCount is deprecated with no intended replacement. It was never implemented, and does not belong +in this interface. The methods uiOrder and compareTo(PropertyDescriptor) are deprecated for the +same reason. These methods mix presentation logic with business logic and are not necessary for PropertyDescriptors to work. +PropertyDescriptor will not extend Comparable<PropertyDescriptor> anymore come 7.0.0.
    • +
    • The method propertyErrorFor is deprecated and will be removed with no intended +replacement. It’s really just a shortcut for prop.errorFor(rule.getProperty(prop)).
    • +
    • T valueFrom(String) and String asDelimitedString(T) are deprecated and will be removed. These were +used to serialize and deserialize properties to/from a string, but 7.0.0 will introduce a more flexible +XML syntax which will make them obsolete.
    • +
    • isMultiValue and type are deprecated and won’t be replaced. The new XML syntax will remove the need +for a divide between multi- and single-value properties, and will allow arbitrary types to be represented. +Since arbitrary types may be represented, type will become obsolete as it can’t represent generic types, +which will nevertheless be representable with the XML syntax. It was only used for documentation, but a +new way to document these properties exhaustively will be added with 7.0.0.
    • +
    • errorFor is deprecated as its return type will be changed to Optional<String> with the shift to Java 8.
    • +
    + +

    Deprecated APIs

    + +
    For internalization
    + + + +
    For removal
    + + + +

    External Contributions

    + + + +

    28-October-2018 - 6.9.0

    + +

    The PMD team is pleased to announce PMD 6.9.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Improved Golang CPD Support

    + +

    Thanks to the work of ITBA students Matías Fraga, +Tomi De Lucca and Lucas Soncini, +Golang is now backed by a proper Antlr Grammar. This means CPD is now better at detecting duplicates, +as comments are recognized as such and ignored.

    + +

    New Rules

    + +
      +
    • The new PLSQL rule CodeFormat (plsql-codestyle) verifies that +PLSQL code is properly formatted. It checks e.g. for correct indentation in select statements and verifies +that each parameter is defined on a separate line.
    • +
    + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #649: [core] Exclude specific files from command line
      • +
      • #1272: [core] Could not find or load main class when using symlinked run.sh
      • +
      • #1377: [core] LanguageRegistry uses default class loader when invoking ServiceLocator
      • +
      • #1394: [doc] How to configure “-cache "
      • +
      • #1412: [doc] Broken link to adding new cpd language documentation
      • +
      +
    • +
    • apex +
        +
      • #1396: [apex] ClassCastException caused by Javadoc
      • +
      +
    • +
    • java +
        +
      • #1330: [java] PMD crashes with java.lang.ClassFormatError: Absent Code attribute in method that is not native or abstract in class file javax/xml/ws/Service
      • +
      +
    • +
    • java-bestpractices +
        +
      • #1202: [java] GuardLogStatement: “There is log block not surrounded by if” doesn’t sound right
      • +
      • #1209: [java] UnusedImports false positive for static import with package-private method usage
      • +
      • #1343: [java] Update CommentDefaultAccessModifierRule to extend AbstractIgnoredAnnotationRule
      • +
      • #1365: [java] JUnitTestsShouldIncludeAssert false positive
      • +
      • #1404: [java] UnusedImports false positive with static ondemand import with method call
      • +
      +
    • +
    • java-codestyle +
        +
      • #1199: [java] UnnecessaryFullyQualifiedName doesn’t flag same package FQCNs
      • +
      • #1356: [java] UnnecessaryModifier wrong message public->static
      • +
      +
    • +
    • java-design +
        +
      • #1369: [java] Processing error (ClassCastException) if a TYPE_USE annotation is used on a base class in the “extends” clause
      • +
      +
    • +
    • jsp +
        +
      • #1402: [jsp] JspTokenManager has a problem about jsp scriptlet
      • +
      +
    • +
    • documentation +
        +
      • #1349: [doc] Provide some explanation for WHY duplicate code is bad, like mutations
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • PMD has a new CLI option -ignorelist. With that, you can provide a file containing a comma-delimit list of files, +that should be excluded during analysis. The ignorelist is applied after the files have been selected +via -dir or -filelist, which means, if the file is in both lists, then it will be ignored. +Note: there is no corresponding option for the Ant task, since the feature is already available via +Ant’s FileSet include/exclude filters.
    • +
    + +

    External Contributions

    + + + +

    30-September-2018 - 6.8.0

    + +

    The PMD team is pleased to announce PMD 6.8.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Drawing a line between private and public API

    + +

    Until now, all released public members and types were implicitly considered part +of PMD’s public API, including inheritance-specific members (protected members, abstract methods). +We have maintained those APIs with the goal to preserve full binary compatibility between minor releases, +only breaking those APIs infrequently, for major releases.

    + +

    In order to allow PMD to move forward at a faster pace, this implicit contract will +be invalidated with PMD 7.0.0. We now introduce more fine-grained distinctions between +the type of compatibility support we guarantee for our libraries, and ways to make +them explicit to clients of PMD.

    + +
    .internal packages and @InternalApi annotation
    + +

    Internal API is meant for use only by the main PMD codebase. Internal types and methods +may be modified in any way, or even removed, at any time.

    + +

    Any API in a package that contains an .internal segment is considered internal. +The @InternalApi annotation will be used for APIs that have to live outside of +these packages, e.g. methods of a public type that shouldn’t be used outside of PMD (again, +these can be removed anytime).

    + +
    @ReservedSubclassing
    + +

    Types marked with the @ReservedSubclassing annotation are only meant to be subclassed +by classes within PMD. As such, we may add new abstract methods, or remove protected methods, +at any time. All published public members remain supported. The annotation is not inherited, which +means a reserved interface doesn’t prevent its implementors to be subclassed.

    + +
    @Experimental
    + +

    APIs marked with the @Experimental annotation at the class or method level are subject to change. +They can be modified in any way, or even removed, at any time. You should not use or rely + on them in any production code. They are purely to allow broad testing and feedback.

    + +
    @Deprecated
    + +

    APIs marked with the @Deprecated annotation at the class or method level will remain supported +until the next major release but it is recommended to stop using them.

    + +
    The transition
    + +

    All currently supported APIs will remain so until 7.0.0. All APIs that are to be moved to +.internal packages or hidden will be tagged @InternalApi before that major release, and +the breaking API changes will be performed in 7.0.0.

    + +

    Quickstart Ruleset

    + +

    PMD 6.8.0 provides a first quickstart ruleset for Java, which you can use as a base ruleset to get your +custom ruleset started. You can reference it with rulesets/java/quickstart.xml. +You are strongly encouraged to create your own ruleset +though.

    + +

    The quickstart ruleset has the intention, to be useful out-of-the-box for many projects. Therefore it +references only rules, that are most likely to apply everywhere.

    + +

    Any feedback would be greatly appreciated.

    + +

    New Rules

    + +
      +
    • The new Apex rule ApexDoc (apex-documentation) +enforces the inclusion of ApexDoc on classes, interfaces, properties and methods; as well as some +sanity rules for such docs (no missing parameters, parameters’ order, and return value). By default, +method overrides and test classes are allowed to not include ApexDoc.
    • +
    + +

    Modified Rules

    + +
      +
    • The rule MissingSerialVersionUID (java-errorprone) has been modified +in order to recognize also missing serialVersionUID fields in abstract classes, if they are serializable. +Each individual class in the inheritance chain needs an own serialVersionUID field. See also Should an abstract class have a serialVersionUID. +This change might lead to additional violations in existing code bases.
    • +
    + +

    PLSQL

    + +

    The grammar for PLSQL has been revamped in order to fully parse SELECT INTO, UPDATE, and DELETE +statements. Previously such statements have been simply skipped ahead, now PMD is parsing them, giving access +to the individual parts of a SELECT-statement, such as the Where-Clause. This might produce new parsing errors +where PMD previously could successfully parse PLSQL code. If this happens, please report a new issue to get this problem fixed.

    + +

    Fixed Issues

    + +
      +
    • apex-bestpractices +
        +
      • #1348: [apex] AvoidGlobalModifierRule gives warning even when its a webservice - false positive
      • +
      +
    • +
    • java-codestyle +
        +
      • #1329: [java] FieldNamingConventions: false positive in serializable class with serialVersionUID
      • +
      • #1334: [java] LinguisticNaming should support AtomicBooleans
      • +
      +
    • +
    • java-errorprone +
        +
      • #1350: [java] MissingSerialVersionUID false-positive on interfaces
      • +
      • #1352: [java] MissingSerialVersionUID false-negative with abstract classes
      • +
      +
    • +
    • java-performance +
        +
      • #1325: [java] False positive in ConsecutiveLiteralAppends
      • +
      +
    • +
    • plsql +
        +
      • #1279: [plsql] Support for SELECT INTO
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • +

      A couple of methods and fields in net.sourceforge.pmd.properties.AbstractPropertySource have been +deprecated, as they are replaced by already existing functionality or expose internal implementation +details: propertyDescriptors, propertyValuesByDescriptor, +copyPropertyDescriptors(), copyPropertyValues(), ignoredProperties(), usesDefaultValues(), +useDefaultValueFor().

      +
    • +
    • +

      Some methods in net.sourceforge.pmd.properties.PropertySource have been deprecated as well: +usesDefaultValues(), useDefaultValueFor(), ignoredProperties().

      +
    • +
    • +

      The class net.sourceforge.pmd.lang.rule.AbstractDelegateRule has been deprecated and will +be removed with PMD 7.0.0. It is internally only in use by RuleReference.

      +
    • +
    • +

      The default constructor of net.sourceforge.pmd.lang.rule.RuleReference has been deprecated +and will be removed with PMD 7.0.0. RuleReferences should only be created by providing a Rule and +a RuleSetReference. Furthermore the following methods are deprecated: setRuleReference(), +hasOverriddenProperty(), usesDefaultValues(), useDefaultValueFor().

      +
    • +
    + +

    External Contributions

    + + + +

    02-September-2018 - 6.7.0

    + +

    The PMD team is pleased to announce PMD 6.7.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Modified Rules

    + +
      +
    • The Java rule OneDeclarationPerLine (java-bestpractices) has been revamped to +consider not only local variable declarations, but field declarations too.
    • +
    + +

    New Rules

    + +
      +
    • +

      The new Java rule LinguisticNaming (java-codestyle) +detects cases, when a method name indicates it returns a boolean (such as isSmall()) but it doesn’t. +Besides method names, the rule also checks field and variable names. It also checks, that getters return +something but setters won’t. The rule has several properties with which it can be customized.

      +
    • +
    • +

      The new PL/SQL rule ForLoopNaming (plsql-codestyle) +enforces a naming convention for “for loops”. Both “cursor for loops” and “index for loops” are covered. +The rule can be customized via patterns. By default, short variable names are reported.

      +
    • +
    • +

      The new Java rule FieldNamingConventions (java-codestyle) +detects field names that don’t comply to a given convention. It defaults to standard Java convention of using camelCase, +but can be configured with ease for e.g. constants or static fields.

      +
    • +
    • +

      The new Apex rule OneDeclarationPerLine (apex-codestyle) enforces declaring a +single field / variable per line; or per statement if the strictMode property is set. +It’s an Apex equivalent of the already existing Java rule of the same name.

      +
    • +
    + +

    Deprecated Rules

    + + + +

    Fixed Issues

    + +
      +
    • core +
        +
      • #1191: [core] Test Framework: Sort violations by line/column
      • +
      • #1283: [core] Deprecate ReportTree
      • +
      • #1288: [core] No supported build listeners found with Gradle
      • +
      • #1300: [core] PMD stops processing file completely, if one rule in a rule chain fails
      • +
      • #1317: [ci] Coveralls hasn’t built the project since June 25th
      • +
      +
    • +
    • java-bestpractices +
        +
      • #940: [java] JUnit 4 false positives for JUnit 5 tests
      • +
      • #1267: [java] MissingOverrideRule: Avoid NoClassDefFoundError with incomplete classpath
      • +
      • #1323: [java] AvoidUsingHardCodedIP ignores match pattern
      • +
      • #1327: [java] AvoidUsingHardCodedIP false positive for “:bee”
      • +
      +
    • +
    • java-codestyle +
        +
      • #1255: [java] UnnecessaryFullyQualifiedName false positive: static method on shadowed implicitly imported class
      • +
      • #1258: [java] False positive “UselessParentheses” for parentheses that contain assignment
      • +
      +
    • +
    • java-errorprone +
        +
      • #1078: [java] MissingSerialVersionUID rule does not seem to catch inherited classes
      • +
      +
    • +
    • java-performance +
        +
      • #1291: [java] InvalidSlf4jMessageFormat false positive: too many arguments with string concatenation operator
      • +
      • #1298: [java] RedundantFieldInitializer - NumberFormatException with Long
      • +
      +
    • +
    • jsp +
        +
      • #1274: [jsp] Support EL in tag attributes
      • +
      • #1276: [jsp] add support for jspf and tag extensions
      • +
      +
    • +
    • plsql +
        +
      • #681: [plsql] Parse error with Cursor For Loop
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • +

      All classes in the package net.sourceforge.pmd.lang.dfa.report have been deprecated and will be removed +with PMD 7.0.0. This includes the class net.sourceforge.pmd.lang.dfa.report.ReportTree. The reason is, +that this class is very specific to Java and not suitable for other languages. It has only been used for +YAHTMLRenderer, which has been rewritten to work without these classes.

      +
    • +
    • +

      The nodes RUNSIGNEDSHIFT and RSIGNEDSHIFT are deprecated and will be removed from the AST with PMD 7.0.0. +These represented the operator of ShiftExpression in two cases out of three, but they’re not needed and +make ShiftExpression inconsistent. The operator of a ShiftExpression is now accessible through +ShiftExpression#getOperator.

      +
    • +
    + +

    External Contributions

    + +
      +
    • #109: [java] Add two linguistics rules under naming - Arda Aslan
    • +
    • #1254: [ci] [GSoC] Integrating the danger and pmdtester to travis CI - BBG
    • +
    • #1258: [java] Use typeof in MissingSerialVersionUID - krichter722
    • +
    • #1264: [cpp] Fix NullPointerException in CPPTokenizer:99 - Rafael Cortês
    • +
    • #1277: [jsp] #1276 add support for jspf and tag extensions - Jordi Llach
    • +
    • #1275: [jsp] Issue #1274 - Support EL in tag attributes - Jordi Llach
    • +
    • #1278: [ci] [GSoC] Use pmdtester 1.0.0.pre.beta3 - BBG
    • +
    • #1289: [java] UselessParentheses: Fix false positive with assignments - cobratbq
    • +
    • #1290: [docs] [GSoC] Create the documentation about pmdtester - BBG
    • +
    • #1256: [java] #940 Avoid JUnit 4 false positives for JUnit 5 tests - Alex Shesterov
    • +
    • #1315: [apex] Add OneDeclarationPerStatement rule - Jeff Hube
    • +
    + +

    29-July-2018 - 6.6.0

    + +

    The PMD team is pleased to announce PMD 6.6.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Java 11 Support

    + +

    PMD is now able to parse the local-variable declaration syntax var xxx, that has been +extended for lambda parameters with Java 11 via +JEP 323: Local-Variable Syntax for Lambda Parameters.

    + +

    New Rules

    + +
      +
    • +

      The new Java rule LocalVariableNamingConventions +(java-codestyle) detects local variable names that don’t comply to a given convention. It defaults to standard +Java convention of using camelCase, but can be configured. Special cases can be configured for final variables +and caught exceptions’ names.

      +
    • +
    • +

      The new Java rule FormalParameterNamingConventions +(java-codestyle) detects formal parameter names that don’t comply to a given convention. It defaults to +standard Java convention of using camelCase, but can be configured. Special cases can be configured for final +parameters and lambda parameters (considering whether they are explicitly typed or not).

      +
    • +
    + +

    Modified Rules

    + + + +

    Fixed Issues

    + +
      +
    • core +
        +
      • #1178: [core] “Unsupported build listener” in gradle build
      • +
      • #1225: [core] Error in sed expression on line 82 of run.sh while detecting installed version of Java
      • +
      +
    • +
    • doc +
        +
      • #1215: [doc] TOC links don’t work?
      • +
      +
    • +
    • java-codestyle +
        +
      • #1211: [java] CommentDefaultAccessModifier false positive with nested interfaces (regression from 6.4.0)
      • +
      • #1216: [java] UnnecessaryFullyQualifiedName false positive for the same name method
      • +
      +
    • +
    • java-design +
        +
      • #1217: [java] CyclomaticComplexityRule counts ?-operator twice
      • +
      • #1226: [java] NPath complexity false negative due to overflow
      • +
      +
    • +
    • plsql +
        +
      • #980: [plsql] ParseException for CREATE TABLE
      • +
      • #981: [plsql] ParseException when parsing VIEW
      • +
      • #1047: [plsql] ParseException when parsing EXECUTE IMMEDIATE
      • +
      +
    • +
    • ui +
        +
      • #1233: [ui] XPath autocomplete arrows on first and last items
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • The findDescendantsOfType methods in net.sourceforge.pmd.lang.ast.AbstractNode no longer search for +exact type matches, but will match subclasses, too. That means, it’s now possible to look for abstract node +types such as AbstractJavaTypeNode and not only for it’s concrete subtypes.
    • +
    + +

    External Contributions

    + + + +

    26-June-2018 - 6.5.0

    + +

    The PMD team is pleased to announce PMD 6.5.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    New Rules

    + +
      +
    • The new Apex rule AvoidNonExistentAnnotations (apex-errorprone) +detects usages non-officially supported annotations. Apex supported non existent annotations for legacy reasons. +In the future, use of such non-existent annotations could result in broken Apex code that will not compile. +A full list of supported annotations can be found here
    • +
    + +

    Modified Rules

    + +
      +
    • The Java rule UnnecessaryModifier (java-codestyle) +now detects enum constrcutors with explicit private modifier. The rule now produces better error messages +letting you know exactly which modifiers are redundant at each declaration.
    • +
    + +

    Fixed Issues

    +
      +
    • all +
        +
      • #1119: [doc] Make the landing page of the documentation website more useful
      • +
      • #1168: [core] xml renderer schema definitions (#538) break included xslt files
      • +
      • #1173: [core] Some characters in CPD are not shown correctly.
      • +
      • #1193: [core] Designer doesn’t start with run.sh
      • +
      +
    • +
    • ecmascript +
        +
      • #861: [ecmascript] InnaccurateNumericLiteral false positive with hex literals
      • +
      +
    • +
    • java +
        +
      • #1074: [java] MissingOverrideRule exception when analyzing PMD under Java 9
      • +
      • #1174: [java] CommentUtil.multiLinesIn() could lead to StringIndexOutOfBoundsException
      • +
      +
    • +
    • java-bestpractices +
        +
      • #651: [java] SwitchStmtsShouldHaveDefault should be aware of enum types
      • +
      • #869: [java] GuardLogStatement false positive on return statements and Math.log
      • +
      +
    • +
    • java-codestyle +
        +
      • #667: [java] Make AtLeastOneConstructor Lombok-aware
      • +
      • #1154: [java] CommentDefaultAccessModifierRule FP with nested enums
      • +
      • #1158: [java] Fix IdenticalCatchBranches false positive
      • +
      • #1186: [java] UnnecessaryFullyQualifiedName doesn’t detect java.lang FQ names as violations
      • +
      +
    • +
    • java-design +
        +
      • #1200: [java] New default NcssCount method report level is drastically reduced from values of deprecated NcssMethodCount and NcssTypeCount
      • +
      +
    • +
    • xml +
        +
      • #715: [xml] ProjectVersionAsDependencyVersion false positive
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • +

      The utility class net.sourceforge.pmd.lang.java.ast.CommentUtil has been deprecated and will be removed +with PMD 7.0.0. Its methods have been intended to parse javadoc tags. A more useful solution will be added +around the AST node FormalComment, which contains as children JavadocElement nodes, which in +turn provide access to the JavadocTag.

      + +

      All comment AST nodes (FormalComment, MultiLineComment, SingleLineComment) have a new method +getFilteredComment() which provide access to the comment text without the leading /* markers.

      +
    • +
    • +

      The method AbstractCommentRule.tagsIndicesIn() has been deprecated and will be removed with +PMD 7.0.0. It is not very useful, since it doesn’t extract the information +in a useful way. You would still need check, which tags have been found, and with which +data they might be accompanied.

      +
    • +
    + +

    External Contributions

    + + + +

    29-May-2018 - 6.4.0

    + +

    The PMD team is pleased to announce PMD 6.4.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Java 10 Support

    + +

    PMD is now able to understand local-variable type inference as introduced by Java 10. +Simple type resolution features are available, e.g. the type of the variable s is inferred +correctly as String:

    + +
    var s = "Java 10";
    +
    + +

    XPath Type Resolution Functions

    + +

    For some time now PMD has supported Type Resolution, and exposed this functionality to XPath rules for the Java language +with the typeof function. This function however had a number of shortcomings:

    + +
      +
    • It would take a first arg with the name to match if types couldn’t be resolved. In all cases this was @Image +but was still required.
    • +
    • It required 2 separate arguments for the Fully Qualified Class Name and the simple name of the class against +which to test.
    • +
    • If only the Fully Qualified Class Name was provided, no simple name check was performed (not documented, +but abused on some rules to “fix” some false positives).
    • +
    + +

    In this release we are deprecating typeof in favor of a simpler typeIs function, which behaves exactly as the +old typeof when given all 3 arguments.

    + +

    typeIs receives a single parameter, which is the fully qualified name of the class to test against.

    + +

    So, calls such as:

    + +
    //ClassOrInterfaceType[typeof(@Image, 'junit.framework.TestCase', 'TestCase')]
    +
    + +

    can now we expressed much more concisely as:

    + +
    //ClassOrInterfaceType[typeIs('junit.framework.TestCase')]
    +
    + +

    With this change, we also allow to check against array types by just appending [] to the fully qualified class name. +These can be repeated for arrays of arrays (e.g. byte[][] or java.lang.String[]).

    + +

    Additionally, we introduce the companion function typeIsExactly, that receives the same parameters as typeIs, +but checks for exact type matches, without considering the type hierarchy. That is, the test +typeIsExactly('junit.framework.TestCase') will match only if the context node is an instance of TestCase, but +not if it’s an instance of a subclass of TestCase. Be aware then, that using that method with abstract types will +never match.

    + +

    New Rules

    + +
      +
    • +

      The new Java rule HardCodedCryptoKey (java-security) +detects hard coded keys used for encryption. It is recommended to store keys outside of the source code.

      +
    • +
    • +

      The new Java rule IdenticalCatchBranches (java-codestyle) +finds catch blocks, +that catch different exception but perform the same exception handling and thus can be collapsed into a +multi-catch try statement.

      +
    • +
    + +

    Modified Rules

    + +
      +
    • +

      The Java rule JUnit4TestShouldUseTestAnnotation (java-bestpractices) +has a new parameter “testClassPattern”. It is used to distinguish test classes from other classes and +avoid false positives. By default, any class, that has “Test” in its name, is considered a test class.

      +
    • +
    • +

      The Java rule CommentDefaultAccessModifier (java-codestyle) +allows now by default the comment “/* package */ in addition to “/* default */. This behavior can +still be adjusted by setting the property regex.

      +
    • +
    + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #1018: [java] Performance degradation of 250% between 6.1.0 and 6.2.0
      • +
      • #1145: [core] JCommander’s help text for option -min is wrong
      • +
      +
    • +
    • java +
        +
      • #672: [java] Support exact type matches for type resolution from XPath
      • +
      • #743: [java] Prepare for Java 10
      • +
      • #1077: [java] Analyzing enum with lambda passed in constructor fails with “The enclosing scope must exist.”
      • +
      • #1115: [java] Simplify xpath typeof syntax
      • +
      • #1131: [java] java.lang.ClassFormatError: Absent Code attribute in method that is not native or abstract in class file javax/faces/application/FacesMessage$Severity
      • +
      +
    • +
    • java-bestpractices +
        +
      • #527: [java] False Alarm of JUnit4TestShouldUseTestAnnotation on Predicates
      • +
      • #1063: [java] MissingOverride is triggered in illegal places
      • +
      +
    • +
    • java-codestyle +
        +
      • #720: [java] ShortVariable should whitelist lambdas
      • +
      • #955: [java] Detect identical catch statements
      • +
      • #1114: [java] Star import overwritten by explicit import is not correctly handled
      • +
      • #1064: [java] ClassNamingConventions suggests to add Util suffix for simple exception wrappers
      • +
      • #1065: [java] ClassNamingConventions shouldn’t prohibit numbers in class names
      • +
      • #1067: [java] [6.3.0] PrematureDeclaration false-positive
      • +
      • #1096: [java] ClassNamingConventions is too ambitious on finding utility classes
      • +
      +
    • +
    • java-design +
        +
      • #824: [java] UseUtilityClass false positive when extending
      • +
      • #1021: [java] False positive for DoNotExtendJavaLangError
      • +
      • #1097: [java] False negative in AvoidThrowingRawExceptionTypes
      • +
      +
    • +
    • java-performance +
        +
      • #1051: [java] ConsecutiveAppendsShouldReuse false-negative
      • +
      • #1098: [java] Simplify LongInstantiation, IntegerInstantiation, ByteInstantiation, and ShortInstantiation using type resolution
      • +
      • #1125: [java] Improve message of InefficientEmptyStringCheck for String.trim().isEmpty()
      • +
      +
    • +
    • doc +
        +
      • #999: [doc] Add a header before the XPath expression in rules
      • +
      • #1082: [doc] Multifile analysis doc is invalid
      • +
      +
    • +
    • vf-security +
        +
      • #1100: [vf] URLENCODE is ignored as valid escape method
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • The following classes in package net.sourceforge.pmd.benchmark have been deprecated: Benchmark, Benchmarker, +BenchmarkReport, BenchmarkResult, RuleDuration, StringBuilderCR and TextReport. Their API is not supported anymore +and is disconnected from the internals of PMD. Use the newer API based around TimeTracker instead, which can be found +in the same package.
    • +
    • The class net.sourceforge.pmd.lang.java.xpath.TypeOfFunction has been deprecated. Use the newer TypeIsFunction in the same package.
    • +
    • The typeof methdos in net.sourceforge.pmd.lang.java.xpath.JavaFunctions have been deprecated. +Use the newer typeIs method in the same class instead..
    • +
    • The methods isA, isEither and isNeither of net.sourceforge.pmd.lang.java.typeresolution.TypeHelper. +Use the new isExactlyAny and isExactlyNone methods in the same class instead.
    • +
    + +

    External Contributions

    + + + +

    29-April-2018 - 6.3.0

    + +

    The PMD team is pleased to announce PMD 6.3.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Tree Traversal Revision

    + +

    As described in #904, when searching for child nodes of the AST methods +such as hasDescendantOfType, getFirstDescendantOfType and findDescendantsOfType were found to behave inconsistently, +not all of them honoring find boundaries; that is, nodes that define a self-contained entity which should be considered separately +(think of lambdas, nested classes, anonymous classes, etc.). We have modified these methods to ensure all of them honor +find boundaries.

    + +

    This change implies several false positives / unexpected results +(ie: ASTBlockStatement falsely returning true to isAllocation()) +have been fixed; and lots of searches are now restricted to smaller search areas, which improves performance +(depending on the project, we have measured up to 10% improvements during Type Resolution, Symbol Table analysis, +and some rules’ application).

    + +

    Naming Rules Enhancements

    + +
      +
    • +

      ClassNamingConventions (java-codestyle) +has been enhanced to allow granular configuration of naming +conventions for different kinds of type declarations (eg enum or abstract +class). Each kind of declaration can use its own naming convention +using a regex property. See the rule’s documentation for more info about +configuration and default conventions.

      +
    • +
    • +

      MethodNamingConventions (java-codestyle) +has been enhanced in the same way.

      +
    • +
    + +

    CPD Suppression

    + +

    Back in PMD 5.6.0 we introduced the ability to suppress CPD warnings in Java using comments, by +including CPD-OFF (to start ignoring code), or CPD-ON (to resume analysis) during CPD execution. +This has proved to be much more flexible and versatile than the old annotation-based approach, +and has since been the preferred way to suppress CPD warnings.

    + +

    On this occasion, we are extending support for comment-based suppressions to many other languages:

    + +
      +
    • C/C++
    • +
    • Ecmascript / Javascript
    • +
    • Matlab
    • +
    • Objective-C
    • +
    • PL/SQL
    • +
    • Python
    • +
    + +

    So for instance, in Python we could now do:

    + +
    class BaseHandler(object):
    +    def __init__(self):
    +        # some unignored code
    +
    +        # tell cpd to start ignoring code - CPD-OFF
    +
    +        # mission critical code, manually loop unroll
    +        GoDoSomethingAwesome(x + x / 2);
    +        GoDoSomethingAwesome(x + x / 2);
    +        GoDoSomethingAwesome(x + x / 2);
    +        GoDoSomethingAwesome(x + x / 2);
    +        GoDoSomethingAwesome(x + x / 2);
    +        GoDoSomethingAwesome(x + x / 2);
    +
    +        # resume CPD analysis - CPD-ON
    +
    +        # further code will *not* be ignored
    +
    + +

    Other languages are equivalent.

    + +

    Swift 4.1 Support

    + +

    Thanks to major contributions from kenji21 the Swift grammar has been updated to +support Swift 4.1. This is a major update, since the old grammar was quite dated, and we are sure all iOS +developers will enjoy it.

    + +

    Unfortunately, this change is not compatible. The grammar elements that have been removed (ie: the keywords __FILE__, +__LINE__, __COLUMN__ and __FUNCTION__) are no longer supported. We don’t usually introduce such +drastic / breaking changes in minor releases, however, given that the whole Swift ecosystem pushes hard towards +always using the latest versions, and that Swift needs all code and libraries to be currently compiling against +the same Swift version, we felt strongly this change was both safe and necessary to be shipped as soon as possible. +We had great feedback from the community during the process but if you have a legitimate use case for older Swift +versions, please let us know on our Issue Tracker.

    + +

    New Rules

    + +
      +
    • The new Java rule InsecureCryptoIv (java-security) +detects hard coded initialization vectors used in cryptographic operations. It is recommended to use +a randomly generated IV.
    • +
    + +

    Modified Rules

    + +
      +
    • +

      The Java rule UnnecessaryConstructor (java-codestyle) +has been rewritten as a Java rule (previously it was a XPath-based rule). It supports a new property +ignoredAnnotations and ignores by default empty constructors, +that are annotated with javax.inject.Inject. Additionally, it detects now also unnecessary private constructors +in enums.

      +
    • +
    • +

      The property checkNativeMethods of the Java rule MethodNamingConventions (java-codestyle) +is now deprecated, as it is now superseded by nativePattern. Support for that property will be maintained until +7.0.0.

      +
    • +
    • +

      The Java rule ControlStatementBraces (java-codestyle) +supports a new boolean property checkSingleIfStmt. When unset, the rule won’t report if statements which lack +braces, if the statement is not part of an if ... else if chain. This property defaults to true.

      +
    • +
    + +

    Deprecated Rules

    + + + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #695: [core] Extend comment-based suppression to all JavaCC languages
      • +
      • #988: [core] FileNotFoundException for missing classes directory with analysis cache enabled
      • +
      • #1036: [core] Non-XML output breaks XML-based CLI integrations
      • +
      +
    • +
    • apex-errorprone +
        +
      • #776: [apex] AvoidHardcodingId false positives
      • +
      +
    • +
    • documentation +
        +
      • #994: [doc] Delete duplicate page contributing.md on the website
      • +
      • #1057: [doc] Documentation of ignoredAnnotations property is misleading
      • +
      +
    • +
    • java +
        +
      • #894: [java] Maven PMD plugin fails to process some files without any explanation
      • +
      • #899: [java] JavaTypeDefinitionSimple.toString can cause NPEs
      • +
      • #1020: [java] The CyclomaticComplexity rule runs forever in 6.2.0
      • +
      • #1030: [java] NoClassDefFoundError when analyzing PMD with PMD
      • +
      • #1061: [java] Update ASM to handle Java 10 bytecode
      • +
      +
    • +
    • java-bestpractices +
        +
      • #370: [java] GuardLogStatementJavaUtil not considering lambdas
      • +
      • #558: [java] ProperLogger Warnings for enums
      • +
      • #719: [java] Unused Code: Java 8 receiver parameter with an internal class
      • +
      • #1009: [java] JUnitAssertionsShouldIncludeMessage - False positive with assertEquals and JUnit5
      • +
      +
    • +
    • java-codestyle +
        +
      • #1003: [java] UnnecessaryConstructor triggered on required empty constructor (Dagger @Inject)
      • +
      • #1023: [java] False positive for useless parenthesis
      • +
      • #1004: [java] ControlStatementBraces is missing checkIfStmt property
      • +
      +
    • +
    • java-design +
        +
      • #1056: [java] Property ignoredAnnotations does not work for SingularField and ImmutableField
      • +
      +
    • +
    • java-errorprone +
        +
      • #629: [java] NullAssignment false positive
      • +
      • #816: [java] SingleMethodSingleton false positives with inner classes
      • +
      +
    • +
    • java-performance +
        +
      • #586: [java] AvoidUsingShortType erroneously triggered on overrides of 3rd party methods
      • +
      +
    • +
    • swift +
        +
      • #678: [swift][cpd] Exception when running for Swift 4 code (KeyPath)
      • +
      +
    • +
    + +

    External Contributions

    + + + +

    26-March-2018 - 6.2.0

    + +

    The PMD team is pleased to announce PMD 6.2.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Ecmascript (JavaScript)

    + +

    The Rhino Library has been upgraded from version 1.7.7 to version 1.7.7.2.

    + +

    Detailed changes for changed in Rhino can be found:

    + + +

    Both are bugfixing releases.

    + +

    Disable Incremental Analysis

    + +

    Some time ago, we added support for Incremental Analysis. On PMD 6.0.0, we +started to add warns when not using it, as we strongly believe it’s a great improvement to our user’s experience as +analysis time is greatly reduced; and in the future we plan to have it enabled by default. However, we realize some +scenarios don’t benefit from it (ie: CI jobs), and having the warning logged can be noisy and cause confusion.

    + +

    To this end, we have added a new flag to allow you to explicitly disable incremental analysis. On CLI, this is +the new -no-cache flag. On Ant, there is a noCache attribute for the <pmd> task.

    + +

    On both scenarios, disabling the cache takes precedence over setting a cache location.

    + +

    New Rules

    + +
      +
    • +

      The new Java rule MissingOverride +(category bestpractices) detects overridden and implemented methods, which are not marked with the +@Override annotation. Annotating overridden methods with @Override ensures at compile time that +the method really overrides one, which helps refactoring and clarifies intent.

      +
    • +
    • +

      The new Java rule UnnecessaryAnnotationValueElement +(category codestyle) detects annotations with a single element (value) that explicitely names it. +That is, doing @SuppressWarnings(value = "unchecked") would be flagged in favor of +@SuppressWarnings("unchecked").

      +
    • +
    • +

      The new Java rule ControlStatementBraces +(category codestyle) enforces the presence of braces on control statements where they are optional. +Properties allow to customize which statements are required to have braces. This rule replaces the now +deprecated rules WhileLoopMustUseBraces, ForLoopMustUseBraces, IfStmtMustUseBraces, and +IfElseStmtMustUseBraces. More than covering the use cases of those rules, this rule also supports +do ... while statements and case labels of switch statements (disabled by default).

      +
    • +
    + +

    Modified Rules

    + +
      +
    • +

      The Java rule CommentContentRule (java-documentation) previously had the property wordsAreRegex. But this +property never had been implemented and is removed now.

      +
    • +
    • +

      The Java rule UnusedPrivateField (java-bestpractices) now has a new ignoredAnnotations property +that allows to configure annotations that imply the field should be ignored. By default @java.lang.Deprecated +and @javafx.fxml.FXML are ignored.

      +
    • +
    • +

      The Java rule UnusedPrivateMethod (java-bestpractices) now has a new ignoredAnnotations property +that allows to configure annotations that imply the method should be ignored. By default @java.lang.Deprecated +is ignored.

      +
    • +
    • +

      The Java rule ImmutableField (java-design) now has a new ignoredAnnotations property +that allows to configure annotations that imply the method should be ignored. By default several lombok +annotations are ignored

      +
    • +
    • +

      The Java rule SingularField (java-design) now has a new ignoredAnnotations property +that allows to configure annotations that imply the method should be ignored. By default several lombok +annotations are ignored

      +
    • +
    + +

    Deprecated Rules

    + +
      +
    • The Java rules WhileLoopMustUseBraces, ForLoopMustUseBraces, IfStmtMustUseBraces, and IfElseStmtMustUseBraces +are deprecated. They will be replaced by the new rule ControlStatementBraces, in the category codestyle.
    • +
    + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #928: [core] PMD build failure on Windows
      • +
      +
    • +
    • java-bestpracrtices +
        +
      • #907: [java] UnusedPrivateField false-positive with @FXML
      • +
      • #963: [java] ArrayIsStoredDirectly not triggered from variadic functions
      • +
      +
    • +
    • java-codestyle +
        +
      • #974: [java] Merge *StmtMustUseBraces rules
      • +
      • #983: [java] Detect annotations with single value element
      • +
      +
    • +
    • java-design +
        +
      • #832: [java] AvoidThrowingNullPointerException documentation suggestion
      • +
      • #837: [java] CFGs of declared but not called lambdas are treated as parts of an enclosing method’s CFG
      • +
      • #839: [java] SignatureDeclareThrowsException’s IgnoreJUnitCompletely property not honored for constructors
      • +
      • #968: [java] UseUtilityClassRule reports false positive with lombok NoArgsConstructor
      • +
      +
    • +
    • documentation +
        +
      • #978: [core] Broken link in CONTRIBUTING.md
      • +
      • #992: [core] Include info about rule doc generation in “Writing Documentation” md page
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • +

      A new CLI switch, -no-cache, disables incremental analysis and the related suggestion. This overrides the + -cache option. The corresponding Ant task parameter is noCache.

      +
    • +
    • +

      The static method PMDParameters.transformParametersIntoConfiguration(PMDParameters) is now deprecated, +for removal in 7.0.0. The new instance method PMDParameters.toConfiguration() replaces it.

      +
    • +
    • +

      The method ASTConstructorDeclaration.getParameters() has been deprecated in favor of the new method +getFormalParameters(). This method is available for both ASTConstructorDeclaration and +ASTMethodDeclaration.

      +
    • +
    + +

    External Contributions

    + +
      +
    • #941: [java] Use char notation to represent a character to improve performance - reudismam
    • +
    • #943: [java] UnusedPrivateField false-positive with @FXML - BBG
    • +
    • #951: [java] Add ignoredAnnotations property to unusedPrivateMethod rule - BBG
    • +
    • #952: [java] SignatureDeclareThrowsException’s IgnoreJUnitCompletely property not honored for constructors - BBG
    • +
    • #958: [java] Refactor how we ignore annotated elements in rules - BBG
    • +
    • #965: [java] Make Varargs trigger ArrayIsStoredDirectly - Stephen
    • +
    • #967: [doc] Issue 959: fixed broken link to XPath Rule Tutorial - Andrey Mochalov
    • +
    • #969: [java] Issue 968 Add logic to handle lombok private constructors with utility classes - Kirk Clemens
    • +
    • #970: [java] Fixed inefficient use of keySet iterator instead of entrySet iterator - Andrey Mochalov
    • +
    • #984: [java] issue983 Add new UnnecessaryAnnotationValueElement rule - Kirk Clemens
    • +
    • #989: [core] Update Contribute.md to close Issue #978 - Bolarinwa Saheed Olayemi
    • +
    • #990: [java] Updated Doc on AvoidThrowingNullPointerException to close Issue #832 - Bolarinwa Saheed Olayemi
    • +
    • #993: [core] Update writing_documentation.md to fix Issue #992 - Bolarinwa Saheed Olayemi
    • +
    + +

    25-February-2018 - 6.1.0

    + +

    The PMD team is pleased to announce PMD 6.1.0.

    + +

    This is a minor release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Designer UI

    + +

    The Designer now supports configuring properties for XPath based rule development. +The Designer is still under development and any feedback is welcome.

    + +

    You can start the designer via run.sh designer or designer.bat.

    + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #569: [core] XPath support requires specific toString implementations
      • +
      • #795: [cpd] java.lang.OutOfMemoryError
      • +
      • #848: [doc] Test failures when building pmd-doc under Windows
      • +
      • #872: [core] NullPointerException at FileDataSource.glomName()
      • +
      • #854: [ci] Use Java9 for building PMD
      • +
      +
    • +
    • doc +
        +
      • #791: [doc] Documentation site reorganisation
      • +
      • #891: [doc] Apex @SuppressWarnings should use single quotes instead of double quotes
      • +
      • #909: [doc] Please add new PMD Eclipse Plugin to tool integration section
      • +
      +
    • +
    • java +
        +
      • #825: [java] Excessive*Length ignores too much
      • +
      • #888: [java] ParseException occurs with valid ‘<>’ in Java 1.8 mode
      • +
      • #920: [java] Update valid identifiers in grammar
      • +
      +
    • +
    • java-bestpractices +
        +
      • #784: [java] ForLoopCanBeForeach false-positive
      • +
      • #925: [java] UnusedImports false positive for static import
      • +
      +
    • +
    • java-design +
        +
      • #855: [java] ImmutableField false-positive with lambdas
      • +
      +
    • +
    • java-documentation +
        +
      • #877: [java] CommentRequired valid rule configuration causes PMD error
      • +
      +
    • +
    • java-errorprone +
        +
      • #885: [java] CompareObjectsWithEqualsRule trigger by enum1 != enum2
      • +
      +
    • +
    • java-performance +
        +
      • #541: [java] ConsecutiveLiteralAppends with types other than string
      • +
      +
    • +
    • scala +
        +
      • #853: [scala] Upgrade scala version to support Java 9
      • +
      +
    • +
    • xml +
        +
      • #739: [xml] IllegalAccessException when accessing attribute using Saxon on JRE 9
      • +
      +
    • +
    + +

    API Changes

    + +

    Changes to the Node interface

    + +

    The method getXPathNodeName is added to the Node interface, which removes the +use of the toString of a node to get its XPath element name (see #569). +A default implementation is provided in AbstractNode, to stay compatible +with existing implementors.

    + +

    The toString method of a Node is not changed for the time being, and still produces +the name of the XPath node. That behaviour may however change in future major releases, +e.g. to produce a more useful message for debugging.

    + +

    Changes to CPD renderers

    + +

    The interface net.sourceforge.pmd.cpd.Renderer has been deprecated. A new interface net.sourceforge.pmd.cpd.renderer.CPDRenderer +has been introduced to replace it. The main difference is that the new interface is meant to render directly to a java.io.Writer +rather than to a String. This allows to greatly reduce the memory footprint of CPD, as on large projects, with many duplications, +it was causing OutOfMemoryErrors (see #795).

    + +

    net.sourceforge.pmd.cpd.FileReporter has also been deprecated as part of this change, as it’s no longer needed.

    + +

    External Contributions

    + + + +

    21-January-2018 - 6.0.1

    + +

    The PMD team is pleased to announce PMD 6.0.1.

    + +

    This is a bug fixing release.

    + +

    Table Of Contents

    + + + +

    Additional information about the new introduced rule categories

    + +

    With the release of PMD 6.0.0, all rules have been sorted into one of the following eight categories:

    + +
      +
    1. Best Practices: These are rules which enforce generally accepted best practices.
    2. +
    3. Code Style: These rules enforce a specific coding style.
    4. +
    5. Design: Rules that help you discover design issues.
    6. +
    7. Documentation: These rules are related to code documentation.
    8. +
    9. Error Prone: Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    10. +
    11. Multithreading: These are rules that flag issues when dealing with multiple threads of execution.
    12. +
    13. Performance: Rules that flag suboptimal code.
    14. +
    15. Security: Rules that flag potential security flaws.
    16. +
    + +

    Please note, that not every category in every language may have a rule. There might be categories with no +rules at all, such as category/java/security.xml, which has currently no rules. +There are even languages, which only have rules of one category (e.g. category/xml/errorprone.xml).

    + +

    You can find the information about available rules in the generated rule documentation, available +at https://pmd.github.io/6.0.1/.

    + +

    In order to help migrate to the new category scheme, the new name for the old, deprecated rule names will +be logged as a warning. See PR #865. Please note, that the deprecated +rule names will keep working throughout PMD 6. You can upgrade to PMD 6 without the immediate need +to migrate your current ruleset. That backwards compatibility will be maintained until PMD 7.0.0 is released.

    + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #842: [core] Use correct java bootclasspath for compiling
      • +
      +
    • +
    • apex-errorprone +
        +
      • #792: [apex] AvoidDirectAccessTriggerMap incorrectly detects array access in classes
      • +
      +
    • +
    • apex-security +
        +
      • #788: [apex] Method chaining breaks ApexCRUDViolation
      • +
      +
    • +
    • doc +
        +
      • #782: [doc] Wrong information in the Release Notes about the Security ruleset
      • +
      • #794: [doc] Broken documentation links for 6.0.0
      • +
      +
    • +
    • java +
        +
      • #793: [java] Parser error with private method in nested classes in interfaces
      • +
      • #814: [java] UnsupportedClassVersionError is failure instead of a warning
      • +
      • #831: [java] StackOverflow in JavaTypeDefinitionSimple.toString
      • +
      +
    • +
    • java-bestpractices +
        +
      • #783: [java] GuardLogStatement regression
      • +
      • #800: [java] ForLoopCanBeForeach NPE when looping on this object
      • +
      +
    • +
    • java-codestyle +
        +
      • #817: [java] UnnecessaryModifierRule crashes on valid code
      • +
      +
    • +
    • java-design +
        +
      • #785: [java] NPE in DataClass rule
      • +
      • #812: [java] Exception applying rule DataClass
      • +
      • #827: [java] GodClass crashes with java.lang.NullPointerException
      • +
      +
    • +
    • java-performance +
        +
      • #841: [java] InsufficientStringBufferDeclaration NumberFormatException
      • +
      +
    • +
    • java-typeresolution +
        +
      • #866: [java] rulesets/java/typeresolution.xml lists non-existent rules
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • The constant net.sourceforge.pmd.PMD.VERSION has been deprecated and will be removed with PMD 7.0.0. +Please use net.sourceforge.pmd.PMDVersion.VERSION instead.
    • +
    + +

    External Contributions

    + + + +

    15-December-2017 - 6.0.0

    + +

    The PMD team is pleased to announce PMD 6.0.0.

    + +

    This is a major release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    New Rule Designer

    + +

    Thanks to Clément Fournier, we now have a new rule designer GUI, which +is based on JavaFX. It replaces the old designer and can be started via

    + +
      +
    • bin/run.sh designer (on Unix-like platform such as Linux and Mac OS X)
    • +
    • bin\designer.bat (on Windows)
    • +
    + +

    Note: At least Java8 is required for the designer. The old designer is still available +as designerold but will be removed with the next major release.

    + +

    Java 9 support

    + +

    The Java grammar has been updated to support analyzing Java 9 projects:

    + +
      +
    • private methods in interfaces are possible
    • +
    • The underscore “_” is considered an invalid identifier
    • +
    • Diamond operator for anonymous classes
    • +
    • The module declarations in module-info.java can be parsed
    • +
    • Concise try-with-resources statements are supported
    • +
    + +

    Java 9 support is enabled by default. You can switch back to an older java version +via the command line, e.g. -language java -version 1.8.

    + +

    Revamped Apex CPD

    + +

    We are now using the Apex Jorje Lexer to tokenize Apex code for CPD. This change means:

    + +
      +
    • All comments are now ignored for CPD. This is consistent with how other languages such as Java and Groovy work.
    • +
    • Tokenization honors the language specification, which improves accuracy.
    • +
    + +

    CPD will therefore have less false positives and false negatives.

    + +

    Java Type Resolution

    + +

    As part of Google Summer of Code 2017, Bendegúz Nagy worked on type resolution +for Java. For this release he has extended support for method calls for both instance and static methods.

    + +

    Method shadowing and overloading are supported, as are varargs. However, the selection of the target method upon +the presence of generics and type inference is still work in progress. Expect it in forecoming releases.

    + +

    As for fields, the basic support was in place for release 5.8.0, but has now been expanded to support static fields.

    + +

    Metrics Framework

    + +

    As part of Google Summer of Code 2017, Clément Fournier is worked +on the new metrics framework for object-oriented metrics.

    + +

    There are already a couple of metrics (e.g. ATFD, WMC, Cyclo, LoC) implemented. More metrics are planned. +Based on those metrics, rules like “GodClass” detection could be implemented more easily. +The following rules benefit from the metrics framework: NcssCount (java), NPathComplexity (java), +CyclomaticComplexity (both java and apex).

    + +

    The Metrics framework has been abstracted and is available in pmd-core for other languages. With this +PMD release, the metrics framework is supported for both Java and Apex.

    + +

    Error Reporting

    + +

    A number of improvements on error reporting have taken place, meaning changes to some of the report formats.

    + +

    Also of note, the xml report now provides a XML Schema definition, allowing easier parsing and validation.

    + +
    Processing Errors
    + +

    Processing errors can now provide not only the message previously included on some reports, but also a full stacktrace. +This will allow better error reports when providing feedback to the PMD team and help in debugging issues.

    + +

    The report formats providing full stacktrace of errors are:

    + +
      +
    • html
    • +
    • summaryhtml
    • +
    • textcolor
    • +
    • vbhtml
    • +
    • xml
    • +
    + +
    Configuration Errors
    + +

    For a long time reports have been notified of configuration errors on rules, but they have remained hidden. +On a push to make these more evident to users, and help them get the best results out of PMD, we have started +to include them on the reports.

    + +

    So far, only reports that include processing errors are showing configuration errors. In other words, the report formats +providing configuration error reporting are:

    + +
      +
    • csv
    • +
    • html
    • +
    • summaryhtml
    • +
    • text
    • +
    • textcolor
    • +
    • vbhtml
    • +
    • xml
    • +
    + +

    As we move forward we will be able to detect and report more configuration errors (ie: incomplete auxclasspath) +and include them to such reports.

    + +

    Apex Rule Suppression

    + +

    Apex violations can now be suppressed very similarly to how it’s done in Java, by making use of a +@SuppressWarnings annotation.

    + +

    Supported syntax includes:

    + +
    @SupressWarnings('PMD') // to supress all Apex rules
    +@SupressWarnings('all') // to supress all Apex rules
    +@SupressWarnings('PMD.ARuleName') // to supress only the rule named ARuleName
    +@SupressWarnings('PMD.ARuleName, PMD.AnotherRuleName') // to supress only the rule named ARuleName or AnotherRuleName
    +
    + +

    Notice this last scenario is slightly different to the Java syntax. This is due to differences in the Apex grammar for annotations.

    + +

    Rule Categories

    + +

    All built-in rules have been sorted into one of eight categories:

    + +
      +
    1. Best Practices: These are rules which enforce generally accepted best practices.
    2. +
    3. Code Style: These rules enforce a specific coding style.
    4. +
    5. Design: Rules that help you discover design issues.
    6. +
    7. Documentation: These rules are related to code documentation.
    8. +
    9. Error Prone: Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    10. +
    11. Multithreading: These are rules that flag issues when dealing with multiple threads of execution.
    12. +
    13. Performance: Rules that flag suboptimal code.
    14. +
    15. Security: Rules that flag potential security flaws.
    16. +
    + +

    These categories help you to find rules and figure out the relevance and impact for your project.

    + +

    All rules have been moved accordingly, e.g. the rule “JumbledIncrementer”, which was previously defined in the +ruleset “java-basic” has now been moved to the “Error Prone” category. The new rule reference to be used is +<rule ref="category/java/errorprone.xml/JumbledIncrementer"/>.

    + +

    The old rulesets like “java-basic” are still kept for backwards-compatibility but will be removed eventually. +The rule reference documentation has been updated to reflect these changes.

    + +

    New Rules

    + +
      +
    • +

      The new Java rule NcssCount (category design) replaces the three rules “NcssConstructorCount”, “NcssMethodCount”, +and “NcssTypeCount”. The new rule uses the metrics framework to achieve the same. It has two properties, to +define the report level for method and class sizes separately. Constructors and methods are considered the same.

      +
    • +
    • +

      The new Java rule DoNotExtendJavaLangThrowable (category errorprone) is a companion for the +java-strictexception.xml/DoNotExtendJavaLangError, detecting direct extensions of java.lang.Throwable.

      +
    • +
    • +

      The new Java rule ForLoopCanBeForeach (category errorprone) helps to identify those for-loops that can +be safely refactored into for-each-loops available since java 1.5.

      +
    • +
    • +

      The new Java rule AvoidFileStream (category performance) helps to identify code relying on FileInputStream / FileOutputStream +which, by using a finalizer, produces extra / unnecessary overhead to garbage collection, and should be replaced with +Files.newInputStream / Files.newOutputStream available since java 1.7.

      +
    • +
    • +

      The new Java rule DataClass (category design) detects simple data-holders without behaviour. This might indicate +that the behaviour is scattered elsewhere and the data class exposes the internal data structure, +which breaks encapsulation.

      +
    • +
    • +

      The new Apex rule AvoidDirectAccessTriggerMap (category errorprone) helps to identify direct array access to triggers, +which can produce bugs by either accessing non-existing indexes, or leaving them out. You should use for-each-loops +instead.

      +
    • +
    • +

      The new Apex rule AvoidHardcodingId (category errorprone) detects hardcoded strings that look like identifiers +and flags them. Record IDs change between environments, meaning hardcoded ids are bound to fail under a different +setup.

      +
    • +
    • +

      The new Apex rule CyclomaticComplexity (category design) detects overly complex classes and methods. The +report threshold can be configured separately for classes and methods.

      +
    • +
    • A whole bunch of new rules has been added to Apex. They all fit into the category errorprone. +The 5 rules are migrated for Apex from the equivalent Java rules and include: +
        +
      • EmptyCatchBlock to detect catch blocks completely ignoring exceptions.
      • +
      • EmptyIfStmt for if blocks with no content, that can be safely removed.
      • +
      • EmptyTryOrFinallyBlock for empty try / finally blocks that can be safely removed.
      • +
      • EmptyWhileStmt for empty while loops that can be safely removed.
      • +
      • EmptyStatementBlock for empty code blocks that can be safely removed.
      • +
      +
    • +
    • The new Apex rule AvoidSoslInLoops (category performance) is the companion of the old +AvoidSoqlInLoops rule, flagging SOSL (Salesforce Object Search Language) queries when within +loops, to avoid governor issues, and hitting the database too often.
    • +
    + +

    Modified Rules

    + +
      +
    • +

      The Java rule UnnecessaryFinalModifier (category codestyle, former ruleset java-unnecessarycode) +has been merged into the rule UnnecessaryModifier. As part of this, the rule has been revamped to detect more cases. +It will now flag anonymous class’ methods marked as final (can’t be overridden, so it’s pointless), along with +final methods overridden / defined within enum instances. It will also flag final modifiers on try-with-resources.

      +
    • +
    • +

      The Java rule UnnecessaryParentheses (category codestyle, former ruleset java-controversial) +has been merged into UselessParentheses (category codestyle, former ruleset java-unnecessary). +The rule covers all scenarios previously covered by either rule.

      +
    • +
    • +

      The Java rule UncommentedEmptyConstructor (category documentation, former ruleset java-design) + will now ignore empty constructors annotated with javax.inject.Inject.

      +
    • +
    • +

      The Java rule AbstractClassWithoutAnyMethod (category bestpractices, former ruleset java-design) +will now ignore classes annotated with com.google.auto.value.AutoValue.

      +
    • +
    • +

      The Java rule GodClass (category design', former ruleset java-design`) has been revamped to use +the new metrics framework.

      +
    • +
    • +

      The Java rule LooseCoupling (category bestpractices, former ruleset java-coupling) has been +replaced by the typeresolution-based implementation.

      +
    • +
    • +

      The Java rule CloneMethodMustImplementCloneable (category errorprone, former ruleset java-clone) +has been replaced by the typeresolution-based +implementation and is now able to detect cases if a class implements or extends a Cloneable class/interface.

      +
    • +
    • +

      The Java rule UnusedImports (category bestpractices, former ruleset java-imports) has been +replaced by the typeresolution-based +implementation and is now able to detect unused on-demand imports.

      +
    • +
    • +

      The Java rule SignatureDeclareThrowsException (category design, former ruleset ‘java-strictexception’) +has been replaced by the +typeresolution-based implementation. It has a new property IgnoreJUnitCompletely, which allows all +methods in a JUnit testcase to throw exceptions.

      +
    • +
    • +

      The Java rule NPathComplexity (category design, former ruleset java-codesize) has been revamped +to use the new metrics framework. +Its report threshold can be configured via the property reportLevel, which replaces the now +deprecated property minimum.

      +
    • +
    • +

      The Java rule CyclomaticComplexity (category design, former ruleset java-codesize) has been +revamped to use the new metrics framework. +Its report threshold can be configured via the properties classReportLevel and methodReportLevel separately. +The old property reportLevel, which configured the level for both total class and method complexity, +is deprecated.

      +
    • +
    • The Java rule CommentRequired (category documentation, former ruleset java-comments) +has been revamped to include 2 new properties: +
        +
      • accessorCommentRequirement to specify documentation requirements for getters and setters (default to ignored)
      • +
      • methodWithOverrideCommentRequirement to specify documentation requirements for methods annotated with @Override (default to ignored)
      • +
      +
    • +
    • +

      The Java rule EmptyCatchBlock (category errorprone, former ruleset java-empty) has been changed to ignore +exceptions named ignore or expected by default. You can still override this behaviour by setting the allowExceptionNameRegex property.

      +
    • +
    • The Java rule OptimizableToArrayCall (category performance, former ruleset design) has been +modified to fit for the current JVM implementations: It basically detects now the opposite and suggests to +use Collection.toArray(new E[0]) with a zero-sized array. +See Arrays of Wisdom of the Ancients.
    • +
    + +

    Deprecated Rules

    + +
      +
    • +

      The Java rules NcssConstructorCount, NcssMethodCount, and NcssTypeCount (ruleset java-codesize) have been +deprecated. They will be replaced by the new rule NcssCount in the category design.

      +
    • +
    • +

      The Java rule LooseCoupling in ruleset java-typeresolution is deprecated. Use the rule with the same name +from category bestpractices instead.

      +
    • +
    • +

      The Java rule CloneMethodMustImplementCloneable in ruleset java-typeresolution is deprecated. Use the rule with +the same name from category errorprone instead.

      +
    • +
    • +

      The Java rule UnusedImports in ruleset java-typeresolution is deprecated. Use the rule with +the same name from category bestpractices instead.

      +
    • +
    • +

      The Java rule SignatureDeclareThrowsException in ruleset java-typeresolution is deprecated. Use the rule +with the same name from category design instead.

      +
    • +
    • +

      The Java rule EmptyStaticInitializer in ruleset java-empty is deprecated. Use the rule EmptyInitializer +from the category errorprone, which covers both static and non-static empty initializers.`

      +
    • +
    • +

      The Java rules GuardDebugLogging (ruleset java-logging-jakarta-commons) and GuardLogStatementJavaUtil +(ruleset java-logging-java) have been deprecated. Use the rule GuardLogStatement from the +category bestpractices, which covers all cases regardless of the logging framework.

      +
    • +
    + +

    Removed Rules

    + +
      +
    • The deprecated Java rule UseSingleton has been removed from the ruleset java-design. The rule has been renamed +long time ago to UseUtilityClass (category design).
    • +
    + +

    Java Symbol Table

    + +

    A bug in symbol table prevented +the symbol table analysis to properly match primitive arrays types. The issue affected the java-unsedcode/UnusedPrivateMethod +rule, but other rules may now produce improved results as consequence of this fix.

    + +

    Apex Parser Update

    + +

    The Apex parser version was bumped, from 1.0-sfdc-187 to 210-SNAPSHOT. This update let us take full advantage +of the latest improvements from Salesforce, but introduces some breaking changes:

    + +
      +
    • BlockStatements are now created for all control structures, even if no brace is used. We have therefore added +a hasCurlyBrace method to differentiate between both scenarios.
    • +
    • New AST node types are available. In particular CastExpression, ConstructorPreamble, IllegalStoreExpression, +MethodBlockStatement, Modifier, MultiStatement, NestedExpression, NestedStoreExpression, +NewKeyValueObjectExpression and StatementExecuted
    • +
    • Some nodes have been removed. Such is the case of TestNode, DottedExpression and NewNameValueObjectExpression +(replaced by NewKeyValueObjectExpression)
    • +
    + +

    All existing rules have been updated to reflect these changes. If you have custom rules, be sure to update them.

    + +

    For more info about the included Apex parser, see the new pmd module “pmd-apex-jorje”, which packages and provides +the parser as a binary.

    + +

    Incremental Analysis

    + +

    The incremental analysis feature first introduced in PMD 5.6.0 has been enhanced. A few minor issues have been fixed, +and several improvements have been performed to make it more accurate.

    + +

    The cache will now detect changes to the JARs referenced in the auxclasspath instead of simply looking at their paths +and order. This means that if you are referencing a JAR you are overwriting in some way, the incremental analysis can +now detect it and invalidate it’s cache to avoid false reports.

    + +

    Similarly, any changes to the execution classpath of PMD will invalidate the cache. This means that if you have custom +rules packaged in a jar, any changes to it will invalidate the cache automatically.

    + +

    We have also improved logging on the analysis code, allowing better insight into how the cache is performing, +under debug / verbose builds you can even see individual hits / misses to the cache (and the reason for any miss!)

    + +

    Finally, as this feature keeps maturing, we are gently pushing this forward. If not using incremental analysis, +a warning will now be produced suggesting users to adopt it for better performance.

    + +

    Rule and Report Properties

    + +

    The implementation around the properties support for rule properties and report properties has been revamped +to be fully typesafe. Along with that change, the support classes have been moved into an own +package net.sourceforge.pmd.properties. While there is no change necessary in the ruleset XML files, +when using/setting values for rules, there are adjustments necessary when declaring properties in Java-implemented +rules.

    + +

    Rule properties can be declared both for Java based rules and XPath rules. +This is now very well documented in Working with properties.

    + +

    With PMD 6.0.0, multivalued properties are now also possible with XPath rules.

    + +

    Fixed Issues

    + +
      +
    • all +
        +
      • #394: [core] PMD exclude rules are failing with IllegalArgumentException with non-default minimumPriority
      • +
      • #532: [core] security concerns on URL-based rulesets
      • +
      • #538: [core] Provide an XML Schema for XML reports
      • +
      • #600: [core] Nullpointer while creating cache File
      • +
      • #604: [core] Incremental analysis should detect changes to jars in classpath
      • +
      • #608: [core] Add DEBUG log when applying incremental analysis
      • +
      • #618: [core] Incremental Analysis doesn’t close file correctly on Windows upon a cache hit
      • +
      • #643: [core] PMD Properties (dev-properties) breaks markup on CodeClimateRenderer
      • +
      • #680: [core] Isolate classloaders for runtime and auxclasspath
      • +
      • #762: [core] Remove method and file property from available property descriptors for XPath rules
      • +
      • #763: [core] Turn property descriptor util into an enum and enrich its interface
      • +
      +
    • +
    • apex +
        +
      • #265: [apex] Make Rule suppression work
      • +
      • #488: [apex] Use Apex lexer for CPD
      • +
      • #489: [apex] Update Apex compiler
      • +
      • #500: [apex] Running through CLI shows jorje optimization messages
      • +
      • #605: [apex] java.lang.NoClassDefFoundError in the latest build
      • +
      • #637: [apex] Avoid SOSL in loops
      • +
      • #760: [apex] EmptyStatementBlock complains about missing rather than empty block
      • +
      • #766: [apex] Replace old Jorje parser with new one
      • +
      • #768: [apex] java.lang.NullPointerException from PMD
      • +
      +
    • +
    • cpp +
        +
      • #448: [cpp] Write custom CharStream to handle continuation characters
      • +
      +
    • +
    • java +
        +
      • #1454: [java] OptimizableToArrayCall is outdated and invalid in current JVMs
      • +
      • #1513: [java] Remove deprecated rule UseSingleton
      • +
      • #328: [java] java.lang.ClassFormatError: Absent Code attribute in method that is not native or abstract in class file javax/servlet/jsp/PageContext
      • +
      • #487: [java] Fix typeresolution for anonymous extending object
      • +
      • #496: [java] processing error on generics inherited from enclosing class
      • +
      • #510: [java] Typeresolution fails on a simple primary when the source is loaded from a class literal
      • +
      • #527: [java] Lombok getter annotation on enum is not recognized correctly
      • +
      • #534: [java] NPE in MethodTypeResolution for static methods
      • +
      • #603: [core] incremental analysis should invalidate upon Java rule plugin changes
      • +
      • #650: [java] ProcesingError analyzing code under 5.8.1
      • +
      • #732: [java] LinkageError with aux classpath
      • +
      +
    • +
    • java-basic +
        +
      • #565: [java] False negative on DontCallThreadRun when extending Thread
      • +
      +
    • +
    • java-comments +
        +
      • #396: [java] CommentRequired: add properties to ignore @Override method and getters / setters
      • +
      • #536: [java] CommentDefaultAccessModifierRule ignores constructors
      • +
      +
    • +
    • java-controversial +
        +
      • #388: [java] controversial.AvoidLiteralsInIfCondition 0.0 false positive
      • +
      • #408: [java] DFA not analyzing asserts
      • +
      • #537: [java] UnnecessaryParentheses fails to detect obvious scenario
      • +
      +
    • +
    • java-design +
        +
      • #357: [java] UncommentedEmptyConstructor consider annotations on Constructor
      • +
      • #438: [java] Relax AbstractClassWithoutAnyMethod when class is annotated by @AutoValue
      • +
      • #590: [java] False positive on MissingStaticMethodInNonInstantiatableClass
      • +
      +
    • +
    • java-logging + * #457: [java] Merge all log guarding rules + * #721: [java] NPE in PMD 5.8.1 InvalidSlf4jMessageFormat
    • +
    • java-sunsecure +
        +
      • #468: [java] ArrayIsStoredDirectly false positive
      • +
      +
    • +
    • java-unusedcode +
        +
      • #521: [java] UnusedPrivateMethod returns false positives with primitive data type in map argument
      • +
      +
    • +
    • java-unnecessarycode +
        +
      • #412: [java] java-unnecessarycode/UnnecessaryFinalModifier missing cases
      • +
      • #676: [java] java-unnecessarycode/UnnecessaryFinalModifier on try-with-resources
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • +

      The class net.sourceforge.pmd.lang.dfa.NodeType has been converted to an enum. +All node types are enum members now instead of int constants. The names for node types are retained.

      +
    • +
    • +

      The Properties API (rule and report properties) has been revamped to be fully typesafe. This is everything +around net.sourceforge.pmd.properties.PropertyDescriptor.

      + +

      Note: All classes related to properties have been moved into the package net.sourceforge.pmd.properties.

      +
    • +
    • +

      The rule classes net.sourceforge.pmd.lang.apex.rule.apexunit.ApexUnitTestClassShouldHaveAsserts +and net.sourceforge.pmd.lang.apex.rule.apexunit.ApexUnitTestShouldNotUseSeeAllDataTrue have been +renamed to ApexUnitTestClassShouldHaveAssertsRule and ApexUnitTestShouldNotUseSeeAllDataTrueRule, +respectively. This is to comply with the naming convention, that each rule class should be suffixed with “Rule”.

      + +

      This change has no impact on custom rulesets, since the rule names themselves didn’t change.

      +
    • +
    • +

      The never implemented method PMD.processFiles(PMDConfiguration, RuleSetFactory, Collection<File>, RuleContext, ProgressMonitor) along with the interface ProgressMonitor has been removed.

      +
    • +
    • +

      The method PMD.setupReport(RuleSets, RuleContext, String) is gone. It was used to report dysfunctional +rules. But PMD does this now automatically before processing the files, so there is no need for this +method anymore.

      +
    • +
    • All APIs deprecated in older versions are now removed. This includes: +
        +
      • Renderer.getPropertyDefinitions
      • +
      • AbstractRenderer.defineProperty(String, String)
      • +
      • AbstractRenderer.propertyDefinitions
      • +
      • ReportListener
      • +
      • Report.addListener(ReportListener)
      • +
      • SynchronizedReportListener
      • +
      • CPDConfiguration.CPDConfiguration(int, Language, String)
      • +
      • CPDConfiguration.getRendererFromString(String)
      • +
      • StreamUtil
      • +
      • StringUtil.appendXmlEscaped(StringBuilder, String)
      • +
      • StringUtil.htmlEncode(String)
      • +
      +
    • +
    • Several methods in net.sourceforge.pmd.util.CollectionUtil have been deprecated and will be removed in PMD 7.0.0. In particular: +
        +
      • CollectionUtil.addWithoutDuplicates(T[], T)
      • +
      • CollectionUtil.addWithoutDuplicates(T[], T[])
      • +
      • CollectionUtil.areSemanticEquals(T[], T[])
      • +
      • CollectionUtil.areEqual(Object, Object)
      • +
      • CollectionUtil.arraysAreEqual(Object, Object)
      • +
      • CollectionUtil.valuesAreTransitivelyEqual(Object[], Object[])
      • +
      +
    • +
    • Several methods in net.sourceforge.pmd.util.StringUtil have been deprecated and will be removed in PMD 7.0.0. In particular: +
        +
      • StringUtil.startsWithAny(String, String[])
      • +
      • StringUtil.isNotEmpty(String)
      • +
      • StringUtil.isEmpty(String)
      • +
      • StringUtil.isMissing(String)
      • +
      • StringUtil.areSemanticEquals(String, String)
      • +
      • StringUtil.replaceString(String, String, String)
      • +
      • StringUtil.replaceString(String, char, String)
      • +
      • StringUtil.substringsOf(String, char)
      • +
      • StringUtil.substringsOf(String, String)
      • +
      • StringUtil.asStringOn(StringBuffer, Iterator, String)
      • +
      • StringUtil.asStringOn(StringBuilder, Object[], String)
      • +
      • StringUtil.lpad(String, int)
      • +
      +
    • +
    • +

      The class net.sourceforge.pmd.lang.java.typeresolution.typedefinition.JavaTypeDefinition is now abstract, and has been enhanced +to provide several new methods.

      +
    • +
    • +

      The constructor of net.sourceforge.pmd.RuleSetFactory, which took a ClassLoader is deprecated. +Please use the alternative constructor with the net.sourceforge.pmd.util.ResourceLoader instead.

      +
    • +
    • The following GUI related classes have been deprecated and will be removed in PMD 7.0.0. +The tool “bgastviewer”, that could be started via the script bgastviewer.bat or run.sh bgastviewer is +deprecated, too, and will be removed in PMD 7.0.0. +Both the “old designer” and “bgastviewer” are replaced by the New Rule Designer. +
        +
      • net.sourceforge.pmd.util.designer.CodeEditorTextPane
      • +
      • net.sourceforge.pmd.util.designer.CreateXMLRulePanel
      • +
      • net.sourceforge.pmd.util.designer.Designer
      • +
      • net.sourceforge.pmd.util.designer.DFAPanel
      • +
      • net.sourceforge.pmd.util.designer.LineGetter
      • +
      • net.sourceforge.pmd.util.viewer.Viewer
      • +
      • net.sourceforge.pmd.util.viewer.gui.ActionCommands
      • +
      • net.sourceforge.pmd.util.viewer.gui.ASTPanel
      • +
      • net.sourceforge.pmd.util.viewer.gui.EvaluationResultsPanel
      • +
      • net.sourceforge.pmd.util.viewer.gui.MainFrame
      • +
      • net.sourceforge.pmd.util.viewer.gui.ParseExceptionHandler
      • +
      • net.sourceforge.pmd.util.viewer.gui.SourceCodePanel
      • +
      • net.sourceforge.pmd.util.viewer.gui.XPathPanel
      • +
      • net.sourceforge.pmd.util.viewer.gui.menu.ASTNodePopupMenu
      • +
      • net.sourceforge.pmd.util.viewer.gui.menu.AttributesSubMenu
      • +
      • net.sourceforge.pmd.util.viewer.gui.menu.SimpleNodeSubMenu
      • +
      • net.sourceforge.pmd.util.viewer.gui.menu.XPathFragmentAddingItem
      • +
      • net.sourceforge.pmd.util.viewer.model.ASTModel
      • +
      • net.sourceforge.pmd.util.viewer.model.AttributeToolkit
      • +
      • net.sourceforge.pmd.util.viewer.model.SimpleNodeTreeNodeAdapter
      • +
      • net.sourceforge.pmd.util.viewer.model.ViewerModel
      • +
      • net.sourceforge.pmd.util.viewer.model.ViewerModelEvent
      • +
      • net.sourceforge.pmd.util.viewer.model.ViewerModelListener
      • +
      • net.sourceforge.pmd.util.viewer.util.NLS
      • +
      +
    • +
    • The following methods in net.sourceforge.pmd.Rule have been deprecated and will be removed in PMD 7.0.0. +All methods are replaced by their bean-like counterparts +
        +
      • void setUsesDFA(). Use void setDfa(boolean) instead.
      • +
      • boolean usesDFA(). Use boolean isDfa() instead.
      • +
      • void setUsesTypeResolution(). Use void setTypeResolution(boolean) instead.
      • +
      • boolean usesTypeResolution(). Use boolean isTypeResolution() instead.
      • +
      • void setUsesMultifile(). Use void setMultifile(boolean) instead.
      • +
      • boolean usesMultifile(). Use boolean isMultifile() instead.
      • +
      • boolean usesRuleChain(). Use boolean isRuleChain() instead.
      • +
      +
    • +
    + +

    External Contributions

    + + + +

    01-July-2017 - 5.8.1

    + +

    The PMD team is pleased to announce PMD 5.8.1.

    + +

    This is a bug fixing release.

    + +

    Fixed Issues

    + +
      +
    • java +
        +
      • #471: [java] Error while processing class when EnumMap is used in PMD 5.8.0
      • +
      • #477: [core] NoClassDefFoundError under 5.8
      • +
      • #478: [core] Processing issues dealing with anonymous classes
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • The getGenericArgs() method introduced to TypeNode in 5.8.0 was removed. You can access to generics’ info through the JavaTypeDefinition object.
    • +
    • The JavaTypeDefinitionBuilder class introduced in 5.8.0 is not more. You can use factory methods available on JavaTypeDefinition
    • +
    + +

    External Contributions

    + +
      +
    • #472: [java] fix error with raw types, bug #471
    • +
    + +

    24-June-2017 - 5.8.0

    + +

    The PMD team is pleased to announce PMD 5.8.0.

    + +

    This is a minor release.

    + +

    New and noteworthy

    + +

    Java Type Resolution

    + +

    As part of Google Summer of Code 2017, Bendegúz Nagy has been working on completing type resolution for Java. +His progress so far has allowed to properly resolve, in addition to previously supported statements:

    + +
      +
    • References to this and super, even when qualified
    • +
    • References to fields, even when chained (ie: this.myObject.aField), and properly handling inheritance / shadowing
    • +
    + +

    Lambda parameter types where these are infered rather than explicit are still not supported. Expect future releases to do so.

    + +

    Metrics Framework

    + +

    As part of Google Summer of Code 2017, Clément Fournier has been working on +a new metrics framework for object-oriented metrics.

    + +

    The basic groundwork has been done already and with this release, including a first rule based on the +metrics framework as a proof-of-concept: The rule CyclomaticComplexity, currently in the temporary +ruleset java-metrics, uses the Cyclomatic Complexity metric to find overly complex code. +This rule will eventually replace the existing three CyclomaticComplexity rules that are currently +defined in the java-codesize ruleset (see also issue #445).

    + +

    Since this work is still in progress, the metrics API (package net.sourceforge.pmd.lang.java.oom) +is not finalized yet and is expected to change.

    + +

    Modified Rules

    + +
      +
    • +

      The Java rule UnnecessaryFinalModifier (ruleset java-unnecessary) now also reports on private methods marked as final. +Being private, such methods can’t be overriden, and therefore, the final keyword is redundant.

      +
    • +
    • +

      The Java rule PreserveStackTrace (ruleset java-design) has been relaxed to support the builder pattern on thrown exception. +This change may introduce some false positives if using the exception in non-orthodox ways for things other than setting the +root cause of the exception. Contact us if you find any such scenarios.

      +
    • +
    • +

      The ruleset java-junit now properly detects JUnit5, and rules are being adapted to the changes on it’s API. +This support is, however, still incomplete. Let us know of any uses we are still missing on the issue tracker

      +
    • +
    • +

      The Java rule EmptyTryBlock (ruleset java-empty) now allows empty blocks when using try-with-resources.

      +
    • +
    • +

      The Java rule EmptyCatchBlock (ruleset java-empty) now exposes a new property called allowExceptionNameRegex. +This allow to setup a regular expression for names of exceptions you wish to ignore for this rule. For instance, +setting it to ^(ignored|expected)$ would ignore all empty catch blocks where the catched exception is named +either ignored or expected. The default ignores no exceptions, being backwards compatible.

      +
    • +
    + +

    Deprecated Rules

    + +
      +
    • The three complexity rules CyclomaticComplexity, StdCyclomaticComplexity, ModifiedCyclomaticComplexity (ruleset java-codesize) have been deprecated. They will be eventually replaced +by a new CyclomaticComplexity rule based on the metrics framework. See also issue #445.
    • +
    + +

    Fixed Issues

    + +
      +
    • General +
        +
      • #380: [core] NPE in RuleSet.hashCode
      • +
      • #407: [web] Release date is not properly formatted
      • +
      • #429: [core] Error when running PMD from folder with space
      • +
      +
    • +
    • apex +
        +
      • #427: [apex] CPD error when parsing apex code from release 5.5.3
      • +
      +
    • +
    • cpp +
        +
      • #431: [cpp] CPD gives wrong duplication blocks for CPP code
      • +
      +
    • +
    • java +
        +
      • #414: [java] Java 8 parsing problem with annotations for wildcards
      • +
      • #415: [java] Parsing Error when having an Annotated Inner class
      • +
      • #417: [java] Parsing Problem with Annotation for Array Member Types
      • +
      +
    • +
    • java-design +
        +
      • #397: [java] ConstructorCallsOverridableMethodRule: false positive for method called from lambda expression
      • +
      • #410: [java] ImmutableField: False positive with lombok
      • +
      • #422: [java] PreserveStackTraceRule: false positive when using builder pattern
      • +
      +
    • +
    • java-empty +
        +
      • #413: [java] EmptyCatchBlock don’t fail when exception is named ignore / expected
      • +
      • #432: [java] EmptyTryBlock: false positive for empty try-with-resource
      • +
      +
    • +
    • java-imports: +
        +
      • #348: [java] imports/UnusedImport rule not considering static inner classes of imports
      • +
      +
    • +
    • java-junit +
        +
      • #428: [java] PMD requires public modifier on JUnit 5 test
      • +
      • #465: [java] NullPointerException in JUnitTestsShouldIncludeAssertRule
      • +
      +
    • +
    • java-logging: +
        +
      • #365: [java] InvalidSlf4jMessageFormat does not handle inline incrementation of arguments
      • +
      +
    • +
    • java-strictexceptions +
        +
      • #350: [java] Throwing Exception in method signature is fine if the method is overriding or implementing something
      • +
      +
    • +
    • java-typeresolution +
        +
      • #350: [java] Throwing Exception in method signature is fine if the method is overriding or implementing something
      • +
      +
    • +
    • java-unnecessary +
        +
      • #421: [java] UnnecessaryFinalModifier final in private method
      • +
      +
    • +
    • jsp +
        +
      • #311: [jsp] Parse error on HTML boolean attribute
      • +
      +
    • +
    + +

    External Contributions

    + +
      +
    • #406: [java] False positive with lambda in java-design/ConstructorCallsOverridableMethod
    • +
    • #409: [java] Groundwork for the upcoming metrics framework
    • +
    • #416: [java] FIXED: Java 8 parsing problem with annotations for wildcards
    • +
    • #418: [java] Type resolution: super and this keywords
    • +
    • #423: [java] Add field access type resolution in non-generic cases
    • +
    • #425: [java] False positive with builder pattern in java-design/PreserveStackTrace
    • +
    • #426: [java] UnnecessaryFinalModifier final in private method
    • +
    • #436: [java] Metrics framework tests and various improvements
    • +
    • #440: [core] Created ruleset schema 3.0.0 (to use metrics)
    • +
    • #443: [java] Optimize typeresolution, by skipping package and import declarations in visit(ASTName)
    • +
    • #444: [java] [typeresolution]: add support for generic fields
    • +
    • #451: [java] Metrics framework: first metrics + first rule
    • +
    + +

    20-Mai-2017 - 5.7.0

    + +

    The PMD team is pleased to announce PMD 5.7.0.

    + +

    This is a minor release.

    + +

    New and noteworthy

    + +

    Modified Rules

    + +
      +
    • +

      The rule “FieldDeclarationsShouldBeAtStartOfClass” of the java-design ruleset has a new property ignoreInterfaceDeclarations. +Setting this property to true ignores interface declarations, that precede fields. +Example usage:

      + + + + + + +
    • +
    + +

    Renderers

    + +
      +
    • Added the ‘empty’ renderer which will write nothing. Does not affect other behaviors, for example the command line PMD exit status +will still indicate whether violations were found.
    • +
    + +

    Fixed Issues

    + +
      +
    • General +
        +
      • #377: [core] Use maven wrapper and upgrade to maven 3.5.0
      • +
      • #376: [core] Improve build time on travis
      • +
      +
    • +
    • java +
        +
      • #378: [java] Parser Error for empty statements
      • +
      +
    • +
    • java-coupling +
        +
      • #1427: [java] Law of Demeter violations for the Builder pattern
      • +
      +
    • +
    • java-design +
        +
      • #345: [java] FieldDeclarationsShouldBeAtStartOfClass: Add ability to ignore interfaces
      • +
      • #389: [java] RuleSetCompatibility - not taking rename of UnusedModifier into account
      • +
      +
    • +
    • java-junit +
        +
      • #358: [java] Mockito verify method is not taken into account in JUnitTestsShouldIncludeAssert rule
      • +
      +
    • +
    • java-strings +
        +
      • #334: [java] [doc] Add suggestion to use StringUtils#isBlank for InefficientEmptyStringCheck
      • +
      +
    • +
    • jsp-basic +
        +
      • #369: [jsp] Wrong issue “JSP file should use UTF-8 encoding”
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • The method net.sourceforge.pmd.util.StringUtil#htmlEncode(String) is deprecated. +org.apache.commons.lang3.StringEscapeUtils#escapeHtml4(String) should be used instead.
    • +
    + +

    External Contributions

    + +
      +
    • #368: [vf] Adding proper AST support for negation expressions
    • +
    • #372: [core] Fix XSS in HTML renderer
    • +
    • #374: [java] Add property to ignore interfaces in FieldDeclarationsShouldBeAtStartOfClassRule
    • +
    • #381: [core] Fix broken link in the site’s doc
    • +
    • #382: [java] Added documentation details on InefficientEmptyStringCheck
    • +
    • #383: [jsp] Fixed JspEncoding false positive
    • +
    • #390: [java] Remove trailing whitespaces in design.xml
    • +
    • #391: [apex] Fix documentation typo
    • +
    • #392: [java] False positive for Law Of Demeter (Builder pattern)
    • +
    • #395: [java] Mockito verify method is not taken into account in JUnitTestsShouldIncludeAssert rule
    • +
    + +

    29-April-2017 - 5.6.1

    + +

    The PMD team is pleased to announce PMD 5.6.1.

    + +

    This is a bug fixing release.

    + +

    Fixed Issues

    + +
      +
    • General +
        +
      • #363: [core] Rule documentation pages are missing
      • +
      • #364: [core] Stream closed exception when running through maven
      • +
      • #373: [core] RuleSetFactory - add more helper methods
      • +
      +
    • +
    + +

    22-April-2017 - 5.6.0

    + +

    The PMD team is pleased to announce PMD 5.6.0.

    + +

    The most significant changes are on analysis performance, support for Salesforce’s Visualforce language +a whole new Apex Security Rule Set and the new Braces Rule Set for Apex.

    + +

    We have added initial support for incremental analysis. The experimental feature allows +PMD to cache analysis results between executions to speed up the analysis for all +languages. New CLI flags and Ant options are available to configure it. Currently +the feature is disabled by default, but this may change as it matures.

    + +

    Multithread performance has been enhanced by reducing thread-contention on a +bunch of areas. This is still an area of work, as the speedup of running +multithreaded analysis is still relatively small (4 threads produce less +than a 50% speedup). Future releases will keep improving on this area.

    + +

    Once again, Symbol Table has been an area of great performance improvements. +This time we were able to further improve it’s performance by roughly 10% on all +supported languages. In Java in particular, several more improvements were possible, +improving Symbol Table performance by a whooping 80%, that’s over 15X faster +than PMD 5.5.1, when we first started working on it.

    + +

    Java developers will also appreciate the revamp of CloneMethodMustImplementCloneable, +making it over 500X faster, and PreserveStackTrace which is now 7X faster.

    + +

    New and noteworthy

    + +

    Incremental Analysis

    + +

    PMD now supports incremental analysis. Analysis results can be cached and reused between runs. +This allows PMD to skip files without violations that have remained unchanged. In future releases, +we plan to extend this behavior to unchanged files with violations too.

    + +

    The cache is automatically invalidated if:

    +
      +
    • the used PMD version changes
    • +
    • the auxclasspath changed and any rules require type resolution
    • +
    • the configured rule set has changed
    • +
    + +

    This feature is incubating and is disabled by default. It’s only enabled if you +specifically configure a cache file.

    + +

    To configure the cache file from CLI, a new -cache <path/to/file> flag has been added.

    + +

    For Ant, a new cacheLocation attribute has been added. For instance:

    + +
        <target name="pmd">
    +        <taskdef name="pmd" classname="net.sourceforge.pmd.ant.PMDTask"/>
    +        <pmd cacheLocation="build/pmd/pmd.cache">
    +            <ruleset>rulesets/java/design.xml</ruleset>
    +            <ruleset>java-basic</ruleset>
    +            <formatter type="xml" toFile="c:\pmd_report.xml"/>
    +            <fileset dir="/usr/local/j2sdk1.4.1_01/src/">
    +                <include name="java/lang/*.java"/>
    +            </fileset>
    +        </pmd>
    +    </target>
    +
    + +

    Visualforce Support

    + +

    Salesforce developers rejoice. To out growing Apex support we have added full Visualforce support. +Both CPD and PD are available. So far only a security ruleset is available (vf-security).

    + +
    Visualforce Security Rule Set
    + +
    VfUnescapeEl
    + +

    The rule looks for Expression Language occurances printing unescaped values from the backend. These +could lead to XSS attacks.

    + +
    VfCsrf
    + +

    The rule looks for <apex:page> tags performing an action on page load, definish such action +through Expression Language, as doing so is vulnerable to CSRF attacks.

    + +

    Apex Security Rule Set

    + +

    A new ruleset focused on security has been added, consisting of a wide range of rules +to detect most common security problems.

    + +
    ApexBadCrypto
    + +

    The rule makes sure you are using randomly generated IVs and keys for Crypto calls. +Hard-wiring these values greatly compromises the security of encrypted data.

    + +

    For instance, it would report violations on code such as:

    + +
    public class without sharing Foo {
    +    Blob hardCodedIV = Blob.valueOf('Hardcoded IV 123');
    +    Blob hardCodedKey = Blob.valueOf('0000000000000000');
    +    Blob data = Blob.valueOf('Data to be encrypted');
    +    Blob encrypted = Crypto.encrypt('AES128', hardCodedKey, hardCodedIV, data);
    +}
    +
    +
    + +
    ApexCRUDViolation
    + +

    The rule validates you are checking for access permissions before a SOQL/SOSL/DML operation. +Since Apex runs in system mode not having proper permissions checks results in escalation of +privilege and may produce runtime errors. This check forces you to handle such scenarios.

    + +

    For example, the following code is considered valid:

    + +
    public class Foo {
    +    public Contact foo(String status, String ID) {
    +        Contact c = [SELECT Status__c FROM Contact WHERE Id=:ID];
    +
    +        // Make sure we can update the database before even trying
    +        if (!Schema.sObjectType.Contact.fields.Name.isUpdateable()) {
    +            return null;
    +        }
    +
    +        c.Status__c = status;
    +        update c;
    +        return c;
    +    }
    +}
    +
    + +
    ApexCSRF
    + +

    Check to avoid making DML operations in Apex class constructor/init method. This prevents +modification of the database just by accessing a page.

    + +

    For instance, the following code would be invalid:

    + +
    public class Foo {
    +    public init() {
    +        insert data;
    +    }
    +
    +    public Foo() {
    +        insert data;
    +    }
    +}
    +
    + +
    ApexDangerousMethods
    + +

    Checks against calling dangerous methods.

    + +

    For the time being, it reports:

    + +
      +
    • Against FinancialForce’s Configuration.disableTriggerCRUDSecurity(). Disabling CRUD security +opens the door to several attacks and requires manual validation, which is unreliable.
    • +
    • Calling System.debug passing sensitive data as parameter, which could lead to exposure +of private data.
    • +
    + +
    ApexInsecureEndpoint
    + +

    Checks against accessing endpoints under plain http. You should always use +https for security.

    + +
    ApexOpenRedirect
    + +

    Checks against redirects to user-controlled locations. This prevents attackers from +redirecting users to phishing sites.

    + +

    For instance, the following code would be reported:

    + +
    public class without sharing Foo {
    +    String unsafeLocation = ApexPage.getCurrentPage().getParameters.get('url_param');
    +    PageReference page() {
    +       return new PageReference(unsafeLocation);
    +    }
    +}
    +
    + +
    ApexSharingViolations
    + +

    Detect classes declared without explicit sharing mode if DML methods are used. This +forces the developer to take access restrictions into account before modifying objects.

    + +
    ApexSOQLInjection
    + +

    Detects the usage of untrusted / unescaped variables in DML queries.

    + +

    For instance, it would report on:

    + +
    public class Foo {
    +    public void test1(String t1) {
    +        Database.query('SELECT Id FROM Account' + t1);
    +    }
    +}
    +
    + +
    ApexSuggestUsingNamedCred
    + +

    Detects hardcoded credentials used in requests to an endpoint.

    + +

    You should refrain from hardcoding credentials:

    +
      +
    • They are hard to mantain by being mixed in application code
    • +
    • Particularly hard to update them when used from different classes
    • +
    • Granting a developer access to the codebase means granting knowledge + of credentials, keeping a two-level access is not possible.
    • +
    • Using different credentials for different environments is troublesome + and error-prone.
    • +
    + +

    Instead, you should use Named Credentials and a callout endpoint.

    + +

    For more information, you can check this

    + +
    ApexXSSFromEscapeFalse
    + +

    Reports on calls to addError with disabled escaping. The message passed to addError +will be displayed directly to the user in the UI, making it prime ground for XSS +attacks if unescaped.

    + +
    ApexXSSFromURLParam
    + +

    Makes sure that all values obtained from URL parameters are properly escaped / sanitized +to avoid XSS attacks.

    + +

    Apex Braces Rule Set

    + +

    The Braces Rule Set has been added and serves the same purpose as the Braces Rule Set from Java: +It checks the use and placement of braces around if-statements, for-loops and so on.

    + +
    IfStmtsMustUseBraces
    + +

    Avoid using if statements without using braces to surround the code block. If the code +formatting or indentation is lost then it becomes difficult to separate the code being +controlled from the rest.

    + +

    For instance, the following code shows the different. PMD would report on the not recommended approach:

    + +
    if (foo)    // not recommended
    +    x++;
    +
    +if (foo) {  // preferred approach
    +    x++;
    +}
    +
    + +
    WhileLoopsMustUseBraces
    + +

    Avoid using ‘while’ statements without using braces to surround the code block. If the code +formatting or indentation is lost then it becomes difficult to separate the code being +controlled from the rest.

    + +

    For instance, the following code shows the different. PMD would report on the not recommended approach:

    + +
    while (true)    // not recommended
    +      x++;
    +
    +while (true) {  // preferred approach
    +      x++;
    +}
    +
    + +
    IfElseStmtsMustUseBraces
    + +

    Avoid using if..else statements without using surrounding braces. If the code formatting +or indentation is lost then it becomes difficult to separate the code being controlled +from the rest.

    + +

    For instance, the following code shows the different. PMD would report on the not recommended approach:

    + +
    // this is not recommended
    +if (foo)
    +       x = x+1;
    +   else
    +       x = x-1;
    +
    +// preferred approach
    +if (foo) {
    +   x = x+1;
    +} else {
    +   x = x-1;
    +}
    +
    + +
    ForLoopsMustUseBraces
    + +

    Avoid using ‘for’ statements without using surrounding braces. If the code formatting or +indentation is lost then it becomes difficult to separate the code being controlled +from the rest.

    + +

    For instance, the following code shows the different. PMD would report on the not recommended approach:

    + +
    for (int i = 0; i < 42; i++) // not recommended
    +    foo();
    +
    +for (int i = 0; i < 42; i++) { // preferred approach
    +    foo();
    +}
    +
    + +

    New Rules

    + +
    AccessorMethodGeneration (java-design)
    + +

    When accessing a private field / method from another class, the Java compiler will generate an accessor method +with package-private visibility. This adds overhead, and to the dex method count on Android. This situation can +be avoided by changing the visibility of the field / method from private to package-private.

    + +

    For instance, it would report violations on code such as:

    + +
    public class OuterClass {
    +    private int counter;
    +    /* package */ int id;
    +
    +    public class InnerClass {
    +        InnerClass() {
    +            OuterClass.this.counter++; // wrong, accessor method will be generated
    +        }
    +
    +        public int getOuterClassId() {
    +            return OuterClass.this.id; // id is package-private, no accessor method needed
    +        }
    +    }
    +}
    +
    + +

    This new rule is part of the java-design ruleset.

    + +

    Modified Rules

    + +
      +
    • +

      The Java rule UnnecessaryLocalBeforeReturn (ruleset java-design) now has a new property statementOrderMatters. +It is enabled by default to stay backwards compatible. But if this property is set to false, this rule +no longer requires the variable declaration +and return statement to be on consecutive lines. Any variable that is used solely in a return statement will be +reported.

      +
    • +
    • +

      The Java rule UseLocaleWithCaseConversions (ruleset java-design) has been modified, to detect calls +to toLowerCase and to toUpperCase also within method call chains. This leads to more detected cases +and potentially new false positives. +See also bugfix #1556.

      +
    • +
    • +

      The Java rule AvoidConstantsInterface (ruleset java-design) has been removed. It is completely replaced by +the rule ConstantsInInterface.

      +
    • +
    • The Java rule UnusedModifier (ruleset java-unusedcode) has been moved to the ruleset java-unnecessary +and has been renamed to UnnecessaryModifier. +Additionally, it has been expanded to consider more redundant modifiers: +
        +
      • Annotations marked as abstract.
      • +
      • Nested annotations marked as static.
      • +
      • Nested annotations within another interface or annotation marked as public.
      • +
      • Classes, interfaces or annotations nested within an annotation marked as public or static.
      • +
      • Nested enums marked as static.
      • +
      +
    • +
    • The Java rule JUnitTestsShouldIncludeAssert (ruleset java-junit) now accepts usage of @Rule ExpectedException +to set expectations on exceptions, and are considered as valid assertions.
    • +
    + +

    CPD Suppression

    + +

    It is now possible to allow CPD suppression through comments in Java. You tell CPD to ignore +the following code with a comment containin CPD-OFF and with CPD-ON you tell CPD to resume +analysis. The old approach via @SuppressWarnings annotation is still supported, but is considered +deprecated, since it is limited to locations where the SuppressWarnings annotation is allowed. +See PR #250.

    + +

    For example:

    + +
        public Object someMethod(int x) throws Exception {
    +        // some unignored code
    +
    +        // tell cpd to start ignoring code - CPD-OFF
    +
    +        // mission critical code, manually loop unroll
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +
    +        // resume CPD analysis - CPD-ON
    +
    +        // further code will *not* be ignored
    +    }
    +
    + +

    CPD filelist command line option

    + +

    CPD now supports the command line option --filelist. With that, you can specify a file, which +contains the names and paths of the files, that should be analyzed. This is similar to PMD’s filelist option. +You need to use this, if you have a large project with many files, and you hit the command line length limit.

    + +

    Fixed Issues

    + +
      +
    • General +
        +
      • #1511: [core] Inconsistent behavior of Rule.start/Rule.end
      • +
      • #234: [core] Zip file stream closes spuriously when loading rulesets
      • +
      • #256: [core] shortnames option is broken with relative paths
      • +
      • #305: [core] PMD not executing under git bash
      • +
      • #324: [core] Automated release - github release notes missing
      • +
      • #337: [core] Version 5.5.4 seems to hold file lock on rules JAR (affects Windows only)
      • +
      +
    • +
    • apex-apexunit +
        +
      • #1543: [apex] ApexUnitTestClassShouldHaveAsserts assumes APEX is case sensitive
      • +
      +
    • +
    • apex-complexity +
        +
      • #183: [apex] NCSS Method length is incorrect when using method chaining
      • +
      • #251: [apex] NCSS Type length is incorrect when using method chaining
      • +
      +
    • +
    • apex-security +
        +
      • #264: [apex] ApexXSSFromURLParamRule shouldn’t enforce ESAPI usage. String.escapeHtml4 is sufficient.
      • +
      • #315: [apex] Documentation flaw on Apex Sharing Violations
      • +
      +
    • +
    • java +
        +
      • #185: [java] CPD runs into NPE when analyzing Lucene
      • +
      • #206: [java] Parse error on annotation fields with generics
      • +
      • #207: [java] Parse error on method reference with generics
      • +
      • #208: [java] Parse error with local class with 2 or more annotations
      • +
      • #213: [java] CPD: OutOfMemory when analyzing Lucene
      • +
      • #309: [java] Parse error on method reference
      • +
      • #1542: [java] CPD throws an NPE when parsing enums with -ignore-identifiers
      • +
      • #1545: [java] Symbol Table fails to resolve inner classes
      • +
      +
    • +
    • java-basic +
        +
      • #232: [java] SimplifiedTernary: Incorrect ternary operation can be simplified.
      • +
      +
    • +
    • java-coupling +
        +
      • #270: [java] LoD false positive
      • +
      +
    • +
    • java-design +
        +
      • #933: [java] UnnecessaryLocalBeforeReturn false positive for SuppressWarnings annotation
      • +
      • #1448: [java] ImmutableField: Private field in inner class gives false positive with lambdas
      • +
      • #1495: [java] UnnecessaryLocalBeforeReturn with assert
      • +
      • #1496: [java] New Rule: AccesorMethodGeneration - complements accessor class rule
      • +
      • #1512: [java] Combine rules AvoidConstantsInInterface and ConstantsInInterface
      • +
      • #1552: [java] MissingBreakInSwitch - False positive for continue
      • +
      • #1556: [java] UseLocaleWithCaseConversions does not works with ResultSet (false negative)
      • +
      • #177: [java] SingularField with lambdas as final fields
      • +
      • #216: [java] [doc] NonThreadSafeSingleton: Be more explicit as to why double checked locking is not recommended
      • +
      • #219: [java] UnnecessaryLocalBeforeReturn: ClassCastException in switch case with local variable returned
      • +
      • #240: [java] UnnecessaryLocalBeforeReturn: Enhance by checking usages
      • +
      • #274: [java] AccessorMethodGeneration: Method inside static inner class incorrectly reported
      • +
      • #275: [java] FinalFieldCouldBeStatic: Constant in @interface incorrectly reported as “could be made static”
      • +
      • #282: [java] UnnecessaryLocalBeforeReturn false positive when cloning Maps
      • +
      • #291: [java] Improve quality of AccessorClassGeneration
      • +
      • #310: [java] UnnecessaryLocalBeforeReturn enhancement is overly restrictive – method order matters
      • +
      • #352: [java] AccessorClassGeneration throws ClassCastException when seeing array construction
      • +
      +
    • +
    • java-imports +
        +
      • #338: [java] False positive on DontImportJavaLang when importing java.lang.ProcessBuilder
      • +
      • #339: [java] False positive on DontImportJavaLang when importing Java 7’s java.lang.invoke.MethodHandles
      • +
      • #1546: [java] UnnecessaryFullyQualifiedNameRule doesn’t take into consideration conflict resolution
      • +
      • #1547: [java] UnusedImportRule - False Positive for only usage in Javadoc - {@link ClassName#CONSTANT}
      • +
      • #1555: [java] UnnecessaryFullyQualifiedName: Really necessary fully qualified name
      • +
      +
    • +
    • java-junit +
        +
      • #285: [java] JUnitTestsShouldIncludeAssertRule should support @Rule as well as @Test(expected = …)
      • +
      • #330: [java] NPE applying rule JUnitTestsShouldIncludeAssert
      • +
      +
    • +
    • java-logging-java +
        +
      • #1541: [java] InvalidSlf4jMessageFormat: False positive with placeholder and exception
      • +
      • #1551: [java] InvalidSlf4jMessageFormat: fails with NPE
      • +
      +
    • +
    • java-optimizations +
        +
      • #215: [java] RedundantFieldInitializer report for annotation field not explicitly marked as final
      • +
      • #222: [java] UseStringBufferForStringAppends: False Positive with ternary operator
      • +
      +
    • +
    • java-strings +
        +
      • #202: [java] [doc] ConsecutiveAppendsShouldReuse is not really an optimization
      • +
      • #290: [java] InefficientEmptyStringCheck misses String.trim().isEmpty()
      • +
      +
    • +
    • java-unnecessary +
        +
      • #199: [java] UselessParentheses: Parentheses in return statement are incorrectly reported as useless
      • +
      +
    • +
    • java-unusedcode +
        +
      • #246: [java] UnusedModifier doesn’t check annotations
      • +
      • #247: [java] UnusedModifier doesn’t check annotations inner classes
      • +
      • #248: [java] UnusedModifier doesn’t check static keyword on nested enum declaration
      • +
      • #257: [java] UnusedLocalVariable false positive
      • +
      +
    • +
    • XML +
        +
      • #1518: [xml] Error while processing xml file with “.webapp” in the file or directory name
      • +
      +
    • +
    • psql +
        +
      • #1549: [plsql] Parse error for IS [NOT] NULL construct
      • +
      +
    • +
    • javascript +
        +
      • #201: [javascript] template strings are not correctly parsed
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • net.sourceforge.pmd.RuleSetFactory is now immutable and its behavior cannot be changed anymore. +It provides constructors to create new adjusted instances. This allows to avoid synchronization in RuleSetFactory. +See PR #131.
    • +
    • net.sourceforge.pmd.RuleSet is now immutable, too, and can only be created via RuleSetFactory. +See PR #145.
    • +
    • net.sourceforge.pmd.cli.XPathCLI has been removed. It’s functionality is fully covered by the Designer.
    • +
    • net.sourceforge.pmd.Report now works with ThreadSafeReportListeners. Both ReportListener and +SynchronizedReportListener are deprecated in favor of net.sourceforge.pmd.ThreadSafeReportListener. +Therefore, the methods getSynchronizedListeners() and addSynchronizedListeners(...) have been +replaced by getListeners() and addListeners(...). See PR #193.
    • +
    + +

    External Contributions

    + +
      +
    • #123: [apex] Changing method names to lowercase so casing doesn’t matter
    • +
    • #129: [plsql] Added correct parse of IS [NOT] NULL and multiline DML
    • +
    • #137: [apex] Adjusted remediation points
    • +
    • #146: [apex] Detection of missing Apex CRUD checks for SOQL/DML operations
    • +
    • #147: [apex] Adding XSS detection to return statements
    • +
    • #148: [apex] Improving detection of SOQL injection
    • +
    • #149: [apex] Whitelisting String.isEmpty and casting
    • +
    • #152: [java] fixes #1552 continue does not require break
    • +
    • #154: [java] Fix #1547: UnusedImports: Adjust regex to support underscores
    • +
    • #158: [apex] Reducing FPs in SOQL with VF getter methods
    • +
    • #160: [apex] Flagging of dangerous method call
    • +
    • #163: [apex] Flagging of System.debug
    • +
    • #165: [apex] Improving open redirect rule to avoid test classes/methods
    • +
    • #167: [apex] GC and thread safety changes
    • +
    • #169: [apex] Improving detection for DML with inline new object
    • +
    • #170: [core] Ant Task Formatter encoding issue with XMLRenderer
    • +
    • #172: [apex] Bug fix, detects both Apex fields and class members
    • +
    • #175: [apex] ApexXSSFromURLParam: Adding missing casting methods
    • +
    • #176: [apex] Bug fix for FP: open redirect for strings prefixed with / is safe
    • +
    • #179: [apex] Legacy test class declaration support
    • +
    • #181: [apex] Control flow based CRUD rule checking
    • +
    • #184: [apex] Improving open redirect detection for static fields & assignment operations
    • +
    • #189: [apex] Bug fix of SOQL concatenated vars detection
    • +
    • #191: [apex] Detection of sharing violation when Database. methods are used
    • +
    • #192: [apex] Dead code removal
    • +
    • #200: [javascript] Templatestring grammar fix
    • +
    • #204: [apex] Sharing violation SOQL detection bug fix
    • +
    • #214: [apex] Sharing violation improving reporting of the correct node, de-duping
    • +
    • #217: [core] Make it build on Windows
    • +
    • #227: [apex] Improving detection of getters
    • +
    • #228: [apex] Excluding count from CRUD/FLS checks
    • +
    • #229: [apex] Dynamic SOQL is safe against Integer, Boolean, Double
    • +
    • #231: [apex] CRUD/FLS rule - add support for fields
    • +
    • #266: [java] corrected invalid reporting of LoD violation
    • +
    • #268: [apex] Support safe escaping via String method
    • +
    • #273: [apex] Shade jackson on apex
    • +
    • #279: [vf] New Salesforce VisualForce language support
    • +
    • #280: [apex] Support for Aggregate Result in CRUD rules
    • +
    • #281: [apex] Add Braces Rule Set
    • +
    • #283: [vf] CSRF in VF controller pages
    • +
    • #284: [vf] Adding support for parsing EL in script tags
    • +
    • #288: [vf] Setting the tab size to 4 for VF
    • +
    • #289: [apex] Complex SOQL Crud check bug fixes
    • +
    • #296: [apex] Adding String.IsNotBlank to the whitelist to prevent False positives
    • +
    • #297: [core] CPD: Adding the –filelist option from pmd to cpd
    • +
    • #303: [java] InefficientEmptyStringCheckRule now reports String.trim().isEmpty()
    • +
    • #307: [java] Fix false positive with UseStringBufferForStringAppendsRule
    • +
    • #308: [java] JUnitTestsShouldIncludeAssertRule supports @Rule annotated ExpectedExceptions
    • +
    • #313: [vf] Apex:iFrame not being detected - bug fix
    • +
    • #314: [vf] Bug fixes for incorrect Id detection and escaping
    • +
    • #316: [apex] Ignoring certain rules in Batch classes, Queueable, and install scripts
    • +
    • #317: [apex] Add support for safe ID assignment from URL param
    • +
    • #326: [vf] Quote detection improvement and method argument detection
    • +
    • #327: [apex] Fixed SOQL injection detection for escaped vars
    • +
    • #331: [java] JunitTestsShouldIncludeAssertRule now handles AllocationExpression correctly
    • +
    • #332: [java] Future-proof DontImportJavaLangRule
    • +
    • #340: [vf] Multiple parser bug fixes
    • +
    • #341: [vf] JSON.parse(..) and NOT(..) are safely evaluated
    • +
    • #343: [apex] int,id,boolean,ternary operator condition are not injection in Soql
    • +
    • #344: [apex] ApexCRUDViolationRule: Bug fix for ClassCastException
    • +
    • #351: [vf] Fixing regression introduced by #341
    • +
    + +

    29-April-2017 - 5.5.7

    + +

    The PMD team is pleased to announce PMD 5.5.7.

    + +

    This is a bug fixing release.

    + +

    Fixed Issues

    + +
      +
    • General +
        +
      • #364: [core] Stream closed exception when running through maven
      • +
      +
    • +
    + +

    19-April-2017 - 5.5.6

    + +

    The PMD team is pleased to announce PMD 5.5.6.

    + +

    This is a bug fixing release.

    + +

    Fixed Issues

    + +
      +
    • General +
        +
      • #324: [core] Automated release - github release notes missing
      • +
      • #337: [core] Version 5.5.4 seems to hold file lock on rules JAR (affects Windows only)
      • +
      +
    • +
    + +

    27-March-2017 - 5.5.5

    + +

    The PMD team is pleased to announce PMD 5.5.5.

    + +

    Fixed Issues

    + +
      +
    • general: +
        +
      • #305: [core] PMD not executing under git bash
      • +
      +
    • +
    • java: +
        +
      • #309: [java] Parse error on method reference
      • +
      +
    • +
    • java-design +
        +
      • #274: [java] AccessorMethodGeneration: Method inside static inner class incorrectly reported
      • +
      • #275: [java] FinalFieldCouldBeStatic: Constant in @interface incorrectly reported as “could be made static”
      • +
      • #282: [java] UnnecessaryLocalBeforeReturn false positive when cloning Maps
      • +
      • #291: [java] Improve quality of AccessorClassGeneration
      • +
      +
    • +
    • java-junit: +
        +
      • #285: [java] JUnitTestsShouldIncludeAssertRule should support @Rule as well as @Test(expected = …)
      • +
      +
    • +
    • java-optimizations: +
        +
      • #222: [java] UseStringBufferForStringAppends: False Positive with ternary operator
      • +
      +
    • +
    • java-strings: +
        +
      • #290: [java] InefficientEmptyStringCheck misses String.trim().isEmpty()
      • +
      +
    • +
    + +

    External Contributions

    + +
      +
    • #280: [apex] Support for Aggregate Result in CRUD rules
    • +
    • #289: [apex] Complex SOQL Crud check bug fixes
    • +
    • #296: [apex] Adding String.IsNotBlank to the whitelist to prevent False positives
    • +
    • #303: [java] InefficientEmptyStringCheckRule now reports String.trim().isEmpty()
    • +
    • #307: [java] Fix false positive with UseStringBufferForStringAppendsRule
    • +
    • #308: [java] JUnitTestsShouldIncludeAssertRule supports @Rule annotated ExpectedExceptions
    • +
    + +

    25-Februar-2017 - 5.5.4

    + +

    The PMD team is pleased to announce PMD 5.5.4

    + +

    New and noteworthy

    + +

    New Rules

    + +
    AccessorMethodGeneration (java-design)
    + +

    When accessing a private field / method from another class, the Java compiler will generate a accessor methods +with package-private visibility. This adds overhead, and to the dex method count on Android. This situation can +be avoided by changing the visibility of the field / method from private to package-private.

    + +

    For instance, it would report violations on code such as:

    + +
    public class OuterClass {
    +    private int counter;
    +    /* package */ int id;
    +
    +    public class InnerClass {
    +        InnerClass() {
    +            OuterClass.this.counter++; // wrong, accessor method will be generated
    +        }
    +
    +        public int getOuterClassId() {
    +            return OuterClass.this.id; // id is package-private, no accessor method needed
    +        }
    +    }
    +}
    +
    + +

    This new rule is part of the java-design ruleset.

    + +

    Modified Rules

    + +
      +
    • The Java rule UnusedModifier (ruleset java-unusedcode) has been expanded to consider more redundant modifiers. +
        +
      • Annotations marked as abstract.
      • +
      • Nested annotations marked as static.
      • +
      • Nested annotations within another interface or annotation marked as public.
      • +
      • Classes, interfaces or annotations nested within an annotation marked as public or static.
      • +
      • Nested enums marked as static.
      • +
      +
    • +
    • The Java rule UnnecessaryLocalBeforeReturn (ruleset java-design) no longer requires the variable declaration +and return statement to be on consecutive lines. Any variable that is used solely in a return statement will be +reported.
    • +
    + +

    Fixed Issues

    + +
      +
    • General +
        +
      • #234: [core] Zip file stream closes spuriously when loading rulesets
      • +
      • #256: [core] shortnames option is broken with relative paths
      • +
      +
    • +
    • apex-complexity +
        +
      • #251: [apex] NCSS Type length is incorrect when using method chaining
      • +
      +
    • +
    • apex-security +
        +
      • #264: [apex] ApexXSSFromURLParamRule shouldn’t enforce ESAPI usage. String.escapeHtml4 is sufficient.
      • +
      +
    • +
    • java-basic +
        +
      • #232: [java] SimplifiedTernary: Incorrect ternary operation can be simplified.
      • +
      +
    • +
    • java-coupling +
        +
      • #270: [java] LoD false positive
      • +
      +
    • +
    • java-design +
        +
      • #933: [java] UnnecessaryLocalBeforeReturn false positive for SuppressWarnings annotation
      • +
      • #1496: [java] New Rule: AccesorMethodGeneration - complements accessor class rule
      • +
      • #216: [java] [doc] NonThreadSafeSingleton: Be more explicit as to why double checked locking is not recommended
      • +
      • #219: [java] UnnecessaryLocalBeforeReturn: ClassCastException in switch case with local variable returned
      • +
      • #240: [java] UnnecessaryLocalBeforeReturn: Enhance by checking usages
      • +
      +
    • +
    • java-optimizations +
        +
      • #215: [java] RedundantFieldInitializer report for annotation field not explicitly marked as final
      • +
      +
    • +
    • java-unusedcode +
        +
      • #246: [java] UnusedModifier doesn’t check annotations
      • +
      • #247: [java] UnusedModifier doesn’t check annotations inner classes
      • +
      • #248: [java] UnusedModifier doesn’t check static keyword on nested enum declaration
      • +
      • #257: [java] UnusedLocalVariable false positive
      • +
      +
    • +
    + +

    External Contributions

    + +
      +
    • #227: [apex] Improving detection of getters
    • +
    • #228: [apex] Excluding count from CRUD/FLS checks
    • +
    • #229: [apex] Dynamic SOQL is safe against Integer, Boolean, Double
    • +
    • #231: [apex] CRUD/FLS rule - add support for fields
    • +
    • #266: [java] corrected invalid reporting of LoD violation
    • +
    • #268: [apex] Support safe escaping via String method
    • +
    • #273: [apex] Shade jackson on apex
    • +
    + +

    28-January-2017 - 5.5.3

    + +

    The PMD team is pleased to announce PMD 5.5.3

    + +

    The most significant changes are on analysis performance and a whole new Apex Security Rule Set.

    + +

    Multithread performance has been enhanced by reducing thread-contention on a +bunch of areas. This is still an area of work, as the speedup of running +multithreaded analysis is still relatively small (4 threads produce less +than a 50% speedup). Future releases will keep improving on this area.

    + +

    Once again, Symbol Table has been an area of great performance improvements. +This time we were able to further improve it’s performance by roughly 10% on all +supported languages. In Java in particular, several more improvements were possible, +improving Symbol Table performance by a whooping 30%, that’s over 5X faster +than PMD 5.5.1, when we first started working on it.

    + +

    Java developers will also appreciate the revamp of CloneMethodMustImplementCloneable, +making it over 500X faster, and PreserveStackTrace which is now 7X faster.

    + +

    New and noteworthy

    + +

    Apex Security Rule Set

    + +

    A new ruleset focused on security has been added, consisting of a wide range of rules +to detect most common security problems.

    + +
    ApexBadCrypto
    + +

    The rule makes sure you are using randomly generated IVs and keys for Crypto calls. +Hard-wiring these values greatly compromises the security of encrypted data.

    + +

    For instance, it would report violations on code such as:

    + +
    public class without sharing Foo {
    +    Blob hardCodedIV = Blob.valueOf('Hardcoded IV 123');
    +    Blob hardCodedKey = Blob.valueOf('0000000000000000');
    +    Blob data = Blob.valueOf('Data to be encrypted');
    +    Blob encrypted = Crypto.encrypt('AES128', hardCodedKey, hardCodedIV, data);
    +}
    +
    +
    + +
    ApexCRUDViolation
    + +

    The rule validates you are checking for access permissions before a SOQL/SOSL/DML operation. +Since Apex runs in system mode not having proper permissions checks results in escalation of +privilege and may produce runtime errors. This check forces you to handle such scenarios.

    + +

    For example, the following code is considered valid:

    + +
    public class Foo {
    +    public Contact foo(String status, String ID) {
    +        Contact c = [SELECT Status__c FROM Contact WHERE Id=:ID];
    +
    +        // Make sure we can update the database before even trying
    +        if (!Schema.sObjectType.Contact.fields.Name.isUpdateable()) {
    +            return null;
    +        }
    +
    +        c.Status__c = status;
    +        update c;
    +        return c;
    +    }
    +}
    +
    + +
    ApexCSRF
    + +

    Check to avoid making DML operations in Apex class constructor/init method. This prevents +modification of the database just by accessing a page.

    + +

    For instance, the following code would be invalid:

    + +
    public class Foo {
    +    public init() {
    +        insert data;
    +    }
    +
    +    public Foo() {
    +        insert data;
    +    }
    +}
    +
    + +
    ApexDangerousMethods
    + +

    Checks against calling dangerous methods.

    + +

    For the time being, it reports:

    + +
      +
    • Against FinancialForce’s Configuration.disableTriggerCRUDSecurity(). Disabling CRUD security +opens the door to several attacks and requires manual validation, which is unreliable.
    • +
    • Calling System.debug passing sensitive data as parameter, which could lead to exposure +of private data.
    • +
    + +
    ApexInsecureEndpoint
    + +

    Checks against accessing endpoints under plain http. You should always use +https for security.

    + +
    ApexOpenRedirect
    + +

    Checks against redirects to user-controlled locations. This prevents attackers from +redirecting users to phishing sites.

    + +

    For instance, the following code would be reported:

    + +
    public class without sharing Foo {
    +    String unsafeLocation = ApexPage.getCurrentPage().getParameters.get('url_param');
    +    PageReference page() {
    +       return new PageReference(unsafeLocation);
    +    }
    +}
    +
    + +
    ApexSharingViolations
    + +

    Detect classes declared without explicit sharing mode if DML methods are used. This +forces the developer to take access restrictions into account before modifying objects.

    + +
    ApexSOQLInjection
    + +

    Detects the usage of untrusted / unescaped variables in DML queries.

    + +

    For instance, it would report on:

    + +
    public class Foo {
    +    public void test1(String t1) {
    +        Database.query('SELECT Id FROM Account' + t1);
    +    }
    +}
    +
    + +
    ApexSuggestUsingNamedCred
    + +

    Detects hardcoded credentials used in requests to an endpoint.

    + +

    You should refrain from hardcoding credentials:

    +
      +
    • They are hard to mantain by being mixed in application code
    • +
    • Particularly hard to update them when used from different classes
    • +
    • Granting a developer access to the codebase means granting knowledge + of credentials, keeping a two-level access is not possible.
    • +
    • Using different credentials for different environments is troublesome + and error-prone.
    • +
    + +

    Instead, you should use Named Credentials and a callout endpoint.

    + +

    For more information, you can check this

    + +
    ApexXSSFromEscapeFalse
    + +

    Reports on calls to addError with disabled escaping. The message passed to addError +will be displayed directly to the user in the UI, making it prime ground for XSS +attacks if unescaped.

    + +
    ApexXSSFromURLParam
    + +

    Makes sure that all values obtained from URL parameters are properly escaped / sanitized +to avoid XSS attacks.

    + +

    Modified Rules

    + +

    The Java rule “UseLocaleWithCaseConversions” (ruleset java-design) has been modified, to detect calls +to toLowerCase and to toUpperCase also within method call chains. This leads to more detected cases +and potentially new false positives. +See also bugfix #1556.

    + +

    Fixed Issues

    + +
      +
    • General +
        +
      • #1511: [core] Inconsistent behavior of Rule.start/Rule.end
      • +
      +
    • +
    • apex-apexunit +
        +
      • #1543: [apex] ApexUnitTestClassShouldHaveAsserts assumes APEX is case sensitive
      • +
      +
    • +
    • apex-complexity +
        +
      • #183: [apex] NCSS Method length is incorrect when using method chaining
      • +
      +
    • +
    • java +
        +
      • #185: [java] CPD runs into NPE when analyzing Lucene
      • +
      • #206: [java] Parse error on annotation fields with generics
      • +
      • #207: [java] Parse error on method reference with generics
      • +
      • #208: [java] Parse error with local class with 2 or more annotations
      • +
      • #213: [java] CPD: OutOfMemory when analyzing Lucene
      • +
      • #1542: [java] CPD throws an NPE when parsing enums with -ignore-identifiers
      • +
      • #1545: [java] Symbol Table fails to resolve inner classes
      • +
      +
    • +
    • java-design +
        +
      • #1448: [java] ImmutableField: Private field in inner class gives false positive with lambdas
      • +
      • #1495: [java] UnnecessaryLocalBeforeReturn with assert
      • +
      • #1552: [java] MissingBreakInSwitch - False positive for continue
      • +
      • #1556: [java] UseLocaleWithCaseConversions does not works with ResultSet (false negative)
      • +
      • #177: [java] SingularField with lambdas as final fields
      • +
      +
    • +
    • java-imports +
        +
      • #1546: [java] UnnecessaryFullyQualifiedNameRule doesn’t take into consideration conflict resolution
      • +
      • #1547: [java] UnusedImportRule - False Positive for only usage in Javadoc - {@link ClassName#CONSTANT}
      • +
      • #1555: [java] UnnecessaryFullyQualifiedName: Really necessary fully qualified name
      • +
      +
    • +
    • java-logging-java +
        +
      • #1541: [java] InvalidSlf4jMessageFormat: False positive with placeholder and exception
      • +
      • #1551: [java] InvalidSlf4jMessageFormat: fails with NPE
      • +
      +
    • +
    • java-unnecessary +
        +
      • #199: [java] UselessParentheses: Parentheses in return statement are incorrectly reported as useless
      • +
      +
    • +
    • java-strings +
        +
      • #202: [java] [doc] ConsecutiveAppendsShouldReuse is not really an optimization
      • +
      +
    • +
    • XML +
        +
      • #1518: [xml] Error while processing xml file with “.webapp” in the file or directory name
      • +
      +
    • +
    • psql +
        +
      • #1549: [plsql] Parse error for IS [NOT] NULL construct
      • +
      +
    • +
    • javascript +
        +
      • #201: [javascript] template strings are not correctly parsed
      • +
      +
    • +
    + +

    API Changes

    + +
      +
    • net.sourceforge.pmd.RuleSetFactory is now immutable and its behavior cannot be changed anymore. +It provides constructors to create new adjusted instances. This allows to avoid synchronization in RuleSetFactory. +See PR #131.
    • +
    + +

    External Contributions

    + +
      +
    • #123: [apex] Changing method names to lowercase so casing doesn’t matter
    • +
    • #129: [plsql] Added correct parse of IS [NOT] NULL and multiline DML
    • +
    • #137: [apex] Adjusted remediation points
    • +
    • #146: [apex] Detection of missing Apex CRUD checks for SOQL/DML operations
    • +
    • #147: [apex] Adding XSS detection to return statements
    • +
    • #148: [apex] Improving detection of SOQL injection
    • +
    • #149: [apex] Whitelisting String.isEmpty and casting
    • +
    • #152: [java] fixes #1552 continue does not require break
    • +
    • #154: [java] Fix #1547: UnusedImports: Adjust regex to support underscores
    • +
    • #158: [apex] Reducing FPs in SOQL with VF getter methods
    • +
    • #160: [apex] Flagging of dangerous method call
    • +
    • #163: [apex] Flagging of System.debug
    • +
    • #165: [apex] Improving open redirect rule to avoid test classes/methods
    • +
    • #167: [apex] GC and thread safety changes
    • +
    • #169: [apex] Improving detection for DML with inline new object
    • +
    • #170: [core] Ant Task Formatter encoding issue with XMLRenderer
    • +
    • #172: [apex] Bug fix, detects both Apex fields and class members
    • +
    • #175: [apex] ApexXSSFromURLParam: Adding missing casting methods
    • +
    • #176: [apex] Bug fix for FP: open redirect for strings prefixed with / is safe
    • +
    • #179: [apex] Legacy test class declaration support
    • +
    • #181: [apex] Control flow based CRUD rule checking
    • +
    • #184: [apex] Improving open redirect detection for static fields & assignment operations
    • +
    • #189: [apex] Bug fix of SOQL concatenated vars detection
    • +
    • #191: [apex] Detection of sharing violation when Database. methods are used
    • +
    • #192: [apex] Dead code removal
    • +
    • #200: [javascript] Templatestring grammar fix
    • +
    • #204: [apex] Sharing violation SOQL detection bug fix
    • +
    • #214: [apex] Sharing violation improving reporting of the correct node, de-duping
    • +
    + +

    05-November-2016 - 5.5.2

    + +

    Summary:

    + +
      +
    • 1 new language for CPD: Groovy
    • +
    • 1 new rule: plsql-strictsyntax/MisplacedPragma
    • +
    • 12 pull requests
    • +
    • 17 bug fixes
    • +
    + +

    New Supported Languages:

    + +
      +
    • CPD now supports Groovy. See PR#107.
    • +
    + +

    Feature Requests and Improvements:

    + +
      +
    • plsql +
        +
      • #1539: [plsql] Create new rule for strict syntax checking: MisplacedPragma
      • +
      +
    • +
    + +

    New Rules:

    + +
      +
    • New Rules for plsql +
        +
      • plsql-strictsyntax: MisplacedPragma
      • +
      +
    • +
    + +

    Pull Requests:

    + +
      +
    • #106: [java] CPD: Keep constructor names under ignoreIdentifiers
    • +
    • #107: [groovy] Initial support for CPD Groovy
    • +
    • #110: [java] Fix parser error (issue 1530)
    • +
    • #111: [java] Fix BooleanInstantiationRule for Java 8
    • +
    • #112: [java] Fix ClassCastException on CloneMethodMustImplementCloneable
    • +
    • #113: [java] Fix ClassCastException on SignatureDeclareThrowsException
    • +
    • #114: [core] Remove multihreading workaround for JRE5, as no PMD version supports running on JRE5 anymore
    • +
    • #115: [java] Simplify lambda parsing
    • +
    • #116: [core] [java] Improve collection usage
    • +
    • #117: [java] Improve symboltable performance
    • +
    • #118: [java] Simplify VariableDeclaratorId parsing
    • +
    • #119: [plsql] Fix PMD issue 1531- endless loop followed by OOM while parsing (PL)SQL
    • +
    + +

    Bugfixes:

    + +
      +
    • apex-apexunit +
        +
      • #1521: [apex] ApexUnitTestClassShouldHaveAsserts: Parsing error on APEX class: expected one element but was: <BlockStatement, BlockStatement>
      • +
      +
    • +
    • Java +
        +
      • #1530: [java] Parser exception on Java code
      • +
      • #1490: [java] PMD Error while processing - NullPointerException
      • +
      +
    • +
    • java-basic/BooleanInstantiation +
        +
      • #1533: [java] BooleanInstantiation: ClassCastException with Annotation
      • +
      +
    • +
    • java-comments +
        +
      • #1522: [java] CommentRequired: false positive
      • +
      +
    • +
    • java-design/SingularField +
        +
      • #1494: [java] SingularField: lombok.Data false positive
      • +
      +
    • +
    • java-imports/UnusedImports +
        +
      • #1529: [java] UnusedImports: The created rule violation has no class name
      • +
      +
    • +
    • java-logging-java +
        +
      • #1500 [java] InvalidSlf4jMessageFormat: doesn’t ignore exception param
      • +
      • #1509 [java] InvalidSlf4jMessageFormat: NPE
      • +
      +
    • +
    • java-typeresolution/CloneMethodMustImplementCloneable +
        +
      • #1532: [java] CloneMethodMustImplementCloneable: Implemented Interface extends Cloneable
      • +
      • #1534: [java] CloneMethodMustImplementCloneable: ClassCastException with Annotation (java8)
      • +
      +
    • +
    • java-typeresolution/SignatureDeclareThrowsException +
        +
      • #1535: [java] SignatureDeclareThrowsException: ClassCastException with Annotation
      • +
      +
    • +
    • PLSQL +
        +
      • #1520: [plsql] Missing PL/SQL language constructs in parser: Is Of Type, Using
      • +
      • #1527: [plsql] PRAGMA AUTONOMOUS_TRANSACTION gives processing errors
      • +
      • #1531: [plsql] OOM/Endless loop while parsing (PL)SQL
      • +
      +
    • +
    • General +
        +
      • #1506: [core] When runing any RuleTst, start/end methods not called
      • +
      • #1517: [java] CPD reports on Java constructors when using ignoreIdentifiers
      • +
      +
    • +
    + +

    27-July-2016 - 5.5.1

    + +

    New Rules:

    + +
      +
    • New rules for Salesforce.com Apex: +
        +
      • apex-apexunit: ApexUnitTestClassShouldHaveAsserts, ApexUnitTestShouldNotUseSeeAllDataTrue
      • +
      +
    • +
    + +

    Pull Requests:

    + +
      +
    • #101: [java] Improve multithreading performance: do not lock on classloader
    • +
    • #102: [apex] Restrict AvoidLogicInTrigger rule to max. 1 violation per file
    • +
    • #103: [java] [apex] Fix for 1501: CyclomaticComplexity rule causes OOM when class reporting is disabled
    • +
    • #104: [core] [java] Close opened file handles
    • +
    • apex #43: [apex] Basic apex unit test rules
    • +
    + +

    Bugfixes:

    + +
      +
    • Apex +
        +
      • #1501: [java] [apex] CyclomaticComplexity rule causes OOM when class reporting is disabled
      • +
      +
    • +
    • Java +
        +
      • #1501: [java] [apex] CyclomaticComplexity rule causes OOM when class reporting is disabled
      • +
      +
    • +
    • General +
        +
      • #1499: [core] CPD test break PMD 5.5.1 build on Windows
      • +
      • #1508: [core] [java] PMD is leaking file handles
      • +
      +
    • +
    + +

    25-June-2016 - 5.5.0

    + +

    System requirements:

    + +

    PMD and CPD need at least a java7 runtime environment. For analyzing Salesforce.com Apex source code, +you’ll need a java8 runtime environment.

    + +

    New Supported Languages:

    + +
      +
    • Salesforce.com Apex is now supported by PMD and CPD. See PR#86.
    • +
    • CPD now supports Perl. See PR#82.
    • +
    • CPD now supports Swift. See PR#33.
    • +
    + +

    New and modified Rules:

    + +
      +
    • New rules in Java: +
        +
      • java-logging-java/InvalidSlf4jMessageFormat: Check for invalid message format in slf4j loggers. +See PR#73.
      • +
      • java-design/ConstantsInInterface: Avoid constants in interfaces. +Interfaces should define types, constants are implementation details +better placed in classes or enums. See Effective Java, item 19. +See PR#93.
      • +
      +
    • +
    • Modified rules in Java: +
        +
      • java-comments/CommentRequired: New property serialVersionUIDCommentRequired which controls the comment requirements +for serialVersionUID fields. By default, no comment is required for this field.
      • +
      • java-design/UseVargs: public static void main method is ignored now and so are methods, that are annotated +with Override. See PR#79.
      • +
      +
    • +
    • New rules for Salesforce.com Apex: +
        +
      • apex-complexity: AvoidDeeplyNestedIfStmts, ExcessiveParameterList, ExcessiveClassLength, +NcssMethodCount, NcssTypeCount, NcssConstructorCount, StdCyclomaticComplexity, +TooManyFields, ExcessivePublicCount
      • +
      • apex-performance: AvoidDmlStatementsInLoops, AvoidSoqlInLoops
      • +
      • apex-style: VariableNamingConventions, MethodNamingConventions, ClassNamingConventions, +MethodWithSameNameAsEnclosingClass, AvoidLogicInTrigger, AvoidGlobalModifier
      • +
      +
    • +
    • Javascript +
        +
      • New Rule: ecmascript-unnecessary/NoElseReturn: The else block in a if-else-construct is +unnecessary if the if block contains a return. Then the content of the else block can be +put outside. See #1486.
      • +
      +
    • +
    + +

    Improvements and CLI changes:

    + +
      +
    • A JSON-renderer for PMD which is compatible with CodeClimate. See PR#83.
    • +
    • #1360: [core] [java] Provide backwards compatibility for PMD configuration file
    • +
    • CPD: If a complete filename is specified, the language dependent filename filter is not applied. This allows +to scan files, that are not using the standard file extension. If a directory is specified, the filename filter +is still applied and only those files with the correct file extension of the language are scanned.
    • +
    • CPD: If no problems found, an empty report will be output instead of nothing. See also #1481
    • +
    • CPD: New command line parameter --ignore-usings: Ignore using directives in C# when comparing text.
    • +
    • PMD: New command line parameter: -norulesetcompatibility - this disables the ruleset factory +compatibility filter and fails, if e.g. an old rule name is used in the ruleset. +See also #1360. +This option is also available for the ant task: <noRuleSetCompatibility>true</noRuleSetCompatibility>.
    • +
    • PMD: New command line parameter: -filelist- this provides an alternative way to define, which +files should be process by PMD. With this option, you can provide the path to a single file containing a comma +delimited list of files to analyze. If this is given, then you don’t need to provide -dir. +See PR#98.
    • +
    + +

    Pull Requests:

    + +
      +
    • #25: [cs] Added option to exclude C# using directives from CPD analysis
    • +
    • #27: [cpp] Added support for Raw String Literals (C++11).
    • +
    • [#29)(https://github.com/adangel/pmd/pull/29): [jsp] Added support for files with UTF-8 BOM to JSP tokenizer.
    • +
    • #30: [core] CPD: Removed file filter for files that are explicitly specified on the CPD command line using the ‘–files’ command line option.
    • +
    • #31: [core] CPD: Added file encoding detection to CPD.
    • +
    • #32: [objectivec] Extended Objective-C grammar to accept UTF-8 escapes (\uXXXX) in string literals.
    • +
    • #33: [swift] Added support for Swift to CPD.
    • +
    • #34: multiple code improvements: squid:S1192, squid:S1118, squid:S1066, squid:S1854, squid:S2864
    • +
    • #35: [javascript] Javascript tokenizer now ignores comment tokens.
    • +
    • #72: [java] [jsp] Added capability in Java and JSP parser for tracking tokens.
    • +
    • #73: [java] InvalidSlf4jMessageFormat: Add rule to look for invalid message format in slf4j loggers
    • +
    • #74: [java] CommentDefaultAccessModifier: Fix rendering CommentDefaultAccessModifier description as code
    • +
    • #75: [core] RuleSetFactory Performance Enhancement
    • +
    • #76: [java] DoNotCallGarbageCollectionExplicitly: fix formatting typos in an example
    • +
    • #77: [java] [plsql] Fix various typos
    • +
    • #78: [java] MissingStaticMethodInNonInstantiatableClass: Add Builder pattern check
    • +
    • #79: [java] UseVarargs: do not flag public static void main(String[]), ignore @Override
    • +
    • #80: [site] Update mvn-plugin.md
    • +
    • #82: [perl] Add Perl support to CPD.
    • +
    • #83: [core] CodeClimateRenderer: Adds new Code Climate-compliant JSON renderer
    • +
    • #84: [java] EmptyMethodInAbstractClassShouldBeAbstract: Change rule’s description.
    • +
    • #85: [java] UseStringBufferForStringAppends: False Positive with Ternary Operator (#1340)
    • +
    • #86: [apex] Added language module for Salesforce.com Apex incl. rules ported from Java and new ones.
    • +
    • #87: [core] [apex] Customize Code Climate Json “categories” + “remediation_points” as PMD rule properties
    • +
    • #88: [core] [apex] Fixed typo in ruleset.xml and problems with the CodeClimate renderer
    • +
    • #89: [core] Some code enhancements
    • +
    • #90: [core] Refactored two test to stop using the deprecated ant class BuildFileTest
    • +
    • #91: [core] [java] [jsp] [plsql] [test] [vm] Small code enhancements, basically reordering variable declarations, constructors and variable modifiers
    • +
    • #92: [core] [apex] Improved Code Climate Renderer Output and a Bugfix for Apex StdCyclomaticComplexityRule on triggers
    • +
    • #93: [java] ConstantsInInterface: Add ConstantsInInterface rule. Effective Java, 19
    • +
    • #94: [core] [apex] Added property, fixed code climate renderer output and deleted unused rulessets
    • +
    • #95: [apex] AvoidDmlStatementsInLoops: New apex rule AvoidDmlStatementsInLoops
    • +
    • #96: [core] CodeClimateRenderer: Clean up Code Climate renderer
    • +
    • #97: [java] BooleanGetMethodName: Don’t report bad method names on @Override
    • +
    • #98: [core] PMD: Input filelist parameter
    • +
    • #99: [apex] Fixed Trigger name is reported incorrectly
    • +
    • #100: [core] CSVRenderer: escape filenames with commas in csvrenderer
    • +
    + +

    Bugfixes:

    + +
      +
    • java-basic +
        +
      • #1471: [java] DoubleCheckedLocking: False positives
      • +
      • #1424: [java] SimplifiedTernary: False positive with ternary operator
      • +
      +
    • +
    • java-codesize +
        +
      • #1457: [java] TooManyMethods: counts inner class methods
      • +
      +
    • +
    • java-comments +
        +
      • #1430: [java] CommentDefaultAccessModifier: triggers on field +annotated with @VisibleForTesting
      • +
      • #1434: [java] CommentRequired: raises violation on serialVersionUID field
      • +
      +
    • +
    • java-controversial +
        +
      • #1449: [java] AvoidUsingShortType: false positive when casting a variable to short
      • +
      +
    • +
    • java-design +
        +
      • #1452: [java] AccessorClassGenerationRule: ArrayIndexOutOfBoundsException with Annotations
      • +
      • #1479: [java] CloseResource: false positive on Statement
      • +
      • #1438: [java] UseNotifyAllInsteadOfNotify: false positive
      • +
      • #1467: [java] UseUtilityClass: can’t correctly check functions with multiple annotations
      • +
      +
    • +
    • java-finalizers +
        +
      • #1440: [java] AvoidCallingFinalize: NPE
      • +
      +
    • +
    • java-imports +
        +
      • #1436: [java] UnnecessaryFullyQualifiedName: false positive on clashing static imports with enums
      • +
      • #1465: [java] UnusedImports: False Positve with javadoc @link
      • +
      +
    • +
    • java-junit +
        +
      • #1373: [java] JUnitAssertionsShouldIncludeMessage: is no longer compatible with TestNG
      • +
      • #1453: [java] TestClassWithoutTestCases: false positive
      • +
      +
    • +
    • java-migrating +
        +
      • #1446: [java] JUnit4TestShouldUseBeforeAnnotation: False positive when TestNG is used
      • +
      +
    • +
    • java-naming +
        +
      • #1431: [java] SuspiciousEqualsMethodName: false positive
      • +
      +
    • +
    • java-optimizations +
        +
      • #1443: [java] RedundantFieldInitializer: False positive for small floats
      • +
      • #1340: [java] UseStringBufferForStringAppends: False Positive with ternary operator
      • +
      +
    • +
    • java-sunsecure +
        +
      • #1476: [java] ArrayIsStoredDirectly: False positive
      • +
      • #1475: [java] MethodReturnsInternalArray: False positive
      • +
      +
    • +
    • java-unnecessary +
        +
      • #1464: [java] UnnecessaryFinalModifier: false positive on a @SafeVarargs method
      • +
      • #1422: [java] UselessQualifiedThis: False positive with Java 8 Function
      • +
      +
    • +
    • java-unusedcode +
        +
      • #1456: [java] UnusedFormalParameter: should ignore overriding methods
      • +
      • #1484: [java] UnusedLocalVariable: false positive - parenthesis
      • +
      • #1480: [java] UnusedModifier: false positive on public modifier used with inner interface in enum
      • +
      • #1428: [java] UnusedPrivateField: False positive when local variable hides member variable +hides member variable
      • +
      +
    • +
    • General +
        +
      • #1425: [core] XMLRenderer: Invalid XML Characters in Output
      • +
      • #1429: [java] Parser Error: Cast in return expression
      • +
      • #1441: [site] PMD: Update documentation how to compile after modularization
      • +
      • #1442: [java] PDMASMClassLoader: Java 9 Jigsaw readiness
      • +
      • #1455: [java] Parser: PMD doesn’t handle Java 8 explicit receiver parameters
      • +
      • #1458: [xml] Performance degradation scanning large XML files with XPath custom rules
      • +
      • #1461: [core] RuleSetFactory: Possible threading issue due to PR#75
      • +
      • #1470: [java] Parser: Error with type-bound lambda
      • +
      • #1478: [core] PMD CLI: Use first language as default if Java is not available
      • +
      • #1481: [core] CPD: no problems found results in blank file instead of empty xml
      • +
      • #1485: [apex] Analysis of some apex classes cause a stackoverflow error
      • +
      • #1488: [apex] Windows line endings falsify the location of issues
      • +
      • #1491: [core] CodeClimateRenderer: corrupt JSON output with real line breaks
      • +
      • #1492: [core] PMD CLI: IncompatibleClassChangeError when running PMD
      • +
      +
    • +
    + +

    27-March-2017 - 5.4.6

    + +

    The PMD team is pleased to announce PMD 5.4.6.

    + +

    This is a bug fixing release.

    + +

    Table Of Contents

    + + + +

    Fixed Issues

    + +
      +
    • general: +
        +
      • #305: [core] PMD not executing under git bash
      • +
      +
    • +
    • java: +
        +
      • #309: [java] Parse error on method reference
      • +
      +
    • +
    • java-design: +
        +
      • #275: [java] FinalFieldCouldBeStatic: Constant in @interface incorrectly reported as “could be made static”
      • +
      +
    • +
    • java-junit: +
        +
      • #285: [java] JUnitTestsShouldIncludeAssertRule should support @Rule as well as @Test(expected = …)
      • +
      +
    • +
    • java-optimizations: +
        +
      • #222: [java] UseStringBufferForStringAppends: False Positive with ternary operator
      • +
      +
    • +
    • java-strings: +
        +
      • #290: [java] InefficientEmptyStringCheck misses String.trim().isEmpty()
      • +
      +
    • +
    + +

    External Contributions

    + +
      +
    • #303: [java] InefficientEmptyStringCheckRule now reports String.trim().isEmpty()
    • +
    • #307: [java] Fix false positive with UseStringBufferForStringAppendsRule
    • +
    • #308: [java] JUnitTestsShouldIncludeAssertRule supports @Rule annotated ExpectedExceptions
    • +
    + +

    25-Februar-2017 - 5.4.5

    + +

    The PMD team is pleased to announce PMD 5.4.5

    + +

    This is a bug fixing release.

    + +

    Table Of Contents

    + + + +

    New and noteworthy

    + +

    Modified Rules

    + +
      +
    • The Java rule UnusedModifier (ruleset java-unusedcode) has been expanded to consider more redundant modifiers. +
        +
      • Annotations marked as abstract.
      • +
      • Nested annotations marked as static.
      • +
      • Nested annotations within another interface or annotation marked as public.
      • +
      • Classes, interfaces or annotations nested within an annotation marked as public or static.
      • +
      • Nested enums marked as static.
      • +
      +
    • +
    + +

    Fixed Issues

    + +
      +
    • general +
        +
      • #234: [core] Zip file stream closes spuriously when loading rulesets
      • +
      • #256: [core] shortnames option is broken with relative paths
      • +
      +
    • +
    • java-basic +
        +
      • #232: [java] SimplifiedTernary: Incorrect ternary operation can be simplified.
      • +
      +
    • +
    • java-coupling +
        +
      • #270: [java] LoD false positive
      • +
      +
    • +
    • java-design +
        +
      • #216: [java] [doc] NonThreadSafeSingleton: Be more explicit as to why double checked locking is not recommended
      • +
      • #219: [java] UnnecessaryLocalBeforeReturn: ClassCastException in switch case with local variable returned
      • +
      +
    • +
    • java-optimizations +
        +
      • #215: [java] RedundantFieldInitializer report for annotation field not explicitly marked as final
      • +
      +
    • +
    • java-unusedcode +
        +
      • #246: [java] UnusedModifier doesn’t check annotations
      • +
      • #247: [java] UnusedModifier doesn’t check annotations inner classes
      • +
      • #248: [java] UnusedModifier doesn’t check static keyword on nested enum declaration
      • +
      • #257: [java] UnusedLocalVariable false positive
      • +
      +
    • +
    + +

    External Contributions

    + +
      +
    • #266: [java] corrected invalid reporting of LoD violation
    • +
    + +

    28-January-2017 - 5.4.4

    + +

    The PMD team is pleased to announce PMD 5.4.4

    + +

    This is a bug fixing release. The most significant changes are on analysis performance.

    + +

    Multithread performance has been enhanced by reducing thread-contention on a +bunch of areas. This is still an area of work, as the speedup of running +multithreaded analysis is still relatively small (4 threads produce less +than a 50% speedup). Future releases will keep improving on this area.

    + +

    Once again, Symbol Table has been an area of great performance improvements. +This time we were able to further improve it’s performance by roughly 10% on all +supported languages. In Java in particular, several more improvements were possible, +improving Symbol Table performance by a whooping 30%, that’s over 5X faster +than PMD 5.4.2, when we first started working on it.

    + +

    Java developers will also appreciate the revamp of CloneMethodMustImplementCloneable, +making it over 500X faster, and PreserveStackTrace which is now 7X faster.

    + +

    New and noteworthy

    + +

    This is a bug fixing release, no major changes were introduced.

    + +

    Modified Rules

    + +

    The Java rule “UseLocaleWithCaseConversions” (ruleset java-design) has been modified, to detect calls +to toLowerCase and to toUpperCase also within method call chains. This leads to more detected cases +and potentially new false positives. +See also bugfix #1556.

    + +

    Fixed Issues

    + +
      +
    • java +
        +
      • #206: [java] Parse error on annotation fields with generics
      • +
      • #207: [java] Parse error on method reference with generics
      • +
      • #208: [java] Parse error with local class with 2 or more annotations
      • +
      • #213: [java] CPD: OutOfMemory when analyzing Lucene
      • +
      +
    • +
    • java-design +
        +
      • #1448: [java] ImmutableField: Private field in inner class gives false positive with lambdas
      • +
      • #1495: [java] UnnecessaryLocalBeforeReturn with assert
      • +
      • #1552: [java] MissingBreakInSwitch - False positive for continue
      • +
      • #1556: [java] UseLocaleWithCaseConversions does not works with ResultSet (false negative)
      • +
      • #177: [java] SingularField with lambdas as final fields
      • +
      +
    • +
    • java-imports +
        +
      • #1546: [java] UnnecessaryFullyQualifiedNameRule doesn’t take into consideration conflict resolution
      • +
      • #1547: [java] UnusedImportRule - False Positive for only usage in Javadoc - {@link ClassName#CONSTANT}
      • +
      • #1555: [java] UnnecessaryFullyQualifiedName: Really necessary fully qualified name
      • +
      +
    • +
    • java-unnecessary +
        +
      • #199: [java] UselessParentheses: Parentheses in return statement are incorrectly reported as useless
      • +
      +
    • +
    • java-strings +
        +
      • #202: [java] [doc] ConsecutiveAppendsShouldReuse is not really an optimization
      • +
      +
    • +
    • XML +
        +
      • #1518: [xml] Error while processing xml file with “.webapp” in the file or directory name
      • +
      +
    • +
    • psql +
        +
      • #1549: [plsql] Parse error for IS [NOT] NULL construct
      • +
      +
    • +
    • javascript +
        +
      • #201: [javascript] template strings are not correctly parsed
      • +
      +
    • +
    • General +
        +
      • #1511: [core] Inconsistent behavior of Rule.start/Rule.end
      • +
      +
    • +
    + +

    External Contributions

    + +
      +
    • #129: [plsql] Added correct parse of IS [NOT] NULL and multiline DML
    • +
    • #152: [java] fixes #1552 continue does not require break
    • +
    • #154: [java] Fix #1547: UnusedImports: Adjust regex to support underscores
    • +
    • #170: [core] Ant Task Formatter encoding issue with XMLRenderer
    • +
    • #200: [javascript] Templatestring grammar fix
    • +
    + +

    04-November-2016 - 5.4.3

    + +

    Summary:

    + +
      +
    • 7 pull requests
    • +
    • 16 bug fixes
    • +
    + +

    Pull Requests:

    + +
      +
    • #35: [javascript] Javascript tokenizer now ignores comment tokens.
    • +
    • #103: [java] Fix for 1501: CyclomaticComplexity rule causes OOM when class reporting is disabled
    • +
    • #110: [java] Fix parser error (issue 1530)
    • +
    • #111: [java] Fix BooleanInstantiationRule for Java 8
    • +
    • #112: [java] Fix ClassCastException on CloneMethodMustImplementCloneable
    • +
    • #113: [java] Fix ClassCastException on SignatureDeclareThrowsException
    • +
    • #119: [plsql] Fix PMD issue 1531- endless loop followed by OOM while parsing (PL)SQL
    • +
    + +

    Bugfixes:

    + +
      +
    • Java +
        +
      • #1501: [java] CyclomaticComplexity rule causes OOM when class reporting is disabled
      • +
      • #1530: [java] Parser exception on Java code
      • +
      • #1490: [java] PMD Error while processing - NullPointerException
      • +
      +
    • +
    • java-basic/BooleanInstantiation +
        +
      • #1533: [java] BooleanInstantiation: ClassCastException with Annotation
      • +
      +
    • +
    • java-comments +
        +
      • #1522: [java] CommentRequired: false positive
      • +
      +
    • +
    • java-design/SingularField +
        +
      • #1494: [java] SingularField: lombok.Data false positive
      • +
      +
    • +
    • java-imports/UnusedImports +
        +
      • #1529: [java] UnusedImports: The created rule violation has no class name
      • +
      +
    • +
    • java-typeresolution/CloneMethodMustImplementCloneable +
        +
      • #1532: [java] CloneMethodMustImplementCloneable: Implemented Interface extends Cloneable
      • +
      • #1534: [java] CloneMethodMustImplementCloneable: ClassCastException with Annotation (java8)
      • +
      +
    • +
    • java-typeresolution/SignatureDeclareThrowsException +
        +
      • #1535: [java] SignatureDeclareThrowsException: ClassCastException with Annotation
      • +
      +
    • +
    • PLSQL +
        +
      • #1520: [plsql] Missing PL/SQL language constructs in parser: Is Of Type, Using
      • +
      • #1527: [plsql] PRAGMA AUTONOMOUS_TRANSACTION gives processing errors
      • +
      • #1531: [plsql] OOM/Endless loop while parsing (PL)SQL
      • +
      +
    • +
    • General +
        +
      • #1499: [core] CPD test break PMD 5.5.1 build on Windows
      • +
      • #1506: [core] When runing any RuleTst, start/end methods not called
      • +
      • #1508: [core] [java] PMD is leaking file handles
      • +
      +
    • +
    + +

    29-May-2016 - 5.4.2

    + +

    New Supported Languages:

    + +
      +
    • CPD supports now Swift (see PR#33).
    • +
    + +

    Feature Request and Improvements:

    + +
      +
    • A JSON-renderer for PMD which is compatible with CodeClimate. See PR#83.
    • +
    • #1360: Provide backwards compatibility for PMD configuration file
    • +
    + +

    Modified Rules:

    + +
      +
    • java-design/UseVargs: public static void main method is ignored now and so are methods, that are annotated +with Override. See PR#79.
    • +
    + +

    Pull Requests:

    + +
      +
    • #27: Added support for Raw String Literals (C++11).
    • +
    • #29: Added support for files with UTF-8 BOM to JSP tokenizer.
    • +
    • #30: Removed file filter for files that are explicitly specified on the CPD command line using the ‘–files’ command line option.
    • +
    • #31: Added file encoding detection to CPD.
    • +
    • #32: Extended Objective-C grammar to accept UTF-8 escapes (\uXXXX) in string literals.
    • +
    • #33: Added support for Swift to CPD.
    • +
    • #79: do not flag public static void main(String[]) as UseVarargs; ignore @Override for UseVarargs
    • +
    • #80: Update mvn-plugin.md
    • +
    • #83: Adds new Code Climate-compliant JSON renderer
    • +
    • #85: #1340 UseStringBufferForStringAppends False Positive with Ternary Operator
    • +
    + +

    Bugfixes:

    + +
      +
    • java-basic/DoubleCheckedLocking: +
        +
      • #1471: False positives for DoubleCheckedLocking
      • +
      +
    • +
    • java-basic/SimplifiedTernary: +
        +
      • #1424: False positive with ternary operator
      • +
      +
    • +
    • java-codesize/TooManyMethods: +
        +
      • #1457: TooManyMethods counts inner class methods
      • +
      +
    • +
    • java-controversial/AvoidUsingShortType: +
        +
      • #1449: false positive when casting a variable to short
      • +
      +
    • +
    • java-design/AccessorClassGeneration: +
        +
      • #1452: ArrayIndexOutOfBoundsException with Annotations for AccessorClassGenerationRule
      • +
      +
    • +
    • java-design/CloseResource +
        +
      • #1479: CloseResource false positive on Statement
      • +
      +
    • +
    • java-design/UseUtilityClass: +
        +
      • #1467: UseUtilityClass can’t correctly check functions with multiple annotations
      • +
      +
    • +
    • java-imports/UnusedImports: +
        +
      • #1465: False Positve UnusedImports with javadoc @link
      • +
      +
    • +
    • java-junit/TestClassWithoutTestCases: +
        +
      • #1453: Test Class Without Test Cases gives false positive
      • +
      +
    • +
    • java-optimizations/UseStringBufferForStringAppends: +
        +
      • #1340: UseStringBufferForStringAppends False Positive with ternary operator
      • +
      +
    • +
    • java-sunsecure/ArrayIsStoredDirectly: +
        +
      • #1475: False positive of MethodReturnsInternalArray
      • +
      • #1476: False positive of ArrayIsStoredDirectly
      • +
      +
    • +
    • java-unnecessary/UnnecessaryFinalModifier: +
        +
      • #1464: UnnecessaryFinalModifier false positive on a @SafeVarargs method
      • +
      +
    • +
    • java-unusedcode/UnusedFormalParameter: +
        +
      • #1456: UnusedFormalParameter should ignore overriding methods
      • +
      +
    • +
    • java-unusedcode/UnusedLocalVariable +
        +
      • #1484: UnusedLocalVariable - false positive - parenthesis
      • +
      +
    • +
    • java-unusedcode/UnusedModifier +
        +
      • #1480: false positive on public modifier used with inner interface in enum
      • +
      +
    • +
    • General +
        +
      • #1455: PMD doesn’t handle Java 8 explicit receiver parameters
      • +
      • #1458: Performance degradation scanning large XML files with XPath custom rules
      • +
      • #1461: Possible threading issue due to PR#75
      • +
      • #1470: Error with type-bound lambda
      • +
      • #1481: no problems found results in blank file instead of empty xml
      • +
      +
    • +
    + +

    CLI Changes:

    + +
      +
    • CPD: If a complete filename is specified, the language dependent filename filter is not applied. This allows +to scan files, that are not using the standard file extension. If a directory is specified, the filename filter +is still applied and only those files with the correct file extension of the language are scanned.
    • +
    • CPD: If no problems found, an empty report will be output instead of nothing. See also #1481
    • +
    • New command line parameter for PMD: -norulesetcompatibility - this disables the ruleset factory +compatibility filter and fails, if e.g. an old rule name is used in the ruleset. +See also #1360. +This option is also available for the ant task: <noRuleSetCompatibility>true</noRuleSetCompatibility>.
    • +
    + +

    04-December-2015 - 5.4.1

    + +

    Feature Request and Improvements:

    + +
      +
    • CPD: New command line parameter --ignore-usings: Ignore using directives in C# when comparing text.
    • +
    + +

    Modified Rules:

    + +
      +
    • java-comments/CommentRequired: New property serialVersionUIDCommentRequired which controls the comment requirements +for serialVersionUID fields. By default, no comment is required for this field.
    • +
    + +

    Pull Requests:

    + +
      +
    • #25: Added option to exclude C# using directives from CPD analysis
    • +
    • #72: Added capability in Java and JSP parser for tracking tokens.
    • +
    • #74: Fix rendering CommentDefaultAccessModifier description as code
    • +
    • #75: RuleSetFactory Performance Enhancement
    • +
    + +

    Bugfixes:

    + +
      +
    • java-comments/CommentDefaultAccessModifier +
        +
      • #1430: CommentDefaultAccessModifier triggers on field +annotated with @VisibleForTesting
      • +
      +
    • +
    • java-comments/CommentRequired +
        +
      • #1434: CommentRequired raises violation on serialVersionUID field
      • +
      +
    • +
    • java-design/UseNotifyAllInsteadOfNotify +
        +
      • #1438: UseNotifyAllInsteadOfNotify gives false positive
      • +
      +
    • +
    • java-finalizers/AvoidCallingFinalize +
        +
      • #1440: NPE in AvoidCallingFinalize
      • +
      +
    • +
    • java-imports/UnnecessaryFullyQualifiedName +
        +
      • #1436: UnnecessaryFullyQualifiedName false positive on clashing static imports with enums
      • +
      +
    • +
    • java-junit/JUnitAssertionsShouldIncludeMessage +
        +
      • #1373: JUnitAssertionsShouldIncludeMessage is no longer compatible with TestNG
      • +
      +
    • +
    • java-migrating/JUnit4TestShouldUseBeforeAnnotation +
        +
      • #1446: False positive with JUnit4TestShouldUseBeforeAnnotation when TestNG is used
      • +
      +
    • +
    • java-naming/SuspiciousEqualsMethodName +
        +
      • #1431: SuspiciousEqualsMethodName false positive
      • +
      +
    • +
    • java-optimizations/RedundantFieldInitializer +
        +
      • #1443: RedundantFieldInitializer: False positive for small floats
      • +
      +
    • +
    • java-unnecessary/UselessQualifiedThis +
        +
      • #1422: UselessQualifiedThis: False positive with Java 8 Function
      • +
      +
    • +
    • java-unusedcode/UnusedPrivateField +
        +
      • #1428: False positive in UnusedPrivateField when local variable +hides member variable
      • +
      +
    • +
    • General +
        +
      • #1425: Invalid XML Characters in Output
      • +
      • #1429: Java - Parse Error: Cast in return expression
      • +
      • #1441: PMD: Update documentation how to compile after modularization
      • +
      +
    • +
    + +

    04-October-2015 - 5.4.0

    + +
    +Note: PMD 5.4.0 requires JDK 1.7 or above. +
    + +

    Summary:

    + +
      +
    • 9 new rules
    • +
    • 4 features requests
    • +
    • 18 pull requests
    • +
    + +

    Feature Request and Improvements:

    + +
      +
    • #1344: AbstractNaming should check reverse
    • +
    • #1361: ShortVariable and ShortMethodName configuration
    • +
    • #1414: Command line parameter to disable “failOnViolation” behavior +PMD and CPD Command Line Interfaces have a new optional parameter: failOnViolation. Executing PMD with the option +-failOnViolation false will perform the PMD checks but won’t fail the build and still exit with status 0. +This is useful if you only want to generate the report with violations but don’t want to fail your build.
    • +
    • #1420: UnusedPrivateField: Ignore fields if using lombok
    • +
    + +

    New Rules:

    + +
      +
    • +

      Java:

      + +
        +
      • +

        Basic: SimplifiedTernary (rulesets/java/basic.xml/SimplifiedTernary)
        +Ternary operator with a boolean literal can be simplified with a boolean +expression.

        +
      • +
      • +

        Clone: CloneMethodMustBePublic (rulesets/java/clone.xml/CloneMethodMustBePublic)
        +The java manual says “By convention, +classes that implement the Cloneable interface should override Object.clone (which is protected) +with a public method.”

        +
      • +
      • +

        Clone: CloneMethodReturnTypeMustMatchClassName (rulesets/java/clone.xml/CloneMethodReturnTypeMustMatchClassName)
        +If a class implements Cloneable +the return type of the method clone() must be the class name.

        +
      • +
      • +

        Comments: CommentDefaultAccessModifier (rulesets/java/comments.xml/CommentDefaultAccessModifier)
        +In order to avoid mistakes with +forgotten access modifiers for methods, this rule ensures, that you explicitly mark the usage of the +default access modifier by placing a comment.

        +
      • +
      • +

        Design: SingletonClassReturningNewInstance (rulesets/java/design.xml/SingletonClassReturningNewInstance)
        +Verifies that the method called getInstance returns a cached instance and not always a fresh, new instance.

        +
      • +
      • +

        Design: SingleMethodRule (rulesets/java/design.xml/SingleMethodSingletonRule)
        +Verifies that there is only one method called +getInstance. If there are more methods that return the singleton, then it can easily happen, that these +are not the same instances - and thus no singleton.

        +
      • +
      • +

        Unnecessary: UselessQualifiedThis (rulesets/java/unnecessary.xml/UselessQualifiedThis)
        +Flags unnecessary qualified usages +of this, when this alone would be unique. E.g. use just this instead of Foo.this.

        +
      • +
      +
    • +
    • +

      Maven POM: (The rules can be found in the pmd-xml module)

      + +
        +
      • +

        Basic: ProjectVersionAsDependencyVersion (rulesets/pom/basic.xml/ProjectVersionAsDependencyVersion)
        +Checks the usage of ${project.version} in Maven POM files.

        +
      • +
      • +

        Basic: InvalidDependencyTypes (rulesets/pom/basic.xml/InvalidDependencyTypes)
        +Verifies that only the default types (jar, war, …) for dependencies are used.

        +
      • +
      +
    • +
    + +

    Ruleset snippet to activate the new rules:

    + +
    <rule ref="rulesets/java/basic.xml/SimplifiedTernary"/>
    +<rule ref="rulesets/java/clone.xml/CloneMethodReturnTypeMustMatchClassName"/>
    +<rule ref="rulesets/java/clone.xml/CloneMethodMustBePublic"/>
    +<rule ref="rulesets/java/comments.xml/CommentDefaultAccessModifier"/>
    +<rule ref="rulesets/java/design.xml/SingleMethodSingleton"/>
    +<rule ref="rulesets/java/design.xml/SingletonClassReturningNewInstance"/>
    +<rule ref="rulesets/java/unnecessary.xml/UselessQualifiedThis"/>
    +
    +<rule ref="rulesets/pom/basic.xml/ProjectVersionAsDependencyVersion"/>
    +<rule ref="rulesets/pom/basic.xml/InvalidDependencyTypes"/>
    +
    + +

    Modified Rules:

    + +
      +
    • +

      Java

      + +
        +
      • +

        Basic: CheckResultSet (rulesets/java/basic.xml/CheckResultSet)
        +Do not require to check the result of a navigation method, if it is returned.

        +
      • +
      • +

        JUnit: UseAssertTrueInsteadOfAssertEquals (rulesets/java/junit.xml/UseAssertTrueInsteadOfAssertEquals)
        +This rule also flags assertEquals, that use Boolean.TRUE/FALSE constants.

        +
      • +
      • +

        Naming: AbstractNaming (rulesets/java/naming.xml/AbstractNaming)
        +By default, this rule flags now classes, +that are named “Abstract” but are not abstract. This behavior can be disabled by setting +the new property strict to false.

        +
      • +
      • +

        Naming: ShortMethodName (rulesets/java/naming.xml/ShortMethodName)
        +Additional property minimum to configure the minimum required length of a method name.

        +
      • +
      • +

        Naming: ShortVariable (rulesets/java/naming.xml/ShortVariable)
        +Additional property minimum to configure the minimum required length of a variable name.

        +
      • +
      • +

        UnusedCode: UnusedPrivateField (rulesets/java/unusedcode.xml/UnusedPrivateField)
        +This rule won’t trigger anymore if Lombok is in use. +See #1420.

        +
      • +
      +
    • +
    + +

    Renamed Rules:

    + +
      +
    • Java +
        +
      • Design: UseSingleton - UseUtilityClass (rulesets/java/design.xml/UseUtilityClass)
        +The rule “UseSingleton” has been renamed to “UseUtilityClass”. +See also bugs #1059 and #1339.
      • +
      +
    • +
    + +

    Removed Rules:

    + +
      +
    • Java +
        +
      • +

        Basic: The following rules of ruleset “Basic” were marked as deprecated and are removed with this release now:
        +
        +EmptyCatchBlock, EmptyIfStatement, EmptyWhileStmt, EmptyTryBlock, EmptyFinallyBlock, EmptySwitchStatements, EmptySynchronizedBlock, EmptyStatementNotInLoop, EmptyInitializer, EmptyStatementBlock, EmptyStaticInitializer +

        +UnnecessaryConversionTemporary, UnnecessaryReturn, UnnecessaryFinalModifier, UselessOverridingMethod, UselessOperationOnImmutable, UnusedNullCheckInEquals, UselessParentheses +

        +These rules are still available in the rulesets “Empty” (rulesets/java/empty.xml) and +“Unnecessary” (rulesets/java/unnecessary.xml) respectively.

        +
      • +
      • +

        Design: The rule “UncommentedEmptyMethod” has been renamed last release to “UncommentedEmptyMethodBody”. The +old rule name reference has been removed with this release now.

        +
      • +
      • +

        Controversial: The rule “BooleanInversion” has been deprecated last release +and has been removed with this release completely.

        +
      • +
      +
    • +
    + +

    Pull Requests:

    + +
      +
    • #21: Added PMD Rules for Singleton pattern violations.
    • +
    • #23: Extended Objective-C grammar to accept Unicode characters in identifiers
    • +
    • #54: Add a new rulesets for Maven’s POM rules
    • +
    • #55: Fix run.sh for paths with spaces
    • +
    • #56: Adding support for WSDL rules
    • +
    • #57: Add default access modifier as comment rule
    • +
    • #58: Add rule for unnecessary literal boolean in ternary operators
    • +
    • #59: Add check to Boxed booleans in UseAssertTrueInsteadOfAssertEquals rule
    • +
    • #60: Add UselessQualifiedThisRule
    • +
    • #61: Add CloneMethodReturnTypeMustMatchClassName rule
    • +
    • #62: Add CloneMethodMustBePublic rule
    • +
    • #63: Change CheckResultSet to allow for the result of the navigation methods to be returned
    • +
    • #65: Fix ClassCastException in UselessOverridingMethodRule.
    • +
    • #66: #1370 ConsecutiveAppendsShouldReuse not detected properly on StringBuffer
    • +
    • #67: Use Path instead of string to check file exclusions to fix windows-only bug
    • +
    • #68: #1370 ConsecutiveAppendsShouldReuse not detected properly on StringBuffer
    • +
    • #69: #1371 InsufficientStringBufferDeclaration not detected properly on StringBuffer
    • +
    • #70: Fix code example
    • +
    + +

    Bugfixes:

    + +
      +
    • java-unusedcode/UnusedPrivateMethod: +
        +
      • #1412: UnusedPrivateMethod false positive: Issue #1403 not completely solved
      • +
      +
    • +
    + +

    API Changes:

    + +
      +
    • +

      pmd requires now JDK 1.7 or above.

      +
    • +
    • +

      pmd-core: net.sourceforge.pmd.lang.symboltable.Scope:

      + +

      The method addNameOccurrence returns now a Set of +NameDeclarations to which the given occurrence has been added. This is useful in case there are ambiguous declarations +of methods.

      +
    • +
    • +

      pmd-core: net.sourceforge.pmd.lang.symboltable.AbstractScope:

      + +

      The method findVariableHere returns now +a Set of NameDeclarations which match the given occurrence. This is useful in case there are ambiguous declarations +of methods.

      +
    • +
    + +

    04-November-2016 - 5.3.8

    + +

    Summary

    + +
      +
    • 1 feature requests
    • +
    • 6 pull requests
    • +
    • 17 bug fixes
    • +
    + +

    Feature Requests and Improvements:

    + +
      +
    • #1360: [core] [java] Provide backwards compatibility for PMD configuration file
    • +
    + +

    Pull Requests:

    + +
      +
    • #35: [javascript] Javascript tokenizer now ignores comment tokens.
    • +
    • #103: [java] Fix for 1501: CyclomaticComplexity rule causes OOM when class reporting is disabled
    • +
    • #111: [java] Fix BooleanInstantiationRule for Java 8
    • +
    • #112: [java] Fix ClassCastException on CloneMethodMustImplementCloneable
    • +
    • #113: [java] Fix ClassCastException on SignatureDeclareThrowsException
    • +
    • #119: [plsql] Fix PMD issue 1531- endless loop followed by OOM while parsing (PL)SQL
    • +
    + +

    Bugfixes:

    + +
      +
    • java +
        +
      • #1501: [java] [apex] CyclomaticComplexity rule causes OOM when class reporting is disabled
      • +
      +
    • +
    • java-basic/BooleanInstantiation +
        +
      • #1533: [java] BooleanInstantiation: ClassCastException with Annotation
      • +
      +
    • +
    • java-comments +
        +
      • #1522: [java] CommentRequired: false positive
      • +
      +
    • +
    • java-design/CloseResource +
        +
      • #1479: [java] CloseResource: false positive on Statement
      • +
      +
    • +
    • java-imports/UnusedImports +
        +
      • #1529: [java] UnusedImports: The created rule violation has no class name
      • +
      +
    • +
    • java-typeresolution/CloneMethodMustImplementCloneable +
        +
      • #1532: [java] CloneMethodMustImplementCloneable: Implemented Interface extends Cloneable
      • +
      • #1534: [java] CloneMethodMustImplementCloneable: ClassCastException with Annotation (java8)
      • +
      +
    • +
    • java-typeresolution/SignatureDeclareThrowsException +
        +
      • #1535: [java] SignatureDeclareThrowsException: ClassCastException with Annotation
      • +
      +
    • +
    • java-unusedcode/UnusedLocalVariable +
        +
      • #1484: [java] UnusedLocalVariable: false positive - parenthesis
      • +
      +
    • +
    • java-unusedcode/UnusedModifier +
        +
      • #1480: [java] UnusedModifier: false positive on public modifier used with inner interface in enum
      • +
      +
    • +
    • plsql +
        +
      • #1520: [plsql] Missing PL/SQL language constructs in parser: Is Of Type, Using
      • +
      • #1527: [plsql] PRAGMA AUTONOMOUS_TRANSACTION gives processing errors
      • +
      • #1531: [plsql] OOM/Endless loop while parsing (PL)SQL
      • +
      +
    • +
    • General +
        +
      • #1481: [core] CPD: no problems found results in blank file instead of empty xml
      • +
      • #1499: [core] CPD test break PMD 5.5.1 build on Windows
      • +
      • #1506: [core] When runing any RuleTst, start/end methods not called
      • +
      • #1508: [core] [java] PMD is leaking file handles
      • +
      +
    • +
    + +

    API Changes:

    + +
      +
    • New command line parameter for PMD: -norulesetcompatibility - this disables the ruleset factory +compatibility filter and fails, if e.g. an old rule name is used in the ruleset. +See also #1360. +This option is also available for the ant task: <noRuleSetCompatibility>true</noRuleSetCompatibility>.
    • +
    • CPD: If no problems found, an empty report will be output instead of nothing. See also #1481
    • +
    + +

    30-April-2016 - 5.3.7

    + +

    New Supported Languages:

    + +
      +
    • CPD supports now Swift (see PR#33).
    • +
    + +

    Feature Request and Improvements:

    + +
      +
    • A JSON-renderer for PMD which is compatible with CodeClimate. See PR#83.
    • +
    + +

    Modified Rules:

    + +
      +
    • java-design/UseVargs: public static void main method is ignored now and so are methods, that are annotated +with Override. See PR#79.
    • +
    + +

    Pull Requests:

    + +
      +
    • #27: Added support for Raw String Literals (C++11).
    • +
    • #29: Added support for files with UTF-8 BOM to JSP tokenizer.
    • +
    • #30: Removed file filter for files that are explicitly specified on the CPD command line using the ‘–files’ command line option.
    • +
    • #31: Added file encoding detection to CPD.
    • +
    • #32: Extended Objective-C grammar to accept UTF-8 escapes (\uXXXX) in string literals.
    • +
    • #33: Added support for Swift to CPD.
    • +
    • #79: do not flag public static void main(String[]) as UseVarargs; ignore @Override for UseVarargs
    • +
    • #80: Update mvn-plugin.md
    • +
    • #83: Adds new Code Climate-compliant JSON renderer
    • +
    • #85: #1340 UseStringBufferForStringAppends False Positive with Ternary Operator
    • +
    + +

    Bugfixes:

    + +
      +
    • java-basic/DoubleCheckedLocking: +
        +
      • #1471: False positives for DoubleCheckedLocking
      • +
      +
    • +
    • java-codesize/TooManyMethods: +
        +
      • #1457: TooManyMethods counts inner class methods
      • +
      +
    • +
    • java-controversial/AvoidUsingShortType: +
        +
      • #1449: false positive when casting a variable to short
      • +
      +
    • +
    • java-design/AccessorClassGeneration: +
        +
      • #1452: ArrayIndexOutOfBoundsException with Annotations for AccessorClassGenerationRule
      • +
      +
    • +
    • java-design/UseUtilityClass: +
        +
      • #1467: UseUtilityClass can’t correctly check functions with multiple annotations
      • +
      +
    • +
    • java-imports/UnusedImports: +
        +
      • #1465: False Positve UnusedImports with javadoc @link
      • +
      +
    • +
    • java-junit/TestClassWithoutTestCases: +
        +
      • #1453: Test Class Without Test Cases gives false positive
      • +
      +
    • +
    • java-optimizations/UseStringBufferForStringAppends: +
        +
      • #1340: UseStringBufferForStringAppends False Positive with ternary operator
      • +
      +
    • +
    • java-sunsecure/ArrayIsStoredDirectly: +
        +
      • #1475: False positive of MethodReturnsInternalArray
      • +
      • #1476: False positive of ArrayIsStoredDirectly
      • +
      +
    • +
    • java-unnecessary/UnnecessaryFinalModifier: +
        +
      • #1464: UnnecessaryFinalModifier false positive on a @SafeVarargs method
      • +
      +
    • +
    • java-unusedcode/UnusedFormalParameter: +
        +
      • #1456: UnusedFormalParameter should ignore overriding methods
      • +
      +
    • +
    • General +
        +
      • #1455: PMD doesn’t handle Java 8 explicit receiver parameters
      • +
      • #1458: Performance degradation scanning large XML files with XPath custom rules
      • +
      • #1461: Possible threading issue due to PR#75
      • +
      • #1470: Error with type-bound lambda
      • +
      +
    • +
    + +

    CLI Changes:

    + +
      +
    • CPD: If a complete filename is specified, the language dependent filename filter is not applied. This allows +to scan files, that are not using the standard file extension. If a directory is specified, the filename filter +is still applied and only those files with the correct file extension of the language are scanned.
    • +
    + +

    04-December-2015 - 5.3.6

    + +

    Feature Request and Improvements:

    + +
      +
    • CPD: New command line parameter --ignore-usings: Ignore using directives in C# when comparing text.
    • +
    + +

    Modified Rules:

    + +
      +
    • java-comments/CommentRequired: New property serialVersionUIDCommentRequired which controls the comment requirements +for serialVersionUID fields. By default, no comment is required for this field.
    • +
    + +

    Pull Requests:

    + +
      +
    • #25: Added option to exclude C# using directives from CPD analysis +
        +
      • Note: This also contains the fix from #23
      • +
      +
    • +
    • #72: Added capability in Java and JSP parser for tracking tokens.
    • +
    • #75: RuleSetFactory Performance Enhancement
    • +
    + +

    Bugfixes:

    + +
      +
    • java-comments/CommentRequired +
        +
      • #1434: CommentRequired raises violation on serialVersionUID field
      • +
      +
    • +
    • java-design/UseNotifyAllInsteadOfNotify +
        +
      • #1438: UseNotifyAllInsteadOfNotify gives false positive
      • +
      +
    • +
    • java-finalizers/AvoidCallingFinalize +
        +
      • #1440: NPE in AvoidCallingFinalize
      • +
      +
    • +
    • java-imports/UnnecessaryFullyQualifiedName +
        +
      • #1436: UnnecessaryFullyQualifiedName false positive on clashing static imports with enums
      • +
      +
    • +
    • java-junit/JUnitAssertionsShouldIncludeMessage +
        +
      • #1373: JUnitAssertionsShouldIncludeMessage is no longer compatible with TestNG
      • +
      +
    • +
    • java-migrating/JUnit4TestShouldUseBeforeAnnotation +
        +
      • #1446: False positive with JUnit4TestShouldUseBeforeAnnotation when TestNG is used
      • +
      +
    • +
    • java-naming/SuspiciousEqualsMethodName +
        +
      • #1431: SuspiciousEqualsMethodName false positive
      • +
      +
    • +
    • java-optimizations/RedundantFieldInitializer +
        +
      • #1443: RedundantFieldInitializer: False positive for small floats
      • +
      +
    • +
    • java-unusedcode/UnusedPrivateField +
        +
      • #1428: False positive in UnusedPrivateField when local variable hides member variable
      • +
      +
    • +
    • General +
        +
      • #1429: Java - Parse Error: Cast in return expression
      • +
      • #1425: Invalid XML Characters in Output
      • +
      • #1441: PMD: Update documentation how to compile after modularization
      • +
      +
    • +
    + +

    04-October-2015 - 5.3.5

    + +

    Modified Rules:

    + +
      +
    • java-design/CloseResource: New Property closeAsDefaultTarget which is true by default to stay +backwards compatible. If this property is true, the rule will make sure, that close itself is +always considered as a closeTarget - no matter whether it is configured with the closeTargets property +or not.
    • +
    + +

    Pull Requests:

    + +
      +
    • #71: #1410 Improve description of DefaultPackage rule
    • +
    + +

    Bugfixes:

    + +
      +
    • java-controversial/DefaultPackage: +
        +
      • #1410: DefaultPackage triggers on field annotated with @VisibleForTesting
      • +
      +
    • +
    • java-design/CloseResource: +
        +
      • #1387: CloseResource has false positive for ResultSet
      • +
      +
    • +
    • java-optimizations/RedundantFieldInitializer +
        +
      • #1418: RedundantFieldInitializer false positive with large long value
      • +
      +
    • +
    • java-strings/InsufficientStringBufferDeclaration: +
        +
      • #1409: NullPointerException in InsufficientStringBufferRule
      • +
      • #1413: False positive StringBuffer constructor with ?: int value
      • +
      +
    • +
    • java-unnecessary/UselessParentheses: +
        +
      • #1407: UselessParentheses “&” and “+” operator precedence
      • +
      +
    • +
    + +

    18-September-2015 - 5.3.4

    + +

    Bugfixes:

    + +
      +
    • #1370: ConsecutiveAppendsShouldReuse not detected properly on StringBuffer
    • +
    • #1371: InsufficientStringBufferDeclaration not detected properly on StringBuffer
    • +
    • #1380: InsufficientStringBufferDeclaration false positive when literal string passed to a lookup service
    • +
    • #1384: NullPointerException in ConsecutiveLiteralAppendsRule
    • +
    • #1388: ConstructorCallsOverridableMethodRule doesn’t work with params?
    • +
    • #1392: SimplifyStartsWith false-negative
    • +
    • #1393: PMD hanging during DataflowAnomalyAnalysis
    • +
    • #1394: dogfood.xml - Unable to exclude rules [UncommentedEmptyMethod]
    • +
    • #1395: UnusedPrivateMethod false positive for array element method call
    • +
    • #1396: PrematureDeclaration lambda false positive
    • +
    • #1397: StringToString should ignore method references
    • +
    • #1398: False positive for GuardLogStatementJavaUtil with Log4j
    • +
    • #1399: False positive for VariableNamingConventions with annotation @interface
    • +
    • #1400: False positive with JUnit4TestShouldUseBeforeAnnotation
    • +
    • #1401: False positive for StringBuilder.append called with constructor
    • +
    • #1402: Windows-Only: File exclusions are not case insensitive
    • +
    • #1403: False positive UnusedPrivateMethod with JAVA8
    • +
    • #1404: Java8 ‘Unnecessary use of fully qualified name’ in Streams Collector
    • +
    • #1405: UnusedPrivateMethod false positive?
    • +
    + +

    25-July-2015 - 5.3.3

    + +

    Pull Requests:

    + +
      +
    • #55: Fix run.sh for paths with spaces
    • +
    + +

    Bugfixes:

    + +
      +
    • #1364: FieldDeclarationsShouldBeAtStartOfClass false positive using multiple annotations
    • +
    • #1365: Aggregated javadoc report is missing
    • +
    • #1366: UselessParentheses false positive on multiple equality operators
    • +
    • #1369: ConsecutiveLiteralAppends not detected properly on StringBuffer
    • +
    • #1372: False Negative for CloseResource rule.
    • +
    • #1375: CloseResource not detected properly
    • +
    • #1376: CompareObjectsWithEquals fails for type annotated method parameter
    • +
    • #1379: PMD CLI: Cannot specify multiple properties
    • +
    • #1381: CPD Cannot use CSV/VS Renderers because they don’t support encoding property
    • +
    + +

    22-May-2015 - 5.3.2

    + +

    Bugfixes:

    + +
      +
    • #1330: AvoidReassigningParameters does not work with varargs
    • +
    • #1335: GuardLogStatementJavaUtil should not apply to SLF4J Logger
    • +
    • #1342: UseConcurrentHashMap false positive (with documentation example)
    • +
    • #1343: MethodNamingConventions for overrided methods
    • +
    • #1345: UseCollectionIsEmpty throws NullPointerException
    • +
    • #1353: False positive “Only One Return” with lambda
    • +
    • #1354: Complex FieldDeclarationsShouldBeAtStartOfClass false positive with Spring annotations
    • +
    • #1355: NullPointerException in a java file having a single comment line
    • +
    + +

    20-April-2015 - 5.3.1

    + +

    New/Modified/Deprecated Rules:

    + +
      +
    • Language Java, ruleset design.xml: The rule “UseSingleton” has been renamed to “UseUtilityClass”. +See also bugs #1059 and #1339.
    • +
    + +

    Pull Requests:

    + +
      +
    • #53: Fix some NullPointerExceptions
    • +
    + +

    Bugfixes:

    + +
      +
    • #1332: False Positive: UnusedPrivateMethod
    • +
    • #1333: Error while processing Java file with Lambda expressions
    • +
    • #1337: False positive “Avoid throwing raw exception types” when exception is not thrown
    • +
    • #1338: The pmd-java8 POM bears the wrong parent module version
    • +
    + +

    April 1, 2015 - 5.3.0

    + +

    New Supported Languages:

    + +
      +
    • Matlab (CPD)
    • +
    • Objective-C (CPD)
    • +
    • Python (CPD)
    • +
    • Scala (CPD)
    • +
    + +

    Feature Requests and Improvements:

    + +
      +
    • XML: Line numbers for XML documents are more accurate. This is a further improvement of #1054.
    • +
    • CPD: New output format ‘csv_with_linecount_per_file’
    • +
    • #1320: Enhance SimplifyBooleanReturns checks
    • +
    • PMD exits with status 4 if any violations have been found. This behavior has been introduced to ease PMD +integration into scripts or hooks, such as SVN hooks.
    • +
    + +

    New/Modified/Deprecated Rules:

    + +

    The following rules have been +enhanced +:

    + +
      +
    • Language Java, ruleset design.xml: The rule “SimplifyBooleanReturns” now also marks methods where the else case is omitted and just a return. +See also feature #1320.
    • +
    + +

    The following rules are marked as +deprecated +and will be removed with the next release of PMD.

    + +
      +
    • +

      Language Java, ruleset basic.xml: The following rules have been moved into the empty.xml ruleset. You’ll need +to enable the “empty” ruleset explicitly from now on, if you want to have these rules executed:

      + +

      EmptyCatchBlock, EmptyIfStatement, EmptyWhileStmt, EmptyTryBlock, EmptyFinallyBlock, EmptySwitchStatements, +EmptySynchronizedBlock, EmptyStatementNotInLoop, EmptyInitializer, EmptyStatementBlock, EmptyStaticInitializer.

      +
    • +
    • +

      Language Java, ruleset basic.xml: The following rules have been moved into the unnecessary.xml ruleset. You’ll need +to enable the “unnecessary” ruleset explicitly from now on, if you want to have these rules executed:

      + +

      UnnecessaryConversionTemporary, UnnecessaryReturn, UnnecessaryFinalModifier, UselessOverridingMethod, +UselessOperationOnImmutable, UnusedNullCheckInEquals, UselessParentheses.

      +
    • +
    • +

      Language Java, ruleset design.xml: The rule “UncommentedEmptyMethod” has been renamed to “UncommentedEmptyMethodBody”. +See also bug #1283.

      +
    • +
    • +

      Language Java, ruleset controversial.xml: The rule “BooleanInversion” is deprecated and will be removed with +the next release. See #1277 for more details.

      +
    • +
    + +

    Pull Requests:

    + +
      +
    • #11: Added support for Python to CPD.
    • +
    • #12: Added support for Matlab to CPD.
    • +
    • #13: Added support for Objective-C to CPD.
    • +
    • #14: Added support for Scala to CPD.
    • +
    • #15: (pmd-cs) Fixed incorrect line numbers after mutiline comments and verbatim strings.
    • +
    • #16: Fixed several C++ lexical / tokenize errors.
    • +
    • #17: Fixed ‘–files’ command line option of CPD, so it also works for files and not only for directories.
    • +
    • #18: Created extra CSV output format csv_with_linecount_per_file which outputs the correct line count per file.
    • +
    • #19: Fixed exit status of PMD when error occurs
    • +
    • #48: Handle NoClassDefFoundError along ClassNotFoundException
    • +
    • #49: Fix some false positives in UnusedPrivateField
    • +
    • #50: Add missing assertions in JUnitAssertionsShouldIncludeMessage test
    • +
    • #51: [JUnit] Check assertion message present in assertEquals with delta
    • +
    • #52: Improves JDK8 support for default methods and static methods in interfaces
    • +
    + +

    Bugfixes:

    + +
      +
    • #914: False +ve from UnusedImports with wildcard static imports
    • +
    • #1197: JUnit4TestShouldUseTestAnnotation for private method
    • +
    • #1277: Delete BooleanInversion as it makes no sense
    • +
    • #1283: Rename UncommentedEmptyMethod to UncommentedEmptyMethodBody
    • +
    • #1296: PMD UnusedPrivateMethod invalid detection of ‘private void method(int,boolean,Integer…)’
    • +
    • #1298: Member variable int type with value 0xff000000 causes processing error
    • +
    • #1299: MethodReturnsInternalArray false positive
    • +
    • #1302: False Positive: UnusedPrivateField when accessed by inner class
    • +
    • #1303: OverrideBothEqualsAndHashcodeRule does not work on class implements resolvable interfaces
    • +
    • #1304: UseCollectionIsEmpty false positive comparing to 1
    • +
    • #1305: variable declaration inside switch causes ClassCastException
    • +
    • #1306: False positive on duplicate when using static imports
    • +
    • #1307: False positive: SingularField and lambda-expression
    • +
    • #1308: PMD runs endlessly on some generated files
    • +
    • #1312: Rule reference must not override rule name of referenced rule
    • +
    • #1313: Missing assertion message in assertEquals with delta not detected
    • +
    • #1316: Multi Rule Properties with delimiter not possible
    • +
    • #1317: RuntimeException when parsing class with multiple lambdas
    • +
    • #1319: PMD stops with NoClassDefFoundError (typeresolution)
    • +
    • #1321: CPD format XML fails with NullPointer
    • +
    • #1322: MethodReturnsInternalArray on private methods
    • +
    • #1323: False positive case of UseAssertTrueInsteadOfAssertEquals
    • +
    • #1324: MethodReturnsInternalArray false positive with clone()
    • +
    • #1325: Inner class declared within a method fails to parse (ClassCastException)
    • +
    • #1326: PMD 5.3.0-SNAPSHOT doesn’t compile under Windows
    • +
    + +

    API Changes:

    + +
      +
    • +

      net.sourceforge.pmd.cpd.Match.iterator() now returns an iterator of the new type net.sourceforge.pmd.cpd.Mark instead +of TokenEntry. A Mark contains all the informations about each single duplication, including the TokenEntry via Mark.getToken(). +This Mark is useful for reporting the correct line count for each duplication. Previously only one line count was available. +As for some languages CPD can be instructed to ignore comments, the line count could be different in the different files +for the same duplication.

      +
    • +
    • +

      pmd-test: The utility class StreamUtil is deprecated. Just use Apache Commons IO Utils instead.

      +
    • +
    + +

    December 21, 2014 - 5.2.3:

    + +

    Feature Requests and Improvements:

    + +
      +
    • #1288: MethodNamingConventions for native should be deactivated
    • +
    • #1293: Disable VariableNamingConventions for native methods
    • +
    + +

    Modified Rules:

    + + + +

    Pull requests:

    + +
      +
    • #45: #1290 RuleSetReferenceId does not process HTTP(S) correctly.
    • +
    • #46: Allow byte[] as no-vargars last argument
    • +
    • #47: Allow byte[] data and byte data[] as no-varargs last argument
    • +
    + +

    Bugfixes:

    + +
      +
    • #1252: net.sourceforge.pmd.lang.ast.TokenMgrError: Lexical error in file xxx.cpp
    • +
    • #1289: CommentRequired not ignored if javadoc {@inheritDoc} anon inner classes
    • +
    • #1290: RuleSetReferenceId does not process HTTP(S) correctly.
    • +
    • #1294: False positive UnusedPrivateMethod with public inner enum from another class
    • +
    + +

    December 3, 2014 - 5.2.2:

    + +

    New Parameters for CPD:

    + +

    For the language cpp, the following new parameters are supported:

    + +
      +
    • --no-skip-blocks: Disables skipping of code blocks like a pre-processor. This is by default enabled.
    • +
    • --skip-blocks-pattern: Pattern to find the blocks to skip. Start and End pattern separated by “|”. Default value is “#if 0|#endif”.
    • +
    + +

    Bugfixes:

    + +
      +
    • #1090: cpp parser exception with inline asm
    • +
    • #1128: CompareObjectsWithEquals False Positive comparing boolean (primitive) values
    • +
    • #1254: CPD run that worked in 5.1.2 fails in 5.1.3 with OOM
    • +
    • #1276: False positive in UnusedPrivateMethod with inner enum
    • +
    • #1280: False Positive in UnusedImports when import used in javadoc
    • +
    • #1281: UnusedPrivateMethod incorrectly flagged for methods nested private classes
    • +
    • #1282: False Positive with implicit String.valuesOf() (Java)
    • +
    • #1285: Prevent to modify the System environment
    • +
    • #1286: UnusedPrivateMethod returns false positives for varags and enums
    • +
    + +

    November 3, 2014 - 5.2.1:

    + +

    Bugfixes:

    + +
      +
    • #550: False +: MissingBreakInSwitch
    • +
    • #1252: net.sourceforge.pmd.lang.ast.TokenMgrError: Lexical error in file xxx.cpp
    • +
    • #1253: Document default behaviour when CPD command line arguments “encoding” and “ignoreAnnotations” are not specified
    • +
    • #1255: UseUtilityClass false positive with Exceptions
    • +
    • #1256: PositionLiteralsFirstInComparisons false positive with Characters
    • +
    • #1258: Java 8 Lambda parse error on direct field access
    • +
    • #1259: CloseResource rule ignores conditionnals within finally blocks
    • +
    • #1261: False positive “Avoid unused private methods” with Generics
    • +
    • #1262: False positive for MissingBreakInSwitch
    • +
    • #1263: PMD reports CheckResultSet violation in completely unrelated source files.
    • +
    • #1272: varargs in methods are causing IndexOutOfBoundException when trying to process files
    • +
    • #1273: CheckResultSet false positive in try-with-resources nested in if
    • +
    • #1274: ant integration broken with pmd-5.2.0
    • +
    • #1275: False positive: UnusedModifier rule for static inner class in enum
    • +
    + +

    October 17, 2014 - 5.2.0:

    + +

    Modularization of the source code:

    + +

    The source code of pmd was undergoing a major restructuring. Each language is separated +out into its own module. This reduces the size of the artifacts significantly, if only +one language is needed. It also makes it easier, to add new languages as extensions.

    + +

    Therefore, the maven coordinates needed to change. In order to just use pmd with java support, you’ll need +the following two dependencies:

    + +
    <dependency>
    +    <groupId>net.sourceforge.pmd</groupId>
    +    <artifactId>pmd-core</artifactId>
    +    <version>5.2.0</version>
    +</dependency>
    +<dependency>
    +    <groupId>net.sourceforge.pmd</groupId>
    +    <artifactId>pmd-java</artifactId>
    +    <version>5.2.0</version>
    +</dependency>
    +
    + +

    The binary package still contains all languages and can be used as usual. Have a look at +the central repository for available modules.

    + +

    New Languages

    + +
      +
    • CPD supports now Go.
    • +
    + +

    Pull requests:

    + +
      +
    • #9: New rule: NoUnsanitizedJSPExpressionRule
    • +
    • #44: Add GoLang support to CPD
    • +
    + +

    New/Modified Rules:

    + +
      +
    • JSP - Basic ruleset: +
        +
      • NoUnsanitizedJSPExpression: Using unsanitized JSP expression can lead to Cross Site Scripting (XSS) attacks
      • +
      +
    • +
    + +

    August 31, 2014 - 5.1.3:

    + +

    Bugfixes:

    + +
      +
    • #1156: False failure with “Avoid unused private methods”
    • +
    • #1187: double variable with AvoidDecimalLiteralsInBigDecimalConstructor
    • +
    • #1228: UnusedPrivateMethod returns false positives
    • +
    • #1230: UseCollectionIsEmpty gets false positives
    • +
    • #1231: No Error Message on Missing Rule
    • +
    • #1233: UnusedPrivateMethod: False positive : method called on returned object.
    • +
    • #1234: Unused private methods still giving false positives in 5.1.3 snapshot
    • +
    • #1235: scope dependencies in POM file
    • +
    • #1239: StackOverflowError in AbstractTokenizer.parseString running CPD on >1MB JS file
    • +
    • #1241: False+ AvoidProtectedMethodInFinalClassNotExtending
    • +
    • #1243: Useless Parentheses False Positive
    • +
    • #1245: False Positive for Law of Demeter
    • +
    • #1246: False positive from MissingBreakInSwitch
    • +
    • #1247: Not able to recognize JDK 8 Static Method References
    • +
    • #1249: Regression: UnusedPrivateMethod from 5.0.5 to 5.1.2
    • +
    • #1250: Method attribute missing for some violations
    • +
    • #1251: UnusedPrivateMethod false positives for boxing & unboxing arguments
    • +
    + +

    Feature Requests and Improvements:

    + +
      +
    • #1232: Make ShortClassName configurable
    • +
    • #1244: FieldDeclarationsShouldBeAtStartOfClass and anonymous classes
    • +
    + +

    New/Modified Rules:

    + +
      +
    • FieldDeclarationsShouldBeAtStartOfClass (ruleset java-design) has a new property called ignoreAnonymousClassDeclarations: +Ignore Field Declarations, that are initialized with anonymous class declarations. This property is enabled by default. +See feature #1244.
    • +
    • ShortClassName (ruleset java-naming) has a new property called minimum: Number of characters that are required +as a minimum for a class name. By default, 5 characters are required - if the class name is shorter, a violation +will be reported. See feature #1232.
    • +
    + +

    July 20, 2014 - 5.1.2:

    + +

    Bugfixes:

    + +
      +
    • Fixed bug #1181: unused import false positive if used as parameter in javadoc only.
    • +
    • Fixed bug #1192: Ecmascript fails to parse this operator “ ^= “
    • +
    • Fixed bug #1198: ConfusingTernary does not ignore else if blocks even when property is set
    • +
    • Fixed bug #1200: setRuleSets method javadoc mistype commands instead commas
    • +
    • Fixed bug #1201: Error “Can’t find resource null” when ruleset contains spaces after comma
    • +
    • Fixed bug #1202: StackOverflowError in RuleSetReferenceId
    • +
    • Fixed bug #1205: Parse error on lambda with if
    • +
    • Fixed bug #1206: SummaryHTMLRenderer always shows suppressed warnings/violations
    • +
    • Fixed bug #1208: yahtml’s outputDir property does not work
    • +
    • Fixed bug #1209: XPath 2.0 following-sibling incorrectly includes context node
    • +
    • Fixed bug #1211: PMD is failing with NPE for rule UseIndexOfChar while analyzing Jdk 8 Lambda expression
    • +
    • Fixed bug #1214: UseCollectionIsEmpty misses some usage
    • +
    • Fixed bug #1215: AvoidInstantiatingObjectsInLoops matches the right side of a list iteration loop
    • +
    • Fixed bug #1216: AtLeastOneConstructor ignores classes with any methods
    • +
    • Fixed bug #1218: TooFewBranchesForASwitchStatement misprioritized
    • +
    • Fixed bug #1219: PrimarySuffix/@Image does not work in some cases in xpath 2.0
    • +
    • Fixed bug #1223: UnusedPrivateMethod: Java 8 method reference causing false positives
    • +
    • Fixed bug #1224: GuardDebugLogging broken in 5.1.1 - missing additive statement check in log statement
    • +
    • Fixed bug #1226: False Positive: UnusedPrivateMethod overloading with varargs
    • +
    • Fixed bug #1227: GuardLogStatementJavaUtil doesn’t catch log(Level.FINE, “msg” + “ msg”) calls
    • +
    + +

    Feature Requests and Improvements:

    + +
      +
    • +
    • +
    • +
    • +
    + +

    Pull requests:

    + +
      +
    • #41: Update to use asm 5.0.2
    • +
    • #42: Add SLF4j Logger type to MoreThanOneLogger rule
    • +
    • #43: Standard and modified cyclomatic complexity
    • +
    + +

    New Rules:

    + +
      +
    • Java - codesize ruleset: +
        +
      • StdCyclomaticComplexity: Like CyclomaticComplexityRule, but not including boolean operators
      • +
      • ModifiedCyclomaticComplexity: Like StdCyclomaticComplexity, but switch statement plus all cases count as 1
      • +
      • Thanks to Alan Hohn
      • +
      +
    • +
    + +

    April 27, 2014 - 5.1.1:

    + +

    Bugfixes:

    + +
      +
    • Fixed bug 1165: SimplifyConditional false positive
    • +
    • Fixed bug 1166: PLSQL XPath Rules Fail for XPath 1.0
    • +
    • Fixed bug 1167: Error while processing PLSQL file with BOM
    • +
    • Fixed bug 1168: Designer errors when trying to copy xml to clipboard
    • +
    • Fixed bug 1170: false positive with switch in loop
    • +
    • Fixed bug 1171: Specifying minimum priority from command line gives NPE
    • +
    • Fixed bug 1173: Java 8 support: method references
    • +
    • Fixed bug 1175: false positive for StringBuilder.append called 2 consecutive times
    • +
    • Fixed bug 1176: ShortVariable false positive with for-each loops
    • +
    • Fixed bug 1177: Incorrect StringBuffer warning when that class is not used
    • +
    • Fixed bug 1178: LexicalError while parsing Java code aborts CPD run
    • +
    • Fixed bug 1180: False Positive for ConsecutiveAppendsShouldReuse on different variable names
    • +
    • Fixed bug 1185: UnusedModifier throws NPE when parsing enum with a nested static interface
    • +
    • Fixed bug 1188: False positive in UnusedPrivateField
    • +
    • Fixed bug 1191: Ecmascript fails to parse “void(0)”
    • +
    • Document that PMD requires Java 1.6, see discussion.
    • +
    • +
    • +
    • +
    + +

    CPD Changes:

    + +
      +
    • Command Line +
        +
      • Added option “–skip-lexical-errors” to skip files, which can’t be tokenized +due to invalid characters instead of aborting CPD. See also bug 1178.
      • +
      +
    • +
    • Ant +
        +
      • New optional parameter “skipDuplicateFiles”: Ignore multiple copies of files of the same name and length in +comparison; defaults to “false”. +This was already a command line option, but now also available in in CPD’s ant task.
      • +
      • New optional parameter “skipLexicalErros”: Skip files which can’t be tokenized due to invalid characters +instead of aborting CPD; defaults to “false”.
      • +
      +
    • +
    + +

    February 11, 2014 - 5.1.0:

    + +

    New/Updated Languages:

    + +
      +
    • Java 1.8 support added.
    • +
    • PLSQL support added; thanks to Stuart Turton. See also http://pldoc.sourceforge.net/
    • +
    • Apache Velocity support added; thanks to Andrey Utis. See also http://velocity.apache.org
    • +
    + +

    New/Updated Rulesets and Rules:

    + +
      +
    • EcmaScript +
        +
      • Controversial ruleset, featuring AvoidWithStatement
      • +
      • UseBaseWithParseInt
      • +
      +
    • +
    • Java +
        +
      • GuardLogStatement +
          +
        • replace xpath implementation of GuardDebugLogging by GuardLogStatement (better perf)
        • +
        +
      • +
      • CommentRequired +
          +
        • basic rule to check for existence for formal (javadoc) comments.
        • +
        +
      • +
      • AvoidProtectedMethodInFinalClassNotExtending +
          +
        • rule to avoid protected methods in final classes that don’t extend anything other than Object.
        • +
        +
      • +
      • ConsecutiveAppendsShouldReuse +
          +
        • rule to encourage to reuse StringBuilder.append returned object for consecutive calls.
        • +
        +
      • +
      • PositionLiteralsFirstInCaseInsensitiveComparisons +
          +
        • rule similar to PositionLiteralsFirstInComparisons, but for case insensitive comparisons (equalsIgnoreCase). +Thanks to Larry Diamond
        • +
        +
      • +
      • ConfusingTernary +
          +
        • new property “ignoreElseIf” to suppress this rule in case of if-else-if-else usage. +See feature 1161: Confusing Ternary should skip else if statements (or have a property to do so)
        • +
        +
      • +
      • FieldDeclarationsShouldBeAtStartOfClass +
          +
        • new property “ignoreEnumDeclarations” which is enabled by default. This relaxes the rule, so +that enums can be declared before fields and the rule is not triggered.
        • +
        +
      • +
      +
    • +
    + +

    Bugfixes:

    + +

    http://sourceforge.net/p/pmd/bugs/milestone/PMD-5.1.0/

    + +
      +
    • Fixed bug 881: private final without setter is flagged
    • +
    • Fixed bug 1059: Change rule name “Use Singleton” should be “Use Utility class”
    • +
    • Fixed bug 1106: PMD 5.0.4 fails with NPE on parsing java enum with inner class instance creation
    • +
    • Fixed bug 1045: //NOPMD not working (or not implemented) with ECMAscript
    • +
    • Fixed bug 1054: XML Rules ever report a line -1 and not the line/column where the error occurs
    • +
    • Fixed bug 1115: commentRequiredRule in pmd 5.1 is not working properly
    • +
    • Fixed bug 1120: equalsnull false positive
    • +
    • Fixed bug 1121: NullPointerException when invoking XPathCLI
    • +
    • Fixed bug 1123: failure in help examples
    • +
    • Fixed bug 1124: PMD.run() multithreading issue
    • +
    • Fixed bug 1125: Missing Static Method In Non Instantiatable Class
    • +
    • Fixed bug 1126: False positive with FieldDeclarationsShouldBeAtStartOfClass for static enums
    • +
    • Fixed bug 1130: CloseResource doesn’t recognize custom close method
    • +
    • Fixed bug 1131: CloseResource should complain if code between declaration of resource and try
    • +
    • Fixed bug 1134: UseStringBufferLength: false positives
    • +
    • Fixed bug 1135: CheckResultSet ignores results set declared outside of try/catch
    • +
    • Fixed bug 1136: ECMAScript: NullPointerException in getLeft() and getRight()
    • +
    • Fixed bug 1140: public EcmascriptNode getBody(int index)
    • +
    • Fixed bug 1141: ECMAScript: getFinallyBlock() is buggy.
    • +
    • Fixed bug 1142: ECMAScript: getCatchClause() is buggy.
    • +
    • Fixed bug 1144: CPD encoding argument has no effect
    • +
    • Fixed bug 1146: UseArrayListInsteadOfVector false positive when using own Vector class
    • +
    • Fixed bug 1147: EmptyMethodInAbstractClassShouldBeAbstract false positives
    • +
    • Fixed bug 1150: “EmptyExpression” for valid statements!
    • +
    • Fixed bug 1154: Call super onPause when there is no super
    • +
    • Fixed bug 1155: maven pmd plugin does not like empty rule sets
    • +
    • Fixed bug 1159: false positive UnusedFormalParameter readObject(ObjectInputStream) if not used
    • +
    • Fixed bug 1164: Violations are not suppressed with @java.lang.SuppressWarnings(“all”)
    • +
    + +

    CPD Changes:

    +
      +
    • Command Line +
        +
      • Added non-recursive option “–non-recursive” to not scan sub-directories
      • +
      • Added option “–exclude” to exclude specific files from being scanned (thanks to Delmas for patch #272)
      • +
      +
    • +
    • CPD is now thread-safe, so that multiple instances of CPD can run concurrently without stepping + on each other (eg: multi-module Maven projects.). Thanks to David Golpira.
    • +
    + +

    Miscellaneous:

    + +
      +
    • Upgrade to javacc 5.0 (see patch #1109 Patch to build with Javacc 5.0)
    • +
    • DBURI as DataSource possible - directly scan plsql code stored within the database
    • +
    + +

    API Changes

    + +
      +
    • Deprecated APIs: +
        +
      • net.sourceforge.pmd.lang.ecmascript.ast.ASTFunctionNode: getBody(int index) deprecated, use getBody() instead
      • +
      • net.sourceforge.pmd.lang.ecmascript.ast.ASTTryStatement: isCatch() and isFinally() deprecated, use hasCatch() and hasBody() instead
      • +
      +
    • +
    • Generalize Symbol Table treatement +
        +
      • Added net.sourceforge.pmd.lang.symboltable.ScopedNode
      • +
      • Added net.sourceforge.pmd.lang.symboltable.Scope
      • +
      • Added net.sourceforge.pmd.lang.symboltable.NameDeclaration
      • +
      • Added net.sourceforge.pmd.lang.symboltable.NameOccurrence
      • +
      • Added net.sourceforge.pmd.lang.symboltable.AbstractScope
      • +
      • Added net.sourceforge.pmd.lang.symboltable.AbstractNameDeclaration
      • +
      +
    • +
    + +

    August 11, 2013 - 5.0.5:

    + +
    Fixed bug  991: AvoidSynchronizedAtMethodLevel for static methods
    +Fixed bug 1084: NPE at UselessStringValueOfRule.java:36
    +Fixed bug 1091: file extension for fortran seems to be wrong in cpdgui tools
    +Fixed bug 1092: Wrong Attribute "excludemarker" in Ant Task Documentation
    +Fixed bug 1095: AvoidFinalLocalVariable false positive
    +Fixed bug 1099: UseArraysAsList false positives
    +Fixed bug 1102: False positive: shift operator parenthesis
    +Fixed bug 1104: IdempotentOperation false positive
    +Fixed bug 1107: PMD 5.0.4 couldn't parse call of parent outer java class method from inner class
    +Fixed bug 1069: Eclipse plugin does not accept project-local config
    +Fixed bug 1111: False positive: Useless parentheses
    +Fixed bug 1114: CPD - Tokenizer not initialized with requested properties
    +Fixed bug 1118: ClassCastException in pmd.lang.ecmascript.ast.ASTElementGet
    +
    + +

    May 1, 2013 - 5.0.4:

    + +
    Fixed bug  254: False+ : UnusedImport with Javadoc @throws
    +Fixed bug  794: False positive on PreserveStackTrace with anonymous inner
    +Fixed bug 1063: False+: ArrayIsStoredDirectly
    +Fixed bug 1080: net.sourceforge.pmd.cpd.CPDTest test failing
    +Fixed bug 1081: Regression: CPD skipping all files when using relative paths
    +Fixed bug 1082: CPD performance issue on larger projects
    +Fixed bug 1085: NullPointerException by at net.sourceforge.pmd.lang.java.rule.design.GodClassRule.visit(GodClassRule.java:313)
    +Fixed bug 1086: Unsupported Element and Attribute in Ant Task Example
    +Fixed bug 1087: PreserveStackTrace (still) ignores initCause()
    +Fixed bug 1089: When changing priority in a custom ruleset, violations reported twice
    +
    + +

    April 5, 2013 - 5.0.3:

    + +
    Fixed bug  938: False positive on LooseCoupling for overriding methods
    +Fixed bug  940: False positive on UnsynchronizedStaticDateFormatter
    +Fixed bug  942: CheckResultSet False Positive and Negative
    +Fixed bug  943: PreserveStackTrace false positive if a StringBuffer exists
    +Fixed bug  945: PMD generates RuleSets it cannot read.
    +Fixed bug  958: Intermittent NullPointerException while loading XPath node attributes
    +Fixed bug  968: Issues with JUnit4 @Test annotation with expected exception (Thanks to Yiannis Paschalidis)
    +Fixed bug  975: false positive in ClassCastExceptionWithToArray
    +Fixed bug  976: UselessStringValueOf wrong when appending character arrays
    +Fixed bug  977: MisplacedNullCheck makes false positives
    +Fixed bug  984: Cyclomatic complexity should treat constructors like methods
    +Fixed bug  985: Suppressed methods shouldn't affect avg CyclomaticComplexity
    +Fixed bug  992: Class java.beans.Statement triggered in CloseResource rule
    +Fixed bug  997: Rule NonThreadSafeSingleton gives analysis problem
    +Fixed bug  999: Law of Demeter: False positives and negatives
    +Fixed bug 1002: False +: FinalFieldCouldBeStatic on inner class
    +Fixed bug 1005: False + for ConstructorCallsOverridableMethod - overloaded methods
    +Fixed bug 1027: PMD Ant: java.lang.ClassCastException
    +Fixed bug 1032: ImmutableField Rule: Private field in inner class gives false positive
    +Fixed bug 1064: Exception running PrematureDeclaration
    +Fixed bug 1068: CPD fails on broken symbolic links
    +Fixed bug 1073: Hard coded violation messages CommentSize
    +Fixed bug 1074: rule priority doesn't work on group definitions
    +Fixed bug 1076: Report.treeIterator() does not return all violations
    +Fixed bug 1077: Missing JavaDocs for Xref-Test Files
    +Fixed bug 1078: Package statement introduces false positive UnnecessaryFullyQualifiedName violation
    +Merged pull request #14: fix Nullpointer Exception when using -l jsp
    +
    + +

    February 3, 2013 - 5.0.2:

    + +
    Fixed bug  878: False positive: UnusedFormalParameter for abstract methods
    +Fixed bug  913: SignatureDeclareThrowsException is raised twice
    +Fixed bug  947: CloseResource rule fails if field is marked with annotation
    +Fixed bug 1004: targetjdk isn't attribute of PMD task
    +Fixed bug 1007: Parse Exception with annotation
    +Fixed bug 1011: CloseResource Rule ignores Constructors
    +Fixed bug 1012: False positive: Useless parentheses.
    +Fixed bug 1020: Parsing Error
    +Fixed bug 1026: PMD doesn't handle 'value =' in SuppressWarnings annotation
    +Fixed bug 1028: False-positive: Compare objects with equals for Enums
    +Fixed bug 1030: CPD Java.lang.IndexOutOfBoundsException: Index:
    +Fixed bug 1037: Facing a showstopper issue in PMD Report Class (report listeners)
    +Fixed bug 1039: pmd-nicerhtml.xsl is packaged in wrong location
    +Fixed bug 1043: node.getEndLine() always returns 0 (ECMAscript)
    +Fixed bug 1044: Unknown option: -excludemarker
    +Fixed bug 1046: ant task CPDTask doesn't accept ecmascript
    +Fixed bug 1047: False Positive in 'for' loops for LocalVariableCouldBeFinal in 5.0.1
    +Fixed bug 1048: CommentContent Rule, String Index out of range Exception
    +Fixed bug 1049: Errors in "How to write a rule"
    +Fixed bug 1055: Please add a colon in the ant output after line,column for Oracle JDeveloper IDE usage
    +Fixed bug 1056: "Error while processing" while running on xml file with DOCTYPE reference
    +Fixed bug 1060: GodClassRule >>> wrong method
    +
    + +

    November 28, 2012 - 5.0.1:

    + +
    Fixed bug  820: False+ AvoidReassigningParameters
    +Fixed bug 1008: pmd-5.0.0: ImmutableField false positive on self-inc/dec
    +Fixed bug 1009: pmd-5.0.0: False + UselessParentheses
    +Fixed bug 1003: newline characters stripped from CPD data in PMD 5.0.0
    +Fixed bug 1001: InsufficientStringBufferDeclaration fails to parse hex
    +Fixed bug  522: InefficientStringBuffering bug false +
    +Fixed bug  953: String.InefficientStringBuffering false +
    +Fixed bug  981: Unable to parse
    +Fixed bug 1010: pmd: parsing of generic method call with super fails
    +Fixed bug  996: pmd-4.2.6: MissingBreakInSwitch fails to report violation
    +Fixed bug  993: Invalid NPath calculation in return statement. Thanks to Prabhjot Singh for the patch.
    +Fixed bug 1023: c/c++ \ as a continuation character not supported
    +Fixed bug 1033: False+ : SingularField
    +Fixed bug 1025: Regression of Crash in PMDTask due to multithreading (Eclipse and Java 1.5)
    +Fixed bug 1017: Type resolution very slow for big project. Thanks to Roman for the patch.
    +Fixed bug 1036: Documentation: default threshold values removed from v5.0
    +Fixed bug 1035: UseObjectForClearerAPI has misspelled message
    +Fixed bug 1031: false DontImportJavaLang
    +Fixed bug 1034: UseConcurrentHashMap flags calls to methods that return Map
    +Fixed bug 1006: Problem with implementation of getPackageNameImage method
    +Fixed bug 1014: AvoidLiteralsInIfCondition must NOT consider null
    +Fixed bug 1013: jnlp link for CPD is wrong
    +
    +PMD Command Line Changes:
    +  Improved command line interface (CLI) parsing using JCommander.
    +  Note: this breaks compatibility, but should be easy to fix.
    +  With "-d" you specify nowtThe source files / source directory to be scanned.
    +  With "-f" you select the report format (like text, html, ...)
    +  With "-R" you select the rulesets to be used.
    +  Example: pmd -d c:\data\pmd\pmd\test-data\Unused1.java -f xml -R rulesets/java/unusedcode.xml
    +
    +Improved JSP parser to be less strict with not valid XML documents (like HTML). Thanks to Victor Bucutea.
    +Fixed bgastviewer not working. Thanks to Victor Bucutea.
    +Improved CPD: Support in CPD for IgnoreAnnotations and SuppressWarnings("CPD-START"). Thanks to Matthew Short.
    +Fixed C# support for CPD - thanks to TIOBE Software.
    +
    +New Ecmascript rules:
    +
    +    Basic ruleset: AvoidTrailingComma
    +
    + +

    May, 1, 2012 - 5.0.0:

    + +
    Fixed bug 3515487: Inconsistent reference to ruleset file in documentation
    +Fixed bug 3470274: Using Label for lines in XMLRenderer
    +Fixed bug 3175710: NPE in InsufficientStringBufferDeclaration
    +
    +CPD:
    +- Exit with status code 4 when CPD detects code duplication (Patch ID: 3497021)
    +
    + +

    January 31, 2012 - 5.0-alpha:

    + +
    This version of PMD breaks API compatibility with prior versions of PMD, as well
    +as RuleSet XML compatibility. Also the maven coordinates (groupId) have been changed.
    +The decision to break compatibility, allows PMD
    +internals and code organization to be improved to better handle additional
    +languages.  This opportunity was used to remove depreciated APIs, and beat up
    +any code which has thumbed its nose at the developers over the years. ;)
    +
    +The following is relatively complete list of the major changes (this may not be
    +100% accurate, see actual source code when in doubt):
    +
    +Fixed bug (no number) - Fixed UseStringBufferLengthRule only worked once per class
    +All StringBuffer-related rules now also catch StringBuilder-related issues in the same way
    +
    +    API Change - Unification of treatment of languages within PMD core:
    +       Added - net.sourceforge.pmd.lang.Language (now an 'enum')
    +       Added - net.sourceforge.pmd.lang.LanguageVersion
    +       Added - net.sourceforge.pmd.lang.LanguageVersionDiscoverer
    +       Added - net.sourceforge.pmd.lang.LanguageVersionHandler
    +       Added - net.sourceforge.pmd.lang.XPathHandler
    +       Added - net.sourceforge.pmd.lang.ast.xpath.AbstractASTXPathHandler
    +       Added - net.sourceforge.pmd.lang.xpath.Initializer
    +       Added - net.sourceforge.pmd.lang.ast.AbstractTokenManager
    +       Added - net.sourceforge.pmd.lang.ast.CharStream
    +       Added - net.sourceforge.pmd.lang.ast.JavaCharStream
    +       Added - net.sourceforge.pmd.lang.ast.SimpleCharStream
    +       Added - net.sourceforge.pmd.lang.ast.TokenMgrError
    +       Added - net.sourceforge.pmd.lang.rule.stat.StatisticalRule
    +       Added - net.sourceforge.pmd.lang.rule.stat.StatisticalRuleHelper
    +       Added - net.sourceforge.pmd.lang.java.rule.AbstractStatisticalJavaRule
    +       Added - net.sourceforge.pmd.lang.rule.AbstractRuleViolationFactory
    +       Added - net.sourceforge.pmd.lang.rule.RuleViolationFactory
    +       Added - net.sourceforge.pmd.lang.java.rule.JavaRuleViolationFactory
    +       Added - net.sourceforge.pmd.lang.jsp.rule.JspRuleViolationFactory
    +       Renamed - net.sourceforge.pmd.AbstractRule to net.sourceforge.pmd.lang.rule.AbstractRule
    +       Renamed - net.sourceforge.pmd.AbstractJavaRule to net.sourceforge.pmd.lang.java.rule.AbstractJavaRule
    +       Renamed - net.sourceforge.pmd.AbstractRuleChainVisitor to net.sourceforge.pmd.lang.rule.AbstractRuleChainVisitor
    +       Renamed - net.sourceforge.pmd.RuleChainVisitor to net.sourceforge.pmd.lang.rule.RuleChainVisitor
    +       Renamed - net.sourceforge.pmd.SourceFileSelector to net.sourceforge.pmd.lang.rule.LanguageFilenameFilter
    +       Renamed - net.sourceforge.pmd.rule.XPathRule to net.sourceforge.pmd.lang.rule.XPathRule
    +       Renamed - net.sourceforge.pmd.jsp.rule.AbstractJspRule to net.sourceforge.pmd.lang.jsp.rule.AbstractJspRule
    +       Renamed - net.sourceforge.pmd.ast.CompilationUnit to net.sourceforge.pmd.lang.ast.RootNode
    +       Renamed - net.sourceforge.pmd.ast.JavaRuleChainVisitor to net.sourceforge.pmd.lang.java.rule.JavaRuleChainVisitor
    +       Renamed - net.sourceforge.pmd.jsp.ast.JspRuleChainVisitor to net.sourceforge.pmd.lang.jsp.rule.JspRuleChainVisitor
    +       Renamed - net.sourceforge.pmd.parser.Parser to net.sourceforge.pmd.lang.Parser
    +       Renamed - net.sourceforge.pmd.parser.TokenManager to net.sourceforge.pmd.lang.TokenManager
    +       Renamed - net.sourceforge.pmd.parser.* into net.sourceforge.pmd.lang.{Language}
    +       Renamed - net.sourceforge.pmd.sourcetypehandlers.SourceTypeHandler to net.sourceforge.pmd.lang.LanguageVersionHandler
    +       Renamed - net.sourceforge.pmd.sourcetypehandlers.VisitorStarter to net.sourceforge.pmd.lang.VisitorStarter
    +       Renamed - net.sourceforge.pmd.sourcetypehandlers.* into net.sourceforge.pmd.lang.{Language}
    +       Renamed - net.sourceforge.pmd.stat.StatisticalRule to net.sourceforge.pmd.lang.rule.StatisticalRuleHelper
    +       Renamed - net.sourceforge.pmd.jaxen.TypeOfFunction to net.sourceforge.pmd.lang.java.xpath.TypeOfFunction
    +       Renamed - net.sourceforge.pmd.jaxen.MatchesFunction to net.sourceforge.pmd.lang.xpath.MatchesFunction
    +       Renamed - net.sourceforge.pmd.jaxen.Attribute to net.sourceforge.pmd.lang.ast.xpath.Attribute
    +       Renamed - net.sourceforge.pmd.jaxen.AttributeAxisIterator to net.sourceforge.pmd.lang.ast.xpath.AttributeAxisIterator
    +       Renamed - net.sourceforge.pmd.jaxen.DocumentNavigator to net.sourceforge.pmd.lang.ast.xpath.DocumentNavigator
    +       Renamed - net.sourceforge.pmd.jaxen.NodeIterator to net.sourceforge.pmd.lang.ast.xpath.NodeIterator
    +       Renamed - net.sourceforge.pmd.ast.* into net.sourceforge.pmd.lang.java.ast.*
    +       Renamed - net.sourceforge.pmd.rules.* into net.sourceforge.pmd.lang.java.rule.* and updated to follow conventions
    +       Renamed - net.sourceforge.pmd.jsp.ast.* into net.sourceforge.pmd.lang.jsp.ast.*
    +       Renamed - net.sourceforge.pmd.jsp.rules.* into net.sourceforge.pmd.lang.jsp.ast.rule.* and updated to follow conventions
    +       Deleted - net.sourceforge.pmd.cpd.cppast.* into net.sourceforge.pmd.lang.cpp.ast.*
    +       Deleted - net.sourceforge.pmd.CommonAbstractRule
    +       Deleted - net.sourceforge.pmd.SourceFileConstants
    +       Deleted - net.sourceforge.pmd.SourceType
    +       Deleted - net.sourceforge.pmd.SourceTypeDiscoverer
    +       Deleted - net.sourceforge.pmd.SourceTypeToRuleLanguageMapper
    +       Deleted - net.sourceforge.pmd.TargetJDK1_3
    +       Deleted - net.sourceforge.pmd.TargetJDK1_4
    +       Deleted - net.sourceforge.pmd.TargetJDK1_5
    +       Deleted - net.sourceforge.pmd.TargetJDK1_6
    +       Deleted - net.sourceforge.pmd.TargetJDK1_7
    +       Deleted - net.sourceforge.pmd.TargetJDKVersion
    +       Deleted - net.sourceforge.pmd.cpd.SourceFileOrDirectoryFilter
    +       Deleted - net.sourceforge.pmd.sourcetypehandlers.SourceTypeHandlerBroker
    +       Deleted - net.sourceforge.pmd.ast.JavaCharStream
    +       Deleted - net.sourceforge.pmd.ast.CharStream
    +       Deleted - net.sourceforge.pmd.ast.TokenMgrError
    +       Deleted - net.sourceforge.pmd.jsp.ast.JspCharStream
    +       Deleted - net.sourceforge.pmd.jsp.ast.TokenMgrError
    +
    +    API Change - Generalize RuleViolation treatment
    +       Renamed - net.sourceforge.pmd.IRuleViolation to net.sourceforge.pmd.RuleViolation
    +       Renamed - net.sourceforge.pmd.RuleViolation to net.sourceforge.pmd.lang.rule.AbstractRuleViolation
    +       Added - net.sourceforge.pmd.RuleViolationComparator
    +       Added - net.sourceforge.pmd.lang.java.rule.JavaRuleViolation
    +       Added - net.sourceforge.pmd.lang.jsp.rule.JspRuleViolation
    +
    +    API Change - Generalize DFA treatment
    +       Renamed - net.sourceforge.pmd.dfa.IDataFlowNode to net.sourceforge.pmd.lang.dfa.DataFlowNode
    +       Renamed - net.sourceforge.pmd.dfa.DataFlowNode to net.sourceforge.pmd.lang.dfa.AbstractDataFlowNode
    +       Renamed - net.sourceforge.pmd.dfa.Linker to net.sourceforge.pmd.lang.dfa.Linker
    +       Renamed - net.sourceforge.pmd.dfa.LinkerException to net.sourceforge.pmd.lang.dfa.LinkerException
    +       Renamed - net.sourceforge.pmd.dfa.NodeType to net.sourceforge.pmd.lang.dfa.NodeType
    +       Renamed - net.sourceforge.pmd.dfa.StackObject to net.sourceforge.pmd.lang.dfa.StackObject
    +       Renamed - net.sourceforge.pmd.dfa.SequenceChecker to net.sourceforge.pmd.lang.dfa.SequenceChecker
    +       Renamed - net.sourceforge.pmd.dfa.SequenceException to net.sourceforge.pmd.lang.dfa.SequenceException
    +       Renamed - net.sourceforge.pmd.dfa.StartOrEndDataFlowNode to net.sourceforge.pmd.lang.dfa.StartOrEndDataFlowNode
    +       Renamed - net.sourceforge.pmd.dfa.Structure to net.sourceforge.pmd.lang.dfa.Structure
    +       Renamed - net.sourceforge.pmd.dfa.variableaccess.VariableAccess to net.sourceforge.pmd.lang.dfa.VariableAccess
    +       Renamed - net.sourceforge.pmd.dfa.variableaccess.VariableAccessException to net.sourceforge.pmd.lang.dfa.VariableAccessException
    +       Renamed - net.sourceforge.pmd.dfa.pathfinder.* to net.sourceforge.pmd.lang.dfa.pathfinder.*
    +       Renamed - net.sourceforge.pmd.dfa.report.* to net.sourceforge.pmd.lang.dfa.report.*
    +       Renamed - net.sourceforge.pmd.dfa.DaaRuleViolation to net.sourceforge.pmd.lang.java.dfa.DaaRuleViolation
    +       Renamed - net.sourceforge.pmd.dfa.DataFlowFacade to net.sourceforge.pmd.lang.java.dfa.DataFlowFacade
    +       Renamed - net.sourceforge.pmd.dfa.StatementAndBraceFinder to net.sourceforge.pmd.lang.java.dfa.StatementAndBraceFinder
    +       Renamed - net.sourceforge.pmd.dfa.variableaccess.VariableAccessVisitor to net.sourceforge.pmd.lang.java.dfa.VariableAccessVisitor
    +       Added - net.sourceforge.pmd.lang.java.dfa.JavaDataFlowNode
    +       Added - net.sourceforge.pmd.lang.DataFlowHandler
    +
    +   API Change - Generalize Symbol Table treatement
    +       Deleted - net.sourceforge.pmd.symboltable.JspSymbolFacade
    +       Deleted - net.sourceforge.pmd.symboltable.JspScopeAndDeclarationFinder
    +       Renamed - net.sourceforge.pmd.symboltable.* to net.sourceforge.pmd.lang.java.symboltable.*
    +
    +   API Change - Generalize Type Resolution treatment
    +       Renamed - net.sourceforge.pmd.typeresolution.* to net.sourceforge.pmd.lang.java.typeresolution.*
    +
    +    API Change - Generalize Property Descriptor treatment
    +       Renamed - net.sourceforge.pmd.properties.* to net.sourceforge.pmd.lang.rule.properties.*
    +       Renamed - net.sourceforge.pmd.properties.AbstractPMDProperty to net.sourceforge.pmd.lang.rule.properties.AbstractProperty
    +       Changed - net.sourceforge.pmd.properties.PropertyDescriptor to use Generics, and other changes
    +       Added - net.sourceforge.pmd.lang.rule.properties.* new types and other API changes
    +
    +    API Change - Generalize AST treatment
    +       Added - net.sourceforge.pmd.lang.ast.Node (interface extracted from old Node/SimpleNode)
    +       Added - net.sourceforge.pmd.lang.ast.AbstractNode
    +       Added - net.sourceforge.pmd.ast.DummyJavaNode
    +       Added - net.sourceforge.pmd.jsp.ast.AbstractJspNode
    +       Added - net.sourceforge.pmd.jsp.ast.JspNode
    +       Renamed - net.sourceforge.pmd.ast.SimpleJavaNode to net.sourceforge.pmd.ast.AbstractJavaNode
    +       Renamed - net.sourceforge.pmd.ast.SimpleJavaTypeNode to net.sourceforge.pmd.ast.AbstractJavaTypeNode
    +       Renamed - net.sourceforge.pmd.ast.SimpleJavaAccessNode to net.sourceforge.pmd.ast.AbstractJavaAccessNode
    +       Renamed - net.sourceforge.pmd.ast.SimpleJavaAccessTypeNode to net.sourceforge.pmd.ast.AbstractJavaAccessTypeNode
    +       Deleted - net.sourceforge.pmd.ast.Node
    +       Deleted - net.sourceforge.pmd.ast.SimpleNode
    +       Deleted - net.sourceforge.pmd.ast.AccessNodeInterface
    +       Deleted - net.sourceforge.pmd.jsp.ast.Node
    +       Deleted - net.sourceforge.pmd.jsp.ast.SimpleNode
    +
    +    API Change - General code reorganization/cleanup
    +       Renamed - net.sourceforge.pmd.AbstractDelegateRule to net.sourceforge.pmd.lang.rule.AbstractDelegateRule
    +       Renamed - net.sourceforge.pmd.MockRule to net.sourceforge.pmd.lang.rule.MockRule
    +       Renamed - net.sourceforge.pmd.RuleReference to net.sourceforge.pmd.lang.rule.RuleReference
    +       Renamed - net.sourceforge.pmd.ScopedLogHandlersManager to net.sourceforge.pmd.util.log.ScopedLogHandlersManager
    +       Renamed - net.sourceforge.pmd.util.AntLogHandler to net.sourceforge.pmd.util.log.AntLogHandler
    +       Renamed - net.sourceforge.pmd.util.ConsoleLogHandler to net.sourceforge.pmd.util.log.ConsoleLogHandler
    +       Renamed - net.sourceforge.pmd.util.PmdLogFormatter to net.sourceforge.pmd.util.log.PmdLogFormatter
    +
    +   API Change - Changes to Rule/RuleSet/RuleSets
    +      Removed - boolean Rule.include()
    +      Removed - void Rule.setInclude(boolean)
    +      Removed - String Rule.getRulePriorityName()
    +      Removed - String Rule.getExample()
    +      Removed - Rule.LOWEST_PRIORITY
    +      Removed - Rule.PRIORITIES
    +       Removed - Properties Rule.getProperties()
    +       Removed - Rule.addProperties(Properties)
    +       Removed - boolean Rule.hasProperty(String)
    +       Removed - RuleSet.applies(Language,Language)
    +       Removed - RuleSet.getLanguage()
    +       Removed - RuleSet.setLanguage(Language)
    +       Removed - RuleSets.applies(Language,Language)
    +      Changed - void Rule.setPriority(int) to void Rule.setPriority(RulePriority)
    +      Changed - int Rule.getPriority() to void RulePriority Rule.getPriority()
    +       Changed - XXX Rule.getXXXProperty(String) to <T> Rule.getProperty(PropertyDescriptor<T>)
    +       Changed - XXX Rule.getXXXProperty(PropertyDescriptor) to <T> Rule.getProperty(PropertyDescriptor<T>)
    +       Changed - Rule.addProperty(String, String) to Rule.setProperty(PropertyDescriptor<T>, T)
    +       Changed - Rule.setProperty(PropertyDescriptor, Object) to Rule.setProperty(PropertyDescriptor<T>, T)
    +       Changed - Rule.setProperty(PropertyDescriptor, Object[]) to Rule.setProperty(PropertyDescriptor<T>, T)
    +       Changed - Rule.propertyValuesByDescriptor() to Rule.getPropertiesByPropertyDescriptor()
    +       Changed - PropertyDescriptor Rule.propertyDescriptorFor(String) to PropertyDescriptor Rule.getPropertyDescriptor(String)
    +       Changed - boolean RuleSet.usesDFA() to boolean RuleSet.usesDFA(Language)
    +       Changed - boolean RuleSet.usesTypeResolution() to boolean RuleSet.usesTypeResolution(Language)
    +      Added - Rule.setLanguage(Language)
    +      Added - Language Rule.getLanguage()
    +      Added - Rule.setMinimumLanguageVersion(LanguageVersion)
    +      Added - LanguageVersion Rule.getMinimumLanguageVersion()
    +      Added - Rule.setMaximumLanguageVersion(LanguageVersion)
    +      Added - LanguageVersion Rule.getMaximumLanguageVersion()
    +      Added - Rule.setDeprecated(boolean)
    +      Added - boolean Rule.isDeprecated()
    +      Added - String Rule.dysfunctionReason();
    +       Added - Rule.definePropertyDescriptor(PropertyDescriptor)
    +       Added - List<PropertyDescriptor> Rule.getPropertyDescriptors()
    +       Added - RuleSet.applies(Rule,LanguageVersion)
    +
    +   API Change - Changes to PMD class
    +      Renamed - PMD.EXCLUDE_MARKER to PMD.SUPPRESS_MARKER
    +      Removed - PMD.processFile(InputStream, RuleSet, RuleContext)
    +      Removed - PMD.processFile(InputStream, String, RuleSet, RuleContext)
    +      Removed - PMD.processFile(Reader, RuleSet, RuleContext)
    +      Removed - PMD.processFile(Reader, RuleSets, RuleContext, LanguageVersion)
    +      Moved - PMD.getExcludeMarker() to Configuration.getSuppressMarker()
    +      Moved - PMD.setExcludeMarker(String) to Configuration.getSuppressMarker(String)
    +      Moved - PMD.getClassLoader() to Configuration.getClassLoader()
    +      Moved - PMD.setClassLoader(ClassLoader) to Configuration.getClassLoader(ClassLoader)
    +      Moved - PMD.setDefaultLanguageVersion(LanguageVersion) to Configuration.setDefaultLanguageVersion(LanguageVersion)
    +      Moved - PMD.setDefaultLanguageVersions(List<LanguageVersion>) to Configuration.setDefaultLanguageVersions(List<LanguageVersion>)
    +      Moved - PMD.createClasspathClassLoader(String) to Configuration.createClasspathClassLoader(String)
    +
    +   API Change - Changes to Node interface
    +      Renamed - Node.findChildrenOfType(Class) as Node.findDescendantsOfType(Class)
    +      Renamed - Node.getFirstChildOfType(Class) as Node.getFirstDescendantOfType(Class)
    +      Renamed - Node.containsChildOfType(Class) as Node.hasDescendantOfType(Class)
    +      Renamed - Node.getAsXml() as Node.getAsDocument()
    +      Added - Node.findChildrenOfType(Class), non recursive version
    +      Added - Node.getFirstChildOfType(Class), non recursive version
    +
    +   API Change - Remove deprecated APIs
    +      Removed - AccessNode.setXXX() methods, use AccessNode.setXXX(boolean) instead.
    +      Removed - PMDException.getReason()
    +      Removed - RuleSetFactory.createRuleSet(String,ClassLoader), use RuleSetFactory.setClassLoader(ClassLoader) and RuleSetFactory.createRuleSets(String) instead.
    +      Removed - net.sourceforge.pmd.cpd.FileFinder use net.sourceforge.pmd.util.FileFinder instead.
    +
    +   API Change - RuleSetFactory
    +        Added - RuleSetFactory.setClassLoader(ClassLoader)
    +        Added - RuleSetFactory.createRuleSets(List<RuleSetReferenceId>)
    +        Added - RuleSetFactory.createRuleSet(RuleSetReferenceId)
    +        Added - RuleSetFactory.setClassLoader(ClassLoader)
    +        Added - RuleSetReferenceId class to handle parsing of RuleSet strings, see RuleSetReferenceId.parse(String)
    +      Renamed - RuleSetFactory.createSingleRuleSet(String) to RuleSetFactory.createRuleSet(String);
    +      Removed - RuleSetFactory.createRuleSets(String, ClassLoader), use RuleSetFactory.createRuleSets(String) instead.
    +      Removed - RuleSetFactory.createSingleRuleSet(String, ClassLoader), use RuleSetFactory.createSingleRuleSet(String) instead.
    +      Removed - RuleSetFactory.createRuleSet(InputStream, ClassLoader), use RuleSetFactory.createRuleSet(RuleSetReferenceId) instead.
    +      Removed - ExternalRuleID, use RuleSetReferenceId instead
    +      Removed - SimpleRuleSetNameMapper, use RuleSetReferenceId instead
    +
    +   API Change - Changes to Renderer class, and Renderer implementations
    +        Added - Renderer.getName()
    +        Added - Renderer.setName(String)
    +        Added - Renderer.getDescription()
    +        Added - Renderer.setDescription(String)
    +        Added - Renderer.getPropertyDefinitions()
    +        Added - Renderer.isShowSuppressedViolations()
    +        Added - AbstractAccumulatingRenderer
    +      Removed - Renderer.render(Report)
    +      Removed - Renderer.render(Report, Writer)
    +      Renamed - Renderer.showSuppressedViolations(boolean) to Renderer.setShowSuppressedViolations(boolean)
    +      Renamed - PapariTextRenderer to TextColorRenderer
    +      Renamed - OntheFlyRenderer to AbstractIncrementingRenderer
    +
    +PMD command line changes:
    +
    +   Removed -lineprefix use -property linePrefix {value} instead
    +   Removed -linkprefix use -property linkPrefix {value} instead
    +   Removed -xslt use -property xsltFilename {value} instead
    +   Removed -nojsp now obsolete
    +   Removed -targetjdk use -version {name} {version} instead
    +   Added -version {name} {version} to set language version to use for a given language
    +   Added -property {name} {value} as generic way to pass properties to Renderers
    +   Added -showsuppressed as a means to show suppressed rule violations (consistent with Ant task behavior)
    +   Renamed 'nicehtml' report to 'xslt'
    +   Renamed 'papari' report to 'textcolor'
    +   Renamed -excludemarker option to -suppressmarker
    +   Renamed -cpus option to -threads
    +
    +Ant changes:
    +
    +   Removed - <formatter> 'linkPrefix' attribute, use <param name="linkPrefix"> instead
    +   Removed - <formatter> 'linePrefix' attribute, use <param name="linePrefix"> instead
    +   Changed - <formatter> is optional - if not specified, falls back to "text" and console output.
    +   Removed - <pmd> 'targetJDK' attribute to <version>lang version</version> instead
    +     Added - <param name="name" value="value"/> as generic way to pass properties to Renderers on <formatter>
    +   Renamed - <pmd> 'excludeMarker' attribute to 'suppressMarker'
    +   Renamed - <pmd> 'cpus' attribute to 'threads'
    +
    +Maven changes:
    +   The new maven coordinates are: net.sourceforge.pmd:pmd, e.g.
    +   <dependency>
    +     <groupId>net.sourceforge.pmd</groupId>
    +     <artifactId>pmd</artifactId>
    +     <version>5.0</version>
    +   </dependency>
    +
    +New features:
    +
    +New Language 'ecmascript' added, for writing XPathRule and Java Rules against ECMAScript/JavaScript documents (must be standalone, not embedded in HTML).  Many thanks to Rhino!
    +New Language 'xml' added, for writing XPathRules against XML documents
    +New Language 'xsl' added, as a derivative from XML.
    +Rules can now define a 'violationSuppressRegex' property to universally suppress violations with messages matching the given regular expression
    +Rules can now define a 'violationSuppressXPath' property to universally suppress violations on nodes which match the given relative XPath expression
    +Rules are now directly associated with a corresponding Language, and a can also be associated with a specific Language Version range if desired.
    +Rules can now be flagged with deprecated='true' in the RuleSet XML to allow the PMD Project to indicate a Rule (1) is scheduled for removal, (2) has been removed, or (3) has been renamed/moved.
    +XPathRules can now query using XPath 2.0 with 'version=2.0"', or XPath 2.0 in XPath 1.0 compatibility mode using 'version="1.0 compatibility"'.  Many thanks to Saxon!
    +Rules can now use property values in messages, for example ${propertyName} will expand to the value of the 'propertyName' property on the Rule.
    +Rules can now use violation specific values in messages, specifically ${variableName}, ${methodName}, ${className}, ${packageName}.
    +New XPath function 'getCommentOn' can be used to search for strings in comments - Thanks to Andy Throgmorton
    +
    +CPD:
    +Add .hxx and .hpp as valid file extension for CPD - Thanks to Ryan Pavlik
    +Add options to to the CPD command line task - Thanks to Cd-Man
    +Add C# support for CPD - thanks to Florian Bauer
    +Fix small bug in Rule Designer UI
    +Performance enhacement when parsing Javadoc (Patch ID: 3217201), thanks to Cd-Man
    +Rework the XMLRenderer to use proper XML API and strictly uses the system value for encoding (Fix bug: 1435751)
    +
    +Other changes:
    +Rule property API upgrades:
    +  All numeric property descriptors can specify upper & lower limits
    +  Newly functional Method & Type descriptors allow rule developers to incorporate/watch for individual methods or types
    +  Better initialization error detection
    +  Deprecated old string-keyed property API, will leave some methods behind for XPath rules however
    +'41' and '42' shortcuts for rulesets added
    +The default Java version processed by PMD is now uniformly Java 1.5.
    +RuleViolations in Reports now uses List internally, and RuleViolationComparator is no longer broken
    +TokenManager errors now include a file name whenever possible for every AST in PMD
    +Added file encoding option to CPD GUI, which already existed for the command line and Ant
    +AssignmentInOperand enhanced to catch assignment in 'for' condition, as well as use of increment/decrement operators.  Customization properties added to allow assignment in if/while/for, or use of increment/decrement.
    +Fix false positive on CastExpressions for UselessParentheses
    +Fix false positive where StringBuffer.setLength(0) was using default constructor size of 16, instead of actual constructor size.
    +Fix false negative for non-primitive types for VariableNamingConventions, also expanded scope to local and method/constructors, and enhanced customization options to choose between members/locals/parameters (all checked by default)
    +Fix false negative for UseArraysAsList when the array was passed as method parameter - thanks to Andy Throgmorton
    +Improve TooManyMethods rule - thanks to a patch from Riku Nykanen
    +Improve DoNotCallSystemExit - thanks to a patch from Steven Christou
    +Correct -benchmark reporting of Rule visits via the RuleChain
    +Creating an Empty Code Ruleset and moved the following rules from Basic ruleset:
    +        * Empty Code Rules
    +        * EmptyCatchBlock
    +        * EmptyIfStmt
    +        * EmptyWhileStmt
    +        * EmptyTryBlock
    +        * EmptyFinallyBlock
    +        * EmptySwitchStatements
    +        * EmptySynchronizedBlock
    +        * EmptyStatementNotInLoop
    +        * EmptyInitializer
    +        * EmptyStatementBlock
    +        * EmptyStaticInitializer
    +    Basic rulesets still includes a reference to those rules.
    +Creating a unnecessary Code Ruleset and moved the following rules from Basic ruleset:
    +        * UnnecessaryConversionTemporary
    +        * UnnecessaryReturn
    +        * UnnecessaryFinalModifier
    +        * UselessOverridingMethod
    +        * UselessOperationOnImmutable
    +        * UnusedNullCheckInEquals
    +        * UselessParentheses
    +    Basic rulesets still includes a reference to those rules.
    +
    +Fixed bug 2920057 - Fixed False + on CloseResource
    +Fixed bug 1808110 - Fixed performance issues on PreserveStackTrace
    +Fixed bug 2832322 - cpd.xml file tag path attribute should be entity-encoded
    +Fixed bug 2826119 - False +: DoubleCheckedLocking warning with volatile field
    +Fixed bug 2835074 - False -: DoubleCheckedLocking with reversed null check
    +Fixed bug 1932242 - EmptyMethodInAbstractClassShouldBeAbstract false +
    +Fixed bug 1928009 - Error using migration ruleset in PMD 4.2
    +Fixed bug 1808110 - PreserveStackTrace
    +Fixed bug 1988829 - Violation reported without source file name (actually a fix to ConsecutiveLiteralAppends)
    +Fixed bug 1989814 - false +: ConsecutiveLiteralAppends
    +Fixed bug 1977230 - false positive: UselessOverridingMethod
    +Fixed bug 1998185 - BeanMembersShouldSerialize vs @SuppressWarnings("serial")
    +Fixed bug 2002722 - false + in UseStringBufferForStringAppends
    +Fixed bug 2056318 - False positive for AvoidInstantiatingObjectsInLoops
    +Fixed bug 1977438 - False positive for UselessStringValueOf
    +Fixed bug 2050064 - False + SuspiciousOctalEscape with backslash literal
    +Fixed bug 1556594 - Wonky detection of NullAssignment
    +Fixed bug 1481051 - false + UnusedNullCheckInEquals (and other false positives too)
    +Fixed bug 1943204 - Ant task: <ruleset> path should be relative to Ant basedir
    +Fixed patch 2075906 - Add toString() to the rule UnnecessaryWrapperObjectCreation
    +Fixed bug 2315623 - @SuppressWarnings("PMD.UseSingleton") has no effect
    +Fixed bug 2230809 - False +: ClassWithOnlyPrivateConstructorsShouldBeFinal
    +Fixed bug 2338341 - ArrayIndexOutOfBoundsException in CPD (on Ruby)
    +Fixed bug 2315599 - False +: UseSingleton with class containing constructor
    +Fixed bug 1955852 - false positives for UnusedPrivateMethod & UnusedLocalVariable
    +Fixed bug 2404700 - UseSingleton should not act on enums
    +Fixed bug - JUnitTestsShouldIncludeAssert now detects Junit 4 Assert.assert...  constructs
    +Fixed bug 1609038 - Xslt report generators break if path contains "java"
    +Fixed bug 2142986 - UselessOverridingMethod doesn't consider annotations
    +Fixed bug 2027626 - False + : AvoidFinalLocalVariable
    +Fixed bug 2606609 - False "UnusedImports" positive in package-info.java
    +Fixed bug 2645268 - ClassCastException in UselessOperationOnImmutable.getDeclaration
    +Fixed bug 2724653 - AvoidThreadGroup reports false positives
    +Fixed bug 2904832 - Type resolution not working for ASTType when using an inner class
    +Fixed bug 1435751 - XML format does not support UTF-8
    +Fixed bug 3303811 - Deadlink on "Similar projects" page
    +Fixed bug 3017616 - Updated documentation regarding Netbeans plugin - thanks to Jesse Glick
    +Fixed bug 3427563 - Deprecated class (android.util.config) - thanks to Lukas Reschke for the patch
    +
    +ruleset.dtd and ruleset_xml_schema.xsd added to jar file in rulesets directory
    +bin and java14/bin scripts:
    +    retroweaver version was not correct in java14/bin scripts
    +    support for extra languages in cpd.sh
    +    standard unix scripts can be used with cygwin
    +Upgrading UselessOperationOnImmutable to detect more use cases, especially on String and fix false positives
    +AvoidDuplicateLiteralRule now has 'skipAnnotations' boolean property
    +Fixed false positive in UnusedImports: javadoc comments are parsed to check @see and other tags
    +Fixed parsing bug: constant fields in annotation classes
    +Bug fix: NPE in MoreThanOneLogger
    +UnnecessaryParentheses now checks all expressions, not just return statements
    +UnusedFormalParameter now reports violations on the parameter node, not the method/constructor node
    +Updates to RuleChain to honor RuleSet exclude-pattern
    +Optimizations and false positive fixes in PreserveStackTrace
    +@SuppressWarnings("all") disables all warnings
    +SingularField now checks for multiple fields in the same declaration
    +Java grammar enhanced to include AnnotationMethodDeclaration as parent node of method related children of AnnotationTypeMemberDeclaration
    +JavaCC generated artifacts updated to JavaCC 4.1.
    +Dependencies updates: asm updated to 3.2
    +Ant requirement is now 1.7.0 or higher for compilation
    +    JUnit testing jar is packaged on 1.7.0+ only in ant binary distributions
    +    Note that the ant task still works with 1.6.0 and higher
    +All comment types are now stored in ASTCompilationUnit, not just formal ones
    +Fixed false negative in UselessOverridingMethod
    +Fixed handling of escape characters in UseIndexOfChar and AppendCharacterWithChar
    +Fixed ClassCastException on generic method in BeanMembersShouldSerialize
    +Fixed ClassCastException in symbol table code
    +Support for Java 1.4 runtime dropped, PMD now requires Java 5 or higher.  PMD can still process Java 1.4 source files.
    +Support for Java 1.7
    +Text renderer is now silent if there's no violation instead of displaying "No problems found!"
    +RuleSet short names now require a language prefix, 'basic' is now 'java-basic', and 'rulesets/basic.xml' is now 'rulesets/java/basic.xml'
    +The JSP RuleSets are now in the 'jsp' language, and are 'jsp-basic', 'jsp-basic-jsf', 'rulesets/jsp/basic.xml' and 'rulesets/jsp/basic-jsp.xml'
    +Enhanced logging in the ClassTypeResolver to provide more detailed messaging.
    +AvoidUsingHardCodedIP modified to not use InetAddress.getByName(String), instead does better pattern analysis.
    +The JSP/JSF parser can now parse Unicode input.
    +The JSP/JSP parser can now handle <script>...</script> tags.  The AST HtmlScript node contains the content.
    +Added Ecmascript as a supported language for CPD.
    +The RuleSet XML Schema namespace is now: http://pmd.sourceforge.net/ruleset/2.0.0
    +The RuleSet XML Schema is located in the source at: etc/ruleset_2_0_0.xsd
    +The RuleSet DTD is located in the source at: etc/ruleset_2_0_0.dtd
    +Improved include/exclude pattern matching performance for ends-with type patterns.
    +Modify (and hopefully fixed) CPD algorithm thanks to a patch from Juan Jesús García de Soria.
    +Fixed character reference in xml report - thanks to Seko
    +Enhanced SuspiciousEqualsMethodName rule - thanks to Andy Throgmorton
    +Add a script to launch CPDGUI on Unix system - thanks to Tom Wheeler
    +
    +New Java rules:
    +
    +    Basic ruleset: ExtendsObject,CheckSkipResult,AvoidBranchingStatementAsLastInLoop,DontCallThreadRun,DontUseFloatTypeForLoopIndices
    +    Controversial ruleset: AvoidLiteralsInIfCondition, AvoidPrefixingMethodParameters, OneDeclarationPerLine, UseConcurrentHashMap
    +    Coupling ruleset: LoosePackageCoupling,LawofDemeter
    +    Design ruleset: LogicInversion,UseVarargs,FieldDeclarationsShouldBeAtStartOfClass,GodClass
    +    Empty ruleset: EmptyInitializer,EmptyStatementBlock
    +    Import ruleset: UnnecessaryFullyQualifiedName
    +    Optimization ruleset: RedundantFieldInitializer
    +    Naming ruleset: ShortClassName, GenericsNaming
    +    StrictException ruleset: AvoidThrowingNewInstanceOfSameException, AvoidCatchingGenericException, AvoidLosingExceptionInformation
    +    Unnecessary ruleset: UselessParentheses
    +    JUnit ruleset: JUnitTestContainsTooManyAsserts, UseAssertTrueInsteadOfAssertEquals
    +    Logging with Jakarta Commons ruleset: GuardDebugLogging
    +
    +New Java ruleset:
    +    android.xml: new rules specific to the Android platform
    +
    +New JSP rules:
    +    Basic ruleset: NoInlineScript
    +
    +New ECMAScript rules:
    +    Basic ruleset: AssignmentInOperand,ConsistentReturn,InnaccurateNumericLiteral,ScopeForInVariable,UnreachableCode,EqualComparison,GlobalVariable
    +    Braces ruleset: ForLoopsMustUseBraces,IfStmtsMustUseBraces,IfElseStmtsMustUseBraces,WhileLoopsMustUseBraces
    +    Unnecessary ruleset: UnnecessaryParentheses,UnnecessaryBlock
    +
    +New XML rules:
    +    Basic ruleset: MistypedCDATASection
    +
    + +

    November 4, 2011 - 4.3:

    + +
    Add support for Java 7 grammer - thanks to Dinesh Bolkensteyn and SonarSource
    +Add options --ignore-literals and --ignore-identifiers to the CPD command line task, thanks to Cd-Man
    +Fixed character reference in xml report - thanks to Seko
    +Add C# support for CPD - thanks to Florian Bauer
    +Fix small bug in Rule Designer UI
    +Improve TooManyMethods rule - thanks to a patch from Riku Nykanen
    +Improve DoNotCallSystemExit - thanks to a patch from Steven Christou
    +Fix false negative for UseArraysAsList when the array was passed as method parameter - thanks to Andy Throgmorton
    +Enhanced SuspiciousEqualsMethodName rule - thanks to Andy Throgmorton
    +Add a script to launch CPDGUI on Unix system - thanks to Tom Wheeler
    +
    +New Rule:
    +    Basic ruleset: DontCallThreadRun - thanks to Andy Throgmorton
    +    Logging with Jakarta Commons ruleset: GuardDebugLogging
    +
    + +

    September 14, 2011 - 4.2.6:

    + +
    Fixed bug 2920057 - False + : CloseRessource whith an external getter
    +Fixed bug 1808110 - Fixed performance issue on PreserveStackTrace
    +Fixed bug 2832322 -  cpd.xml file tag path attribute should be entity-encoded
    +Fixed bug 2590258 - NPE with nicerhtml output
    +Fixed bug 2317099 - False + in SimplifyCondition
    +Fixed bug 2606609 - False "UnusedImports" positive in package-info.java
    +Fixed bug 2645268 - ClassCastException in UselessOperationOnImmutable.getDeclaration
    +Fixed bug 2724653 - AvoidThreadGroup reports false positives
    +Fixed bug 2835074 - False -: DoubleCheckedLocking with reversed null check
    +Fixed bug 2826119 - False +: DoubleCheckedLocking warning with volatile field
    +Fixed bug 2904832 - Type resolution not working for ASTType when using an inner class
    +
    +Modify (and hopefully fixed) CPD algorithm thanks to a patch from Juan Jesús García de Soria.
    +Correct -benchmark reporting of Rule visits via the RuleChain
    +Fix issue with Type Resolution incorrectly handling of Classes with same name as a java.lang Class.
    +The JSP/JSF parser can now parse Unicode input.
    +The JSP/JSP parser can now handle <script>...</script> tags.  The AST HtmlScript node contains the content.
    +Added Ecmascript as a supported language for CPD.
    +Improved include/exclude pattern matching performance for ends-with type patterns.
    +
    +Dependencies updates: asm updated to 3.2
    +
    +Android ruleset: CallSuperLast rule now also checks for finish() redefinitions
    +
    +New rule:
    +    Android: DoNotHardCodeSDCard
    +    Controversial : AvoidLiteralsInIfCondition (patch 2591627), UseConcurrentHashMap
    +    StrictExceptions : AvoidCatchingGenericException, AvoidLosingExceptionInformation
    +    Naming : GenericsNaming
    +    JSP: NoInlineScript
    +
    + +

    February 08, 2009 - 4.2.5:

    + +
    Enhanced logging in the ClassTypeResolver to provide more detailed messaging.
    +Fixed bug 2315623 - @SuppressWarnings("PMD.UseSingleton") has no effect
    +Fixed bug 2230809 - False +: ClassWithOnlyPrivateConstructorsShouldBeFinal
    +Fixed bug 2338341 - ArrayIndexOutOfBoundsException in CPD (on Ruby)
    +Fixed bug 2315599 - False +: UseSingleton with class containing constructor
    +Fixed bug 1955852 - false positives for UnusedPrivateMethod & UnusedLocalVariable
    +Fixed bug 2404700 - UseSingleton should not act on enums
    +Fixed bug 2225474 - VariableNamingConventions does not work with nonprimitives
    +Fixed bug 1609038 - Xslt report generators break if path contains "java"
    +Fixed bug - JUnitTestsShouldIncludeAssert now detects Junit 4 Assert.assert...  constructs
    +Fixed bug 2142986 - UselessOverridingMethod doesn't consider annotations
    +Fixed bug 2027626 - False + : AvoidFinalLocalVariable
    +
    +New rule:
    +    StrictExceptions : AvoidThrowingNewInstanceOfSameException
    +New ruleset:
    +    android.xml: new rules specific to the Android platform
    +
    + +

    October 12, 2008 - 4.2.4:

    + +
    Fixed bug 1481051 - false + UnusedNullCheckInEquals (and other false positives too)
    +Fixed bug 1943204 - Ant task: <ruleset> path should be relative to Ant basedir
    +Fixed bug 2139720 - Exception in PMD Rule Designer for inline comments in source
    +Fixed patch 2075906 - Add toString() to the rule UnnecessaryWrapperObjectCreation
    +Fixed ClassCastException on generic method in BeanMembersShouldSerialize
    +Fixed ClassCastException in symbol table code
    +
    + +

    August 31, 2008 - 4.2.3:

    + +
    JavaCC generated artifacts updated to JavaCC 4.1d1.
    +Java grammar enhanced to include AnnotationMethodDeclaration as parent node of method related children of AnnotationTypeMemberDeclaration
    +Fixes for exclude-pattern
    +Updates to RuleChain to honor RuleSet exclude-pattern
    +Upgrading UselessOperationOnImmutable to detect more use cases, especially on String and fix false positives
    +Fixed bug 1988829 - Violation reported without source file name (actually a fix to ConsecutiveLiteralAppends)
    +Fixed bug 1989814 - false +: ConsecutiveLiteralAppends
    +Fixed bug 1977230 - false positive: UselessOverridingMethod
    +Fixed bug 1998185 - BeanMembersShouldSerialize vs @SuppressWarnings("serial")
    +Fixed bug 2002722 - false + in UseStringBufferForStringAppends
    +Fixed bug 2056318 - False positive for AvoidInstantiatingObjectsInLoops
    +Fixed bug 1977438 - False positive for UselessStringValueOf
    +Fixed bug 2050064 - False + SuspiciousOctalEscape with backslash literal
    +Fixed bug 1556594 - Wonky detection of NullAssignment
    +Optimizations and false positive fixes in PreserveStackTrace
    +@SuppressWarnings("all") disables all warnings
    +All comment types are now stored in ASTCompilationUnit, not just formal ones
    +Fixed false negative in UselessOverridingMethod
    +Fixed handling of escape characters in UseIndexOfChar and AppendCharacterWithChar
    +
    +New rule:
    +    Basic ruleset:  EmptyInitializer
    +
    + +

    May 20, 2008 - 4.2.2:

    + +
    Fixed false positive in UnusedImports: javadoc comments are parsed to check @see and other tags
    +Fixed parsing bug: constant fields in annotation classes
    +Bug fix: NPE in MoreThanOneLogger
    +UnnecessaryParentheses now checks all expressions, not just return statements
    +
    + +

    April 11, 2008 - 4.2.1:

    + +
    '41' and '42' shortcuts for rulesets added
    +Fixed bug 1928009 - Error using migration ruleset in PMD 4.2
    +Fixed bug 1932242 - EmptyMethodInAbstractClassShouldBeAbstract false +
    +Fixed bug 1808110 - PreserveStackTrace
    +
    +AvoidDuplicateLiteralRule now has 'skipAnnotations' boolean property
    +ruleset.dtd and ruleset_xml_schema.xsd added to jar file in rulesets directory
    +Update RuleSetWriter to handle non-Apache TRAX implementations, add an option to not use XML Namespaces
    +Added file encoding option to CPD GUI, which already existed for the command line and Ant
    +bin and java14/bin scripts:
    +    retroweaver version was not correct in java14/bin scripts
    +    support for extra languages in cpd.sh
    +    standard unix scripts can be used with cygwin
    +
    + +

    March 25, 2008 - 4.2:

    + +
    Fixed bug 1920155 - CheckResultSet: Does not pass for loop conditionals
    +
    + +

    March 21, 2008 - 4.2rc2:

    + +
    Fixed bug 1912831 - False + UnusedPrivateMethod with varargs
    +Fixed bug 1913536 - Rule Designer does not recognize JSP(XML)
    +Add -auxclasspath option for specifying Type Resolution classpath from command line and auxclasspath nested element for ant task.
    +Fixed formatting problems in loggers.
    +
    +Ant task upgrade:
    +    Added a new attribute 'maxRuleCount' to indicate whether or not to fail the build if PMD finds that much violations.
    +
    + +

    March 07, 2008 - 4.2rc1:

    + +
    Fixed bug 1866198 - PMD should not register global Logger
    +Fixed bug 1843273 - False - on SimplifyBooleanReturns
    +Fixed bug 1848888 - Fixed false positive in UseEqualsToCompareStrings
    +Fixed bug 1874313 - Documentation bugs
    +Fixed bug 1855409 - False + in EmptyMethodInAbstractClassShouldBeAbstract
    +Fixed bug 1888967 - Updated xpath query to detect more "empty" methods.
    +Fixed bug 1891399 - Check for JUnit4 test method fails
    +Fixed bug 1894821 - False - for Test Class without Test Cases
    +Fixed bug 1882457 - PositionLiteralsFirstInComparisons rule not working OK
    +Fixed bug 1842505 - XML output incorrect for inner classes
    +Fixed bug 1808158 - Constructor args could also be final
    +Fixed bug 1902351 - AvoidReassigningParameters not identify parent field
    +Fixed other false positives in EmptyMethodInAbstractClassShouldBeAbstract
    +Fixed other issues in SimplifyBooleanReturns
    +Modified AvoidReassigningParameter to also check constructor arguments for reassignement
    +
    +New rules:
    +    Basic ruleset: AvoidMultipleUnaryOperators
    +    Controversial ruleset: DoNotCallGarbageCollectionExplicitly,UseObjectForClearerAPI
    +    Design ruleset : ReturnEmptyArrayRatherThanNull,TooFewBranchesForASwitchStatement,AbstractClassWithoutAnyMethod
    +    Codesize : TooManyMethods
    +    StrictExceptions : DoNotThrowExceptionInFinally
    +    Strings : AvoidStringBufferField
    +
    +Rule upgrade:
    +    CyclomaticComplexity now can be configured to display only class average complexity or method complexity, or both.
    +
    +Designer upgrade:
    +    A new panel for symbols and a tooltips on AST node that displays line, column and access node attributes (private,
    +    static, abstract,...)
    +
    +1.7 added as a valid option for targetjdk.
    +New elements under <ruleset>: <exclude-pattern> to match files exclude from processing, with <include-pattern> to override.
    +Rules can now be written which produce violations based upon aggregate file processing (i.e. cross/multiple file violations).
    +PMD Rule Designer can now shows Symbol Table contents for the selected AST node.
    +PMD Rule Designer shows position info in tooltip for AST nodes and highlights matching code for selected AST node in code window.
    +CPD Ant task will report to System.out when 'outputFile' not given.
    +RuleSetWriter class can be used to Serialize a RuleSet to XML in a standard fashion.  Recommend PMD IDE plugins standardize their behavior.
    +retroweaver updated to version 2.0.5.
    +
    + +

    November 17, 2007 - 4.1:

    + +
    Fixed annotation bug: ClassCastException when a formal parameter had multiple annotations
    +Added a Visual Studio renderer for CPD; just use "--format vs".
    +Dependencies updates: asm to 3.1, retroweaver to 2.0.2, junit to 4.4
    +new ant target ("regress") to test regression bugs only
    +
    + +

    November 01, 2007 - 4.1rc1:

    + +
    New rules:
    +    Basic ruleset: AvoidUsingHardCodedIP,CheckResultSet
    +    Controversial ruleset: AvoidFinalLocalVariable,AvoidUsingShortType,AvoidUsingVolatile,AvoidUsingNativeCode,AvoidAccessibilityAlteration
    +    Design ruleset: ClassWithOnlyPrivateConstructorsShouldBeFinal,EmptyMethodInAbstractClassShouldBeAbstract
    +    Imports ruleset: TooManyStaticImports
    +    J2ee ruleset: DoNotCallSystemExit, StaticEJBFieldShouldBeFinal,DoNotUseThreads
    +    Strings ruleset: UseEqualsToCompareStrings
    +
    +Fixed bug 674394  - fixed false positive in DuplicateImports for disambiguation import
    +Fixed bug 631681  - fixed false positive in UnusedPrivateField when field is accessed by outer class
    +Fixed bug 985989  - fixed false negative in ConstructorCallsOverridableMethod for inner static classes
    +Fixed bug 1409944 - fixed false positive in SingularField for lock objects
    +Fixed bug 1472195 - fixed false positives in PositionLiteralsFirstInComparisons when the string is used as a parameter
    +Fixed bug 1522517 - fixed false positive in UselessOverridingMethod for clone method
    +Fixed bug 1744065 - fixed false positive in BooleanInstantiation when a custom Boolean is used
    +Fixed bug 1765613 - fixed NullPointerException in CloneMethodMustImplementCloneable when checking enum
    +Fixed bug 1740480 - fixed false positive in ImmutableField when the assignment is inside an 'if'
    +Fixed bug 1702782 - fixed false positive in UselessOperationOnImmutable when an Immutable on which an operation is performed is compareTo'd
    +Fixed bugs 1764288/1744069/1744071 - When using Type Resolution all junit test cases will notice if you're using an extended TestCase
    +Fixed bug 1793215 - pmd-nicerhtml.xsl does not display line numbers
    +Fixes bug 1796928 - fixed false positive in AvoidThrowingRawExceptionTypes, when a Type name is the same as a RawException.
    +Fixed bug 1811506 - False - : UnusedFormalParameter (property "checkall" needs to be set)
    +Fixed false negative in UnnecessaryCaseChange
    +
    +The Java 1.5 source code parser is now the default for testcode used in PMD's unit tests.
    +Added TypeResolution to the XPath rule. Use typeof function to determine if a node is of a particular type
    +Adding a GenericLiteralChecker, a generic rule that require a regex as property. It will log a violation if a Literal is matched by the regex. See the new rule AvoidUsingHardCodedIP for an example.
    +Adding support for multiple line span String in CPD's AbstractTokenizer, this may change, for the better, CPD's Ruby parsing.
    +This release adds 'nicehtml', with the plan for the next major release to make nicehtml->html, and html->oldhtml. This feature uses an XSLT transformation, default stylesheet maybe override with '-xslt filename'.
    +New CPD command line feature : Using more than one directory for sources. You can now have several '--files' on the command line.
    +SingularField greatly improved to generate very few false positives (none?). Moved from controversial to design. Two options added to restore old behaviour (mostly).
    +Jaxen updated to 1.1.1, now Literal[@Image='""'] works in XPath expressions.
    +
    + +

    July 20, 2007 - 4.0

    + +
    Fixed bug 1697397 - fixed false positives in ClassCastExceptionWithToArray
    +Fixed bug 1728789 - removed redundant rule AvoidNonConstructorMethodsWithClassName; MethodWithSameNameAsEnclosingClass is faster and does the same thing.
    +
    + +

    July 12, 2007 - 4.0rc2:

    + +
    New rules:
    +    Typeresolution ruleset: SignatureDeclareThrowsException - re-implementation using the new Type Resolution facility (old rule is still available)
    +Fixed bug 1698550 - CloneMethodMustImplementCloneable now accepts a clone method that throws CloneNotSupportedException in a final class
    +Fixed bug 1680568 - The new typeresolution SignatureDeclareThrowsException rule now ignores setUp and tearDown in JUnit 4 tests and tests that do not directly extend TestCase
    +The new typeresolution SignatureDeclareThrowsException rule can now ignore JUnit classes completely by setting the IgnoreJUnitCompletely property
    +Fixed false positive in UselessOperationOnImmutable
    +PMD now defaults to using a Java 1.5 source code parser.
    +
    + +

    June 22, 2007 - 4.0rc1:

    + +
    New rules:
    +    Strict exception ruleset: DoNotExtendJavaLangError
    +    Basic JSP ruleset: JspEncoding
    +    J2EE ruleset: MDBAndSessionBeanNamingConvention, RemoteSessionInterfaceNamingConvention, LocalInterfaceSessionNamingConvention, LocalHomeNamingConvention, RemoteInterfaceNamingConvention
    +    Optimizations ruleset: AddEmptyString
    +    Naming: BooleanGetMethodName
    +New rulesets:
    +    Migrating To JUnit4: Rules that help move from JUnit 3 to JUnit 4
    +Fixed bug 1670717 - 'Copy xml to clipboard' menu command now works again in the Designer
    +Fixed bug 1618858 - PMD no longer raises an exception on XPath like '//ConditionalExpression//ConditionalExpression'
    +Fixed bug 1626232 - Commons logging rules (ProperLogger and UseCorrectExceptionLogging) now catch more cases
    +Fixed bugs 1626201 & 1633683 - BrokenNullCheck now catches more cases
    +Fixed bug 1626715 - UseAssertSameInsteadOfAssertTrue now correctly checks classes which contain the null constant
    +Fixed bug 1531216 - ImmutableField. NameOccurrence.isSelfAssignment now recognizes this.x++ as a self assignment
    +Fixed bug 1634078 - StringToString now recognizes toString on a String Array, rather than an element.
    +Fixed bug 1631646 - UselessOperationOnImmutable doesn't throw on variable.method().variable.
    +Fixed bug 1627830 - UseLocaleWithCaseConversions now works with compound string operations
    +Fixed bug 1613807 - DontImportJavaLang rule allows import to Thread inner classes
    +Fixed bug 1637573 - The PMD Ant task no longer closes System.out if toConsole is set
    +Fixed bug 1451251 - A new UnusedImports rule, using typeresolution, finds unused import on demand rules
    +Fixed bug 1613793 - MissingSerialVersionUID rule now doesn't fire on abstract classes
    +Fixed bug 1666646 - ImmutableField rule doesn't report against volatile variables
    +Fixed bug 1693924 - Type resolution now works for implicit imports
    +Fixed bug 1705716 - Annotation declarations now trigger a new scope level in the symbol table.
    +Fixed bug 1743938 - False +: InsufficientStringBufferDeclaration with multiply
    +Fixed bug 1657957 - UseStringBufferForStringAppends now catches self-assignments
    +Applied patch 1612455 - RFE 1411022 CompareObjectsWithEquals now catches the case where comparison is against new Object
    +Implemented RFE 1562230 - Added migration rule to check for instantiation of Short/Byte/Long
    +Implemented RFE 1627581 - SuppressWarnings("unused") now suppresses all warnings in unusedcode.xml
    +XPath rules are now chained together for an extra speedup in processing
    +PMD now requires JDK 1.5 to be compiled. Java 1.4 support is provided using Retroweaver
    +- PMD will still analyze code from earlier JDKs
    +- to run pmd with 1.4, use the files from the java14 directory (weaved pmd jar and support files)
    +TypeResolution now looks at some ASTName nodes.
    +Memory footprint reduced: most renderers now use less memory by generating reports on the fly.
    +Ant task now takes advantage of multithreading code and on the fly renderers
    +Ant task now logs more debug info when using -verbose
    +PMD command line now has -benchmark: output a benchmark report upon completion; default to System.err
    +
    + +

    December 19, 2006 - 3.9:

    + +
    New rules:
    +    Basic ruleset: BigIntegerInstantiation, AvoidUsingOctalValues
    +    Codesize ruleset: NPathComplexity, NcssTypeCount, NcssMethodCount, NcssConstructorCount
    +    Design ruleset: UseCollectionIsEmpty
    +    Strings ruleset: StringBufferInstantiationWithChar
    +    Typeresolution ruleset: Loose Coupling - This is a re-implementation using the new Type Resolution facility
    +Fixed bug 1610730 - MisplacedNullCheck now catches more cases
    +Fixed bug 1570915 - AvoidRethrowingException no longer reports a false positive for certain nested exceptions.
    +Fixed bug 1571324 - UselessStringValueOf no longer reports a false positive for additive expressions.
    +Fixed bug 1573795 - PreserveStackTrace doesn't throw CastClassException on exception with 0 args
    +Fixed bug 1573591 - NonThreadSafeSingleton doesn't throw NPE when using this keyword
    +Fixed bug 1371753 - UnnecessaryLocalBeforeReturn is now less aggressive in its reporting.
    +Fixed bug 1566547 - Annotations with an empty MemberValueArrayInitializer are now parsed properly.
    +Fixed bugs 1060761 / 1433119 & RFE 1196954 - CloseResource now takes an optional parameter to identify closure methods
    +Fixed bug 1579615 - OverrideBothEqualsAndHashcode no longer throws an Exception on equals methods that don't have Object as a parameter type.
    +Fixed bug 1580859 - AvoidDecimalLiteralsInBigDecimalConstructor now catches more cases.
    +Fixed bug 1581123 - False +: UnnecessaryWrapperObjectCreation.
    +Fixed bug 1592710 - VariableNamingConventions no longer reports false positives on certain enum declarations.
    +Fixed bug 1593292 - The CPD GUI now works with the 'by extension' option selected.
    +Fixed bug 1560944 - CPD now skips symlinks.
    +Fixed bug 1570824 - HTML reports generated on Windows no longer contain double backslashes.  This caused problems when viewing those reports with Apache.
    +Fixed bug 1031966 - Re-Implemented CloneMethodMustImplementCloneable as a typeresolution rule. This rule can now detect super classes/interfaces which are cloneable
    +Fixed bug 1571309 - Optional command line options may be used either before or after the mandatory arguments
    +Applied patch 1551189 - SingularField false + for initialization blocks
    +Applied patch 1573981 - false + in CloneMethodMustImplementCloneable
    +Applied patch 1574988 - false + in OverrideBothEqualsAndHashcode
    +Applied patch 1583167 - Better test code management. Internal JUnits can now be written in XML's
    +Applied patch 1613674 - Support classpaths with spaces in pmd.bat
    +Applied patch 1615519 - controversial/DefaultPackage XPath rule is wrong
    +Applied patch 1615546 - Added option to command line to write directly to a file
    +Implemented RFE 1566313 - Command Line now takes minimumpriority attribute to filter out rulesets
    +PMD now requires JDK 1.4 to run
    +- PMD will still analyze code from earlier JDKs
    +- PMD now uses the built-in JDK 1.4 regex utils vs Jakarta ORO
    +- PMD now uses the JDK javax.xml APIs rather than being hardcoded to use Xerces and Xalan
    +SummaryHTML Report changes from Brent Fisher - now contains linePrefix to support source output from javadoc using "linksource"
    +Fixed CSVRenderer - had flipped line and priority columns
    +Fixed bug in Ant task - CSV reports were being output as text.
    +Fixed false negatives in UseArraysAsList.
    +Fixed several JDK 1.5 parsing bugs.
    +Fixed several rules (exceptions on jdk 1.5 and jdk 1.6 source code).
    +Fixed array handling in AvoidReassigningParameters and UnusedFormalParameter.
    +Fixed bug in UselessOverridingMethod: false + when adding synchronization.
    +Fixed false positives in LocalVariableCouldBeFinal.
    +Fixed false positives in MethodArgumentCouldBeFinal.
    +Modified annotation suppression to use @SuppressWarning("PMD") to suppress all warnings and @SuppressWarning("PMD.UnusedLocalVariable") to suppress a particular rule's warnings.
    +Rules can now call RuleContext.getSourceType() if they need to make different checks on JDK 1.4 and 1.5 code.
    +CloseResource rule now checks code without java.sql import.
    +ArrayIsStoredDirectly rule now checks Constructors
    +undo/redo added to text areas in Designer.
    +Better 'create rule XML' panel in Designer.
    +use of entrySet to iterate over Maps.
    +1.6 added as a valid option for targetjdk.
    +PMD now allows rules to use Type Resolution. This was referenced in patch 1257259.
    +Renderers use less memory when generating reports.
    +New DynamicXPathRule class to speed up XPath based rules by providing a base type for the XPath expression.
    +Multithreaded processing on multi core or multi cpu systems.
    +Performance Refactoring, XPath rules re-written as Java:
    +    AssignmentInOperand
    +    AvoidDollarSigns
    +    DontImportJavaLang
    +    DontImportSun
    +    MoreThanOneLogger
    +    SuspiciousHashcodeMethodName
    +    UselessStringValueOf
    +
    + +

    October 4, 2006 - 3.8:

    + +
    New rules:
    +    Basic ruleset: BrokenNullCheck
    +    Strict exceptions ruleset: AvoidRethrowingException
    +    Optimizations ruleset: UnnecessaryWrapperObjectCreation
    +    Strings ruleset: UselessStringValueOf
    +Fixed bug 1498910 - AssignmentInOperand no longer has a typo in the message.
    +Fixed bug 1498960 - DontImportJavaLang no longer reports static imports of java.lang members.
    +Fixed bug 1417106 - MissingBreakInSwitch no longer flags stmts where every case has either a return or a throw.
    +Fixed bug 1412529 - UncommentedEmptyConstructor no longer flags private constructors.
    +Fixed bug 1462189 - InsufficientStringBufferDeclaration now resets when it reaches setLength the same way it does at a Constructor
    +Fixed bug 1497815 - InsufficientStringBufferDeclaration rule now takes the length of the constructor into account, and adds the length of the initial string to its initial length
    +Fixed bug 1504842 - ExceptionSignatureDeclaration no longer flags methods starting with 'test'.
    +Fixed bug 1516728 - UselessOverridingMethod no longer raises an NPE on methods that use generics.
    +Fixed bug 1522054 - BooleanInstantiation now detects instantiations inside method calls.
    +Fixed bug 1522056 - UseStringBufferForStringAppends now flags appends which occur in static initializers and constructors
    +Fixed bug 1526530 - SingularField now finds fields which are hidden at the method or static level
    +Fixed bug 1529805 - UnusedModifier no longer throws NPEs on JDK 1.5 enums.
    +Fixed bug 1531593 - UnnecessaryConversionTemporary no longer reports false positives when toString() is invoked inside the call to 'new Long/Integer/etc()'.
    +Fixed bug 1512871 - Improved C++ tokenizer error messages - now they include the filename.
    +Fixed bug 1531152 - CloneThrowsCloneNotSupportedException now reports the proper line number.
    +Fixed bug 1531236 - IdempotentOperations reports fewer false positives.
    +Fixed bug 1544564 - LooseCoupling rule now checks for ArrayLists
    +Fixed bug 1544565 - NonThreadSafeSingleton now finds if's with compound statements
    +Fixed bug 1561784 - AbstractOptimizationRule no longer throws ClassCastExceptions on certain postfix expressions.
    +Fixed a bug in AvoidProtectedFieldInFinalClass - it no longer reports false positives for protected fields in inner classes.
    +Fixed a bug in the C++ grammar - the tokenizer now properly recognizes macro definitions which are followed by a multiline comment.
    +Modified C++ tokenizer to use the JavaCC STATIC option; this results in about a 30% speedup in tokenizing.
    +Implemented RFE 1501850 - UnusedFormalParameter now catches cases where a parameter is assigned to but not used.
    +Applied patch 1481024 (implementing RFE 1490181)- NOPMD messages can now be reported with a user specified msg, e.g., //NOPMD - this is expected
    +Added JSP support to the copy/paste detector.
    +Placed JSF/JSP ruleset names in rulesets/jsprulesets.properties
    +Added the image to the ASTEnumConstant nodes.
    +Added new XSLT stylesheet for CPD XML->HTML from Max Tardiveau.
    +Refactored UseIndexOfChar to extract common functionality into AbstractPoorMethodCall.
    +Improved CPD GUI and Designer look/functionality; thanks to Brian Remedios for the changes!
    +Rewrote the NOPMD mechanism to collect NOPMD markers as the source file is tokenized.  This eliminates an entire scan of each source file.
    +Applied patch from Jason Bennett to enhance CyclomaticComplexity rule to account for conditional or/and nodes, do stmts, and catch blocks.
    +Applied patch from Xavier Le Vourch to reduce false postives from CloneMethodMustImplementCloneable.
    +Updated Jaxen library to beta 10.
    +Performance Refactoring, XPath rules re-written as Java:
    +    BooleanInstantiation
    +    UselessOperationOnImmutable
    +    OverrideBothEqualsAndHashcode
    +    UnnecessaryReturn
    +    UseStringBufferForStringAppends
    +    SingularField
    +    NonThreadSafeSingleton
    +
    + +

    June 1, 2006 - 3.7:

    + +
    New rules:
    +    Basic-JSP ruleset: DuplicateJspImport
    +    Design ruleset: PreserveStackTrace
    +    J2EE ruleset: UseProperClassLoader
    +Implemented RFE 1462019 - Add JSPs to Ant Task
    +Implemented RFE 1462020 - Add JSPs to Designer
    +Fixed bug 1461426 InsufficientStringBufferDeclaration does not consider paths
    +Fixed bug 1462184 False +: InsufficientStringBufferDeclaration - wrong size
    +Fixed bug 1465574 - UnusedPrivateMethod no longer reports false positives when a private method is called from a method with a parameter of the same name.
    +Fixed bug 1114003 - UnusedPrivateMethod no longer reports false positives when two methods have the same name and number of arguments but different types.  The fix causes PMD to miss a few valid cases, but, c'est la vie.
    +Fixed bug 1472843 - UnusedPrivateMethod no longer reports false positives when a private method is only called from a method that contains a variable with the same name as that method.
    +Fixed bug 1461442 - UseAssertSameInsteadOfAssertTrue now ignores comparisons to null; UseAssertNullInsteadOfAssertTrue will report those.
    +Fixed bug 1474778 - UnnecessaryCaseChange no longer flags usages of toUpperCase(Locale).
    +Fixed bug 1423429 - ImmutableField no longer reports false positives on variables which can be set via an anonymous inner class that is created in the constructor.
    +Fixed major bug in CPD; it was not picking up files other than .java or .jsp.
    +Fixed a bug in CallSuperInConstructor; it now checks inner classes/enums more carefully.
    +Fixed a bug in VariableNamingConventions; it was not setting the warning message properly.
    +Fixed bug in C/C++ parser; a '$' is now allowed in an identifier.  This is useful in VMS.
    +Fixed a symbol table bug; PMD no longer crashes on enumeration declarations in the same scope containing the same field name
    +Fixed a bug in ASTVariableDeclaratorId that triggered a ClassCastException if a annotation was used on a parameter.
    +Added RuleViolation.getBeginColumn()/getEndColumn()
    +Added an optional 'showSuppressed' item to the Ant task; this is false by default and toggles whether or not suppressed items are shown in the report.
    +Added an IRuleViolation interface and modified various code classes (include Renderer implementations and Report) to use it.
    +Modified JJTree grammar to use conditional node descriptors for various expression nodes and to use node suppression for ASTModifier nodes; this replaces a bunch of DiscardableNodeCleaner hackery.  It also fixed bug 1445026.
    +Modified C/CPP grammar to only build the lexical analyzer; we're not using the parser for CPD, just the token manager.  This reduces the PMD jar file size by about 50 KB.
    +
    + +

    March 29, 2006 - 3.6:

    + +
    New rules:
    +    Basic ruleset: AvoidThreadGroup
    +    Design ruleset: UnsynchronizedStaticDateFormatter
    +    Strings ruleset: InefficientEmptyStringCheck, InsufficientStringBufferDeclaration
    +    JUnit ruleset: SimplifyBooleanAssertion
    +    Basic-JSF ruleset: DontNestJsfInJstlIteration
    +    Basic-JSP ruleset: NoLongScripts, NoScriptlets, NoInlineStyleInformation, NoClassAttribute, NoJspForward, IframeMissingSrcAttribute, NoHtmlComments
    +Fixed bug 1414985 - ConsecutiveLiteralAppends now checks for intervening references between appends.
    +Fixed bug 1418424 - ConsecutiveLiteralAppends no longer flags appends in separate methods.
    +Fixed bug 1416167 - AppendCharacterWithChar now catches cases involving escaped characters.
    +Fixed bug 1421409 - Ant task now has setter to allow minimumPriority attribute to be used.
    +Fixed bug 1416164 - InefficientStringBuffering no longer reports false positives on the three argument version of StringBuffer.append().
    +Fixed bug 1415326 - JUnitTestsShouldContainAsserts no longer errors out on JDK 1.5 generics.
    +Fixed bug 1415333 - CyclomaticComplexity no longer errors out on JDK 1.5 enums.
    +Fixed bug 1415663 - PMD no longer fails to parse abstract classes declared in a method.
    +Fixed bug 1433439 - UseIndexOfChar no longer reports false positives on case like indexOf('a' + getFoo()).
    +Fixed bug 1435218 - LoggerIsNotStaticFinal no longer reports false positives for local variables.
    +Fixed bug 1413745 - ArrayIsStoredDirectly no longer reports false positives for array deferences.
    +Fixed bug 1435751 - Added encoding type of UTF-8 to the CPD XML file.
    +Fixed bug 1441539 - ConsecutiveLiteralAppends no longer flags appends() involving method calls.
    +Fixed bug 1339470 - PMD no longer fails to parse certain non-static initializers.
    +Fixed bug 1425772 - PMD no longer fails with errors in ASTFieldDeclaration when parsing some JDK 1.5 code.
    +Fixed bugs 1448123 and 1449175 - AvoidFieldNameMatchingTypeName, SingularField, TooManyFields, and AvoidFieldNameMatchingMethodName no longer error out on enumerations.
    +Fixed bug 1444654 - migrating_to_14 and migrating_to_15 no longer refer to rule tests.
    +Fixed bug 1445231 - TestClassWithoutTestCases: no longer flags abstract classes.
    +Fixed bug 1445765 - PMD no longer uses huge amounts of memory.  However, you need to use RuleViolation.getBeginLine(); RuleViolation.getNode() is no more.
    +Fixed bug 1447295 - UseNotifyAllInsteadOfNotify no longer flags notify() methods that have a parameter.
    +Fixed bug 1455965 - MethodReturnsInternalArray no longer flags variations on 'return new Object[] {}'.
    +Implemented RFE 1415487 - Added a rulesets/releases/35.xml ruleset (and similar rulesets for previous releases) contains rules new to PMD v3.5
    +Wouter Zelle fixed a false positive in NonThreadSafeSingleton.
    +Wouter Zelle fixed a false positive in InefficientStringBuffering.
    +The CPD Ant task now supports an optional 'language' attribute.
    +Removed some ill-advised casts from the parsers.
    +Fixed bug in CallSuperInConstructor; it no longer flag classes without extends clauses.
    +Fixed release packaging; now entire xslt/ directory contents are included.
    +Added more XSLT from Dave Corley - you can use them to filter PMD reports by priority level.
    +You can now access the name of a MemberValuePair node using getImage().
    +PositionLiteralsFirstInComparisons was rewritten in XPath.
    +Added a getVersionString method to the TargetJDKVersion interface.
    +Added an option '--targetjdk' argument to the Benchmark utility.
    +Applied a patch from Wouter Zelle to clean up the Ant Formatter class, fix a TextRenderer bug, and make toConsole cleaner.
    +Rewrote AvoidCallingFinalize in Java; fixed bug and runs much faster, too.
    +Uploaded ruleset schema to http://pmd.sf.net/ruleset_xml_schema.xsd
    +UseIndexOfChar now catches cases involving lastIndexOf.
    +Rules are now run in the order in which they're listed in a ruleset file.  Internally, they're now stored in a List vs a Set, and RuleSet.getRules() now returns a Collection.
    +Upgraded to JUnit version 3.8.2.
    +
    + +

    Jan 25, 2006 - 3.5:

    + +
    New rules:
    + Basic ruleset: UselessOperationOnImmutable, MisplacedNullCheck, UnusedNullCheckInEquals
    + Migration ruleset: IntegerInstantiation
    + JUnit ruleset: UseAssertNullInsteadOfAssertTrue
    + Strings ruleset: AppendCharacterWithChar, ConsecutiveLiteralAppends, UseIndexOfChar
    + Design ruleset: AvoidConstantsInterface
    + Optimizations ruleset: UseArraysAsList, AvoidArrayLoops
    + Controversial ruleset: BooleanInversion
    +Fixed bug 1371980 - InefficientStringBuffering no longer flags StringBuffer methods other than append().
    +Fixed bug 1277373 - InefficientStringBuffering now catches more cases.
    +Fixed bug 1376760 - InefficientStringBuffering no longer throws a NullPointerException when processing certain expressions.
    +Fixed bug 1371757 - Misleading example in AvoidSynchronizedAtMethodLevel
    +Fixed bug 1373510 - UseAssertSameInsteadOfAssertTrue no longer has a typo in its message, and its message is more clear.
    +Fixed bug 1375290 - @SuppressWarnings annotations are now implemented correctly; they accept one blank argument to suppress all warnings.
    +Fixed bug 1376756 - UselessOverridingMethod no longer throws an exception on overloaded methods.
    +Fixed bug 1378358 - StringInstantiation no longer throws ClassCastExceptions on certain allocation patterns.
    +Fixed bug 1371741 - UncommentedEmptyConstructor no longer flags constructors that consist of a this() or a super() invocation.
    +Fixed bug 1277373 - InefficientStringBuffering no longer flags concatenations that involve a static final String.
    +Fixed bug 1379701 - CompareObjectsWithEquals no longer flags comparisons of array elements.
    +Fixed bug 1380969 - UnusedPrivateMethod no longer flags private static methods that are only invoked in a static context from a field declaration.
    +Fixed bug 1384594 - Added a 'prefix' property for BeanMembersShouldSerializeRule
    +Fixed bug 1394808 - Fewer missed hits for AppendCharacterWithChar and InefficientStringBuffering, thanks to Allan Caplan for catching these
    +Fixed bug 1400754 - A NPE is no longer thrown on certain JDK 1.5 enum usages.
    +Partially fixed bug 1371753 - UnnecessaryLocalBeforeReturn message now reflects the fact that that rule flags all types
    +Fixed a bug in UseStringBufferLength; it no longers fails with an exception on expressions like StringBuffer.toString.equals(x)
    +Fixed a bug in CPD's C/C++ parser so that it no longer fails on multi-line literals; thx to Tom Judge for the nice patch.
    +CPD now recognizes '--language c' and '--language cpp' as both mapping to the C/C++ parser.
    +Modified renderers to support disabling printing of suppressed warnings.  Introduced a new AbstractRenderer class that all Renderers can extends to get the current behavior - that is, suppressed violations are printed.
    +Implemented RFE 1375435 - you can now embed regular expressions inside XPath rules, i.e., //ClassOrInterfaceDeclaration[matches(@Image, 'F?o')].
    +Added current CLASSPATH to pmd.bat.
    +UnusedFormalParameter now catches unused constructor parameters, and its warning message now reflects whether it caught a method or a constructor param.
    +Rebuilt JavaCC parser with JavaCC 4.0.
    +Added jakarta-oro-2.0.8.jar as a new dependency to support regular expression in XPath rules.
    +Ant task now supports a 'minimumPriority' attribute; only rules with this priority or higher will be run.
    +Renamed Ant task 'printToConsole' attribute to 'toConsole' and it can only be used inside a formatter element.
    +Added David Corley's Javascript report, more details are here: http://tomcopeland.blogs.com/juniordeveloper/2005/12/demo_of_some_ni.html
    +
    + +

    November 30, 2005 - 3.4:

    + +
    New rules:
    + Basic ruleset: ClassCastExceptionWithToArray, AvoidDecimalLiteralsInBigDecimalConstructor
    + Design ruleset: NonThreadSafeSingleton, UncommentedEmptyMethod, UncommentedEmptyConstructor
    + Controversial ruleset: DefaultPackage
    + Naming ruleset: MisleadingVariableName
    + Migration ruleset: ReplaceVectorWithList, ReplaceHashtableWithMap, ReplaceEnumerationWithIterator, AvoidEnumAsIdentifier, AvoidAssertAsIdentifier
    + Strings ruleset: UseStringBufferLength
    +Fixed bug 1292745 - Removed unused source file ExceptionTypeChecking.java
    +Fixed bug 1292609 - The JDK 1.3 parser now correctly handles certain 'assert' usages.  Also added a 'JDK 1.3' menu item to the Designer.
    +Fixed bug 1292689 - Corrected description for UnnecessaryLocalBeforeReturn
    +Fixed bug 1293157 - UnusedPrivateMethod no longer reports false positives for private methods which are only invoked from static initializers.
    +Fixed bug 1293277 - Messages that used 'pluginname' had duplicated messages.
    +Fixed bug 1291353 - ASTMethodDeclaration isPublic/isAbstract methods always return true.  The syntactical modifier - i.e., whether or not 'public' was used in the source code in the method declaration - is available via 'isSyntacticallyPublic' and 'isSyntacticallyAbstract'
    +Fixed bug 1296544 - TooManyFields no longer checks the wrong property value.
    +Fixed bug 1304739 - StringInstantiation no longer crashes on certain String constructor usages.
    +Fixed bug 1306180 - AvoidConcatenatingNonLiteralsInStringBuffer no longer reports false positives on certain StringBuffer usages.
    +Fixed bug 1309235 - TooManyFields no longer includes static finals towards its count.
    +Fixed bug 1312720 - DefaultPackage no longer flags interface fields.
    +Fixed bug 1312754 - pmd.bat now handles command line arguments better in WinXP.
    +Fixed bug 1312723 - Added isSyntacticallyPublic() behavior to ASTFieldDeclaration nodes.
    +Fixed bug 1313216 - Designer was not displaying 'final' attribute for ASTLocalVariableDeclaration nodes.
    +Fixed bug 1314086 - Added logging-jakarta-commons as a short name for rulesets/logging-jakarta-commons.xml to SimpleRuleSetNameMapper.
    +Fixed bug 1351498 - Improved UnnecessaryCaseChange warning message.
    +Fixed bug 1351706 - CompareObjectsWithEquals now catches more cases.
    +Fixed bug 1277373 (and 1347286) - InefficientStringBuffering now flags fewer false positives.
    +Fixed bug 1363447 - MissingBreakInSwitch no longer reports false positives for switch statements where each switch label has a return statement.
    +Fixed bug 1363458 - MissingStaticMethodInNonInstantiatableClass no longer reports cases where there are public static fields.
    +Fixed bug 1364816 - ImmutableField no longer reports false positives for fields assigned in an anonymous inner class in a constructor.
    +Implemented RFE 1311309 (and 1119854) - Suppressed RuleViolation counts are now included in the reports.
    +Implemented RFE 1220371 - Rule violation suppression via annotations.  Per the JLS, @SuppressWarnings can be placed before the following nodes: TYPE, FIELD, METHOD, PARAMETER, CONSTRUCTOR, LOCAL_VARIABLE.
    +Implemented RFE 1275547 - OverrideBothEqualsAndHashcode now skips Comparator implementations.
    +Applied patch 1306999 - Renamed CloseConnection to CloseResource and added support for checking Statement and ResultSet objects.
    +Applied patch 1344754 - EmptyCatchBlock now skips catch blocks that contain comments.  This is also requested in RFE 1347884.
    +Renamed AvoidConcatenatingNonLiteralsInStringBuffer to InefficientStringBuffering; new name is a bit more concise.
    +Modified LongVariable; now it has a property which can be used to override the minimum reporting value.
    +Improved CPD XML report.
    +CPD no longer skips header files when checking C/C++ code.
    +Reworked CPD command line arguments; old-style arguments will still work for one more version, though.
    +Lots of documentation improvements.
    +
    + +

    September 15, 2005 - 3.3:

    + +
    New rules:
    +    Design: PositionLiteralsFirstInComparisons,  UnnecessaryLocalBeforeReturn
    +    Logging-jakarta-commons: ProperLogger
    +    Basic: UselessOverridingMethod
    +    Naming: PackageCase, NoPackage
    +    Strings: UnnecessaryCaseChange
    +Implemented RFE 1220171 - rule definitions can now contain a link to an external URL for more information on that rule - for example, a link to the rule's web page.  Thanks to Wouter Zelle for designing and implementing this!
    +Implemented RFE 1230685 - The text report now includes parsing errors even if no rule violations are reported
    +Implemented RFE 787860 - UseSingleton now accounts for JUnit test suite declarations.
    +Implemented RFE 1097090 - The Report object now contains the elapsed time for running PMD.  This shows up in the XML report as an elapsedTime attribute in the pmd element in the format '2m 5s' or '1h 5h 35s' or '25s' .
    +Implemented RFE 1246338 - CPD now handles SCCS directories and NTFS junction points.
    +Fixed bug 1226858 - JUnitAssertionsShouldIncludeMessage now checks calls to assertFalse.
    +Fixed bug 1227001 - AvoidCallingFinalize no longer flags calls to finalize() within finalizers.
    +Fixed bug 1229755 - Fixed typo in ArrayIsStoredDirectly description.
    +Fixed bug 1229749 - Improved error message when an external rule is not found.
    +Fixed bug 1224849 - JUnitTestsShouldContainAsserts no longer skips method declarations which include explicit throws clauses.
    +Fixed bug 1225492 - ConstructorCallsOverridableMethod now reports the correct method name.  dvholten's examples in RFE 1235562 also helped with this a great deal.
    +Fixed bug 1228589 - DoubleCheckedLocking and ExceptionSignatureDeclaration no longer throw ClassCastExceptions on method declarations that declare generic return types.
    +Fixed bug 1235299 - NullAssignment no longer flags null equality comparisons in ternary expressions.
    +Fixed bug 1235300 - NullAssignment no longer flags assignments to final fields.
    +Fixed bug 1240201 - The UnnecessaryParentheses message is no longer restricted to return statements.
    +Fixed bug 1242290 - The JDK 1.5 parser no longer chokes on nested enumerations with a constructor.
    +Fixed bug 1242544 - SimplifyConditional no longer flags null checks that precede an instanceof involving an array dereference.
    +Fixed bug 1242946 - ArrayIsStoredDirectly no longer reports false positives for equality expression comparisons.  As a bonus, its message now includes the variable name :-)
    +Fixed bug 1232648 - MethodReturnsInternalArray no longer reports false positives on return statement expressions that involve method invocations on an internal array.
    +Fixed bug 1244428 - MissingStaticMethodInNonInstantiatableClass no longer reports warnings for nested classes.  Some inner class cases will be missed, but false positives will be eliminated as well.
    +Fixed bug 1244443 - EqualsNull now catches more cases.
    +Fixed bug 1250949 - The JDK 1.5 parser no longer chokes on annotated parameters and annotated local variables.
    +Fixed bug 1245139 - TooManyFields no longer throws a ClassCastException when processing anonymous classes.
    +Fixed bug 1251256 - ImmutableField no longer skips assignments in try blocks on methods (which led to false positives).
    +Fixed bug 1250949 - The JDK 1.5 parser no longer chokes on AnnotationTypeMemberDeclaration with a default value.
    +Fixed bug 1245367 - ImmutableField no longer triggers on assignments in loops in constructors.
    +Fixed bug 1251269 - AvoidConcatenatingNonLiteralsInStringBuffer no longer triggers on StringBuffer constructors like 'new StringBuffer(1 + getFoo());'
    +Fixed bug 1244570 - AvoidConcatenatingNonLiteralsInStringBuffer no longer triggers on certain AST patterns involving local variable declarations inside Statement nodes.
    +Fixed bug 695344 - StringInstantiation no longer triggers on the String(byte[]) constructor.
    +Fixed bug 1114754 - UnusedPrivateMethod reports fewer false positives.
    +Fixed bug 1290718 - Command line parameter documentation is now correct for targetjdk options.
    +Applied patch 1228834 - XPath rules can now use properties to customize rules.  Thanks to Wouter Zelle for another great piece of work!
    +Fixed a bug in RuleSetFactory that missed some override cases; thx to Wouter Zelle for the report and a fix.
    +Fixed a bug in the grammar that didn't allow constructors to have type parameters, which couldn't parse some JDK 1.5 constructs.
    +Fixed a bug in ImportFromSamePackage; now it catches the case where a class has an on-demand import for the same package it is in.
    +Fixed a bug in CompareObjectsWithEquals; now it catches some local variable cases.
    +Fixed a bug in CouplingBetweenObjects; it no longer triggers an exception (which is a bug in the symbol table layer) by calling getEnclosingClassScope() when the node in question isn't enclosed by one.
    +Moved AvoidCallingFinalize from the design ruleset to the finalize ruleset and then deleted redundant ExplicitCallToFinalize rule from the finalize ruleset.
    +Deleted redundant ExceptionTypeChecking rule from the strictexception ruleset; use AvoidInstanceofChecksInCatchClause in the design ruleset instead.
    +Added some new XSLT scripts that create nifty HTML output; thanks to Wouter Zelle for the code.
    +Improved UseCorrectExceptionLogging; thx to Wouter Zelle for the new XPath.
    +Improved warning message from UnusedPrivateMethod.
    +Improved EmptyIfStmt; now it catches the case where an IfStatement is followed by an EmptyStatement node.
    +The Ant task now accepts the short names of rulesets (e.g., unusedcode for rulesets/unusedcode.xml).
    +Removed unnecessary '.html' suffix from displayed filenames when the linkPrefix attribute is used with the HTML renderer.
    +Added an optional 'description' attribute to the 'property' element in the ruleset XML files.
    +Added a simplified SimpleNode.addViolation() method to reduce duplicated rule violation creation code.
    +Moved from jaxen-1.0-fcs.jar/saxpath-1.0-fcs.jar to jaxen-1.1-beta-7.jar.  This yielded a 20% speed increase in the basic ruleset!
    +
    + +

    June 21, 2005 - 3.2:

    + +
    New rules: UseCorrectExceptionLogging (logging-jakarta-commons ruleset), AvoidPrintStackTrace (logging-java ruleset), CompareObjectsWithEquals (design ruleset)
    +Fixed bug 1201577 - PMD now correctly parses method declarations that return generic types.
    +Fixed bug 1205709 - PMD no longer takes a long time to report certain parsing errors.
    +Fixed bug 1052356 - ImmutableField no longer triggers on fields which are assigned to in a constructor's try statement.
    +Fixed bug 1215854 - Package/class/method names are now filled in whenever possible, and the XML report includes all three.
    +Fixed bug 1209719 - MethodArgumentCouldBeFinal no longer triggers on arguments which are modified using postfix or prefix expressions.  A bug in AvoidReassigningParameters was also fixed under the same bug id.
    +Fixed bug 1188386 - MethodReturnsInternalArray no longer flags returning a local array declaration.
    +Fixed bug 1172137 - PMD no longer locks up when generating a control flow graph for if statements with labelled breaks.
    +Fixed bug 1221094 - JUnitTestsShouldContainAsserts no longer flags static methods.
    +Fixed bug 1217028 - pmd.bat now correctly passes parameters to PMD.
    +Implemented RFE 1188604 - AvoidThrowingCertainExceptionTypes has been split into AvoidThrowingRawExceptionTypes and AvoidThrowingNullPointerException.
    +Implemented RFE 1188369 - UnnecessaryBooleanAssertion now checks for things like 'assertTrue(!foo)'.  These should be changed to 'assertFalse(foo)' for clarity.
    +Implemented RFE 1199622 - UnusedFormalParameter now defaults to only checking private methods unless a 'checkall' property is set.
    +Implemented RFE 1220314 - the symbol table now includes some rudimentary type information.
    +Break and continue statement labels (if present) are placed in the image field.
    +Fixed bug which caused MissingSerialVersionUID to trigger on all interfaces that implemented other interfaces.
    +Modified NullAssignmentRule to catch null assignments in ternary expressions.
    +Added two new node types - ASTCatchStatement and ASTFinallyStatement.
    +Modified rule XML definition; it no longer includes a symboltable attribute since the symbol table layer is now run for all files analyzed.
    +Harden equality of AbstractRule and RuleSet objects (needed for the Eclipse plugin features)
    +Change RuleSet.getRuleByName. Now return null instead of throwing a RuntimeException when the rule is not found
    +Add .project and .classpath to the module so that it can be checkout as an Eclipse project
    +
    + +

    May 10, 2005 - 3.1:

    + +
    New rules: SimplifyStartsWith, UnnecessaryParentheses, CollapsibleIfStatements, UseAssertEqualsInsteadOfAssertTrue,  UseAssertSameInsteadOfAssertTrue, UseStringBufferForStringAppends, SimplifyConditional, SingularField
    +Fixed bug 1170535 - LongVariable now report variables longer than 17 characters, not 12.
    +Fixed bug 1182755 - SystemPrintln no longer overreports problems.
    +Fixed bug 1188372 - AtLeastOneConstructor no longer fires on interfaces.
    +Fixed bug 1190508 - UnnecessaryBooleanAssertion no longer fires on nested boolean literals.
    +Fixed bug 1190461 - UnusedLocal no longer misses usages which are on the RHS of a right bit shift operator.
    +Fixed bug 1188371 - AvoidInstantiatingObjectsInLoops no longer fires on instantiations in loops when the 'new' keyword is preceded by a 'return' or a 'throw'.
    +Fixed bug 1190526 - TooManyFields now accepts a property setting correctly, and default lower bound is 15 vs 10.
    +Fixed bug 1196238 - UnusedImports no longer reports false positives for various JDK 1.5 java.lang subpackages.
    +Fixed bug 1169731 - UnusedImports no longer reports false positives on types used inside generics.  This bug also resulted in a bug in ForLoopShouldBeWhileLoop being fixed, thanks Wim!
    +Fixed bug 1187325 - UnusedImports no longer reports a false positive on imports which are used inside an Annotation.
    +Fixed bug 1189720 - PMD no longer fails to parse generics that use 'member selectors'.
    +Fixed bug 1170109 - The Ant task now supports an optional 'targetjdk' attribute that accepts values of '1.3', '1.4', or '1.5'.
    +Fixed bug 1183032 - The XMLRenderer no longer throws a SimpleDateFormat exception when run with JDK 1.3.
    +Fixed bug 1097256 - The XMLRenderer now supports optional encoding of UTF8 characters using the 'net.sourceforge.pmd.supportUTF8' environment variable.
    +Fixed bug 1198832 - AbstractClassWithoutAbstractMethod no longer flags classes which implement interfaces since these can partially implement the interface and thus don't need to explicitly declare abstract methods.
    +Implemented RFE 1193979 - BooleanInstantiation now catches cases like Boolean.valueOf(true)
    +Implemented RFE 1171095 - LabeledStatement nodes now contain the image of the label.
    +Implemented RFE 1176401 - UnusedFormalParameter now flags public methods.
    +Implemented RFE 994338 - The msg produced by ConstructorCallsOverridableMethod now includes the offending method name.
    +Modified command line parameters; removed -jdk15 and -jdk13 parameters and added a -'targetjdk [1.3|1.4|1.5]' parameter.
    +Modified CSVRenderer to include more columns.
    +Optimized rules: FinalFieldCouldBeStatic (115 seconds to 7 seconds), SuspiciousConstantFieldName (48 seconds to 14 seconds), UnusedModifer (49 seconds to 4 seconds)
    +
    + +

    March 23, 2005 - 3.0:

    + +
    New rules: MissingSerialVersionUID, UnnecessaryFinalModifier, AbstractClassDoesNotContainAbstractMethod, MissingStaticMethodInNonInstantiatableClass, AvoidSynchronizedAtMethodLevel, AvoidCallingFinalize, UseNotifyAllInsteadOfNotify, MissingBreakInSwitch, AvoidInstanceofChecksInCatchClause, AvoidFieldNameMatchingTypeName, AvoidFieldNameMatchingMethodName, AvoidNonConstructorMethodsWithClassName, TestClassWithoutTestCases, TooManyFields, CallSuperInConstructor, UnnecessaryBooleanAssertion, UseArrayListInsteadOfVector
    +Implemented RFE 1058039 - PMD's command line interface now accepts abbreviated names for the standard rulesets; for example 'java net.sourceforge.pmd.PMD /my/source/code/ text basic,unusedcode' would run the rulesets/basic.xml and the rulesets/unusedcode.xml rulesets on the source in /my/source/code and produce a text report.
    +Implemented RFE 1119851 - PMD's Ant task now supports an 'excludeMarker' attribute.
    +Fixed bug 994400 - False +: ConstructorCallsOverridableMethodRule, thanks to ereissner for reporting it
    +Fixed bug 1146116 - JUnitTestsShouldIncludeAssert no longer crashes on inner Interface
    +Fixed bug 1114625 - UnusedPrivateField no longer throws an NPE on standalone postfix expressions which are prefixed with 'this'.
    +Fixed bug 1114020 - The Ant task now reports a complete stack trace when run with the -verbose flag.
    +Fixed bug 1117983 - MethodArgumentCouldBeFinal no longer reports false positives on try..catch blocks.
    +Fixed bug 797742 - PMD now parses JDK 1.5 source code.  Note that it's not perfect yet; more testing/bug reports are welcome!
    +Fixed a bug - the StatisticalRule no longer 'merges' data points when using the 'topscore' property.
    +Fixed a bug - the PMD Ant task's failOnRuleViolation attribute no longer causes a BuildException in the case when no rule violations occur.
    +Modified the XSLT to add a summary section.
    +Added Ruby support to CPD.
    +Optimized various rules and wrote a benchmarking application; results are here - http://infoether.com/~tom/pmd_timing.txt
    +
    + +

    February 1, 2005 - 2.3:

    + +
    Fixed bug 1113927 - ExceptionAsFlowControl no longer throws NPEs on code where a throw statement exists without a try statement wrapping it.
    +Fixed bug 1113981 - AvoidConcatenatingNonLiteralsInStringBuffer no longer throws NPEs on code where an append appears as a child of an ExplicitConstructorInvocation node.
    +Fixed bug 1114039 - AvoidInstantiatingObjectsInLoops's message no longer contains a spelling error.
    +Fixed bug 1114029 - The 'optimization' rules no longer throw NPEs at various points.
    +Fixed bug 1114251 - The 'sunsecure' rules no longer throw NPEs at various points.
    +
    + +

    January 31, 2005 - 2.2:

    + +
    New rules: LocalVariableCouldBeFinal, MethodArgumentCouldBeFinal, AvoidInstantiatingObjectsInLoops, ArrayIsStoredDirectly, MethodReturnsInternalArray, AssignmentToNonFinalStatic, AvoidConcatenatingNonLiteralsInStringBuffer
    +Fixed bug 1088459 - JUnitTestsShouldContainAsserts no longer throws ClassCastException on interface, native, and abstract method declarations.
    +Fixed bug 1100059 - The Ant task now generates a small empty-ish report if there are no violations.
    +Implemented RFE 1086168 - PMD XML reports now contain a version and timestamp attribute in the <pmd> element.
    +Implemented RFE 1031950 - The PMD Ant task now supports nested ruleset tags
    +Fixed a bug in the rule override logic; it no longer requires the "class" attribute of a rule be listed in the overrides section.
    +Added 'ignoreLiterals' and 'ignoreIdentifiers' boolean options to the CPD task.
    +Cleaned up a good bit of the symbol table code; thanks much to Harald Gurres for the patch.
    +CPD now contains a generic copy/paste checker for programs in any language
    +
    + +

    December 15, 2004 - 2.1:

    + +
    New rules: AvoidProtectedFieldInFinalClass, SystemPrintln
    +Fixed bug 1050173 - ImmutableFieldRule no longer reports false positives for static fields.
    +Fixed bug 1050286 - ImmutableFieldRule no longer reports false positives for classes which have multiple constructors only a subset of which set certain fields.
    +Fixed bug 1055346 - ImmutableFieldRule no longer reports false positive on preinc/predecrement/postfix expressions.
    +Fixed bug 1041739 - EmptyStatementNotInLoop no longer reports false positives for nested class declarations in methods.
    +Fixed bug 1039963 - CPD no longer fails to parse C++ files with multi-line macros.
    +Fixed bug 1053663 - SuspiciousConstantFieldName no longer reports false positives for interface members.
    +Fixed bug 1055930 - CouplingBetweenObjectsRule no longer throws a NPE on interfaces
    +Fixed a possible NPE in dfa.report.ReportTree.
    +Implemented RFE 1058033 - Renamed run.[sh|bat] to pmd.[sh|bat].
    +Implemented RFE 1058042 - XML output is more readable now.
    +Applied patch 1051956 - Rulesets that reference rules using "ref" can now override various properties.
    +Applied patch 1070733 - CPD's Java checker now has an option to ignore both literals and identifiers - this can help find large duplicate code blocks, but can also result in false positives.
    +YAHTMLRenderer no longer has dependence on Ant packages.
    +Modified the AST to correctly include PostfixExpression nodes.  Previously a statement like "x++;" was embedded in the parent StatementExpression node.
    +Moved BooleanInstantiation from the design ruleset to the basic ruleset.
    +Updated Xerces libraries to v2.6.2.
    +Many rule names had the word "Rule" tacked on to the end.  Various folks thought this was a bad idea, so here are the new names of those rules which were renamed:
    +- basic.xml: UnnecessaryConversionTemporary, OverrideBothEqualsAndHashcode, DoubleCheckedLocking
    +- braces.xml: WhileLoopsMustUseBraces, IfElseStmtsMustUseBraces, ForLoopsMustUseBraces
    +- clone.xml: ProperCloneImplementation
    +- codesize.xml: CyclomaticComplexity, ExcessivePublicCount
    +- controversial.xml: UnnecessaryConstructor, AssignmentInOperand, DontImportSun, SuspiciousOctalEscape
    +- coupling.xml: CouplingBetweenObjects, ExcessiveImports, LooseCoupling
    +- design.xml: UseSingleton, SimplifyBooleanReturns, AvoidReassigningParameters, ConstructorCallsOverridableMethod, AccessorClassGeneration, CloseConnection, OptimizableToArrayCall, IdempotentOperations. ImmutableField
    +- junit.xml: JUnitAssertionsShouldIncludeMessage, JUnitTestsShouldIncludeAssert
    +- logging-java.xml: MoreThanOneLogger, LoggerIsNotStaticFinal
    +- naming.xml: ShortMethodName, VariableNamingConventions, ClassNamingConventions, AbstractNaming
    +- strictexception.xml: ExceptionAsFlowControl, AvoidCatchingNPE, AvoidThrowingCertainExceptionTypes
    +Continued working on JDK 1.5 compatibility - added support for static import statements, varargs, and the new for loop syntax
    +- still TODO: generics and annotations (note that autoboxing shouldn't require a grammar change)
    +- Good article on features: http://java.sun.com/developer/technicalArticles/releases/j2se15/
    +
    + +

    October 19, 2004 - 2.0:

    + +
    New rules: InstantiationToGetClass, IdempotentOperationsRule, SuspiciousEqualsMethodName, SimpleDateFormatNeedsLocale, JUnitTestsShouldContainAssertsRule, SuspiciousConstantFieldName, ImmutableFieldRule, MoreThanOneLoggerRule, LoggerIsNotStaticFinalRule, UseLocaleWithCaseConversions
    +Applied patch in RFE 992576 - Enhancements to VariableNamingConventionsRule
    +Implemented RFE 995910 - The HTML report can now include links to HTMLlized source code - for example, the HTML generated by JXR.
    +Implemented RFE 665824 - PMD now ignores rule violations in lines containing the string 'NOPMD'.
    +Fixed bug in SimplifyBooleanExpressions - now it catches more cases.
    +Fixed bugs in AvoidDuplicateLiterals - now it ignores small duplicate literals, its message is more helpful, and it catches more cases.
    +Fixed bug 997893 - UnusedPrivateField now detects assignments to members of private fields as a usage.
    +Fixed bug 1020199 - UnusedLocalVariable no longer flags arrays as unused if an assignment is made to an array slot.
    +Fixed bug 1027133 - Now ExceptionSignatureDeclaration skips certain JUnit framework methods.
    +Fixed bug 1008548 - The 'favorites' ruleset no longer contains a broken reference.
    +Fixed bug 1045583 - UnusedModifier now correctly handles anonymous inner classes within interface field declarations.
    +Partially fixed bug 998122 - CloseConnectionRule now checks for imports of java.sql before reporting a rule violation.
    +Applied patch 1001694 - Now PMD can process zip/jar files of source code.
    +Applied patch 1032927 - The XML report now includes the rule priority.
    +Added data flow analysis facade from Raik Schroeder.
    +Added two new optional attributes to rule definitions - symboltable and dfa.  These allow the symbol table and DFA facades to be configured on a rule-by-rule basis.  Note that if your rule needs the symbol table; you'll need to add symboltable="true" to your rule definition.  FWIW, this also results in about a 5% speedup for rules that don't need either layer.
    +Added a "logging" ruleset - thanks to Miguel Griffa for the code!
    +Enhanced the ASTViewer - and renamed it 'Designer' - to display data flows.
    +Moved development environment to Maven 1.0.
    +Moved development environment to Ant 1.6.2.  This is nice because using the new JUnit task attribute "forkmode='perBatch'" cuts test runtime from 90 seconds to 7 seconds.  Sweet.
    +MethodWithSameNameAsEnclosingClass now reports a more helpful line number.
    +
    + +

    July 14, 2004 - 1.9:

    + +
    New rules: CloneMethodMustImplementCloneable, CloneThrowsCloneNotSupportedException, EqualsNull, ConfusingTernary
    +Created new "clone" ruleset and moved ProperCloneImplementationRule over from the design ruleset.
    +Moved LooseCoupling from design.xml to coupling.xml.
    +Some minor performance optimizations - removed some unnecessary casts from the grammar, simplified some XPath rules.
    +Postfix expressions (i.e., x++) are now available in the grammar.  To access them, search for StatementExpressions with an image of "++" or "--" - i.e., in XPath, //StatementExpression[@Image="++"].  This is an odd hack and hopefully will get cleared up later.
    +Ant task and CLI now used BufferedInputStreams.
    +Converted AtLeastOneConstructor rule from Java code to XPath.
    +Implemented RFE 743460: The XML report now contains the ruleset name.
    +Implemented RFE 958714: Private field and local variables that are assigned but not used are now flagged as unused.
    +Fixed bug 962782 - BeanMembersShouldSerializeRule no longer reports set/is as being a violation.
    +Fixed bug 977022 - UnusedModifier no longer reports false positives for modifiers of nested classes in interfaces
    +Fixed bug 976643 - IfElseStmtsMustUseBracesRule no longer reports false positives for certain if..else constructs.
    +Fixed bug 985961 - UseSingletonRule now fires on classes which contain static fields
    +Fixed bug 977031 - FinalizeDoesNotCallSuperFinalize no longer reports a false positive when a finalizer contains a call to super.finalize in a try {} finally {} block.
    +
    + +

    May 19, 2004 - 1.8:

    + +
    New rules: ExceptionAsFlowControlRule, BadComparisonRule, AvoidThrowingCertainExceptionTypesRule, AvoidCatchingNPERule, OptimizableToArrayCallRule
    +Major grammar changes - lots of new node types added, many superfluous nodes removed from the runtime AST.  Bug 786611 - http://sourceforge.net/tracker/index.php?func=detail&aid=786611&group_id=56262&atid=479921 - explains it a bit more.
    +Fixed bug 786611 - Expressions are no longer over-expanded in the AST
    +Fixed bug 874284 - The AST now contains tokens for bitwise or expressions - i.e., "|"
    +
    + +

    April 22, 2004 - 1.7:

    + +
    Moved development environment to Maven 1.0-RC2.
    +Fixed bug 925840 - Messages were no longer getting variable names plugged in correctly
    +Fixed bug 919308 - XMLRenderer was still messed up; 'twas missing a quotation mark.
    +Fixed bug 923410 - PMD now uses the default platform character set encoding; optionally, you can pass in a character encoding to use.
    +Implemented RFE 925839 - Added some more detail to the UseSingletonRule.
    +Added an optional 'failuresPropertyName' attribute to the Ant task.
    +Refactored away duplicate copies of XPath rule definitions in regress/, yay!
    +Removed manifest from jar file; it was only there for the Main-class attribute, and it's not very useful now since PMD has several dependencies.
    +Began working on JDK 1.5 compatibility - added support for EnumDeclaration nodes.
    +
    + +

    March 15, 2004 - 1.6:

    + +
    Fixed bug 895661 - XML reports containing error elements no longer have malformed XML.
    +Fixed a bug in UnconditionalIfStatement - it no longer flags things like "if (x==true)".
    +Applied Steve Hawkins' improvements to CPD:
    +- Various optimizations; now it runs about 4 times faster!
    +- fixed "single match per file" bug
    +- tweaked source code slicing
    +- CSV renderer
    +Added two new renderers - SummaryHTMLRenderer and PapariTextRenderer.
    +Moved development environment to Ant 1.6 and JavaCC 3.2.
    +
    + +

    February 2, 2004 - 1.5:

    + +
    New rules: DontImportSunRule, EmptyFinalizer, EmptyStaticInitializer, AvoidDollarSigns, FinalizeOnlyCallsSuperFinalize, FinalizeOverloaded, FinalizeDoesNotCallSuperFinalize, MethodWithSameNameAsEnclosingClass, ExplicitCallToFinalize, NonStaticInitializer, DefaultLabelNotLastInSwitchStmt, NonCaseLabelInSwitchStatement, SuspiciousHashcodeMethodName, EmptyStatementNotInLoop, SuspiciousOctalEscapeRule
    +FinalizeShouldBeProtected moved from design.xml to finalizers.xml.
    +Added isTrue() to ASTBooleanLiteral.
    +Added UnaryExpression to the AST.
    +Added isPackagePrivate() to AccessNode.
    +
    + +

    January 7, 2004 - 1.4:

    + +
    New rules: AbstractNamingRule, ProperCloneImplementationRule
    +Fixed bug 840926 - AvoidReassigningParametersRule no longer reports a false positive when assigning a value to an array slot when the array is passed as a parameter to a method
    +Fixed bug 760520 - RuleSetFactory is less strict about whitespace in ruleset.xml files.
    +Fixed bug 826805 - JumbledIncrementorRule no longer reports a false positive when a outer loop incrementor is used as an array index
    +Fixed bug 845343 - AvoidDuplicateLiterals now picks up cases when a duplicate literal appears in field declarations.
    +Fixed bug 853409 - VariableNamingConventionsRule no longer requires that non-static final fields be capitalized
    +Fixed a bug in OverrideBothEqualsAndHashcodeRule; it no longer reports a false positive when equals() is passed the fully qualified name of Object.
    +Implemented RFE 845348 - UnnecessaryReturn yields more useful line numbers now
    +Added a ruleset DTD and a ruleset XML Schema.
    +Added 'ExplicitExtends' and 'ExplicitImplements' attributes to UnmodifiedClassDeclaration nodes.
    +
    + +

    October 23, 2003 - 1.3:

    + +
    Relicensed under a BSD-style license.
    +Fixed bug 822245 - VariableNamingConventionsRule now handles interface fields correctly.
    +Added new rules: EmptySynchronizedBlock, UnnecessaryReturn
    +ASTType now has an getDimensions() method.
    +
    + +

    October 06, 2003 - 1.2.2:

    + +
    Added new rule: CloseConnectionRule
    +Fixed bug 782246 - FinalFieldCouldBeStatic no longer flags fields in interfaces.
    +Fixed bug 782235 - "ant -version" now prints more details when a file errors out.
    +Fixed bug 779874 - LooseCouplingRule no longer triggers on ArrayList
    +Fixed bug 781393 - VariableNameDeclaration no longer throws ClassCastExpression since ASTLocalVariableDeclaration now subclasses AccessNode
    +Fixed bug 797243 - CPD XML report can no longer contain ]]> (CDEnd)
    +Fixed bug 690196 - PMD now handles both JDK 1.3 and 1.4 code - i.e., usage of "assert" as an identifier.
    +Fixed bug 805092 - VariableNamingConventionsRule no longer flags serialVersionUID as a violation
    +Fixed bug - Specifying a non-existing rule format on the command line no longer results in a ClassNotFoundException.
    +XPath rules may now include pluggable parameters.  This feature is very limited.  For now.
    +Tweaked CPD time display field
    +Made CPD text fields uneditable
    +Added more error checking to CPD GUI input
    +Added "dialog cancelled" check to CPD "Save" function
    +Added Boris Gruschko's AST viewer.
    +Added Jeff Epstein's TextPad integration.
    +ASTType now has an isArray() method.
    +
    + +

    August 1, 2003 - 1.2.1:

    + +
    Fixed bug 781077 - line number "-1" no longer appears for nodes with siblings.
    +
    + +

    July 30, 2003 - 1.2:

    + +
    Added new rules: VariableNamingConventionsRule, MethodNamingConventionsRule, ClassNamingConventionsRule, AvoidCatchingThrowable, ExceptionSignatureDeclaration, ExceptionTypeChecking, BooleanInstantiation
    +Fixed bug 583047 - ASTName column numbers are now correct
    +Fixed bug 761048 - Symbol table now creates a scope level for anonymous inner classes
    +Fixed bug 763529 - AccessorClassGenerationRule no longer crashes when given a final inner class
    +Fixed bug 771943 - AtLeastOneConstructorRule and UnnecessaryConstructorRule no longer reports false positives on inner classes.
    +Applied patch from Chris Webster to fix another UnnecessaryConstructorRule problem.
    +Added ability to accept a comma-delimited string of files and directories on the command line.
    +Added a CSVRenderer.
    +Added a "-shortfilenames" argument to the PMD command line interface.
    +Modified grammer to provide information on whether an initializer block is static.
    +ASTViewer now shows node images and modifiers
    +ASTViewer now saves last edited text to ~/.pmd_astviewer
    +Moved the PMD Swing UI into a separate module - pmd-swingui.
    +Updated license.txt to point to new location.
    +
    + +

    June 19, 2003 - 1.1:

    + +
    Added new rules: FinalizeShouldBeProtected, FinalFieldCouldBeStatic, BeanMembersShouldSerializeRule
    +Removed "verbose" attribute from PMD and CPD Ant tasks; now they use built in logging so you can do a "ant -verbose cpd" or "ant -verbose pmd".  Thanks to Philippe T'Seyen for the code.
    +Added "excludes" feature to rulesets; thanks to Gael Marziou for the suggestion.
    +Removed "LinkedList" from LooseCouplingRule checks; thx to Randall Schulz for the suggestion.
    +CPD now processes PHP code.
    +Added VBHTMLRenderer; thanks to Vladimir Bossicard for the code.
    +Added "Save" item to CPD GUI; thanks to mcclain looney for the patch.
    +Fixed bug 732592 - Ant task now accepts a nested classpath element.
    +Fixed bug 744915 - UseSingletonRule no longer fires on abstract classes, thanks to Pablo Casado for the bug report.
    +Fixed bugs 735396 and 735399 - false positives from ConstructorCallsOverridableMethodRule
    +Fixed bug 752809 - UnusedPrivateMethodRule now catches unused private static methods, thanks to Conrad Roche for the bug report.
    +
    + +

    April 17, 2003 - 1.05:

    + +
    Added new rules: ReturnFromFinallyBlock, SimplifyBooleanExpressions
    +Added a new Ant task for CPD; thanks to Andy Glover for the code.
    +Added ability to specify a class name as a renderer on the command line or in the formatter "type" attribute of the Ant task.
    +Brian Ewins completely rewrote CPD using a portion of the Burrows-Wheeler Transform - it's much, much, much faster now.
    +Rebuilt parser with JavaCC 3.0; made several parser optimizations.
    +The Ant task now accepts a <classpath> element to aid in loading custom rulesets.  Thanks to Luke Francl for the suggestion.
    +Fixed several bugs in UnnecessaryConstructorRule; thanks to Adam Nemeth for the reports and fixes.
    +All test-data classes have been inlined into their respective JUnit tests.
    +
    + +

    March 21, 2003 - 1.04

    + +
    Added new rules: ConstructorCallsOverridableMethodRule, AtLeastOneConstructorRule, JUnitAssertionsShouldIncludeMessageRule, DoubleCheckedLockingRule, ExcessivePublicCountRule, AccessorClassGenerationRule
    +The Ant task has been updated; if you set "verbose=true" full stacktraces are printed.  Thx to Paul Roebuck for the suggestion.
    +Moved JUnit rules into their own package - "net.sourceforge.pmd.rules.junit".
    +Incorporated new ResourceLoader; thanks to Dave Fuller
    +Incorporated new XPath-based rule definitions; thanks to Dan Sheppard for the excellent work.
    +Fixed bug 697187 - Problem with nested ifs
    +Fixed bug 699287 - Grammar bug; good catch by David Whitmore
    +
    + +

    February 11, 2003 - 1.03

    + +
    Added new rules: CyclomaticComplexityRule, AssignmentInOperandRule
    +Added numbering to the HTMLRenderer; thx to Luke Francl for the code.
    +Added an optional Ant task attribute 'failOnRuleViolation'.  This stops the build if any rule violations are found.
    +Added an XSLT script for processing the PMD XML report; thx to Mats for the code.
    +The Ant task now determines whether the formatter toFile attribute is absolute or relative and routes the report appropriately.
    +Moved several rules into a new "controversial" ruleset.
    +Fixed bug 672742 - grammar typo was hosing up ASTConstructorDeclaration which was hosing up UseSingletonRule
    +Fixed bug 674393 - OnlyOneReturn rule no longer counts returns that are inside anonymous inner classes as being inside the containing method.  Thx to C. Lamont Gilbert for the bug report.
    +Fixed bug 674420 - AvoidReassigningParametersRule no longer counts parameter field reassignment as a violation.  Thx to C. Lamont Gilbert for the bug report.
    +Fixed bug 673662 - The Ant task's "failOnError" attribute works again.  Changed the semantics of this attribute, though, so it fails the build if errors occurred.  A new attribute 'failOnRuleViolation' serves the purpose of stopping the build if rule violations are found.
    +Fixed bug 676340 - Symbol table now creates new scope level when it encounters a switch statement.  See the bug for code details; generally, this bug would have triggered runtime exceptions on certain blocks of code.
    +Fixed bug 683465 - JavaCC parser no longer has ability to throw java.lang.Error; now it only throws java.lang.RuntimeExceptions.  Thx to Gunnlaugur Thor Briem for a good discussion on this topic.
    +Fixed bug in OverrideBothEqualsAndHashcodeRule - it no longer bails out with a NullPtrException on interfaces that declare a method signature "equals(Object)".  Thx to Don Leckie for catching that.
    +
    + +

    January 22, 2003 - 1.02:

    + +
    Added new rules: ImportFromSamePackageRule, SwitchDensityRule, NullAssignmentRule, UnusedModifierRule, ForLoopShouldBeWhileLoopRule
    +Updated LooseCouplingRule to check for usage of Vector; thx to Vladimir for the good catch.
    +Updated AvoidDuplicateLiteralsRule to report the line number of the first occurrence of the duplicate String.
    +Modified Ant task to use a formatter element; this lets you render a report in several formats without having to rerun PMD.
    +Added a new Ant task attribute - shortFilenames.
    +Modified Ant task to ignore whitespace in the ruleset attribute
    +Added rule priority settings.
    +Added alternate row colorization to HTML renderer.
    +Fixed bug 650623 - the Ant task now uses relative directories for the report file
    +Fixed bug 656944 - PMD no longer prints errors to System.out, instead it just rethrows any exceptions
    +Fixed bug 660069 - this was a symbol table bug; thanks to mcclain looney for the report.
    +Fixed bug 668119 - OverrideBothEqualsAndHashcodeRule now checks the signature on equals(); thanks to mcclain looney for the report.
    +
    + +

    November 07 2002 - 1.01:

    + +
    Fixed bug 633879: EmptyFinallyBlockRule now handles multiple catch blocks followed by a finally block.
    +Fixed bug 633892: StringToStringRule false positive exposed problem in symbol table usage to declaration code.
    +Fixed bug 617971: Statistical rules no longer produce tons of false positives due to accumulated results.
    +Fixed bug 633209: OnlyOneReturn rule no longer requires the return stmt to be the last statement.
    +Enhanced EmptyCatchBlockRule to flag multiple consecutive empty catch blocks.
    +Renamed AvoidStringLiteralsRule to AvoidDuplicateLiteralsRule.
    +Modified Ant task to truncate file paths to make the HTML output neater.
    +
    + +

    November 04 2002 - 1.0:

    + +
    Added new rules: StringToStringRule, AvoidReassigningParametersRule, UnnecessaryConstructorRule, AvoidStringLiteralsRule
    +Fixed bug 631010: AvoidDeeplyNestedIfStmtsRule works correctly with if..else stmts now
    +Fixed bug 631605: OnlyOneReturn handles line spillover now.
    +Moved AvoidDeeplyNestedIfStmts from the braces ruleset to the design ruleset.
    +Moved several rules from the design ruleset to the codesize ruleset.
    +Added a new "favorites" ruleset.
    +
    + +

    October 04 2002 - 1.0rc3:

    + +
    Added new rules: OnlyOneReturnRule, JumbledIncrementerRule, AvoidDeeplyNestedIfStmtsRule
    +PMD is now built and tested with JUnit 3.8.1 and Ant 1.5.
    +Added support for IntelliJ's IDEAJ.
    +Fixed bug 610018 - StringInstantiationRule now allows for String(byte[], int, int) usage.
    +Fixed bug 610693 - UnusedPrivateInstanceVariable handles parameter shadowing better.
    +Fixed bug 616535 - Command line interface input checking is better now.
    +Fixed bug 616615 - Command line interface allows the text renderer to be used now
    +Fixed a bug - the statistics rules now handle interfaces better.
    +
    + +

    September 12 2002 - 1.0rc2:

    + +
    Added new rules: JUnitSpellingRule, JUnitStaticSuiteRule, StringInstantiationRule
    +Added new rulesets - junit, strings.
    +Added a printToConsole attribute to the Ant task so that you can see the report right there in the Ant output.
    +Fixed bug in PMD GUI - rules are now saved correctly.
    +Fixed bug 597916 - CPD line counts are accurate now.
    +
    + +

    September 09 2002 - 1.0rc1:

    + +
    Added new rules: UnusedImportsRule, EmptySwitchStmtRule, SwitchStmtsShouldHaveDefaultRule, IfStmtsMustUseBracesRule
    +Fixed bug 597813 - Rule properties are now parsed correctly
    +Fixed bug 597905 - UseSingletonRule now resets its state correctly
    +Moved several rules into a new ruleset - braces.
    +Improved CPD by removing import statements and package statements from the token set.
    +Added Metrics API to the Report.
    +Updated PMD GUI.
    +
    + +

    August 16 2002 - 0.9:

    + +
    Added new rules: LongParameterListRule, SimplifyBooleanReturnsRule
    +Enhanced statistics rules to support various ways of triggering rule violations
    +Added rule customization via XML parameters
    +Enhanced CopyAndPasteDetector; added a GUI
    +Fixed bug 592060 - UnusedPrivateInstanceVariable handles explicitly referenced statics correctly
    +Fixed bug 593849 - UnusedPrivateInstanceVariable handles nested classes better
    +
    + +

    July 30 2002 - 0.8:

    + +
    Added new rule: UnusedFormalParameterRule
    +Fixed bug 588083 - ForLoopsNeedBraces rule correctly handles a variety of for statement formats
    +Added prototype of the copy and paste detector
    +
    + +

    July 25 2002 - 0.7:

    + +
    Added new rules: UnusedPrivateMethodRule, WhileLoopsMustUseBracesRule, ForLoopsMustUseBracesRule, LooseCouplingRule
    +Fixed bug 583482 - EmptyCatchBlock and EmptyFinallyBlock no longer report an incorrect line number.
    +
    + +

    July 18 2002 - 0.6:

    + +
    Added new rules: ExcessiveClassLength, ExcessiveMethodLength
    +DuplicateImportsRule now reports the correct line number.
    +Fixed bug 582639 - Rule violations are now reported on the proper line
    +Fixed bug 582509 - Removed unneeded throws clause
    +Fixed bug 583009 - Now rulesets.properties is in the jar file
    +
    + +

    July 15 2002 - 0.5:

    + +
    Added new rules: DontImportJavaLangRule, DuplicateImportsRule
    +Added new ruleset: rulesets/imports.xml
    +Changed sorting of RuleViolations to group Files together.
    +Changed XML Renderer to improved format.
    +Created DVSL Stylesheet for the new format.
    +Moved the Cougaar rules out of the PMD core.
    +Fixed bug 580093 - OverrideBothEqualsAndHashcodeRule reports a more correct line number.
    +Fixed bug 581853 - UnusedLocalVariableRule now handles anonymous inner classes correctly.
    +Fixed bug 580278 - this was a side effect of bug 581853.
    +Fixed bug 580123 - UnusedPrivateInstanceVariable now checks for instance variable usage in inner classes.
    +
    + +

    July 10 2002 - 0.4:

    + +
    Added new rules: OverrideBothEqualsAndHashcodeRule, EmptyTryBlock, EmptyFinallyBlock
    +Reports are now sorted by line number
    +RuleSets can now reference rules in other RuleSets
    +Fixed bug 579718 - made 'ruleset not found' error message clearer.
    +
    + +

    July 03 2002 - 0.3:

    + +
    Added new rules: UseSingletonRule, ShortVariableRule, LongVariableRule, ShortMethodNameRule
    +Moved rules into RuleSets which are defined in XML files in the ruleset directory
    +Ant task:
    +-Added a 'failonerror' attribute
    +-Changed 'rulesettype' to 'rulesetfiles'
    +-Removed 'text' report format; only 'html' and 'xml' are available now
    +
    + +

    June 27 2002 - 0.2:

    + +
    Added new rules: IfElseStmtsMustUseBracesRule, EmptyWhileStmtRule
    +Modified command line interface to accept a rule set
    +Fixed bug in EmptyCatchBlockRule
    +Fixed typo in UnnecessaryConversionTemporaryRule
    +Moved Ant task to the net.sourceforge.pmd.ant package
    +Added new HTML report format
    +
    + +

    June 25 2002 - 0.1:

    + +
    Initial release
    +
    + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_apex.html b/pmd_rules_apex.html new file mode 100644 index 0000000000..ade2c4ab50 --- /dev/null +++ b/pmd_rules_apex.html @@ -0,0 +1,1653 @@ + + + + + + + + +Apex Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Apex Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for Apex
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Best Practices

    + +
    Rules which enforce generally accepted best practices.
    + + + +

    Code Style

    + +
    Rules which enforce a specific coding style.
    + +
      +
    • ClassNamingConventions: Configurable naming conventions for type declarations. This rule reports type declara…
    • +
    • FieldDeclarationsShouldBeAtStart: Field declarations should appear before method declarations within a class.
    • +
    • FieldNamingConventions: Configurable naming conventions for field declarations. This rule reports variable declarations …
    • +
    • ForLoopsMustUseBraces: Avoid using ‘for’ statements without using surrounding braces. If the code formatting or indentat…
    • +
    • FormalParameterNamingConventions: Configurable naming conventions for formal parameters of methods. This rule reports f…
    • +
    • IfElseStmtsMustUseBraces: Avoid using if..else statements without using surrounding braces. If the code formatting or inden…
    • +
    • IfStmtsMustUseBraces: Avoid using if statements without using braces to surround the code block. If the code formatting…
    • +
    • LocalVariableNamingConventions: Configurable naming conventions for local variable declarations. This rule reports va…
    • +
    • MethodNamingConventions: Configurable naming conventions for method declarations. This rule reports method dec…
    • +
    • OneDeclarationPerLine: Apex allows the use of several variables declaration of the same type on one line. However, it ca…
    • +
    • PropertyNamingConventions: Configurable naming conventions for property declarations. This rule reports property…
    • +
    • VariableNamingConventions: Deprecated A variable naming conventions rule - customize this to your liking. Currently, it checks for fin…
    • +
    • WhileLoopsMustUseBraces: Avoid using ‘while’ statements without using braces to surround the code block. If the code forma…
    • +
    + +

    Design

    + +
    Rules that help you discover design issues.
    + +
      +
    • AvoidDeeplyNestedIfStmts: Avoid creating deeply nested if-then statements since they are harder to read and error-prone to …
    • +
    • CognitiveComplexity: Methods that are highly complex are difficult to read and more costly to maintain. If you include…
    • +
    • CyclomaticComplexity: The complexity of methods directly affects maintenance costs and readability. Concentrating too m…
    • +
    • ExcessiveClassLength: Excessive class file lengths are usually indications that the class may be burdened with excessiv…
    • +
    • ExcessiveParameterList: Methods with numerous parameters are a challenge to maintain, especially if most of them share th…
    • +
    • ExcessivePublicCount: Classes with large numbers of public methods and attributes require disproportionate testing effo…
    • +
    • NcssConstructorCount: This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of l…
    • +
    • NcssMethodCount: This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of l…
    • +
    • NcssTypeCount: This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of l…
    • +
    • StdCyclomaticComplexity: Complexity directly affects maintenance costs is determined by the number of decision points in a…
    • +
    • TooManyFields: Classes that have too many fields can become unwieldy and could be redesigned to have fewer field…
    • +
    + +

    Documentation

    + +
    Rules that are related to code documentation.
    + +
      +
    • ApexDoc: This rule validates that: ApexDoc comments are present for classes, methods, and properties that…
    • +
    + +

    Error Prone

    + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + +
      +
    • ApexCSRF: Having DML operations in Apex class constructor or initializers can have unexpected side effects:…
    • +
    • AvoidDirectAccessTriggerMap: Avoid directly accessing Trigger.old and Trigger.new as it can lead to a bug. Triggers should be …
    • +
    • AvoidHardcodingId: When deploying Apex code between sandbox and production environments, or installing Force.com App…
    • +
    • AvoidNonExistentAnnotations: Apex supported non existent annotations for legacy reasons. In the future, use of suc…
    • +
    • EmptyCatchBlock: Empty Catch Block finds instances where an exception is caught, but nothing is done. In most circ…
    • +
    • EmptyIfStmt: Empty If Statement finds instances where a condition is checked but nothing is done about it.
    • +
    • EmptyStatementBlock: Empty block statements serve no purpose and should be removed.
    • +
    • EmptyTryOrFinallyBlock: Avoid empty try or finally blocks - what’s the point?
    • +
    • EmptyWhileStmt: Empty While Statement finds all instances where a while statement does nothing. If it is a timing…
    • +
    • MethodWithSameNameAsEnclosingClass: Non-constructor methods should not have the same name as the enclosing class.
    • +
    • TestMethodsMustBeInTestClasses: Test methods marked as a testMethod or annotated with @IsTest, but not residing in a te…
    • +
    + +

    Performance

    + +
    Rules that flag suboptimal code.
    + +
      +
    • AvoidDmlStatementsInLoops: Deprecated Avoid DML statements inside loops to avoid hitting the DML governor limit. Instead, try to batch …
    • +
    • AvoidSoqlInLoops: Deprecated New objects created within loops should be checked to see if they can created outside them and re…
    • +
    • AvoidSoslInLoops: Deprecated Sosl calls within loops can cause governor limit exceptions. This rule is deprecated and will be …
    • +
    • OperationWithLimitsInLoop: Database class methods, DML operations, SOQL queries, or SOSL queries within loops can cause gove…
    • +
    + +

    Security

    + +
    Rules that flag potential security flaws.
    + +
      +
    • ApexBadCrypto: The rule makes sure you are using randomly generated IVs and keys for ‘Crypto’ calls. Hard-wiring…
    • +
    • ApexCRUDViolation: The rule validates you are checking for access permissions before a SOQL/SOSL/DML operation. Sinc…
    • +
    • ApexCSRF: Deprecated The rule has been moved to another ruleset. Use instead ApexCSRF.
    • +
    • ApexDangerousMethods: Checks against calling dangerous methods. For the time being, it reports: Against ‘FinancialForc…
    • +
    • ApexInsecureEndpoint: Checks against accessing endpoints under plain http. You should always use https for security.
    • +
    • ApexOpenRedirect: Checks against redirects to user-controlled locations. This prevents attackers from redirecting u…
    • +
    • ApexSharingViolations: Detect classes declared without explicit sharing mode if DML methods are used. This forces the de…
    • +
    • ApexSOQLInjection: Detects the usage of untrusted / unescaped variables in DML queries.
    • +
    • ApexSuggestUsingNamedCred: Detects hardcoded credentials used in requests to an endpoint. You should refrain from hardcoding…
    • +
    • ApexXSSFromEscapeFalse: Reports on calls to ‘addError’ with disabled escaping. The message passed to ‘addError’ will be d…
    • +
    • ApexXSSFromURLParam: Makes sure that all values obtained from URL parameters are properly escaped / sanitized to avoid…
    • +
    + +

    Additional rulesets

    + + + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_apex_bestpractices.html b/pmd_rules_apex_bestpractices.html new file mode 100644 index 0000000000..4d0e8978a3 --- /dev/null +++ b/pmd_rules_apex_bestpractices.html @@ -0,0 +1,1952 @@ + + + + + + + + +Best Practices | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Best Practices

    +
    + + + +
    + + +
    Rules which enforce generally accepted best practices.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    ApexAssertionsShouldIncludeMessage

    + +

    Since: PMD 6.13.0

    + +

    Priority: Medium (3)

    + +

    The second parameter of System.assert/third parameter of System.assertEquals/System.assertNotEquals is a message. +Having a second/third parameter provides more information and makes it easier to debug the test failure and +improves the readability of test output.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.bestpractices.ApexAssertionsShouldIncludeMessageRule

    + +

    Example(s):

    + +
    @isTest
    +public class Foo {
    +    @isTest
    +    static void methodATest() {
    +        System.assertNotEquals('123', o.StageName); // not good
    +        System.assertEquals('123', o.StageName, 'Opportunity stageName is wrong.'); // good
    +        System.assert(o.isClosed); // not good
    +        System.assert(o.isClosed, 'Opportunity is not closed.'); // good
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesBug RiskDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/bestpractices.xml/ApexAssertionsShouldIncludeMessage" />
    +
    + +

    ApexUnitTestClassShouldHaveAsserts

    + +

    Since: PMD 5.5.1

    + +

    Priority: Medium (3)

    + +

    Apex unit tests should include at least one assertion. This makes the tests more robust, and using assert +with messages provide the developer a clearer idea of what the test does.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.bestpractices.ApexUnitTestClassShouldHaveAssertsRule

    + +

    Example(s):

    + +
    @isTest
    +public class Foo {
    +    public static testMethod void testSomething() {
    +        Account a = null;
    +        // This is better than having a NullPointerException
    +        // System.assertNotEquals(a, null, 'account not found');
    +        a.toString();
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesBug RiskDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/bestpractices.xml/ApexUnitTestClassShouldHaveAsserts" />
    +
    + +

    ApexUnitTestMethodShouldHaveIsTestAnnotation

    + +

    Since: PMD 6.13.0

    + +

    Priority: Medium (3)

    + +

    Apex test methods should have @isTest annotation. +As testMethod keyword is deprecated, Salesforce advices to use @isTest annotation for test class/methods.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.bestpractices.ApexUnitTestMethodShouldHaveIsTestAnnotationRule

    + +

    Example(s):

    + +
    @isTest
    +private class ATest {
    +    @isTest
    +    static void methodATest() {
    +    }
    +    static void methodBTest() {
    +    }
    +    @isTest static void methodCTest() {
    +        System.assert(1==2);
    +    }
    +    @isTest static void methodCTest() {
    +        System.debug('I am a debug statement');
    +    }
    +    private void fetchData() {
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesBug RiskDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/bestpractices.xml/ApexUnitTestMethodShouldHaveIsTestAnnotation" />
    +
    + +

    ApexUnitTestShouldNotUseSeeAllDataTrue

    + +

    Since: PMD 5.5.1

    + +

    Priority: Medium (3)

    + +

    Apex unit tests should not use @isTest(seeAllData=true) because it opens up the existing database data for unexpected modification by tests.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.bestpractices.ApexUnitTestShouldNotUseSeeAllDataTrueRule

    + +

    Example(s):

    + +
    @isTest(seeAllData = true)
    +public class Foo {
    +    public static testMethod void testSomething() {
    +        Account a = null;
    +        // This is better than having a NullPointerException
    +        // System.assertNotEquals(a, null, 'account not found');
    +        a.toString();
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesBug RiskDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/bestpractices.xml/ApexUnitTestShouldNotUseSeeAllDataTrue" />
    +
    + +

    AvoidGlobalModifier

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    Global classes should be avoided (especially in managed packages) as they can never be deleted or changed in signature. Always check twice if something needs to be global. +Many interfaces (e.g. Batch) required global modifiers in the past but don’t require this anymore. Don’t lock yourself in.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.bestpractices.AvoidGlobalModifierRule

    + +

    Example(s):

    + +
    global class Unchangeable {
    +    global UndeletableType unchangable(UndeletableType param) {
    +        // ...
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/bestpractices.xml/AvoidGlobalModifier" />
    +
    + +

    AvoidLogicInTrigger

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    As triggers do not allow methods like regular classes they are less flexible and suited to apply good encapsulation style. +Therefore delegate the triggers work to a regular class (often called Trigger handler class).

    + +

    See more here: https://developer.salesforce.com/page/Trigger_Frameworks_and_Apex_Trigger_Best_Practices

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.bestpractices.AvoidLogicInTriggerRule

    + +

    Example(s):

    + +
    trigger Accounts on Account (before insert, before update, before delete, after insert, after update, after delete, after undelete) {
    +    for(Account acc : Trigger.new) {
    +        if(Trigger.isInsert) {
    +            // ...
    +        }
    +
    +        // ...
    +
    +        if(Trigger.isDelete) {
    +            // ...
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier200Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/bestpractices.xml/AvoidLogicInTrigger" />
    +
    + +

    DebugsShouldUseLoggingLevel

    + +

    Since: PMD 6.18.0

    + +

    Priority: Medium (3)

    + +

    The first parameter of System.debug, when using the signature with two parameters, is a LoggingLevel enum.

    + +

    Having the Logging Level specified provides a cleaner log, and improves readability of it.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodCallExpression[lower-case(@FullMethodName)='system.debug'][count(*)=2
    +    or ($strictMode=true() and count(*)=3 and lower-case(VariableExpression/@Image)='debug')]
    +
    + +

    Example(s):

    + +
    @isTest
    +public class Foo {
    +    @isTest
    +    static void bar() {
    +        System.debug('Hey this code executed.'); // not good
    +        System.debug(LoggingLevel.WARN, 'Hey, something might be wrong.'); // good
    +        System.debug(LoggingLevel.DEBUG, 'Hey, something happened.'); // not good when on strict mode
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    strictModefalseIf true, mark statements that use the DEBUG enum of LoggingLevel.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/bestpractices.xml/DebugsShouldUseLoggingLevel" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/bestpractices.xml/DebugsShouldUseLoggingLevel">
    +    <properties>
    +        <property name="strictMode" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    UnusedLocalVariable

    + +

    Since: PMD 6.23.0

    + +

    Priority: Low (5)

    + +

    Detects when a local variable is declared and/or assigned but not used.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.bestpractices.UnusedLocalVariableRule

    + +

    Example(s):

    + +
    public Boolean bar(String z) {
    +        String x = 'some string'; // not used
    +
    +        String y = 'some other string'; // used in the next line
    +        return z.equals(y);
    +    }
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/bestpractices.xml/UnusedLocalVariable" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_apex_codestyle.html b/pmd_rules_apex_codestyle.html new file mode 100644 index 0000000000..30b49723c9 --- /dev/null +++ b/pmd_rules_apex_codestyle.html @@ -0,0 +1,2525 @@ + + + + + + + + +Code Style | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Code Style

    +
    + + + +
    + + +
    Rules which enforce a specific coding style.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    ClassNamingConventions

    + +

    Since: PMD 5.5.0

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for type declarations. This rule reports +type declarations which do not match the regex that applies to their +specific kind (e.g. enum or interface). Each regex can be configured through +properties.

    + +

    By default this rule uses the standard Apex naming convention (Pascal case).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.codestyle.ClassNamingConventionsRule

    + +

    Example(s):

    + +
    public class FooClass { } // This is in pascal case, so it's ok
    +
    +public class fooClass { } // This will be reported unless you change the regex
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier5Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    testClassPattern[A-Z][a-zA-Z0-9_]*Regex which applies to test class namesno
    abstractClassPattern[A-Z][a-zA-Z0-9_]*Regex which applies to abstract class namesno
    classPattern[A-Z][a-zA-Z0-9_]*Regex which applies to class namesno
    interfacePattern[A-Z][a-zA-Z0-9_]*Regex which applies to interface namesno
    enumPattern[A-Z][a-zA-Z0-9_]*Regex which applies to enum namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/ClassNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/codestyle.xml/ClassNamingConventions">
    +    <properties>
    +        <property name="testClassPattern" value="[A-Z][a-zA-Z0-9_]*" />
    +        <property name="abstractClassPattern" value="[A-Z][a-zA-Z0-9_]*" />
    +        <property name="classPattern" value="[A-Z][a-zA-Z0-9_]*" />
    +        <property name="interfacePattern" value="[A-Z][a-zA-Z0-9_]*" />
    +        <property name="enumPattern" value="[A-Z][a-zA-Z0-9_]*" />
    +    </properties>
    +</rule>
    +
    + +

    FieldDeclarationsShouldBeAtStart

    + +

    Since: PMD 6.23.0

    + +

    Priority: Medium (3)

    + +

    Field declarations should appear before method declarations within a class.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.codestyle.FieldDeclarationsShouldBeAtStartRule

    + +

    Example(s):

    + +
    class Foo {
    +    public Integer someField; // good
    +
    +    public void someMethod() {
    +    }
    +
    +    public Integer anotherField; // bad
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/FieldDeclarationsShouldBeAtStart" />
    +
    + +

    FieldNamingConventions

    + +

    Since: PMD 6.15.0

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for field declarations. This rule reports variable declarations +which do not match the regex that applies to their specific kind —e.g. constants (static final), +static field, final field. Each regex can be configured through properties.

    + +

    By default this rule uses the standard Apex naming convention (Camel case).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.codestyle.FieldNamingConventionsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    Integer instanceField; // This is in camel case, so it's ok
    +
    +    Integer INSTANCE_FIELD; // This will be reported unless you change the regex
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    enumConstantPattern[A-Z][A-Z0-9_]*Regex which applies to enum constant field namesno
    constantPattern[A-Z][A-Z0-9_]*Regex which applies to constant field namesno
    finalPattern[a-z][a-zA-Z0-9]*Regex which applies to final field namesno
    staticPattern[a-z][a-zA-Z0-9]*Regex which applies to static field namesno
    instancePattern[a-z][a-zA-Z0-9]*Regex which applies to instance field namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/FieldNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/codestyle.xml/FieldNamingConventions">
    +    <properties>
    +        <property name="enumConstantPattern" value="[A-Z][A-Z0-9_]*" />
    +        <property name="constantPattern" value="[A-Z][A-Z0-9_]*" />
    +        <property name="finalPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="staticPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="instancePattern" value="[a-z][a-zA-Z0-9]*" />
    +    </properties>
    +</rule>
    +
    + +

    ForLoopsMustUseBraces

    + +

    Since: PMD 5.6.0

    + +

    Priority: Medium (3)

    + +

    Avoid using ‘for’ statements without using surrounding braces. If the code formatting or +indentation is lost then it becomes difficult to separate the code being controlled +from the rest.

    + +

    This rule is defined by the following XPath expression:

    +
    //ForLoopStatement/BlockStatement[@CurlyBrace= false()]
    +|
    +//ForEachStatement/BlockStatement[@CurlyBrace= false()]
    +
    + +

    Example(s):

    + +
    for (int i = 0; i < 42; i++) // not recommended
    +    foo();
    +
    +for (int i = 0; i < 42; i++) { // preferred approach
    +    foo();
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/ForLoopsMustUseBraces" />
    +
    + +

    FormalParameterNamingConventions

    + +

    Since: PMD 6.15.0

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for formal parameters of methods. +This rule reports formal parameters which do not match the regex that applies to their +specific kind (e.g. method parameter, or final method parameter). Each regex can be +configured through properties.

    + +

    By default this rule uses the standard Apex naming convention (Camel case).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.codestyle.FormalParameterNamingConventionsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public bar(Integer methodParameter) { } // This is in camel case, so it's ok
    +
    +    public baz(Integer METHOD_PARAMETER) { } // This will be reported unless you change the regex
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    finalMethodParameterPattern[a-z][a-zA-Z0-9]*Regex which applies to final method parameter namesno
    methodParameterPattern[a-z][a-zA-Z0-9]*Regex which applies to method parameter namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/FormalParameterNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/codestyle.xml/FormalParameterNamingConventions">
    +    <properties>
    +        <property name="finalMethodParameterPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="methodParameterPattern" value="[a-z][a-zA-Z0-9]*" />
    +    </properties>
    +</rule>
    +
    + +

    IfElseStmtsMustUseBraces

    + +

    Since: PMD 5.6.0

    + +

    Priority: Medium (3)

    + +

    Avoid using if..else statements without using surrounding braces. If the code formatting +or indentation is lost then it becomes difficult to separate the code being controlled +from the rest.

    + +

    This rule is defined by the following XPath expression:

    +
    //IfBlockStatement/BlockStatement[@CurlyBrace= false()][count(child::*) > 0]
    +|
    +//IfElseBlockStatement/BlockStatement[@CurlyBrace= false()][count(child::*) > 0]
    +
    + +

    Example(s):

    + +
    // this is OK
    +if (foo) x++;
    +
    +// but this is not
    +if (foo)
    +    x = x+1;
    +else
    +    x = x-1;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/IfElseStmtsMustUseBraces" />
    +
    + +

    IfStmtsMustUseBraces

    + +

    Since: PMD 5.6.0

    + +

    Priority: Medium (3)

    + +

    Avoid using if statements without using braces to surround the code block. If the code +formatting or indentation is lost then it becomes difficult to separate the code being +controlled from the rest.

    + +

    This rule is defined by the following XPath expression:

    +
    //IfBlockStatement/BlockStatement[@CurlyBrace= false()]
    +
    + +

    Example(s):

    + +
    if (foo)    // not recommended
    +    x++;
    +
    +if (foo) {  // preferred approach
    +    x++;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/IfStmtsMustUseBraces" />
    +
    + +

    LocalVariableNamingConventions

    + +

    Since: PMD 6.15.0

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for local variable declarations. +This rule reports variable declarations which do not match the regex that applies to their +specific kind (e.g. local variable, or final local variable). Each regex can be configured through +properties.

    + +

    By default this rule uses the standard Apex naming convention (Camel case).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.codestyle.LocalVariableNamingConventionsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public Foo() {
    +        Integer localVariable; // This is in camel case, so it's ok
    +
    +        Integer LOCAL_VARIABLE; // This will be reported unless you change the regex
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    finalLocalPattern[a-z][a-zA-Z0-9]*Regex which applies to final local variable namesno
    localPattern[a-z][a-zA-Z0-9]*Regex which applies to local variable namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/LocalVariableNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/codestyle.xml/LocalVariableNamingConventions">
    +    <properties>
    +        <property name="finalLocalPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="localPattern" value="[a-z][a-zA-Z0-9]*" />
    +    </properties>
    +</rule>
    +
    + +

    MethodNamingConventions

    + +

    Since: PMD 5.5.0

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for method declarations. This rule reports +method declarations which do not match the regex that applies to their +specific kind (e.g. static method, or test method). Each regex can be +configured through properties.

    + +

    By default this rule uses the standard Apex naming convention (Camel case).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.codestyle.MethodNamingConventionsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void instanceMethod() { } // This is in camel case, so it's ok
    +
    +    public void INSTANCE_METHOD() { } // This will be reported unless you change the regex
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    skipTestMethodUnderscoresfalseDeprecated Skip underscores in test methodsno
    testPattern[a-z][a-zA-Z0-9]*Regex which applies to test method namesno
    staticPattern[a-z][a-zA-Z0-9]*Regex which applies to static method namesno
    instancePattern[a-z][a-zA-Z0-9]*Regex which applies to instance method namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/MethodNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/codestyle.xml/MethodNamingConventions">
    +    <properties>
    +        <property name="testPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="staticPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="instancePattern" value="[a-z][a-zA-Z0-9]*" />
    +    </properties>
    +</rule>
    +
    + +

    OneDeclarationPerLine

    + +

    Since: PMD 6.7.0

    + +

    Priority: High (1)

    + +

    Apex allows the use of several variables declaration of the same type on one line. However, it +can lead to quite messy code. This rule looks for several declarations on the same line.

    + +

    This rule is defined by the following XPath expression:

    +
    //VariableDeclarationStatements
    +  [count(VariableDeclaration) > 1]
    +  [$strictMode or count(distinct-values(VariableDeclaration/@BeginLine)) != count(VariableDeclaration)]
    +|
    +//FieldDeclarationStatements
    +  [count(FieldDeclaration) > 1]
    +  [$strictMode or count(distinct-values(FieldDeclaration/VariableExpression/@BeginLine)) != count(FieldDeclaration/VariableExpression)]
    +
    + +

    Example(s):

    + +
    Integer a, b;   // not recommended
    +
    +Integer a,
    +        b;      // ok by default, can be flagged setting the strictMode property
    +
    +Integer a;      // preferred approach
    +Integer b;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    strictModefalseIf true, mark combined declaration even if the declarations are on separate lines.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/OneDeclarationPerLine" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/codestyle.xml/OneDeclarationPerLine">
    +    <properties>
    +        <property name="strictMode" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    PropertyNamingConventions

    + +

    Since: PMD 6.15.0

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for property declarations. This rule reports +property declarations which do not match the regex that applies to their +specific kind (e.g. static property, or instance property). Each regex can be +configured through properties.

    + +

    By default this rule uses the standard Apex naming convention (Camel case).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.codestyle.PropertyNamingConventionsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public Integer instanceProperty { get; set; } // This is in camel case, so it's ok
    +
    +    public Integer INSTANCE_PROPERTY { get; set; } // This will be reported unless you change the regex
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    staticPattern[a-z][a-zA-Z0-9]*Regex which applies to static property namesno
    instancePattern[a-z][a-zA-Z0-9]*Regex which applies to instance property namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/PropertyNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/codestyle.xml/PropertyNamingConventions">
    +    <properties>
    +        <property name="staticPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="instancePattern" value="[a-z][a-zA-Z0-9]*" />
    +    </properties>
    +</rule>
    +
    + +

    VariableNamingConventions

    + +

    Deprecated

    + +

    Since: PMD 5.5.0

    + +

    Priority: High (1)

    + +

    A variable naming conventions rule - customize this to your liking. Currently, it +checks for final variables that should be fully capitalized and non-final variables +that should not include underscores.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the more general rules FieldNamingConventions, +FormalParameterNamingConventions, +LocalVariableNamingConventions, and +PropertyNamingConventions.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.codestyle.VariableNamingConventionsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public static final Integer MY_NUM = 0;
    +    public String myTest = '';
    +    DataModule dmTest = new DataModule();
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier5Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    checkMemberstrueCheck member variablesno
    checkLocalstrueCheck local variablesno
    checkParameterstrueCheck constructor and method parameter variablesno
    staticPrefix Static variable prefixesyes. Delimiter is ‘,’.
    staticSuffix Static variable suffixesyes. Delimiter is ‘,’.
    memberPrefix Member variable prefixesyes. Delimiter is ‘,’.
    memberSuffix Member variable suffixesyes. Delimiter is ‘,’.
    localPrefix Local variable prefixesyes. Delimiter is ‘,’.
    localSuffix Local variable suffixesyes. Delimiter is ‘,’.
    parameterPrefix Method parameter variable prefixesyes. Delimiter is ‘,’.
    parameterSuffix Method parameter variable suffixesyes. Delimiter is ‘,’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/VariableNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/codestyle.xml/VariableNamingConventions">
    +    <properties>
    +        <property name="checkMembers" value="true" />
    +        <property name="checkLocals" value="true" />
    +        <property name="checkParameters" value="true" />
    +        <property name="staticPrefix" value="" />
    +        <property name="staticSuffix" value="" />
    +        <property name="memberPrefix" value="" />
    +        <property name="memberSuffix" value="" />
    +        <property name="localPrefix" value="" />
    +        <property name="localSuffix" value="" />
    +        <property name="parameterPrefix" value="" />
    +        <property name="parameterSuffix" value="" />
    +    </properties>
    +</rule>
    +
    + +

    WhileLoopsMustUseBraces

    + +

    Since: PMD 5.6.0

    + +

    Priority: Medium (3)

    + +

    Avoid using ‘while’ statements without using braces to surround the code block. If the code +formatting or indentation is lost then it becomes difficult to separate the code being +controlled from the rest.

    + +

    This rule is defined by the following XPath expression:

    +
    //WhileLoopStatement/BlockStatement[@CurlyBrace= false()]
    +
    + +

    Example(s):

    + +
    while (true)    // not recommended
    +    x++;
    +
    +while (true) {  // preferred approach
    +    x++;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/codestyle.xml/WhileLoopsMustUseBraces" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_apex_design.html b/pmd_rules_apex_design.html new file mode 100644 index 0000000000..b30e429dd7 --- /dev/null +++ b/pmd_rules_apex_design.html @@ -0,0 +1,2482 @@ + + + + + + + + +Design | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Design

    +
    + + + +
    + + +
    Rules that help you discover design issues.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AvoidDeeplyNestedIfStmts

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    Avoid creating deeply nested if-then statements since they are harder to read and error-prone to maintain.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.AvoidDeeplyNestedIfStmtsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar(Integer x, Integer y, Integer z) {
    +        if (x>y) {
    +            if (y>z) {
    +                if (z==x) {
    +                    // !! too deep
    +                }
    +            }
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesComplexityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier200Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    problemDepth3The if statement depth reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/AvoidDeeplyNestedIfStmts" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/AvoidDeeplyNestedIfStmts">
    +    <properties>
    +        <property name="problemDepth" value="3" />
    +    </properties>
    +</rule>
    +
    + +

    CognitiveComplexity

    + +

    Since: PMD 6.22.0

    + +

    Priority: Medium (3)

    + +

    Methods that are highly complex are difficult to read and more costly to maintain. If you include too much decisional +logic within a single method, you make its behavior hard to understand and more difficult to modify.

    + +

    Cognitive complexity is a measure of how difficult it is for humans to read and understand a method. Code that contains +a break in the control flow is more complex, whereas the use of language shorthands doesn’t increase the level of +complexity. Nested control flows can make a method more difficult to understand, with each additional nesting of the +control flow leading to an increase in cognitive complexity.

    + +

    Information about Cognitive complexity can be found in the original paper here: +https://www.sonarsource.com/docs/CognitiveComplexity.pdf

    + +

    By default, this rule reports methods with a complexity of 15 or more. Reported methods should be broken down into less +complex components.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.CognitiveComplexityRule

    + +

    Example(s):

    + +
    public class Foo {
    +    // Has a cognitive complexity of 0
    +    public void createAccount() {
    +        Account account = new Account(Name = 'PMD');
    +        insert account;
    +    }
    +
    +    // Has a cognitive complexity of 1
    +    public Boolean setPhoneNumberIfNotExisting(Account a, String phone) {
    +        if (a.Phone == null) {                          // +1
    +            a.Phone = phone;
    +            update a;
    +            return true;
    +        }
    +
    +        return false;
    +    }
    +
    +    // Has a cognitive complexity of 5
    +    public void updateContacts(List<Contact> contacts) {
    +        List<Contact> contactsToUpdate = new List<Contact>();
    +
    +        for (Contact contact : contacts) {                           // +1
    +            if (contact.Department == 'Finance') {                   // +2
    +                contact.Title = 'Finance Specialist';
    +                contactsToUpdate.add(contact);
    +            } else if (contact.Department == 'Sales') {              // +2
    +                contact.Title = 'Sales Specialist';
    +                contactsToUpdate.add(contact);
    +            }
    +        }
    +
    +        update contactsToUpdate;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    classReportLevel50Total class cognitive complexity reporting thresholdno
    methodReportLevel15Cognitive complexity reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/CognitiveComplexity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/CognitiveComplexity">
    +    <properties>
    +        <property name="classReportLevel" value="50" />
    +        <property name="methodReportLevel" value="15" />
    +    </properties>
    +</rule>
    +
    + +

    CyclomaticComplexity

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    The complexity of methods directly affects maintenance costs and readability. Concentrating too much decisional logic +in a single method makes its behaviour hard to read and change.

    + +

    Cyclomatic complexity assesses the complexity of a method by counting the number of decision points in a method, +plus one for the method entry. Decision points are places where the control flow jumps to another place in the +program. As such, they include all control flow statements, such as ‘if’, ‘while’, ‘for’, and ‘case’.

    + +

    Generally, numbers ranging from 1-4 denote low complexity, 5-7 denote moderate complexity, 8-10 denote +high complexity, and 11+ is very high complexity. By default, this rule reports methods with a complexity >= 10. +Additionally, classes with many methods of moderate complexity get reported as well once the total of their +methods’ complexities reaches 40, even if none of the methods was directly reported.

    + +

    Reported methods should be broken down into several smaller methods. Reported classes should probably be broken down +into subcomponents.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.CyclomaticComplexityRule

    + +

    Example(s):

    + +
    public class Complicated {
    +  public void example() { // This method has a cyclomatic complexity of 12
    +    int x = 0, y = 1, z = 2, t = 2;
    +    boolean a = false, b = true, c = false, d = true;
    +    if (a && b || b && d) {
    +      if (y == z) {
    +        x = 2;
    +      } else if (y == t && !d) {
    +        x = 2;
    +      } else {
    +        x = 2;
    +      }
    +    } else if (c && d) {
    +      while (z < y) {
    +        x = 2;
    +      }
    +    } else {
    +      for (int n = 0; n < t; n++) {
    +        x = 2;
    +      }
    +    }
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    classReportLevel40Total class complexity reporting thresholdno
    methodReportLevel10Cyclomatic complexity reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/CyclomaticComplexity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/CyclomaticComplexity">
    +    <properties>
    +        <property name="classReportLevel" value="40" />
    +        <property name="methodReportLevel" value="10" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessiveClassLength

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    Excessive class file lengths are usually indications that the class may be burdened with excessive +responsibilities that could be provided by external classes or functions. In breaking these methods +apart the code becomes more managable and ripe for reuse.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.ExcessiveClassLengthRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar1() {
    +        // 1000 lines of code
    +    }
    +    public void bar2() {
    +        // 1000 lines of code
    +    }
    +    public void bar3() {
    +        // 1000 lines of code
    +    }
    +    public void barN() {
    +        // 1000 lines of code
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum1000.0Minimum reporting thresholdno
    cc_categoriesComplexityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier150Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/ExcessiveClassLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/ExcessiveClassLength">
    +    <properties>
    +        <property name="minimum" value="1000.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessiveParameterList

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    Methods with numerous parameters are a challenge to maintain, especially if most of them share the +same datatype. These situations usually denote the need for new objects to wrap the numerous parameters.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.ExcessiveParameterListRule

    + +

    Example(s):

    + +
    // too many arguments liable to be mixed up
    +public void addPerson(Integer birthYear, Integer birthMonth, Integer birthDate, Integer height, Integer weight, Integer ssn) {
    +    // ...
    +}
    +// preferred approach
    +public void addPerson(Date birthdate, BodyMeasurements measurements, int ssn) {
    +    // ...
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum4.0Minimum reporting thresholdno
    cc_categoriesComplexityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier50Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/ExcessiveParameterList" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/ExcessiveParameterList">
    +    <properties>
    +        <property name="minimum" value="4.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessivePublicCount

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    Classes with large numbers of public methods and attributes require disproportionate testing efforts +since combinational side effects grow rapidly and increase risk. Refactoring these classes into +smaller ones not only increases testability and reliability but also allows new variations to be +developed easily.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.ExcessivePublicCountRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public String value;
    +    public Bar something;
    +    public Variable var;
    +    // [... more more public attributes ...]
    +
    +    public void doWork() {}
    +    public void doMoreWork() {}
    +    public void doWorkAgain() {}
    +    // [... more more public methods ...]
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum20.0Minimum reporting thresholdno
    cc_categoriesComplexityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier150Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/ExcessivePublicCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/ExcessivePublicCount">
    +    <properties>
    +        <property name="minimum" value="20.0" />
    +    </properties>
    +</rule>
    +
    + +

    NcssConstructorCount

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of lines +of code for a given constructor. NCSS ignores comments, and counts actual statements. Using this algorithm, +lines of code that are split are counted as one.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.NcssConstructorCountRule

    + +

    Example(s):

    + +
    public class Foo extends Bar {
    +    //this constructor only has 1 NCSS lines
    +    public Foo() {
    +        super();
    +
    +
    +
    +
    +        super.foo();
    +}
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum20.0Minimum reporting thresholdno
    cc_categoriesComplexityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier50Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/NcssConstructorCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/NcssConstructorCount">
    +    <properties>
    +        <property name="minimum" value="20.0" />
    +    </properties>
    +</rule>
    +
    + +

    NcssMethodCount

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of lines +of code for a given method. NCSS ignores comments, and counts actual statements. Using this algorithm, +lines of code that are split are counted as one.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.NcssMethodCountRule

    + +

    Example(s):

    + +
    public class Foo extends Bar {
    +    //this method only has 1 NCSS lines
    +    public Integer method() {
    +        super.method();
    +
    +
    +
    +        return 1;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum40.0Minimum reporting thresholdno
    cc_categoriesComplexityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier50Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/NcssMethodCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/NcssMethodCount">
    +    <properties>
    +        <property name="minimum" value="40.0" />
    +    </properties>
    +</rule>
    +
    + +

    NcssTypeCount

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of lines +of code for a given type. NCSS ignores comments, and counts actual statements. Using this algorithm, +lines of code that are split are counted as one.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.NcssTypeCountRule

    + +

    Example(s):

    + +
    //this class only has 6 NCSS lines
    +public class Foo extends Bar {
    +    public Foo() {
    +        super();
    +
    +
    +
    +
    +
    +        super.foo();
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum500.0Minimum reporting thresholdno
    cc_categoriesComplexityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier250Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/NcssTypeCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/NcssTypeCount">
    +    <properties>
    +        <property name="minimum" value="500.0" />
    +    </properties>
    +</rule>
    +
    + +

    StdCyclomaticComplexity

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    Complexity directly affects maintenance costs is determined by the number of decision points in a method +plus one for the method entry. The decision points include ‘if’, ‘while’, ‘for’, and ‘case labels’ calls. +Generally, numbers ranging from 1-4 denote low complexity, 5-7 denote moderate complexity, 8-10 denote +high complexity, and 11+ is very high complexity.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.StdCyclomaticComplexityRule

    + +

    Example(s):

    + +
    // This has a Cyclomatic Complexity = 12
    +public class Foo {
    +1   public void example() {
    +2   if (a == b || (c == d && e == f)) {
    +3       if (a1 == b1) {
    +            fiddle();
    +4       } else if a2 == b2) {
    +            fiddle();
    +        }  else {
    +            fiddle();
    +        }
    +5   } else if (c == d) {
    +6       while (c == d) {
    +            fiddle();
    +        }
    +7   } else if (e == f) {
    +8       for (int n = 0; n < h; n++) {
    +            fiddle();
    +        }
    +    } else {
    +        switch (z) {
    +9           case 1:
    +                fiddle();
    +                break;
    +10          case 2:
    +                fiddle();
    +                break;
    +11          case 3:
    +                fiddle();
    +                break;
    +12          default:
    +                fiddle();
    +                break;
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesComplexityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier250Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    reportLevel10Cyclomatic Complexity reporting thresholdno
    showClassesComplexitytrueAdd class average violations to the reportno
    showMethodsComplexitytrueAdd method average violations to the reportno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/StdCyclomaticComplexity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/StdCyclomaticComplexity">
    +    <properties>
    +        <property name="reportLevel" value="10" />
    +        <property name="showClassesComplexity" value="true" />
    +        <property name="showMethodsComplexity" value="true" />
    +    </properties>
    +</rule>
    +
    + +

    TooManyFields

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    Classes that have too many fields can become unwieldy and could be redesigned to have fewer fields, +possibly through grouping related fields in new objects. For example, a class with individual +city/state/zip fields could park them within a single Address field.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.design.TooManyFieldsRule

    + +

    Example(s):

    + +
    public class Person {
    +    // too many separate fields
    +    Integer birthYear;
    +    Integer birthMonth;
    +    Integer birthDate;
    +    Double height;
    +    Double weight;
    +}
    +
    +public class Person {
    +    // this is more manageable
    +    Date birthDate;
    +    BodyMeasurements measurements;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesComplexityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier200Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    maxfields15Max allowable fieldsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/design.xml/TooManyFields" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/apex/design.xml/TooManyFields">
    +    <properties>
    +        <property name="maxfields" value="15" />
    +    </properties>
    +</rule>
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_apex_documentation.html b/pmd_rules_apex_documentation.html new file mode 100644 index 0000000000..16f9278d42 --- /dev/null +++ b/pmd_rules_apex_documentation.html @@ -0,0 +1,1513 @@ + + + + + + + + +Documentation | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Documentation

    +
    + + + +
    + + +
    Rules that are related to code documentation.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    ApexDoc

    + +

    Since: PMD 6.8.0

    + +

    Priority: Medium (3)

    + +

    This rule validates that:

    + +
      +
    • ApexDoc comments are present for classes, methods, and properties that are public or global, excluding +overrides and test classes (as well as the contents of test classes).
    • +
    • ApexDoc comments should contain @description.
    • +
    • ApexDoc comments on non-void, non-constructor methods should contain @return.
    • +
    • ApexDoc comments on void or constructor methods should not contain @return.
    • +
    • ApexDoc comments on methods with parameters should contain @param for each parameter, in the same +order as the method signature.
    • +
    + +

    Method overrides and tests are both exempted from having ApexDoc.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.documentation.ApexDocRule

    + +

    Example(s):

    + +
    /**
    + * @description Hello World
    + */
    +public class HelloWorld {
    +    /**
    +     * @description Bar
    +     * @return Bar
    +     */
    +    public Object bar() { return null; }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/documentation.xml/ApexDoc" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_apex_errorprone.html b/pmd_rules_apex_errorprone.html new file mode 100644 index 0000000000..c560e634f4 --- /dev/null +++ b/pmd_rules_apex_errorprone.html @@ -0,0 +1,2166 @@ + + + + + + + + +Error Prone | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Error Prone

    +
    + + + +
    + + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    ApexCSRF

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Having DML operations in Apex class constructor or initializers can have unexpected side effects: +By just accessing a page, the DML statements would be executed and the database would be modified. +Just querying the database is permitted.

    + +

    In addition to constructors and initializers, any method called init is checked as well.

    + +

    Salesforce Apex already protects against this scenario and raises a runtime exception.

    + +

    Note: This rule has been moved from category "Security" to "Error Prone" with PMD 6.21.0, since +using DML in constructors is not a security problem, but crashes the application.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.errorprone.ApexCSRFRule

    + +

    Example(s):

    + +
    public class Foo {
    +    // initializer
    +    {
    +        insert data;
    +    }
    +
    +    // static initializer
    +    static {
    +        insert data;
    +    }
    +
    +    // constructor
    +    public Foo() {
    +        insert data;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/ApexCSRF" />
    +
    + +

    AvoidDirectAccessTriggerMap

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Avoid directly accessing Trigger.old and Trigger.new as it can lead to a bug. Triggers should be bulkified and iterate through the map to handle the actions for each item separately.

    + +

    This rule is defined by the following XPath expression:

    +
    //ArrayLoadExpression[TriggerVariableExpression and LiteralExpression]
    +
    + +

    Example(s):

    + +
    trigger AccountTrigger on Account (before insert, before update) {
    +   Account a = Trigger.new[0]; //Bad: Accessing the trigger array directly is not recommended.
    +
    +   for ( Account a : Trigger.new ) {
    +        //Good: Iterate through the trigger.new array instead.
    +   }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/AvoidDirectAccessTriggerMap" />
    +
    + +

    AvoidHardcodingId

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    When deploying Apex code between sandbox and production environments, or installing Force.com AppExchange packages, +it is essential to avoid hardcoding IDs in the Apex code. By doing so, if the record IDs change between environments, +the logic can dynamically identify the proper data to operate against and not fail.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.errorprone.AvoidHardcodingIdRule

    + +

    Example(s):

    + +
    public without sharing class Foo {
    +    void foo() {
    +        //Error - hardcoded the record type id
    +        if (a.RecordTypeId == '012500000009WAr') {
    +            //do some logic here.....
    +        } else if (a.RecordTypeId == '0123000000095Km') {
    +            //do some logic here for a different record type...
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/AvoidHardcodingId" />
    +
    + +

    AvoidNonExistentAnnotations

    + +

    Since: PMD 6.5.0

    + +

    Priority: Medium (3)

    + +

    Apex supported non existent annotations for legacy reasons. +In the future, use of such non-existent annotations could result in broken apex code that will not compile. +This will prevent users of garbage annotations from being able to use legitimate annotations added to Apex in the future. +A full list of supported annotations can be found at https://developer.salesforce.com/docs/atlas.en-us.apexcode.meta/apexcode/apex_classes_annotation.htm

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.errorprone.AvoidNonExistentAnnotationsRule

    + +

    Example(s):

    + +
    @NonExistentAnnotation public class ClassWithNonexistentAnnotation {
    +	@NonExistentAnnotation public void methodWithNonExistentAnnotation() {
    +		// ...
    +	}
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/AvoidNonExistentAnnotations" />
    +
    + +

    EmptyCatchBlock

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Empty Catch Block finds instances where an exception is caught, but nothing is done. +In most circumstances, this swallows an exception which should either be acted on +or reported.

    + +

    This rule is defined by the following XPath expression:

    +
    //CatchBlockStatement[./BlockStatement[count(*) = 0]]
    +
    + +

    Example(s):

    + +
    public void doSomething() {
    +    ...
    +    try {
    +        insert accounts;
    +    } catch (DmlException dmle) {
    +        // not good
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/EmptyCatchBlock" />
    +
    + +

    EmptyIfStmt

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Empty If Statement finds instances where a condition is checked but nothing is done about it.

    + +

    This rule is defined by the following XPath expression:

    +
    //IfBlockStatement
    + [BlockStatement[count(*) = 0]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar(Integer x) {
    +        if (x == 0) {
    +            // empty!
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/EmptyIfStmt" />
    +
    + +

    EmptyStatementBlock

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Empty block statements serve no purpose and should be removed.

    + +

    This rule is defined by the following XPath expression:

    +
    //Method/ModifierNode[@Abstract!= true() and ../BlockStatement[count(*) = 0]]
    +| //Method/BlockStatement//BlockStatement[count(*) = 0 and @Location != parent::*/@Location]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +
    +   private Integer _bar;
    +
    +   public void setBar(Integer bar) {
    +        // empty
    +   }
    +
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/EmptyStatementBlock" />
    +
    + +

    EmptyTryOrFinallyBlock

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Avoid empty try or finally blocks - what’s the point?

    + +

    This rule is defined by the following XPath expression:

    +
    //TryCatchFinallyBlockStatement[./BlockStatement[count(*) = 0]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar() {
    +        try {
    +          // empty !
    +        } catch (Exception e) {
    +            e.printStackTrace();
    +        }
    +    }
    +}
    +
    +public class Foo {
    +    public void bar() {
    +        try {
    +            Integer x=2;
    +        } finally {
    +            // empty!
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/EmptyTryOrFinallyBlock" />
    +
    + +

    EmptyWhileStmt

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Empty While Statement finds all instances where a while statement does nothing. +If it is a timing loop, then you should use Thread.sleep() for it; if it is +a while loop that does a lot in the exit expression, rewrite it to make it clearer.

    + +

    This rule is defined by the following XPath expression:

    +
    //WhileLoopStatement[./BlockStatement[count(*) = 0]]
    +
    + +

    Example(s):

    + +
    public void bar(Integer a, Integer b) {
    +  while (a == b) {
    +    // empty!
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/EmptyWhileStmt" />
    +
    + +

    MethodWithSameNameAsEnclosingClass

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    Non-constructor methods should not have the same name as the enclosing class.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.errorprone.MethodWithSameNameAsEnclosingClassRule

    + +

    Example(s):

    + +
    public class MyClass {
    +    // this is OK because it is a constructor
    +    public MyClass() {}
    +    // this is bad because it is a method
    +    public void MyClass() {}
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier50Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/MethodWithSameNameAsEnclosingClass" />
    +
    + +

    TestMethodsMustBeInTestClasses

    + +

    Since: PMD 6.22.0

    + +

    Priority: Medium (3)

    + +

    Test methods marked as a testMethod or annotated with @IsTest, +but not residing in a test class should be moved to a proper +class or have the @IsTest annotation added to the class.

    + +

    Support for tests inside functional classes was removed in Spring-13 (API Version 27.0), +making classes that violate this rule fail compile-time. This rule is mostly usable when +dealing with legacy code.

    + +

    This rule is defined by the following XPath expression:

    +
    //UserClass[
    +      not(./ModifierNode/Annotation[lower-case(@Image) = 'istest']) and
    +      (
    +        (./Method/ModifierNode/Annotation[lower-case(@Image) = 'istest']) or
    +        (./Method/ModifierNode[@Test = true()])
    +      )
    +    ]
    +
    + +

    Example(s):

    + +
    // Violating
    +private class TestClass {
    +  @IsTest static void myTest() {
    +    // Code here
    +  }
    +}
    +
    +private class TestClass {
    +  static testMethod void myTest() {
    +    // Code here
    +  }
    +}
    +
    +// Compliant
    +@IsTest
    +private class TestClass {
    +  @IsTest static void myTest() {
    +    // Code here
    +  }
    +}
    +
    +@IsTest
    +private class TestClass {
    +  static testMethod void myTest() {
    +    // Code here
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesStyleDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier1Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/errorprone.xml/TestMethodsMustBeInTestClasses" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_apex_performance.html b/pmd_rules_apex_performance.html new file mode 100644 index 0000000000..3a9c72f2b2 --- /dev/null +++ b/pmd_rules_apex_performance.html @@ -0,0 +1,1709 @@ + + + + + + + + +Performance | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Performance

    +
    + + + +
    + + +
    Rules that flag suboptimal code.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AvoidDmlStatementsInLoops

    + +

    Deprecated

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    Avoid DML statements inside loops to avoid hitting the DML governor limit. Instead, try to batch up the data into a list and invoke your DML once on that list of data outside the loop.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the more general rule OperationWithLimitsInLoop.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.performance.AvoidDmlStatementsInLoopsRule

    + +

    Example(s):

    + +
    public class Something {
    +    public void foo() {
    +        for (Integer i = 0; i < 151; i++) {
    +            Account account;
    +            // ...
    +            insert account;
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesPerformanceDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier150Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/performance.xml/AvoidDmlStatementsInLoops" />
    +
    + +

    AvoidSoqlInLoops

    + +

    Deprecated

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    New objects created within loops should be checked to see if they can created outside them and reused.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the more general rule OperationWithLimitsInLoop.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.performance.AvoidSoqlInLoopsRule

    + +

    Example(s):

    + +
    public class Something {
    +    public static void main( String as[] ) {
    +        for (Integer i = 0; i < 10; i++) {
    +            List<Account> accounts = [SELECT Id FROM Account];
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesPerformanceDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier150Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/performance.xml/AvoidSoqlInLoops" />
    +
    + +

    AvoidSoslInLoops

    + +

    Deprecated

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Sosl calls within loops can cause governor limit exceptions.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the more general rule OperationWithLimitsInLoop.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.performance.AvoidSoslInLoopsRule

    + +

    Example(s):

    + +
    public class Something {
    +    public static void main( String as[] ) {
    +        for (Integer i = 0; i < 10; i++) {
    +            List<List<SObject>> searchList = [FIND 'map*' IN ALL FIELDS RETURNING Account (Id, Name), Contact, Opportunity, Lead];
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesPerformanceDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier150Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/performance.xml/AvoidSoslInLoops" />
    +
    + +

    OperationWithLimitsInLoop

    + +

    Since: PMD 6.29.0

    + +

    Priority: Medium (3)

    + +

    Database class methods, DML operations, SOQL queries, or SOSL queries within loops can cause governor limit exceptions. Instead, try to batch up the data into a list and invoke the operation once on that list of data outside the loop.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.performance.OperationWithLimitsInLoopRule

    + +

    Example(s):

    + +
    public class Something {
    +    public void databaseMethodInsideOfLoop(List<Account> accounts) {
    +        for (Account a : accounts) {
    +            Database.insert(a);
    +        }
    +    }
    +
    +    public void dmlInsideOfLoop() {
    +        for (Integer i = 0; i < 151; i++) {
    +            Account account;
    +            // ...
    +            insert account;
    +        }
    +    }
    +
    +    public void soqlInsideOfLoop() {
    +        for (Integer i = 0; i < 10; i++) {
    +            List<Account> accounts = [SELECT Id FROM Account];
    +        }
    +    }
    +
    +    public void soslInsideOfLoop() {
    +        for (Integer i = 0; i < 10; i++) {
    +            List<List<SObject>> searchList = [FIND 'map*' IN ALL FIELDS RETURNING Account (Id, Name), Contact, Opportunity, Lead];
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesPerformanceDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier150Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/performance.xml/OperationWithLimitsInLoop" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_apex_security.html b/pmd_rules_apex_security.html new file mode 100644 index 0000000000..f9b043e89f --- /dev/null +++ b/pmd_rules_apex_security.html @@ -0,0 +1,2123 @@ + + + + + + + + +Security | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Security

    +
    + + + +
    + + +
    Rules that flag potential security flaws.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    ApexBadCrypto

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    The rule makes sure you are using randomly generated IVs and keys for Crypto calls. +Hard-wiring these values greatly compromises the security of encrypted data.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexBadCryptoRule

    + +

    Example(s):

    + +
    public without sharing class Foo {
    +    Blob hardCodedIV = Blob.valueOf('Hardcoded IV 123');
    +    Blob hardCodedKey = Blob.valueOf('0000000000000000');
    +    Blob data = Blob.valueOf('Data to be encrypted');
    +    Blob encrypted = Crypto.encrypt('AES128', hardCodedKey, hardCodedIV, data);
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexBadCrypto" />
    +
    + +

    ApexCRUDViolation

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    The rule validates you are checking for access permissions before a SOQL/SOSL/DML operation. +Since Apex runs in system mode not having proper permissions checks results in escalation of +privilege and may produce runtime errors. This check forces you to handle such scenarios.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexCRUDViolationRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public Contact foo(String status, String ID) {
    +        Contact c = [SELECT Status__c FROM Contact WHERE Id=:ID];
    +
    +        // Make sure we can update the database before even trying
    +        if (!Schema.sObjectType.Contact.fields.Name.isUpdateable()) {
    +            return null;
    +        }
    +
    +        c.Status__c = status;
    +        update c;
    +        return c;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexCRUDViolation" />
    +
    + +

    ApexCSRF

    + +

    Deprecated

    + +

    The rule has been moved to another ruleset. Use instead: ApexCSRF

    + +

    Deprecated

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Having DML operations in Apex class constructor or initializers can have unexpected side effects: +By just accessing a page, the DML statements would be executed and the database would be modified. +Just querying the database is permitted.

    + +

    In addition to constructors and initializers, any method called init is checked as well.

    + +

    Salesforce Apex already protects against this scenario and raises a runtime exception.

    + +

    Note: This rule has been moved from category "Security" to "Error Prone" with PMD 6.21.0, since +using DML in constructors is not a security problem, but crashes the application.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.errorprone.ApexCSRFRule

    + +

    Example(s):

    + +
    public class Foo {
    +    // initializer
    +    {
    +        insert data;
    +    }
    +
    +    // static initializer
    +    static {
    +        insert data;
    +    }
    +
    +    // constructor
    +    public Foo() {
    +        insert data;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexCSRF" />
    +
    + +

    ApexDangerousMethods

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Checks against calling dangerous methods.

    + +

    For the time being, it reports:

    + +
      +
    • Against FinancialForce’s Configuration.disableTriggerCRUDSecurity(). Disabling CRUD security +opens the door to several attacks and requires manual validation, which is unreliable.
    • +
    • Calling System.debug passing sensitive data as parameter, which could lead to exposure +of private data.
    • +
    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexDangerousMethodsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public Foo() {
    +        Configuration.disableTriggerCRUDSecurity();
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexDangerousMethods" />
    +
    + +

    ApexInsecureEndpoint

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Checks against accessing endpoints under plain http. You should always use +https for security.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexInsecureEndpointRule

    + +

    Example(s):

    + +
    public without sharing class Foo {
    +    void foo() {
    +        HttpRequest req = new HttpRequest();
    +        req.setEndpoint('http://localhost:com');
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexInsecureEndpoint" />
    +
    + +

    ApexOpenRedirect

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Checks against redirects to user-controlled locations. This prevents attackers from +redirecting users to phishing sites.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexOpenRedirectRule

    + +

    Example(s):

    + +
    public without sharing class Foo {
    +    String unsafeLocation = ApexPage.getCurrentPage().getParameters.get('url_param');
    +    PageReference page() {
    +       return new PageReference(unsafeLocation);
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexOpenRedirect" />
    +
    + +

    ApexSharingViolations

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Detect classes declared without explicit sharing mode if DML methods are used. This +forces the developer to take access restrictions into account before modifying objects.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexSharingViolationsRule

    + +

    Example(s):

    + +
    public without sharing class Foo {
    +    // DML operation here
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexSharingViolations" />
    +
    + +

    ApexSOQLInjection

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Detects the usage of untrusted / unescaped variables in DML queries.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexSOQLInjectionRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void test1(String t1) {
    +        Database.query('SELECT Id FROM Account' + t1);
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexSOQLInjection" />
    +
    + +

    ApexSuggestUsingNamedCred

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Detects hardcoded credentials used in requests to an endpoint.

    + +

    You should refrain from hardcoding credentials:

    +
      +
    • They are hard to mantain by being mixed in application code
    • +
    • Particularly hard to update them when used from different classes
    • +
    • Granting a developer access to the codebase means granting knowledge + of credentials, keeping a two-level access is not possible.
    • +
    • Using different credentials for different environments is troublesome + and error-prone.
    • +
    + +

    Instead, you should use Named Credentials and a callout endpoint.

    + +

    For more information, you can check this

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexSuggestUsingNamedCredRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void foo(String username, String password) {
    +        Blob headerValue = Blob.valueOf(username + ':' + password);
    +        String authorizationHeader = 'BASIC ' + EncodingUtil.base64Encode(headerValue);
    +        req.setHeader('Authorization', authorizationHeader);
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexSuggestUsingNamedCred" />
    +
    + +

    ApexXSSFromEscapeFalse

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Reports on calls to addError with disabled escaping. The message passed to addError +will be displayed directly to the user in the UI, making it prime ground for XSS +attacks if unescaped.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexXSSFromEscapeFalseRule

    + +

    Example(s):

    + +
    public without sharing class Foo {
    +    Trigger.new[0].addError(vulnerableHTMLGoesHere, false);
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier100Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexXSSFromEscapeFalse" />
    +
    + +

    ApexXSSFromURLParam

    + +

    Since: PMD 5.5.3

    + +

    Priority: Medium (3)

    + +

    Makes sure that all values obtained from URL parameters are properly escaped / sanitized +to avoid XSS attacks.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.apex.rule.security.ApexXSSFromURLParamRule

    + +

    Example(s):

    + +
    public without sharing class Foo {
    +    String unescapedstring = ApexPage.getCurrentPage().getParameters.get('url_param');
    +    String usedLater = unescapedstring;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    cc_categoriesSecurityDeprecated Code Climate Categoriesyes. Delimiter is ‘|’.
    cc_remediation_points_multiplier50Deprecated Code Climate Remediation Points multiplierno
    cc_block_highlightingfalseDeprecated Code Climate Block Highlightingno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/apex/security.xml/ApexXSSFromURLParam" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_ecmascript.html b/pmd_rules_ecmascript.html new file mode 100644 index 0000000000..0c95c5103d --- /dev/null +++ b/pmd_rules_ecmascript.html @@ -0,0 +1,1529 @@ + + + + + + + + +Ecmascript Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Ecmascript Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for Ecmascript
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Best Practices

    + +
    Rules which enforce generally accepted best practices.
    + +
      +
    • AvoidWithStatement: Avoid using with - it’s bad news
    • +
    • ConsistentReturn: ECMAScript does provide for return types on functions, and therefore there is no solid rule as to…
    • +
    • GlobalVariable: This rule helps to avoid using accidently global variables by simply missing the "var" declaratio…
    • +
    • ScopeForInVariable: A for-in loop in which the variable name is not explicitly scoped to the enclosing scope with the…
    • +
    • UseBaseWithParseInt: This rule checks for usages of parseInt. While the second parameter is optional and usually defau…
    • +
    + +

    Code Style

    + +
    Rules which enforce a specific coding style.
    + +
      +
    • AssignmentInOperand: Avoid assignments in operands; this can make code more complicated and harder to read. This is s…
    • +
    • ForLoopsMustUseBraces: Avoid using ‘for’ statements without using curly braces.
    • +
    • IfElseStmtsMustUseBraces: Avoid using if..else statements without using curly braces.
    • +
    • IfStmtsMustUseBraces: Avoid using if statements without using curly braces.
    • +
    • NoElseReturn: The else block in a if-else-construct is unnecessary if the ‘if’ block contains a return. Then th…
    • +
    • UnnecessaryBlock: An unnecessary Block is present. Such Blocks are often used in other languages to introduce a ne…
    • +
    • UnnecessaryParentheses: Unnecessary parentheses should be removed.
    • +
    • UnreachableCode: A ‘return’, ‘break’, ‘continue’, or ‘throw’ statement should be the last in a block. Statements a…
    • +
    • WhileLoopsMustUseBraces: Avoid using ‘while’ statements without using curly braces.
    • +
    + +

    Error Prone

    + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + +
      +
    • AvoidTrailingComma: This rule helps improve code portability due to differences in browser treatment of trailing comm…
    • +
    • EqualComparison: Using == in condition may lead to unexpected results, as the variables are automatically casted t…
    • +
    • InnaccurateNumericLiteral: The numeric literal will have a different value at runtime, which can happen if you provide too m…
    • +
    + +

    Additional rulesets

    + + + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_ecmascript_bestpractices.html b/pmd_rules_ecmascript_bestpractices.html new file mode 100644 index 0000000000..690dc4fd66 --- /dev/null +++ b/pmd_rules_ecmascript_bestpractices.html @@ -0,0 +1,1651 @@ + + + + + + + + +Best Practices | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Best Practices

    +
    + + + +
    + + +
    Rules which enforce generally accepted best practices.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AvoidWithStatement

    + +

    Since: PMD 5.0.1

    + +

    Priority: High (1)

    + +

    Avoid using with - it’s bad news

    + +

    This rule is defined by the following XPath expression:

    +
    //WithStatement
    +
    + +

    Example(s):

    + +
    with (object) {
    +    property = 3; // Might be on object, might be on window: who knows.
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/bestpractices.xml/AvoidWithStatement" />
    +
    + +

    ConsistentReturn

    + +

    Since: PMD 5.0

    + +

    Priority: Medium High (2)

    + +

    ECMAScript does provide for return types on functions, and therefore there is no solid rule as to their usage. +However, when a function does use returns they should all have a value, or all with no value. Mixed return +usage is likely a bug, or at best poor style.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.ecmascript.rule.bestpractices.ConsistentReturnRule

    + +

    Example(s):

    + +
    // Ok
    +function foo() {
    +    if (condition1) {
    +        return true;
    +    }
    +    return false;
    +}
    +
    +// Bad
    +function bar() {
    +    if (condition1) {
    +        return;
    +    }
    +    return false;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    rhinoLanguageVersionES6Specifies the Rhino Language Version to use for parsing. Defaults to ES6.no
    recordingLocalJsDocCommentstrueSpecifies that JsDoc comments are produced in the AST.no
    recordingCommentstrueSpecifies that comments are produced in the AST.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/ecmascript/bestpractices.xml/ConsistentReturn" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/ecmascript/bestpractices.xml/ConsistentReturn">
    +    <properties>
    +        <property name="rhinoLanguageVersion" value="ES6" />
    +        <property name="recordingLocalJsDocComments" value="true" />
    +        <property name="recordingComments" value="true" />
    +    </properties>
    +</rule>
    +
    + +

    GlobalVariable

    + +

    Since: PMD 5.0

    + +

    Priority: High (1)

    + +

    This rule helps to avoid using accidently global variables by simply missing the "var" declaration. +Global variables can lead to side-effects that are hard to debug.

    + +

    This rule is defined by the following XPath expression:

    +
    //Assignment[Name/@GlobalName = true()]
    +
    + +

    Example(s):

    + +
    function(arg) {
    +    notDeclaredVariable = 1;    // this will create a global variable and trigger the rule
    +
    +    var someVar = 1;            // this is a local variable, that's ok
    +
    +    window.otherGlobal = 2;     // this will not trigger the rule, although it is a global variable.
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/bestpractices.xml/GlobalVariable" />
    +
    + +

    ScopeForInVariable

    + +

    Since: PMD 5.0

    + +

    Priority: High (1)

    + +

    A for-in loop in which the variable name is not explicitly scoped to the enclosing scope with the ‘var’ keyword can +refer to a variable in an enclosing scope outside the nearest enclosing scope. This will overwrite the +existing value of the variable in the outer scope when the body of the for-in is evaluated. When the for-in loop +has finished, the variable will contain the last value used in the for-in, and the original value from before +the for-in loop will be gone. Since the for-in variable name is most likely intended to be a temporary name, it +is better to explicitly scope the variable name to the nearest enclosing scope with ‘var’.

    + +

    This rule is defined by the following XPath expression:

    +
    //ForInLoop[not(child::VariableDeclaration)]/Name[1]
    +
    + +

    Example(s):

    + +
    // Ok
    +function foo() {
    +    var p = 'clean';
    +    function() {
    +        var obj = { dirty: 'dirty' };
    +        for (var p in obj) { // Use 'var' here.
    +            obj[p] = obj[p];
    +        }
    +        return x;
    +    }();
    +
    +    // 'p' still has value of 'clean'.
    +}
    +// Bad
    +function bar() {
    +    var p = 'clean';
    +    function() {
    +        var obj = { dirty: 'dirty' };
    +        for (p in obj) { // Oh no, missing 'var' here!
    +            obj[p] = obj[p];
    +        }
    +        return x;
    +    }();
    +
    +    // 'p' is trashed and has value of 'dirty'!
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/bestpractices.xml/ScopeForInVariable" />
    +
    + +

    UseBaseWithParseInt

    + +

    Since: PMD 5.0.1

    + +

    Priority: High (1)

    + +

    This rule checks for usages of parseInt. While the second parameter is optional and usually defaults +to 10 (base/radix is 10 for a decimal number), different implementations may behave differently. +It also improves readability, if the base is given.

    + +

    See also: parseInt()

    + +

    This rule is defined by the following XPath expression:

    +
    //FunctionCall/Name[
    +     @Image = 'parseInt'
    +     and
    +     count(../*) < 3
    +]
    +
    + +

    Example(s):

    + +
    parseInt("010");    // unclear, could be interpreted as 10 or 7 (with a base of 7)
    +
    +parseInt("10", 10); // good
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/bestpractices.xml/UseBaseWithParseInt" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_ecmascript_codestyle.html b/pmd_rules_ecmascript_codestyle.html new file mode 100644 index 0000000000..994b0f15d1 --- /dev/null +++ b/pmd_rules_ecmascript_codestyle.html @@ -0,0 +1,1793 @@ + + + + + + + + +Code Style | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Code Style

    +
    + + + +
    + + +
    Rules which enforce a specific coding style.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AssignmentInOperand

    + +

    Since: PMD 5.0

    + +

    Priority: Medium High (2)

    + +

    Avoid assignments in operands; this can make code more complicated and harder to read. This is sometime +indicative of the bug where the assignment operator ‘=’ was used instead of the equality operator ‘==’.

    + +

    This rule is defined by the following XPath expression:

    +
    //IfStatement[$allowIf = false()]/child::node()[1]/descendant-or-self::node()[self::Assignment or self::UnaryExpression[$allowIncrementDecrement = false() and (@Image = "--" or @Image = "++")]]
    +|
    +    //WhileLoop[$allowWhile = false()]/child::node()[1]/descendant-or-self::node()[self::Assignment or self::UnaryExpression[$allowIncrementDecrement = false() and (@Image = "--" or @Image = "++")]]
    +|
    +    //DoLoop[$allowWhile = false()]/child::node()[2]/descendant-or-self::node()[self::Assignment or self::UnaryExpression[$allowIncrementDecrement = false() and (@Image = "--" or @Image = "++")]]
    +|
    +    //ForLoop[$allowFor = false()]/child::node()[2]/descendant-or-self::node()[self::Assignment or self::UnaryExpression[$allowIncrementDecrement = false() and (@Image = "--" or @Image = "++")]]
    +|
    +   //ConditionalExpression[$allowTernary = false()]/child::node()[1]/descendant-or-self::node()[self::Assignment or self::UnaryExpression[$allowIncrementDecrement = false() and (@Image = "--" or @Image = "++")]]
    +|
    +   //ConditionalExpression[$allowTernaryResults = false()]/child::node()[position() = 2 or position() = 3]/descendant-or-self::node()[self::Assignment or self::UnaryExpression[$allowIncrementDecrement = false() and (@Image = "--" or @Image = "++")]]
    +
    + +

    Example(s):

    + +
    var x = 2;
    +// Bad
    +if ((x = getX()) == 3) {
    +    alert('3!');
    +}
    +
    +function getX() {
    +    return 3;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    allowIffalseAllow assignment within the conditional expression of an if statementno
    allowForfalseAllow assignment within the conditional expression of a for statementno
    allowWhilefalseAllow assignment within the conditional expression of a while statementno
    allowTernaryfalseAllow assignment within the conditional expression of a ternary operatorno
    allowTernaryResultsfalseAllow assignment within the result expressions of a ternary operatorno
    allowIncrementDecrementfalseAllow increment or decrement operators within the conditional expression of an if, for, or while statementno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/ecmascript/codestyle.xml/AssignmentInOperand" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/ecmascript/codestyle.xml/AssignmentInOperand">
    +    <properties>
    +        <property name="allowIf" value="false" />
    +        <property name="allowFor" value="false" />
    +        <property name="allowWhile" value="false" />
    +        <property name="allowTernary" value="false" />
    +        <property name="allowTernaryResults" value="false" />
    +        <property name="allowIncrementDecrement" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    ForLoopsMustUseBraces

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Avoid using ‘for’ statements without using curly braces.

    + +

    This rule is defined by the following XPath expression:

    +
    //ForLoop[not(child::Scope)]
    +|
    +//ForInLoop[not(child::Scope)]
    +
    + +

    Example(s):

    + +
    // Ok
    +for (var i = 0; i < 42; i++) {
    +    foo();
    +}
    +
    +// Bad
    +for (var i = 0; i < 42; i++)
    +    foo();
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/codestyle.xml/ForLoopsMustUseBraces" />
    +
    + +

    IfElseStmtsMustUseBraces

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Avoid using if..else statements without using curly braces.

    + +

    This rule is defined by the following XPath expression:

    +
    //ExpressionStatement[parent::IfStatement[@Else = true()]]
    +   [not(child::Scope)]
    +   [not(child::IfStatement)]
    +
    + +

    Example(s):

    + +
    // Ok
    +if (foo) {
    +    x++;
    +} else {
    +    y++;
    +}
    +
    +// Bad
    +if (foo)
    +    x++;
    +else
    +    y++;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/codestyle.xml/IfElseStmtsMustUseBraces" />
    +
    + +

    IfStmtsMustUseBraces

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Avoid using if statements without using curly braces.

    + +

    This rule is defined by the following XPath expression:

    +
    //IfStatement[@Else = false() and not(child::Scope)]
    +
    + +

    Example(s):

    + +
    // Ok
    +if (foo) {
    +    x++;
    +}
    +
    +// Bad
    +if (foo)
    +    x++;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/codestyle.xml/IfStmtsMustUseBraces" />
    +
    + +

    NoElseReturn

    + +

    Since: PMD 5.5.0

    + +

    Priority: Medium (3)

    + +

    The else block in a if-else-construct is unnecessary if the if block contains a return. +Then the content of the else block can be put outside.

    + +

    See also: http://eslint.org/docs/rules/no-else-return

    + +

    This rule is defined by the following XPath expression:

    +
    //IfStatement[@Else=true()][Scope[1]/ReturnStatement]
    +
    + +

    Example(s):

    + +
    // Bad:
    +if (x) {
    +    return y;
    +} else {
    +    return z;
    +}
    +
    +// Good:
    +if (x) {
    +    return y;
    +}
    +return z;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/codestyle.xml/NoElseReturn" />
    +
    + +

    UnnecessaryBlock

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    An unnecessary Block is present. Such Blocks are often used in other languages to +introduce a new variable scope. Blocks do not behave like this in ECMAScipt, and using them can +be misleading. Considering removing this unnecessary Block.

    + +

    This rule is defined by the following XPath expression:

    +
    //Block[not(parent::FunctionNode or parent::IfStatement or parent::ForLoop or parent::ForInLoop
    +    or parent::WhileLoop or parent::DoLoop or parent::TryStatement or parent::CatchClause)]
    +|
    +//Scope[not(parent::FunctionNode or parent::IfStatement or parent::ForLoop or parent::ForInLoop
    +    or parent::WhileLoop or parent::DoLoop or parent::TryStatement or parent::CatchClause)]
    +
    + +

    Example(s):

    + +
    if (foo) {
    +    // Ok
    +}
    +if (bar) {
    +    {
    +        // Bad
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/codestyle.xml/UnnecessaryBlock" />
    +
    + +

    UnnecessaryParentheses

    + +

    Since: PMD 5.0

    + +

    Priority: Medium Low (4)

    + +

    Unnecessary parentheses should be removed.

    + +

    This rule is defined by the following XPath expression:

    +
    //ParenthesizedExpression/ParenthesizedExpression
    +
    + +

    Example(s):

    + +
    var x = 1; // Ok
    +var y = (1 + 1); // Ok
    +var z = ((1 + 1)); // Bad
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/codestyle.xml/UnnecessaryParentheses" />
    +
    + +

    UnreachableCode

    + +

    Since: PMD 5.0

    + +

    Priority: High (1)

    + +

    A ‘return’, ‘break’, ‘continue’, or ‘throw’ statement should be the last in a block. Statements after these +will never execute. This is a bug, or extremely poor style.

    + +

    This rule is defined by the following XPath expression:

    +
    //ReturnStatement[following-sibling::node()]
    +|
    +    //ContinueStatement[following-sibling::node()]
    +|
    +    //BreakStatement[following-sibling::node()]
    +|
    +    //ThrowStatement[following-sibling::node()]
    +
    + +

    Example(s):

    + +
    // Ok
    +function foo() {
    +   return 1;
    +}
    +// Bad
    +function bar() {
    +   var x = 1;
    +   return x;
    +   x = 2;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/codestyle.xml/UnreachableCode" />
    +
    + +

    WhileLoopsMustUseBraces

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Avoid using ‘while’ statements without using curly braces.

    + +

    This rule is defined by the following XPath expression:

    +
    //WhileLoop[not(child::Scope)]
    +
    + +

    Example(s):

    + +
    // Ok
    +while (true) {
    +    x++;
    +}
    +
    +// Bad
    +while (true)
    +    x++;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/codestyle.xml/WhileLoopsMustUseBraces" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_ecmascript_errorprone.html b/pmd_rules_ecmascript_errorprone.html new file mode 100644 index 0000000000..d4732e880b --- /dev/null +++ b/pmd_rules_ecmascript_errorprone.html @@ -0,0 +1,1574 @@ + + + + + + + + +Error Prone | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Error Prone

    +
    + + + +
    + + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AvoidTrailingComma

    + +

    Since: PMD 5.1

    + +

    Priority: High (1)

    + +

    This rule helps improve code portability due to differences in browser treatment of trailing commas in object or array literals.

    + +

    This rule is defined by the following XPath expression:

    +
    //ObjectLiteral[$allowObjectLiteral = false() and @TrailingComma = true()]
    +|
    +//ArrayLiteral[$allowArrayLiteral = false() and @TrailingComma = true()]
    +
    + +

    Example(s):

    + +
    function(arg) {
    +    var obj1 = { a : 1 };   // Ok
    +    var arr1 = [ 1, 2 ];    // Ok
    +
    +    var obj2 = { a : 1, };  // Syntax error in some browsers!
    +    var arr2 = [ 1, 2, ];   // Length 2 or 3 depending on the browser!
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    allowObjectLiteralfalseAllow a trailing comma within an object literalno
    allowArrayLiteralfalseAllow a trailing comma within an array literalno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/ecmascript/errorprone.xml/AvoidTrailingComma" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/ecmascript/errorprone.xml/AvoidTrailingComma">
    +    <properties>
    +        <property name="allowObjectLiteral" value="false" />
    +        <property name="allowArrayLiteral" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    EqualComparison

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Using == in condition may lead to unexpected results, as the variables are automatically casted to be of the +same type. The === operator avoids the casting.

    + +

    This rule is defined by the following XPath expression:

    +
    //InfixExpression[
    +  (@Image = "==" or @Image = "!=")
    +  and
    +  (KeywordLiteral[@Image='true' or @Image = 'false'] or NumberLiteral)
    +]
    +
    + +

    Example(s):

    + +
    // Ok
    +if (someVar === true) {
    +  ...
    +}
    +// Ok
    +if (someVar !== 3) {
    +  ...
    +}
    +// Bad
    +if (someVar == true) {
    +  ...
    +}
    +// Bad
    +if (someVar != 3) {
    +  ...
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/errorprone.xml/EqualComparison" />
    +
    + +

    InnaccurateNumericLiteral

    + +

    Since: PMD 5.0

    + +

    Priority: Medium High (2)

    + +

    The numeric literal will have a different value at runtime, which can happen if you provide too much +precision in a floating point number. This may result in numeric calculations being in error.

    + +

    This rule is defined by the following XPath expression:

    +
    //NumberLiteral[@NormalizedImage != string(@Number)]
    +
    + +

    Example(s):

    + +
    var a = 9; // Ok
    +var b = 999999999999999; // Ok
    +var c = 999999999999999999999; // Not good
    +var w = 1.12e-4; // Ok
    +var x = 1.12; // Ok
    +var y = 1.1234567890123; // Ok
    +var z = 1.12345678901234567; // Not good
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/ecmascript/errorprone.xml/InnaccurateNumericLiteral" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_java.html b/pmd_rules_java.html new file mode 100644 index 0000000000..c9e9b43057 --- /dev/null +++ b/pmd_rules_java.html @@ -0,0 +1,2093 @@ + + + + + + + + +Java Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Java Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for Java
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Best Practices

    + +
    Rules which enforce generally accepted best practices.
    + +
      +
    • AbstractClassWithoutAbstractMethod: The abstract class does not contain any abstract methods. An abstract class suggests an incomplet…
    • +
    • AccessorClassGeneration: Instantiation by way of private constructors from outside of the constructor’s class often causes…
    • +
    • AccessorMethodGeneration: When accessing a private field / method from another class, the Java compiler will generate a acc…
    • +
    • ArrayIsStoredDirectly: Constructors and methods receiving arrays should clone objects and store the copy. This prevents …
    • +
    • AvoidMessageDigestField: Declaring a MessageDigest instance as a field make this instance directly available to multiple t…
    • +
    • AvoidPrintStackTrace: Avoid printStackTrace(); use a logger call instead.
    • +
    • AvoidReassigningCatchVariables: Reassigning exception variables caught in a catch statement should be avoided because of: 1) If i…
    • +
    • AvoidReassigningLoopVariables: Reassigning loop variables can lead to hard-to-find bugs. Prevent or limit how these variables ca…
    • +
    • AvoidReassigningParameters: Reassigning values to incoming parameters is not recommended. Use temporary local variables inst…
    • +
    • AvoidStringBufferField: StringBuffers/StringBuilders can grow considerably, and so may become a source of memory leaks if…
    • +
    • AvoidUsingHardCodedIP: Application with hard-coded IP addresses can become impossible to deploy in some cases. Externali…
    • +
    • CheckResultSet: Always check the return values of navigation methods (next, previous, first, last) of a ResultSet…
    • +
    • ConstantsInInterface: Avoid constants in interfaces. Interfaces should define types, constants are implementation detai…
    • +
    • DefaultLabelNotLastInSwitchStmt: By convention, the default label should be the last label in a switch statement.
    • +
    • DoubleBraceInitialization: Double brace initialisation is a pattern to initialise eg collections concisely. But it implicitl…
    • +
    • ForLoopCanBeForeach: Reports loops that can be safely replaced with the foreach syntax. The rule considers loops over …
    • +
    • ForLoopVariableCount: Having a lot of control variables in a ‘for’ loop makes it harder to see what range of values the…
    • +
    • GuardLogStatement: Whenever using a log level, one should check if the loglevel is actually enabled, or otherwise sk…
    • +
    • JUnit4SuitesShouldUseSuiteAnnotation: In JUnit 3, test suites are indicated by the suite() method. In JUnit 4, suites are indicated thr…
    • +
    • JUnit4TestShouldUseAfterAnnotation: In JUnit 3, the tearDown method was used to clean up all data entities required in running tests….
    • +
    • JUnit4TestShouldUseBeforeAnnotation: In JUnit 3, the setUp method was used to set up all data entities required in running tests. JUni…
    • +
    • JUnit4TestShouldUseTestAnnotation: In JUnit 3, the framework executed all methods which started with the word test as a unit test. I…
    • +
    • JUnitAssertionsShouldIncludeMessage: JUnit assertions should include an informative message - i.e., use the three-argument version of …
    • +
    • JUnitTestContainsTooManyAsserts: Unit tests should not contain too many asserts. Many asserts are indicative of a complex test, fo…
    • +
    • JUnitTestsShouldIncludeAssert: JUnit tests should include at least one assertion. This makes the tests more robust, and using a…
    • +
    • JUnitUseExpected: In JUnit4, use the @Test(expected) annotation to denote tests that should throw exceptions.
    • +
    • LiteralsFirstInComparisons: Position literals first in all String comparisons, if the second argument is null then NullPointe…
    • +
    • LooseCoupling: The use of implementation types (i.e., HashSet) as object references limits your ability to use a…
    • +
    • MethodReturnsInternalArray: Exposing internal arrays to the caller violates object encapsulation since elements can be remove…
    • +
    • MissingOverride: Annotating overridden methods with @Override ensures at compile time that the method …
    • +
    • OneDeclarationPerLine: Java allows the use of several variables declaration of the same type on one line. However, it ca…
    • +
    • PositionLiteralsFirstInCaseInsensitiveComparisons: Deprecated Position literals first in comparisons, if the second argument is null then NullPointerExceptions…
    • +
    • PositionLiteralsFirstInComparisons: Deprecated Position literals first in comparisons, if the second argument is null then NullPointerExceptions…
    • +
    • PreserveStackTrace: Throwing a new exception from a catch block without passing the original exception into the new e…
    • +
    • ReplaceEnumerationWithIterator: Consider replacing Enumeration usages with the newer java.util.Iterator
    • +
    • ReplaceHashtableWithMap: Consider replacing Hashtable usage with the newer java.util.Map if thread safety is not required.
    • +
    • ReplaceVectorWithList: Consider replacing Vector usages with the newer java.util.ArrayList if expensive thread-safe oper…
    • +
    • SwitchStmtsShouldHaveDefault: All switch statements should include a default option to catch any unspecified values.
    • +
    • SystemPrintln: References to System.(out|err).print are usually intended for debugging purposes and can remain …
    • +
    • UnusedAssignment: Reports assignments to variables that are never used before the variable is overwritten, …
    • +
    • UnusedFormalParameter: Avoid passing parameters to methods or constructors without actually referencing them in the meth…
    • +
    • UnusedImports: Avoid unused import statements to prevent unwanted dependencies. This rule will also find unused …
    • +
    • UnusedLocalVariable: Detects when a local variable is declared and/or assigned, but not used.
    • +
    • UnusedPrivateField: Detects when a private field is declared and/or assigned a value, but not used.
    • +
    • UnusedPrivateMethod: Unused Private Method detects when a private method is declared but is unused.
    • +
    • UseAssertEqualsInsteadOfAssertTrue: This rule detects JUnit assertions in object equality. These assertions should be made by more sp…
    • +
    • UseAssertNullInsteadOfAssertTrue: This rule detects JUnit assertions in object references equality. These assertions should be made…
    • +
    • UseAssertSameInsteadOfAssertTrue: This rule detects JUnit assertions in object references equality. These assertions should be made…
    • +
    • UseAssertTrueInsteadOfAssertEquals: When asserting a value is the same as a literal or Boxed boolean, use assertTrue/assertFalse, ins…
    • +
    • UseCollectionIsEmpty: The isEmpty() method on java.util.Collection is provided to determine if a collection has any ele…
    • +
    • UseTryWithResources: Java 7 introduced the try-with-resources statement. This statement ensures that each resource is …
    • +
    • UseVarargs: Java 5 introduced the varargs parameter declaration for methods and constructors. This syntactic…
    • +
    • WhileLoopWithLiteralBoolean: ‘do {} while (true);’ requires reading the end of the statement before it is apparent that it loo…
    • +
    + +

    Code Style

    + +
    Rules which enforce a specific coding style.
    + +
      +
    • AbstractNaming: Deprecated Abstract classes should be named ‘AbstractXXX’. This rule is deprecated and will be removed with …
    • +
    • AtLeastOneConstructor: Each non-static class should declare at least one constructor. Classes with solely static members…
    • +
    • AvoidDollarSigns: Avoid using dollar signs in variable/method/class/interface names.
    • +
    • AvoidFinalLocalVariable: Deprecated Avoid using final local variables, turn them into fields. Note that this is a controversial rule …
    • +
    • AvoidPrefixingMethodParameters: Deprecated Prefixing parameters by ‘in’ or ‘out’ pollutes the name of the parameters and reduces code readab…
    • +
    • AvoidProtectedFieldInFinalClass: Do not use protected fields in final classes since they cannot be subclassed. Clarify your intent…
    • +
    • AvoidProtectedMethodInFinalClassNotExtending: Do not use protected methods in most final classes since they cannot be subclassed. This should o…
    • +
    • AvoidUsingNativeCode: Unnecessary reliance on Java Native Interface (JNI) calls directly reduces application portabilit…
    • +
    • BooleanGetMethodName: Methods that return boolean results should be named as predicate statements to denote this. I.e, …
    • +
    • CallSuperInConstructor: It is a good practice to call super() in a constructor. If super() is not called but another cons…
    • +
    • ClassNamingConventions: Configurable naming conventions for type declarations. This rule reports type declara…
    • +
    • CommentDefaultAccessModifier: To avoid mistakes if we want that an Annotation, Class, Enum, Method, Constructor or Field have a…
    • +
    • ConfusingTernary: Avoid negation within an "if" expression with an "else" clause. For example, rephrase: ‘if (x !=…
    • +
    • ControlStatementBraces: Enforce a policy for braces on control statements. It is recommended to use braces on ‘if … els…
    • +
    • DefaultPackage: Use explicit scoping instead of accidental usage of default package private level. The rule allow…
    • +
    • DontImportJavaLang: Avoid importing anything from the package ‘java.lang’. These classes are automatically imported …
    • +
    • DuplicateImports: Duplicate or overlapping import statements should be avoided.
    • +
    • EmptyMethodInAbstractClassShouldBeAbstract: Empty or auto-generated methods in an abstract class should be tagged as abstract. This helps to …
    • +
    • ExtendsObject: No need to explicitly extend Object.
    • +
    • FieldDeclarationsShouldBeAtStartOfClass: Fields should be declared at the top of the class, before any method declarations, constructors, …
    • +
    • FieldNamingConventions: Configurable naming conventions for field declarations. This rule reports variable declarations …
    • +
    • ForLoopShouldBeWhileLoop: Some for loops can be simplified to while loops, this makes them more concise.
    • +
    • ForLoopsMustUseBraces: Deprecated Avoid using ‘for’ statements without using curly braces. If the code formatting or indentation is…
    • +
    • FormalParameterNamingConventions: Configurable naming conventions for formal parameters of methods and lambdas. This ru…
    • +
    • GenericsNaming: Names for references to generic values should be limited to a single uppercase letter.
    • +
    • IdenticalCatchBranches: Identical ‘catch’ branches use up vertical space and increase the complexity of code without …
    • +
    • IfElseStmtsMustUseBraces: Deprecated Avoid using if..else statements without using surrounding braces. If the code formatting or inden…
    • +
    • IfStmtsMustUseBraces: Deprecated Avoid using if statements without using braces to surround the code block. If the code formatting…
    • +
    • LinguisticNaming: This rule finds Linguistic Naming Antipatterns. It checks for fields, that are named, as if they …
    • +
    • LocalHomeNamingConvention: The Local Home interface of a Session EJB should be suffixed by ‘LocalHome’.
    • +
    • LocalInterfaceSessionNamingConvention: The Local Interface of a Session EJB should be suffixed by ‘Local’.
    • +
    • LocalVariableCouldBeFinal: A local variable assigned only once can be declared final.
    • +
    • LocalVariableNamingConventions: Configurable naming conventions for local variable declarations and other locally-scoped …
    • +
    • LongVariable: Fields, formal arguments, or local variable names that are too long can make the code difficult t…
    • +
    • MDBAndSessionBeanNamingConvention: The EJB Specification states that any MessageDrivenBean or SessionBean should be suffixed by ‘Bean’.
    • +
    • MethodArgumentCouldBeFinal: A method argument that is never re-assigned within the method can be declared final.
    • +
    • MethodNamingConventions: Configurable naming conventions for method declarations. This rule reports method dec…
    • +
    • MIsLeadingVariableName: Deprecated Detects when a non-field has a name starting with ‘m_’. This usually denotes a field and could b…
    • +
    • NoPackage: Detects when a class, interface, enum or annotation does not have a package definition.
    • +
    • OnlyOneReturn: A method should have only one exit point, and that should be the last statement in the method.
    • +
    • PackageCase: Detects when a package definition contains uppercase characters.
    • +
    • PrematureDeclaration: Checks for variables that are defined before they might be used. A reference is deemed to be prem…
    • +
    • RemoteInterfaceNamingConvention: Remote Interface of a Session EJB should not have a suffix.
    • +
    • RemoteSessionInterfaceNamingConvention: A Remote Home interface type of a Session EJB should be suffixed by ‘Home’.
    • +
    • ShortClassName: Short Classnames with fewer than e.g. five characters are not recommended.
    • +
    • ShortMethodName: Method names that are very short are not helpful to the reader.
    • +
    • ShortVariable: Fields, local variables, or parameter names that are very short are not helpful to the reader.
    • +
    • SuspiciousConstantFieldName: Deprecated Field names using all uppercase characters - Sun’s Java naming conventions indicating constants -…
    • +
    • TooManyStaticImports: If you overuse the static import feature, it can make your program unreadable and unmaintainable,…
    • +
    • UnnecessaryAnnotationValueElement: Avoid the use of value in annotations when it’s the only element.
    • +
    • UnnecessaryCast: This rule detects when a cast is unnecessary while accessing collection elements. This rule is mo…
    • +
    • UnnecessaryConstructor: This rule detects when a constructor is not necessary; i.e., when there is only one constructor a…
    • +
    • UnnecessaryFullyQualifiedName: Import statements allow the use of non-fully qualified names. The use of a fully qualified name …
    • +
    • UnnecessaryLocalBeforeReturn: Avoid the creation of unnecessary local variables
    • +
    • UnnecessaryModifier: Fields in interfaces and annotations are automatically ‘public static final’, and methods are ‘pu…
    • +
    • UnnecessaryReturn: Avoid the use of unnecessary return statements.
    • +
    • UseDiamondOperator: Use the diamond operator to let the type be inferred automatically. With the Diamond operator it …
    • +
    • UselessParentheses: Useless parentheses should be removed.
    • +
    • UselessQualifiedThis: Reports qualified this usages in the same class.
    • +
    • UseShortArrayInitializer: When declaring and initializing array fields or variables, it is not necessary to explicitly crea…
    • +
    • UseUnderscoresInNumericLiterals: Since Java 1.7, numeric literals can use underscores to separate digits. This rule enforces that …
    • +
    • VariableNamingConventions: Deprecated A variable naming conventions rule - customize this to your liking. Currently, it checks for fin…
    • +
    • WhileLoopsMustUseBraces: Deprecated Avoid using ‘while’ statements without using braces to surround the code block. If the code forma…
    • +
    + +

    Design

    + +
    Rules that help you discover design issues.
    + +
      +
    • AbstractClassWithoutAnyMethod: If an abstract class does not provides any methods, it may be acting as a simple data container t…
    • +
    • AvoidCatchingGenericException: Avoid catching generic exceptions such as NullPointerException, RuntimeException, Exception in tr…
    • +
    • AvoidDeeplyNestedIfStmts: Avoid creating deeply nested if-then statements since they are harder to read and error-prone to …
    • +
    • AvoidRethrowingException: Catch blocks that merely rethrow a caught exception only add to code size and runtime complexity.
    • +
    • AvoidThrowingNewInstanceOfSameException: Catch blocks that merely rethrow a caught exception wrapped inside a new instance of the same typ…
    • +
    • AvoidThrowingNullPointerException: Avoid throwing NullPointerExceptions manually. These are confusing because most people will assum…
    • +
    • AvoidThrowingRawExceptionTypes: Avoid throwing certain exception types. Rather than throw a raw RuntimeException, Throwable, Exce…
    • +
    • AvoidUncheckedExceptionsInSignatures: A method or constructor should not explicitly declare unchecked exceptions in its ‘throws’ clause…
    • +
    • ClassWithOnlyPrivateConstructorsShouldBeFinal: A class with only private constructors should be final, unless the private constructor is invoked…
    • +
    • CollapsibleIfStatements: Sometimes two consecutive ‘if’ statements can be consolidated by separating their conditions with…
    • +
    • CouplingBetweenObjects: This rule counts the number of unique attributes, local variables, and return types within an obj…
    • +
    • CyclomaticComplexity: The complexity of methods directly affects maintenance costs and readability. Concentrating too m…
    • +
    • DataClass: Data Classes are simple data holders, which reveal most of their state, and without complex funct…
    • +
    • DoNotExtendJavaLangError: Errors are system exceptions. Do not extend them.
    • +
    • ExceptionAsFlowControl: Using Exceptions as form of flow control is not recommended as they obscure true exceptions when …
    • +
    • ExcessiveClassLength: Excessive class file lengths are usually indications that the class may be burdened with excessiv…
    • +
    • ExcessiveImports: A high number of imports can indicate a high degree of coupling within an object. This rule count…
    • +
    • ExcessiveMethodLength: When methods are excessively long this usually indicates that the method is doing more than its n…
    • +
    • ExcessiveParameterList: Methods with numerous parameters are a challenge to maintain, especially if most of them share th…
    • +
    • ExcessivePublicCount: Classes with large numbers of public methods and attributes require disproportionate testing effo…
    • +
    • FinalFieldCouldBeStatic: If a final field is assigned to a compile-time constant, it could be made static, thus saving ove…
    • +
    • GodClass: The God Class rule detects the God Class design flaw using metrics. God classes do too many thing…
    • +
    • ImmutableField: Identifies private fields whose values never change once object initialization ends either in the…
    • +
    • LawOfDemeter: The Law of Demeter is a simple rule, that says "only talk to friends". It helps to reduce couplin…
    • +
    • LogicInversion: Use opposite operator instead of negating the whole expression with a logic complement operator.
    • +
    • LoosePackageCoupling: Avoid using classes from the configured package hierarchy outside of the package hierarchy, excep…
    • +
    • ModifiedCyclomaticComplexity: Deprecated Complexity directly affects maintenance costs is determined by the number of decision points in a…
    • +
    • NcssConstructorCount: Deprecated This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of l…
    • +
    • NcssCount: This rule uses the NCSS (Non-Commenting Source Statements) metric to determine the number of line…
    • +
    • NcssMethodCount: Deprecated This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of l…
    • +
    • NcssTypeCount: Deprecated This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of l…
    • +
    • NPathComplexity: The NPath complexity of a method is the number of acyclic execution paths through that method. Wh…
    • +
    • SignatureDeclareThrowsException: A method/constructor shouldn’t explicitly throw the generic java.lang.Exception, since it is uncl…
    • +
    • SimplifiedTernary: Look for ternary operators with the form ‘condition ? literalBoolean : foo’ or ‘condition ? foo :…
    • +
    • SimplifyBooleanAssertion: Avoid negation in an assertTrue or assertFalse test. For example, rephrase: assertTrue(!expr)…
    • +
    • SimplifyBooleanExpressions: Avoid unnecessary comparisons in boolean expressions, they serve no purpose and impacts readability.
    • +
    • SimplifyBooleanReturns: Avoid unnecessary if-then-else statements when returning a boolean. The result of the conditional…
    • +
    • SimplifyConditional: No need to check for null before an instanceof; the instanceof keyword returns false when given a…
    • +
    • SingularField: Fields whose scopes are limited to just single methods do not rely on the containing object to pr…
    • +
    • StdCyclomaticComplexity: Deprecated Complexity directly affects maintenance costs is determined by the number of decision points in a…
    • +
    • SwitchDensity: A high ratio of statements to labels in a switch statement implies that the switch statement is o…
    • +
    • TooManyFields: Classes that have too many fields can become unwieldy and could be redesigned to have fewer field…
    • +
    • TooManyMethods: A class with too many methods is probably a good suspect for refactoring, in order to reduce its …
    • +
    • UselessOverridingMethod: The overriding method merely calls the same method defined in a superclass.
    • +
    • UseObjectForClearerAPI: When you write a public method, you should be thinking in terms of an API. If your method is publ…
    • +
    • UseUtilityClass: For classes that only have static methods, consider making them utility classes. Note that this d…
    • +
    + +

    Documentation

    + +
    Rules that are related to code documentation.
    + +
      +
    • CommentContent: A rule for the politically correct… we don’t want to offend anyone.
    • +
    • CommentRequired: Denotes whether javadoc (formal) comments are required (or unwanted) for specific language elements.
    • +
    • CommentSize: Determines whether the dimensions of non-header comments found are within the specified limits.
    • +
    • UncommentedEmptyConstructor: Uncommented Empty Constructor finds instances where a constructor does not contain statements, bu…
    • +
    • UncommentedEmptyMethodBody: Uncommented Empty Method Body finds instances where a method body does not contain statements, bu…
    • +
    + +

    Error Prone

    + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + +
      +
    • AssignmentInOperand: Avoid assignments in operands; this can make code more complicated and harder to read.
    • +
    • AssignmentToNonFinalStatic: Identifies a possible unsafe usage of a static field.
    • +
    • AvoidAccessibilityAlteration: Methods such as getDeclaredConstructors(), getDeclaredConstructor(Class[]) and setAccessible(), a…
    • +
    • AvoidAssertAsIdentifier: Use of the term ‘assert’ will conflict with newer versions of Java since it is a reserved word.
    • +
    • AvoidBranchingStatementAsLastInLoop: Using a branching statement as the last part of a loop may be a bug, and/or is confusing. Ensure …
    • +
    • AvoidCallingFinalize: The method Object.finalize() is called by the garbage collector on an object when garbage collect…
    • +
    • AvoidCatchingNPE: Code should never throw NullPointerExceptions under normal circumstances. A catch block may hide…
    • +
    • AvoidCatchingThrowable: Catching Throwable errors is not recommended since its scope is very broad. It includes runtime i…
    • +
    • AvoidDecimalLiteralsInBigDecimalConstructor: One might assume that the result of "new BigDecimal(0.1)" is exactly equal to 0.1, but it is actu…
    • +
    • AvoidDuplicateLiterals: Code containing duplicate String literals can usually be improved by declaring the String as a co…
    • +
    • AvoidEnumAsIdentifier: Use of the term ‘enum’ will conflict with newer versions of Java since it is a reserved word.
    • +
    • AvoidFieldNameMatchingMethodName: It can be confusing to have a field name with the same name as a method. While this is permitted,…
    • +
    • AvoidFieldNameMatchingTypeName: It is somewhat confusing to have a field name matching the declaring class name. This probably me…
    • +
    • AvoidInstanceofChecksInCatchClause: Each caught exception type should be handled in its own catch clause.
    • +
    • AvoidLiteralsInIfCondition: Avoid using hard-coded literals in conditional statements. By declaring them as static variables …
    • +
    • AvoidLosingExceptionInformation: Statements in a catch block that invoke accessors on the exception without using the information …
    • +
    • AvoidMultipleUnaryOperators: The use of multiple unary operators may be problematic, and/or confusing. Ensure that the intende…
    • +
    • AvoidUsingOctalValues: Integer literals should not start with zero since this denotes that the rest of literal will be i…
    • +
    • BadComparison: Avoid equality comparisons with Double.NaN. Due to the implicit lack of representation precision …
    • +
    • BeanMembersShouldSerialize: If a class is a bean, or is referenced by a bean directly or indirectly it needs to be serializab…
    • +
    • BrokenNullCheck: The null check is broken since it will throw a NullPointerException itself. It is likely that you…
    • +
    • CallSuperFirst: Super should be called at the start of the method
    • +
    • CallSuperLast: Super should be called at the end of the method
    • +
    • CheckSkipResult: The skip() method may skip a smaller number of bytes than requested. Check the returned value to …
    • +
    • ClassCastExceptionWithToArray: When deriving an array of a specific class from your Collection, one should provide an array of t…
    • +
    • CloneMethodMustBePublic: The java Manual says "By convention, classes that implement this interface should override Object…
    • +
    • CloneMethodMustImplementCloneable: The method clone() should only be implemented if the class implements the Cloneable interface wit…
    • +
    • CloneMethodReturnTypeMustMatchClassName: If a class implements cloneable the return type of the method clone() must be the class name. Tha…
    • +
    • CloneThrowsCloneNotSupportedException: The method clone() should throw a CloneNotSupportedException.
    • +
    • CloseResource: Ensure that resources (like ‘java.sql.Connection’, ‘java.sql.Statement’, and ‘java.sql.ResultSet’…
    • +
    • CompareObjectsWithEquals: Use equals() to compare object references; avoid comparing them with ==.
    • +
    • ConstructorCallsOverridableMethod: Calling overridable methods during construction poses a risk of invoking methods on an incomplete…
    • +
    • DataflowAnomalyAnalysis: Deprecated The dataflow analysis tracks local definitions, undefinitions and references to variables on diff…
    • +
    • DetachedTestCase: The method appears to be a test case since it has public or default visibility, non-static access…
    • +
    • DoNotCallGarbageCollectionExplicitly: Calls to System.gc(), Runtime.getRuntime().gc(), and System.runFinalization() are not advised. Co…
    • +
    • DoNotCallSystemExit: Deprecated The rule has been renamed. Use instead DoNotTerminateVM.
    • +
    • DoNotExtendJavaLangThrowable: Extend Exception or RuntimeException instead of Throwable.
    • +
    • DoNotHardCodeSDCard: Use Environment.getExternalStorageDirectory() instead of "/sdcard"
    • +
    • DoNotTerminateVM: Web applications should not call ‘System.exit()’, since only the web container or the application…
    • +
    • DoNotThrowExceptionInFinally: Throwing exceptions within a ‘finally’ block is confusing since they may mask other exceptions or…
    • +
    • DontImportSun: Avoid importing anything from the ‘sun.’ packages. These packages are not portable and are likel…
    • +
    • DontUseFloatTypeForLoopIndices: Don’t use floating point for loop indices. If you must use floating point, use double unless you’…
    • +
    • EmptyCatchBlock: Empty Catch Block finds instances where an exception is caught, but nothing is done. In most circ…
    • +
    • EmptyFinalizer: Empty finalize methods serve no purpose and should be removed. Note that Oracle has declared Obje…
    • +
    • EmptyFinallyBlock: Empty finally blocks serve no purpose and should be removed.
    • +
    • EmptyIfStmt: Empty If Statement finds instances where a condition is checked but nothing is done about it.
    • +
    • EmptyInitializer: Empty initializers serve no purpose and should be removed.
    • +
    • EmptyStatementBlock: Empty block statements serve no purpose and should be removed.
    • +
    • EmptyStatementNotInLoop: An empty statement (or a semicolon by itself) that is not used as the sole body of a ‘for’ or ‘wh…
    • +
    • EmptySwitchStatements: Empty switch statements serve no purpose and should be removed.
    • +
    • EmptySynchronizedBlock: Empty synchronized blocks serve no purpose and should be removed.
    • +
    • EmptyTryBlock: Avoid empty try blocks - what’s the point?
    • +
    • EmptyWhileStmt: Empty While Statement finds all instances where a while statement does nothing. If it is a timing…
    • +
    • EqualsNull: Tests for null should not use the equals() method. The ‘==’ operator should be used instead.
    • +
    • FinalizeDoesNotCallSuperFinalize: If the finalize() is implemented, its last action should be to call super.finalize. Note that Ora…
    • +
    • FinalizeOnlyCallsSuperFinalize: If the finalize() is implemented, it should do something besides just calling super.finalize(). N…
    • +
    • FinalizeOverloaded: Methods named finalize() should not have parameters. It is confusing and most likely an attempt …
    • +
    • FinalizeShouldBeProtected: When overriding the finalize(), the new method should be set as protected. If made public, other…
    • +
    • IdempotentOperations: Avoid idempotent operations - they have no effect.
    • +
    • ImportFromSamePackage: There is no need to import a type that lives in the same package.
    • +
    • InstantiationToGetClass: Avoid instantiating an object just to call getClass() on it; use the .class public member instead.
    • +
    • InvalidLogMessageFormat: Check for messages in slf4j and log4j2 (since 6.19.0) loggers with non matching number of argumen…
    • +
    • InvalidSlf4jMessageFormat: Deprecated The rule has been renamed. Use instead InvalidLogMessageFormat.
    • +
    • JumbledIncrementer: Avoid jumbled loop incrementers - its usually a mistake, and is confusing even if intentional.
    • +
    • JUnitSpelling: In JUnit 3, the setUp method is used to set up all data entities required in running tests. …
    • +
    • JUnitStaticSuite: The suite() method in a JUnit test needs to be both public and static.
    • +
    • LoggerIsNotStaticFinal: Deprecated In most cases, the Logger reference can be declared as static and final. This rule is deprecated …
    • +
    • MethodWithSameNameAsEnclosingClass: Non-constructor methods should not have the same name as the enclosing class.
    • +
    • MisplacedNullCheck: The null check here is misplaced. If the variable is null a NullPointerException will be thrown. …
    • +
    • MissingBreakInSwitch: Switch statements without break or return statements for each case option may indicate problemati…
    • +
    • MissingSerialVersionUID: Serializable classes should provide a serialVersionUID field. The serialVersionUID field is also …
    • +
    • MissingStaticMethodInNonInstantiatableClass: A class that has private constructors and does not have any static methods or fields cannot be us…
    • +
    • MoreThanOneLogger: Normally only one logger is used in each class. This rule supports slf4j, log4j, Java Util Loggin…
    • +
    • NonCaseLabelInSwitchStatement: A non-case label (e.g. a named break/continue label) was present in a switch statement. This lega…
    • +
    • NonStaticInitializer: A non-static initializer block will be called any time a constructor is invoked (just prior to in…
    • +
    • NullAssignment: Assigning a "null" to a variable (outside of its declaration) is usually bad form. Sometimes, th…
    • +
    • OverrideBothEqualsAndHashcode: Override both public boolean Object.equals(Object other), and public int Object.hashCode(), or ov…
    • +
    • ProperCloneImplementation: Object clone() should be implemented with super.clone().
    • +
    • ProperLogger: A logger should normally be defined private static final and be associated with the correct class…
    • +
    • ReturnEmptyArrayRatherThanNull: For any method that returns an array, it is a better to return an empty array rather than a null …
    • +
    • ReturnFromFinallyBlock: Avoid returning from a finally block, this can discard exceptions.
    • +
    • SimpleDateFormatNeedsLocale: Be sure to specify a Locale when creating SimpleDateFormat instances to ensure that locale-approp…
    • +
    • SingleMethodSingleton: Some classes contain overloaded getInstance. The problem with overloaded getInstance methods is t…
    • +
    • SingletonClassReturningNewInstance: Some classes contain overloaded getInstance. The problem with overloaded getInstance methods is t…
    • +
    • StaticEJBFieldShouldBeFinal: According to the J2EE specification, an EJB should not have any static fields with write access. …
    • +
    • StringBufferInstantiationWithChar: Individual character values provided as initialization arguments will be converted into integers….
    • +
    • SuspiciousEqualsMethodName: The method name and parameter number are suspiciously close to ‘Object.equals’, which can denote …
    • +
    • SuspiciousHashcodeMethodName: The method name and return type are suspiciously close to hashCode(), which may denote an intenti…
    • +
    • SuspiciousOctalEscape: A suspicious octal escape sequence was found inside a String literal. The Java language specifica…
    • +
    • TestClassWithoutTestCases: Test classes end with the suffix Test. Having a non-test class with that name is not a good pract…
    • +
    • UnconditionalIfStatement: Do not use "if" statements whose conditionals are always true or always false.
    • +
    • UnnecessaryBooleanAssertion: A JUnit test assertion with a boolean literal is unnecessary since it always will evaluate to the…
    • +
    • UnnecessaryCaseChange: Using equalsIgnoreCase() is faster than using toUpperCase/toLowerCase().equals()
    • +
    • UnnecessaryConversionTemporary: Avoid the use temporary objects when converting primitives to Strings. Use the static conversion …
    • +
    • UnusedNullCheckInEquals: After checking an object reference for null, you should invoke equals() on that object rather tha…
    • +
    • UseCorrectExceptionLogging: To make sure the full stacktrace is printed out, use the logging statement with two arguments: a …
    • +
    • UseEqualsToCompareStrings: Using ‘==’ or ‘!=’ to compare strings only works if intern version is used on both sides. Use the…
    • +
    • UselessOperationOnImmutable: An operation on an Immutable object (String, BigDecimal or BigInteger) won’t change the object it…
    • +
    • UseLocaleWithCaseConversions: When doing ‘String::toLowerCase()/toUpperCase()’ conversions, use an explicit locale argument to …
    • +
    • UseProperClassLoader: In J2EE, the getClassLoader() method might not work as expected. Use Thread.currentThread().getCo…
    • +
    + +

    Multithreading

    + +
    Rules that flag issues when dealing with multiple threads of execution.
    + +
      +
    • AvoidSynchronizedAtMethodLevel: Method-level synchronization can cause problems when new code is added to the method. Block-level…
    • +
    • AvoidThreadGroup: Avoid using java.lang.ThreadGroup; although it is intended to be used in a threaded environment i…
    • +
    • AvoidUsingVolatile: Use of the keyword ‘volatile’ is generally used to fine tune a Java application, and therefore, r…
    • +
    • DoNotUseThreads: The J2EE specification explicitly forbids the use of threads. Threads are resources, that should …
    • +
    • DontCallThreadRun: Explicitly calling Thread.run() method will execute in the caller’s thread of control. Instead, …
    • +
    • DoubleCheckedLocking: Partially created objects can be returned by the Double Checked Locking pattern when used in Java…
    • +
    • NonThreadSafeSingleton: Non-thread safe singletons can result in bad state changes. Eliminate static singletons if possib…
    • +
    • UnsynchronizedStaticDateFormatter: Deprecated SimpleDateFormat instances are not synchronized. Sun recommends using separate format instances f…
    • +
    • UnsynchronizedStaticFormatter: Instances of ‘java.text.Format’ are generally not synchronized. Sun recommends using separate for…
    • +
    • UseConcurrentHashMap: Since Java5 brought a new implementation of the Map designed for multi-threaded access, you can p…
    • +
    • UseNotifyAllInsteadOfNotify: Thread.notify() awakens a thread monitoring the object. If more than one thread is monitoring, th…
    • +
    + +

    Performance

    + +
    Rules that flag suboptimal code.
    + +
      +
    • AddEmptyString: The conversion of literals to strings by concatenating them with empty strings is inefficient. It…
    • +
    • AppendCharacterWithChar: Avoid concatenating characters as strings in StringBuffer/StringBuilder.append methods.
    • +
    • AvoidArrayLoops: Instead of manually copying data between two arrays, use the efficient Arrays.copyOf or System.ar…
    • +
    • AvoidCalendarDateCreation: Problem: A Calendar is a heavyweight object and expensive to create. Solution: Use ‘new Date()’, …
    • +
    • AvoidFileStream: The FileInputStream and FileOutputStream classes contains a finalizer method which will cause gar…
    • +
    • AvoidInstantiatingObjectsInLoops: New objects created within loops should be checked to see if they can created outside them and re…
    • +
    • AvoidUsingShortType: Java uses the ‘short’ type to reduce memory usage, not to optimize calculation. In fact, the JVM …
    • +
    • BigIntegerInstantiation: Don’t create instances of already existing BigInteger (BigInteger.ZERO, BigInteger.ONE) and for J…
    • +
    • BooleanInstantiation: Avoid instantiating Boolean objects; you can reference Boolean.TRUE, Boolean.FALSE, or call Boole…
    • +
    • ByteInstantiation: Calling new Byte() causes memory allocation that can be avoided by the static Byte.valueOf(). It …
    • +
    • ConsecutiveAppendsShouldReuse: Consecutive calls to StringBuffer/StringBuilder .append should be chained, reusing the target obj…
    • +
    • ConsecutiveLiteralAppends: Consecutively calling StringBuffer/StringBuilder.append(…) with literals should be avoided. Sin…
    • +
    • InefficientEmptyStringCheck: String.trim().length() == 0 (or String.trim().isEmpty() for the same reason) is an inefficient wa…
    • +
    • InefficientStringBuffering: Avoid concatenating non-literals in a StringBuffer constructor or append() since intermediate buf…
    • +
    • InsufficientStringBufferDeclaration: Failing to pre-size a StringBuffer or StringBuilder properly could cause it to re-size many times…
    • +
    • IntegerInstantiation: Calling new Integer() causes memory allocation that can be avoided by the static Integer.valueOf(…
    • +
    • LongInstantiation: Calling new Long() causes memory allocation that can be avoided by the static Long.valueOf(). It …
    • +
    • OptimizableToArrayCall: Calls to a collection’s ‘toArray(E[])’ method should specify a target array of zero size. This al…
    • +
    • RedundantFieldInitializer: Java will initialize fields with known default values so any explicit initialization of those sam…
    • +
    • ShortInstantiation: Calling new Short() causes memory allocation that can be avoided by the static Short.valueOf(). I…
    • +
    • SimplifyStartsWith: Calls to ‘string.startsWith("x")’ with a string literal of length 1 can be rewritten using ‘strin…
    • +
    • StringInstantiation: Avoid instantiating String objects; this is usually unnecessary since they are immutable and can …
    • +
    • StringToString: Avoid calling toString() on objects already known to be string instances; this is unnecessary.
    • +
    • TooFewBranchesForASwitchStatement: Switch statements are intended to be used to support complex branching behaviour. Using a switch …
    • +
    • UnnecessaryWrapperObjectCreation: Most wrapper classes provide static conversion methods that avoid the need to create intermediate…
    • +
    • UseArrayListInsteadOfVector: ArrayList is a much better Collection implementation than Vector if thread-safe operation is not …
    • +
    • UseArraysAsList: The java.util.Arrays class has a "asList" method that should be used when you want to create a ne…
    • +
    • UseIndexOfChar: Use String.indexOf(char) when checking for the index of a single character; it executes faster.
    • +
    • UseIOStreamsWithApacheCommonsFileItem: Problem: Use of [FileItem.get()](https://commons.apache.org/proper/commons-fileupload/apidocs/org…
    • +
    • UselessStringValueOf: No need to call String.valueOf to append to a string; just use the valueOf() argument directly.
    • +
    • UseStringBufferForStringAppends: The use of the ‘+=’ operator for appending strings causes the JVM to create and use an internal S…
    • +
    • UseStringBufferLength: Use StringBuffer.length() to determine StringBuffer length rather than using StringBuffer.toStrin…
    • +
    + +

    Security

    + +
    Rules that flag potential security flaws.
    + +
      +
    • HardCodedCryptoKey: Do not use hard coded values for cryptographic operations. Please store keys outside of source code.
    • +
    • InsecureCryptoIv: Do not use hard coded initialization vector in cryptographic operations. Please use a randomly ge…
    • +
    + +

    Additional rulesets

    + + + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_java_bestpractices.html b/pmd_rules_java_bestpractices.html new file mode 100644 index 0000000000..254c85fa78 --- /dev/null +++ b/pmd_rules_java_bestpractices.html @@ -0,0 +1,3731 @@ + + + + + + + + +Best Practices | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Best Practices

    +
    + + + +
    + + +
    Rules which enforce generally accepted best practices.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AbstractClassWithoutAbstractMethod

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    The abstract class does not contain any abstract methods. An abstract class suggests +an incomplete implementation, which is to be completed by subclasses implementing the +abstract methods. If the class is intended to be used as a base class only (not to be instantiated +directly) a protected constructor can be provided prevent direct instantiation.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.AbstractClassWithoutAbstractMethodRule

    + +

    Example(s):

    + +
    public abstract class Foo {
    +  void int method1() { ... }
    +  void int method2() { ... }
    +  // consider using abstract methods or removing
    +  // the abstract modifier and adding protected constructors
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AbstractClassWithoutAbstractMethod" />
    +
    + +

    AccessorClassGeneration

    + +

    Since: PMD 1.04

    + +

    Priority: Medium (3)

    + +

    Instantiation by way of private constructors from outside of the constructor’s class often causes the +generation of an accessor. A factory method, or non-privatization of the constructor can eliminate this +situation. The generated class file is actually an interface. It gives the accessing class the ability +to invoke a new hidden package scope constructor that takes the interface as a supplementary parameter. +This turns a private constructor effectively into one with package scope, and is challenging to discern.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.AccessorClassGenerationRule

    + +

    Example(s):

    + +
    public class Outer {
    + void method(){
    +  Inner ic = new Inner();//Causes generation of accessor class
    + }
    + public class Inner {
    +  private Inner(){}
    + }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AccessorClassGeneration" />
    +
    + +

    AccessorMethodGeneration

    + +

    Since: PMD 5.5.4

    + +

    Priority: Medium (3)

    + +

    When accessing a private field / method from another class, the Java compiler will generate a accessor methods +with package-private visibility. This adds overhead, and to the dex method count on Android. This situation can +be avoided by changing the visibility of the field / method from private to package-private.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.AccessorMethodGenerationRule

    + +

    Example(s):

    + +
    public class OuterClass {
    +    private int counter;
    +    /* package */ int id;
    +
    +    public class InnerClass {
    +        InnerClass() {
    +            OuterClass.this.counter++; // wrong accessor method will be generated
    +        }
    +
    +        public int getOuterClassId() {
    +            return OuterClass.this.id; // id is package-private, no accessor method needed
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AccessorMethodGeneration" />
    +
    + +

    ArrayIsStoredDirectly

    + +

    Since: PMD 2.2

    + +

    Priority: Medium (3)

    + +

    Constructors and methods receiving arrays should clone objects and store the copy. +This prevents future changes from the user from affecting the original array.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.ArrayIsStoredDirectlyRule

    + +

    Example(s):

    + +
    public class Foo {
    +    private String [] x;
    +        public void foo (String [] param) {
    +        // Don't do this, make a copy of the array at least
    +        this.x=param;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    allowPrivatetrueIf true, allow private methods/constructors to store arrays directlyno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/ArrayIsStoredDirectly" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/ArrayIsStoredDirectly">
    +    <properties>
    +        <property name="allowPrivate" value="true" />
    +    </properties>
    +</rule>
    +
    + +

    AvoidMessageDigestField

    + +

    Since: PMD 6.18.0

    + +

    Priority: Medium (3)

    + +

    Declaring a MessageDigest instance as a field make this instance directly available to multiple threads. +Such sharing of MessageDigest instances should be avoided if possible since it leads to wrong results +if the access is not synchronized correctly. +Just create a new instance and use it locally, where you need it. +Creating a new instance is easier than synchronizing access to a shared instance.

    + +

    This rule is defined by the following XPath expression:

    +
    //FieldDeclaration[pmd-java:typeIs('java.security.MessageDigest')]
    +
    + +

    Example(s):

    + +
    import java.security.MessageDigest;
    +public class AvoidMessageDigestFieldExample {
    +    private final MessageDigest sharedMd;
    +    public AvoidMessageDigestFieldExample() throws Exception {
    +        sharedMd = MessageDigest.getInstance("SHA-256");
    +    }
    +    public byte[] calculateHashShared(byte[] data) {
    +        // sharing a MessageDigest like this without synchronizing access
    +        // might lead to wrong results
    +        sharedMd.reset();
    +        sharedMd.update(data);
    +        return sharedMd.digest();
    +    }
    +
    +    // better
    +    public byte[] calculateHash(byte[] data) throws Exception {
    +        MessageDigest md = MessageDigest.getInstance("SHA-256");
    +        md.update(data);
    +        return md.digest();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AvoidMessageDigestField" />
    +
    + +

    AvoidPrintStackTrace

    + +

    Since: PMD 3.2

    + +

    Priority: Medium (3)

    + +

    Avoid printStackTrace(); use a logger call instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryExpression[
    +   ( PrimaryPrefix[Name[contains(@Image,'printStackTrace')]]
    +   | PrimarySuffix[@Image='printStackTrace']
    +   )/following-sibling::*[1][self::PrimarySuffix/Arguments[@Size=0]]
    +]
    +
    + +

    Example(s):

    + +
    class Foo {
    +    void bar() {
    +        try {
    +            // do something
    +        } catch (Exception e) {
    +            e.printStackTrace();
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AvoidPrintStackTrace" />
    +
    + +

    AvoidReassigningCatchVariables

    + +

    Since: PMD 6.27.0

    + +

    Priority: Medium (3)

    + +

    Reassigning exception variables caught in a catch statement should be avoided because of:

    + +

    1) If it is needed, multi catch can be easily added and code will still compile.

    + +

    2) Following the principle of least surprise we want to make sure that a variable caught in a catch statement +is always the one thrown in a try block.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.AvoidReassigningCatchVariablesRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void foo() {
    +        try {
    +            // do something
    +        } catch (Exception e) {
    +            e = new NullPointerException(); // not recommended
    +        }
    +
    +        try {
    +            // do something
    +        } catch (MyException | ServerException e) {
    +            e = new RuntimeException(); // won't compile
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AvoidReassigningCatchVariables" />
    +
    + +

    AvoidReassigningLoopVariables

    + +

    Since: PMD 6.11.0

    + +

    Priority: Medium (3)

    + +

    Reassigning loop variables can lead to hard-to-find bugs. Prevent or limit how these variables can be changed.

    + +

    In foreach-loops, configured by the foreachReassign property:

    +
      +
    • deny: Report any reassignment of the loop variable in the loop body. This is the default.
    • +
    • allow: Don’t check the loop variable.
    • +
    • firstOnly: Report any reassignments of the loop variable, except as the first statement in the loop body. + This is useful if some kind of normalization or clean-up of the value before using is permitted, but any other change of the variable is not.
    • +
    + +

    In for-loops, configured by the forReassign property:

    +
      +
    • deny: Report any reassignment of the control variable in the loop body. This is the default.
    • +
    • allow: Don’t check the control variable.
    • +
    • skip: Report any reassignments of the control variable, except conditional increments/decrements (++, --, +=, -=). + This prevents accidental reassignments or unconditional increments of the control variable.
    • +
    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.AvoidReassigningLoopVariablesRule

    + +

    Example(s):

    + +
    public class Foo {
    +  private void foo() {
    +    for (String s : listOfStrings()) {
    +      s = s.trim(); // OK, when foreachReassign is "firstOnly" or "allow"
    +      doSomethingWith(s);
    +
    +      s = s.toUpper(); // OK, when foreachReassign is "allow"
    +      doSomethingElseWith(s);
    +    }
    +
    +    for (int i=0; i < 10; i++) {
    +      if (check(i)) {
    +        i++; // OK, when forReassign is "skip" or "allow"
    +      }
    +
    +      i = 5;  // OK, when forReassign is "allow"
    +
    +      doSomethingWith(i);
    +    }
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    foreachReassigndenyhow/if foreach control variables may be reassignedno
    forReassigndenyhow/if for control variables may be reassignedno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AvoidReassigningLoopVariables" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/AvoidReassigningLoopVariables">
    +    <properties>
    +        <property name="foreachReassign" value="deny" />
    +        <property name="forReassign" value="deny" />
    +    </properties>
    +</rule>
    +
    + +

    AvoidReassigningParameters

    + +

    Since: PMD 1.0

    + +

    Priority: Medium High (2)

    + +

    Reassigning values to incoming parameters is not recommended. Use temporary local variables instead.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.AvoidReassigningParametersRule

    + +

    Example(s):

    + +
    public class Foo {
    +  private void foo(String bar) {
    +    bar = "something else";
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AvoidReassigningParameters" />
    +
    + +

    AvoidStringBufferField

    + +

    Since: PMD 4.2

    + +

    Priority: Medium (3)

    + +

    StringBuffers/StringBuilders can grow considerably, and so may become a source of memory leaks +if held within objects with long lifetimes.

    + +

    This rule is defined by the following XPath expression:

    +
    //FieldDeclaration/Type/ReferenceType/ClassOrInterfaceType[@Image = 'StringBuffer' or @Image = 'StringBuilder']
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    private StringBuffer buffer;    // potential memory leak as an instance variable;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AvoidStringBufferField" />
    +
    + +

    AvoidUsingHardCodedIP

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    Application with hard-coded IP addresses can become impossible to deploy in some cases. +Externalizing IP adresses is preferable.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.AvoidUsingHardCodedIPRule

    + +

    Example(s):

    + +
    public class Foo {
    +    private String ip = "127.0.0.1";     // not recommended
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    checkAddressTypesIPv4 mapped IPv6 | IPv6 | IPv4Check for IP address types.yes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/AvoidUsingHardCodedIP" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/AvoidUsingHardCodedIP">
    +    <properties>
    +        <property name="checkAddressTypes" value="IPv4 mapped IPv6|IPv6|IPv4" />
    +    </properties>
    +</rule>
    +
    + +

    CheckResultSet

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    Always check the return values of navigation methods (next, previous, first, last) of a ResultSet. +If the value return is ‘false’, it should be handled properly.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.CheckResultSetRule

    + +

    Example(s):

    + +
    Statement stat = conn.createStatement();
    +ResultSet rst = stat.executeQuery("SELECT name FROM person");
    +rst.next();     // what if it returns false? bad form
    +String firstName = rst.getString(1);
    +
    +Statement stat = conn.createStatement();
    +ResultSet rst = stat.executeQuery("SELECT name FROM person");
    +if (rst.next()) {    // result is properly examined and used
    +    String firstName = rst.getString(1);
    +    } else  {
    +        // handle missing data
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/CheckResultSet" />
    +
    + +

    ConstantsInInterface

    + +

    Since: PMD 5.5

    + +

    Priority: Medium (3)

    + +

    Avoid constants in interfaces. Interfaces should define types, constants are implementation details +better placed in classes or enums. See Effective Java, item 19.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[@Interface= true()][$ignoreIfHasMethods= false() or not(.//MethodDeclaration)]//FieldDeclaration
    +
    + +

    Example(s):

    + +
    public interface ConstantInterface {
    +    public static final int CONST1 = 1; // violation, no fields allowed in interface!
    +    static final int CONST2 = 1;        // violation, no fields allowed in interface!
    +    final int CONST3 = 1;               // violation, no fields allowed in interface!
    +    int CONST4 = 1;                     // violation, no fields allowed in interface!
    +}
    +
    +// with ignoreIfHasMethods = false
    +public interface AnotherConstantInterface {
    +    public static final int CONST1 = 1; // violation, no fields allowed in interface!
    +
    +    int anyMethod();
    +}
    +
    +// with ignoreIfHasMethods = true
    +public interface YetAnotherConstantInterface {
    +    public static final int CONST1 = 1; // no violation
    +
    +    int anyMethod();
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoreIfHasMethodstrueWhether to ignore constants in interfaces if the interface defines any methodsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/ConstantsInInterface" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/ConstantsInInterface">
    +    <properties>
    +        <property name="ignoreIfHasMethods" value="true" />
    +    </properties>
    +</rule>
    +
    + +

    DefaultLabelNotLastInSwitchStmt

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    By convention, the default label should be the last label in a switch statement.

    + +

    This rule is defined by the following XPath expression:

    +
    //SwitchStatement
    + [not(SwitchLabel[position() = last()][@Default= true()])]
    + [SwitchLabel[@Default= true()]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +  void bar(int a) {
    +   switch (a) {
    +    case 1:  // do something
    +       break;
    +    default:  // the default case should be last, by convention
    +       break;
    +    case 2:
    +       break;
    +   }
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/DefaultLabelNotLastInSwitchStmt" />
    +
    + +

    DoubleBraceInitialization

    + +

    Since: PMD 6.16.0

    + +

    Priority: Medium (3)

    + +

    Double brace initialisation is a pattern to initialise eg collections concisely. But it implicitly +generates a new .class file, and the object holds a strong reference to the enclosing object. For those +reasons, it is preferable to initialize the object normally, even though it’s verbose.

    + +

    This rule counts any anonymous class which only has a single initializer as an instance of double-brace +initialization. There is currently no way to find out whether a method called in the initializer is not +accessible from outside the anonymous class, and those legit cases should be suppressed for the time being.

    + +

    This rule is defined by the following XPath expression:

    +
    //AllocationExpression/ClassOrInterfaceBody[count(*)=1]/*/Initializer[@Static=false()]
    +
    + +

    Example(s):

    + +
    // this is double-brace initialization
    +return new ArrayList<String>(){{
    +    add("a");
    +    add("b");
    +    add("c");
    +}};
    +
    +// the better way is to not create an anonymous class:
    +List<String> a = new ArrayList<>();
    +a.add("a");
    +a.add("b");
    +a.add("c");
    +return a;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/DoubleBraceInitialization" />
    +
    + +

    ForLoopCanBeForeach

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.5

    + +

    Reports loops that can be safely replaced with the foreach syntax. The rule considers loops over +lists, arrays and iterators. A loop is safe to replace if it only uses the index variable to +access an element of the list or array, only has one update statement, and loops through every +element of the list or array left to right.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.ForLoopCanBeForeachRule

    + +

    Example(s):

    + +
    public class MyClass {
    +  void loop(List<String> l) {
    +    for (int i = 0; i < l.size(); i++) { // pre Java 1.5
    +      System.out.println(l.get(i));
    +    }
    +
    +    for (String s : l) {        // post Java 1.5
    +      System.out.println(s);
    +    }
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/ForLoopCanBeForeach" />
    +
    + +

    ForLoopVariableCount

    + +

    Since: PMD 6.11.0

    + +

    Priority: Medium (3)

    + +

    Having a lot of control variables in a ‘for’ loop makes it harder to see what range of values +the loop iterates over. By default this rule allows a regular ‘for’ loop with only one variable.

    + +

    This rule is defined by the following XPath expression:

    +
    //ForInit/LocalVariableDeclaration[count(VariableDeclarator) > $maximumVariables]
    +
    + +

    Example(s):

    + +
    // this will be reported with the default setting of at most one control variable in a for loop
    +for (int i = 0, j = 0; i < 10; i++, j += 2) {
    +   foo();
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maximumVariables1A regular for statement will have 1 control variableno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/ForLoopVariableCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/ForLoopVariableCount">
    +    <properties>
    +        <property name="maximumVariables" value="1" />
    +    </properties>
    +</rule>
    +
    + +

    GuardLogStatement

    + +

    Since: PMD 5.1.0

    + +

    Priority: Medium High (2)

    + +

    Whenever using a log level, one should check if the loglevel is actually enabled, or +otherwise skip the associate String creation and manipulation.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.GuardLogStatementRule

    + +

    Example(s):

    + +
    // Add this for performance
    +    if (log.isDebugEnabled() { ...
    +        log.debug("log something" + " and " + "concat strings");
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    logLevelstrace , debug , info , warn , error , log , finest , finer , fine , info , warning , severeLogLevels to guardyes. Delimiter is ‘,’.
    guardsMethodsisTraceEnabled , isDebugEnabled , isInfoEnabled , isWarnEnabled , isErrorEnabled , isLoggableMethod use to guard the log statementyes. Delimiter is ‘,’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/GuardLogStatement" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/GuardLogStatement">
    +    <properties>
    +        <property name="logLevels" value="trace,debug,info,warn,error,log,finest,finer,fine,info,warning,severe" />
    +        <property name="guardsMethods" value="isTraceEnabled,isDebugEnabled,isInfoEnabled,isWarnEnabled,isErrorEnabled,isLoggable" />
    +    </properties>
    +</rule>
    +
    + +

    JUnit4SuitesShouldUseSuiteAnnotation

    + +

    Since: PMD 4.0

    + +

    Priority: Medium (3)

    + +

    In JUnit 3, test suites are indicated by the suite() method. In JUnit 4, suites are indicated +through the @RunWith(Suite.class) annotation.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceBodyDeclaration
    +[MethodDeclaration[@Name='suite']/ResultType/Type/ReferenceType/ClassOrInterfaceType[pmd-java:typeIs('junit.framework.Test')]]
    +[not(MethodDeclaration/Block/BlockStatement/Statement/ReturnStatement//ClassOrInterfaceType[pmd-java:typeIs('junit.framework.JUnit4TestAdapter')])]
    +
    + +

    Example(s):

    + +
    public class BadExample extends TestCase{
    +
    +    public static Test suite(){
    +        return new Suite();
    +    }
    +}
    +
    +@RunWith(Suite.class)
    +@SuiteClasses( { TestOne.class, TestTwo.class })
    +public class GoodTest {
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/JUnit4SuitesShouldUseSuiteAnnotation" />
    +
    + +

    JUnit4TestShouldUseAfterAnnotation

    + +

    Since: PMD 4.0

    + +

    Priority: Medium (3)

    + +

    In JUnit 3, the tearDown method was used to clean up all data entities required in running tests. +JUnit 4 skips the tearDown method and executes all methods annotated with @After after running each test. +JUnit 5 introduced @AfterEach and @AfterAll annotations to execute methods after each test or after all tests in the class, respectively.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceBodyDeclaration
    +    [MethodDeclaration[@Name='tearDown']]
    +    [not(Annotation/*/Name[
    +           pmd-java:typeIs('org.junit.After')
    +        or pmd-java:typeIs('org.junit.jupiter.api.AfterEach')
    +        or pmd-java:typeIs('org.junit.jupiter.api.AfterAll')
    +        or pmd-java:typeIs('org.testng.annotations.AfterMethod')])]
    +
    + +

    Example(s):

    + +
    public class MyTest {
    +    public void tearDown() {
    +        bad();
    +    }
    +}
    +public class MyTest2 {
    +    @After public void tearDown() {
    +        good();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/JUnit4TestShouldUseAfterAnnotation" />
    +
    + +

    JUnit4TestShouldUseBeforeAnnotation

    + +

    Since: PMD 4.0

    + +

    Priority: Medium (3)

    + +

    In JUnit 3, the setUp method was used to set up all data entities required in running tests. +JUnit 4 skips the setUp method and executes all methods annotated with @Before before all tests. +JUnit 5 introduced @BeforeEach and @BeforeAll annotations to execute methods before each test or before all tests in the class, respectively.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceBodyDeclaration
    +    [MethodDeclaration[@Name='setUp']]
    +    [not(Annotation/*/Name[
    +           pmd-java:typeIs('org.junit.Before')
    +        or pmd-java:typeIs('org.junit.jupiter.api.BeforeEach')
    +        or pmd-java:typeIs('org.junit.jupiter.api.BeforeAll')
    +        or pmd-java:typeIs('org.testng.annotations.BeforeMethod')])]
    +
    + +

    Example(s):

    + +
    public class MyTest {
    +    public void setUp() {
    +        bad();
    +    }
    +}
    +public class MyTest2 {
    +    @Before public void setUp() {
    +        good();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/JUnit4TestShouldUseBeforeAnnotation" />
    +
    + +

    JUnit4TestShouldUseTestAnnotation

    + +

    Since: PMD 4.0

    + +

    Priority: Medium (3)

    + +

    In JUnit 3, the framework executed all methods which started with the word test as a unit test. +In JUnit 4, only methods annotated with the @Test annotation are executed. +In JUnit 5, one of the following annotations should be used for tests: @Test, @RepeatedTest, @TestFactory, @TestTemplate or @ParameterizedTest.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[
    +       matches(@SimpleName, $testClassPattern)
    +        or ExtendsList/ClassOrInterfaceType[pmd-java:typeIs('junit.framework.TestCase')]]
    +
    +    /ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration[MethodDeclaration[@Public=true() and starts-with(@Name, 'test')]]
    +    [not(Annotation//Name[
    +        pmd-java:typeIs('org.junit.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.Test') or pmd-java:typeIs('org.junit.jupiter.api.RepeatedTest')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestFactory') or pmd-java:typeIs('org.junit.jupiter.api.TestTemplate')
    +        or pmd-java:typeIs('org.junit.jupiter.params.ParameterizedTest')
    +    ])]
    +
    + +

    Example(s):

    + +
    public class MyTest {
    +    public void testBad() {
    +        doSomething();
    +    }
    +
    +    @Test
    +    public void testGood() {
    +        doSomething();
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    testClassPatternTestThe regex pattern used to identify test classesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/JUnit4TestShouldUseTestAnnotation" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/JUnit4TestShouldUseTestAnnotation">
    +    <properties>
    +        <property name="testClassPattern" value="Test" />
    +    </properties>
    +</rule>
    +
    + +

    JUnitAssertionsShouldIncludeMessage

    + +

    Since: PMD 1.04

    + +

    Priority: Medium (3)

    + +

    JUnit assertions should include an informative message - i.e., use the three-argument version of +assertEquals(), not the two-argument version.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.JUnitAssertionsShouldIncludeMessageRule

    + +

    Example(s):

    + +
    public class Foo extends TestCase {
    +    public void testSomething() {
    +        assertEquals("foo", "bar");
    +        // Use the form:
    +        // assertEquals("Foo does not equals bar", "foo", "bar");
    +        // instead
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/JUnitAssertionsShouldIncludeMessage" />
    +
    + +

    JUnitTestContainsTooManyAsserts

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Unit tests should not contain too many asserts. Many asserts are indicative of a complex test, for which +it is harder to verify correctness. Consider breaking the test scenario into multiple, shorter test scenarios. +Customize the maximum number of assertions used by this Rule to suit your needs.

    + +

    This rule checks for JUnit4, JUnit5 and TestNG Tests, as well as methods starting with "test".

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Name[matches(.,'^test')] or ../Annotation/MarkerAnnotation/Name[
    +           pmd-java:typeIs('org.junit.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.RepeatedTest')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestFactory')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestTemplate')
    +        or pmd-java:typeIs('org.junit.jupiter.params.ParameterizedTest')
    +        or pmd-java:typeIs('org.testng.annotations.Test')
    +    ]]
    +    [count(.//PrimaryPrefix/Name[@Image[matches(.,'^assert')]]) > $maximumAsserts]
    +
    + +

    Example(s):

    + +
    public class MyTestCase extends TestCase {
    +    // Ok
    +    public void testMyCaseWithOneAssert() {
    +        boolean myVar = false;
    +        assertFalse("should be false", myVar);
    +    }
    +
    +    // Bad, too many asserts (assuming max=1)
    +    public void testMyCaseWithMoreAsserts() {
    +        boolean myVar = false;
    +        assertFalse("myVar should be false", myVar);
    +        assertEquals("should equals false", false, myVar);
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maximumAsserts1Maximum number of Asserts in a test methodno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/JUnitTestContainsTooManyAsserts" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/JUnitTestContainsTooManyAsserts">
    +    <properties>
    +        <property name="maximumAsserts" value="1" />
    +    </properties>
    +</rule>
    +
    + +

    JUnitTestsShouldIncludeAssert

    + +

    Since: PMD 2.0

    + +

    Priority: Medium (3)

    + +

    JUnit tests should include at least one assertion. This makes the tests more robust, and using assert +with messages provide the developer a clearer idea of what the test does.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.JUnitTestsShouldIncludeAssertRule

    + +

    Example(s):

    + +
    public class Foo extends TestCase {
    +   public void testSomething() {
    +      Bar b = findBar();
    +   // This is better than having a NullPointerException
    +   // assertNotNull("bar not found", b);
    +   b.work();
    +   }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/JUnitTestsShouldIncludeAssert" />
    +
    + +

    JUnitUseExpected

    + +

    Since: PMD 4.0

    + +

    Priority: Medium (3)

    + +

    In JUnit4, use the @Test(expected) annotation to denote tests that should throw exceptions.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.JUnitUseExpectedRule

    + +

    Example(s):

    + +
    public class MyTest {
    +    @Test
    +    public void testBad() {
    +        try {
    +            doSomething();
    +            fail("should have thrown an exception");
    +        } catch (Exception e) {
    +        }
    +    }
    +
    +    @Test(expected=Exception.class)
    +    public void testGood() {
    +        doSomething();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/JUnitUseExpected" />
    +
    + +

    LiteralsFirstInComparisons

    + +

    Since: PMD 6.24.0

    + +

    Priority: Medium (3)

    + +

    Position literals first in all String comparisons, if the second argument is null then NullPointerExceptions +can be avoided, they will just return false. Note that switching literal positions for compareTo and +compareToIgnoreCase may change the result, see examples.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.LiteralsFirstInComparisonsRule

    + +

    Example(s):

    + +
    class Foo {
    +    boolean bar(String x) {
    +        return x.equals("2"); // should be "2".equals(x)
    +    }
    +    boolean bar(String x) {
    +        return x.equalsIgnoreCase("2"); // should be "2".equalsIgnoreCase(x)
    +    }
    +    boolean bar(String x) {
    +        return (x.compareTo("bar") > 0); // should be: "bar".compareTo(x) < 0
    +    }
    +    boolean bar(String x) {
    +        return (x.compareToIgnoreCase("bar") > 0); // should be: "bar".compareToIgnoreCase(x) < 0
    +    }
    +    boolean bar(String x) {
    +        return x.contentEquals("bar"); // should be "bar".contentEquals(x)
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/LiteralsFirstInComparisons" />
    +
    + +

    LooseCoupling

    + +

    Since: PMD 0.7

    + +

    Priority: Medium (3)

    + +

    The use of implementation types (i.e., HashSet) as object references limits your ability to use alternate +implementations in the future as requirements change. Whenever available, referencing objects +by their interface types (i.e, Set) provides much more flexibility.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.LooseCouplingRule

    + +

    Example(s):

    + +
    import java.util.ArrayList;
    +import java.util.HashSet;
    +
    +public class Bar {
    +    // sub-optimal approach
    +    private ArrayList<SomeType> list = new ArrayList<>();
    +
    +    public HashSet<SomeType> getFoo() {
    +        return new HashSet<SomeType>();
    +    }
    +
    +    // preferred approach
    +    private List<SomeType> list = new ArrayList<>();
    +
    +    public Set<SomeType> getFoo() {
    +        return new HashSet<SomeType>();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/LooseCoupling" />
    +
    + +

    MethodReturnsInternalArray

    + +

    Since: PMD 2.2

    + +

    Priority: Medium (3)

    + +

    Exposing internal arrays to the caller violates object encapsulation since elements can be +removed or replaced outside of the object that owns it. It is safer to return a copy of the array.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.MethodReturnsInternalArrayRule

    + +

    Example(s):

    + +
    public class SecureSystem {
    +    UserData [] ud;
    +    public UserData [] getUserData() {
    +        // Don't return directly the internal array, return a copy
    +        return ud;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/MethodReturnsInternalArray" />
    +
    + +

    MissingOverride

    + +

    Since: PMD 6.2.0

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.5

    + +

    Annotating overridden methods with @Override ensures at compile time that +the method really overrides one, which helps refactoring and clarifies intent.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.MissingOverrideRule

    + +

    Example(s):

    + +
    public class Foo implements Runnable {
    +                // This method is overridden, and should have an @Override annotation
    +                public void run() {
    +
    +                }
    +            }
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/MissingOverride" />
    +
    + +

    OneDeclarationPerLine

    + +

    Since: PMD 5.0

    + +

    Priority: Medium Low (4)

    + +

    Java allows the use of several variables declaration of the same type on one line. However, it +can lead to quite messy code. This rule looks for several declarations on the same line.

    + +

    This rule is defined by the following XPath expression:

    +
    //LocalVariableDeclaration
    +   [not(parent::ForInit)]
    +   [count(VariableDeclarator) > 1]
    +   [$strictMode or count(distinct-values(VariableDeclarator/@BeginLine)) != count(VariableDeclarator)]
    +|
    +//FieldDeclaration
    +   [count(VariableDeclarator) > 1]
    +   [$strictMode or count(distinct-values(VariableDeclarator/@BeginLine)) != count(VariableDeclarator)]
    +
    + +

    Example(s):

    + +
    String name;            // separate declarations
    +String lastname;
    +
    +String name, lastname;  // combined declaration, a violation
    +
    +String name,
    +       lastname;        // combined declaration on multiple lines, no violation by default.
    +                        // Set property strictMode to true to mark this as violation.
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    strictModefalseIf true, mark combined declaration even if the declarations are on separate lines.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/OneDeclarationPerLine" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/OneDeclarationPerLine">
    +    <properties>
    +        <property name="strictMode" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    PositionLiteralsFirstInCaseInsensitiveComparisons

    + +

    Deprecated

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Position literals first in comparisons, if the second argument is null then NullPointerExceptions +can be avoided, they will just return false.

    + +

    This rule is replaced by the more general rule LiteralsFirstInComparisons.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.PositionLiteralsFirstInCaseInsensitiveComparisonsRule

    + +

    Example(s):

    + +
    class Foo {
    +  boolean bar(String x) {
    +    return x.equalsIgnoreCase("2"); // should be "2".equalsIgnoreCase(x)
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/PositionLiteralsFirstInCaseInsensitiveComparisons" />
    +
    + +

    PositionLiteralsFirstInComparisons

    + +

    Deprecated

    + +

    Since: PMD 3.3

    + +

    Priority: Medium (3)

    + +

    Position literals first in comparisons, if the second argument is null then NullPointerExceptions +can be avoided, they will just return false.

    + +

    This rule is replaced by the more general rule LiteralsFirstInComparisons.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.PositionLiteralsFirstInComparisonsRule

    + +

    Example(s):

    + +
    class Foo {
    +  boolean bar(String x) {
    +    return x.equals("2"); // should be "2".equals(x)
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/PositionLiteralsFirstInComparisons" />
    +
    + +

    PreserveStackTrace

    + +

    Since: PMD 3.7

    + +

    Priority: Medium (3)

    + +

    Throwing a new exception from a catch block without passing the original exception into the +new exception will cause the original stack trace to be lost making it difficult to debug +effectively.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.PreserveStackTraceRule

    + +

    Example(s):

    + +
    public class Foo {
    +    void good() {
    +        try{
    +            Integer.parseInt("a");
    +        } catch (Exception e) {
    +            throw new Exception(e); // first possibility to create exception chain
    +        }
    +        try {
    +            Integer.parseInt("a");
    +        } catch (Exception e) {
    +            throw (IllegalStateException)new IllegalStateException().initCause(e); // second possibility to create exception chain.
    +        }
    +    }
    +    void bad() {
    +        try{
    +            Integer.parseInt("a");
    +        } catch (Exception e) {
    +            throw new Exception(e.getMessage());
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/PreserveStackTrace" />
    +
    + +

    ReplaceEnumerationWithIterator

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Consider replacing Enumeration usages with the newer java.util.Iterator

    + +

    This rule is defined by the following XPath expression:

    +
    //ImplementsList/ClassOrInterfaceType[@Image='Enumeration']
    +
    + +

    Example(s):

    + +
    public class Foo implements Enumeration {
    +    private int x = 42;
    +    public boolean hasMoreElements() {
    +        return true;
    +    }
    +    public Object nextElement() {
    +        return String.valueOf(i++);
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/ReplaceEnumerationWithIterator" />
    +
    + +

    ReplaceHashtableWithMap

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Consider replacing Hashtable usage with the newer java.util.Map if thread safety is not required.

    + +

    This rule is defined by the following XPath expression:

    +
    //Type/ReferenceType/ClassOrInterfaceType[@Image='Hashtable']
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    void bar() {
    +        Hashtable h = new Hashtable();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/ReplaceHashtableWithMap" />
    +
    + +

    ReplaceVectorWithList

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Consider replacing Vector usages with the newer java.util.ArrayList if expensive thread-safe operations are not required.

    + +

    This rule is defined by the following XPath expression:

    +
    //Type/ReferenceType/ClassOrInterfaceType[@Image='Vector']
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    void bar() {
    +        Vector v = new Vector();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/ReplaceVectorWithList" />
    +
    + +

    SwitchStmtsShouldHaveDefault

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    All switch statements should include a default option to catch any unspecified values.

    + +

    This rule is defined by the following XPath expression:

    +
    //SwitchStatement[@DefaultCase = false() and @ExhaustiveEnumSwitch = false()]
    +
    + +

    Example(s):

    + +
    public void bar() {
    +    int x = 2;
    +    switch (x) {
    +      case 1: int j = 6;
    +      case 2: int j = 8;
    +          // missing default: here
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/SwitchStmtsShouldHaveDefault" />
    +
    + +

    SystemPrintln

    + +

    Since: PMD 2.1

    + +

    Priority: Medium High (2)

    + +

    References to System.(out|err).print are usually intended for debugging purposes and can remain in +the codebase even in production code. By using a logger one can enable/disable this behaviour at +will (and by priority) and avoid clogging the Standard out log.

    + +

    This rule is defined by the following XPath expression:

    +
    //Name[
    +    starts-with(@Image, 'System.out.print')
    +    or
    +    starts-with(@Image, 'System.err.print')
    +    ]
    +
    + +

    Example(s):

    + +
    class Foo{
    +    Logger log = Logger.getLogger(Foo.class.getName());
    +    public void testA () {
    +        System.out.println("Entering test");
    +        // Better use this
    +        log.fine("Entering test");
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/SystemPrintln" />
    +
    + +

    UnusedAssignment

    + +

    Since: PMD 6.26.0

    + +

    Priority: Medium (3)

    + +

    Reports assignments to variables that are never used before the variable is overwritten, +or goes out of scope. Unused assignments are those for which

    +
      +
    1. The variable is never read after the assignment, or
    2. +
    3. The assigned value is always overwritten by other assignments before the next read of +the variable.
    4. +
    + +

    The rule doesn’t consider assignments to fields except for those of this in a constructor, +or static fields of the current class in static initializers.

    + +

    The rule may be suppressed with the standard @SuppressWarnings("unused") tag.

    + +

    The rule subsumes UnusedLocalVariable, and UnusedFormalParameter. +Those violations are filtered +out by default, in case you already have enabled those rules, but may be enabled with the property +reportUnusedVariables. Variables whose name starts with ignored are filtered out, as +is standard practice for exceptions.

    + +

    Limitations:

    +
      +
    • The rule currently cannot know which method calls throw exceptions, or which exceptions they throw. +In the body of a try block, every method or constructor call is assumed to throw. This may cause false-negatives. +The only other language construct that is assumed to throw is the throw statement, in particular, +things like assert statements, or NullPointerExceptions on dereference are ignored.
    • +
    • The rule cannot resolve assignments across constructors, when they’re called with the special +this(...) syntax. This may cause false-negatives.
    • +
    + +

    Both of those limitations may be partly relaxed in PMD 7.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.UnusedAssignmentRule

    + +

    Example(s):

    + +
    class A {
    +                // this field initializer is redundant,
    +                // it is always overwritten in the constructor
    +                int f = 1;
    +
    +                A(int f) {
    +                    this.f = f;
    +                }
    +            }
    +
    + +
    class B {
    +
    +    int method(int i, int j) {
    +        // this initializer is redundant,
    +        // it is overwritten in all branches of the `if`
    +        int k = 0;
    +
    +        // Both the assignments to k are unused, because k is
    +        // not read after the if/else
    +        // This may hide a bug: the programmer probably wanted to return k
    +        if (i < j)
    +            k = i;
    +        else
    +            k = j;
    +
    +        return j;
    +    }
    +
    +}
    +
    + +
    class C {
    +
    +    int method() {
    +        int i = 0;
    +
    +        checkSomething(++i);
    +        checkSomething(++i);
    +        checkSomething(++i);
    +        checkSomething(++i);
    +
    +        // That last increment is not reported unless
    +        // the property `checkUnusedPrefixIncrement` is
    +        // set to `true`
    +        // Technically it could be written (i+1), but it
    +        // is not very important
    +    }
    +
    +}
    +
    + +
    class C {
    +
    +    // variables that are truly unused (at most assigned to, but never accessed)
    +    // are only reported if property `reportUnusedVariables` is true
    +
    +    void method(int param) { } // for example this method parameter
    +
    +    // even then, you can suppress the violation with an annotation:
    +
    +    void method(@SuppressWarning("unused") int param) { } // no violation, even if `reportUnusedVariables` is true
    +
    +    // For catch parameters, or for resources which don't need to be used explicitly,
    +    // you can give a name that starts with "ignored" to ignore such warnings
    +
    +    {
    +        try (Something ignored = Something.create()) {
    +            // even if ignored is unused, it won't be flagged
    +            // its purpose might be to side-effect in the create/close routines
    +
    +        } catch (Exception e) { // this is unused and will cause a warning if `reportUnusedVariables` is true
    +            // you should choose a name that starts with "ignored"
    +            return;
    +        }
    +    }
    +
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    checkUnusedPrefixIncrementfalseReport expressions like ++i that may be replaced with (i + 1)no
    reportUnusedVariablesfalseReport variables that are only initialized, and never read at all. The rule UnusedVariable already cares for that, but you can enable it if neededno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedAssignment" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedAssignment">
    +    <properties>
    +        <property name="checkUnusedPrefixIncrement" value="false" />
    +        <property name="reportUnusedVariables" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    UnusedFormalParameter

    + +

    Since: PMD 0.8

    + +

    Priority: Medium (3)

    + +

    Avoid passing parameters to methods or constructors without actually referencing them in the method body. +Removing unused formal parameters from public methods could cause a ripple effect through the code base. +Hence, by default, this rule only considers private methods. To include non-private methods, set the +checkAll property to true.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.UnusedFormalParameterRule

    + +

    Example(s):

    + +
    public class Foo {
    +    private void bar(String howdy) {
    +        // howdy is not used
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    checkAllfalseCheck all methods, including non-private onesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedFormalParameter" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedFormalParameter">
    +    <properties>
    +        <property name="checkAll" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    UnusedImports

    + +

    Since: PMD 1.0

    + +

    Priority: Medium Low (4)

    + +

    Avoid unused import statements to prevent unwanted dependencies. +This rule will also find unused on demand imports, i.e. import com.foo.*.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.UnusedImportsRule

    + +

    Example(s):

    + +
    import java.io.File;  // not referenced or required
    +import java.util.*;   // not referenced or required
    +
    +public class Foo {}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedImports" />
    +
    + +

    UnusedLocalVariable

    + +

    Since: PMD 0.1

    + +

    Priority: Medium (3)

    + +

    Detects when a local variable is declared and/or assigned, but not used.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.UnusedLocalVariableRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void doSomething() {
    +        int i = 5; // Unused
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedLocalVariable" />
    +
    + +

    UnusedPrivateField

    + +

    Since: PMD 0.1

    + +

    Priority: Medium (3)

    + +

    Detects when a private field is declared and/or assigned a value, but not used.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.UnusedPrivateFieldRule

    + +

    Example(s):

    + +
    public class Something {
    +    private static int FOO = 2; // Unused
    +    private int i = 5; // Unused
    +    private int j = 6;
    +    public int addOne() {
    +        return j++;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationslombok.Setter | lombok.Getter | lombok.Builder | lombok.Data | lombok.RequiredArgsConstructor | lombok.AllArgsConstructor | lombok.Value | lombok.NoArgsConstructor | java.lang.Deprecated | javafx.fxml.FXML | lombok.experimental.Delegate | lombok.EqualsAndHashCodeFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedPrivateField" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedPrivateField">
    +    <properties>
    +        <property name="ignoredAnnotations" value="lombok.Setter|lombok.Getter|lombok.Builder|lombok.Data|lombok.RequiredArgsConstructor|lombok.AllArgsConstructor|lombok.Value|lombok.NoArgsConstructor|java.lang.Deprecated|javafx.fxml.FXML|lombok.experimental.Delegate|lombok.EqualsAndHashCode" />
    +    </properties>
    +</rule>
    +
    + +

    UnusedPrivateMethod

    + +

    Since: PMD 0.7

    + +

    Priority: Medium (3)

    + +

    Unused Private Method detects when a private method is declared but is unused.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.UnusedPrivateMethodRule

    + +

    Example(s):

    + +
    public class Something {
    +    private void foo() {} // unused
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationsjava.lang.DeprecatedFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedPrivateMethod" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/UnusedPrivateMethod">
    +    <properties>
    +        <property name="ignoredAnnotations" value="java.lang.Deprecated" />
    +    </properties>
    +</rule>
    +
    + +

    UseAssertEqualsInsteadOfAssertTrue

    + +

    Since: PMD 3.1

    + +

    Priority: Medium (3)

    + +

    This rule detects JUnit assertions in object equality. These assertions should be made by more specific methods, like assertEquals.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[
    +    pmd-java:typeIs('junit.framework.TestCase')
    +    or .//MarkerAnnotation/Name[
    +        pmd-java:typeIs('org.junit.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.RepeatedTest')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestFactory')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestTemplate')
    +        or pmd-java:typeIs('org.junit.jupiter.params.ParameterizedTest')
    +        ]
    +    ]
    +//PrimaryExpression[
    +    PrimaryPrefix/Name[@Image = 'assertTrue']
    +][
    +    PrimarySuffix/Arguments/ArgumentList/Expression/PrimaryExpression/PrimaryPrefix/Name
    +        [ends-with(@Image, '.equals')]
    +]
    +
    + +

    Example(s):

    + +
    public class FooTest extends TestCase {
    +    void testCode() {
    +        Object a, b;
    +        assertTrue(a.equals(b));                    // bad usage
    +        assertEquals("a should equals b", a, b);    // good usage
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UseAssertEqualsInsteadOfAssertTrue" />
    +
    + +

    UseAssertNullInsteadOfAssertTrue

    + +

    Since: PMD 3.5

    + +

    Priority: Medium (3)

    + +

    This rule detects JUnit assertions in object references equality. These assertions should be made by +more specific methods, like assertNull, assertNotNull.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[
    +    pmd-java:typeIs('junit.framework.TestCase')
    +    or .//MarkerAnnotation/Name[
    +        pmd-java:typeIs('org.junit.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.RepeatedTest')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestFactory')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestTemplate')
    +        or pmd-java:typeIs('org.junit.jupiter.params.ParameterizedTest')
    +        ]
    +    ]
    +//PrimaryExpression[
    +    PrimaryPrefix/Name[@Image = 'assertTrue' or @Image = 'assertFalse']
    +][
    +    PrimarySuffix/Arguments/ArgumentList[
    +        Expression/EqualityExpression/PrimaryExpression/PrimaryPrefix/Literal/NullLiteral
    +    ]
    +]
    +
    + +

    Example(s):

    + +
    public class FooTest extends TestCase {
    +    void testCode() {
    +        Object a = doSomething();
    +        assertTrue(a==null);    // bad usage
    +        assertNull(a);          // good usage
    +        assertTrue(a != null);  // bad usage
    +        assertNotNull(a);       // good usage
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UseAssertNullInsteadOfAssertTrue" />
    +
    + +

    UseAssertSameInsteadOfAssertTrue

    + +

    Since: PMD 3.1

    + +

    Priority: Medium (3)

    + +

    This rule detects JUnit assertions in object references equality. These assertions should be made +by more specific methods, like assertSame, assertNotSame.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[
    +    pmd-java:typeIs('junit.framework.TestCase')
    +    or .//MarkerAnnotation/Name[
    +        pmd-java:typeIs('org.junit.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.RepeatedTest')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestFactory')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestTemplate')
    +        or pmd-java:typeIs('org.junit.jupiter.params.ParameterizedTest')
    +        ]
    +    ]
    +//PrimaryExpression[
    +    PrimaryPrefix/Name[@Image = 'assertTrue' or @Image = 'assertFalse']
    +]
    +[
    +    PrimarySuffix/Arguments/ArgumentList/Expression/EqualityExpression
    +        [not(.//NullLiteral)]
    +]
    +
    + +

    Example(s):

    + +
    public class FooTest extends TestCase {
    +    void testCode() {
    +        Object a, b;
    +        assertTrue(a == b); // bad usage
    +        assertSame(a, b);   // good usage
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UseAssertSameInsteadOfAssertTrue" />
    +
    + +

    UseAssertTrueInsteadOfAssertEquals

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    When asserting a value is the same as a literal or Boxed boolean, use assertTrue/assertFalse, instead of assertEquals.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryExpression[PrimaryPrefix/Name[@Image = 'assertEquals']]
    +[
    +  PrimarySuffix/Arguments/ArgumentList/Expression/PrimaryExpression/PrimaryPrefix/Literal/BooleanLiteral
    +  or
    +  PrimarySuffix/Arguments/ArgumentList/Expression/PrimaryExpression/PrimaryPrefix
    +  /Name[(@Image = 'Boolean.TRUE' or @Image = 'Boolean.FALSE')]
    +]
    +
    + +

    Example(s):

    + +
    public class MyTestCase extends TestCase {
    +    public void testMyCase() {
    +        boolean myVar = true;
    +        // Ok
    +        assertTrue("myVar is true", myVar);
    +        // Bad
    +        assertEquals("myVar is true", true, myVar);
    +        // Bad
    +        assertEquals("myVar is false", false, myVar);
    +        // Bad
    +        assertEquals("myVar is true", Boolean.TRUE, myVar);
    +        // Bad
    +        assertEquals("myVar is false", Boolean.FALSE, myVar);
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UseAssertTrueInsteadOfAssertEquals" />
    +
    + +

    UseCollectionIsEmpty

    + +

    Since: PMD 3.9

    + +

    Priority: Medium (3)

    + +

    The isEmpty() method on java.util.Collection is provided to determine if a collection has any elements. +Comparing the value of size() to 0 does not convey intent as well as the isEmpty() method.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.bestpractices.UseCollectionIsEmptyRule

    + +

    Example(s):

    + +
    public class Foo {
    +    void good() {
    +        List foo = getList();
    +        if (foo.isEmpty()) {
    +            // blah
    +        }
    +    }
    +
    +    void bad() {
    +        List foo = getList();
    +        if (foo.size() == 0) {
    +            // blah
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UseCollectionIsEmpty" />
    +
    + +

    UseTryWithResources

    + +

    Since: PMD 6.12.0

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.7

    + +

    Java 7 introduced the try-with-resources statement. This statement ensures that each resource is closed at the end +of the statement. It avoids the need of explicitly closing the resources in a finally block. Additionally exceptions +are better handled: If an exception occurred both in the try block and finally block, then the exception from +the try block was suppressed. With the try-with-resources statement, the exception thrown from the try-block is +preserved.

    + +

    This rule is defined by the following XPath expression:

    +
    //TryStatement[FinallyStatement//Name[
    +    tokenize(@Image, '\.')[last()] = $closeMethods
    +][
    +    pmd-java:typeIs('java.lang.AutoCloseable')
    +    or
    +    ../../PrimarySuffix/Arguments//PrimaryPrefix[pmd-java:typeIs('java.lang.AutoCloseable')]
    +]]
    +
    + +

    Example(s):

    + +
    public class TryWithResources {
    +    public void run() {
    +        InputStream in = null;
    +        try {
    +            in = openInputStream();
    +            int i = in.read();
    +        } catch (IOException e) {
    +            e.printStackTrace();
    +        } finally {
    +            try {
    +                if (in != null) in.close();
    +            } catch (IOException ignored) {
    +                // ignored
    +            }
    +        }
    +
    +        // better use try-with-resources
    +        try (InputStream in2 = openInputStream()) {
    +            int i = in2.read();
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    closeMethodsclose , closeQuietlyMethod names in finally block, which trigger this ruleyes. Delimiter is ‘,’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UseTryWithResources" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/bestpractices.xml/UseTryWithResources">
    +    <properties>
    +        <property name="closeMethods" value="close,closeQuietly" />
    +    </properties>
    +</rule>
    +
    + +

    UseVarargs

    + +

    Since: PMD 5.0

    + +

    Priority: Medium Low (4)

    + +

    Minimum Language Version: Java 1.5

    + +

    Java 5 introduced the varargs parameter declaration for methods and constructors. This syntactic +sugar provides flexibility for users of these methods and constructors, allowing them to avoid +having to deal with the creation of an array.

    + +

    This rule is defined by the following XPath expression:

    +
    //FormalParameters/FormalParameter
    +    [position()=last()]
    +    [VariableDeclaratorId/@ArrayType=true()]
    +    [@Varargs=false()]
    +    [not (./Type[@ArrayType=true()]/ReferenceType[PrimitiveType[@Image='byte']])]
    +    [not (./Type/ReferenceType[ClassOrInterfaceType[@Image='Byte']])]
    +    [not (./Type/PrimitiveType[@Image='byte'])]
    +    [not (ancestor::MethodDeclaration/preceding-sibling::Annotation/*/Name[@Image='Override'])]
    +    [not(
    +         ancestor::MethodDeclaration
    +            [    @Public=true()
    +             and @Static=true()
    +             and child::ResultType[@Void=true()]
    +             and @Name = 'main'
    +             and @Arity = 1
    +            ]
    +         (: Type of the formal parameter here. :)
    +         and pmd-java:typeIs('java.lang.String[]')
    +    )]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public void foo(String s, Object[] args) {
    +        // Do something here...
    +    }
    +
    +    public void bar(String s, Object... args) {
    +        // Ahh, varargs tastes much better...
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/UseVarargs" />
    +
    + +

    WhileLoopWithLiteralBoolean

    + +

    Since: PMD 6.13.0

    + +

    Priority: Medium (3)

    + +

    do {} while (true); requires reading the end of the statement before it is +apparent that it loops forever, whereas while (true) {} is easier to understand.

    + +

    do {} while (false); is redundant, and if an inner variable scope is required, +a block {} is sufficient.

    + +

    while (false) {} will never execute the block and can be removed in its entirety.

    + +

    This rule is defined by the following XPath expression:

    +
    //DoStatement[Expression/PrimaryExpression/PrimaryPrefix/Literal/BooleanLiteral] |
    +//WhileStatement[Expression/PrimaryExpression/PrimaryPrefix/Literal/BooleanLiteral[@True = false()]]
    +
    + +

    Example(s):

    + +
    public class Example {
    +  {
    +    while (true) { } // allowed
    +    while (false) { } // disallowed
    +    do { } while (true); // disallowed
    +    do { } while (false); // disallowed
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/bestpractices.xml/WhileLoopWithLiteralBoolean" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_java_codestyle.html b/pmd_rules_java_codestyle.html new file mode 100644 index 0000000000..518ef0b415 --- /dev/null +++ b/pmd_rules_java_codestyle.html @@ -0,0 +1,4654 @@ + + + + + + + + +Code Style | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Code Style

    +
    + + + +
    + + +
    Rules which enforce a specific coding style.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AbstractNaming

    + +

    Deprecated

    + +

    Since: PMD 1.4

    + +

    Priority: Medium (3)

    + +

    Abstract classes should be named ‘AbstractXXX’.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by ClassNamingConventions.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration
    + [@Abstract= true() and @Interface= false()]
    + [not (starts-with(@SimpleName,'Abstract'))]
    +|
    +//ClassOrInterfaceDeclaration
    + [@Abstract= false()]
    + [$strict= true()]
    + [starts-with(@SimpleName, 'Abstract')]
    +
    + +

    Example(s):

    + +
    public abstract class Foo { // should be AbstractFoo
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    stricttrueAlso flag classes, that are named Abstract, but are not abstract.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/AbstractNaming" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/AbstractNaming">
    +    <properties>
    +        <property name="strict" value="true" />
    +    </properties>
    +</rule>
    +
    + +

    AtLeastOneConstructor

    + +

    Since: PMD 1.04

    + +

    Priority: Medium (3)

    + +

    Each non-static class should declare at least one constructor. +Classes with solely static members are ignored, refer to UseUtilityClassRule to detect those.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.AtLeastOneConstructorRule

    + +

    Example(s):

    + +
    public class Foo {
    +   // missing constructor
    +  public void doSomething() { ... }
    +  public void doOtherThing { ... }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationslombok.Data | lombok.Value | lombok.Builder | lombok.NoArgsConstructor | lombok.RequiredArgsConstructor | lombok.AllArgsConstructorFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/AtLeastOneConstructor" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/AtLeastOneConstructor">
    +    <properties>
    +        <property name="ignoredAnnotations" value="lombok.Data|lombok.Value|lombok.Builder|lombok.NoArgsConstructor|lombok.RequiredArgsConstructor|lombok.AllArgsConstructor" />
    +    </properties>
    +</rule>
    +
    + +

    AvoidDollarSigns

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    Avoid using dollar signs in variable/method/class/interface names.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.AvoidDollarSignsRule

    + +

    Example(s):

    + +
    public class Fo$o {  // not a recommended name
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/AvoidDollarSigns" />
    +
    + +

    AvoidFinalLocalVariable

    + +

    Deprecated

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    Avoid using final local variables, turn them into fields.

    + +

    Note that this is a controversial rule which is merely useful to enforce a certain code style +(which is contradictory to good coding practices in most of the cases it’s applied to) and +avoid local literals being declared in a scope smaller than the class.

    + +

    Also note, that this rule is the opposite of LocalVariableCouldBeFinal. +Having both rules enabled results in contradictory violations being reported.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. There is no replacement planned. +If the goal is to avoid defining constants in a scope smaller than the class, then the rule +AvoidDuplicateLiterals should be used instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //LocalVariableDeclaration[
    +  @Final = true()
    +  and not(../../ForStatement)
    +  and
    +  (
    +    (count(VariableDeclarator/VariableInitializer) = 0)
    +    or
    +    (VariableDeclarator/VariableInitializer/Expression/PrimaryExpression/PrimaryPrefix/Literal)
    +  )
    +]
    +
    + +

    Example(s):

    + +
    public class MyClass {
    +    public void foo() {
    +        final String finalLocalVariable;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/AvoidFinalLocalVariable" />
    +
    + +

    AvoidPrefixingMethodParameters

    + +

    Deprecated

    + +

    Since: PMD 5.0

    + +

    Priority: Medium Low (4)

    + +

    Prefixing parameters by ‘in’ or ‘out’ pollutes the name of the parameters and reduces code readability. +To indicate whether or not a parameter will be modify in a method, its better to document method +behavior with Javadoc.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the more general rule FormalParameterNamingConventions.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration/MethodDeclarator/FormalParameters/FormalParameter/VariableDeclaratorId[
    +        pmd:matches(@Name,'^in[A-Z].*','^out[A-Z].*','^in$','^out$')
    +]
    +
    + +

    Example(s):

    + +
    // Not really clear
    +public class Foo {
    +  public void bar(
    +      int inLeftOperand,
    +      Result outRightOperand) {
    +      outRightOperand.setValue(inLeftOperand * outRightOperand.getValue());
    +  }
    +}
    +
    + +
    // Far more useful
    +public class Foo {
    +  /**
    +   *
    +   * @param leftOperand, (purpose), not modified by method.
    +   * @param rightOperand (purpose), will be modified by the method: contains the result.
    +   */
    +  public void bar(
    +        int leftOperand,
    +        Result rightOperand) {
    +        rightOperand.setValue(leftOperand * rightOperand.getValue());
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/AvoidPrefixingMethodParameters" />
    +
    + +

    AvoidProtectedFieldInFinalClass

    + +

    Since: PMD 2.1

    + +

    Priority: Medium (3)

    + +

    Do not use protected fields in final classes since they cannot be subclassed. +Clarify your intent by using private or package access modifiers instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[@Final= true()]
    +/ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration
    +/FieldDeclaration[@Protected= true()]
    +
    + +

    Example(s):

    + +
    public final class Bar {
    +  private int x;
    +  protected int y;  // bar cannot be subclassed, so is y really private or package visible?
    +  Bar() {}
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/AvoidProtectedFieldInFinalClass" />
    +
    + +

    AvoidProtectedMethodInFinalClassNotExtending

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Do not use protected methods in most final classes since they cannot be subclassed. This should +only be allowed in final classes that extend other classes with protected methods (whose +visibility cannot be reduced). Clarify your intent by using private or package access modifiers instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[@Final= true() and not(ExtendsList)]
    +/ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration
    +/MethodDeclaration[@Protected=true() and @Name != 'finalize']
    +
    + +

    Example(s):

    + +
    public final class Foo {
    +  private int bar() {}
    +  protected int baz() {} // Foo cannot be subclassed, and doesn't extend anything, so is baz() really private or package visible?
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/AvoidProtectedMethodInFinalClassNotExtending" />
    +
    + +

    AvoidUsingNativeCode

    + +

    Since: PMD 4.1

    + +

    Priority: Medium High (2)

    + +

    Unnecessary reliance on Java Native Interface (JNI) calls directly reduces application portability +and increases the maintenance burden.

    + +

    This rule is defined by the following XPath expression:

    +
    //Name[starts-with(@Image,'System.loadLibrary')]
    +
    + +

    Example(s):

    + +
    public class SomeJNIClass {
    +
    +     public SomeJNIClass() {
    +         System.loadLibrary("nativelib");
    +     }
    +
    +     static {
    +         System.loadLibrary("nativelib");
    +     }
    +
    +     public void invalidCallsInMethod() throws SecurityException, NoSuchMethodException {
    +         System.loadLibrary("nativelib");
    +     }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/AvoidUsingNativeCode" />
    +
    + +

    BooleanGetMethodName

    + +

    Since: PMD 4.0

    + +

    Priority: Medium Low (4)

    + +

    Methods that return boolean results should be named as predicate statements to denote this. +I.e, ‘isReady()’, ‘hasValues()’, ‘canCommit()’, ‘willFail()’, etc. Avoid the use of the ‘get’ +prefix for these methods.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration
    +    [starts-with(@Name, 'get')]
    +    [@Arity = 0 or $checkParameterizedMethods = true()]
    +    [
    +        ResultType/Type/PrimitiveType[@Image = 'boolean']
    +        and not(../Annotation//Name[@Image = 'Override'])
    +    ]
    +
    + +

    Example(s):

    + +
    public boolean getFoo();            // bad
    +public boolean isFoo();             // ok
    +public boolean getFoo(boolean bar); // ok, unless checkParameterizedMethods=true
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    checkParameterizedMethodsfalseCheck parameterized methodsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/BooleanGetMethodName" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/BooleanGetMethodName">
    +    <properties>
    +        <property name="checkParameterizedMethods" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    CallSuperInConstructor

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    It is a good practice to call super() in a constructor. If super() is not called but +another constructor (such as an overloaded constructor) is called, this rule will not report it.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[ExtendsList/*]
    +/ClassOrInterfaceBody
    + /ClassOrInterfaceBodyDeclaration
    + /ConstructorDeclaration[ not(.//ExplicitConstructorInvocation) ]
    +
    + +

    Example(s):

    + +
    public class Foo extends Bar{
    +  public Foo() {
    +   // call the constructor of Bar
    +   super();
    +  }
    + public Foo(int code) {
    +  // do something with code
    +   this();
    +   // no problem with this
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/CallSuperInConstructor" />
    +
    + +

    ClassNamingConventions

    + +

    Since: PMD 1.2

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for type declarations. This rule reports +type declarations which do not match the regex that applies to their +specific kind (e.g. enum or interface). Each regex can be configured through +properties.

    + +

    By default this rule uses the standard Java naming convention (Pascal case), +and reports utility class names not ending with ‘Util’.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.ClassNamingConventionsRule

    + +

    Example(s):

    + +
    // This is Pascal case, the recommended naming convention in Java
    +// Note that the default values of this rule don't allow underscores
    +// or accented characters in type names
    +public class FooBar {}
    +
    +// You may want abstract classes to be named 'AbstractXXX',
    +// in which case you can customize the regex for abstract
    +// classes to 'Abstract[A-Z]\w+'
    +public abstract class Thing {}
    +
    +// This class doesn't respect the convention, and will be flagged
    +public class Éléphant {}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    classPattern[A-Z][a-zA-Z0-9]*Regex which applies to concrete class namesno
    abstractClassPattern[A-Z][a-zA-Z0-9]*Regex which applies to abstract class namesno
    interfacePattern[A-Z][a-zA-Z0-9]*Regex which applies to interface namesno
    enumPattern[A-Z][a-zA-Z0-9]*Regex which applies to enum namesno
    annotationPattern[A-Z][a-zA-Z0-9]*Regex which applies to annotation namesno
    utilityClassPattern[A-Z][a-zA-Z0-9]+(Utils?|Helper|Constants)Regex which applies to utility class namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/ClassNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/ClassNamingConventions">
    +    <properties>
    +        <property name="classPattern" value="[A-Z][a-zA-Z0-9]*" />
    +        <property name="abstractClassPattern" value="[A-Z][a-zA-Z0-9]*" />
    +        <property name="interfacePattern" value="[A-Z][a-zA-Z0-9]*" />
    +        <property name="enumPattern" value="[A-Z][a-zA-Z0-9]*" />
    +        <property name="annotationPattern" value="[A-Z][a-zA-Z0-9]*" />
    +        <property name="utilityClassPattern" value="[A-Z][a-zA-Z0-9]+(Utils?|Helper|Constants)" />
    +    </properties>
    +</rule>
    +
    + +

    CommentDefaultAccessModifier

    + +

    Since: PMD 5.4.0

    + +

    Priority: Medium (3)

    + +

    To avoid mistakes if we want that an Annotation, Class, Enum, Method, Constructor or Field have a default access modifier +we must add a comment at the beginning of it’s declaration. +By default the comment must be /* default */ or /* package */, if you want another, you have to provide a regular expression. +This rule ignores by default all cases that have a @VisibleForTesting annotation. Use the +property "ignoredAnnotations" to customize the recognized annotations.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.CommentDefaultAccessModifierRule

    + +

    Example(s):

    + +
    public class Foo {
    +    final String stringValue = "some string";
    +    String getString() {
    +       return stringValue;
    +    }
    +
    +    class NestedFoo {
    +    }
    +}
    +
    +// should be
    +public class Foo {
    +    /* default */ final String stringValue = "some string";
    +    /* default */ String getString() {
    +       return stringValue;
    +    }
    +
    +    /* default */ class NestedFoo {
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationscom.google.common.annotations.VisibleForTesting | android.support.annotation.VisibleForTestingFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    regex\/\*\s+(default|package)\s+\*\/Regular expressionno
    checkTopLevelTypesfalseCheck for default access modifier in top-level classes, annotations, and enumsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/CommentDefaultAccessModifier" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/CommentDefaultAccessModifier">
    +    <properties>
    +        <property name="ignoredAnnotations" value="com.google.common.annotations.VisibleForTesting|android.support.annotation.VisibleForTesting" />
    +        <property name="regex" value="\/\*\s+(default|package)\s+\*\/" />
    +        <property name="checkTopLevelTypes" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    ConfusingTernary

    + +

    Since: PMD 1.9

    + +

    Priority: Medium (3)

    + +

    Avoid negation within an "if" expression with an "else" clause. For example, rephrase: +if (x != y) diff(); else same(); as: if (x == y) same(); else diff();.

    + +

    Most "if (x != y)" cases without an "else" are often return cases, so consistent use of this +rule makes the code easier to read. Also, this resolves trivial ordering problems, such +as "does the error case go first?" or "does the common case go first?".

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.ConfusingTernaryRule

    + +

    Example(s):

    + +
    boolean bar(int x, int y) {
    +    return (x != y) ? diff : same;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoreElseIffalseIgnore conditions with an else-if caseno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/ConfusingTernary" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/ConfusingTernary">
    +    <properties>
    +        <property name="ignoreElseIf" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    ControlStatementBraces

    + +

    Since: PMD 6.2.0

    + +

    Priority: Medium (3)

    + +

    Enforce a policy for braces on control statements. It is recommended to use braces on ‘if … else’ +statements and loop statements, even if they are optional. This usually makes the code clearer, and +helps prepare the future when you need to add another statement. That said, this rule lets you control +which statements are required to have braces via properties.

    + +

    From 6.2.0 on, this rule supersedes WhileLoopMustUseBraces, ForLoopMustUseBraces, IfStmtMustUseBraces, +and IfElseStmtMustUseBraces.

    + +

    This rule is defined by the following XPath expression:

    +
    //WhileStatement[$checkWhileStmt and not(Statement/Block) and not($allowEmptyLoop and Statement/EmptyStatement)]
    +                |
    +                //ForStatement[$checkForStmt and not(Statement/Block) and not($allowEmptyLoop and Statement/EmptyStatement)]
    +                |
    +                //DoStatement[$checkDoWhileStmt and not(Statement/Block) and not($allowEmptyLoop and Statement/EmptyStatement)]
    +                |
    +                (: The violation is reported on the sub statement -- not the if statement :)
    +                //Statement[$checkIfElseStmt and parent::IfStatement and not(child::Block or child::IfStatement)
    +                            (: Whitelists single if statements :)
    +                            and ($checkSingleIfStmt
    +                                 (: Inside this not(...) is the definition of a "single if statement" :)
    +                                 or not(count(../Statement) = 1 (: No else stmt :)
    +                                        (: Not the last branch of an 'if ... else if' chain :)
    +                                        and not(parent::IfStatement[parent::Statement[parent::IfStatement]])))]
    +                |
    +                (: Reports case labels if one of their subordinate statements is not braced :)
    +                //SwitchLabel[$checkCaseStmt]
    +                             [count(following-sibling::BlockStatement except following-sibling::SwitchLabel[1]/following-sibling::BlockStatement) > 1
    +                              or (some $stmt (: in only the block statements until the next label :)
    +                                  in following-sibling::BlockStatement except following-sibling::SwitchLabel[1]/following-sibling::BlockStatement
    +                                  satisfies not($stmt/Statement/Block))]
    +
    + +

    Example(s):

    + +
    while (true)    // not recommended
    +  x++;
    +
    +while (true) {  // preferred approach
    +  x++;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    checkIfElseStmttrueRequire that ‘if … else’ statements use bracesno
    checkSingleIfStmttrueRequire that ‘if’ statements with a single branch use bracesno
    checkWhileStmttrueRequire that ‘while’ loops use bracesno
    checkForStmttrueRequire that ‘for’ loops should use bracesno
    checkDoWhileStmttrueRequire that ‘do … while’ loops use bracesno
    checkCaseStmtfalseRequire that cases of a switch have bracesno
    allowEmptyLoopfalseAllow loops with an empty statement, e.g. ‘while(true);’no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/ControlStatementBraces" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/ControlStatementBraces">
    +    <properties>
    +        <property name="checkIfElseStmt" value="true" />
    +        <property name="checkSingleIfStmt" value="true" />
    +        <property name="checkWhileStmt" value="true" />
    +        <property name="checkForStmt" value="true" />
    +        <property name="checkDoWhileStmt" value="true" />
    +        <property name="checkCaseStmt" value="false" />
    +        <property name="allowEmptyLoop" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    DefaultPackage

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Use explicit scoping instead of accidental usage of default package private level. +The rule allows methods and fields annotated with Guava’s @VisibleForTesting and JUnit 5’s annotations.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[@Interface= false()]
    +/ClassOrInterfaceBody
    +/ClassOrInterfaceBodyDeclaration
    +[not(Annotation//Name[
    +    pmd-java:typeIs('org.junit.jupiter.api.Test')
    +    or pmd-java:typeIs('org.junit.jupiter.api.RepeatedTest')
    +    or pmd-java:typeIs('org.junit.jupiter.api.ParameterizedTest')
    +    or pmd-java:typeIs('org.junit.jupiter.api.TestFactory')
    +    or pmd-java:typeIs('org.junit.jupiter.api.TestTemplate')
    +    or pmd-java:typeIs('org.junit.jupiter.api.BeforeAll')
    +    or pmd-java:typeIs('org.junit.jupiter.api.AfterAll')
    +    or pmd-java:typeIs('org.junit.jupiter.api.BeforeEach')
    +    or pmd-java:typeIs('org.junit.jupiter.api.AfterEach')
    +    or ends-with(@Image, 'VisibleForTesting')])]
    +[
    +FieldDeclaration[@PackagePrivate= true()]
    +or MethodDeclaration[@PackagePrivate= true()]
    +]
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/DefaultPackage" />
    +
    + +

    DontImportJavaLang

    + +

    Since: PMD 0.5

    + +

    Priority: Medium Low (4)

    + +

    Avoid importing anything from the package ‘java.lang’. These classes are automatically imported (JLS 7.5.3).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.DontImportJavaLangRule

    + +

    Example(s):

    + +
    import java.lang.String;    // this is unnecessary
    +
    +public class Foo {}
    +
    +// --- in another source code file...
    +
    +import java.lang.*;         // this is bad
    +
    +public class Foo {}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/DontImportJavaLang" />
    +
    + +

    DuplicateImports

    + +

    Since: PMD 0.5

    + +

    Priority: Medium Low (4)

    + +

    Duplicate or overlapping import statements should be avoided.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.DuplicateImportsRule

    + +

    Example(s):

    + +
    import java.lang.String;
    +import java.lang.*;
    +public class Foo {}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/DuplicateImports" />
    +
    + +

    EmptyMethodInAbstractClassShouldBeAbstract

    + +

    Since: PMD 4.1

    + +

    Priority: High (1)

    + +

    Empty or auto-generated methods in an abstract class should be tagged as abstract. This helps to remove their inapproprate +usage by developers who should be implementing their own versions in the concrete subclasses.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[@Abstract = true()]
    +    /ClassOrInterfaceBody
    +    /ClassOrInterfaceBodyDeclaration
    +    /MethodDeclaration[@Abstract = false() and @Native = false()]
    +    [
    +        ( boolean(./Block[count(./BlockStatement) =  1]/BlockStatement/Statement/ReturnStatement/Expression/PrimaryExpression/PrimaryPrefix/Literal/NullLiteral) = true() )
    +        or
    +        ( boolean(./Block[count(./BlockStatement) =  1]/BlockStatement/Statement/ReturnStatement/Expression/PrimaryExpression/PrimaryPrefix/Literal[@Image = '0']) = true() )
    +        or
    +        ( boolean(./Block[count(./BlockStatement) =  1]/BlockStatement/Statement/ReturnStatement/Expression/PrimaryExpression/PrimaryPrefix/Literal[string-length(@Image) = 2]) = true() )
    +        or
    +        (./Block[count(./BlockStatement) =  1]/BlockStatement/Statement/EmptyStatement)
    +        or
    +        ( not (./Block/*) )
    +    ]
    +
    + +

    Example(s):

    + +
    public abstract class ShouldBeAbstract {
    +    public Object couldBeAbstract() {
    +        // Should be abstract method ?
    +        return null;
    +    }
    +
    +    public void couldBeAbstract() {
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/EmptyMethodInAbstractClassShouldBeAbstract" />
    +
    + +

    ExtendsObject

    + +

    Since: PMD 5.0

    + +

    Priority: Medium Low (4)

    + +

    No need to explicitly extend Object.

    + +

    This rule is defined by the following XPath expression:

    +
    //ExtendsList/ClassOrInterfaceType[@Image='Object' or @Image='java.lang.Object']
    +
    + +

    Example(s):

    + +
    public class Foo extends Object {     // not required
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/ExtendsObject" />
    +
    + +

    FieldDeclarationsShouldBeAtStartOfClass

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Fields should be declared at the top of the class, before any method declarations, constructors, initializers or inner classes.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.FieldDeclarationsShouldBeAtStartOfClassRule

    + +

    Example(s):

    + +
    public class HelloWorldBean {
    +
    +  // Field declared before methods / inner classes - OK
    +  private String _thing;
    +
    +  public String getMessage() {
    +    return "Hello World!";
    +  }
    +
    +  // Field declared after methods / inner classes - avoid this
    +  private String _fieldInWrongLocation;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoreEnumDeclarationstrueIgnore Enum Declarations that precede fields.no
    ignoreAnonymousClassDeclarationstrueIgnore Field Declarations, that are initialized with anonymous class declarationsno
    ignoreInterfaceDeclarationsfalseIgnore Interface Declarations that precede fields.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/FieldDeclarationsShouldBeAtStartOfClass" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/FieldDeclarationsShouldBeAtStartOfClass">
    +    <properties>
    +        <property name="ignoreEnumDeclarations" value="true" />
    +        <property name="ignoreAnonymousClassDeclarations" value="true" />
    +        <property name="ignoreInterfaceDeclarations" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    FieldNamingConventions

    + +

    Since: PMD 6.7.0

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for field declarations. This rule reports variable declarations +which do not match the regex that applies to their specific kind —e.g. constants (static final), +enum constant, final field. Each regex can be configured through properties.

    + +

    By default this rule uses the standard Java naming convention (Camel case), and uses the ALL_UPPER +convention for constants and enum constants.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.FieldNamingConventionsRule

    + +

    Example(s):

    + +
    class Foo {
    +                int myField = 1; // This is in camel case, so it's ok
    +                int my_Field = 1; // This contains an underscore, it's not ok by default
    +                                  // but you may allow it, or even require the "my_" prefix
    +
    +                final int FinalField = 1; // you may configure a different convention for final fields,
    +                                          // e.g. here PascalCase: [A-Z][a-zA-Z0-9]*
    +
    +                interface Interface {
    +                    double PI = 3.14; // interface "fields" use the constantPattern property
    +                }
    +
    +                enum AnEnum {
    +                    ORG, NET, COM; // These use a separate property but are set to ALL_UPPER by default
    +                }
    +            }
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    publicConstantPattern[A-Z][A-Z_0-9]*Regex which applies to public constant namesno
    constantPattern[A-Z][A-Z_0-9]*Regex which applies to non-public static final field namesno
    enumConstantPattern[A-Z][A-Z_0-9]*Regex which applies to enum constant namesno
    finalFieldPattern[a-z][a-zA-Z0-9]*Regex which applies to final field namesno
    staticFieldPattern[a-z][a-zA-Z0-9]*Regex which applies to static field namesno
    defaultFieldPattern[a-z][a-zA-Z0-9]*Regex which applies to field namesno
    exclusionsserialVersionUID | serialPersistentFieldsNames of fields to whitelist.yes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/FieldNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/FieldNamingConventions">
    +    <properties>
    +        <property name="publicConstantPattern" value="[A-Z][A-Z_0-9]*" />
    +        <property name="constantPattern" value="[A-Z][A-Z_0-9]*" />
    +        <property name="enumConstantPattern" value="[A-Z][A-Z_0-9]*" />
    +        <property name="finalFieldPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="staticFieldPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="defaultFieldPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="exclusions" value="serialVersionUID|serialPersistentFields" />
    +    </properties>
    +</rule>
    +
    + +

    ForLoopShouldBeWhileLoop

    + +

    Since: PMD 1.02

    + +

    Priority: Medium (3)

    + +

    Some for loops can be simplified to while loops, this makes them more concise.

    + +

    This rule is defined by the following XPath expression:

    +
    //ForStatement
    +  [not(LocalVariableDeclaration)]
    +  [not(ForInit)]
    +  [not(ForUpdate)]
    +  [Expression]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    void bar() {
    +        for (;true;) true; // No Init or Update part, may as well be: while (true)
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/ForLoopShouldBeWhileLoop" />
    +
    + +

    ForLoopsMustUseBraces

    + +

    Deprecated

    + +

    Since: PMD 0.7

    + +

    Priority: Medium (3)

    + +

    Avoid using ‘for’ statements without using curly braces. If the code formatting or +indentation is lost then it becomes difficult to separate the code being controlled +from the rest.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the rule ControlStatementBraces.

    + +

    This rule is defined by the following XPath expression:

    +
    //ForStatement[not(Statement/Block)]
    +
    + +

    Example(s):

    + +
    for (int i = 0; i < 42; i++)
    +   foo();
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/ForLoopsMustUseBraces" />
    +
    + +

    FormalParameterNamingConventions

    + +

    Since: PMD 6.6.0

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for formal parameters of methods and lambdas. +This rule reports formal parameters which do not match the regex that applies to their +specific kind (e.g. lambda parameter, or final formal parameter). Each regex can be +configured through properties.

    + +

    By default this rule uses the standard Java naming convention (Camel case).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.FormalParameterNamingConventionsRule

    + +

    Example(s):

    + +
    class Foo {
    +
    +                abstract void bar(int myInt); // This is Camel case, so it's ok
    +
    +                void bar(int my_i) { // this will be reported
    +
    +                }
    +
    +                void lambdas() {
    +
    +                    // lambdas parameters can be configured separately
    +                    Consumer<String> lambda1 = s_str -> { };
    +
    +                    // lambda parameters with an explicit type can be configured separately
    +                    Consumer<String> lambda1 = (String str) -> { };
    +
    +                }
    +
    +            }
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    methodParameterPattern[a-z][a-zA-Z0-9]*Regex which applies to formal parameter namesno
    finalMethodParameterPattern[a-z][a-zA-Z0-9]*Regex which applies to final formal parameter namesno
    lambdaParameterPattern[a-z][a-zA-Z0-9]*Regex which applies to inferred-type lambda parameter namesno
    explicitLambdaParameterPattern[a-z][a-zA-Z0-9]*Regex which applies to explicitly-typed lambda parameter namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/FormalParameterNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/FormalParameterNamingConventions">
    +    <properties>
    +        <property name="methodParameterPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="finalMethodParameterPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="lambdaParameterPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="explicitLambdaParameterPattern" value="[a-z][a-zA-Z0-9]*" />
    +    </properties>
    +</rule>
    +
    + +

    GenericsNaming

    + +

    Since: PMD 4.2.6

    + +

    Priority: Medium Low (4)

    + +

    Names for references to generic values should be limited to a single uppercase letter.

    + +

    This rule is defined by the following XPath expression:

    +
    //TypeDeclaration/ClassOrInterfaceDeclaration/TypeParameters/TypeParameter[
    +  string-length(@Image) > 1
    +  or
    +  upper-case(@Image) != @Image
    +]
    +
    + +

    Example(s):

    + +
    public interface GenericDao<E extends BaseModel, K extends Serializable> extends BaseDao {
    +    // This is ok...
    +}
    +
    +public interface GenericDao<E extends BaseModel, K extends Serializable> {
    +    // Also this
    +}
    +
    +public interface GenericDao<e extends BaseModel, K extends Serializable> {
    +    // 'e' should be an 'E'
    +}
    +
    +public interface GenericDao<EF extends BaseModel, K extends Serializable> {
    +   // 'EF' is not ok.
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/GenericsNaming" />
    +
    + +

    IdenticalCatchBranches

    + +

    Since: PMD 6.4.0

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.7

    + +

    Identical catch branches use up vertical space and increase the complexity of code without +adding functionality. It’s better style to collapse identical branches into a single multi-catch +branch.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.IdenticalCatchBranchesRule

    + +

    Example(s):

    + +
    try {
    +    // do something
    +} catch (IllegalArgumentException e) {
    +    throw e;
    +} catch (IllegalStateException e) { // Can be collapsed into the previous block
    +    throw e;
    +}
    +
    +try {
    +    // do something
    +} catch (IllegalArgumentException | IllegalStateException e) { // This is better
    +    throw e;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/IdenticalCatchBranches" />
    +
    + +

    IfElseStmtsMustUseBraces

    + +

    Deprecated

    + +

    Since: PMD 0.2

    + +

    Priority: Medium (3)

    + +

    Avoid using if..else statements without using surrounding braces. If the code formatting +or indentation is lost then it becomes difficult to separate the code being controlled +from the rest.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the rule ControlStatementBraces.

    + +

    This rule is defined by the following XPath expression:

    +
    //Statement
    + [parent::IfStatement[@Else= true()]]
    + [not(child::Block)]
    + [not(child::IfStatement)]
    +
    + +

    Example(s):

    + +
    // this is OK
    +if (foo) x++;
    +
    +   // but this is not
    +if (foo)
    +       x = x+1;
    +   else
    +       x = x-1;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/IfElseStmtsMustUseBraces" />
    +
    + +

    IfStmtsMustUseBraces

    + +

    Deprecated

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    Avoid using if statements without using braces to surround the code block. If the code +formatting or indentation is lost then it becomes difficult to separate the code being +controlled from the rest.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the rule ControlStatementBraces.

    + +

    This rule is defined by the following XPath expression:

    +
    //IfStatement[count(*) < 3][not(Statement/Block)]
    +
    + +

    Example(s):

    + +
    if (foo)    // not recommended
    +    x++;
    +
    +if (foo) {  // preferred approach
    +    x++;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/IfStmtsMustUseBraces" />
    +
    + +

    LinguisticNaming

    + +

    Since: PMD 6.7.0

    + +

    Priority: Medium (3)

    + +

    This rule finds Linguistic Naming Antipatterns. It checks for fields, that are named, as if they should +be boolean but have a different type. It also checks for methods, that according to their name, should +return a boolean, but don’t. Further, it checks, that getters return something and setters won’t. +Finally, it checks that methods, that start with "to" - so called transform methods - actually return +something, since according to their name, they should convert or transform one object into another. +There is additionally an option, to check for methods that contain "To" in their name - which are +also transform methods. However, this is disabled by default, since this detection is prone to +false positives.

    + +

    For more information, see Linguistic Antipatterns - What They Are and How +Developers Perceive Them.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.LinguisticNamingRule

    + +

    Example(s):

    + +
    public class LinguisticNaming {
    +    int isValid;    // the field name indicates a boolean, but it is an int.
    +    boolean isTrue; // correct type of the field
    +
    +    void myMethod() {
    +        int hasMoneyLocal;      // the local variable name indicates a boolean, but it is an int.
    +        boolean hasSalaryLocal; // correct naming and type
    +    }
    +
    +    // the name of the method indicates, it is a boolean, but the method returns an int.
    +    int isValid() {
    +        return 1;
    +    }
    +    // correct naming and return type
    +    boolean isSmall() {
    +        return true;
    +    }
    +
    +    // the name indicates, this is a setter, but it returns something
    +    int setName() {
    +        return 1;
    +    }
    +
    +    // the name indicates, this is a getter, but it doesn't return anything
    +    void getName() {
    +        // nothing to return?
    +    }
    +
    +    // the name indicates, it transforms an object and should return the result
    +    void toDataType() {
    +        // nothing to return?
    +    }
    +    // the name indicates, it transforms an object and should return the result
    +    void grapeToWine() {
    +        // nothing to return?
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationsjava.lang.OverrideFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    checkBooleanMethodtrueCheck method names and types for inconsistent naming.no
    checkGetterstrueCheck return type of getters.no
    checkSetterstrueCheck return type of setters.no
    checkPrefixedTransformMethodstrueCheck return type of methods whose names start with the configured prefix (see transformMethodNames property).no
    checkTransformMethodsfalseCheck return type of methods which contain the configured infix in their name (see transformMethodNames property).no
    booleanMethodPrefixesis | has | can | have | will | shouldThe prefixes of methods that return boolean.yes. Delimiter is ‘|’.
    transformMethodNamesto | asThe prefixes and infixes that indicate a transform method.yes. Delimiter is ‘|’.
    checkFieldstrueCheck field names and types for inconsistent naming.no
    checkVariablestrueCheck local variable names and types for inconsistent naming.no
    booleanFieldPrefixesis | has | can | have | will | shouldThe prefixes of fields and variables that indicate boolean.yes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/LinguisticNaming" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/LinguisticNaming">
    +    <properties>
    +        <property name="ignoredAnnotations" value="java.lang.Override" />
    +        <property name="checkBooleanMethod" value="true" />
    +        <property name="checkGetters" value="true" />
    +        <property name="checkSetters" value="true" />
    +        <property name="checkPrefixedTransformMethods" value="true" />
    +        <property name="checkTransformMethods" value="false" />
    +        <property name="booleanMethodPrefixes" value="is|has|can|have|will|should" />
    +        <property name="transformMethodNames" value="to|as" />
    +        <property name="checkFields" value="true" />
    +        <property name="checkVariables" value="true" />
    +        <property name="booleanFieldPrefixes" value="is|has|can|have|will|should" />
    +    </properties>
    +</rule>
    +
    + +

    LocalHomeNamingConvention

    + +

    Since: PMD 4.0

    + +

    Priority: Medium Low (4)

    + +

    The Local Home interface of a Session EJB should be suffixed by ‘LocalHome’.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration
    +[
    +    (
    +        (./ExtendsList/ClassOrInterfaceType[ends-with(@Image,'EJBLocalHome')])
    +    )
    +    and
    +    not
    +    (
    +        ends-with(@SimpleName,'LocalHome')
    +    )
    +]
    +
    + +

    Example(s):

    + +
    public interface MyBeautifulLocalHome extends javax.ejb.EJBLocalHome {} // proper name
    +
    +public interface MissingProperSuffix extends javax.ejb.EJBLocalHome {}  // non-standard name
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/LocalHomeNamingConvention" />
    +
    + +

    LocalInterfaceSessionNamingConvention

    + +

    Since: PMD 4.0

    + +

    Priority: Medium Low (4)

    + +

    The Local Interface of a Session EJB should be suffixed by ‘Local’.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration
    +[
    +    (
    +        (./ExtendsList/ClassOrInterfaceType[ends-with(@Image,'EJBLocalObject')])
    +    )
    +    and
    +    not
    +    (
    +        ends-with(@SimpleName,'Local')
    +    )
    +]
    +
    + +

    Example(s):

    + +
    public interface MyLocal extends javax.ejb.EJBLocalObject {}                // proper name
    +
    +public interface MissingProperSuffix extends javax.ejb.EJBLocalObject {}    // non-standard name
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/LocalInterfaceSessionNamingConvention" />
    +
    + +

    LocalVariableCouldBeFinal

    + +

    Since: PMD 2.2

    + +

    Priority: Medium (3)

    + +

    A local variable assigned only once can be declared final.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.LocalVariableCouldBeFinalRule

    + +

    Example(s):

    + +
    public class Bar {
    +    public void foo () {
    +    String txtA = "a";          // if txtA will not be assigned again it is better to do this:
    +    final String txtB = "b";
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoreForEachDeclfalseIgnore non-final loop variables in a for-each statement.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/LocalVariableCouldBeFinal" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/LocalVariableCouldBeFinal">
    +    <properties>
    +        <property name="ignoreForEachDecl" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    LocalVariableNamingConventions

    + +

    Since: PMD 6.6.0

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for local variable declarations and other locally-scoped +variables. This rule reports variable declarations which do not match the regex that applies to their +specific kind (e.g. final variable, or catch-clause parameter). Each regex can be configured through +properties.

    + +

    By default this rule uses the standard Java naming convention (Camel case).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.LocalVariableNamingConventionsRule

    + +

    Example(s):

    + +
    class Foo {
    +                void bar() {
    +                    int localVariable = 1; // This is in camel case, so it's ok
    +                    int local_variable = 1; // This will be reported unless you change the regex
    +
    +                    final int i_var = 1; // final local variables can be configured separately
    +
    +                    try {
    +                        foo();
    +                    } catch (IllegalArgumentException e_illegal) {
    +                        // exception block parameters can be configured separately
    +                    }
    +
    +                }
    +            }
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    localVarPattern[a-z][a-zA-Z0-9]*Regex which applies to non-final local variable namesno
    finalVarPattern[a-z][a-zA-Z0-9]*Regex which applies to final local variable namesno
    catchParameterPattern[a-z][a-zA-Z0-9]*Regex which applies to exception block parameter namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/LocalVariableNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/LocalVariableNamingConventions">
    +    <properties>
    +        <property name="localVarPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="finalVarPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="catchParameterPattern" value="[a-z][a-zA-Z0-9]*" />
    +    </properties>
    +</rule>
    +
    + +

    LongVariable

    + +

    Since: PMD 0.3

    + +

    Priority: Medium (3)

    + +

    Fields, formal arguments, or local variable names that are too long can make the code difficult to follow.

    + +

    This rule is defined by the following XPath expression:

    +
    //VariableDeclaratorId[string-length(@Name) > $minimum]
    +
    + +

    Example(s):

    + +
    public class Something {
    +    int reallyLongIntName = -3;             // VIOLATION - Field
    +    public static void main( String argumentsList[] ) { // VIOLATION - Formal
    +        int otherReallyLongName = -5;       // VIOLATION - Local
    +        for (int interestingIntIndex = 0;   // VIOLATION - For
    +             interestingIntIndex < 10;
    +             interestingIntIndex ++ ) {
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    minimum17The variable length reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/LongVariable" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/LongVariable">
    +    <properties>
    +        <property name="minimum" value="17" />
    +    </properties>
    +</rule>
    +
    + +

    MDBAndSessionBeanNamingConvention

    + +

    Since: PMD 4.0

    + +

    Priority: Medium Low (4)

    + +

    The EJB Specification states that any MessageDrivenBean or SessionBean should be suffixed by ‘Bean’.

    + +

    This rule is defined by the following XPath expression:

    +
    //TypeDeclaration/ClassOrInterfaceDeclaration
    +[
    +    (
    +        (./ImplementsList/ClassOrInterfaceType[ends-with(@Image,'SessionBean')])
    +        or
    +        (./ImplementsList/ClassOrInterfaceType[ends-with(@Image,'MessageDrivenBean')])
    +    )
    +    and
    +    not
    +    (
    +        ends-with(@SimpleName,'Bean')
    +    )
    +]
    +
    + +

    Example(s):

    + +
    public class SomeBean implements SessionBean{}                  // proper name
    +
    +public class MissingTheProperSuffix implements SessionBean {}   // non-standard name
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/MDBAndSessionBeanNamingConvention" />
    +
    + +

    MethodArgumentCouldBeFinal

    + +

    Since: PMD 2.2

    + +

    Priority: Medium (3)

    + +

    A method argument that is never re-assigned within the method can be declared final.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.MethodArgumentCouldBeFinalRule

    + +

    Example(s):

    + +
    public void foo1 (String param) {       // do stuff with param never assigning it
    +
    +}
    +
    +public void foo2 (final String param) { // better, do stuff with param never assigning it
    +
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/MethodArgumentCouldBeFinal" />
    +
    + +

    MethodNamingConventions

    + +

    Since: PMD 1.2

    + +

    Priority: High (1)

    + +

    Configurable naming conventions for method declarations. This rule reports +method declarations which do not match the regex that applies to their +specific kind (e.g. JUnit test or native method). Each regex can be +configured through properties.

    + +

    By default this rule uses the standard Java naming convention (Camel case).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.MethodNamingConventionsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void fooStuff() {
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    checkNativeMethodstrueDeprecated Check native methodsno
    methodPattern[a-z][a-zA-Z0-9]*Regex which applies to instance method namesno
    staticPattern[a-z][a-zA-Z0-9]*Regex which applies to static method namesno
    nativePattern[a-z][a-zA-Z0-9]*Regex which applies to native method namesno
    junit3TestPatterntest[A-Z0-9][a-zA-Z0-9]*Regex which applies to JUnit 3 test method namesno
    junit4TestPattern[a-z][a-zA-Z0-9]*Regex which applies to JUnit 4 test method namesno
    junit5TestPattern[a-z][a-zA-Z0-9]*Regex which applies to JUnit 5 test method namesno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/MethodNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/MethodNamingConventions">
    +    <properties>
    +        <property name="methodPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="staticPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="nativePattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="junit3TestPattern" value="test[A-Z0-9][a-zA-Z0-9]*" />
    +        <property name="junit4TestPattern" value="[a-z][a-zA-Z0-9]*" />
    +        <property name="junit5TestPattern" value="[a-z][a-zA-Z0-9]*" />
    +    </properties>
    +</rule>
    +
    + +

    MIsLeadingVariableName

    + +

    Deprecated

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Detects when a non-field has a name starting with ‘m_’. This usually denotes a field and could be confusing.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the more general rule +LocalVariableNamingConventions.

    + +

    This rule is defined by the following XPath expression:

    +
    //VariableDeclaratorId
    +[starts-with(@Name, 'm_')]
    +[not (../../../FieldDeclaration)]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    private int m_foo; // OK
    +    public void bar(String m_baz) { // Bad
    +      int m_boz = 42; // Bad
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/MIsLeadingVariableName" />
    +
    + +

    NoPackage

    + +

    Since: PMD 3.3

    + +

    Priority: Medium (3)

    + +

    Detects when a class, interface, enum or annotation does not have a package definition.

    + +

    This rule is defined by the following XPath expression:

    +
    /CompilationUnit[not(./PackageDeclaration)]/TypeDeclaration[1]
    +
    + +

    Example(s):

    + +
    // no package declaration
    +public class ClassInDefaultPackage {
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/NoPackage" />
    +
    + +

    OnlyOneReturn

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    A method should have only one exit point, and that should be the last statement in the method.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.OnlyOneReturnRule

    + +

    Example(s):

    + +
    public class OneReturnOnly1 {
    +  public String foo(int x) {
    +    if (x > 0) {
    +      return "hey";   // first exit
    +    }
    +    return "hi";    // second exit
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/OnlyOneReturn" />
    +
    + +

    PackageCase

    + +

    Since: PMD 3.3

    + +

    Priority: Medium (3)

    + +

    Detects when a package definition contains uppercase characters.

    + +

    This rule is defined by the following XPath expression:

    +
    //PackageDeclaration/Name[lower-case(@Image)!=@Image]
    +
    + +

    Example(s):

    + +
    package com.MyCompany;  // should be lowercase name
    +
    +public class SomeClass {
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/PackageCase" />
    +
    + +

    PrematureDeclaration

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Checks for variables that are defined before they might be used. A reference is deemed to be premature if it is created right before a block of code that doesn’t use it that also has the ability to return or throw an exception.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.PrematureDeclarationRule

    + +

    Example(s):

    + +
    public int getLength(String[] strings) {
    +
    +    int length = 0; // declared prematurely
    +
    +    if (strings == null || strings.length == 0) return 0;
    +
    +    for (String str : strings) {
    +        length += str.length();
    +    }
    +
    +    return length;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/PrematureDeclaration" />
    +
    + +

    RemoteInterfaceNamingConvention

    + +

    Since: PMD 4.0

    + +

    Priority: Medium Low (4)

    + +

    Remote Interface of a Session EJB should not have a suffix.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration
    +[
    +    (
    +        (./ExtendsList/ClassOrInterfaceType[ends-with(@Image,'EJBObject')])
    +    )
    +    and
    +    (
    +        ends-with(@SimpleName,'Session')
    +        or
    +        ends-with(@SimpleName,'EJB')
    +        or
    +        ends-with(@SimpleName,'Bean')
    +    )
    +]
    +
    + +

    Example(s):

    + +
    /* Poor Session suffix */
    +public interface BadSuffixSession extends javax.ejb.EJBObject {}
    +
    +/* Poor EJB suffix */
    +public interface BadSuffixEJB extends javax.ejb.EJBObject {}
    +
    +/* Poor Bean suffix */
    +public interface BadSuffixBean extends javax.ejb.EJBObject {}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/RemoteInterfaceNamingConvention" />
    +
    + +

    RemoteSessionInterfaceNamingConvention

    + +

    Since: PMD 4.0

    + +

    Priority: Medium Low (4)

    + +

    A Remote Home interface type of a Session EJB should be suffixed by ‘Home’.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration
    +[
    +    (
    +        (./ExtendsList/ClassOrInterfaceType[ends-with(@Image,'EJBHome')])
    +    )
    +    and
    +    not
    +    (
    +        ends-with(@SimpleName,'Home')
    +    )
    +]
    +
    + +

    Example(s):

    + +
    public interface MyBeautifulHome extends javax.ejb.EJBHome {}       // proper name
    +
    +public interface MissingProperSuffix extends javax.ejb.EJBHome {}   // non-standard name
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/RemoteSessionInterfaceNamingConvention" />
    +
    + +

    ShortClassName

    + +

    Since: PMD 5.0

    + +

    Priority: Medium Low (4)

    + +

    Short Classnames with fewer than e.g. five characters are not recommended.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[string-length(@SimpleName) < $minimum]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    minimum5Number of characters that are required as a minimum for a class name.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/ShortClassName" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/ShortClassName">
    +    <properties>
    +        <property name="minimum" value="5" />
    +    </properties>
    +</rule>
    +
    + +

    ShortMethodName

    + +

    Since: PMD 0.3

    + +

    Priority: Medium (3)

    + +

    Method names that are very short are not helpful to the reader.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[string-length(@Name) < $minimum]
    +
    + +

    Example(s):

    + +
    public class ShortMethod {
    +    public void a( int i ) { // Violation
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    minimum3Number of characters that are required as a minimum for a method name.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/ShortMethodName" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/ShortMethodName">
    +    <properties>
    +        <property name="minimum" value="3" />
    +    </properties>
    +</rule>
    +
    + +

    ShortVariable

    + +

    Since: PMD 0.3

    + +

    Priority: Medium (3)

    + +

    Fields, local variables, or parameter names that are very short are not helpful to the reader.

    + +

    This rule is defined by the following XPath expression:

    +
    //VariableDeclaratorId[string-length(@Name) < $minimum]
    + (: ForStatement :)
    + [not(../../..[self::ForInit])]
    + (: Foreach statement :)
    + [not(../../..[self::ForStatement])]
    + (: Catch statement parameter :)
    + [not(../..[self::CatchStatement])]
    + (: Lambda expression parameter :)
    + [not(parent::LambdaExpression or ../../..[self::LambdaExpression])]
    +
    + +

    Example(s):

    + +
    public class Something {
    +    private int q = 15;                         // field - too short
    +    public static void main( String as[] ) {    // formal arg - too short
    +        int r = 20 + q;                         // local var - too short
    +        for (int i = 0; i < 10; i++) {          // not a violation (inside 'for' loop)
    +            r += q;
    +        }
    +        for (Integer i : numbers) {             // not a violation (inside 'for-each' loop)
    +            r += q;
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    minimum3Number of characters that are required as a minimum for a variable name.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/ShortVariable" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/ShortVariable">
    +    <properties>
    +        <property name="minimum" value="3" />
    +    </properties>
    +</rule>
    +
    + +

    SuspiciousConstantFieldName

    + +

    Deprecated

    + +

    Since: PMD 2.0

    + +

    Priority: Medium (3)

    + +

    Field names using all uppercase characters - Sun’s Java naming conventions indicating constants - should +be declared as final.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the more general rule FieldNamingConventions.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[@Interface= false()]
    + /ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/FieldDeclaration
    +  [@Final= false()]
    +  [VariableDeclarator/VariableDeclaratorId[upper-case(@Name)=@Name]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    + // this is bad, since someone could accidentally
    + // do PI = 2.71828; which is actually e
    + // final double PI = 3.16; is ok
    +  double PI = 3.16;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/SuspiciousConstantFieldName" />
    +
    + +

    TooManyStaticImports

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    If you overuse the static import feature, it can make your program unreadable and +unmaintainable, polluting its namespace with all the static members you import. +Readers of your code (including you, a few months after you wrote it) will not know +which class a static member comes from (Sun 1.5 Language Guide).

    + +

    This rule is defined by the following XPath expression:

    +
    .[count(ImportDeclaration[@Static = true()]) > $maximumStaticImports]
    +
    + +

    Example(s):

    + +
    import static Lennon;
    +import static Ringo;
    +import static George;
    +import static Paul;
    +import static Yoko; // Too much !
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maximumStaticImports4All static imports can be disallowed by setting this to 0no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/TooManyStaticImports" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/TooManyStaticImports">
    +    <properties>
    +        <property name="maximumStaticImports" value="4" />
    +    </properties>
    +</rule>
    +
    + +

    UnnecessaryAnnotationValueElement

    + +

    Since: PMD 6.2.0

    + +

    Priority: Medium (3)

    + +

    Avoid the use of value in annotations when it’s the only element.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.UnnecessaryAnnotationValueElementRule

    + +

    Example(s):

    + +
    @TestClassAnnotation(value = "TEST")
    +public class Foo {
    +
    +    @TestMemberAnnotation(value = "TEST")
    +    private String y;
    +
    +    @TestMethodAnnotation(value = "TEST")
    +    public void bar() {
    +        int x = 42;
    +        return;
    +    }
    +}
    +
    +// should be
    +
    +@TestClassAnnotation("TEST")
    +public class Foo {
    +
    +    @TestMemberAnnotation("TEST")
    +    private String y;
    +
    +    @TestMethodAnnotation("TEST")
    +    public void bar() {
    +        int x = 42;
    +        return;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/UnnecessaryAnnotationValueElement" />
    +
    + +

    UnnecessaryCast

    + +

    Since: PMD 6.24.0

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.5

    + +

    This rule detects when a cast is unnecessary while accessing collection elements. This rule is mostly useful +for old java code before generics where introduced with java 1.5.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.UnnecessaryCastRule

    + +

    Example(s):

    + +
    public class UnnecessaryCastSample {
    +    public void method() {
    +        List<String> stringList = Arrays.asList("a", "b");
    +        String element = (String) stringList.get(0); // this cast is unnecessary
    +        String element2 = stringList.get(0);
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/UnnecessaryCast" />
    +
    + +

    UnnecessaryConstructor

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    This rule detects when a constructor is not necessary; i.e., when there is only one constructor and the +constructor is identical to the default constructor. The default constructor should has same access +modifier as the declaring class. In an enum type, the default constructor is implicitly private.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.UnnecessaryConstructorRule

    + +

    Example(s):

    + +
    public class Foo {
    +  public Foo() {}
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationsjavax.inject.InjectFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/UnnecessaryConstructor" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/UnnecessaryConstructor">
    +    <properties>
    +        <property name="ignoredAnnotations" value="javax.inject.Inject" />
    +    </properties>
    +</rule>
    +
    + +

    UnnecessaryFullyQualifiedName

    + +

    Since: PMD 5.0

    + +

    Priority: Medium Low (4)

    + +

    Import statements allow the use of non-fully qualified names. The use of a fully qualified name +which is covered by an import statement is redundant. Consider using the non-fully qualified name.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.UnnecessaryFullyQualifiedNameRule

    + +

    Example(s):

    + +
    import java.util.List;
    +
    +public class Foo {
    +    private java.util.List list1;   // Unnecessary FQN
    +    private List list2;             // More appropriate given import of 'java.util.List'
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/UnnecessaryFullyQualifiedName" />
    +
    + +

    UnnecessaryLocalBeforeReturn

    + +

    Since: PMD 3.3

    + +

    Priority: Medium (3)

    + +

    Avoid the creation of unnecessary local variables

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.UnnecessaryLocalBeforeReturnRule

    + +

    Example(s):

    + +
    public class Foo {
    +   public int foo() {
    +     int x = doSomething();
    +     return x;  // instead, just 'return doSomething();'
    +   }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    statementOrderMatterstrueIf set to false this rule no longer requires the variable declaration and return statement to be on consecutive lines. Any variable that is used solely in a return statement will be reported.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/UnnecessaryLocalBeforeReturn" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/UnnecessaryLocalBeforeReturn">
    +    <properties>
    +        <property name="statementOrderMatters" value="true" />
    +    </properties>
    +</rule>
    +
    + +

    UnnecessaryModifier

    + +

    Since: PMD 1.02

    + +

    Priority: Medium (3)

    + +

    Fields in interfaces and annotations are automatically public static final, and methods are public abstract. +Classes, interfaces or annotations nested in an interface or annotation are automatically public static +(all nested interfaces and annotations are automatically static). +Nested enums are automatically static. +For historical reasons, modifiers which are implied by the context are accepted by the compiler, but are superfluous.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.UnnecessaryModifierRule

    + +

    Example(s):

    + +
    public @interface Annotation {
    +    public abstract void bar();     // both abstract and public are ignored by the compiler
    +    public static final int X = 0;  // public, static, and final all ignored
    +    public static class Bar {}      // public, static ignored
    +    public static interface Baz {}  // ditto
    +}
    +public interface Foo {
    +    public abstract void bar();     // both abstract and public are ignored by the compiler
    +    public static final int X = 0;  // public, static, and final all ignored
    +    public static class Bar {}      // public, static ignored
    +    public static interface Baz {}  // ditto
    +}
    +public class Bar {
    +    public static interface Baz {}  // static ignored
    +    public static enum FoorBar {    // static ignored
    +        FOO;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/UnnecessaryModifier" />
    +
    + +

    UnnecessaryReturn

    + +

    Since: PMD 1.3

    + +

    Priority: Medium (3)

    + +

    Avoid the use of unnecessary return statements.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.UnnecessaryReturnRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar() {
    +        int x = 42;
    +        return;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/UnnecessaryReturn" />
    +
    + +

    UseDiamondOperator

    + +

    Since: PMD 6.11.0

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.7

    + +

    Use the diamond operator to let the type be inferred automatically. With the Diamond operator it is possible +to avoid duplication of the type parameters. +Instead, the compiler is now able to infer the parameter types for constructor calls, +which makes the code also more readable.

    + +

    The diamond operator has been introduced with java 7. However, type inference has been improved further +with java8, rendering more type parameters unnecessary. This is only possible with java8 and the resulting +code won’t compile with java7. If you use java7, make sure to enable java7Compatibility for this rule to avoid +false positives.

    + +

    This rule is defined by the following XPath expression:

    +
    (
    +//VariableInitializer[preceding-sibling::VariableDeclaratorId[1]/@TypeInferred=false()]
    +|
    +//StatementExpression[AssignmentOperator and PrimaryExpression/PrimaryPrefix[not(Expression)]]
    +)
    +/(Expression | Expression[$java7Compatibility = false()]/ConditionalExpression | Expression[$java7Compatibility = false()]/ConditionalExpression/Expression)
    +/PrimaryExpression[not(PrimarySuffix) and not(ancestor::ArgumentList)]
    +/PrimaryPrefix
    +/AllocationExpression
    +    [@AnonymousClass=false()]
    +    [ClassOrInterfaceType/TypeArguments[@Diamond=false() and not($java7Compatibility = true() and .//TypeArgument[@Wildcard=true()])]]
    +    [not(ArrayDimsAndInits)]
    +
    + +

    Example(s):

    + +
    List<String> strings = new ArrayList<String>(); // unnecessary duplication of type parameters
    +List<String> stringsWithDiamond = new ArrayList<>(); // using the diamond operator is more concise
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    java7CompatibilityfalseIf disabled, the rule shows also violations that are applicable for java8+no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/UseDiamondOperator" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/UseDiamondOperator">
    +    <properties>
    +        <property name="java7Compatibility" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    UselessParentheses

    + +

    Since: PMD 5.0

    + +

    Priority: Medium Low (4)

    + +

    Useless parentheses should be removed.

    + +

    This rule is defined by the following XPath expression:

    +
    //Expression[not(parent::PrimaryPrefix)]/PrimaryExpression[count(*)>1]
    +  /PrimaryPrefix/Expression
    +    [not(./CastExpression)]
    +    [not(./ConditionalExpression)]
    +    [not(./AdditiveExpression)]
    +    [not(./AssignmentOperator)]
    +|
    +//Expression[not(parent::PrimaryPrefix)]/PrimaryExpression[count(*)=1]
    +  /PrimaryPrefix/Expression
    +|
    +//Expression/ConditionalAndExpression/PrimaryExpression/PrimaryPrefix/Expression[
    +    count(*)=1 and
    +    not(./CastExpression) and
    +    not(./EqualityExpression/MultiplicativeExpression) and
    +    not(./ConditionalExpression) and
    +    not(./ConditionalOrExpression)]
    +|
    +//Expression/ConditionalOrExpression/PrimaryExpression/PrimaryPrefix/Expression[
    +    count(*)=1 and
    +    not(./CastExpression) and
    +    not(./ConditionalExpression) and
    +    not(./EqualityExpression/MultiplicativeExpression)]
    +|
    +//Expression/ConditionalExpression/PrimaryExpression/PrimaryPrefix/Expression[
    +    count(*)=1 and
    +    not(./CastExpression) and
    +    not(./EqualityExpression)]
    +|
    +//Expression/AdditiveExpression[not(./PrimaryExpression/PrimaryPrefix/Literal[@StringLiteral= true()])]
    +  /PrimaryExpression[1]/PrimaryPrefix/Expression[
    +    count(*)=1 and
    +    not(./CastExpression) and
    +    not(./AdditiveExpression[@Operator = '-']) and
    +    not(./ShiftExpression) and
    +    not(./RelationalExpression) and
    +    not(./InstanceOfExpression) and
    +    not(./EqualityExpression) and
    +    not(./AndExpression) and
    +    not(./ExclusiveOrExpression) and
    +    not(./InclusiveOrExpression) and
    +    not(./ConditionalAndExpression) and
    +    not(./ConditionalOrExpression) and
    +    not(./ConditionalExpression)]
    +|
    +//Expression/EqualityExpression/PrimaryExpression/PrimaryPrefix/Expression[
    +    count(*)=1 and
    +    not(./CastExpression) and
    +    not(./AndExpression) and
    +    not(./InclusiveOrExpression) and
    +    not(./ExclusiveOrExpression) and
    +    not(./ConditionalExpression) and
    +    not(./ConditionalAndExpression) and
    +    not(./ConditionalOrExpression) and
    +    not(./EqualityExpression)]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +
    +    private int _bar1;
    +    private Integer _bar2;
    +
    +    public void setBar(int n) {
    +        _bar1 = Integer.valueOf((n)); // here
    +        _bar2 = (n); // and here
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/UselessParentheses" />
    +
    + +

    UselessQualifiedThis

    + +

    Since: PMD 5.4.0

    + +

    Priority: Medium (3)

    + +

    Reports qualified this usages in the same class.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryExpression
    +[PrimaryPrefix/Name[@Image]]
    +[PrimarySuffix[@Arguments= false() and @ArrayDereference = false()]]
    +[not(PrimarySuffix/MemberSelector)]
    +[ancestor::ClassOrInterfaceBodyDeclaration[1][@AnonymousInnerClass= false()]]
    +/PrimaryPrefix/Name[@Image = ancestor::ClassOrInterfaceDeclaration[1]/@SimpleName]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    final Foo otherFoo = Foo.this;  // use "this" directly
    +
    +    public void doSomething() {
    +         final Foo anotherFoo = Foo.this;  // use "this" directly
    +    }
    +
    +    private ActionListener returnListener() {
    +        return new ActionListener() {
    +            @Override
    +            public void actionPerformed(ActionEvent e) {
    +                doSomethingWithQualifiedThis(Foo.this);  // This is fine
    +            }
    +        };
    +    }
    +
    +    private class Foo3 {
    +        final Foo myFoo = Foo.this;  // This is fine
    +    }
    +
    +    private class Foo2 {
    +        final Foo2 myFoo2 = Foo2.this;  // Use "this" direclty
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/UselessQualifiedThis" />
    +
    + +

    UseShortArrayInitializer

    + +

    Since: PMD 6.15.0

    + +

    Priority: Medium (3)

    + +

    When declaring and initializing array fields or variables, it is not necessary to explicitly create a new array +using new. Instead one can simply define the initial content of the array as a expression in curly braces.

    + +

    E.g. int[] x = new int[] { 1, 2, 3 }; can be written as int[] x = { 1, 2, 3 };.

    + +

    This rule is defined by the following XPath expression:

    +
    //VariableDeclarator
    +    [VariableDeclaratorId[@ArrayType = true() and @TypeInferred = false()]]
    +    [VariableInitializer/Expression/PrimaryExpression/PrimaryPrefix/AllocationExpression/ArrayDimsAndInits/ArrayInitializer]
    +
    + +

    Example(s):

    + +
    Foo[] x = new Foo[] { ... }; // Overly verbose
    +Foo[] x = { ... }; //Equivalent to above line
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/UseShortArrayInitializer" />
    +
    + +

    UseUnderscoresInNumericLiterals

    + +

    Since: PMD 6.10.0

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.7

    + +

    Since Java 1.7, numeric literals can use underscores to separate digits. This rule enforces that +numeric literals above a certain length use these underscores to increase readability.

    + +

    The rule only supports decimal (base 10) literals for now. The acceptable length under which literals +are not required to have underscores is configurable via a property. Even under that length, underscores +that are misplaced (not making groups of 3 digits) are reported.

    + +

    This rule is defined by the following XPath expression:

    +
    //Literal[
    +     @IntLiteral = true()
    +  or @LongLiteral = true()
    +  or @DoubleLiteral = true()
    +  or @FloatLiteral = true()
    +]
    + (: Filter out literals in base other than 10 :)
    + [not(matches(@Image, "^0[^.]"))]
    + (: Filter out ignored field name :)
    + [not(ancestor::VariableDeclarator[1][@Name = 'serialVersionUID'])]
    + [
    +   some $num in tokenize(@Image, "[dDfFlLeE+\-]")
    +   satisfies not(
    +                  ( contains($num, ".")
    +                    and string-length(substring-before($num, ".")) <= $acceptableDecimalLength
    +                    and string-length(substring-after($num, ".")) <= $acceptableDecimalLength
    +                    or string-length($num) <= $acceptableDecimalLength
    +                  )
    +                  and not(contains($num,"_"))
    +                  or matches($num, "^[0-9]{1,3}(_[0-9]{3})*(\.([0-9]{3}_)*[0-9]{1,3})?$")
    +                )
    + ]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    private int num = 1000000; // should be 1_000_000
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    acceptableDecimalLength4Length under which literals in base 10 are not required to have underscoresno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/UseUnderscoresInNumericLiterals" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/UseUnderscoresInNumericLiterals">
    +    <properties>
    +        <property name="acceptableDecimalLength" value="4" />
    +    </properties>
    +</rule>
    +
    + +

    VariableNamingConventions

    + +

    Deprecated

    + +

    Since: PMD 1.2

    + +

    Priority: High (1)

    + +

    A variable naming conventions rule - customize this to your liking. Currently, it +checks for final variables that should be fully capitalized and non-final variables +that should not include underscores.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the more general rules FieldNamingConventions, +FormalParameterNamingConventions, and +LocalVariableNamingConventions.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.codestyle.VariableNamingConventionsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public static final int MY_NUM = 0;
    +    public String myTest = "";
    +    DataModule dmTest = new DataModule();
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    parameterSuffix Method parameter variable suffixesyes. Delimiter is ‘,’.
    parameterPrefix Method parameter variable prefixesyes. Delimiter is ‘,’.
    localSuffix Local variable suffixesyes. Delimiter is ‘,’.
    localPrefix Local variable prefixesyes. Delimiter is ‘,’.
    memberSuffix Member variable suffixesyes. Delimiter is ‘,’.
    memberPrefix Member variable prefixesyes. Delimiter is ‘,’.
    staticSuffix Static variable suffixesyes. Delimiter is ‘,’.
    staticPrefix Static variable prefixesyes. Delimiter is ‘,’.
    checkMemberstrueCheck member variablesno
    checkLocalstrueCheck local variablesno
    checkParameterstrueCheck constructor and method parameter variablesno
    checkNativeMethodParameterstrueCheck method parameter of native methodsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/codestyle.xml/VariableNamingConventions" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/codestyle.xml/VariableNamingConventions">
    +    <properties>
    +        <property name="parameterSuffix" value="" />
    +        <property name="parameterPrefix" value="" />
    +        <property name="localSuffix" value="" />
    +        <property name="localPrefix" value="" />
    +        <property name="memberSuffix" value="" />
    +        <property name="memberPrefix" value="" />
    +        <property name="staticSuffix" value="" />
    +        <property name="staticPrefix" value="" />
    +        <property name="checkMembers" value="true" />
    +        <property name="checkLocals" value="true" />
    +        <property name="checkParameters" value="true" />
    +        <property name="checkNativeMethodParameters" value="true" />
    +    </properties>
    +</rule>
    +
    + +

    WhileLoopsMustUseBraces

    + +

    Deprecated

    + +

    Since: PMD 0.7

    + +

    Priority: Medium (3)

    + +

    Avoid using ‘while’ statements without using braces to surround the code block. If the code +formatting or indentation is lost then it becomes difficult to separate the code being +controlled from the rest.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the rule ControlStatementBraces.

    + +

    This rule is defined by the following XPath expression:

    +
    //WhileStatement[not(Statement/Block)]
    +
    + +

    Example(s):

    + +
    while (true)    // not recommended
    +      x++;
    +
    +while (true) {  // preferred approach
    +      x++;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/codestyle.xml/WhileLoopsMustUseBraces" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_java_design.html b/pmd_rules_java_design.html new file mode 100644 index 0000000000..2d9c30d13c --- /dev/null +++ b/pmd_rules_java_design.html @@ -0,0 +1,3987 @@ + + + + + + + + +Design | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Design

    +
    + + + +
    + + +
    Rules that help you discover design issues.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AbstractClassWithoutAnyMethod

    + +

    Since: PMD 4.2

    + +

    Priority: High (1)

    + +

    If an abstract class does not provides any methods, it may be acting as a simple data container +that is not meant to be instantiated. In this case, it is probably better to use a private or +protected constructor in order to prevent instantiation than make the class misleadingly abstract.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration
    +    [@Abstract = true()]
    +    [not(./ClassOrInterfaceBody/*/ConstructorDeclaration)]
    +    [not(./ClassOrInterfaceBody/*/MethodDeclaration)]
    +    [not(../Annotation/MarkerAnnotation/Name[pmd-java:typeIs('com.google.auto.value.AutoValue')])]
    +
    + +

    Example(s):

    + +
    public abstract class Example {
    +    String field;
    +    int otherField;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/AbstractClassWithoutAnyMethod" />
    +
    + +

    AvoidCatchingGenericException

    + +

    Since: PMD 4.2.6

    + +

    Priority: Medium (3)

    + +

    Avoid catching generic exceptions such as NullPointerException, RuntimeException, Exception in try-catch block

    + +

    This rule is defined by the following XPath expression:

    +
    //CatchStatement/FormalParameter/Type/ReferenceType/ClassOrInterfaceType[
    +    @Image='NullPointerException' or
    +    @Image='Exception' or
    +    @Image='RuntimeException']
    +
    + +

    Example(s):

    + +
    package com.igate.primitive;
    +
    +public class PrimitiveType {
    +
    +    public void downCastPrimitiveType() {
    +        try {
    +            System.out.println(" i [" + i + "]");
    +        } catch(Exception e) {
    +            e.printStackTrace();
    +        } catch(RuntimeException e) {
    +            e.printStackTrace();
    +        } catch(NullPointerException e) {
    +            e.printStackTrace();
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/AvoidCatchingGenericException" />
    +
    + +

    AvoidDeeplyNestedIfStmts

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    Avoid creating deeply nested if-then statements since they are harder to read and error-prone to maintain.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.AvoidDeeplyNestedIfStmtsRule

    + +

    Example(s):

    + +
    public class Foo {
    +  public void bar(int x, int y, int z) {
    +    if (x>y) {
    +      if (y>z) {
    +        if (z==x) {
    +         // !! too deep
    +        }
    +      }
    +    }
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    problemDepth3The if statement depth reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/AvoidDeeplyNestedIfStmts" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/AvoidDeeplyNestedIfStmts">
    +    <properties>
    +        <property name="problemDepth" value="3" />
    +    </properties>
    +</rule>
    +
    + +

    AvoidRethrowingException

    + +

    Since: PMD 3.8

    + +

    Priority: Medium (3)

    + +

    Catch blocks that merely rethrow a caught exception only add to code size and runtime complexity.

    + +

    This rule is defined by the following XPath expression:

    +
    //CatchStatement[FormalParameter
    + /VariableDeclaratorId/@Name = Block/BlockStatement/Statement
    + /ThrowStatement/Expression/PrimaryExpression[count(PrimarySuffix)=0]/PrimaryPrefix/Name/@Image
    + and count(Block/BlockStatement/Statement) =1]
    +
    + +

    Example(s):

    + +
    public void bar() {
    +    try {
    +        // do something
    +    }  catch (SomeException se) {
    +       throw se;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/AvoidRethrowingException" />
    +
    + +

    AvoidThrowingNewInstanceOfSameException

    + +

    Since: PMD 4.2.5

    + +

    Priority: Medium (3)

    + +

    Catch blocks that merely rethrow a caught exception wrapped inside a new instance of the same type only add to +code size and runtime complexity.

    + +

    This rule is defined by the following XPath expression:

    +
    //CatchStatement[
    +  count(Block/BlockStatement/Statement) = 1
    +  and
    +  FormalParameter/Type/ReferenceType/ClassOrInterfaceType/@Image = Block/BlockStatement/Statement/ThrowStatement/Expression/PrimaryExpression/PrimaryPrefix/AllocationExpression/ClassOrInterfaceType/@Image
    +  and
    +  count(Block/BlockStatement/Statement/ThrowStatement/Expression/PrimaryExpression/PrimaryPrefix/AllocationExpression/Arguments/ArgumentList/Expression) = 1
    +  and
    +  FormalParameter/VariableDeclaratorId = Block/BlockStatement/Statement/ThrowStatement/Expression/PrimaryExpression/PrimaryPrefix/AllocationExpression/Arguments/ArgumentList/Expression/PrimaryExpression/PrimaryPrefix/Name
    +  ]
    +
    + +

    Example(s):

    + +
    public void bar() {
    +    try {
    +        // do something
    +    } catch (SomeException se) {
    +        // harmless comment
    +        throw new SomeException(se);
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/AvoidThrowingNewInstanceOfSameException" />
    +
    + +

    AvoidThrowingNullPointerException

    + +

    Since: PMD 1.8

    + +

    Priority: High (1)

    + +

    Avoid throwing NullPointerExceptions manually. These are confusing because most people will assume that the +virtual machine threw it. To avoid a method being called with a null parameter, you may consider +using an IllegalArgumentException instead, making it clearly seen as a programmer-initiated exception. +However, there are better ways to handle this:

    + +
    +

    Effective Java, 3rd Edition, Item 72: Favor the use of standard exceptions

    + +

    Arguably, every erroneous method invocation boils down to an illegal argument or state, +but other exceptions are standardly used for certain kinds of illegal arguments and states. +If a caller passes null in some parameter for which null values are prohibited, convention dictates that +NullPointerException be thrown rather than IllegalArgumentException.

    +
    + +

    To implement that, you are encouraged to use java.util.Objects.requireNonNull() +(introduced in Java 1.7). This method is designed primarily for doing parameter +validation in methods and constructors with multiple parameters.

    + +

    Your parameter validation could thus look like the following:

    +
    public class Foo {
    +    private String exampleValue;
    +
    +    void setExampleValue(String exampleValue) {
    +      // check, throw and assignment in a single standard call
    +      this.exampleValue = Objects.requireNonNull(exampleValue, "exampleValue must not be null!");
    +    }
    +  }
    +
    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.AvoidThrowingNullPointerExceptionRule

    + +

    Example(s):

    + +
    public class Foo {
    +    void bar() {
    +        throw new NullPointerException();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/AvoidThrowingNullPointerException" />
    +
    + +

    AvoidThrowingRawExceptionTypes

    + +

    Since: PMD 1.8

    + +

    Priority: High (1)

    + +

    Avoid throwing certain exception types. Rather than throw a raw RuntimeException, Throwable, +Exception, or Error, use a subclassed exception or error instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //ThrowStatement//AllocationExpression
    + /ClassOrInterfaceType[
    + pmd-java:typeIsExactly('java.lang.Throwable')
    +or
    + pmd-java:typeIsExactly('java.lang.Exception')
    +or
    + pmd-java:typeIsExactly('java.lang.Error')
    +or
    + pmd-java:typeIsExactly('java.lang.RuntimeException')
    +]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar() throws Exception {
    +        throw new Exception();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/AvoidThrowingRawExceptionTypes" />
    +
    + +

    AvoidUncheckedExceptionsInSignatures

    + +

    Since: PMD 6.13.0

    + +

    Priority: Medium (3)

    + +

    A method or constructor should not explicitly declare unchecked exceptions in its +throws clause. Java doesn’t force the caller to handle an unchecked exception, +so it’s unnecessary except for documentation. A better practice is to document the +exceptional cases with a @throws Javadoc tag, which allows being more descriptive.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration/NameList/Name[pmd-java:typeIs("java.lang.RuntimeException")]
    +|
    +//ConstructorDeclaration/NameList/Name[pmd-java:typeIs("java.lang.RuntimeException")]
    +
    + +

    Example(s):

    + +
    public void foo() throws RuntimeException {
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/AvoidUncheckedExceptionsInSignatures" />
    +
    + +

    ClassWithOnlyPrivateConstructorsShouldBeFinal

    + +

    Since: PMD 4.1

    + +

    Priority: High (1)

    + +

    A class with only private constructors should be final, unless the private constructor +is invoked by a inner class.

    + +

    This rule is defined by the following XPath expression:

    +
    //TypeDeclaration[count(../TypeDeclaration) = 1]/ClassOrInterfaceDeclaration
    +[@Final = false()]
    +[ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/ConstructorDeclaration[@Private = true()]]
    +[not(./ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/ConstructorDeclaration[(@Public = true()) or (@Protected = true()) or (@PackagePrivate = true())])]
    +[not(.//ClassOrInterfaceDeclaration)]
    +
    + +

    Example(s):

    + +
    public class Foo {  //Should be final
    +    private Foo() { }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/ClassWithOnlyPrivateConstructorsShouldBeFinal" />
    +
    + +

    CollapsibleIfStatements

    + +

    Since: PMD 3.1

    + +

    Priority: Medium (3)

    + +

    Sometimes two consecutive ‘if’ statements can be consolidated by separating their conditions with a boolean short-circuit operator.

    + +

    This rule is defined by the following XPath expression:

    +
    //IfStatement[@Else= false()]/Statement
    + /IfStatement[@Else= false()]
    + |
    +//IfStatement[@Else= false()]/Statement
    + /Block[count(BlockStatement)=1]/BlockStatement
    +  /Statement/IfStatement[@Else= false()]
    +
    + +

    Example(s):

    + +
    void bar() {
    +    if (x) {            // original implementation
    +        if (y) {
    +            // do stuff
    +        }
    +    }
    +}
    +
    +void bar() {
    +    if (x && y) {        // optimized implementation
    +        // do stuff
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/CollapsibleIfStatements" />
    +
    + +

    CouplingBetweenObjects

    + +

    Since: PMD 1.04

    + +

    Priority: Medium (3)

    + +

    This rule counts the number of unique attributes, local variables, and return types within an object. +A number higher than the specified threshold can indicate a high degree of coupling.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.CouplingBetweenObjectsRule

    + +

    Example(s):

    + +
    import com.Blah;
    +import org.Bar;
    +import org.Bardo;
    +
    +public class Foo {
    +    private Blah var1;
    +    private Bar var2;
    +
    +    //followed by many imports of unique objects
    +    ObjectC doWork() {
    +        Bardo var55;
    +        ObjectA var44;
    +        ObjectZ var93;
    +        return something();
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    threshold20Unique type reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/CouplingBetweenObjects" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/CouplingBetweenObjects">
    +    <properties>
    +        <property name="threshold" value="20" />
    +    </properties>
    +</rule>
    +
    + +

    CyclomaticComplexity

    + +

    Since: PMD 1.03

    + +

    Priority: Medium (3)

    + +

    The complexity of methods directly affects maintenance costs and readability. Concentrating too much decisional logic +in a single method makes its behaviour hard to read and change.

    + +

    Cyclomatic complexity assesses the complexity of a method by counting the number of decision points in a method, +plus one for the method entry. Decision points are places where the control flow jumps to another place in the +program. As such, they include all control flow statements, such as if, while, for, and case. For more +details on the calculation, see the documentation of the Cyclo metric.

    + +

    Generally, numbers ranging from 1-4 denote low complexity, 5-7 denote moderate complexity, 8-10 denote +high complexity, and 11+ is very high complexity. By default, this rule reports methods with a complexity >= 10. +Additionally, classes with many methods of moderate complexity get reported as well once the total of their +methods’ complexities reaches 80, even if none of the methods was directly reported.

    + +

    Reported methods should be broken down into several smaller methods. Reported classes should probably be broken down +into subcomponents.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.CyclomaticComplexityRule

    + +

    Example(s):

    + +
    class Foo {
    +  void baseCyclo() {                // Cyclo = 1
    +    highCyclo();
    +  }
    +
    +  void highCyclo() {                // Cyclo = 10: reported!
    +    int x = 0, y = 2;
    +    boolean a = false, b = true;
    +
    +    if (a && (y == 1 ? b : true)) { // +3
    +      if (y == x) {                 // +1
    +        while (true) {              // +1
    +          if (x++ < 20) {           // +1
    +            break;                  // +1
    +          }
    +        }
    +      } else if (y == t && !d) {    // +2
    +        x = a ? y : x;              // +1
    +      } else {
    +        x = 2;
    +      }
    +    }
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    classReportLevel80Total class complexity reporting thresholdno
    methodReportLevel10Cyclomatic complexity reporting thresholdno
    cycloOptions Choose options for the computation of Cycloyes. Delimiter is ‘|’.
    reportLevel10Deprecated Cyclomatic Complexity reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/CyclomaticComplexity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/CyclomaticComplexity">
    +    <properties>
    +        <property name="classReportLevel" value="80" />
    +        <property name="methodReportLevel" value="10" />
    +        <property name="cycloOptions" value="" />
    +    </properties>
    +</rule>
    +
    + +

    DataClass

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Data Classes are simple data holders, which reveal most of their state, and +without complex functionality. The lack of functionality may indicate that +their behaviour is defined elsewhere, which is a sign of poor data-behaviour +proximity. By directly exposing their internals, Data Classes break encapsulation, +and therefore reduce the system’s maintainability and understandability. Moreover, +classes tend to strongly rely on their data representation, which makes for a brittle +design.

    + +

    Refactoring a Data Class should focus on restoring a good data-behaviour proximity. In +most cases, that means moving the operations defined on the data back into the class. +In some other cases it may make sense to remove entirely the class and move the data +into the former client classes.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.DataClassRule

    + +

    Example(s):

    + +
    public class DataClass {
    +
    +  public int bar = 0;
    +  public int na = 0;
    +  private int bee = 0;
    +
    +  public void setBee(int n) {
    +    bee = n;
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/DataClass" />
    +
    + +

    DoNotExtendJavaLangError

    + +

    Since: PMD 4.0

    + +

    Priority: Medium (3)

    + +

    Errors are system exceptions. Do not extend them.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration/ExtendsList/ClassOrInterfaceType
    +  [pmd-java:typeIs('java.lang.Error')]
    +
    + +

    Example(s):

    + +
    public class Foo extends Error { }
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/DoNotExtendJavaLangError" />
    +
    + +

    ExceptionAsFlowControl

    + +

    Since: PMD 1.8

    + +

    Priority: Medium (3)

    + +

    Using Exceptions as form of flow control is not recommended as they obscure true exceptions when debugging. +Either add the necessary validation or use an alternate control structure.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.ExceptionAsFlowControlRule

    + +

    Example(s):

    + +
    public void bar() {
    +    try {
    +        try {
    +        } catch (Exception e) {
    +            throw new WrapperException(e);
    +            // this is essentially a GOTO to the WrapperException catch block
    +        }
    +    } catch (WrapperException e) {
    +        // do some more stuff
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/ExceptionAsFlowControl" />
    +
    + +

    ExcessiveClassLength

    + +

    Since: PMD 0.6

    + +

    Priority: Medium (3)

    + +

    Excessive class file lengths are usually indications that the class may be burdened with excessive +responsibilities that could be provided by external classes or functions. In breaking these methods +apart the code becomes more manageable and ripe for reuse.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.ExcessiveClassLengthRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar1() {
    +        // 1000 lines of code
    +    }
    +    public void bar2() {
    +        // 1000 lines of code
    +    }
    +    public void bar3() {
    +        // 1000 lines of code
    +    }
    +
    +    public void barN() {
    +        // 1000 lines of code
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum1000.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/ExcessiveClassLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/ExcessiveClassLength">
    +    <properties>
    +        <property name="minimum" value="1000.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessiveImports

    + +

    Since: PMD 1.04

    + +

    Priority: Medium (3)

    + +

    A high number of imports can indicate a high degree of coupling within an object. This rule +counts the number of unique imports and reports a violation if the count is above the +user-specified threshold.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.ExcessiveImportsRule

    + +

    Example(s):

    + +
    import blah.blah.Baz;
    +import blah.blah.Bif;
    +// 28 others from the same package elided
    +public class Foo {
    +    public void doWork() {}
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum30.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/ExcessiveImports" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/ExcessiveImports">
    +    <properties>
    +        <property name="minimum" value="30.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessiveMethodLength

    + +

    Since: PMD 0.6

    + +

    Priority: Medium (3)

    + +

    When methods are excessively long this usually indicates that the method is doing more than its +name/signature might suggest. They also become challenging for others to digest since excessive +scrolling causes readers to lose focus. +Try to reduce the method length by creating helper methods and removing any copy/pasted code.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.ExcessiveMethodLengthRule

    + +

    Example(s):

    + +
    public void doSomething() {
    +    System.out.println("Hello world!");
    +    System.out.println("Hello world!");
    +    // 98 copies omitted for brevity.
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum100.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/ExcessiveMethodLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/ExcessiveMethodLength">
    +    <properties>
    +        <property name="minimum" value="100.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessiveParameterList

    + +

    Since: PMD 0.9

    + +

    Priority: Medium (3)

    + +

    Methods with numerous parameters are a challenge to maintain, especially if most of them share the +same datatype. These situations usually denote the need for new objects to wrap the numerous parameters.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.ExcessiveParameterListRule

    + +

    Example(s):

    + +
    public void addPerson(      // too many arguments liable to be mixed up
    +    int birthYear, int birthMonth, int birthDate, int height, int weight, int ssn) {
    +
    +    . . . .
    +}
    +
    +public void addPerson(      // preferred approach
    +    Date birthdate, BodyMeasurements measurements, int ssn) {
    +
    +    . . . .
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum10.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/ExcessiveParameterList" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/ExcessiveParameterList">
    +    <properties>
    +        <property name="minimum" value="10.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessivePublicCount

    + +

    Since: PMD 1.04

    + +

    Priority: Medium (3)

    + +

    Classes with large numbers of public methods and attributes require disproportionate testing efforts +since combinational side effects grow rapidly and increase risk. Refactoring these classes into +smaller ones not only increases testability and reliability but also allows new variations to be +developed easily.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.ExcessivePublicCountRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public String value;
    +    public Bar something;
    +    public Variable var;
    +    // [... more more public attributes ...]
    +
    +    public void doWork() {}
    +    public void doMoreWork() {}
    +    public void doWorkAgain() {}
    +    // [... more more public methods ...]
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum45.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/ExcessivePublicCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/ExcessivePublicCount">
    +    <properties>
    +        <property name="minimum" value="45.0" />
    +    </properties>
    +</rule>
    +
    + +

    FinalFieldCouldBeStatic

    + +

    Since: PMD 1.1

    + +

    Priority: Medium (3)

    + +

    If a final field is assigned to a compile-time constant, it could be made static, thus saving overhead +in each object at runtime.

    + +

    This rule is defined by the following XPath expression:

    +
    //FieldDeclaration
    + [@Final= true() and @Static= false()]
    + [not(preceding-sibling::Annotation/MarkerAnnotation/Name[@Image="Builder.Default"]
    +    and //ImportDeclaration/Name[@Image="lombok.Builder"])]
    +/VariableDeclarator
    + [VariableInitializer/Expression/PrimaryExpression[not(PrimarySuffix)]/PrimaryPrefix/Literal]
    +/VariableDeclaratorId
    +
    + +

    Example(s):

    + +
    public class Foo {
    +  public final int BAR = 42; // this could be static and save some space
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/FinalFieldCouldBeStatic" />
    +
    + +

    GodClass

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    The God Class rule detects the God Class design flaw using metrics. God classes do too many things, +are very big and overly complex. They should be split apart to be more object-oriented. +The rule uses the detection strategy described in "Object-Oriented Metrics in Practice". +The violations are reported against the entire class.

    + +

    See also the references:

    + +

    Michele Lanza and Radu Marinescu. Object-Oriented Metrics in Practice: +Using Software Metrics to Characterize, Evaluate, and Improve the Design +of Object-Oriented Systems. Springer, Berlin, 1 edition, October 2006. Page 80.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.GodClassRule

    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/GodClass" />
    +
    + +

    ImmutableField

    + +

    Since: PMD 2.0

    + +

    Priority: Medium (3)

    + +

    Identifies private fields whose values never change once object initialization ends either in the declaration +of the field or by a constructor. This helps in converting existing classes to becoming immutable ones. +Note that this rule does not enforce referenced object to be immutable itself. A class can still be mutable, even +if all its member fields are declared final. This is referred to as shallow immutability. For more information on +mutability, see Effective Java, 3rd Edition, Item 17: Minimize mutability.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.ImmutableFieldRule

    + +

    Example(s):

    + +
    public class Foo {
    +  private int x; // could be final
    +  public Foo() {
    +      x = 7;
    +  }
    +  public void foo() {
    +     int a = x + 2;
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationslombok.Setter | lombok.Getter | lombok.Builder | lombok.Data | lombok.RequiredArgsConstructor | lombok.AllArgsConstructor | lombok.Value | lombok.NoArgsConstructorFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/ImmutableField" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/ImmutableField">
    +    <properties>
    +        <property name="ignoredAnnotations" value="lombok.Setter|lombok.Getter|lombok.Builder|lombok.Data|lombok.RequiredArgsConstructor|lombok.AllArgsConstructor|lombok.Value|lombok.NoArgsConstructor" />
    +    </properties>
    +</rule>
    +
    + +

    LawOfDemeter

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    The Law of Demeter is a simple rule, that says "only talk to friends". It helps to reduce coupling between classes +or objects.

    + +

    See also the references:

    + + + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.LawOfDemeterRule

    + +

    Example(s):

    + +
    public class Foo {
    +    /**
    +     * This example will result in two violations.
    +     */
    +    public void example(Bar b) {
    +        // this method call is ok, as b is a parameter of "example"
    +        C c = b.getC();
    +
    +        // this method call is a violation, as we are using c, which we got from B.
    +        // We should ask b directly instead, e.g. "b.doItOnC();"
    +        c.doIt();
    +
    +        // this is also a violation, just expressed differently as a method chain without temporary variables.
    +        b.getC().doIt();
    +
    +        // a constructor call, not a method call.
    +        D d = new D();
    +        // this method call is ok, because we have create the new instance of D locally.
    +        d.doSomethingElse();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/LawOfDemeter" />
    +
    + +

    LogicInversion

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Use opposite operator instead of negating the whole expression with a logic complement operator.

    + +

    This rule is defined by the following XPath expression:

    +
    //UnaryExpressionNotPlusMinus[@Image='!']/PrimaryExpression/PrimaryPrefix/Expression[EqualityExpression or RelationalExpression]
    +
    + +

    Example(s):

    + +
    public boolean bar(int a, int b) {
    +
    +    if (!(a == b)) { // use !=
    +         return false;
    +     }
    +
    +    if (!(a < b)) { // use >=
    +         return false;
    +    }
    +
    +    return true;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/LogicInversion" />
    +
    + +

    LoosePackageCoupling

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Avoid using classes from the configured package hierarchy outside of the package hierarchy, +except when using one of the configured allowed classes.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.LoosePackageCouplingRule

    + +

    Example(s):

    + +
    package some.package;
    +
    +import some.other.package.subpackage.subsubpackage.DontUseThisClass;
    +
    +public class Bar {
    +    DontUseThisClass boo = new DontUseThisClass();
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    packages Restricted packagesyes. Delimiter is ‘,’.
    classes Allowed classesyes. Delimiter is ‘,’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/LoosePackageCoupling" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/LoosePackageCoupling">
    +    <properties>
    +        <property name="packages" value="" />
    +        <property name="classes" value="" />
    +    </properties>
    +</rule>
    +
    + +

    ModifiedCyclomaticComplexity

    + +

    Deprecated

    + +

    Since: PMD 5.1.2

    + +

    Priority: Medium (3)

    + +

    Complexity directly affects maintenance costs is determined by the number of decision points in a method +plus one for the method entry. The decision points include ‘if’, ‘while’, ‘for’, and ‘case labels’ calls. +Generally, numbers ranging from 1-4 denote low complexity, 5-7 denote moderate complexity, 8-10 denote +high complexity, and 11+ is very high complexity. Modified complexity treats switch statements as a single +decision point.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the rule CyclomaticComplexity.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.ModifiedCyclomaticComplexityRule

    + +

    Example(s):

    + +
    public class Foo {    // This has a Cyclomatic Complexity = 9
    +1   public void example()  {
    +2       if (a == b)  {
    +3           if (a1 == b1) {
    +                fiddle();
    +4           } else if a2 == b2) {
    +                fiddle();
    +            }  else {
    +                fiddle();
    +            }
    +5       } else if (c == d) {
    +6           while (c == d) {
    +                fiddle();
    +            }
    +7        } else if (e == f) {
    +8           for (int n = 0; n < h; n++) {
    +                fiddle();
    +            }
    +        } else{
    +9           switch (z) {
    +                case 1:
    +                    fiddle();
    +                    break;
    +                case 2:
    +                    fiddle();
    +                    break;
    +                case 3:
    +                    fiddle();
    +                    break;
    +                default:
    +                    fiddle();
    +                    break;
    +            }
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    showMethodsComplexitytrueAdd method average violations to the reportno
    showClassesComplexitytrueAdd class average violations to the reportno
    reportLevel10Cyclomatic Complexity reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/ModifiedCyclomaticComplexity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/ModifiedCyclomaticComplexity">
    +    <properties>
    +        <property name="showMethodsComplexity" value="true" />
    +        <property name="showClassesComplexity" value="true" />
    +        <property name="reportLevel" value="10" />
    +    </properties>
    +</rule>
    +
    + +

    NcssConstructorCount

    + +

    Deprecated

    + +

    Since: PMD 3.9

    + +

    Priority: Medium (3)

    + +

    This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of lines +of code for a given constructor. NCSS ignores comments, and counts actual statements. Using this algorithm, +lines of code that are split are counted as one.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the rule NcssCount.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.NcssConstructorCountRule

    + +

    Example(s):

    + +
    public class Foo extends Bar {
    +    public Foo() {
    +        super();
    +
    +
    +
    +
    +
    +        //this constructor only has 1 NCSS lines
    +        super.foo();
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum100.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/NcssConstructorCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/NcssConstructorCount">
    +    <properties>
    +        <property name="minimum" value="100.0" />
    +    </properties>
    +</rule>
    +
    + +

    NcssCount

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    This rule uses the NCSS (Non-Commenting Source Statements) metric to determine the number of lines +of code in a class, method or constructor. NCSS ignores comments, blank lines, and only counts actual +statements. For more details on the calculation, see the documentation of +the NCSS metric.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.NcssCountRule

    + +

    Example(s):

    + +
    import java.util.Collections;       // +0
    +import java.io.IOException;         // +0
    +
    +class Foo {                         // +1, total Ncss = 12
    +
    +  public void bigMethod()           // +1
    +      throws IOException {
    +    int x = 0, y = 2;               // +1
    +    boolean a = false, b = true;    // +1
    +
    +    if (a || b) {                   // +1
    +      try {                         // +1
    +        do {                        // +1
    +          x += 2;                   // +1
    +        } while (x < 12);
    +
    +        System.exit(0);             // +1
    +      } catch (IOException ioe) {   // +1
    +        throw new PatheticFailException(ioe); // +1
    +      }
    +    } else {
    +      assert false;                 // +1
    +    }
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    methodReportLevel60NCSS reporting threshold for methodsno
    classReportLevel1500NCSS reporting threshold for classesno
    ncssOptions Choose options for the computation of Ncssyes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/NcssCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/NcssCount">
    +    <properties>
    +        <property name="methodReportLevel" value="60" />
    +        <property name="classReportLevel" value="1500" />
    +        <property name="ncssOptions" value="" />
    +    </properties>
    +</rule>
    +
    + +

    NcssMethodCount

    + +

    Deprecated

    + +

    Since: PMD 3.9

    + +

    Priority: Medium (3)

    + +

    This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of lines +of code for a given method. NCSS ignores comments, and counts actual statements. Using this algorithm, +lines of code that are split are counted as one.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the rule NcssCount.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.NcssMethodCountRule

    + +

    Example(s):

    + +
    public class Foo extends Bar {
    +    public int methd() {
    +        super.methd();
    +
    +
    +
    +
    +
    +
    +        //this method only has 1 NCSS lines
    +        return 1;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum100.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/NcssMethodCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/NcssMethodCount">
    +    <properties>
    +        <property name="minimum" value="100.0" />
    +    </properties>
    +</rule>
    +
    + +

    NcssTypeCount

    + +

    Deprecated

    + +

    Since: PMD 3.9

    + +

    Priority: Medium (3)

    + +

    This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of lines +of code for a given type. NCSS ignores comments, and counts actual statements. Using this algorithm, +lines of code that are split are counted as one.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the rule NcssCount.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.NcssTypeCountRule

    + +

    Example(s):

    + +
    public class Foo extends Bar {
    +    public Foo() {
    +        //this class only has 6 NCSS lines
    +        super();
    +
    +
    +
    +
    +
    +        super.foo();
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum1500.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/NcssTypeCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/NcssTypeCount">
    +    <properties>
    +        <property name="minimum" value="1500.0" />
    +    </properties>
    +</rule>
    +
    + +

    NPathComplexity

    + +

    Since: PMD 3.9

    + +

    Priority: Medium (3)

    + +

    The NPath complexity of a method is the number of acyclic execution paths through that method. +While cyclomatic complexity counts the number of decision points in a method, NPath counts the number of +full paths from the beginning to the end of the block of the method. That metric grows exponentially, as +it multiplies the complexity of statements in the same block. For more details on the calculation, see the +documentation of the NPath metric.

    + +

    A threshold of 200 is generally considered the point where measures should be taken to reduce +complexity and increase readability.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.NPathComplexityRule

    + +

    Example(s):

    + +
    public class Foo {
    +  public static void bar() { // Ncss = 252: reported!
    +    boolean a, b = true;
    +    try { // 2 * 2 + 2 = 6
    +      if (true) { // 2
    +        List buz = new ArrayList();
    +      }
    +
    +      for(int i = 0; i < 19; i++) { // * 2
    +        List buz = new ArrayList();
    +      }
    +    } catch(Exception e) {
    +      if (true) { // 2
    +        e.printStackTrace();
    +      }
    +    }
    +
    +    while (j++ < 20) { //  * 2
    +      List buz = new ArrayList();
    +    }
    +
    +    switch(j) { // * 7
    +      case 1:
    +      case 2: break;
    +      case 3: j = 5; break;
    +      case 4: if (b && a) { bar(); } break;
    +      default: break;
    +    }
    +
    +    do { // * 3
    +        List buz = new ArrayList();
    +    } while (a && j++ < 30);
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    reportLevel200N-Path Complexity reporting thresholdno
    minimum200.0Deprecated Minimum reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/NPathComplexity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/NPathComplexity">
    +    <properties>
    +        <property name="reportLevel" value="200" />
    +    </properties>
    +</rule>
    +
    + +

    SignatureDeclareThrowsException

    + +

    Since: PMD 1.2

    + +

    Priority: Medium (3)

    + +

    A method/constructor shouldn’t explicitly throw the generic java.lang.Exception, since it +is unclear which exceptions that can be thrown from the methods. It might be +difficult to document and understand such vague interfaces. Use either a class +derived from RuntimeException or a checked exception.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.SignatureDeclareThrowsExceptionRule

    + +

    Example(s):

    + +
    public void foo() throws Exception {
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    IgnoreJUnitCompletelyfalseAllow all methods in a JUnit testcase to throw Exceptionsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/SignatureDeclareThrowsException" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/SignatureDeclareThrowsException">
    +    <properties>
    +        <property name="IgnoreJUnitCompletely" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    SimplifiedTernary

    + +

    Since: PMD 5.4.0

    + +

    Priority: Medium (3)

    + +

    Look for ternary operators with the form condition ? literalBoolean : foo +or condition ? foo : literalBoolean.

    + +

    These expressions can be simplified respectively to +condition || foo when the literalBoolean is true +!condition && foo when the literalBoolean is false +or +!condition || foo when the literalBoolean is true +condition && foo when the literalBoolean is false

    + +

    This rule is defined by the following XPath expression:

    +
    //ConditionalExpression[not(PrimaryExpression/*/Literal) and (Expression/PrimaryExpression/*/Literal/BooleanLiteral)]
    +|
    +//ConditionalExpression[not(Expression/PrimaryExpression/*/Literal) and (PrimaryExpression/*/Literal/BooleanLiteral)]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public boolean test() {
    +        return condition ? true : something(); // can be as simple as return condition || something();
    +    }
    +
    +    public void test2() {
    +        final boolean value = condition ? false : something(); // can be as simple as value = !condition && something();
    +    }
    +
    +    public boolean test3() {
    +        return condition ? something() : true; // can be as simple as return !condition || something();
    +    }
    +
    +    public void test4() {
    +        final boolean otherValue = condition ? something() : false; // can be as simple as condition && something();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/SimplifiedTernary" />
    +
    + +

    SimplifyBooleanAssertion

    + +

    Since: PMD 3.6

    + +

    Priority: Medium (3)

    + +

    Avoid negation in an assertTrue or assertFalse test.

    + +

    For example, rephrase:

    + +
    assertTrue(!expr);
    +
    + +

    as:

    + +
    assertFalse(expr);
    +
    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[
    +    pmd-java:typeIs('junit.framework.TestCase')
    +    or .//MarkerAnnotation/Name[
    +        pmd-java:typeIs('org.junit.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.RepeatedTest')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestFactory')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestTemplate')
    +        or pmd-java:typeIs('org.junit.jupiter.params.ParameterizedTest')
    +        ]
    +    ]
    +//StatementExpression
    +[
    +    .//Name[@Image='assertTrue' or  @Image='assertFalse']
    +    and
    +    PrimaryExpression/PrimarySuffix/Arguments/ArgumentList/Expression/UnaryExpressionNotPlusMinus[@Image='!']
    +        /PrimaryExpression/PrimaryPrefix
    +]
    +
    + +

    Example(s):

    + +
    public class SimpleTest extends TestCase {
    +    public void testX() {
    +        assertTrue("not empty", !r.isEmpty());  // replace with assertFalse("not empty", r.isEmpty())
    +        assertFalse(!r.isEmpty());              // replace with assertTrue(r.isEmpty())
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/SimplifyBooleanAssertion" />
    +
    + +

    SimplifyBooleanExpressions

    + +

    Since: PMD 1.05

    + +

    Priority: Medium (3)

    + +

    Avoid unnecessary comparisons in boolean expressions, they serve no purpose and impacts readability.

    + +

    This rule is defined by the following XPath expression:

    +
    //EqualityExpression/PrimaryExpression
    + /PrimaryPrefix/Literal/BooleanLiteral
    +
    + +

    Example(s):

    + +
    public class Bar {
    +  // can be simplified to
    +  // bar = isFoo();
    +  private boolean bar = (isFoo() == true);
    +
    +  public isFoo() { return false;}
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/SimplifyBooleanExpressions" />
    +
    + +

    SimplifyBooleanReturns

    + +

    Since: PMD 0.9

    + +

    Priority: Medium (3)

    + +

    Avoid unnecessary if-then-else statements when returning a boolean. The result of +the conditional test can be returned instead.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.SimplifyBooleanReturnsRule

    + +

    Example(s):

    + +
    public boolean isBarEqualTo(int x) {
    +    if (bar == x) {      // this bit of code...
    +        return true;
    +    } else {
    +        return false;
    +    }
    +}
    +
    +public boolean isBarEqualTo(int x) {
    +    return bar == x;    // can be replaced with this
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/SimplifyBooleanReturns" />
    +
    + +

    SimplifyConditional

    + +

    Since: PMD 3.1

    + +

    Priority: Medium (3)

    + +

    No need to check for null before an instanceof; the instanceof keyword returns false when given a null argument.

    + +

    This rule is defined by the following XPath expression:

    +
    //Expression
    + [ConditionalOrExpression
    + [EqualityExpression[@Image='==']
    +  //NullLiteral
    +  and
    +  UnaryExpressionNotPlusMinus
    +   [@Image='!']//InstanceOfExpression[PrimaryExpression
    +     //Name/@Image = ancestor::ConditionalOrExpression/EqualityExpression
    +      /PrimaryExpression/PrimaryPrefix/Name/@Image]
    +  and
    +  (count(UnaryExpressionNotPlusMinus) + 1 = count(*))
    + ]
    +or
    +ConditionalAndExpression
    + [EqualityExpression[@Image='!=']//NullLiteral
    + and
    +InstanceOfExpression
    + [PrimaryExpression[not(PrimarySuffix[@ArrayDereference= true()])]
    +  //Name[not(contains(@Image,'.'))]/@Image = ancestor::ConditionalAndExpression
    +   /EqualityExpression/PrimaryExpression/PrimaryPrefix/Name/@Image]
    + and
    +(count(InstanceOfExpression) + 1 = count(*))
    + ]
    +]
    +
    + +

    Example(s):

    + +
    class Foo {
    +  void bar(Object x) {
    +    if (x != null && x instanceof Bar) {
    +      // just drop the "x != null" check
    +    }
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/SimplifyConditional" />
    +
    + +

    SingularField

    + +

    Since: PMD 3.1

    + +

    Priority: Medium (3)

    + +

    Fields whose scopes are limited to just single methods do not rely on the containing +object to provide them to other methods. They may be better implemented as local variables +within those methods.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.SingularFieldRule

    + +

    Example(s):

    + +
    public class Foo {
    +    private int x;  // no reason to exist at the Foo instance level
    +    public void foo(int y) {
    +     x = y + 5;
    +     return x;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationslombok.Setter | lombok.Getter | lombok.Builder | lombok.Data | lombok.RequiredArgsConstructor | lombok.AllArgsConstructor | lombok.Value | lombok.NoArgsConstructor | lombok.experimental.Delegate | lombok.EqualsAndHashCodeFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    checkInnerClassesfalseCheck inner classesno
    disallowNotAssignmentfalseDisallow violations where the first usage is not an assignmentno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/SingularField" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/SingularField">
    +    <properties>
    +        <property name="ignoredAnnotations" value="lombok.Setter|lombok.Getter|lombok.Builder|lombok.Data|lombok.RequiredArgsConstructor|lombok.AllArgsConstructor|lombok.Value|lombok.NoArgsConstructor|lombok.experimental.Delegate|lombok.EqualsAndHashCode" />
    +        <property name="checkInnerClasses" value="false" />
    +        <property name="disallowNotAssignment" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    StdCyclomaticComplexity

    + +

    Deprecated

    + +

    Since: PMD 5.1.2

    + +

    Priority: Medium (3)

    + +

    Complexity directly affects maintenance costs is determined by the number of decision points in a method +plus one for the method entry. The decision points include ‘if’, ‘while’, ‘for’, and ‘case labels’ calls. +Generally, numbers ranging from 1-4 denote low complexity, 5-7 denote moderate complexity, 8-10 denote +high complexity, and 11+ is very high complexity.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. The rule is replaced +by the rule CyclomaticComplexity.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.StdCyclomaticComplexityRule

    + +

    Example(s):

    + +
    public class Foo {    // This has a Cyclomatic Complexity = 12
    +1   public void example()  {
    +2       if (a == b || (c == d && e == f))  { // Only one
    +3           if (a1 == b1) {
    +                fiddle();
    +4           } else if a2 == b2) {
    +                fiddle();
    +            }  else {
    +                fiddle();
    +            }
    +5       } else if (c == d) {
    +6           while (c == d) {
    +                fiddle();
    +            }
    +7        } else if (e == f) {
    +8           for (int n = 0; n < h; n++) {
    +                fiddle();
    +            }
    +        } else{
    +            switch (z) {
    +9               case 1:
    +                    fiddle();
    +                    break;
    +10              case 2:
    +                    fiddle();
    +                    break;
    +11              case 3:
    +                    fiddle();
    +                    break;
    +12              default:
    +                    fiddle();
    +                    break;
    +            }
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    showMethodsComplexitytrueAdd method average violations to the reportno
    showClassesComplexitytrueAdd class average violations to the reportno
    reportLevel10Cyclomatic Complexity reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/StdCyclomaticComplexity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/StdCyclomaticComplexity">
    +    <properties>
    +        <property name="showMethodsComplexity" value="true" />
    +        <property name="showClassesComplexity" value="true" />
    +        <property name="reportLevel" value="10" />
    +    </properties>
    +</rule>
    +
    + +

    SwitchDensity

    + +

    Since: PMD 1.02

    + +

    Priority: Medium (3)

    + +

    A high ratio of statements to labels in a switch statement implies that the switch statement +is overloaded. Consider moving the statements into new methods or creating subclasses based +on the switch variable.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.SwitchDensityRule

    + +

    Example(s):

    + +
    public class Foo {
    +  public void bar(int x) {
    +    switch (x) {
    +      case 1: {
    +        // lots of statements
    +        break;
    +      } case 2: {
    +        // lots of statements
    +        break;
    +      }
    +    }
    +  }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum10.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/SwitchDensity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/SwitchDensity">
    +    <properties>
    +        <property name="minimum" value="10.0" />
    +    </properties>
    +</rule>
    +
    + +

    TooManyFields

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    Classes that have too many fields can become unwieldy and could be redesigned to have fewer fields, +possibly through grouping related fields in new objects. For example, a class with individual +city/state/zip fields could park them within a single Address field.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.TooManyFieldsRule

    + +

    Example(s):

    + +
    public class Person {   // too many separate fields
    +   int birthYear;
    +   int birthMonth;
    +   int birthDate;
    +   float height;
    +   float weight;
    +}
    +
    +public class Person {   // this is more manageable
    +   Date birthDate;
    +   BodyMeasurements measurements;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maxfields15Max allowable fieldsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/TooManyFields" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/TooManyFields">
    +    <properties>
    +        <property name="maxfields" value="15" />
    +    </properties>
    +</rule>
    +
    + +

    TooManyMethods

    + +

    Since: PMD 4.2

    + +

    Priority: Medium (3)

    + +

    A class with too many methods is probably a good suspect for refactoring, in order to reduce its +complexity and find a way to have more fine grained objects.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration/ClassOrInterfaceBody
    +     [
    +      count(./ClassOrInterfaceBodyDeclaration/MethodDeclaration[
    +         not (
    +                starts-with(@Name,'get')
    +                or
    +                starts-with(@Name,'set')
    +                or
    +                starts-with(@Name,'is')
    +            )
    +      ]) > $maxmethods
    +   ]
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maxmethods10The method count reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/TooManyMethods" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/TooManyMethods">
    +    <properties>
    +        <property name="maxmethods" value="10" />
    +    </properties>
    +</rule>
    +
    + +

    UselessOverridingMethod

    + +

    Since: PMD 3.3

    + +

    Priority: Medium (3)

    + +

    The overriding method merely calls the same method defined in a superclass.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.UselessOverridingMethodRule

    + +

    Example(s):

    + +
    public void foo(String bar) {
    +    super.foo(bar);      // why bother overriding?
    +}
    +
    +public String foo() {
    +    return super.foo();  // why bother overriding?
    +}
    +
    +@Id
    +public Long getId() {
    +    return super.getId();  // OK if 'ignoreAnnotations' is false, which is the default behavior
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoreAnnotationsfalseIgnore annotationsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/UselessOverridingMethod" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/UselessOverridingMethod">
    +    <properties>
    +        <property name="ignoreAnnotations" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    UseObjectForClearerAPI

    + +

    Since: PMD 4.2.6

    + +

    Priority: Medium (3)

    + +

    When you write a public method, you should be thinking in terms of an API. If your method is public, it means other class +will use it, therefore, you want (or need) to offer a comprehensive and evolutive API. If you pass a lot of information +as a simple series of Strings, you may think of using an Object to represent all those information. You’ll get a simpler +API (such as doWork(Workload workload), rather than a tedious series of Strings) and more importantly, if you need at some +point to pass extra data, you’ll be able to do so by simply modifying or extending Workload without any modification to +your API.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Public=true()]/MethodDeclarator/FormalParameters[
    +     count(FormalParameter/Type/ReferenceType/ClassOrInterfaceType[@Image = 'String' and @Array=false()]) > 3
    +]
    +
    + +

    Example(s):

    + +
    public class MyClass {
    +    public void connect(String username,
    +        String pssd,
    +        String databaseName,
    +        String databaseAdress)
    +        // Instead of those parameters object
    +        // would ensure a cleaner API and permit
    +        // to add extra data transparently (no code change):
    +        // void connect(UserData data);
    +    {
    +
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/design.xml/UseObjectForClearerAPI" />
    +
    + +

    UseUtilityClass

    + +

    Since: PMD 0.3

    + +

    Priority: Medium (3)

    + +

    For classes that only have static methods, consider making them utility classes. +Note that this doesn’t apply to abstract classes, since their subclasses may +well include non-static methods. Also, if you want this class to be a utility class, +remember to add a private constructor to prevent instantiation. +(Note, that this use was known before PMD 5.1.0 as UseSingleton).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.design.UseUtilityClassRule

    + +

    Example(s):

    + +
    public class MaybeAUtility {
    +  public static void foo() {}
    +  public static void bar() {}
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationslombok.experimental.UtilityClassFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/design.xml/UseUtilityClass" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/design.xml/UseUtilityClass">
    +    <properties>
    +        <property name="ignoredAnnotations" value="lombok.experimental.UtilityClass" />
    +    </properties>
    +</rule>
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_java_documentation.html b/pmd_rules_java_documentation.html new file mode 100644 index 0000000000..f32b04803b --- /dev/null +++ b/pmd_rules_java_documentation.html @@ -0,0 +1,1763 @@ + + + + + + + + +Documentation | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Documentation

    +
    + + + +
    + + +
    Rules that are related to code documentation.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    CommentContent

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    A rule for the politically correct… we don’t want to offend anyone.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.documentation.CommentContentRule

    + +

    Example(s):

    + +
    //OMG, this is horrible, Bob is an idiot !!!
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    caseSensitivefalseCase sensitiveno
    disallowedTermsidiot | jerkIllegal terms or phrasesyes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/documentation.xml/CommentContent" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/documentation.xml/CommentContent">
    +    <properties>
    +        <property name="caseSensitive" value="false" />
    +        <property name="disallowedTerms" value="idiot|jerk" />
    +    </properties>
    +</rule>
    +
    + +

    CommentRequired

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Denotes whether javadoc (formal) comments are required (or unwanted) for specific language elements.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.documentation.CommentRequiredRule

    + +

    Example(s):

    + +
    /**
    +*
    +*
    +* @author Jon Doe
    +*/
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    methodWithOverrideCommentRequirementIgnoredComments on @Override methods. Possible values: [Required, Ignored, Unwanted]no
    accessorCommentRequirementIgnoredComments on getters and setters". Possible values: [Required, Ignored, Unwanted]no
    classCommentRequirementRequiredClass comments. Possible values: [Required, Ignored, Unwanted]no
    headerCommentRequirementRequiredDeprecated Header comments. Please use the property "classCommentRequired" instead.. Possible values: [Required, Ignored, Unwanted]no
    fieldCommentRequirementRequiredField comments. Possible values: [Required, Ignored, Unwanted]no
    publicMethodCommentRequirementRequiredPublic method and constructor comments. Possible values: [Required, Ignored, Unwanted]no
    protectedMethodCommentRequirementRequiredProtected method constructor comments. Possible values: [Required, Ignored, Unwanted]no
    enumCommentRequirementRequiredEnum comments. Possible values: [Required, Ignored, Unwanted]no
    serialVersionUIDCommentRequiredIgnoredSerial version UID comments. Possible values: [Required, Ignored, Unwanted]no
    serialPersistentFieldsCommentRequiredIgnoredSerial persistent fields comments. Possible values: [Required, Ignored, Unwanted]no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/documentation.xml/CommentRequired" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/documentation.xml/CommentRequired">
    +    <properties>
    +        <property name="methodWithOverrideCommentRequirement" value="Ignored" />
    +        <property name="accessorCommentRequirement" value="Ignored" />
    +        <property name="classCommentRequirement" value="Required" />
    +        <property name="fieldCommentRequirement" value="Required" />
    +        <property name="publicMethodCommentRequirement" value="Required" />
    +        <property name="protectedMethodCommentRequirement" value="Required" />
    +        <property name="enumCommentRequirement" value="Required" />
    +        <property name="serialVersionUIDCommentRequired" value="Ignored" />
    +        <property name="serialPersistentFieldsCommentRequired" value="Ignored" />
    +    </properties>
    +</rule>
    +
    + +

    CommentSize

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Determines whether the dimensions of non-header comments found are within the specified limits.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.documentation.CommentSizeRule

    + +

    Example(s):

    + +
    /**
    +*
    +*   too many lines!
    +*
    +*
    +*
    +*
    +*
    +*
    +*
    +*
    +*
    +*
    +*
    +*
    +*/
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maxLines6Maximum linesno
    maxLineLength80Maximum line lengthno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/documentation.xml/CommentSize" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/documentation.xml/CommentSize">
    +    <properties>
    +        <property name="maxLines" value="6" />
    +        <property name="maxLineLength" value="80" />
    +    </properties>
    +</rule>
    +
    + +

    UncommentedEmptyConstructor

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Uncommented Empty Constructor finds instances where a constructor does not +contain statements, but there is no comment. By explicitly commenting empty +constructors it is easier to distinguish between intentional (commented) +and unintentional empty constructors.

    + +

    This rule is defined by the following XPath expression:

    +
    //ConstructorDeclaration[@Private= false()]
    +                        [@containsComment = false()]
    +                        [not(BlockStatement)]
    +                        [$ignoreExplicitConstructorInvocation = true() or not(ExplicitConstructorInvocation)]
    +                        [not(../Annotation/MarkerAnnotation/Name[pmd-java:typeIs('javax.inject.Inject')])]
    +
    + +

    Example(s):

    + +
    public Foo() {
    +  // This constructor is intentionally empty. Nothing special is needed here.
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoreExplicitConstructorInvocationfalseIgnore explicit constructor invocation when deciding whether constructor is empty or notno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/documentation.xml/UncommentedEmptyConstructor" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/documentation.xml/UncommentedEmptyConstructor">
    +    <properties>
    +        <property name="ignoreExplicitConstructorInvocation" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    UncommentedEmptyMethodBody

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Uncommented Empty Method Body finds instances where a method body does not contain +statements, but there is no comment. By explicitly commenting empty method bodies +it is easier to distinguish between intentional (commented) and unintentional +empty methods.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration/Block[count(BlockStatement) = 0 and @containsComment = false()]
    +
    + +

    Example(s):

    + +
    public void doSomething() {
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/documentation.xml/UncommentedEmptyMethodBody" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_java_errorprone.html b/pmd_rules_java_errorprone.html new file mode 100644 index 0000000000..96e629d3f1 --- /dev/null +++ b/pmd_rules_java_errorprone.html @@ -0,0 +1,5277 @@ + + + + + + + + +Error Prone | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Error Prone

    +
    + + + +
    + + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AssignmentInOperand

    + +

    Since: PMD 1.03

    + +

    Priority: Medium (3)

    + +

    Avoid assignments in operands; this can make code more complicated and harder to read.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AssignmentInOperandRule

    + +

    Example(s):

    + +
    public void bar() {
    +    int x = 2;
    +    if ((x = getX()) == 3) {
    +      System.out.println("3!");
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    allowIffalseAllow assignment within the conditional expression of an if statementno
    allowForfalseAllow assignment within the conditional expression of a for statementno
    allowWhilefalseAllow assignment within the conditional expression of a while statementno
    allowIncrementDecrementfalseAllow increment or decrement operators within the conditional expression of an if, for, or while statementno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/AssignmentInOperand" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/AssignmentInOperand">
    +    <properties>
    +        <property name="allowIf" value="false" />
    +        <property name="allowFor" value="false" />
    +        <property name="allowWhile" value="false" />
    +        <property name="allowIncrementDecrement" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    AssignmentToNonFinalStatic

    + +

    Since: PMD 2.2

    + +

    Priority: Medium (3)

    + +

    Identifies a possible unsafe usage of a static field.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AssignmentToNonFinalStaticRule

    + +

    Example(s):

    + +
    public class StaticField {
    +   static int x;
    +   public FinalFields(int y) {
    +    x = y; // unsafe
    +   }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AssignmentToNonFinalStatic" />
    +
    + +

    AvoidAccessibilityAlteration

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    Methods such as getDeclaredConstructors(), getDeclaredConstructor(Class[]) and setAccessible(), +as the interface PrivilegedAction, allow for the runtime alteration of variable, class, or +method visibility, even if they are private. This violates the principle of encapsulation.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryExpression[
    +(
    +(PrimarySuffix[
    +        ends-with(@Image,'getDeclaredConstructors')
    +                or
    +        ends-with(@Image,'getDeclaredConstructor')
    +                or
    +        ends-with(@Image,'setAccessible')
    +        ])
    +or
    +(PrimaryPrefix/Name[
    +        ends-with(@Image,'getDeclaredConstructor')
    +        or
    +        ends-with(@Image,'getDeclaredConstructors')
    +        or
    +        starts-with(@Image,'AccessibleObject.setAccessible')
    +        ])
    +)
    +and
    +(//ImportDeclaration/Name[
    +        contains(@Image,'java.security.PrivilegedAction')])
    +]
    +
    + +

    Example(s):

    + +
    import java.lang.reflect.AccessibleObject;
    +import java.lang.reflect.Method;
    +import java.security.PrivilegedAction;
    +
    +public class Violation {
    +  public void invalidCallsInMethod() throws SecurityException, NoSuchMethodException {
    +    // Possible call to forbidden getDeclaredConstructors
    +    Class[] arrayOfClass = new Class[1];
    +    this.getClass().getDeclaredConstructors();
    +    this.getClass().getDeclaredConstructor(arrayOfClass);
    +    Class clazz = this.getClass();
    +    clazz.getDeclaredConstructor(arrayOfClass);
    +    clazz.getDeclaredConstructors();
    +      // Possible call to forbidden setAccessible
    +    clazz.getMethod("", arrayOfClass).setAccessible(false);
    +    AccessibleObject.setAccessible(null, false);
    +    Method.setAccessible(null, false);
    +    Method[] methodsArray = clazz.getMethods();
    +    int nbMethod;
    +    for ( nbMethod = 0; nbMethod < methodsArray.length; nbMethod++ ) {
    +      methodsArray[nbMethod].setAccessible(false);
    +    }
    +
    +      // Possible call to forbidden PrivilegedAction
    +    PrivilegedAction priv = (PrivilegedAction) new Object(); priv.run();
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidAccessibilityAlteration" />
    +
    + +

    AvoidAssertAsIdentifier

    + +

    Since: PMD 3.4

    + +

    Priority: Medium High (2)

    + +

    Use of the term ‘assert’ will conflict with newer versions of Java since it is a reserved word.

    + +

    This rule is defined by the following XPath expression:

    +
    //VariableDeclaratorId[@Name='assert']
    +
    + +

    Example(s):

    + +
    public class A {
    +    public class Foo {
    +        String assert = "foo";
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidAssertAsIdentifier" />
    +
    + +

    AvoidBranchingStatementAsLastInLoop

    + +

    Since: PMD 5.0

    + +

    Priority: Medium High (2)

    + +

    Using a branching statement as the last part of a loop may be a bug, and/or is confusing. +Ensure that the usage is not a bug, or consider using another approach.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AvoidBranchingStatementAsLastInLoopRule

    + +

    Example(s):

    + +
    // unusual use of branching statement in a loop
    +for (int i = 0; i < 10; i++) {
    +    if (i*i <= 25) {
    +        continue;
    +    }
    +    break;
    +}
    +
    +// this makes more sense...
    +for (int i = 0; i < 10; i++) {
    +    if (i*i > 25) {
    +        break;
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    checkBreakLoopTypesfor | do | whileList of loop types in which break statements will be checkedyes. Delimiter is ‘|’.
    checkContinueLoopTypesfor | do | whileList of loop types in which continue statements will be checkedyes. Delimiter is ‘|’.
    checkReturnLoopTypesfor | do | whileList of loop types in which return statements will be checkedyes. Delimiter is ‘|’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidBranchingStatementAsLastInLoop" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/AvoidBranchingStatementAsLastInLoop">
    +    <properties>
    +        <property name="checkBreakLoopTypes" value="for|do|while" />
    +        <property name="checkContinueLoopTypes" value="for|do|while" />
    +        <property name="checkReturnLoopTypes" value="for|do|while" />
    +    </properties>
    +</rule>
    +
    + +

    AvoidCallingFinalize

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    The method Object.finalize() is called by the garbage collector on an object when garbage collection determines +that there are no more references to the object. It should not be invoked by application logic.

    + +

    Note that Oracle has declared Object.finalize() as deprecated since JDK 9.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AvoidCallingFinalizeRule

    + +

    Example(s):

    + +
    void foo() {
    +    Bar b = new Bar();
    +    b.finalize();
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidCallingFinalize" />
    +
    + +

    AvoidCatchingNPE

    + +

    Since: PMD 1.8

    + +

    Priority: Medium (3)

    + +

    Code should never throw NullPointerExceptions under normal circumstances. A catch block may hide the +original error, causing other, more subtle problems later on.

    + +

    This rule is defined by the following XPath expression:

    +
    //CatchStatement/FormalParameter/Type
    + /ReferenceType/ClassOrInterfaceType[@Image='NullPointerException']
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    void bar() {
    +        try {
    +            // do something
    +        } catch (NullPointerException npe) {
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidCatchingNPE" />
    +
    + +

    AvoidCatchingThrowable

    + +

    Since: PMD 1.2

    + +

    Priority: Medium (3)

    + +

    Catching Throwable errors is not recommended since its scope is very broad. It includes runtime issues such as +OutOfMemoryError that should be exposed and managed separately.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AvoidCatchingThrowableRule

    + +

    Example(s):

    + +
    public void bar() {
    +    try {
    +        // do something
    +    } catch (Throwable th) {  // should not catch Throwable
    +        th.printStackTrace();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidCatchingThrowable" />
    +
    + +

    AvoidDecimalLiteralsInBigDecimalConstructor

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    One might assume that the result of "new BigDecimal(0.1)" is exactly equal to 0.1, but it is actually +equal to .1000000000000000055511151231257827021181583404541015625. +This is because 0.1 cannot be represented exactly as a double (or as a binary fraction of any finite +length). Thus, the long value that is being passed in to the constructor is not exactly equal to 0.1, +appearances notwithstanding.

    + +

    The (String) constructor, on the other hand, is perfectly predictable: ‘new BigDecimal("0.1")’ is +exactly equal to 0.1, as one would expect. Therefore, it is generally recommended that the +(String) constructor be used in preference to this one.

    + +

    This rule is defined by the following XPath expression:

    +
    //AllocationExpression[pmd-java:typeIs('java.math.BigDecimal')]
    +[Arguments/ArgumentList/Expression/PrimaryExpression
    +    [
    +        pmd-java:typeIs('float') or
    +        pmd-java:typeIs('java.lang.Float') or
    +        pmd-java:typeIs('double') or
    +        pmd-java:typeIs('java.lang.Double')
    +    ]
    +]
    +
    + +

    Example(s):

    + +
    BigDecimal bd = new BigDecimal(1.123);       // loss of precision, this would trigger the rule
    +
    +BigDecimal bd = new BigDecimal("1.123");     // preferred approach
    +
    +BigDecimal bd = new BigDecimal(12);          // preferred approach, ok for integer values
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidDecimalLiteralsInBigDecimalConstructor" />
    +
    + +

    AvoidDuplicateLiterals

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    Code containing duplicate String literals can usually be improved by declaring the String as a constant field.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AvoidDuplicateLiteralsRule

    + +

    Example(s):

    + +
    private void bar() {
    +     buz("Howdy");
    +     buz("Howdy");
    +     buz("Howdy");
    +     buz("Howdy");
    +}
    +private void buz(String x) {}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    exceptionfile Deprecated (Use ‘exceptionList’ property) File containing strings to skip (one string per line), only used if ignore list is not set. File must be UTF-8 encoded.no
    separator,Ignore list separatorno
    maxDuplicateLiterals4Max duplicate literalsno
    minimumLength3Minimum string length to checkno
    skipAnnotationsfalseSkip literals within annotationsno
    exceptionList List of literals to ignore. A literal is ignored if its image can be found in this list. Components of this list should not be surrounded by double quotes.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidDuplicateLiterals" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/AvoidDuplicateLiterals">
    +    <properties>
    +        <property name="separator" value="," />
    +        <property name="maxDuplicateLiterals" value="4" />
    +        <property name="minimumLength" value="3" />
    +        <property name="skipAnnotations" value="false" />
    +        <property name="exceptionList" value="" />
    +    </properties>
    +</rule>
    +
    + +

    AvoidEnumAsIdentifier

    + +

    Since: PMD 3.4

    + +

    Priority: Medium High (2)

    + +

    Use of the term ‘enum’ will conflict with newer versions of Java since it is a reserved word.

    + +

    This rule is defined by the following XPath expression:

    +
    //VariableDeclaratorId[@Name='enum']
    +
    + +

    Example(s):

    + +
    public class A {
    +    public class Foo {
    +        String enum = "foo";
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidEnumAsIdentifier" />
    +
    + +

    AvoidFieldNameMatchingMethodName

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    It can be confusing to have a field name with the same name as a method. While this is permitted, +having information (field) and actions (method) is not clear naming. Developers versed in +Smalltalk often prefer this approach as the methods denote accessor methods.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AvoidFieldNameMatchingMethodNameRule

    + +

    Example(s):

    + +
    public class Foo {
    +    Object bar;
    +    // bar is data or an action or both?
    +    void bar() {
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidFieldNameMatchingMethodName" />
    +
    + +

    AvoidFieldNameMatchingTypeName

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    It is somewhat confusing to have a field name matching the declaring class name. +This probably means that type and/or field names should be chosen more carefully.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AvoidFieldNameMatchingTypeNameRule

    + +

    Example(s):

    + +
    public class Foo extends Bar {
    +    int foo;    // There is probably a better name that can be used
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidFieldNameMatchingTypeName" />
    +
    + +

    AvoidInstanceofChecksInCatchClause

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    Each caught exception type should be handled in its own catch clause.

    + +

    This rule is defined by the following XPath expression:

    +
    //CatchStatement/FormalParameter
    + /following-sibling::Block//InstanceOfExpression/PrimaryExpression/PrimaryPrefix
    +  /Name[
    +   @Image = ./ancestor::Block/preceding-sibling::FormalParameter
    +    /VariableDeclaratorId/@Name
    +  ]
    +
    + +

    Example(s):

    + +
    try { // Avoid this
    +    // do something
    +} catch (Exception ee) {
    +    if (ee instanceof IOException) {
    +        cleanup();
    +    }
    +}
    +
    +try {  // Prefer this:
    +    // do something
    +} catch (IOException ee) {
    +    cleanup();
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidInstanceofChecksInCatchClause" />
    +
    + +

    AvoidLiteralsInIfCondition

    + +

    Since: PMD 4.2.6

    + +

    Priority: Medium (3)

    + +

    Avoid using hard-coded literals in conditional statements. By declaring them as static variables +or private members with descriptive names maintainability is enhanced. By default, the literals "-1" and "0" are ignored. +More exceptions can be defined with the property "ignoreMagicNumbers".

    + +

    The rule doesn’t consider deeper expressions by default, but this can be enabled via the property ignoreExpressions. +With this property set to false, if-conditions like i == 1 + 5 are reported as well. Note that in that case, +the property ignoreMagicNumbers is not taken into account, if there are multiple literals involved in such an expression.

    + +

    This rule is defined by the following XPath expression:

    +
    (: simple case - no deep expressions :)
    +//IfStatement[$ignoreExpressions = true()]/Expression/*/PrimaryExpression/PrimaryPrefix/Literal
    +    [not(NullLiteral)]
    +    [not(BooleanLiteral)]
    +    [empty(index-of(tokenize($ignoreMagicNumbers, '\s*,\s*'), @Image))]
    +|
    +(: consider also deeper expressions :)
    +//IfStatement[$ignoreExpressions = false()]/Expression//*[local-name() != 'UnaryExpression' or @Operator != '-']/PrimaryExpression/PrimaryPrefix/Literal
    +    [not(NullLiteral)]
    +    [not(BooleanLiteral)]
    +    [empty(index-of(tokenize($ignoreMagicNumbers, '\s*,\s*'), @Image))]
    +|
    +(: consider negative literals :)
    +//IfStatement[$ignoreExpressions = false()]/Expression//UnaryExpression[@Operator = '-']/PrimaryExpression/PrimaryPrefix/Literal
    +    [not(NullLiteral)]
    +    [not(BooleanLiteral)]
    +    [empty(index-of(tokenize($ignoreMagicNumbers, '\s*,\s*'), concat('-', @Image)))]
    +|
    +(: consider multiple literals in expressions :)
    +//IfStatement[$ignoreExpressions = false()]/Expression[count(*/PrimaryExpression/PrimaryPrefix/Literal
    +    [not(NullLiteral)]
    +    [not(BooleanLiteral)]) > 1]
    +
    + +

    Example(s):

    + +
    private static final int MAX_NUMBER_OF_REQUESTS = 10;
    +
    +public void checkRequests() {
    +
    +    if (i == 10) {                        // magic number, buried in a method
    +      doSomething();
    +    }
    +
    +    if (i == MAX_NUMBER_OF_REQUESTS) {    // preferred approach
    +      doSomething();
    +    }
    +
    +    if (aString.indexOf('.') != -1) {}     // magic number -1, by default ignored
    +    if (aString.indexOf('.') >= 0) { }     // alternative approach
    +
    +    if (aDouble > 0.0) {}                  // magic number 0.0
    +    if (aDouble >= Double.MIN_VALUE) {}    // preferred approach
    +
    +    // with rule property "ignoreExpressions" set to "false"
    +    if (i == pos + 5) {}  // violation: magic number 5 within an (additive) expression
    +    if (i == pos + SUFFIX_LENGTH) {} // preferred approach
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoreMagicNumbers-1,0Comma-separated list of magic numbers, that should be ignoredno
    ignoreExpressionstrueIf true, only literals in simple if conditions are considered. Otherwise literals in expressions are checked, too.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidLiteralsInIfCondition" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/AvoidLiteralsInIfCondition">
    +    <properties>
    +        <property name="ignoreMagicNumbers" value="-1,0" />
    +        <property name="ignoreExpressions" value="true" />
    +    </properties>
    +</rule>
    +
    + +

    AvoidLosingExceptionInformation

    + +

    Since: PMD 4.2.6

    + +

    Priority: Medium High (2)

    + +

    Statements in a catch block that invoke accessors on the exception without using the information +only add to code size. Either remove the invocation, or use the return result.

    + +

    This rule is defined by the following XPath expression:

    +
    //CatchStatement/Block/BlockStatement/Statement/StatementExpression/PrimaryExpression/PrimaryPrefix/Name
    +[
    +   @Image = concat(../../../../../../../FormalParameter/VariableDeclaratorId/@Name, '.getMessage')
    +   or
    +   @Image = concat(../../../../../../../FormalParameter/VariableDeclaratorId/@Name, '.getLocalizedMessage')
    +   or
    +   @Image = concat(../../../../../../../FormalParameter/VariableDeclaratorId/@Name, '.getCause')
    +   or
    +   @Image = concat(../../../../../../../FormalParameter/VariableDeclaratorId/@Name, '.getStackTrace')
    +   or
    +   @Image = concat(../../../../../../../FormalParameter/VariableDeclaratorId/@Name, '.toString')
    +]
    +
    + +

    Example(s):

    + +
    public void bar() {
    +    try {
    +        // do something
    +    } catch (SomeException se) {
    +        se.getMessage();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidLosingExceptionInformation" />
    +
    + +

    AvoidMultipleUnaryOperators

    + +

    Since: PMD 4.2

    + +

    Priority: Medium High (2)

    + +

    The use of multiple unary operators may be problematic, and/or confusing. +Ensure that the intended usage is not a bug, or consider simplifying the expression.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AvoidMultipleUnaryOperatorsRule

    + +

    Example(s):

    + +
    // These are typo bugs, or at best needlessly complex and confusing:
    +int i = - -1;
    +int j = + - +1;
    +int z = ~~2;
    +boolean b = !!true;
    +boolean c = !!!true;
    +
    +// These are better:
    +int i = 1;
    +int j = -1;
    +int z = 2;
    +boolean b = true;
    +boolean c = false;
    +
    +// And these just make your brain hurt:
    +int i = ~-2;
    +int j = -~7;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidMultipleUnaryOperators" />
    +
    + +

    AvoidUsingOctalValues

    + +

    Since: PMD 3.9

    + +

    Priority: Medium (3)

    + +

    Integer literals should not start with zero since this denotes that the rest of literal will be +interpreted as an octal value.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.AvoidUsingOctalValuesRule

    + +

    Example(s):

    + +
    int i = 012;    // set i with 10 not 12
    +int j = 010;    // set j with 8 not 10
    +k = i * j;      // set k with 80 not 120
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    strictfalseDetect violations between 00 and 07no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/AvoidUsingOctalValues" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/AvoidUsingOctalValues">
    +    <properties>
    +        <property name="strict" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    BadComparison

    + +

    Since: PMD 1.8

    + +

    Priority: Medium (3)

    + +

    Avoid equality comparisons with Double.NaN. Due to the implicit lack of representation +precision when comparing floating point numbers these are likely to cause logic errors.

    + +

    This rule is defined by the following XPath expression:

    +
    //EqualityExpression[@Image='==']
    + /PrimaryExpression/PrimaryPrefix
    + /Name[@Image='Double.NaN' or @Image='Float.NaN']
    +
    + +

    Example(s):

    + +
    boolean x = (y == Double.NaN);
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/BadComparison" />
    +
    + +

    BeanMembersShouldSerialize

    + +

    Since: PMD 1.1

    + +

    Priority: Medium (3)

    + +

    If a class is a bean, or is referenced by a bean directly or indirectly it needs to be serializable. +Member variables need to be marked as transient, static, or have accessor methods in the class. Marking +variables as transient is the safest and easiest modification. Accessor methods should follow the Java +naming conventions, i.e. for a variable named foo, getFoo() and setFoo() accessor methods should be provided.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.BeanMembersShouldSerializeRule

    + +

    Example(s):

    + +
    private transient int someFoo;  // good, it's transient
    +private static int otherFoo;    // also OK
    +private int moreFoo;            // OK, has proper accessors, see below
    +private int badFoo;             // bad, should be marked transient
    +
    +private void setMoreFoo(int moreFoo){
    +      this.moreFoo = moreFoo;
    +}
    +
    +private int getMoreFoo(){
    +      return this.moreFoo;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    ignoredAnnotationslombok.Data | lombok.Getter | lombok.ValueFully qualified names of the annotation types that should be ignored by this ruleyes. Delimiter is ‘|’.
    prefix A variable prefix to skip, i.e., m_no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/BeanMembersShouldSerialize" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/BeanMembersShouldSerialize">
    +    <properties>
    +        <property name="ignoredAnnotations" value="lombok.Data|lombok.Getter|lombok.Value" />
    +        <property name="prefix" value="" />
    +    </properties>
    +</rule>
    +
    + +

    BrokenNullCheck

    + +

    Since: PMD 3.8

    + +

    Priority: Medium High (2)

    + +

    The null check is broken since it will throw a NullPointerException itself. +It is likely that you used || instead of && or vice versa.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.BrokenNullCheckRule

    + +

    Example(s):

    + +
    public String bar(String string) {
    +  // should be &&
    +    if (string!=null || !string.equals(""))
    +        return string;
    +  // should be ||
    +    if (string==null && string.equals(""))
    +        return string;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/BrokenNullCheck" />
    +
    + +

    CallSuperFirst

    + +

    Since: PMD 4.2.5

    + +

    Priority: Medium (3)

    + +

    Super should be called at the start of the method

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[
    +  @Name='onCreate' or
    +  @Name='onConfigurationChanged' or
    +  @Name='onPostCreate' or
    +  @Name='onPostResume' or
    +  @Name='onRestart' or
    +  @Name='onRestoreInstanceState' or
    +  @Name='onResume' or
    +  @Name='onStart'
    +  ]
    +    /Block[not(
    +      (BlockStatement[1]/Statement/StatementExpression/PrimaryExpression[./PrimaryPrefix[@SuperModifier= true()]]/PrimarySuffix[@Image= ancestor::MethodDeclaration/@Name]))]
    +[ancestor::ClassOrInterfaceDeclaration[ExtendsList/ClassOrInterfaceType[
    +  pmd-java:typeIs('android.app.Activity') or
    +  pmd-java:typeIs('android.app.Application') or
    +  pmd-java:typeIs('android.app.Service')
    +]]]
    +
    + +

    Example(s):

    + +
    public class DummyActivity extends Activity {
    +    public void onCreate(Bundle bundle) {
    +        // missing call to super.onCreate(bundle)
    +        foo();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/CallSuperFirst" />
    +
    + +

    CallSuperLast

    + +

    Since: PMD 4.2.5

    + +

    Priority: Medium (3)

    + +

    Super should be called at the end of the method

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[
    +  @Name='finish' or
    +  @Name='onDestroy' or
    +  @Name='onPause' or
    +  @Name='onSaveInstanceState' or
    +  @Name='onStop' or
    +  @Name='onTerminate'
    +  ]
    +   /Block/BlockStatement[last()]
    +    [not(Statement/StatementExpression/PrimaryExpression[./PrimaryPrefix[@SuperModifier= true()]]/PrimarySuffix[@Image= ancestor::MethodDeclaration/@Name])]
    +[ancestor::ClassOrInterfaceDeclaration[ExtendsList/ClassOrInterfaceType[
    +  pmd-java:typeIs('android.app.Activity') or
    +  pmd-java:typeIs('android.app.Application') or
    +  pmd-java:typeIs('android.app.Service')
    +]]]
    +
    + +

    Example(s):

    + +
    public class DummyActivity extends Activity {
    +    public void onPause() {
    +        foo();
    +        // missing call to super.onPause()
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/CallSuperLast" />
    +
    + +

    CheckSkipResult

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    The skip() method may skip a smaller number of bytes than requested. Check the returned value to find out if it was the case or not.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.CheckSkipResultRule

    + +

    Example(s):

    + +
    public class Foo {
    +
    +   private FileInputStream _s = new FileInputStream("file");
    +
    +   public void skip(int n) throws IOException {
    +      _s.skip(n); // You are not sure that exactly n bytes are skipped
    +   }
    +
    +   public void skipExactly(int n) throws IOException {
    +      while (n != 0) {
    +         long skipped = _s.skip(n);
    +         if (skipped == 0)
    +            throw new EOFException();
    +         n -= skipped;
    +      }
    +   }
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/CheckSkipResult" />
    +
    + +

    ClassCastExceptionWithToArray

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    When deriving an array of a specific class from your Collection, one should provide an array of +the same class as the parameter of the toArray() method. Doing otherwise you will will result +in a ClassCastException.

    + +

    This rule is defined by the following XPath expression:

    +
    //CastExpression[Type/ReferenceType/ClassOrInterfaceType[@Image != "Object"]]
    +    /PrimaryExpression
    +    [PrimaryPrefix/Name[ends-with(@Image, '.toArray')]]
    +    [PrimarySuffix/Arguments[not(*)]]
    +    [count(PrimarySuffix) = 1]
    +
    + +

    Example(s):

    + +
    Collection c = new ArrayList();
    +Integer obj = new Integer(1);
    +c.add(obj);
    +
    +    // this would trigger the rule (and throw a ClassCastException if executed)
    +Integer[] a = (Integer [])c.toArray();
    +
    +   // this is fine and will not trigger the rule
    +Integer[] b = (Integer [])c.toArray(new Integer[c.size()]);
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/ClassCastExceptionWithToArray" />
    +
    + +

    CloneMethodMustBePublic

    + +

    Since: PMD 5.4.0

    + +

    Priority: Medium (3)

    + +

    The java Manual says "By convention, classes that implement this interface should override +Object.clone (which is protected) with a public method."

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Public= false()]
    +  [@Name = 'clone']
    +  [@Arity = 0]
    +
    + +

    Example(s):

    + +
    public class Foo implements Cloneable {
    +    @Override
    +    protected Object clone() throws CloneNotSupportedException { // Violation, must be public
    +    }
    +}
    +
    +public class Foo implements Cloneable {
    +    @Override
    +    protected Foo clone() { // Violation, must be public
    +    }
    +}
    +
    +public class Foo implements Cloneable {
    +    @Override
    +    public Object clone() // Ok
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/CloneMethodMustBePublic" />
    +
    + +

    CloneMethodMustImplementCloneable

    + +

    Since: PMD 1.9

    + +

    Priority: Medium (3)

    + +

    The method clone() should only be implemented if the class implements the Cloneable interface with the exception of +a final method that only throws CloneNotSupportedException.

    + +

    The rule can also detect, if the class implements or extends a Cloneable class.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.CloneMethodMustImplementCloneableRule

    + +

    Example(s):

    + +
    public class MyClass {
    + public Object clone() throws CloneNotSupportedException {
    +  return foo;
    + }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/CloneMethodMustImplementCloneable" />
    +
    + +

    CloneMethodReturnTypeMustMatchClassName

    + +

    Since: PMD 5.4.0

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.5

    + +

    If a class implements cloneable the return type of the method clone() must be the class name. That way, the caller +of the clone method doesn’t need to cast the returned clone to the correct type.

    + +

    Note: This is only possible with Java 1.5 or higher.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration
    +[
    +@Name = 'clone'
    +and @Arity = 0
    +and not (ResultType//ClassOrInterfaceType/@Image = ancestor::ClassOrInterfaceDeclaration[1]/@SimpleName)
    +]
    +
    + +

    Example(s):

    + +
    public class Foo implements Cloneable {
    +    @Override
    +    protected Object clone() { // Violation, Object must be Foo
    +    }
    +}
    +
    +public class Foo implements Cloneable {
    +    @Override
    +    public Foo clone() { //Ok
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/CloneMethodReturnTypeMustMatchClassName" />
    +
    + +

    CloneThrowsCloneNotSupportedException

    + +

    Since: PMD 1.9

    + +

    Priority: Medium (3)

    + +

    The method clone() should throw a CloneNotSupportedException.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration
    +[
    +@Name = 'clone'
    +and @Arity = 0
    +and count(NameList/Name[contains
    +(@Image,'CloneNotSupportedException')]) = 0
    +]
    +[
    +../../../../ClassOrInterfaceDeclaration[@Final = false()]
    +]
    +
    + +

    Example(s):

    + +
    public class MyClass implements Cloneable{
    +    public Object clone() { // will cause an error
    +         MyClass clone = (MyClass)super.clone();
    +         return clone;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/CloneThrowsCloneNotSupportedException" />
    +
    + +

    CloseResource

    + +

    Since: PMD 1.2.2

    + +

    Priority: Medium (3)

    + +

    Ensure that resources (like java.sql.Connection, java.sql.Statement, and java.sql.ResultSet objects +and any subtype of java.lang.AutoCloseable) are always closed after use. +Failing to do so might result in resource leaks.

    + +

    Note: It suffices to configure the super type, e.g. java.lang.AutoClosable, so that this rule automatically triggers +on any subtype (e.g. java.io.FileInputStream). Additionally specifying java.sql.Connection helps in detecting +the types, if the type resolution / auxclasspath is not correctly setup.

    + +

    Note: Since PMD 6.16.0 the default value for the property types contains java.lang.AutoCloseable and detects +now cases where the standard java.io.*Stream classes are involved. In order to restore the old behaviour, +just remove "AutoCloseable" from the types.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.CloseResourceRule

    + +

    Example(s):

    + +
    public class Bar {
    +    public void withSQL() {
    +        Connection c = pool.getConnection();
    +        try {
    +            // do stuff
    +        } catch (SQLException ex) {
    +           // handle exception
    +        } finally {
    +            // oops, should close the connection using 'close'!
    +            // c.close();
    +        }
    +    }
    +
    +    public void withFile() {
    +        InputStream file = new FileInputStream(new File("/tmp/foo"));
    +        try {
    +            int c = file.in();
    +        } catch (IOException e) {
    +            // handle exception
    +        } finally {
    +            // TODO: close file
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    closeTargets Methods which may close this resourceyes. Delimiter is ‘,’.
    typesjava.lang.AutoCloseable , java.sql.Connection , java.sql.Statement , java.sql.ResultSetAffected typesyes. Delimiter is ‘,’.
    closeAsDefaultTargettrueConsider ‘close’ as a target by defaultno
    allowedResourceTypesjava.io.ByteArrayOutputStream | java.io.ByteArrayInputStream | java.io.StringWriter | java.io.CharArrayWriter | java.util.stream.Stream | java.util.stream.IntStream | java.util.stream.LongStream | java.util.stream.DoubleStreamExact class names that do not need to be closedyes. Delimiter is ‘|’.
    closeNotInFinallyfalseDetect if ‘close’ (or other closeTargets) is called outside of a finally-blockno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/CloseResource" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/CloseResource">
    +    <properties>
    +        <property name="closeTargets" value="" />
    +        <property name="types" value="java.lang.AutoCloseable,java.sql.Connection,java.sql.Statement,java.sql.ResultSet" />
    +        <property name="closeAsDefaultTarget" value="true" />
    +        <property name="allowedResourceTypes" value="java.io.ByteArrayOutputStream|java.io.ByteArrayInputStream|java.io.StringWriter|java.io.CharArrayWriter|java.util.stream.Stream|java.util.stream.IntStream|java.util.stream.LongStream|java.util.stream.DoubleStream" />
    +        <property name="closeNotInFinally" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    CompareObjectsWithEquals

    + +

    Since: PMD 3.2

    + +

    Priority: Medium (3)

    + +

    Use equals() to compare object references; avoid comparing them with ==.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.CompareObjectsWithEqualsRule

    + +

    Example(s):

    + +
    class Foo {
    +  boolean bar(String a, String b) {
    +    return a == b;
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/CompareObjectsWithEquals" />
    +
    + +

    ConstructorCallsOverridableMethod

    + +

    Since: PMD 1.04

    + +

    Priority: High (1)

    + +

    Calling overridable methods during construction poses a risk of invoking methods on an incompletely +constructed object and can be difficult to debug. +It may leave the sub-class unable to construct its superclass or forced to replicate the construction +process completely within itself, losing the ability to call super(). If the default constructor +contains a call to an overridable method, the subclass may be completely uninstantiable. Note that +this includes method calls throughout the control flow graph - i.e., if a constructor Foo() calls a +private method bar() that calls a public method buz(), this denotes a problem.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.ConstructorCallsOverridableMethodRule

    + +

    Example(s):

    + +
    public class SeniorClass {
    +  public SeniorClass(){
    +      toString(); //may throw NullPointerException if overridden
    +  }
    +  public String toString(){
    +    return "IAmSeniorClass";
    +  }
    +}
    +public class JuniorClass extends SeniorClass {
    +  private String name;
    +  public JuniorClass(){
    +    super(); //Automatic call leads to NullPointerException
    +    name = "JuniorClass";
    +  }
    +  public String toString(){
    +    return name.toUpperCase();
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/ConstructorCallsOverridableMethod" />
    +
    + +

    DataflowAnomalyAnalysis

    + +

    Deprecated

    + +

    Since: PMD 3.9

    + +

    Priority: Low (5)

    + +

    The dataflow analysis tracks local definitions, undefinitions and references to variables on different paths on the data flow. +From those informations there can be found various problems.

    + +
      +
    1. DU - Anomaly: A recently defined variable is undefined. These anomalies may appear in normal source text.
    2. +
    3. DD - Anomaly: A recently defined variable is redefined. This is ominous but don’t have to be a bug.
    4. +
    + +

    This rule is deprecated. Use UnusedAssignment in category bestpractices instead.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.DataflowAnomalyAnalysisRule

    + +

    Example(s):

    + +
    public void foo() {
    +  int buz = 5;
    +  buz = 6; // redefinition of buz -> dd-anomaly
    +  foo(buz);
    +  buz = 2;
    +} // buz is undefined when leaving scope -> du-anomaly
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maxPaths1000Maximum number of checked paths per method. A lower value will increase the performance of the rule but may decrease anomalies found.no
    maxViolations100Maximum number of anomalies per classno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/DataflowAnomalyAnalysis" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/DataflowAnomalyAnalysis">
    +    <properties>
    +        <property name="maxPaths" value="1000" />
    +        <property name="maxViolations" value="100" />
    +    </properties>
    +</rule>
    +
    + +

    DetachedTestCase

    + +

    Since: PMD 6.13.0

    + +

    Priority: Medium (3)

    + +

    The method appears to be a test case since it has public or default visibility, +non-static access, no arguments, no return value, has no annotations, but is a +member of a class that has one or more JUnit test cases. If it is a utility +method, it should likely have private visibility. If it is an ignored test, it +should be annotated with @Test and @Ignore.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceBodyDeclaration
    +[../ClassOrInterfaceBodyDeclaration/Annotation/*/Name
    +        [pmd-java:typeIs('org.junit.Test')
    +         or pmd-java:typeIs('org.junit.jupiter.api.Test')
    +         or pmd-java:typeIs('org.junit.jupiter.api.RepeatedTest')
    +         or pmd-java:typeIs('org.junit.jupiter.api.TestFactory')
    +         or pmd-java:typeIs('org.junit.jupiter.api.TestTemplate')
    +         or pmd-java:typeIs('org.junit.jupiter.params.ParameterizedTest')]
    +]
    +[not(Annotation)]
    +[MethodDeclaration[(@Public = true() or @PackagePrivate = true()) and @Static = false() and
    +        ResultType[@Void = true()] and
    +        MethodDeclarator/FormalParameters[@Size = 0]
    +    ]
    +]
    +
    + +

    Example(s):

    + +
    public class MyTest {
    +    @Test
    +    public void someTest() {
    +    }
    +
    +    // violation: Not annotated
    +    public void someOtherTest () {
    +    }
    +
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/DetachedTestCase" />
    +
    + +

    DoNotCallGarbageCollectionExplicitly

    + +

    Since: PMD 4.2

    + +

    Priority: Medium High (2)

    + +

    Calls to System.gc(), Runtime.getRuntime().gc(), and System.runFinalization() are not advised. Code should have the +same behavior whether the garbage collection is disabled using the option -Xdisableexplicitgc or not. +Moreover, "modern" jvms do a very good job handling garbage collections. If memory usage issues unrelated to memory +leaks develop within an application, it should be dealt with JVM options rather than within the code itself.

    + +

    This rule is defined by the following XPath expression:

    +
    //Name[
    +(starts-with(@Image, 'System.') and
    +(starts-with(@Image, 'System.gc') or
    +starts-with(@Image, 'System.runFinalization'))) or
    +(
    +starts-with(@Image,'Runtime.getRuntime') and
    +../../PrimarySuffix[ends-with(@Image,'gc')]
    +)
    +]
    +
    + +

    Example(s):

    + +
    public class GCCall {
    +    public GCCall() {
    +        // Explicit gc call !
    +        System.gc();
    +    }
    +
    +    public void doSomething() {
    +        // Explicit gc call !
    +        Runtime.getRuntime().gc();
    +    }
    +
    +    public explicitGCcall() {
    +        // Explicit gc call !
    +        System.gc();
    +    }
    +
    +    public void doSomething() {
    +        // Explicit gc call !
    +        Runtime.getRuntime().gc();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/DoNotCallGarbageCollectionExplicitly" />
    +
    + +

    DoNotCallSystemExit

    + +

    Deprecated

    + +

    This rule has been renamed. Use instead: DoNotTerminateVM

    + +

    Deprecated

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    Web applications should not call System.exit(), since only the web container or the +application server should stop the JVM. Otherwise a web application would terminate all other applications +running on the same application server.

    + +

    This rule also checks for the equivalent calls Runtime.getRuntime().exit() and Runtime.getRuntime().halt().

    + +

    This rule was called DoNotCallSystemExit until PMD 6.29.0.

    + +

    This rule is defined by the following XPath expression:

    +
    //Name[
    +    starts-with(@Image,'System.exit')
    +    or
    +    (starts-with(@Image,'Runtime.getRuntime') and ../../PrimarySuffix[ends-with(@Image,'exit') or ends-with(@Image,'halt')])
    +][not(ancestor::MethodDeclaration[1][@Name="main" and @Static = true()])]
    +
    + +

    Example(s):

    + +
    public void bar() {
    +    System.exit(0);                 // never call this when running in an application server!
    +}
    +public void foo() {
    +    Runtime.getRuntime().exit(0);   // never stop the JVM manually, the container will do this.
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/DoNotCallSystemExit" />
    +
    + +

    DoNotExtendJavaLangThrowable

    + +

    Since: PMD 6.0.0

    + +

    Priority: Medium (3)

    + +

    Extend Exception or RuntimeException instead of Throwable.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration/ExtendsList/ClassOrInterfaceType
    +  [@Image="Throwable" or @Image="java.lang.Throwable"]
    +
    + +

    Example(s):

    + +
    public class Foo extends Throwable { }
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/DoNotExtendJavaLangThrowable" />
    +
    + +

    DoNotHardCodeSDCard

    + +

    Since: PMD 4.2.6

    + +

    Priority: Medium (3)

    + +

    Use Environment.getExternalStorageDirectory() instead of "/sdcard"

    + +

    This rule is defined by the following XPath expression:

    +
    //Literal[starts-with(@Image,'"/sdcard')]
    +
    + +

    Example(s):

    + +
    public class MyActivity extends Activity {
    +    protected void foo() {
    +        String storageLocation = "/sdcard/mypackage";   // hard-coded, poor approach
    +
    +       storageLocation = Environment.getExternalStorageDirectory() + "/mypackage"; // preferred approach
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/DoNotHardCodeSDCard" />
    +
    + +

    DoNotTerminateVM

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    Web applications should not call System.exit(), since only the web container or the +application server should stop the JVM. Otherwise a web application would terminate all other applications +running on the same application server.

    + +

    This rule also checks for the equivalent calls Runtime.getRuntime().exit() and Runtime.getRuntime().halt().

    + +

    This rule was called DoNotCallSystemExit until PMD 6.29.0.

    + +

    This rule is defined by the following XPath expression:

    +
    //Name[
    +    starts-with(@Image,'System.exit')
    +    or
    +    (starts-with(@Image,'Runtime.getRuntime') and ../../PrimarySuffix[ends-with(@Image,'exit') or ends-with(@Image,'halt')])
    +][not(ancestor::MethodDeclaration[1][@Name="main" and @Static = true()])]
    +
    + +

    Example(s):

    + +
    public void bar() {
    +    System.exit(0);                 // never call this when running in an application server!
    +}
    +public void foo() {
    +    Runtime.getRuntime().exit(0);   // never stop the JVM manually, the container will do this.
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/DoNotTerminateVM" />
    +
    + +

    DoNotThrowExceptionInFinally

    + +

    Since: PMD 4.2

    + +

    Priority: Medium Low (4)

    + +

    Throwing exceptions within a ‘finally’ block is confusing since they may mask other exceptions +or code defects. +Note: This is a PMD implementation of the Lint4j rule "A throw in a finally block"

    + +

    This rule is defined by the following XPath expression:

    +
    //FinallyStatement[descendant::ThrowStatement]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar() {
    +        try {
    +            // Here do some stuff
    +        } catch( Exception e) {
    +            // Handling the issue
    +        } finally {
    +            // is this really a good idea ?
    +            throw new Exception();
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/DoNotThrowExceptionInFinally" />
    +
    + +

    DontImportSun

    + +

    Since: PMD 1.5

    + +

    Priority: Medium Low (4)

    + +

    Avoid importing anything from the ‘sun.*’ packages. These packages are not portable and are likely to change.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.DontImportSunRule

    + +

    Example(s):

    + +
    import sun.misc.foo;
    +public class Foo {}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/DontImportSun" />
    +
    + +

    DontUseFloatTypeForLoopIndices

    + +

    Since: PMD 4.3

    + +

    Priority: Medium (3)

    + +

    Don’t use floating point for loop indices. If you must use floating point, use double +unless you’re certain that float provides enough precision and you have a compelling +performance need (space or time).

    + +

    This rule is defined by the following XPath expression:

    +
    //ForStatement/ForInit/LocalVariableDeclaration
    +/Type/PrimitiveType[@Image="float"]
    +
    + +

    Example(s):

    + +
    public class Count {
    +  public static void main(String[] args) {
    +    final int START = 2000000000;
    +    int count = 0;
    +    for (float f = START; f < START + 50; f++)
    +      count++;
    +      //Prints 0 because (float) START == (float) (START + 50).
    +      System.out.println(count);
    +      //The termination test misbehaves due to floating point granularity.
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/DontUseFloatTypeForLoopIndices" />
    +
    + +

    EmptyCatchBlock

    + +

    Since: PMD 0.1

    + +

    Priority: Medium (3)

    + +

    Empty Catch Block finds instances where an exception is caught, but nothing is done. +In most circumstances, this swallows an exception which should either be acted on +or reported.

    + +

    This rule is defined by the following XPath expression:

    +
    //CatchStatement
    + [not(Block/BlockStatement)]
    + [$allowCommentedBlocks != true() or Block/@containsComment = false()]
    + [FormalParameter/Type/ReferenceType
    +   /ClassOrInterfaceType[@Image != 'InterruptedException' and @Image != 'CloneNotSupportedException']
    + ]
    + [FormalParameter/VariableDeclaratorId[not(matches(@Name, $allowExceptionNameRegex))]]
    +
    + +

    Example(s):

    + +
    public void doSomething() {
    +    try {
    +        FileInputStream fis = new FileInputStream("/tmp/bugger");
    +    } catch (IOException ioe) {
    +        // not good
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    allowCommentedBlocksfalseEmpty blocks containing comments will be skippedno
    allowExceptionNameRegex^(ignored|expected)$Empty blocks catching exceptions with names matching this regular expression will be skippedno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptyCatchBlock" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/EmptyCatchBlock">
    +    <properties>
    +        <property name="allowCommentedBlocks" value="false" />
    +        <property name="allowExceptionNameRegex" value="^(ignored|expected)$" />
    +    </properties>
    +</rule>
    +
    + +

    EmptyFinalizer

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    Empty finalize methods serve no purpose and should be removed. Note that Oracle has declared Object.finalize() as deprecated since JDK 9.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Name='finalize'][@Arity = 0]
    +  /Block[not(*)]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +   protected void finalize() {}
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptyFinalizer" />
    +
    + +

    EmptyFinallyBlock

    + +

    Since: PMD 0.4

    + +

    Priority: Medium (3)

    + +

    Empty finally blocks serve no purpose and should be removed.

    + +

    This rule is defined by the following XPath expression:

    +
    //FinallyStatement[not(Block/BlockStatement)]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar() {
    +        try {
    +            int x=2;
    +        } finally {
    +            // empty!
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptyFinallyBlock" />
    +
    + +

    EmptyIfStmt

    + +

    Since: PMD 0.1

    + +

    Priority: Medium (3)

    + +

    Empty If Statement finds instances where a condition is checked but nothing is done about it.

    + +

    This rule is defined by the following XPath expression:

    +
    //IfStatement/Statement
    + [EmptyStatement or Block[not(*)]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    + void bar(int x) {
    +  if (x == 0) {
    +   // empty!
    +  }
    + }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptyIfStmt" />
    +
    + +

    EmptyInitializer

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Empty initializers serve no purpose and should be removed.

    + +

    This rule is defined by the following XPath expression:

    +
    //Initializer/Block[not(*)]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +
    +   static {} // Why ?
    +
    +   {} // Again, why ?
    +
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptyInitializer" />
    +
    + +

    EmptyStatementBlock

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Empty block statements serve no purpose and should be removed.

    + +

    This rule is defined by the following XPath expression:

    +
    //BlockStatement/Statement/Block[not(*)]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +
    +   private int _bar;
    +
    +   public void setBar(int bar) {
    +      { _bar = bar; } // Why not?
    +      {} // But remove this.
    +   }
    +
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptyStatementBlock" />
    +
    + +

    EmptyStatementNotInLoop

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    An empty statement (or a semicolon by itself) that is not used as the sole body of a ‘for’ +or ‘while’ loop is probably a bug. It could also be a double semicolon, which has no purpose +and should be removed.

    + +

    This rule is defined by the following XPath expression:

    +
    //EmptyStatement
    + [not(
    +       ../../../ForStatement
    +       or ../../../WhileStatement
    +       or ../../../BlockStatement/ClassOrInterfaceDeclaration
    +       or ../../../../../../ForStatement/Statement[1]
    +        /Block[1]/BlockStatement[1]/Statement/EmptyStatement
    +       or ../../../../../../WhileStatement/Statement[1]
    +        /Block[1]/BlockStatement[1]/Statement/EmptyStatement)
    + ]
    +
    + +

    Example(s):

    + +
    public void doit() {
    +      // this is probably not what you meant to do
    +      ;
    +      // the extra semicolon here this is not necessary
    +      System.out.println("look at the extra semicolon");;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptyStatementNotInLoop" />
    +
    + +

    EmptySwitchStatements

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    Empty switch statements serve no purpose and should be removed.

    + +

    This rule is defined by the following XPath expression:

    +
    //SwitchStatement[count(*) = 1]
    +
    + +

    Example(s):

    + +
    public void bar() {
    +    int x = 2;
    +    switch (x) {
    +        // once there was code here
    +        // but it's been commented out or something
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptySwitchStatements" />
    +
    + +

    EmptySynchronizedBlock

    + +

    Since: PMD 1.3

    + +

    Priority: Medium (3)

    + +

    Empty synchronized blocks serve no purpose and should be removed.

    + +

    This rule is defined by the following XPath expression:

    +
    //SynchronizedStatement/Block[1][not(*)]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar() {
    +        synchronized (this) {
    +            // empty!
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptySynchronizedBlock" />
    +
    + +

    EmptyTryBlock

    + +

    Since: PMD 0.4

    + +

    Priority: Medium (3)

    + +

    Avoid empty try blocks - what’s the point?

    + +

    This rule is defined by the following XPath expression:

    +
    //TryStatement[not(ResourceSpecification)]/Block[1][not(*)]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public void bar() {
    +        try {
    +        } catch (Exception e) {
    +            e.printStackTrace();
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptyTryBlock" />
    +
    + +

    EmptyWhileStmt

    + +

    Since: PMD 0.2

    + +

    Priority: Medium (3)

    + +

    Empty While Statement finds all instances where a while statement does nothing. +If it is a timing loop, then you should use Thread.sleep() for it; if it is +a while loop that does a lot in the exit expression, rewrite it to make it clearer.

    + +

    This rule is defined by the following XPath expression:

    +
    //WhileStatement/Statement[Block[not(*)] or EmptyStatement]
    +
    + +

    Example(s):

    + +
    void bar(int a, int b) {
    +    while (a == b) {
    +        // empty!
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EmptyWhileStmt" />
    +
    + +

    EqualsNull

    + +

    Since: PMD 1.9

    + +

    Priority: High (1)

    + +

    Tests for null should not use the equals() method. The ‘==’ operator should be used instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryExpression
    +  [
    +    PrimaryPrefix[Name[ends-with(@Image, 'equals')]]
    +      [following-sibling::node()/Arguments/ArgumentList[count(Expression)=1]
    +          /Expression/PrimaryExpression/PrimaryPrefix/Literal/NullLiteral]
    +
    +    or
    +
    +    PrimarySuffix[ends-with(@Image, 'equals')]
    +      [following-sibling::node()/Arguments/ArgumentList[count(Expression)=1]
    +          /Expression/PrimaryExpression/PrimaryPrefix/Literal/NullLiteral]
    +
    +  ]
    +
    + +

    Example(s):

    + +
    String x = "foo";
    +
    +if (x.equals(null)) {   // bad form
    +    doSomething();
    +}
    +
    +if (x == null) {        // preferred
    +    doSomething();
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/EqualsNull" />
    +
    + +

    FinalizeDoesNotCallSuperFinalize

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    If the finalize() is implemented, its last action should be to call super.finalize. Note that Oracle has declared Object.finalize() as deprecated since JDK 9.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Name='finalize'][@Arity = 0]
    +   /Block
    +      /BlockStatement[last()]
    +      [not(Statement/StatementExpression/PrimaryExpression
    +            [./PrimaryPrefix[@SuperModifier= true()]]
    +            [./PrimarySuffix[@Image='finalize']]
    +          )
    +      ]
    +      [not(Statement/TryStatement/FinallyStatement
    +       /Block/BlockStatement/Statement/StatementExpression/PrimaryExpression
    +            [./PrimaryPrefix[@SuperModifier= true()]]
    +            [./PrimarySuffix[@Image='finalize']]
    +          )
    +      ]
    +
    + +

    Example(s):

    + +
    protected void finalize() {
    +    something();
    +    // neglected to call super.finalize()
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/FinalizeDoesNotCallSuperFinalize" />
    +
    + +

    FinalizeOnlyCallsSuperFinalize

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    If the finalize() is implemented, it should do something besides just calling super.finalize(). Note that Oracle has declared Object.finalize() as deprecated since JDK 9.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Name='finalize'][@Arity = 0]
    +   /Block[count(BlockStatement)=1]
    +     /BlockStatement[
    +       Statement/StatementExpression/PrimaryExpression
    +       [./PrimaryPrefix[@SuperModifier= true()]]
    +       [./PrimarySuffix[@Image='finalize']]
    +     ]
    +
    + +

    Example(s):

    + +
    protected void finalize() {
    +    super.finalize();
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/FinalizeOnlyCallsSuperFinalize" />
    +
    + +

    FinalizeOverloaded

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    Methods named finalize() should not have parameters. It is confusing and most likely an attempt to +overload Object.finalize(). It will not be called by the VM.

    + +

    Note that Oracle has declared Object.finalize() as deprecated since JDK 9.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Name='finalize'][@Arity > 0]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    // this is confusing and probably a bug
    +    protected void finalize(int a) {
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/FinalizeOverloaded" />
    +
    + +

    FinalizeShouldBeProtected

    + +

    Since: PMD 1.1

    + +

    Priority: Medium (3)

    + +

    When overriding the finalize(), the new method should be set as protected. If made public, +other classes may invoke it at inappropriate times.

    + +

    Note that Oracle has declared Object.finalize() as deprecated since JDK 9.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Protected=false()][@Name='finalize'][@Arity = 0]
    +
    + +

    Example(s):

    + +
    public void finalize() {
    +    // do something
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/FinalizeShouldBeProtected" />
    +
    + +

    IdempotentOperations

    + +

    Since: PMD 2.0

    + +

    Priority: Medium (3)

    + +

    Avoid idempotent operations - they have no effect.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.IdempotentOperationsRule

    + +

    Example(s):

    + +
    public class Foo {
    + public void bar() {
    +  int x = 2;
    +  x = x;
    + }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/IdempotentOperations" />
    +
    + +

    ImportFromSamePackage

    + +

    Since: PMD 1.02

    + +

    Priority: Medium (3)

    + +

    There is no need to import a type that lives in the same package.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.ImportFromSamePackageRule

    + +

    Example(s):

    + +
    package foo;
    +
    +import foo.Buz;     // no need for this
    +import foo.*;       // or this
    +
    +public class Bar{}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/ImportFromSamePackage" />
    +
    + +

    InstantiationToGetClass

    + +

    Since: PMD 2.0

    + +

    Priority: Medium Low (4)

    + +

    Avoid instantiating an object just to call getClass() on it; use the .class public member instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimarySuffix
    + [@Image='getClass']
    + [parent::PrimaryExpression
    +  [PrimaryPrefix/AllocationExpression]
    +  [count(PrimarySuffix) = 2]
    + ]
    +
    + +

    Example(s):

    + +
    // replace this
    +Class c = new String().getClass();
    +
    +// with this:
    +Class c = String.class;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/InstantiationToGetClass" />
    +
    + +

    InvalidLogMessageFormat

    + +

    Since: PMD 5.5.0

    + +

    Priority: Low (5)

    + +

    Check for messages in slf4j and log4j2 (since 6.19.0) loggers with non matching number of arguments and placeholders.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.InvalidLogMessageFormatRule

    + +

    Example(s):

    + +
    LOGGER.error("forget the arg {}");
    +LOGGER.error("too many args {}", "arg1", "arg2");
    +LOGGER.error("param {}", "arg1", new IllegalStateException("arg")); //The exception is shown separately, so is correct.
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/InvalidLogMessageFormat" />
    +
    + +

    InvalidSlf4jMessageFormat

    + +

    Deprecated

    + +

    This rule has been renamed. Use instead: InvalidLogMessageFormat

    + +

    Deprecated

    + +

    Since: PMD 5.5.0

    + +

    Priority: Low (5)

    + +

    Check for messages in slf4j and log4j2 (since 6.19.0) loggers with non matching number of arguments and placeholders.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.InvalidLogMessageFormatRule

    + +

    Example(s):

    + +
    LOGGER.error("forget the arg {}");
    +LOGGER.error("too many args {}", "arg1", "arg2");
    +LOGGER.error("param {}", "arg1", new IllegalStateException("arg")); //The exception is shown separately, so is correct.
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/InvalidSlf4jMessageFormat" />
    +
    + +

    JumbledIncrementer

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    Avoid jumbled loop incrementers - its usually a mistake, and is confusing even if intentional.

    + +

    This rule is defined by the following XPath expression:

    +
    //ForStatement
    +  [
    +    ForUpdate/StatementExpressionList/StatementExpression/PostfixExpression/PrimaryExpression/PrimaryPrefix/Name/@Image
    +    =
    +    ancestor::ForStatement/ForInit//VariableDeclaratorId/@Name
    +  ]
    +
    + +

    Example(s):

    + +
    public class JumbledIncrementerRule1 {
    +    public void foo() {
    +        for (int i = 0; i < 10; i++) {          // only references 'i'
    +            for (int k = 0; k < 20; i++) {      // references both 'i' and 'k'
    +                System.out.println("Hello");
    +            }
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/JumbledIncrementer" />
    +
    + +

    JUnitSpelling

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    In JUnit 3, the setUp method is used to set up all data entities required in running tests. +The tearDown method is used to clean up all data entities required in running tests. +You should not misspell method name if you want your test to set up and clean up everything correctly.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.JUnitSpellingRule

    + +

    Example(s):

    + +
    import junit.framework.*;
    +
    +public class Foo extends TestCase {
    +    public void setup() {}    // oops, should be setUp
    +    public void TearDown() {} // oops, should be tearDown
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/JUnitSpelling" />
    +
    + +

    JUnitStaticSuite

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    The suite() method in a JUnit test needs to be both public and static.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.JUnitStaticSuiteRule

    + +

    Example(s):

    + +
    import junit.framework.*;
    +
    +public class Foo extends TestCase {
    +    public void suite() {}         // oops, should be static
    +    private static void suite() {} // oops, should be public
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/JUnitStaticSuite" />
    +
    + +

    LoggerIsNotStaticFinal

    + +

    Deprecated

    + +

    Since: PMD 2.0

    + +

    Priority: Medium High (2)

    + +

    In most cases, the Logger reference can be declared as static and final.

    + +

    This rule is deprecated and will be removed with PMD 7.0.0. +The rule is replaced by ProperLogger.

    + +

    This rule is defined by the following XPath expression:

    +
    //VariableDeclarator
    + [parent::FieldDeclaration]
    + [../Type/ReferenceType
    +  /ClassOrInterfaceType[@Image='Logger']
    +   and
    +  (..[@Final= false()] or ..[@Static = false()] ) ]
    +
    + +

    Example(s):

    + +
    public class Foo{
    +    Logger log = Logger.getLogger(Foo.class.getName());                 // not recommended
    +
    +    static final Logger log = Logger.getLogger(Foo.class.getName());    // preferred approach
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/LoggerIsNotStaticFinal" />
    +
    + +

    MethodWithSameNameAsEnclosingClass

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    Non-constructor methods should not have the same name as the enclosing class.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.MethodWithSameNameAsEnclosingClassRule

    + +

    Example(s):

    + +
    public class MyClass {
    +
    +    public MyClass() {}         // this is OK because it is a constructor
    +
    +    public void MyClass() {}    // this is bad because it is a method
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/MethodWithSameNameAsEnclosingClass" />
    +
    + +

    MisplacedNullCheck

    + +

    Since: PMD 3.5

    + +

    Priority: Medium (3)

    + +

    The null check here is misplaced. If the variable is null a NullPointerException will be thrown. +Either the check is useless (the variable will never be "null") or it is incorrect.

    + +

    This rule is defined by the following XPath expression:

    +
    //ConditionalAndExpression
    +  /EqualityExpression
    +    [@Image = '!=']
    +    (: one side is null :)
    +    [PrimaryExpression/PrimaryPrefix/Literal/NullLiteral]
    +    (: other side checks for the variable used somewhere in the first child of conditional and expression :)
    +    [some $var in preceding-sibling::PrimaryExpression//Name
    +      [not(ancestor::ConditionalOrExpression/EqualityExpression[@Image = '=='])]
    +      /@Image
    +      satisfies starts-with($var, concat(PrimaryExpression/PrimaryPrefix/Name/@Image, '.'))]
    +  /PrimaryExpression/PrimaryPrefix/Name
    +|
    +//ConditionalOrExpression
    +  /EqualityExpression
    +    [@Image = '==']
    +    (: one side is null :)
    +    [PrimaryExpression/PrimaryPrefix/Literal/NullLiteral]
    +    (: other side checks for the variable used somewhere in the first child of conditional or expression :)
    +    [some $var in preceding-sibling::PrimaryExpression//Name
    +      [not(ancestor::ConditionalAndExpression/EqualityExpression[@Image = '!='])]
    +      /@Image
    +      satisfies starts-with($var, concat(PrimaryExpression/PrimaryPrefix/Name/@Image, '.'))]
    +  /PrimaryExpression/PrimaryPrefix/Name
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    void bar() {
    +        if (a.equals(baz) && a != null) {} // a could be null, misplaced null check
    +
    +        if (a != null && a.equals(baz)) {} // correct null check
    +    }
    +}
    +
    + +
    public class Foo {
    +    void bar() {
    +        if (a.equals(baz) || a == null) {} // a could be null, misplaced null check
    +
    +        if (a == null || a.equals(baz)) {} // correct null check
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/MisplacedNullCheck" />
    +
    + +

    MissingBreakInSwitch

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    Switch statements without break or return statements for each case option +may indicate problematic behaviour. Empty cases are ignored as these indicate an intentional fall-through.

    + +

    This rule is defined by the following XPath expression:

    +
    //SwitchStatement
    +[(count(.//BreakStatement)
    + + count(BlockStatement//Statement/ReturnStatement)
    + + count(BlockStatement//Statement/ContinueStatement)
    + + count(BlockStatement//Statement/ThrowStatement)
    + + count(BlockStatement//Statement/IfStatement[@Else= true() and Statement[2][ReturnStatement|ContinueStatement|ThrowStatement]]/Statement[1][ReturnStatement|ContinueStatement|ThrowStatement])
    + + count(SwitchLabel[ following-sibling::node()[1][self::SwitchLabel] ])
    + + count(SwitchLabel[count(following-sibling::node()) = 0])
    +  < count (SwitchLabel))]
    +
    + +

    Example(s):

    + +
    public void bar(int status) {
    +    switch(status) {
    +      case CANCELLED:
    +        doCancelled();
    +        // break; hm, should this be commented out?
    +      case NEW:
    +        doNew();
    +        // is this really a fall-through?
    +      case REMOVED:
    +        doRemoved();
    +        // what happens if you add another case after this one?
    +      case OTHER: // empty case - this is interpreted as an intentional fall-through
    +      case ERROR:
    +        doErrorHandling();
    +        break;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/MissingBreakInSwitch" />
    +
    + +

    MissingSerialVersionUID

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    Serializable classes should provide a serialVersionUID field. +The serialVersionUID field is also needed for abstract base classes. Each individual class in the inheritance +chain needs an own serialVersionUID field. See also Should an abstract class have a serialVersionUID.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration
    +    [@Interface = false()]
    +    [count(ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration
    +        /FieldDeclaration/VariableDeclarator/VariableDeclaratorId[@Name='serialVersionUID']) = 0]
    +    [(ImplementsList | ExtendsList)/ClassOrInterfaceType[pmd-java:typeIs('java.io.Serializable')]]
    +
    + +

    Example(s):

    + +
    public class Foo implements java.io.Serializable {
    +    String name;
    +    // Define serialization id to avoid serialization related bugs
    +    // i.e., public static final long serialVersionUID = 4328743;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/MissingSerialVersionUID" />
    +
    + +

    MissingStaticMethodInNonInstantiatableClass

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    A class that has private constructors and does not have any static methods or fields cannot be used.

    + +

    When one of the private constructors is annotated with one of the annotations, then the class is not considered +non-instantiatable anymore and no violation will be reported. +See the property annotations.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[@Nested= false()]
    +[
    +  (
    +    (: at least one constructor :)
    +    ./ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/ConstructorDeclaration
    +    and
    +    (: only private constructors :)count(./ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/ConstructorDeclaration) = count(./ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/ConstructorDeclaration[@Private= true()])
    +    and
    +    (: all constructors must not be annotated :)
    +    (every $x in $annotations satisfies
    +      not(./ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/ConstructorDeclaration/
    +            ../Annotation/MarkerAnnotation/Name[pmd-java:typeIs($x)]))
    +  )
    +  and
    +  (: no static methods :)not(.//MethodDeclaration[@Static= true()])
    +  and
    +  (: no (public, package-private, protected) static fields :)not(.//FieldDeclaration[@Private= false()][@Static= true()])
    +  and
    +  (: no nested classes, that are public and static, and have no constructors at all or a public constructor :)
    +  (: and have a method returning the outer class type :)
    +  (: or the inner class extends the outer class :)not(.//ClassOrInterfaceDeclaration[@Nested= true()]
    +           [@Public= true()]
    +           [@Static= true()]
    +           [not(./ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/ConstructorDeclaration) or ./ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/ConstructorDeclaration[@Public= true()]]
    +           [(./ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/MethodDeclaration
    +                [@Public= true()]
    +                [./ResultType/Type/ReferenceType/ClassOrInterfaceType
    +                    [@Image = //ClassOrInterfaceDeclaration[@Nested= false()]/@SimpleName]
    +                ]
    +            ) or (
    +                ./ExtendsList/ClassOrInterfaceType[@Image = //ClassOrInterfaceDeclaration[@Nested=false()]/@SimpleName]
    +            )]
    +        )
    +]
    +
    + +

    Example(s):

    + +
    // This class is unusable, since it cannot be
    +// instantiated (private constructor),
    +// and no static method can be called.
    +
    +public class Foo {
    +  private Foo() {}
    +  void foo() {}
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    annotationsorg.springframework.beans.factory.annotation.Autowired , javax.inject.InjectIf a constructor is annotated with one of these annotations, then the class is ignored.yes. Delimiter is ‘,’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/MissingStaticMethodInNonInstantiatableClass" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/MissingStaticMethodInNonInstantiatableClass">
    +    <properties>
    +        <property name="annotations" value="org.springframework.beans.factory.annotation.Autowired, javax.inject.Inject" />
    +    </properties>
    +</rule>
    +
    + +

    MoreThanOneLogger

    + +

    Since: PMD 2.0

    + +

    Priority: Medium High (2)

    + +

    Normally only one logger is used in each class. This rule supports slf4j, log4j, Java Util Logging and +log4j2 (since 6.19.0).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.MoreThanOneLoggerRule

    + +

    Example(s):

    + +
    public class Foo {
    +    Logger log = Logger.getLogger(Foo.class.getName());
    +    // It is very rare to see two loggers on a class, normally
    +    // log information is multiplexed by levels
    +    Logger log2= Logger.getLogger(Foo.class.getName());
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/MoreThanOneLogger" />
    +
    + +

    NonCaseLabelInSwitchStatement

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    A non-case label (e.g. a named break/continue label) was present in a switch statement. +This legal, but confusing. It is easy to mix up the case labels and the non-case labels.

    + +

    This rule is defined by the following XPath expression:

    +
    //SwitchStatement//BlockStatement/Statement/LabeledStatement
    +
    + +

    Example(s):

    + +
    public class Foo {
    +  void bar(int a) {
    +   switch (a) {
    +     case 1:
    +       // do something
    +       break;
    +     mylabel: // this is legal, but confusing!
    +       break;
    +     default:
    +       break;
    +    }
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/NonCaseLabelInSwitchStatement" />
    +
    + +

    NonStaticInitializer

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    A non-static initializer block will be called any time a constructor is invoked (just prior to +invoking the constructor). While this is a valid language construct, it is rarely used and is +confusing.

    + +

    This rule is defined by the following XPath expression:

    +
    //Initializer[@Static=false()][not(ancestor::*[3][self::AllocationExpression or self::EnumConstant])]
    +
    + +

    Example(s):

    + +
    public class MyClass {
    +  // this block gets run before any call to a constructor
    +  {
    +    System.out.println("I am about to construct myself");
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/NonStaticInitializer" />
    +
    + +

    NullAssignment

    + +

    Since: PMD 1.02

    + +

    Priority: Medium (3)

    + +

    Assigning a "null" to a variable (outside of its declaration) is usually bad form. Sometimes, this type +of assignment is an indication that the programmer doesn’t completely understand what is going on in the code.

    + +

    NOTE: This sort of assignment may used in some cases to dereference objects and encourage garbage collection.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.NullAssignmentRule

    + +

    Example(s):

    + +
    public void bar() {
    +  Object x = null; // this is OK
    +  x = new Object();
    +     // big, complex piece of code here
    +  x = null; // this is not required
    +     // big, complex piece of code here
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/NullAssignment" />
    +
    + +

    OverrideBothEqualsAndHashcode

    + +

    Since: PMD 0.4

    + +

    Priority: Medium (3)

    + +

    Override both public boolean Object.equals(Object other), and public int Object.hashCode(), or override neither. Even if you are inheriting a hashCode() from a parent class, consider implementing hashCode and explicitly delegating to your superclass.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.OverrideBothEqualsAndHashcodeRule

    + +

    Example(s):

    + +
    public class Bar {        // poor, missing a hashcode() method
    +    public boolean equals(Object o) {
    +      // do some comparison
    +    }
    +}
    +
    +public class Baz {        // poor, missing an equals() method
    +    public int hashCode() {
    +      // return some hash value
    +    }
    +}
    +
    +public class Foo {        // perfect, both methods provided
    +    public boolean equals(Object other) {
    +      // do some comparison
    +    }
    +    public int hashCode() {
    +      // return some hash value
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/OverrideBothEqualsAndHashcode" />
    +
    + +

    ProperCloneImplementation

    + +

    Since: PMD 1.4

    + +

    Priority: Medium High (2)

    + +

    Object clone() should be implemented with super.clone().

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.ProperCloneImplementationRule

    + +

    Example(s):

    + +
    class Foo{
    +    public Object clone(){
    +        return new Foo(); // This is bad
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/ProperCloneImplementation" />
    +
    + +

    ProperLogger

    + +

    Since: PMD 3.3

    + +

    Priority: Medium (3)

    + +

    A logger should normally be defined private static final and be associated with the correct class. +private final Log log; is also allowed for rare cases where loggers need to be passed around, +with the restriction that the logger needs to be passed into the constructor.

    + +

    This rule is defined by the following XPath expression:

    +
    //FieldDeclaration
    +[Type/ReferenceType/ClassOrInterfaceType[pmd-java:typeIs($loggerClass)]]
    +[
    +    (: check modifiers :)
    +    (@Private = false() or @Final = false())
    +    (: check logger name :)
    +    or (@Static and VariableDeclarator/VariableDeclaratorId[@Name != $staticLoggerName])
    +    or (@Static = false() and VariableDeclarator/VariableDeclaratorId[@Name != $loggerName])
    +
    +    (: check logger argument type matches class or enum name :)
    +    or .//ArgumentList//ClassOrInterfaceType[@Image != ancestor::ClassOrInterfaceDeclaration/@SimpleName]
    +    or .//ArgumentList//ClassOrInterfaceType[@Image != ancestor::EnumDeclaration/@SimpleName]
    +]
    +[not(
    +     (: special case - final logger initialized inside constructor :)
    +     not(VariableDeclarator/VariableInitializer)
    +     and @Static = false()
    +     and
    +     ancestor::ClassOrInterfaceBody//ConstructorDeclaration//StatementExpression
    +        [PrimaryExpression[PrimaryPrefix[@ThisModifier]]/PrimarySuffix[@Image=$loggerName]]
    +        [AssignmentOperator[@Image = '=']]
    +        [Expression/PrimaryExpression/PrimaryPrefix/Name[@Image = ancestor::ConstructorDeclaration//FormalParameter/VariableDeclaratorId/@Name]]
    +        [not(.//AllocationExpression)]
    +  )
    +]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +
    +    private static final Log LOG = LogFactory.getLog(Foo.class);    // proper way
    +
    +    protected Log LOG = LogFactory.getLog(Testclass.class);         // wrong approach
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    staticLoggerNameLOGName of the static Logger variableno
    loggerNamelogName of the Logger instance variableno
    loggerClassLogClass name of the loggerno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/errorprone.xml/ProperLogger" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/errorprone.xml/ProperLogger">
    +    <properties>
    +        <property name="staticLoggerName" value="LOG" />
    +        <property name="loggerName" value="log" />
    +        <property name="loggerClass" value="Log" />
    +    </properties>
    +</rule>
    +
    + +

    ReturnEmptyArrayRatherThanNull

    + +

    Since: PMD 4.2

    + +

    Priority: High (1)

    + +

    For any method that returns an array, it is a better to return an empty array rather than a +null reference. This removes the need for null checking all results and avoids inadvertent +NullPointerExceptions.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration
    +[
    +(./ResultType/Type[@ArrayType= true()])
    +and
    +(./Block/BlockStatement/Statement/ReturnStatement/Expression/PrimaryExpression/PrimaryPrefix/Literal/NullLiteral)
    +]
    +
    + +

    Example(s):

    + +
    public class Example {
    +    // Not a good idea...
    +    public int[] badBehavior() {
    +        // ...
    +        return null;
    +    }
    +
    +    // Good behavior
    +    public String[] bonnePratique() {
    +        //...
    +        return new String[0];
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/ReturnEmptyArrayRatherThanNull" />
    +
    + +

    ReturnFromFinallyBlock

    + +

    Since: PMD 1.05

    + +

    Priority: Medium (3)

    + +

    Avoid returning from a finally block, this can discard exceptions.

    + +

    This rule is defined by the following XPath expression:

    +
    //FinallyStatement//ReturnStatement except //FinallyStatement//(MethodDeclaration|LambdaExpression)//ReturnStatement
    +
    + +

    Example(s):

    + +
    public class Bar {
    +    public String foo() {
    +        try {
    +            throw new Exception( "My Exception" );
    +        } catch (Exception e) {
    +            throw e;
    +        } finally {
    +            return "A. O. K."; // return not recommended here
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/ReturnFromFinallyBlock" />
    +
    + +

    SimpleDateFormatNeedsLocale

    + +

    Since: PMD 2.0

    + +

    Priority: Medium (3)

    + +

    Be sure to specify a Locale when creating SimpleDateFormat instances to ensure that locale-appropriate +formatting is used.

    + +

    This rule is defined by the following XPath expression:

    +
    //AllocationExpression
    + [ClassOrInterfaceType[@Image='SimpleDateFormat']]
    + [Arguments[@Size=1]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +  // Should specify Locale.US (or whatever)
    +  private SimpleDateFormat sdf = new SimpleDateFormat("pattern");
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/SimpleDateFormatNeedsLocale" />
    +
    + +

    SingleMethodSingleton

    + +

    Since: PMD 5.4

    + +

    Priority: Medium High (2)

    + +

    Some classes contain overloaded getInstance. The problem with overloaded getInstance methods +is that the instance created using the overloaded method is not cached and so, +for each call and new objects will be created for every invocation.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.SingleMethodSingletonRule

    + +

    Example(s):

    + +
    public class Singleton {
    +
    +    private static Singleton singleton = new Singleton( );
    +
    +    private Singleton(){ }
    +
    +    public static Singleton getInstance( ) {
    +        return singleton;
    +    }
    +
    +    public static Singleton getInstance(Object obj){
    +        Singleton singleton = (Singleton) obj;
    +        return singleton;           //violation
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/SingleMethodSingleton" />
    +
    + +

    SingletonClassReturningNewInstance

    + +

    Since: PMD 5.4

    + +

    Priority: Medium High (2)

    + +

    Some classes contain overloaded getInstance. The problem with overloaded getInstance methods +is that the instance created using the overloaded method is not cached and so, +for each call and new objects will be created for every invocation.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.SingletonClassReturningNewInstanceRule

    + +

    Example(s):

    + +
    class Singleton {
    +    private static Singleton instance = null;
    +    public static Singleton getInstance() {
    +        synchronized(Singleton.class) {
    +            return new Singleton();
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/SingletonClassReturningNewInstance" />
    +
    + +

    StaticEJBFieldShouldBeFinal

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    According to the J2EE specification, an EJB should not have any static fields +with write access. However, static read-only fields are allowed. This ensures proper +behavior especially when instances are distributed by the container on several JREs.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[
    +    (
    +    (./ImplementsList/ClassOrInterfaceType[ends-with(@Image,'SessionBean')])
    +    or
    +    (./ImplementsList/ClassOrInterfaceType[ends-with(@Image,'EJBHome')])
    +    or
    +    (./ImplementsList/ClassOrInterfaceType[ends-with(@Image,'EJBLocalObject')])
    +    or
    +    (./ImplementsList/ClassOrInterfaceType[ends-with(@Image,'EJBLocalHome')])
    +    or
    +    (./ExtendsList/ClassOrInterfaceType[ends-with(@Image,'EJBObject')])
    +    )
    +    and
    +    (./ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration[
    +         (./FieldDeclaration[@Static = true()])
    +         and
    +         (./FieldDeclaration[@Final = false()])
    +    ])
    +]
    +
    + +

    Example(s):

    + +
    public class SomeEJB extends EJBObject implements EJBLocalHome {
    +
    +    private static int CountA;          // poor, field can be edited
    +
    +    private static final int CountB;    // preferred, read-only access
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/StaticEJBFieldShouldBeFinal" />
    +
    + +

    StringBufferInstantiationWithChar

    + +

    Since: PMD 3.9

    + +

    Priority: Medium Low (4)

    + +

    Individual character values provided as initialization arguments will be converted into integers. +This can lead to internal buffer sizes that are larger than expected. Some examples:

    + +
    new StringBuffer()      //  16
    +new StringBuffer(6)     //  6
    +new StringBuffer("hello world")  // 11 + 16 = 27
    +new StringBuffer('A')   //  chr(A) = 65
    +new StringBuffer("A")   //  1 + 16 = 17
    +
    +new StringBuilder()     //  16
    +new StringBuilder(6)    //  6
    +new StringBuilder("hello world")  // 11 + 16 = 27
    +new StringBuilder('C')   //  chr(C) = 67
    +new StringBuilder("A")   //  1 + 16 = 17
    +
    + +

    This rule is defined by the following XPath expression:

    +
    //AllocationExpression/ClassOrInterfaceType
    +[@Image='StringBuffer' or @Image='StringBuilder']
    +/../Arguments/ArgumentList/Expression/PrimaryExpression
    +/PrimaryPrefix/
    +Literal
    +  [starts-with(@Image, "'")]
    +  [ends-with(@Image, "'")]
    +
    + +

    Example(s):

    + +
    // misleading instantiation, these buffers
    +// are actually sized to 99 characters long
    +StringBuffer  sb1 = new StringBuffer('c');
    +StringBuilder sb2 = new StringBuilder('c');
    +
    +// in these forms, just single characters are allocated
    +StringBuffer  sb3 = new StringBuffer("c");
    +StringBuilder sb4 = new StringBuilder("c");
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/StringBufferInstantiationWithChar" />
    +
    + +

    SuspiciousEqualsMethodName

    + +

    Since: PMD 2.0

    + +

    Priority: Medium High (2)

    + +

    The method name and parameter number are suspiciously close to Object.equals, which can denote an +intention to override it. However, the method does not override Object.equals, but overloads it instead. +Overloading Object.equals method is confusing for other programmers, error-prone and hard to maintain, +especially when using inheritance, because @Override annotations used in subclasses can provide a false +sense of security. For more information on Object.equals method, see Effective Java, 3rd Edition, +Item 10: Obey the general contract when overriding equals.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Name = 'equals']
    +[
    +    (@Arity = 1
    +    and not (MethodDeclarator/FormalParameters/FormalParameter/Type/ReferenceType/ClassOrInterfaceType
    +        [@Image = 'Object' or @Image = 'java.lang.Object'])
    +    or not (ResultType/Type/PrimitiveType[@Image = 'boolean'])
    +    )  or  (
    +    @Arity = 2
    +    and ResultType/Type/PrimitiveType[@Image = 'boolean']
    +    and MethodDeclarator/FormalParameters//ClassOrInterfaceType[@Image = 'Object' or @Image = 'java.lang.Object']
    +    and not(../Annotation/MarkerAnnotation/Name[@Image='Override'])
    +    )
    +]
    +| //MethodDeclaration[@Name = 'equal']
    +[
    +    @Arity = 1
    +    and MethodDeclarator/FormalParameters/FormalParameter/Type/ReferenceType/ClassOrInterfaceType
    +        [@Image = 'Object' or @Image = 'java.lang.Object']
    +]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +   public int equals(Object o) {
    +     // oops, this probably was supposed to be boolean equals
    +   }
    +   public boolean equals(String s) {
    +     // oops, this probably was supposed to be equals(Object)
    +   }
    +   public boolean equals(Object o1, Object o2) {
    +     // oops, this probably was supposed to be equals(Object)
    +   }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/SuspiciousEqualsMethodName" />
    +
    + +

    SuspiciousHashcodeMethodName

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    The method name and return type are suspiciously close to hashCode(), which may denote an intention +to override the hashCode() method.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.SuspiciousHashcodeMethodNameRule

    + +

    Example(s):

    + +
    public class Foo {
    +    public int hashcode() { // oops, this probably was supposed to be 'hashCode'
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/SuspiciousHashcodeMethodName" />
    +
    + +

    SuspiciousOctalEscape

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    A suspicious octal escape sequence was found inside a String literal. +The Java language specification (section 3.10.6) says an octal +escape sequence inside a literal String shall consist of a backslash +followed by:

    + +
    OctalDigit | OctalDigit OctalDigit | ZeroToThree OctalDigit OctalDigit
    +
    + +

    Any octal escape sequence followed by non-octal digits can be confusing, +e.g. "\038" is interpreted as the octal escape sequence "\03" followed by +the literal character "8".

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.SuspiciousOctalEscapeRule

    + +

    Example(s):

    + +
    public void foo() {
    +  // interpreted as octal 12, followed by character '8'
    +  System.out.println("suspicious: \128");
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/SuspiciousOctalEscape" />
    +
    + +

    TestClassWithoutTestCases

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    Test classes end with the suffix Test. Having a non-test class with that name is not a good practice, +since most people will assume it is a test case. Test classes have test methods named testXXX.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.TestClassWithoutTestCasesRule

    + +

    Example(s):

    + +
    //Consider changing the name of the class if it is not a test
    +//Consider adding test methods if it is a test
    +public class CarTest {
    +   public static void main(String[] args) {
    +    // do something
    +   }
    +   // code
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/TestClassWithoutTestCases" />
    +
    + +

    UnconditionalIfStatement

    + +

    Since: PMD 1.5

    + +

    Priority: Medium (3)

    + +

    Do not use "if" statements whose conditionals are always true or always false.

    + +

    This rule is defined by the following XPath expression:

    +
    //IfStatement/Expression
    + [count(PrimaryExpression)=1]
    + /PrimaryExpression/PrimaryPrefix/Literal/BooleanLiteral
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    public void close() {
    +        if (true) {        // fixed conditional, not recommended
    +            // ...
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UnconditionalIfStatement" />
    +
    + +

    UnnecessaryBooleanAssertion

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    A JUnit test assertion with a boolean literal is unnecessary since it always will evaluate to the same thing. +Consider using flow control (in case of assertTrue(false) or similar) or simply removing +statements like assertTrue(true) and assertFalse(false). If you just want a test to halt after finding +an error, use the fail() method and provide an indication message of why it did.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceDeclaration[
    +    pmd-java:typeIs('junit.framework.TestCase')
    +    or .//MarkerAnnotation/Name[
    +        pmd-java:typeIs('org.junit.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.Test')
    +        or pmd-java:typeIs('org.junit.jupiter.api.RepeatedTest')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestFactory')
    +        or pmd-java:typeIs('org.junit.jupiter.api.TestTemplate')
    +        or pmd-java:typeIs('org.junit.jupiter.params.ParameterizedTest')
    +        ]
    +    ]
    +//StatementExpression
    +[
    +    PrimaryExpression/PrimaryPrefix/Name[@Image='assertTrue' or  @Image='assertFalse']
    +    and
    +    PrimaryExpression/PrimarySuffix/Arguments/ArgumentList/Expression[
    +        PrimaryExpression/PrimaryPrefix/Literal/BooleanLiteral
    +        or
    +        UnaryExpressionNotPlusMinus[@Image='!']
    +            /PrimaryExpression/PrimaryPrefix[Literal/BooleanLiteral or Name[count(../../*)=1]]
    +    ]
    +]
    +
    + +

    Example(s):

    + +
    public class SimpleTest extends TestCase {
    +    public void testX() {
    +        assertTrue(true);       // serves no real purpose
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UnnecessaryBooleanAssertion" />
    +
    + +

    UnnecessaryCaseChange

    + +

    Since: PMD 3.3

    + +

    Priority: Medium (3)

    + +

    Using equalsIgnoreCase() is faster than using toUpperCase/toLowerCase().equals()

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.UnnecessaryCaseChangeRule

    + +

    Example(s):

    + +
    boolean answer1 = buz.toUpperCase().equals("baz");              // should be buz.equalsIgnoreCase("baz")
    +
    +boolean answer2 = buz.toUpperCase().equalsIgnoreCase("baz");    // another unnecessary toUpperCase()
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UnnecessaryCaseChange" />
    +
    + +

    UnnecessaryConversionTemporary

    + +

    Since: PMD 0.1

    + +

    Priority: Medium (3)

    + +

    Avoid the use temporary objects when converting primitives to Strings. Use the static conversion methods +on the wrapper classes instead.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.UnnecessaryConversionTemporaryRule

    + +

    Example(s):

    + +
    public String convert(int x) {
    +    String foo = new Integer(x).toString(); // this wastes an object
    +
    +    return Integer.toString(x);             // preferred approach
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UnnecessaryConversionTemporary" />
    +
    + +

    UnusedNullCheckInEquals

    + +

    Since: PMD 3.5

    + +

    Priority: Medium (3)

    + +

    After checking an object reference for null, you should invoke equals() on that object rather than passing it to another object’s equals() method.

    + +

    This rule is defined by the following XPath expression:

    +
    (//PrimaryPrefix[ends-with(Name/@Image, '.equals') and Name/@Image != 'Arrays.equals'] | //PrimarySuffix[@Image='equals' and not(../PrimaryPrefix/Literal)])
    + /following-sibling::PrimarySuffix/Arguments/ArgumentList/Expression
    + /PrimaryExpression[not(PrimarySuffix)]/PrimaryPrefix
    + /Name[@Image = ./../../../../../../../../../../Expression/ConditionalAndExpression
    + /EqualityExpression[@Image="!=" and not(./preceding-sibling::*) and
    + ./PrimaryExpression/PrimaryPrefix/Literal/NullLiteral]
    +  /PrimaryExpression/PrimaryPrefix/Name/@Image]
    +
    + +

    Example(s):

    + +
    public class Test {
    +
    +    public String method1() { return "ok";}
    +    public String method2() { return null;}
    +
    +    public void method(String a) {
    +        String b;
    +        // I don't know it method1() can be "null"
    +        // but I know "a" is not null..
    +        // I'd better write a.equals(method1())
    +
    +        if (a!=null && method1().equals(a)) { // will trigger the rule
    +            //whatever
    +        }
    +
    +        if (method1().equals(a) && a != null) { // won't trigger the rule
    +            //whatever
    +        }
    +
    +        if (a!=null && method1().equals(b)) { // won't trigger the rule
    +            //whatever
    +        }
    +
    +        if (a!=null && "LITERAL".equals(a)) { // won't trigger the rule
    +            //whatever
    +        }
    +
    +        if (a!=null && !a.equals("go")) { // won't trigger the rule
    +            a=method2();
    +            if (method1().equals(a)) {
    +                //whatever
    +            }
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UnusedNullCheckInEquals" />
    +
    + +

    UseCorrectExceptionLogging

    + +

    Since: PMD 3.2

    + +

    Priority: Medium (3)

    + +

    To make sure the full stacktrace is printed out, use the logging statement with two arguments: a String and a Throwable.

    + +

    This rule is defined by the following XPath expression:

    +
    //CatchStatement/Block/BlockStatement/Statement/StatementExpression
    +    /PrimaryExpression
    +        [PrimaryPrefix/Name
    +            [starts-with(@Image,
    +             concat((ancestor::ClassOrInterfaceDeclaration/ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/FieldDeclaration
    +                [Type//ClassOrInterfaceType[@Image='Log']]
    +                /VariableDeclarator/VariableDeclaratorId/@Name)[1], '.'))
    +            ]
    +        ]
    +        [PrimarySuffix/Arguments[@Size= 1]]
    +        [PrimarySuffix/Arguments//Name/@Image = ancestor::CatchStatement/FormalParameter/VariableDeclaratorId/@Name]
    +
    + +

    Example(s):

    + +
    public class Main {
    +    private static final Log _LOG = LogFactory.getLog( Main.class );
    +    void bar() {
    +        try {
    +        } catch( Exception e ) {
    +            _LOG.error( e ); //Wrong!
    +        } catch( OtherException oe ) {
    +            _LOG.error( oe.getMessage(), oe ); //Correct
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UseCorrectExceptionLogging" />
    +
    + +

    UseEqualsToCompareStrings

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    Using ‘==’ or ‘!=’ to compare strings only works if intern version is used on both sides. +Use the equals() method instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //EqualityExpression/PrimaryExpression
    +[not(PrimarySuffix)]
    +[PrimaryPrefix/Literal
    +   [starts-with(@Image, '"')]
    +   [ends-with(@Image, '"')]]
    +
    + +

    Example(s):

    + +
    public boolean test(String s) {
    +    if (s == "one") return true;        // unreliable
    +    if ("two".equals(s)) return true;   // better
    +    return false;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UseEqualsToCompareStrings" />
    +
    + +

    UselessOperationOnImmutable

    + +

    Since: PMD 3.5

    + +

    Priority: Medium (3)

    + +

    An operation on an Immutable object (String, BigDecimal or BigInteger) won’t change the object itself +since the result of the operation is a new object. Therefore, ignoring the operation result is an error.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.errorprone.UselessOperationOnImmutableRule

    + +

    Example(s):

    + +
    import java.math.*;
    +
    +class Test {
    +    void method1() {
    +        BigDecimal bd=new BigDecimal(10);
    +        bd.add(new BigDecimal(5));      // this will trigger the rule
    +    }
    +    void method2() {
    +        BigDecimal bd=new BigDecimal(10);
    +        bd = bd.add(new BigDecimal(5)); // this won't trigger the rule
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UselessOperationOnImmutable" />
    +
    + +

    UseLocaleWithCaseConversions

    + +

    Since: PMD 2.0

    + +

    Priority: Medium (3)

    + +

    When doing String::toLowerCase()/toUpperCase() conversions, use an explicit locale argument to specify the case transformation rules.

    + +

    Using String::toLowerCase() without arguments implicitly uses Locale::getDefault(). +The problem is that the default locale depends on the current JVM setup (and usually on the system in which it is running). +Using the system default may be exactly what you want (e.g. if you are manipulating strings you got through standard input), +but it may as well not be the case (e.g. if you are getting the string over the network or a file, and the encoding is well-defined +and independent of the environment). In the latter case, using the default locale makes the case transformation brittle, as +it may yield unexpected results on a machine whose locale has other case translation rules. For example, in Turkish, the +uppercase form of i is İ (U+0130, not ASCII) and not I (U+0049) as in English.

    + +

    The rule is intended to force developers to think about locales when dealing with strings. By taking a conscious decision about +the choice of locale at the time of writing, you reduce the risk of surprising behaviour down the line, and communicate your intent +to future readers.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryExpression
    +[
    +PrimaryPrefix
    +[Name[ends-with(@Image, 'toLowerCase') or ends-with(@Image, 'toUpperCase')]]
    +[following-sibling::PrimarySuffix[position() = 1]/Arguments[@Size=0]]
    +
    +or
    +
    +PrimarySuffix
    +[ends-with(@Image, 'toLowerCase') or ends-with(@Image, 'toUpperCase')]
    +[following-sibling::PrimarySuffix[position() = 1]/Arguments[@Size=0]]
    +]
    +[not(PrimaryPrefix/Name[ends-with(@Image, 'toHexString')])]
    +
    + +

    Example(s):

    + +
    // violation - implicitly system-dependent conversion
    +if (x.toLowerCase().equals("list")) {}
    +
    +// The above will not match "LIST" on a system with a Turkish locale.
    +// It could be replaced with
    +if (x.toLowerCase(Locale.US).equals("list")) { }
    +// or simply
    +if (x.equalsIgnoreCase("list")) { }
    +
    +// ok - system independent conversion
    +String z = a.toLowerCase(Locale.ROOT);
    +
    +// ok - explicit system-dependent conversion
    +String z2 = a.toLowerCase(Locale.getDefault());
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UseLocaleWithCaseConversions" />
    +
    + +

    UseProperClassLoader

    + +

    Since: PMD 3.7

    + +

    Priority: Medium (3)

    + +

    In J2EE, the getClassLoader() method might not work as expected. Use +Thread.currentThread().getContextClassLoader() instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimarySuffix[@Image='getClassLoader'] | //PrimaryPrefix[ends-with(Name/@Image, '.getClassLoader')]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    ClassLoader cl = Bar.class.getClassLoader();
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/errorprone.xml/UseProperClassLoader" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_java_multithreading.html b/pmd_rules_java_multithreading.html new file mode 100644 index 0000000000..1d0260594e --- /dev/null +++ b/pmd_rules_java_multithreading.html @@ -0,0 +1,1949 @@ + + + + + + + + +Multithreading | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Multithreading

    +
    + + + +
    + + +
    Rules that flag issues when dealing with multiple threads of execution.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AvoidSynchronizedAtMethodLevel

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    Method-level synchronization can cause problems when new code is added to the method. +Block-level synchronization helps to ensure that only the code that needs synchronization +gets it.

    + +

    This rule is defined by the following XPath expression:

    +
    //MethodDeclaration[@Synchronized = true()]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    // Try to avoid this:
    +    synchronized void foo() {
    +        // code, that doesn't need synchronization
    +        // ...
    +        // code, that requires synchronization
    +        if (!sharedData.has("bar")) {
    +            sharedData.add("bar");
    +        }
    +        // more code, that doesn't need synchronization
    +        // ...
    +    }
    +    // Prefer this:
    +    void bar() {
    +        // code, that doesn't need synchronization
    +        // ...
    +        synchronized(this) {
    +            if (!sharedData.has("bar")) {
    +                sharedData.add("bar");
    +            }
    +        }
    +        // more code, that doesn't need synchronization
    +        // ...
    +    }
    +
    +    // Try to avoid this for static methods:
    +    static synchronized void fooStatic() {
    +    }
    +
    +    // Prefer this:
    +    static void barStatic() {
    +        // code, that doesn't need synchronization
    +        // ...
    +        synchronized(Foo.class) {
    +            // code, that requires synchronization
    +        }
    +        // more code, that doesn't need synchronization
    +        // ...
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/multithreading.xml/AvoidSynchronizedAtMethodLevel" />
    +
    + +

    AvoidThreadGroup

    + +

    Since: PMD 3.6

    + +

    Priority: Medium (3)

    + +

    Avoid using java.lang.ThreadGroup; although it is intended to be used in a threaded environment +it contains methods that are not thread-safe.

    + +

    This rule is defined by the following XPath expression:

    +
    //AllocationExpression/ClassOrInterfaceType[pmd-java:typeIs('java.lang.ThreadGroup')]|
    +//PrimarySuffix[contains(@Image, 'getThreadGroup')]
    +
    + +

    Example(s):

    + +
    public class Bar {
    +    void buz() {
    +        ThreadGroup tg = new ThreadGroup("My threadgroup");
    +        tg = new ThreadGroup(tg, "my thread group");
    +        tg = Thread.currentThread().getThreadGroup();
    +        tg = System.getSecurityManager().getThreadGroup();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/multithreading.xml/AvoidThreadGroup" />
    +
    + +

    AvoidUsingVolatile

    + +

    Since: PMD 4.1

    + +

    Priority: Medium High (2)

    + +

    Use of the keyword ‘volatile’ is generally used to fine tune a Java application, and therefore, requires +a good expertise of the Java Memory Model. Moreover, its range of action is somewhat misknown. Therefore, +the volatile keyword should not be used for maintenance purpose and portability.

    + +

    This rule is defined by the following XPath expression:

    +
    //FieldDeclaration[@Volatile = true()]
    +
    + +

    Example(s):

    + +
    public class ThrDeux {
    +  private volatile String var1; // not suggested
    +  private          String var2; // preferred
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/multithreading.xml/AvoidUsingVolatile" />
    +
    + +

    DoNotUseThreads

    + +

    Since: PMD 4.1

    + +

    Priority: Medium (3)

    + +

    The J2EE specification explicitly forbids the use of threads. Threads are resources, that should be managed and monitored by the J2EE server. +If the application creates threads on its own or uses own custom thread pools, then these threads are not managed, which could lead to resource exhaustion. +Also EJB’s might be moved between machines in a cluster and only managed resources can be moved along.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassOrInterfaceType[pmd-java:typeIs('java.lang.Thread') or pmd-java:typeIs('java.util.concurrent.ExecutorService')]
    +|
    +//StatementExpression/PrimaryExpression/PrimaryPrefix/Name[pmd-java:typeIs('java.util.concurrent.Executors') or pmd-java:typeIs('java.util.concurrent.ExecutorService')]
    +
    + +

    Example(s):

    + +
    // This is not allowed
    +public class UsingThread extends Thread {
    +
    +}
    +
    +// Neither this,
    +public class UsingExecutorService {
    +
    +    public void methodX() {
    +        ExecutorService executorService = Executors.newFixedThreadPool(5);
    +    }
    +}
    +
    +// Nor this,
    +public class Example implements ExecutorService {
    +
    +}
    +
    +// Nor this,
    +public class Example extends AbstractExecutorService {
    +
    +}
    +
    +// Nor this
    +public class UsingExecutors {
    +
    +    public void methodX() {
    +        Executors.newSingleThreadExecutor().submit(() -> System.out.println("Hello!"));
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/multithreading.xml/DoNotUseThreads" />
    +
    + +

    DontCallThreadRun

    + +

    Since: PMD 4.3

    + +

    Priority: Medium Low (4)

    + +

    Explicitly calling Thread.run() method will execute in the caller’s thread of control. Instead, call Thread.start() for the intended behavior.

    + +

    This rule is defined by the following XPath expression:

    +
    //StatementExpression/PrimaryExpression
    +[
    +    PrimaryPrefix
    +    [pmd-java:typeIs('java.lang.Thread')]
    +    [
    +            ./Name[ends-with(@Image, '.run') or @Image = 'run']
    +        or
    +            ./AllocationExpression/ClassOrInterfaceType[pmd-java:typeIs('java.lang.Thread')]
    +            and ../PrimarySuffix[@Image = 'run']
    +    ]
    +]
    +
    + +

    Example(s):

    + +
    Thread t = new Thread();
    +t.run();            // use t.start() instead
    +new Thread().run(); // same violation
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/multithreading.xml/DontCallThreadRun" />
    +
    + +

    DoubleCheckedLocking

    + +

    Since: PMD 1.04

    + +

    Priority: High (1)

    + +

    Partially created objects can be returned by the Double Checked Locking pattern when used in Java. +An optimizing JRE may assign a reference to the baz variable before it calls the constructor of the object the +reference points to.

    + +

    Note: With Java 5, you can make Double checked locking work, if you declare the variable to be volatile.

    + +

    For more details refer to: http://www.javaworld.com/javaworld/jw-02-2001/jw-0209-double.html +or http://www.cs.umd.edu/~pugh/java/memoryModel/DoubleCheckedLocking.html

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.multithreading.DoubleCheckedLockingRule

    + +

    Example(s):

    + +
    public class Foo {
    +    /*volatile */ Object baz = null; // fix for Java5 and later: volatile
    +    Object bar() {
    +        if (baz == null) { // baz may be non-null yet not fully created
    +            synchronized(this) {
    +                if (baz == null) {
    +                    baz = new Object();
    +                }
    +              }
    +        }
    +        return baz;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/multithreading.xml/DoubleCheckedLocking" />
    +
    + +

    NonThreadSafeSingleton

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Non-thread safe singletons can result in bad state changes. Eliminate +static singletons if possible by instantiating the object directly. Static +singletons are usually not needed as only a single instance exists anyway. +Other possible fixes are to synchronize the entire method or to use an +initialize-on-demand holder class.

    + +

    Refrain from using the double-checked locking pattern. The Java Memory Model doesn’t +guarantee it to work unless the variable is declared as volatile, adding an uneeded +performance penalty. Reference

    + +

    See Effective Java, item 48.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.multithreading.NonThreadSafeSingletonRule

    + +

    Example(s):

    + +
    private static Foo foo = null;
    +
    +//multiple simultaneous callers may see partially initialized objects
    +public static Foo getFoo() {
    +    if (foo==null) {
    +        foo = new Foo();
    +    }
    +    return foo;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    checkNonStaticMethodstrueCheck for non-static methods. Do not set this to false and checkNonStaticFields to true.no
    checkNonStaticFieldsfalseCheck for non-static fields. Do not set this to true and checkNonStaticMethods to false.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/multithreading.xml/NonThreadSafeSingleton" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/multithreading.xml/NonThreadSafeSingleton">
    +    <properties>
    +        <property name="checkNonStaticMethods" value="true" />
    +        <property name="checkNonStaticFields" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    UnsynchronizedStaticDateFormatter

    + +

    Deprecated

    + +

    Since: PMD 3.6

    + +

    Priority: Medium (3)

    + +

    SimpleDateFormat instances are not synchronized. Sun recommends using separate format instances +for each thread. If multiple threads must access a static formatter, the formatter must be +synchronized on block level.

    + +

    This rule has been deprecated in favor of the rule UnsynchronizedStaticFormatter.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.multithreading.UnsynchronizedStaticDateFormatterRule

    + +

    Example(s):

    + +
    public class Foo {
    +    private static final SimpleDateFormat sdf = new SimpleDateFormat();
    +    void bar() {
    +        sdf.format(); // poor, no thread-safety
    +    }
    +    void foo() {
    +        synchronized (sdf) { // preferred
    +            sdf.format();
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    allowMethodLevelSynchronizationfalseIf true, method level synchronization is allowed as well as synchronized block. Otherwise only synchronized blocks are allowed.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/multithreading.xml/UnsynchronizedStaticDateFormatter" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/multithreading.xml/UnsynchronizedStaticDateFormatter">
    +    <properties>
    +        <property name="allowMethodLevelSynchronization" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    UnsynchronizedStaticFormatter

    + +

    Since: PMD 6.11.0

    + +

    Priority: Medium (3)

    + +

    Instances of java.text.Format are generally not synchronized. +Sun recommends using separate format instances for each thread. +If multiple threads must access a static formatter, the formatter must be +synchronized on block level.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.multithreading.UnsynchronizedStaticFormatterRule

    + +

    Example(s):

    + +
    public class Foo {
    +    private static final SimpleDateFormat sdf = new SimpleDateFormat();
    +    void bar() {
    +        sdf.format(); // poor, no thread-safety
    +    }
    +    void foo() {
    +        synchronized (sdf) { // preferred
    +            sdf.format();
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    allowMethodLevelSynchronizationfalseIf true, method level synchronization is allowed as well as synchronized block. Otherwise only synchronized blocks are allowed.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/multithreading.xml/UnsynchronizedStaticFormatter" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/multithreading.xml/UnsynchronizedStaticFormatter">
    +    <properties>
    +        <property name="allowMethodLevelSynchronization" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    UseConcurrentHashMap

    + +

    Since: PMD 4.2.6

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.5

    + +

    Since Java5 brought a new implementation of the Map designed for multi-threaded access, you can +perform efficient map reads without blocking other threads.

    + +

    This rule is defined by the following XPath expression:

    +
    //Type[../VariableDeclarator/VariableInitializer//AllocationExpression/ClassOrInterfaceType[@Image != 'ConcurrentHashMap']]
    +/ReferenceType/ClassOrInterfaceType[@Image = 'Map']
    +
    + +

    Example(s):

    + +
    public class ConcurrentApp {
    +  public void getMyInstance() {
    +    Map map1 = new HashMap();           // fine for single-threaded access
    +    Map map2 = new ConcurrentHashMap(); // preferred for use with multiple threads
    +
    +    // the following case will be ignored by this rule
    +    Map map3 = someModule.methodThatReturnMap(); // might be OK, if the returned map is already thread-safe
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/multithreading.xml/UseConcurrentHashMap" />
    +
    + +

    UseNotifyAllInsteadOfNotify

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    Thread.notify() awakens a thread monitoring the object. If more than one thread is monitoring, then only +one is chosen. The thread chosen is arbitrary; thus its usually safer to call notifyAll() instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //StatementExpression/PrimaryExpression
    +[PrimarySuffix/Arguments[@Size = 0]]
    +[
    +    PrimaryPrefix[
    +        ./Name[@Image='notify' or ends-with(@Image,'.notify')]
    +        or ../PrimarySuffix/@Image='notify'
    +        or (./AllocationExpression and ../PrimarySuffix[@Image='notify'])
    +    ]
    +]
    +
    + +

    Example(s):

    + +
    void bar() {
    +    x.notify();
    +    // If many threads are monitoring x, only one (and you won't know which) will be notified.
    +    // use instead:
    +    x.notifyAll();
    +  }
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/multithreading.xml/UseNotifyAllInsteadOfNotify" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_java_performance.html b/pmd_rules_java_performance.html new file mode 100644 index 0000000000..1a0fe68104 --- /dev/null +++ b/pmd_rules_java_performance.html @@ -0,0 +1,2569 @@ + + + + + + + + +Performance | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Performance

    +
    + + + +
    + + +
    Rules that flag suboptimal code.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AddEmptyString

    + +

    Since: PMD 4.0

    + +

    Priority: Medium (3)

    + +

    The conversion of literals to strings by concatenating them with empty strings is inefficient. +It is much better to use one of the type-specific toString() methods instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //AdditiveExpression/PrimaryExpression/PrimaryPrefix/Literal[@Image='""']
    +
    + +

    Example(s):

    + +
    String s = "" + 123;                // inefficient
    +String t = Integer.toString(456);   // preferred approach
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/AddEmptyString" />
    +
    + +

    AppendCharacterWithChar

    + +

    Since: PMD 3.5

    + +

    Priority: Medium (3)

    + +

    Avoid concatenating characters as strings in StringBuffer/StringBuilder.append methods.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.AppendCharacterWithCharRule

    + +

    Example(s):

    + +
    StringBuffer sb = new StringBuffer();
    +sb.append("a");     // avoid this
    +
    +StringBuffer sb = new StringBuffer();
    +sb.append('a');     // use this instead
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/AppendCharacterWithChar" />
    +
    + +

    AvoidArrayLoops

    + +

    Since: PMD 3.5

    + +

    Priority: Medium (3)

    + +

    Instead of manually copying data between two arrays, use the efficient Arrays.copyOf or System.arraycopy method instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //Statement[(ForStatement or WhileStatement) and
    +count(*//AssignmentOperator[@Image = '='])=1
    +and
    +*/Statement
    +[
    +./Block/BlockStatement/Statement/StatementExpression/PrimaryExpression
    +/PrimaryPrefix/Name/../../PrimarySuffix/Expression
    +[(PrimaryExpression or AdditiveExpression) and count
    +(.//PrimaryPrefix/Name)=1]//PrimaryPrefix/Name/@Image
    +and
    +./Block/BlockStatement/Statement/StatementExpression/Expression/PrimaryExpression
    +/PrimaryPrefix/Name/../../PrimarySuffix[count
    +(..//PrimarySuffix)=1]/Expression[(PrimaryExpression
    +or AdditiveExpression) and count(.//PrimaryPrefix/Name)=1]
    +//PrimaryPrefix/Name/@Image
    +]]
    +
    + +

    Example(s):

    + +
    public class Test {
    +    public void bar() {
    +        int[] a = new int[10];
    +        int[] b = new int[10];
    +        for (int i=0;i<10;i++) {
    +            b[i]=a[i];
    +        }
    +
    +        int[] c = new int[10];
    +        // this will trigger the rule
    +        for (int i=0;i<10;i++) {
    +            b[i]=a[c[i]];
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/AvoidArrayLoops" />
    +
    + +

    AvoidCalendarDateCreation

    + +

    Since: PMD 6.25.0

    + +

    Priority: Medium (3)

    + +

    Problem: A Calendar is a heavyweight object and expensive to create.

    + +

    Solution: Use new Date(), Java 8+ java.time.LocalDateTime.now() or ZonedDateTime.now().

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryPrefix[Name[ends-with(@Image, 'Calendar.getInstance')]] [count(../PrimarySuffix) > 2 and ../PrimarySuffix[last()-1][@Image = 'getTime' or @Image='getTimeInMillis']]
    +|
    +//MethodDeclaration[not(MethodDeclarator/FormalParameters//ClassOrInterfaceType[pmd-java:typeIs('java.util.Calendar')])]
    +  /Block/BlockStatement//PrimaryExpression
    +  /PrimaryPrefix/Name
    +    [pmd-java:typeIs('java.util.Calendar')]
    +    [every $var in @Image satisfies (
    +       (ends-with($var, '.getTime') or ends-with($var, '.getTimeInMillis'))
    +       and
    +       (: ignore if .set* or .add* or .clear is called on the variable :)
    +       not(ancestor::Block/BlockStatement//Name[
    +          starts-with(@Image, concat((tokenize($var, '\.'), $var)[1], '.set'))
    +          or
    +          starts-with(@Image, concat((tokenize($var, '\.'), $var)[1], '.add'))
    +          or
    +          starts-with(@Image, concat((tokenize($var, '\.'), $var)[1], '.clear'))
    +       ])
    +    )]
    +|
    +//ClassOrInterfaceType[pmd-java:typeIs('org.joda.time.DateTime') or pmd-java:typeIs('org.joda.time.LocalDateTime')][../Arguments/ArgumentList/Expression/PrimaryExpression/PrimaryPrefix/Name[ends-with(@Image, 'Calendar.getInstance')]]
    +
    + +

    Example(s):

    + +
    import java.time.LocalDateTime;
    +import java.util.Calendar;
    +import java.util.Date;
    +
    +public class DateStuff {
    +    private Date bad1() {
    +        return Calendar.getInstance().getTime(); // now
    +    }
    +    private Date good1a() {
    +        return new Date(); // now
    +    }
    +    private LocalDateTime good1b() {
    +        return LocalDateTime.now();
    +    }
    +    private long bad2() {
    +        return Calendar.getInstance().getTimeInMillis();
    +    }
    +    private long good2() {
    +        return System.currentTimeMillis();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/AvoidCalendarDateCreation" />
    +
    + +

    AvoidFileStream

    + +

    Since: PMD 6.0.0

    + +

    Priority: High (1)

    + +

    Minimum Language Version: Java 1.7

    + +

    The FileInputStream and FileOutputStream classes contains a finalizer method which will cause garbage +collection pauses. +See JDK-8080225 for details.

    + +

    The FileReader and FileWriter constructors instantiate FileInputStream and FileOutputStream, +again causing garbage collection issues while finalizer methods are called.

    + +
      +
    • Use Files.newInputStream(Paths.get(fileName)) instead of new FileInputStream(fileName).
    • +
    • Use Files.newOutputStream(Paths.get(fileName)) instead of new FileOutputStream(fileName).
    • +
    • Use Files.newBufferedReader(Paths.get(fileName)) instead of new FileReader(fileName).
    • +
    • Use Files.newBufferedWriter(Paths.get(fileName)) instead of new FileWriter(fileName).
    • +
    + +

    Please note, that the java.nio API does not throw a FileNotFoundException anymore, instead +it throws a NoSuchFileException. If your code dealt explicitly with a FileNotFoundException, +then this needs to be adjusted. Both exceptions are subclasses of IOException, so catching +that one covers both.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryPrefix/AllocationExpression/ClassOrInterfaceType[
    +       pmd-java:typeIs('java.io.FileInputStream')
    +    or pmd-java:typeIs('java.io.FileOutputStream')
    +    or pmd-java:typeIs('java.io.FileReader')
    +    or pmd-java:typeIs('java.io.FileWriter')
    +  ]
    +
    + +

    Example(s):

    + +
    // these instantiations cause garbage collection pauses, even if properly closed
    +
    +    FileInputStream fis = new FileInputStream(fileName);
    +    FileOutputStream fos = new FileOutputStream(fileName);
    +    FileReader fr = new FileReader(fileName);
    +    FileWriter fw = new FileWriter(fileName);
    +
    +    // the following instantiations help prevent Garbage Collection pauses, no finalization
    +
    +    try(InputStream is = Files.newInputStream(Paths.get(fileName))) {
    +    }
    +    try(OutputStream os = Files.newOutputStream(Paths.get(fileName))) {
    +    }
    +    try(BufferedReader br = Files.newBufferedReader(Paths.get(fileName), StandardCharsets.UTF_8)) {
    +    }
    +    try(BufferedWriter wr = Files.newBufferedWriter(Paths.get(fileName), StandardCharsets.UTF_8)) {
    +    }
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/AvoidFileStream" />
    +
    + +

    AvoidInstantiatingObjectsInLoops

    + +

    Since: PMD 2.2

    + +

    Priority: Medium (3)

    + +

    New objects created within loops should be checked to see if they can created outside them and reused.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.AvoidInstantiatingObjectsInLoopsRule

    + +

    Example(s):

    + +
    public class Something {
    +    public static void main( String as[] ) {
    +        for (int i = 0; i < 10; i++) {
    +            Foo f = new Foo(); // Avoid this whenever you can it's really expensive
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/AvoidInstantiatingObjectsInLoops" />
    +
    + +

    AvoidUsingShortType

    + +

    Since: PMD 4.1

    + +

    Priority: High (1)

    + +

    Java uses the ‘short’ type to reduce memory usage, not to optimize calculation. In fact, the JVM does not have any +arithmetic capabilities for the short type: the JVM must convert the short into an int, do the proper calculation +and convert the int back to a short. Thus any storage gains found through use of the ‘short’ type may be offset by +adverse impacts on performance.

    + +

    This rule is defined by the following XPath expression:

    +
    //FieldDeclaration/Type/PrimitiveType[@Image = 'short']
    +|
    +//ClassOrInterfaceBodyDeclaration[not(Annotation/MarkerAnnotation/Name[pmd-java:typeIs('java.lang.Override')])]
    +    /MethodDeclaration/ResultType/Type/PrimitiveType[@Image = 'short']
    +|
    +//ClassOrInterfaceBodyDeclaration[not(Annotation/MarkerAnnotation/Name[pmd-java:typeIs('java.lang.Override')])]
    +    /MethodDeclaration/MethodDeclarator/FormalParameters/FormalParameter/Type/PrimitiveType[@Image = 'short']
    +|
    +//LocalVariableDeclaration/Type/PrimitiveType[@Image = 'short']
    +|
    +//AnnotationMethodDeclaration/Type/PrimitiveType[@Image = 'short']
    +
    + +

    Example(s):

    + +
    public class UsingShort {
    +   private short doNotUseShort = 0;
    +
    +   public UsingShort() {
    +    short shouldNotBeUsed = 1;
    +    doNotUseShort += shouldNotBeUsed;
    +  }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/AvoidUsingShortType" />
    +
    + +

    BigIntegerInstantiation

    + +

    Since: PMD 3.9

    + +

    Priority: Medium (3)

    + +

    Don’t create instances of already existing BigInteger (BigInteger.ZERO, BigInteger.ONE) and +for Java 1.5 onwards, BigInteger.TEN and BigDecimal (BigDecimal.ZERO, BigDecimal.ONE, BigDecimal.TEN)

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.BigIntegerInstantiationRule

    + +

    Example(s):

    + +
    BigInteger bi = new BigInteger(1);       // reference BigInteger.ONE instead
    +BigInteger bi2 = new BigInteger("0");    // reference BigInteger.ZERO instead
    +BigInteger bi3 = new BigInteger(0.0);    // reference BigInteger.ZERO instead
    +BigInteger bi4;
    +bi4 = new BigInteger(0);                 // reference BigInteger.ZERO instead
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/BigIntegerInstantiation" />
    +
    + +

    BooleanInstantiation

    + +

    Since: PMD 1.2

    + +

    Priority: Medium High (2)

    + +

    Avoid instantiating Boolean objects; you can reference Boolean.TRUE, Boolean.FALSE, or call Boolean.valueOf() instead. +Note that new Boolean() is deprecated since JDK 9 for that reason.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.BooleanInstantiationRule

    + +

    Example(s):

    + +
    Boolean bar = new Boolean("true");        // unnecessary creation, just reference Boolean.TRUE;
    +Boolean buz = Boolean.valueOf(false);    // ...., just reference Boolean.FALSE;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/BooleanInstantiation" />
    +
    + +

    ByteInstantiation

    + +

    Since: PMD 4.0

    + +

    Priority: Medium High (2)

    + +

    Calling new Byte() causes memory allocation that can be avoided by the static Byte.valueOf(). +It makes use of an internal cache that recycles earlier instances making it more memory efficient. +Note that new Byte() is deprecated since JDK 9 for that reason.

    + +

    This rule is defined by the following XPath expression:

    +
    //AllocationExpression
    +[not (ArrayDimsAndInits)
    +and ClassOrInterfaceType[pmd-java:typeIs('java.lang.Byte')]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    private Byte i = new Byte(0); // change to Byte i = Byte.valueOf(0);
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/ByteInstantiation" />
    +
    + +

    ConsecutiveAppendsShouldReuse

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Consecutive calls to StringBuffer/StringBuilder .append should be chained, reusing the target object. This can improve the performance +by producing a smaller bytecode, reducing overhead and improving inlining. A complete analysis can be found here

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.ConsecutiveAppendsShouldReuseRule

    + +

    Example(s):

    + +
    String foo = " ";
    +
    +StringBuffer buf = new StringBuffer();
    +buf.append("Hello"); // poor
    +buf.append(foo);
    +buf.append("World");
    +
    +StringBuffer buf = new StringBuffer();
    +buf.append("Hello").append(foo).append("World"); // good
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/ConsecutiveAppendsShouldReuse" />
    +
    + +

    ConsecutiveLiteralAppends

    + +

    Since: PMD 3.5

    + +

    Priority: Medium (3)

    + +

    Consecutively calling StringBuffer/StringBuilder.append(…) with literals should be avoided. +Since the literals are constants, they can already be combined into a single String literal and this String +can be appended in a single method call.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.ConsecutiveLiteralAppendsRule

    + +

    Example(s):

    + +
    StringBuilder buf = new StringBuilder();
    +buf.append("Hello").append(" ").append("World");    // poor
    +buf.append("Hello World");                          // good
    +
    +buf.append('h').append('e').append('l').append('l').append('o'); // poor
    +buf.append("hello");                                             // good
    +
    +buf.append(1).append('m');  // poor
    +buf.append("1m");           // good
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    threshold1Max consecutive appendsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/performance.xml/ConsecutiveLiteralAppends" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/performance.xml/ConsecutiveLiteralAppends">
    +    <properties>
    +        <property name="threshold" value="1" />
    +    </properties>
    +</rule>
    +
    + +

    InefficientEmptyStringCheck

    + +

    Since: PMD 3.6

    + +

    Priority: Medium (3)

    + +

    String.trim().length() == 0 (or String.trim().isEmpty() for the same reason) is an inefficient +way to check if a String is really blank, as it creates a new String object just to check its size. +Consider creating a static function that loops through a string, checking Character.isWhitespace() +on each character and returning false if a non-whitespace character is found. A Smarter code to +check for an empty string would be:

    + +
    private boolean checkTrimEmpty(String str) {
    +    for(int i = 0; i < str.length(); i++) {
    +        if(!Character.isWhitespace(str.charAt(i))) {
    +            return false;
    +        }
    +    }
    +    return true;
    +}
    +
    + +

    You can refer to Apache’s StringUtils#isBlank (in commons-lang), +Spring’s StringUtils#hasText (in the Spring framework) or Google’s +CharMatcher#whitespace (in Guava) for existing implementations (some might +include the check for != null).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.InefficientEmptyStringCheckRule

    + +

    Example(s):

    + +
    public void bar(String string) {
    +    if (string != null && string.trim().length() > 0) {
    +        doSomething();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/InefficientEmptyStringCheck" />
    +
    + +

    InefficientStringBuffering

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Avoid concatenating non-literals in a StringBuffer constructor or append() since intermediate buffers will +need to be be created and destroyed by the JVM.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.InefficientStringBufferingRule

    + +

    Example(s):

    + +
    // Avoid this, two buffers are actually being created here
    +StringBuffer sb = new StringBuffer("tmp = "+System.getProperty("java.io.tmpdir"));
    +
    +// do this instead
    +StringBuffer sb = new StringBuffer("tmp = ");
    +sb.append(System.getProperty("java.io.tmpdir"));
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/InefficientStringBuffering" />
    +
    + +

    InsufficientStringBufferDeclaration

    + +

    Since: PMD 3.6

    + +

    Priority: Medium (3)

    + +

    Failing to pre-size a StringBuffer or StringBuilder properly could cause it to re-size many times +during runtime. This rule attempts to determine the total number the characters that are actually +passed into StringBuffer.append(), but represents a best guess "worst case" scenario. An empty +StringBuffer/StringBuilder constructor initializes the object to 16 characters. This default +is assumed if the length of the constructor can not be determined.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.InsufficientStringBufferDeclarationRule

    + +

    Example(s):

    + +
    StringBuffer bad = new StringBuffer();
    +bad.append("This is a long string that will exceed the default 16 characters");
    +
    +StringBuffer good = new StringBuffer(41);
    +good.append("This is a long string, which is pre-sized");
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/InsufficientStringBufferDeclaration" />
    +
    + +

    IntegerInstantiation

    + +

    Since: PMD 3.5

    + +

    Priority: Medium High (2)

    + +

    Calling new Integer() causes memory allocation that can be avoided by the static Integer.valueOf(). +It makes use of an internal cache that recycles earlier instances making it more memory efficient. +Note that new Integer() is deprecated since JDK 9 for that reason.

    + +

    This rule is defined by the following XPath expression:

    +
    //AllocationExpression
    +  [not (ArrayDimsAndInits)
    +   and ClassOrInterfaceType[pmd-java:typeIs('java.lang.Integer')]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    private Integer i = new Integer(0); // change to Integer i = Integer.valueOf(0);
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/IntegerInstantiation" />
    +
    + +

    LongInstantiation

    + +

    Since: PMD 4.0

    + +

    Priority: Medium High (2)

    + +

    Calling new Long() causes memory allocation that can be avoided by the static Long.valueOf(). +It makes use of an internal cache that recycles earlier instances making it more memory efficient. +Note that new Long() is deprecated since JDK 9 for that reason.

    + +

    This rule is defined by the following XPath expression:

    +
    //AllocationExpression
    +[not (ArrayDimsAndInits)
    +and ClassOrInterfaceType[pmd-java:typeIs('java.lang.Long')]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    private Long i = new Long(0); // change to Long i = Long.valueOf(0);
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/LongInstantiation" />
    +
    + +

    OptimizableToArrayCall

    + +

    Since: PMD 1.8

    + +

    Priority: Medium (3)

    + +

    Minimum Language Version: Java 1.6

    + +

    Calls to a collection’s toArray(E[]) method should specify a target array of zero size. This allows the JVM +to optimize the memory allocation and copying as much as possible.

    + +

    Previous versions of this rule (pre PMD 6.0.0) suggested the opposite, but current JVM implementations +perform always better, when they have full control over the target array. And allocation an array via +reflection is nowadays as fast as the direct allocation.

    + +

    See also Arrays of Wisdom of the Ancients

    + +

    Note: If you don’t need an array of the correct type, then the simple toArray() method without an array +is faster, but returns only an array of type Object[].

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryExpression
    +[PrimaryPrefix/Name[ends-with(@Image, 'toArray')]]
    +[
    +PrimarySuffix/Arguments/ArgumentList/Expression
    + /PrimaryExpression/PrimaryPrefix/AllocationExpression
    + /ArrayDimsAndInits/Expression/PrimaryExpression/PrimaryPrefix[not(Literal[@Image='0'])]
    +]
    +
    + +

    Example(s):

    + +
    List<Foo> foos = getFoos();
    +
    +// much better; this one allows the jvm to allocate an array of the correct size and effectively skip
    +// the zeroing, since each array element will be overridden anyways
    +Foo[] fooArray = foos.toArray(new Foo[0]);
    +
    +// inefficient, the array needs to be zeroed out by the jvm before it is handed over to the toArray method
    +Foo[] fooArray = foos.toArray(new Foo[foos.size()]);
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/OptimizableToArrayCall" />
    +
    + +

    RedundantFieldInitializer

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Java will initialize fields with known default values so any explicit initialization of those same defaults +is redundant and results in a larger class file (approximately three additional bytecode instructions per field).

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.RedundantFieldInitializerRule

    + +

    Example(s):

    + +
    public class C {
    +    boolean b   = false;    // examples of redundant initializers
    +    byte by     = 0;
    +    short s     = 0;
    +    char c      = 0;
    +    int i       = 0;
    +    long l      = 0;
    +
    +    float f     = .0f;    // all possible float literals
    +    doable d    = 0d;     // all possible double literals
    +    Object o    = null;
    +
    +    MyClass mca[] = null;
    +    int i1 = 0, ia1[] = null;
    +
    +    class Nested {
    +        boolean b = false;
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/RedundantFieldInitializer" />
    +
    + +

    ShortInstantiation

    + +

    Since: PMD 4.0

    + +

    Priority: Medium High (2)

    + +

    Calling new Short() causes memory allocation that can be avoided by the static Short.valueOf(). +It makes use of an internal cache that recycles earlier instances making it more memory efficient. +Note that new Short() is deprecated since JDK 9 for that reason.

    + +

    This rule is defined by the following XPath expression:

    +
    //AllocationExpression
    +[not (ArrayDimsAndInits)
    +and ClassOrInterfaceType[pmd-java:typeIs('java.lang.Short')]]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +    private Short i = new Short(0); // change to Short i = Short.valueOf(0);
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/ShortInstantiation" />
    +
    + +

    SimplifyStartsWith

    + +

    Since: PMD 3.1

    + +

    Priority: Medium (3)

    + +

    Calls to string.startsWith("x") with a string literal of length 1 can be rewritten using string.charAt(0), +at the expense of some readability. To prevent IndexOutOfBoundsException being thrown by the charAt method, +ensure that the string is not empty by making an additional check first.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryExpression
    + [PrimaryPrefix/Name
    +  [ends-with(@Image, '.startsWith')] or PrimarySuffix[@Image='startsWith']]
    + [PrimarySuffix/Arguments/ArgumentList
    +  /Expression/PrimaryExpression/PrimaryPrefix
    +  /Literal
    +   [string-length(@Image)=3]
    +   [starts-with(@Image, '"')]
    +   [ends-with(@Image, '"')]
    + ]
    +
    + +

    Example(s):

    + +
    public class Foo {
    +
    +    boolean checkIt(String x) {
    +        return x.startsWith("a");   // suboptimal
    +    }
    +
    +    boolean fasterCheckIt(String x) {
    +        return !x.isEmpty() && x.charAt(0) == 'a';  // faster approach
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/SimplifyStartsWith" />
    +
    + +

    StringInstantiation

    + +

    Since: PMD 1.0

    + +

    Priority: Medium High (2)

    + +

    Avoid instantiating String objects; this is usually unnecessary since they are immutable and can be safely shared.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.StringInstantiationRule

    + +

    Example(s):

    + +
    private String bar = new String("bar"); // just do a String bar = "bar";
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/StringInstantiation" />
    +
    + +

    StringToString

    + +

    Since: PMD 1.0

    + +

    Priority: Medium (3)

    + +

    Avoid calling toString() on objects already known to be string instances; this is unnecessary.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.StringToStringRule

    + +

    Example(s):

    + +
    private String baz() {
    +    String bar = "howdy";
    +    return bar.toString();
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/StringToString" />
    +
    + +

    TooFewBranchesForASwitchStatement

    + +

    Since: PMD 4.2

    + +

    Priority: Medium (3)

    + +

    Switch statements are intended to be used to support complex branching behaviour. Using a switch for only a few +cases is ill-advised, since switches are not as easy to understand as if-then statements. In these cases use the +if-then statement to increase code readability.

    + +

    This rule is defined by the following XPath expression:

    +
    //SwitchStatement[
    +    (count(.//SwitchLabel) < $minimumNumberCaseForASwitch)
    +]
    +
    + +

    Example(s):

    + +
    // With a minimumNumberCaseForASwitch of 3
    +public class Foo {
    +    public void bar() {
    +        switch (condition) {
    +            case ONE:
    +                instruction;
    +                break;
    +            default:
    +                break; // not enough for a 'switch' stmt, a simple 'if' stmt would have been more appropriate
    +        }
    +    }
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    minimumNumberCaseForASwitch3Minimum number of branches for a switchno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/java/performance.xml/TooFewBranchesForASwitchStatement" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/java/performance.xml/TooFewBranchesForASwitchStatement">
    +    <properties>
    +        <property name="minimumNumberCaseForASwitch" value="3" />
    +    </properties>
    +</rule>
    +
    + +

    UnnecessaryWrapperObjectCreation

    + +

    Since: PMD 3.8

    + +

    Priority: Medium (3)

    + +

    Most wrapper classes provide static conversion methods that avoid the need to create intermediate objects +just to create the primitive forms. Using these avoids the cost of creating objects that also need to be +garbage-collected later.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.UnnecessaryWrapperObjectCreationRule

    + +

    Example(s):

    + +
    public int convert(String s) {
    +    int i, i2;
    +
    +    i = Integer.valueOf(s).intValue();  // this wastes an object
    +    i = Integer.parseInt(s);            // this is better
    +
    +    i2 = Integer.valueOf(i).intValue(); // this wastes an object
    +    i2 = i;                             // this is better
    +
    +    String s3 = Integer.valueOf(i2).toString(); // this wastes an object
    +    s3 = Integer.toString(i2);                  // this is better
    +
    +    return i2;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/UnnecessaryWrapperObjectCreation" />
    +
    + +

    UseArrayListInsteadOfVector

    + +

    Since: PMD 3.0

    + +

    Priority: Medium (3)

    + +

    ArrayList is a much better Collection implementation than Vector if thread-safe operation is not required.

    + +

    This rule is defined by the following XPath expression:

    +
    //CompilationUnit[not(ImportDeclaration) or ImportDeclaration[@ImportedName='java.util.Vector']]
    +  //AllocationExpression/ClassOrInterfaceType
    +    [@Image='Vector' or @Image='java.util.Vector']
    +
    + +

    Example(s):

    + +
    public class SimpleTest extends TestCase {
    +    public void testX() {
    +    Collection c1 = new Vector();
    +    Collection c2 = new ArrayList();    // achieves the same with much better performance
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/UseArrayListInsteadOfVector" />
    +
    + +

    UseArraysAsList

    + +

    Since: PMD 3.5

    + +

    Priority: Medium (3)

    + +

    The java.util.Arrays class has a "asList" method that should be used when you want to create a new List from +an array of objects. It is faster than executing a loop to copy all the elements of the array one by one.

    + +

    Note that the result of Arrays.asList() is backed by the specified array, +changes in the returned list will result in the array to be modified. +For that reason, it is not possible to add new elements to the returned list of Arrays.asList() (UnsupportedOperationException). +You must use new ArrayList<>(Arrays.asList(…)) if that is inconvenient for you (e.g. because of concurrent access).

    + +

    This rule is defined by the following XPath expression:

    +
    //Statement[
    +    (ForStatement) and (ForStatement//VariableInitializer//Literal[@IntLiteral= true() and @Image='0']) and (not(.//IfStatement))
    +   ]
    +   //StatementExpression[
    +    PrimaryExpression/PrimaryPrefix/Name[
    +     substring-before(@Image,'.add') = ancestor::MethodDeclaration//LocalVariableDeclaration[
    +      ./Type//ClassOrInterfaceType[
    +       @Image = 'Collection' or
    +       @Image = 'List' or @Image='ArrayList'
    +      ]
    +     ]
    +     /VariableDeclarator/VariableDeclaratorId[
    +      count(..//AllocationExpression/ClassOrInterfaceType[
    +       @Image="ArrayList"
    +      ]
    +      )=1
    +     ]/@Name
    +    ]
    +   and
    +   PrimaryExpression/PrimarySuffix/Arguments/ArgumentList/Expression/PrimaryExpression/PrimaryPrefix/Name
    +   [
    +     @Image = ancestor::MethodDeclaration[1]//LocalVariableDeclaration/VariableDeclarator/VariableDeclaratorId[@ArrayType=true()]/@Name
    +     or
    +     @Image = ancestor::MethodDeclaration[1]//FormalParameter/VariableDeclaratorId/@Name
    +   ]
    +   /../..[count(.//PrimarySuffix)
    +   =1]/PrimarySuffix/Expression/PrimaryExpression/PrimaryPrefix
    +   /Name
    +   ]
    +
    + +

    Example(s):

    + +
    public class Test {
    +    public void foo(Integer[] ints) {
    +        // could just use Arrays.asList(ints)
    +        List<Integer> l= new ArrayList<>(100);
    +        for (int i=0; i< 100; i++) {
    +            l.add(ints[i]);
    +        }
    +        for (int i=0; i< 100; i++) {
    +            l.add(a[i].toString()); // won't trigger the rule
    +        }
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/UseArraysAsList" />
    +
    + +

    UseIndexOfChar

    + +

    Since: PMD 3.5

    + +

    Priority: Medium (3)

    + +

    Use String.indexOf(char) when checking for the index of a single character; it executes faster.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.UseIndexOfCharRule

    + +

    Example(s):

    + +
    String s = "hello world";
    +// avoid this
    +if (s.indexOf("d") {}
    +// instead do this
    +if (s.indexOf('d') {}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/UseIndexOfChar" />
    +
    + +

    UseIOStreamsWithApacheCommonsFileItem

    + +

    Since: PMD 6.25.0

    + +

    Priority: Medium (3)

    + +

    Problem: Use of FileItem.get() +and FileItem.getString() +could exhaust memory since they load the entire file into memory.

    + +

    Solution: Use FileItem.getInputStream() +and buffering.

    + +

    This rule is defined by the following XPath expression:

    +
    //PrimaryPrefix/Name
    +[ends-with(@Image, '.get') or ends-with(@Image, '.getString')]
    +[
    +    starts-with(@Image, concat(
    +        ancestor::MethodDeclaration//FormalParameter/Type/ReferenceType/ClassOrInterfaceType[pmd-java:typeIs('org.apache.commons.fileupload.FileItem')]/../../..//VariableDeclaratorId/@Name,
    +        '.')
    +    ) or
    +    starts-with(@Image, concat(
    +        ancestor::MethodDeclaration//LocalVariableDeclaration/Type/ReferenceType/ClassOrInterfaceType[pmd-java:typeIs('org.apache.commons.fileupload.FileItem')]/../../..//VariableDeclaratorId/@Name,
    +        '.')
    +    ) or
    +    starts-with(@Image, concat(
    +        ancestor::ClassOrInterfaceBody/ClassOrInterfaceBodyDeclaration/FieldDeclaration/Type/ReferenceType/ClassOrInterfaceType[pmd-java:typeIs('org.apache.commons.fileupload.FileItem')]/../../..//VariableDeclaratorId/@Name,
    +        '.')
    +    )
    +]
    +
    + +

    Example(s):

    + +
    import org.apache.commons.fileupload.FileItem;
    +
    +public class FileStuff {
    +   private String bad(FileItem fileItem) {
    +        return fileItem.getString();
    +   }
    +
    +   private InputStream good(FileItem fileItem) {
    +        return fileItem.getInputStream();
    +   }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/UseIOStreamsWithApacheCommonsFileItem" />
    +
    + +

    UselessStringValueOf

    + +

    Since: PMD 3.8

    + +

    Priority: Medium (3)

    + +

    No need to call String.valueOf to append to a string; just use the valueOf() argument directly.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.UselessStringValueOfRule

    + +

    Example(s):

    + +
    public String convert(int i) {
    +    String s;
    +    s = "a" + String.valueOf(i);    // not required
    +    s = "a" + i;                    // preferred approach
    +    return s;
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/UselessStringValueOf" />
    +
    + +

    UseStringBufferForStringAppends

    + +

    Since: PMD 3.1

    + +

    Priority: Medium (3)

    + +

    The use of the ‘+=’ operator for appending strings causes the JVM to create and use an internal StringBuffer. +If a non-trivial number of these concatenations are being used then the explicit use of a StringBuilder or +threadsafe StringBuffer is recommended to avoid this.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.UseStringBufferForStringAppendsRule

    + +

    Example(s):

    + +
    public class Foo {
    +    void bar() {
    +        String a;
    +        a = "foo";
    +        a += " bar";
    +        // better would be:
    +        // StringBuilder a = new StringBuilder("foo");
    +        // a.append(" bar");
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/UseStringBufferForStringAppends" />
    +
    + +

    UseStringBufferLength

    + +

    Since: PMD 3.4

    + +

    Priority: Medium (3)

    + +

    Use StringBuffer.length() to determine StringBuffer length rather than using StringBuffer.toString().equals("") +or StringBuffer.toString().length() == …

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.performance.UseStringBufferLengthRule

    + +

    Example(s):

    + +
    StringBuffer sb = new StringBuffer();
    +
    +if (sb.toString().equals("")) {}        // inefficient
    +
    +if (sb.length() == 0) {}                // preferred
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/performance.xml/UseStringBufferLength" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_java_security.html b/pmd_rules_java_security.html new file mode 100644 index 0000000000..167047c9fb --- /dev/null +++ b/pmd_rules_java_security.html @@ -0,0 +1,1500 @@ + + + + + + + + +Security | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Security

    +
    + + + +
    + + +
    Rules that flag potential security flaws.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    HardCodedCryptoKey

    + +

    Since: PMD 6.4.0

    + +

    Priority: Medium (3)

    + +

    Do not use hard coded values for cryptographic operations. Please store keys outside of source code.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.security.HardCodedCryptoKeyRule

    + +

    Example(s):

    + +
    public class Foo {
    +    void good() {
    +        SecretKeySpec secretKeySpec = new SecretKeySpec(Properties.getKey(), "AES");
    +    }
    +
    +    void bad() {
    +        SecretKeySpec secretKeySpec = new SecretKeySpec("my secret here".getBytes(), "AES");
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/security.xml/HardCodedCryptoKey" />
    +
    + +

    InsecureCryptoIv

    + +

    Since: PMD 6.3.0

    + +

    Priority: Medium (3)

    + +

    Do not use hard coded initialization vector in cryptographic operations. Please use a randomly generated IV.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.java.rule.security.InsecureCryptoIvRule

    + +

    Example(s):

    + +
    public class Foo {
    +    void good() {
    +        SecureRandom random = new SecureRandom();
    +        byte iv[] = new byte[16];
    +        random.nextBytes(bytes);
    +    }
    +
    +    void bad() {
    +        byte[] iv = new byte[] { 00, 00, 00, 00, 00, 00, 00, 00, 00, 00, 00, 00, 00, 00, 00, 00, };
    +    }
    +
    +    void alsoBad() {
    +        byte[] iv = "secret iv in here".getBytes();
    +    }
    +}
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/java/security.xml/InsecureCryptoIv" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_jsp.html b/pmd_rules_jsp.html new file mode 100644 index 0000000000..bd93b9a092 --- /dev/null +++ b/pmd_rules_jsp.html @@ -0,0 +1,1511 @@ + + + + + + + + +Java Server Pages Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Java Server Pages Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for Java Server Pages
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Best Practices

    + +
    Rules which enforce generally accepted best practices.
    + +
      +
    • DontNestJsfInJstlIteration: Do not nest JSF component custom actions inside a custom action that iterates over its body.
    • +
    • NoClassAttribute: Do not use an attribute called ‘class’. Use "styleclass" for CSS styles.
    • +
    • NoHtmlComments: In a production system, HTML comments increase the payload between the application server to the …
    • +
    • NoJspForward: Do not do a forward from within a JSP file.
    • +
    + +

    Code Style

    + +
    Rules which enforce a specific coding style.
    + + + +

    Design

    + +
    Rules that help you discover design issues.
    + +
      +
    • NoInlineScript: Avoid inlining HTML script content. Consider externalizing the HTML script using the ‘src’ attri…
    • +
    • NoInlineStyleInformation: Style information should be put in CSS files, not in JSPs. Therefore, don’t use <B> or <FONT> tag…
    • +
    • NoLongScripts: Scripts should be part of Tag Libraries, rather than part of JSP pages.
    • +
    • NoScriptlets: Scriptlets should be factored into Tag Libraries or JSP declarations, rather than being part of J…
    • +
    + +

    Error Prone

    + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + +
      +
    • JspEncoding: A missing ‘meta’ tag or page directive will trigger this rule, as well as a non-UTF-8 charset.
    • +
    + +

    Security

    + +
    Rules that flag potential security flaws.
    + +
      +
    • IframeMissingSrcAttribute: IFrames which are missing a src element can cause security information popups in IE if you are ac…
    • +
    • NoUnsanitizedJSPExpression: Avoid using expressions without escaping / sanitizing. This could lead to cross site scripting - …
    • +
    + +

    Additional rulesets

    + + + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_jsp_bestpractices.html b/pmd_rules_jsp_bestpractices.html new file mode 100644 index 0000000000..c4624038e5 --- /dev/null +++ b/pmd_rules_jsp_bestpractices.html @@ -0,0 +1,1542 @@ + + + + + + + + +Best Practices | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Best Practices

    +
    + + + +
    + + +
    Rules which enforce generally accepted best practices.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    DontNestJsfInJstlIteration

    + +

    Since: PMD 3.6

    + +

    Priority: Medium (3)

    + +

    Do not nest JSF component custom actions inside a custom action that iterates over its body.

    + +

    This rule is defined by the following XPath expression:

    +
    //Element[ @Name="c:forEach" ] // Element[ @NamespacePrefix="h" or @NamespacePrefix="f" ]
    +
    + +

    Example(s):

    + +
    <html>
    +  <body>
    +    <ul>
    +      <c:forEach items='${books}' var='b'>
    +        <li> <h:outputText value='#{b}' /> </li>
    +      </c:forEach>
    +    </ul>
    +  </body>
    +</html>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/bestpractices.xml/DontNestJsfInJstlIteration" />
    +
    + +

    NoClassAttribute

    + +

    Since: PMD 3.6

    + +

    Priority: Medium High (2)

    + +

    Do not use an attribute called ‘class’. Use "styleclass" for CSS styles.

    + +

    This rule is defined by the following XPath expression:

    +
    //Attribute[ upper-case(@Name)="CLASS" ]
    +
    + +

    Example(s):

    + +
    <HTML> <BODY>
    +<P class="MajorHeading">Some text</P>
    +</BODY> </HTML>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/bestpractices.xml/NoClassAttribute" />
    +
    + +

    NoHtmlComments

    + +

    Since: PMD 3.6

    + +

    Priority: Medium High (2)

    + +

    In a production system, HTML comments increase the payload +between the application server to the client, and serve +little other purpose. Consider switching to JSP comments.

    + +

    This rule is defined by the following XPath expression:

    +
    //CommentTag
    +
    + +

    Example(s):

    + +
    <HTML><title>bad example><BODY>
    +<!-- HTML comment -->
    +</BODY> </HTML>
    +
    +<HTML><title>good example><BODY>
    +<%-- JSP comment --%>
    +</BODY> </HTML>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/bestpractices.xml/NoHtmlComments" />
    +
    + +

    NoJspForward

    + +

    Since: PMD 3.6

    + +

    Priority: Medium (3)

    + +

    Do not do a forward from within a JSP file.

    + +

    This rule is defined by the following XPath expression:

    +
    //Element[ @Name="jsp:forward" ]
    +
    + +

    Example(s):

    + +
    <jsp:forward page='UnderConstruction.jsp'/>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/bestpractices.xml/NoJspForward" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_jsp_codestyle.html b/pmd_rules_jsp_codestyle.html new file mode 100644 index 0000000000..9202db17c6 --- /dev/null +++ b/pmd_rules_jsp_codestyle.html @@ -0,0 +1,1459 @@ + + + + + + + + +Code Style | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Code Style

    +
    + + + +
    + + +
    Rules which enforce a specific coding style.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    DuplicateJspImports

    + +

    Since: PMD 3.7

    + +

    Priority: Medium (3)

    + +

    Avoid duplicate import statements inside JSP’s.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.jsp.rule.codestyle.DuplicateJspImportsRule

    + +

    Example(s):

    + +
    <%@ page import=\"com.foo.MyClass,com.foo.MyClass\"%><html><body><b><img src=\"<%=Some.get()%>/foo\">xx</img>text</b></body></html>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/codestyle.xml/DuplicateJspImports" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_jsp_design.html b/pmd_rules_jsp_design.html new file mode 100644 index 0000000000..d2dceb01cb --- /dev/null +++ b/pmd_rules_jsp_design.html @@ -0,0 +1,1550 @@ + + + + + + + + +Design | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Design

    +
    + + + +
    + + +
    Rules that help you discover design issues.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    NoInlineScript

    + +

    Since: PMD 4.0

    + +

    Priority: Medium (3)

    + +

    Avoid inlining HTML script content. Consider externalizing the HTML script using the ‘src’ attribute on the "script" element. +Externalized script could be reused between pages. Browsers can also cache the script, reducing overall download bandwidth.

    + +

    This rule is defined by the following XPath expression:

    +
    //HtmlScript[@Image != '']
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/design.xml/NoInlineScript" />
    +
    + +

    NoInlineStyleInformation

    + +

    Since: PMD 3.6

    + +

    Priority: Medium (3)

    + +

    Style information should be put in CSS files, not in JSPs. Therefore, don’t use <B> or <FONT> +tags, or attributes like "align=’center’".

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.jsp.rule.design.NoInlineStyleInformationRule

    + +

    Example(s):

    + +
    <html><body><p align='center'><b>text</b></p></body></html>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/design.xml/NoInlineStyleInformation" />
    +
    + +

    NoLongScripts

    + +

    Since: PMD 3.6

    + +

    Priority: Medium High (2)

    + +

    Scripts should be part of Tag Libraries, rather than part of JSP pages.

    + +

    This rule is defined by the following XPath expression:

    +
    //HtmlScript[(@EndLine - @BeginLine > 10)]
    +
    + +

    Example(s):

    + +
    <HTML>
    +<BODY>
    +<!--Java Script-->
    +<SCRIPT language="JavaScript" type="text/javascript">
    +<!--
    +function calcDays(){
    +  var date1 = document.getElementById('d1').lastChild.data;
    +  var date2 = document.getElementById('d2').lastChild.data;
    +  date1 = date1.split("-");
    +  date2 = date2.split("-");
    +  var sDate = new Date(date1[0]+"/"+date1[1]+"/"+date1[2]);
    +  var eDate = new Date(date2[0]+"/"+date2[1]+"/"+date2[2]);
    +  var daysApart = Math.abs(Math.round((sDate-eDate)/86400000));
    +  document.getElementById('diffDays').lastChild.data = daysApart;
    +}
    +
    +onload=calcDays;
    +//-->
    +</SCRIPT>
    +</BODY>
    +</HTML>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/design.xml/NoLongScripts" />
    +
    + +

    NoScriptlets

    + +

    Since: PMD 3.6

    + +

    Priority: Medium (3)

    + +

    Scriptlets should be factored into Tag Libraries or JSP declarations, rather than being part of JSP pages.

    + +

    This rule is defined by the following XPath expression:

    +
    //JspScriptlet
    +|
    +//Element[ upper-case(@Name)="JSP:SCRIPTLET" ]
    +
    + +

    Example(s):

    + +
    <HTML>
    +<HEAD>
    +<%
    +response.setHeader("Pragma", "No-cache");
    +%>
    +</HEAD>
    +    <BODY>
    +        <jsp:scriptlet>String title = "Hello world!";</jsp:scriptlet>
    +    </BODY>
    +</HTML>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/design.xml/NoScriptlets" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_jsp_errorprone.html b/pmd_rules_jsp_errorprone.html new file mode 100644 index 0000000000..e03ff0d087 --- /dev/null +++ b/pmd_rules_jsp_errorprone.html @@ -0,0 +1,1471 @@ + + + + + + + + +Error Prone | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Error Prone

    +
    + + + +
    + + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    JspEncoding

    + +

    Since: PMD 4.0

    + +

    Priority: Medium (3)

    + +

    A missing ‘meta’ tag or page directive will trigger this rule, as well as a non-UTF-8 charset.

    + +

    This rule is defined by the following XPath expression:

    +
    //CompilationUnit/Content[
    +not(Element[@Name="meta"][
    +   Attribute[@Name="content"]/AttributeValue[contains(lower-case(@Image),"charset=utf-8")]
    +])
    +and
    +    not(JspDirective[@Name='page']/JspDirectiveAttribute[@Name='contentType'][contains(lower-case(@Value),"charset=utf-8")])
    +]
    +
    + +

    Example(s):

    + +
    Most browsers should be able to interpret the following headers:
    +
    +<%@ page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" %>
    +
    +<meta http-equiv="Content-Type"  content="text/html; charset=UTF-8" />
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/errorprone.xml/JspEncoding" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_jsp_security.html b/pmd_rules_jsp_security.html new file mode 100644 index 0000000000..ca99fa095b --- /dev/null +++ b/pmd_rules_jsp_security.html @@ -0,0 +1,1492 @@ + + + + + + + + +Security | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Security

    +
    + + + +
    + + +
    Rules that flag potential security flaws.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    IframeMissingSrcAttribute

    + +

    Since: PMD 3.6

    + +

    Priority: Medium High (2)

    + +

    IFrames which are missing a src element can cause security information popups in IE if you are accessing the page +through SSL. See http://support.microsoft.com/default.aspx?scid=kb;EN-US;Q261188

    + +

    This rule is defined by the following XPath expression:

    +
    //Element[upper-case(@Name)="IFRAME"][count(Attribute[upper-case(@Name)="SRC" ]) = 0]
    +
    + +

    Example(s):

    + +
    <HTML><title>bad example><BODY>
    +<iframe></iframe>
    +</BODY> </HTML>
    +
    +<HTML><title>good example><BODY>
    +<iframe src="foo"></iframe>
    +</BODY> </HTML>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/security.xml/IframeMissingSrcAttribute" />
    +
    + +

    NoUnsanitizedJSPExpression

    + +

    Since: PMD 5.1.4

    + +

    Priority: Medium (3)

    + +

    Avoid using expressions without escaping / sanitizing. This could lead to cross site scripting - as the expression +would be interpreted by the browser directly (e.g. "<script>alert(‘hello’);</script>").

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.jsp.rule.security.NoUnsanitizedJSPExpressionRule

    + +

    Example(s):

    + +
    <%@ page contentType="text/html; charset=UTF-8" %>
    +<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %>
    +${expression}                    <!-- don't use this -->
    +${fn:escapeXml(expression)}      <!-- instead, escape it -->
    +<c:out value="${expression}" />  <!-- or use c:out -->
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/jsp/security.xml/NoUnsanitizedJSPExpression" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_modelica.html b/pmd_rules_modelica.html new file mode 100644 index 0000000000..debfdaec31 --- /dev/null +++ b/pmd_rules_modelica.html @@ -0,0 +1,1460 @@ + + + + + + + + +Modelica Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Modelica Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for Modelica
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Best Practices

    + +
    Rules which enforce generally accepted best practices.
    + +
      +
    • AmbiguousResolution: There is multiple candidates for this type resolution. While generally this is not an error, …
    • +
    • ClassStartNameEqualsEndName: Having a class starting with some name and some different name in its end clause is a…
    • +
    • ConnectUsingNonConnector: Modelica specification requires passing connectors to the ‘connect’ clause, while som…
    • +
    + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_modelica_bestpractices.html b/pmd_rules_modelica_bestpractices.html new file mode 100644 index 0000000000..121c48cfac --- /dev/null +++ b/pmd_rules_modelica_bestpractices.html @@ -0,0 +1,1534 @@ + + + + + + + + +Best Practices | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Best Practices

    +
    + + + +
    + + +
    Rules which enforce generally accepted best practices.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AmbiguousResolution

    + +

    Priority: Medium (3)

    + +

    There is multiple candidates for this type resolution. While generally this is not an error, +this may indicate a bug.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.modelica.rule.AmbiguousResolutionRule

    + +

    Example(s):

    + +
    package Test
    +  package Inc1
    +    model X
    +    end X;
    +    model Y
    +    end Y;
    +  end Inc1;
    +  package Inc2
    +    model Y
    +    end Y;
    +    model Z
    +    end Z;
    +  end Inc2;
    +  model B
    +    import Test.Inc1.*;
    +    import Test.Inc2.*;
    +    Y y; // Class Y is imported twice
    +  end B;
    +end Test;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/modelica/bestpractices.xml/AmbiguousResolution" />
    +
    + +

    ClassStartNameEqualsEndName

    + +

    Priority: High (1)

    + +

    Having a class starting with some name and some different +name in its end clause is an error.

    + +

    This rule is defined by the following XPath expression:

    +
    //ClassSpecifier/*[SimpleName[1]/@Image != SimpleName[last()]/@Image]
    +
    + +

    Example(s):

    + +
    model SomeName
    +  Real x;
    +equation
    +  x = 1;
    +end SomeOtherName /* should be SomeName */;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/modelica/bestpractices.xml/ClassStartNameEqualsEndName" />
    +
    + +

    ConnectUsingNonConnector

    + +

    Priority: Medium High (2)

    + +

    Modelica specification requires passing connectors to the connect clause, +while some implementations tolerate using it on plain variables, etc..

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.modelica.rule.ConnectUsingNonConnector

    + +

    Example(s):

    + +
    package Example
    +  connector Conn
    +    Real x;
    +    Real y;
    +  end Conn;
    +
    +  model Test
    +    input Conn c1;
    +    output Conn c2;
    +    input Real x1;
    +    output Real x2;
    +  equation
    +    connect(c1, c2); // OK
    +    connect(x1, x2); // error, x1 and x2 are not (both) connectors
    +    // x1 = x2; // OK
    +  end Test;
    +end Example;
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/modelica/bestpractices.xml/ConnectUsingNonConnector" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_plsql.html b/pmd_rules_plsql.html new file mode 100644 index 0000000000..0ea7e81154 --- /dev/null +++ b/pmd_rules_plsql.html @@ -0,0 +1,1540 @@ + + + + + + + + +PLSQL Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    PLSQL Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for PLSQL
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Best Practices

    + +
    Rules which enforce generally accepted best practices.
    + +
      +
    • TomKytesDespair: "WHEN OTHERS THEN NULL" hides all errors - (Re)RAISE an exception or call RAISE_APPLICATION_ERROR
    • +
    + +

    Code Style

    + +
    Rules which enforce a specific coding style.
    + +
      +
    • AvoidTabCharacter: This rule checks, that there are no tab characters (‘\t’) in the source file. It reports only the…
    • +
    • CodeFormat: This rule verifies that the PLSQL code is properly formatted. The following checks are executed: …
    • +
    • ForLoopNaming: In case you have loops please name the loop variables more meaningful.
    • +
    • LineLength: This rule checks for long lines. Please note that comments are not ignored. This rule is the PMD …
    • +
    • MisplacedPragma: Oracle states that the PRAQMA AUTONOMOUS_TRANSACTION must be in the declaration block, but the co…
    • +
    + +

    Design

    + +
    Rules that help you discover design issues.
    + +
      +
    • CyclomaticComplexity: Complexity directly affects maintenance costs is determined by the number of decision points in a…
    • +
    • ExcessiveMethodLength: When methods are excessively long this usually indicates that the method is doing more than its n…
    • +
    • ExcessiveObjectLength: Excessive object line lengths are usually indications that the object may be burdened with excess…
    • +
    • ExcessivePackageBodyLength: Excessive class file lengths are usually indications that the class may be burdened with excessiv…
    • +
    • ExcessivePackageSpecificationLength: Excessive class file lengths are usually indications that the class may be burdened with excessiv…
    • +
    • ExcessiveParameterList: Methods with numerous parameters are a challenge to maintain, especially if most of them share th…
    • +
    • ExcessiveTypeLength: Excessive class file lengths are usually indications that the class may be burdened with excessiv…
    • +
    • NcssMethodCount: This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of l…
    • +
    • NcssObjectCount: This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of l…
    • +
    • NPathComplexity: The NPath complexity of a method is the number of acyclic execution paths through that method. A …
    • +
    • TooManyFields: Classes that have too many fields can become unwieldy and could be redesigned to have fewer field…
    • +
    • TooManyMethods: A package or type with too many methods is probably a good suspect for refactoring, in order to r…
    • +
    + +

    Error Prone

    + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + +

    Additional rulesets

    + + + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_plsql_bestpractices.html b/pmd_rules_plsql_bestpractices.html new file mode 100644 index 0000000000..9fac767f53 --- /dev/null +++ b/pmd_rules_plsql_bestpractices.html @@ -0,0 +1,1500 @@ + + + + + + + + +Best Practices | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Best Practices

    +
    + + + +
    + + +
    Rules which enforce generally accepted best practices.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    TomKytesDespair

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    "WHEN OTHERS THEN NULL" hides all errors - (Re)RAISE an exception or call RAISE_APPLICATION_ERROR

    + +

    This rule is defined by the following XPath expression:

    +
    //ExceptionHandler[QualifiedName/@Image='OTHERS' and upper-case(Statement/UnlabelledStatement/Expression/@Image)='NULL']
    +
    + +

    Example(s):

    + +
    CREATE OR REPLACE PACKAGE BODY update_planned_hrs
    +IS
    +
    +PROCEDURE set_new_planned (p_emp_id IN NUMBER, p_project_id IN NUMBER, p_hours IN NUMBER)
    +IS
    +BEGIN
    +   UPDATE employee_on_activity ea
    +   SET ea.ea_planned_hours = p_hours
    +   WHERE
    +            ea.ea_emp_id = p_emp_id
    +            AND ea.ea_proj_id = p_project_id;
    +
    +EXCEPTION
    +          WHEN NO_DATA_FOUND THEN
    +          RAISE_APPLICATION_ERROR (-20100, 'No such employee or project');
    +
    +END set_new_planned;
    +
    +FUNCTION existing_planned (p_emp_id IN NUMBER, p_project_id IN NUMBER) RETURN NUMBER
    +
    +IS
    +
    +existing_hours NUMBER(4);
    +
    +BEGIN
    +   SELECT ea.ea_planned_hours INTO existing_hours
    +   FROM employee_on_activity ea
    +   WHERE
    +            ea.ea_emp_id = p_emp_id
    +            AND ea.ea_proj_id = p_project_id;
    +
    +   RETURN (existing_hours);
    +
    +   EXCEPTION
    +          WHEN OTHERS THEN NULL;
    +
    +   END existing_planned;
    +
    +END update_planned_hrs;
    +/
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/plsql/bestpractices.xml/TomKytesDespair" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_plsql_codestyle.html b/pmd_rules_plsql_codestyle.html new file mode 100644 index 0000000000..159bd4dd1d --- /dev/null +++ b/pmd_rules_plsql_codestyle.html @@ -0,0 +1,1784 @@ + + + + + + + + +Code Style | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Code Style

    +
    + + + +
    + + +
    Rules which enforce a specific coding style.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AvoidTabCharacter

    + +

    Since: PMD 6.13.0

    + +

    Priority: Medium (3)

    + +

    This rule checks, that there are no tab characters (\t) in the source file. +It reports only the first occurrence per file.

    + +

    Using tab characters for indentation is not recommended, since this requires that every developer +uses the same tab with in their editor.

    + +

    This rule is the PMD equivalent of checkstyle’s FileTabCharacter check.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.codestyle.AvoidTabCharacterRule

    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    eachLinefalseWhether to report each line with a tab character or only the first lineno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/codestyle.xml/AvoidTabCharacter" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/codestyle.xml/AvoidTabCharacter">
    +    <properties>
    +        <property name="eachLine" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    CodeFormat

    + +

    Since: PMD 6.9.0

    + +

    Priority: Medium (3)

    + +

    This rule verifies that the PLSQL code is properly formatted. The following checks are executed:

    + +

    SQL Queries:

    + +
      +
    • The selected columns must be each on a new line
    • +
    • The keywords (BULK COLLECT INTO, FROM) start on a new line and are indented by one level
    • +
    • UNION should be on the same indentation level as SELECT
    • +
    • Each JOIN is on a new line. If there are more than one JOIN conditions, then each condition should be +on a separate line.
    • +
    + +

    Parameter definitions for procedures:

    + +
      +
    • Each parameter should be on a new line
    • +
    • Variable names as well as their types should be aligned
    • +
    + +

    Variable declarations:

    + +
      +
    • Each variable should be on a new line
    • +
    • Variable names as well as their types should be aligned
    • +
    + +

    Calling a procedure:

    + +
      +
    • If there are more than 3 parameters +
        +
      • then named parameters should be used
      • +
      • and each parameter should be on a new line
      • +
      +
    • +
    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.codestyle.CodeFormatRule

    + +

    Example(s):

    + +
    BEGIN
    +  -- select columns each on a separate line
    +  SELECT cmer_id
    +        ,version
    +        ,cmp_id
    +    BULK COLLECT INTO v_cmer_ids
    +        ,v_versions
    +        ,v_cmp_ids
    +    FROM cmer;
    +
    +  -- each parameter on a new line
    +  PROCEDURE create_prospect(
    +    company_info_in      IN    prospects.company_info%TYPE -- Organization
    +   ,firstname_in         IN    persons.firstname%TYPE      -- FirstName
    +   ,lastname_in          IN    persons.lastname%TYPE       -- LastName
    +  );
    +
    +  -- more than three parameters, each parameter on a separate line
    +  webcrm_marketing.prospect_ins(
    +    cmp_id_in            => NULL
    +   ,company_info_in      => company_info_in
    +   ,firstname_in         => firstname_in
    +   ,lastname_in          => lastname_in
    +   ,slt_code_in          => NULL
    +  );
    +
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    indentation2Indentation to be used for blocksno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/codestyle.xml/CodeFormat" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/codestyle.xml/CodeFormat">
    +    <properties>
    +        <property name="indentation" value="2" />
    +    </properties>
    +</rule>
    +
    + +

    ForLoopNaming

    + +

    Since: PMD 6.7.0

    + +

    Priority: Medium (3)

    + +

    In case you have loops please name the loop variables more meaningful.

    + +

    This rule is defined by the following XPath expression:

    +
    //CursorForLoopStatement[
    +    $allowSimpleLoops = false() or
    +    (Statement//CursorForLoopStatement or ancestor::CursorForLoopStatement)
    +]
    +/ForIndex[not(matches(@Image, $cursorPattern))]
    +|
    +//ForStatement[
    +    $allowSimpleLoops = false() or
    +    (Statement//ForStatement or ancestor::ForStatement)
    +]
    +/ForIndex[not(matches(@Image, $indexPattern))]
    +
    + +

    Example(s):

    + +
    -- good example
    +BEGIN
    +FOR company IN (SELECT * FROM companies) LOOP
    +  FOR contact IN (SELECT * FROM contacts) LOOP
    +    FOR party IN (SELECT * FROM parties) LOOP
    +      NULL;
    +    END LOOP;
    +  END LOOP;
    +END LOOP;
    +END;
    +/
    +
    +-- bad example
    +BEGIN
    +FOR c1 IN (SELECT * FROM companies) LOOP
    +  FOR c2 IN (SELECT * FROM contacts) LOOP
    +    FOR c3 IN (SELECT * FROM parties) LOOP
    +      NULL;
    +    END LOOP;
    +  END LOOP;
    +END LOOP;
    +END;
    +/
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    allowSimpleLoopsfalseIgnore simple loops, that are not nestedno
    cursorPattern[a-zA-Z_0-9]{5,}The pattern used for the curosr loop variableno
    indexPattern[a-zA-Z_0-9]{5,}The pattern used for the index loop variableno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/codestyle.xml/ForLoopNaming" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/codestyle.xml/ForLoopNaming">
    +    <properties>
    +        <property name="allowSimpleLoops" value="false" />
    +        <property name="cursorPattern" value="[a-zA-Z_0-9]{5,}" />
    +        <property name="indexPattern" value="[a-zA-Z_0-9]{5,}" />
    +    </properties>
    +</rule>
    +
    + +

    LineLength

    + +

    Since: PMD 6.13.0

    + +

    Priority: Medium (3)

    + +

    This rule checks for long lines. Please note that comments are not ignored.

    + +

    This rule is the PMD equivalent of checkstyle’s LineLength check.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.codestyle.LineLengthRule

    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maxLineLength80The maximum allowed line lengthno
    eachLinefalseWhether to report each line that is longer only the first lineno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/codestyle.xml/LineLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/codestyle.xml/LineLength">
    +    <properties>
    +        <property name="maxLineLength" value="80" />
    +        <property name="eachLine" value="false" />
    +    </properties>
    +</rule>
    +
    + +

    MisplacedPragma

    + +

    Since: PMD 5.5.2

    + +

    Priority: Medium (3)

    + +

    Oracle states that the PRAQMA AUTONOMOUS_TRANSACTION must be in the declaration block, +but the code does not complain, when being compiled on the 11g DB. +https://docs.oracle.com/cd/B28359_01/appdev.111/b28370/static.htm#BABIIHBJ

    + +

    This rule is defined by the following XPath expression:

    +
    //ProgramUnit/Pragma
    +
    + +

    Example(s):

    + +
    create or replace package inline_pragma_error is
    +
    +end;
    +/
    +
    +create or replace package body inline_pragma_error is
    +  procedure do_transaction(p_input_token        in varchar(200)) is
    +  PRAGMA AUTONOMOUS_TRANSACTION; /* this is correct place for PRAGMA */
    +  begin
    +    PRAGMA AUTONOMOUS_TRANSACTION; /* this is the wrong place for PRAGMA -> violation */
    +    /* do something */
    +    COMMIT;
    +   end do_transaction;
    +
    +end inline_pragma_error;
    +/
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/plsql/codestyle.xml/MisplacedPragma" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_plsql_design.html b/pmd_rules_plsql_design.html new file mode 100644 index 0000000000..5d8730a38c --- /dev/null +++ b/pmd_rules_plsql_design.html @@ -0,0 +1,2424 @@ + + + + + + + + +Design | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Design

    +
    + + + +
    + + +
    Rules that help you discover design issues.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    CyclomaticComplexity

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Complexity directly affects maintenance costs is determined by the number of decision points in a method +plus one for the method entry. The decision points include ‘if’, ‘while’, ‘for’, and ‘case labels’ calls. +Generally, numbers ranging from 1-4 denote low complexity, 5-7 denote moderate complexity, 8-10 denote +high complexity, and 11+ is very high complexity.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.CyclomaticComplexityRule

    + +

    Example(s):

    + +
    -- Cyclomatic Complexity of 25
    +CREATE OR REPLACE PACKAGE BODY pkg_pmd_working_sequence  AS
    +1 PROCEDURE ty_logger  IS BEGIN
    +2        IF true
    +         THEN
    +              DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +3        IF true
    +         THEN
    +              DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +4            IF true
    +             THEN
    +                  DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +5            ELSIF false
    +             THEN
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             ELSE
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             END IF;
    +6        ELSIF false
    +         THEN
    +            DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +7            IF true
    +             THEN
    +                  DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +8            ELSIF false
    +             THEN
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             ELSE
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             END IF;
    +         ELSE
    +            DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +9            IF true
    +             THEN
    +                  DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +10           ELSIF false
    +             THEN
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             ELSE
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             END IF;
    +         END IF;
    +11         ELSIF false
    +         THEN
    +            DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +12       IF true
    +         THEN
    +              DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +13           IF true
    +             THEN
    +                  DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +14           ELSIF false
    +             THEN
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             ELSE
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             END IF;
    +15       ELSIF false
    +         THEN
    +16           IF true
    +             THEN
    +                  DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +17           ELSIF false
    +             THEN
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             ELSE
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             END IF;
    +             DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +         ELSE
    +             DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +         END IF;
    +     ELSE
    +        DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +18       IF true
    +         THEN
    +              DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +19           IF true
    +             THEN
    +                  DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +20           ELSIF false
    +             THEN
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             ELSE
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             END IF;
    +21       ELSIF false
    +         THEN
    +            DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +22           IF true
    +             THEN
    +                DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +23           ELSIF false
    +             THEN
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             ELSE
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             END IF;
    +             ELSE
    +             DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +24           IF true
    +             THEN
    +                  DBMS_OUTPUT.PUT_LINE('IF/THEN l_Integer='||l_integer);
    +25           ELSIF false
    +             THEN
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             ELSE
    +                DBMS_OUTPUT.PUT_LINE('ELSIF l_Integer='||l_integer);
    +             END IF;
    +         END IF;
    +     END IF;
    +END;
    +
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    showMethodsComplexitytrueAdd method average violations to the reportno
    showClassesComplexitytrueAdd class average violations to the reportno
    reportLevel10Cyclomatic Complexity reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/CyclomaticComplexity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/CyclomaticComplexity">
    +    <properties>
    +        <property name="showMethodsComplexity" value="true" />
    +        <property name="showClassesComplexity" value="true" />
    +        <property name="reportLevel" value="10" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessiveMethodLength

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    When methods are excessively long this usually indicates that the method is doing more than its +name/signature might suggest. They also become challenging for others to digest since excessive +scrolling causes readers to lose focus. +Try to reduce the method length by creating helper methods and removing any copy/pasted code.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.ExcessiveMethodLengthRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE
    +PROCEDURE doSomething BEGIN
    +    DBMS_OUTPUT.PUT_LINE("Hello world!");
    +    DBMS_OUTPUT.PUT_LINE("Hello world!");
    +        -- 98 copies omitted for brevity.
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum100.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/ExcessiveMethodLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/ExcessiveMethodLength">
    +    <properties>
    +        <property name="minimum" value="100.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessiveObjectLength

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Excessive object line lengths are usually indications that the object may be burdened with excessive +responsibilities that could be provided by other objects. In breaking these methods +apart the code becomes more managable and ripe for reuse.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.ExcessiveObjectLengthRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE
    +PACKAGE BODY Foo AS
    +    PROCEDURE bar1 IS BEGIN
    +    -- 1000 lines of code
    +    END bar1;
    +    PROCEDURE bar2 IS BEGIN
    +    -- 1000 lines of code
    +    END bar2;
    +    PROCEDURE bar3 IS BEGIN
    +    -- 1000 lines of code
    +    END bar3;
    +
    +
    +    PROCEDURE barN IS BEGIN
    +    -- 1000 lines of code
    +    END barn;
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum1000.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/ExcessiveObjectLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/ExcessiveObjectLength">
    +    <properties>
    +        <property name="minimum" value="1000.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessivePackageBodyLength

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Excessive class file lengths are usually indications that the class may be burdened with excessive +responsibilities that could be provided by external classes or functions. In breaking these methods +apart the code becomes more managable and ripe for reuse.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.ExcessivePackageBodyLengthRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE
    +PACKAGE BODY Foo AS
    +    PROCEDURE bar1 IS BEGIN
    +    -- 1000 lines of code
    +    END bar1;
    +    PROCEDURE bar2 IS BEGIN
    +    -- 1000 lines of code
    +    END bar2;
    +    PROCEDURE bar3 IS BEGIN
    +    -- 1000 lines of code
    +    END bar3;
    +
    +
    +    PROCEDURE barN IS BEGIN
    +    -- 1000 lines of code
    +    END barn;
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum1000.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/ExcessivePackageBodyLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/ExcessivePackageBodyLength">
    +    <properties>
    +        <property name="minimum" value="1000.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessivePackageSpecificationLength

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Excessive class file lengths are usually indications that the class may be burdened with excessive +responsibilities that could be provided by external classes or functions. In breaking these methods +apart the code becomes more managable and ripe for reuse.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.ExcessivePackageSpecificationLengthRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE
    +PACKAGE Foo AS
    +    PROCEDURE bar1;
    +    PROCEDURE bar2;
    +    PROCEDURE bar3;
    +
    +    ...
    +
    +    PROCEDURE barN;
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum1000.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/ExcessivePackageSpecificationLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/ExcessivePackageSpecificationLength">
    +    <properties>
    +        <property name="minimum" value="1000.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessiveParameterList

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Methods with numerous parameters are a challenge to maintain, especially if most of them share the +same datatype. These situations usually denote the need for new objects to wrap the numerous parameters.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.ExcessiveParameterListRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE
    +PROCEDURE addPerson(        -- too many arguments liable to be mixed up
    +    birthYear pls_integer, birthMonth pls_integer, birthDate pls_integer, height pls_integer, weight pls_integer, ssn pls_integer) {
    +
    +    . . . .
    +END ADDPERSON;
    +
    +CREATE OR REPLACE
    +PROCEDURE addPerson(        -- preferred approach
    +    birthdate DATE, measurements BodyMeasurements , ssn INTEGER) BEGIN
    +
    +    . . . .
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum10.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/ExcessiveParameterList" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/ExcessiveParameterList">
    +    <properties>
    +        <property name="minimum" value="10.0" />
    +    </properties>
    +</rule>
    +
    + +

    ExcessiveTypeLength

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Excessive class file lengths are usually indications that the class may be burdened with excessive +responsibilities that could be provided by external classes or functions. In breaking these methods +apart the code becomes more managable and ripe for reuse.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.ExcessiveTypeLengthRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE
    +TYPE BODY Foo AS
    +    MEMBER PROCEDURE bar1 IS BEGIN
    +    -- 1000 lines of code
    +    END bar1;
    +    MEMBER PROCEDURE bar2 IS BEGIN
    +    -- 1000 lines of code
    +    END bar2;
    +    MEMBER PROCEDURE bar3 IS BEGIN
    +    -- 1000 lines of code
    +    END bar3;
    +
    +
    +    MEMBER PROCEDURE barN IS BEGIN
    +    -- 1000 lines of code
    +    END barn;
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum1000.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/ExcessiveTypeLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/ExcessiveTypeLength">
    +    <properties>
    +        <property name="minimum" value="1000.0" />
    +    </properties>
    +</rule>
    +
    + +

    NcssMethodCount

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of lines +of code for a given method. NCSS ignores comments, and counts actual statements. Using this algorithm, +lines of code that are split are counted as one.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.NcssMethodCountRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE PACKAGE BODY AS
    + FUNCTION methd RETURN INTEGER IS
    + BEGIN
    +   RETURN 1;;
    + END;
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum100.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/NcssMethodCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/NcssMethodCount">
    +    <properties>
    +        <property name="minimum" value="100.0" />
    +    </properties>
    +</rule>
    +
    + +

    NcssObjectCount

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    This rule uses the NCSS (Non-Commenting Source Statements) algorithm to determine the number of lines +of code for a given Oracle object. NCSS ignores comments, and counts actual statements. Using this algorithm, +lines of code that are split are counted as one.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.NcssObjectCountRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE PACKAGE pkg_
    + PROCEDURE Foo IS
    + BEGIN
    + --this class only has 6 NCSS lines
    +     super();
    +     super();
    + END;
    +}
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum1500.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/NcssObjectCount" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/NcssObjectCount">
    +    <properties>
    +        <property name="minimum" value="1500.0" />
    +    </properties>
    +</rule>
    +
    + +

    NPathComplexity

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    The NPath complexity of a method is the number of acyclic execution paths through that method. +A threshold of 200 is generally considered the point where measures should be taken to reduce +complexity and increase readability.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.NPathComplexityRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE
    +PROCEDURE bar AS BEGIN  -- this is something more complex than it needs to be,
    +    if (y) THEN -- it should be broken down into smaller methods or functions
    +        for j IN 0 .. j-1 LOOP
    +            if (j > r) THEN
    +                doSomething;
    +                while (f < 5 ) LOOP
    +                    anotherThing;
    +                    f := f - 27;
    +                    END LOOP;
    +            else
    +                tryThis();
    +            END IF;
    +        END LOOP;
    +    END IF;
    +    if ( r - n > 45) THEN
    +        while (doMagic) LOOP
    +            findRabbits;
    +        END LOOP;
    +    END IF;
    +    BEGIN
    +        doSomethingDangerous();
    +    EXCEPTION WHEN FooException THEN
    +        makeAmends;
    +        BEGIN
    +            dontDoItAgain;
    +        EXCEPTION
    +        WHEN OTHERS THEN
    +            log_problem;
    +        END;
    +    END;
    +END;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum200.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/NPathComplexity" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/NPathComplexity">
    +    <properties>
    +        <property name="minimum" value="200.0" />
    +    </properties>
    +</rule>
    +
    + +

    TooManyFields

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Classes that have too many fields can become unwieldy and could be redesigned to have fewer fields, +possibly through grouping related fields in new objects. For example, a class with individual +city/state/zip fields could park them within a single Address field.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.plsql.rule.design.TooManyFieldsRule

    + +

    Example(s):

    + +
    CREATE OR REPLACE PACKAGE pkg_too_many_fields AS
    +    C_CHAR_A CONSTANT CHAR(1 CHAR) := 'A';
    +    C_CHAR_B CONSTANT CHAR(1 CHAR) := 'B';
    +    ...
    +    C_CHAR_Z CONSTANT CHAR(1 CHAR) := 'Z';
    +END pkg_too_many_fields;
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maxfields15Max allowable fieldsno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/TooManyFields" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/TooManyFields">
    +    <properties>
    +        <property name="maxfields" value="15" />
    +    </properties>
    +</rule>
    +
    + +

    TooManyMethods

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    A package or type with too many methods is probably a good suspect for refactoring, in order to reduce its complexity and find a way to +have more fine grained objects.

    + +

    This rule is defined by the following XPath expression:

    +
    //node()
    +     [ (
    +        local-name(.) = 'PackageSpecification'
    +        or
    +        local-name(.) = 'TypeSpecification'
    +       )
    +       and
    +      (
    +      count(/descendant::ProgramUnit[
    +                                         not (
    +                                                starts-with(@Name,'get')
    +                                                or
    +                                                starts-with(@Name,'set')
    +                                                or
    +                                                starts-with(@Name,'is')
    +                                            )
    +                                       ]
    +           )
    +      +
    +      count(/descendant::TypeMethod[
    +                                         not (
    +                                                starts-with(@Name,'get')
    +                                                or
    +                                                starts-with(@Name,'set')
    +                                                or
    +                                                starts-with(@Name,'is')
    +                                            )
    +                                       ]
    +           )
    +      ) > $maxmethods
    +     ]
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    maxmethods1The method count reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/plsql/design.xml/TooManyMethods" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/plsql/design.xml/TooManyMethods">
    +    <properties>
    +        <property name="maxmethods" value="1" />
    +    </properties>
    +</rule>
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_plsql_errorprone.html b/pmd_rules_plsql_errorprone.html new file mode 100644 index 0000000000..4b87669ee8 --- /dev/null +++ b/pmd_rules_plsql_errorprone.html @@ -0,0 +1,1569 @@ + + + + + + + + +Error Prone | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Error Prone

    +
    + + + +
    + + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    TO_DATE_TO_CHAR

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    TO_DATE(TO_CHAR(date-variable)) used to remove time component - use TRUNC(date-variable)

    + +

    This rule is defined by the following XPath expression:

    +
    //FunctionCall[@Image='TO_DATE']
    +  [count(Arguments/ArgumentList/Argument) = 1]
    +  [Arguments/ArgumentList/Argument//FunctionCall[@Image='TO_CHAR']]
    +
    + +

    Example(s):

    + +
    CREATE OR REPLACE PACKAGE BODY date_utilities
    +IS
    +
    +-- Take single parameter, relying on current default NLS date format
    +FUNCTION strip_time (p_date IN DATE) RETURN DATE
    +IS
    +BEGIN
    +   RETURN TO_DATE(TO_CHAR(p_date));
    +END strip_time;
    +
    +
    +END date_utilities;
    +/
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/plsql/errorprone.xml/TO_DATE_TO_CHAR" />
    +
    + +

    TO_DATEWithoutDateFormat

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    TO_DATE without date format- use TO_DATE(expression, date-format)

    + +

    This rule is defined by the following XPath expression:

    +
    //FunctionCall[@Image='TO_DATE']
    +  [count(Arguments/ArgumentList/Argument) = 1]
    +
    + +

    Example(s):

    + +
    CREATE OR REPLACE PACKAGE BODY date_utilities
    +IS
    +
    +-- Take single parameter, relying on current default NLS date format
    +FUNCTION to_date_single_parameter (p_date_string IN VARCHAR2) RETURN DATE
    +IS
    +BEGIN
    +   RETURN TO_DATE(p_date_string);
    +END to_date_single_parameter ;
    +
    +-- Take 2 parameters, using an explicit date format string
    +FUNCTION to_date_two_parameters (p_date_string IN VARCHAR2, p_format_mask IN VARCHAR2) RETURN DATE
    +IS
    +BEGIN
    +   TO_DATE(p_date_string, p_date_format);
    +END to_date_two_parameters;
    +
    +-- Take 3 parameters, using an explicit date format string and an explicit language
    +FUNCTION to_date_three_parameters (p_date_string IN VARCHAR2, p_format_mask IN VARCHAR2, p_nls_language VARCHAR2 ) RETURN DATE
    +IS
    +BEGIN
    +   TO_DATE(p_date_string, p_format_mask, p_nls_language);
    +END to_date_three_parameters;
    +
    +END date_utilities;
    +/
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/plsql/errorprone.xml/TO_DATEWithoutDateFormat" />
    +
    + +

    TO_TIMESTAMPWithoutDateFormat

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    TO_TIMESTAMP without date format- use TO_TIMESTAMP(expression, date-format)

    + +

    This rule is defined by the following XPath expression:

    +
    //FunctionCall[@Image='TO_TIMESTAMP']
    +  [count(Arguments/ArgumentList/Argument) = 1]
    +
    + +

    Example(s):

    + +
    CREATE OR REPLACE PACKAGE BODY date_utilities
    +IS
    +
    +-- Take single parameter, relying on current default NLS date format
    +FUNCTION to_timestamp_single_parameter (p_date_string IN VARCHAR2) RETURN DATE
    +IS
    +BEGIN
    +   RETURN TO_TIMESTAMP(p_date_string);
    +END to_timestamp_single_parameter;
    +
    +-- Take 2 parameters, using an explicit date format string
    +FUNCTION to_timestamp_two_parameters (p_date_string IN VARCHAR2, p_format_mask IN VARCHAR2) RETURN DATE
    +IS
    +BEGIN
    +   TO_TIMESTAMP(p_date_string, p_date_format);
    +END to_timestamp_two_parameters;
    +
    +-- Take 3 parameters, using an explicit date format string and an explicit language
    +FUNCTION to_timestamp_three_parameters (p_date_string IN VARCHAR2, p_format_mask IN VARCHAR2, p_nls_language VARCHAR2 ) RETURN DATE
    +IS
    +BEGIN
    +   TO_TIMESTAMP(p_date_string, p_format_mask, p_nls_language);
    +END to_timestamp_three_parameters;
    +
    +END date_utilities;
    +/
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/plsql/errorprone.xml/TO_TIMESTAMPWithoutDateFormat" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_pom.html b/pmd_rules_pom.html new file mode 100644 index 0000000000..146287bb6f --- /dev/null +++ b/pmd_rules_pom.html @@ -0,0 +1,1473 @@ + + + + + + + + +Maven POM Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Maven POM Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for Maven POM
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Error Prone

    + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + +

    Additional rulesets

    + + + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_pom_errorprone.html b/pmd_rules_pom_errorprone.html new file mode 100644 index 0000000000..58b388cf63 --- /dev/null +++ b/pmd_rules_pom_errorprone.html @@ -0,0 +1,1540 @@ + + + + + + + + +Error Prone | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Error Prone

    +
    + + + +
    + + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    InvalidDependencyTypes

    + +

    Since: PMD 5.4

    + +

    Priority: Medium (3)

    + +

    If you use an invalid dependency type in the dependency management section, Maven doesn’t fail. Instead, +the entry is just ignored, which might have the effect, that the wrong version of the dependency is used.

    + +

    The following types are considered valid: pom, jar, maven-plugin, ejb, war, ear, rar, par.

    + +

    This rule is defined by the following XPath expression:

    +
    //dependencyManagement/dependency/type/text[not(@Image = $validTypes)]
    +
    + +

    Example(s):

    + +
    <project...>
    +  ...
    +  <dependencyManagement>
    +      ...
    +    <dependency>
    +      <groupId>org.jboss.arquillian</groupId>
    +      <artifactId>arquillian-bom</artifactId>
    +      <version>${arquillian.version}</version>
    +      <type>bom</type> <!-- not a valid type ! 'pom' is ! -->
    +      <scope>import</scope>
    +    </dependency>
    +    ...
    +  </dependencyManagement>
    +</project>
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    validTypespom , jar , maven-plugin , ejb , war , ear , rar , parSet of valid types.yes. Delimiter is ‘,’.
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/pom/errorprone.xml/InvalidDependencyTypes" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/pom/errorprone.xml/InvalidDependencyTypes">
    +    <properties>
    +        <property name="validTypes" value="pom,jar,maven-plugin,ejb,war,ear,rar,par" />
    +    </properties>
    +</rule>
    +
    + +

    ProjectVersionAsDependencyVersion

    + +

    Since: PMD 5.4

    + +

    Priority: Medium (3)

    + +

    Using that expression in dependency declarations seems like a shortcut, but it can go wrong. +By far the most common problem is the use of ${project.version} in a BOM or parent POM.

    + +

    This rule is defined by the following XPath expression:

    +
    //dependencies/dependency
    +    [contains(version/text/@Image,'{project.version}')]
    +    [
    +        (/document/project/parent/groupId and groupId/text/@Image != /document/project/parent/groupId/text/@Image)
    +        or
    +        (/document/project/groupId and groupId/text/@Image != /document/project/groupId/text/@Image)
    +    ]/version
    +
    + +

    Example(s):

    + +
    <project...>
    +  ...
    +  <dependency>
    +    ...
    +    <version>6.30.0-SNAPSHOT</version>
    +  </dependency>
    +</project>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/pom/errorprone.xml/ProjectVersionAsDependencyVersion" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_scala.html b/pmd_rules_scala.html new file mode 100644 index 0000000000..2c9d579075 --- /dev/null +++ b/pmd_rules_scala.html @@ -0,0 +1,1453 @@ + + + + + + + + +Scala Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Scala Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for Scala
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Currently there are no built-in rules yet for Scala.

    + +

    Contributions are welcome!

    + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_vf.html b/pmd_rules_vf.html new file mode 100644 index 0000000000..443eeb6157 --- /dev/null +++ b/pmd_rules_vf.html @@ -0,0 +1,1473 @@ + + + + + + + + +Salesforce VisualForce Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Salesforce VisualForce Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for Salesforce VisualForce
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Security

    + +
    Rules that flag potential security flaws.
    + +
      +
    • VfCsrf: Avoid calling VF action upon page load as the action becomes vulnerable to CSRF.
    • +
    • VfUnescapeEl: Avoid unescaped user controlled content in EL as it results in XSS.
    • +
    + +

    Additional rulesets

    + +
      +
    • +

      Basic VF (rulesets/vf/security.xml):

      + +

      Deprecated This ruleset is for backwards compatibility.

      + +

      It contains the following rules:

      + +

      VfCsrf, VfUnescapeEl

      +
    • +
    + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_vf_security.html b/pmd_rules_vf_security.html new file mode 100644 index 0000000000..08da167111 --- /dev/null +++ b/pmd_rules_vf_security.html @@ -0,0 +1,1478 @@ + + + + + + + + +Security | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Security

    +
    + + + +
    + + +
    Rules that flag potential security flaws.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    VfCsrf

    + +

    Since: PMD 5.6.0

    + +

    Priority: Medium (3)

    + +

    Avoid calling VF action upon page load as the action becomes vulnerable to CSRF.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vf.rule.security.VfCsrfRule

    + +

    Example(s):

    + +
    <apex:page controller="AcRestActionsController" action="{!csrfInitMethod}" >
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/vf/security.xml/VfCsrf" />
    +
    + +

    VfUnescapeEl

    + +

    Since: PMD 5.6.0

    + +

    Priority: Medium (3)

    + +

    Avoid unescaped user controlled content in EL as it results in XSS.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vf.rule.security.VfUnescapeElRule

    + +

    Example(s):

    + +
    <apex:outputText value="Potential XSS is {! here }" escape="false" />
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/vf/security.xml/VfUnescapeEl" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_vm.html b/pmd_rules_vm.html new file mode 100644 index 0000000000..5152005fca --- /dev/null +++ b/pmd_rules_vm.html @@ -0,0 +1,1494 @@ + + + + + + + + +VM Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    VM Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for VM
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Best Practices

    + +
    Rules which enforce generally accepted best practices.
    + + + +

    Design

    + +
    Rules that help you discover design issues.
    + + + +

    Error Prone

    + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + +

    Additional rulesets

    + + + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_vm_bestpractices.html b/pmd_rules_vm_bestpractices.html new file mode 100644 index 0000000000..cd12b66167 --- /dev/null +++ b/pmd_rules_vm_bestpractices.html @@ -0,0 +1,1468 @@ + + + + + + + + +Best Practices | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Best Practices

    +
    + + + +
    + + +
    Rules which enforce generally accepted best practices.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AvoidReassigningParameters

    + +

    Since: PMD 5.1

    + +

    Priority: Medium High (2)

    + +

    Reassigning values to incoming parameters is not recommended. Use temporary local variables instead.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vm.rule.bestpractices.AvoidReassigningParametersRule

    + +

    Use this rule by referencing it:

    +
    <rule ref="category/vm/bestpractices.xml/AvoidReassigningParameters" />
    +
    + +

    UnusedMacroParameter

    + +

    Since: PMD 5.1

    + +

    Priority: Medium High (2)

    + +

    Avoid unused macro parameters. They should be deleted.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vm.rule.bestpractices.UnusedMacroParameterRule

    + +

    Use this rule by referencing it:

    +
    <rule ref="category/vm/bestpractices.xml/UnusedMacroParameter" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_vm_design.html b/pmd_rules_vm_design.html new file mode 100644 index 0000000000..7fcd3ab0f9 --- /dev/null +++ b/pmd_rules_vm_design.html @@ -0,0 +1,1582 @@ + + + + + + + + +Design | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Design

    +
    + + + +
    + + +
    Rules that help you discover design issues.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AvoidDeeplyNestedIfStmts

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Avoid creating deeply nested if-then statements since they are harder to read and error-prone to maintain.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vm.rule.design.AvoidDeeplyNestedIfStmtsRule

    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    problemDepth3The if statement depth reporting thresholdno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/vm/design.xml/AvoidDeeplyNestedIfStmts" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/vm/design.xml/AvoidDeeplyNestedIfStmts">
    +    <properties>
    +        <property name="problemDepth" value="3" />
    +    </properties>
    +</rule>
    +
    + +

    CollapsibleIfStatements

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    Sometimes two consecutive ‘if’ statements can be consolidated by separating their conditions with a boolean short-circuit operator.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vm.rule.design.CollapsibleIfStatementsRule

    + +

    Use this rule by referencing it:

    +
    <rule ref="category/vm/design.xml/CollapsibleIfStatements" />
    +
    + +

    ExcessiveTemplateLength

    + +

    Since: PMD 5.1

    + +

    Priority: Medium (3)

    + +

    The template is too long. It should be broken up into smaller pieces.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vm.rule.design.ExcessiveTemplateLengthRule

    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    topscore Deprecated Top score valueno
    minimum1000.0Minimum reporting thresholdno
    sigma Deprecated Sigma valueno
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/vm/design.xml/ExcessiveTemplateLength" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/vm/design.xml/ExcessiveTemplateLength">
    +    <properties>
    +        <property name="minimum" value="1000.0" />
    +    </properties>
    +</rule>
    +
    + +

    NoInlineJavaScript

    + +

    Since: PMD 5.1

    + +

    Priority: Medium High (2)

    + +

    Avoid inline JavaScript. Import .js files instead.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vm.rule.design.NoInlineJavaScriptRule

    + +

    Use this rule by referencing it:

    +
    <rule ref="category/vm/design.xml/NoInlineJavaScript" />
    +
    + +

    NoInlineStyles

    + +

    Since: PMD 5.1

    + +

    Priority: Medium High (2)

    + +

    Avoid inline styles. Use css classes instead.

    + +

    This rule is defined by the following XPath expression:

    +
    //Text[matches(@literal, "<[^>]+\s[sS][tT][yY][lL][eE]\s*=")]
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/vm/design.xml/NoInlineStyles" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_vm_errorprone.html b/pmd_rules_vm_errorprone.html new file mode 100644 index 0000000000..d73c612544 --- /dev/null +++ b/pmd_rules_vm_errorprone.html @@ -0,0 +1,1468 @@ + + + + + + + + +Error Prone | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Error Prone

    +
    + + + +
    + + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    EmptyForeachStmt

    + +

    Since: PMD 5.1

    + +

    Priority: Medium High (2)

    + +

    Empty foreach statements should be deleted.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vm.rule.errorprone.EmptyForeachStmtRule

    + +

    Use this rule by referencing it:

    +
    <rule ref="category/vm/errorprone.xml/EmptyForeachStmt" />
    +
    + +

    EmptyIfStmt

    + +

    Since: PMD 5.1

    + +

    Priority: Medium High (2)

    + +

    Empty if statements should be deleted.

    + +

    This rule is defined by the following Java class: net.sourceforge.pmd.lang.vm.rule.errorprone.EmptyIfStmtRule

    + +

    Use this rule by referencing it:

    +
    <rule ref="category/vm/errorprone.xml/EmptyIfStmt" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_xml.html b/pmd_rules_xml.html new file mode 100644 index 0000000000..b9248bb68b --- /dev/null +++ b/pmd_rules_xml.html @@ -0,0 +1,1472 @@ + + + + + + + + +XML Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    XML Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for XML
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Error Prone

    + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + +
      +
    • MistypedCDATASection: An XML CDATA section begins with a <![CDATA[ marker, which has only one [, and ends with a ]]> ma…
    • +
    + +

    Additional rulesets

    + +
      +
    • +

      Basic XML (rulesets/xml/basic.xml):

      + +

      Deprecated This ruleset is for backwards compatibility.

      + +

      It contains the following rules:

      + +

      MistypedCDATASection

      +
    • +
    + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_xml_errorprone.html b/pmd_rules_xml_errorprone.html new file mode 100644 index 0000000000..8eb8b84b9d --- /dev/null +++ b/pmd_rules_xml_errorprone.html @@ -0,0 +1,1472 @@ + + + + + + + + +Error Prone | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Error Prone

    +
    + + + +
    + + +
    Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    MistypedCDATASection

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    An XML CDATA section begins with a <![CDATA[ marker, which has only one [, and ends with a ]]> marker, which has two ].

    + +

    This rule is defined by the following XPath expression:

    +
    //cdata-section[starts-with(@Image,'[') or ends-with(@Image,']')]
    +
    + +

    Example(s):

    + +
    <root>
    +    <child>
    +        <![CDATA[[ character data ]]> - this cdata section is valid, but it contains an
    +        additional square bracket at the beginning.
    +        It should probably be just <![CDATA[ character data ]]>.
    +    </child>
    +    <child>
    +        <![CDATA[ character data ]]]> - this cdata section is valid, but it contains an
    +        additional square bracket in the end.
    +        It should probably be just <![CDATA[ character data ]]>.
    +    </child>
    +</root>
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/xml/errorprone.xml/MistypedCDATASection" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_xsl.html b/pmd_rules_xsl.html new file mode 100644 index 0000000000..6fe56f3012 --- /dev/null +++ b/pmd_rules_xsl.html @@ -0,0 +1,1480 @@ + + + + + + + + +XSL Rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    XSL Rules

    +
    + + + +
    + + +
    Index of all built-in rules available for XSL
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Code Style

    + +
    Rules which enforce a specific coding style.
    + +
      +
    • UseConcatOnce: The XPath concat() functions accepts as many arguments as required so you can have "concat($a,’b’…
    • +
    + +

    Performance

    + +
    Rules that flag suboptimal code.
    + +
      +
    • AvoidAxisNavigation: Avoid using the ‘following’ or ‘preceding’ axes whenever possible, as these can cut through 100% …
    • +
    + +

    Additional rulesets

    + +
      +
    • +

      XPath in XSL (rulesets/xsl/xpath.xml):

      + +

      Deprecated This ruleset is for backwards compatibility.

      + +

      It contains the following rules:

      + +

      AvoidAxisNavigation, UseConcatOnce

      +
    • +
    + + + +
    + + Tags: + + + + rule_references + + + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_xsl_codestyle.html b/pmd_rules_xsl_codestyle.html new file mode 100644 index 0000000000..567fed6f08 --- /dev/null +++ b/pmd_rules_xsl_codestyle.html @@ -0,0 +1,1463 @@ + + + + + + + + +Code Style | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Code Style

    +
    + + + +
    + + +
    Rules which enforce a specific coding style.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    UseConcatOnce

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    The XPath concat() functions accepts as many arguments as required so you can have +"concat($a,’b’,$c)" rather than "concat($a,concat(‘b’,$c)".

    + +

    This rule is defined by the following XPath expression:

    +
    //node()[contains(substring-after(@select,'concat'),'concat')]
    +
    + +

    Example(s):

    + +
    <xsl:variable name="var" select="concat("Welcome",concat("to you ",$name))"/>
    +<xsl:variable name="var" select="concat("Welcome","to you ",$name))">
    +
    + +

    Use this rule by referencing it:

    +
    <rule ref="category/xsl/codestyle.xml/UseConcatOnce" />
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_rules_xsl_performance.html b/pmd_rules_xsl_performance.html new file mode 100644 index 0000000000..f82cbc2e39 --- /dev/null +++ b/pmd_rules_xsl_performance.html @@ -0,0 +1,1506 @@ + + + + + + + + +Performance | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Performance

    +
    + + + +
    + + +
    Rules that flag suboptimal code.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    AvoidAxisNavigation

    + +

    Since: PMD 5.0

    + +

    Priority: Medium (3)

    + +

    Avoid using the ‘following’ or ‘preceding’ axes whenever possible, as these can cut +through 100% of the document in the worst case. Also, try to avoid using ‘descendant’ +or ‘descendant-or-self’ axes, as if you’re at the top of the Document, it necessarily means +cutting through 100% of the document.

    + +

    This rule is defined by the following XPath expression:

    +
    //node()[
    +  contains(@select,'preceding::')
    +  or
    +  contains(@select,'following::')
    +  or
    +  contains(@select,'descendant::')
    +  or
    +  contains(@select,'descendant-self::')
    +  or (
    +    ($checkSelfDescendantAbreviation = true() )
    +    and
    +    contains(@select,'//')
    +    )
    +]
    +
    + +

    Example(s):

    + +
    <xsl:variable name="var" select="//item/descendant::child"/>
    +
    + +

    This rule has the following properties:

    + + + + + + + + + + + + + + + + + + +
    NameDefault ValueDescriptionMultivalued
    checkSelfDescendantAbreviationfalsedescendant::self abreviation, ‘//’, will also trigger this rule.no
    + +

    Use this rule with the default properties by just referencing it:

    +
    <rule ref="category/xsl/performance.xml/AvoidAxisNavigation" />
    +
    + +

    Use this rule and customize it:

    +
    <rule ref="category/xsl/performance.xml/AvoidAxisNavigation">
    +    <properties>
    +        <property name="checkSelfDescendantAbreviation" value="false" />
    +    </properties>
    +</rule>
    +
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_best_practices.html b/pmd_userdocs_best_practices.html new file mode 100644 index 0000000000..d0989597f0 --- /dev/null +++ b/pmd_userdocs_best_practices.html @@ -0,0 +1,1475 @@ + + + + + + + + +Best Practices | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Best Practices

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Choose the rules that are right for you

    + +

    Running every existing rule will result in a huge number of rule violations, most of which will be unimportant. +Having to sort through a thousand line report to find the few you’re really interested in takes +all the fun out of things.

    + +

    Instead, start with some selected specific rules, e.g. the rules that detect unused code from +the category Best Practices and fix any unused locals and fields.

    + +

    Then, run rules, that detect empty if statements and such-like. You can find these rules in the category +Error Prone.

    + +

    After that, look at all the categories and select the rules, that are useful for your project. +You can find an overview of the rules on the Rule Index.

    + +

    Use the rules you like via a custom ruleset.

    + +

    PMD rules are not set in stone

    + +

    Generally, pick the ones you like, and ignore or suppress +the warnings you don’t like. It’s just a tool.

    + +

    PMD IDE plugins are nice

    + +

    Using PMD within your IDE is much more enjoyable than flipping back and forth +between an HTML report and your IDE. Most IDE plugins have the “click on the rule +violation and jump to that line of code” feature. Find the PMD plugin for your IDE, install it, +and soon you’ll be fixing problems much faster.

    + +

    Suggestions? Comments? Post them here. Thanks!

    + + +
    + + Tags: + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_cli_reference.html b/pmd_userdocs_cli_reference.html new file mode 100644 index 0000000000..c1b4b27583 --- /dev/null +++ b/pmd_userdocs_cli_reference.html @@ -0,0 +1,2094 @@ + + + + + + + + +PMD CLI reference | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    PMD CLI reference

    +
    + + + +
    + + +
    Full reference for PMD's command-line interface, including options, output formats and supported languages
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Options

    + +

    The tool comes with a rather extensive help text, simply running with -help!

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    OptionDescriptionDefault valueApplies to
    -rulesets <refs>
    -R <refs>
    Required Comma-separated list of ruleset or rule references.
    -dir <path>
    -d <path>
    Required Root directory for the analyzed sources.
    -format <format>
    -f <format>
    Output format of the analysis report. The available formats + are described here.text
    -auxclasspath <cp>Specifies the classpath for libraries used by the source code. + This is used to resolve types in source files. The platform specific path delimiter + (":" on Linux, ";" on Windows) is used to separate the entries. + Alternatively, a single file: URL + to a text file containing path elements on consecutive lines can be specified.Java
    -benchmark
    -b
    Enables benchmark mode, which outputs a benchmark report upon completion. + The report is sent to standard error.
    -cache <filepath>Specify the location of the cache file for incremental analysis. + This should be the full path to the file, including the desired file name (not just the parent directory). + If the file doesn't exist, it will be created on the first run. The file will be overwritten on each run + with the most up-to-date rule violations. + This can greatly improve analysis performance and is highly recommended.
    -debug
    -verbose
    -D
    -V
    Debug mode. Prints more log output.
    -encoding <charset>
    -e <charset>
    Specifies the character set encoding of the source code files PMD is reading. + The valid values are the standard character sets of java.nio.charset.Charset.UTF-8
    -failOnViolation <bool>
    --failOnViolation <bool>
    Specifies whether PMD exits with non-zero status if violations are found. + By default PMD exits with status 4 if violations are found. + Disable this feature with -failOnViolation false to exit with 0 instead and just output the report.true
    -filelist <filepath>Path to file containing a comma delimited list of files to analyze. + If this is given, then you don't need to provide -dir.
    -ignorelist <filepath>Path to file containing a comma delimited list of files to ignore. + This option can be combined with -dir and -filelist. + This ignore list takes precedence over any files in the filelist.
    -help
    -h
    -H
    Display help on usage.
    -language <lang>
    -l <lang>
    Specify the language PMD should use. Used together with -version. See also Supported Languages.
    -minimumpriority <num>
    -min <num>
    Rule priority threshold; rules with lower priority than configured here won't be used.5
    -norulesetcompatibilityDisable automatic fixing of invalid rule references. Without the switch, PMD tries to automatically replace rule references that point to moved or renamed rules with the newer location if possible. Disabling it is not recommended.
    -no-cacheExplicitly disables incremental analysis. This switch turns off suggestions to use Incremental Analysis, + and causes the -cache option to be discarded if it is provided.
    -property <name>=<value>
    -P <name>=<value>
    Specifies a property for the report renderer. The option can be specified several times.[]
    -reportfile <path>
    -r <path>
    Path to a file in which the report output will be sent. By default the report is printed on standard output.
    -shortnamesPrints shortened filenames in the report.
    -showsuppressedCauses the suppressed rule violations to be added to the report.
    -stress
    -S
    Performs a stress test.
    -suppressmarker <marker>Specifies the comment token that marks lines which PMD should ignore.NOPMD
    -threads <num>
    -t <num>
    Sets the number of threads used by PMD. + Set threads to 0 to disable multi-threading processing.1
    -uri <uri>
    -u <uri>
    Database URI for sources. If this is given, then you don't need to provide -dir.PLSQL
    -version <version>
    -v <version>
    Specify the version of a language PMD should use. Used together with -language. See also Supported Languages.
    + +

    Additional Java Runtime Options

    + +

    PMD is executed via a Java runtime. In some cases, you might need to set additional runtime options, e.g. +if you want to analyze a project, that uses one of OpenJDK’s Preview Language Features.

    + +

    Just set the environment variable PMD_JAVA_OPTS before executing PMD, e.g.

    + +
    export PMD_JAVA_OPTS="--enable-preview"
    +./run.sh pmd -d ../../../src/main/java/ -f text -R rulesets/java/quickstart.xml
    +
    + +

    Exit Status

    + +

    Please note that if PMD detects any violations, it will exit with status 4 (since 5.3). +This behavior has been introduced to ease PMD integration into scripts or hooks, such as SVN hooks.

    + + + + + +
    0Everything is fine, no violations found
    1Couldn't understand command-line parameters or PMD exited with an exception
    4At least one violation has been detected, unless -failOnViolation false is set.
    + +

    Supported Languages

    + +

    The language is determined automatically by PMD from the file extensions. Some languages such as “Java” +however support multiple versions. The default version will be used, which is usually the latest supported +version. If you want to use an older version, so that e.g. rules, that suggest usage of language features, +that are not available yet, won’t be executed, you need to specify a specific version via the -language +and -version parameter.

    + +

    These parameters are irrelevant for languages that don’t support different versions.

    + +

    Example:

    + +
    ./run.sh pmd -d src/main/java -f text -R rulesets/java/quickstart.xml -language java -version 8
    +
    + +
      +
    • apex (Salesforce Apex)
    • +
    • java +
        +
      • Supported Versions: 1.3, 1.4, 1.5, 5, 1.6, 6, 1.7, 7, 1.8, 8, 9, 1.9, 10, 1.10, 11, 12, +13, 14, 14-preview, 15 (default), 15-preview
      • +
      +
    • +
    • ecmascript (JavaScript)
    • +
    • jsp
    • +
    • modelica
    • +
    • plsql
    • +
    • scala +
        +
      • Supported Versions: 2.10, 2.11, 2.12, 2.13 (default)
      • +
      +
    • +
    • vf (Salesforce VisualForce)
    • +
    • vm (Apache Velocity)
    • +
    • xml and xsl
    • +
    + +

    Available Report Formats

    + +

    PMD comes with many different renderers. +All formats are described at PMD Report formats

    + + + +
    + + Tags: + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_configuring_rules.html b/pmd_userdocs_configuring_rules.html new file mode 100644 index 0000000000..33c765f048 --- /dev/null +++ b/pmd_userdocs_configuring_rules.html @@ -0,0 +1,1501 @@ + + + + + + + + +Configuring rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Configuring rules

    +
    + + + +
    + + +
    Learn how to configure your rules directly from the ruleset XML.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Message and priority overriding

    + +

    You can change a rule’s message by specifying a message +attribute on the rule element. This will override the previous +value and change the message the rule will print on the report.

    + +

    Similarly, the priority of a rule can be changed via a nested +element. Using priority, you can deactivate some rules based on a +minimum priority threshold (set using the -min CLI option). +Priority is an integer ranging from 1 to 5, with 1 being the highest +priority.

    + +

    Putting things together, the following rule reference lowers the priority +of EmptyCatchBlock to 5, such that e.g. using the -min 4 CLI parameters +will cause the rule to be ignored.

    + +
    <rule ref="category/java/errorprone.xml/EmptyCatchBlock"
    +      message="Empty catch blocks should be avoided" >
    +      <priority>5</priority>
    +</rule>
    +
    + +

    Rule properties

    + +

    Properties make it easy to customise the behaviour of a rule directly from the xml. They come in several types, which correspond to the type of their values. For example, NPathComplexity declares a property “reportLevel”, with an integer value type, and which corresponds to the threshold above which a method will be reported. If you believe that its default value of 200 is too high, you could lower it to e.g. 150 in the following way:

    + +
    <rule ref="category/java/design.xml/NPathComplexity">
    +    <properties>
    +        <property name="reportLevel">
    +              <value>150</value>
    +        </property>
    +    </properties>
    +</rule>
    +
    + +

    Properties are assigned a value with a property element, which should mention the name of a property as an attribute. The value of the property can be specified either in the content of the element, like above, or in the value attribute, e.g.

    + +
    <property name="reportLevel" value="150"/>
    +
    + +

    All property assignments must be enclosed in a properties element, which is itself inside a rule element.

    + + + +

    Some properties take multiple values (a list), in which case you can provide them all by delimiting them with a delimiter character. It is usually a pipe (‘|’), or a comma (‘,’) for numeric properties, e.g.

    +
     <property name="legalCollectionTypes"
    +           value="java.util.ArrayList|java.util.Vector|java.util.HashMap"/>
    +
    + +

    These properties are referred to as multivalued properties in this documentation.

    + + +
    + + Tags: + + + + userdocs + + + + getting_started + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_cpd.html b/pmd_userdocs_cpd.html new file mode 100644 index 0000000000..c139ecde9b --- /dev/null +++ b/pmd_userdocs_cpd.html @@ -0,0 +1,2458 @@ + + + + + + + + +Finding duplicated code with CPD | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Finding duplicated code with CPD

    +
    + + + +
    + + +
    Learn how to use CPD, the copy-paste detector shipped with PMD.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Overview

    + +

    Duplicate code can be hard to find, especially in a large project. +But PMD’s Copy/Paste Detector (CPD) can find it for you!

    + +

    CPD works with Java, JSP, C/C++, C#, Go, Kotlin, Ruby, Swift and many more languages. +It can be used via command-line, or via an Ant task. +It can also be run with Maven by using the cpd-check goal on the Maven PMD Plugin.

    + +

    Your own language is missing? +See how to add it here.

    + +

    Why should you care about duplicates?

    + +

    It’s certainly important to know where to get CPD, and how to call it, but it’s worth stepping back for a moment and asking yourself why you should care about this, being the occurrence of duplicate code blocks.

    + +

    Assuming duplicated blocks of code are supposed to do the same thing, any refactoring, even simple, must be duplicated too – which is unrewarding grunt work, and puts pressure on the developer to find every place in which to perform the refactoring. Automated tools like CPD can help with that to some extent.

    + +

    However, failure to keep the code in sync may mean automated tools will no longer recognise these blocks as duplicates. This means the task of finding duplicates to keep them in sync when doing subsequent refactorings can no longer be entrusted to an automated tool – adding more burden on the maintainer. Segments of code initially supposed to do the same thing may grow apart undetected upon further refactoring.

    + +

    Now, if the code may never change in the future, then this is not a problem.

    + +

    Otherwise, the most viable solution is to not duplicate. If the duplicates are already there, then they should be refactored out. We thus advise developers to use CPD to help remove duplicates, not to help keep duplicates in sync.

    + +

    Refactoring duplicates

    + +

    Once you have located some duplicates, several refactoring strategies may apply depending of the scope and extent of the duplication. Here’s a quick summary:

    + +
      +
    • If the duplication is local to a method or single class: +
        +
      • Extract a local variable if the duplicated logic is not prohibitively long
      • +
      • Extract the duplicated logic into a private method
      • +
      +
    • +
    • If the duplication occurs in siblings within a class hierarchy: +
        +
      • Extract a method and pull it up in the class hierarchy, along with common fields
      • +
      • Use the Template Method design pattern
      • +
      +
    • +
    • If the duplication occurs consistently in unrelated hierarchies: +
        +
      • Introduce a common ancestor to those class hierarchies
      • +
      +
    • +
    + +

    Novice as much as advanced readers may want to read on on Refactoring Guru for more in-depth strategies, use cases and explanations.

    + +

    CLI Usage

    + +

    CLI options reference

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    OptionDescriptionDefaultApplies to
    --minimum-tokensRequired The minimum token length which should be reported as a duplicate.
    --filesRequired List of files and directories to process
    --filelistPath to file containing a comma delimited list of files to analyze. If this is given, then you don't need to provide --files.
    --languageSources code language.java
    --encodingCharacter encoding to use when processing files. If not specified, CPD uses the system default encoding.
    --skip-duplicate-filesIgnore multiple copies of files of the same name and length in comparison.false
    --excludeFiles to be excluded from CPD check
    --non-recursiveDon't scan subdirectoriesfalse
    --skip-lexical-errorsSkip files which can't be tokenized due to invalid characters instead of aborting CPDfalse
    --formatReport format.text
    --failOnViolation <bool>By default CPD exits with status 4 if code duplications are found. + Disable this option with --failOnViolation false to exit with 0 instead and just write the report.true
    --ignore-literalsIgnore number values and string contents when comparing textfalseJava
    --ignore-identifiersIgnore constant and variable names when comparing textfalseJava
    --ignore-annotationsIgnore language annotations when comparing textfalseJava
    --ignore-usingsIgnore using directives in C# when comparing textfalseC#
    --no-skip-blocksDo not skip code blocks matched by --skip-blocks-patternfalseC++
    --skip-blocks-patternPattern to find the blocks to skip. It is a string property and contains of two parts, + separated by |. The first part is the start pattern, the second part is the ending pattern.#if 0|#endifC++
    --uriURI to processPLSQL
    --help
    -h
    Print help textfalse
    + +

    Examples

    + +

    Note: The following example use the Linux start script. For Windows, just replace “./run.sh cpd” by “cpd.bat”.

    + +

    Minimum required options: Just give it the minimum duplicate size and the source directory:

    + +
    $ ./run.sh cpd --minimum-tokens 100 --files /usr/local/java/src/java
    +
    + +

    You can also specify the language:

    + +
    $ ./run.sh cpd --minimum-tokens 100 --files /path/to/c/source --language cpp
    +
    + +

    You may wish to check sources that are stored in different directories:

    + +
    $ ./run.sh cpd --minimum-tokens 100 --files /path/to/other/source  --files /path/to/other/source --files /path/to/other/source --language fortran
    +
    + +

    There should be no limit to the number of ‘–files’, you may add… But if you stumble one, please tell us !

    + +

    And if you’re checking a C source tree with duplicate files in different architecture directories +you can skip those using –skip-duplicate-files:

    + +
    $ ./run.sh cpd --minimum-tokens 100 --files /path/to/c/source --language cpp --skip-duplicate-files
    +
    + +

    You can also specify the encoding to use when parsing files:

    + +
    $ ./run.sh cpd --minimum-tokens 100 --files /usr/local/java/src/java --encoding utf-16le
    +
    + +

    You can also specify a report format - here we’re using the XML report:

    + +
    $ ./run.sh cpd --minimum-tokens 100 --files /usr/local/java/src/java --format xml
    +
    + +

    The default format is a text report, and there’s also a csv report.

    + +

    Note that CPD is pretty memory-hungry; you may need to give Java more memory to run it, like this:

    + +
    $ export PMD_JAVA_OPTS=-Xmx512m
    +$ ./run.sh cpd --minimum-tokens 100 --files /usr/local/java/src/java
    +
    + +

    In order to change the heap size under Windows, you’ll need to edit the batch file cpd.bat or +set the environment variable PMD_JAVA_OPTS prior to starting CPD:

    + +
    C:\ > cd C:\pmd-bin-6.30.0-SNAPSHOT\bin
    +C:\...\bin > set PMD_JAVA_OPTS=-Xmx512m
    +C:\...\bin > .\cpd.bat --minimum-tokens 100 --files c:\temp\src
    +
    + +

    If you specify a source directory but don’t want to scan the sub-directories, you can use the non-recursive option:

    + +
    $ ./run.sh cpd --minimum-tokens 100 --non-recursive --files /usr/local/java/src/java
    +
    + +

    Exit status

    + +

    Please note that if CPD detects duplicated source code, it will exit with status 4 (since 5.0). +This behavior has been introduced to ease CPD integration into scripts or hooks, such as SVN hooks.

    + + + + + +
    0Everything is fine, no code duplications found
    1Couldn't understand command line parameters or CPD exited with an exception
    4At least one code duplication has been detected unless '--failOnViolation false' is used.
    + +

    Supported Languages

    + +
      +
    • C#
    • +
    • C/C++
    • +
    • Dart
    • +
    • EcmaScript (JavaScript)
    • +
    • Fortran
    • +
    • Go
    • +
    • Groovy
    • +
    • Java
    • +
    • Jsp
    • +
    • Kotlin
    • +
    • Lua
    • +
    • Matlab
    • +
    • Modelica
    • +
    • Objective-C
    • +
    • Perl
    • +
    • PHP
    • +
    • PL/SQL
    • +
    • Python
    • +
    • Ruby
    • +
    • Salesforce.com Apex
    • +
    • Scala
    • +
    • Swift
    • +
    • Visualforce
    • +
    • XML
    • +
    + +

    Available report formats

    + +
      +
    • text : Default format
    • +
    • xml
    • +
    • csv
    • +
    • csv_with_linecount_per_file
    • +
    • vs
    • +
    + +

    For details, see CPD Report Formats.

    + +

    Ant task

    + +

    Andy Glover wrote an Ant task for CPD; here’s how to use it:

    + +
        <target name="cpd">
    +        <taskdef name="cpd" classname="net.sourceforge.pmd.cpd.CPDTask" />
    +        <cpd minimumTokenCount="100" outputFile="/home/tom/cpd.txt">
    +            <fileset dir="/home/tom/tmp/ant">
    +                <include name="**/*.java"/>
    +            </fileset>
    +        </cpd>
    +    </target>
    +
    + + + +

    Attribute reference

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    AttributeDescriptionDefaultApplies to
    minimumtokencountRequired A positive integer indicating the minimum duplicate size.
    encodingThe character set encoding (e.g., UTF-8) to use when reading the source code files, but also when + producing the report. A piece of warning, even if you set properly the encoding value, + let's say to UTF-8, but you are running CPD encoded with CP1252, you may end up with not UTF-8 file. + Indeed, CPD copy piece of source code in its report directly, therefore, the source files + keep their encoding.
    + If not specified, CPD uses the system default encoding.
    formatThe format of the report (e.g. csv, text, xml).text
    ignoreLiteralsif true, CPD ignores literal value differences when evaluating a duplicate + block. This means that foo=42; and foo=43; will be seen as equivalent. You may want + to run PMD with this option off to start with and then switch it on to see what it turns up.falseJava
    ignoreIdentifiersSimilar to ignoreLiterals but for identifiers; i.e., variable names, methods names, and so forth.falseJava
    ignoreAnnotationsIgnore annotations. More and more modern frameworks use annotations on classes and methods, + which can be very redundant and trigger CPD matches. With J2EE (CDI, Transaction Handling, etc) + and Spring (everything) annotations become very redundant. Often classes or methods have the + same 5-6 lines of annotations. This causes false positives.falseJava
    ignoreUsingsIgnore using directives in C#.falseC#
    skipDuplicateFilesIgnore multiple copies of files of the same name and length in comparison.false
    skipLexicalErrorsSkip files which can't be tokenized due to invalid characters instead of aborting CPD.false
    skipBlocksEnables or disabled skipping of blocks like a pre-processor. See also option skipBlocksPattern.trueC++
    skipBlocksPatternConfigures the pattern, to find the blocks to skip. It is a string property and contains of two parts, + separated by |. The first part is the start pattern, the second part is the ending pattern.#if 0|#endifC++
    languageFlag to select the appropriate language (e.g. c, cpp, cs, java, jsp, php, ruby, fortran + ecmascript, and plsql).java
    outputfileThe destination file for the report. If not specified the console will be used instead.
    + +

    Also, you can get verbose output from this task by running ant with the -v flag; i.e.:

    + +
    ant -v -f mybuildfile.xml cpd
    +
    + +

    Also, you can get an HTML report from CPD by using the XSLT script in pmd/etc/xslt/cpdhtml.xslt. Just run +the CPD task as usual and right after it invoke the Ant XSLT script like this:

    + +
        <xslt in="cpd.xml" style="etc/xslt/cpdhtml.xslt" out="cpd.html" />
    +
    + +

    GUI

    + +

    CPD also comes with a simple GUI. You can start it via some scripts in the bin folder:

    + +

    For Windows:

    + +
    cpdgui.bat
    +
    + +

    For Linux:

    + +
    ./run.sh cpdgui
    +
    + +

    Here’s a screenshot of CPD after running on the JDK 8 java.lang package:

    + +
    CPD Screenshot after running on the JDK 8 java.lang package
    + +

    Suppression

    + +

    Arbitrary blocks of code can be ignored through comments on Java, C/C++, Dart, Go, Javascript, +Kotlin, Lua, Matlab, Objective-C, PL/SQL, Python, Swift and C# by including the keywords CPD-OFF and CPD-ON.

    + +
        public Object someParameterizedFactoryMethod(int x) throws Exception {
    +        // some unignored code
    +
    +        // tell cpd to start ignoring code - CPD-OFF
    +
    +        // mission critical code, manually loop unroll
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +        goDoSomethingAwesome(x + x / 2);
    +
    +        // resume CPD analysis - CPD-ON
    +
    +        // further code will *not* be ignored
    +    }
    +
    + +

    Additionally, Java allows to toggle suppression by adding the annotations +@SuppressWarnings("CPD-START") and @SuppressWarnings("CPD-END") +all code within will be ignored by CPD.

    + +

    This approach however, is limited to the locations were @SuppressWarnings is accepted. +It’s legacy and the new comment’s based approach should be favored.

    + +
        //enable suppression
    +    @SuppressWarnings("CPD-START")
    +    public Object someParameterizedFactoryMethod(int x) throws Exception {
    +        // any code here will be ignored for the duplication detection
    +    }
    +    //disable suppression
    +    @SuppressWarnings("CPD-END)
    +    public void nextMethod() {
    +    }
    +
    + +

    Other languages currently have no support to suppress CPD reports. In the future, +the comment based approach will be extended to those of them that can support it.

    + +

    Credits

    +

    CPD has been through three major incarnations:

    + +
      +
    • +

      First we wrote it using a variant of Michael Wise’s Greedy String Tiling algorithm (our variant is described +here).

      +
    • +
    • +

      Then it was completely rewritten by Brian Ewins using the +Burrows-Wheeler transform.

      +
    • +
    • +

      Finally, it was rewritten by Steve Hawkins to use the +Karp-Rabin string matching algorithm.

      +
    • +
    + + +
    + + Tags: + + + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_cpd_report_formats.html b/pmd_userdocs_cpd_report_formats.html new file mode 100644 index 0000000000..2eedec95fe --- /dev/null +++ b/pmd_userdocs_cpd_report_formats.html @@ -0,0 +1,1652 @@ + + + + + + + + +Report formats for CPD | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Report formats for CPD

    +
    + + + +
    + + +
    Overview of the built-in report formats for CPD
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Overview

    + +

    CPD collects occurrences of found duplications and provides them to the selected report format. +Each found code duplication appears in one or more other files, so that each code duplication can +have multiple locations. Not all report formats display all locations.

    + +

    The following examples always describe the same duplications:

    + +
      +
    1. a code block of 239 tokens spanning 33 lines in RuleReferenceTest. This is a duplication within the same file.
    2. +
    3. a code block of 110 tokens spanning 16 lines in JaxenXPathRuleQueryTest. This is a duplication that appears +3 times within the same file.
    4. +
    + +

    text

    + +

    This is the default format.

    + +

    All duplications are reported one after another. For each duplication, the complete code snippet is output. +Each duplication is separated by ======.

    + +

    Example:

    + +
    Found a 33 line (239 tokens) duplication in the following files: 
    +Starting at line 32 of /home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenceTest.java
    +Starting at line 68 of /home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenceTest.java
    +
    +    public void testOverride() {
    +        final StringProperty PROPERTY1_DESCRIPTOR = new StringProperty("property1", "Test property", null, 0f);
    +        MockRule rule = new MockRule();
    +        rule.definePropertyDescriptor(PROPERTY1_DESCRIPTOR);
    +        rule.setLanguage(LanguageRegistry.getLanguage(Dummy2LanguageModule.NAME));
    +        rule.setName("name1");
    +        rule.setProperty(PROPERTY1_DESCRIPTOR, "value1");
    +        rule.setMessage("message1");
    +        rule.setDescription("description1");
    +        rule.addExample("example1");
    +        rule.setExternalInfoUrl("externalInfoUrl1");
    +        rule.setPriority(RulePriority.HIGH);
    +
    +        final StringProperty PROPERTY2_DESCRIPTOR = new StringProperty("property2", "Test property", null, 0f);
    +        RuleReference ruleReference = new RuleReference();
    +        ruleReference.setRule(rule);
    +        ruleReference.definePropertyDescriptor(PROPERTY2_DESCRIPTOR);
    +        ruleReference.setLanguage(LanguageRegistry.getLanguage(DummyLanguageModule.NAME));
    +        ruleReference
    +                .setMinimumLanguageVersion(LanguageRegistry.getLanguage(DummyLanguageModule.NAME).getVersion("1.3"));
    +        ruleReference
    +                .setMaximumLanguageVersion(LanguageRegistry.getLanguage(DummyLanguageModule.NAME).getVersion("1.7"));
    +        ruleReference.setDeprecated(true);
    +        ruleReference.setName("name2");
    +        ruleReference.setProperty(PROPERTY1_DESCRIPTOR, "value2");
    +        ruleReference.setProperty(PROPERTY2_DESCRIPTOR, "value3");
    +        ruleReference.setMessage("message2");
    +        ruleReference.setDescription("description2");
    +        ruleReference.addExample("example2");
    +        ruleReference.setExternalInfoUrl("externalInfoUrl2");
    +        ruleReference.setPriority(RulePriority.MEDIUM_HIGH);
    +
    +        validateOverriddenValues(PROPERTY1_DESCRIPTOR, PROPERTY2_DESCRIPTOR, ruleReference);
    +=====================================================================
    +Found a 16 line (110 tokens) duplication in the following files: 
    +Starting at line 66 of /home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java
    +Starting at line 88 of /home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java
    +Starting at line 110 of /home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java
    +
    +        JaxenXPathRuleQuery query = createQuery(xpath);
    +        List<String> ruleChainVisits = query.getRuleChainVisits();
    +        Assert.assertEquals(2, ruleChainVisits.size());
    +        Assert.assertTrue(ruleChainVisits.contains("dummyNode"));
    +        // Note: Having AST_ROOT in the rule chain visits is probably a mistake. But it doesn't hurt, it shouldn't
    +        // match a real node name.
    +        Assert.assertTrue(ruleChainVisits.contains(JaxenXPathRuleQuery.AST_ROOT));
    +
    +        DummyNodeWithListAndEnum dummy = new DummyNodeWithListAndEnum(1);
    +        RuleContext data = new RuleContext();
    +        data.setLanguageVersion(LanguageRegistry.findLanguageByTerseName("dummy").getDefaultVersion());
    +
    +        query.evaluate(dummy, data);
    +        // note: the actual xpath queries are only available after evaluating
    +        Assert.assertEquals(2, query.nodeNameToXPaths.size());
    +        Assert.assertEquals("self::node()[(attribute::Test1 = \"false\")][(attribute::Test2 = \"true\")]", query.nodeNameToXPaths.get("dummyNode").get(0).toString());
    +
    + +

    xml

    + +

    This format uses XML to output the duplications in a more structured format.

    + +

    Example:

    + +
    <?xml version="1.0" encoding="UTF-8"?>
    +<pmd-cpd>
    +   <duplication lines="33" tokens="239">
    +      <file column="29" endcolumn="75" endline="64" line="32"
    +            path="/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenceTest.java"/>
    +      <file column="37" endcolumn="75" endline="100" line="68"
    +            path="/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenceTest.java"/>
    +      <codefragment><![CDATA[    public void testOverride() {
    +        final StringProperty PROPERTY1_DESCRIPTOR = new StringProperty("property1", "Test property", null, 0f);
    +        MockRule rule = new MockRule();
    +        rule.definePropertyDescriptor(PROPERTY1_DESCRIPTOR);
    +        rule.setLanguage(LanguageRegistry.getLanguage(Dummy2LanguageModule.NAME));
    +        rule.setName("name1");
    +        rule.setProperty(PROPERTY1_DESCRIPTOR, "value1");
    +        rule.setMessage("message1");
    +        rule.setDescription("description1");
    +        rule.addExample("example1");
    +        rule.setExternalInfoUrl("externalInfoUrl1");
    +        rule.setPriority(RulePriority.HIGH);
    +
    +        final StringProperty PROPERTY2_DESCRIPTOR = new StringProperty("property2", "Test property", null, 0f);
    +        RuleReference ruleReference = new RuleReference();
    +        ruleReference.setRule(rule);
    +        ruleReference.definePropertyDescriptor(PROPERTY2_DESCRIPTOR);
    +        ruleReference.setLanguage(LanguageRegistry.getLanguage(DummyLanguageModule.NAME));
    +        ruleReference
    +                .setMinimumLanguageVersion(LanguageRegistry.getLanguage(DummyLanguageModule.NAME).getVersion("1.3"));
    +        ruleReference
    +                .setMaximumLanguageVersion(LanguageRegistry.getLanguage(DummyLanguageModule.NAME).getVersion("1.7"));
    +        ruleReference.setDeprecated(true);
    +        ruleReference.setName("name2");
    +        ruleReference.setProperty(PROPERTY1_DESCRIPTOR, "value2");
    +        ruleReference.setProperty(PROPERTY2_DESCRIPTOR, "value3");
    +        ruleReference.setMessage("message2");
    +        ruleReference.setDescription("description2");
    +        ruleReference.addExample("example2");
    +        ruleReference.setExternalInfoUrl("externalInfoUrl2");
    +        ruleReference.setPriority(RulePriority.MEDIUM_HIGH);
    +
    +        validateOverriddenValues(PROPERTY1_DESCRIPTOR, PROPERTY2_DESCRIPTOR, ruleReference);]]></codefragment>
    +   </duplication>
    +   <duplication lines="16" tokens="110">
    +      <file column="9" endcolumn="28" endline="81" line="66"
    +            path="/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java"/>
    +      <file column="9" endcolumn="28" endline="103" line="88"
    +            path="/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java"/>
    +      <file column="9" endcolumn="28" endline="125" line="110"
    +            path="/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java"/>
    +      <codefragment><![CDATA[        JaxenXPathRuleQuery query = createQuery(xpath);
    +        List<String> ruleChainVisits = query.getRuleChainVisits();
    +        Assert.assertEquals(2, ruleChainVisits.size());
    +        Assert.assertTrue(ruleChainVisits.contains("dummyNode"));
    +        // Note: Having AST_ROOT in the rule chain visits is probably a mistake. But it doesn't hurt, it shouldn't
    +        // match a real node name.
    +        Assert.assertTrue(ruleChainVisits.contains(JaxenXPathRuleQuery.AST_ROOT));
    +
    +        DummyNodeWithListAndEnum dummy = new DummyNodeWithListAndEnum(1);
    +        RuleContext data = new RuleContext();
    +        data.setLanguageVersion(LanguageRegistry.findLanguageByTerseName("dummy").getDefaultVersion());
    +
    +        query.evaluate(dummy, data);
    +        // note: the actual xpath queries are only available after evaluating
    +        Assert.assertEquals(2, query.nodeNameToXPaths.size());
    +        Assert.assertEquals("self::node()[(attribute::Test1 = \"false\")][(attribute::Test2 = \"true\")]", query.nodeNameToXPaths.get("dummyNode").get(0).toString());]]></codefragment>
    +   </duplication>
    +</pmd-cpd>
    +
    + +

    csv

    + +

    This outputs the duplication as comma separated values. It only reports the duplication size (number +of lines and tokens) and the number of occurrences. After that, the begin lines and filenames are reported on +after another.

    + +

    Example:

    + +
    lines,tokens,occurrences
    +33,239,2,32,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenceTest.java,68,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenceTest.java
    +16,110,3,66,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java,88,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java,110,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java
    +
    + +

    csv_with_linecount_per_file

    + +

    This format is similar to “csv”, but it has one difference: The duplication size in number of lines is reported +for each occurrence separately. While the tokens are the same, due to formatting or comments, the code blocks might be +different. Whitespace and comments are usually ignored when finding duplicated code.

    + +

    In each line, the duplication size in tokens is reported, then the number of occurrences. And after that, for each +file, the begin line, the number of duplicated lines and the filename.

    + +

    Example:

    + +
    tokens,occurrences
    +239,2,32,33,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenceTest.java,68,33,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenc
    +eTest.java
    +110,3,66,16,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java,88,16,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java,110,16,/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java
    +
    + +

    vs

    + +

    This outputs the duplication in a format, that Visual Studio. CPD can be added as a external tool and the output +is shown in the console. You can then click on the filenames to jump to the source where the duplication is located.

    + +

    Each occurrence of a duplication is reported in a separate line, that’s why in this example, we have 5 lines.

    + +

    Example:

    + +
    /home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenceTest.java(32): Between lines 32 and 65
    +/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/RuleReferenceTest.java(68): Between lines 68 and 101
    +/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java(66): Between lines 66 and 82
    +/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java(88): Between lines 88 and 104
    +/home/pmd/source/pmd-core/src/test/java/net/sourceforge/pmd/lang/rule/xpath/JaxenXPathRuleQueryTest.java(110): Between lines 110 and 126
    +
    + + +
    + + Tags: + + + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_defining_properties.html b/pmd_userdocs_extending_defining_properties.html new file mode 100644 index 0000000000..34ed367715 --- /dev/null +++ b/pmd_userdocs_extending_defining_properties.html @@ -0,0 +1,1651 @@ + + + + + + + + +Defining rule properties | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Defining rule properties

    +
    + + + +
    + + +
    Learn how to define your own properties both for Java and XPath rules.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Rule properties are a way to make your rules configurable directly from the +ruleset XML. Their usage is described on the Configuring Rules page.

    + +

    If you’re a rule developer, you may want to think about what would be useful for +a user of your rule to parameterise. It could be a numeric report level, a boolean +flag changing the behaviour of your rule… Chances are there is some detail +that can be abstracted away from your implementation, and in that case, this +page can help you squeeze that sweet flexibility out of your rule.

    + +

    Overview of properties

    + +

    The basic thing you need to do as a developer is to define a property descriptor and declare that your rule uses it. A property descriptor defines a number of attributes for your property:

    +
      +
    • Its name, with which the user will refer to your property;
    • +
    • Its description, for documentation purposes;
    • +
    • Its default value
    • +
    + +

    Don’t worry, all of these attributes can be specified in a single Java statement (or xml element for XPath rules).

    + +

    For Java rules

    + +

    The procedure to define a property is quite straightforward:

    + + +

    You can then retrieve the value of the property at any time using getProperty(PropertyDescriptor).

    + +

    Creating a descriptor

    + +

    Properties can be built using type-specific builders, which can be obtained +from the factory methods of PropertyFactory. For example, to build a +string property, you’d call

    +
    PropertyFactory.stringProperty("myProperty")
    +               .desc("This is my property")
    +               .defaultValue("foo")
    +               .build();
    +
    + +

    This is fairly more readable than a constructor call, but keep in mind the description and the default value are not optional.

    + + + +

    For numeric properties, you can add constraints on the range of acceptable values, e.g.

    +
    PropertyFactory.intProperty("myIntProperty")
    +               .desc("This is my property")
    +               .defaultValue(3)
    +               .require(positive())
    +               .range(0, 100)
    +               .build();
    +
    + +

    The positive method is part of +the NumericConstraints class, which provides some +other constraints. The constraint mechanism will be completely unlocked with 7.0.0, +since we’ll be migrating our API to Java 8.

    + +

    Enumerated properties are a bit less straightforward to define, though they are +arguably more powerful. These properties don’t have a specific value type, instead, +you can choose any type of value, provided the values are from a closed set. To make +that actionable, you give string labels to each of the acceptable values, and the user +will provide one of those labels as a value in the XML. The property will give you back +the associated value, not the label. Here’s an example:

    +
    static Map<String, ModeStrategy> map = new HashMap<>();
    +
    +static {
    +  map.put("easyMode", new EasyStrategy());
    +  map.put("hardMode", new HardStrategy());
    +}
    +
    +static PropertyDescriptor<ModeStrategy> modeProperty
    + = PropertyFactory.enumProperty("modeProperty", map)
    +                  .desc("This is my property")
    +                  .defaultValue(new EasyStrategy())
    +                  .build();
    +
    + +

    Example

    + +

    You can see an example of properties used in a PMD rule here. +There are several things to notice here:

    +
      +
    • The property descriptors are declared static final, which should generally be +the case, as descriptors are immutable and can be shared between instances of the same rule;
    • +
    • The property is declared using definePropertyDescriptor` in the constructor, +which ensures the property gets recognised by PMD at the time the properties +are overridden (which happens before rule execution);
    • +
    • The value of the property is not retrieved in the constructor, but in one of +the visit methods (typically on the highest node in the tree, since the property +doesn’t change).
    • +
    + +

    For XPath rules

    + +

    XPath rules can also define their own properties. To do so, you must add a property element in the properties element of your rule, which declares the type attribute. This attribute conditions what type the underlying property has, and can have the following values:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    type attributeXSD type
    Integerxs:integer
    Longxs:integer
    Doublexs:decimal
    Booleanxs:boolean
    Stringxs:string
    Characterxs:string
    Regexxs:string
    + + + +

    Note that enumerated properties are not available in XPath rules (yet?).

    + +

    Properties defined in XPath also must declare the description attribute. +Numeric properties also expect the min and max attributes for now. Here are +a few examples to sum it up:

    + +
    <property name="stringProp" type="Boolean" value="true" description="A BooleanProperty."/>
    +<property name="intProp" type="Integer" value="3" min="1" max="20" description="An IntegerProperty."/>
    +
    + +

    You can then use the property in XPath with the syntax $propertyName, for example:

    + +
    <rule name="MyXpathRule" ...>
    +  <properties>
    +    <property name="maxStatements" type="Integer" value="10" min="1" max="40"
    +              description="Max number of statements per method"/>
    +    <property name="xpath">
    +    <![CDATA[
    +      //MethodDeclaration/Block[count(//BlockStatement) > $maxStatements]
    +    ]]></property>
    +  </properties>
    +</rule>
    +
    + +

    Multivalued properties

    + +

    Multivalued properties are also allowed and their type attribute has the form +List[Boolean] or List[Character], with every above type allowed. These +properties require XPath 2.0 to work properly, and make use of the +sequence datatype provided by that language. You thus need to set the +version property to 2.0 to use them. Properties can also declare the +delimiter attribute.

    + +
    <rule name="MyXpathRule" ...>
    +  <properties>
    +    <property name="version" value="2.0" />
    +    <property name="intProp" type="List[Integer]" value="1,2,5" description="An IntegerMultiProperty." />
    +    <property name="reportedIdentifiers" type="List[String]" value="foo$bar" delimiter="$"
    +              description="A StringMultiProperty." />
    +    <property name="xpath">
    +    <![CDATA[
    +      //VariableDeclaratorId[@Image = $reportedIdentifiers]
    +    ]]></property>
    +  </properties>
    +</rule>
    +
    + +

    Notice that in the example above, @Image = $reportedIdentifiers doesn’t test +@Image for equality with the whole sequence ('foo', 'bar'), it tests whether +the sequence contains @Image. That is, the above rule will report all variables +named foo or bar. All other XPath 2.0 functions operating on sequences +are supported.

    + + + + +
    + + Tags: + + + + extending + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_designer_reference.html b/pmd_userdocs_extending_designer_reference.html new file mode 100644 index 0000000000..897eb2f0fc --- /dev/null +++ b/pmd_userdocs_extending_designer_reference.html @@ -0,0 +1,1690 @@ + + + + + + + + +The rule designer | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    The rule designer

    +
    + + + +
    + + +
    Learn about the usage and features of the rule designer.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Installing, running, updating

    + +

    The designer is part of PMD’s binary distributions. To install a distribution, see the documentation page about installing PMD.

    + +

    The app needs JRE 1.8 or above to run. Be aware that on JRE 11+, the JavaFX distribution should be installed separately. Visit the JavaFX download page to download a distribution, extract it, and set the JAVAFX_HOME environment variable.

    + +

    If the bin directory of your PMD distribution is on your shell’s path, then you can launch the app with

    + +
    run.sh designer on Linux/ OSX
    +designer.bat on Windows
    +
    + + + +

    This is to allow easy updating, and let you choose the dependencies you’re interested in. +The available language modules are those on the classpath of the app’s JVM. That’s why it’s recommended to use the standard PMD startup scripts, which setup the classpath with the available PMD libraries.

    + +

    Updating

    + +

    The latest version of the designer currently works with PMD 6.12.0 and above. You can simply replace pmd-ui-6.X.Y.jar with the latest build in the installation folder of your PMD distribution, and run it normally. Note that updating may cause some persisted state to get lost, for example the code snippet.

    + +

    Usage reference

    + +

    The rule designer is both a tool to inspect the tree on which PMD rules run on, and to write XPath rules in an integrated manner. This page describes the features that enable this.

    + +

    AST inspection

    + +

    Designer top UI

    + +

    You can enter source code in the middle zone.

    +
      +
    • Make sure to select the correct language and version for your source code: +
        +
      • Language is set app-wide with the blue button in the menu-bar
      • +
      • If the language has several language versions, you can select a specific one with the choicebox just above the code area
      • +
      +
    • +
    • If the source is valid using this setting, the tree to the right will update to display the AST of the code
    • +
    • When selecting a node, the left panel updates with information about a node
    • +
    + +

    Selecting nodes

    + +

    There are several ways to focus a node for inspection:

    +
      +
    • From the tree view: just click on an item +
        +
      • Since 6.16.0, the tree view is also searchable: press CTRL+F when it’s focused, or click on the Search button and enter a search query. You can cycle through results with CTRL+TAB or CTRL+F3, and cycle back with CTRL+SHIFT+TAB or CTRL+SHIFT+F3
      • +
      +
    • +
    • From the crumb bar: the crumb bar below the code area shows the ancestors of the currently selected node, and is empty if you have no selection:
    • +
    + +
    Ancestor crumb bar demo +

    Ancestor crumb bar demo

    + +
    + +
      +
    • From the source code: maintain CTRL for a second until the code area becomes mostly blue. Then, each node you hover over on the code area will be selected automatically. Example:
    • +
    + +
    CTRL-hover selection demo +

    CTRL-hover selection demo

    + +
    + +

    Node inspection

    + +

    The left panel displays the following information:

    + +
      +
    • XPath attributes: this basically are all the attributes available in XPath queries. Those attributes are wrappers around a Java getter, so you can obtain documentation on the relevant Javadoc (that’s not yet integrated into the designer)
    • +
    • Metrics: for nodes that support it, the values of metrics are displayed in this panel
    • +
    • Scopes: This is java specific and displays some representation of the symbol table. You mostly don’t need it. If you select eg a variable id, its usages are already highlighted automatically without opening the panel:
    • +
    + +

    Usages highlight example

    + +

    XPath rule design

    + +

    The bottom part of the UI is dedicated to designing XPath rules:

    + +

    Bottom UI

    + +

    The center is an XPath expression. As you type it, the matched nodes are updated on the right, and highlighted on the code area. Autocompletion is available on some languages.

    + +

    Note: you can keep several rules in the editor (there’s a tab for each of them).

    + +

    Rule properties

    + +

    Above the XPath expression area, the “Properties” button allows you to define new properties for your prototype rule. You can also edit the existing properties.

    + +

    When you click on it, a small popup appears:

    + +

    Property definition popup

    + +

    The popup contains in the center a list of currently defined properties, displaying their name and expected type.

    + +
      +
    • Adding: the “Add property” button adds a row to the table
    • +
    • Deleting: each item has a “Trash” button to delete the property
    • +
    • Editing: each property can be further edited by clicking on the “Ellipsis” button on the right
    • +
    + +

    Editing properties

    + +

    The edition menu of a property looks like the following:

    + +

    Property edition popup

    + +
      +
    • You can edit the name, description, expected type, and default value of the property
    • +
    • All this information is exported with the rule definition (see Exporting to an XML rule)
    • +
    • The default value is used unless you’re editing a test case, and you set a custom value for the test case. TODO link
    • +
    + +

    Exporting to an XML rule

    + +

    The little export icon next to the gear icon opens a menu to export your rule. This menu lets you fill-in the metadata necessary for an XPath rule to be included in a ruleset.

    + +
    Rule export demo +

    Rule export demo

    + +
    + +

    Testing a rule

    + +

    PMD has its own XML format to describe rule tests and execute them using our test framework. The designer includes a test editor, which allows you to edit such files or create a new one directly as you edit the rule. This is what the panel left of the XPath expression area is for.

    + +

    See also the test framework documentation.

    + +

    Testing model

    + +

    A rule test describes

    +
      +
    • the configuration of the rule
    • +
    • the source on which to run
    • +
    • the expected violations
    • +
    • a description (to name the test)
    • +
    + +

    When executing a test, the rule is run on the source with the given configuration, then the violations it finds are compared to the expected ones.

    + +

    Adding tests

    + +

    Tests can be added in one of four ways:

    +
      +
    • From an XML file: if you already have a test XML file for your tests, you can load all the tests it defines easily.
    • +
    + +
    Test import demo +

    Test import example

    + +
    + +
      +
    • +

      From the current source: A new test case with a default configuration is created, with the source that is currently in the editor

      +
    • +
    • +

      With an empty source: A new test case with a default configuration is created, with an empty source file. You must edit the source yourself then.

      +
    • +
    • +

      From an existing test case: Each test case list item has a “Copy” button which duplicates the test and loads the new one.

      +
    • +
    + +

    Test status

    + +

    In the designer, the test panel is a list of test cases. Their status (passing, failing, error, unknown) is color coded.

    + +
    Test status color coding examples +

    All tests passing (green):

    + +

    All green

    + +

    A failing test (orange):

    + +

    Failing

    + +
    + +

    Loading a test case

    + +

    Each test has a piece of source, which you can edit independently of the others, when the test is loaded in the editor. Additional rule configuration options can be chosen when the test is loaded.

    + +

    Loading is done with the Load button:

    + +
    Test loading demo +

    Test loading demo

    + +
    + +

    Only one test case may be loaded at a time. If the loaded test is unloaded, the editor reverts back to the state it had before the first test case was loaded.

    + +

    Editing a loaded test case

    + +

    When a test is loaded, the source you edit in the code area is the source of the test. Changes are independent from other tests, and from the piece of source that was previously in the editor.

    + +

    When a test is loaded, an additional toolbar shows up at the top of the code area:

    + +

    Failing

    + +

    Expected violations

    + +

    The “Expected violations” button is used to add or edit the expected violations.

    + +

    Initially the list of violations is empty. You can add violations by dragging and dropping nodes onto the button or its popup, from any control that displays nodes. For example:

    + +
    Adding a violation demo +

    Add violation gif

    + +
    + +

    Test case rule configuration

    + +

    Rule properties can be configured for each test case independently using the “Property mapping” button. For example:

    + +
    Test rule property demo +

    Configure properties demo

    + +
    + +

    This configuration will be used when executing the test to check its status.

    + +

    Exporting tests

    + +

    When you’re done editing tests, it’s a good idea to save the test file to an XML file. Exporting is done using the “Export” button above the list of test cases:

    + +
    Test export demo +

    Test export demo

    + +
    + +

    Note that the exported file does not contain any information about the rule. The rule must be in a ruleset file somewhere else.

    + +

    If you want to use PMD’s test framework to use the test file in your build, please refer to the conventions explained in the test framework documentation.

    + + + +
    + + Tags: + + + + extending + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_metrics_howto.html b/pmd_userdocs_extending_metrics_howto.html new file mode 100644 index 0000000000..deefd2f3a7 --- /dev/null +++ b/pmd_userdocs_extending_metrics_howto.html @@ -0,0 +1,1776 @@ + + + + + + + + +Using and defining code metrics for custom rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Using and defining code metrics for custom rules

    +
    + + + +
    + + +
    Since version 6.0.0, PMD is enhanced with the ability to compute code metrics on Java and Apex source (the so-called Metrics Framework). This framework provides developers with a straightforward interface to use code metrics in their rules, and to extend the framework with their own custom metrics.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    Using the metrics framework

    + + + +

    In PMD’s Metrics framework, a metric is an operation that can be carried out on nodes of a certain type and produces +a numeric result. In the Java framework, metrics can be computed on operation declaration nodes (constructor and +method declaration), and type declaration nodes (class, interface, enum, and annotation declarations). A metric +object in the framework can only handle either types or operations, but not both.

    + +

    PMD ships with a library of already implemented metrics. These metrics are referenced by MetricKey objects, +which are listed in two public enums: JavaClassMetricKey and JavaOperationMetricKey. +Metric keys wrap a metric, and know which type of node their metric can be computed on. That way, you cannot compute an operation metric on a class +declaration node. Metrics that can be computed on both operation and type declarations (e.g. NCSS) have one metric key in +each enum.

    + +

    For XPath rules

    + +

    XPath rules can compute metrics using the metric function. This function takes a single string argument, +which is the name of the metric key as defined in JavaClassMetricKey or JavaOperationMetricKey. The metric + will be computed on the context node.

    + +

    The function will throw an exception in the following cases:

    + + + + +

    Examples

    + +
      +
    • //ClassOrInterfaceDeclaration[metric('NCSS') > 200]
    • +
    • //MethodDeclaration[metric('CYCLO') > 10 and metric('NCSS') > 20]
    • +
    • //ClassOrInterfaceDeclaration[metric('CYCLO') > 50]: IllegalArgumentException! +CYCLO’s only defined for methods and constructors.
    • +
    + +

    For Java Rules

    + +

    The static façade class JavaMetrics is the single entry point to compute metrics in the Java framework.

    + +

    This class provides the method get and its overloads. The following sections describes the interface of this class.

    + +

    Basic usage

    + +

    The simplest overloads of JavaMetrics.get take two parameters: a MetricKey and a node of the corresponding type. +Say you want to write a rule to report methods that have a high cyclomatic complexity. In your rule’s visitor, you +can get the value of Cyclo for a method node like so:

    +
    public Object visit(ASTMethodDeclaration method, Object data) {
    +  int cyclo = (int) JavaMetrics.get(JavaOperationMetricKey.CYCLO, method);
    +  if (cyclo > 10) {
    +    // add violation
    +  }
    +  return data;
    +}
    +
    + +

    The same goes for class metrics: you select one among JavaClassMetricKey’s constants and pass it along with the node +to JavaMetrics.get.

    + + + +

    Capability checking

    + +

    Metrics are not necessarily computable on any node of the type they handle. For example, Cyclo cannot be computed on +abstract methods. Metric keys provides a supports(Node) boolean method +to find out if the metric can be computed on +the specified node. If the metric cannot be computed on the given node, JavaMetrics.get will return Double.NaN . +If you’re concerned about that, you can condition your call on whether the node is supported or not:

    +
    public Object visit(ASTMethodDeclaration method, Object data) {
    +  if (JavaOperationMetricKey.CYCLO.supports(node)) {
    +    int cyclo = (int) JavaMetrics.get(JavaOperationMetricKey.CYCLO, method);
    +    if (cyclo > 10) {
    +      // add violation
    +    }
    +    return data;
    +  }
    +}
    +
    + +

    Metric options

    + +

    Some metrics define options that can be used to slightly modify the computation. You’ll typically see these options +gathered inside an enum in the implementation class of the metric, for example CycloMetric.CycloOption. They’re +also documented on the index of metrics.

    + +

    To use options with a metric, you must first bundle them into a MetricOptions object. MetricOptions provides the +utility method ofOptions to get a MetricOptions bundle from a collection or with varargs parameters. You can then +pass this bundle as a parameter to JavaMetrics.get:

    +
    public Object visit(ASTMethodDeclaration method, Object data) {
    +  int cyclo = (int) JavaMetrics.get(JavaOperationMetricKey.CYCLO, method,
    +                                    MetricOptions.ofOptions(CycloOptions.IGNORE_BOOLEAN_PATHS));
    +  if (cyclo > 10) {
    +      // add violation
    +  }
    +    return data;
    +}
    +
    + +

    The version of MetricOptions.ofOptions using a collection is useful when you’re building a MetricOptions from eg +the value of an EnumeratedMultiProperty, which gives users control of the options they use. See +CyclomaticComplexityRule +for an example usage.

    + +

    Result options

    + +

    The Metrics API also gives you the possibility to aggregate the result of an operation metric on all operations of a +class very simply. You can for example get the highest value of the metric over a class that way:

    +
    public Object visit(ASTClassOrInterfaceDeclaration clazz, Object data) {
    +  int highest = (int) JavaMetrics.get(JavaOperationMetricKey.CYCLO, clazz,
    +                                      ResultOption.HIGHEST);
    +  if (highest > 10) {
    +      // add violation
    +  }
    +    return data;
    +}
    +
    + +

    Notice that we use an operation metric and a class node. The ResultOption parameter controls what result will be +computed: you can choose among HIGHEST, SUM and AVERAGE. You can use metric options together with a result +option too.

    + +

    Complete use case

    + +

    The following is a sample code for a rule reporting methods with a cyclomatic +complexity over 10 and classes with a total cyclo over 50. A metric option can be +user-configured with a rule property. More complete examples can be found in +CyclomaticComplexityRule, +NcssCountRule, +or GodClassRule.

    + +
    public class CycloRule extends AbstractJavaMetricsRule {
    +
    +  public static final BooleanProperty COUNT_BOOLEAN_PATHS
    +      = BooleanProperty.named("countBooleanPaths")
    +                       .desc("Count boolean paths")
    +                       .defaultValue(true).build();
    +
    +  private static final MetricOptions options;
    +
    +  public CycloRule() {
    +    definePropertyDescriptor(COUNT_BOOLEAN_PATHS);
    +  }
    +
    +  @Override
    +  public Object visit(ASTCompilationUnit node, Object data) {
    +    options = getProperty(COUNT_BOOLEAN_PATHS)
    +              ? MetricOptions.ofOptions(CycloOptions.IGNORE_BOOLEAN_PATHS)
    +              : MetricOptions.emptyOptions();
    +  }
    +
    +  @Override
    +  public Object visit(ASTAnyTypeDeclaration clazz, Object data) {
    +    int total = (int) JavaMetrics.get(JavaOperationMetricKey.CYCLO, clazz,
    +                                      options, ResultOption.SUM);
    +
    +    if (total > 50) {
    +     // add violation
    +    }
    +
    +    return data;
    +  }
    +
    +  @Override
    +  public Object visit(ASTMethodDeclaration method, Object data) {
    +    int cyclo = (int) JavaMetrics.get(JavaOperationMetricKey.CYCLO, method,
    +                                      options);
    +    if (cyclo > 10) { // this is safe if the node is not supported, as (Double.NaN > 10) == false
    +      // add violation
    +    }
    +    return data;
    +  }
    +}
    +
    + +

    Available metrics

    + +

    There are already many metrics ready to use. We maintain the following documentation +pages to describe them all, including their usage and options:

    + + +

    Writing custom metrics

    + +

    You can use the framework to customize the existing metrics at will, or define +new ones quite easily. Here’s some info to get you started. Again, the examples are for +the Java framework but it’s symmetrical in the Apex framework.

    + +

    The really short guide

    + +
      +
    1. Determine whether your metric is an operation metric or a class metric and +extend the correct base class (AbstractJavaClassMetric or +AbstractJavaOperationMetric)
    2. +
    3. You’re immediately prompted by your IDE to implement the computeFor method. +This method takes a node of the type you want to handle, a bundle of options, +and returns the result of the metric.
    4. +
    5. Optionally specify a predicate to check if a node can be handled by overriding +the supports method.
    6. +
    7. Optionally define options (implementing MetricOption) +and handle them as you see fit in your computeFor method
    8. +
    9. Create a metric key using MetricKeyUtil’s of method, specifying a name +for your metric and an instance of your metric. You’re done and can use your +metric key as if it were a standard one.
    10. +
    + +

    Best practices

    + +
      +
    • Metrics should be stateless. In any case, instances of the same metric class +are considered equals. The same instance of your metric will be used to +compute the metric on the AST of different nodes so it should really be +“functionnally pure”. That rule also makes you keep it simple and understandable +which is nice.
    • +
    • Implementation patterns: You can implement your computeFor method as you +like it. But most metrics in our library are implemented following a few +patterns you may want to look at: +
        +
      • +

        Visitor metrics: Those metrics use one or more AST visitor to compute their +value. That’s especially good to implement metrics that count some kind of node, +e.g. NPath complexity +or NCSS. +Additionally, it makes your metric more easily generalisable to other node types.

        +
      • +
      • +

        Signature matching metrics: That’s even more straightforward when you want +to count the number of methods or fields that match a specific signature, e.g. +public static final fields. Basically a signature is an object that describes +a field or method, with info about its modifers and other node-specific info. + AbstractJavaClassMetric has a few methods that allow you to count signatures + directly, see e.g. the metrics NOPA + and WOC.

        +
      • +
      +
    • +
    + +

    Capability checking

    + +

    You may have noticed that when you extend e.g. AbstractJavaClassMetric, the +computeFor method you’re prompted to implement takes a node of type +ASTAnyTypeDeclaration as a parameter. That’s not a concrete node type, but +an interface, implemented by several concrete node types. Basically that’s done +so that class metrics are given the ability to be computed on any type +declaration, and operation metrics on constructors and methods. Here are the +concrete node types you can target with class and operation metrics, by language:

    + + + + + + + + + + + + + + + + + + + + + +
    LanguageJavaApex
    Operation declarationASTMethodOrConstructorDeclaration
    >: ASTMethodDeclaration, ASTConstructorDeclaration
    ASTMethod*
    Type declarationASTAnyTypeDeclaration >: ASTEnumDeclaration,
    ASTAnnotationDeclaration, ASTClassOrInterfaceDeclaration
    ASTUserClassOrInterface >: ASTUserClass, ASTUserInterface
    + +

    *Apex method metrics are also applied to triggers by default (see #771). Finer capability checking is not available out of the box for now.

    + +

    What if you don’t want such a generalisation? The supports method lets you +define a predicate to check that the node is supported by your metric. For example, +if your metric can only be computed on classes, you may override the default behaviour +like so:

    +
    @Override
    +public boolean supports(ASTAnyTypeDeclaration node) {
    +  return node.getTypeKind() == TypeKind.CLASS;
    +}
    +
    + + + +

    The supports method already has a default implementation in the abstract base +classes. Here’s the default behaviour by language and type of metric:

    + + + + + + + + + + + + + + + + + + + + + +
    LanguageJavaApex
    Operation metricssupports constructors and non abstract methodssupports any non abstract method (including triggers), except <init>, <clinit>, and clone
    Type declarationsupports classes and enumssupports classes
    + + + +
    + + Tags: + + + + extending + + + + userdocs + + + + metrics + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_rule_guidelines.html b/pmd_userdocs_extending_rule_guidelines.html new file mode 100644 index 0000000000..ae81d280d2 --- /dev/null +++ b/pmd_userdocs_extending_rule_guidelines.html @@ -0,0 +1,1480 @@ + + + + + + + + +Rule guidelines | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Rule guidelines

    +
    + + + +
    + + +
    Rule Guidelines, or the last touches to a rule
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Here is a bunch of thing to do you may consider once your rule is “up and running”.

    + +

    How to define rules priority

    + +

    Rule priority may, of course, changes a lot depending on the context of the project. However, you can use the following guidelines to assert the legitimate priority of your rule:

    + +
      +
    1. Change absolutely required. Behavior is critically broken/buggy.
    2. +
    3. Change highly recommended. Behavior is quite likely to be broken/buggy.
    4. +
    5. Change recommended. Behavior is confusing, perhaps buggy, and/or against standards/best practices.
    6. +
    7. Change optional. Behavior is not likely to be buggy, but more just flies in the face of standards/style/good taste.
    8. +
    9. Change highly optional. Nice to have, such as a consistent naming policy for package/class/fields…
    10. +
    + +

    For instance, let’s take the ExplicitCallToGC rule (“Do not explicitly trigger a garbage collection.”). Calling GC is a bad idea, but it doesn’t break the application. So we skip priority one. However, as explicit call to gc may really hinder application performances, we set for the priority 2.

    + +

    Correctness

    + +

    You should try to run the rule on a large code base, like the jdk source code for instance. This will help ensure that the rule does not raise exceptions when dealing with unusual constructs.

    + +

    If your rule is stateful, make sure that it is reinitialized correctly. The “-stress” command line option can be used as the files will then not be ordered but processed randomly. Running pmd with the “-stress” option several times and sorting the text output should produce identical results if the state information is correctly reset.

    + +

    Performance issues

    + +

    When writing a new rule, using command line option “-benchmark” on a few rules can give an indication on how the rule compares to others. To get the full picture, use the rulesets/internal/all-java.xml ruleset with “-benchmark”.

    + +

    Rules which use the RuleChain to visit the AST are faster than rules which perform manual visitation of the AST. The difference is small for an individual Java rule, but when running 100s of rules, it is measurable. For XPath rules, the difference is extremely noticeable due to Jaxen overhead for AST navigation. Make sure your XPath rules using the RuleChain.

    + +

    (TODO How does one know except by running in a debugger or horrendous performance?).

    + + +
    + + Tags: + + + + extending + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_testing.html b/pmd_userdocs_extending_testing.html new file mode 100644 index 0000000000..64bffd5777 --- /dev/null +++ b/pmd_userdocs_extending_testing.html @@ -0,0 +1,1756 @@ + + + + + + + + +Testing your rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Testing your rules

    +
    + + + +
    + + +
    Learn how to use PMD's simple test framework for unit testing rules.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Introduction

    + +

    Good rules have tests. At least a positive test case - a code example, that triggers the rule and reports +a violation - and a negative test case - a code example, that doesn’t trigger the rule - should be created. +Of course, the more tests, the better the rule is verified. If the rule is more complex or defines properties, +with which the behavior can be modified, then these different cases can also be tested.

    + +

    And if there is a bug fix for a rule, be it a false positive or a false negative case, it should be accompanied +with an additional test case, so that the bug is not accidentally reintroduced later on.

    + +

    How it works

    + +

    PMD’s built-in rules are organized in rulesets, where all rules belonging to the same category are placed +in a single ruleset, such as “category/java/bestpractices.xml”. +Each category-ruleset has a single abstract base test class, from which the individual test classes inherit. +We have one test class per rule, which executes all test cases for a single rule. The actual test cases are +stored in separate XML files, for each rule a separate file is used.

    + +

    All the test classes inherit from net.sourceforge.pmd.testframework.PmdRuleTst, +which provides the seamless integration with JUnit. This base class determines the language, the category name +and the rule name from the concrete test class. It then searches the test code on its own. +E.g. the individual rule test class +net.sourceforge.pmd.lang.java.rule.bestpractices.AbstractClassWithoutAbstractMethodTest tests the +rule with the name “AbstractClassWithoutAbstractMethod”, which is in the category “bestpractices” for the +language “java”.

    + +

    The test code (see below Test XML Reference) describes the test case completely with +the expected behavior like number of expected rule violations, where the violations are expected, and so on.

    + +

    When you are running the test class in your IDE (e.g. Eclipse or IntelliJ IDEA) you can also select a single +test case and just execute this one.

    + +

    Where to place the test code

    + +

    The PmdRuleTst class searches the XML file, that describes the test cases for a certain rule +using the following convention: +The XML file is a test resource, so it is searched in the tree under src/test/resources.

    + +

    The sub package xml of the test class’s package should contain a file with the same name as the rule’s name +which is under test.

    + +

    For example, to test the rule “AbstractClassWithoutAbstractMethod”, the fully qualified test class is:

    + +
    net.sourceforge.pmd.lang.java.rule.bestpractices.AbstractClassWithoutAbstractMethodTest
    +
    + +

    The test code for the rule can be found in the file:

    + +
    src/test/resources/net/sourceforge/pmd/lang/java/rule/bestpractices/xml/AbstractClassWithoutAbstractMethod.xml
    +
    + +

    In general, the class name and file name pattern for the test class and data is this:

    + +
    net.sourceforge.pmd.lang.<Language Terse Name>.rule.<Category Name>.<Rule Name>Test
    +src/test/resources/net/sourceforge/pmd/lang/<Language Terse Name>/rule/<Category Name>/xml/<Rule Name>.xml
    +
    + + + + + +

    Simple example

    + +

    Test Class: AbstractClassWithoutAbstractMethodTest

    + +

    This class inherits from PmdRuleTst and is located in the package “bestpractices”, since the rule +belongs to the category “Best Practices”:

    + +
    package net.sourceforge.pmd.lang.java.rule.bestpractices;
    +
    +import net.sourceforge.pmd.testframework.PmdRuleTst;
    +
    +public class AbstractClassWithoutAbstractMethodTest extends PmdRuleTst {
    +    // no additional unit tests
    +}
    +
    + + + +

    Test Data: AvoidBranchingStatementAsLastInLoop.xml

    + +

    This is a stripped down example which just contains two test cases.

    + +
    <?xml version="1.0" encoding="UTF-8"?>
    +<test-data
    +    xmlns="http://pmd.sourceforge.net/rule-tests"
    +    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    +    xsi:schemaLocation="http://pmd.sourceforge.net/rule-tests https://pmd.sourceforge.io/rule-tests_1_0_0.xsd">
    +
    +    <test-code>
    +        <description>concrete class</description>
    +        <expected-problems>0</expected-problems>
    +        <code><![CDATA[
    +public class Foo {}
    +    ]]></code>
    +    </test-code>
    +
    +    <test-code>
    +        <description>failure case</description>
    +        <expected-problems>1</expected-problems>
    +        <expected-linenumbers>1</expected-linenumbers>
    +        <code><![CDATA[
    +public abstract class Foo {}
    +    ]]></code>
    +    </test-code>
    +</test-data>
    +
    + +

    Each test case is in an own <test-code> element. The first defines 0 expected problems, means this code doesn’t +trigger the rule. The second test case expects 1 problem. Since the rule violations also report the exact AST node, +you can verify the line number, too.

    + +

    Test XML Reference

    + +

    The root element is <test-data>. It can contain one or more <test-code> and <code-fragment> elements. +Each <test-code> element defines a single test case. <code-fragment> elements are used to share code snippets +between different test cases.

    + + + +

    <test-code> attributes

    + +

    The <test-code> elements understands three optional attributes:

    + +
      +
    • +

      reinitializeRule: By default, it’s true, so each test case starts with a fresh instantiated rule. Set it +to false to reproduce cases, where the previous run has influences.

      +
    • +
    • +

      regressionTest: By default, it’s true. Set it to false, to ignore and skip a test case.

      +
    • +
    • +

      useAuxClasspath: By default, it’s true. Set it to false to reproduce issues which only +appear without type resolution.

      +
    • +
    + +

    <test-code> children

    + +
      +
    • +

      <description>: Short description of the test case. This will be the JUnit test name in the report. +If applicable, this description should contain a reference to the bug number, this test case reproduces.

      +
    • +
    • +

      <rule-property>: Optional rule properties, if the rule is configurable. Just add multiple elements, to +set multiple properties for one test case. For an example, see below.

      +
    • +
    • +

      <expected-problems>: The the raw number of expected rule violations, that this rule is expected to report. +For false-positive test cases, this is always “0”. For false-negative test cases, it can be any positive number.

      +
    • +
    • +

      <expected-linenumbers>: Optional element. It’s a comma separated list of line numbers. +If there are rule violations reported, then this allows you to +assert the line numbers. Useful if multiple violations should be detected and to be sure that +false positives and negatives don’t erase each other.

      +
    • +
    • +

      <expected-messages>: Optional element, with <message> elements as children. +Can be used to validate the correct error message, e.g. if the error message references a variable name.

      +
    • +
    • +

      <code>: Either the <code> element or the <code-ref> element is required. It provides the actual code +snippet on which the rule is executed. The code itself is usually wrapped in a “CDATA” section, so that no +further XML escapes (entity references such as &lt;) are necessary.

      +
    • +
    • +

      <code-ref id=...>: Alternative to <code>. References a <code-fragment> defined earlier in the file. +This allows you to share the same code snippet with several test cases. The attribute id must match the +id of the references code fragment.

      +
    • +
    • +

      <source-type>: Optional element that specifies a specific language version. This can be used +to select a specific parser version for parsing the code snippet. If not given, the default version of +the rule’s language is used. This element can almost always be omitted.

      +
    • +
    + +

    <code-fragment>

    + +

    The code fragment has just one required attribute: id. This is used to reference it via a <code-ref> element +inside a <test-code>. Similar like the <code> element, the content of <code-fragment> is usually wrapped +in a “CDATA” section, so that no further XML escapes (entity references such as &lt;) are necessary.

    + +

    Complete XML example

    + +
    <?xml version="1.0" encoding="UTF-8"?>
    +<test-data
    +    xmlns="http://pmd.sourceforge.net/rule-tests"
    +    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    +    xsi:schemaLocation="http://pmd.sourceforge.net/rule-tests https://pmd.sourceforge.io/rule-tests_1_0_0.xsd">
    +
    +    <test-code reinitializeRule="true" regressionTest="true" useAuxClasspath="true">
    +        <description>Just a description, will be used as the test name for JUnit in the reports</description>
    +        <rule-property name="somePropName">propValue</rule-property>    <!-- optional -->
    +        <expected-problems>2</expected-problems>
    +        <expected-linenumbers>5,14</expected-linenumbers>               <!-- optional -->
    +        <expected-messages>                                             <!-- optional -->
    +            <message>Violation message 1</message>
    +            <message>Violation message 2</message>
    +        </expected-messages>
    +        <code><![CDATA[
    +public class ConsistentReturn {
    +    public Boolean foo() {
    +    }
    +}
    +        ]]></code>
    +        <source-type>java 1.5</source-type>                             <!-- optional -->
    +    </test-code>
    +
    +    <code-fragment id="codeSnippet1"><![CDATA[
    +public class ConsistentReturn {
    +    public Boolean foo() {
    +    }
    +}
    +    ]]></code-fragment>
    +
    +    <test-code>
    +        <description>test case using a code fragment</description>
    +        <expected-problems>0</expected-problems>
    +        <code-ref id="codeSnippet1"/>
    +    </test-code>
    +</test-data>
    +
    + + + +

    Using the test framework externally

    + +

    It is also possible to use the test framework for custom rules developed outside the PMD source base. +Therefore you just need to reference the dependency net.sourceforge.pmd:pmd-test.

    + +

    For maven, you can use this snippet:

    + +
    <dependency>
    +    <groupId>net.sourceforge.pmd</groupId>
    +    <artifactId>pmd-test</artifactId>
    +    <version>6.30.0-SNAPSHOT</version>
    +    <scope>test</scope>
    +</dependency>
    +
    + +

    Then proceed as described earlier: create your test class, create your test cases and run the unit test.

    + +

    There is one difference however: Since your package structure is probably different, you’ll need to register +the rule test manually, as SimpleAggregatorTst will fail to determine it correctly from the package and class names:

    + +
    package com.example.pmd.rules;
    +
    +import net.sourceforge.pmd.testframework.SimpleAggregatorTst;
    +
    +public class CustomRuleTest extends SimpleAggregatorTst {
    +    @Override
    +    public void setUp() {
    +        addRule("com/example/pmd/ruleset.xml", "CustomRule");
    +    }
    +}
    +
    + +

    This will then search for a rule named “CustomRule” in the ruleset, that is located in “src/main/resources” under +the path “com/example/pmd/ruleset.xml”.

    + +

    The test data should be placed in an xml file located in “src/test/resources” under the path +“com/example/pmd/rules/xml/CustomRule.xml”.

    + +

    How the test framework is implemented

    + +

    The framework uses a custom JUnit test runner under the hood, among a couple of utility classes:

    + +
      +
    • +

      PmdRuleTst: This is the base class for tests in PMD’s code base. It is a subclass of RuleTst and just +contains the logic to determine the test resources based on the test class name.

      +
    • +
    • +

      SimpleAggregatorTst: This is a more generic base class for the test classes and defines +the custom JUnit test runner. It doesn’t register any test cases on its own. +It itself is a subclass of RuleTst.

      +
    • +
    • +

      RuleTst: contains the logic to parse the XML files and provide a list of TestDescriptors. Each test descriptor +describes a single test case. It also contains the logic to execute such a test descriptor and assert the results.

      +
    • +
    • +

      PMDTestRunner: A custom JUnit test runner, that combines two separate test runners: The custom RuleTestRunner +and the standard JUnit4 test runner. This combination allows you to add additional standard unit test methods +annotated with @Test to your test class.

      + +

      Note: Since the test class is executed through two test runners, it is actually instantiated twice. Be aware +of this, if you do any initialization in the constructor. Also, the static hooks @BeforeClass and @AfterClass +will be executed twice.

      +
    • +
    • +

      RuleTestRunner: This test runner executes the test descriptors with the help of RuleTst.

      +
    • +
    + + +
    + + Tags: + + + + extending + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_writing_java_rules.html b/pmd_userdocs_extending_writing_java_rules.html new file mode 100644 index 0000000000..483ccc4b23 --- /dev/null +++ b/pmd_userdocs_extending_writing_java_rules.html @@ -0,0 +1,1608 @@ + + + + + + + + +Writing a custom rule | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Writing a custom rule

    +
    + + + +
    + + +
    Learn how to write a custom rule for PMD
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + + + + + +

    This page covers the specifics of writing a rule in Java. The basic development +process is very similar to the process for XPath rules, which is described in +Your First Rule.

    + +

    Basically, you open the designer, look at the structure of the AST, and refine +your rule as you add test cases.

    + +

    In this page we’ll talk about rules for the Java language, but the process is +very similar for other languages.

    + +

    Basics

    + +

    To write a rule in Java you’ll have to:

    +
      +
    1. write a Java class that implements the interface Rule. Each +language implementation provides a base rule class to ease your pain, +e.g. AbstractJavaRule.
    2. +
    3. compile this class, linking it to PMD APIs (eg using PMD as a maven dependency)
    4. +
    5. bundle this into a JAR and add it to the execution classpath of PMD
    6. +
    7. declare the rule in your ruleset XML
    8. +
    + +

    Rule execution

    + +

    Most base rule classes use a Visitor pattern +to explore the AST.

    + +

    Tree traversal

    + +

    When a rule is applied to a file, it’s handed the root of the AST and told +to traverse all the tree to look for violations. Each rule defines a specific +visit method for each type of node for of the language, which +by default just visits the children.

    + +

    So the following rule would traverse the whole tree and do nothing:

    + +
    public class MyRule extends AbstractJavaRule {
    +    // all methods are default implementations!
    +}
    +
    + +

    Generally, a rule wants to check for only some node types. In our XPath example +in Your First Rule, +we wanted to check for some VariableDeclaratorId nodes. That’s the XPath name, +but in Java, you’ll get access to the ASTVariableDeclaratorId +full API.

    + +

    If you want to check for some specific node types, you can override the +corresponding visit method:

    + +
    public class MyRule extends AbstractJavaRule {
    +
    +    @Override
    +    public Object visit(ASTVariableDeclaratorId node, Object data) {
    +        // This method is called on each node of type ASTVariableDeclaratorId
    +        // in the AST
    +
    +        if (node.getType() == short.class) {
    +            // reports a violation at the position of the node
    +            // the "data" parameter is a context object handed to by your rule
    +            // the message for the violation is the message defined in the rule declaration XML element
    +            addViolation(data, node);
    +        }
    +
    +        // this calls back to the default implementation, which recurses further down the subtree
    +        return super.visit(node, data);
    +    }
    +}
    +
    + +

    The super.visit(node, data) call is super common in rule implementations, +because it makes the traversal continue by visiting all the descendants of the +current node.

    + +

    Stopping the traversal

    + +

    Sometimes you have checked all you needed and you’re sure that the descendants +of a node may not contain violations. In that case, you can avoid calling the +super implementation and the traversal will not continue further down. This +means that your callbacks (visit implementations) won’t be called on the rest +of the subtree. The siblings of the current node may be visited +recursively nevertheless.

    + +

    Economic traversal: the rulechain

    + +

    If you don’t care about the order in which the nodes are traversed (e.g. your +rule doesn’t maintain any state between visits), then you can monumentally +speed-up your rule by using the rulechain.

    + +

    That mechanism doesn’t recurse on all the tree, instead, your rule will only be +passed the nodes it is interested in. To use the rulechain correctly:

    +
      +
    • Your rule must register those node types by calling addRuleChainVisit +in its constructor.
    • +
    • Your visit methods must not recurse! In effect, you should call never +call super.visit in the methods.
    • +
    + +

    Execution across files, thread-safety and statefulness

    + +

    When starting execution, PMD will instantiate a new instance of your rule. +If PMD is executed in multiple threads, then each thread is using its own +instance of the rule. This means, that the rule implementation does not need to care about +threading issues, as PMD makes sure, that a single instance is not used concurrently +by multiple threads.

    + +

    However, for performance reasons, the rule instances are used for multiple files. +This means, that the constructor of the rule is only executed once (per thread) +and the rule instance is reused. If you rely on a proper initialization of instance +properties, you can do the initialization e.g. in the visit-method of the ASTCompilationUnit +node - which is visited first and only once per file. However, this +solution would only work for rules written for the Java language. A language +independent way is to override the method start of the rule. +The start method is called exactly once per file.

    + + + +

    Rule lifecycle reference

    + +

    Construction

    + +

    Exactly once:

    + +
      +
    1. The rule’s no-arg constructor is called when loading the ruleset. +The rule’s constructor must define: + +
    2. +
    3. If the rule was included in the ruleset as a rule reference, +some properties may be overridden. +If an overridden property is unknown, an error is reported.
    4. +
    5. Misconfigured rules are removed from the ruleset
    6. +
    + +

    Execution

    + +

    For each thread, a deep copy of the rule is created. Each thread is given +a different set of files to analyse. Then, for each such file, for each +rule copy:

    + +
      +
    1. start is called once, before parsing
    2. +
    3. apply is called with the root +of the AST. That method performs the AST traversal that ultimately calls visit methods. +It’s not called for RuleChain rules.
    4. +
    5. end is called when the rule is done processing +the file
    6. +
    + + +
    + + Tags: + + + + extending + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_writing_pmd_rules.html b/pmd_userdocs_extending_writing_pmd_rules.html new file mode 100644 index 0000000000..32a6aa5fec --- /dev/null +++ b/pmd_userdocs_extending_writing_pmd_rules.html @@ -0,0 +1,1472 @@ + + + + + + + + +Writing a custom rule | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Writing a custom rule

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The information on this page has been split into several separate pages. Please update your bookmarks:

    + + + +

    To go further:

    +
      +
    • Defining Properties +describes how to make your rules more configurable with rule properties
    • +
    • Testing your Rules introduces +our testing framework and how you can use it to safeguard the quality of +your rule
    • +
    + + +
    + + Tags: + + + + extending + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_writing_rules_intro.html b/pmd_userdocs_extending_writing_rules_intro.html new file mode 100644 index 0000000000..10a65528e4 --- /dev/null +++ b/pmd_userdocs_extending_writing_rules_intro.html @@ -0,0 +1,1590 @@ + + + + + + + + +Introduction to writing PMD rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Introduction to writing PMD rules

    +
    + + + +
    + + +
    Writing your own PMD rules
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    PMD is a framework to perform code analysis. You can create your own rules to +check for patterns specific to your codebase, or the coding practices of your +team.

    + +

    How rules work: the AST

    + +

    Before running rules, PMD parses the source file into a data structure called an +abstract syntax tree (AST). This tree represents the syntactic structure of the +code, and encodes syntactic relations between source code elements. For instance, +in Java, method declarations belong to a class: in the AST, the nodes representing +method declarations will be descendants of a node representing the declaration of +their enclosing class. This representation is thus much richer than the original +source code (which, for a program, is just a chain of characters), or the token +chain produced by a lexer (which is e.g. what Checkstyle works on). For example:

    + + ++++ + + + + + + + + + + + + +
    Sample code (Java)AST
    + +
    class Foo extends Object {
    +
    +}
    +
    + +
    + +
    └─ CompilationUnit
    +   └─ TypeDeclaration
    +      └─ ClassOrInterfaceDeclaration "Foo"
    +         ├─ ExtendsList
    +           └─ ClassOrInterfaceType "Object"
    +         └─ ClassOrInterfaceBody
    +
    + +
    + +

    Conceptually, PMD rules work by matching a “pattern” against the AST of a +file. +Rules explore the AST and find nodes that satisfy some conditions that are characteristic +of the specific thing the rule is trying to flag. Rules then report a violation on these nodes.

    + +

    Discovering the AST

    + +

    ASTs are represented by Java classes deriving from Node. +Each PMD language has its own set of such classes, and its own rules about how +these classes relate to one another, based on the grammar of the language. For +example, all Java AST nodes extend JavaNode.

    + +

    The structure of the AST can be discovered through

    + + +

    Writing new rules

    + +

    PMD supports two ways to define rules: using an XPath query, or using a +Java visitor. XPath rules are much easier to set up, since they’re defined +directly in your ruleset XML, and are expressive enough for nearly any task.

    + +

    On the other hand, some parts of PMD’s API are only accessible from Java, e.g. +accessing the usages of a declaration. And Java rules allow you to do some +complicated processing, to which an XPath rule couldn’t scale.

    + +

    In the end, choosing one strategy or the other depends on the difficulty of what +your rule does. I’d advise to keep to XPath unless you have no other choice.

    + +

    XML rule definition

    + +

    New rules must be declared in a ruleset before they’re referenced. This is the +case for both XPath and Java rules. To do this, the rule element is used, but +instead of mentioning the ref attribute, it mentions the class attribute, +with the implementation class of your rule.

    + +
      +
    • For Java rules: this is the class extending AbstractRule (transitively)
    • +
    • For XPath rules: this is net.sourceforge.pmd.lang.rule.XPathRule
    • +
    + +

    Example:

    + +
    <rule name="MyJavaRule"
    +      language="java"
    +      message="Violation!"
    +      class="com.me.MyJavaRule" >
    +    <description>
    +        Description
    +    </description>
    +    <priority>3</priority>
    +</rule>
    +
    + + + +

    Resource index

    + +

    To learn how to write a rule:

    + + + +

    To go further:

    +
      +
    • Defining Properties +describes how to make your rules more configurable with rule properties
    • +
    • Testing your Rules introduces +our testing framework and how you can use it to safeguard the quality of +your rule
    • +
    + + + +
    + + Tags: + + + + extending + + + + userdocs + + + + getting_started + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_writing_xpath_rules.html b/pmd_userdocs_extending_writing_xpath_rules.html new file mode 100644 index 0000000000..5c90daf017 --- /dev/null +++ b/pmd_userdocs_extending_writing_xpath_rules.html @@ -0,0 +1,1870 @@ + + + + + + + + +Writing XPath rules | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Writing XPath rules

    +
    + + + +
    + + +
    This page describes XPath rule support in more details
    + + + + + + + +
    + + + + + + + + + + Edit me + + + + +

    This page describes some points of XPath rule support in more details. See +also the tutorial about how to write an XPath rule.

    + + + +

    XPath version

    + +

    PMD supports three XPath versions for now: 1.0, 2.0, and 1.0 compatibility mode. +The version can be specified with the version property in the rule definition, like so:

    + +
    <property version="2.0" /> <!-- or "1.0", or "1.0 compatibility" -->
    +
    + +

    The default has always been version 1.0.

    + +

    As of PMD version 6.22.0, XPath versions 1.0 and the 1.0 compatibility mode are +deprecated. XPath 2.0 is superior in many ways, for example for its support for +type checking, sequence values, or quantified expressions. For a detailed +but approachable review of the features of XPath 2.0 and above, see the Saxon documentation.

    + +

    It is recommended that you migrate to 2.0 before 7.0.0, but we expect +to be able to provide an automatic migration tool when releasing 7.0.0. +See the migration guide below.

    + +

    DOM representation of ASTs

    + +

    XPath rules view the AST as an XML-like DOM, which is what the XPath language is +defined on. Concretely, this means:

    +
      +
    • Every AST node is viewed as an XML element +
        +
      • The element has for local name the value of getXPathNodeName +for the given node
      • +
      +
    • +
    • Some Java getters are exposed as XML attributes on those elements +
        +
      • This means, that documentation for attributes can be found in our Javadocs. For +example, the attribute @SimpleName of the Java node EnumDeclaration is backed +by the Java getter getSimpleName.
      • +
      +
    • +
    + +

    Value conversion

    + +

    To represent attributes, we must map Java values to XPath Data Model (XDM) values. The conversion +depends on the XPath version used.

    + +

    XPath 1.0

    + +

    On XPath 1.0 we map every Java value to an xs:string value by using the toString +of the object. Since XPath 1.0 allows many implicit conversions this works, but it +causes some incompatibilities with XPath 2.0 (see the section about migration further + down).

    + +

    XPath 2.0

    + +

    XPath 2.0 is a strongly typed language, and so we use more precise type annotations. +In the following table we refer to the type conversion function as conv, a +function from Java types to XDM types.

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    Java type TXSD type conv(T)
    intxs:integer
    longxs:integer
    doublexs:decimal
    floatxs:decimal
    booleanxs:boolean
    Stringxs:string
    Characterxs:string
    Enum<E>xs:string (uses Object::toString)
    List<E>conv(E)* (a sequence type)
    ⚠️ List support is deprecated with 6.25.0. See below.
    + +

    The same conv function is used to translate rule property values to XDM values.

    + + + +

    Migrating from 1.0 to 2.0

    + +

    XPath 1.0 and 2.0 have some incompatibilities. The XPath 2.0 specification +describes them precisely. Those are however mostly corner cases and XPath +rules usually don’t feature any of them.

    + +

    The incompatibilities that are most relevant to migrating your rules are not +caused by the specification, but by the different engines we use to run +XPath 1.0 and 2.0 queries. Here’s a list of known incompatibilities:

    + +
      +
    • The namespace prefixes fn: and string: should not be mentioned explicitly. +In XPath 2.0 mode, the engine will complain about an undeclared namespace, but +the functions are in the default namespace. Removing the namespace prefixes fixes it. +
        +
      • fn:substring("Foo", 1)substring("Foo", 1)
      • +
      +
    • +
    • Conversely, calls to custom PMD functions like typeIs must be prefixed +with the namespace of the declaring module (pmd-java). +
        +
      • typeIs("Foo")pmd-java:typeIs("Foo")
      • +
      +
    • +
    • Boolean attribute values on our 1.0 engine are represented as the string values +"true" and "false". In 2.0 mode though, boolean values are truly represented +as boolean values, which in XPath may only be obtained through the functions +true() and false(). +If your XPath 1.0 rule tests an attribute like @Private="true", then it just +needs to be changed to @Private=true() when migrating. A type error will warn +you that you must update the comparison. More is explained on issue #1244. +
        +
      • "true", 'true'true()
      • +
      • "false", 'false'false()
      • +
      +
    • +
    • In XPath 1.0, comparing a number to a string coerces the string to a number. +In XPath 2.0, a type error occurs. Like for boolean values, numeric values are +represented by our 1.0 implementation as strings, meaning that @BeginLine > "1" +worked —that’s not the case in 2.0 mode. +
        +
      • @ArgumentCount > '1'@ArgumentCount > 1
      • +
      +
    • +
    • In XPath 1.0, the expression /Foo matches the children of the root named Foo. +In XPath 2.0, that expression matches the root, if it is named Foo. Consider the following tree: +
      Foo
      +└─ Foo
      +└─ Foo
      +
      +

      Then /Foo will match the root in XPath 2, and the other nodes (but not the root) in XPath 1. +See eg an issue caused by this in Apex, +with nested classes.

      +
    • +
    + +

    Rule properties

    + +

    See Defining rule properties

    + +

    PMD extension functions

    + +

    PMD provides some language-specific XPath functions to access semantic +information from the AST.

    + +

    On XPath 2.0, the namespace of custom PMD function must be explicitly mentioned.

    + + + +

    Java

    + +

    Java functions are in the namespace pmd-java.

    + +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    Function nameDescription (click for details)
    typeIsTests a node's static type + +
    +
    + +
    + + + +

    + pmd-java:typeIs(xs:string) as xs:boolean +

    + +
    + +
    +
    Returns true if the context node's static Java type is a subtype of the given type. This tests for the resolved type of the Java construct, not the type of the AST node. For example, the AST node for a literal (e.g. 5d) has type ASTLiteral, however this function will compare the type of the literal (eg here, double) against the argument.
    +
    Remarks
    +
    The context node must be a TypeNode
    + + + +
    Parameters
    + +
    +
    + +
    + javaQualifiedName + as xs:string +
    +
    The qualified name of a Java class, possibly with pairs of brackets to indicate an array type. Can also be a primitive type name.
    + +
    +
    + + + + + +
    Examples
    + +
    +
    + +
    //FormalParameter[pmd-java:typeIs("java.lang.String[]")]
    +
    Matches formal parameters of type String[] (including vararg parameters)
    + +
    //VariableDeclaratorId[pmd-java:typeIs("java.lang.List")]
    +
    Matches variable declarators of type List or any of its subtypes (including e.g. ArrayList)
    + +
    +
    + +
    +
    +
    +
    +
    typeIsExactlyTests a node's static type, ignoring subtypes + +
    +
    + +
    + + + +

    + pmd-java:typeIsExactly(xs:string) as xs:boolean +

    + +
    + +
    +
    Returns true if the context node's static type is exactly the given type. In particular, returns false if the context node's type is a subtype of the given type.
    +
    Remarks
    +
    The context node must be a TypeNode
    + + + +
    Parameters
    + +
    +
    + +
    + javaQualifiedName + as xs:string +
    +
    The qualified name of a Java class, possibly with pairs of brackets to indicate an array type. Can also be a primitive type name.
    + +
    +
    + + + + + +
    Examples
    + +
    +
    + +
    //VariableDeclaratorId[pmd-java:typeIsExactly("java.lang.List")]
    +
    Matches variable declarators of type List (but not e.g. ArrayList)
    + +
    +
    + +
    +
    +
    +
    +
    metricComputes and returns the value of a metric + +
    +
    + +
    + + + +

    + pmd-java:metric(xs:string) as xs:decimal? +

    + +
    + +
    +
    Returns the value of the metric as evaluated on the context node
    +
    Remarks
    +
    The context node must be a ASTAnyTypeDeclaration or a MethodLikeNode
    + + + +
    Parameters
    + +
    +
    + +
    + metricKey + as xs:string +
    +
    The name of an enum constant in JavaOperationMetricKey or JavaClassMetricKey
    + +
    +
    + + + + +
    +
    +
    +
    +
    + +
    + + + + + +
    + + Tags: + + + + extending + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_extending_your_first_rule.html b/pmd_userdocs_extending_your_first_rule.html new file mode 100644 index 0000000000..a32ee61d4d --- /dev/null +++ b/pmd_userdocs_extending_your_first_rule.html @@ -0,0 +1,1579 @@ + + + + + + + + +Your first rule XPath | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Your first rule XPath

    +
    + + + +
    + + +
    Introduction to rule writing through an example.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    This page is a gentle introduction to rule writing, and the Rule Designer.

    + +

    Using the designer is useful both to write Java +rules and XPath rules, but it’s more specifically geared towards XPath rules. +This page uses a simple XPath rule to illustrate the common workflow. We assume +here that you already know what XPath is and how to read basic XPath queries. W3C +has a good tutorial here if +you don’t (in the context of XML only), and the Saxon documentation +features a comprehensive but approachable description of the syntax of XPath +expressions.

    + +

    The Rule Designer

    + +

    The rule designer is a tool that packs a lot of features to help you develop XPath +rules quickly and painlessly. Basically, it allows you to examine the AST of a code +snippet and evaluate an XPath expression against it.

    + +

    Like for PMD and CPD, you can launch it using run.sh designer on Linux/Unix +and designer.bat on Windows. The interface looks like the following:

    + +
    Designer overview
    + +

    The zone (2) is the main editor. When you write a code snippet in the + code area to the left, you’ll see that the tree to the right will be updated + automatically: it’s the AST of the code. + Note that the code snippet must be a syntactically valid compilation unit for the + language you’ve chosen, e.g. for Java, a compilation unit necessarily has a top-level + type declaration.

    + +

    If you select a node in the AST, its specific properties will also be displayed +in the panel (1): they’re the XPath attributes of the node. More on that later.

    + +

    The zone (3) is the XPath editor. If you enter an XPath query in that area, +it will be evaluated on the current AST and the results will be displayed in the +list to the bottom right.

    + +

    Rule development process

    + +

    The basic development process is straightforward:

    + +
      +
    1. Write a code snippet in the main editor that features the offending code you’re looking for
    2. +
    3. Examine the AST and determine what node the violation should be reported on
    4. +
    5. Write an XPath expression matching that node in the XPath editor
    6. +
    7. Refine the XPath expression iteratively using different code snippets, so that +it matches violation cases, but no other node
    8. +
    9. Export your XPath expression to an XML rule element, and place it in your ruleset
    10. +
    + +

    Each time you test your rule against a different snippet, it’s a good idea to +save it to make test cases.

    + +

    In the following sections, we walk through several examples to refine your rule.

    + +

    A simple rule

    + +

    Let’s say you want to prevent your coding team from naming variables of type +short after your boss, whose name is Bill. You try the designer on the following + offending code snippet:

    + +
    
    +public class KeepingItSerious {
    +
    +    public void method() {
    +        short bill; // LocalVariableDeclaration
    +    }
    +
    +}
    +
    +
    + +

    Examining the AST, you find out that the LocalVariableDeclaration has a VariableDeclaratorId +descendant, whose Image XPath attribute is exactly bill. You thus write your first attempt +in the XPath editor:

    +
    //VariableDeclaratorId[@Image = "bill"]
    +
    + +

    You can see the XPath result list is updated with the variable declarator. +If you try the query against the following updated snippet though, you can +see that the field declaration id is matched even though it’s not of type short.

    + +
    public class KeepingItSerious {
    +
    +    Delegator bill; // FieldDeclaration
    +
    +    public void method() {
    +        short bill; // LocalVariableDeclaration
    +    }
    +
    +}
    +
    + +

    You thus refine your XPath expression with an additional predicate, +based on your examination of the Type node of the field and local variable +declaration nodes.

    + +
    //VariableDeclaratorId[@Image = "bill" and ../../Type[@TypeImage = "short"]]
    +
    + +

    Exporting to XML

    + +

    You estimate that your rule is now production ready, and you’d like to use it in your ruleset. +The File > Export XPath to rule... allows you to do that in a few clicks: just enter some +additional metadata for your rule, and the popup will generate an XML element that you can +copy-paste into your ruleset XML. The resulting element looks like so:

    + +
    <rule name="DontCallBossShort"
    +      language="java"
    +      message="Boss wants to talk to you."
    +      class="net.sourceforge.pmd.lang.rule.XPathRule" >
    +    <description>
    +TODO
    +    </description>
    +    <priority>3</priority>
    +    <properties>
    +        <property name="xpath">
    +            <value>
    +<![CDATA[
    +//VariableDeclaratorId[../../Type[@TypeImage="short"] and @Image = "bill"]
    +]]>
    +            </value>
    +        </property>
    +    </properties>
    +</rule>
    +
    + +

    You can notice that your XPath expression ends up inside a property +of a rule of type XPathRule, which is how XPath rules are implemented.

    + + +
    + + Tags: + + + + extending + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_incremental_analysis.html b/pmd_userdocs_incremental_analysis.html new file mode 100644 index 0000000000..74b72264b3 --- /dev/null +++ b/pmd_userdocs_incremental_analysis.html @@ -0,0 +1,1555 @@ + + + + + + + + +Incremental Analysis | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Incremental Analysis

    +
    + + + +
    + + +
    Explains how to use incremental analysis to speed up analysis
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Ever since PMD 5.6.0, PMD has been able to perform Incremental Analysis.

    + +

    When performing Incremental Analysis for the first time, PMD will cache analysis data and results. +This allows subsequent analysis to only look into those files that are new / have changed. For +a typical development environment, where you only change a few files at a time, this can reduce +analysis time dramatically.

    + +

    The generated report will be exactly the same as it would if running without incremental analysis. +Files included in the final report will reflect exactly those files in your filesystem. Even if +untouched, files with violations will be listed with full detail. Therefore, its usage is highly recommended.

    + +

    Enabling incremental analysis

    + +

    Incremental analysis is enabled automatically once a location to store the cache has been defined. +From command-line that is done through the -cache argument, but support for the feature is +available for tools integrating PMD such as Ant, +Maven, and Gradle.

    + +

    Disabling incremental analysis

    + +

    By default, PMD will suggest to use an analysis cache by logging a warning. +If you’d like to disable this warning, or ignore the analysis cache for a +few runs, you can use the -no-cache switch.

    + +

    FAQ

    + +

    When is the cache invalidated?

    + +

    On the following reasons, the complete cache file is considered invalid:

    + +
      +
    • The PMD version differs. Since each PMD version might have fixed some false-positives or false-negatives for rules, +a cache file created with a different version is considered invalid. The version comparison is exact.
    • +
    • The used ruleset has been changed. If the ruleset is changed in any way (e.g. adding/removing rules, changing +rule properties, …), the cache is considered invalid.
    • +
    • The auxclasspath changed. The auxclasspath is used during +type resolution. A changed auxclasspath can result for rules, that use type resolution, in different +violations. Usually, if the auxclasspath is correct and type resolution works, the rules report less false-positives. +To make sure, the correct violations are reported, the cache is considered invalid, if the auxclasspath has changed.
    • +
    • The execution classpath has been changed. On the execution classpath not only the PMD classes are located, but also +the implementation of e.g. custom rules. If any jar file/class file on the execution classpath is changed, then +the cache is considered invalid as well.
    • +
    + +

    What is stored in the cache file?

    + +

    The cache file consists of a header and a body. The header stores the information which is used to decided +whether the whole cache file is valid or not (see above). The following information is stored:

    + +
      +
    • PMD Version
    • +
    • Ruleset checksum
    • +
    • Auxclasspath checksum
    • +
    • Execution classpath checksum
    • +
    + +

    The body contains an entry for every file that has been analyzed. For every file, the following information +is stored:

    + +
      +
    • The full (absolute) pathname of the file
    • +
    • The checksum of the file itself
    • +
    • 0 or more rule violations with all the info (line number, etc.)
    • +
    + +

    You can think of the cache as a Map where the filepath is used as the key +and the violations found in previous runs are the value.

    + +

    The cache is in the end just a file with serialized data (binary). The implementation is +FileAnalysisCache.

    + +

    How does PMD detect whether a file has been changed?

    + +

    When analyzing a file, PMD records the checksum of the file content and stores this +together with the violations in the cache file. When running PMD with the cache file, +PMD looks up the file in the cache and compares the checksums. +If the checksums match, then the file is not even parsed, the rules +are not executed and the violations for this file are entirely used from the cache. +If the checksum doesn’t match, then the cached violations are discarded (if there are any) +and the file is fully processed: the file is parsed and all the rules are run for it. +After we are done, the cache is updated with the new violations.

    + +

    Can I reuse a cache created on branch A for analyzing my project on branch B?

    + +

    This is possible. As long as the same PMD version and same ruleset is used on both branches. +Also note, that if the branch uses a different dependencies, the auxclasspath is different on both +classes, which invalidates the cache completely. If you project uses e.g. Maven for dependency +management and your branch uses different dependencies (either different version or completely different +artifacts), then the auxclasspath is changed.

    + +

    If files have been renamed on the branch, these files will be analyzed again since PMD uses +the file names to assign existing rule violations from the cache. Also, if the full path name +of the file changes, because the other branch is checked out at a different location, then all +the cached files don’t match.

    + +

    Apart from these restrictions, PMD will only analyze files that changed between runs. +If your previous run was on branch A and then you run on branch B using the same cache file, +it will only look at files that are different between the 2 branches.

    + +

    Can I reuse a cache file across different machines?

    + +

    This is only possible, if the other machine uses the exact same path names. That means that +your project needs to be checked out into the same directory structure.

    + +

    Additionally, all the other restrictions apply (same PMD version, same ruleset, same auxclasspath, +same execution classpath).

    + +

    See also issue #2063 [core] Support sharing incremental analysis cache file across different machines.

    + + +
    + + Tags: + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_installation.html b/pmd_userdocs_installation.html new file mode 100644 index 0000000000..4aca14b3ce --- /dev/null +++ b/pmd_userdocs_installation.html @@ -0,0 +1,1608 @@ + + + + + + + + +Installation and basic CLI usage | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Installation and basic CLI usage

    +
    + + + +
    + + +
    Sums up the first steps to set up a CLI installation and get started using PMD
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    How to install PMD and CPD

    + +

    Requirements

    + + + + + +

    Installation

    + +

    PMD is distributed as a zip archive, which includes both PMD and CPD. +You can download the latest binary distribution from the github releases page.

    + +

    Unzip it into any directory, optionally add the bin subdirectory in your PATH, and you’re good to go!

    + +

    Running PMD via command line

    + +
    PMD comes with several command line utilities, like CPD, the rule designer or PMD itself. + On Unix, you can run any of them using the script run.sh, located inside the bin/ + directory of the PMD distribution. The first argument is the name of the utility you want + to execute (‘pmd’, ‘designer’, …), e.g. PMD is launched via run.sh pmd. The rest of + the arguments are specific to the utility used.

    + On Windows, each utility has its own startup script, e.g. pmd.bat, cpd.bat.
    + +

    The PMD command (pmd.bat or run.sh pmd) requires two options:

    + +
      +
    • -d <path>: path to the sources to analyse. This can be a file name, a directory, or a jar or zip file containing the +sources.
    • +
    • -R <path>: the ruleset file you want to use. PMD uses xml configuration files, called rulesets, which specify +which rules to execute on your sources. You can also run a single rule by referencing it using its category and +name (more details here). For example, you can check for unnecessary +modifiers on Java sources with -R category/java/codestyle.xml/UnnecessaryModifier.
    • +
    + + + +

    Additionally, the following options, are specified most of the time even though they’re not required:

    +
      +
    • -f <format>: report format. PMD supports many report formats out of the box. You may want to start with the basic +text format (default) or xml format. The supported formats are documented here.
    • +
    • -auxclasspath <classpath>: class path containing the compiled class files of the analysed Java sources, if any. +Setting this up correctly allows PMD to do much deeper analysis using reflection. Some rules, such as MissingOverride, +require it to function properly.
    • +
    + + + +

    Sample usage

    + +

    The following shows a sample run of PMD with the text format:

    + +
    + + +
    +
    +
    ~ $ cd ~/bin/pmd-bin-6.30.0-SNAPSHOT/bin
    +~/.../bin $ ./run.sh pmd -d ../../../src/main/java/ -f text -R rulesets/java/quickstart.xml
    +  
    +  .../src/main/java/com/me/RuleSet.java:123  These nested if statements could be combined
    +  .../src/main/java/com/me/RuleSet.java:231  Useless parentheses.
    +  .../src/main/java/com/me/RuleSet.java:232  Useless parentheses.
    +  .../src/main/java/com/me/RuleSet.java:357  These nested if statements could be combined
    +  .../src/main/java/com/me/RuleSetWriter.java:66     Avoid empty catch blocks
    +
    +
    +
    C:\ > cd C:\pmd-bin-6.30.0-SNAPSHOT\bin
    +C:\...\bin > .\pmd.bat -d ..\..\src\main\java\ -f text -R rulesets/java/quickstart.xml
    +      
    +  .../src/main/java/com/me/RuleSet.java:123  These nested if statements could be combined
    +  .../src/main/java/com/me/RuleSet.java:231  Useless parentheses.
    +  .../src/main/java/com/me/RuleSet.java:232  Useless parentheses.
    +  .../src/main/java/com/me/RuleSet.java:357  These nested if statements could be combined
    +  .../src/main/java/com/me/RuleSetWriter.java:66     Avoid empty catch blocks
    +
    +
    +
    + +

    Running CPD via command line

    + + + +

    Like for PMD, CPD is started on Unix by run.sh cpd and on Windows by cpd.bat.

    + +

    There are two required parameters:

    +
      +
    • --files <path>: path to the sources to analyse. This can be a file name, a +directory or a jar or zip file containing the sources.
    • +
    • --minimum-tokens <number>: the minimum token length which should be reported as a duplicate.
    • +
    + + + +

    Sample usage

    + +

    The following shows a sample run of CPD with the text format:

    + +
    + + +
    +
    +
    ~ $ cd ~/bin/pmd-bin-6.30.0-SNAPSHOT/bin
    +~/.../bin $ ./run.sh cpd --minimum-tokens 100 --files /home/me/src
    +
    +  Found a 7 line (110 tokens) duplication in the following files:
    +  Starting at line 579 of /home/me/src/test/java/foo/FooTypeTest.java
    +  Starting at line 586 of /home/me/src/test/java/foo/FooTypeTest.java
    +
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +
    +
    +
    C:\ > cd C:\pmd-bin-6.30.0-SNAPSHOT\bin
    +C:\...\bin > .\cpd.bat --minimum-tokens 100 --files c:\temp\src
    +
    +  Found a 7 line (110 tokens) duplication in the following files:
    +  Starting at line 579 of c:\temp\src\test\java\foo\FooTypeTest.java
    +  Starting at line 586 of c:\temp\src\test\java\foo\FooTypeTest.java
    +
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +          assertEquals(Boolean.TYPE, expressions.get(index++).getType());
    +
    +
    +
    + + +
    + + Tags: + + + + getting_started + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_making_rulesets.html b/pmd_userdocs_making_rulesets.html new file mode 100644 index 0000000000..e43eb4b362 --- /dev/null +++ b/pmd_userdocs_making_rulesets.html @@ -0,0 +1,1558 @@ + + + + + + + + +Making rulesets | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Making rulesets

    +
    + + + +
    + + +
    A ruleset is an XML configuration file, which describes a collection of rules to be executed in a PMD run. PMD includes built-in rulesets to run quick analyses with a default configuration, but users are encouraged to make their own rulesets from the start, because they allow for so much configurability. This page walk you through the creation of a ruleset and the multiple configuration features offered by rulesets.
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Creating a ruleset

    + +

    The first step is to create a new empty ruleset. You can use the following template:

    + +
    <?xml version="1.0"?>
    +
    +<ruleset name="Custom Rules"
    +    xmlns="http://pmd.sourceforge.net/ruleset/2.0.0"
    +    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    +    xsi:schemaLocation="http://pmd.sourceforge.net/ruleset/2.0.0 https://pmd.sourceforge.io/ruleset_2_0_0.xsd">
    +
    +    <description>
    +        My custom rules
    +    </description>
    +
    +
    +    <!-- Your rules will come here -->
    +
    +</ruleset>
    +
    + +

    Referencing a single rule

    + + + +

    To use the built-in rules PMD provides, you need to add some references to them. Here’s a +basic rule reference:

    + +
    <rule ref="category/java/errorprone.xml/EmptyCatchBlock" />
    +
    + +

    Adding that element into the ruleset element adds the rule EmptyCatchBlock +to your ruleset. This is a Java rule, so it will be executed on every Java file PMD encounters in +its search space.

    + +

    How to read the ref attribute?

    + +
      +
    • +

      category/java/errorprone.xml is a reference to the Java category errorprone. Since PMD 6.0.0, +all PMD built-in rules are sorted in one of eight categories, which are consistent across languages:

      + +
        +
      1. Best Practices: These are rules which enforce generally accepted best practices.
      2. +
      3. Code Style: These rules enforce a specific coding style.
      4. +
      5. Design: Rules that help you discover design issues.
      6. +
      7. Documentation: These rules are related to code documentation.
      8. +
      9. Error Prone: Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors.
      10. +
      11. Multithreading: These are rules that flag issues when dealing with multiple threads of execution.
      12. +
      13. Performance: Rules that flag suboptimal code.
      14. +
      15. Security: Rules that flag potential security flaws.”
      16. +
      +
    • +
    + + + +
      +
    • EmptyCatchBlock is simply the name of the rule. If there were no rule with that name within the specified +category, then PMD would fail before starting the analysis.
    • +
    + +

    Configuring individual rules

    + +

    How you can configure individual rules is described on Configuring Rules.

    + +

    Bulk-adding rules

    + +

    You can also reference rules in bulk by referencing a complete category or ruleset, possibly excluding certain rules, like in the following:

    + +
    <rule ref="category/java/codestyle.xml">
    +    <exclude name="WhileLoopsMustUseBraces"/>
    +    <exclude name="IfElseStmtsMustUseBraces"/>
    +</rule>
    +
    + +

    Here, the ref attribute references a whole category. You can also use a file system path or classpath relative path. In any case, the path must address an accessible ruleset XML file.

    + + + + + +

    Filtering the processed files

    + +

    You can exclude some files from being processed by a ruleset using exclude patterns, with an optional overridding include pattern. A file will be excluded from processing when there is a matching exclude pattern, but no matching include pattern. This exclude/include technique works regardless of how PMD is used (e.g. command line, IDE, Ant), making it easier to keep application of your PMD rules consistent throughout your environment. Here is an example:

    + +
    <?xml version="1.0"?>
    +<ruleset name="myruleset"
    +		xmlns="http://pmd.sourceforge.net/ruleset/2.0.0"
    +		xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    +		xsi:schemaLocation="http://pmd.sourceforge.net/ruleset/2.0.0 https://pmd.sourceforge.io/ruleset_2_0_0.xsd">
    +    <description>My ruleset</description>
    +
    +    <exclude-pattern>.*/some/package/.*</exclude-pattern>
    +    <exclude-pattern>.*/some/other/package/FunkyClassNamePrefix.*</exclude-pattern>
    +    <include-pattern>.*/some/package/ButNotThisClass.*</include-pattern>
    +
    +    <!-- Rules here ... -->
    +
    +</ruleset>
    +
    + + +
    + + Tags: + + + + getting_started + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_report_formats.html b/pmd_userdocs_report_formats.html new file mode 100644 index 0000000000..fd1be118b5 --- /dev/null +++ b/pmd_userdocs_report_formats.html @@ -0,0 +1,1809 @@ + + + + + + + + +Report formats for PMD | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Report formats for PMD

    +
    + + + +
    + + +
    Overview of the built-in report formats for PMD
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Overview

    + +

    PMD can report the found rule violations in various formats. Some formats can +be customized further via properties. Violations might also be suppressed and there might +be processing errors or configuration errors. Not all report formats display all information.

    + +

    The header of the sections below are used to select the format on the command line, as +arguments to the -format option. When a format accepts properties, +those can be specified with the -property / -P option on the command-line.

    + + + +

    codeclimate

    + +

    Renderer for Code Climate JSON format.

    + +

    This format is used when running PMD within Code Climate. +The renderer will stream JSON objects, each object is a own issue (a PMD rule violation). Each issue +is separated by the null character (\0).

    + +

    The format is specified here: https://github.com/codeclimate/platform/blob/master/spec/analyzers/SPEC.md.

    + +

    The code climate format doesn’t support suppressed violations. It also doesn’t report any errors. But it contains +the full rule details for each reported rule violation.

    + +

    Example:

    + +
    {"type":"issue","check_name":"GuardLogStatement","description":"Logger calls should be surrounded by log level guards.","content":{"body":"## GuardLogStatement\n\nSince: PMD 5.1.0\n\nPriority: Medium High\n\n[Categories](https://github.com/codeclimate/platform/blob/master/spec/analyzers/SPEC.md#categories): Style\n\n[Remediation Points](https://github.com/codeclimate/platform/blob/master/spec/analyzers/SPEC.md#remediation-points): 50000\n\nWhenever using a log level, one should check if the loglevel is actually enabled, or otherwise skip the associate String creation and manipulation.\n\n### Example:\n\n```java\n\n\n // Add this for performance\n if (log.isDebugEnabled() { ...\n log.debug('log something' + ' and ' + 'concat strings');\n\n \n``` \n\n### [PMD properties](https://pmd.github.io/pmd-6.22.0/pmd_userdocs_configuring_rules.html#rule-properties)\n\nName | Value | Description\n--- | --- | ---\nviolationSuppressRegex | | Suppress violations with messages matching a regular expression\nviolationSuppressXPath | | Suppress violations on nodes which match a given relative XPath expression.\nlogLevels | trace,debug,info,warn,error,log,finest,finer,fine,info,warning,severe | LogLevels to guard\nguardsMethods | isTraceEnabled,isDebugEnabled,isInfoEnabled,isWarnEnabled,isErrorEnabled,isLoggable | Method use to guard the log statement\n"},"categories":["Style"],"location":{"path":"/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java","lines":{"begin":124,"end":125}},"severity":"normal","remediation_points":50000}
    +{"type":"issue","check_name":"ForLoopCanBeForeach","description":"This for loop can be replaced by a foreach loop","content":{"body":"## ForLoopCanBeForeach\n\nSince: PMD 6.0.0\n\nPriority: Medium\n\n[Categories](https://github.com/codeclimate/platform/blob/master/spec/analyzers/SPEC.md#categories): Style\n\n[Remediation Points](https://github.com/codeclimate/platform/blob/master/spec/analyzers/SPEC.md#remediation-points): 50000\n\nReports loops that can be safely replaced with the foreach syntax. The rule considers loops over lists, arrays and iterators. A loop is safe to replace if it only uses the index variable to access an element of the list or array, only has one update statement, and loops through *every* element of the list or array left to right.\n\n### Example:\n\n```java\n\n\npublic class MyClass {\n void loop(List<String> l) {\n for (int i = 0; i < l.size(); i++) { // pre Java 1.5\n System.out.println(l.get(i));\n }\n\n for (String s : l) { // post Java 1.5\n System.out.println(s);\n }\n }\n}\n\n \n``` \n\n### [PMD properties](https://pmd.github.io/pmd-6.22.0/pmd_userdocs_configuring_rules.html#rule-properties)\n\nName | Value | Description\n--- | --- | ---\nviolationSuppressRegex | | Suppress violations with messages matching a regular expression\nviolationSuppressXPath | | Suppress violations on nodes which match a given relative XPath expression.\n"},"categories":["Style"],"location":{"path":"/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java","lines":{"begin":58,"end":62}},"severity":"normal","remediation_points":50000}
    +
    + +

    csv

    + +

    Comma-separated values tabular format.

    + +

    This format only renders rule violations. Suppressed violations or errors are ignored.

    + +

    Example:

    + +
    "Problem","Package","File","Priority","Line","Description","Rule set","Rule"
    +"1","net.sourceforge.pmd","/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java","2","124","Logger calls should be surrounded by log level guards.","Best Practices","GuardLogStatement"
    +"1","net.sourceforge.pmd.benchmark","/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java","3","58","This for loop can be replaced by a foreach loop","Best Practices","ForLoopCanBeForeach"
    +
    + +

    This format can be configured to display only certain columns. In order to not show the problem counter and package +columns, use these CLI parameters additionally: -property problem=false -property package=false

    + +

    Properties:

    + +
      +
    • problem: Include problem column. Default: true.
    • +
    • package: Include package column. Default: true.
    • +
    • file: Include file column. Default: true.
    • +
    • priority: Include priority column. Default: true.
    • +
    • line: Include line column. Default: true.
    • +
    • desc: Include description column. Default: true.
    • +
    • ruleSet: Include Rule set column. Default: true.
    • +
    • rule: Include Rule column. Default: true.
    • +
    + +

    emacs

    + +

    GNU Emacs integration.

    + +

    Example:

    + +
    /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java:124: Logger calls should be surrounded by log level guards.
    +/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java:58: This for loop can be replaced by a foreach loop
    +
    + +

    html

    + +

    HTML format.

    + +

    This renderer provides two properties to render a link to the source where the violations +have been found. The following example has been created with -property linkPrefix=https://github.com/pmd/pmd/blob/master/ -property linePrefix=L -shortnames -d pmd. +If “linkPrefix” is not set, then “linePrefix” has no effect anyway: just the filename will +be rendered, with no html link. Otherwise if “linePrefix” is not set, then the link will +not contain a line number.

    + +

    When using Maven JXR Plugin to generate a html view +of the project’s sources, then the property “htmlExtension” needs to be set to “true”. This will then replace the +normal source file extensions (e.g. “.java”) with “.html”, so that the generated html pages are referenced.

    + +

    Example

    + +

    Properties:

    + +
      +
    • linePrefix: Prefix for line number anchor in the source file.
    • +
    • linkPrefix: Path to HTML source.
    • +
    • htmlExtension: Replace file extension with .html for the links (default: false)
    • +
    + +

    ideaj

    + +

    IntelliJ IDEA integration.

    + + + +

    It has two ways of calling:

    + +
      +
    1. For a single file: then all three properties need to be provided
    2. +
    + +

    run.sh pmd -d src/Foo.java -R rulesets/java/quickstart.xml -f ideaj -P fileName=src/Foo.java -P sourcePath=/home/pmd/src -P classAndMethodName=Foo

    + +
      +
    1. For a directory: then the fileName property can be omitted
    2. +
    + +

    run.sh pmd -d src -R rulesets/java/quickstart.xml -f ideaj -P sourcePath=/home/pmd/src -P classAndMethodName=.method

    + +

    Example:

    + +
    Logger calls should be surrounded by log level guards.
    + at Foo(:124)
    +This for loop can be replaced by a foreach loop
    + at Foo(:58)
    +
    + +

    Properties:

    + +
      +
    • classAndMethodName: Class and method name, pass .method when processing a directory.
    • +
    • sourcePath:
    • +
    • fileName:
    • +
    + +

    json

    + +

    JSON format.

    + +

    This prints a single JSON object containing some header information, +and then the violations grouped by file. The root object fields are

    +
      +
    • formatVersion: an integer which will be incremented if we change the serialization format
    • +
    • pmdVersion: the version of PMD that produced the report
    • +
    • timestamp: explicit
    • +
    • files: an array of objects (see the example)
    • +
    + +

    Example

    + +

    summaryhtml

    + +

    Summary HTML format.

    + +

    This is the html renderer but with an extra section, the summarizes the violations per rule.

    + +

    Example

    + +

    Properties:

    + +
      +
    • linePrefix: Prefix for line number anchor in the source file.
    • +
    • linkPrefix: Path to HTML source.
    • +
    • htmlExtension: Replace file extension with .html for the links (default: false)
    • +
    + +

    text (default)

    + +

    This is the default format.

    + +

    This format outputs one line per violation. At the end, processing errors, suppressed violations +and configuration errors are reported.

    + +

    Example:

    + +
    /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java:124:    Logger calls should be surrounded by log level guards.
    +/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java:58:   This for loop can be replaced by a foreach loop
    +/home/pmd/source/pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java    -   PMDException: Error while parsing /home/pmd/source/pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    +CloseResource rule violation suppressed by Annotation in /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/PMD.java
    +LoosePackageCoupling    -   No packages or classes specified
    +
    + +

    textcolor

    + +

    Text format, with color support (requires ANSI console support, e.g. xterm, rxvt, etc.).

    + +

    Example:

    + +
    +* file: ./pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java
    +    src:  RuleContext.java:124:125
    +    rule: GuardLogStatement
    +    msg:  Logger calls should be surrounded by log level guards.
    +    code: LOG.warning("The method RuleContext::setSourceCodeFilename(String) has been deprecated and will be removed."
    +
    +* file: ./pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java
    +    src:  Benchmarker.java:58:62
    +    rule: ForLoopCanBeForeach
    +    msg:  This for loop can be replaced by a foreach loop
    +    code: for (int i = 0; i < args.length; i++) {
    +
    +
    +
    +Summary:
    +
    +net.sourceforge.pmd.RuleContext : 1
    +net.sourceforge.pmd.benchmark.Benchmarker : 1
    +* file: ./pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    +    err:  PMDException: Error while parsing /home/pmd/source/pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    +net.sourceforge.pmd.PMDException: Error while parsing /home/pmd/source/pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:110)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:89)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:51)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:78)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:24)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1130)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:630)
    +    at java.base/java.lang.Thread.run(Thread.java:832)
    +Caused by: net.sourceforge.pmd.lang.java.ast.ParseException: Encountered " "-" "- "" at line 6, column 30.
    +Was expecting one of:
    +    "extends" ...
    +    "implements" ...
    +    "{" ...
    +    "<" ...
    +    
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.generateParseException(JavaParser.java:12713)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.jj_consume_token(JavaParser.java:12597)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceBody(JavaParser.java:1554)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceDeclaration(JavaParser.java:732)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.TypeDeclaration(JavaParser.java:639)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.CompilationUnit(JavaParser.java:373)
    +    at net.sourceforge.pmd.lang.java.AbstractJavaParser.parse(AbstractJavaParser.java:62)
    +    at net.sourceforge.pmd.SourceCodeProcessor.parse(SourceCodeProcessor.java:121)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSource(SourceCodeProcessor.java:185)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:107)
    +    ... 10 more
    +
    +
    +* rule: LoosePackageCoupling
    +    err:  No packages or classes specified
    +
    +* errors:   2
    +* warnings: 2
    +
    + +

    Properties:

    + +
      +
    • color: Enables colors with anything other than false or 0. Default: yes.
    • +
    + +

    textpad

    + +

    TextPad integration.

    + +

    Example:

    + +
    /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java(124,  GuardLogStatement):  Logger calls should be surrounded by log level guards.
    +/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java(58,  ForLoopCanBeForeach):  This for loop can be replaced by a foreach loop
    +
    + +

    vbhtml

    + +

    Vladimir Bossicard HTML format.

    + +

    xml

    + +

    XML format.

    + +

    This format is a XML document, that can be validated by a XSD schema. The schema is report_2_0_0.xsd.

    + +

    Example:

    + +
    <?xml version="1.0" encoding="UTF-8"?>
    +<pmd xmlns="http://pmd.sourceforge.net/report/2.0.0"
    +    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    +    xsi:schemaLocation="http://pmd.sourceforge.net/report/2.0.0 https://pmd.sourceforge.io/report_2_0_0.xsd"
    +    version="6.22.0" timestamp="2020-04-11T19:17:03.207">
    +<file name="/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java">
    +<violation beginline="124" endline="125" begincolumn="9" endcolumn="111" rule="GuardLogStatement" ruleset="Best Practices" package="net.sourceforge.pmd" class="RuleContext" method="setSourceCodeFilename" externalInfoUrl="https://pmd.github.io/pmd-6.22.0/pmd_rules_java_bestpractices.html#guardlogstatement" priority="2">
    +Logger calls should be surrounded by log level guards.
    +</violation>
    +</file>
    +<file name="/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java">
    +<violation beginline="58" endline="62" begincolumn="9" endcolumn="9" rule="ForLoopCanBeForeach" ruleset="Best Practices" package="net.sourceforge.pmd.benchmark" class="Benchmarker" method="findBooleanSwitch" externalInfoUrl="https://pmd.github.io/pmd-6.22.0/pmd_rules_java_bestpractices.html#forloopcanbeforeach" priority="3">
    +This for loop can be replaced by a foreach loop
    +</violation>
    +</file>
    +<error filename="/home/pmd/source/pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java" msg="PMDException: Error while parsing /home/pmd/source/pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java">
    +<![CDATA[net.sourceforge.pmd.PMDException: Error while parsing /home/pmd/source/pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:110)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:89)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:51)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:78)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:24)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1130)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:630)
    +    at java.base/java.lang.Thread.run(Thread.java:832)
    +Caused by: net.sourceforge.pmd.lang.java.ast.ParseException: Encountered " "-" "- "" at line 6, column 30.
    +Was expecting one of:
    +    "extends" ...
    +    "implements" ...
    +    "{" ...
    +    "<" ...
    +    
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.generateParseException(JavaParser.java:12713)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.jj_consume_token(JavaParser.java:12597)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceBody(JavaParser.java:1554)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceDeclaration(JavaParser.java:732)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.TypeDeclaration(JavaParser.java:639)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.CompilationUnit(JavaParser.java:373)
    +    at net.sourceforge.pmd.lang.java.AbstractJavaParser.parse(AbstractJavaParser.java:62)
    +    at net.sourceforge.pmd.SourceCodeProcessor.parse(SourceCodeProcessor.java:121)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSource(SourceCodeProcessor.java:185)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:107)
    +    ... 10 more
    +]]>
    +</error>
    +<suppressedviolation filename="/home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/PMD.java" suppressiontype="annotation" msg="Ensure that resources like this OutputStreamWriter object are closed after use" usermsg=""/>
    +<configerror rule="LoosePackageCoupling" msg="No packages or classes specified"/>
    +</pmd>
    +
    + +

    Properties:

    + +
      +
    • encoding: XML encoding format, defaults to UTF-8.
    • +
    + +

    xslt

    + +

    XML with a XSL transformation applied.

    + +

    PMD provides one built-in stylesheet, that is used by default, if no other +stylesheet with the property “xsltFilename” is specified. It is called pmd-nicerhtml.xsl and can be used for customization.

    + +

    Example with pmd-nicerhtml.xsl

    + +

    Properties:

    + +
      +
    • encoding: XML encoding format, defaults to UTF-8.
    • +
    • xsltFilename: The XSLT file name.
    • +
    + +

    yahtml

    + +

    Yet Another HTML format.

    + +

    This renderer creates an html file per analyzed source file, hence you need to specify a output directory. +The output directory must exist. If not specified, the html files are created in the current directory.

    + +

    Example

    + +

    Properties:

    + +
      +
    • outputDir: Output directory.
    • +
    + + +
    + + Tags: + + + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_suppressing_warnings.html b/pmd_userdocs_suppressing_warnings.html new file mode 100644 index 0000000000..ddb2b3d7ac --- /dev/null +++ b/pmd_userdocs_suppressing_warnings.html @@ -0,0 +1,1659 @@ + + + + + + + + +Suppressing warnings | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Suppressing warnings

    +
    + + + +
    + + +
    Learn how to suppress some rule violations, from the source code using annotations or comments, or globally from the ruleset
    + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    PMD provides several methods by which Rule violations can be suppressed. +Follow these steps to help you determine which expression method works best +for you:

    + +
      +
    1. +

      Is the thing you need to suppress universally appealing to other +users of PMD, or is it a false positive? Can you modify the Rule to +support this specific suppression via a configuration property, or to +fix the false positive? If you can do this, then please do so, and +submit a patch back to the PMD project. Since PMD is built by users +for users, your help would be greatly appreciated by everyone. If you +cannot…

      +
    2. +
    3. +

      Can you use Annotations or the NOPMD marker to work around your +particular issue on a case by case basis? If not…

      +
    4. +
    5. +

      Can a regular expression matching the violation message work +around your particular issue? If not…

      +
    6. +
    7. +

      Can a XPath query on the violation node work around your particular +issue? If not…

      +
    8. +
    9. +

      Your last and final option is to see the first point about +changing the Rule, but you do not need to submit a patch back to the +PMD project.

      +
    10. +
    + +

    If you need to modify the Rule, see How to write a rule. +Otherwise, the other suppression methods are explained in the following sections.

    + +

    Annotations

    + +

    When using Java 1.5 or later, you can use annotations to suppress PMD warnings, like this:

    + +
    // This will suppress all the PMD warnings in this class
    +@SuppressWarnings("PMD")
    +public class Bar {
    +    void bar() {
    +        int foo;
    +    }
    +}
    +
    + +

    When using Apex make sure to use single quotes instead of double quotes

    + +
    // This will suppress all the PMD warnings in this class
    +@SuppressWarnings('PMD')
    +
    + +

    Or you can suppress one rule with an annotation like this:

    + +
    // This will suppress UnusedLocalVariable warnings in this class
    +@SuppressWarnings("PMD.UnusedLocalVariable")
    +public class Bar {
    +    void bar() {
    +        int foo;
    +    }
    +}
    +
    + +

    Multiple rules can be suppressed by providing multiple values, ie:

    + +
    @SuppressWarnings({"PMD.UnusedLocalVariable", "PMD.UnusedPrivateMethod"})
    +
    + +

    For Apex, the syntax for this is slightly different:

    + +
    @SuppressWarnings('PMD.UnusedLocalVariable, PMD.UnusedPrivateMethod')
    +
    + +

    PMD Java also obeys the JDK annotation @SuppressWarnings(“unused”), which will apply to all rules in the unused ruleset.

    + +
    // This will suppress UnusedLocalVariable and UnusedPrivateMethod warnings in this class
    +@SuppressWarnings("unused")
    +public class Bar {
    +    void bar() {
    +        int foo;
    +    }
    +    private void foobar(){}
    +}
    +
    + +

    NOPMD comment

    + +

    Alternatively, you can tell PMD to ignore a specific line by using the “NOPMD” marker in a comment, like this:

    + +
    public class Bar {
    +    // 'bar' is accessed by a native method, so we want to suppress warnings for it
    +    private int bar; //NOPMD
    +}
    +
    + +

    You can use whatever text string you want to suppress warnings, by using the -suppressmarker CLI option. +For example, here’s how to use TURN_OFF_WARNINGS as the suppressor:

    + +
    $ cat Foo.java
    +public class Foo {
    +    void bar() {
    +        int x = 2; // TURN_OFF_WARNINGS
    +    }
    +}
    +
    +$ ./run.sh pmd -d Foo.java -f text -R java-unusedcode -suppressmarker TURN_OFF_WARNINGS
    +No problems found!
    +UnusedLocalVariable rule violation suppressed by //NOPMD in /home/tom/pmd/pmd/bin/Foo.java
    +
    +

    Note that PMD expects the //NOPMD marker to be on the same line as the violation. So, for +example, if you want to suppress an “empty if statement” warning, you’ll need to place it on +the line containing the if keyword, e.g.:

    + +
    $ cat ~/tmp/Foo.java
    +public class Foo {
    +    void bar() {
    +        int x = 42;
    +        if (x > 5) { // NOPMD
    +        }
    +    }
    +}
    +$ java net.sourceforge.pmd.PMD -d ~/tmp/Foo.java -f text -R java-basic
    +No problems found!
    +
    + +

    A message placed after the NOPMD marker will get placed in the report, e.g.:

    + +
    public class Foo {
    +    void bar() {
    +        try {
    +            bar();
    +        } catch (FileNotFoundException e) {} // NOPMD - this surely will never happen
    +    }
    +}
    +
    + +

    XPath and Regex message suppression

    + +

    If a particular rule consistently reports a warning in a particular context, you can fall +back to disabling the rule for all these contexts using one of two rule properties +that are defined on every rule. Depending on what you’re after, you can suppress +violations for specific messages using regular expressions, or specific nodes +using an XPath expression.

    + +

    The property violationSuppressRegex

    + +

    This property defines a regular expression to match against the +message of the violation. If the regular expression matches, +then the violation will be suppressed.

    + +

    For example, to suppress reporting specifically named parameters which +are unused:

    + +
    <rule ref="rulesets/java/unusedcode.xml/UnusedFormalParameter">
    +  <properties>
    +    <property name="violationSuppressRegex" value=".*'mySpecialParameterName'.*"/>
    +  </properties>
    +</rule>
    +
    + +

    Note for message based suppression to work, you must know how to write +a regular expression that matches the message of violations you wish to +suppress. Regular expressions are explained in the JavaDoc for standard +Java class java.util.regex.Pattern.

    + +

    This technique of course relies on how the rule’s message is implemented. +Some rules always report the same message, in which case this property is +of no use.

    + +

    The property violationSuppressXPath

    + +

    This property defines an XPath query to be executed using the +violation node as the context node. If the XPath query matches anything, +then the violation will be suppressed. Note that the query shouldn’t be finding +the violation nodes to suppress, but rather, finding a non-empty sequence of nodes +when evaluated with the violation node as a context node.

    + +

    The XPath version used by those queries is XPath 1.0, so it doesn’t support various XPath 2.0 +features. This will be updated with PMD 7.0.0.

    + +

    For example, to suppress reporting specifically “String” parameters which are unused:

    + +
    <rule ref="rulesets/java/unusedcode.xml/UnusedFormalParameter">
    +  <properties>
    +    <property name="violationSuppressXPath" value=".[typeIs('java.lang.String')]"/>
    +  </properties>
    +</rule>
    +
    + +

    Note the use of . to refer to the context node. Using // at the start of the +expression should be avoided, as it would test all nodes in the file, and suppress +more violations than expected.

    + +

    Another example, to suppress violations occurring in classes whose name contains Bean:

    +
    <property name="violationSuppressXPath" value="./ancestor::ClassOrInterfaceDeclaration[contains(@Image, 'Bean')]"/>
    +
    + +

    You can also use regex for string comparison. The next example suppresses violations in classes ending with Bean:

    +
    <property name="violationSuppressXPath" value="./ancestor::ClassOrInterfaceDeclaration[matches(@Image, '^.*Bean$')]"/>
    +
    + +

    Note here the usage of the ./ancestor:: axis instead of //. The latter would match +any ClassOrInterfaceDeclaration in the file, while the former matches only class +declaration nodes that enclose the violation node, which is usually what you’d want.

    + +

    Note for XPath based suppression to work, you must know how to write +an XPath query that matches the AST structure of the nodes of the +violations you wish to suppress. XPath queries are explained in +XPath Rule tutorial.

    + + +
    + + Tags: + + + + userdocs + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_tools.html b/pmd_userdocs_tools.html new file mode 100644 index 0000000000..8c33d890b4 --- /dev/null +++ b/pmd_userdocs_tools.html @@ -0,0 +1,1899 @@ + + + + + + + + +Tools / Integrations | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Tools / Integrations

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Automated Code Review

    + +

    Codacy

    + +

    Codacy automates code reviews and monitors code quality on every commit and pull request. +It gives visibility into the technical debt and it can track code style and security issues, code coverage, code duplication, cyclomatic complexity and enforce best practices. +Codacy is static analysis without the hassle.

    + +

    With Codacy you have PMDJava analysis out-of-the-box, and it is free for open source projects.

    + + + +

    IDE Integrations

    + +

    Summary

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    IDEHomepageSource CodeMaintainers
    BlueJpmd-bluejTom Copeland
    CodeGuideN/AAustin Moore
    Eclipsegithub: pmd/pmd-eclipsePhilippe Herlin
    qa-Eclipseqa-EclipseChristian Wulf
    eclipse-pmdhttp://acanda.github.io/eclipse-pmd/github: acanda/eclipse-pmdPhilip Graf
    Emacsgithub: pmd/pmd-emacsNascif Abousalh Neto
    Gelgithub: pmd/pmd-misc/pmd-gelAndrei Lumianski
    GradleGradle: The PMD Plugingithub: gradle/gradleGradle.org
    IntelliJ IDEAgithub: amitdev/PMD-IntellijAmit Dev
    IntelliJ IDEA - QAPlughttp://qaplug.com/N/AJakub Sławiński
    JBuildergithub: pmd/pmd-misc/pmd-jbuilderTom Copeland
    JCreatorN/ABrant Gurganus
    JDevelopergithub: pmd/pmd-jdeveloperTorsten Kleiber
    JEditjEdit - PMD Pluginsourceforge: jedit/PMDPluginJiger Patel, Dale Anson
    NetBeansSQEgithub: sqe-team/sqeN/A
    TextPadN/AJeff Epstein
    WebLogic Workshop 8.1.xN/AKevin Conaway
    + +

    General comments

    + +

    A general note - most plugins include the PMD jar files, which has the rulesets +inside it. So even though the rulesets parameter that some plugins +use (i.e., “rulesets/java/unusedcode.xml”) looks like a filesystem reference, it’s really +being used by a getResourceAsStream() call to load it out of the PMD jar files.

    + +

    BlueJ

    + +

    BlueJ is a teaching IDE. To install the PMD extension for BlueJ, download +the PMDExtension jar file +and place it in your bluej/lib/extensions/ directory.

    + +

    Eclipse

    + +

    To install the PMD plugin for Eclipse:

    + +
      +
    • Start Eclipse and open a project
    • +
    • Select “Help”->”Software Updates”->”Find and Install”
    • +
    • Click “Next”, then click “New remote site”
    • +
    • Enter “PMD” into the Name field and https://dl.bintray.com/pmd/pmd-eclipse-plugin/updates/ into the URL field
    • +
    • Click through the rest of the dialog boxes to install the plugin
    • +
    + +

    Alternatively, you can download the latest zip file and follow the above procedures +except for using “New local site” and browsing to the downloaded zip file.

    + +

    To configure PMD, select “Windows”->”Preferences”, then select PMD.

    + +

    To run PMD, right-click on a project node and select “PMD”->”Check code with PMD”.

    + +

    To run the duplicate code detector, right-click on a project node and +select “PMD”->”Find suspect cut and paste”. The report will be placed in a “reports” directory +in a file called “cpd-report.txt”.

    + +

    To find additional help for other features, please read included help by selecting +Help->Help Contents and browse the “How to…” section in the “PMD Plugin Documentation” book.

    + +

    After installing an update, if you get an Exception such as +“java.lang.RuntimeException: Couldn’t find that class xxxxx”, +try deleting the ruleset.xml file in the .metadata/plugins/net.sourceforge.pmd.eclipse directory in your workspace.

    + +

    To get Eclipse to not flag the @SuppressWarnings(“PMD”) annotation, look +under the menu headings Java -> Compiler -> Errors/Warnings -> Annotations -> Unhandled Warning Token.

    + +

    Emacs

    + +

    Integration with GNU Emacs is performed through an ELisp package, pmd.el. +It supports two commands, “pmd-current-buffer” and “pmd-current-dir”. +The output is captured in a compilation buffer which allows the user to “jump” +directly to the source code position associated with the PMD warnings.

    + +

    Gel

    + +

    Here’s how to set up the Gel plugin:

    + +
      +
    • Download the pmd-gel-[version].zip file
    • +
    • Close Gel
    • +
    • Remove any old plugin versions from your gel\plugins directory
    • +
    • Unzip the new zip file into your gel\plugins directory
    • +
    • Start Gel
    • +
    • Go to Tools->Options->Plugin
    • +
    • Select the PMD plugin and click “Remove”
    • +
    • Click “Add” and select “net.sourceforge.pmd.gel.PMDPlugin”
    • +
    • Restart Gel
    • +
    + +

    That’s pretty much it. Now you can open a Java project and click on Plugins->PMD and +a configuration panel will pop up. You can pick which ruleset you want to run and +you can also pick whether you want to run PMD on the current file or on every +source file in your project.

    + +

    IDEA

    + +

    You can use an integrated plugin or just use it as an IDEA “External Tool”.

    + +

    Amit Dev wrote an integrated plugin for IDEA; you can download that +from the IntelliJ plugins site.

    + +

    Here’s how to set it up as an “External Tool”:

    + +
      +
    • Open IDEA and go to File->Settings
    • +
    • Click on the “External Tools” icon
    • +
    • Click on the Add button
    • +
    • Fill in the blocks +
        +
      • Name: PMD
      • +
      • Description: PMD, good for what ails you.
      • +
      • Menu: Select the “Main menu”, “Project views”, “Editor menu”, and “Search results” checkboxes.
      • +
      • Program: c:\pmd\bin\pmd.bat
      • +
      • For the next parameter you’ll need to plug in the location of your PMD installation +and the rulesets you want to use
      • +
      • Parameters: +-d "$FilePath$" -f ideaj -R rulesets/java/quickstart.xml -P sourcePath="$Sourcepath$" -P classAndMethodName=$FileClass$.method -P fileName=$FileName$
      • +
      +
    • +
    + +

    That’s pretty much it. Now you can right click on a source directory and select PMD, +it’ll run recursively on the source files, and the results should +be displayed in a window and hyperlinked into the correct file and line of code. I usually +right-click on the message window title bar and unselect “autohide” so the window doesn’t go +away every time I fix something in the code window.

    + +

    IDEA - QAPlug

    + +

    QAPlug is an Intellij IDEA plugin to manage code quality. It integrates no less than Checkstyle, FindBugs, and PMD.

    + +

    The plugin is available at http://www.qaplug.com/.

    + +

    Also available at the JetBrains site, QAPlug-PMD +and QAPlug.

    + +

    JBuilder

    + +

    To enable this OpenTool in JBuilder:

    + +
      +
    • Download the latest binary release
    • +
    • Unzip it into your jbuilder/lib/ext/ directory
    • +
    • Restart JBuilder
    • +
    + +

    What you can do:

    + +
      +
    • Check a single file by bringing up the context menu from the file tab and selecting PMDCheck
    • +
    • Configure the rulesets that the PMD OpenTool will use by selecting Tools->PMD->Configure PMD
    • +
    • Check all the files in a project by bringing up the context menu for +the project node and selecting PMD Check Project
    • +
    • Locate duplicate code by right clicking on a package and selection “Check with CPD”
    • +
    + +

    When running PMD, the results will be displayed in the MessageView under a tab called PMD Results. If you click on a +violation message within this view, you will be taken to the line in the source code where the violation was detected.

    + +

    Things still to do:

    + +
      +
    • Enable selection of individual rules within a rule set (maybe)
    • +
    • Optional insertion of @todo comments at the point of a violation
    • +
    • Possibly provide configurable ability to limit the number of violations per rule per file
    • +
    + +

    JCreator

    + +
      +
    1. Open Configure > Options
    2. +
    3. Go to the Tools panel
    4. +
    5. Click New > Program
    6. +
    7. Browse for PMD’s pmd.bat
    8. +
    9. Put quotations around the path if it has spaces.
    10. +
    11. Set the initial directory to PMD’s \bin directory
    12. +
    13. Check capture output
    14. +
    15. Put ‘”$[PrjDir]” emacs’ followed by desired rulesets in the arguments
    16. +
    + +

    To run PMD on a project, just pick pmd from the Tools menu.

    + +

    JDeveloper

    + +

    To install the PMD plugin for JDeveloper:

    + +
      +
    • JDeveloper 10.1.2: Download the binary release and unzip it into your jdev/lib/ext directory
    • +
    • JDeveloper 10.1.3 upwards: Click “Help”, click “Check for Updates” +
        +
      • JDeveloper 10.1.3: + +
      • +
      • JDeveloper 11 upwards: Select Update Center: Open Source and Partner Extensions
      • +
      • Press Next and select the actual PMD Plugin and install it
      • +
      +
    • +
    • Restart JDeveloper
    • +
    + +

    To run the PMD plugin for JDeveloper:

    + +
      +
    • Open the Tools-&Preferences menu
    • +
    • Click on the PMD option
    • +
    • Select a couple of rules to try
    • +
    • To run PMD, right click on either a file, folder, package, project or workspace and select PMD via +Toolbar Icon, Context Menu or File Menu
    • +
    • Any rule violations should show up in a LogWindow tab at the bottom of the screen
    • +
    + +

    JEdit

    + +

    The way I use the JEdit plugin is:

    + +
      +
    • Dock the ErrorList by going to Utilities->Global Options->Docking and +putting ErrorList at the bottom of the screen
    • +
    • Open the File Browser if it isn’t already open
    • +
    • Double-click on a source directory
    • +
    • Select Plugins->PMD->Check directory recursively
    • +
    + +

    Note that you can select individual rules by going to Utilities->Global Options->Plugin Options->PMD. +Also, you can change the plugin to prompt you for a directory to check by going to that same menu and +selecting the “Ask for Directory” checkbox.

    + +

    NetBeans

    + +

    The SQE project includes PMD integration for NetBeans.

    + +

    TextPad

    + +

    Assumptions

    + +
      +
    • The Java Development Kit, version 1.4.2 (versions 1.4 and higher are acceptable) is properly installed +into your machine, and exists in D:\java\jdk\_142\. This means that D:\java\jdk\_142\bin\java.exe exists.
    • +
    • PMD version 5.0 exists in D:\java\pmd-bin-\. +This means that D:\java\pmd-bin-\lib\pmd-.jar (among other jar files +in the same directory) exist.
    • +
    + +

    To integrate into TextPad

    + +
      +
    1. In the Configure menu, choose Preferences…. This opens the Preferences dialog
    2. +
    3. In the left pane of the Preferences dialog, choose the Tools branch by clicking on the word “Tools”.
    4. +
    5. On the far right of the dialog, click on the Add button, and then select Program… from the drop-down. +This opens the standard Windows Open File dialog.
    6. +
    7. Type D:\java\jdk_142\bin\java.exe and click the Open button. In the center pane of the Preferences dialog, +an item “Java” has now been added, and is currently selected.
    8. +
    9. Click the word Java, which makes the word editable. Select the entire word, and type “PMD directory”. Press Return.
    10. +
    11. Repeat steps three through five, but type “PMD file”, instead of “PMD directory”.
    12. +
    13. Click Apply.
    14. +
    15. Expand the Tools branch (if not already) by clicking on the ‘+’ directly to its left.
    16. +
    17. In the expanded list, select PMD directory. This changes the right side of this dialog to the “tool” form.
    18. +
    19. In the “tool” form, enter these parameters: +
        +
      • Parameters: -classpath D:\java\pmd-bin-\lib\pmd-.jar;D:\java\pmd-bin-\lib\asm-3.2.jar;D:\java\pmd-bin-\lib\jaxen-1.1.1.jar net.sourceforge.pmd.PMD -d <i><b>$FileDir</b></i> -f net.sourceforge.pmd.renderers.TextPadRenderer -R E:\directory\my_pmd_ruleset.xml -debug
      • +
      • Initial Folder: $FileDir
      • +
      • Save all documents first: Checked
      • +
      • Capture output: Checked
      • +
      • All other checkboxes: Unchecked
      • +
      • Regular expression to match output: ^\([^(]+\)(\([0-9]+\),
      • +
      • Registers/File: 1
      • +
      • Registers/Line: 2
      • +
      +
    20. +
    21. In the expanded list, select PMD file.
    22. +
    23. In the “tool” form, enter the same parameters as above, except replace ‘$FileDir’ with ‘$File’, +in the Parameters textbox.
    24. +
    25. To save your work (truly, given a quirk of TextPad), click on OK, which closes the Preferences dialog. +Restart TextPad and re-open the Preferences dialog.
    26. +
    27. Go back to both the “PMD directory” and “PMD file” Tools branches, and replace ‘E:\directory\my_pmd_ruleset.xml’ +with the ruleset of your choice. For example, basic.
    28. +
    29. Go to the Keyboard branch in the left pane (above Tools), which changes the right side to +the “keyboard configuration” form.
    30. +
    31. In the Categories list box, select Tools.
    32. +
    33. In the Command list box, select PMD directory.
    34. +
    35. Put your cursor into the Press new shortcut key, and type your desired key command. +For example Ctrl+Page Up
    36. +
    37. Click Assign.
    38. +
    39. In the Command list box, select PMD file.
    40. +
    41. Put your cursor into the Press new shortcut key, and type your desired key command. +For example Ctrl+Page Down
    42. +
    43. Click Assign.
    44. +
    45. Save your work again: Click on OK, which closes the Preferences dialog, and then restart TextPad.
    46. +
    + +

    To run PMD against a single Java file

    + +
      +
    1. In TextPad, open any Java file.
    2. +
    3. Click Ctrl+Page Down. This opens an empty, read-only text document (titled “Command Results”). +When PMD completes its analysis, this document will be populated with a listing of violated rules +(or “Command completed successfully” indicating no violations).
    4. +
    5. Double click any line to go to it.
    6. +
    + +

    To run PMD against a directory of Java files

    + +
      +
    1. In TextPad, open any file in the root directory you wish to analyze. Unfortunately, you’ll need to +create a dummy file, if no file exists there.
    2. +
    3. Click Ctrl+Page Up. This opens an empty, read-only text document (titled “Command Results”). +When PMD completes its analysis, this document will be populated with a listing of violated rules +(or “Command completed successfully” indicating no violations).
    4. +
    5. Double click any line to go to it.
    6. +
    + +

    Because directory analysis may take a while, you may choose to cancel this operation. Do so by closing +the (blank Command Results) document, and then confirming that, “yes, I do really want to exit the tool”.

    + +

    WebLogic Workshop 8.1.x

    + +

    Please see the WebLogic Workshop plugin project home page for more information.

    + + +
    + + Tags: + + + + userdocs + + + + tools + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_tools_ant.html b/pmd_userdocs_tools_ant.html new file mode 100644 index 0000000000..fd5662f86e --- /dev/null +++ b/pmd_userdocs_tools_ant.html @@ -0,0 +1,1878 @@ + + + + + + + + +Ant Task Usage | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Ant Task Usage

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    PMD

    + +

    Description

    + +

    Runs a set of static code analysis rules on some source code files and generates a list of problems found.

    + +

    Installation

    + +

    Before you can use the pmd task in your ant build.xml file, you need to install PMD and its libraries into +ant’s classpath, as described in Optional Tasks.

    + +

    First you need to download PMD’s binary distribution zip file. +Then you can either copy all “*.jar” files from PMD’s lib folder into one of ANT’s library folders +(ANT_HOME/lib, ${user.home}/.ant/lib) or using the -lib command line parameter.

    + +

    However, the preferred way is to define a <classpath> for pmd itself and use this classpath when +adding the PMD Task. Assuming, you have extracted the PMD zip file to /home/joe/pmd-bin-6.30.0-SNAPSHOT, +then you can make use of the PMD Task like this:

    + +
    <taskdef name="pmd" classname="net.sourceforge.pmd.ant.PMDTask">
    +    <classpath>
    +        <fileset dir="/home/joe/pmd-bin-6.30.0-SNAPSHOT/lib">
    +            <include name="*.jar"/>
    +        </fileset>
    +    </classpath>
    +</taskdef>
    +
    + +

    Alternatively, a path can be defined and used via classpathref:

    + +
    <path id="pmd.classpath">
    +    <fileset dir="/home/joe/pmd-bin-6.30.0-SNAPSHOT/lib">
    +        <include name="*.jar"/>
    +    </fileset>
    +</path>
    +<taskdef name="pmd" classname="net.sourceforge.pmd.ant.PMDTask" classpathref="pmd.classpath" />
    +
    + +

    The examples below won’t repeat this taskdef element, as this is always required.

    + +

    Parameters

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    AttributeDescriptionRequired
    rulesetfiles + A comma delimited list of ruleset files ('rulesets/java/quickstart.xml,config/my-ruleset.xml'). + If you write your own ruleset files, you can put them on the classpath and plug them in here. + Yes, unless the ruleset nested element is used
    failonerrorWhether or not to fail the build if any errors occur while processing the filesNo
    failOnRuleViolationWhether or not to fail the build if PMD finds any problemsNo
    minimumPriorityThe rule priority threshold; rules with lower priority than they will not be usedNo
    shortFilenamesPlaces truncated filenames in the report. This can reduce your report file size by 15%-20%.No
    failuresPropertyNameA property name to plug the number of rule violations into when the task finishesNo
    encodingThe character set encoding (e.g. UTF-8) to use when reading the source code filesNo
    suppressMarkerThe series of characters to use to tell PMD to skip lines - the default is NOPMD.No
    maxRuleViolations + Whether or not to fail the build if PMD finds more than the value of this attribute. + Note that setting this attribute does not require to set the failOnRuleViolation to true. + No
    cacheLocation + The location of the analysis cache file to be used. + Setting this property enables Incremental Analysis, which can greatly improve analysis time without loosing analysis quality. + Its use is strongly recommended. + No
    noCache + Setting this property to true disables Incremental Analysis, even if cacheLocation is provided. + You can use this to explicitly turn off suggestions to use incremental analysis, or for testing purposes. + No
    + +

    formatter nested element - specifies the format of and the files to which the report is written. You can +configure multiple formatters.

    + + + + + + + + + + + + + + + + + + + + + + +
    NameValues
    typexml,ideaj,textcolor,text,textpad,emacs,csv,html,xslt,yahtml,summaryhtml,vbhtml,codeclimate
    showSuppressedWhether to show suppressed warnings; "false" is the default.
    toFileA filename to which to write the report
    toConsoleWhether to output the report to the console; "false" is the default.
    +

    The formatter element can contain nested param elements to configure the formatter in detail, e.g.

    +
    +
    encoding
    +
    Specifies the encoding to be used in the generated report (only honored when used with `toFile`). When rendering `toConsole` PMD will automatically detect the terminal's encoding and use it, unless the output is being redirected / piped, in which case `file.encoding` is used. See example below.
    +
    linkPrefix
    +
    Used for linking to online HTMLized source (like this). See example below. Note, this only works with + maven-jxr-plugin.
    +
    linePrefix
    +
    Used for linking to online HTMLized source (like this). See example below. Note, this only works with maven-jxr-plugin.
    +
    +
    + +

    classpath nested element - useful for specifying custom rules. More details on the classpath +element are in the Ant documentation for path-like structures and there’s +an example below.

    + +

    auxclasspath nested element - extra classpath used for type resolution. Some rules make use of type resolution +in order to avoid false positives. The auxclasspath is configured also with path-like structures. It should contain the compiled classes of the project that is being analyzed and all the compile time +dependencies.

    + +

    sourceLanguage nested element - specify which language (Java, Ecmascript, XML,…) +and the associated version (1.5, 1.6,…). This element is optional. The language is determined by file extension +automatically and the latest language version is used.

    + +

    ruleset nested element - another way to specify rulesets. You can specify multiple elements. Here’s an example:

    + +
    <target name="pmd">
    +    <taskdef name="pmd" classname="net.sourceforge.pmd.ant.PMDTask"/>
    +    <pmd shortFilenames="true">
    +        <ruleset>rulesets/java/quickstart.xml</ruleset>
    +        <ruleset>config/my-ruleset.xml</ruleset>
    +        <fileset dir="/usr/local/j2sdk1.4.1_01/src/">
    +            <include name="java/lang/*.java"/>
    +        </fileset>
    +    </pmd>
    +</target>
    +
    + +

    fileset nested element - specify the actual java source files, that PMD should analyze. You can use multiple +fileset elements. See FileSet for the syntax and usage.

    + +

    Language version selection

    + +

    PMD selects the language automatically using the file extension. If multiple versions of a language are +supported, PMD uses the latest version as default. This is currently the case for Java only, which has +support for multiple versions.

    + +

    If a languages supports multiple versions, you can select a specific version here, so that e.g. rules, that only apply +to specific versions, are not executed. E.g. the rule UseTryWithResources only makes +sense with Java 1.7 and later. If your project uses Java 1.5, then you should configure the sourceLanguage +accordingly and this rule won’t be executed.

    + +

    The specific version of a language to be used is selected via the sourceLanguage +nested element. Possible values are:

    + +
    <sourceLanguage name="apex" version="48"/>
    +<sourceLanguage name="ecmascript" version="3"/>
    +<sourceLanguage name="java" version="1.3"/>
    +<sourceLanguage name="java" version="1.4"/>
    +<sourceLanguage name="java" version="1.5"/>
    +<sourceLanguage name="java" version="5"/> <!-- alias for 1.5 -->
    +<sourceLanguage name="java" version="1.6"/>
    +<sourceLanguage name="java" version="6"/> <!-- alias for 1.6 -->
    +<sourceLanguage name="java" version="1.7"/>
    +<sourceLanguage name="java" version="7"/> <!-- alias for 1.7 -->
    +<sourceLanguage name="java" version="1.8"/>
    +<sourceLanguage name="java" version="8"/> <!-- alias for 1.8 -->
    +<sourceLanguage name="java" version="9"/>
    +<sourceLanguage name="java" version="1.9"/> <!-- alias for 9 -->
    +<sourceLanguage name="java" version="10"/>
    +<sourceLanguage name="java" version="1.10"/> <!-- alias for 10 -->
    +<sourceLanguage name="java" version="11"/>
    +<sourceLanguage name="java" version="12"/>
    +<sourceLanguage name="java" version="13"/>
    +<sourceLanguage name="java" version="13-preview"/>
    +<sourceLanguage name="java" version="14"/> <!-- this is the default -->
    +<sourceLanguage name="java" version="14-preview"/>
    +<sourceLanguage name="jsp" version=""/>
    +<sourceLanguage name="modelica" version=""/>
    +<sourceLanguage name="pom" version=""/>
    +<sourceLanguage name="plsql" version=""/>
    +<sourceLanguage name="scala" version="2.10"/>
    +<sourceLanguage name="scala" version="2.11"/>
    +<sourceLanguage name="scala" version="2.12"/>
    +<sourceLanguage name="scala" version="2.13"/> <!-- this is the default -->
    +<sourceLanguage name="vf" version=""/>
    +<sourceLanguage name="vm" version=""/>
    +<sourceLanguage name="wsdl" version=""/>
    +<sourceLanguage name="xml" version=""/>
    +<sourceLanguage name="xsl" version=""/>
    +
    + +

    Postprocessing the report file with XSLT

    + +

    Several folks (most recently, Wouter Zelle) have written XSLT scripts +which you can use to transform the XML report into nifty HTML. To do this, +make sure you use the XML formatter in the PMD task invocation, i.e.:

    + +
    <formatter type="xml" toFile="${tempbuild}/report_pmd.xml">
    +    <param name="encoding" value="UTF-8" /> <!-- enforce UTF-8 encoding for the XML -->
    +</formatter>
    +
    + +

    Then, after the end of the PMD task, do this:

    + +
    <xslt in="${tempbuild}/report_pmd.xml" style="${pmdConfig}/wz-pmd-report.xslt" out="${pmdOutput}/report_pmd.html" />
    +
    + +

    Examples

    + +

    One ruleset

    + +

    Running one ruleset to produce a HTML report (and printing the report to the console as well) using a file cache

    + +
    <target name="pmd">
    +    <pmd rulesetfiles="rulesets/java/quickstart.xml" cacheLocation="build/pmd/pmd.cache">
    +        <formatter type="html" toFile="pmd_report.html" toConsole="true"/>
    +        <fileset dir="C:\j2sdk1.4.1_01\src\java\lang\">
    +            <include name="**/*.java"/>
    +        </fileset>
    +    </pmd>
    +</target>
    +
    + +

    Multiple rulesets

    + +

    Running multiple rulesets to produce an XML report with the same analysis cache

    + +
    <target name="pmd">
    +    <pmd rulesetfiles="rulesets/java/quickstart.xml,config/my-ruleset.xml" cacheLocation="build/pmd/pmd.cache">
    +        <formatter type="xml" toFile="c:\pmd_report.xml"/>
    +        <fileset dir="C:\j2sdk1.4.1_01\src\java\lang\">
    +            <include name="**/*.java"/>
    +        </fileset>
    +    </pmd>
    +</target>
    +
    + +

    Custom renderer

    + +

    Using a custom renderer. For this to work, you need to add you custom renderer to the classpath of PMD. This +need to be configured when defining the task:

    + +
    <path id="pmd.classpath">
    +    <fileset dir="/home/joe/pmd-bin-6.30.0-SNAPSHOT/lib">
    +        <include name="*.jar"/>
    +    </fileset>
    +    <!-- the custom renderer is expected to be in /home/joe/pmd-addons/com/company/MyRenderer.class -->
    +    <pathelement location="/home/joe/pmd-addons" />
    +</path>
    +<taskdef name="pmd" classname="net.sourceforge.pmd.ant.PMDTask" classpathref="pmd.classpath" />
    +
    +<target name="pmd">
    +    <pmd rulesetfiles="rulesets/java/quickstart.xml">
    +        <formatter type="com.mycompany.MyRenderer" toFile="foo.html"/>
    +        <fileset dir="/path/to/java/src">
    +            <include name="**/*.java"/>
    +        </fileset>
    +    </pmd>
    +</target>
    +
    + +

    Full example with auxclasspath

    + +

    Full build file example using the correct auxclasspath configuration. +Your project needs to be compiled first which happens in the target “compile”:

    + +
    <project name="MyProject" default="pmd" basedir=".">
    +    <property name="src" location="src"/>
    +    <property name="build" location="build"/>
    +    <path id="project.dependencies">
    +        <pathelement location="lib/third-party.jar"/>
    +        <pathelement location="lib/xyz.jar"/>
    +    </path>
    +    <path id="pmd.classpath">
    +        <fileset dir="/home/joe/pmd-bin-6.30.0-SNAPSHOT/lib">
    +            <include name="*.jar"/>
    +        </fileset>
    +    </path>
    +    <taskdef name="pmd" classname="net.sourceforge.pmd.ant.PMDTask" classpathref="pmd.classpath" />
    +    
    +    <target name="init">
    +        <mkdir dir="${build}"/>
    +    </target>
    +    
    +    <target name="compile" depends="init">
    +        <javac srcdir="${src}" destdir="${build}" classpathref="project.dependencies"
    +            source="1.8" target="1.8" />
    +    </target>
    +    
    +    <target name="pmd" depends="compile">
    +        <pmd cacheLocation="${build}/pmd.cache">
    +            <auxclasspath>
    +                <pathelement location="${build}"/>
    +                <path refid="project.dependencies"/>
    +            </auxclasspath>
    +            <ruleset>rulesets/java/quickstart.xml</ruleset>
    +            <formatter type="html" toFile="${build}/pmd_report.html"/>
    +            <sourceLanguage name="java" version="1.8"/>
    +            <fileset dir="${src}">
    +                <include name="**/*.java"/>
    +            </fileset>
    +        </pmd>
    +    </target>
    +    
    +    <target name="clean">
    +        <delete dir="${build}"/>
    +    </target>
    +</project>
    +
    + +

    You can run pmd then with ant pmd.

    + +

    Getting verbose output

    + +
    [tom@hal bin]$ ant -v pmd
    +Apache Ant version 1.6.2 compiled on July 16 2004
    +Buildfile: build.xml
    +Detected Java version: 1.4 in: /usr/local/j2sdk1.4.2_03/jre
    +Detected OS: Linux
    +parsing buildfile build.xml with URI = file:/home/tom/data/pmd/pmd/bin/build.xml
    +Project base dir set to: /home/tom/data/pmd/pmd
    +Build sequence for target `pmd' is [pmd]
    +Complete build sequence is [pmd, copy, cppjavacc, cpd, delete,
    + compile, clean, jar, dist, cpdjnlp, jjtree, javadoc, test, tomserver]
    +
    +pmd:
    +      [pmd] Using the normal ClassLoader
    +      [pmd] Using these rulesets: rulesets/java/quickstart.xml
    +      [pmd] Using rule AvoidMessageDigestField
    +      [pmd] Using rule AvoidStringBufferField
    +      [pmd] Using rule AvoidUsingHardCodedIP
    +      [pmd] Using rule CheckResultSet
    +      [pmd] Using rule ConstantsInInterface
    +      ...
    +      [pmd] Processing file /usr/local/java/src/java/lang/ref/Finalizer.java
    +      [pmd] Processing file /usr/local/java/src/java/lang/ref/FinalReference.java
    +      [pmd] Processing file /usr/local/java/src/java/lang/ref/PhantomReference.java
    +      [pmd] Processing file /usr/local/java/src/java/lang/ref/Reference.java
    +      [pmd] Processing file /usr/local/java/src/java/lang/ref/ReferenceQueue.java
    +      [pmd] Processing file /usr/local/java/src/java/lang/ref/SoftReference.java
    +      [pmd] Processing file /usr/local/java/src/java/lang/ref/WeakReference.java
    +      [pmd] 0 problems found
    +
    +BUILD SUCCESSFUL
    +Total time: 2 seconds
    +[tom@hal bin]$
    +
    + +

    HTML report with linkPrefix

    + +

    An HTML report with the “linkPrefix” and “linePrefix” properties:

    + +
    <target name="pmd">
    +    <taskdef name="pmd" classname="net.sourceforge.pmd.ant.PMDTask"/>
    +    <pmd rulesetfiles="rulesets/java/quickstart.xml" shortFilenames="true">
    +        <formatter type="html" toFile="pmd_report.html">
    +            <param name="linkPrefix" value="https://maven.apache.org/plugins/maven-pmd-plugin/xref/"/>
    +            <param name="linePrefix" value="L"/>
    +        </formatter>
    +        <fileset dir="/usr/local/j2sdk1.4.1_01/src/">
    +            <include name="java/lang/*.java"/>
    +        </fileset>
    +    </pmd>
    +</target>
    +
    + +

    Memory Usage

    + +

    Memory usage has been reduced significantly starting with the PMD 4.0 release. +When testing all Java rules on the jdk 1.6 source code (about 7000 classes), +the allocated heap space does not go over 60M.

    + +

    However, on very large projects, the Ant task may still fail with a OutOfMemoryError. +To prevent this from happening, increase the maximum memory usable by ant using the ANT_OPTS variable +(adjust the size according to your available memory):

    + +

    On Windows:

    + +
    set ANT_OPTS=-Xmx1024m -Xms512m
    +
    + +

    On Linux

    + +
    export ANT_OPTS="-Xmx1024m -Xms512m"
    +
    + + +
    + + Tags: + + + + userdocs + + + + tools + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_tools_ci.html b/pmd_userdocs_tools_ci.html new file mode 100644 index 0000000000..f902becbb7 --- /dev/null +++ b/pmd_userdocs_tools_ci.html @@ -0,0 +1,1465 @@ + + + + + + + + +Continuous Integrations plugins | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Continuous Integrations plugins

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Introduction

    + +

    PMD can be integrate through some of the Continuous Integration tools that exist now. +Here is a list of known (to us) plugin to do so.

    + +

    Hudson Plugin

    + +

    Hafner Ullrich has developed a PMD plugin for Hudson. +Please check the plugin homepage for more info.

    + +

    Continuum

    + +

    Continuum does not have a plugin for PMD per see, but can failed the build according to the +result of the PMD maven plugin.

    + + + + +
    + + Tags: + + + + userdocs + + + + tools + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_tools_gradle.html b/pmd_userdocs_tools_gradle.html new file mode 100644 index 0000000000..f935097745 --- /dev/null +++ b/pmd_userdocs_tools_gradle.html @@ -0,0 +1,1508 @@ + + + + + + + + +Gradle | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Gradle

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The Gradle Build Tool provides a PMD Plugin +that can be added to your build configuration. Technically it is based on the Ant Task.

    + +

    Example

    + +

    In your build.gradle add the following:

    + +
    plugins {
    +    id 'pmd'
    +}
    +
    + +

    Custom ruleset

    + +

    Configuration of a custom ruleset looks like this:

    + +
    pmd {
    +    ruleSetFiles = files("custom-pmd-ruleset.xml")
    +    ruleSets = []
    +}
    +
    + +

    Note: The ruleSets array is explicitly set to empty to avoid using the default configuration.

    + +

    Fail the build

    + +

    If you want to fail the build for pmd violations, you need to set ignoreFailures:

    + +
    pmd {
    +    ignoreFailures = false
    +}
    +
    + +

    More configuration options are documented on PMD Extension.

    + +

    Upgrade PMD version

    + +

    If you want to use a newer PMD version than the default one provided with gradle, you can do so +with the property toolVersion:

    + +
    pmd {
    +    toolVersion = "6.21.0"
    +}
    +
    + +

    References

    + +

    Source code for Gradles PMD Plugin is available here:

    + + + + +
    + + Tags: + + + + userdocs + + + + tools + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_tools_java_api.html b/pmd_userdocs_tools_java_api.html new file mode 100644 index 0000000000..19bb4e83c1 --- /dev/null +++ b/pmd_userdocs_tools_java_api.html @@ -0,0 +1,1724 @@ + + + + + + + + +PMD Java API | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    PMD Java API

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The easiest way to run PMD is to just use a build plugin in your favorite build tool +like Apache Ant, Apache Maven or +Gradle.

    + +

    There are also many integrations for IDEs available, see Tools.

    + +

    If you have your own build tool or want to integrate PMD in a different way, you can call PMD programmatically, +as described here.

    + +

    Dependencies

    + +

    You’ll need to add the dependency to the language, you want to analyze. For Java, it will be +net.sourceforge.pmd:pmd-java. If you use Maven, you can add a new (compile time) dependency like this:

    + +
    <dependency>
    +    <groupId>net.sourceforge.pmd</groupId>
    +    <artifactId>pmd-java</artifactId>
    +    <version>${pmdVersion}</version>
    +</dependency>
    +
    + +

    Note: You’ll need to select a specific version. This is done in the example via the property pmdVersion.

    + +

    This will transitively pull in the artifact pmd-core which contains the API.

    + +

    Command line interface

    + +

    The easiest way is to call PMD with the same interface as from command line. The main class is +net.sourceforge.pmd.PMD:

    + +
    import net.sourceforge.pmd.PMD;
    +
    +public class Example {
    +    public static void main(String[] args) {
    +        String[] pmdArgs = {
    +            "-d", "/home/workspace/src/main/java/code",
    +            "-R", "rulesets/java/quickstart.xml",
    +            "-f", "xml",
    +            "-r", "/home/workspace/pmd-report.xml"
    +        };
    +        PMD.main(pmdArgs);
    +    }
    +}
    +
    + +

    It uses the same options as described in PMD CLI reference.

    + +

    Programmatically, variant 1

    + +

    This is very similar:

    + +
    import net.sourceforge.pmd.PMD;
    +import net.sourceforge.pmd.PMDConfiguration;
    +
    +public class PmdExample {
    +
    +    public static void main(String[] args) {
    +        PMDConfiguration configuration = new PMDConfiguration();
    +        configuration.setInputPaths("/home/workspace/src/main/java/code");
    +        configuration.setRuleSets("rulesets/java/quickstart.xml");
    +        configuration.setReportFormat("xml");
    +        configuration.setReportFile("/home/workspace/pmd-report.xml");
    +
    +        PMD.doPMD(configuration);
    +    }
    +}
    +
    + +

    Programmatically, variant 2

    + +

    This gives you more control over which files are processed, but is also more complicated. +You can also provide your own listeners and renderers.

    + +
      +
    1. +

      First we create a PMDConfiguration. This is currently the only way to specify a ruleset:

      + +
      PMDConfiguration configuration = new PMDConfiguration();
      +configuration.setMinimumPriority(RulePriority.MEDIUM);
      +configuration.setRuleSets("rulesets/java/quickstart.xml");
      +
      +
    2. +
    3. +

      In order to support type resolution, PMD needs to have access to the compiled classes and dependencies +as well. This is called “auxclasspath” and is also configured here. +Note: you can specify multiple class paths separated by : on Unix-systems or ; under Windows.

      + +
      configuration.prependClasspath("/home/workspace/target/classes:/home/.m2/repository/my/dependency.jar");
      +
      +
    4. +
    5. +

      Then we need a ruleset factory. This is created using the configuration, taking the minimum priority into +account:

      + +
      RuleSetFactory ruleSetFactory = RulesetsFactoryUtils.createFactory(configuration);
      +
      +
    6. +
    7. +

      PMD operates on a list of DataSource. You can assemble a own list of FileDataSource, e.g.

      + +
      List<DataSource> files = Arrays.asList(new FileDataSource(new File("/path/to/src/MyClass.java")));
      +
      +
    8. +
    9. +

      For reporting, you can use a built-in renderer, e.g. XMLRenderer. Note, that you must manually initialize +the renderer by setting a suitable Writer and calling start(). After the PMD run, you need to call +end() and flush(). Then your writer should have received all output.

      + +
      StringWriter rendererOutput = new StringWriter();
      +Renderer xmlRenderer = new XMLRenderer("UTF-8");
      +xmlRenderer.setWriter(rendererOutput);
      +xmlRenderer.start();
      +
      +
    10. +
    11. +

      Create a RuleContext. This is the context instance, that is available then in the rule implementations. +Note: when running in multi-threaded mode (which is the default), the rule context instance is cloned for +each thread.

      + +
      RuleContext ctx = new RuleContext();
      +
      +
    12. +
    13. +

      Optionally register a report listener. This allows you to react immediately on found violations. You could also +use such a listener to implement your own renderer. The listener must implement the interface +ThreadSafeReportListener and can be registered via ctx.getReport().addListener(...).

      + +
      ctx.getReport().addListener(new ThreadSafeReportListener() {
      +    public void ruleViolationAdded(RuleViolation ruleViolation) {
      +    }
      +    public void metricAdded(Metric metric) {
      +    }
      +
      +
    14. +
    15. +

      Now, all the preparations are done, and PMD can be executed. This is done by calling +PMD.processFiles(...). This method call takes the configuration, the ruleset factory, the files +to process, the rule context and the list of renderers. Provide an empty list, if you don’t want to use +any renderer. Note: The auxclasspath needs to be closed explicitly. Otherwise the class or jar files may +remain open and file resources are leaked.

      + +
      try {
      +    PMD.processFiles(configuration, ruleSetFactory, files, ctx,
      +            Collections.singletonList(renderer));
      +} finally {
      +    ClassLoader auxiliaryClassLoader = configuration.getClassLoader();
      +    if (auxiliaryClassLoader instanceof ClasspathClassLoader) {
      +        ((ClasspathClassLoader) auxiliaryClassLoader).close();
      +    }
      +}
      +
      +
    16. +
    17. +

      After the call, you need to finish the renderer via end() and flush(). +Then you can check the rendered output.

      + +
      renderer.end();
      +renderer.flush();
      +System.out.println("Rendered Report:");
      +System.out.println(rendererOutput.toString());
      +
      +
    18. +
    + +

    Here is a complete example:

    + +
    import java.io.IOException;
    +import java.io.StringWriter;
    +import java.io.Writer;
    +import java.nio.file.FileSystems;
    +import java.nio.file.FileVisitResult;
    +import java.nio.file.Files;
    +import java.nio.file.Path;
    +import java.nio.file.PathMatcher;
    +import java.nio.file.SimpleFileVisitor;
    +import java.nio.file.attribute.BasicFileAttributes;
    +import java.util.ArrayList;
    +import java.util.Collections;
    +import java.util.List;
    +
    +import net.sourceforge.pmd.PMD;
    +import net.sourceforge.pmd.PMDConfiguration;
    +import net.sourceforge.pmd.RuleContext;
    +import net.sourceforge.pmd.RulePriority;
    +import net.sourceforge.pmd.RuleSetFactory;
    +import net.sourceforge.pmd.RuleViolation;
    +import net.sourceforge.pmd.RulesetsFactoryUtils;
    +import net.sourceforge.pmd.ThreadSafeReportListener;
    +import net.sourceforge.pmd.renderers.Renderer;
    +import net.sourceforge.pmd.renderers.XMLRenderer;
    +import net.sourceforge.pmd.stat.Metric;
    +import net.sourceforge.pmd.util.ClasspathClassLoader;
    +import net.sourceforge.pmd.util.datasource.DataSource;
    +import net.sourceforge.pmd.util.datasource.FileDataSource;
    +
    +public class PmdExample2 {
    +
    +    public static void main(String[] args) throws IOException {
    +        PMDConfiguration configuration = new PMDConfiguration();
    +        configuration.setMinimumPriority(RulePriority.MEDIUM);
    +        configuration.setRuleSets("rulesets/java/quickstart.xml");
    +        configuration.prependClasspath("/home/workspace/target/classes");
    +        RuleSetFactory ruleSetFactory = RulesetsFactoryUtils.createFactory(configuration);
    +
    +        List<DataSource> files = determineFiles("/home/workspace/src/main/java/code");
    +
    +        Writer rendererOutput = new StringWriter();
    +        Renderer renderer = createRenderer(rendererOutput);
    +        renderer.start();
    +
    +        RuleContext ctx = new RuleContext();
    +
    +        ctx.getReport().addListener(createReportListener()); // alternative way to collect violations
    +
    +        try {
    +            PMD.processFiles(configuration, ruleSetFactory, files, ctx,
    +                Collections.singletonList(renderer));
    +        } finally {
    +            ClassLoader auxiliaryClassLoader = configuration.getClassLoader();
    +            if (auxiliaryClassLoader instanceof ClasspathClassLoader) {
    +                ((ClasspathClassLoader) auxiliaryClassLoader).close();
    +            }
    +        }
    +
    +        renderer.end();
    +        renderer.flush();
    +        System.out.println("Rendered Report:");
    +        System.out.println(rendererOutput.toString());
    +    }
    +
    +    private static ThreadSafeReportListener createReportListener() {
    +        return new ThreadSafeReportListener() {
    +            @Override
    +            public void ruleViolationAdded(RuleViolation ruleViolation) {
    +                System.out.printf("%-20s:%d %s%n", ruleViolation.getFilename(),
    +                        ruleViolation.getBeginLine(), ruleViolation.getDescription());
    +            }
    +
    +            @Override
    +            public void metricAdded(Metric metric) {
    +                // ignored
    +            }
    +        };
    +    }
    +
    +    private static Renderer createRenderer(Writer writer) {
    +        XMLRenderer xml = new XMLRenderer("UTF-8");
    +        xml.setWriter(writer);
    +        return xml;
    +    }
    +
    +    private static List<DataSource> determineFiles(String basePath) throws IOException {
    +        Path dirPath = FileSystems.getDefault().getPath(basePath);
    +        PathMatcher matcher = FileSystems.getDefault().getPathMatcher("glob:*.java");
    +
    +        List<DataSource> files = new ArrayList<>();
    +
    +        Files.walkFileTree(dirPath, new SimpleFileVisitor<Path>() {
    +            @Override
    +            public FileVisitResult visitFile(Path path, BasicFileAttributes attrs) throws IOException {
    +                if (matcher.matches(path.getFileName())) {
    +                    System.out.printf("Using %s%n", path);
    +                    files.add(new FileDataSource(path.toFile()));
    +                } else {
    +                    System.out.printf("Ignoring %s%n", path);
    +                }
    +                return super.visitFile(path, attrs);
    +            }
    +        });
    +        System.out.printf("Analyzing %d files in %s%n", files.size(), basePath);
    +        return files;
    +    }
    +}
    +
    + + + +
    + + Tags: + + + + userdocs + + + + tools + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/pmd_userdocs_tools_maven.html b/pmd_userdocs_tools_maven.html new file mode 100644 index 0000000000..2515f8db93 --- /dev/null +++ b/pmd_userdocs_tools_maven.html @@ -0,0 +1,1723 @@ + + + + + + + + +Maven PMD Plugin | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Maven PMD Plugin

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    Maven 2 and 3

    + +

    Running the pmd plugin

    + +

    Choosing the plugin version

    + +

    When adding the maven-pmd-plugin to your pom.xml, you need to select a version. To figure out the +latest available version, have a look at the official maven-pmd-plugin documentation.

    + +

    As of March 2020, the current plugin version is 3.13.0.

    + +

    The version of the plugin should be specified in <build><pluginManagement/></build> and if using the project +report additionally in <reporting><plugins/></reporting> elements. Here’s an example for the pluginManagement +section:

    + +
        <build>
    +        <pluginManagement>
    +            <plugins>
    +                <plugin>
    +                    <groupId>org.apache.maven.plugins</groupId>
    +                    <artifactId>maven-pmd-plugin</artifactId>
    +                    <version>3.13.0</version>
    +                </plugin>
    +            </plugins>
    +        </pluginManagement>
    +    </build>
    +
    + +

    When defining the version in the pluginManagment section, then it doesn’t need to be specified in the normal plugins +section. However, it should additionally be specified in the reporting section.

    + +

    More information, see Guide to Configuring Plugin-ins.

    + +

    Generating a project report

    + +

    To include the PMD report in the project reports section add the following lines under +the reports element in your pom.xml:

    + +
    <project>
    +    ...
    +    <reporting>
    +        <plugins>
    +            <plugin>
    +                <groupId>org.apache.maven.plugins</groupId>
    +                <artifactId>maven-pmd-plugin</artifactId>
    +                <version>3.13.0</version>
    +            </plugin>
    +        </plugins>
    +    </reporting>
    +    ...
    +</project>
    +
    + +

    This will add an entry to the ‘project reports’ section with the PMD report when you build the maven site.

    + +

    Executing PMD manually

    + +

    To run PMD on a Maven project without adding it as a report, simply run

    + +
    mvn pmd:pmd
    +
    + +

    The PMD plugin writes the report in XML which will then be formatted into more readable HTML.

    + +

    Integrated into the build process

    + +

    You can also run PMD automatically when building your project. You even let the build fail, if +PMD finds some violations. Therefore the check goal is used:

    + +
    <project>
    +  ...
    +  <build>
    +    <plugins>
    +      <plugin>
    +        <groupId>org.apache.maven.plugins</groupId>
    +        <artifactId>maven-pmd-plugin</artifactId>
    +        <version>3.13.0</version> <!-- or use version from pluginManagement -->
    +        <configuration>
    +            <!-- failOnViolation is actually true by default, but can be disabled -->
    +            <failOnViolation>true</failOnViolation>
    +            <!-- printFailingErrors is pretty useful -->
    +            <printFailingErrors>true</printFailingErrors>
    +        </configuration>
    +        <executions>
    +          <execution>
    +            <goals>
    +              <goal>check</goal>
    +            </goals>
    +          </execution>
    +        </executions>
    +      </plugin>
    +    </plugins>
    +  </build>
    +  ...
    +</project>
    +
    + +

    This will run PMD automatically during the verify phase of the build. You can additionally run CPD, if +you add cpd-check as a goal.

    + +

    Customization

    + +

    Changing rulesets

    + +

    To specify a ruleset, simply edit the previous configuration:

    + +
        <reporting>
    +        <plugins>
    +            <plugin>
    +                <groupId>org.apache.maven.plugins</groupId>
    +                <artifactId>maven-pmd-plugin</artifactId>
    +                <version>3.13.0</version>
    +                <configuration>
    +                    <rulesets>
    +                        <ruleset>/rulesets/java/quickstart.xml</ruleset>
    +                        <ruleset>d:\rulesets\my-ruleset.xml</ruleset>
    +                        <ruleset>http://localhost/design.xml</ruleset>
    +                    </rulesets>
    +                </configuration>
    +            </plugin>
    +        </plugins>
    +    </reporting>
    +
    + +

    The value of the ‘ruleset’ element can either be a relative address, an absolute address or even an url.

    + +

    A clean strategy for customizing which rules to use for a project is to write a ruleset file. +In this file you can define which rules to use, add custom rules, and +customizing which rules to include/exclude from official rulesets. More information on +writing a ruleset can be found here. +Note that if you include other rulesets in your own rulesets, you have to be sure that the plugin +will be able to resolve those other ruleset references.

    + +

    Enabling Incremental Analysis

    + +

    When using the Maven PMD plugin 3.8 or later along with PMD 5.6.0 or later, you can enable incremental analysis to +speed up PMD’s execution while retaining the quality of the analysis. You can additionally customize where the cache is stored::

    + +
        <plugin>
    +        <groupId>org.apache.maven.plugins</groupId>
    +        <artifactId>maven-pmd-plugin</artifactId>
    +        <version>3.13.0</version> <!-- or use version from pluginManagement -->
    +        <configuration>
    +            <!-- enable incremental analysis -->
    +            <analysisCache>true</analysisCache>
    +            <!-- analysisCacheLocation: optional - points to the following location by default -->
    +            <analysisCacheLocation>${project.build.directory}/pmd/pmd.cache</analysisCacheLocation>
    +        </configuration>
    +    </plugin>
    +
    + +

    Other configurations

    + +

    The Maven PMD plugin allows you to configure CPD, targetJDK, and the use of XRef to link +the report to html source files, and the file encoding:

    + +
        <plugin>
    +        <groupId>org.apache.maven.plugins</groupId>
    +        <artifactId>maven-pmd-plugin</artifactId>
    +        <version>3.13.0</version> <!-- or use version from pluginManagement -->
    +        <configuration>
    +            <linkXRef>true</linkXRef>
    +            <sourceEncoding>ISO-8859-1</sourceEncoding>
    +            <minimumTokens>30</minimumTokens>
    +            <targetJdk>1.4</targetJdk>
    +        </configuration>
    +    </plugin>
    +
    + +

    Upgrading the PMD version at runtime

    + +

    The Maven PMD plugin comes with a specific PMD version, which is documented on the +plugin project page.

    + +

    Given that the newer PMD version is compatible, you can override the PMD version, that the +Maven plugin will use and benefit from the latest bugfixes and enhancements:

    + +
    <project>
    +    <properties>
    +        <pmdVersion>...choose your version...</pmdVersion>
    +    </properties>
    +...
    +    <build>
    +        <pluginManagement>
    +            <plugins>
    +                <plugin>
    +                    <groupId>org.apache.maven.plugins</groupId>
    +                    <artifactId>maven-pmd-plugin</artifactId>
    +                    <version>3.13.0</version>
    +                    <dependencies>
    +                        <dependency>
    +                            <groupId>net.sourceforge.pmd</groupId>
    +                            <artifactId>pmd-core</artifactId>
    +                            <version>${pmdVersion}</version>
    +                        </dependency>
    +                        <dependency>
    +                            <groupId>net.sourceforge.pmd</groupId>
    +                            <artifactId>pmd-java</artifactId>
    +                            <version>${pmdVersion}</version>
    +                        </dependency>
    +                        <dependency>
    +                            <groupId>net.sourceforge.pmd</groupId>
    +                            <artifactId>pmd-javascript</artifactId>
    +                            <version>${pmdVersion}</version>
    +                        </dependency>
    +                        <dependency>
    +                            <groupId>net.sourceforge.pmd</groupId>
    +                            <artifactId>pmd-jsp</artifactId>
    +                            <version>${pmdVersion}</version>
    +                        </dependency>
    +                    </dependencies>
    +                </plugin>
    +            </plugins>
    +        </pluginManagement>
    +    </build>
    +...
    +</project>
    +
    + +

    Reference

    + +

    For more information, please see the well documented PMD plugin project page here: +http://maven.apache.org/plugins/maven-pmd-plugin/index.html. +Also, the bug tracker for this plugin is here.

    + +

    Maven 1

    + + + +

    This section is about the maven 1 PMD plugin.

    + +

    Running the pmd plugin

    + +

    Generating a project report

    + +

    To include the PMD report in the project reports section add the following line under +the reports element in your project.xml:

    + +
    <report>maven-pmd-plugin</report>
    +
    + +

    This will add an entry to the ‘project reports’ section with the PMD report.

    + +

    Executing PMD manually

    + +

    To run PMD on a Maven project without adding it as a report, simply run

    + +
    maven pmd xdoc
    +
    + +

    The PMD plugin writes the report in XML which will then be formatted into more readable HTML.

    + +

    Customization

    + +

    Changing rulesets

    + +

    To specify a set of official, built-in rulesets to be used set them in the property +maven.pmd.rulesets. You can include this setting in your project.properties file.

    + +

    A clean strategy for customizing which rules to use for a project is to write a ruleset file. +In this file you can define which rules to use, add custom rules, and +customizing which rules to include/exclude from official rulesets. More information on +writing a ruleset can be found here.

    + +

    Add to the root of your Maven project a pmd.xml file which contains the ruleset mentioned in +the previous paragraph. Add the following property to your project now:

    + +
    maven.pmd.rulesetfiles = ${basedir}/pmd.xml
    +
    + +

    Reference

    + +

    See the PMD plugin project page here: +http://maven.apache.org/maven-1.x/plugins/pmd/

    + + +
    + + Tags: + + + + userdocs + + + + tools + + + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/report-examples/pmd-report-html.html b/report-examples/pmd-report-html.html new file mode 100644 index 0000000000..2c1c41342d --- /dev/null +++ b/report-examples/pmd-report-html.html @@ -0,0 +1,67 @@ +PMD +

    PMD report

    Problems found

    + + + + + + + + + + + + + +
    #FileLineProblem
    1pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java124Logger calls should be surrounded by log level guards.
    2pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java58This for loop can be replaced by a foreach loop

    Processing errors

    + + + + + +
    FileProblem
    pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    net.sourceforge.pmd.PMDException: Error while parsing pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:110)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:89)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:51)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:78)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:24)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1130)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:630)
    +    at java.base/java.lang.Thread.run(Thread.java:832)
    +Caused by: net.sourceforge.pmd.lang.java.ast.ParseException: Encountered " "-" "- "" at line 6, column 30.
    +Was expecting one of:
    +    "extends" ...
    +    "implements" ...
    +    "{" ...
    +    "<" ...
    +    
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.generateParseException(JavaParser.java:12713)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.jj_consume_token(JavaParser.java:12597)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceBody(JavaParser.java:1554)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceDeclaration(JavaParser.java:732)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.TypeDeclaration(JavaParser.java:639)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.CompilationUnit(JavaParser.java:373)
    +    at net.sourceforge.pmd.lang.java.AbstractJavaParser.parse(AbstractJavaParser.java:62)
    +    at net.sourceforge.pmd.SourceCodeProcessor.parse(SourceCodeProcessor.java:121)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSource(SourceCodeProcessor.java:185)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:107)
    +    ... 10 more
    +

    Suppressed warnings

    + + + + + + + + +
    FileLineRuleNOPMD or AnnotationReason
    pmd-core/src/main/java/net/sourceforge/pmd/PMD.java505CloseResourceAnnotation

    Configuration errors

    + + + + + +
    RuleProblem
    LoosePackageCouplingNo packages or classes specified
    \ No newline at end of file diff --git a/report-examples/pmd-report-json.json b/report-examples/pmd-report-json.json new file mode 100644 index 0000000000..fe1f3ce473 --- /dev/null +++ b/report-examples/pmd-report-json.json @@ -0,0 +1,39 @@ +{ + "formatVersion": 0, + "pmdVersion": "6.23.0-SNAPSHOT", + "timestamp": "2020-04-05T20:13:49.698+02:00", + "files": [ + { + "filename": "/home/me/pmd/src/main/java/net/sourceforge/pmd/PMDVersion.java", + "violations": [ + { + "beginline": 16, + "begincolumn": 14, + "endline": 79, + "endcolumn": 1, + "description": "The utility class name \u0027PMDVersion\u0027 doesn\u0027t match \u0027[A-Z][a-zA-Z0-9]+(Utils?|Helper)\u0027", + "rule": "ClassNamingConventions", + "ruleset": "Code Style", + "priority": 1, + "externalInfoUrl": "https://pmd.github.io/pmd/pmd_rules_java_codestyle.html#classnamingconventions" + } + ] + }, + { + "filename": "/home/me/pmd/src/main/java/net/sourceforge/pmd/RuleContext.java", + "violations": [ + { + "beginline": 124, + "begincolumn": 9, + "endline": 125, + "endcolumn": 111, + "description": "Logger calls should be surrounded by log level guards.", + "rule": "GuardLogStatement", + "ruleset": "Best Practices", + "priority": 2, + "externalInfoUrl": "https://pmd.github.io/pmd/pmd_rules_java_bestpractices.html#guardlogstatement" + } + ] + } + ] +} diff --git a/report-examples/pmd-report-pmd-nicerhtml.html b/report-examples/pmd-report-pmd-nicerhtml.html new file mode 100644 index 0000000000..702d8b1e8f --- /dev/null +++ b/report-examples/pmd-report-pmd-nicerhtml.html @@ -0,0 +1,223 @@ + + + + + PMD 6.22.0 Report + + + + + + + + +
    + +

    PMD 6.22.0 Report. Generated on 2020-04-11 - 19:23:45

    +
    +
    +

    Summary

    + + + + + + + + + + + + + + + + + + + +
    FilesTotal +
    Priority 1
    +
    +
    Priority 2
    +
    +
    Priority 3
    +
    +
    Priority 4
    +
    +
    Priority 5
    +
    2201100
    +
    +

    Rules

    + + + + + + + + + + + + + + + + +
    RuleViolationsSeverity
    + [Best Practices] GuardLogStatement1 +
    2
    +
    + [Best Practices] ForLoopCanBeForeach1 +
    3
    +
    +
    +

    Files

    + + + + + + + + + + + + + + + + + + + + + + + + + +
    File +
    5
    +
    +
    4
    +
    +
    3
    +
    +
    2
    +
    +
    1
    +
    + /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java + 00010
    + /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java + 00100
    +
    +
    +

    File /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java

    + + + + + + + + + + + +
    ViolationError DescriptionLine
    +
    2
    +
    + [Best Practices.GuardLogStatement] + - + +Logger calls should be surrounded by log level guards. + + 124 - 125
    +
    Back to top + +

    File /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java

    + + + + + + + + + + + +
    ViolationError DescriptionLine
    +
    3
    +
    + [Best Practices.ForLoopCanBeForeach] + - + +This for loop can be replaced by a foreach loop + + 58 - 62
    +
    Back to top +
    + + \ No newline at end of file diff --git a/report-examples/pmd-report-summaryhtml.html b/report-examples/pmd-report-summaryhtml.html new file mode 100644 index 0000000000..92dc3e1f72 --- /dev/null +++ b/report-examples/pmd-report-summaryhtml.html @@ -0,0 +1,74 @@ +PMD +

    Summary

    + + + + +
    Rule nameNumber of violations
    GuardLogStatement1
    ForLoopCanBeForeach1
    +

    Detail

    +

    PMD report

    Problems found

    + + + + + + + + + + + + + +
    #FileLineProblem
    1pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java124Logger calls should be surrounded by log level guards.
    2pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java58This for loop can be replaced by a foreach loop

    Processing errors

    + + + + + +
    FileProblem
    pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    net.sourceforge.pmd.PMDException: Error while parsing pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:110)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:89)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:51)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:78)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:1)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
    +    at java.base/java.lang.Thread.run(Thread.java:834)
    +Caused by: net.sourceforge.pmd.lang.java.ast.ParseException: Encountered " "-" "- "" at line 6, column 30.
    +Was expecting one of:
    +    "extends" ...
    +    "implements" ...
    +    "{" ...
    +    "<" ...
    +    
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.generateParseException(JavaParser.java:12731)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.jj_consume_token(JavaParser.java:12615)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceBody(JavaParser.java:1574)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceDeclaration(JavaParser.java:779)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.TypeDeclaration(JavaParser.java:686)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.CompilationUnit(JavaParser.java:420)
    +    at net.sourceforge.pmd.lang.java.AbstractJavaParser.parse(AbstractJavaParser.java:62)
    +    at net.sourceforge.pmd.SourceCodeProcessor.parse(SourceCodeProcessor.java:121)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSource(SourceCodeProcessor.java:185)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:107)
    +    ... 10 more
    +

    Suppressed warnings

    + + + + + + + + +
    FileLineRuleNOPMD or AnnotationReason
    pmd-core/src/main/java/net/sourceforge/pmd/PMD.java505CloseResourceAnnotation

    Configuration errors

    + + + + + +
    RuleProblem
    LoosePackageCouplingNo packages or classes specified
    \ No newline at end of file diff --git a/report-examples/pmd-report-vbhtml.html b/report-examples/pmd-report-vbhtml.html new file mode 100644 index 0000000000..f6ce69c610 --- /dev/null +++ b/report-examples/pmd-report-vbhtml.html @@ -0,0 +1,42 @@ +PMD
    + +
     /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/RuleContext.java
    124   Logger calls should be surrounded by log level guards.
    + +
     /home/pmd/source/pmd-core/src/main/java/net/sourceforge/pmd/benchmark/Benchmarker.java
    58   This for loop can be replaced by a foreach loop

     Problems found
    /home/pmd/source/pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    net.sourceforge.pmd.PMDException: Error while parsing /home/pmd/source/pmd-core/src/test/resources/net/sourceforge/pmd/cpd/files/file_with_ISO-8859-1_encoding.java
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:110)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:89)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCode(SourceCodeProcessor.java:51)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:78)
    +    at net.sourceforge.pmd.processor.PmdRunnable.call(PmdRunnable.java:24)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515)
    +    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1130)
    +    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:630)
    +    at java.base/java.lang.Thread.run(Thread.java:832)
    +Caused by: net.sourceforge.pmd.lang.java.ast.ParseException: Encountered " "-" "- "" at line 6, column 30.
    +Was expecting one of:
    +    "extends" ...
    +    "implements" ...
    +    "{" ...
    +    "<" ...
    +    
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.generateParseException(JavaParser.java:12713)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.jj_consume_token(JavaParser.java:12597)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceBody(JavaParser.java:1554)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.ClassOrInterfaceDeclaration(JavaParser.java:732)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.TypeDeclaration(JavaParser.java:639)
    +    at net.sourceforge.pmd.lang.java.ast.JavaParser.CompilationUnit(JavaParser.java:373)
    +    at net.sourceforge.pmd.lang.java.AbstractJavaParser.parse(AbstractJavaParser.java:62)
    +    at net.sourceforge.pmd.SourceCodeProcessor.parse(SourceCodeProcessor.java:121)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSource(SourceCodeProcessor.java:185)
    +    at net.sourceforge.pmd.SourceCodeProcessor.processSourceCodeWithoutCache(SourceCodeProcessor.java:107)
    +    ... 10 more
    +
     Configuration problems found
    LoosePackageCouplingNo packages or classes specified
    diff --git a/report-examples/pmd-report-yahtml/Benchmarker.html b/report-examples/pmd-report-yahtml/Benchmarker.html new file mode 100644 index 0000000000..2e0da807d1 --- /dev/null +++ b/report-examples/pmd-report-yahtml/Benchmarker.html @@ -0,0 +1,15 @@ + + + + + PMD - Benchmarker + + +

    Class View

    +

    Class: Benchmarker

    + + + +
    MethodViolation
    findBooleanSwitch
    Rule:ForLoopCanBeForeach
    Description:This for loop can be replaced by a foreach loop
    Line:58 and 62
    + + diff --git a/report-examples/pmd-report-yahtml/RuleContext.html b/report-examples/pmd-report-yahtml/RuleContext.html new file mode 100644 index 0000000000..1f401103f4 --- /dev/null +++ b/report-examples/pmd-report-yahtml/RuleContext.html @@ -0,0 +1,15 @@ + + + + + PMD - RuleContext + + +

    Class View

    +

    Class: RuleContext

    + + + +
    MethodViolation
    setSourceCodeFilename
    Rule:GuardLogStatement
    Description:Logger calls should be surrounded by log level guards.
    Line:124 and 125
    + + diff --git a/report-examples/pmd-report-yahtml/index.html b/report-examples/pmd-report-yahtml/index.html new file mode 100644 index 0000000000..c8a696b998 --- /dev/null +++ b/report-examples/pmd-report-yahtml/index.html @@ -0,0 +1,20 @@ + + + + + PMD + + +

    Package View

    + + + + + + + + + +
    PackageClass#
    Aggregate - 2
    net - 2
    net.sourceforge - 2
    net.sourceforge.pmd - 2
    net.sourceforge.pmd RuleContext 1
    net.sourceforge.pmd.benchmark - 1
    net.sourceforge.pmd.benchmark Benchmarker 1
    + + diff --git a/search.json b/search.json new file mode 100644 index 0000000000..30ecd25d15 --- /dev/null +++ b/search.json @@ -0,0 +1,5838 @@ +[ + + + + + + +{ +"title": "How to add a new CPD language", +"tags": "devdocsextending", +"keywords": "", +"url": "pmd_devdocs_major_adding_new_cpd_language.html", +"summary": "How to add a new CPD language" +} + + + +, + + + + + +{ +"title": "Adding PMD support for a new language", +"tags": "devdocsextending", +"keywords": "", +"url": "pmd_devdocs_major_adding_new_language.html", +"summary": "How to add a new language to PMD." +} + + + +, + + + + + +{ +"title": "Adding support for metrics to a language", +"tags": "devdocsextendingmetrics", +"keywords": "", +"url": "pmd_devdocs_major_adding_new_metrics_framework.html", +"summary": "PMD's Java module has an extensive framework for the calculation of metrics, which allows rule developers to implement and use new code metrics very simply. Most of the functionality of this framework is abstracted in such a way that any PMD supported language can implement such a framework without too much trouble. Here's how." +} + + + +, + + + + + +{ +"title": "Ant Task Usage", +"tags": "userdocstools", +"keywords": "", +"url": "pmd_userdocs_tools_ant.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Apex Rules", +"tags": "rule_referencesapex", +"keywords": "", +"url": "pmd_rules_apex.html", +"summary": "Index of all built-in rules available for Apex" +} + + + +, + + + + + +{ +"title": "Index of Apex code metrics", +"tags": "extendingmetrics", +"keywords": "", +"url": "pmd_apex_metrics_index.html", +"summary": "Index of the code metrics available out of the box to Apex rule developers." +} + + + +, + + + + + +{ +"title": "Creating XML dump of the AST", +"tags": "devdocsexperimental", +"keywords": "", +"url": "pmd_devdocs_experimental_ast_dump.html", +"summary": "Creating a XML representation of the AST allows to analyze the AST with other tools." +} + + + +, + + + + + +{ +"title": "Best Practices", +"tags": "userdocs", +"keywords": "", +"url": "pmd_userdocs_best_practices.html", +"summary": "" +} + + + +, + + + + + + + +{ +"title": "Best Practices (Java Server Pages, Best Practices)", +"tags": "", +"keywords": "Best Practices", +"url": "pmd_rules_jsp_bestpractices.html#best practices", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "DontNestJsfInJstlIteration (Java Server Pages, Best Practices)", +"tags": "", +"keywords": "DontNestJsfInJstlIteration", +"url": "pmd_rules_jsp_bestpractices.html#dontnestjsfinjstliteration", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "NoClassAttribute (Java Server Pages, Best Practices)", +"tags": "", +"keywords": "NoClassAttribute", +"url": "pmd_rules_jsp_bestpractices.html#noclassattribute", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "NoHtmlComments (Java Server Pages, Best Practices)", +"tags": "", +"keywords": "NoHtmlComments", +"url": "pmd_rules_jsp_bestpractices.html#nohtmlcomments", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "NoJspForward (Java Server Pages, Best Practices)", +"tags": "", +"keywords": "NoJspForward", +"url": "pmd_rules_jsp_bestpractices.html#nojspforward", +"summary": "Rules which enforce generally accepted best practices." +} + + + + + +, + + + + + + + +{ +"title": "Best Practices (Ecmascript, Best Practices)", +"tags": "", +"keywords": "Best Practices", +"url": "pmd_rules_ecmascript_bestpractices.html#best practices", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidWithStatement (Ecmascript, Best Practices)", +"tags": "", +"keywords": "AvoidWithStatement", +"url": "pmd_rules_ecmascript_bestpractices.html#avoidwithstatement", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ConsistentReturn (Ecmascript, Best Practices)", +"tags": "", +"keywords": "ConsistentReturn", +"url": "pmd_rules_ecmascript_bestpractices.html#consistentreturn", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "GlobalVariable (Ecmascript, Best Practices)", +"tags": "", +"keywords": "GlobalVariable", +"url": "pmd_rules_ecmascript_bestpractices.html#globalvariable", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ScopeForInVariable (Ecmascript, Best Practices)", +"tags": "", +"keywords": "ScopeForInVariable", +"url": "pmd_rules_ecmascript_bestpractices.html#scopeforinvariable", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UseBaseWithParseInt (Ecmascript, Best Practices)", +"tags": "", +"keywords": "UseBaseWithParseInt", +"url": "pmd_rules_ecmascript_bestpractices.html#usebasewithparseint", +"summary": "Rules which enforce generally accepted best practices." +} + + + + + +, + + + + + + + +{ +"title": "Best Practices (Apex, Best Practices)", +"tags": "", +"keywords": "Best Practices", +"url": "pmd_rules_apex_bestpractices.html#best practices", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ApexAssertionsShouldIncludeMessage (Apex, Best Practices)", +"tags": "", +"keywords": "ApexAssertionsShouldIncludeMessage", +"url": "pmd_rules_apex_bestpractices.html#apexassertionsshouldincludemessage", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ApexUnitTestClassShouldHaveAsserts (Apex, Best Practices)", +"tags": "", +"keywords": "ApexUnitTestClassShouldHaveAsserts", +"url": "pmd_rules_apex_bestpractices.html#apexunittestclassshouldhaveasserts", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ApexUnitTestMethodShouldHaveIsTestAnnotation (Apex, Best Practices)", +"tags": "", +"keywords": "ApexUnitTestMethodShouldHaveIsTestAnnotation", +"url": "pmd_rules_apex_bestpractices.html#apexunittestmethodshouldhaveistestannotation", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ApexUnitTestShouldNotUseSeeAllDataTrue (Apex, Best Practices)", +"tags": "", +"keywords": "ApexUnitTestShouldNotUseSeeAllDataTrue", +"url": "pmd_rules_apex_bestpractices.html#apexunittestshouldnotuseseealldatatrue", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidGlobalModifier (Apex, Best Practices)", +"tags": "", +"keywords": "AvoidGlobalModifier", +"url": "pmd_rules_apex_bestpractices.html#avoidglobalmodifier", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidLogicInTrigger (Apex, Best Practices)", +"tags": "", +"keywords": "AvoidLogicInTrigger", +"url": "pmd_rules_apex_bestpractices.html#avoidlogicintrigger", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "DebugsShouldUseLoggingLevel (Apex, Best Practices)", +"tags": "", +"keywords": "DebugsShouldUseLoggingLevel", +"url": "pmd_rules_apex_bestpractices.html#debugsshoulduselogginglevel", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UnusedLocalVariable (Apex, Best Practices)", +"tags": "", +"keywords": "UnusedLocalVariable", +"url": "pmd_rules_apex_bestpractices.html#unusedlocalvariable", +"summary": "Rules which enforce generally accepted best practices." +} + + + + + +, + + + + + + + +{ +"title": "Best Practices (VM, Best Practices)", +"tags": "", +"keywords": "Best Practices", +"url": "pmd_rules_vm_bestpractices.html#best practices", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidReassigningParameters (VM, Best Practices)", +"tags": "", +"keywords": "AvoidReassigningParameters", +"url": "pmd_rules_vm_bestpractices.html#avoidreassigningparameters", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UnusedMacroParameter (VM, Best Practices)", +"tags": "", +"keywords": "UnusedMacroParameter", +"url": "pmd_rules_vm_bestpractices.html#unusedmacroparameter", +"summary": "Rules which enforce generally accepted best practices." +} + + + + + +, + + + + + + + +{ +"title": "Best Practices (PLSQL, Best Practices)", +"tags": "", +"keywords": "Best Practices", +"url": "pmd_rules_plsql_bestpractices.html#best practices", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "TomKytesDespair (PLSQL, Best Practices)", +"tags": "", +"keywords": "TomKytesDespair", +"url": "pmd_rules_plsql_bestpractices.html#tomkytesdespair", +"summary": "Rules which enforce generally accepted best practices." +} + + + + + +, + + + + + + + +{ +"title": "Best Practices (Modelica, Best Practices)", +"tags": "", +"keywords": "Best Practices", +"url": "pmd_rules_modelica_bestpractices.html#best practices", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ClassStartNameEqualsEndName (Modelica, Best Practices)", +"tags": "", +"keywords": "ClassStartNameEqualsEndName", +"url": "pmd_rules_modelica_bestpractices.html#classstartnameequalsendname", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ConnectUsingNonConnector (Modelica, Best Practices)", +"tags": "", +"keywords": "ConnectUsingNonConnector", +"url": "pmd_rules_modelica_bestpractices.html#connectusingnonconnector", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AmbiguousResolution (Modelica, Best Practices)", +"tags": "", +"keywords": "AmbiguousResolution", +"url": "pmd_rules_modelica_bestpractices.html#ambiguousresolution", +"summary": "Rules which enforce generally accepted best practices." +} + + + + + +, + + + + + + + +{ +"title": "Best Practices (Java, Best Practices)", +"tags": "", +"keywords": "Best Practices", +"url": "pmd_rules_java_bestpractices.html#best practices", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AbstractClassWithoutAbstractMethod (Java, Best Practices)", +"tags": "", +"keywords": "AbstractClassWithoutAbstractMethod", +"url": "pmd_rules_java_bestpractices.html#abstractclasswithoutabstractmethod", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AccessorClassGeneration (Java, Best Practices)", +"tags": "", +"keywords": "AccessorClassGeneration", +"url": "pmd_rules_java_bestpractices.html#accessorclassgeneration", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AccessorMethodGeneration (Java, Best Practices)", +"tags": "", +"keywords": "AccessorMethodGeneration", +"url": "pmd_rules_java_bestpractices.html#accessormethodgeneration", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ArrayIsStoredDirectly (Java, Best Practices)", +"tags": "", +"keywords": "ArrayIsStoredDirectly", +"url": "pmd_rules_java_bestpractices.html#arrayisstoreddirectly", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidMessageDigestField (Java, Best Practices)", +"tags": "", +"keywords": "AvoidMessageDigestField", +"url": "pmd_rules_java_bestpractices.html#avoidmessagedigestfield", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidPrintStackTrace (Java, Best Practices)", +"tags": "", +"keywords": "AvoidPrintStackTrace", +"url": "pmd_rules_java_bestpractices.html#avoidprintstacktrace", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidReassigningCatchVariables (Java, Best Practices)", +"tags": "", +"keywords": "AvoidReassigningCatchVariables", +"url": "pmd_rules_java_bestpractices.html#avoidreassigningcatchvariables", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidReassigningLoopVariables (Java, Best Practices)", +"tags": "", +"keywords": "AvoidReassigningLoopVariables", +"url": "pmd_rules_java_bestpractices.html#avoidreassigningloopvariables", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidReassigningParameters (Java, Best Practices)", +"tags": "", +"keywords": "AvoidReassigningParameters", +"url": "pmd_rules_java_bestpractices.html#avoidreassigningparameters", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidStringBufferField (Java, Best Practices)", +"tags": "", +"keywords": "AvoidStringBufferField", +"url": "pmd_rules_java_bestpractices.html#avoidstringbufferfield", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "AvoidUsingHardCodedIP (Java, Best Practices)", +"tags": "", +"keywords": "AvoidUsingHardCodedIP", +"url": "pmd_rules_java_bestpractices.html#avoidusinghardcodedip", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "CheckResultSet (Java, Best Practices)", +"tags": "", +"keywords": "CheckResultSet", +"url": "pmd_rules_java_bestpractices.html#checkresultset", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ConstantsInInterface (Java, Best Practices)", +"tags": "", +"keywords": "ConstantsInInterface", +"url": "pmd_rules_java_bestpractices.html#constantsininterface", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "DefaultLabelNotLastInSwitchStmt (Java, Best Practices)", +"tags": "", +"keywords": "DefaultLabelNotLastInSwitchStmt", +"url": "pmd_rules_java_bestpractices.html#defaultlabelnotlastinswitchstmt", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "DoubleBraceInitialization (Java, Best Practices)", +"tags": "", +"keywords": "DoubleBraceInitialization", +"url": "pmd_rules_java_bestpractices.html#doublebraceinitialization", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ForLoopCanBeForeach (Java, Best Practices)", +"tags": "", +"keywords": "ForLoopCanBeForeach", +"url": "pmd_rules_java_bestpractices.html#forloopcanbeforeach", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ForLoopVariableCount (Java, Best Practices)", +"tags": "", +"keywords": "ForLoopVariableCount", +"url": "pmd_rules_java_bestpractices.html#forloopvariablecount", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "GuardLogStatement (Java, Best Practices)", +"tags": "", +"keywords": "GuardLogStatement", +"url": "pmd_rules_java_bestpractices.html#guardlogstatement", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "JUnit4SuitesShouldUseSuiteAnnotation (Java, Best Practices)", +"tags": "", +"keywords": "JUnit4SuitesShouldUseSuiteAnnotation", +"url": "pmd_rules_java_bestpractices.html#junit4suitesshouldusesuiteannotation", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "JUnit4TestShouldUseAfterAnnotation (Java, Best Practices)", +"tags": "", +"keywords": "JUnit4TestShouldUseAfterAnnotation", +"url": "pmd_rules_java_bestpractices.html#junit4testshoulduseafterannotation", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "JUnit4TestShouldUseBeforeAnnotation (Java, Best Practices)", +"tags": "", +"keywords": "JUnit4TestShouldUseBeforeAnnotation", +"url": "pmd_rules_java_bestpractices.html#junit4testshouldusebeforeannotation", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "JUnit4TestShouldUseTestAnnotation (Java, Best Practices)", +"tags": "", +"keywords": "JUnit4TestShouldUseTestAnnotation", +"url": "pmd_rules_java_bestpractices.html#junit4testshouldusetestannotation", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "JUnitAssertionsShouldIncludeMessage (Java, Best Practices)", +"tags": "", +"keywords": "JUnitAssertionsShouldIncludeMessage", +"url": "pmd_rules_java_bestpractices.html#junitassertionsshouldincludemessage", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "JUnitTestContainsTooManyAsserts (Java, Best Practices)", +"tags": "", +"keywords": "JUnitTestContainsTooManyAsserts", +"url": "pmd_rules_java_bestpractices.html#junittestcontainstoomanyasserts", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "JUnitTestsShouldIncludeAssert (Java, Best Practices)", +"tags": "", +"keywords": "JUnitTestsShouldIncludeAssert", +"url": "pmd_rules_java_bestpractices.html#junittestsshouldincludeassert", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "JUnitUseExpected (Java, Best Practices)", +"tags": "", +"keywords": "JUnitUseExpected", +"url": "pmd_rules_java_bestpractices.html#junituseexpected", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "LiteralsFirstInComparisons (Java, Best Practices)", +"tags": "", +"keywords": "LiteralsFirstInComparisons", +"url": "pmd_rules_java_bestpractices.html#literalsfirstincomparisons", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "LooseCoupling (Java, Best Practices)", +"tags": "", +"keywords": "LooseCoupling", +"url": "pmd_rules_java_bestpractices.html#loosecoupling", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "MethodReturnsInternalArray (Java, Best Practices)", +"tags": "", +"keywords": "MethodReturnsInternalArray", +"url": "pmd_rules_java_bestpractices.html#methodreturnsinternalarray", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "MissingOverride (Java, Best Practices)", +"tags": "", +"keywords": "MissingOverride", +"url": "pmd_rules_java_bestpractices.html#missingoverride", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "OneDeclarationPerLine (Java, Best Practices)", +"tags": "", +"keywords": "OneDeclarationPerLine", +"url": "pmd_rules_java_bestpractices.html#onedeclarationperline", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "PositionLiteralsFirstInCaseInsensitiveComparisons (Java, Best Practices)", +"tags": "", +"keywords": "PositionLiteralsFirstInCaseInsensitiveComparisons", +"url": "pmd_rules_java_bestpractices.html#positionliteralsfirstincaseinsensitivecomparisons", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "PositionLiteralsFirstInComparisons (Java, Best Practices)", +"tags": "", +"keywords": "PositionLiteralsFirstInComparisons", +"url": "pmd_rules_java_bestpractices.html#positionliteralsfirstincomparisons", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "PreserveStackTrace (Java, Best Practices)", +"tags": "", +"keywords": "PreserveStackTrace", +"url": "pmd_rules_java_bestpractices.html#preservestacktrace", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ReplaceEnumerationWithIterator (Java, Best Practices)", +"tags": "", +"keywords": "ReplaceEnumerationWithIterator", +"url": "pmd_rules_java_bestpractices.html#replaceenumerationwithiterator", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ReplaceHashtableWithMap (Java, Best Practices)", +"tags": "", +"keywords": "ReplaceHashtableWithMap", +"url": "pmd_rules_java_bestpractices.html#replacehashtablewithmap", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "ReplaceVectorWithList (Java, Best Practices)", +"tags": "", +"keywords": "ReplaceVectorWithList", +"url": "pmd_rules_java_bestpractices.html#replacevectorwithlist", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "SwitchStmtsShouldHaveDefault (Java, Best Practices)", +"tags": "", +"keywords": "SwitchStmtsShouldHaveDefault", +"url": "pmd_rules_java_bestpractices.html#switchstmtsshouldhavedefault", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "SystemPrintln (Java, Best Practices)", +"tags": "", +"keywords": "SystemPrintln", +"url": "pmd_rules_java_bestpractices.html#systemprintln", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UnusedAssignment (Java, Best Practices)", +"tags": "", +"keywords": "UnusedAssignment", +"url": "pmd_rules_java_bestpractices.html#unusedassignment", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UnusedFormalParameter (Java, Best Practices)", +"tags": "", +"keywords": "UnusedFormalParameter", +"url": "pmd_rules_java_bestpractices.html#unusedformalparameter", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UnusedImports (Java, Best Practices)", +"tags": "", +"keywords": "UnusedImports", +"url": "pmd_rules_java_bestpractices.html#unusedimports", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UnusedLocalVariable (Java, Best Practices)", +"tags": "", +"keywords": "UnusedLocalVariable", +"url": "pmd_rules_java_bestpractices.html#unusedlocalvariable", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UnusedPrivateField (Java, Best Practices)", +"tags": "", +"keywords": "UnusedPrivateField", +"url": "pmd_rules_java_bestpractices.html#unusedprivatefield", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UnusedPrivateMethod (Java, Best Practices)", +"tags": "", +"keywords": "UnusedPrivateMethod", +"url": "pmd_rules_java_bestpractices.html#unusedprivatemethod", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UseAssertEqualsInsteadOfAssertTrue (Java, Best Practices)", +"tags": "", +"keywords": "UseAssertEqualsInsteadOfAssertTrue", +"url": "pmd_rules_java_bestpractices.html#useassertequalsinsteadofasserttrue", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UseAssertNullInsteadOfAssertTrue (Java, Best Practices)", +"tags": "", +"keywords": "UseAssertNullInsteadOfAssertTrue", +"url": "pmd_rules_java_bestpractices.html#useassertnullinsteadofasserttrue", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UseAssertSameInsteadOfAssertTrue (Java, Best Practices)", +"tags": "", +"keywords": "UseAssertSameInsteadOfAssertTrue", +"url": "pmd_rules_java_bestpractices.html#useassertsameinsteadofasserttrue", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UseAssertTrueInsteadOfAssertEquals (Java, Best Practices)", +"tags": "", +"keywords": "UseAssertTrueInsteadOfAssertEquals", +"url": "pmd_rules_java_bestpractices.html#useasserttrueinsteadofassertequals", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UseCollectionIsEmpty (Java, Best Practices)", +"tags": "", +"keywords": "UseCollectionIsEmpty", +"url": "pmd_rules_java_bestpractices.html#usecollectionisempty", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UseTryWithResources (Java, Best Practices)", +"tags": "", +"keywords": "UseTryWithResources", +"url": "pmd_rules_java_bestpractices.html#usetrywithresources", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "UseVarargs (Java, Best Practices)", +"tags": "", +"keywords": "UseVarargs", +"url": "pmd_rules_java_bestpractices.html#usevarargs", +"summary": "Rules which enforce generally accepted best practices." +} +, + +{ +"title": "WhileLoopWithLiteralBoolean (Java, Best Practices)", +"tags": "", +"keywords": "WhileLoopWithLiteralBoolean", +"url": "pmd_rules_java_bestpractices.html#whileloopwithliteralboolean", +"summary": "Rules which enforce generally accepted best practices." +} + + + + + +, + + + + + +{ +"title": "Building PMD from source", +"tags": "devdocs", +"keywords": "", +"url": "pmd_devdocs_building.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Continuous Integrations plugins", +"tags": "userdocstools", +"keywords": "", +"url": "pmd_userdocs_tools_ci.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "PMD CLI reference", +"tags": "userdocs", +"keywords": "commandlineoptionshelpformatsrenderers", +"url": "pmd_userdocs_cli_reference.html", +"summary": "Full reference for PMD's command-line interface, including options, output formats and supported languages" +} + + + +, + + + + + + + +{ +"title": "Code Style (Java Server Pages, Code Style)", +"tags": "", +"keywords": "Code Style", +"url": "pmd_rules_jsp_codestyle.html#code style", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "DuplicateJspImports (Java Server Pages, Code Style)", +"tags": "", +"keywords": "DuplicateJspImports", +"url": "pmd_rules_jsp_codestyle.html#duplicatejspimports", +"summary": "Rules which enforce a specific coding style." +} + + + + + +, + + + + + + + +{ +"title": "Code Style (Ecmascript, Code Style)", +"tags": "", +"keywords": "Code Style", +"url": "pmd_rules_ecmascript_codestyle.html#code style", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AssignmentInOperand (Ecmascript, Code Style)", +"tags": "", +"keywords": "AssignmentInOperand", +"url": "pmd_rules_ecmascript_codestyle.html#assignmentinoperand", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ForLoopsMustUseBraces (Ecmascript, Code Style)", +"tags": "", +"keywords": "ForLoopsMustUseBraces", +"url": "pmd_rules_ecmascript_codestyle.html#forloopsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "IfElseStmtsMustUseBraces (Ecmascript, Code Style)", +"tags": "", +"keywords": "IfElseStmtsMustUseBraces", +"url": "pmd_rules_ecmascript_codestyle.html#ifelsestmtsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "IfStmtsMustUseBraces (Ecmascript, Code Style)", +"tags": "", +"keywords": "IfStmtsMustUseBraces", +"url": "pmd_rules_ecmascript_codestyle.html#ifstmtsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "NoElseReturn (Ecmascript, Code Style)", +"tags": "", +"keywords": "NoElseReturn", +"url": "pmd_rules_ecmascript_codestyle.html#noelsereturn", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnnecessaryBlock (Ecmascript, Code Style)", +"tags": "", +"keywords": "UnnecessaryBlock", +"url": "pmd_rules_ecmascript_codestyle.html#unnecessaryblock", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnnecessaryParentheses (Ecmascript, Code Style)", +"tags": "", +"keywords": "UnnecessaryParentheses", +"url": "pmd_rules_ecmascript_codestyle.html#unnecessaryparentheses", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnreachableCode (Ecmascript, Code Style)", +"tags": "", +"keywords": "UnreachableCode", +"url": "pmd_rules_ecmascript_codestyle.html#unreachablecode", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "WhileLoopsMustUseBraces (Ecmascript, Code Style)", +"tags": "", +"keywords": "WhileLoopsMustUseBraces", +"url": "pmd_rules_ecmascript_codestyle.html#whileloopsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} + + + + + +, + + + + + + + +{ +"title": "Code Style (Apex, Code Style)", +"tags": "", +"keywords": "Code Style", +"url": "pmd_rules_apex_codestyle.html#code style", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ClassNamingConventions (Apex, Code Style)", +"tags": "", +"keywords": "ClassNamingConventions", +"url": "pmd_rules_apex_codestyle.html#classnamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "IfElseStmtsMustUseBraces (Apex, Code Style)", +"tags": "", +"keywords": "IfElseStmtsMustUseBraces", +"url": "pmd_rules_apex_codestyle.html#ifelsestmtsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "IfStmtsMustUseBraces (Apex, Code Style)", +"tags": "", +"keywords": "IfStmtsMustUseBraces", +"url": "pmd_rules_apex_codestyle.html#ifstmtsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "FieldDeclarationsShouldBeAtStart (Apex, Code Style)", +"tags": "", +"keywords": "FieldDeclarationsShouldBeAtStart", +"url": "pmd_rules_apex_codestyle.html#fielddeclarationsshouldbeatstart", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "FieldNamingConventions (Apex, Code Style)", +"tags": "", +"keywords": "FieldNamingConventions", +"url": "pmd_rules_apex_codestyle.html#fieldnamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ForLoopsMustUseBraces (Apex, Code Style)", +"tags": "", +"keywords": "ForLoopsMustUseBraces", +"url": "pmd_rules_apex_codestyle.html#forloopsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "FormalParameterNamingConventions (Apex, Code Style)", +"tags": "", +"keywords": "FormalParameterNamingConventions", +"url": "pmd_rules_apex_codestyle.html#formalparameternamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "LocalVariableNamingConventions (Apex, Code Style)", +"tags": "", +"keywords": "LocalVariableNamingConventions", +"url": "pmd_rules_apex_codestyle.html#localvariablenamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "MethodNamingConventions (Apex, Code Style)", +"tags": "", +"keywords": "MethodNamingConventions", +"url": "pmd_rules_apex_codestyle.html#methodnamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "OneDeclarationPerLine (Apex, Code Style)", +"tags": "", +"keywords": "OneDeclarationPerLine", +"url": "pmd_rules_apex_codestyle.html#onedeclarationperline", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "PropertyNamingConventions (Apex, Code Style)", +"tags": "", +"keywords": "PropertyNamingConventions", +"url": "pmd_rules_apex_codestyle.html#propertynamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "VariableNamingConventions (Apex, Code Style)", +"tags": "", +"keywords": "VariableNamingConventions", +"url": "pmd_rules_apex_codestyle.html#variablenamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "WhileLoopsMustUseBraces (Apex, Code Style)", +"tags": "", +"keywords": "WhileLoopsMustUseBraces", +"url": "pmd_rules_apex_codestyle.html#whileloopsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} + + + + + +, + + + + + + + +{ +"title": "Code Style (PLSQL, Code Style)", +"tags": "", +"keywords": "Code Style", +"url": "pmd_rules_plsql_codestyle.html#code style", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AvoidTabCharacter (PLSQL, Code Style)", +"tags": "", +"keywords": "AvoidTabCharacter", +"url": "pmd_rules_plsql_codestyle.html#avoidtabcharacter", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "CodeFormat (PLSQL, Code Style)", +"tags": "", +"keywords": "CodeFormat", +"url": "pmd_rules_plsql_codestyle.html#codeformat", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "MisplacedPragma (PLSQL, Code Style)", +"tags": "", +"keywords": "MisplacedPragma", +"url": "pmd_rules_plsql_codestyle.html#misplacedpragma", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ForLoopNaming (PLSQL, Code Style)", +"tags": "", +"keywords": "ForLoopNaming", +"url": "pmd_rules_plsql_codestyle.html#forloopnaming", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "LineLength (PLSQL, Code Style)", +"tags": "", +"keywords": "LineLength", +"url": "pmd_rules_plsql_codestyle.html#linelength", +"summary": "Rules which enforce a specific coding style." +} + + + + + +, + + + + + + + +{ +"title": "Code Style (Java, Code Style)", +"tags": "", +"keywords": "Code Style", +"url": "pmd_rules_java_codestyle.html#code style", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AbstractNaming (Java, Code Style)", +"tags": "", +"keywords": "AbstractNaming", +"url": "pmd_rules_java_codestyle.html#abstractnaming", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AtLeastOneConstructor (Java, Code Style)", +"tags": "", +"keywords": "AtLeastOneConstructor", +"url": "pmd_rules_java_codestyle.html#atleastoneconstructor", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AvoidDollarSigns (Java, Code Style)", +"tags": "", +"keywords": "AvoidDollarSigns", +"url": "pmd_rules_java_codestyle.html#avoiddollarsigns", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AvoidFinalLocalVariable (Java, Code Style)", +"tags": "", +"keywords": "AvoidFinalLocalVariable", +"url": "pmd_rules_java_codestyle.html#avoidfinallocalvariable", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AvoidPrefixingMethodParameters (Java, Code Style)", +"tags": "", +"keywords": "AvoidPrefixingMethodParameters", +"url": "pmd_rules_java_codestyle.html#avoidprefixingmethodparameters", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AvoidProtectedFieldInFinalClass (Java, Code Style)", +"tags": "", +"keywords": "AvoidProtectedFieldInFinalClass", +"url": "pmd_rules_java_codestyle.html#avoidprotectedfieldinfinalclass", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AvoidProtectedMethodInFinalClassNotExtending (Java, Code Style)", +"tags": "", +"keywords": "AvoidProtectedMethodInFinalClassNotExtending", +"url": "pmd_rules_java_codestyle.html#avoidprotectedmethodinfinalclassnotextending", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "AvoidUsingNativeCode (Java, Code Style)", +"tags": "", +"keywords": "AvoidUsingNativeCode", +"url": "pmd_rules_java_codestyle.html#avoidusingnativecode", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "BooleanGetMethodName (Java, Code Style)", +"tags": "", +"keywords": "BooleanGetMethodName", +"url": "pmd_rules_java_codestyle.html#booleangetmethodname", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "CallSuperInConstructor (Java, Code Style)", +"tags": "", +"keywords": "CallSuperInConstructor", +"url": "pmd_rules_java_codestyle.html#callsuperinconstructor", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ClassNamingConventions (Java, Code Style)", +"tags": "", +"keywords": "ClassNamingConventions", +"url": "pmd_rules_java_codestyle.html#classnamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "CommentDefaultAccessModifier (Java, Code Style)", +"tags": "", +"keywords": "CommentDefaultAccessModifier", +"url": "pmd_rules_java_codestyle.html#commentdefaultaccessmodifier", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ConfusingTernary (Java, Code Style)", +"tags": "", +"keywords": "ConfusingTernary", +"url": "pmd_rules_java_codestyle.html#confusingternary", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ControlStatementBraces (Java, Code Style)", +"tags": "", +"keywords": "ControlStatementBraces", +"url": "pmd_rules_java_codestyle.html#controlstatementbraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "DefaultPackage (Java, Code Style)", +"tags": "", +"keywords": "DefaultPackage", +"url": "pmd_rules_java_codestyle.html#defaultpackage", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "DontImportJavaLang (Java, Code Style)", +"tags": "", +"keywords": "DontImportJavaLang", +"url": "pmd_rules_java_codestyle.html#dontimportjavalang", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "DuplicateImports (Java, Code Style)", +"tags": "", +"keywords": "DuplicateImports", +"url": "pmd_rules_java_codestyle.html#duplicateimports", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "EmptyMethodInAbstractClassShouldBeAbstract (Java, Code Style)", +"tags": "", +"keywords": "EmptyMethodInAbstractClassShouldBeAbstract", +"url": "pmd_rules_java_codestyle.html#emptymethodinabstractclassshouldbeabstract", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ExtendsObject (Java, Code Style)", +"tags": "", +"keywords": "ExtendsObject", +"url": "pmd_rules_java_codestyle.html#extendsobject", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "FieldDeclarationsShouldBeAtStartOfClass (Java, Code Style)", +"tags": "", +"keywords": "FieldDeclarationsShouldBeAtStartOfClass", +"url": "pmd_rules_java_codestyle.html#fielddeclarationsshouldbeatstartofclass", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "FieldNamingConventions (Java, Code Style)", +"tags": "", +"keywords": "FieldNamingConventions", +"url": "pmd_rules_java_codestyle.html#fieldnamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ForLoopShouldBeWhileLoop (Java, Code Style)", +"tags": "", +"keywords": "ForLoopShouldBeWhileLoop", +"url": "pmd_rules_java_codestyle.html#forloopshouldbewhileloop", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ForLoopsMustUseBraces (Java, Code Style)", +"tags": "", +"keywords": "ForLoopsMustUseBraces", +"url": "pmd_rules_java_codestyle.html#forloopsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "FormalParameterNamingConventions (Java, Code Style)", +"tags": "", +"keywords": "FormalParameterNamingConventions", +"url": "pmd_rules_java_codestyle.html#formalparameternamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "GenericsNaming (Java, Code Style)", +"tags": "", +"keywords": "GenericsNaming", +"url": "pmd_rules_java_codestyle.html#genericsnaming", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "IdenticalCatchBranches (Java, Code Style)", +"tags": "", +"keywords": "IdenticalCatchBranches", +"url": "pmd_rules_java_codestyle.html#identicalcatchbranches", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "IfElseStmtsMustUseBraces (Java, Code Style)", +"tags": "", +"keywords": "IfElseStmtsMustUseBraces", +"url": "pmd_rules_java_codestyle.html#ifelsestmtsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "IfStmtsMustUseBraces (Java, Code Style)", +"tags": "", +"keywords": "IfStmtsMustUseBraces", +"url": "pmd_rules_java_codestyle.html#ifstmtsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "LinguisticNaming (Java, Code Style)", +"tags": "", +"keywords": "LinguisticNaming", +"url": "pmd_rules_java_codestyle.html#linguisticnaming", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "LocalHomeNamingConvention (Java, Code Style)", +"tags": "", +"keywords": "LocalHomeNamingConvention", +"url": "pmd_rules_java_codestyle.html#localhomenamingconvention", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "LocalInterfaceSessionNamingConvention (Java, Code Style)", +"tags": "", +"keywords": "LocalInterfaceSessionNamingConvention", +"url": "pmd_rules_java_codestyle.html#localinterfacesessionnamingconvention", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "LocalVariableCouldBeFinal (Java, Code Style)", +"tags": "", +"keywords": "LocalVariableCouldBeFinal", +"url": "pmd_rules_java_codestyle.html#localvariablecouldbefinal", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "LocalVariableNamingConventions (Java, Code Style)", +"tags": "", +"keywords": "LocalVariableNamingConventions", +"url": "pmd_rules_java_codestyle.html#localvariablenamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "LongVariable (Java, Code Style)", +"tags": "", +"keywords": "LongVariable", +"url": "pmd_rules_java_codestyle.html#longvariable", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "MDBAndSessionBeanNamingConvention (Java, Code Style)", +"tags": "", +"keywords": "MDBAndSessionBeanNamingConvention", +"url": "pmd_rules_java_codestyle.html#mdbandsessionbeannamingconvention", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "MethodArgumentCouldBeFinal (Java, Code Style)", +"tags": "", +"keywords": "MethodArgumentCouldBeFinal", +"url": "pmd_rules_java_codestyle.html#methodargumentcouldbefinal", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "MethodNamingConventions (Java, Code Style)", +"tags": "", +"keywords": "MethodNamingConventions", +"url": "pmd_rules_java_codestyle.html#methodnamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "MIsLeadingVariableName (Java, Code Style)", +"tags": "", +"keywords": "MIsLeadingVariableName", +"url": "pmd_rules_java_codestyle.html#misleadingvariablename", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "NoPackage (Java, Code Style)", +"tags": "", +"keywords": "NoPackage", +"url": "pmd_rules_java_codestyle.html#nopackage", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UseUnderscoresInNumericLiterals (Java, Code Style)", +"tags": "", +"keywords": "UseUnderscoresInNumericLiterals", +"url": "pmd_rules_java_codestyle.html#useunderscoresinnumericliterals", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "OnlyOneReturn (Java, Code Style)", +"tags": "", +"keywords": "OnlyOneReturn", +"url": "pmd_rules_java_codestyle.html#onlyonereturn", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "PackageCase (Java, Code Style)", +"tags": "", +"keywords": "PackageCase", +"url": "pmd_rules_java_codestyle.html#packagecase", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "PrematureDeclaration (Java, Code Style)", +"tags": "", +"keywords": "PrematureDeclaration", +"url": "pmd_rules_java_codestyle.html#prematuredeclaration", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "RemoteInterfaceNamingConvention (Java, Code Style)", +"tags": "", +"keywords": "RemoteInterfaceNamingConvention", +"url": "pmd_rules_java_codestyle.html#remoteinterfacenamingconvention", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "RemoteSessionInterfaceNamingConvention (Java, Code Style)", +"tags": "", +"keywords": "RemoteSessionInterfaceNamingConvention", +"url": "pmd_rules_java_codestyle.html#remotesessioninterfacenamingconvention", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ShortClassName (Java, Code Style)", +"tags": "", +"keywords": "ShortClassName", +"url": "pmd_rules_java_codestyle.html#shortclassname", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ShortMethodName (Java, Code Style)", +"tags": "", +"keywords": "ShortMethodName", +"url": "pmd_rules_java_codestyle.html#shortmethodname", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "ShortVariable (Java, Code Style)", +"tags": "", +"keywords": "ShortVariable", +"url": "pmd_rules_java_codestyle.html#shortvariable", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "SuspiciousConstantFieldName (Java, Code Style)", +"tags": "", +"keywords": "SuspiciousConstantFieldName", +"url": "pmd_rules_java_codestyle.html#suspiciousconstantfieldname", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "TooManyStaticImports (Java, Code Style)", +"tags": "", +"keywords": "TooManyStaticImports", +"url": "pmd_rules_java_codestyle.html#toomanystaticimports", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnnecessaryAnnotationValueElement (Java, Code Style)", +"tags": "", +"keywords": "UnnecessaryAnnotationValueElement", +"url": "pmd_rules_java_codestyle.html#unnecessaryannotationvalueelement", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnnecessaryCast (Java, Code Style)", +"tags": "", +"keywords": "UnnecessaryCast", +"url": "pmd_rules_java_codestyle.html#unnecessarycast", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnnecessaryConstructor (Java, Code Style)", +"tags": "", +"keywords": "UnnecessaryConstructor", +"url": "pmd_rules_java_codestyle.html#unnecessaryconstructor", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnnecessaryFullyQualifiedName (Java, Code Style)", +"tags": "", +"keywords": "UnnecessaryFullyQualifiedName", +"url": "pmd_rules_java_codestyle.html#unnecessaryfullyqualifiedname", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnnecessaryLocalBeforeReturn (Java, Code Style)", +"tags": "", +"keywords": "UnnecessaryLocalBeforeReturn", +"url": "pmd_rules_java_codestyle.html#unnecessarylocalbeforereturn", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnnecessaryModifier (Java, Code Style)", +"tags": "", +"keywords": "UnnecessaryModifier", +"url": "pmd_rules_java_codestyle.html#unnecessarymodifier", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UnnecessaryReturn (Java, Code Style)", +"tags": "", +"keywords": "UnnecessaryReturn", +"url": "pmd_rules_java_codestyle.html#unnecessaryreturn", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UseDiamondOperator (Java, Code Style)", +"tags": "", +"keywords": "UseDiamondOperator", +"url": "pmd_rules_java_codestyle.html#usediamondoperator", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UselessParentheses (Java, Code Style)", +"tags": "", +"keywords": "UselessParentheses", +"url": "pmd_rules_java_codestyle.html#uselessparentheses", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UselessQualifiedThis (Java, Code Style)", +"tags": "", +"keywords": "UselessQualifiedThis", +"url": "pmd_rules_java_codestyle.html#uselessqualifiedthis", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UseShortArrayInitializer (Java, Code Style)", +"tags": "", +"keywords": "UseShortArrayInitializer", +"url": "pmd_rules_java_codestyle.html#useshortarrayinitializer", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "VariableNamingConventions (Java, Code Style)", +"tags": "", +"keywords": "VariableNamingConventions", +"url": "pmd_rules_java_codestyle.html#variablenamingconventions", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "WhileLoopsMustUseBraces (Java, Code Style)", +"tags": "", +"keywords": "WhileLoopsMustUseBraces", +"url": "pmd_rules_java_codestyle.html#whileloopsmustusebraces", +"summary": "Rules which enforce a specific coding style." +} + + + + + +, + + + + + + + +{ +"title": "Code Style (XSL, Code Style)", +"tags": "", +"keywords": "Code Style", +"url": "pmd_rules_xsl_codestyle.html#code style", +"summary": "Rules which enforce a specific coding style." +} +, + +{ +"title": "UseConcatOnce (XSL, Code Style)", +"tags": "", +"keywords": "UseConcatOnce", +"url": "pmd_rules_xsl_codestyle.html#useconcatonce", +"summary": "Rules which enforce a specific coding style." +} + + + + + +, + + + + + +{ +"title": "Configuring rules", +"tags": "userdocsgetting_started", +"keywords": "propertypropertiesmessagepriority", +"url": "pmd_userdocs_configuring_rules.html", +"summary": "Learn how to configure your rules directly from the ruleset XML." +} + + + +, + + + + + +{ +"title": "Finding duplicated code with CPD", +"tags": "cpduserdocs", +"keywords": "", +"url": "pmd_userdocs_cpd.html", +"summary": "Learn how to use CPD, the copy-paste detector shipped with PMD." +} + + + +, + + + + + +{ +"title": "Report formats for CPD", +"tags": "cpduserdocs", +"keywords": "formatsrenderers", +"url": "pmd_userdocs_cpd_report_formats.html", +"summary": "Overview of the built-in report formats for CPD" +} + + + +, + + + + + +{ +"title": "Credits", +"tags": "", +"keywords": "", +"url": "pmd_projectdocs_credits.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Defining rule properties", +"tags": "extendinguserdocs", +"keywords": "", +"url": "pmd_userdocs_extending_defining_properties.html", +"summary": "Learn how to define your own properties both for Java and XPath rules." +} + + + +, + + + + + + + +{ +"title": "Design (Java Server Pages, Design)", +"tags": "", +"keywords": "Design", +"url": "pmd_rules_jsp_design.html#design", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NoInlineScript (Java Server Pages, Design)", +"tags": "", +"keywords": "NoInlineScript", +"url": "pmd_rules_jsp_design.html#noinlinescript", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NoInlineStyleInformation (Java Server Pages, Design)", +"tags": "", +"keywords": "NoInlineStyleInformation", +"url": "pmd_rules_jsp_design.html#noinlinestyleinformation", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NoLongScripts (Java Server Pages, Design)", +"tags": "", +"keywords": "NoLongScripts", +"url": "pmd_rules_jsp_design.html#nolongscripts", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NoScriptlets (Java Server Pages, Design)", +"tags": "", +"keywords": "NoScriptlets", +"url": "pmd_rules_jsp_design.html#noscriptlets", +"summary": "Rules that help you discover design issues." +} + + + + + +, + + + + + + + +{ +"title": "Design (Apex, Design)", +"tags": "", +"keywords": "Design", +"url": "pmd_rules_apex_design.html#design", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AvoidDeeplyNestedIfStmts (Apex, Design)", +"tags": "", +"keywords": "AvoidDeeplyNestedIfStmts", +"url": "pmd_rules_apex_design.html#avoiddeeplynestedifstmts", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "CyclomaticComplexity (Apex, Design)", +"tags": "", +"keywords": "CyclomaticComplexity", +"url": "pmd_rules_apex_design.html#cyclomaticcomplexity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "CognitiveComplexity (Apex, Design)", +"tags": "", +"keywords": "CognitiveComplexity", +"url": "pmd_rules_apex_design.html#cognitivecomplexity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveClassLength (Apex, Design)", +"tags": "", +"keywords": "ExcessiveClassLength", +"url": "pmd_rules_apex_design.html#excessiveclasslength", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveParameterList (Apex, Design)", +"tags": "", +"keywords": "ExcessiveParameterList", +"url": "pmd_rules_apex_design.html#excessiveparameterlist", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessivePublicCount (Apex, Design)", +"tags": "", +"keywords": "ExcessivePublicCount", +"url": "pmd_rules_apex_design.html#excessivepubliccount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NcssConstructorCount (Apex, Design)", +"tags": "", +"keywords": "NcssConstructorCount", +"url": "pmd_rules_apex_design.html#ncssconstructorcount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NcssMethodCount (Apex, Design)", +"tags": "", +"keywords": "NcssMethodCount", +"url": "pmd_rules_apex_design.html#ncssmethodcount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NcssTypeCount (Apex, Design)", +"tags": "", +"keywords": "NcssTypeCount", +"url": "pmd_rules_apex_design.html#ncsstypecount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "StdCyclomaticComplexity (Apex, Design)", +"tags": "", +"keywords": "StdCyclomaticComplexity", +"url": "pmd_rules_apex_design.html#stdcyclomaticcomplexity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "TooManyFields (Apex, Design)", +"tags": "", +"keywords": "TooManyFields", +"url": "pmd_rules_apex_design.html#toomanyfields", +"summary": "Rules that help you discover design issues." +} + + + + + +, + + + + + + + +{ +"title": "Design (VM, Design)", +"tags": "", +"keywords": "Design", +"url": "pmd_rules_vm_design.html#design", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AvoidDeeplyNestedIfStmts (VM, Design)", +"tags": "", +"keywords": "AvoidDeeplyNestedIfStmts", +"url": "pmd_rules_vm_design.html#avoiddeeplynestedifstmts", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "CollapsibleIfStatements (VM, Design)", +"tags": "", +"keywords": "CollapsibleIfStatements", +"url": "pmd_rules_vm_design.html#collapsibleifstatements", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveTemplateLength (VM, Design)", +"tags": "", +"keywords": "ExcessiveTemplateLength", +"url": "pmd_rules_vm_design.html#excessivetemplatelength", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NoInlineJavaScript (VM, Design)", +"tags": "", +"keywords": "NoInlineJavaScript", +"url": "pmd_rules_vm_design.html#noinlinejavascript", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NoInlineStyles (VM, Design)", +"tags": "", +"keywords": "NoInlineStyles", +"url": "pmd_rules_vm_design.html#noinlinestyles", +"summary": "Rules that help you discover design issues." +} + + + + + +, + + + + + + + +{ +"title": "Design (PLSQL, Design)", +"tags": "", +"keywords": "Design", +"url": "pmd_rules_plsql_design.html#design", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "CyclomaticComplexity (PLSQL, Design)", +"tags": "", +"keywords": "CyclomaticComplexity", +"url": "pmd_rules_plsql_design.html#cyclomaticcomplexity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveMethodLength (PLSQL, Design)", +"tags": "", +"keywords": "ExcessiveMethodLength", +"url": "pmd_rules_plsql_design.html#excessivemethodlength", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveObjectLength (PLSQL, Design)", +"tags": "", +"keywords": "ExcessiveObjectLength", +"url": "pmd_rules_plsql_design.html#excessiveobjectlength", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessivePackageBodyLength (PLSQL, Design)", +"tags": "", +"keywords": "ExcessivePackageBodyLength", +"url": "pmd_rules_plsql_design.html#excessivepackagebodylength", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessivePackageSpecificationLength (PLSQL, Design)", +"tags": "", +"keywords": "ExcessivePackageSpecificationLength", +"url": "pmd_rules_plsql_design.html#excessivepackagespecificationlength", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveParameterList (PLSQL, Design)", +"tags": "", +"keywords": "ExcessiveParameterList", +"url": "pmd_rules_plsql_design.html#excessiveparameterlist", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveTypeLength (PLSQL, Design)", +"tags": "", +"keywords": "ExcessiveTypeLength", +"url": "pmd_rules_plsql_design.html#excessivetypelength", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NcssMethodCount (PLSQL, Design)", +"tags": "", +"keywords": "NcssMethodCount", +"url": "pmd_rules_plsql_design.html#ncssmethodcount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NcssObjectCount (PLSQL, Design)", +"tags": "", +"keywords": "NcssObjectCount", +"url": "pmd_rules_plsql_design.html#ncssobjectcount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NPathComplexity (PLSQL, Design)", +"tags": "", +"keywords": "NPathComplexity", +"url": "pmd_rules_plsql_design.html#npathcomplexity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "TooManyFields (PLSQL, Design)", +"tags": "", +"keywords": "TooManyFields", +"url": "pmd_rules_plsql_design.html#toomanyfields", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "TooManyMethods (PLSQL, Design)", +"tags": "", +"keywords": "TooManyMethods", +"url": "pmd_rules_plsql_design.html#toomanymethods", +"summary": "Rules that help you discover design issues." +} + + + + + +, + + + + + + + +{ +"title": "Design (Java, Design)", +"tags": "", +"keywords": "Design", +"url": "pmd_rules_java_design.html#design", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AbstractClassWithoutAnyMethod (Java, Design)", +"tags": "", +"keywords": "AbstractClassWithoutAnyMethod", +"url": "pmd_rules_java_design.html#abstractclasswithoutanymethod", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AvoidCatchingGenericException (Java, Design)", +"tags": "", +"keywords": "AvoidCatchingGenericException", +"url": "pmd_rules_java_design.html#avoidcatchinggenericexception", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AvoidDeeplyNestedIfStmts (Java, Design)", +"tags": "", +"keywords": "AvoidDeeplyNestedIfStmts", +"url": "pmd_rules_java_design.html#avoiddeeplynestedifstmts", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AvoidRethrowingException (Java, Design)", +"tags": "", +"keywords": "AvoidRethrowingException", +"url": "pmd_rules_java_design.html#avoidrethrowingexception", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AvoidThrowingNewInstanceOfSameException (Java, Design)", +"tags": "", +"keywords": "AvoidThrowingNewInstanceOfSameException", +"url": "pmd_rules_java_design.html#avoidthrowingnewinstanceofsameexception", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AvoidThrowingNullPointerException (Java, Design)", +"tags": "", +"keywords": "AvoidThrowingNullPointerException", +"url": "pmd_rules_java_design.html#avoidthrowingnullpointerexception", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AvoidThrowingRawExceptionTypes (Java, Design)", +"tags": "", +"keywords": "AvoidThrowingRawExceptionTypes", +"url": "pmd_rules_java_design.html#avoidthrowingrawexceptiontypes", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "AvoidUncheckedExceptionsInSignatures (Java, Design)", +"tags": "", +"keywords": "AvoidUncheckedExceptionsInSignatures", +"url": "pmd_rules_java_design.html#avoiduncheckedexceptionsinsignatures", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ClassWithOnlyPrivateConstructorsShouldBeFinal (Java, Design)", +"tags": "", +"keywords": "ClassWithOnlyPrivateConstructorsShouldBeFinal", +"url": "pmd_rules_java_design.html#classwithonlyprivateconstructorsshouldbefinal", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "CollapsibleIfStatements (Java, Design)", +"tags": "", +"keywords": "CollapsibleIfStatements", +"url": "pmd_rules_java_design.html#collapsibleifstatements", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "CouplingBetweenObjects (Java, Design)", +"tags": "", +"keywords": "CouplingBetweenObjects", +"url": "pmd_rules_java_design.html#couplingbetweenobjects", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "CyclomaticComplexity (Java, Design)", +"tags": "", +"keywords": "CyclomaticComplexity", +"url": "pmd_rules_java_design.html#cyclomaticcomplexity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "DataClass (Java, Design)", +"tags": "", +"keywords": "DataClass", +"url": "pmd_rules_java_design.html#dataclass", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "DoNotExtendJavaLangError (Java, Design)", +"tags": "", +"keywords": "DoNotExtendJavaLangError", +"url": "pmd_rules_java_design.html#donotextendjavalangerror", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExceptionAsFlowControl (Java, Design)", +"tags": "", +"keywords": "ExceptionAsFlowControl", +"url": "pmd_rules_java_design.html#exceptionasflowcontrol", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveClassLength (Java, Design)", +"tags": "", +"keywords": "ExcessiveClassLength", +"url": "pmd_rules_java_design.html#excessiveclasslength", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveImports (Java, Design)", +"tags": "", +"keywords": "ExcessiveImports", +"url": "pmd_rules_java_design.html#excessiveimports", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveMethodLength (Java, Design)", +"tags": "", +"keywords": "ExcessiveMethodLength", +"url": "pmd_rules_java_design.html#excessivemethodlength", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessiveParameterList (Java, Design)", +"tags": "", +"keywords": "ExcessiveParameterList", +"url": "pmd_rules_java_design.html#excessiveparameterlist", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ExcessivePublicCount (Java, Design)", +"tags": "", +"keywords": "ExcessivePublicCount", +"url": "pmd_rules_java_design.html#excessivepubliccount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "FinalFieldCouldBeStatic (Java, Design)", +"tags": "", +"keywords": "FinalFieldCouldBeStatic", +"url": "pmd_rules_java_design.html#finalfieldcouldbestatic", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "GodClass (Java, Design)", +"tags": "", +"keywords": "GodClass", +"url": "pmd_rules_java_design.html#godclass", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ImmutableField (Java, Design)", +"tags": "", +"keywords": "ImmutableField", +"url": "pmd_rules_java_design.html#immutablefield", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "LawOfDemeter (Java, Design)", +"tags": "", +"keywords": "LawOfDemeter", +"url": "pmd_rules_java_design.html#lawofdemeter", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "LogicInversion (Java, Design)", +"tags": "", +"keywords": "LogicInversion", +"url": "pmd_rules_java_design.html#logicinversion", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "LoosePackageCoupling (Java, Design)", +"tags": "", +"keywords": "LoosePackageCoupling", +"url": "pmd_rules_java_design.html#loosepackagecoupling", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "ModifiedCyclomaticComplexity (Java, Design)", +"tags": "", +"keywords": "ModifiedCyclomaticComplexity", +"url": "pmd_rules_java_design.html#modifiedcyclomaticcomplexity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NcssConstructorCount (Java, Design)", +"tags": "", +"keywords": "NcssConstructorCount", +"url": "pmd_rules_java_design.html#ncssconstructorcount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NcssCount (Java, Design)", +"tags": "", +"keywords": "NcssCount", +"url": "pmd_rules_java_design.html#ncsscount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NcssMethodCount (Java, Design)", +"tags": "", +"keywords": "NcssMethodCount", +"url": "pmd_rules_java_design.html#ncssmethodcount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NcssTypeCount (Java, Design)", +"tags": "", +"keywords": "NcssTypeCount", +"url": "pmd_rules_java_design.html#ncsstypecount", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "NPathComplexity (Java, Design)", +"tags": "", +"keywords": "NPathComplexity", +"url": "pmd_rules_java_design.html#npathcomplexity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "SignatureDeclareThrowsException (Java, Design)", +"tags": "", +"keywords": "SignatureDeclareThrowsException", +"url": "pmd_rules_java_design.html#signaturedeclarethrowsexception", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "SimplifiedTernary (Java, Design)", +"tags": "", +"keywords": "SimplifiedTernary", +"url": "pmd_rules_java_design.html#simplifiedternary", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "SimplifyBooleanAssertion (Java, Design)", +"tags": "", +"keywords": "SimplifyBooleanAssertion", +"url": "pmd_rules_java_design.html#simplifybooleanassertion", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "SimplifyBooleanExpressions (Java, Design)", +"tags": "", +"keywords": "SimplifyBooleanExpressions", +"url": "pmd_rules_java_design.html#simplifybooleanexpressions", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "SimplifyBooleanReturns (Java, Design)", +"tags": "", +"keywords": "SimplifyBooleanReturns", +"url": "pmd_rules_java_design.html#simplifybooleanreturns", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "SimplifyConditional (Java, Design)", +"tags": "", +"keywords": "SimplifyConditional", +"url": "pmd_rules_java_design.html#simplifyconditional", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "SingularField (Java, Design)", +"tags": "", +"keywords": "SingularField", +"url": "pmd_rules_java_design.html#singularfield", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "StdCyclomaticComplexity (Java, Design)", +"tags": "", +"keywords": "StdCyclomaticComplexity", +"url": "pmd_rules_java_design.html#stdcyclomaticcomplexity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "SwitchDensity (Java, Design)", +"tags": "", +"keywords": "SwitchDensity", +"url": "pmd_rules_java_design.html#switchdensity", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "TooManyFields (Java, Design)", +"tags": "", +"keywords": "TooManyFields", +"url": "pmd_rules_java_design.html#toomanyfields", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "TooManyMethods (Java, Design)", +"tags": "", +"keywords": "TooManyMethods", +"url": "pmd_rules_java_design.html#toomanymethods", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "UselessOverridingMethod (Java, Design)", +"tags": "", +"keywords": "UselessOverridingMethod", +"url": "pmd_rules_java_design.html#uselessoverridingmethod", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "UseObjectForClearerAPI (Java, Design)", +"tags": "", +"keywords": "UseObjectForClearerAPI", +"url": "pmd_rules_java_design.html#useobjectforclearerapi", +"summary": "Rules that help you discover design issues." +} +, + +{ +"title": "UseUtilityClass (Java, Design)", +"tags": "", +"keywords": "UseUtilityClass", +"url": "pmd_rules_java_design.html#useutilityclass", +"summary": "Rules that help you discover design issues." +} + + + + + +, + + + + + +{ +"title": "The rule designer", +"tags": "extendinguserdocs", +"keywords": "", +"url": "pmd_userdocs_extending_designer_reference.html", +"summary": "Learn about the usage and features of the rule designer." +} + + + +, + + + + + +{ +"title": "Developer Resources", +"tags": "devdocs", +"keywords": "", +"url": "pmd_devdocs_development.html", +"summary": "" +} + + + +, + + + + + + + +{ +"title": "Documentation (Apex, Documentation)", +"tags": "", +"keywords": "Documentation", +"url": "pmd_rules_apex_documentation.html#documentation", +"summary": "Rules that are related to code documentation." +} +, + +{ +"title": "ApexDoc (Apex, Documentation)", +"tags": "", +"keywords": "ApexDoc", +"url": "pmd_rules_apex_documentation.html#apexdoc", +"summary": "Rules that are related to code documentation." +} + + + + + +, + + + + + + + +{ +"title": "Documentation (Java, Documentation)", +"tags": "", +"keywords": "Documentation", +"url": "pmd_rules_java_documentation.html#documentation", +"summary": "Rules that are related to code documentation." +} +, + +{ +"title": "CommentContent (Java, Documentation)", +"tags": "", +"keywords": "CommentContent", +"url": "pmd_rules_java_documentation.html#commentcontent", +"summary": "Rules that are related to code documentation." +} +, + +{ +"title": "CommentRequired (Java, Documentation)", +"tags": "", +"keywords": "CommentRequired", +"url": "pmd_rules_java_documentation.html#commentrequired", +"summary": "Rules that are related to code documentation." +} +, + +{ +"title": "CommentSize (Java, Documentation)", +"tags": "", +"keywords": "CommentSize", +"url": "pmd_rules_java_documentation.html#commentsize", +"summary": "Rules that are related to code documentation." +} +, + +{ +"title": "UncommentedEmptyConstructor (Java, Documentation)", +"tags": "", +"keywords": "UncommentedEmptyConstructor", +"url": "pmd_rules_java_documentation.html#uncommentedemptyconstructor", +"summary": "Rules that are related to code documentation." +} +, + +{ +"title": "UncommentedEmptyMethodBody (Java, Documentation)", +"tags": "", +"keywords": "UncommentedEmptyMethodBody", +"url": "pmd_rules_java_documentation.html#uncommentedemptymethodbody", +"summary": "Rules that are related to code documentation." +} + + + + + +, + + + + + +{ +"title": "Ecmascript Rules", +"tags": "rule_referencesecmascript", +"keywords": "", +"url": "pmd_rules_ecmascript.html", +"summary": "Index of all built-in rules available for Ecmascript" +} + + + +, + + + + + + + +{ +"title": "Error Prone (Java Server Pages, Error Prone)", +"tags": "", +"keywords": "Error Prone", +"url": "pmd_rules_jsp_errorprone.html#error prone", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "JspEncoding (Java Server Pages, Error Prone)", +"tags": "", +"keywords": "JspEncoding", +"url": "pmd_rules_jsp_errorprone.html#jspencoding", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} + + + + + +, + + + + + + + +{ +"title": "Error Prone (Ecmascript, Error Prone)", +"tags": "", +"keywords": "Error Prone", +"url": "pmd_rules_ecmascript_errorprone.html#error prone", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidTrailingComma (Ecmascript, Error Prone)", +"tags": "", +"keywords": "AvoidTrailingComma", +"url": "pmd_rules_ecmascript_errorprone.html#avoidtrailingcomma", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EqualComparison (Ecmascript, Error Prone)", +"tags": "", +"keywords": "EqualComparison", +"url": "pmd_rules_ecmascript_errorprone.html#equalcomparison", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "InnaccurateNumericLiteral (Ecmascript, Error Prone)", +"tags": "", +"keywords": "InnaccurateNumericLiteral", +"url": "pmd_rules_ecmascript_errorprone.html#innaccuratenumericliteral", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} + + + + + +, + + + + + + + +{ +"title": "Error Prone (Apex, Error Prone)", +"tags": "", +"keywords": "Error Prone", +"url": "pmd_rules_apex_errorprone.html#error prone", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "ApexCSRF (Apex, Error Prone)", +"tags": "", +"keywords": "ApexCSRF", +"url": "pmd_rules_apex_errorprone.html#apexcsrf", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidDirectAccessTriggerMap (Apex, Error Prone)", +"tags": "", +"keywords": "AvoidDirectAccessTriggerMap", +"url": "pmd_rules_apex_errorprone.html#avoiddirectaccesstriggermap", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidHardcodingId (Apex, Error Prone)", +"tags": "", +"keywords": "AvoidHardcodingId", +"url": "pmd_rules_apex_errorprone.html#avoidhardcodingid", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyCatchBlock (Apex, Error Prone)", +"tags": "", +"keywords": "EmptyCatchBlock", +"url": "pmd_rules_apex_errorprone.html#emptycatchblock", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyIfStmt (Apex, Error Prone)", +"tags": "", +"keywords": "EmptyIfStmt", +"url": "pmd_rules_apex_errorprone.html#emptyifstmt", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyStatementBlock (Apex, Error Prone)", +"tags": "", +"keywords": "EmptyStatementBlock", +"url": "pmd_rules_apex_errorprone.html#emptystatementblock", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyTryOrFinallyBlock (Apex, Error Prone)", +"tags": "", +"keywords": "EmptyTryOrFinallyBlock", +"url": "pmd_rules_apex_errorprone.html#emptytryorfinallyblock", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyWhileStmt (Apex, Error Prone)", +"tags": "", +"keywords": "EmptyWhileStmt", +"url": "pmd_rules_apex_errorprone.html#emptywhilestmt", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "MethodWithSameNameAsEnclosingClass (Apex, Error Prone)", +"tags": "", +"keywords": "MethodWithSameNameAsEnclosingClass", +"url": "pmd_rules_apex_errorprone.html#methodwithsamenameasenclosingclass", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidNonExistentAnnotations (Apex, Error Prone)", +"tags": "", +"keywords": "AvoidNonExistentAnnotations", +"url": "pmd_rules_apex_errorprone.html#avoidnonexistentannotations", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "TestMethodsMustBeInTestClasses (Apex, Error Prone)", +"tags": "", +"keywords": "TestMethodsMustBeInTestClasses", +"url": "pmd_rules_apex_errorprone.html#testmethodsmustbeintestclasses", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} + + + + + +, + + + + + + + +{ +"title": "Error Prone (VM, Error Prone)", +"tags": "", +"keywords": "Error Prone", +"url": "pmd_rules_vm_errorprone.html#error prone", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyForeachStmt (VM, Error Prone)", +"tags": "", +"keywords": "EmptyForeachStmt", +"url": "pmd_rules_vm_errorprone.html#emptyforeachstmt", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyIfStmt (VM, Error Prone)", +"tags": "", +"keywords": "EmptyIfStmt", +"url": "pmd_rules_vm_errorprone.html#emptyifstmt", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} + + + + + +, + + + + + + + +{ +"title": "Error Prone (PLSQL, Error Prone)", +"tags": "", +"keywords": "Error Prone", +"url": "pmd_rules_plsql_errorprone.html#error prone", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "TO_DATE_TO_CHAR (PLSQL, Error Prone)", +"tags": "", +"keywords": "TO_DATE_TO_CHAR", +"url": "pmd_rules_plsql_errorprone.html#to_date_to_char", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "TO_DATEWithoutDateFormat (PLSQL, Error Prone)", +"tags": "", +"keywords": "TO_DATEWithoutDateFormat", +"url": "pmd_rules_plsql_errorprone.html#to_datewithoutdateformat", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "TO_TIMESTAMPWithoutDateFormat (PLSQL, Error Prone)", +"tags": "", +"keywords": "TO_TIMESTAMPWithoutDateFormat", +"url": "pmd_rules_plsql_errorprone.html#to_timestampwithoutdateformat", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} + + + + + +, + + + + + + + +{ +"title": "Error Prone (Java, Error Prone)", +"tags": "", +"keywords": "Error Prone", +"url": "pmd_rules_java_errorprone.html#error prone", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AssignmentInOperand (Java, Error Prone)", +"tags": "", +"keywords": "AssignmentInOperand", +"url": "pmd_rules_java_errorprone.html#assignmentinoperand", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AssignmentToNonFinalStatic (Java, Error Prone)", +"tags": "", +"keywords": "AssignmentToNonFinalStatic", +"url": "pmd_rules_java_errorprone.html#assignmenttononfinalstatic", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidAccessibilityAlteration (Java, Error Prone)", +"tags": "", +"keywords": "AvoidAccessibilityAlteration", +"url": "pmd_rules_java_errorprone.html#avoidaccessibilityalteration", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidAssertAsIdentifier (Java, Error Prone)", +"tags": "", +"keywords": "AvoidAssertAsIdentifier", +"url": "pmd_rules_java_errorprone.html#avoidassertasidentifier", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidBranchingStatementAsLastInLoop (Java, Error Prone)", +"tags": "", +"keywords": "AvoidBranchingStatementAsLastInLoop", +"url": "pmd_rules_java_errorprone.html#avoidbranchingstatementaslastinloop", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidCallingFinalize (Java, Error Prone)", +"tags": "", +"keywords": "AvoidCallingFinalize", +"url": "pmd_rules_java_errorprone.html#avoidcallingfinalize", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidCatchingNPE (Java, Error Prone)", +"tags": "", +"keywords": "AvoidCatchingNPE", +"url": "pmd_rules_java_errorprone.html#avoidcatchingnpe", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidCatchingThrowable (Java, Error Prone)", +"tags": "", +"keywords": "AvoidCatchingThrowable", +"url": "pmd_rules_java_errorprone.html#avoidcatchingthrowable", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidDecimalLiteralsInBigDecimalConstructor (Java, Error Prone)", +"tags": "", +"keywords": "AvoidDecimalLiteralsInBigDecimalConstructor", +"url": "pmd_rules_java_errorprone.html#avoiddecimalliteralsinbigdecimalconstructor", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidDuplicateLiterals (Java, Error Prone)", +"tags": "", +"keywords": "AvoidDuplicateLiterals", +"url": "pmd_rules_java_errorprone.html#avoidduplicateliterals", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidEnumAsIdentifier (Java, Error Prone)", +"tags": "", +"keywords": "AvoidEnumAsIdentifier", +"url": "pmd_rules_java_errorprone.html#avoidenumasidentifier", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidFieldNameMatchingMethodName (Java, Error Prone)", +"tags": "", +"keywords": "AvoidFieldNameMatchingMethodName", +"url": "pmd_rules_java_errorprone.html#avoidfieldnamematchingmethodname", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidFieldNameMatchingTypeName (Java, Error Prone)", +"tags": "", +"keywords": "AvoidFieldNameMatchingTypeName", +"url": "pmd_rules_java_errorprone.html#avoidfieldnamematchingtypename", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidInstanceofChecksInCatchClause (Java, Error Prone)", +"tags": "", +"keywords": "AvoidInstanceofChecksInCatchClause", +"url": "pmd_rules_java_errorprone.html#avoidinstanceofchecksincatchclause", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidLiteralsInIfCondition (Java, Error Prone)", +"tags": "", +"keywords": "AvoidLiteralsInIfCondition", +"url": "pmd_rules_java_errorprone.html#avoidliteralsinifcondition", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidLosingExceptionInformation (Java, Error Prone)", +"tags": "", +"keywords": "AvoidLosingExceptionInformation", +"url": "pmd_rules_java_errorprone.html#avoidlosingexceptioninformation", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidMultipleUnaryOperators (Java, Error Prone)", +"tags": "", +"keywords": "AvoidMultipleUnaryOperators", +"url": "pmd_rules_java_errorprone.html#avoidmultipleunaryoperators", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "AvoidUsingOctalValues (Java, Error Prone)", +"tags": "", +"keywords": "AvoidUsingOctalValues", +"url": "pmd_rules_java_errorprone.html#avoidusingoctalvalues", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "BadComparison (Java, Error Prone)", +"tags": "", +"keywords": "BadComparison", +"url": "pmd_rules_java_errorprone.html#badcomparison", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "BeanMembersShouldSerialize (Java, Error Prone)", +"tags": "", +"keywords": "BeanMembersShouldSerialize", +"url": "pmd_rules_java_errorprone.html#beanmembersshouldserialize", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "BrokenNullCheck (Java, Error Prone)", +"tags": "", +"keywords": "BrokenNullCheck", +"url": "pmd_rules_java_errorprone.html#brokennullcheck", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "CallSuperFirst (Java, Error Prone)", +"tags": "", +"keywords": "CallSuperFirst", +"url": "pmd_rules_java_errorprone.html#callsuperfirst", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "CallSuperLast (Java, Error Prone)", +"tags": "", +"keywords": "CallSuperLast", +"url": "pmd_rules_java_errorprone.html#callsuperlast", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "CheckSkipResult (Java, Error Prone)", +"tags": "", +"keywords": "CheckSkipResult", +"url": "pmd_rules_java_errorprone.html#checkskipresult", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "ClassCastExceptionWithToArray (Java, Error Prone)", +"tags": "", +"keywords": "ClassCastExceptionWithToArray", +"url": "pmd_rules_java_errorprone.html#classcastexceptionwithtoarray", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "CloneMethodMustBePublic (Java, Error Prone)", +"tags": "", +"keywords": "CloneMethodMustBePublic", +"url": "pmd_rules_java_errorprone.html#clonemethodmustbepublic", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "CloneMethodMustImplementCloneable (Java, Error Prone)", +"tags": "", +"keywords": "CloneMethodMustImplementCloneable", +"url": "pmd_rules_java_errorprone.html#clonemethodmustimplementcloneable", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "CloneMethodReturnTypeMustMatchClassName (Java, Error Prone)", +"tags": "", +"keywords": "CloneMethodReturnTypeMustMatchClassName", +"url": "pmd_rules_java_errorprone.html#clonemethodreturntypemustmatchclassname", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "CloneThrowsCloneNotSupportedException (Java, Error Prone)", +"tags": "", +"keywords": "CloneThrowsCloneNotSupportedException", +"url": "pmd_rules_java_errorprone.html#clonethrowsclonenotsupportedexception", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "CloseResource (Java, Error Prone)", +"tags": "", +"keywords": "CloseResource", +"url": "pmd_rules_java_errorprone.html#closeresource", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "CompareObjectsWithEquals (Java, Error Prone)", +"tags": "", +"keywords": "CompareObjectsWithEquals", +"url": "pmd_rules_java_errorprone.html#compareobjectswithequals", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "ConstructorCallsOverridableMethod (Java, Error Prone)", +"tags": "", +"keywords": "ConstructorCallsOverridableMethod", +"url": "pmd_rules_java_errorprone.html#constructorcallsoverridablemethod", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DataflowAnomalyAnalysis (Java, Error Prone)", +"tags": "", +"keywords": "DataflowAnomalyAnalysis", +"url": "pmd_rules_java_errorprone.html#dataflowanomalyanalysis", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DetachedTestCase (Java, Error Prone)", +"tags": "", +"keywords": "DetachedTestCase", +"url": "pmd_rules_java_errorprone.html#detachedtestcase", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DoNotCallGarbageCollectionExplicitly (Java, Error Prone)", +"tags": "", +"keywords": "DoNotCallGarbageCollectionExplicitly", +"url": "pmd_rules_java_errorprone.html#donotcallgarbagecollectionexplicitly", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DoNotCallSystemExit (Java, Error Prone)", +"tags": "", +"keywords": "DoNotCallSystemExit", +"url": "pmd_rules_java_errorprone.html#donotcallsystemexit", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DoNotExtendJavaLangThrowable (Java, Error Prone)", +"tags": "", +"keywords": "DoNotExtendJavaLangThrowable", +"url": "pmd_rules_java_errorprone.html#donotextendjavalangthrowable", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DoNotHardCodeSDCard (Java, Error Prone)", +"tags": "", +"keywords": "DoNotHardCodeSDCard", +"url": "pmd_rules_java_errorprone.html#donothardcodesdcard", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DoNotTerminateVM (Java, Error Prone)", +"tags": "", +"keywords": "DoNotTerminateVM", +"url": "pmd_rules_java_errorprone.html#donotterminatevm", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DoNotThrowExceptionInFinally (Java, Error Prone)", +"tags": "", +"keywords": "DoNotThrowExceptionInFinally", +"url": "pmd_rules_java_errorprone.html#donotthrowexceptioninfinally", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DontImportSun (Java, Error Prone)", +"tags": "", +"keywords": "DontImportSun", +"url": "pmd_rules_java_errorprone.html#dontimportsun", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "DontUseFloatTypeForLoopIndices (Java, Error Prone)", +"tags": "", +"keywords": "DontUseFloatTypeForLoopIndices", +"url": "pmd_rules_java_errorprone.html#dontusefloattypeforloopindices", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyCatchBlock (Java, Error Prone)", +"tags": "", +"keywords": "EmptyCatchBlock", +"url": "pmd_rules_java_errorprone.html#emptycatchblock", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyFinalizer (Java, Error Prone)", +"tags": "", +"keywords": "EmptyFinalizer", +"url": "pmd_rules_java_errorprone.html#emptyfinalizer", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyFinallyBlock (Java, Error Prone)", +"tags": "", +"keywords": "EmptyFinallyBlock", +"url": "pmd_rules_java_errorprone.html#emptyfinallyblock", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyIfStmt (Java, Error Prone)", +"tags": "", +"keywords": "EmptyIfStmt", +"url": "pmd_rules_java_errorprone.html#emptyifstmt", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyInitializer (Java, Error Prone)", +"tags": "", +"keywords": "EmptyInitializer", +"url": "pmd_rules_java_errorprone.html#emptyinitializer", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyStatementBlock (Java, Error Prone)", +"tags": "", +"keywords": "EmptyStatementBlock", +"url": "pmd_rules_java_errorprone.html#emptystatementblock", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyStatementNotInLoop (Java, Error Prone)", +"tags": "", +"keywords": "EmptyStatementNotInLoop", +"url": "pmd_rules_java_errorprone.html#emptystatementnotinloop", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptySwitchStatements (Java, Error Prone)", +"tags": "", +"keywords": "EmptySwitchStatements", +"url": "pmd_rules_java_errorprone.html#emptyswitchstatements", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptySynchronizedBlock (Java, Error Prone)", +"tags": "", +"keywords": "EmptySynchronizedBlock", +"url": "pmd_rules_java_errorprone.html#emptysynchronizedblock", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyTryBlock (Java, Error Prone)", +"tags": "", +"keywords": "EmptyTryBlock", +"url": "pmd_rules_java_errorprone.html#emptytryblock", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EmptyWhileStmt (Java, Error Prone)", +"tags": "", +"keywords": "EmptyWhileStmt", +"url": "pmd_rules_java_errorprone.html#emptywhilestmt", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "EqualsNull (Java, Error Prone)", +"tags": "", +"keywords": "EqualsNull", +"url": "pmd_rules_java_errorprone.html#equalsnull", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "FinalizeDoesNotCallSuperFinalize (Java, Error Prone)", +"tags": "", +"keywords": "FinalizeDoesNotCallSuperFinalize", +"url": "pmd_rules_java_errorprone.html#finalizedoesnotcallsuperfinalize", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "FinalizeOnlyCallsSuperFinalize (Java, Error Prone)", +"tags": "", +"keywords": "FinalizeOnlyCallsSuperFinalize", +"url": "pmd_rules_java_errorprone.html#finalizeonlycallssuperfinalize", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "FinalizeOverloaded (Java, Error Prone)", +"tags": "", +"keywords": "FinalizeOverloaded", +"url": "pmd_rules_java_errorprone.html#finalizeoverloaded", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "FinalizeShouldBeProtected (Java, Error Prone)", +"tags": "", +"keywords": "FinalizeShouldBeProtected", +"url": "pmd_rules_java_errorprone.html#finalizeshouldbeprotected", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "IdempotentOperations (Java, Error Prone)", +"tags": "", +"keywords": "IdempotentOperations", +"url": "pmd_rules_java_errorprone.html#idempotentoperations", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "ImportFromSamePackage (Java, Error Prone)", +"tags": "", +"keywords": "ImportFromSamePackage", +"url": "pmd_rules_java_errorprone.html#importfromsamepackage", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "InstantiationToGetClass (Java, Error Prone)", +"tags": "", +"keywords": "InstantiationToGetClass", +"url": "pmd_rules_java_errorprone.html#instantiationtogetclass", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "InvalidSlf4jMessageFormat (Java, Error Prone)", +"tags": "", +"keywords": "InvalidSlf4jMessageFormat", +"url": "pmd_rules_java_errorprone.html#invalidslf4jmessageformat", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "InvalidLogMessageFormat (Java, Error Prone)", +"tags": "", +"keywords": "InvalidLogMessageFormat", +"url": "pmd_rules_java_errorprone.html#invalidlogmessageformat", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "JumbledIncrementer (Java, Error Prone)", +"tags": "", +"keywords": "JumbledIncrementer", +"url": "pmd_rules_java_errorprone.html#jumbledincrementer", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "JUnitSpelling (Java, Error Prone)", +"tags": "", +"keywords": "JUnitSpelling", +"url": "pmd_rules_java_errorprone.html#junitspelling", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "JUnitStaticSuite (Java, Error Prone)", +"tags": "", +"keywords": "JUnitStaticSuite", +"url": "pmd_rules_java_errorprone.html#junitstaticsuite", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "LoggerIsNotStaticFinal (Java, Error Prone)", +"tags": "", +"keywords": "LoggerIsNotStaticFinal", +"url": "pmd_rules_java_errorprone.html#loggerisnotstaticfinal", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "MethodWithSameNameAsEnclosingClass (Java, Error Prone)", +"tags": "", +"keywords": "MethodWithSameNameAsEnclosingClass", +"url": "pmd_rules_java_errorprone.html#methodwithsamenameasenclosingclass", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "MisplacedNullCheck (Java, Error Prone)", +"tags": "", +"keywords": "MisplacedNullCheck", +"url": "pmd_rules_java_errorprone.html#misplacednullcheck", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "MissingBreakInSwitch (Java, Error Prone)", +"tags": "", +"keywords": "MissingBreakInSwitch", +"url": "pmd_rules_java_errorprone.html#missingbreakinswitch", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "MissingSerialVersionUID (Java, Error Prone)", +"tags": "", +"keywords": "MissingSerialVersionUID", +"url": "pmd_rules_java_errorprone.html#missingserialversionuid", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "MissingStaticMethodInNonInstantiatableClass (Java, Error Prone)", +"tags": "", +"keywords": "MissingStaticMethodInNonInstantiatableClass", +"url": "pmd_rules_java_errorprone.html#missingstaticmethodinnoninstantiatableclass", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "MoreThanOneLogger (Java, Error Prone)", +"tags": "", +"keywords": "MoreThanOneLogger", +"url": "pmd_rules_java_errorprone.html#morethanonelogger", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "NonCaseLabelInSwitchStatement (Java, Error Prone)", +"tags": "", +"keywords": "NonCaseLabelInSwitchStatement", +"url": "pmd_rules_java_errorprone.html#noncaselabelinswitchstatement", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "NonStaticInitializer (Java, Error Prone)", +"tags": "", +"keywords": "NonStaticInitializer", +"url": "pmd_rules_java_errorprone.html#nonstaticinitializer", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "NullAssignment (Java, Error Prone)", +"tags": "", +"keywords": "NullAssignment", +"url": "pmd_rules_java_errorprone.html#nullassignment", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "OverrideBothEqualsAndHashcode (Java, Error Prone)", +"tags": "", +"keywords": "OverrideBothEqualsAndHashcode", +"url": "pmd_rules_java_errorprone.html#overridebothequalsandhashcode", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "ProperCloneImplementation (Java, Error Prone)", +"tags": "", +"keywords": "ProperCloneImplementation", +"url": "pmd_rules_java_errorprone.html#propercloneimplementation", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "ProperLogger (Java, Error Prone)", +"tags": "", +"keywords": "ProperLogger", +"url": "pmd_rules_java_errorprone.html#properlogger", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "ReturnEmptyArrayRatherThanNull (Java, Error Prone)", +"tags": "", +"keywords": "ReturnEmptyArrayRatherThanNull", +"url": "pmd_rules_java_errorprone.html#returnemptyarrayratherthannull", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "ReturnFromFinallyBlock (Java, Error Prone)", +"tags": "", +"keywords": "ReturnFromFinallyBlock", +"url": "pmd_rules_java_errorprone.html#returnfromfinallyblock", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "SimpleDateFormatNeedsLocale (Java, Error Prone)", +"tags": "", +"keywords": "SimpleDateFormatNeedsLocale", +"url": "pmd_rules_java_errorprone.html#simpledateformatneedslocale", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "SingleMethodSingleton (Java, Error Prone)", +"tags": "", +"keywords": "SingleMethodSingleton", +"url": "pmd_rules_java_errorprone.html#singlemethodsingleton", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "SingletonClassReturningNewInstance (Java, Error Prone)", +"tags": "", +"keywords": "SingletonClassReturningNewInstance", +"url": "pmd_rules_java_errorprone.html#singletonclassreturningnewinstance", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "StaticEJBFieldShouldBeFinal (Java, Error Prone)", +"tags": "", +"keywords": "StaticEJBFieldShouldBeFinal", +"url": "pmd_rules_java_errorprone.html#staticejbfieldshouldbefinal", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "StringBufferInstantiationWithChar (Java, Error Prone)", +"tags": "", +"keywords": "StringBufferInstantiationWithChar", +"url": "pmd_rules_java_errorprone.html#stringbufferinstantiationwithchar", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "SuspiciousEqualsMethodName (Java, Error Prone)", +"tags": "", +"keywords": "SuspiciousEqualsMethodName", +"url": "pmd_rules_java_errorprone.html#suspiciousequalsmethodname", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "SuspiciousHashcodeMethodName (Java, Error Prone)", +"tags": "", +"keywords": "SuspiciousHashcodeMethodName", +"url": "pmd_rules_java_errorprone.html#suspicioushashcodemethodname", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "SuspiciousOctalEscape (Java, Error Prone)", +"tags": "", +"keywords": "SuspiciousOctalEscape", +"url": "pmd_rules_java_errorprone.html#suspiciousoctalescape", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "TestClassWithoutTestCases (Java, Error Prone)", +"tags": "", +"keywords": "TestClassWithoutTestCases", +"url": "pmd_rules_java_errorprone.html#testclasswithouttestcases", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UnconditionalIfStatement (Java, Error Prone)", +"tags": "", +"keywords": "UnconditionalIfStatement", +"url": "pmd_rules_java_errorprone.html#unconditionalifstatement", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UnnecessaryBooleanAssertion (Java, Error Prone)", +"tags": "", +"keywords": "UnnecessaryBooleanAssertion", +"url": "pmd_rules_java_errorprone.html#unnecessarybooleanassertion", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UnnecessaryCaseChange (Java, Error Prone)", +"tags": "", +"keywords": "UnnecessaryCaseChange", +"url": "pmd_rules_java_errorprone.html#unnecessarycasechange", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UnnecessaryConversionTemporary (Java, Error Prone)", +"tags": "", +"keywords": "UnnecessaryConversionTemporary", +"url": "pmd_rules_java_errorprone.html#unnecessaryconversiontemporary", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UnusedNullCheckInEquals (Java, Error Prone)", +"tags": "", +"keywords": "UnusedNullCheckInEquals", +"url": "pmd_rules_java_errorprone.html#unusednullcheckinequals", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UseCorrectExceptionLogging (Java, Error Prone)", +"tags": "", +"keywords": "UseCorrectExceptionLogging", +"url": "pmd_rules_java_errorprone.html#usecorrectexceptionlogging", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UseEqualsToCompareStrings (Java, Error Prone)", +"tags": "", +"keywords": "UseEqualsToCompareStrings", +"url": "pmd_rules_java_errorprone.html#useequalstocomparestrings", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UselessOperationOnImmutable (Java, Error Prone)", +"tags": "", +"keywords": "UselessOperationOnImmutable", +"url": "pmd_rules_java_errorprone.html#uselessoperationonimmutable", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UseLocaleWithCaseConversions (Java, Error Prone)", +"tags": "", +"keywords": "UseLocaleWithCaseConversions", +"url": "pmd_rules_java_errorprone.html#uselocalewithcaseconversions", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "UseProperClassLoader (Java, Error Prone)", +"tags": "", +"keywords": "UseProperClassLoader", +"url": "pmd_rules_java_errorprone.html#useproperclassloader", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} + + + + + +, + + + + + + + +{ +"title": "Error Prone (Maven POM, Error Prone)", +"tags": "", +"keywords": "Error Prone", +"url": "pmd_rules_pom_errorprone.html#error prone", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "InvalidDependencyTypes (Maven POM, Error Prone)", +"tags": "", +"keywords": "InvalidDependencyTypes", +"url": "pmd_rules_pom_errorprone.html#invaliddependencytypes", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "ProjectVersionAsDependencyVersion (Maven POM, Error Prone)", +"tags": "", +"keywords": "ProjectVersionAsDependencyVersion", +"url": "pmd_rules_pom_errorprone.html#projectversionasdependencyversion", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} + + + + + +, + + + + + + + +{ +"title": "Error Prone (XML, Error Prone)", +"tags": "", +"keywords": "Error Prone", +"url": "pmd_rules_xml_errorprone.html#error prone", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} +, + +{ +"title": "MistypedCDATASection (XML, Error Prone)", +"tags": "", +"keywords": "MistypedCDATASection", +"url": "pmd_rules_xml_errorprone.html#mistypedcdatasection", +"summary": "Rules to detect constructs that are either broken, extremely confusing or prone to runtime errors." +} + + + + + +, + + + + + +{ +"title": "FAQ", +"tags": "", +"keywords": "", +"url": "pmd_projectdocs_faq.html", +"summary": "" +} + + + +, + + + + + + + +{ +"title": "Gradle", +"tags": "userdocstools", +"keywords": "", +"url": "pmd_userdocs_tools_gradle.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Getting Help", +"tags": "", +"keywords": "", +"url": "pmd_about_help.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "How PMD Works", +"tags": "devdocs", +"keywords": "", +"url": "pmd_devdocs_how_pmd_works.html", +"summary": "Processing overview of the different steps taken by PMD." +} + + + +, + + + + + +{ +"title": "Incremental Analysis", +"tags": "userdocs", +"keywords": "pmdoptionscommandincrementalanalysisperformance", +"url": "pmd_userdocs_incremental_analysis.html", +"summary": "Explains how to use incremental analysis to speed up analysis" +} + + + +, + + + + + +{ +"title": "Documentation Index", +"tags": "", +"keywords": "java", +"url": "index.html", +"summary": "Welcome to the documentation site for PMD and CPD!

    " +} + + + +, + + + + + +{ +"title": "Installation and basic CLI usage", +"tags": "getting_starteduserdocs", +"keywords": "pmdcpdoptionscommandauxclasspath", +"url": "pmd_userdocs_installation.html", +"summary": "Sums up the first steps to set up a CLI installation and get started using PMD" +} + + + +, + + + + + +{ +"title": "PMD Java API", +"tags": "userdocstools", +"keywords": "", +"url": "pmd_userdocs_tools_java_api.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Java Rules", +"tags": "rule_referencesjava", +"keywords": "", +"url": "pmd_rules_java.html", +"summary": "Index of all built-in rules available for Java" +} + + + +, + + + + + +{ +"title": "Index of Java code metrics", +"tags": "extendingmetrics", +"keywords": "", +"url": "pmd_java_metrics_index.html", +"summary": "Index of the code metrics available out of the box to Java rule developers." +} + + + +, + + + + + +{ +"title": "JSP Support", +"tags": "", +"keywords": "", +"url": "pmd_languages_jsp.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Java Server Pages Rules", +"tags": "rule_referencesjsp", +"keywords": "", +"url": "pmd_rules_jsp.html", +"summary": "Index of all built-in rules available for Java Server Pages" +} + + + +, + + + + + +{ +"title": "License", +"tags": "", +"keywords": "", +"url": "license.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Main Landing Page", +"tags": "", +"keywords": "", +"url": "pmd_projectdocs_committers_main_landing_page.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Making rulesets", +"tags": "getting_starteduserdocs", +"keywords": "rulesetsreferenceruleexcludeincludepatternfilter", +"url": "pmd_userdocs_making_rulesets.html", +"summary": "A ruleset is an XML configuration file, which describes a collection of rules to be executed in a PMD run. PMD includes built-in rulesets to run quick analyses with a default configuration, but users are encouraged to make their own rulesets from the start, because they allow for so much configurability. This page walk you through the creation of a ruleset and the multiple configuration features offered by rulesets." +} + + + +, + + + + + +{ +"title": "Maven PMD Plugin", +"tags": "userdocstools", +"keywords": "", +"url": "pmd_userdocs_tools_maven.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "What does 'PMD' mean?", +"tags": "", +"keywords": "", +"url": "pmd_projectdocs_trivia_meaning.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Merging pull requests", +"tags": "", +"keywords": "", +"url": "pmd_projectdocs_committers_merging_pull_requests.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Using and defining code metrics for custom rules", +"tags": "extendinguserdocsmetrics", +"keywords": "", +"url": "pmd_userdocs_extending_metrics_howto.html", +"summary": "Since version 6.0.0, PMD is enhanced with the ability to compute code metrics on Java and Apex source (the so-called Metrics Framework). This framework provides developers with a straightforward interface to use code metrics in their rules, and to extend the framework with their own custom metrics." +} + + + +, + + + + + +{ +"title": "Modelica Rules", +"tags": "rule_referencesmodelica", +"keywords": "", +"url": "pmd_rules_modelica.html", +"summary": "Index of all built-in rules available for Modelica" +} + + + +, + + + + + + + +{ +"title": "Multithreading (Java, Multithreading)", +"tags": "", +"keywords": "Multithreading", +"url": "pmd_rules_java_multithreading.html#multithreading", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "AvoidSynchronizedAtMethodLevel (Java, Multithreading)", +"tags": "", +"keywords": "AvoidSynchronizedAtMethodLevel", +"url": "pmd_rules_java_multithreading.html#avoidsynchronizedatmethodlevel", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "AvoidThreadGroup (Java, Multithreading)", +"tags": "", +"keywords": "AvoidThreadGroup", +"url": "pmd_rules_java_multithreading.html#avoidthreadgroup", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "AvoidUsingVolatile (Java, Multithreading)", +"tags": "", +"keywords": "AvoidUsingVolatile", +"url": "pmd_rules_java_multithreading.html#avoidusingvolatile", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "DoNotUseThreads (Java, Multithreading)", +"tags": "", +"keywords": "DoNotUseThreads", +"url": "pmd_rules_java_multithreading.html#donotusethreads", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "DontCallThreadRun (Java, Multithreading)", +"tags": "", +"keywords": "DontCallThreadRun", +"url": "pmd_rules_java_multithreading.html#dontcallthreadrun", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "DoubleCheckedLocking (Java, Multithreading)", +"tags": "", +"keywords": "DoubleCheckedLocking", +"url": "pmd_rules_java_multithreading.html#doublecheckedlocking", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "NonThreadSafeSingleton (Java, Multithreading)", +"tags": "", +"keywords": "NonThreadSafeSingleton", +"url": "pmd_rules_java_multithreading.html#nonthreadsafesingleton", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "UnsynchronizedStaticDateFormatter (Java, Multithreading)", +"tags": "", +"keywords": "UnsynchronizedStaticDateFormatter", +"url": "pmd_rules_java_multithreading.html#unsynchronizedstaticdateformatter", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "UnsynchronizedStaticFormatter (Java, Multithreading)", +"tags": "", +"keywords": "UnsynchronizedStaticFormatter", +"url": "pmd_rules_java_multithreading.html#unsynchronizedstaticformatter", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "UseConcurrentHashMap (Java, Multithreading)", +"tags": "", +"keywords": "UseConcurrentHashMap", +"url": "pmd_rules_java_multithreading.html#useconcurrenthashmap", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} +, + +{ +"title": "UseNotifyAllInsteadOfNotify (Java, Multithreading)", +"tags": "", +"keywords": "UseNotifyAllInsteadOfNotify", +"url": "pmd_rules_java_multithreading.html#usenotifyallinsteadofnotify", +"summary": "Rules that flag issues when dealing with multiple threads of execution." +} + + + + + +, + + + + + +{ +"title": "Scroll layout", +"tags": "special_layouts", +"keywords": "json, scrolling, scrollto, jquery plugin", +"url": "jsmydoc_scroll.html", +"summary": "This page demonstrates how you the integration of a script called ScrollTo, which is used here to link definitions of a JSON code sample to a list of definitions for that particular term. The scenario here is that the JSON blocks are really long, with extensive nesting and subnesting, which makes it difficult for tables below the JSON to adequately explain the term in a usable way." +} + + + +, + + + + + +{ +"title": "News", +"tags": "", +"keywords": "news, blog, updates, release notes, announcements", +"url": "news.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "PMD in the press", +"tags": "", +"keywords": "", +"url": "pmd_projectdocs_trivia_news.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "News", +"tags": "", +"keywords": "news, blog, updates, release notes, announcements", +"url": "news_archive.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "PMD 7.0.0 development", +"tags": "", +"keywords": "changelog, release notes, deprecation, api changes", +"url": "pmd_next_major_development.html", +"summary": "" +} + + + +, + + + + + + + +{ +"title": "Performance (Apex, Performance)", +"tags": "", +"keywords": "Performance", +"url": "pmd_rules_apex_performance.html#performance", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AvoidDmlStatementsInLoops (Apex, Performance)", +"tags": "", +"keywords": "AvoidDmlStatementsInLoops", +"url": "pmd_rules_apex_performance.html#avoiddmlstatementsinloops", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AvoidSoqlInLoops (Apex, Performance)", +"tags": "", +"keywords": "AvoidSoqlInLoops", +"url": "pmd_rules_apex_performance.html#avoidsoqlinloops", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AvoidSoslInLoops (Apex, Performance)", +"tags": "", +"keywords": "AvoidSoslInLoops", +"url": "pmd_rules_apex_performance.html#avoidsoslinloops", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "OperationWithLimitsInLoop (Apex, Performance)", +"tags": "", +"keywords": "OperationWithLimitsInLoop", +"url": "pmd_rules_apex_performance.html#operationwithlimitsinloop", +"summary": "Rules that flag suboptimal code." +} + + + + + +, + + + + + + + +{ +"title": "Performance (Java, Performance)", +"tags": "", +"keywords": "Performance", +"url": "pmd_rules_java_performance.html#performance", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AddEmptyString (Java, Performance)", +"tags": "", +"keywords": "AddEmptyString", +"url": "pmd_rules_java_performance.html#addemptystring", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AppendCharacterWithChar (Java, Performance)", +"tags": "", +"keywords": "AppendCharacterWithChar", +"url": "pmd_rules_java_performance.html#appendcharacterwithchar", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AvoidArrayLoops (Java, Performance)", +"tags": "", +"keywords": "AvoidArrayLoops", +"url": "pmd_rules_java_performance.html#avoidarrayloops", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AvoidCalendarDateCreation (Java, Performance)", +"tags": "", +"keywords": "AvoidCalendarDateCreation", +"url": "pmd_rules_java_performance.html#avoidcalendardatecreation", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AvoidFileStream (Java, Performance)", +"tags": "", +"keywords": "AvoidFileStream", +"url": "pmd_rules_java_performance.html#avoidfilestream", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AvoidInstantiatingObjectsInLoops (Java, Performance)", +"tags": "", +"keywords": "AvoidInstantiatingObjectsInLoops", +"url": "pmd_rules_java_performance.html#avoidinstantiatingobjectsinloops", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AvoidUsingShortType (Java, Performance)", +"tags": "", +"keywords": "AvoidUsingShortType", +"url": "pmd_rules_java_performance.html#avoidusingshorttype", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "BigIntegerInstantiation (Java, Performance)", +"tags": "", +"keywords": "BigIntegerInstantiation", +"url": "pmd_rules_java_performance.html#bigintegerinstantiation", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "BooleanInstantiation (Java, Performance)", +"tags": "", +"keywords": "BooleanInstantiation", +"url": "pmd_rules_java_performance.html#booleaninstantiation", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "ByteInstantiation (Java, Performance)", +"tags": "", +"keywords": "ByteInstantiation", +"url": "pmd_rules_java_performance.html#byteinstantiation", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "ConsecutiveAppendsShouldReuse (Java, Performance)", +"tags": "", +"keywords": "ConsecutiveAppendsShouldReuse", +"url": "pmd_rules_java_performance.html#consecutiveappendsshouldreuse", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "ConsecutiveLiteralAppends (Java, Performance)", +"tags": "", +"keywords": "ConsecutiveLiteralAppends", +"url": "pmd_rules_java_performance.html#consecutiveliteralappends", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "InefficientEmptyStringCheck (Java, Performance)", +"tags": "", +"keywords": "InefficientEmptyStringCheck", +"url": "pmd_rules_java_performance.html#inefficientemptystringcheck", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "InefficientStringBuffering (Java, Performance)", +"tags": "", +"keywords": "InefficientStringBuffering", +"url": "pmd_rules_java_performance.html#inefficientstringbuffering", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "InsufficientStringBufferDeclaration (Java, Performance)", +"tags": "", +"keywords": "InsufficientStringBufferDeclaration", +"url": "pmd_rules_java_performance.html#insufficientstringbufferdeclaration", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "IntegerInstantiation (Java, Performance)", +"tags": "", +"keywords": "IntegerInstantiation", +"url": "pmd_rules_java_performance.html#integerinstantiation", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "LongInstantiation (Java, Performance)", +"tags": "", +"keywords": "LongInstantiation", +"url": "pmd_rules_java_performance.html#longinstantiation", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "OptimizableToArrayCall (Java, Performance)", +"tags": "", +"keywords": "OptimizableToArrayCall", +"url": "pmd_rules_java_performance.html#optimizabletoarraycall", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "RedundantFieldInitializer (Java, Performance)", +"tags": "", +"keywords": "RedundantFieldInitializer", +"url": "pmd_rules_java_performance.html#redundantfieldinitializer", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "SimplifyStartsWith (Java, Performance)", +"tags": "", +"keywords": "SimplifyStartsWith", +"url": "pmd_rules_java_performance.html#simplifystartswith", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "ShortInstantiation (Java, Performance)", +"tags": "", +"keywords": "ShortInstantiation", +"url": "pmd_rules_java_performance.html#shortinstantiation", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "StringInstantiation (Java, Performance)", +"tags": "", +"keywords": "StringInstantiation", +"url": "pmd_rules_java_performance.html#stringinstantiation", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "StringToString (Java, Performance)", +"tags": "", +"keywords": "StringToString", +"url": "pmd_rules_java_performance.html#stringtostring", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "TooFewBranchesForASwitchStatement (Java, Performance)", +"tags": "", +"keywords": "TooFewBranchesForASwitchStatement", +"url": "pmd_rules_java_performance.html#toofewbranchesforaswitchstatement", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "UnnecessaryWrapperObjectCreation (Java, Performance)", +"tags": "", +"keywords": "UnnecessaryWrapperObjectCreation", +"url": "pmd_rules_java_performance.html#unnecessarywrapperobjectcreation", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "UseArrayListInsteadOfVector (Java, Performance)", +"tags": "", +"keywords": "UseArrayListInsteadOfVector", +"url": "pmd_rules_java_performance.html#usearraylistinsteadofvector", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "UseArraysAsList (Java, Performance)", +"tags": "", +"keywords": "UseArraysAsList", +"url": "pmd_rules_java_performance.html#usearraysaslist", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "UseIndexOfChar (Java, Performance)", +"tags": "", +"keywords": "UseIndexOfChar", +"url": "pmd_rules_java_performance.html#useindexofchar", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "UseIOStreamsWithApacheCommonsFileItem (Java, Performance)", +"tags": "", +"keywords": "UseIOStreamsWithApacheCommonsFileItem", +"url": "pmd_rules_java_performance.html#useiostreamswithapachecommonsfileitem", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "UselessStringValueOf (Java, Performance)", +"tags": "", +"keywords": "UselessStringValueOf", +"url": "pmd_rules_java_performance.html#uselessstringvalueof", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "UseStringBufferForStringAppends (Java, Performance)", +"tags": "", +"keywords": "UseStringBufferForStringAppends", +"url": "pmd_rules_java_performance.html#usestringbufferforstringappends", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "UseStringBufferLength (Java, Performance)", +"tags": "", +"keywords": "UseStringBufferLength", +"url": "pmd_rules_java_performance.html#usestringbufferlength", +"summary": "Rules that flag suboptimal code." +} + + + + + +, + + + + + + + +{ +"title": "Performance (XSL, Performance)", +"tags": "", +"keywords": "Performance", +"url": "pmd_rules_xsl_performance.html#performance", +"summary": "Rules that flag suboptimal code." +} +, + +{ +"title": "AvoidAxisNavigation (XSL, Performance)", +"tags": "", +"keywords": "AvoidAxisNavigation", +"url": "pmd_rules_xsl_performance.html#avoidaxisnavigation", +"summary": "Rules that flag suboptimal code." +} + + + + + +, + + + + + +{ +"title": "PLSQL Rules", +"tags": "rule_referencesplsql", +"keywords": "", +"url": "pmd_rules_plsql.html", +"summary": "Index of all built-in rules available for PLSQL" +} + + + +, + + + + + +{ +"title": "Report formats for PMD", +"tags": "pmduserdocs", +"keywords": "formatsrenderers", +"url": "pmd_userdocs_report_formats.html", +"summary": "Overview of the built-in report formats for PMD" +} + + + +, + + + + + +{ +"title": "Pmdtester", +"tags": "devdocs", +"keywords": "", +"url": "pmd_devdocs_pmdtester.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Maven POM Rules", +"tags": "rule_referencespom", +"keywords": "", +"url": "pmd_rules_pom.html", +"summary": "Index of all built-in rules available for Maven POM" +} + + + +, + + + + + +{ +"title": "Products/books related to PMD", +"tags": "", +"keywords": "", +"url": "pmd_projectdocs_trivia_products.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "PMD Release Notes", +"tags": "", +"keywords": "changelog, release notes", +"url": "pmd_release_notes.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Old Release Notes", +"tags": "", +"keywords": "", +"url": "pmd_release_notes_old.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Release process", +"tags": "", +"keywords": "", +"url": "pmd_projectdocs_committers_releasing.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Roadmap", +"tags": "devdocs", +"keywords": "", +"url": "pmd_devdocs_roadmap.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Rule deprecation policy", +"tags": "devdocs", +"keywords": "", +"url": "pmd_devdocs_rule_deprecation_policy.html", +"summary": "Describes when and how rules are deprecated" +} + + + +, + + + + + +{ +"title": "Rule guidelines", +"tags": "extendinguserdocs", +"keywords": "", +"url": "pmd_userdocs_extending_rule_guidelines.html", +"summary": "Rule Guidelines, or the last touches to a rule" +} + + + +, + + + + + +{ +"title": "Scala Rules", +"tags": "rule_referencesscala", +"keywords": "", +"url": "pmd_rules_scala.html", +"summary": "Index of all built-in rules available for Scala" +} + + + +, + + + + + + + + + +{ +"title": "Security (Java Server Pages, Security)", +"tags": "", +"keywords": "Security", +"url": "pmd_rules_jsp_security.html#security", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "IframeMissingSrcAttribute (Java Server Pages, Security)", +"tags": "", +"keywords": "IframeMissingSrcAttribute", +"url": "pmd_rules_jsp_security.html#iframemissingsrcattribute", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "NoUnsanitizedJSPExpression (Java Server Pages, Security)", +"tags": "", +"keywords": "NoUnsanitizedJSPExpression", +"url": "pmd_rules_jsp_security.html#nounsanitizedjspexpression", +"summary": "Rules that flag potential security flaws." +} + + + + + +, + + + + + + + +{ +"title": "Security (Apex, Security)", +"tags": "", +"keywords": "Security", +"url": "pmd_rules_apex_security.html#security", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexBadCrypto (Apex, Security)", +"tags": "", +"keywords": "ApexBadCrypto", +"url": "pmd_rules_apex_security.html#apexbadcrypto", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexCRUDViolation (Apex, Security)", +"tags": "", +"keywords": "ApexCRUDViolation", +"url": "pmd_rules_apex_security.html#apexcrudviolation", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexCSRF (Apex, Security)", +"tags": "", +"keywords": "ApexCSRF", +"url": "pmd_rules_apex_security.html#apexcsrf", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexDangerousMethods (Apex, Security)", +"tags": "", +"keywords": "ApexDangerousMethods", +"url": "pmd_rules_apex_security.html#apexdangerousmethods", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexInsecureEndpoint (Apex, Security)", +"tags": "", +"keywords": "ApexInsecureEndpoint", +"url": "pmd_rules_apex_security.html#apexinsecureendpoint", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexOpenRedirect (Apex, Security)", +"tags": "", +"keywords": "ApexOpenRedirect", +"url": "pmd_rules_apex_security.html#apexopenredirect", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexSharingViolations (Apex, Security)", +"tags": "", +"keywords": "ApexSharingViolations", +"url": "pmd_rules_apex_security.html#apexsharingviolations", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexSOQLInjection (Apex, Security)", +"tags": "", +"keywords": "ApexSOQLInjection", +"url": "pmd_rules_apex_security.html#apexsoqlinjection", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexSuggestUsingNamedCred (Apex, Security)", +"tags": "", +"keywords": "ApexSuggestUsingNamedCred", +"url": "pmd_rules_apex_security.html#apexsuggestusingnamedcred", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexXSSFromEscapeFalse (Apex, Security)", +"tags": "", +"keywords": "ApexXSSFromEscapeFalse", +"url": "pmd_rules_apex_security.html#apexxssfromescapefalse", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "ApexXSSFromURLParam (Apex, Security)", +"tags": "", +"keywords": "ApexXSSFromURLParam", +"url": "pmd_rules_apex_security.html#apexxssfromurlparam", +"summary": "Rules that flag potential security flaws." +} + + + + + +, + + + + + + + +{ +"title": "Security (Salesforce VisualForce, Security)", +"tags": "", +"keywords": "Security", +"url": "pmd_rules_vf_security.html#security", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "VfCsrf (Salesforce VisualForce, Security)", +"tags": "", +"keywords": "VfCsrf", +"url": "pmd_rules_vf_security.html#vfcsrf", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "VfUnescapeEl (Salesforce VisualForce, Security)", +"tags": "", +"keywords": "VfUnescapeEl", +"url": "pmd_rules_vf_security.html#vfunescapeel", +"summary": "Rules that flag potential security flaws." +} + + + + + +, + + + + + + + +{ +"title": "Security (Java, Security)", +"tags": "", +"keywords": "Security", +"url": "pmd_rules_java_security.html#security", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "HardCodedCryptoKey (Java, Security)", +"tags": "", +"keywords": "HardCodedCryptoKey", +"url": "pmd_rules_java_security.html#hardcodedcryptokey", +"summary": "Rules that flag potential security flaws." +} +, + +{ +"title": "InsecureCryptoIv (Java, Security)", +"tags": "", +"keywords": "InsecureCryptoIv", +"url": "pmd_rules_java_security.html#insecurecryptoiv", +"summary": "Rules that flag potential security flaws." +} + + + + + +, + + + + + +{ +"title": "Similar projects", +"tags": "", +"keywords": "", +"url": "pmd_projectdocs_trivia_similarprojects.html", +"summary": "" +} + + + +, + + + + + + + +{ +"title": "Suppressing warnings", +"tags": "userdocs", +"keywords": "suppressingwarningssuppresswarningsnopmdviolationSuppressXPathviolationSuppressRegex", +"url": "pmd_userdocs_suppressing_warnings.html", +"summary": "Learn how to suppress some rule violations, from the source code using annotations or comments, or globally from the ruleset" +} + + + +, + + + + + + + + + + + + + + + + + + + + + + + + + +{ +"title": "Testing your rules", +"tags": "extendinguserdocs", +"keywords": "", +"url": "pmd_userdocs_extending_testing.html", +"summary": "Learn how to use PMD's simple test framework for unit testing rules." +} + + + +, + + + + + +{ +"title": "Tools / Integrations", +"tags": "userdocstools", +"keywords": "", +"url": "pmd_userdocs_tools.html", +"summary": "" +} + + + +, + + + + + + + + + +{ +"title": "Salesforce VisualForce Rules", +"tags": "rule_referencesvf", +"keywords": "", +"url": "pmd_rules_vf.html", +"summary": "Index of all built-in rules available for Salesforce VisualForce" +} + + + +, + + + + + +{ +"title": "VM Rules", +"tags": "rule_referencesvm", +"keywords": "", +"url": "pmd_rules_vm.html", +"summary": "Index of all built-in rules available for VM" +} + + + +, + + + + + +{ +"title": "Writing documentation", +"tags": "devdocs", +"keywords": "documentation, jekyll, markdown", +"url": "pmd_devdocs_writing_documentation.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Writing a custom rule", +"tags": "extendinguserdocs", +"keywords": "", +"url": "pmd_userdocs_extending_writing_java_rules.html", +"summary": "Learn how to write a custom rule for PMD" +} + + + +, + + + + + +{ +"title": "Writing a custom rule", +"tags": "extendinguserdocs", +"keywords": "", +"url": "pmd_userdocs_extending_writing_pmd_rules.html", +"summary": "" +} + + + +, + + + + + +{ +"title": "Introduction to writing PMD rules", +"tags": "extendinguserdocsgetting_started", +"keywords": "", +"url": "pmd_userdocs_extending_writing_rules_intro.html", +"summary": "Writing your own PMD rules" +} + + + +, + + + + + +{ +"title": "Writing XPath rules", +"tags": "extendinguserdocs", +"keywords": "", +"url": "pmd_userdocs_extending_writing_xpath_rules.html", +"summary": "This page describes XPath rule support in more details" +} + + + +, + + + + + +{ +"title": "XML Rules", +"tags": "rule_referencesxml", +"keywords": "", +"url": "pmd_rules_xml.html", +"summary": "Index of all built-in rules available for XML" +} + + + +, + + + + + +{ +"title": "XSL Rules", +"tags": "rule_referencesxsl", +"keywords": "", +"url": "pmd_rules_xsl.html", +"summary": "Index of all built-in rules available for XSL" +} + + + +, + + + + + +{ +"title": "Your first rule XPath", +"tags": "extendinguserdocs", +"keywords": "", +"url": "pmd_userdocs_extending_your_first_rule.html", +"summary": "Introduction to rule writing through an example." +} + + + + + + + + + +] diff --git a/sitemap.xml b/sitemap.xml new file mode 100644 index 0000000000..d09943ce93 --- /dev/null +++ b/sitemap.xml @@ -0,0 +1,675 @@ + + + + + + + + + + + https://pmd.github.io/pmd/pmd_devdocs_major_adding_new_cpd_language.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_major_adding_new_language.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_major_adding_new_metrics_framework.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_tools_ant.html + + + + + + https://pmd.github.io/pmd/pmd_rules_apex.html + + + + + + https://pmd.github.io/pmd/pmd_apex_metrics_index.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_experimental_ast_dump.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_best_practices.html + + + + + + https://pmd.github.io/pmd/pmd_rules_jsp_bestpractices.html + + + + + + https://pmd.github.io/pmd/pmd_rules_ecmascript_bestpractices.html + + + + + + https://pmd.github.io/pmd/pmd_rules_apex_bestpractices.html + + + + + + https://pmd.github.io/pmd/pmd_rules_vm_bestpractices.html + + + + + + https://pmd.github.io/pmd/pmd_rules_plsql_bestpractices.html + + + + + + https://pmd.github.io/pmd/pmd_rules_modelica_bestpractices.html + + + + + + https://pmd.github.io/pmd/pmd_rules_java_bestpractices.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_building.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_tools_ci.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_cli_reference.html + + + + + + https://pmd.github.io/pmd/pmd_rules_jsp_codestyle.html + + + + + + https://pmd.github.io/pmd/pmd_rules_ecmascript_codestyle.html + + + + + + https://pmd.github.io/pmd/pmd_rules_apex_codestyle.html + + + + + + https://pmd.github.io/pmd/pmd_rules_plsql_codestyle.html + + + + + + https://pmd.github.io/pmd/pmd_rules_java_codestyle.html + + + + + + https://pmd.github.io/pmd/pmd_rules_xsl_codestyle.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_configuring_rules.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_cpd.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_cpd_report_formats.html + + + + + + https://pmd.github.io/pmd/pmd_projectdocs_credits.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_defining_properties.html + + + + + + https://pmd.github.io/pmd/pmd_rules_jsp_design.html + + + + + + https://pmd.github.io/pmd/pmd_rules_apex_design.html + + + + + + https://pmd.github.io/pmd/pmd_rules_vm_design.html + + + + + + https://pmd.github.io/pmd/pmd_rules_plsql_design.html + + + + + + https://pmd.github.io/pmd/pmd_rules_java_design.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_designer_reference.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_development.html + + + + + + https://pmd.github.io/pmd/pmd_rules_apex_documentation.html + + + + + + https://pmd.github.io/pmd/pmd_rules_java_documentation.html + + + + + + https://pmd.github.io/pmd/pmd_rules_ecmascript.html + + + + + + https://pmd.github.io/pmd/pmd_rules_jsp_errorprone.html + + + + + + https://pmd.github.io/pmd/pmd_rules_ecmascript_errorprone.html + + + + + + https://pmd.github.io/pmd/pmd_rules_apex_errorprone.html + + + + + + https://pmd.github.io/pmd/pmd_rules_vm_errorprone.html + + + + + + https://pmd.github.io/pmd/pmd_rules_plsql_errorprone.html + + + + + + https://pmd.github.io/pmd/pmd_rules_java_errorprone.html + + + + + + https://pmd.github.io/pmd/pmd_rules_pom_errorprone.html + + + + + + https://pmd.github.io/pmd/pmd_rules_xml_errorprone.html + + + + + + https://pmd.github.io/pmd/pmd_projectdocs_faq.html + + + + + + + + https://pmd.github.io/pmd/pmd_userdocs_tools_gradle.html + + + + + + https://pmd.github.io/pmd/pmd_about_help.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_how_pmd_works.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_incremental_analysis.html + + + + + + https://pmd.github.io/pmd/index.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_installation.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_tools_java_api.html + + + + + + https://pmd.github.io/pmd/pmd_rules_java.html + + + + + + https://pmd.github.io/pmd/pmd_java_metrics_index.html + + + + + + https://pmd.github.io/pmd/pmd_languages_jsp.html + + + + + + https://pmd.github.io/pmd/pmd_rules_jsp.html + + + + + + https://pmd.github.io/pmd/license.html + + + + + + https://pmd.github.io/pmd/pmd_projectdocs_committers_main_landing_page.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_making_rulesets.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_tools_maven.html + + + + + + https://pmd.github.io/pmd/pmd_projectdocs_trivia_meaning.html + + + + + + https://pmd.github.io/pmd/pmd_projectdocs_committers_merging_pull_requests.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_metrics_howto.html + + + + + + https://pmd.github.io/pmd/pmd_rules_modelica.html + + + + + + https://pmd.github.io/pmd/pmd_rules_java_multithreading.html + + + + + + https://pmd.github.io/pmd/js/mydoc_scroll.html + + + + + + https://pmd.github.io/pmd/news.html + + + + + + https://pmd.github.io/pmd/pmd_projectdocs_trivia_news.html + + + + + + https://pmd.github.io/pmd/news_archive.html + + + + + + https://pmd.github.io/pmd/pmd_next_major_development.html + + + + + + https://pmd.github.io/pmd/pmd_rules_apex_performance.html + + + + + + https://pmd.github.io/pmd/pmd_rules_java_performance.html + + + + + + https://pmd.github.io/pmd/pmd_rules_xsl_performance.html + + + + + + https://pmd.github.io/pmd/pmd_rules_plsql.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_report_formats.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_pmdtester.html + + + + + + https://pmd.github.io/pmd/pmd_rules_pom.html + + + + + + https://pmd.github.io/pmd/pmd_projectdocs_trivia_products.html + + + + + + https://pmd.github.io/pmd/pmd_release_notes.html + + + + + + https://pmd.github.io/pmd/pmd_release_notes_old.html + + + + + + https://pmd.github.io/pmd/pmd_projectdocs_committers_releasing.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_roadmap.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_rule_deprecation_policy.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_rule_guidelines.html + + + + + + https://pmd.github.io/pmd/pmd_rules_scala.html + + + + + + + + https://pmd.github.io/pmd/pmd_rules_jsp_security.html + + + + + + https://pmd.github.io/pmd/pmd_rules_apex_security.html + + + + + + https://pmd.github.io/pmd/pmd_rules_vf_security.html + + + + + + https://pmd.github.io/pmd/pmd_rules_java_security.html + + + + + + https://pmd.github.io/pmd/pmd_projectdocs_trivia_similarprojects.html + + + + + + + + https://pmd.github.io/pmd/pmd_userdocs_suppressing_warnings.html + + + + + + + + + + + + + + + + + + + + + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_testing.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_tools.html + + + + + + + + + + https://pmd.github.io/pmd/pmd_rules_vf.html + + + + + + https://pmd.github.io/pmd/pmd_rules_vm.html + + + + + + https://pmd.github.io/pmd/pmd_devdocs_writing_documentation.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_writing_java_rules.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_writing_pmd_rules.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_writing_rules_intro.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_writing_xpath_rules.html + + + + + + https://pmd.github.io/pmd/pmd_rules_xml.html + + + + + + https://pmd.github.io/pmd/pmd_rules_xsl.html + + + + + + https://pmd.github.io/pmd/pmd_userdocs_extending_your_first_rule.html + + + + \ No newline at end of file diff --git a/sitemap_generator.sh b/sitemap_generator.sh new file mode 100755 index 0000000000..03e25a0bcf --- /dev/null +++ b/sitemap_generator.sh @@ -0,0 +1,56 @@ +#!/usr/bin/env bash + +# Sitemap generator for pmd.github.io main landing page. +# Assumes we have the latest version of the site under "latest" +# https://www.sitemaps.org/protocol.html + +WEBSITE_PREFIX="https://pmd.github.io/" +DOC_PREFIX="latest/" +DATE=`date +%Y-%m-%d` +# Priority is relative to the website, can be chosen in {0.1, 0.2, ..., 1} +# Default priority is 0.5 +LATEST_PRIORITY=0.8 + + +# Writes to standard output + +cat << HEADER_END + + + + + ${WEBSITE_PREFIX}index.html + 1 + monthly + $DATE + + + + ${WEBSITE_PREFIX}${DOC_PREFIX}index.html + 0.9 + monthly + $DATE + + + + +HEADER_END + + +for page in ${DOC_PREFIX}pmd_*.html +do + + cat << ENTRY_END + + ${WEBSITE_PREFIX}$page + $LATEST_PRIORITY + monthly + $DATE + + +ENTRY_END + +done + +echo "" + diff --git a/tag_devdocs.html b/tag_devdocs.html new file mode 100644 index 0000000000..d4bb17c3ff --- /dev/null +++ b/tag_devdocs.html @@ -0,0 +1,1949 @@ + + + + + + + + +Developer and contributor documentation | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Developer and contributor documentation

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    How to add a new CPD languagePage How to add a new CPD language
    Adding PMD support for a new languagePage How to add a new language to PMD.
    Adding support for metrics to a languagePage PMD's Java module has an extensive framework for the calculation of metrics, which allows rule developers to implement and use new code metrics very simply. ...
    Creating XML dump of the ASTPage Creating a XML representation of the AST allows to analyze the AST with other tools.
    Building PMD from sourcePage Note: TODO add IDE specific indications Compiling PMD JDK 11 or higher Note: While Java 11 is required for building, running PMD only requires Java 7 (or Java 8 for Apex...
    Developer ResourcesPage The next version of PMD will be developed in parallel with this release. We will release additional bugfix versions as needed. Source Code The complete source code can be found on github: github.com/pmd/pmd - main PMD repository. Includes all the code to support all languages, including this...
    How PMD WorksPage Processing overview of the different steps taken by PMD.
    PmdtesterPage Introduction Pmdtester is a regression testing tool that ensures no new problems and unexpected behaviors will be introduced to PMD after fixing an issue. It can also be used to verify, that new rules work as expected. It has been integrated into travis CI and is actually used automatically...
    RoadmapPage TODO: Update Future direction projects, plans Google Summer of Code Future directions Want to know what’s coming? Or, better, wanna contribute ? Here is the page listing what are our plans - when we have ones, for the future of PMD. It also give you hints at...
    Rule deprecation policyPage Describes when and how rules are deprecated
    Writing documentationPage PMD's documentation uses [Jekyll](https://jekyllrb.com/) with the [I'd rather be writing Jekyll Theme](http://idratherbewriting.com/documentation-theme-jekyll/index.html). Here are some quick tips. ## Format The pages are in general in [Github Flavored Markdown](https://kramdown.gettalong.org/parser/gfm.html). ## Structure The documentation sources can be found in two places based on how they are generated: - the ones that are...
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tag_extending.html b/tag_extending.html new file mode 100644 index 0000000000..e330169a4a --- /dev/null +++ b/tag_extending.html @@ -0,0 +1,1973 @@ + + + + + + + + +Extending PMD | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Extending PMD

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    How to add a new CPD languagePage How to add a new CPD language
    Adding PMD support for a new languagePage How to add a new language to PMD.
    Adding support for metrics to a languagePage PMD's Java module has an extensive framework for the calculation of metrics, which allows rule developers to implement and use new code metrics very simply. ...
    Index of Apex code metricsPage Index of the code metrics available out of the box to Apex rule developers.
    Defining rule propertiesPage Learn how to define your own properties both for Java and XPath rules.
    The rule designerPage Learn about the usage and features of the rule designer.
    Index of Java code metricsPage Index of the code metrics available out of the box to Java rule developers.
    Using and defining code metrics for custom rulesPage Since version 6.0.0, PMD is enhanced with the ability to compute code metrics on Java and Apex source (the so-called Metrics Framework). This framework provi...
    Rule guidelinesPage Rule Guidelines, or the last touches to a rule
    Testing your rulesPage Learn how to use PMD's simple test framework for unit testing rules.
    Writing a custom rulePage Learn how to write a custom rule for PMD
    Writing a custom rulePage The information on this page has been split into several separate pages. Please update your bookmarks: * [Introduction to writing rules](pmd_userdocs_extending_writing_rules_intro.html) * [Your First Rule](pmd_userdocs_extending_your_first_rule.html) introduces the basic development process of a rule with a running example * [Writing XPath Rules](pmd_userdocs_extending_writing_xpath_rules.html) explains a bit more about XPath rules and our...
    Introduction to writing PMD rulesPage Writing your own PMD rules
    Writing XPath rulesPage This page describes XPath rule support in more details
    Your first rule XPathPage Introduction to rule writing through an example.
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tag_getting_started.html b/tag_getting_started.html new file mode 100644 index 0000000000..4141129a25 --- /dev/null +++ b/tag_getting_started.html @@ -0,0 +1,1907 @@ + + + + + + + + +Getting started pages | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Getting started pages

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    Configuring rulesPage Learn how to configure your rules directly from the ruleset XML.
    Installation and basic CLI usagePage Sums up the first steps to set up a CLI installation and get started using PMD
    Making rulesetsPage A ruleset is an XML configuration file, which describes a collection of rules to be executed in a PMD run. PMD includes built-in rulesets to run quick analys...
    Introduction to writing PMD rulesPage Writing your own PMD rules
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tag_languages.html b/tag_languages.html new file mode 100644 index 0000000000..3d5916d863 --- /dev/null +++ b/tag_languages.html @@ -0,0 +1,1883 @@ + + + + + + + + +Supported Lanugages | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Supported Lanugages

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tag_metrics.html b/tag_metrics.html new file mode 100644 index 0000000000..951e3b64d4 --- /dev/null +++ b/tag_metrics.html @@ -0,0 +1,1907 @@ + + + + + + + + +Code metrics | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Code metrics

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    Adding support for metrics to a languagePage PMD's Java module has an extensive framework for the calculation of metrics, which allows rule developers to implement and use new code metrics very simply. ...
    Index of Apex code metricsPage Index of the code metrics available out of the box to Apex rule developers.
    Index of Java code metricsPage Index of the code metrics available out of the box to Java rule developers.
    Using and defining code metrics for custom rulesPage Since version 6.0.0, PMD is enhanced with the ability to compute code metrics on Java and Apex source (the so-called Metrics Framework). This framework provi...
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tag_release_notes.html b/tag_release_notes.html new file mode 100644 index 0000000000..d9c29c89a5 --- /dev/null +++ b/tag_release_notes.html @@ -0,0 +1,1883 @@ + + + + + + + + +Release Notes Pages | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Release Notes Pages

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tag_rule_references.html b/tag_rule_references.html new file mode 100644 index 0000000000..a58b94c409 --- /dev/null +++ b/tag_rule_references.html @@ -0,0 +1,1955 @@ + + + + + + + + +Rule references | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Rule references

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    Apex RulesPage Index of all built-in rules available for Apex
    Ecmascript RulesPage Index of all built-in rules available for Ecmascript
    Java RulesPage Index of all built-in rules available for Java
    Java Server Pages RulesPage Index of all built-in rules available for Java Server Pages
    Modelica RulesPage Index of all built-in rules available for Modelica
    PLSQL RulesPage Index of all built-in rules available for PLSQL
    Maven POM RulesPage Index of all built-in rules available for Maven POM
    Scala RulesPage Index of all built-in rules available for Scala
    Salesforce VisualForce RulesPage Index of all built-in rules available for Salesforce VisualForce
    VM RulesPage Index of all built-in rules available for VM
    XML RulesPage Index of all built-in rules available for XML
    XSL RulesPage Index of all built-in rules available for XSL
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tag_tools.html b/tag_tools.html new file mode 100644 index 0000000000..36159a741e --- /dev/null +++ b/tag_tools.html @@ -0,0 +1,1919 @@ + + + + + + + + +Tools and integrations | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Tools and integrations

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    Ant Task UsagePage PMD Description Runs a set of static code analysis rules on some source code files and generates a list of problems found. Installation Before you can use the pmd task in your ant build.xml file, you need to install PMD and its libraries...
    Continuous Integrations pluginsPage Introduction PMD can be integrate through some of the Continuous Integration tools that exist now. Here is a list of known (to us) plugin to do so. Hudson Plugin Hafner Ullrich has developed a PMD plugin for Hudson. Please check the plugin homepage for more info. <h2...
    GradlePage The Gradle Build Tool provides a PMD Plugin that can be added to your build configuration. Technically it is based on the Ant Task. Example In your build.gradle add the following: plugins { id 'pmd' } Custom ruleset...
    PMD Java APIPage The easiest way to run PMD is to just use a build plugin in your favorite build tool like Apache Ant, Apache Maven or Gradle. There are also many integrations for IDEs available, see Tools. If you have your own build tool or want to integrate...
    Maven PMD PluginPage Maven 2 and 3 Running the pmd plugin Choosing the plugin version When adding the maven-pmd-plugin to your pom.xml, you need to select a version. To figure out the latest available version, have a look at the official maven-pmd-plugin documentation. As of March 2020, the current...
    Tools / IntegrationsPage ## Automated Code Review ### Codacy [Codacy](https://www.codacy.com/) automates code reviews and monitors code quality on every commit and pull request. It gives visibility into the technical debt and it can track code style and security issues, code coverage, code duplication, cyclomatic complexity and enforce best practices. Codacy is static analysis...
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tag_troubleshooting.html b/tag_troubleshooting.html new file mode 100644 index 0000000000..3ad1051dc6 --- /dev/null +++ b/tag_troubleshooting.html @@ -0,0 +1,1883 @@ + + + + + + + + +Troubleshooting pages | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    Troubleshooting pages

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tag_userdocs.html b/tag_userdocs.html new file mode 100644 index 0000000000..e78052954b --- /dev/null +++ b/tag_userdocs.html @@ -0,0 +1,2039 @@ + + + + + + + + +User documentation | PMD Source Code Analyzer + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + + + +
    +
     
    + +
    + + + +
    + + + + + + + + + + + + + + +
    + + + + +
    +
    +

    User documentation

    +
    + + + +
    + + + + + + + + +
    + + + + + + + + + + Edit me + + + +

    The following pages and posts are tagged with

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    TitleTypeExcerpt
    Ant Task UsagePage PMD Description Runs a set of static code analysis rules on some source code files and generates a list of problems found. Installation Before you can use the pmd task in your ant build.xml file, you need to install PMD and its libraries...
    Best PracticesPage Choose the rules that are right for you Running every existing rule will result in a huge number of rule violations, most of which will be unimportant. Having to sort through a thousand line report to find the few you’re really interested in takes all the fun out of...
    Continuous Integrations pluginsPage Introduction PMD can be integrate through some of the Continuous Integration tools that exist now. Here is a list of known (to us) plugin to do so. Hudson Plugin Hafner Ullrich has developed a PMD plugin for Hudson. Please check the plugin homepage for more info. <h2...
    PMD CLI referencePage Full reference for PMD's command-line interface, including options, output formats and supported languages
    Configuring rulesPage Learn how to configure your rules directly from the ruleset XML.
    Finding duplicated code with CPDPage Learn how to use CPD, the copy-paste detector shipped with PMD.
    Report formats for CPDPage Overview of the built-in report formats for CPD
    Defining rule propertiesPage Learn how to define your own properties both for Java and XPath rules.
    The rule designerPage Learn about the usage and features of the rule designer.
    GradlePage The Gradle Build Tool provides a PMD Plugin that can be added to your build configuration. Technically it is based on the Ant Task. Example In your build.gradle add the following: plugins { id 'pmd' } Custom ruleset...
    Incremental AnalysisPage Explains how to use incremental analysis to speed up analysis
    Installation and basic CLI usagePage Sums up the first steps to set up a CLI installation and get started using PMD
    PMD Java APIPage The easiest way to run PMD is to just use a build plugin in your favorite build tool like Apache Ant, Apache Maven or Gradle. There are also many integrations for IDEs available, see Tools. If you have your own build tool or want to integrate...
    Making rulesetsPage A ruleset is an XML configuration file, which describes a collection of rules to be executed in a PMD run. PMD includes built-in rulesets to run quick analys...
    Maven PMD PluginPage Maven 2 and 3 Running the pmd plugin Choosing the plugin version When adding the maven-pmd-plugin to your pom.xml, you need to select a version. To figure out the latest available version, have a look at the official maven-pmd-plugin documentation. As of March 2020, the current...
    Using and defining code metrics for custom rulesPage Since version 6.0.0, PMD is enhanced with the ability to compute code metrics on Java and Apex source (the so-called Metrics Framework). This framework provi...
    Report formats for PMDPage Overview of the built-in report formats for PMD
    Rule guidelinesPage Rule Guidelines, or the last touches to a rule
    Suppressing warningsPage Learn how to suppress some rule violations, from the source code using annotations or comments, or globally from the ruleset
    Testing your rulesPage Learn how to use PMD's simple test framework for unit testing rules.
    Tools / IntegrationsPage ## Automated Code Review ### Codacy [Codacy](https://www.codacy.com/) automates code reviews and monitors code quality on every commit and pull request. It gives visibility into the technical debt and it can track code style and security issues, code coverage, code duplication, cyclomatic complexity and enforce best practices. Codacy is static analysis...
    Writing a custom rulePage Learn how to write a custom rule for PMD
    Writing a custom rulePage The information on this page has been split into several separate pages. Please update your bookmarks: * [Introduction to writing rules](pmd_userdocs_extending_writing_rules_intro.html) * [Your First Rule](pmd_userdocs_extending_your_first_rule.html) introduces the basic development process of a rule with a running example * [Writing XPath Rules](pmd_userdocs_extending_writing_xpath_rules.html) explains a bit more about XPath rules and our...
    Introduction to writing PMD rulesPage Writing your own PMD rules
    Writing XPath rulesPage This page describes XPath rule support in more details
    Your first rule XPathPage Introduction to rule writing through an example.
    + + + +
    + +
    + + + +
    + +
    + +
    +
    + +
    +
    + + +
    + +
    + +
    +
    + + + diff --git a/tooltips.html b/tooltips.html new file mode 100644 index 0000000000..6406932903 --- /dev/null +++ b/tooltips.html @@ -0,0 +1,75 @@ + + + Tooltip Demo + + + + + + + + + + + +

    Tooltip Demo

    + +

    This page is purposely separated out from the rest of theme so you can see the bare minimum code to add to a page, without all the other theme's code getting in the way.

    + +

    Content in the tooltips (actually "popovers" according to Bootstrap lingo) can be pulled in dynamically by placing the JSON file on a remote host.

    + + + + + +

    Basketball

    + +

    Baseball

    + +

    Football

    + +

    Soccer

    + diff --git a/tooltips.json b/tooltips.json new file mode 100644 index 0000000000..73773c9ef3 --- /dev/null +++ b/tooltips.json @@ -0,0 +1,29 @@ +{ +"entries": +[ + +{ +"doc_id": "baseball", +"body": "Baseball is considered America's pasttime sport, though that may be more of a historical term than a current one. There's a lot more excitement about football than baseball. A baseball game is somewhat of a snooze to watch, for the most part." +} , + +{ +"doc_id": "basketball", +"body": "Basketball is a sport involving two teams of five players each competing to put a ball through a small circular rim 10 feet above the ground. Basketball requires players to be in top physical condition, since they spend most of the game running back and forth along a 94-foot-long floor." +} , + +{ +"doc_id": "football", +"body": "No doubt the most fun sport to watch, football also manages to accrue the most injuries with the players. From concussions to blown knees, football players have short sport lives." +} , + +{ +"doc_id": "soccer", +"body": "If there's one sport that dominates the world landscape, it's soccer. However, US soccer fans are few and far between. Apart from the popularity of soccer during the World Cup, most people don't even know the name of the professional soccer organization in their area." +} + +] +} + + +