[LON-CAPA-cvs] cvs: loncom /interface lonwhatsnew.pm /localize lonlocal.pm

droeschl droeschl@source.lon-capa.org
Wed, 06 May 2009 19:25:56 -0000


droeschl		Wed May  6 19:25:56 2009 EDT

  Modified files:              
    /loncom/localize	lonlocal.pm 
    /loncom/interface	lonwhatsnew.pm 
  Log:
  - reverted changes made in lonlocal.pm 1.58 and lonwhatsnew.pm 1.92
  - the root cause for slow performance in lonwhatsnew while looking up received mails 
    was found in DateTime::TimeZone's methods for looking up the 'local' timezone:
    [SOURCE: http://search.cpan.org/~drolsky/DateTime-TimeZone-0.90/lib/DateTime/TimeZone/Local/Unix.pm]
    "This class tries the following methods of determining the local time zone:
  
      * $ENV{TZ}
        It checks $ENV{TZ} for a valid time zone name.
  
      * /etc/localtime
        If this file is a symlink to an Olson database time zone file (usually in /usr/share/zoneinfo) then 
        it uses the target file's path name to determine the time zone name. For example, if the path is 
        /usr/share/zoneinfo/America/Chicago, the time zone is "America/Chicago".
  
        Some systems just copy the relevant file to /etc/localtime instead of making a symlink. In this case, 
        we look in /usr/share/zoneinfo for a file that has the same size and content as /etc/localtime to 
        determine the local time zone.[...]"
  
    On our CentOS server /etc/localtime happens to be a copy and this causes TimeZone to do an expensive 
    search through the files in /usr/share/zoneinfo (everytime locallocaltime needs the 'local' timezone).
    To prevent TimeZone from doing this search we store the timezone found after the first run in $ENV{TZ}.
    Future calls of locallocaltime will be significantly improved in performance. 
    This affects every module that calls locallocaltime (not only lonwhatsnew.pm).
  
  
  
Index: loncom/localize/lonlocal.pm
diff -u loncom/localize/lonlocal.pm:1.58 loncom/localize/lonlocal.pm:1.59
--- loncom/localize/lonlocal.pm:1.58	Mon May  4 21:44:00 2009
+++ loncom/localize/lonlocal.pm	Wed May  6 19:25:49 2009
@@ -1,7 +1,7 @@
 # The LearningOnline Network with CAPA
 # Localization routines
 #
-# $Id: lonlocal.pm,v 1.58 2009/05/04 21:44:00 lueken Exp $
+# $Id: lonlocal.pm,v 1.59 2009/05/06 19:25:49 droeschl Exp $
 #
 # Copyright Michigan State University Board of Trustees
 #
@@ -393,10 +393,8 @@
     return 'local';
 }
 
