{"id":1370,"date":"2020-04-08T07:54:26","date_gmt":"2020-04-08T14:54:26","guid":{"rendered":"http:\/\/mitchmckenna.com\/blog\/?p=1370"},"modified":"2022-02-06T09:32:10","modified_gmt":"2022-02-06T16:32:10","slug":"is-your-code-up-to-sniff","status":"publish","type":"post","link":"http:\/\/mitchmckenna.com\/blog\/2020\/04\/is-your-code-up-to-sniff\/","title":{"rendered":"Is Your Code Up To Sniff?"},"content":{"rendered":"\n<p><strong>PHP Code Standards<\/strong><\/p>\n\n\n\n<figure class=\"wp-block-image\"><img decoding=\"async\" src=\"https:\/\/lh5.googleusercontent.com\/6HPAtv8NbvLvbntTHsqcbDF49ib4Jmabk39zMK3s92a94Nht1ifq3sV_j0n--ucS89bznavpfHyYDIAx-rzQN8Bu0T5gFGD19nLFanX5oT5v81p4pt1LUx9fj01yBkIuHxwR8Syu\" alt=\"\"\/><\/figure>\n\n\n\n<p>Following coding standards in PHP is now easier than ever. Let&#8217;s go over the benefits of following a coding standard, how to enforce it, and look at how modern tooling and new features in IDE\u2019s like PHPStorm makes it nicer than ever before.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Why Follow a Coding Standard?<\/h2>\n\n\n\n<ol class=\"wp-block-list\"><li><strong>Stop Wasting Time<\/strong><br \/>If you&#8217;ve ever worked with another developer or worked on a team, no doubt you&#8217;ve debated coding styles. Focus on what&#8217;s important (getting things done) and stop debating:<br \/>&#8211; Tabs vs spaces<br \/>&#8211; camelCase vs snake_case<br \/>&#8211; Opening brackets {} on new line or same line<br \/>&#8211; Control structure format<br \/>&#8211; TRUE\/FALSE\/NULL vs true\/false\/null<br \/>&#8211; Spacing that could go anywhere and everywhere<br \/>&#8211; &#8230; the list is never ending.<\/li><li><strong>More Readable Code<\/strong><br \/>Easier to read code comes from using a consistent code style. Your brain isn\u2019t distracted by the personal preferences of the previous developer. In Jason McCreary\u2019s book \u200f<a href=\"https:\/\/basecodefieldguide.com\/\">Basecode<\/a>, he does an excellent job of explaining a concept which Kevlin Henney has coined \u201c<a href=\"https:\/\/www.infoq.com\/presentations\/7-ineffective-coding-habits\/\">visual honesty<\/a>\u201d. It\u2019s the concept that you should be able to generally tell what\u2019s happening in a function just by the shape of the code blocks. He illustrates this by showing that if all the characters were <a href=\"https:\/\/twitter.com\/gonedark\/status\/951477799289786369\">replaced with X\u2019s<\/a>, when code is formatted properly, you can still recognize what\u2019s happening. I had noticed the benefits of this before, but had a hard time putting it into words; what an excellent way to demonstrate it!<\/li><li><strong>Save Money<\/strong><br \/>Time is money, whether it&#8217;s your time or the company&#8217;s. Save time in both new developer on-boarding,<strong> <\/strong>as well as on code maintenance.<strong> <\/strong>New hire ramp-up time can be reduced if your codebase is in a popular format. It increases the chances the new developer has previous experience developing, reading and writing code in that format. For maintenance, code reviews are simpler, as there are less stylistic changes from developer to developer. As code reviews and new hires are a constant, this savings in developer time translates to real cost savings for the business over time.<\/li><\/ol>\n\n\n\n<h2 class=\"wp-block-heading\">EditorConfig<\/h2>\n\n\n\n<p>At the very least, a project in any language should add an <a href=\"https:\/\/editorconfig.org\">EditorConfig<\/a>. EditorConfig is a widely adopted open standard that helps maintain <em>general<\/em> coding styles. It\u2019s a file which sits in the root of your project that many IDE\u2019s will automatically (or with a plugin) read settings to set tabs vs spaces, tab length to 4 spaces, etc. PHPStorm now has EditorConfig support built-in since <a href=\"https:\/\/blog.jetbrains.com\/phpstorm\/2019\/07\/phpstorm-2019-2-release\/#editorconfig\">PHPStorm 2019.2<\/a>, VS Code has a <a href=\"https:\/\/marketplace.visualstudio.com\/items?itemName=EditorConfig.EditorConfig\">plugin<\/a>, and so does <a href=\"https:\/\/editorconfig.org\/#download\">almost all code editors<\/a>.&nbsp;<\/p>\n\n\n\n<p>EditorConfig can only specify generic coding style settings, for the rest of the article we\u2019ll look at standards and tools that go a lot further, specific to PHP.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">PSR-12<\/h2>\n\n\n\n<p>In 2009, all the popular frameworks came together (<a href=\"https:\/\/www.php-fig.org\" class=\"aioseop-link\">PHP-FIG<\/a>) and agreed on common coding standards PSR-1 and PSR-2. Since then, PSR-2 (which builds upon PSR-1) had become the defacto coding standard in PHP, which is nice because you know any framework or 3rd-party php package you come across will follow the same coding style.&nbsp;<\/p>\n\n\n\n<p>In August 2019, <a href=\"https:\/\/twitter.com\/phpfig\/status\/1160902933854203904\">PSR-12 was approved<\/a>, adding rules for new language features introduced in PHP 7. PSR-12 is now the recommended standard to follow.<\/p>\n\n\n\n<p><strong>But We Can\u2019t Follow PSR-12 Because Of ________<\/strong><\/p>\n\n\n\n<p>Here\u2019s some of the popular reasons holding team\u2019s back from following PSR-12:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\"><p><em>\u201cWe have so much code already, it\u2019d be too much work to convert it all.\u201d<\/em><\/p><\/blockquote>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\"><p><em>\u201cWe have certain folders we can\u2019t (or don\u2019t want to) touch.\u201d<\/em><\/p><\/blockquote>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\"><p><em>\u201cThere\u2019s certain rules in PSR-12 that would break our code\u201d<\/em><\/p><\/blockquote>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\"><p><em>\u201cThere\u2019s rules in PSR-12 my team strongly disagrees with.\u201d<\/em><\/p><\/blockquote>\n\n\n\n<p>Historically, it\u2019s been difficult to perform large stylistic changes on an existing code base. Luckily there are tools which can convert all your files for you! We\u2019ll walk through these tools in \u201cLinters\u201d.&nbsp;<\/p>\n\n\n\n<p>There might be disagreement around the merit of specific rules within a coding standard. The tooling today easily addresses these concerns. It\u2019s super easy to <em>extend<\/em><strong> <\/strong>the PSR-12 coding standard and exclude certain folders or rules. We\u2019ll walk through how to do this in <a class=\"aioseop-link\" href=\"#phpcs-xml-config-file\">Creating a Configuration File<\/a>.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Linters<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\">PHP_CodeSniffer<\/h3>\n\n\n\n<p>PHP_CodeSniffer is a linter command line tool for following PHP coding standards. You can install it globally so that from any project you can run the <code>phpcs<\/code> command to analyze files and <code>phpcbf<\/code> to fix them. Starting in version <a class=\"aioseop-link\" href=\"https:\/\/github.com\/squizlabs\/PHP_CodeSniffer\/releases\/tag\/3.5.0\">3.5 has support for PSR-12<\/a>.<\/p>\n\n\n\n<p><strong>Install PHP_CodeSniffer (Globally)<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ Install globally\ncomposer global require \"squizlabs\/php_codesniffer=*\"<\/pre>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ Set the coding standard\nphpcs --standard=PSR12<\/pre>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ Scan a specific file<br \/>phpcs app\/Controllers\/HomeController.php&nbsp;<\/pre>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ Scan all files\nphpcs .<\/pre>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ Fix a specific file<br \/>phpbf app\/Controllers\/HomeController.php&nbsp;<\/pre>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ Fix all files<br \/>phpcbf .<\/pre>\n\n\n\n<p><strong>Install PHP_CodeSniffer (Project Dependency)<\/strong><\/p>\n\n\n\n<p>Having it installed globally is handy, the command is short so no matter what project you jump into it\u2019s easy to remember. But I recommend <em>also<\/em> installing it as a composer dev dependency in your project. This way, no matter what, it\u2019s installed for all your teammates and you all have the same version. <\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ Install locally\ncomposer require --dev \"squizlabs\/php_codesniffer=*\"<\/pre>\n\n\n\n<p>Then you can run it the same way as demonstrated globally above, you just need to specify the vendor bin path where composer installs it to. <\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ Scan<br \/>vendor\/bin\/phpcs --standard=PSR12 app\/Controllers\/HomeController.php<\/pre>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ Fix\nvendor\/bin\/phpcbf --standard=PSR12 app\/Controllers\/HomeController.php<\/pre>\n\n\n\n<p>We can avoid potentially forgetting to pass <code>--standard=PSR12<\/code> by <a class=\"aioseop-link\" href=\"#phpcs-xml-config-file\">creating a phpcs.xml configuration file<\/a> like we&#8217;ll demonstrate below.<\/p>\n\n\n\n<p>If you find it annoying to type out the entire vendor path or have a hard time remembering the vendor path, maybe create a <a href=\"http:\/\/mitchmckenna.com\/blog\/wp-admin\/post.php?post=1370&amp;action=edit#composer-run-script\">composer run-script<\/a> which we&#8217;ll also go over below.<\/p>\n\n\n\n<p>Even so, I&#8217;ll be honest, I usually just use the globally installed version; it&#8217;s easier to just type <code>phpcs<\/code>, and PHP_CodeSniffer doesn&#8217;t change too much from version to version. But I install it as a dev dependency anyway so that it&#8217;s there if I need it to run it on a server or another system. Plus there&#8217;s an added benefit that by setting it as a dev dependency and creating the composer run-script, our teammates IDE\u2019s can <a href=\"#set-the-coding-standard-automatically\" class=\"aioseop-link\">set the coding standard automatically<\/a> for them.<\/p>\n\n\n\n<h4 class=\"wp-block-heading\" id=\"phpcs-xml-config-file\">Create a phpcs.xml Configuration File<\/h4>\n\n\n\n<p>Like I said above, you may <em>Extend PSR-12<\/em> if you want to exclude files or folders, or exclude certain rules. By placing a <code>phpcs.xml<\/code> file at the root of your project, anyone who runs <code>phpcs<\/code> doesn&#8217;t have to worry about passing any arguments to set the coding standard to PSR-12 or any custom settings for your project. PHP_CodeSniffer will automatically read them from this config file instead. <\/p>\n\n\n\n<p>As a simple example, here\u2019s how you create a custom standard that extends PSR-12 but excludes the 120 character line length limit, adds a rule to disallow long array syntax, and ignores a \/views\/ folder. <\/p>\n\n\n\n<p><strong>phpcs.xml<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&lt;?xml version=\"1.0\"?&gt;\n&lt;ruleset name=\"My Company Coding Standard\"&gt;\n   &lt;description&gt;PSR12 with tweaks.&lt;\/description&gt;\n   &lt;rule ref=\"PSR12\"&gt;\n       &lt;exclude name=\"Generic.Files.LineLength.TooLong\"\/&gt;\n   &lt;\/rule&gt;\n   &lt;rule ref=\"Generic.Arrays.DisallowLongArraySyntax\"\/&gt;\n   &lt;exclude-pattern&gt;*\/views\/*&lt;\/exclude-pattern&gt;\n&lt;\/ruleset&gt;<\/code><\/pre>\n\n\n\n<p>Here\u2019s a more complex example: <a href=\"https:\/\/github.com\/squizlabs\/PHP_CodeSniffer\/blob\/master\/phpcs.xml.dist\">https:\/\/github.com\/squizlabs\/PHP_CodeSniffer\/blob\/master\/phpcs.xml.dist<\/a><\/p>\n\n\n\n<p>And full documentation can be found here: <a class=\"aioseop-link\" href=\"https:\/\/github.com\/squizlabs\/PHP_CodeSniffer\/wiki\/Annotated-Ruleset\">https:\/\/github.com\/squizlabs\/PHP_CodeSniffer\/wiki\/Annotated-Ruleset<\/a><\/p>\n\n\n\n<h4 class=\"wp-block-heading\" id=\"composer-run-script\">Create a Composer Script<\/h4>\n\n\n\n<p>Remembering the path to the local installation of <code>phpcs<\/code> and typing it out every time can get tedious, not to mention remembering to pass the flag for what standard to use if you don&#8217;t need a <code>phpcs.xml<\/code>, so you can create a composer script to make it easier:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>\"scripts\": {\n   \"phpcs\": \"vendor\/bin\/phpcs --standard=PSR12 app\"\n}<\/code><\/pre>\n\n\n\n<p>Then you only have to run:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">composer phpcs<\/pre>\n\n\n\n<p>This has 2 additional benefits:<\/p>\n\n\n\n<ol class=\"wp-block-list\"><li><a class=\"aioseop-link\" href=\"https:\/\/blog.jetbrains.com\/phpstorm\/2020\/01\/phpstorm-2020-1-early-access-program-is-now-open\/\">PHPStorm 2020.1<\/a> will provide <img data-recalc-dims=\"1\" decoding=\"async\" src=\"https:\/\/i0.wp.com\/d3nmt5vlzunoa1.cloudfront.net\/phpstorm\/files\/2020\/01\/gutter_play_tr.png?w=17&#038;ssl=1\" class=\"alignnone wp-image-15301\"  alt=\"gutter_play_tr\" \/> play buttons to run composer run-scripts with just one click.<\/li><li>PHPStorm can <a class=\"aioseop-link\" href=\"#set-the-coding-standard-automatically\">automagically set your standard<\/a> in PHPStorm.<\/li><\/ol>\n\n\n\n<h3 class=\"wp-block-heading\">PHP CS Fixer<\/h3>\n\n\n\n<p>PHP CS Fixer is an alternative linter to PHP_CodeSniffer. It doesn\u2019t have PSR-12 yet, but they are <a href=\"https:\/\/github.com\/FriendsOfPHP\/PHP-CS-Fixer\/issues\/4502\" class=\"aioseop-link\">working to add PSR-12 support<\/a>. It does, however, include all the other same popular standards that PHP_CodeSniffer supports, like PSR-12&#8217;s predecessor PSR-2 and others.&nbsp;<\/p>\n\n\n\n<p>As well, PHP CS Fixer also includes support for the <a href=\"https:\/\/symfony.com\/doc\/current\/contributing\/code\/standards.html\">Symfony coding standard<\/a>. It takes the PSR-2 coding standard (PSR-12 soon) and builds upon it with coding opinions common in their framework\u2019s community. I personally really like it, except I do tweak a couple settings. I like to turn off <a href=\"https:\/\/en.wikipedia.org\/wiki\/Yoda_conditions\">yoda_style<\/a>, and turn on a couple handy fixers that PHP_CodeSniffer doesn\u2019t have, like sorting import statements alphabetically, and removing unnecessary fully qualified class names.&nbsp;<\/p>\n\n\n\n<p>Unlike PHP_CodeSniffer where you set the standard\/rules in an xml file, for PHP CS Fixer you set them in a PHP file (either .php_cs or .php_cs.dist). Here\u2019s an example for PHP CS Fixer on how to set the standard as the Symfony coding standard and make the other tweaks I just mentioned:<\/p>\n\n\n\n<p><strong>.php_cs.dist<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&lt;?php\n$finder = PhpCsFixer\\Finder::create()\n   -&gt;exclude([\n       'views',\n   ])\n   -&gt;in(__DIR__);\nreturn PhpCsFixer\\Config::create()\n   -&gt;setRules([\n       '@Symfony' =&gt; true,\n       'array_syntax' =&gt; ['syntax' =&gt; 'short'],\n       'concat_space' =&gt; ['spacing' =&gt; 'one'],\n       'yoda_style' =&gt; false,\n       'fully_qualified_strict_types' =&gt; true,\n       'ordered_imports' =&gt; true,\n       'phpdoc_align' =&gt; false,\n       'phpdoc_separation' =&gt; false,\n   ])\n   -&gt;setFinder($finder);<\/code><\/pre>\n\n\n\n<p>Documentation for these and other settings can be here: <a href=\"https:\/\/github.com\/FriendsOfPHP\/PHP-CS-Fixer#config-file\">https:\/\/github.com\/FriendsOfPHP\/PHP-CS-Fixer#config-file<\/a><\/p>\n\n\n\n<h2 class=\"wp-block-heading\">IDE Support<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\">PHPStorm<\/h3>\n\n\n\n<p>PHPStorm + PHP Linters = \ud83d\udd25. IntelliJ has made linters a first class citizen in their PHPStorm IDE. There\u2019s no plugin needed. You can utilize PHP_CodeSniffer or PHP CS Fixer right inside the IDE so you don\u2019t have to run commands on the command line. What\u2019s nice about this integration is that it will help you follow the PSR-12 coding standard in real-time as you write code. <\/p>\n\n\n\n<p>Here\u2019s the 3 steps you\u2019ll need to do in order to get PHPStorm setup with either PHP_CodeSniffer or PHP CS Fixer:<\/p>\n\n\n\n<ol class=\"wp-block-list\"><li><strong>Set the \u201cCode Style\u201d<\/strong><\/li><\/ol>\n\n\n\n<p>By setting the code style we make sure that when you <a href=\"https:\/\/www.jetbrains.com\/help\/phpstorm\/reformat-and-rearrange-code.html\">reformat entire classes<\/a>, <a href=\"https:\/\/www.jetbrains.com\/help\/phpstorm\/generating-code.html\">generate code<\/a>, or <a href=\"https:\/\/www.jetbrains.com\/help\/phpstorm\/refactoring-source-code.html\">refactor code<\/a>, PHPStorm will follow PSR-12 when it rewrites your code for you. Starting in <a href=\"https:\/\/blog.jetbrains.com\/phpstorm\/2019\/11\/phpstorm-2019-3-release#psr\">PHPStorm 2019.3<\/a>, PSR-12 is available as one of the built-in code styles to pick from.<\/p>\n\n\n\n<p>Preferences &gt; Editor &gt; Code Style &gt; PHP &gt; \u201cSet from\u2026\u201d &gt; Predefined Style &gt; PSR12<\/p>\n\n\n\n<ol class=\"wp-block-list\" start=\"2\"><li><strong>Turn on \u201cCode Quality Tools\u201d<\/strong><\/li><\/ol>\n\n\n\n<p>We need to validate that PHPStorm knows where the linter is installed for when it needs to use it to lint your code.<\/p>\n\n\n\n<p>Preferences &gt; Languages &amp; Frameworks &gt; PHP &gt; Quality Tools &gt; Code Sniffer<\/p>\n\n\n\n<p>Click the ellipsis (&#8230;) and use the validate button to make sure it can detect where PHP_CodeSniffer is installed.<\/p>\n\n\n\n<ol class=\"wp-block-list\" start=\"3\"><li><strong>Turn on \u201cInspections\u201d<\/strong><\/li><\/ol>\n\n\n\n<p>By turning on Inspections for the linter, PHPStorm will put a squiggly line below any code for any issues the linter detects. Opening the intention actions menu on an inspection will even provide an action to fix the issue for you starting in <a href=\"https:\/\/youtrack.jetbrains.com\/issue\/WI-25815%20https:\/\/blog.jetbrains.com\/phpstorm\/2019\/01\/phpstorm-2019-1-early-access-program-is-open\/\">PHPStorm 2019.1<\/a> for PHP_CodeSniffer (and <a href=\"https:\/\/blog.jetbrains.com\/phpstorm\/2018\/09\/phpstorm-2018-3-early-access-program-is-open\/\">PHPStorm 2018.3 for PHP-CS-Fixer<\/a>). You can see this in action in the gif at the top of this article!<\/p>\n\n\n\n<p>Preferences &gt; Editor &gt; Inspections &gt; PHP &gt; Quality Tools &gt; PHP_CodeSniffer Validation \u2705<\/p>\n\n\n\n<h4 class=\"wp-block-heading\" id=\"set-the-coding-standard-automatically\">Set the Coding Standard Automatically for Teammates<\/h4>\n\n\n\n<p>PHPStorm recently made it super easy to have the coding standard set automatically for all your team members by simply adding a line to your composer.json:<\/p>\n\n\n\n<p><a href=\"https:\/\/www.jetbrains.com\/help\/phpstorm\/using-php-code-sniffer.html#configure-tool-inspection-composer\" class=\"aioseop-link\">https:\/\/www.jetbrains.com\/help\/phpstorm\/using-php-code-sniffer.html#configure-tool-inspection-composer<\/a><\/p>\n\n\n\n<p>Note: You\u2019re teammates must use Composer through PHPStorm (eg. Tools &gt; Composer &gt; Install\/Update) for it to automatically set the path and turn on the inspections for them.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Visual Studio Code<\/h3>\n\n\n\n<p>PHPStorm is probably the most popular IDE for PHP, but Visual Studio Code (VS Code) is becoming a very popular (and free) IDE for PHP developers. You can install the <a href=\"https:\/\/marketplace.visualstudio.com\/items?itemName=ikappas.phpcs\">phpcs plugin<\/a> for PHP_CodeSniffer integration or the <a href=\"https:\/\/marketplace.visualstudio.com\/items?itemName=junstyle.php-cs-fixer\">php cs fixer plugin<\/a> for PHP CS Fixer integration.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Sublime Text, Vim, Atom &amp; Others<\/h3>\n\n\n\n<p>Sublime Text has <a href=\"https:\/\/benmatselby.dev\/sublime-phpcs\/\">sublime-phpcs<\/a>. Vim has <a href=\"https:\/\/github.com\/vim-syntastic\/syntastic\" class=\"aioseop-link\">Syntastic<\/a> or <a href=\"https:\/\/github.com\/dense-analysis\/ale\" class=\"aioseop-link\">Ale<\/a>. Atom has a <a href=\"https:\/\/atom.io\/packages\/linter-phpcs\">linter-phpcs<\/a> package. As for PHP CS Fixer, they have a list of <a href=\"https:\/\/github.com\/FriendsOfPHP\/PHP-CS-Fixer#helpers\" class=\"aioseop-link\">plugins for various editors<\/a> right on their Github readme.&nbsp;<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Taking It a Step Further<\/h2>\n\n\n\n<p>So now you\u2019ve got linting working on the command-line, you&#8217;ve reformatted your codebase to PSR-12, and your IDE of choice is setup to lint in real-time! Now how do you keep your codebase PSR-12 compliant? Ever opened up a class to find others had committed a bunch of code that doesn&#8217;t follow PSR-12? Do you find yourself having to run <code>phpcs<\/code> across the whole codebase every couple months?<\/p>\n\n\n\n<p>In my next blog post we&#8217;ll go over how to make sure PSR-12 errors never makes it into master again. I&#8217;ll go a step further and show how you can catch PSR-12 violations before they even make it into a commit! <a class=\"aioseop-link\" href=\"http:\/\/mitchmckenna.com\/blog\/category\/programming\/feed\/\">Subscribe via RSS<\/a>, or <a class=\"aioseop-link\" href=\"https:\/\/twitter.com\/mitchellmckenna\">follow me on twitter<\/a> to find out about the next blog post comes out!<\/p>\n","protected":false},"excerpt":{"rendered":"<a href=\"http:\/\/mitchmckenna.com\/blog\/2020\/04\/is-your-code-up-to-sniff\/\" rel=\"bookmark\" title=\"Permalink to Is Your Code Up To Sniff?\"><p>PHP Code Standards Following coding standards in PHP is now easier than ever. Let&#8217;s go over the benefits of following a coding standard, how to enforce it, and look at how modern tooling and new features in IDE\u2019s like PHPStorm makes it nicer than ever before. Why Follow a Coding Standard? Stop Wasting TimeIf you&#8217;ve [&hellip;]<\/p>\n<\/a>","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_jetpack_memberships_contains_paid_content":false,"footnotes":""},"categories":[16],"tags":[178,176,177,63],"class_list":{"0":"post-1370","1":"post","2":"type-post","3":"status-publish","4":"format-standard","6":"category-programming","7":"tag-code-quality","8":"tag-code-standards","9":"tag-linting","10":"tag-php","11":"h-entry","12":"hentry"},"jetpack_featured_media_url":"","jetpack_shortlink":"https:\/\/wp.me\/p92wZA-m6","jetpack-related-posts":[],"jetpack_sharing_enabled":true,"_links":{"self":[{"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/posts\/1370","targetHints":{"allow":["GET"]}}],"collection":[{"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/comments?post=1370"}],"version-history":[{"count":88,"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/posts\/1370\/revisions"}],"predecessor-version":[{"id":1503,"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/posts\/1370\/revisions\/1503"}],"wp:attachment":[{"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/media?parent=1370"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/categories?post=1370"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/mitchmckenna.com\/blog\/wp-json\/wp\/v2\/tags?post=1370"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}