Index: /branches/release-36/php/lib/function.mtinclude.php
===================================================================
--- /branches/release-36/php/lib/function.mtinclude.php (revision 1554)
+++ /branches/release-36/php/lib/function.mtinclude.php (revision 2104)
@@ -24,42 +24,9 @@
     }
 
-    static $_include_cache = array();
     $blog_id = $args['blog_id'];
     $blog_id or $blog_id = $ctx->stash('blog_id');
-    $cache_id = '';
-
-    # Try to read from cache
-    global $mt;
-
-    $cache_enable = false;
-    $cacje_key = '';
-    $cache_ttl = 0;
     $blog = $ctx->mt->db->fetch_blog($blog_id);
 
-    if ((isset($args['module']) || isset($args['widget']) || isset($args['identifier']))
-        && $blog['blog_include_cache'] == 1
-        && ((isset($args['cache']) && $args['cache'] == '1') || isset($args['key']) || isset($args['ttl'])) )
-    {
-        $tmpl_name = $args['module'];
-        $tmpl_name or $tmpl_name = $args['widget'];
-        $tmpl_name or $tmpl_name = $args['identifier'];
-        $type = $args['Widget'] ? 'widget' : 'custom';
-        if ($type == 'custom' && preg_match('/^Widget:/', $tmpl_name))
-            $type = 'widget';
-
-
-        $cache_enable = true;
-        $cache_key = isset($args['key'])
-            ? $args['key']
-            : 'blog::' . $blog_id . '::template_' . $type  . '::' . $tmpl_name;
-        $cache_ttl = isset($args['ttl']) ? $args['ttl'] : 60 * 60; # default 60 min.
-
-
-        $cache_driver = $mt->cache_driver($cache_ttl);
-        $cached_val = $cache_driver->get($cache_key, $cache_ttl);
-        if (!empty($cached_val))
-            return $cached_val;
-    }
-
+    // When the module name starts by 'Widget', it converts to 'Widget' from 'Module'.
     if (isset($args['module']) && ($args['module'])) {
         $module = $args['module'];
@@ -69,84 +36,149 @@
         }
     }
