Verbieten Sie Aufrufe von beliebigen Funktionen / Klassen in externem Code

12

Ich habe Fälle erlebt, in denen es nützlich wäre, den Zugriff auf die API externer Bibliotheken und Frameworks einzuschränken, um negative Konsequenzen im System zu vermeiden.

In einer SharePoint-Anwendung kann es beispielsweise logisch erscheinen spList.Items.GetItemById, ein Listenelement aufzurufen , auch wenn es sich um eine Schleife handelt, ohne zu wissen, dass dies zu erheblichen Leistungsproblemen führen kann.

Es kann auch sein, dass wir die Verwendung von SmtpClient verbieten müssen, um alle zu zwingen, unsere eigene Klasse zum Senden von E-Mails zu verwenden, um sicherzustellen, dass wir alle E-Mails in der Testumgebung ordnungsgemäß proxen und verspotten können.

Gibt es zuverlässige und einigermaßen einfache Möglichkeiten, diese Einschränkungen für externen Code zu erreichen, außer an bestimmten Stellen in unserem eigenen Code? Es ist nicht unbedingt erforderlich, den Zugriff auf diese Methoden / Klassen zu unterbinden, zum Beispiel durch Reflektion oder einfach durch Deaktivierung. Es sollte vielmehr eine strikte Warnung sein, dass sie nicht verwendet werden sollten. Erzwingen Sie vorzugsweise, dass der Programmierer aktiv Maßnahmen ergreift, um diese Einschränkungen zu umgehen, wenn dies möglich / erforderlich ist.

Alex - Hör auf damit SE
quelle
11
Dies klingt wie die Durchsetzung einer extremen Form der Codierung (Verboten, einen bestimmten Bibliotheksaufruf zu verwenden). Für mich stellt sich die Frage, ob Sie überhaupt Code-Reviews oder Style-Checks durchführen.
Peter M
3
Wollen Sie diese Aufrufe zur Laufzeit oder zur Kompilierungszeit abfangen und blockieren ?
MetaFight
1
Haben Sie schon einmal von StyleCop gehört, seit Sie C # verwenden ? Sie wissen, dass Sie benutzerdefinierte Regeln erstellen können, wie Sie möchten, oder?
Machado
10
" Gibt es zuverlässige und einigermaßen einfache Möglichkeiten, diese Einschränkungen für externen Code zu erreichen, außer an bestimmten Stellen in unserem eigenen Code? " Ja: Schreiben Sie Ihren eigenen Roslyn Analyzer , um den Zugriff auf bestimmte APIs als Kompilierungsfehler zu melden.
David Arno
3
@Machado, StyleCop ist praktisch ein totes Produkt. Es wird durch StyleCopAnalyzers ersetzt, das auf Roslyn aufgebaut ist. Es wäre definitiv keine gute Idee, in diesen Tagen Zeit in das Schreiben von benutzerdefinierten StyleCop-Regeln zu investieren.
David Arno

Antworten:

8

Gibt es zuverlässige und einigermaßen einfache Möglichkeiten, diese Einschränkungen für externen Code zu erreichen, außer an bestimmten Stellen in unserem eigenen Code?

Da es sich bei der Frage speziell um C # handelt, gibt es eine compilerbasierte Lösung, mit der solche Regeln erzwungen werden können : Roslyn Analyzers . Sie können einen eigenen Analyzer schreiben, der den Zugriff auf bestimmte APIs als Kompilierungsfehler oder Warnung meldet.

Ein Beispielsatz von Analysatoren, der viele Beispiele für das Schreiben eigener Codes enthält, sind die StyleCop-Analysatoren , die die alte StyleCop-Funktion für C # ersetzen.

Allerdings können solche automatisierten Überprüfungen immer von Leuten umgangen werden, die entschlossen sind, "die Regeln zu brechen". Daher ist dieser Ansatz kein Ersatz für Code Reviews, wie in der Antwort von Karl Bielefeldt erörtert. Es kann bei solchen Überprüfungen behilflich sein, sollte sie jedoch nicht ersetzen.

David Arno
quelle
Es war nie die Absicht, etwas anderes zu ersetzen, ich suchte nur nach einem speziellen Werkzeug für meine Werkzeugkiste.
Alex - Hör auf SE
25

