Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Refactoring with Rector

Refactoring with Rector

As big codebases age they often struggle to keep up with changes to programming languages and package development. New language features can't be easily adopted, and packages are often stuck on an old version due to a backwards-incompatible change. Fixing this requires large scale refactoring which can often take hundreds of hours. Why not automate it?

In this talk we'll look at Rector, a PHP refactoring tool that automates hundreds of different refactorings. We'll look at different use cases, writing our own refactorings, and even converting an entire project from one framework to another!

Glynn Forrest

October 08, 2019
Tweet

Other Decks in Programming

Transcript

  1. @glynn_forrest Overview • Why we refactor • How Rector can

    help • Custom Rectors • How it works • Recommendations • Demo
  2. @glynn_forrest Code is a liability • Without care, your codebase

    will rot • Packages and frameworks have deprecations and breaking changes • Upgrading a large codebase takes time • Bad code sneaks in, very rarely leaves • Quick fixes / cludges
  3. @glynn_forrest Easy wins • Linting ◦ jakub-onderka/php-parallel-lint ◦ squizlabs/php_codesniffer ◦

    friendsofphp/php-cs-fixer --dry-run • Static analysis ◦ phpstan/phpstan ◦ vimeo/psalm ◦ phan/phan • Run these in your CI builds
  4. @glynn_forrest Rector solves this for you • “Upgrade your Legacy

    App to Modern Codebase” ◦ “Rector is a reconstructor tool - it does instant upgrades and instant refactoring of your code.” • github.com/rectorphp/rector • getrector.org
  5. @glynn_forrest But what is it? • Command line tool to

    automatically modify PHP code • The ‘process’ command runs various transformations (Rectors) • Configured with a YAML file • Has built in configurations called ‘sets’
  6. @glynn_forrest Install • As a dev package • Docker image

    • Separate repository for a group of projects
  7. @glynn_forrest First steps • Pick a basic rector • Create

    a simple rector.yaml • Run on a directory of code • Review diff
  8. @glynn_forrest With arguments • Based on Symfony’s DI component •

    Magic performed by compiler passes • Extends argument handling to be less verbose
  9. @glynn_forrest Sets • Premade config files for a specific use

    case • Upgrade PHP versions • Upgrade framework package versions • Fix deprecated usages • Best practices
  10. @glynn_forrest Other config • Tweak autoloading paths • Classes must

    be autoload-able • Command line flag or config file
  11. @glynn_forrest Other config • Skip files or directories • Use

    language features of a specific PHP version • Skip specific rules in a set
  12. @glynn_forrest Custom Rectors getNodeTypes() for the parts of the syntax

    tree changed by this Rector See rector/docs/NodesOverview.md
  13. @glynn_forrest Architecture • Uses nikic/php-parser and phpstan/phpstan to analyse and

    manipulate the code • Glued together with Symfony packages (console, dependency injection, finder, yaml, etc) • Yaml file is Symfony services config (services, parameters, imports) • Rectors are only used when registered as services
  14. @glynn_forrest Recommendations • Use the code-quality and dead-code sets for

    an easy win on an old codebase • Also consider the coding-style set
  15. @glynn_forrest Recommendations • Write your own Rector for any non-trivial

    change across a large codebase • Consistency • Next time will be easier
  16. @glynn_forrest Recommendations • Don’t name your config file rector.yaml •

    Principle of least surprise • Running with --set will also include the rules in the config file
  17. @glynn_forrest Recommendations • Browse a specific tag on Github •

    Rector moves very fast • Default branch is master