-    if (isset($args['module']) && ($args['module'])) {
-        $module = $args['module'];
-        $cache_id = 'module::' . $blog_id . '::' . $module;
+
+    // Fetch template meta data
+    $load_type = null;
+    $load_name = null;
+    if (isset($args['module'])) {
+        $load_type = 'custom';
+        $load_name = $args['module'];
+    } elseif (isset($args['widget'])) {
+        $load_type = 'widget';
+        $load_name = $args['widget'];
+    } elseif (isset($args['identifier'])) {
+        $load_type = 'identifier';
+        $load_name = $args['identifier'];
+    }
+
+    $tmpl_meta = array();
+    if (!empty($load_type)) {
+        $is_global = isset($args['global']) && $args['global'] ? 1 : 0;
+        $tmpl_meta = $ctx->mt->db->fetch_template_meta($load_type, $load_name, $blog_id, $is_global);
+    }
+
+    # Convert to phrase of PHP Include
+    $ssi_enable = false;
+    $include_file = '';
+    if (!empty($load_type) &&
+        isset($blog) && $blog['blog_include_system'] == 'php' &&
+        ((isset($args['ssi']) && $args['ssi']) || (isset($tmpl_meta['include_with_ssi']) && $tmpl_meta['include_with_ssi']))) {
+
+        $ssi_enable = true;
+
+        // Generates include path using Key
+        $base_path = '';
+        if (isset($args['key'])) {
+            $base_path = $args['key'];
+        } elseif(isset($args['cache_key'])) {
+            $base_path or $base_path = $args['cache_key'];
+        }
+        $include_path_array = _include_path($base_path);
+
+        require_once('MTUtil.php');
+        $filename = dirify($tmpl_meta['template_name']);
+        $filename or $filename = 'template_' . $tmpl_meta['template_id'];
+        $filename .= '.'.$blog['blog_file_extension'];
+
+        $include_path = $blog['blog_site_path'];
+        if (substr($include_path, strlen($include_path) - 1, 1) != DIRECTORY_SEPARATOR)
+            $include_path .= DIRECTORY_SEPARATOR;
+        foreach ($include_path_array as $p) {
+            $include_path .= $p . DIRECTORY_SEPARATOR;
+        }
+        $include_file = $include_path . $filename;
+    }
+
+    # Try to read from cache
+    $cache_enable = false;
+    $cache_id = '';
+    $cacje_key = '';
+    $cache_ttl = 0;
+    if (!empty($load_type) &&
+        isset($blog) && $blog['blog_include_cache'] == 1 &&
+        ((isset($tmpl_meta['cache_expire_type']) && ($tmpl_meta['cache_expire_type'] == '1' || $tmpl_meta['cache_expire_type'] == '2')) ||
+         ((isset($args['cache']) && $args['cache'] == '1') || isset($args['key']) || isset($args['cache_key']) || isset($args['ttl']))))
+    {
+        global $mt;
+        $cache_enable = true;
+        $cache_key = isset($args['key'])
+            ? $args['key']
+            : isset($args['cache_key'])
+                ? $args['cache_key']
+                : 'blog::' . $blog_id . '::template_' . $load_type  . '::' . $load_name;
+
+        if (isset($args['ttl']))
+            $cache_ttl = $args['ttl'];
+        elseif (isset($tmpl_meta['cache_expire_type']) && $tmpl_meta['cache_expire_type'] == '1')
+            $cache_ttl = $tmpl_meta['cache_expire_interval'];
+        else
+            $cache_ttl = 60 * 60; # default 60 min.
+
+        if (isset($tmpl_meta['cache_expire_type']) && $tmpl_meta['cache_expire_type'] == '2') {
+            $expire_types = preg_split('/,/', $tmpl_meta['cache_expire_event'], -1, PREG_SPLIT_NO_EMPTY);
+            if (!empty($expire_types)) {
+                $latest = $ctx->mt->db->get_latest_touch($blog_id, $expire_types);
+                if ($latest) {
+                    if ($ssi_enable) {
+                        $file_stat = stat($include_file);
+                        if ($file_stat) {
+                            $file_stamp = gmdate("Y-m-d H:i:s", $file_stat[9]);
+                            if (strtotime($latest) > strtotime($file_stamp))
+                                $cache_ttl = 1;
+                        }
+                    } else {
+                      $cache_ttl = time() - strtotime($latest);
+                    }
+                }
+            }
+        }
+
+        if ($cache_ttl == 0 || (time() - strtotime($tmpl_meta['template_modified_on']) < $cache_ttl)) {
+            $cache_ttl = time() - strtotime($tmpl_meta['template_modified_on']);
+        }
+
+        $cache_driver = $mt->cache_driver($cache_ttl);
+        $cached_val = $cache_driver->get($cache_key, $cache_ttl);
+        if (!empty($cached_val)) {
+            _clear_vars($ctx, $ext_args);
+            if ($ssi_enable) {
+                if (file_exists($include_file) && is_readable($include_file)) {
+                  $content = file_get_contents($include_file);
+                  if ($content)
+                      return $content;
+                }
+            } else {
+                return $cached_val;
+            }
+        }
+    }
+
+    # Compile template
+    static $_include_cache = array();
+    $_var_compiled = '';
+
+    if (!empty($load_type)) {
+        $cache_id = $load_type . '::' . $blog_id . '::' . $load_name;
         if (isset($_include_cache[$cache_id])) {
             $_var_compiled = $_include_cache[$cache_id];
         } else {
-            $tmpl = $ctx->mt->db->get_template_text($ctx, $module, $blog_id, 'custom', $args['global']);
-            if ($ctx->_compile_source('evaluated template', $tmpl, $_var_compiled)) {
-                $_include_cache[$cache_id] = $_var_compiled;
-            } else {
+            $tmpl = $ctx->mt->db->get_template_text($ctx, $load_name, $blog_id, $load_type, $args['global']);
+            if (!$ctx->_compile_source('evaluated template', $tmpl, $_var_compiled)) {
                 _clear_vars($ctx, $ext_args);
                 return $ctx->error("Error compiling template module '$module'");
             }
-        }
-    } elseif (isset($args['widget']) && ($args['widget'])) {
-        $module = $args['widget'];
-        $cache_id = 'widget::' . $blog_id . '::' . $module;
-        if (isset($_include_cache[$cache_id])) {
-            $_var_compiled = $_include_cache[$cache_id];
-        } else {
-            $tmpl = $ctx->mt->db->get_template_text($ctx, $module, $blog_id, 'widget', $args['global']);
-            if ($ctx->_compile_source('evaluated template', $tmpl, $_var_compiled)) {
-                $_include_cache[$cache_id] = $_var_compiled;
-            } else {
-                _clear_vars($ctx, $ext_args);
-                return $ctx->error("Error compiling template module '$module'");
-            }
-        }
-    } elseif (isset($args['identifier']) && ($args['identifier'])) {
-        $module = $args['identifier'];
-        $cache_id = 'identifier::' . $blog_id . '::' . $module;
-        if (isset($_include_cache[$cache_id])) {
-            $_var_compiled = $_include_cache[$cache_id];
-        } else {
-            $tmpl = $ctx->mt->db->get_template_text($ctx, $module, $blog_id, '', $args['global']);
-            if ($ctx->_compile_source('evaluated template', $tmpl, $_var_compiled)) {
-                $_include_cache[$cache_id] = $_var_compiled;
-            } else {
-                _clear_vars($ctx, $ext_args);
-                return $ctx->error("Error compiling template module '$module'");
-            }
+            $_include_cache[$cache_id] = $_var_compiled;
         }
     } elseif (isset($args['file']) && ($args['file'])) {
         $file = $args['file'];
-        $base_filename = basename($file);
-        global $restricted_include_filenames;
-        if (array_key_exists(strtolower($base_filename), $restricted_include_filenames)) {
-            _clear_vars($ctx, $ext_args);
-            return "";
-        }
         $cache_id = 'file::' . $blog_id . '::' . $file;
         if (isset($_include_cache[$cache_id])) {
             $_var_compiled = $_include_cache[$cache_id];
         } else {
-            if (is_file($file) && is_readable($file)) {
-                $contents = @file($file);
-                $tmpl = implode('', $contents);
-            } else {
-                $blog = $ctx->stash('blog');
-                if ($blog['blog_id'] != $blog_id) {
-                    $blog = $ctx->mt->db->fetch_blog($blog_id);
-                }
-                $path = $blog['blog_site_path'];
-                if (!preg_match('!/$!', $path))
-                    $path .= '/';
-                $path .= $file;
-                if (is_file($path) && is_readable($path)) {
-                    $contents = @file($path);
-                    $tmpl = implode('', $contents);
-                } else {
-                    _clear_vars($ctx, $ext_args);
-                    return $ctx->error("Could not open file '$file'");
-                }
-            }
-            if ($ctx->_compile_source('evaluated template', $tmpl, $_var_compiled)) {
-                $_include_cache[$cache_id] = $_var_compiled;
-            } else {
+            $tmpl = _get_template_from_file($ctx, $file, $blog_id);
+            if (!$ctx->_compile_source('evaluated template', $tmpl, $_var_compiled)) {
                 _clear_vars($ctx, $ext_args);
                 return $ctx->error("Error compiling template file '$file'");
             }
+            $_include_cache[$cache_id] = $_var_compiled;
         }
     } elseif (isset($args['type']) && ($args['type'])) {
@@ -188,5 +220,47 @@
     }
 
+    if ($ssi_enable) {
+        $include_dir = dirname($include_file);
+        if (!file_exists($include_dir) && !is_dir($include_dir)) {
+            mkdir($include_dir, 0777, true);
+        }
+        if (is_writable($include_dir)) {
+            if ($h_file = fopen($include_file, 'w')) {
+                fwrite($h_file, $_contents);
+                fclose($h_file);
+            }
+        }
+    }
+
     return $_contents;
+}
+
+function _get_template_from_file ($ctx, $file, $blog_id) {
+    $base_filename = basename($file);
+    global $restricted_include_filenames;
+    if (array_key_exists(strtolower($base_filename), $restricted_include_filenames)) {
+        return '';
+    }
+    if (is_file($file) && is_readable($file)) {
+        $contents = @file($file);
+        $tmpl = implode('', $contents);
+    } else {
+        $blog = $ctx->stash('blog');
+        if ($blog['blog_id'] != $blog_id) {
+            $blog = $ctx->mt->db->fetch_blog($blog_id);
+        }
+        $path = $blog['blog_site_path'];
+        if (!preg_match('!/$!', $path))
+            $path .= '/';
+        $path .= $file;
+        if (is_file($path) && is_readable($path)) {
+            $contents = @file($path);
+            $tmpl = implode('', $contents);
+        } else {
+            return false;
+        }
+    }
+
+    return $tmpl;
 }
 
@@ -199,3 +273,15 @@
     $ctx->__stash['vars'] =& $vars;
 }
+
+function _include_path($path) {
+    $path_array = array();
+    if (preg_match('/^\//', $path)) {
+        $path_array = preg_split('/\//', $path, -1, PREG_SPLIT_NO_EMPTY);
+    } else {
+        $path_array = preg_split('/\//', $path, -1, PREG_SPLIT_NO_EMPTY);
+        global $mt;
+        array_unshift($path_array, $mt->config('IncludesDir'));
+    }
+    return $path_array;
+}
 ?>
Index: /branches/release-36/php/lib/mtdb_base.php
===================================================================
--- /branches/release-36/php/lib/mtdb_base.php (revision 2103)
+++ /branches/release-36/php/lib/mtdb_base.php (revision 2104)
@@ -152,4 +152,40 @@
         $result = $this->get_results($sql, ARRAY_A);
         return $result;
+    }
+
+    function fetch_template_meta($type, $name, $blog_id, $global) {
+        if ($type === 'identifier') {
+            $col = 'template_identifier';
+            $type_filter = "";
+        } else {
+            $col = 'template_name';
+            $type_filter = "and template_type='$type'";
+        }
+        if (!isset($global)) {
+            $blog_filter = "and template_blog_id in (".$this->escape($blog_id).",0)";
+        } elseif ($global) {
+            $blog_filter = "and template_blog_id=0";
+        } else {
+            $blog_filter = "and template_blog_id=".$this->escape($blog_id);
+        }
+
+        $tmpl_name = $this->escape($name);
+
+        $sql = "
+            select
+                template_id, template_name, template_modified_on
+            from
+                mt_template
+            where
+                $col = '$tmpl_name'
+                $blog_filter
+                $type_filter
+            order by
+                template_blog_id desc";
+        $row = $this->get_row($sql, ARRAY_A);
+        if (!$row) return '';
+
+        $data = $this->get_meta('template', $row['template_id']);
+        return array_merge($row, $data);
     }
 
