为什么我在 Heroku 上使用 hypnotoad 会崩溃?
Why is my use of hypnotoad crashing on Heroku?
我正在尝试让 Mojolicious::Lite app running on Heroku with Perloku. There's something that doesn't happen when hypnotoad 进入其运行循环导致其崩溃的 hypnotoad。我想我遗漏了一些简单的东西,但 Heroku 文档没有帮助,我也无法从中提取好的错误消息。
我从一个非常简单的应用程序开始,所以显示一些环境变量:
#!/usr/bin/env perl
# today
use Mojolicious::Lite;
get '/' => sub {
my $c = shift;
my $content = "Perl: $^X Pid: $\n\n";
foreach my $key ( keys %ENV ) {
next unless $key =~ /Mojo|toad/i;
$content .= "$key $ENV{$key}\n";
}
$c->stash( content => $content );
$c->render('index');
};
app->start;
__DATA__
@@ index.html.ep
% layout 'default';
% title 'Welcome';
<p>Welcome to the Mojolicious real-time web framework!</p>
<pre>
<%= $content %>
</pre>
@@ layouts/default.html.ep
<!DOCTYPE html>
<html>
<head><title><%= title %></title></head>
<body><%= content %></body>
</html>
当我在本地运行时,没有问题。我从环境变量中看到我的程序是在hypnotoad下运行的:
Welcome to the Mojolicious real-time web framework!
Perl: /Users/brian/Dropbox/bin/perls/perl5.20.0 Pid: 40006
HYPNOTOAD_PID 39981
MOJO_HELP
HYPNOTOAD_TEST
HYPNOTOAD_EXE /Users/brian/bin/perls/hypnotoad5.20.0
MOJO_REUSE 0.0.0.0:8080:6
HYPNOTOAD_REV 3
HYPNOTOAD_APP /Users/brian/Desktop/toady.d/toady
MOJO_MODE production
MOJO_HOME
HYPNOTOAD_STOP
HYPNOTOAD_FOREGROUND
现在,我用 Mojolicious::Command::deploy::heroku 部署它:
% toady deploy heroku --create
这是在 https://frozen-brushlands-4002.herokuapp.com 运行,使用默认的 Perloku 文件:
#!/bin/sh
./toady daemon --listen http://*:$PORT --mode production
尽管我看到一些参考资料说这是我应该得到的,但这并没有运行 hypnotoad。不过,该应用程序有效:
Welcome to the Mojolicious real-time web framework!
Perl: /app/vendor/perl/bin/perl Pid: 3
MOJO_REUSE 0.0.0.0:12270:4
MOJO_HOME
MOJO_HELP
MOJO_MODE production
MOJO_EXE ./toady
我想我可以更改 Perloku 文件来启动 hypnotoad:
#!/bin/sh
/app/vendor/perl/bin/perl /app/vendor/perl-deps/bin/hypnotoad toady
hypnotoad 启动并几乎立即关闭,没有其他日志消息:
% heroku logs --app ...
2015-01-04T09:23:36.516864+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-04T09:23:38.321628+00:00 heroku[web.1]: State changed from starting to crashed
我可以更改调用以使用 -t
来测试应用程序以查看是否:
#!/bin/sh
/app/vendor/perl/bin/perl /app/vendor/perl-deps/bin/hypnotoad -t toady
有效,我收到 "Everything looks good!" 消息,所以 hypnotoad 正在运行:
2015-01-04T09:36:36.955680+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-04T09:36:38.340717+00:00 app[web.1]: Everything looks good!
2015-01-04T09:36:39.085887+00:00 heroku[web.1]: State changed from starting to crashed
我打开了 Mojo 调试日志记录,但除了我自己的语句外,我没有看到其他输出。
#!/usr/bin/env perl
use Mojolicious::Lite;
$|++;
my $log = app->log;
$log->level( 'debug' );
$log->debug( "INC: @INC" );
get '/' => sub {
...;
};
$log->debug( "Right before start" );
my $app = app->start;
$log->debug( "Right after start" );
$app; # must return application object
我尝试了其他方法,例如让它加载一个我知道不存在的模块,我在日志中得到了预期的 "Could not find" 错误。
从 heroku (heroku run bash
) 中的 shell 运行并没有启发性。 mojo version
的输出与我本地机器上的输出相同:
$ perl vendor/perl-deps/bin/mojo version
CORE
Perl (v5.16.2, linux)
Mojolicious (5.71, Tiger Face)
OPTIONAL
EV 4.0+ (n/a)
IO::Socket::Socks 0.64+ (n/a)
IO::Socket::SSL 1.84+ (n/a)
Net::DNS::Native 0.15+ (n/a)
You might want to update your Mojolicious to 5.72.
我想我遗漏了一些非常简单的东西,但与此同时,这些都不是为了便于调试而设计的。
奥列格靠得更近了一点,但还是有问题。我以前试过前台选项,也遇到了同样的问题,但没有提到。
如果我在前台启动 hypnotoad,它会尝试绑定到一个地址。绑定不了80(或443)端口就死机了,127.0.0.1: 几乎可以监听,但是貌似没有完全监听:
2015-01-13T11:47:54+00:00 heroku[slug-compiler]: Slug compilation started
2015-01-13T11:48:32+00:00 heroku[slug-compiler]: Slug compilation finished
2015-01-13T11:48:32.735095+00:
00 heroku[api]: Deploy dcab778 by ...
2015-01-13T11:48:32.735095+00:00 heroku[api]: Release v31 created by ...
2015-01-13T11:48:32.969489+00:00 heroku[web.1]: State changed from crashed to starting
2015-01-13T11:48:34.909134+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-13T11:48:36.045985+00:00 app[web.1]: Can't create listen socket: Permission denied at /app/vendor/perl-deps/lib/perl5/Mojo/IOLoop.pm line 120.
2015-01-13T11:48:36.920004+00:00 heroku[web.1]: Process exited with status 13
2015-01-13T11:48:36.932014+00:00 heroku[web.1]: State changed from starting to crashed
这是一个非特权端口:
2015-01-13T11:39:10+00:00 heroku[slug-compiler]: Slug compilation started
2015-01-13T11:39:44+00:00 heroku[slug-compiler]: Slug compilation finished
2015-01-13T11:39:44.519679+00:00 heroku[api]: Deploy bbd1f68 by ...
2015-01-13T11:39:44.519679+00:00 heroku[api]: Release v29 created by ...
2015-01-13T11:39:44.811111+00:00 heroku[web.1]: State changed from crashed to starting
2015-01-13T11:39:47.382298+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-13T11:39:48.454706+00:00 app[web.1]: [Tue Jan 13 11:39:48 2015] [info] Listening at "http://*:8000".
2015-01-13T11:39:48.454733+00:00 app[web.1]: Server available at http://127.0.0.1:8000.
2015-01-13T11:39:48.454803+00:00 app[web.1]: [Tue Jan 13 11:39:48 2015] [info] Manager 3 started.
2015-01-13T11:39:48.480084+00:00 app[web.1]: [Tue Jan 13 11:39:48 2015] [info] Creating process id file "/app/hypnotoad.pid".
2015-01-13T11:40:47.703110+00:00 heroku[web.1]: Stopping process with SIGKILL
2015-01-13T11:40:47.702867+00:00 heroku[web.1]: Error R10 (Boot timeout) -> Web process failed to bind to $PORT within 60 seconds of launch
2015-01-13T11:40:48.524470+00:00 heroku[web.1]: Process exited with status 137
2015-01-13T11:40:48.534002+00:00 heroku[web.1]: State changed from starting to crashed
这真的只是一个大胆的猜测,但也许 heroku 基础设施不希望运行程序终止?如果是这样,您可以尝试使用 --foreground
或 -f
.
启动 hypnotoad
此外,您可以尝试从应用程序内部进行一些日志记录,看看它是否曾经运行过它。
经过一些测试,我找到了在 heroku
上 运行 hypnotoad 的方法
1. Perloku 内容应如下所示
#!/bin/sh
perl /app/vendor/perl-deps/bin/hypnotoad -f mojocrashtest
描述
首先我们需要显式调用perl。因为
heroku run bash
head /app/vendor/perl-deps/bin/hypnotoad
显示
#!/tmp/perl/perls/perl-5.18.1/bin/perl
eval 'exec /tmp/perl/perls/perl-5.18.1/bin/perl -S [=12=] ${1+"$@"}'
if 0; # not running under some shell
其中 /tmp/perl/perls/perl-5.18.1/bin/perl
不存在。所以,/app/vendor/perl-deps/bin/hypnotoad
不会启动,但是perl /app/vendor/perl-deps/bin/hypnotoad
会好的。
然后正如@moritz 猜测的那样,我们需要 hypnotoad 的密钥 -f
。否则 heroku 会认为您的应用程序意外完成。
2。你应该在端口 $ENV{PORT}
上启动 hypnotoad
对于 Mojolicious::Lite
你只需要在你的应用程序的顶部写这样的东西:
plugin Config => {default => {hypnotoad => {listen => ["http://*:$ENV{PORT}"]}}};
对于完整的应用程序,您可以在 startup
处理程序中完成。
3。 heroku 打开
这是 Mojolicious::Lite application 的完整代码
#!/usr/bin/env perl
# today
use Mojolicious::Lite;
plugin Config => {default => {hypnotoad => {listen => ["http://*:$ENV{PORT}"]}}};
get '/' => sub {
my $c = shift;
my $content = "Perl: $^X Pid: $$\n\n";
foreach my $key ( keys %ENV ) {
next unless $key =~ /Mojo|toad/i;
$content .= "$key $ENV{$key}\n";
}
$c->stash( content => $content );
$c->render('index');
};
app->start;
__DATA__
@@ index.html.ep
% layout 'default';
% title 'Welcome';
<p>Welcome to the Mojolicious real-time web framework!</p>
<pre>
<%= $content %>
</pre>
@@ layouts/default.html.ep
<!DOCTYPE html>
<html>
<head><title><%= title %></title></head>
<body><%= content %></body>
</html>
heroku 日志
2015-01-13T12:08:04.843204+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-13T12:08:06.019070+00:00 app[web.1]: Server available at http://127.0.0.1:13533.
2015-01-13T12:08:06.018899+00:00 app[web.1]: [Tue Jan 13 12:08:06 2015] [info] Listening at "http://*:13533".
2015-01-13T12:08:06.019035+00:00 app[web.1]: [Tue Jan 13 12:08:06 2015] [info] Manager 3 started.
2015-01-13T12:08:06.055437+00:00 app[web.1]: [Tue Jan 13 12:08:06 2015] [info] Creating process id file "/app/hypnotoad.pid".
2015-01-13T12:08:06.412283+00:00 heroku[web.1]: State changed from starting to up
2015-01-13T12:08:08.040072+00:00 heroku[router]: at=info method=GET path="/" host=floating-temple-3676.herokuapp.com request_id=e9f9bb4d-f71f-4b4c-a129-70faf044c38b fwd=194" dyno=web.1 connect=3ms service=34ms status=200 bytes=586
2015-01-13T12:08:08.029819+00:00 app[web.1]: Use of uninitialized value in concatenation (.) or string at /app/mojocrashtest line 13, <DATA> line 39.
2015-01-13T12:08:08.029836+00:00 app[web.1]: Use of uninitialized value in concatenation (.) or string at /app/mojocrashtest line 13, <DATA> line 39.
2015-01-13T12:08:08.029839+00:00 app[web.1]: Use of uninitialized value in concatenation (.) or string at /app/mojocrashtest line 13, <DATA> line 39.
2015-01-13T12:08:08.029842+00:00 app[web.1]: Use of uninitialized value in concatenation (.) or string at /app/mojocrashtest line 13, <DATA> line 39.
URL 对于我的应用:http://floating-temple-3676.herokuapp.com/
顺便说一句,我没有使用 mojo deploy
,只是 git
,但假设中缺少一些部分。
首先,创建一个新的 heroku 应用程序并记住应用程序的名称:
$ heroku create
Creating vast-spire-6174... done, stack is cedar-14
https://vast-spire-6174.herokuapp.com/ | https://git.heroku.com/vast-spire-6174.git
接下来,添加 Perloku 构建包:
$ heroku config:add BUILDPACK_URL=https://github.com/judofyr/perloku.git
在 Heroku 上创建 git 存储库和设置:
$ mkdir testapp
$ cd testapp
$ git init
$ heroku git:remote -a vast-spire-6174
要使一切正常,您需要一个 Perloku 文件在前台启动 hypnotoad
。您必须明确指定 perl
,因为 hypnotoad
中的 shebang 行指的是 perl
构建时的临时位置以及不再存在的位置。将 myapp.pl 更改为您为应用程序命名的任何名称。
#!/bin/sh
/app/vendor/perl/bin/perl /app/vendor/perl-deps/bin/hypnotoad -f myapp.pl
要安装所有内容,请使用标准 Makefile.PL。将 Mojolicious 指定为先决条件之一:
use strict;
use warnings;
use ExtUtils::MakeMaker;
WriteMakefile(
VERSION => '0.01',
PREREQ_PM => {'Mojolicious' => '5.72'},
test => {TESTS => 't/*.t'}
);
最后,您可以使用 mojo
创建的应用程序本身(调用是 myapp.ppl)
$ mojo generate lite_app
这是生成的源代码:
#!/usr/bin/env perl
use Mojolicious::Lite;
# Documentation browser under "/perldoc"
plugin 'PODRenderer';
get '/' => sub {
my $c = shift;
$c->render('index');
};
app->start;
__DATA__
@@ index.html.ep
% layout 'default';
% title 'Welcome';
Welcome to the Mojolicious real-time web framework!
@@ layouts/default.html.ep
<!DOCTYPE html>
<html>
<head><title><%= title %></title></head>
<body><%= content %></body>
</html>
您必须修改基本程序,因为 hypnotoad 需要一些配置(默认服务器不需要):
#!/usr/bin/env perl
use Mojolicious::Lite;
# Documentation browser under "/perldoc"
plugin 'PODRenderer';
plugin Config => {
default => {
hypnotoad => {
listen => ["http://*:$ENV{PORT}"]
}
}
};
get '/' => sub {
my $c = shift;
$c->render('index');
};
app->start;
__DATA__
@@ index.html.ep
% layout 'default';
% title 'Welcome';
Welcome to the Mojolicious real-time web framework!
@@ layouts/default.html.ep
<!DOCTYPE html>
<html>
<head><title><%= title %></title></head>
<body><%= content %></body>
</html>
获得所有文件后,提交它们,然后推送到 heroku 分支。
$ git add .
$ git commit -am "make it better"
$ git push heroku master
当你推动时,一个钩子将启动一切。
Counting objects: 7, done.
Delta compression using up to 4 threads.
Compressing objects: 100% (7/7), done.
Writing objects: 100% (7/7), 1.14 KiB | 0 bytes/s, done.
Total 7 (delta 0), reused 0 (delta 0)
remote: Compressing source files... done.
remote: Building source:
remote:
remote: -----> Fetching custom git buildpack... done
remote: -----> Perloku app detected
remote: -----> Vendoring Perl
remote: Using Perl 5.18.1
remote: -----> Installing dependencies
remote: --> Working on /tmp/build_a73f24f0619fa2ab299586098c5e8daf
remote: Configuring /tmp/build_a73f24f0619fa2ab299586098c5e8daf ... OK
remote: ==> Found dependencies: Mojolicious
remote: --> Working on Mojolicious
remote: Fetching http://www.cpan.org/authors/id/S/SR/SRI/Mojolicious-5.72.tar.gz ... OK
remote: Configuring Mojolicious-5.72 ... OK
remote: ==> Found dependencies: IO::Socket::IP
remote: --> Working on IO::Socket::IP
remote: Fetching http://www.cpan.org/authors/id/P/PE/PEVANS/IO-Socket-IP-0.36.tar.gz ... OK
remote: Configuring IO-Socket-IP-0.36 ... OK
remote: Building IO-Socket-IP-0.36 ... OK
remote: Successfully installed IO-Socket-IP-0.36
remote: Building Mojolicious-5.72 ... OK
remote: Successfully installed Mojolicious-5.72
remote: <== Installed dependencies for /tmp/build_a73f24f0619fa2ab299586098c5e8daf. Finishing.
remote: 2 distributions installed
remote: Dependencies installed
remote: -----> Discovering process types
remote: Procfile declares types -> (none)
remote: Default types for Perloku -> web
remote:
remote: -----> Compressing... done, 14.1MB
remote: -----> Launching... done, v5
remote: https://vast-spire-6174.herokuapp.com/ deployed to Heroku
remote:
remote: Verifying deploy... done.
To https://git.heroku.com/vast-spire-6174.git
* [new branch] master -> master
您的应用程序的 URL 显示在输出的末尾。
为什么这在我不知道之前对我有用。我让一个 mojo 命令为我部署,所以那里可能有一些东西需要调查。但是,在没有中介的情况下提交和推送会更容易一些。
我正在尝试让 Mojolicious::Lite app running on Heroku with Perloku. There's something that doesn't happen when hypnotoad 进入其运行循环导致其崩溃的 hypnotoad。我想我遗漏了一些简单的东西,但 Heroku 文档没有帮助,我也无法从中提取好的错误消息。
我从一个非常简单的应用程序开始,所以显示一些环境变量:
#!/usr/bin/env perl
# today
use Mojolicious::Lite;
get '/' => sub {
my $c = shift;
my $content = "Perl: $^X Pid: $\n\n";
foreach my $key ( keys %ENV ) {
next unless $key =~ /Mojo|toad/i;
$content .= "$key $ENV{$key}\n";
}
$c->stash( content => $content );
$c->render('index');
};
app->start;
__DATA__
@@ index.html.ep
% layout 'default';
% title 'Welcome';
<p>Welcome to the Mojolicious real-time web framework!</p>
<pre>
<%= $content %>
</pre>
@@ layouts/default.html.ep
<!DOCTYPE html>
<html>
<head><title><%= title %></title></head>
<body><%= content %></body>
</html>
当我在本地运行时,没有问题。我从环境变量中看到我的程序是在hypnotoad下运行的:
Welcome to the Mojolicious real-time web framework!
Perl: /Users/brian/Dropbox/bin/perls/perl5.20.0 Pid: 40006
HYPNOTOAD_PID 39981
MOJO_HELP
HYPNOTOAD_TEST
HYPNOTOAD_EXE /Users/brian/bin/perls/hypnotoad5.20.0
MOJO_REUSE 0.0.0.0:8080:6
HYPNOTOAD_REV 3
HYPNOTOAD_APP /Users/brian/Desktop/toady.d/toady
MOJO_MODE production
MOJO_HOME
HYPNOTOAD_STOP
HYPNOTOAD_FOREGROUND
现在,我用 Mojolicious::Command::deploy::heroku 部署它:
% toady deploy heroku --create
这是在 https://frozen-brushlands-4002.herokuapp.com 运行,使用默认的 Perloku 文件:
#!/bin/sh
./toady daemon --listen http://*:$PORT --mode production
尽管我看到一些参考资料说这是我应该得到的,但这并没有运行 hypnotoad。不过,该应用程序有效:
Welcome to the Mojolicious real-time web framework!
Perl: /app/vendor/perl/bin/perl Pid: 3
MOJO_REUSE 0.0.0.0:12270:4
MOJO_HOME
MOJO_HELP
MOJO_MODE production
MOJO_EXE ./toady
我想我可以更改 Perloku 文件来启动 hypnotoad:
#!/bin/sh
/app/vendor/perl/bin/perl /app/vendor/perl-deps/bin/hypnotoad toady
hypnotoad 启动并几乎立即关闭,没有其他日志消息:
% heroku logs --app ...
2015-01-04T09:23:36.516864+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-04T09:23:38.321628+00:00 heroku[web.1]: State changed from starting to crashed
我可以更改调用以使用 -t
来测试应用程序以查看是否:
#!/bin/sh
/app/vendor/perl/bin/perl /app/vendor/perl-deps/bin/hypnotoad -t toady
有效,我收到 "Everything looks good!" 消息,所以 hypnotoad 正在运行:
2015-01-04T09:36:36.955680+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-04T09:36:38.340717+00:00 app[web.1]: Everything looks good!
2015-01-04T09:36:39.085887+00:00 heroku[web.1]: State changed from starting to crashed
我打开了 Mojo 调试日志记录,但除了我自己的语句外,我没有看到其他输出。
#!/usr/bin/env perl
use Mojolicious::Lite;
$|++;
my $log = app->log;
$log->level( 'debug' );
$log->debug( "INC: @INC" );
get '/' => sub {
...;
};
$log->debug( "Right before start" );
my $app = app->start;
$log->debug( "Right after start" );
$app; # must return application object
我尝试了其他方法,例如让它加载一个我知道不存在的模块,我在日志中得到了预期的 "Could not find" 错误。
从 heroku (heroku run bash
) 中的 shell 运行并没有启发性。 mojo version
的输出与我本地机器上的输出相同:
$ perl vendor/perl-deps/bin/mojo version
CORE
Perl (v5.16.2, linux)
Mojolicious (5.71, Tiger Face)
OPTIONAL
EV 4.0+ (n/a)
IO::Socket::Socks 0.64+ (n/a)
IO::Socket::SSL 1.84+ (n/a)
Net::DNS::Native 0.15+ (n/a)
You might want to update your Mojolicious to 5.72.
我想我遗漏了一些非常简单的东西,但与此同时,这些都不是为了便于调试而设计的。
奥列格靠得更近了一点,但还是有问题。我以前试过前台选项,也遇到了同样的问题,但没有提到。
如果我在前台启动 hypnotoad,它会尝试绑定到一个地址。绑定不了80(或443)端口就死机了,127.0.0.1: 几乎可以监听,但是貌似没有完全监听:
2015-01-13T11:47:54+00:00 heroku[slug-compiler]: Slug compilation started
2015-01-13T11:48:32+00:00 heroku[slug-compiler]: Slug compilation finished
2015-01-13T11:48:32.735095+00:
00 heroku[api]: Deploy dcab778 by ...
2015-01-13T11:48:32.735095+00:00 heroku[api]: Release v31 created by ...
2015-01-13T11:48:32.969489+00:00 heroku[web.1]: State changed from crashed to starting
2015-01-13T11:48:34.909134+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-13T11:48:36.045985+00:00 app[web.1]: Can't create listen socket: Permission denied at /app/vendor/perl-deps/lib/perl5/Mojo/IOLoop.pm line 120.
2015-01-13T11:48:36.920004+00:00 heroku[web.1]: Process exited with status 13
2015-01-13T11:48:36.932014+00:00 heroku[web.1]: State changed from starting to crashed
这是一个非特权端口:
2015-01-13T11:39:10+00:00 heroku[slug-compiler]: Slug compilation started
2015-01-13T11:39:44+00:00 heroku[slug-compiler]: Slug compilation finished
2015-01-13T11:39:44.519679+00:00 heroku[api]: Deploy bbd1f68 by ...
2015-01-13T11:39:44.519679+00:00 heroku[api]: Release v29 created by ...
2015-01-13T11:39:44.811111+00:00 heroku[web.1]: State changed from crashed to starting
2015-01-13T11:39:47.382298+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-13T11:39:48.454706+00:00 app[web.1]: [Tue Jan 13 11:39:48 2015] [info] Listening at "http://*:8000".
2015-01-13T11:39:48.454733+00:00 app[web.1]: Server available at http://127.0.0.1:8000.
2015-01-13T11:39:48.454803+00:00 app[web.1]: [Tue Jan 13 11:39:48 2015] [info] Manager 3 started.
2015-01-13T11:39:48.480084+00:00 app[web.1]: [Tue Jan 13 11:39:48 2015] [info] Creating process id file "/app/hypnotoad.pid".
2015-01-13T11:40:47.703110+00:00 heroku[web.1]: Stopping process with SIGKILL
2015-01-13T11:40:47.702867+00:00 heroku[web.1]: Error R10 (Boot timeout) -> Web process failed to bind to $PORT within 60 seconds of launch
2015-01-13T11:40:48.524470+00:00 heroku[web.1]: Process exited with status 137
2015-01-13T11:40:48.534002+00:00 heroku[web.1]: State changed from starting to crashed
这真的只是一个大胆的猜测,但也许 heroku 基础设施不希望运行程序终止?如果是这样,您可以尝试使用 --foreground
或 -f
.
此外,您可以尝试从应用程序内部进行一些日志记录,看看它是否曾经运行过它。
经过一些测试,我找到了在 heroku
上 运行 hypnotoad 的方法1. Perloku 内容应如下所示
#!/bin/sh
perl /app/vendor/perl-deps/bin/hypnotoad -f mojocrashtest
描述
首先我们需要显式调用perl。因为
heroku run bash
head /app/vendor/perl-deps/bin/hypnotoad
显示
#!/tmp/perl/perls/perl-5.18.1/bin/perl
eval 'exec /tmp/perl/perls/perl-5.18.1/bin/perl -S [=12=] ${1+"$@"}'
if 0; # not running under some shell
其中 /tmp/perl/perls/perl-5.18.1/bin/perl
不存在。所以,/app/vendor/perl-deps/bin/hypnotoad
不会启动,但是perl /app/vendor/perl-deps/bin/hypnotoad
会好的。
然后正如@moritz 猜测的那样,我们需要 hypnotoad 的密钥 -f
。否则 heroku 会认为您的应用程序意外完成。
2。你应该在端口 $ENV{PORT}
上启动 hypnotoad对于 Mojolicious::Lite
你只需要在你的应用程序的顶部写这样的东西:
plugin Config => {default => {hypnotoad => {listen => ["http://*:$ENV{PORT}"]}}};
对于完整的应用程序,您可以在 startup
处理程序中完成。
3。 heroku 打开
这是 Mojolicious::Lite application 的完整代码
#!/usr/bin/env perl
# today
use Mojolicious::Lite;
plugin Config => {default => {hypnotoad => {listen => ["http://*:$ENV{PORT}"]}}};
get '/' => sub {
my $c = shift;
my $content = "Perl: $^X Pid: $$\n\n";
foreach my $key ( keys %ENV ) {
next unless $key =~ /Mojo|toad/i;
$content .= "$key $ENV{$key}\n";
}
$c->stash( content => $content );
$c->render('index');
};
app->start;
__DATA__
@@ index.html.ep
% layout 'default';
% title 'Welcome';
<p>Welcome to the Mojolicious real-time web framework!</p>
<pre>
<%= $content %>
</pre>
@@ layouts/default.html.ep
<!DOCTYPE html>
<html>
<head><title><%= title %></title></head>
<body><%= content %></body>
</html>
heroku 日志
2015-01-13T12:08:04.843204+00:00 heroku[web.1]: Starting process with command `./Perloku`
2015-01-13T12:08:06.019070+00:00 app[web.1]: Server available at http://127.0.0.1:13533.
2015-01-13T12:08:06.018899+00:00 app[web.1]: [Tue Jan 13 12:08:06 2015] [info] Listening at "http://*:13533".
2015-01-13T12:08:06.019035+00:00 app[web.1]: [Tue Jan 13 12:08:06 2015] [info] Manager 3 started.
2015-01-13T12:08:06.055437+00:00 app[web.1]: [Tue Jan 13 12:08:06 2015] [info] Creating process id file "/app/hypnotoad.pid".
2015-01-13T12:08:06.412283+00:00 heroku[web.1]: State changed from starting to up
2015-01-13T12:08:08.040072+00:00 heroku[router]: at=info method=GET path="/" host=floating-temple-3676.herokuapp.com request_id=e9f9bb4d-f71f-4b4c-a129-70faf044c38b fwd=194" dyno=web.1 connect=3ms service=34ms status=200 bytes=586
2015-01-13T12:08:08.029819+00:00 app[web.1]: Use of uninitialized value in concatenation (.) or string at /app/mojocrashtest line 13, <DATA> line 39.
2015-01-13T12:08:08.029836+00:00 app[web.1]: Use of uninitialized value in concatenation (.) or string at /app/mojocrashtest line 13, <DATA> line 39.
2015-01-13T12:08:08.029839+00:00 app[web.1]: Use of uninitialized value in concatenation (.) or string at /app/mojocrashtest line 13, <DATA> line 39.
2015-01-13T12:08:08.029842+00:00 app[web.1]: Use of uninitialized value in concatenation (.) or string at /app/mojocrashtest line 13, <DATA> line 39.
URL 对于我的应用:http://floating-temple-3676.herokuapp.com/
顺便说一句,我没有使用 mojo deploy
,只是 git
首先,创建一个新的 heroku 应用程序并记住应用程序的名称:
$ heroku create
Creating vast-spire-6174... done, stack is cedar-14
https://vast-spire-6174.herokuapp.com/ | https://git.heroku.com/vast-spire-6174.git
接下来,添加 Perloku 构建包:
$ heroku config:add BUILDPACK_URL=https://github.com/judofyr/perloku.git
在 Heroku 上创建 git 存储库和设置:
$ mkdir testapp
$ cd testapp
$ git init
$ heroku git:remote -a vast-spire-6174
要使一切正常,您需要一个 Perloku 文件在前台启动 hypnotoad
。您必须明确指定 perl
,因为 hypnotoad
中的 shebang 行指的是 perl
构建时的临时位置以及不再存在的位置。将 myapp.pl 更改为您为应用程序命名的任何名称。
#!/bin/sh
/app/vendor/perl/bin/perl /app/vendor/perl-deps/bin/hypnotoad -f myapp.pl
要安装所有内容,请使用标准 Makefile.PL。将 Mojolicious 指定为先决条件之一:
use strict;
use warnings;
use ExtUtils::MakeMaker;
WriteMakefile(
VERSION => '0.01',
PREREQ_PM => {'Mojolicious' => '5.72'},
test => {TESTS => 't/*.t'}
);
最后,您可以使用 mojo
创建的应用程序本身(调用是 myapp.ppl)
$ mojo generate lite_app
这是生成的源代码:
#!/usr/bin/env perl
use Mojolicious::Lite;
# Documentation browser under "/perldoc"
plugin 'PODRenderer';
get '/' => sub {
my $c = shift;
$c->render('index');
};
app->start;
__DATA__
@@ index.html.ep
% layout 'default';
% title 'Welcome';
Welcome to the Mojolicious real-time web framework!
@@ layouts/default.html.ep
<!DOCTYPE html>
<html>
<head><title><%= title %></title></head>
<body><%= content %></body>
</html>
您必须修改基本程序,因为 hypnotoad 需要一些配置(默认服务器不需要):
#!/usr/bin/env perl
use Mojolicious::Lite;
# Documentation browser under "/perldoc"
plugin 'PODRenderer';
plugin Config => {
default => {
hypnotoad => {
listen => ["http://*:$ENV{PORT}"]
}
}
};
get '/' => sub {
my $c = shift;
$c->render('index');
};
app->start;
__DATA__
@@ index.html.ep
% layout 'default';
% title 'Welcome';
Welcome to the Mojolicious real-time web framework!
@@ layouts/default.html.ep
<!DOCTYPE html>
<html>
<head><title><%= title %></title></head>
<body><%= content %></body>
</html>
获得所有文件后,提交它们,然后推送到 heroku 分支。
$ git add .
$ git commit -am "make it better"
$ git push heroku master
当你推动时,一个钩子将启动一切。
Counting objects: 7, done.
Delta compression using up to 4 threads.
Compressing objects: 100% (7/7), done.
Writing objects: 100% (7/7), 1.14 KiB | 0 bytes/s, done.
Total 7 (delta 0), reused 0 (delta 0)
remote: Compressing source files... done.
remote: Building source:
remote:
remote: -----> Fetching custom git buildpack... done
remote: -----> Perloku app detected
remote: -----> Vendoring Perl
remote: Using Perl 5.18.1
remote: -----> Installing dependencies
remote: --> Working on /tmp/build_a73f24f0619fa2ab299586098c5e8daf
remote: Configuring /tmp/build_a73f24f0619fa2ab299586098c5e8daf ... OK
remote: ==> Found dependencies: Mojolicious
remote: --> Working on Mojolicious
remote: Fetching http://www.cpan.org/authors/id/S/SR/SRI/Mojolicious-5.72.tar.gz ... OK
remote: Configuring Mojolicious-5.72 ... OK
remote: ==> Found dependencies: IO::Socket::IP
remote: --> Working on IO::Socket::IP
remote: Fetching http://www.cpan.org/authors/id/P/PE/PEVANS/IO-Socket-IP-0.36.tar.gz ... OK
remote: Configuring IO-Socket-IP-0.36 ... OK
remote: Building IO-Socket-IP-0.36 ... OK
remote: Successfully installed IO-Socket-IP-0.36
remote: Building Mojolicious-5.72 ... OK
remote: Successfully installed Mojolicious-5.72
remote: <== Installed dependencies for /tmp/build_a73f24f0619fa2ab299586098c5e8daf. Finishing.
remote: 2 distributions installed
remote: Dependencies installed
remote: -----> Discovering process types
remote: Procfile declares types -> (none)
remote: Default types for Perloku -> web
remote:
remote: -----> Compressing... done, 14.1MB
remote: -----> Launching... done, v5
remote: https://vast-spire-6174.herokuapp.com/ deployed to Heroku
remote:
remote: Verifying deploy... done.
To https://git.heroku.com/vast-spire-6174.git
* [new branch] master -> master
您的应用程序的 URL 显示在输出的末尾。
为什么这在我不知道之前对我有用。我让一个 mojo 命令为我部署,所以那里可能有一些东西需要调查。但是,在没有中介的情况下提交和推送会更容易一些。