Sie können zeitaufwändige Dinge tun, wie das Schreiben eines Wrappers um die externe API, der Ihre unerwünschten Vorgänge ausschließt, aber nichts geht über Schulungen und Codeüberprüfungen, denn unabhängig von den von Ihnen eingeführten Standards oder technischen Maßnahmen werden die Leute kreative Wege finden, um sie zu umgehen .

Zum Beispiel haben wir mehrere Services in Scala geschrieben, und eines der Dinge, die wir zur Zeit der Codeüberprüfung fragen, ist die Unveränderlichkeit, aber wir kommunizieren dies oft, indem wir das loswerden vars. Jemand hat neulich einen val x: ListBuffer [Boolean] verwendet , um eine einzelne veränderbare Variable als einziges Element in der Liste zu speichern . Sie können ListBufferx keine andere zuweisen , aber Sie können die vorhandenen Elemente der Liste so oft ersetzen, wie Sie möchten. Genauso schlecht wie mit einem var, aber schlauer.

Mit anderen Worten, Sie müssen überprüfen, ob Ihre technischen Lösungen von Personen umgangen werden. Wenn diese technischen Lösungen kostenintensiv sind und die Komplexität erhöhen, können Sie auch einfach überprüfen, ob sie korrekt codiert sind.

Karl Bielefeldt
quelle
verdammt, das ist hinterhältig!
am
@snb Entspricht dem, was Java als Hack tut, um zu umgehen, dass nur ein Objekt / Wert zurückgegeben werden kann und keine richtigen Referenzargumente vorhanden sind. Übergeben Sie stattdessen ein Array, dessen Inhalt aktualisiert wird. (Einige Beispiele: AtomicMarkableReference.getund AtomicStampedReference.get).
JAB
Vielen Dank für Ihre Antwort, aber ich bin definitiv nicht daran interessiert, zeitaufwändige komplexe Dinge wie das Schreiben von Wrappern um den externen Code zu erledigen. Das würde wahrscheinlich nicht einmal helfen, da sie einfach zur Quelle gehen können. Diese Antwort scheint anzunehmen , dass eine Lösung wird teuer sein und die Komplexität hinzuzufügen. Was ist mit einer reinen und einfachen Lösung?
Alex - Hör auf SE
1
@Alex die einfachste Lösung ist genau dort: "Nichts ist besser als Training und Code-Reviews".
Mr.Mindor
2
"Nichts ist besser, als es manuell zu machen" ist richtig, bis jemand es automatisiert.
Ewan
0

Karls Antwort ist zu 100% richtig. Konformität kann nicht garantiert werden. Berücksichtigen Sie jedoch zusätzlich zu Schulungen und Codeüberprüfungen die Verwendung von statischen Analysetools, um die Einhaltung sicherzustellen. (Anmerkung: Ich sagte "zusätzlich zu", da man diese genauso umgehen kann, wie Karl es sagte).

Der Vorteil der Verwendung von statischen Analysetools besteht darin, dass die mühsame Analyse von menschlichem Code entfällt, wenn nach Beispielen für die "mehrfache Verwendung von IEnumerable" oder nach Leistungsproblemen der Woche gesucht wird (oder zumindest das Gefühl besteht, dass ich es immer bin) anschauen). Auf diese Weise können sich die Code-Überprüfungen und das Training auf "interessantere" Themen konzentrieren.

Speziell für C # habe ich unten einige Vorschläge aufgenommen. Schließen Sie diese an Ihre Build-Umgebung an, und Sie können loslegen. Aber im Allgemeinen gibt es, unabhängig von der verwendeten Sprache, irgendwo ein statisches Analysetool.

