バックグラウンド
PHP はマルチスレッドをサポートしていませんが、完全なシステムとしては、非同期で完了する必要がある操作が多数あります。これらの非同期操作を完了するために、Redis キュー タスク システムを構築しました。
ご存知のとおり、メッセージ キュー処理システムは主にコンシューマーとプロデューサーの 2 つの部分に分かれています。
私たちのシステムでは、メインシステムがプロデューサーとして機能し、タスクシステムがコンシューマーとして機能します。
具体的なワークフローは次のとおりです: 1. メイン システムは、処理する必要があるタスク名とタスク パラメーターをキューにプッシュします。 2. タスク システムは、タスク キューをリアルタイムでポップアウトし、サブプロセスをフォークし、サブプロセスが特定のタスク ロジックを完了します。
具体的なコードは次のとおりです:
/** * 启动守护进程 */public function runAction() { Tools::log_message('ERROR', 'daemon/run' . ' | action: restart', 'daemon-'); while (true) { $this->fork_process(); } exit;}/** * 创建子进程 */private function fork_process() { $ppid = getmypid(); $pid = pcntl_fork(); if ($pid == 0) {//子进程 $pid = posix_getpid(); //echo "* Process {$pid} was created \n\n"; $this->mq_process(); exit; } else {//主进程 $pid = pcntl_wait($status, WUNTRACED); //取得子进程结束状态 if (pcntl_wifexited($status)) { //echo "\n\n* Sub process: {$pid} exited with {$status}"; //Tools::log_message('INFO', 'daemon/run succ' . '|status:' . $status . '|pid:' . $ppid . '|childpid:' . $pid ); } else { Tools::log_message('ERROR', 'daemon/run fail' . '|status:' . $status . '|pid:' . $ppid . '|childpid:' . $pid, 'daemon-'); } }}/** * 业务任务队列处理 */private function mq_process() { $data_pop = $this->masterRedis->rPop($this->redis_list_key); $data = json_decode($data_pop, 1); if (!$data) { return FALSE; } $worker = '_task_' . $data['worker']; $class_name = isset($data['class']) ? $data['class'] : 'TaskproModel'; $params = $data['params']; $class = new $class_name(); $class->$worker($params); return TRUE;}
これは単純なタスク処理システムです。
このタスク システムは非同期実装の実現に役立ち、これまでのところ 1 年近く安定して実行されています。
しかし、残念ながら、これは単一プロセス システムです。常にフォークしており、タスクがあれば処理され、タスクがなければスキップされます。
これは非常に安定しています。
しかし、問題が 2 つあります。1 つは、常にフォークとポップを行うとサーバー リソースが無駄になるということです。もう 1 つは、同時実行がサポートされていないということです。
最初の問題は大丈夫ですが、2 番目の問題は非常に深刻です。
メインシステム が同時に多数のタスクをスローすると、タスクの処理時間は無限に延長されます。
新しいデザイン同時実行の問題を解決するために、より効率的で強力なチーム処理システムを作成する予定です。
PHP7 より前はマルチスレッドがサポートされていなかったため、マルチプロセスを使用します。
インターネット上で多くの情報を見つけました。いわゆるマルチプロセスのほとんどは、バックグラウンドで同時に実行されている N 個のプロセスです。
明らかにこれは不適切です。
私の期待は次のとおりです:
タスクが飛び出すたびにタスクをフォークし、タスクの実行が完了した後に子プロセスが終了します。
発生した問題1. プロセスの最大数を制御する方法
この問題は非常に単純です。つまり、子プロセスの各フォークがそれ自身を増加させます。子プロセスが完了すると一度デクリメントされます。
自動インクリメントには問題はありません。メインプロセスで操作するだけです。では、自分で減らすにはどうすればよいでしょうか?
おそらく、それは子プロセス内にあると言うかもしれません。ただし、ここで注意が必要です。フォークすると、リソースがメインプロセスから子プロセスにコピーされるため、メインプロセスのカウンタを子プロセスで操作することはできません。
つまり、ここで理解する必要がある知識点があります。それはシグナルです。
詳細については自分で Google で調べたり、ここでコードを直接確認したりできます。
// install signal handler for dead kidspcntl_signal(SIGCHLD, array($this, "sig_handler"));これにより、シグナルプロセッサがインストールされます。もちろん、まだ足りないものが 1 つあります。
declare(ticks = 1);declare は制御構造ステートメントです。具体的な使用法については Google を参照してください。
このコードの意味は、低レベルのステートメントが実行されるたびにシグナルプロセッサを呼び出すことです。
このようにして、子プロセスが終了するたびにシグナルプロセッサが呼び出され、シグナルプロセッサ内でそれをデクリメントすることができます。
2. プロセス残留問題の解決方法
マルチプロセス開発では、適切に処理されないとプロセス残留が発生します。
プロセス残留物の問題を解決するには、子プロセスをリサイクルする必要があります。
次に、子プロセスをどのようにリサイクルするかが技術的なポイントになります。
多くのブログ投稿を含む pcntl のデモでは、子プロセスがメインプロセスで再利用されていると言われています。
しかし、私たちは Redis の brpop に基づいており、brpop はブロックしています。
これにより問題が発生します。N 個のタスクを実行した後、タスク システムがアイドル状態のときにメイン プロセスがブロックされ、ブロックが発生したときに子プロセスがまだ実行中であるため、最後のいくつかの子プロセスのプロセス リサイクルを完了できません。 。 。
これはいつも複雑な場所でしたが、信号プロセッサを手に入れてからは非常に簡単になりました。
プロセスリサイクルも信号プロセッサに配置されます。
新システムの評価
pcntl はプロセス処理拡張機能ですが、残念ながらマルチプロセスのサポートが非常に弱いです。
ここでは Swoole 拡張機能のプロセスが使用されています。
具体的なコードは次のとおりです:
declare(ticks = 1);class JobDaemonController extends Yaf_Controller_Abstract{ use Trait_Redis; private $maxProcesses = 800; private $child; private $masterRedis; private $redis_task_wing = 'task:wing'; //待处理队列 public function init(){ // install signal handler for dead kids pcntl_signal(SIGCHLD, array($this, "sig_handler")); set_time_limit(0); ini_set('default_socket_timeout', -1); //队列处理不超时,解决redis报错:read error on connection } private function redis_client(){ $rds = new Redis(); $rds->connect('redis.master.host',6379); return $rds; } public function process(swoole_process $worker){// 第一个处理 $GLOBALS['worker'] = $worker; swoole_event_add($worker->pipe, function($pipe) { $worker = $GLOBALS['worker']; $recv = $worker->read(); //send data to master sleep(rand(1, 3)); echo "From Master: $recv\n"; $worker->exit(0); }); exit; } public function testAction(){ for ($i = 0; $i < 10000; $i++){ $data = [ 'abc' => $i, 'timestamp' => time().rand(100,999) ]; $this->masterRedis->lpush($this->redis_task_wing, json_encode($data)); } exit; } public function runAction(){ while (1){// echo "\t now we de have $this->child child processes\n"; if ($this->child < $this->maxProcesses){ $rds = $this->redis_client(); $data_pop = $rds->brpop($this->redis_task_wing, 3);//无任务时,阻塞等待 if (!$data_pop){ continue; } echo "\t Starting new child | now we de have $this->child child processes\n"; $this->child++; $process = new swoole_process([$this, 'process']); $process->write(json_encode($data_pop)); $pid = $process->start(); } } } private function sig_handler($signo) {// echo "Recive: $signo \r\n"; switch ($signo) { case SIGCHLD: while($ret = swoole_process::wait(false)) {// echo "PID={$ret['pid']}\n"; $this->child--; } } }}
最後に、テストの後、シングルコア 1G サーバーは 1 ~ 3 秒間タスクを実行することで 800 の同時実行性を達成できます。
追伸: マスターの皆様、私とコミュニケーションを取るのを歓迎します。私はもっと上手くできるだろうか〜
私はヤンおじさん、2 週間一生懸命働いてきた野生のプログラマーです

まだ人気があるのは、使いやすさ、柔軟性、強力なエコシステムです。 1)使いやすさとシンプルな構文により、初心者にとって最初の選択肢になります。 2)Web開発、HTTP要求とデータベースとの優れた相互作用と密接に統合されています。 3)巨大なエコシステムは、豊富なツールとライブラリを提供します。 4)アクティブなコミュニティとオープンソースの性質は、それらを新しいニーズとテクノロジーの傾向に適応させます。

