[RFC PATCH 06/10] gitweb/cache.pm - Adaptive cache expiration time (WIP)

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Signed-off-by: Jakub Narebski <jnareb@xxxxxxxxx>
---
This patch, as you can see, lack proper commit message: it is work in
progress.

As it is quick'n'dirty proof of concept patch, it lacks variables in
gitweb.perl that can be used to control cache behaviour.  In original
patch in J.H. those were the following variables: $minCacheTime,
$maxCacheTime.

In the final version we should probably leave $check_load undefined,
or set it to 'sub { return 0; }' instead of requiring that there is
get_loadavg() subroutine in main namespace (see t9503 test change).
It would be alos good idea to leave ->set_expires_in() subroutine
which would set min and max range so that adaptive cache lifetime is
effectively disabled.

 gitweb/cache.pm                 |   82 ++++++++++++++++++++++++++++++++++----
 t/t9503/test_cache_interface.pl |    8 +++-
 2 files changed, 80 insertions(+), 10 deletions(-)

diff --git a/gitweb/cache.pm b/gitweb/cache.pm
index 3a33158..9692e8d 100644
--- a/gitweb/cache.pm
+++ b/gitweb/cache.pm
@@ -61,24 +61,36 @@ sub new {
 	my $self  = {};
 	$self = bless($self, $class);
 
-	my ($root, $depth, $ns, $expires_in);
+	my ($root, $depth, $ns);
+	my ($expires_min, $expires_max, $increase_factor, $check_load);
 	if (defined $p_options_hash_ref) {
 		$root  = $p_options_hash_ref->{'cache_root'};
 		$depth = $p_options_hash_ref->{'cache_depth'};
 		$ns    = $p_options_hash_ref->{'namespace'};
-		$expires_in =
+		$expires_min =
+			$p_options_hash_ref->{'expires_min'} ||
 			$p_options_hash_ref->{'default_expires_in'} ||
 			$p_options_hash_ref->{'expires_in'};
+		$expires_max =
+			$p_options_hash_ref->{'expires_max'};
+		$increase_factor = $p_options_hash_ref->{'expires_factor'};
+		$check_load      = $p_options_hash_ref->{'check_load'};
 	}
 	$root  = $DEFAULT_CACHE_ROOT  unless defined($root);
 	$depth = $DEFAULT_CACHE_DEPTH unless defined($depth);
 	$ns    = '' unless defined($ns);
-	$expires_in = -1 unless defined($expires_in); # <0 means never
+	$expires_min =   20 unless defined($expires_min);
+	$expires_max = 1200 unless defined($expires_max);
+	$increase_factor = 60 unless defined($increase_factor);
+	$check_load = \&main::get_loadavg unless defined($check_load);
 
 	$self->set_root($root);
 	$self->set_depth($depth);
 	$self->set_namespace($ns);
-	$self->set_expires_in($expires_in);
+	$self->set_expires_min($expires_min);
+	$self->set_expires_max($expires_max);
+	$self->set_increase_factor($increase_factor);
+	$self->set_check_load($check_load);
 
 	return $self;
 }
@@ -124,19 +136,71 @@ sub set_namespace {
 	$self->{'_Namespace'} = $namespace;
 }
 
-sub get_expires_in {
+
+sub get_expires_min {
 	my ($self) = @_;
 
-	return $self->{'_Expires_In'};
+	return $self->{'_Expires_Min'};
+}
+
+sub set_expires_min {
+	my ($self, $expires_min) = @_;
+
+	$self->{'_Expires_Min'} = $expires_min;
 }
 
+sub get_expires_max {
+	my ($self) = @_;
+
+	return $self->{'_Expires_Max'};
+}
+
+sub set_expires_max {
+	my ($self, $expires_max) = @_;
+
+	$self->{'_Expires_Max'} = $expires_max;
+}
+
+sub get_increase_factor {
+	my ($self) = @_;
+
+	return $self->{'_Increase_Factor'};
+}
 
-sub set_expires_in {
-	my ($self, $expires_in) = @_;
+sub set_increase_factor {
+	my ($self, $increase_factor) = @_;
 
-	$self->{'_Expires_In'} = $expires_in;
+	$self->{'_Increase_Factor'} = $increase_factor;
 }
 
+sub get_check_load {
+	my ($self) = @_;
+
+	return $self->{'_Check_Load'};
+}
+
+sub set_check_load {
+	my ($self, $sub) = @_;
+
+	$self->{'_Check_Load'} = $sub;
+}
+
+# ......................................................................
+
+sub get_expires_in {
+	my ($self) = @_;
+	my $expires_in =
+		#$self->get_expires_min() +
+		$self->get_increase_factor() * $self->get_check_load()->();
+
+	if ($expires_in < $self->get_expires_min()) {
+		return $self->get_expires_min();
+	} elsif ($expires_in > $self->get_expires_max()) {
+		return $self->get_expires_max();
+	}
+
+	return $expires_in;
+}
 
 # ----------------------------------------------------------------------
 # (private) utility functions and methods
diff --git a/t/t9503/test_cache_interface.pl b/t/t9503/test_cache_interface.pl
index 3644ca8..0870b87 100755
--- a/t/t9503/test_cache_interface.pl
+++ b/t/t9503/test_cache_interface.pl
@@ -6,6 +6,11 @@ use strict;
 
 use Test::More;
 
+# mockup
+sub get_loadavg {
+	return 0.0;
+}
+
 # test source version; there is no installation target for gitweb
 my $cache_pm = "$ENV{TEST_DIRECTORY}/../gitweb/cache.pm";
 
@@ -77,7 +82,8 @@ cmp_ok($call_count, '==', 1, 'get_value() is called once');
 
 # Test cache expiration for 'expire now'
 #
-$cache->set_expires_in(0);
+$cache->set_expires_min(0);
+$cache->set_expires_max(0);
 is($cache->get_expires_in(), 0,        '"expires in" is set to now (0)');
 $cache->set($key, $value);
 ok(!defined($cache->get($key)),        'cache is expired');
-- 
1.6.6.1

--
To unsubscribe from this list: send the line "unsubscribe git" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Linux Kernel Development]     [Gcc Help]     [IETF Annouce]     [DCCP]     [Netdev]     [Networking]     [Security]     [V4L]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux SCSI]     [Fedora Users]