Kopieren / Einfügen direkt von der Wikipedia-Seite, verwenden Sie die Wiki-Seite für die neuesten Informationen und Links: https://en.wikipedia.org/wiki/List_of_tools_for_static_code_analysis#.NET

  • .NET Compiler Platform (Codename Roslyn) - Open-Source-Compiler-Framework für C # und Visual Basic .NET, entwickelt von Microsoft .NET. Bietet eine API zum Analysieren und Bearbeiten der Syntax.
  • CodeIt.Right - Kombiniert statische Code-Analyse und automatisches Refactoring zu Best Practices, die die automatische Korrektur von Codefehlern und -verstößen ermöglichen. unterstützt C # und VB.NET.
  • CodeRush - Ein Plugin für Visual Studio, das Benutzer auf Verstöße gegen Best Practices hinweist.
  • FxCop - Kostenlose statische Analyse für Microsoft .NET-Programme, die nach CIL kompiliert werden. Standalone und in einigen Microsoft Visual Studio-Editionen integriert; von Microsoft.
  • NDepend - Vereinfacht das Verwalten einer komplexen .NET-Codebasis durch Analysieren und Visualisieren von Codeabhängigkeiten, Definieren von Entwurfsregeln, Durchführen einer Auswirkungsanalyse und Vergleichen verschiedener Codeversionen. Integriert in Visual Studio.
  • Parasoft dotTEST - Ein statisches Analyse-, Unit-Test- und Code-Review-Plugin für Visual Studio. Funktioniert mit Sprachen für Microsoft .NET Framework und .NET Compact Framework, einschließlich C #, VB.NET, ASP.NET und Managed C ++.
  • Sonargraph - Unterstützt C #, Java und C / C ++ mit Schwerpunkt auf Abhängigkeitsanalyse, automatisierter Architekturprüfung, Metriken und der Möglichkeit, benutzerdefinierte Metriken und Code-Checker hinzuzufügen.
  • StyleCop - Analysiert C # -Quellcode, um eine Reihe von Stil- und Konsistenzregeln durchzusetzen. Es kann in Microsoft Visual Studio ausgeführt oder in ein MSBuild-Projekt integriert werden.
Reginald Blue
quelle
-1

Um auf den in einer anderen Antwort enthaltenen Vorschlag "Schulung und Codeüberprüfung" einzugehen: Da es sich bei dem Code, den Sie verbieten möchten, um legalen Code handelt, können Sie nicht darauf zählen, dass der Compiler dies verhindert, und Sie müssen sich auf einen späteren Prozess verlassen. die Überprüfung.

Dies kann (und sollte) sowohl manuelle als auch automatische Überprüfungsschritte umfassen:

  • Bereiten Sie eine Checkliste mit bekannten Problemen vor und gehen Sie diese nacheinander in Ihren manuellen Code-Überprüfungen durch. Führen Sie eine wiederkehrende Besprechung durch, um die Checkliste zu überprüfen und zu aktualisieren. Wenn ein böser Fehler aufgefangen und analysiert wird, fügen Sie ihn der Checkliste hinzu.

  • Fügen Sie Eincheckregeln hinzu, um nach bekannten Mustern zu suchen. Das Schreiben kann kompliziert sein, aber für ein großes Projekt kann es im Laufe der Zeit nützlich sein. Mit TFS können Sie Regeln in C # schreiben, und andere Buildsysteme haben ihre eigenen Hooks. Erwägen Sie die Verwendung von Gated Builds, um Check-Ins abzulehnen, die dem Muster entsprechen. Ja, es verlangsamt die Entwicklung, aber nach einer bestimmten Projektgröße und Komplexität kann es eine gute Sache sein, die Entwicklung zu verlangsamen.

Avner Shahar-Kashtan
quelle
-1

Möglicherweise kann Ihnen der Compiler dabei helfen, unerwünschte Anrufe abzufangen.

Benennen Sie Klassen / Methoden des Codes in Ihrer eigenen Bibliothek um, die nicht von externen Bibliotheksclients verwendet werden sollen. Alternativ können Sie Klassen / Methoden intern machen und Interna zu den Klassen hinzufügen, die diese verwenden dürfen.

Externe lib-Benutzer erhalten eine Kompilierungsfehlermethode / -klasse, die nicht gefunden wurde.

Verbotene Klassen / Methoden aus öffentlichen Bibliotheken: Erstellen Sie denselben Namespace / dieselbe Klasse / Methode in Ihrer Bibliothek

Externe Benutzer von lib erhalten einen Kompilierungsfehler, weil eine doppelte Klasse gefunden wurde

[aktualisieren]

Es ist nicht unbedingt erforderlich, den Zugriff auf diese Methoden / Klassen unter allen Umständen zu verhindern, z. B. durch Reflektion oder einfach durch Deaktivierung.

den Programmierer (... Client der Bibliothek ...) zwingen, aktiv Maßnahmen zu ergreifen, um diese Einschränkungen zu umgehen, wenn dies möglich / erforderlich ist.

k3b
quelle
Downvoting, nicht nur, weil es ein böser Hack ist, sondern es kann leicht mit C # (mit dem das OP die Frage markiert hat) unter Verwendung externer Aliase umgangen werden .
David Arno