PHPとPythonはどちらも、Web開発、データ処理、自動化タスクで広く使用されている高レベルのプログラミング言語です。 1.PHPは、ダイナミックウェブサイトとコンテンツ管理システムの構築によく使用されますが、PythonはWebフレームワークとデータサイエンスの構築に使用されることがよくあります。 2.PHPはエコーを使用してコンテンツを出力し、Pythonは印刷を使用します。 3.両方ともオブジェクト指向プログラミングをサポートしますが、構文とキーワードは異なります。 4。PHPは弱いタイプの変換をサポートしますが、Pythonはより厳しくなります。 5. PHPパフォーマンスの最適化には、Opcacheおよび非同期プログラミングの使用が含まれますが、PythonはCprofileおよび非同期プログラミングを使用します。

PHPは主に手順プログラミングですが、オブジェクト指向プログラミング(OOP)もサポートしています。 Pythonは、OOP、機能、手続き上のプログラミングなど、さまざまなパラダイムをサポートしています。 PHPはWeb開発に適しており、Pythonはデータ分析や機械学習などのさまざまなアプリケーションに適しています。

PHPは1994年に発信され、Rasmuslerdorfによって開発されました。もともとはウェブサイトの訪問者を追跡するために使用され、サーバー側のスクリプト言語に徐々に進化し、Web開発で広く使用されていました。 Pythonは、1980年代後半にGuidovan Rossumによって開発され、1991年に最初にリリースされました。コードの読みやすさとシンプルさを強調し、科学的コンピューティング、データ分析、その他の分野に適しています。

