<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
  <channel>
    <title>leijun (leijun)</title>
    <link>https://ruby-china.org/leijun</link>
    <description/>
    <language>en-us</language>
    <item>
      <title>ActiveStorage 问题</title>
      <description>&lt;p&gt;大家好
现在有一个 S3 问题
Couldn't find ActiveStorage::Blob with id = ‘’‘’&lt;/p&gt;

&lt;p&gt;背景：
一个 portfolio 产生了 3 万左右条的 xlsx ,发送到 s3 服务器，然后给用户发一个带有链接的邮件，然后点击这条链接就出现了这个 Couldn't find ActiveStorage::Blob with id = ‘’‘’问题。
是什么原因呢？大概？我网上找了一遍，都没有答案。&lt;/p&gt;</description>
      <author>leijun</author>
      <pubDate>Tue, 06 Jun 2023 00:43:49 +0800</pubDate>
      <link>https://ruby-china.org/topics/43149</link>
      <guid>https://ruby-china.org/topics/43149</guid>
    </item>
    <item>
      <title>一道 PG buffer full 问题  </title>
      <description>&lt;p&gt;我现在碰到了一道难题
现在有一个很大的 query 表，里面大概几千万 record
这个表里面有一个 column response 里存的是 xml,&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;    &lt;span class="no"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;count&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
             &lt;span class="no"&gt;CASE&lt;/span&gt; &lt;span class="no"&gt;WHEN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt;  &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt; &lt;span class="no"&gt;THEN&lt;/span&gt; &lt;span class="s1"&gt;'0'&lt;/span&gt;
                  &lt;span class="no"&gt;WHEN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt; &lt;span class="no"&gt;BETWEEN&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="no"&gt;AND&lt;/span&gt; &lt;span class="mi"&gt;10&lt;/span&gt; &lt;span class="no"&gt;THEN&lt;/span&gt; &lt;span class="s1"&gt;'1-10'&lt;/span&gt; 
                  &lt;span class="no"&gt;WHEN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt; &lt;span class="no"&gt;BETWEEN&lt;/span&gt; &lt;span class="mi"&gt;11&lt;/span&gt; &lt;span class="no"&gt;AND&lt;/span&gt; &lt;span class="mi"&gt;20&lt;/span&gt; &lt;span class="no"&gt;THEN&lt;/span&gt; &lt;span class="s1"&gt;'11-20'&lt;/span&gt; 
                  &lt;span class="no"&gt;WHEN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt; &lt;span class="no"&gt;BETWEEN&lt;/span&gt; &lt;span class="mi"&gt;21&lt;/span&gt; &lt;span class="no"&gt;AND&lt;/span&gt; &lt;span class="mi"&gt;30&lt;/span&gt; &lt;span class="no"&gt;THEN&lt;/span&gt; &lt;span class="s1"&gt;'21-30'&lt;/span&gt; 
                  &lt;span class="no"&gt;WHEN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt; &lt;span class="no"&gt;BETWEEN&lt;/span&gt; &lt;span class="mi"&gt;31&lt;/span&gt; &lt;span class="no"&gt;AND&lt;/span&gt; &lt;span class="mi"&gt;40&lt;/span&gt; &lt;span class="no"&gt;THEN&lt;/span&gt; &lt;span class="s1"&gt;'31-40'&lt;/span&gt; 
                  &lt;span class="no"&gt;WHEN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt; &lt;span class="no"&gt;BETWEEN&lt;/span&gt; &lt;span class="mi"&gt;41&lt;/span&gt; &lt;span class="no"&gt;AND&lt;/span&gt; &lt;span class="mi"&gt;50&lt;/span&gt; &lt;span class="no"&gt;THEN&lt;/span&gt; &lt;span class="s1"&gt;'41-50'&lt;/span&gt; 
                  &lt;span class="no"&gt;WHEN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt; &lt;span class="no"&gt;BETWEEN&lt;/span&gt; &lt;span class="mi"&gt;51&lt;/span&gt; &lt;span class="no"&gt;AND&lt;/span&gt; &lt;span class="mi"&gt;60&lt;/span&gt; &lt;span class="no"&gt;THEN&lt;/span&gt; &lt;span class="s1"&gt;'51-60'&lt;/span&gt; 
                  &lt;span class="no"&gt;WHEN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt; &lt;span class="no"&gt;BETWEEN&lt;/span&gt; &lt;span class="mi"&gt;61&lt;/span&gt; &lt;span class="no"&gt;AND&lt;/span&gt; &lt;span class="mi"&gt;70&lt;/span&gt; &lt;span class="no"&gt;THEN&lt;/span&gt; &lt;span class="s1"&gt;'61-70'&lt;/span&gt; 
                  &lt;span class="no"&gt;WHEN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;70&lt;/span&gt; &lt;span class="no"&gt;THEN&lt;/span&gt; &lt;span class="s1"&gt;'+70'&lt;/span&gt; 
             &lt;span class="k"&gt;END&lt;/span&gt; &lt;span class="no"&gt;AS&lt;/span&gt; &lt;span class="no"&gt;RANGE&lt;/span&gt;
      &lt;span class="no"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;queries&lt;/span&gt;
      &lt;span class="no"&gt;WHERE&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xpath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'/search-results'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;))[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="no"&gt;IS&lt;/span&gt; &lt;span class="no"&gt;NOT&lt;/span&gt; &lt;span class="no"&gt;NULL&lt;/span&gt;
      &lt;span class="no"&gt;GROUP&lt;/span&gt; &lt;span class="no"&gt;BY&lt;/span&gt; &lt;span class="no"&gt;RANGE&lt;/span&gt; 

&lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;ActiveRecord&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="no"&gt;Base&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;connection&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;execute&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;sql&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;然后允许这个 rake 的时候，发生问题&lt;/p&gt;
&lt;pre class="highlight ruby"&gt;&lt;code&gt;&lt;span class="n"&gt;rails&lt;/span&gt; &lt;span class="n"&gt;aborted!&lt;/span&gt;
&lt;span class="no"&gt;ActiveRecord&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="no"&gt;StatementInvalid&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="no"&gt;PG&lt;/span&gt;&lt;span class="o"&gt;::&lt;/span&gt;&lt;span class="no"&gt;InvalidXmlContent&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="no"&gt;ERROR&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;  &lt;span class="n"&gt;invalid&lt;/span&gt; &lt;span class="no"&gt;XML&lt;/span&gt; &lt;span class="n"&gt;content&lt;/span&gt;
&lt;span class="no"&gt;DETAIL&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;  &lt;span class="n"&gt;buffer&lt;/span&gt; &lt;span class="n"&gt;full&lt;/span&gt;
&lt;span class="no"&gt;CONTEXT&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;  &lt;span class="n"&gt;parallel&lt;/span&gt; &lt;span class="n"&gt;worker&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;这是怎么情况啊？
请教各位大神&lt;/p&gt;</description>
      <author>leijun</author>
      <pubDate>Tue, 29 Nov 2022 18:56:49 +0800</pubDate>
      <link>https://ruby-china.org/topics/42770</link>
      <guid>https://ruby-china.org/topics/42770</guid>
    </item>
    <item>
      <title>Ruby on Rails 工程师去大厂</title>
      <description>&lt;p&gt;最近面试的时候，HR 说我简历做不了他们的后端工程师，不断强调我没有分布式经验。
还说他们公司的 ful stack 岗位百分之 80 都是做前端工作，所以叫我要投的话那么就投前端做 typescript + react, 然后叫我重新拾起 javascript 用它来刷 leetcode, 最好要刷到 hard 难度，
所以我的总结是大厂的后端和中小后端要求不一样，所以这是不是和 github 使用 rails 做前端，使用 GO 做后端分布式有点类似啊？
这换 tech stack 对我好不好？？？&lt;/p&gt;</description>
      <author>leijun</author>
      <pubDate>Mon, 19 Oct 2020 16:01:22 +0800</pubDate>
      <link>https://ruby-china.org/topics/40488</link>
      <guid>https://ruby-china.org/topics/40488</guid>
    </item>
    <item>
      <title>请教如何检测 docker rails application </title>
      <description>&lt;p&gt;又来像大佬们发问了。
我公司从 Heroku 迁移到 IBM Cloud 上，就感觉复杂了很多，会出现不懂的错误。
我们在云上使用 docker,  比如 sidekiq 和 application. 
现在我们发现 docker 上 sidekiq 会丢失 job, 目前 devops 人察觉到的是 sidekiq on docker 有时候发生错误会重启，这个错误是 OutOfMemoryError, 内存爆了 (举个例子，比如有时有 pdf generation，会占用超过 10 GB 的内存，好几千页的 pdf )
一般发生这种错误的情况都发生在 auto scale up / down 的时候，目前 auto scaling 是根据 cpu 使用率来 scale 的。&lt;/p&gt;

&lt;p&gt;所以呢 我的 leader 给了我一个开放性的任务， 
第一，如何侦测和抓到 OutOfMemoryError 错误。然后使用 AirBrake 之类的插件发送 notification 给自己，然后确定丢失的 job 就是这个 OutOfMemoryError 引起的。(目前不确定，只是猜想)
 第二，在 scale up 特别是 scale down 的时候，SIGTERM 这个信号有没有造成 job 丢失，还有然后观察 job 是如何被重新推进 sidekia queue 的。&lt;/p&gt;

&lt;p&gt;目前我的做法是：
我现在还是 docker 初学者，先试着在本地搭建 docker, 然后适合把 rails sidekiq 放到 docker 上，然后试试如何把它爆掉，还有本地 scale up scale down. 
这做法对吗？还有什么好的方法吗？&lt;/p&gt;

&lt;p&gt;先谢谢大家了。&lt;/p&gt;</description>
      <author>leijun</author>
      <pubDate>Mon, 03 Aug 2020 21:04:50 +0800</pubDate>
      <link>https://ruby-china.org/topics/40227</link>
      <guid>https://ruby-china.org/topics/40227</guid>
    </item>
    <item>
      <title>Sidekiq limit fetch 一个问题</title>
      <description>&lt;p&gt;大家好，我又过来问问题了。现在我公司碰到了一个奇怪的问题，一个 sidekiq queue 动不了了。
目前我们使用 gem 'sidekiq-limit_fetch'
对一个外部 API 访问，我们设置了 limit
比如
:limits:
    my_queue: 1
因为这个外部 API 要一个接一个访问，不能 simultaneously.&lt;/p&gt;

&lt;p&gt;以前我们在本地还有 heroku 的时候没有问题，这个 queue 不会动不了，现在我们移到了 IBM cloud, 经常出现这种 queue 动不了的情况，
如果出现这种情况的时候，我们可以手动把 limit my_queue: 调到 2 或者更高，然后才可以通过。&lt;/p&gt;

&lt;p&gt;主要是在本地完全不能重现这一情况，我都不知道哪里出错了。
目前有一条线索也不知道对不对，就是 IBM cloud 使用 auto scaling, 就是会自动重启 sidekiq, 不知道这是不是一条正确的线索呢？
还有现在该如何 debug, 疯狂在所以可能的地方打上 log ? 
 对了 IBM CLOUD 我们开发人员没有权限，所以我们看不了 terminal log, 也看不了储存在服务器上的 log 文件，这样的化，对我们好使的看 log 的方法是把 log 全部放到 active_admin 上吗？&lt;/p&gt;

&lt;p&gt;先感谢看完我问题的大家们。&lt;/p&gt;</description>
      <author>leijun</author>
      <pubDate>Wed, 03 Jun 2020 23:36:03 +0800</pubDate>
      <link>https://ruby-china.org/topics/39936</link>
      <guid>https://ruby-china.org/topics/39936</guid>
    </item>
    <item>
      <title>Sidekiq 如何 load balance queue 和 worker</title>
      <description>&lt;p&gt;大家好，我还是新手，来询问一个关于 sidekiq 和 redis 相关的问题
我现在遇到一个难题，现在的项目做公司分析
平均一个公司分析大概耗时 40 秒，我们把它放在 sidekiq 里 后台执行。
每一个客户可以有很多公司分析.
问题来了，&lt;/p&gt;

&lt;p&gt;第一种情况 : 
    如果客户 A 开启 1000 个公司分析.，另外客户 B 在 1 分钟后开启一个公司分析.，那么我们不想要客户 B 等客户 A 分析完 1000 个公司，然后再分析客户 B 的单个公司分析。
我的提议的使用两个不同的 queue &lt;/p&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;queues&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="pi"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;normal_client&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;20&lt;/span&gt;&lt;span class="pi"&gt;]&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="pi"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;urgent_client&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;40&lt;/span&gt;&lt;span class="pi"&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;这样客户 B 就能先插队&lt;/p&gt;

