Codequalität ist ein Thema, das mit der Programmierung geboren wurde. ISO 9000 wird zur Bewertung und Kontrolle der Qualität des Unternehmensmanagements verwendet. GOST und dieselbe ISO werden für Produkte verwendet, es gibt jedoch keinen GOST-Code für die Qualitätsbewertung. Es gibt auch keine genaue Definition und keinen Standard für die Codequalität.

Jeder Entwickler versteht Qualität auf seine eigene Art und Weise, basierend auf Erfahrung. Die Ansichten der Joons und der Leine sind unterschiedlich, und dies führt zu Meinungsverschiedenheiten. Jedes Team für einzelne Projekte bewertet den Code auf seine Weise. Das Team wird aktualisiert, Entwickler gehen, Teamleiter ändern sich - die Definition von Qualität ändert sich.
Ivan Botanov (
StressoID ) von Tinkoff.ru, Frontend-Entwickler, Online-Tutor bei Angular, Redner bei Meetings und Konferenzen, Tutor bei YouTube und manchmal Team-Coach in Unternehmen, wird versuchen, dieses Problem zu lösen.
Bei der Entschlüsselung von Iwans Bericht über
Frontend Conf werden wir über Lesbarkeit, Benennung, Deklarativität, Code-Stil sprechen und indirekt auf die Beziehungen von Juni und Lead eingehen: Fehler, Rechen und "Brennen" von Teamleitern.
Haftungsausschluss: Bereiten Sie sich mental vor, der Text enthält
viel schlechten Code, der von einer "speziellen" Site stammt .Ein bisschen Geschichte
Wir alle schreiben auf unterschiedliche Weise. Möglicherweise haben Sie dies bemerkt, als Sie Ihren Arbeitsplatz, Ihr Projekt oder Ihr Team gewechselt haben - ungewöhnliche Dinge sind sofort erkennbar. Das ist mir auch oft passiert, weshalb dieser Bericht geboren wurde. Ich habe mich auf unerfahrene Entwickler konzentriert, aber der Artikel wird für diejenigen nützlich sein, die bereits mehr verwalten als schreiben oder Entwicklungsprozesse anpassen. Worüber werden wir sprechen:
- Über die Probleme von unlesbarem Code.
- Lassen Sie uns die Benennung diskutieren.
- Mal sehen, was die Unterschiede zwischen deklarativem und imperativem Stil sind und was die Probleme sind.
- Informationen zur Codemodularisierung und -eingabe.
- Über Code-Stil und technische Schulden, über Commits und Git-Flow.
- Informationen zu Tools, die Sie verwenden können, und zur Behebung von Fehlern im Produkt.
Bevor wir beginnen, stelle ich die Frage:
"Wie viele Programmierer muss der Bus abheben, damit sich das Projekt nicht mehr entwickelt?" . Die richtige Antwort: alle.
Was ist ein Busfaktor?
Bedingt arbeiten Petya oder Vasya im Team, die alles über das Projekt wissen: Sie gehen zu ihm, fragen nach diesem und jenem, wie es hier funktioniert und wie es funktioniert. Jeder ist auf Petja angewiesen, die Busnummer des Projekts ist eins. Je kleiner die Anzahl, desto schwieriger ist es, das Projekt zu entwickeln, da jeder Petya ablenkt und er cool ist und die Aufgaben erledigen und keine Fragen beantworten muss.
Du wirst sagen,
wie cool es ist, Pete zu sein! Jeder liebt ihn, schätzt ihn, braucht ihn.Es ist nicht so. Normalerweise ist Petya ein Teamleiter, und er muss sich mit anderen Aufgaben befassen: die Entwicklung des Projekts besprechen, Architektur erstellen, das Team verwalten, aber nicht in die Dünen gehen und erklären, warum es hier geschrieben ist und nicht anders.
Wenn der Code sauber und gut ist, ist es schön, ihn zu lesen, und es gibt weniger Fragen von den Jones.
Sauberer Code erhöht die Rentabilität des Projekts und senkt den Schwellenwert für die Eingabe . Wenn neue Leute im Team erscheinen, stellen sie weniger Fragen. In einem solchen Projekt ist
es aufgrund der niedrigen Einstiegsschwelle
einfacher, Entwickler zu gewinnen .
Der Qualitätscode erhöht die Busnummern.
Lesbarkeit
Die Lesbarkeit wird durch Einrückungen, krumme Namen und starke Verschachtelungen beeinträchtigt - viele Projekte leiden darunter. Zusätzlich zum Einrücken verringern mehrzeilige ternäre Operatoren, das Fehlen eines einzelnen Codestils, eine Kombination von Entwicklungsansätzen und eine nicht offensichtliche Neudefinition von Variablen die Lesbarkeit. All dies sind die häufigsten Ursachen für eine schlechte Lesbarkeit des Codes.
Für mich selbst habe ich den Begriff
linearer Code identifiziert - dies ist Code, der wie ein Buch gelesen werden kann.
Der lineare Code wird von links nach rechts, von oben nach unten gelesen, ohne zum zuvor geschriebenen Code zurückkehren zu müssen.
Ein Beispiel für einen solchen Code:
list.forEach((element1) => { if (element1.parent_id == null) { output.push(element1); list.forEach((element2) => { if (element2.parent_id == element1.id) { output.push(element2); list.forEach((element3) => { if (element3.parent_id == element2.id) { output.push(element3); list.forEach((element4) => { if (element4.parent_id == element3.id) { output.push(element4); } }) } }) } }) } })
Dieser Code ist linear, hat aber ein anderes Problem - er ist stark verschachtelt. Daher müssen wir auch die Verschachtelung überwachen.
Nichtlineares Codebeispiel:
if(!brk && html.childNodes[0].value && html.childNodes[0].max) { if(clear) html.childNodes[0].value = 1; else if(html.childNodes[0].value <= html.childNodes[0].max) { ++ html.childNodes[0].value; if(brk) { for(id = 1; id < html.childNodes.length; ++ id) findActive(html.childNodes[id], true); html.parentNode.className = ""; } return null; } else { html.parentNode.className = "Ready"; html.className = ""; return html; } }
Wenn wir alles überflüssige verwerfen und herausfinden, was die Linearität bricht, werden wir so etwas sehen:
if (condition) { return; } else { return; }
Wenn es etwas anderes gibt, müssen Sie zuerst schauen, was an einer Stelle geschrieben ist, dann an einer anderen. Wenn es sich um ein großes oder stark verschachteltes if handelt, ist die Aufmerksamkeit verstreut und der Code ist schwer zu lesen.
Wie kann man die Verschachtelung reduzieren und linearen Code erzielen?
Bedingungen kombinieren . Dies ist das Einfachste, was wir tun können - verschachtelt, wenn ich in gutem Zustand kombinieren und die Verschachtelung leicht reduzieren kann.
Es war:
if (isUser()) { if (isAdmin()) { console.log('admin'); } }
Es wurde:
if(isUser() && isAdmin()) { console.log('admin'); }
Wenden Sie ein
frühes Rückgabemuster an . Es ermöglicht Ihnen, andere vollständig loszuwerden. Ich kann die Methode oder einen Code durch if-else mit einer frühen Rückgabe ersetzen, und dann wird entweder der eine oder der andere Codeblock ausgeführt. Dies ist sehr praktisch - Sie müssen nicht scrollen und zu einigen Teilen des Codes zurückkehren.
Es war:
if (isAdmin()) { return admin; } else { return user; }
Es wurde:
if (isAdmin()) { return admin; } return user;
Versprechenskette anwenden . Dies ist ein typischer Winkelmesser-Code. Ich habe vor nicht allzu langer Zeit E2E-Tests geschrieben, und ein solcher Code hat meine Augen verletzt:
ptor.findElement(protractor.By.id('q01_D')).click().then(() => { ptor.findElement(protractor.By.id('q02_C')).click().then(() => { ptor.findElement(protractor.By.id('q03_D')).click().then(() => { console.log('done'); }); }); })
Mit der Versprechen-Kette dreht sich der Code:
ptor.findElement(protractor.By.id('q01_D')).click() .then(() => { return ptor.findElement(protractor.By.id('q02_C')).click(); }) .then(() => { return ptor.findElement(protractor.By.id('q03_D')).click(); }) .then(() => { console.log('done'); });
Wenn wir das Wissen über die Pfeilfunktion nutzen, können wir dies tun:
ptor.findElement(protractor.By.id('q01_D')).click() .then(() => ptor.findElement(protractor.By.id('q02_C')).click()) .then(() => ptor.findElement(protractor.By.id('q03_D')).click()) .then(() => console.log('done'));
Es ist lesbar, deklarativ, schön - alles ist deutlich sichtbar.
Höhere Ordnung beobachtbar. Da ich ein Winkelelement bin und RxJS verwende, stehe ich vor dem Problem der starken Verschachtelung von Spaghetti-Code - verschachtelten
Observable ,
dh verschachtelten Abonnements. Es gibt einen Stream, und innerhalb des Streams müssen Sie den Wert abrufen und dann etwas mit einem anderen Stream zu tun haben. Einige schreiben so:
Observable.of(1,2,3) .subscribe(item => { item += 2; Observable.of(item) .subscribe(element => { element += 1; }) })
Und das betrifft wirklich Projekte für Erwachsene. Sie können dies tun:
Observable.of(1,2,3) .mergeMap(item => Observable.of(item + 2)) .mergeMap(element => Observable.of(element + 1)) .subscribe()
Mit dem Wissen über die RxJS-API haben wir uns dank der
beobachtbaren höheren Ordnung von der starken Verschachtelung entfernt und sind
deklarativ geworden . Dieses Ding, das den Wert des inneren Flusses in den äußeren wirft, ist alles. Aber es ist sauber, linear, schön und nicht investiert.
Verschachtelte ternäre Operatoren
Meiner Meinung nach sind
verschachtelte ternäre Operatoren das Schlimmste, was im Code zu finden ist. Schreiben Sie sie in blockbedingte Anweisungen um und versuchen Sie, sie überhaupt nicht zu verwenden. Wir werden überhaupt nicht über implizite Bedingungen sprechen - dies ist ein Fehler.
Ein Beispiel für verschachtelte ternäre Operatoren und implizite Bedingungen:
arr.length > 0 ? arr[1] == 1 ? arr[1] = 2 : arr[1] = 1 : console.log('empty arr'); !a && b && func()
Ich habe dieses einfache Ternär in 5 Minuten geschrieben. Es hat die Länge des Arrays und einige Operationen, aber es ist schwer zu lesen, weil irgendwo eine Frage, irgendwo anders - alles ist nicht klar. Dieser Code kann mit mehrzeiligen verschachtelten ternären Operatoren neu geschrieben werden:
arr.length > 0 ? arr[1] === 1 ? arr[1] = 2 : arr[1] = 1 : console.log('empty arr');
Sie werden sagen:
-
OK, gut!-
Gesehen?-
Es ist
sichtbar!Und was sagst du dazu:
return query instanceof RegExp ? (function () { fn.each(function (id) { if (id.match(query)) { seatSet.push(id, this); } }); return seatSet; })() : (query.length == 1 ? (function (character) {
Jemand hat diese Ternarnik geschrieben und unterstützt. Durch den Zugriff auf einen solchen Codeabschnitt ist es schwierig herauszufinden, wo das Fragezeichen beginnt und wo es endet. Wenn Sie Ternaries verwenden, investieren Sie bitte nicht ineinander - das ist schlecht.
Benennen
Ein weiterer schlechter Code:
var _0x30119c = function() { var _0x3af68e = { 'data': { 'key': 'cookie', 'value': 'timeout' }, 'setCookie': function(_0x3543f3, _0x13e5c1, _0x586dac, _0x1c9d63) { _0x1c9d63 = _0x1c9d63 || {}; var _0x47b83f = _0x13e5c1 + '=' + _0x586dac; var _0xae3be = 0x0; for (var _0xae3be = 0x0, _0x5d2845 = _0x3543f3['length']; _0xae3be < _0x5d2845; _0xae3be++) { var _0x440369 = _0x3543f3[_0xae3be]; _0x47b83f += ';\x20' + _0x440369; var _0x411875 = _0x3543f3[_0x440369]; _0x3543f3['push'](_0x411875); _0x5d2845 = _0x3543f3['length']; if (_0x411875 !== !![]) { _0x47b83f += '=' + _0x411875; } } _0x1c9d63['cookie'] = _0x47b83f; } };
Wir können sagen, dass dieser Code
verschleiert ist , aber trotzdem: Wir sehen, dass es eine verständliche Funktion gibt, klare 'Daten', setCookie macht etwas, und dann ist es nur eine Decke und nichts ist klar - etwas ist
verkettet , irgendwo Leerzeichen. Alles ist sehr schlecht.
Was Sie bei der Benennung beachten müssen
Verwenden Sie die
CamelCase-Notation :
camelCaseNotation
.
Es gibt keine Transliteration, alle Namen der Methoden sind nur in Englisch :
ssylka, vikup, tovar, yslyga
oder
checkTovaraNaNalichieTseni
ist ein Fehler. Letzteres habe ich übrigens geschrieben, als ich gerade mit dem Programmieren angefangen habe.
Kein Element, keine Daten, el, html, arr , insbesondere beim Durchlaufen von Arrays. Wählen Sie beispielsweise für eine Reihe von Produkten oder Angeboten Anzeigenamen aus:
product, offer, etc
Der Unterschied zwischen Artikel und Produkt ist nicht so groß, aber die Lesbarkeit ist höher. Selbst wenn Sie eine einzeilige Funktion haben, die etwas Plus bringt, erhöht ein geschäftsfreundlicher Name die Lesbarkeit.
private_property
für private Immobilien :
private_property
. Ich habe diese Regel hinzugefügt, weil ich TypeScript das zweite Jahr geschrieben habe, aber in JS keine Zugriffsmodifikatoren vorhanden sind. In der Namenskonvention haben wir vereinbart, dass der Unterstrich private Eigenschaften für andere Entwickler definiert.
Konstanten in Großbuchstaben :
const BLOCK_WIDTH = 300;
und
Klassennamen in class SomeClass
: class SomeClass
. Ich schreibe in TypeScript und dort ist alles klar, in
ES6 ist alles klar, aber es gibt auch Legacy-Projekte, in denen alle Funktionsklassen mit dem
new
Operator in Großbuchstaben schreiben.
Keine Ein-Buchstaben-Variablen :
u = user
. Dies ist ein Verweis auf
i - nicht. Schreiben Sie klar, dh funktional. Es ist nicht erforderlich, die Check-Methode durchzuführen, die etwas überprüft, aber was nicht klar ist. Schreiben Sie die
addProductToCard(); sendFeedback()
der Methoden :
addProductToCard(); sendFeedback()
addProductToCard(); sendFeedback()
.
Imperativität
Ein kleiner Exkurs. Imperativität trat gleichzeitig mit der Programmierung auf. Zu dieser Zeit codierten sie in Assembler und schrieben zwingend: Jeder Befehl, jeder Schritt wurde detailliert beschrieben, und dem Wert wurde eine Speicherzelle zugewiesen. Wir leben im Jahr 2019 und schreiben daher nicht mehr auf JS.

Dies ist ein einfacher, aber zwingender Code mit einer for-Schleife und Variablen. Es ist unklar, warum sie hier hinzugefügt werden.
for (let i = 0; i >= 10; i++) { const someItem = conferences[i]; const prefixString = 'Hello '; if (someItem === 'Frontend Conf') { console.log(prefixString + someItem); } }
Imperative Codeprobleme
: viele Variablen, viele Wartungskonstruktionen dieser Variablen und viele Kommentare, da diese Variablen irgendwie beschrieben werden müssen - Sie können keine Variable erstellen und sie vergessen. All dies beeinträchtigt die Lesbarkeit des Codes.
Deklarativität
Der deklarative Stil wurde ersetzt. Wir schreiben in JavaScript und es steht uns zur Verfügung. Der deklarative Stil sieht folgendermaßen aus:
conferences .filter(someItem => someItem === 'Frontend Conf') .forEach(someItem => console.log('Hello' + someItem));
Dies ist das gleiche wie im Imperativ, aber viel einfacher und verständlicher.
Vorteile eines deklarativen Codes
Solcher Code ist einfacher zu lesen, zu warten und zu testen, und komplexe Codekonstrukte können hinter Methoden und Abstraktionen verborgen werden. Sie können die Unterschiede zwischen imperativem und deklarativem Stil am Beispiel des Bratens von Eiern verstehen. Um Spiegeleier in einem zwingenden Stil zu braten, nehmen wir eine Pfanne, stellen sie auf ein Feuer, gießen Öl ein, nehmen ein Ei, brechen es, gießen es aus. In einem deklarativen Stil sagen wir: „Spiegeleier“, und der Prozess wird hinter Abstraktionen verborgen. Wir wollen Rührei braten, nicht herausfinden, wie es funktioniert.
Probleme beginnen, wenn nicht sehr erfahrene Entwickler von der Universität kommen, an der sie Pascal studiert haben, und so schreiben:
const prefix = 'Hello '; conferences .forEach(someItem => { if (someItem === 'Frontend Conf') { const result = prefix + someItem; console.log(result) } });
Dies ist eine
Kombination aus deklarativen und imperativen Stilen. Es gibt keine Lesbarkeit, keinen vollständigen Imperativ, einige Variablen und
if
. Dies,
if
Person hinzugefügt, weil sie einfach nicht über den Filter wusste. Wenn Sie ein Lead sind und einen solchen Code sehen, kommen Sie, stecken Sie einen Link
mit einem Stick und bringen Sie den Code zu deklarativ.
Variablen erstellen
Erstellen Sie keine Variablen für Variablen - dies ist eine schlechte Idee. Als ich von den Entwicklern herausfand, warum sie das tun, hörte ich:
- Nun, es erhöht die Lesbarkeit!
Was erhöht hier die Lesbarkeit -
const username = user.name
? Wenn Sie eine Variable erstellen möchten, geben Sie die Namensbedeutung an. Zum Beispiel haben wir einen regulären Ausdruck:
const somePattern = /[0-9]+/; str.split(somePattern); const someResult = a + b - c;
Hier würde ich eine Variable erstellen, damit eine Person keine Zeit mit Verfahren verschwendet, sondern liest, dass diese regelmäßig das Telefon überprüft und weiter geht. Wenn Sie über mathematische Operationen verfügen, schreiben Sie auch in eine Variable, da die mathematische Operation mit Sicherheit eine Geschäftseinheit oder einen bestimmten Geschäftsmarker hat, um beispielsweise den Warenkorb zu berechnen oder einen Rabatt zu gewähren. In diesem Fall können Sie eine Variable erstellen.
Das Erstellen einer Variablen zum Erstellen von Variablen lohnt sich nicht.
Nicht offensichtliche Neudefinition von Variablen
Angenommen, wir haben eine Elementvariable erstellt, aus deren Namen nicht klar ist, um was es sich handelt. Wir haben ein DOM-
element
, seine Überschreibung aus irgendeinem Grund in ein Array geschrieben und sind gegangen:
let element = document.getElementById('someId'); arr.forEach(item => {
Alles ist in Ordnung, weg, vergessen. Nach Petya, die in unserem Team arbeitet, kam sie herein und fügte den
if
Block hinzu. Was ist das Definieren Sie die Variable einfach erneut und gehen Sie. Und der Umfang ist schon anders. Wenn der nächste Entwickler versucht, diesen Code zu verstehen, insbesondere wenn die Methode groß ist, wartet er auf
someId
oder
someItem
, und dort ist er überhaupt nicht vorhanden. Dies ist ein Ort, an dem Sie viel Zeit verlieren können, um nach dem Problem zu suchen. Wir werden einen
debugger
schreiben, einen
debugger
setzen, sehen, was da ist - im Allgemeinen nicht so schreiben.
Einteilung in Methoden
Wir betrachten kurz die Unterteilung in Methoden und gehen reibungslos zu Abstraktionen über.
Methoden sollten
atomare Funktionalität tragen:
eine Methode - eine Aktion . Wenn Sie eine einzeilige Aktion haben, mischen Sie sie noch nicht, einfach weil die Methode so klein ist. Die Methode sollte
nicht mehr als 10 Zeilen umfassen. Diese Aussage provoziert einen Holivar und "schießt" jetzt auch, also schreibe mir oder in den Kommentaren, und ich werde erklären, warum ich diese Regel geschrieben habe.
Codemodularität
Die Modularität
verbessert die Lesbarkeit des
Codes durch Aufteilen in Abstraktionen,
hilft, schwer lesbaren Code zu „verbergen“, ist
einfacher zu testen und
Fehler können leichter
behoben werden . Ich werde es genauer erklären.
Versteckt sich hinter Abstraktionen
Zum Beispiel gibt es Code, der eine Schaltfläche erstellt, ihr eine ID und eine Klasse zuweist und darauf klickt - alles ist einfach.
const element = document.createElement('button'); element.id = 'id_button'; element.classList = 'red'; document.body.appendChild(element); element.click();
Sie können dem Schaltflächencode eine Funktion hinzufügen, ihn
createButton
beim Erstellen der Schaltfläche die Funktion
createButton
verwenden:
const.button = createButton('id_button'); button.click(); function createButton((id') { element = document.createElement('button'); element.id = id; element.classList = 'red'; document.body.appendChild(element); return element; }
Durch den "sprechenden" Namen wird klar, was die Funktion tut und diese ID wird übergeben. Wenn wir eine Schaltfläche erstellen möchten und nicht verstehen, wie und warum sie erstellt wird, schreiben wir mit dieser Funktion Code.
button.component.js let button = createButton('id_button'); button.click();
Als nächstes schreiben wir einen
Helfer , der später von anderen Entwicklern verwendet wird. Wenn sie verstehen wollen, wie Rührei gebraten wird, oder das Rezept ändern wollen - Salz hinzufügen oder entfernen, kommen sie vorbei und verehren.
button.helpers.js function createButton(id) { let button = document.createElement('button'); button.id = id; button.classList = 'red'; document.body.appendChild(element); return button; }
Tippen
Ich werde lange nicht über das Tippen sprechen - es gibt eine Reihe von Berichten. Ich schreibe in TypeScript, es gefällt mir, aber es gibt immer noch Flow- und andere Tools. Wenn Sie Ihr Projekt nicht eingeben müssen, ist es Zeit, es zu implementieren. Dies hilft beim Debuggen einer Reihe von Fehlern.
Code riecht
Code-Gerüche sind sehr stark mit meinem Thema verflochten, da das Schreiben von Code mit schlechter Qualität genau die Gerüche erzeugt. Schauen Sie sich den
coolen Bericht von Alexei Okhrimenko an , er geht ausführlich auf dieses Thema ein.
Codestil
Dies sind die Team-, Projekt- oder Unternehmensregeln, die Entwickler einhalten. Ein guter
Codestil enthält Beispiele für guten und schlechten Code. Es kann in jedem geeigneten Werkzeug und an jedem Ort geschrieben werden. Wir haben dieses Wiki und für ein kleines Unternehmen reicht eine Datei in Word aus. Sie können auch den vorgefertigten Codestil verwenden, der bereits von anderen Unternehmen verwendet wird:
JQuery ,
Google oder
Airbnb - der beliebteste Codestil.
Wenn Sie eine bestimmte Technologie oder ein bestimmtes Framework verwenden, haben diese normalerweise auch einen eigenen Codestil, der einen Blick wert ist. In Angular ist dies beispielsweise der
Angular Style Guide oder der
React / JSX Style Guide von Airbnb.
Dies ist ein Beispiel für unseren Codestil.

Hier ist ein Abschnitt zum Erstellen von Variablen und beschreibt, wie und wie dies nicht zu tun ist.
Technische Schulden
Dies ist eine Art Bezahlung für die Tatsache, dass wir irgendwo einmal gemäht haben. Oft entsteht eine technische Schuld, wenn wir keine Zeit haben, eine Aufgabe zu erledigen und eine Erinnerung zu schreiben, um später darauf zurückzukommen. Bei Fällen, die nicht mit Geschäftsfunktionen zusammenhängen, wird beispielsweise das Framework aktualisiert.
Tech-Schulden erzeugen Krücken und einen Code von geringer Qualität.
Wegen der technischen Schulden schreibe ich schlechten Code und Krücken. Der nächste Entwickler wird sich das ansehen, das ist alles, die Pfosten sehen und eine weitere Krücke hinzufügen: "Wenn es noch Unterstützung gibt, ist nichts falsch." Tech-Schulden bringen Krücken hervor, Qualität geht verloren, was wiederum Krücken hervorbringt, und sie erhöhen die Tech-Schulden noch mehr.
Es gibt eine
Theorie von "zerbrochenen Fenstern". Wenn im Gebäude ein zerbrochenes Fenster erscheint und es nicht geändert wird, erscheint nach einer Weile ein zweites zerbrochenes Fenster, ein drittes Graffiti. Die Leute sehen, dass niemand dem Gebäude folgt und die Bestrafung für zerbrochene Fenster nicht sein sollte. So ist der Code. Oft ist der Code in Legacy-Projekten von Krücken umgeben, weil die bedingten Petit und Vasya Krücken sehen und denken: "Es ist okay, ich werde der erste sein." Daher wird in normalen Unternehmen der technischen Verschuldung genügend Zeit eingeräumt - sie nehmen entweder eine Quote oder einen technischen Sprint in Anspruch, um das Problem zu lösen. Wenn Sie führend sind oder die Prozesse beim Erstellen von Sprints und die Liste der Aufgaben, die in die Arbeit aufgenommen werden, irgendwie beeinflussen, achten Sie auf die technische Verschuldung - dies ist wichtig.
Repository
Lassen Sie uns die Commit-Nachrichten diskutieren. Das Bild zeigt Beispiele für echte Botschaften, die ich in verschiedenen Projekten gesehen habe. Welche davon halten Sie für informativ?

Richtige AntwortInformative Nachrichten sind in Blöcken, aber "Feature hinzugefügt", "Fehler behoben" - sind nicht informativ.
Nachrichten festschreiben
Ich schreibe in
WebStorm und liebe es. Darin können Sie die Hervorhebung von Aufgabennummern konfigurieren, der Übergang beim Klicken in Task Tracker ist cool. Wenn jemand WebStorm nicht verwendet, ist es an der Zeit, denn mit ihm werden die Festschreibungsnachrichten in hoher Qualität erhalten. Was ist eine Qualitäts-Commit-Nachricht? Dies ist ein Commit, bei dem es
eine Aufgabennummer und eine kurze, aber prägnante Darstellung des
Wesens der Änderungen gibt : "Neues Modul erstellt", "Schaltfläche hinzugefügt", "Feature hinzugefügt, bei dem die Komponente erstellt wird" und kein gesichtsloses "Feature hinzugefügt". Beim Anzeigen von Commits wird deutlich, wo die Komponente hinzugefügt wurde und wo der Fehler behoben wurde. Selbst in Festschreibungsnachrichten muss die
Art der Änderungen angegeben werden : Feature, Bugfix, damit klar ist, innerhalb welcher Änderungen die Änderungen vorgenommen wurden.
Gitflow
Ich werde kurz über Gitflow sprechen. Detaillierte Beschreibung in der
Übersetzung des Artikels von Vincent Driessen . Gitflow ist eines der beliebtesten und erfolgreichsten Repository-Verwaltungsmodelle mit den
Hauptzweigen - Entwickeln, Mastern, Preprod, Prod und
temporäre Zweige : Feature, Bug, Release. Wenn wir die Aufgabe starten, leiten wir den Feature-Zweig vom Entwicklungszweig ab. Nachdem wir die Codeüberprüfung für den Feature-Zweig bestanden haben, geben wir sie wieder in die Entwicklung ein. Am Ende sammeln wir Releases von Develop und Release in Master.

Die Werkzeuge
Der erste ist
Commitizen . Dies ist ein Software-Dienstprogramm, von dem ich vor nicht allzu langer Zeit erfahren habe - ich habe es gesehen, gefühlt, gemocht. Es ermöglicht Ihnen das Standardisieren von Nachrichten-Commits und verfügt über eine schöne Konsolenoberfläche, in der Sie Funktionen auswählen können. Wenn Sie Commits im Sinne von "Korrigieren einer Funktion" oder "Beheben eines Fehlers" haben, ist es Zeit, Ihren Jungs Commitizen zu zeigen, damit sie es zumindest für den Anfang verwenden können, und dann können Sie es aus dem Kopf schreiben.
Linters ist ein Muss in jedem Projekt. Es gibt viele vorgefertigte Konfigurationen in Lintern, aber Sie können
Ihre eigenen Regeln schreiben . Wenn Sie Ihre eigenen Regeln haben, sollte der Linter diese Regeln fusseln - Sie müssen die Regeln für Ihren Codestil schreiben.
Nützliche Links zu Linter:
In einem separaten Absatz wurde
sonarJS zugewiesen
. Dies ist ein Tool, mit dem Sie die Codeüberprüfung in CI integrieren können. Zum Beispiel stellen wir eine Pull-Anfrage, und dann schreibt sonarJS, um eine Pull-Anfrage über unsere Schulen zu stellen, und entweder verärgert oder nicht. Das ist cool - es hat mir gefallen. Selbst wenn der bedingte Vasya glaubt, dass niemand seine Neigung bemerken wird - er wird SonarJS bemerken.
Das Tool lässt sich problemlos in Jenkins integrieren. Unsere Jungs haben schnell genug eingebaut. Höchstwahrscheinlich lässt es sich in andere Systeme integrieren, aber wir haben es nicht ausprobiert. SonarJS überprüft den Code immer noch auf Codegerüche. Um ehrlich zu sein, weiß ich nicht, ob gewöhnliche Linter dies tun.
Formatierer oder Stylisten ist ein Tool, das Code gemäß einer Konfiguration
formatiert , z. B.
Prettier . Sie können es für den
Pre-Push-Hook konfigurieren und einen einheitlichen Codestil im Repository erhalten. Petja aus unserem Team kann 500 Leerzeichen setzen oder gar kein Semikolon schreiben - alles wird im Repository sauber und schön sein.
Mit dem Formatierer können Sie den Code in einem einzigen Stil halten.
Ich wollte eine Geschichte erzählen, die uns passiert ist. Wir haben Prettier in einem Projekt implementiert, das viele Aufgaben geschrieben hat, und beschlossen, nicht das gesamte Projekt durchzugehen, sondern nur Code mit Funktionen. Es schien uns, dass wir nach und nach herauskommen und die Geschichte der Commits nicht verderben würden: In der Anmerkung werden wir sehen, wer die letzten Regeln hat. Das war eine schlechte Entscheidung. Als wir die Aufgabe und die Pull-Anfrage erledigten und ein paar Zeilen änderten, formatierte Prettier die gesamte Datei, und als wir die Pull-Anfrage sahen, gab es nur zwei Zeilen! Dies nahm eine Menge Zeit für die Codeüberprüfung in Anspruch.
Wenn Sie Prettier implementieren möchten, führen Sie daher das gesamte Projekt aus .
—
error tracking runtime. , , . - — . Error tracking DOM-, , .
Sentry ,
TrackJS , .
Sentry, . Warum? , Sentry. .

.

, , : «, iOS, , , Android — , iOS».
Sentry
StackTrace — , .

Sentry. , — : . , , : « , ?». — . , . , — «» .
Checkliste
- , .
- .
- — .
- .
- . , frontend-developer Tinkoff.ru.
- Code style, . — .
- — . , , .
- Git Flow — , . — .
- — , . , .
. « » , — , . . , , , . , , .
:
Twitter Facebook .
— Frontend Conf . Hat es dir gefallen? Frontend Conf ++ : , , .
— FrontendConf ++. — , . , 27