[Python-de] select.epoll() vs async framework (PostgreSQL)

Stefan Behnel python-de at behnel.de
Mi Jan 24 13:40:00 EST 2018


Hallo Sven,

ich vermute mal, du wolltest deine Antwort eigentlich an die Liste
schicken, also hier meine Antwort öffentlich.

Sven R. Kunze schrieb am 24.01.2018 um 12:21:
> On 23.01.2018 06:29, Stefan Behnel wrote:
>> Sven R. Kunze schrieb am 22.01.2018 um 17:14:
>>> Mit anderen Worten, wenn ich in den Projekten bereits einen
>>> Aufgaben-Verteiler-Prozess (Steuerprozess) habe, dann brauche ich mir um
>>> asyncio eigentlich keine Gedanken zu machen.
>> Doch, denn genau das war ja der Aufmacher für diese Diskussion. Es lohnt
>> sich oft, einen wie auch immer existierenden (async-)Steuerprozess durch
>> asyncio zu ersetzen, weil dadurch ein ganzer Haufen wiederverwendbarer Code
>> verfügbar wird.
> 
> Durchaus richtig, wenn wir den Steuerprozess betrachten. Dann macht
> Referenz auf asyncio schon Sinn.
> 
> Nur leider kann man die asyncio-Loop nicht ohne async/await nutzen.

Ah, ja, ich dachte mir schon, dass das deine Annahme ist. Das stimmt aber
nicht.


> Ich
> denke, dadurch zwing man viele Leute in eine Richtung, die sie gar nicht
> gehen wollen. Für mich sind das zwei getrennt Dinge, denn bisherige
> Steuerprozesse konnten bisher ThreadPools/ProcessPools auch gut ohne
> async/await launchen. Vielleicht ergibt sich da ja etwas in der Zukunft,
> die standardisierte asyncio-Loop ohne await/async zu verwenden. Sicherlich
> ist das nicht so IO-performant, aber es ging vorher ja auch ganz gut ohne.

Dann habe ich eine gute Nachricht für dich: du kannst jederzeit Dinge
außerhalb des I/O-Loops machen, auch ohne async/await. asyncio unterstützt
natürlich async/await, und das ist auch die empfohlene Art, asyncio-Code
unter Py3.5+ zu schreiben, aber weder ist asyncio auf async/await
beschränkt, noch ist async/await auf I/O (oder asyncio) beschränkt, sondern
implementiert nur eine Art von Koroutinen. Und mit "async with" und "async
for" gibt es dazu noch zwei recht mächtige Sprachkonstrukte, die
verschiedene Kooperationsmuster zwischen Koroutinen sehr sauber kapseln.


> Ich kann abrupte Migrationen nicht leider.
> 
> Darüber hinaus ist es auch oft nicht möglich, den Steuerprozess so einfach
> zu ersetzen, z.B. Apache WSGI.

WSGI ist kein Steuerprozess, sondern eine API. Genauso wie asyncio eine API
ist. Es gibt durchaus WSGI-Implementierungen auf asyncio-Basis, aber wie du
weiter oben schon selbst anmerktest, nutzen die die Möglichkeiten eines
asynchronen I/O-Loops nicht aus. Insbesondere Latenz und Nebenläufigkeit
leiden natürlich sehr, wenn zu viel in dem synchronen WSGI-Aufruf außerhalb
des I/O-Loops passiert (z.B. ganze Datenbankabfragen usw.). Allerdings gäbe
es durchaus die Möglichkeit, WSGI so zu erweitern, dass statt eines
Generators eine Future zurück geliefert wird. Dann ließe sich das Interface
auch wieder async bauen. Und da die Idee so offensichtlich ist, haben es
andere vermutlich auch schon ausprobiert.

Andersherum, also async auf sync (dein "Apache WSGI"), wüsste ich jetzt
gerade nichts, aber das heißt weder, dass es nichts gibt, noch, dass es
grundsätzlich nicht geht. Wenn's dich interessiert, kannst du ja mal ein
bisschen suchen, oder selbst etwas ausprobieren.


>> Du hast von einem sync/async Zwei-Welten-Problem gesprochen, aber das
>> wirkliche Problem war die Zersplitterung innerhalb der async-Welt. Das ist
>> das, was asyncio beseitigt.
> 
> Nun das Problem scheint ja nun erstmal behoben zu sein. Das
> Zwei-Welten-Problem bleibt leider. Und ist zumindest aus meiner Sicht, das
> größere; YMMV.

Ceterum censeo ...

Stefan


Mehr Informationen über die Mailingliste python-de