@@ -3097,3 +3133,60 @@
         $this->query($sql);
     }
+
+    function get_latest_touch($blog_id, $types) {
+        $type_user = false;
+        if (is_array($types)) {
+            $array = preg_grep('/author/', $types);
+            if (!empty($array)) $type_user = true;
+        } else {
+            $type_user = $types == 'author';
+        }
+
+        $blog_filter = '';
+        if (!empty($blog_id)) {
+            if ($type_user)
+                $blog_filter = 'and touch_blog_id = 0';
+            else
+                $blog_filter = 'and touch_blog_id = ' . $blog_id;
+        }
+
+        $type_filter = '';
+        if (!empty($types)) {
+            if ($type_user) {
+                $type_filter = 'and touch_object_type ="author"';
+            } else {
+                if (is_array($types)) {
+                    foreach ($types as $type) {
+                        if ($type_filter != '') $type_filter .= ',';
+                        $type_filter .= "'$type'";
+                    }
+                    $type_filter = 'and touch_object_type in (' . $type_filter . ')';
+                } else {
+                    $type_filter = 'and touch_object_type ="' . $type_filter . '"';
+                }
+            }
+        }
+
+        $sql = "
+            select
+                touch_modified_on
+            from
+                mt_touch
+            where
+                1 = 1
+                $blog_filter
+                $type_filter
+            order by
+                touch_modified_on desc
+            <LIMIT>";
+
+        $sql = $this->apply_limit_sql($sql, 1);
+        $result = $this->get_row($sql, ARRAY_N);
+
+        if (!empty($result))
+            return $result[0];
+
+        return false;
+    }
+
 }
Index: /branches/release-36/php/mt.php.pre
===================================================================
--- /branches/release-36/php/mt.php.pre (revision 2029)
+++ /branches/release-36/php/mt.php.pre (revision 2104)
@@ -363,4 +363,6 @@
         isset($cfg['timeoffset']) or
             $cfg['timeoffset'] = '__DEFAULT_TIMEZONE__';
+        isset($cfg['includesdir']) or
+            $cfg['includesdir'] = 'includes_c';
     }
 
