Diese Woche ist mir aufgefallen, dass einige der Service-Frameworks nicht sehr gut geschrieben sind, insbesondere bestimmte Java-Frameworks. Wenn die CPU-Auslastung etwa 40% erreicht, kommt es zu vielen Timeouts. Bei diesen Diensten reichen die CPU-Kerne und die Speicherkapazität nicht aus, die Anzahl der arbeitenden Threads ist nicht hoch genug. Es ist jedoch nicht genug, um die CPU laufen zu lassen. Mit Hilfe von Java-Performance-Tools zur Analyse der Entdeckung, in der Tat, festgestellt, dass die meisten der Arbeits-Threads in der Idel oder Waiting Status. Derzeit ist die umfassende Analyse aller Umstände, noch rätselhaft. NIO auch verwendet, auch die Netty Rahmen verwendet, aber der Durchsatz ist nicht nach oben. Bei der Analyse der Threads wurde festgestellt, dass es keine besonders beschäftigten Business-Threads gibt. Es wird angenommen, dass IO oder eine Art von Wartemechanismus zu dieser geringen Verarbeitungseffizienz führt.
Diesmal wollte ich die Kosten senken, indem ich die Anzahl der Knoten verringerte, und ich habe vor der Ausführung nicht besonders viele Faktoren berücksichtigt. Wenn ich also die Knotenkapazität reduziere, prüfe ich nur die CPU-Auslastung, um zu beurteilen, ob der Knoten dies verkraften kann oder nicht. Als ich die durchschnittliche CPU-Auslastung der Arbeitslast in der Region Peking auf 35%-40% erhöhte, kam es beim gesamten Dienst zu einer großen Anzahl von Timeouts. Zu diesem Zeitpunkt war ich schockiert. Als ich es später auf dem Monitor analysierte, waren fast alle Knoten in der Hintergrundumgebung ausgefallen, das heißt, sie befanden sich in einem „Schockzustand“.
In dieser Woche habe ich auch die Umstrukturierung eines alten PHP-Gateway-Dienstes fortgesetzt, und das neue Gateway ist in Java geschrieben. Aber ich bin nicht wirklich dafür, Java als Gateway zu verwenden, denn die Ausführungseigenschaften der Java-Sprache bestimmen weitgehend, dass sie nicht für besonders hohe Gleichzeitigkeit geeignet ist. Und wir verwenden derzeit JDK 8 und haben keine leichtgewichtigen Threads eingeführt, jeder 4c8g-Container hat bis zu 800 Threads, der Overhead für das Umschalten von Threads ist besonders groß. Der Durchsatz eines einzelnen Containers ist also begrenzt, für die gleiche Menge an Datenverkehr sind mehrere Container erforderlich. Zunächst wurde ich in Go umgeschrieben, dieses Framework ist sehr gut und hat auch ein eigenes Team zur Pflege, aber der Leiter ließ mich trotzdem die Abteilung für selbstentwickelte Java-Frameworks benutzen. Vielleicht sind es vor allem personelle Erwägungen, aber ich habe keine andere Wahl, als es zuerst zu schreiben.