mirror of
https://github.com/webmin/webmin.git
synced 2026-06-04 20:30:22 +01:00
Add ability to show pending apply state after config changes
This commit is contained in:
@@ -32,6 +32,7 @@ index_stopdesc=Shut down all running Nginx webserver processes.
|
||||
index_start=Start Nginx Webserver
|
||||
index_startdesc=Start up the Nginx webserver using the current configuration.
|
||||
index_restart=Apply Nginx Configuration
|
||||
index_apply_changes=Apply Changes
|
||||
index_restartdesc=Apply the current configuration by stopping and re-starting the Nginx webserver.
|
||||
index_delete=Delete Selected Server Blocks
|
||||
index_eglobal=You are not allowed to edit global settings
|
||||
|
||||
@@ -11,8 +11,11 @@ eval "use WebminCore;";
|
||||
our %access = &get_module_acl();
|
||||
our ($get_config_cache, $get_config_parent_cache, %list_directives_cache,
|
||||
@list_modules_cache, @open_config_files);
|
||||
our (%config, %text, %in, $module_root_directory);
|
||||
our ($last_config_change_flag, $last_restart_time_flag);
|
||||
our (%config, %text, %in, $module_root_directory, $module_var_directory);
|
||||
&set_nginx_config_defaults();
|
||||
$last_config_change_flag = $module_var_directory."/config-flag";
|
||||
$last_restart_time_flag = $module_var_directory."/restart-flag";
|
||||
|
||||
my @lock_all_config_files_cache;
|
||||
|
||||
@@ -522,9 +525,11 @@ if ($parent->{'type'}) {
|
||||
sub flush_config_file_lines
|
||||
{
|
||||
my ($parent) = @_;
|
||||
foreach my $f (&unique(@open_config_files)) {
|
||||
my @files = &unique(@open_config_files);
|
||||
foreach my $f (@files) {
|
||||
&flush_file_lines($f);
|
||||
}
|
||||
&update_last_config_change() if (@files);
|
||||
@open_config_files = ( );
|
||||
}
|
||||
|
||||
@@ -1480,7 +1485,11 @@ return $? ? $out : undef;
|
||||
sub start_nginx
|
||||
{
|
||||
my $out = &backquote_logged("$config{'start_cmd'} 2>&1 </dev/null");
|
||||
return $? ? $out : undef;
|
||||
if ($?) {
|
||||
return $out;
|
||||
}
|
||||
&update_last_restart_time();
|
||||
return undef;
|
||||
}
|
||||
|
||||
# apply_nginx()
|
||||
@@ -1489,7 +1498,11 @@ return $? ? $out : undef;
|
||||
sub apply_nginx
|
||||
{
|
||||
my $out = &backquote_logged("$config{'apply_cmd'} 2>&1 </dev/null");
|
||||
return $? ? $out : undef;
|
||||
if ($?) {
|
||||
return $out;
|
||||
}
|
||||
&update_last_restart_time();
|
||||
return undef;
|
||||
}
|
||||
|
||||
# nginx_action_links()
|
||||
@@ -1502,7 +1515,11 @@ if (&is_nginx_running()) {
|
||||
if ($access{'stop'}) {
|
||||
push(@rv, &ui_link("stop.cgi?$args", $text{'index_stop'}));
|
||||
}
|
||||
push(@rv, &ui_link("restart.cgi?$args", $text{'index_restart'}));
|
||||
my $needs = &needs_config_restart();
|
||||
my $apply = $text{'index_apply_changes'} || $text{'index_restart'};
|
||||
my $label = $needs ? "<b>$apply</b>" : $apply;
|
||||
my $url = "restart.cgi?$args";
|
||||
push(@rv, &ui_link($url, $label));
|
||||
}
|
||||
elsif ($access{'stop'}) {
|
||||
push(@rv, &ui_link("start.cgi?$args", $text{'index_start'}));
|
||||
@@ -1510,6 +1527,33 @@ elsif ($access{'stop'}) {
|
||||
return join("<br>\n", @rv);
|
||||
}
|
||||
|
||||
# update_last_config_change()
|
||||
# Updates the flag file indicating when the config was changed
|
||||
sub update_last_config_change
|
||||
{
|
||||
&open_lock_tempfile(my $fh, ">$last_config_change_flag", 0, 1);
|
||||
&close_tempfile($fh);
|
||||
}
|
||||
|
||||
# update_last_restart_time()
|
||||
# Updates the flag file indicating when the config was applied
|
||||
sub update_last_restart_time
|
||||
{
|
||||
&open_lock_tempfile(my $fh, ">$last_restart_time_flag", 0, 1);
|
||||
&close_tempfile($fh);
|
||||
}
|
||||
|
||||
# needs_config_restart()
|
||||
# Returns 1 if a restart is needed after a config change
|
||||
sub needs_config_restart
|
||||
{
|
||||
my @cst = stat($last_config_change_flag);
|
||||
my @rst = stat($last_restart_time_flag);
|
||||
return 0 if (!@cst);
|
||||
return 1 if (!@rst);
|
||||
return $cst[9] > $rst[9] ? 1 : 0;
|
||||
}
|
||||
|
||||
# this_url()
|
||||
# Returns the current module URL
|
||||
sub this_url
|
||||
@@ -1610,6 +1654,7 @@ if ($empty) {
|
||||
}
|
||||
&unlink_logged($file);
|
||||
}
|
||||
&update_last_config_change();
|
||||
return scalar(@servers);
|
||||
}
|
||||
|
||||
@@ -1723,6 +1768,7 @@ if ($err) {
|
||||
&unlink_logged($link);
|
||||
return &text('enable_etest', "<tt>".&html_escape($err)."</tt>");
|
||||
}
|
||||
&update_last_config_change();
|
||||
return undef;
|
||||
}
|
||||
|
||||
@@ -1756,6 +1802,7 @@ if ($err) {
|
||||
}
|
||||
return &text('enable_etest', "<tt>".&html_escape($err)."</tt>");
|
||||
}
|
||||
&update_last_config_change();
|
||||
return undef;
|
||||
}
|
||||
|
||||
@@ -2037,7 +2084,8 @@ if ($config{'add_link'}) {
|
||||
my $link = $server->{'file'};
|
||||
$link =~ s/^.*\///;
|
||||
$link = $config{'add_link'}."/".$link;
|
||||
&symlink_logged($server->{'file'}, $link);
|
||||
&update_last_config_change()
|
||||
if (&symlink_logged($server->{'file'}, $link));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2049,6 +2097,7 @@ sub delete_server_link
|
||||
my ($server) = @_;
|
||||
if ($config{'add_link'}) {
|
||||
my $file = $server->{'file'};
|
||||
my $changed;
|
||||
my $short = $file;
|
||||
$short =~ s/^.*\///;
|
||||
opendir(LINKDIR, $config{'add_link'});
|
||||
@@ -2056,10 +2105,11 @@ if ($config{'add_link'}) {
|
||||
if ($f ne "." && $f ne ".." &&
|
||||
(&resolve_links($config{'add_link'}."/".$f) eq $file ||
|
||||
$short eq $f)) {
|
||||
&unlink_logged($config{'add_link'}."/".$f);
|
||||
$changed++ if (&unlink_logged($config{'add_link'}."/".$f));
|
||||
}
|
||||
}
|
||||
closedir(LINKDIR);
|
||||
&update_last_config_change() if ($changed);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2074,7 +2124,8 @@ foreach my $l (@$lref) {
|
||||
$count++ if ($l =~ /\S/);
|
||||
}
|
||||
if (!$count) {
|
||||
&unlink_logged($server->{'file'});
|
||||
&update_last_config_change()
|
||||
if (&unlink_logged($server->{'file'}));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -43,6 +43,6 @@ else {
|
||||
&print_tempfile($fh, $in{'data'});
|
||||
&close_tempfile($fh);
|
||||
}
|
||||
&update_last_config_change();
|
||||
&webmin_log("manual", undef, $in{'file'});
|
||||
&redirect("");
|
||||
|
||||
|
||||
@@ -130,11 +130,17 @@ subtest 'sites-available files are manageable and ordered' => sub {
|
||||
};
|
||||
|
||||
subtest 'disable removes only the enabled symlink' => sub {
|
||||
no warnings 'once';
|
||||
unlink($main::last_config_change_flag);
|
||||
unlink($main::last_restart_time_flag);
|
||||
|
||||
{
|
||||
no warnings 'redefine';
|
||||
local *main::test_config = sub { return undef; };
|
||||
is(main::disable_server_file($alpha), undef, 'disable succeeds');
|
||||
}
|
||||
ok(main::needs_config_restart(),
|
||||
'disable marks config as needing apply');
|
||||
|
||||
ok(-f $alpha, 'disable leaves the sites-available file in place');
|
||||
ok(!-e File::Spec->catfile($enabled, 'alpha.conf'),
|
||||
@@ -150,11 +156,17 @@ subtest 'disable removes only the enabled symlink' => sub {
|
||||
};
|
||||
|
||||
subtest 'enable creates a symlink without touching the source file' => sub {
|
||||
no warnings 'once';
|
||||
unlink($main::last_config_change_flag);
|
||||
unlink($main::last_restart_time_flag);
|
||||
|
||||
{
|
||||
no warnings 'redefine';
|
||||
local *main::test_config = sub { return undef; };
|
||||
is(main::enable_server_file($beta), undef, 'enable succeeds');
|
||||
}
|
||||
ok(main::needs_config_restart(),
|
||||
'enable marks config as needing apply');
|
||||
|
||||
my $link = File::Spec->catfile($enabled, 'beta.conf');
|
||||
ok(-f $beta, 'enable leaves the sites-available file in place');
|
||||
@@ -164,18 +176,28 @@ subtest 'enable creates a symlink without touching the source file' => sub {
|
||||
};
|
||||
|
||||
subtest 'legacy create/delete link helpers still manage symlinks' => sub {
|
||||
no warnings 'once';
|
||||
my $echo = File::Spec->catfile($available, 'echo.conf');
|
||||
my $echo_link = File::Spec->catfile($enabled, 'echo.conf');
|
||||
write_text($echo, server_conf('echo.example', "\troot /srv/echo;\n"));
|
||||
my $server = { 'file' => $echo };
|
||||
|
||||
unlink($main::last_config_change_flag);
|
||||
unlink($main::last_restart_time_flag);
|
||||
main::create_server_link($server);
|
||||
ok(-l $echo_link, 'create_server_link creates expected symlink');
|
||||
is(readlink($echo_link), $echo, 'created symlink points to server file');
|
||||
ok(main::needs_config_restart(),
|
||||
'create_server_link marks config as needing apply');
|
||||
|
||||
main::update_last_restart_time();
|
||||
my $old = time() - 10;
|
||||
utime($old, $old, $main::last_restart_time_flag);
|
||||
main::delete_server_link($server);
|
||||
ok(!-e $echo_link, 'delete_server_link removes expected symlink');
|
||||
ok(-f $echo, 'delete_server_link leaves server file in place');
|
||||
ok(main::needs_config_restart(),
|
||||
'delete_server_link marks config as needing apply');
|
||||
};
|
||||
|
||||
subtest 'disabled server blocks can be deleted from available files' => sub {
|
||||
@@ -342,4 +364,25 @@ subtest 'root and proxy summaries are detected' => sub {
|
||||
'named-location proxy URL uses HTTP default port');
|
||||
};
|
||||
|
||||
subtest 'config change apply flag tracks pending changes' => sub {
|
||||
no warnings 'once';
|
||||
unlink($main::last_config_change_flag);
|
||||
unlink($main::last_restart_time_flag);
|
||||
|
||||
ok(!main::needs_config_restart(),
|
||||
'no apply needed when no change flag exists');
|
||||
main::update_last_config_change();
|
||||
ok(main::needs_config_restart(),
|
||||
'apply needed after config change');
|
||||
main::update_last_restart_time();
|
||||
ok(!main::needs_config_restart(),
|
||||
'apply not needed after config has been applied');
|
||||
|
||||
my $old = time() - 10;
|
||||
utime($old, $old, $main::last_restart_time_flag);
|
||||
main::update_last_config_change();
|
||||
ok(main::needs_config_restart(),
|
||||
'apply needed when config change is newer than last apply');
|
||||
};
|
||||
|
||||
done_testing();
|
||||
|
||||
Reference in New Issue
Block a user