PHPはWeb開発と迅速なプロトタイピングに適しており、Pythonはデータサイエンスと機械学習に適しています。 1.PHPは、単純な構文と迅速な開発に適した動的なWeb開発に使用されます。 2。Pythonには簡潔な構文があり、複数のフィールドに適しており、強力なライブラリエコシステムがあります。

PHPは、多数のWebサイトとアプリケーションをサポートし、フレームワークを通じて開発ニーズに適応するため、近代化プロセスで依然として重要です。 1.PHP7はパフォーマンスを向上させ、新機能を紹介します。 2。Laravel、Symfony、Codeigniterなどの最新のフレームワークは、開発を簡素化し、コードの品質を向上させます。 3.パフォーマンスの最適化とベストプラクティスは、アプリケーションの効率をさらに改善します。

phphassiblasifly-impactedwebdevevermentandsbeyondit.1)itpowersmajorplatformslikewordpratsandexcelsindatabase interactions.2)php'sadaptableability allowsitale forlargeapplicationsusingframeworkslikelavel.3)

PHPタイプは、コードの品質と読みやすさを向上させるためのプロンプトがあります。 1)スカラータイプのヒント:php7.0であるため、基本データ型は、int、floatなどの関数パラメーターで指定できます。 3)ユニオンタイプのプロンプト:PHP8.0であるため、関数パラメーターまたは戻り値で複数のタイプを指定することができます。 4)Nullable Typeプロンプト:null値を含めることができ、null値を返す可能性のある機能を処理できます。


ホットAIツール

Undresser.AI Undress
リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover
写真から衣服を削除するオンライン AI ツール。

Undress AI Tool
脱衣画像を無料で

Clothoff.io
AI衣類リムーバー

Video Face Swap
完全無料の AI 顔交換ツールを使用して、あらゆるビデオの顔を簡単に交換できます。

人気の記事

ホットツール

MantisBT
Mantis は、製品の欠陥追跡を支援するために設計された、導入が簡単な Web ベースの欠陥追跡ツールです。 PHP、MySQL、Web サーバーが必要です。デモおよびホスティング サービスをチェックしてください。

VSCode Windows 64 ビットのダウンロード
Microsoft によって発売された無料で強力な IDE エディター

SublimeText3 Linux 新バージョン
SublimeText3 Linux 最新バージョン

SAP NetWeaver Server Adapter for Eclipse
Eclipse を SAP NetWeaver アプリケーション サーバーと統合します。

ドリームウィーバー CS6
ビジュアル Web 開発ツール
