forked from lix-project/hydra
Merge pull request #1065 from DeterminateSystems/project-jobset-links
project:jobset:job: make clickable links in titles
This commit is contained in:
commit
e5be4a9022
|
@ -3,6 +3,7 @@ package Hydra::View::TT;
|
||||||
use strict;
|
use strict;
|
||||||
use warnings;
|
use warnings;
|
||||||
use base 'Catalyst::View::TT';
|
use base 'Catalyst::View::TT';
|
||||||
|
use Template::Plugin::HTML;
|
||||||
use Hydra::Helper::Nix;
|
use Hydra::Helper::Nix;
|
||||||
use Time::Seconds;
|
use Time::Seconds;
|
||||||
|
|
||||||
|
@ -11,7 +12,20 @@ __PACKAGE__->config(
|
||||||
ENCODING => 'utf-8',
|
ENCODING => 'utf-8',
|
||||||
PRE_CHOMP => 1,
|
PRE_CHOMP => 1,
|
||||||
POST_CHOMP => 1,
|
POST_CHOMP => 1,
|
||||||
expose_methods => [qw/buildLogExists buildStepLogExists jobExists relativeDuration stripSSHUser/]);
|
expose_methods => [qw/
|
||||||
|
buildLogExists
|
||||||
|
buildStepLogExists
|
||||||
|
jobExists
|
||||||
|
linkToJob
|
||||||
|
linkToJobset
|
||||||
|
linkToProject
|
||||||
|
makeNameLinksForJob
|
||||||
|
makeNameLinksForJobset
|
||||||
|
makeNameTextForJob
|
||||||
|
makeNameTextForJobset
|
||||||
|
relativeDuration
|
||||||
|
stripSSHUser
|
||||||
|
/]);
|
||||||
|
|
||||||
sub buildLogExists {
|
sub buildLogExists {
|
||||||
my ($self, $c, $build) = @_;
|
my ($self, $c, $build) = @_;
|
||||||
|
@ -64,4 +78,250 @@ sub jobExists {
|
||||||
return defined $jobset->builds->search({ job => $jobName, iscurrent => 1 })->single;
|
return defined $jobset->builds->search({ job => $jobName, iscurrent => 1 })->single;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
=head2 linkToProject
|
||||||
|
|
||||||
|
Given a L<Hydra::Schema::Result::Project>, return a link to the project.
|
||||||
|
|
||||||
|
Arguments:
|
||||||
|
|
||||||
|
=over 3
|
||||||
|
|
||||||
|
=item C<$self>
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$c>
|
||||||
|
Catalyst Context
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$project>
|
||||||
|
|
||||||
|
The L<Hydra::Schema::Result::Project> to link to.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
|
=cut
|
||||||
|
sub linkToProject {
|
||||||
|
my ($self, $c, $project) = @_;
|
||||||
|
|
||||||
|
my $html = Template::Plugin::HTML->new();
|
||||||
|
|
||||||
|
my $projectName = $project->name;
|
||||||
|
my $escapedProjectName = $html->escape($projectName);
|
||||||
|
|
||||||
|
return '<a href="' . $c->uri_for('/project', $projectName) . '">' . $escapedProjectName . '</a>';
|
||||||
|
}
|
||||||
|
|
||||||
|
=head2 linkToJobset
|
||||||
|
|
||||||
|
Given a L<Hydra::Schema::Result::Jobset>, return a link to the jobset
|
||||||
|
and its project in project:jobset notation.
|
||||||
|
|
||||||
|
Arguments:
|
||||||
|
|
||||||
|
=over 3
|
||||||
|
|
||||||
|
=item C<$self>
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$c>
|
||||||
|
Catalyst Context
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$jobset>
|
||||||
|
|
||||||
|
The L<Hydra::Schema::Result::Jobset> to link to.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
|
=cut
|
||||||
|
sub linkToJobset {
|
||||||
|
my ($self, $c, $jobset) = @_;
|
||||||
|
|
||||||
|
my $html = Template::Plugin::HTML->new();
|
||||||
|
|
||||||
|
my $jobsetName = $jobset->name;
|
||||||
|
my $escapedJobsetName = $html->escape($jobsetName);
|
||||||
|
|
||||||
|
return linkToProject($self, $c, $jobset->project) .
|
||||||
|
':<a href="' . $c->uri_for('/jobset', $jobset->project->name, $jobsetName) . '">' . $escapedJobsetName . '</a>';
|
||||||
|
}
|
||||||
|
|
||||||
|
=head2 linkToJobset
|
||||||
|
|
||||||
|
Given a L<Hydra::Schema::Result::Jobset> and L<String> Job name, return
|
||||||
|
a link to the job, jobset, and project in project:jobset:job notation.
|
||||||
|
|
||||||
|
Arguments:
|
||||||
|
|
||||||
|
=over 4
|
||||||
|
|
||||||
|
=item C<$self>
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$c>
|
||||||
|
Catalyst Context
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$jobset>
|
||||||
|
|
||||||
|
The L<Hydra::Schema::Result::Jobset> to link to.
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$jobName>
|
||||||
|
|
||||||
|
The L<String> job name to link to.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
|
=cut
|
||||||
|
sub linkToJob {
|
||||||
|
my ($self, $c, $jobset, $jobName) = @_;
|
||||||
|
|
||||||
|
my $html = Template::Plugin::HTML->new();
|
||||||
|
|
||||||
|
my $escapedJobName = $html->escape($jobName);
|
||||||
|
|
||||||
|
return linkToJobset($self, $c, $jobset) .
|
||||||
|
':<a href="' . $c->uri_for('/job', $jobset->project->name, $jobset->name, $jobName) . '">' . $escapedJobName . '</a>';
|
||||||
|
}
|
||||||
|
|
||||||
|
=head2 makeNameLinksForJobset
|
||||||
|
|
||||||
|
Given a L<Hydra::Schema::Result::Jobset>, return a link to the jobset's
|
||||||
|
project and a non-link to the jobset in project:jobset notation.
|
||||||
|
|
||||||
|
Arguments:
|
||||||
|
|
||||||
|
=over 3
|
||||||
|
|
||||||
|
=item C<$self>
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$c>
|
||||||
|
Catalyst Context
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$jobset>
|
||||||
|
|
||||||
|
The L<Hydra::Schema::Result::Jobset> to link to.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
|
=cut
|
||||||
|
sub makeNameLinksForJobset {
|
||||||
|
my ($self, $c, $jobset) = @_;
|
||||||
|
|
||||||
|
my $html = Template::Plugin::HTML->new();
|
||||||
|
|
||||||
|
my $escapedJobsetName = $html->escape($jobset->name);
|
||||||
|
|
||||||
|
return linkToProject($self, $c, $jobset->project) . ':' . $escapedJobsetName;
|
||||||
|
}
|
||||||
|
|
||||||
|
=head2 makeNameLinksForJob
|
||||||
|
|
||||||
|
Given a L<Hydra::Schema::Result::Jobset> and L<String> Job name, return
|
||||||
|
a link to the jobset and project, and a non-link to the job in
|
||||||
|
project:jobset:job notation.
|
||||||
|
|
||||||
|
Arguments:
|
||||||
|
|
||||||
|
=over 4
|
||||||
|
|
||||||
|
=item C<$self>
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$c>
|
||||||
|
Catalyst Context
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$jobset>
|
||||||
|
|
||||||
|
The L<Hydra::Schema::Result::Jobset> to link to.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
|
|
||||||
|
=item C<$jobName>
|
||||||
|
|
||||||
|
The L<String> job name to link to.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
|
=cut
|
||||||
|
sub makeNameLinksForJob {
|
||||||
|
my ($self, $c, $jobset, $jobName) = @_;
|
||||||
|
|
||||||
|
my $html = Template::Plugin::HTML->new();
|
||||||
|
|
||||||
|
my $escapedJobName = $html->escape($jobName);
|
||||||
|
|
||||||
|
return linkToJobset($self, $c, $jobset) . ':' . $escapedJobName;
|
||||||
|
}
|
||||||
|
|
||||||
|
=head2 makeNameTextForJobset
|
||||||
|
|
||||||
|
Given a L<Hydra::Schema::Result::Jobset>, return the project and
|
||||||
|
jobset in project:jobset notation.
|
||||||
|
|
||||||
|
Arguments:
|
||||||
|
|
||||||
|
=over 3
|
||||||
|
|
||||||
|
=item C<$self>
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$c>
|
||||||
|
Catalyst Context
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$jobset>
|
||||||
|
|
||||||
|
The L<Hydra::Schema::Result::Jobset> to link to.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
|
=cut
|
||||||
|
sub makeNameTextForJobset {
|
||||||
|
my ($self, $c, $jobset) = @_;
|
||||||
|
|
||||||
|
return $jobset->project->name . ":" . $jobset->name;
|
||||||
|
}
|
||||||
|
|
||||||
|
=head2 makeNameTextForJob
|
||||||
|
|
||||||
|
Given a L<Hydra::Schema::Result::Jobset> and L<String> Job name, return
|
||||||
|
the job, jobset, and project in project:jobset:job notation.
|
||||||
|
|
||||||
|
Arguments:
|
||||||
|
|
||||||
|
=over 4
|
||||||
|
|
||||||
|
=item C<$self>
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$c>
|
||||||
|
Catalyst Context
|
||||||
|
=back
|
||||||
|
|
||||||
|
=item C<$jobset>
|
||||||
|
|
||||||
|
The L<Hydra::Schema::Result::Jobset> to link to.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
|
|
||||||
|
=item C<$jobName>
|
||||||
|
|
||||||
|
The L<String> job name to link to.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
|
=cut
|
||||||
|
sub makeNameTextForJob {
|
||||||
|
my ($self, $c, $jobset, $jobName) = @_;
|
||||||
|
|
||||||
|
return $jobset->project->name . ":" . $jobset->name . ":" . $jobName;
|
||||||
|
}
|
||||||
|
|
||||||
1;
|
1;
|
||||||
|
|
|
@ -1,7 +1,14 @@
|
||||||
[% WRAPPER layout.tt title="Latest builds" _
|
[% WRAPPER layout.tt
|
||||||
(job ? " for job $project.name:$jobset.name:$job" :
|
titleHTML="Latest builds" _
|
||||||
jobset ? " for jobset $project.name:$jobset.name" :
|
(job ? " for job " _ linkToJob(jobset, job) :
|
||||||
project ? " for project $project.name" : "") %]
|
jobset ? " for jobset " _ linkToJobset(jobset) :
|
||||||
|
project ? " for project " _ linkToProject(project) :
|
||||||
|
"")
|
||||||
|
title="Latest builds" _
|
||||||
|
(job ? " for job " _ makeNameTextForJob(jobset, job) :
|
||||||
|
jobset ? " for jobset " _ makeNameTextForJobset(jobset) :
|
||||||
|
project ? " for project $project.name" :
|
||||||
|
"") %]
|
||||||
[% PROCESS common.tt %]
|
[% PROCESS common.tt %]
|
||||||
|
|
||||||
<p>Showing builds [% (page - 1) * resultsPerPage + 1 %] - [% (page - 1) * resultsPerPage + builds.size %] out of [% total %] in order of descending finish time.</p>
|
<p>Showing builds [% (page - 1) * resultsPerPage + 1 %] - [% (page - 1) * resultsPerPage + builds.size %] out of [% total %] in order of descending finish time.</p>
|
||||||
|
|
|
@ -1,4 +1,7 @@
|
||||||
[% WRAPPER layout.tt title="Build $id of job $project.name:$jobset.name:$job" %]
|
[% WRAPPER layout.tt
|
||||||
|
title="Build $id of job " _ makeNameTextForJob(jobset, job)
|
||||||
|
titleHTML="Build $id of job " _ linkToJob(jobset, job)
|
||||||
|
%]
|
||||||
[% PROCESS common.tt %]
|
[% PROCESS common.tt %]
|
||||||
[% PROCESS "product-list.tt" %]
|
[% PROCESS "product-list.tt" %]
|
||||||
[% USE HTML %]
|
[% USE HTML %]
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
[% WRAPPER layout.tt title=
|
[% WRAPPER layout.tt title=
|
||||||
(create ? "Creating jobset in project $project.name" :
|
(create ? "Creating jobset in project $project.name" :
|
||||||
createFromEval ? "Creating jobset from evaluation $eval.id of $project.name:$jobset.name" :
|
createFromEval ? "Creating jobset from evaluation $eval.id of " _ makeNameTextForJobset(jobset) :
|
||||||
cloneJobset ? "Cloning jobset $project.name:$jobset.name" :
|
cloneJobset ? "Cloning jobset " _ makeNameTextForJobset(jobset) :
|
||||||
"Editing jobset $project.name:$jobset.name") %]
|
"Editing jobset " _ makeNameTextForJobset(jobset)) %]
|
||||||
[% PROCESS common.tt %]
|
[% PROCESS common.tt %]
|
||||||
[% USE format %]
|
[% USE format %]
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,11 @@
|
||||||
[% WRAPPER layout.tt title=
|
[% WRAPPER layout.tt
|
||||||
|
title=
|
||||||
(build ? "Evaluations containing build $build.id" :
|
(build ? "Evaluations containing build $build.id" :
|
||||||
jobset ? "Evaluations of jobset $project.name:$jobset.name" :
|
jobset ? "Evaluations of jobset " _ makeNameTextForJobset(jobset) :
|
||||||
|
"Latest evaluations")
|
||||||
|
titleHTML =
|
||||||
|
(build ? "Evaluations containing build $build.id" :
|
||||||
|
jobset ? "Evaluations of jobset " _ linkToJobset(jobset) :
|
||||||
"Latest evaluations") %]
|
"Latest evaluations") %]
|
||||||
[% PROCESS common.tt %]
|
[% PROCESS common.tt %]
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
[% WRAPPER layout.tt
|
[% WRAPPER layout.tt
|
||||||
title="Job $project.name:$jobset.name:$job"
|
title=makeNameTextForJob(jobset, job)
|
||||||
|
titleHTML=makeNameLinksForJob(jobset, job)
|
||||||
starUri=c.uri_for(c.controller('Job').action_for('star'), c.req.captures)
|
starUri=c.uri_for(c.controller('Job').action_for('star'), c.req.captures)
|
||||||
%]
|
%]
|
||||||
[% PROCESS common.tt %]
|
[% PROCESS common.tt %]
|
||||||
|
|
|
@ -1,4 +1,6 @@
|
||||||
[% WRAPPER layout.tt title="Evaluation $eval.id of jobset $project.name:$jobset.name " %]
|
[% WRAPPER layout.tt
|
||||||
|
title="Evaluation $eval.id of jobset " _ makeNameTextForJobset(jobset)
|
||||||
|
titleHTML="Evaluation $eval.id of jobset " _ linkToJobset(jobset) %]
|
||||||
[% PROCESS common.tt %]
|
[% PROCESS common.tt %]
|
||||||
|
|
||||||
<div class="dropdown">
|
<div class="dropdown">
|
||||||
|
|
|
@ -1,4 +1,6 @@
|
||||||
[% WRAPPER layout.tt title="Jobset $project.name:$jobset.name" %]
|
[% WRAPPER layout.tt
|
||||||
|
titleHTML=makeNameLinksForJobset(jobset)
|
||||||
|
title=makeNameTextForJobset(jobset) %]
|
||||||
[% PROCESS common.tt %]
|
[% PROCESS common.tt %]
|
||||||
[% USE format %]
|
[% USE format %]
|
||||||
|
|
||||||
|
|
|
@ -81,7 +81,8 @@
|
||||||
|
|
||||||
[% IF !hideHeader %]
|
[% IF !hideHeader %]
|
||||||
<div class="page-header">
|
<div class="page-header">
|
||||||
[% IF c.user_exists && starUri; INCLUDE makeStar; " "; END; HTML.escape(title) %]
|
[% IF c.user_exists && starUri; INCLUDE makeStar; " "; END %]
|
||||||
|
[% IF titleHTML != ""; titleHTML; ELSE; HTML.escape(title); END %]
|
||||||
</div>
|
</div>
|
||||||
[% ELSE %]
|
[% ELSE %]
|
||||||
[% IF first %]<br />[% first = 0; END; %]
|
[% IF first %]<br />[% first = 0; END; %]
|
||||||
|
|
|
@ -1,4 +1,7 @@
|
||||||
[% WRAPPER layout.tt title="Log of " _ (step ? " step $step.stepnr of " : "") _ "build ${build.id} of job $build.project.name:$build.jobset.name:$build.job.name" %]
|
[% WRAPPER layout.tt
|
||||||
|
titleHTML="Log of " _ (step ? " step $step.stepnr of " : "") _ "build ${build.id} of job " _ linkToJob(build.jobset, job)
|
||||||
|
title="Log of " _ (step ? " step $step.stepnr of " : "") _ "build ${build.id} of job " _ makeNameTextForJob(build.jobset, job)
|
||||||
|
%]
|
||||||
[% PROCESS common.tt %]
|
[% PROCESS common.tt %]
|
||||||
|
|
||||||
<p>
|
<p>
|
||||||
|
|
77
t/View/TT.t
Normal file
77
t/View/TT.t
Normal file
|
@ -0,0 +1,77 @@
|
||||||
|
use feature 'unicode_strings';
|
||||||
|
use strict;
|
||||||
|
use warnings;
|
||||||
|
use Setup;
|
||||||
|
|
||||||
|
my %ctx = test_init();
|
||||||
|
|
||||||
|
require Hydra::Schema;
|
||||||
|
require Hydra::Model::DB;
|
||||||
|
|
||||||
|
use Test2::V0;
|
||||||
|
|
||||||
|
require Hydra; # calls setup()
|
||||||
|
|
||||||
|
|
||||||
|
my $db = Hydra::Model::DB->new;
|
||||||
|
hydra_setup($db);
|
||||||
|
|
||||||
|
require Hydra::View::TT;
|
||||||
|
|
||||||
|
# The following lines are a cheap and hacky trick to get $c,
|
||||||
|
# there is no other reason to call /.
|
||||||
|
require Catalyst::Test;
|
||||||
|
Catalyst::Test->import('Hydra');
|
||||||
|
my($_, $c) = ctx_request('/');
|
||||||
|
|
||||||
|
|
||||||
|
my $project = $db->resultset('Projects')->create({name => "tests", displayname => "", owner => "root"});
|
||||||
|
my $jobset = createBaseJobset("example", "bogus.nix", $ctx{jobsdir});
|
||||||
|
my $job = "myjob";
|
||||||
|
|
||||||
|
|
||||||
|
is(
|
||||||
|
Hydra::View::TT::linkToProject(undef, $c, $project),
|
||||||
|
'<a href="http://localhost/project/tests">tests</a>',
|
||||||
|
"linkToProject"
|
||||||
|
);
|
||||||
|
is(
|
||||||
|
Hydra::View::TT::linkToJobset(undef, $c, $jobset),
|
||||||
|
'<a href="http://localhost/project/tests">tests</a>'
|
||||||
|
. ':<a href="http://localhost/jobset/tests/example">example</a>',
|
||||||
|
"linkToJobset"
|
||||||
|
);
|
||||||
|
is(
|
||||||
|
Hydra::View::TT::linkToJob(undef, $c, $jobset, $job),
|
||||||
|
'<a href="http://localhost/project/tests">tests</a>'
|
||||||
|
. ':<a href="http://localhost/jobset/tests/example">example</a>'
|
||||||
|
. ':<a href="http://localhost/job/tests/example/myjob">myjob</a>',
|
||||||
|
"linkToJob"
|
||||||
|
);
|
||||||
|
|
||||||
|
is(
|
||||||
|
Hydra::View::TT::makeNameLinksForJobset(undef, $c, $jobset),
|
||||||
|
'<a href="http://localhost/project/tests">tests</a>'
|
||||||
|
. ':example',
|
||||||
|
"makeNameLinksForJobset"
|
||||||
|
);
|
||||||
|
is(
|
||||||
|
Hydra::View::TT::makeNameLinksForJob(undef, $c, $jobset, $job),
|
||||||
|
'<a href="http://localhost/project/tests">tests</a>'
|
||||||
|
. ':<a href="http://localhost/jobset/tests/example">example</a>'
|
||||||
|
. ':myjob',
|
||||||
|
"makeNameLinksForJob"
|
||||||
|
);
|
||||||
|
|
||||||
|
is(
|
||||||
|
Hydra::View::TT::makeNameTextForJobset(undef, $c, $jobset),
|
||||||
|
'tests:example',
|
||||||
|
"makeNameTextForJobset"
|
||||||
|
);
|
||||||
|
is(
|
||||||
|
Hydra::View::TT::makeNameTextForJob(undef, $c, $jobset, $job),
|
||||||
|
'tests:example:myjob',
|
||||||
|
"makeNameTextForJob"
|
||||||
|
);
|
||||||
|
|
||||||
|
done_testing;
|
Loading…
Reference in a new issue