Changeset 4065
- Timestamp:
- 06/09/09 11:34:42 (4 years ago)
- Location:
- trunk/core/lib
- Files:
-
- 16 added
- 7 edited
-
Foswiki.pm (modified) (28 diffs)
-
Foswiki.spec (modified) (1 diff)
-
Foswiki/Cache (added)
-
Foswiki/Cache.pm (added)
-
Foswiki/Cache/BDB.pm (added)
-
Foswiki/Cache/DB_File.pm (added)
-
Foswiki/Cache/FastMmap.pm (added)
-
Foswiki/Cache/FileCache.pm (added)
-
Foswiki/Cache/Memcached.pm (added)
-
Foswiki/Cache/MemcachedFast.pm (added)
-
Foswiki/Cache/MemoryCache.pm (added)
-
Foswiki/Cache/MemoryHash.pm (added)
-
Foswiki/Cache/MemoryLRU.pm (added)
-
Foswiki/Cache/Mmap.pm (added)
-
Foswiki/Cache/SizeAwareFileCache.pm (added)
-
Foswiki/Cache/SizeAwareMemoryCache.pm (added)
-
Foswiki/Cache/TDB_File.pm (added)
-
Foswiki/Meta.pm (modified) (10 diffs)
-
Foswiki/PageCache.pm (added)
-
Foswiki/Render.pm (modified) (5 diffs)
-
Foswiki/Search.pm (modified) (1 diff)
-
Foswiki/UI.pm (modified) (1 diff)
-
Foswiki/UI/View.pm (modified) (2 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/core/lib/Foswiki.pm
r3980 r4065 63 63 use Foswiki::Store (); 64 64 use Foswiki::Users (); 65 use Foswiki::PageCache (); 65 66 66 67 require 5.005; # For regex objects and internationalisation … … 208 209 REMOTE_PORT => \&REMOTE_PORT_deprecated, 209 210 REMOTE_USER => \&REMOTE_USER_deprecated, 210 RENDERHEAD => \&RENDERHEAD,211 211 REVINFO => \&REVINFO, 212 212 REVTITLE => \&REVTITLE, … … 232 232 WIKINAME => \&WIKINAME_deprecated, 233 233 WIKIUSERNAME => \&WIKIUSERNAME_deprecated, 234 DISPLAYDEPENDENCIES => \&DISPLAYDEPENDENCIES, 234 235 235 236 # Constant tag strings _not_ dependent on config. These get nicely … … 639 640 $contentType ||= 'text/html'; 640 641 641 if ( $contentType ne 'text/plain' ) { 642 643 # Remove <nop> and <noautolink> tags 644 $text =~ s/([\t ]?)[ \t]*<\/?(nop|noautolink)\/?>/$1/gis; 645 $text .= "\n" unless $text =~ /\n$/s; 646 647 my $cgis = $this->getCGISession(); 648 if ( $cgis && $contentType eq 'text/html' 649 && $Foswiki::cfg{Validation}{Method} ne 'none') { 650 651 # Don't expire the validation key through login, or when 652 # endpoint is an error. 653 Foswiki::Validation::expireValidationKeys($cgis) 654 unless ( $this->{request}->action() eq 'login' 655 or ( $ENV{REDIRECT_STATUS} || 0 ) >= 400 ); 656 657 my $usingStrikeOne = 0; 658 if ($Foswiki::cfg{Validation}{Method} eq 'strikeone' 659 # Add the onsubmit handler to the form 660 && $text =~ s/(<form[^>]*method=['"]POST['"][^>]*>)/ 661 Foswiki::Validation::addOnSubmit($1)/gei) { 662 # At least one form has been touched; add the validation 663 # cookie 664 $this->{users}->{loginManager}->addCookie( 665 Foswiki::Validation::getCookie( 666 $cgis, $this->{response})); 667 # Add the JS module to the page. Note that this is *not* 668 # incorporated into the foswikilib.js because that module 669 # is conditionally loaded under the control of the 670 # templates, and we have to be *sure* it gets loaded. 671 $this->addToHEAD( 'FOSWIKI STRIKE ONE', 672 <<STRIKEONE); 642 my $cgis = $this->getCGISession(); 643 if ( $cgis && $contentType eq 'text/html' 644 && $Foswiki::cfg{Validation}{Method} ne 'none') { 645 646 # Don't expire the validation key through login, or when 647 # endpoint is an error. 648 Foswiki::Validation::expireValidationKeys($cgis) 649 unless ( $this->{request}->action() eq 'login' 650 or ( $ENV{REDIRECT_STATUS} || 0 ) >= 400 ); 651 652 my $usingStrikeOne = 0; 653 if ($Foswiki::cfg{Validation}{Method} eq 'strikeone' 654 # Add the onsubmit handler to the form 655 && $text =~ s/(<form[^>]*method=['"]POST['"][^>]*>)/ 656 Foswiki::Validation::addOnSubmit($1)/gei) { 657 658 # At least one form has been touched; add the validation 659 # cookie 660 $this->{users}->{loginManager}->addCookie( 661 Foswiki::Validation::getCookie( 662 $cgis, $this->{response})); 663 # Add the JS module to the page. Note that this is *not* 664 # incorporated into the foswikilib.js because that module 665 # is conditionally loaded under the control of the 666 # templates, and we have to be *sure* it gets loaded. 667 $this->addToHEAD( 'FOSWIKI STRIKE ONE', 668 <<STRIKEONE); 673 669 <script type="text/javascript" src="$Foswiki::cfg{PubUrlPath}/$Foswiki::cfg{SystemWebName}/JavascriptFiles/strikeone.js"></script> 674 670 STRIKEONE 675 $usingStrikeOne = 1; 676 } 677 # Inject validation key in HTML forms 678 my $context = 679 $this->{request}->url( -full => 1, -path => 1, -query => 1 ) 680 . time(); 681 $text =~ s/(<form[^>]*method=['"]POST['"][^>]*>)/ 682 $1 . Foswiki::Validation::addValidationKey( 683 $cgis, $context, $usingStrikeOne )/gei; 684 } 685 my $htmlHeader = join( "\n", 686 map { '<!--' . $_ . '-->' . $this->{_HTMLHEADERS}{$_} } 687 keys %{ $this->{_HTMLHEADERS} } ); 688 $text =~ s!(</head>)!$htmlHeader$1!i if $htmlHeader; 689 chomp($text); 690 } 691 692 $this->generateHTTPHeaders( $pageType, $contentType ); 693 my $hdr = $this->{response}->printHeaders; 671 $usingStrikeOne = 1; 672 } 673 674 # Inject validation key in HTML forms 675 my $context = 676 $this->{request}->url( -full => 1, -path => 1, -query => 1 ) 677 . time(); 678 $text =~ s/(<form[^>]*method=['"]POST['"][^>]*>)/ 679 $1 . Foswiki::Validation::addValidationKey( 680 $cgis, $context, $usingStrikeOne )/gei; 681 } 682 683 my $htmlHeader = _genHeaders($this); 684 unless ($text =~ s/%RENDERHEAD%/$htmlHeader/g) { 685 # fallback if there's no RENDERHEAD in the skin 686 $text =~ s!(</head>)!$htmlHeader$1!i if $htmlHeader; 687 } 688 chomp($text); 689 690 # SMELL: can't compute; faking content-type for backwards compatibility; 691 # any other information might become bogus later anyway 692 my $hdr = "Content-type: ".$contentType."\r\n"; 694 693 695 694 # Call final handler 696 $this->{plugins}->dispatch( 'completePageHandler', $text, $hdr ); 695 $this->{plugins}->dispatch('completePageHandler', $text, $hdr); 696 697 # cache final page, but only view 698 my $cachedPage; 699 if ($this->inContext('view') && $Foswiki::cfg{Cache}{Enabled}) { 700 $cachedPage = $this->{cache}->cachePage($contentType, $text); 701 $this->{cache}->renderDirtyAreas(\$text) if $cachedPage->{isDirty}; 702 } else { 703 # remove <dirtyarea> tags 704 $text =~ s/<\/?dirtyarea[^>]*>//go; 705 } 706 707 # Remove <nop> and <noautolink> tags 708 $text =~ s/([\t ]?)[ \t]*<\/?(nop|noautolink)\/?>/$1/gis; 709 710 $this->generateHTTPHeaders( $pageType, $contentType, $text, $cachedPage ); 711 712 # SMELL: null operation. the http headers are written out during Foswiki::Engine::finalize 713 #$hdr = $this->{response}->printHeaders; 697 714 698 715 $this->{response}->print($text); … … 701 718 =begin TML 702 719 703 ---++ ObjectMethod generateHTTPHeaders( $pageType, $contentType ) -> $header720 ---++ ObjectMethod generateHTTPHeaders( $pageType, $contentType, $text, $cachedPage ) 704 721 705 722 All parameters are optional. … … 707 724 * =$pageType= - May be "edit", which will cause headers to be generated that force caching for 24 hours, to prevent Codev.BackFromPreviewLosesText bug, which caused data loss with IE5 and IE6. 708 725 * =$contentType= - page content type | text/html 726 * =$text= - page content 727 * =$cachedPage= - a pointer to the page container as fetched from the page cache 709 728 710 729 =cut 711 730 712 731 sub generateHTTPHeaders { 713 my ( $this, $pageType, $contentType ) = @_; 732 my( $this, $pageType, $contentType, $text, $cachedPage ) = @_; 733 734 my $hopts = {}; 714 735 715 736 # Handle Edit pages - future versions will extend to caching 716 737 # of other types of page, with expiry time driven by page type. 717 my ( $pluginHeaders, $coreHeaders );718 719 my $hopts = {};720 721 738 if ( $pageType && $pageType eq 'edit' ) { 722 739 … … 743 760 # DEPRECATED plugins header handler. Plugins should use 744 761 # modifyHeaderHandler instead. 745 $pluginHeaders =762 my $pluginHeaders = 746 763 $this->{plugins}->dispatch( 'writeHeaderHandler', $this->{request} ) 747 764 || ''; … … 770 787 # add cookie(s) 771 788 $this->{users}->{loginManager}->modifyHeader($hopts); 789 790 # add http compression and conditional cache controls 791 if (!$this->inContext('command_line') && $text) { 792 793 my $contentEncodingHdr = ''; 794 if ($Foswiki::cfg{Cache}{Enabled} && 795 $Foswiki::cfg{Cache}{Compress}) { 796 # compress 797 if ($ENV{'HTTP_ACCEPT_ENCODING'} && 798 $ENV{'HTTP_ACCEPT_ENCODING'} =~ /(x-gzip|gzip)/i) { 799 my $encoding = $1; 800 801 # check if we take the compressed version from the cache 802 if ($cachedPage && !$cachedPage->{isDirty}) { 803 $text = $cachedPage->{text}; 804 } else { 805 806 # well, then compress it now 807 if (!$cachedPage || $cachedPage->{isDirty}) { 808 require Compress::Zlib; 809 $text = Compress::Zlib::memGzip($text); 810 #print STDERR "compressing\n"; 811 } 812 } 813 814 $hopts->{'Content-Encoding'} = $encoding; 815 $hopts->{'Vary'} = 'Accept-Encoding'; 816 817 } else { 818 if ($cachedPage && !$cachedPage->{isDirty}) { 819 820 # sorry, we need to uncompressed pages from cache again 821 require Compress::Zlib; 822 $text = Compress::Zlib::memGunzip($text); 823 #print STDERR "uncompressing\n"; 824 } 825 } 826 } else { 827 if ($cachedPage && !$cachedPage->{isDirty}) { 828 $text = $cachedPage->{text} 829 } 830 } 831 832 # we need to force the browser into a check on every 833 # request; let the server decide on an 304 as below 834 $hopts->{'Cache-Control'} = 'max-age=0'; 835 836 # check etag and last modification time 837 # if we have a cached page on the server side 838 if ($cachedPage) { 839 my $etag = $cachedPage->{etag}; 840 my $lastModified = $cachedPage->{lastModified}; 841 842 $hopts->{'ETag'} = $etag; 843 $hopts->{'Last-Modified'} = $lastModified; 844 845 # only send a 304 if both criteria are true 846 my $etagFlag = 1; 847 my $lastModifiedFlag = 1; 848 849 # check etag 850 unless ($ENV{'HTTP_IF_NONE_MATCH'} && 851 $etag eq $ENV{'HTTP_IF_NONE_MATCH'}) { 852 $etagFlag = 0; 853 } 854 855 # check last-modified 856 unless ($ENV{'HTTP_IF_MODIFIED_SINCE'} && 857 $lastModified eq $ENV{'HTTP_IF_MODIFIED_SINCE'}) { 858 $lastModifiedFlag = 0; 859 } 860 861 # finally decide on a 304 reply 862 if ($etagFlag && $lastModified) { 863 $hopts->{'Status'} = '304 Not Modified'; 864 $text = ''; 865 #print STDERR "NOT modified\n"; 866 } 867 } 868 869 # write back to text 870 $_[3] = $text; 871 } 872 873 $hopts->{"X-FoswikiAction"} = $this->{request}->action; 874 $hopts->{"X-FoswikiURI"} = $this->{request}->uri; 772 875 773 876 # The headers method resets all headers to what we pass … … 1435 1538 $this->{context} = $initialContext; 1436 1539 1540 $this->{cache} = new Foswiki::PageCache( $this ); 1437 1541 my $prefs = new Foswiki::Prefs($this); 1438 1542 $this->{prefs} = $prefs; … … 1797 1901 $this->{i18n}->finish() if $this->{i18n}; 1798 1902 undef $this->{i18n}; 1903 $this->{cache}->finish() if $this->{cache}; 1799 1904 1800 1905 undef $this->{_HTMLHEADERS}; … … 1852 1957 my $agent = $cgiQuery->user_agent(); 1853 1958 if ($agent) { 1854 if ( $agent =~ m/([\w]+)/ ) { 1855 $extra .= ' ' . $1; 1959 $extra .= ' ' if $extra; 1960 if ( $agent =~ /(MSIE 6|MSIE 7|Firefox|Opera|Konqueror|Safari)/ ) { 1961 $extra .= $1; 1962 } else { 1963 $agent =~ m/([\w]+)/; 1964 $extra .= $1; 1856 1965 } 1857 1966 } … … 2561 2670 2562 2671 my $verbatim = {}; 2563 $text = $this->renderer->takeOutBlocks( $text, 'verbatim', $verbatim ); 2672 $text = $this->renderer->takeOutBlocks( $text, 'verbatim', 2673 $verbatim); 2674 2675 my $dirtyAreas = {}; 2676 $text = $this->renderer->takeOutBlocks( $text, 'dirtyarea', $dirtyAreas) 2677 if $Foswiki::cfg{Cache}{Enabled}; 2678 2564 2679 2565 2680 # See Item1442 … … 2677 2792 #$stackTop =~ s/$percent/%/go; 2678 2793 2794 $this->renderer->putBackBlocks( \$stackTop, $dirtyAreas, 'dirtyarea' ) 2795 if $Foswiki::cfg{Cache}{Enabled}; 2679 2796 $this->renderer->putBackBlocks( \$stackTop, $verbatim, 'verbatim' ); 2680 2797 … … 2812 2929 =begin TML 2813 2930 2814 ---++ ObjectMethod handleCommonTags( $text, $topicObject ) -> $text2931 ---++ ObjectMethod expandMacros( $text, $topicObject ) -> $text 2815 2932 2816 2933 Processes %<nop>VARIABLE%, and %<nop>TOC% syntax; also includes … … 2831 2948 2832 2949 return $text unless $text; 2833 my $verbatim = {};2834 2950 2835 2951 # Plugin Hook (for cache Plugins only) … … 2840 2956 #use a "global var", so included topics can extract and putback 2841 2957 #their verbatim blocks safetly. 2842 $text = $this->renderer->takeOutBlocks( $text, 'verbatim', $verbatim ); 2958 my $verbatim={}; 2959 $text = $this->renderer->takeOutBlocks( $text, 'verbatim', 2960 $verbatim); 2961 2962 # take out dirty areas 2963 my $dirtyAreas = {}; 2964 $text = $this->renderer->takeOutBlocks( $text, 'dirtyarea', $dirtyAreas ) 2965 if $Foswiki::cfg{Cache}{Enabled}; 2966 2843 2967 2844 2968 # Require defaults for plugin handlers :-( … … 2881 3005 $text =~ s/^<nop>\r?\n//gm; 2882 3006 3007 # restore dirty areas 3008 $this->renderer->putBackBlocks( \$text, $dirtyAreas, 'dirtyarea' ) 3009 if $Foswiki::cfg{Cache}{Enabled}; 3010 3011 2883 3012 $this->renderer->putBackBlocks( \$text, $verbatim, 'verbatim' ); 2884 3013 … … 2904 3033 my ( $this, $tag, $header, $requires, $topicObject ) = @_; 2905 3034 3035 return unless $header; # don't add empty or even undef stuff 3036 2906 3037 # Expand macros in the header 2907 3038 $header = $topicObject->expandMacros($header) if $topicObject; 2908 3039 2909 $this->{_ SORTEDHEADS} ||= {};3040 $this->{_HTMLHEADERS} ||= {}; 2910 3041 $tag ||= ''; 2911 3042 … … 2916 3047 my @requires; 2917 3048 foreach my $req ( split( /,\s*/, $requires ) ) { 2918 unless ( $this->{_ SORTEDHEADS}->{$req} ) {2919 $this->{_ SORTEDHEADS}->{$req} = {3049 unless ( $this->{_HTMLHEADERS}->{$req} ) { 3050 $this->{_HTMLHEADERS}->{$req} = { 2920 3051 tag => $req, 2921 3052 requires => [], … … 2923 3054 }; 2924 3055 } 2925 push( @requires, $this->{_ SORTEDHEADS}->{$req} );2926 } 2927 my $record = $this->{_ SORTEDHEADS}->{$tag};3056 push( @requires, $this->{_HTMLHEADERS}->{$req} ); 3057 } 3058 my $record = $this->{_HTMLHEADERS}->{$tag}; 2928 3059 unless ($record) { 2929 3060 $record = { tag => $tag }; 2930 $this->{_ SORTEDHEADS}->{$tag} = $record;3061 $this->{_HTMLHEADERS}->{$tag} = $record; 2931 3062 } 2932 3063 $record->{requires} = \@requires; 2933 3064 $record->{header} = $header; 2934 2935 # Temporary, for compatibility until %RENDERHEAD% is embedded2936 # in the skins2937 $this->{_HTMLHEADERS}{GENERATED_HEADERS} = _genHeaders($this);2938 3065 } 2939 3066 … … 2950 3077 sub _genHeaders { 2951 3078 my ($this) = @_; 2952 return '' unless $this->{_ SORTEDHEADS};3079 return '' unless $this->{_HTMLHEADERS}; 2953 3080 2954 3081 # Loop through the vertices of the graph, in any order, initiating … … 2963 3090 my %visited; 2964 3091 my @total; 2965 foreach my $v ( values %{ $this->{_ SORTEDHEADS} } ) {3092 foreach my $v ( values %{ $this->{_HTMLHEADERS} } ) { 2966 3093 _visit( $v, \%visited, \@total ); 2967 3094 } 2968 3095 2969 3096 return join( "\n", map { "<!-- $_->{tag} --> $_->{header}" } @total ); 2970 }2971 2972 =begin TML2973 2974 ---+++ %<nop}RENDERHEAD%2975 =%RENDERHEAD%= should be written where you want the sorted head tags to be generated. This will normally be in a template. The variable expands to a sorted list of the head blocks added up to the point the RENDERHEAD variable is expanded. Each expanded head block is preceded by an HTML comment that records the ID of the head block.2976 2977 Head blocks are sorted to satisfy all their =requires= constraints.2978 The output order of blocks with no =requires= value is undefined. If cycles2979 exist in the dependency order, the cycles will be broken but the resulting2980 order of blocks in the cycle is undefined.2981 2982 =cut2983 2984 sub RENDERHEAD {2985 my $this = shift;2986 return _genHeaders($this);2987 3097 } 2988 3098 … … 3317 3427 # local (SESSION) macro definitions without polluting the including 3318 3428 # topic namespace. 3319 $this->{prefs}->pushTopicContext( $ includedWeb, $includedTopic);3429 $this->{prefs}->pushTopicContext( $this->{webName}, $this->{topicName} ); 3320 3430 3321 3431 $this->{_INCLUDES}->{$key} = 1; … … 3333 3443 my $memTopic = $this->{prefs}->getPreference('INCLUDINGTOPIC'); 3334 3444 3445 my $dirtyAreas = {}; 3335 3446 try { 3336 3447 … … 3359 3470 $text =~ s/%STOPINCLUDE%.*//s; 3360 3471 } 3472 3473 # prevent dirty areas in included topics from being parsed 3474 $text = $this->renderer->takeOutBlocks( $text, 'dirtyarea', $dirtyAreas) 3475 if $Foswiki::cfg{Cache}{Enabled}; 3361 3476 3362 3477 # handle sections … … 3447 3562 INCLUDINGTOPIC => $memTopic 3448 3563 ); 3564 3565 # restoring dirty areas 3566 $this->renderer->putBackBlocks( \$text, $dirtyAreas, 'dirtyarea' ) 3567 if $Foswiki::cfg{Cache}{Enabled}; 3449 3568 3450 3569 ( $this->{webName}, $this->{topicName} ) = … … 4134 4253 sub META { 4135 4254 my ( $this, $params, $topicObject ) = @_; 4255 4256 $topicObject->reload() unless $topicObject->getLoadedRev(); 4136 4257 4137 4258 my $option = $params->{_DEFAULT} || ''; … … 4312 4433 4313 4434 return '| *Group* | *Members* |' . "\n" . join( "\n", sort @table ); 4435 } 4436 4437 sub DISPLAYDEPENDENCIES { 4438 my ( $this, $params ) = @_; 4439 4440 my $web = $params->{web} || $this->{webName}; 4441 my $topic = $params->{topic} || $this->{topicName}; 4442 my $header = $params->{header} || ''; 4443 my $footer = $params->{footer} || ''; 4444 my $format = $params->{format} || ' 1 [[$web.$topic]]'; 4445 my $separator = $params->{sep} || $params->{separator} || "\n"; 4446 my $exclude = $params->{exclude}; 4447 4448 ($web, $topic) = $this->normalizeWebTopicName($web, $topic); 4449 4450 my $deps = $this->{cache}->getDependencies($web, $topic); 4451 my @lines; 4452 my $thisWeb; 4453 my $thisTopic; 4454 foreach my $dep (sort @$deps) { 4455 next if $exclude && $dep =~ /$exclude/; 4456 $dep =~ /^(.*)[\.\/](.*?)$/; 4457 $thisWeb = $1; 4458 $thisTopic = $2; 4459 my $text = $format; 4460 $text =~ s/\$web/$thisWeb/g; 4461 $text =~ s/\$topic/$thisTopic/g; 4462 push @lines, $text; 4463 } 4464 return '' unless @lines; 4465 return expandStandardEscapes($header.join($separator, @lines).$footer); 4314 4466 } 4315 4467 -
trunk/core/lib/Foswiki.spec
r4036 r4065 1000 1000 $Foswiki::cfg{UsersWebName} = 'Main'; 1001 1001 1002 #---+ Cache settings 1003 1004 #---++ Enable page caching 1005 # This setting will switch on/off caching of html pages rendered by a view action. 1006 # This can dramatically increase performance, i.e. if there are a lot more 1007 # page views than changes. 1008 # **BOOLEAN** 1009 $Foswiki::cfg{Cache}{Enabled} = $FALSE; 1010 1011 #---++ Cache namespace 1012 # Specify the namespace used by this site in a store shared with other systems. 1013 # Leave this empty to use the <code>DefaultUrlHost</code> as a default. 1014 $Foswiki::cfg{Cache}{NameSpace} = ''; 1015 1016 #---++ CacheManager for PageCache 1017 # Select the default caching mechanism. Note, that individual subsystems might 1018 # chose a different backend for their own purposes. Some recommendations: 1019 # <ul> 1020 # <li>Use <code>Foswiki::Cache::FileCache</code> for long term 1021 # caching. Cached pages will be stored on disk.</li> 1022 # <li>Use <code>Foswiki::Cache::Memcached</code> for distributed caching 1023 # on high end sites</li> 1024 # <li>Use <code>Foswiki::Cache::MemoryLRU</code> for an in-memory LRU cache. 1025 # Note that this CacheManager will only keep pages during one call or for 1026 # the time of a perl persistent backend.</li> 1027 # </ul> 1028 # **SELECTCLASS none,Foswiki::Cache::*** 1029 $Foswiki::cfg{CacheManager} = 'Foswiki::Cache::FileCache'; 1030 1031 #---++ CacheRoot directory 1032 # Specify the root directory for CacheManagers with a file-system based storage 1033 # **PATH** 1034 $Foswiki::cfg{Cache}{RootDir} = '/tmp/cache'; 1035 1036 #---++ DB_File 1037 # Specify the database file for the <code>Foswiki::Cache::DB_File</code> 1038 # CacheManager 1039 $Foswiki::cfg{Cache}{DBFile} = '/tmp/foswiki_db'; 1040 1041 #---++ MaxSize 1042 # Specify the maximum number of cache entries for size-aware CacheManagers like 1043 # <code>MemoryLRU</code>. This won't have any effect on other CacheManagers. 1044 $Foswiki::cfg{Cache}{MaxSize} = 1000; 1045 1046 #---++ Cache Servers 1047 # Specify a comma separated list of servers for distributed CacheManagers like 1048 # <code>Memcached</code>. This setting won't have any effect on other CacheManagers. 1049 # **STRING 30** 1050 $Foswiki::cfg{Cache}{Servers} = '127.0.0.1:11211'; 1051 1002 1052 #---+ Mail and Proxies 1003 1053 # **BOOLEAN** -
trunk/core/lib/Foswiki/Meta.pm
r3965 r4065 315 315 my $this = shift; 316 316 if ( defined $this->{_topic} ) { 317 318 # only checking for a topic existence already establishes a dependency 319 $this->addDependency(); 320 317 321 return $this->{_session}->{store} 318 322 ->topicExists( $this->{_web}, $this->{_topic} ); … … 345 349 return $s; 346 350 } 351 352 =begin TML 353 354 ---++ ObjectMethod addDependency() -> $this 355 356 This establishes a dependency between $this and the 357 base topic this session is currently rendering. The dependency 358 will be asserted during Foswiki::PageCache::cachePage(). 359 See Foswiki::PageCache::addDependency(). 360 361 =cut 362 363 sub addDependency { 364 my $cache = $_[0]->{_session}->{cache}; 365 return unless $cache; 366 return $cache->addDependency( 367 $_[0]->{_web}, $_[0]->{_topic}); 368 } 369 370 =begin TML 371 372 ---++ ObjectMethod fireDependency() -> $this 373 374 Invalidates the cache bucked of the current meta object 375 within the Foswiki::PageCache. See Foswiki::PageCache::fireDependency(). 376 377 =cut 378 379 sub fireDependency { 380 return $_[0]->{_session}->{cache}->fireDependency( 381 $_[0]->{_web}, $_[0]->{_topic}); 382 } 383 347 384 348 385 ############# WEB METHODS ############# … … 607 644 $this->{_preferences}->finish() if defined $this->{_preferences}; 608 645 $this->{_preferences} = undef; 646 647 $this->addDependency(); 609 648 } 610 649 … … 881 920 882 921 if ($type) { 922 return if $type =~ /^_/; 883 923 my @data; 884 924 foreach my $item ( @{ $other->{$type} } ) { … … 1451 1491 finally { 1452 1492 $this->_atomicUnlock($cUID); 1493 $this->fireDependency(); 1453 1494 }; 1454 1495 } … … 1544 1585 $this->_atomicUnlock($cUID); 1545 1586 $to->_atomicUnlock($cUID); 1587 $this->fireDependency(); 1588 $to->fireDependency(); 1546 1589 }; 1547 1590 … … 1958 2001 $error = shift; 1959 2002 }; 2003 finally { 2004 $this->fireDependency(); 2005 }; 1960 2006 1961 2007 my $fileVersion = $this->getMaxRevNo( $opts{name} ); … … 2048 2094 my ( $this, $attachment, $test ) = @_; 2049 2095 2096 $this->addDependency(); 2097 2050 2098 $test =~ /(\w)/; 2051 2099 $test = $1; … … 2125 2173 $to->_atomicUnlock($cUID); 2126 2174 $this->_atomicUnlock($cUID); 2175 $this->fireDependency(); 2176 $to->fireDependency(); 2127 2177 }; 2128 2178 … … 2423 2473 2424 2474 foreach my $type (@types) { 2475 next if $type eq '_session'; 2425 2476 my $data = $this->{$type}; 2426 2477 foreach my $item (@$data) { -
trunk/core/lib/Foswiki/Render.pm
r3947 r4065 458 458 # $anchorName is a *byte* string. If it contains any wide characters 459 459 # the encoding algorithm will not work. 460 #ASSERT($text !~ /[^\x00-\xFF]/) if DEBUG; 461 $text =~ s/[^\x00-\xFF]//g; 460 462 ASSERT( $text !~ /[^\x00-\xFF]/ ) if DEBUG; 463 464 # remove HTML tags and entities 465 $text =~ s/<\/?[a-zA-Z][^>]*>//gi; 466 $text =~ s/&#?[a-zA-Z0-9]+;//g; 467 468 # remove spaces 469 $text =~ s/\s+/_/g; 461 470 462 471 # use _ as an escape character to escape any byte outside the 463 472 # range specified by http://www.w3.org/TR/html401/struct/links.html 464 $text =~ s/([^A-Za-z0-9:.])/'_'.sprintf('%02d', ord($1))/ge; 473 $text =~ s/([^A-Za-z0-9:._])/'_'.sprintf('%02d', ord($1))/ge; 474 475 # clean up a bit 476 $text =~ s/__/_/g; 477 $text =~ s/^_*(.*?)_*$/$1/; 465 478 466 479 # Ensure the anchor always starts with an [A-Za-z] 467 $text = 'A ' . $text;480 $text = 'A_'.$text unless $text =~ /^[A-Za-z]/; 468 481 469 482 return $text; … … 611 624 612 625 if ($topicExists) { 626 # add a dependency so that the page gets invalidated as soon as the 627 # topic is deleted 628 $this->{session}->{cache}->addDependency($web, $topic) 629 if $Foswiki::cfg{Cache}{Enabled}; 630 613 631 return _renderExistingWikiWord( $this, $web, $topic, $linkText, 614 632 $anchor ); … … 620 638 # #unshift( @topics, $singular); 621 639 # } 640 641 # add a dependency so that the page gets invalidated as soon as the 642 # WikiWord comes into existance 643 $this->{session}->{cache}->addDependency($web, $topic) 644 if $Foswiki::cfg{Cache}{Enabled}; 645 622 646 return _renderNonExistingWikiWord( $this, $web, $topic, $linkText ); 623 647 } … … 974 998 $text = $this->takeOutBlocks( $text, 'verbatim', $removed ); 975 999 $text = $this->takeOutBlocks( $text, 'literal', $removed ); 1000 $text = $this->takeOutBlocks( $text, 'dirtyarea', $removed ) 1001 if $Foswiki::cfg{Cache}{Enabled}; 976 1002 977 1003 $text = … … 1268 1294 $this->_putBackProtected( \$text, 'script', $removed, \&_filterScript ); 1269 1295 $this->putBackBlocks( \$text, $removed, 'literal', '', \&_filterLiteral ); 1270 1271 1296 $this->_putBackProtected( \$text, 'literal', $removed ); 1297 $this->putBackBlocks( \$text, $removed, 'dirtyarea' ) 1298 if $Foswiki::cfg{Cache}{Enabled}; 1272 1299 $this->_putBackProtected( \$text, 'comment', $removed ); 1273 1300 $this->_putBackProtected( \$text, 'head', $removed ); -
trunk/core/lib/Foswiki/Search.pm
r4024 r4065 465 465 my $infoCache = $webObject->query( $query, $inputTopicSet, $options ); 466 466 $this->sortResults( $web, $infoCache, %params ); 467 468 # add dependencies 469 my $cache = $session->{cache}; 470 if ($cache) { 471 foreach my $topic ( $infoCache->{list} ) { 472 $cache->addDependency($web, $topic); 473 } 474 } 475 467 476 my ( $web_ttopics, $web_searchResult ); 468 477 ( $web_ttopics, $web_searchResult, $tmplTail ) = -
trunk/core/lib/Foswiki/UI.pm
r4036 r4065 298 298 my $res = $session->{response}; 299 299 300 $res->pushHeader( 'X-FoswikiAction' => $req->action() );301 $res->pushHeader( 'X-FoswikiURI' => $req->uri() );302 303 300 unless ( defined $session->{response}->status() 304 301 && $session->{response}->status() =~ /^\s*3\d\d/ ) -
trunk/core/lib/Foswiki/UI/View.pm
r3947 r4065 47 47 my $web = $session->{webName}; 48 48 my $topic = $session->{topicName}; 49 50 my $fire = $query->param('firedependency') || ''; 51 my $cachedPage; 52 my $cache = $session->{cache}; 53 if ($cache) { 54 if ($fire eq 'on') { 55 $cache->fireDependency($web, $topic); 56 } else { 57 $cachedPage = $cache->getPage($web, $topic); 58 } 59 } 60 if ($cachedPage) { 61 print STDERR "found $web.$topic in cache\n" if $Foswiki::cfg{Cache}{Debug}; 62 Monitor::MARK("found page in cache"); 63 64 # render uncacheable areas 65 my $text = $cachedPage->{text}; 66 $session->{cache}->renderDirtyAreas(\$text) if $cachedPage->{isDirty}; 67 68 # compute headers 69 my $contentType = $cachedPage->{contentType}; 70 $session->generateHTTPHeaders('view', $contentType, $text, $cachedPage); 71 $session->{response}->print($text); 72 73 Monitor::MARK('Wrote HTML'); 74 if ($Foswiki::cfg{Log}{view}) { 75 $session->logEvent('view', $web . '.' . $topic, '(cached)' ); 76 } 77 return; 78 } 79 80 print STDERR "computing page for $web.$topic\n" if $Foswiki::cfg{Cache}{Debug}; 49 81 50 82 my $raw = $query->param('raw') || ''; … … 398 430 $text = $topicObject->expandMacros($text); 399 431 $text = $topicObject->renderTML($text); 400 $text =~ s/( ?) *<\/?(nop|noautolink)\/?>\n?/$1/gois;401 432 402 433 if ($minimalist) {
Note: See TracChangeset
for help on using the changeset viewer.
