点击成名,或如何激发机器人等...



从前,在一个遥远的商店的前面进行了一次窃听的谈话:
NB: -         ? 

GURU : - «» . . . , ...

 NB: -      ,     ? 

GURU : - google yandex , . . , .

 NB: -       ? 

GURU : - ?… ...
NB停止询问,显然是担心惹恼一个显然更有经验的对话者。
GURU翻了个白眼,仿佛在强调代理主题的用尽,沉默了……

当然, GURU知道搜索查询(例如,用词:proxy)会很快导致NB获得所需的地址:端口列表。 但是经过第一个实验后, NB很快就会知道:

  • 并非他列表上的所有地址都可以使用;
  • 并非所有代理都同样出色。
  • 手动通过代理“粘贴”站点是一项需要大量意愿的任务;
  • “错误”的代理人会伤害情况,因为 该站点可能会被包装中的巨人脚本所怀疑。


在本文中,我将讨论即兴演奏(最重要的是通用)的含义
(不使用特定的专有软件,如ZennoPoster等)
构建一个自动化工具,以获取“非常合适”的代理列表,并使用它们来组织(自动)访问被推广的代理
使用Chrome浏览器的网站。

按照说明进行操作,您将获得现成的工具,该工具将允许:

  • 完全自动“单击”(访问)目标站点,而不必担心受到威胁;
  • 完全模拟用户行为;
  • 根据时间表(场景)组织所有访问;
  • 进行必要的多次上述操作。

尽管我的所有工作(以及研究工作)都花了一周的时间,但您无需花两天的时间就可以构建这样的工具,并且具有命令行PHPJavaScript的基本知识。


但是,在滚动到下图之前 ,我会说几句话,说明为什么准备这份材料以及为谁准备。

如果您想了解结构(或构造器?)的排列方式,那么该材料将使您可以相对快速,轻松,无成本地构建应用程序,以适应负载变化。 如果您对基于服务总线( ESB )构建应用程序的可能性感兴趣。

如果您想熟悉Docker即时构建系统中的使用,该文本将非常有用。 或者,如果您只是对Selenium Server和接收HTTPx活动的内容/表现的细微差别感兴趣。
对于“立即使用”,若有所思地阅读所有这些都不值得。 该代码是肯定的。
直接安装完成的工具。 安装程序不到20分钟。
本手册假定您有两台安装了Ubuntu 18.04的计算机供您使用。
一个用于基础架构( docker ),另一个用于流程控制( process )。

假设以下软件包已安装在docker上
git,码头工人,码头工人组成

假定在进程中已经安装了以下软件包:
git,php-common,php-cli,php-curl,php-zip,php-memcached,作曲家
如果您现在有任何疑问,建议您花15分​​钟阅读全部内容。

码头工人

 #    root-. # ,     TCP-: # 11300, 11211, 4444, 5930, 8080, 8081, 8082, 8083 #        # " root-"    git clone \ https://oauth2:YRGzV8Ktx2ztoZg_oZZL@git.ituse.ru/deploy/esb-infrastructure.git cd esb-infrastructure docker-compose up --build -d #      3     #   . #       web-. 

过程

 #      . #      process-   , #     -  php- git clone \ https://oauth2:YRGzV8Ktx2ztoZg_oZZL@git.ituse.ru/deploy/clicker-noserver.git cd clicker-noserver composer update #  .       "XXXXXXXX" mv app/settings.php.dist app/settings.php #   . gnome-terminal \ --tab -e 'bash -c "php app/src/Process/noserver/singleProcess.php curl"' \ --tab -e 'bash -c "php app/src/Process/noserver/singleProcess.php timezone"' \ --tab -e 'bash -c "php app/src/Process/noserver/singleProcess.php whoer"' #  . ,     , #  : - log/list.proxy php app/src/Utils/givethejob.php ./log/list.proxy 

