<p>您可以使用<a href="https://code.google.com/p/modwsgi/wiki/ConfigurationDirectives#WSGIDaemonProcess" rel="nofollow">^{<cd1>}</a>指令来拥有多个worker<em>线程</em>,而不是有多个worker<em>进程</em>,它们都在一个进程中运行。这样,所有线程都可以共享相同的DB连接映射。在</p>
<p>在你的apache配置中有这样的东西。。。在</p>
<pre><code># mydomain.com.conf
<VirtualHost *:80>
ServerName mydomain.com
ServerAdmin webmaster@mydomain.com
<Directory />
Require all granted
</Directory>
WSGIDaemonProcess myapp processes=1 threads=50 python-path=/path/to/django/root display-name=%{GROUP}
WSGIProcessGroup myapp
WSGIScriptAlias / /path/to/django/root/myapp/wsgi.py
</VirtualHost>
</code></pre>
<p>…然后你可以在你的Django应用程序中使用像这样简单的东西。。。在</p>
^{pr2}$
<p>…在第一次击中时,会产生。。。在</p>
<pre><code>Thread ID = 140597557241600
We made a connection for 'bob'
Query results for 'SELECT * FROM my_table'
</code></pre>
<p>…第二天。。。在</p>
<pre><code>Thread ID = 140597145999104
We reused an existing connection for 'bob'
Query results for 'SELECT * FROM my_table'
</code></pre>
<p>显然,当不再需要数据库连接时,你需要添加一些东西来断开它们,但是如果没有更多关于你的应用程序应该如何工作的信息,很难知道最好的方法。在</p>
<p><strong>更新1:关于I/O多路复用与多线程</strong></p>
<blockquote>
<p>I worked with threads twice in my live and each time it was a
nightmare. A lot of time was wasted on debugging non reproducible
problems. I think an event-driven and a non-blocking I/O architecture
might be more solid.</p>
</blockquote>
<p>使用I/O多路复用的解决方案可能更好,但会更复杂,而且还需要您的“strangedb”库来支持它,也就是说,它必须能够处理<code>EAGAIN</code>/<code>EWOULDBLOCK</code>),并且在必要时能够重试系统调用。在</p>
<p>Python中的多线程处理远没有其他大多数语言中的危险,这是因为Python的<a href="https://wiki.python.org/moin/GlobalInterpreterLock" rel="nofollow">GIL</a>,它本质上使所有Python字节码都是线程安全的。在</p>
<p>实际上,线程只在底层C代码使用<a href="https://docs.python.org/2/c-api/init.html#c.Py_BEGIN_ALLOW_THREADS" rel="nofollow">^{<cd4>}</a>宏时并发运行,该宏及其对应的宏<code>Py_END_ALLOW_THREADS</code>通常围绕系统调用和CPU密集型操作进行包装。在</p>
<p>这样做的好处是,在Python代码中几乎不可能发生线程冲突,但缺点是它不能总是在一台机器上最佳地使用多个CPU核。在</p>
<p>我建议使用上面的解决方案的原因是它相对简单,并且需要最少的代码更改,但是如果您可以详细介绍您的“strangedb”库,可能会有更好的选择。对于每个并发用户需要单独的网络连接的数据库来说,这似乎很奇怪。在</p>
<p><strong>更新2:关于多处理与多线程</strong></p>
<blockquote>
<p>...the GIL limitations around threading seem to be a bit of an issue.
Isn't this one of the reasons why the trend is to use separate
processes instead?</p>
</blockquote>
<p>这很可能是Python的<a href="https://docs.python.org/2/library/multiprocessing.html" rel="nofollow">^{<cd6>}</a>模块存在的主要原因,即提供跨多个CPU内核的Python字节码的并发执行,尽管该模块中有一个使用线程而不是进程的<a href="https://bugs.python.org/issue17140" rel="nofollow">undocumented</a><code>ThreadPool</code>类。在</p>
<p>如果你在游戏中每秒钟都有60个CPU的限制,那你就需要每秒钟都有一个CPU。在</p>
<p>然而,大多数基于web的服务可能会花费大部分时间等待发生的事情,例如网络I/O或磁盘I/O,Python线程允许这些事情并发发生。在</p>
<p>归根结底,这是性能和可维护性之间的权衡,考虑到硬件通常比开发人员的时间便宜得多,支持可维护性而不是性能通常更具成本效益。在</p>
<p>坦白地说,当你决定使用一种虚拟机语言,比如Python,而不是一种可以编译成真实机器代码的语言,比如C,你已经在说你准备牺牲一些性能来换取方便。在</p>
<p>另请参阅<a href="http://www.kegel.com/c10k.html" rel="nofollow">The C10K problem</a>,以了解缩放基于web的服务的技术的比较。在</p>