-our $timezone_local;
-
 sub locallocaltime {
-    my ($thistime,$timezone,$datetime) = @_;
+    my ($thistime,$timezone) = @_;
 
     if (!defined($thistime) || $thistime eq '') {
 	return &mt('Never');
@@ -410,69 +408,16 @@
         return &mt('Never');
     }
 
-   my $dt;
-   my $convert_time;
+    my $dt = DateTime->from_epoch(epoch => $thistime)
+                     ->set_time_zone(gettimezone($timezone));
 
-   #### START # Speed up if this function is called often #### 
-   
-   # Is a $datetime parameter set?
-   if(defined($datetime)) {
-	# Check for an instance of a DateTime object
-   	if(!(defined $$datetime)) {
-		# No object, create one
-		$$datetime = DateTime->from_epoch(epoch => $thistime)
-       	                  ->set_time_zone(&gettimezone($timezone));
-		$dt = $$datetime;
-	   } else {
-		# If the return-value is "local", we have to convert it for DateTime	
-	
-		# Converts the "local"-String only once
-		if(!defined($timezone_local))	
-		{
-			$timezone_local = DateTime::TimeZone->new( name => gettimezone('local'))->name();
-		}
-
-		my $timezone_now;
-
-		if(gettimezone($timezone) == 'local')
-		{
-			$timezone_now = $timezone_local;
-		} else {
-			$timezone_now = gettimezone($timezone);
-		}
-
-		# Has the timezone changed?
-		if($timezone_now eq $$datetime->time_zone_short_name() ||
-		   $timezone_now eq $$datetime->time_zone_long_name())
-		{
-			# There is already an object (dereference)
-			$dt = $$datetime;
-		
-			# We need this as temporary value	
-			$convert_time = DateTime->from_epoch( epoch => $thistime );
-        	                                #->set_time_zone('floating');
- 
-			# Preventing a set_time_zone call (time consuming)	
-			# Using old instance of DateTime with timezone
-			$dt->set( year => $convert_time->year(),
-				  month => $convert_time->month(),
-				  day => $convert_time->day(),
-				  hour => $convert_time->hour(),
-				  minute => $convert_time->minute(),
-				  second => $convert_time->second() );
-   		} else {
-			# The timezone has changed since last time
-			$$datetime = DateTime->from_epoch(epoch => $thistime)
-                          ->set_time_zone(&gettimezone($timezone));
-			$dt = $$datetime;
-		} 
-	}
-   } else {
-	# There is no $datetime parameter
-	$dt = DateTime->from_epoch(epoch => $thistime)
-                      ->set_time_zone(&gettimezone($timezone));
-   }
-   #### END # Speed up if this function is called often ####
+    # TimeZone tries to determine the 'local' timezone from $ENV{TZ} if this
+    # fails it searches through various system files. Under certain
+    # circumstances this is an extremly expensive operation.
+    # So after the first run we store the timezone in $ENV{TZ} to significantly
+    # speed up future lookups. 
+    $ENV{TZ} = $dt->time_zone()->name() 
+        if (! $ENV{TZ} && gettimezone($timezone) eq 'local');
 
     if ((&current_language=~/^en/) || (!$lh)) {
 
Index: loncom/interface/lonwhatsnew.pm
diff -u loncom/interface/lonwhatsnew.pm:1.92 loncom/interface/lonwhatsnew.pm:1.93
--- loncom/interface/lonwhatsnew.pm:1.92	Mon May  4 21:44:54 2009
+++ loncom/interface/lonwhatsnew.pm	Wed May  6 19:25:56 2009
@@ -1,5 +1,5 @@
 #
-# $Id: lonwhatsnew.pm,v 1.92 2009/05/04 21:44:54 lueken Exp $
+# $Id: lonwhatsnew.pm,v 1.93 2009/05/06 19:25:56 droeschl Exp $
 #
 # Copyright Michigan State University Board of Trustees
 #
@@ -1153,8 +1153,6 @@
 # Check for unread mail in course
     my $msgcount = 0;
 
-    my $datetime;
-
     my @messages = sort(&Apache::lonnet::getkeys('nohist_email'));
     foreach my $message (@messages) {
 	my $msgid=&escape($message);
@@ -1164,7 +1162,7 @@
             if (defined($sendtime) && $sendtime!~/error/) {
                 my $numsendtime = $sendtime;
                 if ($status eq 'new') {
-                $sendtime = &Apache::lonlocal::locallocaltime($sendtime,'',\$datetime);
+                $sendtime = &Apache::lonlocal::locallocaltime($sendtime);
 		    $msgcount ++;
                     if ($shortsubj eq '') {
                         $shortsubj = &mt('No subject');
@@ -1188,7 +1186,6 @@
 # Check for critical messages in course
     my %what=&Apache::lonnet::dump('critical');
     my $result = '';
-    my $datetime;
     my $critmsgcount = 0;
     foreach my $msgid (sort(keys(%what))) {
         my ($sendtime,$shortsubj,$fromname,$fromdom,$status,$fromcid)=
@@ -1196,7 +1193,7 @@
         if (($fromcid) && ($fromcid eq  $env{'request.course.id'})) {
             if (defined($sendtime) && $sendtime!~/error/) {
                 my $numsendtime = $sendtime;
-                $sendtime = &Apache::lonlocal::locallocaltime($sendtime,'',\$datetime);
+                $sendtime = &Apache::lonlocal::locallocaltime($sendtime);
                 $critmsgcount ++;
                 if ($shortsubj eq '') {
                     $shortsubj = &mt('No subject');
@@ -1617,7 +1614,6 @@
 sub display_rolechanges {
     my ($r,$chgcount,$changed,$interval,$crstype) = @_;
     my $now = time();
-    my $datetime;
     my %lt = &Apache::lonlocal::texthash(
         'user'  => 'User',
         'tich'  => 'Time of change',
@@ -1655,7 +1651,7 @@
                             my $link = 
                                 &Apache::loncommon::aboutmewrapper(&Apache::loncommon::plainname($uname,$udom),$uname,$udom);
                             $r->print('<tr'.$css_class.'>'.
-                                      '<td>'.&Apache::lonlocal::locallocaltime($item,'',\$datetime).'</td>'.
+                                      '<td>'.&Apache::lonlocal::locallocaltime($item).'</td>'.
                                       '<td>'.$link.'</td>'.
                                       '<td>'.$role.'</td>'.
                                       '<td>'.$section.'</td>'.