&lt;p&gt;第二种情况 : 
  如果客户 A 开启 1000 个公司分析，另外客户 B 在 1 分钟后也开启 100 公司分析，这样我们不希望客户 B 的 100 个公司分析要等到客户 A 的 1000 个公司分析 之后，我希望找一个好的解决方案，比如客户 A 和客户 B 交互分析，客户 A 分析一下，然后客户 B 分析一下，这样大概 客户 A 分析完前 100 个客户的时候，客户 B 的 100 也要分析完毕。
这种情况下该如何设计 queue,  或者如何设计如何把 job 放进 worker 里？或者前面再来一层数据结构？&lt;/p&gt;

&lt;p&gt;第三张情况:
我希望每个客户都能有大概时间等待现实，现在不止两个客户，我们假设有很多客户，每个客户有不同数量的公司分析，如果 客户 A 开始分析 , 然后 客户 B  C  D etc.. 开始 插队。那势必导致客户 A 不断延长他的等待时间，这将造成我们刚开始给客户 A 的等待时间不断延长，这将到底客户 A 的不信任感，客户 A 会想，我可是你们的大金主，什么阿猫阿狗都能插我的队！
那这种情况下该有什么好的解决方案？&lt;/p&gt;

&lt;p&gt;这个帖子 我想和大家探讨学习。
先提前感谢大家&lt;/p&gt;</description>
      <author>leijun</author>
      <pubDate>Fri, 22 Mar 2019 17:26:04 +0800</pubDate>
      <link>https://ruby-china.org/topics/38276</link>
      <guid>https://ruby-china.org/topics/38276</guid>
    </item>
    <item>
      <title>新手贴 ，程序员换语言了，努力学习 ruby on rails</title>
      <description>&lt;p&gt;还有三个月就入职了，我现在还要留在原职位 3 个月继续原来职位 java javascript .
我想问问大家该如何利用这 3 个月提升自己 ROR 水平，该怎么学习呢？
我跟着 www.railstutorial.org 做了好多次了，感觉还不够，准备再刷几次.
请问大家还有什么特别有效的方法呢？&lt;/p&gt;

&lt;p&gt;谢谢大家&lt;/p&gt;</description>
      <author>leijun</author>
      <pubDate>Fri, 03 Aug 2018 02:53:14 +0800</pubDate>
      <link>https://ruby-china.org/topics/37271</link>
      <guid>https://ruby-china.org/topics/37271</guid>
    </item>
  </channel>
</rss>
