colinodell/indentation

Library to detect and manipulate indentation in strings and files

v1.0.0 2022-03-20 19:44 UTC

README

Latest Version Total Downloads Software License Build Status Coverage Status Quality Score Psalm Type Coverage Sponsor development of this project

PHP library to detect and manipulate the indentation of files and strings

Installation

composer require --dev colinodell/indentation

Usage

Detecting the indentation of a string or file

use ColinODell\Indentation\Indentation;

$indentation = Indentation::detect(file_get_contents('composer.json'));

assert($indentation->getAmount() === 4);
assert($indentation->getType() === Indentation::TYPE_SPACE);
assert((string)$indentation === '    ');

Changing the indentation of a string or file

use ColinODell\Indentation\Indentation;

$composerJson = file_get_contents('composer.json');
$composerJson = Indentation::change($composerJson, new Indentation(1, Indentation::TYPE_TAB));
file_put_contents('composer.json', $composerJson);

Adding leading indentation to all lines

Need to add indent all lines by some amount?

use ColinODell\Indentation\Indentation;

$codeExample = file_get_contents('file.php');
$indented = Indentation::indent($codeExample, new Indentation(4, Indentation::TYPE_SPACE));

Now you can embed the indented code into a Markdown document! (Hint: This works great with the league/commonmark library.)

Removing leading indentation from all lines

Imagine you have a file where every line is indented by at least 4 spaces:

    /**
     * Just a silly example
     */
    class Cat extends Animal
    {
        // ...
    }

You can trim that leading indentation while preserving the nested indentation with the unindent() method:

use ColinODell\Indentation\Indentation;

$contents = file_get_contents('Cat.php');
$trimmed = Indentation::unindent($contents);
file_put_contents('Cat.php', $trimmed);

Giving you:

/**
 * Just a silly example
 */
class Cat extends Animal
{
    // ...
}

Note how the leading 4 spaces are removed but all other indentation (like in the docblock and method body) is preserved.

Detection Algorithm

The current algorithm looks for the most common difference between two consecutive non-empty lines.

In the following example, even if the 4-space indentation is used 3 times whereas the 2-space one is used 2 times, it is detected as less used because there were only 2 differences with this value instead of 4 for the 2-space indentation:

html {
  box-sizing: border-box;
}

body {
  background: gray;
}

p {
    line-height: 1.3em;
    margin-top: 1em;
    text-indent: 2em;
}

Source.

Furthermore, if there are more than one most used difference, the indentation with the most lines is selected.

In the following example, the indentation is detected as 4-spaces:

body {
  background: gray;
}

p {
    line-height: 1.3em;
    margin-top: 1em;
    text-indent: 2em;
}