【问题标题】:Can't stop WEBrick 1.3.1 with ctrl-c on Ubuntu 11.04无法在 Ubuntu 11.04 上使用 ctrl-c 停止 WEBrick 1.3.1
【发布时间】:2011-08-18 23:50:00
【问题描述】:

我正在使用 RVM、Ruby 1.9.2 和 Rails 3.0.7

从另一个终端标准终止进程也不起作用,但是 kill -9 当然可以。

我发现了一个类似的问题,CTRL+C to Webbrick server ignored,但不清楚该问题是否描述了相同的潜在问题。此外,该决议似乎并不适用,因为我没有在我的 Gemfile 中使用 :git。

更新 1:(现在已经旧了......请参阅下面的更新 2,了解真正的独家新闻)

我设法将问题缩小到一个宝石。如果您使用以下测试脚本,您也可以看到问题(假设您使用的是 Ubuntu 11.04...10.04 中没有问题)

rm -rf tmpkilltest

rvm 1.9.2
rvm --force gemset delete tmpkilltest
rvm gemset create tmpkilltest
rvm 1.9.2@tmpkilltest

gem install rails -v=3.0.7 --no-rdoc --no-ri
gem install sqlite3 -v=1.3.3 --no-rdoc --no-ri

rails new tmpkilltest

cd tmpkilltest

echo "gem 'barista', '1.0'" >> Gemfile

bundle

rails s

这个问题是由 Rails 与 gem 的交互引起的,这让我现在相信这个问题实际上与 CTRL+C to Webbrick server ignored 相关,尽管上面的测试用例表明这个问题是显然不是使用 :git 作为 gem 造成的。

更新 2:

update 1 中,我提到我将其范围缩小到一个 gem。当我通过那颗宝石时,我最终找到了真正的罪魁祸首。 gem 进行了一次系统调用。我对测试脚本进行了非常小的修改,不再加载 barista gem,而是在 application.rb 的末尾附加了一个系统调用。使用该系统调用, ctrl-c 不起作用。删除系统调用,它确实可以工作。

rm -rf tmpkilltest

rvm 1.9.2
rvm --force gemset delete tmpkilltest
rvm gemset create tmpkilltest
rvm 1.9.2@tmpkilltest

gem install rails -v=3.0.7 --no-rdoc --no-ri
gem install sqlite3 -v=1.3.3 --no-rdoc --no-ri

rails new tmpkilltest

cd tmpkilltest

bundle

echo "\`date\`" >> config/application.rb

rails s

这可以解释这个问题与CTRL+C to Webbrick server ignored 之间的相似之处。我的预感是他们提到的 gem 也会进行系统调用。

【问题讨论】:

  • 我对 ruby​​ 1.9.2 和 ubuntu 11.04 确实有同样的问题,这真的很烦人。请让我了解可能的解决方案:)
  • 您能接受答案吗?它不一定是我的,但那会很好:-P
  • 这是个好问题,但我不知道答案。如果没有实际的解决方案,我通常会接受一种解决方法作为答案。我想 SO 的部分用处是让通过 Google 解决问题变得更容易,所以对于大多数实际上不在 Webrick 上工作的人来说,解决方法可能就很好了。除此之外的任何东西都可能属于 Webrick 错误跟踪器(或任何有问题的组件)。

标签: ruby-on-rails ruby-on-rails-3 ubuntu ubuntu-11.04


【解决方案1】:

我宁愿发表评论也不愿为此添加答案,但没有足够的代表。

我有同样的问题,发现在输入 ctrl-c 然后暂停(使用 ctrl- z,如上所述)可以解决问题。

所以配方是:

  1. ctrl-c(什么都不做)
  2. ctrl-z(暂停WEBrick,返回shell)
  3. fg(恢复 WEBrick,立即跟进 SIGINT)

    lampadmin@lampadmin-DX4840:/var/www/rails/agences$ r s
    => Booting WEBrick
    => Rails 3.0.5 application starting in development on http://0.0.0.0:3000
    => Call with -d to detach
    => Ctrl-C to shutdown server
    [2011-05-14 14:25:36] INFO  WEBrick 1.3.1
    [2011-05-14 14:25:36] INFO  ruby 1.9.2 (2011-02-18) [x86_64-linux]
    [2011-05-14 14:25:36] INFO  WEBrick::HTTPServer#start: pid=2585 port=3000
    

    ^C^Z

    [1]+  Stopped                 rails s
    lampadmin@lampadmin-DX4840:/var/www/rails/agences$ fg
    rails s
    [2011-05-14 14:25:45] INFO  going to shutdown ...
    [2011-05-14 14:25:45] INFO  WEBrick::HTTPServer#start done.
    Exiting
    

