Mai bine Git diff cu difftastic

URMĂREȘTE-NE
16,065FaniÎmi place
1,142CititoriConectați-vă

În prezent, sunt în căutarea de a cunoaște și înțelege mai bine instrumentele bazate pe treesitter pentru R. Pentru a fi scurt, treesitter este un instrument pentru analizarea codului, de exemplu, recunoașterea a ceea ce este o funcție, un argument, o logică într-un șir de cod. Cu instrumentele construite pe treesitter, puteți căuta, reformata, scame și repara etc. codul dvs. Lucruri interesante, care rulează local și determinist pe mașina dvs.

Vorbind despre „etc.”, Etienne Bacher a sugerat cu ajutor să mă uit și la instrumentele bazate pe treesitter pentru alte limbi pentru a vedea ce mai lipsește din ecosistemul nostru. Așa am dat peste difftastic de Wilfred Hughes, „un instrument structural diff care înțelege sintaxa”. ✨ Aceasta înseamnă că difftastic nu compară doar linia sau „cuvintele”, ci și sintaxa reală, uitându-se la liniile din jurul liniilor care s-au schimbat (în mod implicit, 3), și mai bine, înțelege R din cutie.

Mulțumesc mult lui Etienne Bacher nu numai pentru că m-a făcut să descopăr difftastic, ci și pentru feedback-ul util despre această postare!

Instalarea difftastic

difftastic pe două fișiere

Puteți rula difftastic pe două fișiere, un pic așa cum ați folosi pachetul Waldo R pe două obiecte.

Să comparăm:

a <- gsub("bad", "good", x)

la

a <- stringr::str_replace(x, "bad", "good")

cu respect salvat în old.R şi new.R. CLI se numește difft nu difftastic. Folosesc afișarea „inline” în loc de cele două coloane implicite pentru a economisi spațiu orizontal.

difft old.R new.R --display inline

Am ajunge la această diferență frumoasă:

diferența dintre cele două linii de cod, unde „gsub” și „, x” sunt în roșu, apoi „strinrr::str_replace” și „x” în verde

Parantezele și "bad" şi "good" argumentele sunt ignorate.

De asemenea, putem obține versiunea JSON a acestui difer, care este o caracteristică instabilă, care necesită setarea unei variabile de mediu:

export DFT_UNSTABLE=yes
difft old.R new.R --display json

Asta ne prinde

{"aligned_lines":((0,0),(1,1)),"chunks":(({"lhs":{"line_number":0,"changes":({"start":5,"end":9,"content":"gsub","highlight":"normal"},{"start":23,"end":24,"content":",","highlight":"normal"},{"start":25,"end":26,"content":"x","highlight":"normal"})},"rhs":{"line_number":0,"changes":({"start":5,"end":12,"content":"stringr","highlight":"normal"},{"start":12,"end":14,"content":"::","highlight":"keyword"},{"start":14,"end":25,"content":"str_replace","highlight":"normal"},{"start":26,"end":27,"content":"x","highlight":"normal"},{"start":27,"end":28,"content":",","highlight":"normal"})}})),"language":"R","path":"content/post/2026-03-26-difftastic/new.R","status":"changed"}

Acum, nimic din toate acestea nu este foarte util pentru că nu aș compara niciodată fișierele în acest fel… Folosesc controlul versiunilor!

difftastic cu Git

Putem seta difftastic ca instrument de diff extern pentru Git la nivel global sau pentru proiectul curent.

De exemplu, cu pachetul gert R, pentru a-l seta local:

gert::git_config_set("diff.external", "difft")

Dacă vreau să folosesc afișajul inline, aș seta:

gert::git_config_set("diff.external", "difft --display inline")

Apoi git diff va folosi în mod implicit difftastic. Cel mai interesant pentru mine, git show --ext-diff va folosi difftastic. Nu folosesc niciodată git diff direct, dar mă uit foarte mult la comiterile mai mult sau mai puțin recente.

