Was ist fibjs?
fibjs ist ein Anwendungsserver-Entwicklungsframework, das für die Web-Backend-Entwicklung entwickelt wurde. Es basiert auf der JavaScript-Engine Google V8 und verwendet eine andere Parallelitätslösung als herkömmliche Rückrufe. fibjs verwendet Fiber (Faser), um die durch asynchrone Aufrufe verursachte Geschäftskomplexität auf Framework-Ebene zu isolieren, wodurch die Entwicklungsschwierigkeiten erheblich verringert und Leistungsprobleme durch häufige asynchrone Verarbeitung im Benutzerbereich verringert werden.
Aus historischen Gründen wird JavaScript hauptsächlich zur Handhabung der Browser-Benutzeroberfläche verwendet. Die UI-Entwicklung ist ein typisches ereignisgesteuertes Single-Thread-Modell, daher hat sich JavaScript nach und nach zur asynchronen Verarbeitung als Hauptprogrammierparadigma entwickelt.
Mit dem Erfolg von JavaScript beginnen immer mehr Menschen, JavaScript auf andere Szenarien anzuwenden. Gleichzeitig wird den Menschen zunehmend bewusst, dass die asynchrone Verarbeitung in vielen Szenarien nicht die beste Wahl ist.
Rückkehr zur Natur, agile Entwicklung
fibjs verwendet Glasfaser (Faser) auf Framework-Ebene, um die durch asynchrone Aufrufe verursachte Geschäftskomplexität zu isolieren, und kapselt die asynchrone E/A-Verarbeitung in intuitivere synchrone Aufrufe. Ingenieure müssen nur Code gemäß der üblichen synchronen Geschäftslogik schreiben und können den großen Komfort der asynchronen Verarbeitung genießen.
Der folgende Code stammt aus der Dokumentation des MySQL-Moduls:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32conn.beginTransaction(err => {
if (err) {
throw err;
}
conn.query('INSERT INTO posts SET title=?', title,
(error, results, fields) => {
if (error) {
return conn.rollback(() => {
throw error;
});
}
var log = 'Post ' + results.insertId + ' added';
conn.query('INSERT INTO log SET data=?', log,
(error, results, fields) => {
if (error) {
return conn.rollback(() => {
throw error;
});
}
conn.commit((err) => {
if (err) {
return conn.rollback(() => {
throw err;
});
}
console.log('success!');
});
});
});
});
In fibjs wird die gleiche Arbeit erledigt, der Code lautet wie folgt:
1
2
3
4
5
6conn.trans(() => {
var result = conn.execute('INSERT INTO posts SET title=?', title);
var log = 'Post ' + results.insertId + ' added';
conn.execute('INSERT INTO log SET data=?', log);
});
console.log('success!');
Wenn Sie Einfachheit suchen, können Sie den Code auch so schreiben:
1
2
3
4conn.trans(() => conn.execute('INSERT INTO log SET data=?',
'Post ' + conn.execute('INSERT INTO posts SET title=?', title).insertId +
' added'));
console.log('success!');
Durch den Vergleich können wir deutlich die Unterschiede erkennen, die verschiedene Programmierstile mit sich bringen. Weniger Code bedeutet weniger Fehler und mit weniger Code wird die Logik des Codes klarer. In diesem Fall profitieren sowohl die Entwicklungs- als auch die Wartungsarbeiten.
Genießen Sie hohe Energie
Obwohl es relativ einfach ist, einen Server zu skalieren, um die Reaktionsfähigkeit zu verbessern, ist die Leistung immer noch einer der wichtigen Aspekte bei der Auswahl eines Entwicklungsframeworks. Mit der Einführung von ES7 wurde Async als neues asynchrones Entwicklungsmodell in JavaScript eingeführt. Obwohl uns der synchrone Programmierstil von Async gefällt, müssen wir uns auch mit seinen Auswirkungen auf die Leistung auseinandersetzen.
Um die Leistungsunterschiede verschiedener Programmierstile zu vergleichen, können wir den folgenden Testcode verwenden:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39var count = 1000;
async function test_async(n) {
if (n == count)
return;
await test_async(n + 1);
}
function test_callback(n, cb) {
if (n == count)
return cb();
test_callback(n + 1, () => {
cb();
});
}
function test_sync(n) {
if (n == count)
return;
test_sync(n + 1);
}
async function test() {
console.time("async");
await test_async(0);
console.timeEnd("async");
console.time("callback");
test_callback(0, () => {
console.timeEnd("callback");
});
console.time("sync");
test_sync(0);
console.timeEnd("sync");
}
test();
Unter der neuesten Version 8 lauten die laufenden Ergebnisse dieses Codes wie folgt:
1
2
3async: 0.539ms
callback: 0.221ms
sync: 0.061ms
Aus den Testergebnissen können wir deutlich erkennen, dass der Server bei weit verbreiteter Verwendung von Async viel Zeit damit verbringt, die Aufrufe und Rückgaben von Async-Funktionen zu verarbeiten. Dies haben wir auch in einigen tatsächlichen serverseitigen Anwendungstests festgestellt. Dieser drastische Leistungsabfall ist jedoch völlig inakzeptabel.
Im Gegensatz dazu nutzt fibjs die Glasfasertechnologie, nutzt die Eigenschaften der JavaScript-Sprache selbst voll aus und maximiert die überlegene Leistung der V8-Engine. Ingenieure können die Serverleistung problemlos maximieren.
Wählen Sie flexibel Paradigmen, ohne entführt zu werden
Die Entscheidung für die Verwendung von fibjs bedeutet nicht, dass Sie einen synchronen Entwicklungsstil verwenden müssen. Tatsächlich unterstützt fibjs verschiedene asynchrone Programmierparadigmen, mit denen Sie vertraut sind, und kann flexibel zwischen synchronen und asynchronen Stilen wechseln.
Unabhängig davon, ob es sich um Rückruffunktionen oder asynchrone Funktionen handelt, weisen sie jedoch einen schwerwiegenden Fehler auf, der ansteckend ist. Wenn es sich bei einer Funktion um eine Callback- oder asynchrone Funktion handelt, müssen alle anderen davon abhängigen Funktionen ebenfalls Callback- oder asynchrone Funktionen sein. Bei der Softwareentwicklung im großen Maßstab wird dies zu enormen Entwicklungskosten führen.
Nehmen Sie als Beispiel ein einfaches Serverentwicklungsszenario. Zu Beginn des Projekts haben wir uns dafür entschieden, die Sitzungsdaten im Speicher zu speichern. Zu diesem Zeitpunkt können wir die Daten mithilfe der Synchronisierung direkt lesen und speichern und darauf basierend vollständige Geschäftsfunktionen entwickeln. Mit zunehmender Geschäftsgröße müssen wir Sitzungsdaten in Redis oder MongoDB speichern. Zu diesem Zeitpunkt müssen wir sitzungsbezogene Vorgänge in den asynchronen Modus ändern.
Theoretisch können wir jede Funktion einzeln ändern, um sie an die Anforderungen der abhängigen Funktionen anzupassen. Dazu müssen wir jedoch alle Module vollständig verstehen und in der Lage sein, sie zu ändern. Dies ist nahezu unmöglich, wenn mehrere Personen gemeinsam entwickeln oder Module von Drittanbietern verwenden.
Daher sollten in allen gängigen Modulen sowohl synchrone als auch asynchrone Schnittstellen bereitgestellt werden, um das Verhältnis zwischen Asynchronität und Leistung auszugleichen. Gewöhnliche Entwickler entscheiden sich normalerweise dafür, nur asynchrone Schnittstellen bereitzustellen, was zu Leistungsproblemen führt.
In fibjs können Sie ähnliche Probleme leicht lösen und die unkontrollierte Ausbreitung expliziter Asynchronität vermeiden:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17var util = require('util');
function session_get(sid) {
return sdata;
}
async function async_session_get(sid) {
return sdata;
}
function callback_session_get(sid, cb) {
cb(null, sdata);
}
data = session_get(sid);
data = util.sync(async_session_get)(sid);
data = util.sync(callback_session_get)(sid);
fibjs stellt die Funktion util.sync bereit, mit der Rückruffunktionen oder asynchrone Funktionen in synchrone Funktionen umgewandelt und direkt aufgerufen werden können. Auf diese Weise können wir problemlos Module aus verschiedenen Programmierparadigmen integrieren und die Entwicklungskosten minimieren, indem wir sie in synchronisierte Paradigmen umwandeln und so die durch die Paradigmenansteckung verursachte Katastrophe effektiv vermeiden.
Beginnen Sie mit dem Erleben
Sind Sie bereit für eine großartige Entwicklungserfahrung? Beginnen wir also mit der Installation.