【讨论】:

  • 不错的发现。我宁愿这样做也不愿诉诸kill -9
【解决方案2】:

我遇到了类似的问题,一直在使用 Ctrl+Z 暂停作业,然后使用 kill -9 %1 终止第一个暂停的作业。迂回的方式杀死它,但它的工作原理。

有关更多信息,请参阅超级用户上的此问题:https://superuser.com/questions/243460/what-to-do-when-ctrl-c-cant-kill-a-process

【讨论】:

    【解决方案3】:

    我相信^C 无法杀死 WEBrick 服务器,因为服务器会创建一个新会话:

    webrick/server.rb:

      class Daemon
        def Daemon.start
          exit!(0) if fork
          Process::setsid
          exit!(0) if fork
          Dir::chdir("/")
          File::umask(0)
          STDIN.reopen("/dev/null")
          STDOUT.reopen("/dev/null", "w")
          STDERR.reopen("/dev/null", "w")
          yield if block_given?
        end
      end
    

    rack/server.rb 中存在非常相似的代码,因此如果您通过机架启动 WEBrick,您可能希望省略 -D--daemonize 命令行选项。)

    来自setsid(2) 联机帮助页:

       setsid() creates a new session if the calling process is not
       a process group leader.  The calling process is the leader of
       the new session, the process group leader of the new process
       group, and has no controlling tty.
    

    has no control tty表示终端产生的信号(^ZSIGTSTP^\SIGKILLSIGTTINSIGTTOU等)不能即使该进程已在该终端上启动,也可以到达该进程。链接已被切断。

    【讨论】:

    • 我能够在单独的终端中杀死它,但只能使用 -9。在我看来,这意味着当我按下 ctrl-c 时,SIGINT 很可能被传递给进程,但进程忽略了它(就像它忽略了另一个终端中的显式终止,直到我用 - 9)
    • 我不确定我明白你在说什么。我也遇到了同样的问题,ctrl + c 曾经在 10.04 中运行良好,现在我发现它在 11.04 中间歇性运行。
    • 如果您查看 webrick.rb,它会说:“要将 WEBrick 服务器作为守护程序启动,只需运行 WEBrick::Daemon.start”。我 grepped 了 webrick 代码,默认情况下我没有看到它启动守护进程。不错的尝试,但这不适用于通常的情况。
    【解决方案4】:

    好的,问题已为我解决。我最近作为 Ubuntu 标准更新的一部分应用的内核更新解决了这个问题。

    另外,这里对这个问题进行了很好的讨论,它解释了根本原因是 2.6.38 中引入的内核回归 (http://redmine.ruby-lang.org/issues/4777)

    该回归已被修补,并且看起来该修补程序最近已进入 Ubuntu 的更新,因此如果您受到此问题的影响,您应该应用最新的更新。

    【讨论】:

      【解决方案5】:

      这也发生在我的 Mac OS X 上。

      令人惊讶的是,RackWEBrick 都没有设置自定义信号处理程序。我把它放在我的机架应用程序的 call 方法中,它告诉我 SIGINT 的 DEFAULT 处理程序是当前处理程序(返回字符串 "DEFAULT"):

      p Signal.trap('INT', 'DEFAULT')
      

      我怀疑 ruby​​ 的 select 中发生了一些事情,导致信号被捕获。

      以下是停止服务器的两种方法:

      1) 按 ctrl-z 暂停。然后kill -ABRT pid_or_job_id。我不知道该过程退出的“干净程度”如何。这很烦人,但您不必添加任何代码。

      2a) 如果您使用 Rack,请在致电 Rack::Handler::WEBrick.run 之前添加此内容:

      Signal.trap('INT') {
        Rack::Handler::WEBrick.shutdown
      }
      

      2b) 如果您使用的是原版WEBrick

      Signal.trap('INT') { server.shutdown }
      

      其中server 是您的WEBrick 服务器对象。

      如果您要经常使用SIGINT,这些都很好。您可能还想为TERMHUP 添加处理程序。

      【讨论】:

        【解决方案6】:

        使用此行创建带有 ccsm 的快捷方式(compiz conig 设置管理器或类似这样的 smth)-> 命令:

        kill -9 `pgrep -fl 'script/rails s' | awk '{print $1}'`
        

        设置为 (ctrl+shift+`) 或任何你喜欢的东西

        【讨论】:

          【解决方案7】:

          我在更新我的 Ubuntu 时遇到了同样的问题。使用 Ctrl+C 无法正常退出 webrick,必须使用 kill -9...

          【讨论】:

            【解决方案8】:

            我自己也遇到了这个问题。我正在使用 rvm rails 3.0.9 和 ubuntu 11.04 32bit 运行统一。我发现终结者会将 Ctrl+c 传递给 rails。

            【讨论】:

              【解决方案9】:

              似乎是 Unity 和终端的问题,由于某种原因,^c 未正确处理。尝试使用terminator(更好的终端)做同样的事情。或者只使用 gnome。

              至少我是这样解决问题的。我建议我们将其移至 askubuntu.com。

              在 U10.04 中,我在运行 webrick、mongrel、console、sqlite 时遇到了这个问题,不管我实际运行的是什么。

              【讨论】:

              • 我刚刚使用“ubuntu classic no effects”(没有 Unity 的 gnome)登录并在常规终端和终结器中运行“Update 2”中列出的测试脚本。它继续表现出同样的不良行为。请注意,正常的 kill(没有 -9)也不起作用,因此并不是因为 gui 组件之间的一些不良交互而导致信号没有通过。此外,如果没有进行系统调用,ctrl-c 也可以正常工作。 (见更新 2)
              • 除非你需要 webrick,否则为什么不直接安装 mongrel gem install mongrel 或将其放入 bundler 依赖项中,再也不用担心它了。
              • 这实际上是个好主意,但我刚刚检查过,使用 mongrel 时问题并没有消失。
              • @Gordon 你试过其他终端程序吗?默认的有问题。
              • 终结者对我来说也有同样的问题。鉴于通过 kill 传递 SIGINT 也不起作用,我非常怀疑替代终端是否会为任何人解决问题。
              【解决方案10】:

              我的最后一个答案被删除了,不知道为什么,但我再试一次,因为我真的认为这与问题非常相关。

              在我的 Gemfile 中,我只有一个使用参数 :git 的 gem。

              gem 'rails_admin', :git => 'git://github.com/sferik/rails_admin.git'
              

              大家都有同样的问题,ctrl+C被忽略了;但是如果我删除这个 gem 依赖项,(并且我删除了 de 相关的初始化程序)问题就消失了,我可以像以前一样使用 ctrl+c。

              我认为这是一个与 rails_admin gem 相关的错误,但正如我在另一个问题中所读到的: CTRL+C to Webbrick server ignored 它更有可能与使用 :git 参数的任何 gem 相关...

              希望对您有所帮助。

              【讨论】:

                【解决方案11】:

                找到某种解决方案。在终端中运行:

                stty -echoctl
                

                然后 Ctrl-C 将起作用。 http://linux.m2osw.com/remove-ctrl-C-from-being-printed-in-console

                只工作了一次。 附近发布了更好的解决方案。

                【讨论】:

                  【解决方案12】:

                  有趣的经历(以及接下来几周的好解决方法):

                  如果你在 Ubuntu 下使用 Guake 进行快速终端访问,你可以启动

                  rails s
                  

                  那里。 Ctrl + C 可重复地为我工作并停止服务器。

                  希望我能帮上忙! :)

                  编辑: 显然这不是每个人都可以重现的,这是我的设置:Ubuntu 11.04, 32-bit, Guake 0.4.2-4ubuntu1

                  【讨论】:

                  • 谢谢你的回答,多里安。 Guake 似乎对我的设置没有影响(我很肯定这不是终端仿真器问题,因为您无法从其他地方“杀死”该进程,除非使用 -9)。也就是说,我和 Guake 玩得很开心……很酷的术语!
                  • 嗨,Gordon,真可惜,我很好奇我们的系统之间可能有什么区别?
                  【解决方案13】:

                  如果 ctr+c 不起作用, 然后在执行上述方法之前,只需查看您的终端设置。有时我们可能会为了方便而更改终端的快捷键。我们为终端的复制内容分配了ctr+c。在这种情况下 ctr+c 将无法停止服务器,而是用作复制目的。

                  如果设置未更改,请尝试使用其他端口,例如 4000。

                  【讨论】:

                    猜你喜欢
                    • 1970-01-01
                    • 2012-01-12
                    • 2022-01-16
                    • 2020-06-29
                    • 2011-08-29
                    • 1970-01-01
                    • 1970-01-01
                    • 2012-04-21
                    • 1970-01-01
                    相关资源
                    最近更新 更多