Să spunem că sunt interesat de commit-ul care a eliminat dependența lui roxygen2 de stringi, voi rula:

git show 7a1dd39866699a2b0a034bb15244c07698a1e2e7 --ext-diff

și obțineți:

diff unde parantezele unui apel imbricat sunt frumos evidențiatediff unde parantezele unui apel imbricat sunt frumos evidențiate

Acest lucru nu este spectaculos pentru că acesta este o mică diferență, dar îmi place evidențierea parantezelor apelului imbricat eliminat și a celui logic.

Caracteristici interesante ale difftastic

Pornind de la două exemple ale paginii de pornire difftastic…

Ignorarea modificărilor de formatare

Deoarece formatatorii vă pot aplica atât de util preferințele de formatare, revizuirea modificărilor de formatare într-un patch care se referă la cu totul altceva este inutilă și enervantă. Imaginați-vă că aveți o definiție a funcției care se potrivește pe o singură linie, apoi adăugați un argument la ea.

Trecand de la

f <- function(myarg1 = foo, myarg2 = bar) {}

la

f <- function(
  myarg1 = foo,
  myarg2 = bar,
  myarg3 = baz
) {}

Deoarece definiția are acum mai mult de 80 de caractere, formatatorul poate schimba definiția pentru a fi pe mai multe linii. Dar schimbarea de fapt interesantă este adăugarea unui argument.

Diferența Git nativă ar arata:

diff unde toate liniile sunt evidențiate deoarece funcția a fost reformatată, nu doar completată cu un singur argumentdiff unde toate liniile sunt evidențiate deoarece funcția a fost reformatată, nu doar completată cu un singur argument

Git cu difftastic ar arăta:

diff unde sunt evidențiate doar virgula după `bar` și linia cu noul argumentdiff unde sunt evidențiate doar virgula după `bar` și linia cu noul argument

Potrivirea delimitatorilor este motivul pentru care mi s-a părut mai plăcută afișarea roxygen2 de către difftastic.

Potrivirea delimitatorilor în ambalaje

Diferența Git poate arăta puțin urâtă atunci când pur și simplu mutați codul de la o funcție la alta.

Să zicem că plecăm de la

f <- function() {
  1 + 1
}

la

f <- function() {
  g()
}

g <- function() {
  1 + 1
}

Diferența Git ar arăta:

uncool diff care arată liniile modificate atât în ​​wrapper, cât și în funcție, fără delimitatori care se potrivescuncool diff care arată liniile modificate atât în ​​wrapper, cât și în funcție, fără delimitatori care se potrivesc

În timp ce Git cu difftastic ar arăta:

cool diff care arată `g` ca o nouă funcție prin evidențierea numelui și săgeata stânga, în timp ce întreaga definiție a lui `f` este marcată ca schimbată.cool diff care arată `g` ca o nouă funcție prin evidențierea numelui și săgeata stânga, în timp ce întreaga definiție a lui `f` este marcată ca schimbată.

Voi folosi difftastic?

Îmi place foarte mult conceptul din spatele difftastic și cele câteva comite-uri Git la care m-am uitat cu el redate frumos. Acum, ceea ce îmi lipsește pentru a folosi difftastic mult este integrarea sa cu instrumentele în care folosesc de fapt Git:

  • Positron inclusiv extensia GitLens;
  • Fila GitHub Pull Request Files.

În orice caz, voi continua să învăț despre instrumente bazate pe treesitter, dintre care unele precum Air și Jarl le pot utiliza deja direct din IDE-ul meu. 😸

Dominic Botezariu
Dominic Botezariuhttps://www.noobz.ro/
Creator de site și redactor-șef.

Cele mai noi știri

Pe același subiect

LĂSAȚI UN MESAJ

Vă rugăm să introduceți comentariul dvs.!
Introduceți aici numele dvs.