等待,通过Web面板观察正在发生的事情(http:// ip-address-docker-machines:8080)。
结果将在找到的队列中可用。

破碎与计划




上图描述了处理步骤的顺序,每个步骤的预期结果以及创建每个零件所需的资源(详细信息: 任务2任务3任务4,5,6 )。

就我而言,一切都发生在两台Ubuntu 18.04计算机上。 其中之一控制过程。 另一方面,几个基础架构泊坞窗容器正在运行。

借口和失败


所有程序包代码均由三部分组成。
其中之一不是我的(我注意到这是一个简洁漂亮的代码)。 该代码的来源是packagist.org

我自己写了另一本书,我试图使其易于理解,并花了大约一周的时间来编写这部分代码。

其余的是“艰难的历史遗产”。 这部分代码是在相当长的时间内创建的。 包括在我没有太多编程技能的时候。

这正是在我的GitLabSatis上的软件包位置放置存储库的原因。 要在GitHub.compackagist.org上发布此代码将需要处理和更详尽的文档。

该代码的所有部分均开放供无限使用。 存储库和软件包将永远可用。

但是,当重新发布代码时,感谢您发布指向我或本文的链接。

关于架构的一点点


用于创建工具的方法是编写(或使用现成的)实用程序来解决每个特定任务。 而且,每个实用程序,无论要解决的任务如何,都具有两个共有的属性:

  • 可以从命令行使用包含任务的参数独立启动该实用程序;
  • 该实用程序可以将执行结果返回到stdout(以某种方式进行配置之后)。

通过此原理制定的解决方案使您可以更改每个流程步骤的正在运行的任务处理程序(工作人员)的数量。 由于先前步骤的处理任务很长,因此每个步骤使用的工人数量不同,将导致后续步骤的“ 0”停机时间。

获取过程结果的单位(在我们的情况下是经过验证的代理)所花费的时间取决于外部因素(不合适的代理数量,外部资源的响应时间等)。

通过更改每个流程步骤的工作人员数量,我们将这种依赖性转换为对正在运行的工作人员数量的依赖性(即,取决于所涉及的计算和通道容量)。

为了同步各个独立部分的操作,将消息传递队列服务器用作单个数据总线很方便。 它将允许您在队列中累积已完成步骤的结果,并在适当的时候将其提供给“下一步”实用程序作为输入。

消息队列。 MQ和ESB


作为较低级别( MQ ),我们将使用beantalkd 。 小型,轻巧,无需配置,可在deb包和Docker容器中使用,这是一个不起眼的艰苦工作。 逻辑级别( ESB )将用PHP实现代码。

两个类将用于实现。 esbTasknextStepWorker

esbTask

 class esbTask //   ,     { // immutable-; // "" (   ESB-),  payload //    //     "" .... } 

此类的一个实例用于通过流程的各个步骤“解决” 付款问题ESB概念采用了几种原理/模式。 其中两个值得分别注意:

  • 关于流程的路径(步骤顺序),在流程的每个时间点,
    除了要发送的信封,没人知道。
  • 每个信封都有三个可能的结果方向:
    • 流程的下一步(正常继续);
    • 停止步骤(停止目标-如果没有必要继续进行该过程/停止情况,则由下一步选择);
    • 错误步骤(紧急终止目标-如果出现工作人员错误,则由下一步选择)。

排队的对象以json表示,隐藏在这里...
 // json- esbTask { //    (   esbTask) "_type":"App\\\\rebean\\\\payloads\\\\ESBtaskQueue", //  "task":"task:queue@XXX.XXX.XXX.XXX:11300", //    () "replyto":[ "othertask1:nextqueue1@yyy.XXX.XXX.XXX:11300", "othertask2:nextqueue2", "othertask3:nextqueue3", ], //    () "onerror":[ "error:errorsstep@zzz.XXX.XXX.XXX:11300", "error:errorsstep1", "error:errorsstep2", "error:errorsstep3" ], //     () "onstop":[ "stop:stopstep@kkk.XXX.XXX.XXX:11300", "stop:stopstep1", "stop:stopstep2", "stop:stopstep3" ], //   "payload":{ .... }, //   ... () "till":[ .... ], //     ... () //        // -  (LINUX-TimeStamp) "since":[ 1540073089.8833, ], // -     "points":1, //  .     "groupid":"" } 


nextStepWorker

队列中显示的每条消息均由负责它的工作人员处理。 为此,实现了以下功能集:

 class nextStepWorker extends workerConstructor { //       //     esbTask //    () //    MQ- (beanstalkd) //     (Memcached) //     (MySQL) // : -  (  - ); -    stop-; -      (log, event, mq) .... } 

每个过程步骤的工作人员都是基于此类来实现的。 处理,寻址和发送路径中下一步的整个例程,由类负责。

解决每个问题的方法是:

  1. 获取esbTask并运行worker;
  2. 通过将结果存储在有效载荷中来实现逻辑;
  3. 完成工人的处决(紧急还是正常-没关系)。

如果步骤完成,结果将以适当的名称排队,下一个工作程序将开始处理。

做一次。 查看空房


实际上,创建工人解决任何问题是一种方法的实现。 解决问题2的工人的实现示例(简化)如下:

 // app/src/Process/worker/curlChecker.php .... class curlChecker extends nextStepWorker { const PROXY_INFO = 'https://api.ipfy.me?format=json&geo=true'; const PROXY_TIMEOUT = '40'; const COMMAND = "curl -m %s -Lx http://%s:%s '%s'"; public function logic() { //    .  ..   payload extract($this->context()); //  defaults    payload  $curltimeout = $curltimeout ?? self::PROXY_TIMEOUT; $curlchecker = $curlchecker ?? self::PROXY_INFO; //     $line = sprintf( static::COMMAND, $curltimeout, $host, $port, $curlchecker ); exec($line, $info); //      // ( ,  stop-) $info = arrays::valid_json(implode('', info)); if (empty($info)) throw new \Exception("Bad proxy: $host:$port!", static::STATUS_STOP); //    payload $this->enrich(['info']) ->sets(compact('info')); } } 

几行代码即可完成所有工作,并将其“分流”到下一个阶段。

定义时区。 TimeZoneDB及其用途...


对传入请求的深入测试涉及将浏览器窗口时间与请求源IP地址存在的时间进行匹配。

为了避免被柜台怀疑,我们需要知道本地代理时间。

为了找出时间,我们从过程上一步的结果中获取经度和纬度,并获取有关将来的浏览器窗口实例将在其中工作的时区的数据。 这些数据将由时间领域的专业人员提供给我们。

解决此问题的简化工人( 任务3 )与上一个工人完全类似。 唯一的区别是请求URL。 您可以在文件中找到完整版本:
// app / src / Process / worker / timeZone.php

关于基础架构的一些知识


除了所描述的beantalkd之外 ,我们的工具还需要:

  • Memcached-用于缓存任务;
  • Selenium Server-在一个单独的容器中运行Selenium Web Driver很方便,您可以通过VNC监视该过程;
  • 用于监视beantaldmemcachedVNC的仪表板。

为了快速部署所有这些,Docker( 如何在Ubuntu上安装 )非常方便。

而他的“协调者”是docker-compose(安装命令)...
 sudo apt-get -y update sudo apt-get -y install docker-compose 


这些工具使您可以在父操作系统的单独“容器”中运行已配置和配置(由较早的人员配置)的服务器/进程。 有关详细信息,建议参考本文或本文。

所以...

要启动基础结构,您需要在控制台中输入以下命令:

 #   ,    docker- #     (   ) #    sudo -s git clone \ https://oauth2:YRGzV8Ktx2ztoZg_oZZL@git.ituse.ru/deploy/esb-infrastructure.git \ panels cd panels docker-compose up --build -d #   . 

在地址为XXX.XXX.XXX.XXX的计算机上成功执行命令后,
您将收到以下服务集:
-XXX.XXX.XXX.XXX:11300-缠豆
-XXX.XXX.XXX.XXX:11211-Memcached
-XXX.XXX.XXX.XXX-00-00444- Selenium服务器
-XXX.XXX.XXX.XXX:5930-VNC服务器来控制Chrome中发生的情况
-XXX.XXX.XXX.XXX:8081-用于与Memcached通信的Web面板(管理员:通过)
-XXX.XXX.XXX.XXX:8082-用于与beantalkd通信的Web面板
-XXX.XXX.XXX.XXX:8083-用于与VNC通信的Web面板(密码:秘密)
-XXX.XXX.XXX.XXX:8080-常规网络面板

“扰流板”中的命令是“查看是否一切就绪”,“进入控制台进入容器”,“停止基础结构”。
 #   ,    docker-, #    ..../panels/ #    docker-compose ps # Name Command State Ports # ------------------------------------------------------------------------------------------------------------------------ # beanstalkd /usr/bin/beanstalkd Up 0.0.0.0:11300->11300/tcp # chrome start-cron Up 0.0.0.0:4444->4444/tcp, 0.0.0.0:5930->5900/tcp # memcached docker-entrypoint.sh memcached Up 0.0.0.0:11211->11211/tcp # nginx docker-php-entrypoint /sta ... Up 0.0.0.0:8443->443/tcp, 0.0.0.0:8080->80/tcp, # 0.0.0.0:8082->8082/tcp, 0.0.0.0:8083->8083/tcp, 9000/tcp # vnc /usr/bin/supervisord -c /e ... Up 0.0.0.0:8081->8081/tcp #       chrome docker exec -ti chrome /bin/bash #       docker-compose stop && docker rm $(docker ps -a -q) 

任务4,5,6-合并为一个实用程序


详细研究了任务(上 )后,很容易确保其余任务( 任务6 )中只有一个依赖于外部资源。 在“有条件保证”的运行时(不受不受控制的因素影响)的情况下执行任务,我们不会在整个过程的速度上获得更多优势。 在这方面,这些任务( 4,5,6 )被合并为一名工人。 工作文件称为:
// app / src / Process / worker / whoerChecker.php

为Chrome进行设置。 外挂程式


Chrome通过插件灵活配置。

Chrome的插件是一个包含manifest.json文件的存档。 他描述了插件。 该归档文件还包含该插件所需的一组JavaScript,html,css和其他文件( 详细信息 )。

在我们的情况下,其中一个JavaScript文件将在Chrome工作窗口的上下文中执行,所有必要的设置都会生效。

我们只需要获取插件模板,然后在正确的位置替换必要的数据(交互协议,地址和端口或时区)以代替被测试的代理服务器即可。

组成档案的一段代码:

 // app/src/Chrome/proxyHelper.php .... class proxyHelper extends sshDocker{ .... // $name -  - // $files - [ ... '   -' => '', ...] protected function buildPlugin(string $name, array $files) { $this->last = "$this->cache/$name"; if (!file_exists("$this->last")) { $zip = new \ZipArchive(); $zip->open("$this->last", \ZipArchive::CREATE | \ZipArchive::OVERWRITE); foreach ($files as $n => $data) { $zip->addFromString(basename($n), $data); } $zip->close(); } $this->all[] = $this->last; $this->all = array_unique($this->all); return $this; } .... } 

代理调整插件的模板是在热爱专业人士的工作成果的存钱罐中找到 ,在协议部分进行了更改,然后添加到了存储库中。

窗口时间改变


要更改正在运行的Chrome实例的全球时间,我们需要使用功能相似但在正确时区有效的类替换window.Date

我非常感谢Sampo Juustila的工作 。 该脚本是为UI的自动化测试而制作的,但是经过了一些改进。

我想在此引起您的注意。 它与manifest.json中描述的脚本的上下文相关联。

整个秘密在于,全局上下文(在该上下文中启动了插件的主脚本并设置了设置,例如,连接到网络)与页面加载到的选项卡的上下文隔离。

根据经验,发现在全局上下文中对类的原型的影响并未导致其在选项卡中的更改。 但是,在已加载的页面中注册了脚本并在其他页面之前执行了脚本之后,问题得以解决。

解决方案由以下代码片段表示:

 // app/chromePlugins/timeShift/content.js //     var s = document.createElement('script'); //        s.src = chrome.extension.getURL('timeshift.js'); //      (document.head || document.documentElement).appendChild(s); 

代理设定


在Chrome中设置代理非常简单,以至于我会将js代码隐藏在扰流器中
 // app/chromePlugins/proxy/background.js var config = { mode: "fixed_servers", rules: { singleProxy: { scheme: "%scheme", host: "%proxy_host", port: parseInt(%proxy_port) }, bypassList: ["foobar.com"] } }; chrome.proxy.settings.set({value: config, scope: "regular"}, function () { }); function callbackFn(details) { return { authCredentials: { username: "%username", password: "%password" } }; } chrome.webRequest.onAuthRequired.addListener( callbackFn, {urls: ["&gtall_urls&lt"]}, ['blocking'] ); 


Chrome插件路径


所有插件均根据方案命名,并被添加到控制该过程的计算机的临时文件夹中。
//代理插件的命名方案:
代理服务器-[地址]-[端口]-[协议]>。zip
timeshift-[“-” |“”]-[shift_in_minutes_from_GMT] .zip

接下来,我们需要将这些插件安装在负责基础结构的机器上运行的docker容器中。

我们将使用ssh进行此操作。为此,我遇到了phpseclib(甚至后来对此感到遗憾)。被图书馆的异常行为所吸引,我花了一天的时间研究它。

ssh控制台客户端将在此处更好地工作,并且将更快地工作,但是该工作已经完成。

对于低级别(使用SFTP和SSH),基类负责(以下)。替换此类将用控制台客户端替换phpseclib

 // app/src/Chrome/sshDocker.php //    (DOCKER_HOST, DOCKER_USER, DOCKER_PASS) //   : app/settings.php //      .... class sshDocker { .... //  .     docker //    .         // : app/techs.php const EXEC_DOCKER = DOCKER_BIN_PATH . "/docker exec -i %s %s"; .... //     sudo    (  ),  DOCKER_USER -  protected function sudo(string $command, string $expect = '.*'){...} //     Docker-,      //       -    self::EXEC_DOCKER protected function execDocker(string $command, string $expect){...} .... } 

从基础sshDocker和已知的proxyHelper类派生而来,它不仅产生插件,而且将它们放在基础结构容器的临时文件夹中。

 // app/src/Chrome/proxyHelper.php .... class proxyHelper extends sshDocker { .... public static function new(string $docker, $plugins) { return (new self($docker, $plugins)) ->setupPlugins(); } .... } 

使用设置启动Chome


Selenium Server将帮助我们启动定制的ChromeSelenium Server是FaceBook团队创建的专门用于测试WEB界面的框架框架使开发人员能够以编程方式模拟浏览器窗口中的任何用户操作(使用ChromeFirefox)。Selenium Server适用于多种语言,实际上是编写测试脚本的标准工具。获得要在项目中使用的新发行版的最佳方法:









 composer require facebook/webdriver 

Selenium Server对象的主要实例(RemoteWebDriver)的传统配置对我来说很冗长。
 // URL- $url = "https://example.com/books/196/empire-v-povest-o-nastoyashem-sverhcheloveke"; // URL,     (Selenium Server) $server = 'http://' . DOCKER_HOST . '/wd/hub'; //   ,      $options = new ChromeOptions(); $options->addArguments(array( '--disable-notifications' )); //    - $capabilities = DesiredCapabilities::chrome(); $capabilities->setCapability(ChromeOptions::CAPABILITY, $options); //        5000     URL $driver = RemoteWebDriver::create($server, $capabilities, 5000); $page = $driver->get($url); 


因此,我稍微减少了所有这些,针对我的需求优化了配置:

 // app/src/Process/worker/whoerChecker.php .... class whoerChecker extends nextStepWorker { //    : app/settings.php // URL Selenium Server const SELENIUM_SERVER = CHVM; //  - const DOCKER_NAME = DOCKER_NAME; .... public function config() .... //        : // $driver = RemoteWebDriver::create($server, $capabilities, 5000); $chrome = Chrome::driver( static::SELENIUM_SERVER, Chrome::capabilities(static::DOCKER_NAME, $plugins), 5000 ); .... } .... 

眼睛立即紧紧抓住$插件。$ plugins是负责配置插件的数据结构。对于每个目录以及替换插件JavaScript文件占位符

该结构在app / plugs.php文件中进行了描述,并且是全局选项app / settings.php的一部分。
 // app/plugs.php const PLUGS = [ 'timeshift' => [ 'path' => PROJECTPATH . '/app/chromePlugins/timeShift', 'files' => ['manifest.json', 'timeshift.js', 'content.js'], 'fields' => ['%addsminutes' => 'timeshift'] ], 'proxy' => [ 'path' => PROJECTPATH . '/app/chromePlugins/proxy', 'files' => ['manifest.json', 'background.js'], 'fields' => [ '%proxy_host' => 'host', '%proxy_port' => 'port', '%scheme' => 'scheme', '%username' => 'user', '%password' => 'pass' ] ] ]; 


使用Selenium WebDriver解析页面非常简单。

 .... $url = 'https://__/_-_'; $page = $chrome->get($url); .... //   xPath-   $xpath = '/html[1]/body[1]/div[1]/div[1]/div[1]/div[2]/div[1]/div[1]/div[1]/div[1]/strong[1]'; $element = page->findElement(WebDriverBy::xpath($xpath)); .... //   $text = $element->getText(); // HTML- $html = $element->>getAttribute('innerHTML'); .... 

正如我已经写过的,所有这些操作都是通过第三步的实用程序(任务4,5,6)实现的:
// app / src / Process / worker / whoerChecker.php
结束语关于Selenium Server的使用的说明,我想提请您注意以下事实:在工业规模上使用该技术(页面打开数为1000-3000),与Selenium Server的会话错误结束的情况并不少见。窗口是无主的。这样的窗户会积累很多。

考虑了几种对抗“胸针”的方法。工作“吃” 2天。最有效的是cron。正确安装和设置在多克尔容器变成一个独立的任务,并仔细描述很详细renskiy致力于只有这个主题的文章中(我很惊讶)。

基础结构存储库 docker-compose.yml中介绍了自动重建原始Docker映像以及安装多个脚本以关闭胸针并清理未使用的插件的过程清理频率在同一存储库的killcron文件中设置。

WebRTC


尽管我们已经设置了正确的时间,并且浏览器的流量通过了代理,但仍然可以检测到我们。

除了时差(浏览器和IP地址)外,还有两个其他的去匿名化来源:“坐在代理后面”。这些是嵌入在浏览器中的Flash和WebRTC技术。在我们的浏览器中Flash已禁用,而WebRTC则未禁用

两种失败可能性的原因是相同的-普遍存在的灵活UDP数据包。对于WebRTC,这是两个端口:347819302

为了阻止侦察兵从chrome容器中外逃,iptables规则应用于具有基础结构容器的主机:

 iptables -t raw -I PREROUTING -p udp -m multiport --dports 3478,19302 -j DROP 

相同的proxyHelper实现此任务。

其余的工人


为了成功实现目标-通过匿名代理在目标站点上实现“点击”,我们还需要一名工作人员。

这将是whoerChecker的截断版本我认为,使用所写的所有内容自行完成,这并不困难。

整个过程的结果将落入已定位的队列中,其中包含有关已验证的每个代理服务器地址的匿名程度的数据。

在柜台上“比赛”时,要记住的主要是匿名性,不会被机器人的访问所迷惑。坚持的原则是“不要得意忘形点击”提供机会的活动如期组织,这是在合并esbTask(场,因为我们的ESB信封)。

如果您尝试仔细地做所有事情,那么目标站点yandex度量将类似于下图。



如何将所有东西放在一起


因此,鉴于:

  • 能够接受json-string形式的“作为输入”(作为命令行参数)esbTask的实用程序,并执行一些逻辑,然后将结果发送给beanstalkd
  • 基于beantalkd的消息队列MQ
  • Linux机器(Process machine);

有了这个“给定”,通常我使用libeventReact PHP所有这些,再加上几种工具,可让您自动控制过程每个阶段的处理程序实例的数量(在指定的限制内)。

但是,考虑到文章的大小和主题的细节,我很乐意在单独的文章中描述所有这些内容。本文是noserver技术未来的东西是“ 服务器 ”。
亲爱的读者,它的出版日期与您的兴趣有关。
. , ,… . , , , , , .

habr , . , , .

. , " server ", README.md .

在“ noserver ”中,一个实例将处理一个队列(一个处理步骤)。这种方法只会激怒我在调试工人时使用的精神

根据所需的处理速度,您可以“手动”开始任意数量的副本。

它可能看起来像这样:

 // app/src/Process/noserver/singleProcess.php //   ,    //   include __DIR__ . '/../../../settings.php'; use App\ESB\pipeNcacheService; use App\arrayNstring\queueDSN; use App\arrayNstring\timeSpent; use App\arrayNstring\progressString; //    $path = __DIR__ . '/../worker'; //   $queues = array_keys(WORKERS); $queue = $argv[1] ?? end($queues); $queue = strtolower($queue); if (!in_array($queue, $queues)) die("php $argv[0] <queue_name>" . PHP_EOL); //  - $progress = new progressString("Listenning... Idle: ", 40, 20); // ,      $stopwatch = timeSpent::start(); //    beanstalkd- list($worker, $task) = WORKERS[$queue]; $procid = ['procid' => posix_getpid()]; //   beanstalkd  Memcached, //     ( ) $dsn = new queueDSN($task, $queue, ...QUEUE_SERVER); //     ESB- $pnc = new pipeNcacheService($dsn); $pipe = $pnc->getPipe(); echo "Start listener for queue: $queue." . PHP_EOL; echo "Press Ctrl-C to stop listener." . PHP_EOL; //      //       while (true) { try { $job = $pipe->watch($queue) ->reserve(1); $now = new DateTime(); $opts = json_encode($pipe->getPayload($job) + $procid); $pipe->delete($job); echo PHP_EOL . "Task recived at: " . $now->format('H:i:s') . " Starting worker: $worker. "; $stopwatch = timeSpent::start(); exec("php $path/$worker $opts", $out); echo "Finished. Time spent: $stopwatch" . PHP_EOL; $stopwatch = timeSpent::start(); } catch (Throwable $exception) { echo $progress($stopwatch('%I:%S', null, $now)); } } 

工人的奇怪起点令人震惊……尽管每个工人都是一个PHP对象,但我还是使用exec(...)

这样做是为了节省时间,以便不要为“ noserver创建单独的工作程序,或者不为了以“ server模式启动而更改工作程序

关于配置和部署的几句话


配置常量


您的实例的配置文件是app / settings.php您应该在克隆存储库后立即创建它。为此,请重命名文件app / settings.php.dist所有常量均在内部进行描述。

app / settings.php以及其他内容包括具有其他常量的文件。
- 应用程序/ queues.php包含队列和作业的名称
- 应用程序/ plugs.php描述 -plaginov
- 应用程序/ techs.php包含常数计算

实用工具


为了方便处理过程的结果和放置任务,有几个实用程序。实用程序从命令行启动。提供参数说明。位于:app / src / Utils
 backup.php-将队列保存到文件
    clear.php-清理队列
    exporter.php-从具有已保存队列的文件中导出 
                     配对地址:端口
    Givethejob.php-将任务发布到流程 
                     (源-地址:端口组合框)。
                     可以从列表中排除一些地址
    restore.php-恢复保存的队列 

对工人进行微调


使用书面工作者时,使用以下配置选项可能会很方便:

 // app/src/Process/worker/curlChecker.php .... $worker = new curlChecker( [ //    curlChecker::WORKER => 'curlchecker', //  beanstalkd curlChecker::PIPE_HOSTPORT => implode(':', QUEUE_SERVER), //  Memcached curlChecker::CACHE_HOSTPORT => implode(':', MEMCACHED), // ,    . //    -   curlChecker::DB_SCRIPT => __DIR__ . '/../../../confdb.php', // ,       // (        -) curlChecker::INFO_START => CURL_START, // ,        // (        -) curlChecker::INFO_END => CURL_END, //  ,     //    //        curlChecker::INFO_ADDS_END => ['host', 'port'] ], ['setupworker', 'config', 'logic'] ); .... 


部署方式


本手册假定您有两台安装了Ubuntu 18.04的计算机供您使用
一个用于基础架构(docker),另一个用于流程控制(process)。

码头工人

 #    root-. # ,     TCP-: # 11300, 11211, 4444, 5930, 8080, 8081, 8082, 8083 #   . sudo -s apt -y update apt -y install git snap snap install docker apt -y install docker-compose # C       # " root-"    cd ~ git clone \ https://oauth2:YRGzV8Ktx2ztoZg_oZZL@git.ituse.ru/deploy/esb-infrastructure.git cd esb-infrastructure docker-compose up --build -d #      3     #   . #       web-. 

过程

 #      . #   . sudo apt -y update sudo apt -y install git php-common php-cli php-curl php-zip php-memcached composer # C     process-   , #     -  php- cd /var/www git clone \ https://oauth2:YRGzV8Ktx2ztoZg_oZZL@git.ituse.ru/deploy/clicker-noserver.git cd clicker-noserver composer update #  .       "XXXXXXXX" mv app/settings.php.dist app/settings.php #   . gnome-terminal \ --tab -e 'bash -c "php app/src/Process/noserver/singleProcess.php curl"' \ --tab -e 'bash -c "php app/src/Process/noserver/singleProcess.php timezone"' \ --tab -e 'bash -c "php app/src/Process/noserver/singleProcess.php whoer"' #  . ,     , #  : - log/list.proxy php app/src/Utils/givethejob.php ./log/list.proxy 

等待,通过Web面板观察正在发生的事情(http:// ip-address-docker-machines:8080)。
结果将在队列中可位于

最后


令人惊讶的是,编写和编辑本文所花的时间比编写代码本身要花费更长的时间。

在我看来,如果没有两种意识形态:消息队列企业服务总线,一切都可能相反(并且时差可能会大几倍)

如果您发现提出的编写应用程序的方法很有用,在设计阶段尚不清楚其不同部分的负担,我将非常高兴。

谢谢啦

Source: https://habr.com/ru/post/zh-CN432038/


All Articles