Scripts

Patch reader

Misschien een nuttig script voor diegene die zich met 'patches' bezig houdt. Je kan er de verschillen in een patch-bestand mee uitlezen. Ikzelf gebruik dit voor een systeem die ik aan het bouwen ben om wijzigingen aan artikelen op mijn site bij te houden. Een uitgebreider script met een toffe class om de patches mee te genereren en op te slaan volgt later. Het script is openbaar deels afkomstig uit het vroegere MyReact forumsoftware, dus mijn credits gaan naar die makers. Als download vind je de functie, een proef-patch, en wat CSS om de HTML mooie duidelijke opmaak mee te geven met het laten zien van de wijzigingen. Doorstreept voor verwijderde tekst, en rood voor aangepaste tekst. Wat is 'patch' nou? In het Linux-besturingssysteem, maar met wat zoeken ook voor Windows geschikt, of in de Windows Subsystem for Linux (WSL), is "patch" een opdracht waarmee we patchbestanden kunnen toepassen op de broncodes of configuratiebestanden. Het patchbestand wordt gebruikt voor software- of sourceupdates. Het verschil tussen de originele en nieuwe bestanden wordt bewaard in dergelijke patch-bestanden en normaal wordt de opdracht "diff" wordt gebruikt om het verschil of de patch te krijgen. Maar dit script visualiseert dit.

patch_reader.php
<?php
$string = "*** a.txt	2021-01-03 21:04:05.547897800 +0100
--- b.txt	2021-01-03 21:04:05.563893700 +0100
***************
*** 1,4 ****
  Huis
! Tuin
  Keukendeur
! Bloemetjesgordijn
\ No newline at end of file
--- 1,6 ----
  Huis
! Tuintje
  Keukendeur
! Raamkozijn
! Bloemetjesgordijn
! Stofzuiger
\ No newline at end of file
";


function diff_styled($diff) {
        $diff_pattern = "/\*{3}\s([\d,]+)\s\*{4}\s?(.*)-{3}\s([\d,]+)\s-{4}\s?(.*)$/s";
        $line_pattern = "/^[\r\n]?([ \-+!])\s(.*)$/m";
        $result = '';
        $diff = preg_split("/\*{15}/", htmlentities($diff));

        for ($block_nr=1; $block_nr<count($diff); $block_nr++)
        {
            if (!preg_match($diff_pattern, $diff[$block_nr], $block))
                break;

            preg_match_all($line_pattern, $block[2], $new, PREG_SET_ORDER);
            preg_match_all($line_pattern, $block[4], $old, PREG_SET_ORDER);

            $result .= "<pre class=\"diff\"><address>" . diff_lines($block[3], $block[1]) . ":</address>";

            $old_line = $new_line = 0;
            while ($old_line<count($old) || $new_line<count($new))
            {
                $match = ($old[$old_line] ? $old[$old_line][1] : " ") . ($new[$new_line] ? $new[$new_line][1] : " ");

                switch ($match)
                {
                    case "  ":
                    case " ":
                        $result .= ($old[$old_line] ? $old[$old_line][2] : $new[$new_line][2]);
                        $old_line++; $new_line++; break;
                    case "+ ":
                    case "! ":
                        $result .= "<del>" . $old[$old_line][2] . "</del>";
                        $old_line++; break;
                    case " -":
                    case " !":
                        $result .= "<ins>" . $new[$new_line][2] . "</ins>";
                        $new_line++; break;
                    case "!!":
                        $result .= "<del>" . $old[$old_line][2] . "</del>";
                        $result .= "<ins>" . $new[$new_line][2] . "</ins>";
                        $old_line++; $new_line++; break;
                    default:
                        $result .= "Error: Unknown '" . $match . "'\n";
                        $result .= $old[$old_line][2];
                        $result .= $new[$new_line][2];
                        $old_line++; $new_line++;
                }

            }

            $result .= "";

        }

        return $result;

    }

    function diff_lines($lines_old, $lines_new) {
        $lines_old = explode(",", $lines_old);
        $lines_new = explode(",", $lines_new);
        $lines_start = min($lines_old[0], $lines_new[0]);
        $lines_stop = max($lines_old[1], $lines_new[1]);
        $lines_count = ($lines_new[1] - $lines_new[0]) - ($lines_old[1] - $lines_old[0]);

        #print_r($lines_old);
        #print_r($lines_new);
        
        if (!$lines_stop)
            $result = sprintf("Regel %u", $lines_start);
        else
            $result = sprintf("Regels %u t/m %u", $lines_start, $lines_stop);

        if ($lines_count)
            if ($lines_count == 1 || $lines_count == -1)
                $result .= sprintf(" (%+d regel)", $lines_count);
            else
                $result .= sprintf(" (%+d regels)", $lines_count);

        return $result;

    }
    
    echo diff_styled($string);
?>
patch_voorbeeld.txt
*** a.txt	2021-01-03 21:04:05.547897800 +0100
--- b.txt	2021-01-03 21:04:05.563893700 +0100
***************
*** 1,4 ****
  Huis
! Tuin
  Keukendeur
! Bloemetjesgordijn
\ No newline at end of file
--- 1,6 ----
  Huis
! Tuintje
  Keukendeur
! Raamkozijn
! Bloemetjesgordijn
! Stofzuiger
\ No newline at end of file
diff_reader.css
pre.diff {
    overflow: auto;
    border: 1px solid #000000;
}

pre.diff ins,
pre.diff del {
    display: block;
    text-decoration: none;
}

pre.diff ins {
    background-color: #88ff88;
}

pre.diff del {
    background-color: #ff8888;
}

pre.diff address {
    font-style: normal;
    border-bottom: 1px solid #000000;
    background-color: #eeeeee;
} 

Reacties

0
Nog geen reacties.