diff options
22 files changed, 1201 insertions, 1150 deletions
diff --git a/framework/Exceptions/TErrorHandler.php b/framework/Exceptions/TErrorHandler.php index ebdaf41c..87d5d342 100644 --- a/framework/Exceptions/TErrorHandler.php +++ b/framework/Exceptions/TErrorHandler.php @@ -178,7 +178,7 @@ class TErrorHandler extends TModule '%%ErrorMessage%%' => htmlspecialchars($exception->getMessage()),
'%%ServerAdmin%%' => $serverAdmin,
'%%Version%%' => $_SERVER['SERVER_SOFTWARE'].' <a href="http://www.pradosoft.com/">PRADO</a>/'.Prado::getVersion(),
- '%%Time%%' => strftime('%Y-%m-%d %H:%m',time())
+ '%%Time%%' => @strftime('%Y-%m-%d %H:%M',time())
);
echo strtr($content,$tokens);
}
@@ -240,7 +240,7 @@ class TErrorHandler extends TModule '%%SourceCode%%' => $source,
'%%StackTrace%%' => htmlspecialchars($exception->getTraceAsString()),
'%%Version%%' => $_SERVER['SERVER_SOFTWARE'].' <a href="http://www.pradosoft.com/">PRADO</a>/'.Prado::getVersion(),
- '%%Time%%' => strftime('%Y-%m-%d %H:%m',time())
+ '%%Time%%' => @strftime('%Y-%m-%d %H:%M',time())
);
$lang=Prado::getPreferredLanguage();
$exceptionFile=Prado::getFrameworkPath().'/Exceptions/templates/'.self::EXCEPTION_FILE_NAME.'-'.$lang.'.html';
diff --git a/framework/Exceptions/templates/error-fr.html b/framework/Exceptions/templates/error-fr.html index 5546dcdb..47b681de 100644 --- a/framework/Exceptions/templates/error-fr.html +++ b/framework/Exceptions/templates/error-fr.html @@ -1,19 +1,20 @@ -<html>
-<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="fr"/>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="fr" lang="fr">
<title>%%ErrorMessage%%</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>Erreur %%StatusCode%%</h1>
<h2>%%ErrorMessage%%</h2>
<p>
diff --git a/framework/Exceptions/templates/error-zh.html b/framework/Exceptions/templates/error-zh.html index 545f057c..f69d0e49 100644 --- a/framework/Exceptions/templates/error-zh.html +++ b/framework/Exceptions/templates/error-zh.html @@ -1,19 +1,22 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="zh" lang="zh">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="zh"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>%%ErrorMessage%%</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>错误%%StatusCode%%</h1>
<h2>%%ErrorMessage%%</h2>
<p>
diff --git a/framework/Exceptions/templates/error.html b/framework/Exceptions/templates/error.html index 931f96a3..482da4cd 100644 --- a/framework/Exceptions/templates/error.html +++ b/framework/Exceptions/templates/error.html @@ -1,29 +1,32 @@ -<html>
-<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="en"/>
-<title>%%ErrorMessage%%</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
-h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
-h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
-h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
-p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
-.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
-</style>
-</head>
-
-<body bgcolor="white">
-<h1>Error %%StatusCode%%</h1>
-<h2>%%ErrorMessage%%</h2>
-<p>
-The above error happened when the server was processing your request.
-</p>
-<p>
-If you think this is a server error, please contact the <a href="mailto:%%ServerAdmin%%">webmaster</a>.
-</p>
-<div class="version">
-%%Time%% %%Version%%
-</div>
-</body>
+<!DOCTYPE html PUBLIC + "-//W3C//DTD XHTML 1.0 Transitional//EN" + "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> +<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"> +<head> +<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/> +<title>%%ErrorMessage%%</title> +<style type="text/css"> +/*<![CDATA[*/ +body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;} +h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red } +h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon } +h3 {font-family:"Verdana";font-weight:bold;font-size:11pt} +p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px} +.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;} +/*]]>*/ +</style> +</head> +<body> +<h1>Error %%StatusCode%%</h1> +<h2>%%ErrorMessage%%</h2> +<p> +The above error happened when the server was processing your request. +</p> +<p> +If you think this is a server error, please contact the <a href="mailto:%%ServerAdmin%%">webmaster</a>. +</p> +<div class="version"> +%%Time%% %%Version%% +</div> +</body> </html>
\ No newline at end of file diff --git a/framework/Exceptions/templates/error404-en.html b/framework/Exceptions/templates/error404-en.html index 92ac65b1..abbc84a6 100644 --- a/framework/Exceptions/templates/error404-en.html +++ b/framework/Exceptions/templates/error404-en.html @@ -1,30 +1,33 @@ -<html>
-<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="en"/>
-<title>Page Not Found</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
-h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
-h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
-h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
-p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
-.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
-</style>
-</head>
-
-<body bgcolor="white">
-<h1>%%ErrorMessage%%</h1>
-<h2>Error 404</h2>
-<p>
-The requested URL was not found on this server.
-If you entered the URL manually please check your spelling and try again.
-</p>
-<p>
-If you think this is a server error, please contact the <a href="mailto:%%ServerAdmin%%">webmaster</a>.
-</p>
-<div class="version">
-%%Time%% %%Version%%
-</div>
-</body>
+<!DOCTYPE html PUBLIC + "-//W3C//DTD XHTML 1.0 Transitional//EN" + "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> +<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"> +<head> +<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/> +<title>Page Not Found</title> +<style type="text/css"> +/*<![CDATA[*/ +body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;} +h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red } +h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon } +h3 {font-family:"Verdana";font-weight:bold;font-size:11pt} +p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px} +.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;} +/*]]>*/ +</style> +</head> +<body> +<h1>%%ErrorMessage%%</h1> +<h2>Error 404</h2> +<p> +The requested URL was not found on this server. +If you entered the URL manually please check your spelling and try again. +</p> +<p> +If you think this is a server error, please contact the <a href="mailto:%%ServerAdmin%%">webmaster</a>. +</p> +<div class="version"> +%%Time%% %%Version%% +</div> +</body> </html>
\ No newline at end of file diff --git a/framework/Exceptions/templates/error404-fr.html b/framework/Exceptions/templates/error404-fr.html index 181bd8a7..c353d7c1 100644 --- a/framework/Exceptions/templates/error404-fr.html +++ b/framework/Exceptions/templates/error404-fr.html @@ -1,19 +1,20 @@ -<html>
-<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="fr"/>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="fr" lang="fr">
<title>Page Introuvable</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>%%ErrorMessage%%</h1>
<h2>Erreur 404</h2>
<p>
diff --git a/framework/Exceptions/templates/error404-zh.html b/framework/Exceptions/templates/error404-zh.html index ae5d8275..c834f9b1 100644 --- a/framework/Exceptions/templates/error404-zh.html +++ b/framework/Exceptions/templates/error404-zh.html @@ -1,19 +1,22 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="zh" lang="zh">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="zh"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>无法找到页面</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>%%ErrorMessage%%</h1>
<h2>错误代码404</h2>
<p>
diff --git a/framework/Exceptions/templates/error404.html b/framework/Exceptions/templates/error404.html index 92ac65b1..1ad3c0ac 100644 --- a/framework/Exceptions/templates/error404.html +++ b/framework/Exceptions/templates/error404.html @@ -1,19 +1,22 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="en"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>Page Not Found</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>%%ErrorMessage%%</h1>
<h2>Error 404</h2>
<p>
diff --git a/framework/Exceptions/templates/error500-en.html b/framework/Exceptions/templates/error500-en.html index 25d4ad92..76427f43 100644 --- a/framework/Exceptions/templates/error500-en.html +++ b/framework/Exceptions/templates/error500-en.html @@ -1,19 +1,22 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="en"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>Internal Server Error</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>Internal Server Error</h1>
<h2>%%ErrorMessage%%</h2>
<p>
diff --git a/framework/Exceptions/templates/error500-fr.html b/framework/Exceptions/templates/error500-fr.html index 804425ef..0454e27d 100644 --- a/framework/Exceptions/templates/error500-fr.html +++ b/framework/Exceptions/templates/error500-fr.html @@ -1,19 +1,20 @@ -<html>
-<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="fr"/>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="fr" lang="fr">
<title>Erreur Interne du Serveur</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>Erreur Interne du Serveur</h1>
<h2>%%ErrorMessage%%</h2>
<p>
diff --git a/framework/Exceptions/templates/error500-zh.html b/framework/Exceptions/templates/error500-zh.html index a10dbba4..d655601f 100644 --- a/framework/Exceptions/templates/error500-zh.html +++ b/framework/Exceptions/templates/error500-zh.html @@ -1,19 +1,22 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="zh" lang="zh">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="zh"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>服务器内部错误</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>服务器内部错误</h1>
<h2>%%ErrorMessage%%</h2>
<p>
diff --git a/framework/Exceptions/templates/error500.html b/framework/Exceptions/templates/error500.html index 25d4ad92..76427f43 100644 --- a/framework/Exceptions/templates/error500.html +++ b/framework/Exceptions/templates/error500.html @@ -1,19 +1,22 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="en"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>Internal Server Error</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>Internal Server Error</h1>
<h2>%%ErrorMessage%%</h2>
<p>
diff --git a/framework/Exceptions/templates/error503-en.html b/framework/Exceptions/templates/error503-en.html index 718dd4ea..3a5390de 100644 --- a/framework/Exceptions/templates/error503-en.html +++ b/framework/Exceptions/templates/error503-en.html @@ -1,19 +1,22 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="en"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>Service Unavailable</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>Service Unavailable</h1>
<p>
Our system is currently under maintenance. Please come back later.
diff --git a/framework/Exceptions/templates/error503-fr.html b/framework/Exceptions/templates/error503-fr.html index 699114de..ddc7d537 100644 --- a/framework/Exceptions/templates/error503-fr.html +++ b/framework/Exceptions/templates/error503-fr.html @@ -1,19 +1,20 @@ -<html>
-<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="fr"/>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="fr" lang="fr">
<title>Service Indisponible</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>Service Indisponible</h1>
<p>
Le service est actuellement en maintenance et indisponible. Merci de réessayer prochainement.
diff --git a/framework/Exceptions/templates/error503-zh.html b/framework/Exceptions/templates/error503-zh.html index 5babac19..b7457d68 100644 --- a/framework/Exceptions/templates/error503-zh.html +++ b/framework/Exceptions/templates/error503-zh.html @@ -1,19 +1,22 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="zh" lang="zh">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="zh"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>系统无法提供服务</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>系统无法提供服务</h1>
<p>
系统维护中,请稍后再来访问。
diff --git a/framework/Exceptions/templates/error503.html b/framework/Exceptions/templates/error503.html index 718dd4ea..3a5390de 100644 --- a/framework/Exceptions/templates/error503.html +++ b/framework/Exceptions/templates/error503.html @@ -1,19 +1,22 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="en"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>Service Unavailable</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top: -5px}
.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>Service Unavailable</h1>
<p>
Our system is currently under maintenance. Please come back later.
diff --git a/framework/Exceptions/templates/exception-en.html b/framework/Exceptions/templates/exception-en.html index 45fc264c..2de7f5f1 100644 --- a/framework/Exceptions/templates/exception-en.html +++ b/framework/Exceptions/templates/exception-en.html @@ -1,10 +1,13 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="en"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>%%ErrorType%%</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
@@ -12,15 +15,13 @@ p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top code,pre {font-family:"Lucida Console";}
td,.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
.source {font-family:"Lucida Console";font-weight:normal;background-color:#ffffee;}
-.error {background-color: #ffeeee;}
+.error {background-color: #ffeeee;}/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>%%ErrorType%%</h1>
<h3>Description</h3>
<p style="color:maroon">%%ErrorMessage%%</p>
-<p>
<h3>Source File</h3>
<p>%%SourceFile%%</p>
<div class="source">
diff --git a/framework/Exceptions/templates/exception-fr.html b/framework/Exceptions/templates/exception-fr.html index b6f1369b..002a4583 100644 --- a/framework/Exceptions/templates/exception-fr.html +++ b/framework/Exceptions/templates/exception-fr.html @@ -1,10 +1,11 @@ -<html>
-<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="fr"/>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="fr" lang="fr">
<title>%%ErrorType%%</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
@@ -13,14 +14,13 @@ code,pre {font-family:"Lucida Console";} td,.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
.source {font-family:"Lucida Console";font-weight:normal;background-color:#ffffee;}
.error {background-color: #ffeeee;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>%%ErrorType%%</h1>
<h3>Description</h3>
<p style="color:maroon">%%ErrorMessage%%</p>
-<p>
<h3>Fichier Source</h3>
<p>%%SourceFile%%</p>
<div class="source">
diff --git a/framework/Exceptions/templates/exception-zh.html b/framework/Exceptions/templates/exception-zh.html index 8568dde1..e4c8cbcc 100644 --- a/framework/Exceptions/templates/exception-zh.html +++ b/framework/Exceptions/templates/exception-zh.html @@ -1,10 +1,13 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="zh" lang="zh">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="zh"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>%%ErrorType%%</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
@@ -13,10 +16,10 @@ code,pre {font-family:"Lucida Console";} td,.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
.source {font-family:"Lucida Console";font-weight:normal;background-color:#ffffee;}
.error {background-color: #ffeeee;}
+/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>%%ErrorType%%</h1>
<h3>错误信息</h3>
<p style="color:maroon">%%ErrorMessage%%</p>
diff --git a/framework/Exceptions/templates/exception.html b/framework/Exceptions/templates/exception.html index 45fc264c..2de7f5f1 100644 --- a/framework/Exceptions/templates/exception.html +++ b/framework/Exceptions/templates/exception.html @@ -1,10 +1,13 @@ -<html>
+<!DOCTYPE html PUBLIC
+ "-//W3C//DTD XHTML 1.0 Transitional//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
-<meta http-equiv="Content-Type" content="text/html; charset="utf-8"/>
-<meta http-equiv="content-language" content="en"/>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>%%ErrorType%%</title>
-<style>
-body {font-family:"Verdana";font-weight:normal;color:black;}
+<style type="text/css">
+/*<![CDATA[*/
+body {font-family:"Verdana";font-weight:normal;color:black;background-color:white;}
h1 { font-family:"Verdana";font-weight:normal;font-size:18pt;color:red }
h2 { font-family:"Verdana";font-weight:normal;font-size:14pt;color:maroon }
h3 {font-family:"Verdana";font-weight:bold;font-size:11pt}
@@ -12,15 +15,13 @@ p {font-family:"Verdana";font-weight:normal;color:black;font-size:9pt;margin-top code,pre {font-family:"Lucida Console";}
td,.version {color: gray;font-size:8pt;border-top:1px solid #aaaaaa;}
.source {font-family:"Lucida Console";font-weight:normal;background-color:#ffffee;}
-.error {background-color: #ffeeee;}
+.error {background-color: #ffeeee;}/*]]>*/
</style>
</head>
-
-<body bgcolor="white">
+<body>
<h1>%%ErrorType%%</h1>
<h3>Description</h3>
<p style="color:maroon">%%ErrorMessage%%</p>
-<p>
<h3>Source File</h3>
<p>%%SourceFile%%</p>
<div class="source">
diff --git a/framework/TApplication.php b/framework/TApplication.php index 3f9457ea..9051ea23 100644 --- a/framework/TApplication.php +++ b/framework/TApplication.php @@ -1,902 +1,916 @@ -<?php
-/**
- * TApplication class file
- *
- * @author Qiang Xue <qiang.xue@gmail.com>
- * @link http://www.pradosoft.com/
- * @copyright Copyright © 2005 PradoSoft
- * @license http://www.pradosoft.com/license/
- * @version $Revision: $ $Date: $
- * @package System
- */
-
-/**
- * Includes TErrorHandler class
- */
-require_once(PRADO_DIR.'/Exceptions/TErrorHandler.php');
-/**
- * Includes THttpRequest class
- */
-require_once(PRADO_DIR.'/Web/THttpRequest.php');
-/**
- * Includes THttpResponse class
- */
-require_once(PRADO_DIR.'/Web/THttpResponse.php');
-/**
- * Includes THttpSession class
- */
-require_once(PRADO_DIR.'/Web/THttpSession.php');
-/**
- * Includes TAuthorizationRule class
- */
-require_once(PRADO_DIR.'/Security/TAuthorizationRule.php');
-/**
- * Includes TPageService class (default service)
- */
-require_once(PRADO_DIR.'/Web/Services/TPageService.php');
-
-/**
- * TApplication class.
- *
- * TApplication coordinates modules and services, and serves as a configuration
- * context for all Prado components.
- *
- * TApplication uses a configuration file to specify the settings of
- * the application, the modules, the services, the parameters, and so on.
- *
- * TApplication adopts a modular structure. A TApplication instance is a composition
- * of multiple modules. A module is an instance of class implementing
- * {@link IModule} interface. Each module accomplishes certain functionalities
- * that are shared by all Prado components in an application.
- * There are default modules and user-defined modules. The latter offers extreme
- * flexibility of extending TApplication in a plug-and-play fashion.
- * Modules cooperate with each other to serve a user request by following
- * a sequence of lifecycles predefined in TApplication.
- *
- * TApplication has four modes that can be changed by setting {@link setMode Mode}
- * property (in the application configuration file).
- * - <b>Off</b> mode will prevent the application from serving user requests.
- * - <b>Debug</b> mode is mainly used during application development. It ensures
- * the cache is always up-to-date if caching is enabled. It also allows
- * exceptions are displayed with rich context information if they occur.
- * - <b>Normal</b> mode is mainly used during production stage. Exception information
- * will only be recorded in system error logs. The cache is ensured to be
- * up-to-date if it is enabled.
- * - <b>Performance</b> mode is similar to <b>Normal</b> mode except that it
- * does not ensure the cache is up-to-date.
- *
- * TApplication dispatches each user request to a particular service which
- * finishes the actual work for the request with the aid from the application
- * modules.
- *
- * TApplication maintains a lifecycle with the following stages:
- * - [construct] : construction of the application instance
- * - [initApplication] : load application configuration and instantiate modules and the requested service
- * - BeginRequest : this event happens right after application initialization
- * - Authentication : this event happens when authentication is needed for the current request
- * - PostAuthentication : this event happens right after the authentication is done for the current request
- * - Authorization : this event happens when authorization is needed for the current request
- * - PostAuthorization : this event happens right after the authorization is done for the current request
- * - LoadState : this event happens when application state needs to be loaded
- * - PostLoadState : this event happens right after the application state is loaded
- * - PreRunService : this event happens right before the requested service is to run
- * - RunService : this event happens when the requested service runs
- * - PostRunService : this event happens right after the requested service finishes running
- * - SaveState : this event happens when application needs to save its state
- * - PostSaveState : this event happens right after the application saves its state
- * - EndRequest : this is the last stage an application runs
- * - [destruct] : destruction of the application instance
- * Modules and services can attach their methods to one or several of the above
- * events and do appropriate processing when the events are raised. By this way,
- * the application is able to coordinate the activities of modules and services
- * in the above order. To terminate an application before the whole lifecycle
- * completes, call {@link completeRequest}.
- *
- * Examples:
- * - Create and run a Prado application:
- * <code>
- * $application=new TApplication($configFile);
- * $application->run();
- * </code>
- * - The parsed application configuration file is cached.
- * <code>
- * $application=new TApplication($configFile,$cacheFile);
- * $application->run();
- * </code>
- *
- * @author Qiang Xue <qiang.xue@gmail.com>
- * @version $Revision: $ $Date: $
- * @package System
- * @since 3.0
- */
-class TApplication extends TComponent
-{
- /**
- * Default service ID
- */
- const DEFAULT_SERVICE='page';
- /**
- * @var array list of events that define application lifecycles
- */
- private static $_steps=array(
- 'BeginRequest',
- 'Authentication',
- 'PostAuthentication',
- 'Authorization',
- 'PostAuthorization',
- 'LoadState',
- 'PostLoadState',
- 'PreRunService',
- 'RunService',
- 'PostRunService',
- 'SaveState',
- 'PostSaveState',
- 'EndRequest'
- );
-
- /**
- * @var string application ID
- */
- private $_id;
- /**
- * @var string unique application ID
- */
- private $_uniqueID;
- /**
- * @var boolean whether the request is completed
- */
- private $_requestCompleted=false;
- /**
- * @var integer application state
- */
- private $_step;
- /**
- * @var IService current service instance
- */
- private $_service;
- /**
- * @var array list of application modules
- */
- private $_modules;
- /**
- * @var TMap list of application parameters
- */
- private $_parameters;
- /**
- * @var string configuration file
- */
- private $_configFile;
- /**
- * @var string cache file
- */
- private $_cacheFile;
- /**
- * @var TErrorHandler error handler module
- */
- private $_errorHandler=null;
- /**
- * @var THttpRequest request module
- */
- private $_request=null;
- /**
- * @var THttpResponse response module
- */
- private $_response=null;
- /**
- * @var THttpSession session module, could be null
- */
- private $_session=null;
- /**
- * @var ICache cache module, could be null
- */
- private $_cache=null;
- /**
- * @var IUser user instance, could be null
- */
- private $_user=null;
- /**
- * @var TAuthorizationRuleCollection collection of authorization rules
- */
- private $_authRules=null;
- /**
- * @var string application mode
- */
- private $_mode='Debug';
-
- /**
- * Constructor.
- * Initializes the application singleton. This method ensures that users can
- * only create one application instance.
- * @param string configuration file path (absolute or relative to current running script)
- * @param string cache file path. This is optional. If it is present, it will
- * be used to store and load parsed application configuration (to improve performance).
- */
- public function __construct($configFile,$cacheFile=null)
- {
- parent::__construct();
- Prado::setApplication($this);
- if(($this->_configFile=realpath($configFile))===false || !is_file($this->_configFile))
- throw new TIOException('application_configfile_inexistent',$configFile);
- $this->_cacheFile=$cacheFile;
- // generates unique ID by hashing the configuration file path
- $this->_uniqueID=md5($this->_configFile);
- }
-
- /**
- * Executes the lifecycles of the application.
- * This is the main entry function that leads to the running of the whole
- * Prado application.
- */
- public function run()
- {
- try
- {
- $this->initApplication($this->_configFile,$this->_cacheFile);
- $n=count(self::$_steps);
- $this->_step=0;
- $this->_requestCompleted=false;
- while($this->_step<$n)
- {
- if($this->_mode==='Off')
- throw new THttpException(503,'application_service_unavailable');
- $method='on'.self::$_steps[$this->_step];
- $this->$method($this);
- if($this->_requestCompleted && $this->_step<$n-1)
- $this->_step=$n-1;
- else
- $this->_step++;
- }
- }
- catch(Exception $e)
- {
- $this->onError($e);
- }
- }
-
- /**
- * Completes current request processing.
- * This method can be used to exit the application lifecycles after finishing
- * the current cycle.
- */
- public function completeRequest()
- {
- $this->_requestCompleted=true;
- }
-
- /**
- * @return string application ID
- */
- public function getID()
- {
- return $this->_id;
- }
-
- /**
- * @param string application ID
- */
- public function setID($value)
- {
- $this->_id=$value;
- }
-
- /**
- * @return string an ID that unique identifies this Prado application from the others
- */
- public function getUniqueID()
- {
- return $this->_uniqueID;
- }
-
- /**
- * @return string application mode (Off|Debug|Normal|Peformance), defaults to Debug.
- */
- public function getMode()
- {
- return $this->_mode;
- }
-
- /**
- * @param string application mode. Valid values include Off, Debug, Normal, or Peformance
- */
- public function setMode($value)
- {
- $this->_mode=TPropertyValue::ensureEnum($value,array('Off','Debug','Normal','Performance'));
- }
-
- /**
- * @return string configuration file path
- */
- public function getConfigurationFile()
- {
- return $this->_configFile;
- }
-
- /**
- * @return IService the currently requested service
- */
- public function getService()
- {
- return $this->_service;
- }
-
- /**
- * Adds a module to application.
- * Note, this method does not do module initialization.
- * @param string ID of the module
- * @param IModule module object
- */
- public function setModule($id,IModule $module)
- {
- $this->_modules[$id]=$module;
- }
-
- /**
- * @return IModule the module with the specified ID, null if not found
- */
- public function getModule($id)
- {
- return isset($this->_modules[$id])?$this->_modules[$id]:null;
- }
-
- /**
- * @return array list of loaded application modules, indexed by module IDs
- */
- public function getModules()
- {
- return $this->_modules;
- }
-
- /**
- * Returns the list of application parameters.
- * Since the parameters are returned as a {@link TMap} object, you may use
- * the returned result to access, add or remove individual parameters.
- * @return TMap the list of application parameters
- */
- public function getParameters()
- {
- return $this->_parameters;
- }
-
- /**
- * @return THttpRequest the request module
- */
- public function getRequest()
- {
- if(!$this->_request)
- {
- $this->_request=new THttpRequest;
- $this->_request->init($this,null);
- }
- return $this->_request;
- }
-
- /**
- * @param THttpRequest the request module
- */
- public function setRequest(THttpRequest $request)
- {
- $this->_request=$request;
- }
-
- /**
- * @return THttpResponse the response module
- */
- public function getResponse()
- {
- if(!$this->_response)
- {
- $this->_response=new THttpResponse;
- $this->_response->init($this,null);
- }
- return $this->_response;
- }
-
- /**
- * @param THttpRequest the request module
- */
- public function setResponse(THttpResponse $response)
- {
- $this->_response=$response;
- }
-
- /**
- * @return THttpSession the session module, null if session module is not installed
- */
- public function getSession()
- {
- if(!$this->_session)
- {
- $this->_session=new THttpSession;
- $this->_session->init($this,null);
- }
- return $this->_session;
- }
-
- /**
- * @param THttpSession the session module
- */
- public function setSession(THttpSession $session)
- {
- $this->_session=$session;
- }
-
- /**
- * @return TErrorHandler the error hanlder module
- */
- public function getErrorHandler()
- {
- if(!$this->_errorHandler)
- {
- $this->_errorHandler=new TErrorHandler;
- $this->_errorHandler->init($this,null);
- }
- return $this->_errorHandler;
- }
-
- /**
- * @param TErrorHandler the error hanlder module
- */
- public function setErrorHandler(TErrorHandler $handler)
- {
- $this->_errorHandler=$handler;
- }
-
- /**
- * @return ICache the cache module, null if cache module is not installed
- */
- public function getCache()
- {
- return $this->_cache;
- }
-
- /**
- * @param ICache the cache module
- */
- public function setCache(ICache $cache)
- {
- $this->_cache=$cache;
- }
-
- /**
- * @return IUser the application user
- */
- public function getUser()
- {
- return $this->_user;
- }
-
- /**
- * @param IUser the application user
- */
- public function setUser(IUser $user)
- {
- $this->_user=$user;
- }
-
- /**
- * @return TAuthorizationRuleCollection list of authorization rules for the current request
- */
- public function getAuthorizationRules()
- {
- if($this->_authRules===null)
- $this->_authRules=new TAuthorizationRuleCollection;
- return $this->_authRules;
- }
-
- /**
- * Loads configuration and initializes application.
- * Configuration file will be read and parsed (if a valid cached version exists,
- * it will be used instead). Then, modules are created and initialized;
- * Afterwards, the requested service is created and initialized.
- * @param string configuration file path (absolute or relative to current executing script)
- * @param string cache file path, empty if no present or needed
- * @throws TConfigurationException if module is redefined of invalid type, or service not defined or of invalid type
- */
- protected function initApplication($configFile,$cacheFile)
- {
- if($cacheFile===null || @filemtime($cacheFile)<filemtime($configFile))
- {
- $config=new TApplicationConfiguration;
- $config->loadFromFile($configFile);
- if($cacheFile!==null)
- {
- if(($fp=fopen($cacheFile,'wb'))!==false)
- {
- fputs($fp,Prado::serialize($config));
- fclose($fp);
- }
- else
- syslog(LOG_WARNING,'Prado application config cache file "'.$cacheFile.'" cannot be created.');
- }
- }
- else
- {
- $config=Prado::unserialize(file_get_contents($cacheFile));
- }
-
- // set path aliases and using namespaces
- foreach($config->getAliases() as $alias=>$path)
- Prado::setPathOfAlias($alias,$path);
- foreach($config->getUsings() as $using)
- Prado::using($using);
-
- // set application properties
- foreach($config->getProperties() as $name=>$value)
- $this->setSubProperty($name,$value);
-
- // load parameters
- $this->_parameters=new TMap;
- foreach($config->getParameters() as $id=>$parameter)
- {
- if(is_string($parameter))
- $this->_parameters->add($id,$parameter);
- else
- {
- $component=Prado::createComponent($parameter[0]);
- foreach($parameter[1] as $name=>$value)
- $component->setSubProperty($name,$value);
- $this->_parameters->add($id,$component);
- }
- }
-
- // load and init modules specified in app config
- $this->_modules=array();
- foreach($config->getModules() as $id=>$moduleConfig)
- {
- $module=Prado::createComponent($moduleConfig[0]);
- $this->_modules[$id]=$module;
- foreach($moduleConfig[1] as $name=>$value)
- $module->setSubProperty($name,$value);
- $module->init($this,$moduleConfig[2]);
- }
-
- if(($serviceID=$this->getRequest()->getServiceID())===null)
- $serviceID=self::DEFAULT_SERVICE;
- if(($serviceConfig=$config->getService($serviceID))!==null)
- {
- $service=Prado::createComponent($serviceConfig[0]);
- if(!($service instanceof IService))
- throw new TConfigurationException('application_service_invalid',$serviceID);
- $this->_service=$service;
- foreach($serviceConfig[1] as $name=>$value)
- $service->setSubProperty($name,$value);
- $service->init($this,$serviceConfig[2]);
- $this->attachEventHandler('RunService',array($service,'run'));
- }
- else
- throw new TConfigurationException('application_service_unknown',$serviceID);
- }
-
- /**
- * Raises Error event.
- * This method is invoked when an exception is raised during the lifecycles
- * of the application.
- * @param mixed event parameter
- */
- public function onError($param)
- {
- if($this->hasEventHandler('Error'))
- $this->raiseEvent('Error',$this,$param);
- else
- $this->getErrorHandler()->handleError($this,$param);
- }
-
- /**
- * Raises BeginRequest event.
- * At the time when this method is invoked, application modules are loaded
- * and initialized, user request is resolved and the corresponding service
- * is loaded and initialized. The application is about to start processing
- * the user request.
- * @param mixed event parameter
- */
- public function onBeginRequest($param)
- {
- $this->raiseEvent('BeginRequest',$this,$param);
- }
-
- /**
- * Raises Authentication event.
- * This method is invoked when the user request needs to be authenticated.
- * @param mixed event parameter
- */
- public function onAuthentication($param)
- {
- $this->raiseEvent('Authentication',$this,$param);
- }
-
- /**
- * Raises PostAuthentication event.
- * This method is invoked right after the user request is authenticated.
- * @param mixed event parameter
- */
- public function onPostAuthentication($param)
- {
- $this->raiseEvent('PostAuthentication',$this,$param);
- }
-
- /**
- * Raises Authorization event.
- * This method is invoked when the user request needs to be authorized.
- * @param mixed event parameter
- */
- public function onAuthorization($param)
- {
- $this->raiseEvent('Authorization',$this,$param);
- }
-
- /**
- * Raises PostAuthorization event.
- * This method is invoked right after the user request is authorized.
- * @param mixed event parameter
- */
- public function onPostAuthorization($param)
- {
- $this->raiseEvent('PostAuthorization',$this,$param);
- }
-
- /**
- * Raises LoadState event.
- * This method is invoked when the application needs to load state (probably stored in session).
- * @param mixed event parameter
- */
- public function onLoadState($param)
- {
- $this->raiseEvent('LoadState',$this,$param);
- }
-
- /**
- * Raises PostLoadState event.
- * This method is invoked right after the application state has been loaded.
- * @param mixed event parameter
- */
- public function onPostLoadState($param)
- {
- $this->raiseEvent('PostLoadState',$this,$param);
- }
-
- /**
- * Raises PreRunService event.
- * This method is invoked right before the service is to be run.
- * @param mixed event parameter
- */
- public function onPreRunService($param)
- {
- $this->raiseEvent('PreRunService',$this,$param);
- }
-
- /**
- * Raises RunService event.
- * This method is invoked when the service runs.
- * @param mixed event parameter
- */
- public function onRunService($param)
- {
- $this->raiseEvent('RunService',$this,$param);
- }
-
- /**
- * Raises PostRunService event.
- * This method is invoked right after the servie is run.
- * @param mixed event parameter
- */
- public function onPostRunService($param)
- {
- $this->raiseEvent('PostRunService',$this,$param);
- }
-
- /**
- * Raises SaveState event.
- * This method is invoked when the application needs to save state (probably stored in session).
- * @param mixed event parameter
- */
- public function onSaveState($param)
- {
- $this->raiseEvent('SaveState',$this,$param);
- }
-
- /**
- * Raises PostSaveState event.
- * This method is invoked right after the application state has been saved.
- * @param mixed event parameter
- */
- public function onPostSaveState($param)
- {
- $this->raiseEvent('PostSaveState',$this,$param);
- }
-
- /**
- * Raises EndRequest event.
- * This method is invoked when the application completes the processing of the request.
- * @param mixed event parameter
- */
- public function onEndRequest($param)
- {
- $this->raiseEvent('EndRequest',$this,$param);
- }
-}
-
-
-/**
- * TApplicationConfiguration class.
- *
- * This class is used internally by TApplication to parse and represent application configuration.
- *
- * @author Qiang Xue <qiang.xue@gmail.com>
- * @version $Revision: $ $Date: $
- * @package System
- * @since 3.0
- */
-class TApplicationConfiguration extends TComponent
-{
- /**
- * @var array list of application initial property values, indexed by property names
- */
- private $_properties=array();
- /**
- * @var array list of namespaces to be used
- */
- private $_usings=array();
- /**
- * @var array list of path aliases, indexed by alias names
- */
- private $_aliases=array();
- /**
- * @var array list of module configurations
- */
- private $_modules=array();
- /**
- * @var array list of service configurations
- */
- private $_services=array(
- 'page'=>array('TPageService',array(),null)
- );
- /**
- * @var array list of parameters
- */
- private $_parameters=array();
-
- /**
- * Parses the application configuration file.
- * @param string configuration file name
- * @throws TConfigurationException if there is any parsing error
- */
- public function loadFromFile($fname)
- {
- $configPath=dirname($fname);
- $dom=new TXmlDocument;
- $dom->loadFromFile($fname);
-
- // application properties
- foreach($dom->getAttributes() as $name=>$value)
- $this->_properties[$name]=$value;
-
- // paths
- if(($pathsNode=$dom->getElementByTagName('paths'))!==null)
- {
- foreach($pathsNode->getElementsByTagName('alias') as $aliasNode)
- {
- if(($id=$aliasNode->getAttribute('id'))!==null && ($path=$aliasNode->getAttribute('path'))!==null)
- {
- $path=str_replace('\\','/',$path);
- if(preg_match('/^\\/|.:\\/|.:\\\\/',$path)) // if absolute path
- $p=realpath($path);
- else
- $p=realpath($configPath.'/'.$path);
- if($p===false || !is_dir($p))
- throw new TConfigurationException('appconfig_aliaspath_invalid',$id,$path);
- if(isset($this->_aliases[$id]))
- throw new TConfigurationException('appconfig_alias_redefined',$id);
- $this->_aliases[$id]=$p;
- }
- else
- throw new TConfigurationException('appconfig_alias_invalid');
- }
- foreach($pathsNode->getElementsByTagName('using') as $usingNode)
- {
- if(($namespace=$usingNode->getAttribute('namespace'))!==null)
- $this->_usings[]=$namespace;
- else
- throw new TConfigurationException('appconfig_using_invalid');
- }
- }
-
- // application modules
- if(($modulesNode=$dom->getElementByTagName('modules'))!==null)
- {
- foreach($modulesNode->getElementsByTagName('module') as $node)
- {
- $properties=$node->getAttributes();
- if(($id=$properties->itemAt('id'))===null)
- throw new TConfigurationException('appconfig_moduleid_required');
- if(($type=$properties->remove('class'))===null && isset($this->_modules[$id]) && $this->_modules[$id][2]===null)
- $type=$this->_modules[$id][0];
- if($type===null)
- throw new TConfigurationException('appconfig_moduletype_required',$id);
- $node->setParent(null);
- $this->_modules[$id]=array($type,$properties->toArray(),$node);
- }
- }
-
- // services
- if(($servicesNode=$dom->getElementByTagName('services'))!==null)
- {
- foreach($servicesNode->getElementsByTagName('service') as $node)
- {
- $properties=$node->getAttributes();
- if(($id=$properties->itemAt('id'))===null)
- throw new TConfigurationException('appconfig_serviceid_required');
- if(($type=$properties->remove('class'))===null && isset($this->_services[$id]) && $this->_services[$id][2]===null)
- $type=$this->_services[$id][0];
- if($type===null)
- throw new TConfigurationException('appconfig_servicetype_required',$id);
- $node->setParent(null);
- $this->_services[$id]=array($type,$properties->toArray(),$node);
- }
- }
-
- // parameters
- if(($parametersNode=$dom->getElementByTagName('parameters'))!==null)
- {
- foreach($parametersNode->getElementsByTagName('parameter') as $node)
- {
- $properties=$node->getAttributes();
- if(($id=$properties->remove('id'))===null)
- throw new TConfigurationException('appconfig_parameterid_required');
- if(($type=$properties->remove('class'))===null)
- $this->_parameters[$id]=$node->getValue();
- else
- $this->_parameters[$id]=array($type,$properties->toArray());
- }
- }
- }
-
- /**
- * @return array list of application initial property values, indexed by property names
- */
- public function getProperties()
- {
- return $this->_properties;
- }
-
- /**
- * @return array list of path aliases, indexed by alias names
- */
- public function getAliases()
- {
- return $this->_aliases;
- }
-
- /**
- * @return array list of namespaces to be used
- */
- public function getUsings()
- {
- return $this->_usings;
- }
-
- /**
- * @return array list of module configurations
- */
- public function getModules()
- {
- return $this->_modules;
- }
-
- /**
- * @return array list of service configurations
- */
- public function getService($id)
- {
- return isset($this->_services[$id])?$this->_services[$id]:null;
- }
-
- /**
- * @return array list of parameters
- */
- public function getParameters()
- {
- return $this->_parameters;
- }
-}
-
+<?php +/** + * TApplication class file + * + * @author Qiang Xue <qiang.xue@gmail.com> + * @link http://www.pradosoft.com/ + * @copyright Copyright © 2005 PradoSoft + * @license http://www.pradosoft.com/license/ + * @version $Revision: $ $Date: $ + * @package System + */ + +/** + * Includes TErrorHandler class + */ +require_once(PRADO_DIR.'/Exceptions/TErrorHandler.php'); +/** + * Includes THttpRequest class + */ +require_once(PRADO_DIR.'/Web/THttpRequest.php'); +/** + * Includes THttpResponse class + */ +require_once(PRADO_DIR.'/Web/THttpResponse.php'); +/** + * Includes THttpSession class + */ +require_once(PRADO_DIR.'/Web/THttpSession.php'); +/** + * Includes TAuthorizationRule class + */ +require_once(PRADO_DIR.'/Security/TAuthorizationRule.php'); +/** + * Includes TPageService class (default service) + */ +require_once(PRADO_DIR.'/Web/Services/TPageService.php'); + +/** + * TApplication class. + * + * TApplication coordinates modules and services, and serves as a configuration + * context for all Prado components. + * + * TApplication uses a configuration file to specify the settings of + * the application, the modules, the services, the parameters, and so on. + * + * TApplication adopts a modular structure. A TApplication instance is a composition + * of multiple modules. A module is an instance of class implementing + * {@link IModule} interface. Each module accomplishes certain functionalities + * that are shared by all Prado components in an application. + * There are default modules and user-defined modules. The latter offers extreme + * flexibility of extending TApplication in a plug-and-play fashion. + * Modules cooperate with each other to serve a user request by following + * a sequence of lifecycles predefined in TApplication. + * + * TApplication has four modes that can be changed by setting {@link setMode Mode} + * property (in the application configuration file). + * - <b>Off</b> mode will prevent the application from serving user requests. + * - <b>Debug</b> mode is mainly used during application development. It ensures + * the cache is always up-to-date if caching is enabled. It also allows + * exceptions are displayed with rich context information if they occur. + * - <b>Normal</b> mode is mainly used during production stage. Exception information + * will only be recorded in system error logs. The cache is ensured to be + * up-to-date if it is enabled. + * - <b>Performance</b> mode is similar to <b>Normal</b> mode except that it + * does not ensure the cache is up-to-date. + * + * TApplication dispatches each user request to a particular service which + * finishes the actual work for the request with the aid from the application + * modules. + * + * TApplication maintains a lifecycle with the following stages: + * - [construct] : construction of the application instance + * - [initApplication] : load application configuration and instantiate modules and the requested service + * - BeginRequest : this event happens right after application initialization + * - Authentication : this event happens when authentication is needed for the current request + * - PostAuthentication : this event happens right after the authentication is done for the current request + * - Authorization : this event happens when authorization is needed for the current request + * - PostAuthorization : this event happens right after the authorization is done for the current request + * - LoadState : this event happens when application state needs to be loaded + * - PostLoadState : this event happens right after the application state is loaded + * - PreRunService : this event happens right before the requested service is to run + * - RunService : this event happens when the requested service runs + * - PostRunService : this event happens right after the requested service finishes running + * - SaveState : this event happens when application needs to save its state + * - PostSaveState : this event happens right after the application saves its state + * - EndRequest : this is the last stage an application runs + * - [destruct] : destruction of the application instance + * Modules and services can attach their methods to one or several of the above + * events and do appropriate processing when the events are raised. By this way, + * the application is able to coordinate the activities of modules and services + * in the above order. To terminate an application before the whole lifecycle + * completes, call {@link completeRequest}. + * + * Examples: + * - Create and run a Prado application: + * <code> + * $application=new TApplication($configFile); + * $application->run(); + * </code> + * - The parsed application configuration file is cached. + * <code> + * $application=new TApplication($configFile,$cacheFile); + * $application->run(); + * </code> + * + * @author Qiang Xue <qiang.xue@gmail.com> + * @version $Revision: $ $Date: $ + * @package System + * @since 3.0 + */ +class TApplication extends TComponent +{ + /** + * Default service ID + */ + const DEFAULT_SERVICE='page'; + /** + * @var array list of events that define application lifecycles + */ + private static $_steps=array( + 'BeginRequest', + 'Authentication', + 'PostAuthentication', + 'Authorization', + 'PostAuthorization', + 'LoadState', + 'PostLoadState', + 'PreRunService', + 'RunService', + 'PostRunService', + 'SaveState', + 'PostSaveState', + 'EndRequest' + ); + + /** + * @var string application ID + */ + private $_id; + /** + * @var string unique application ID + */ + private $_uniqueID; + /** + * @var boolean whether the request is completed + */ + private $_requestCompleted=false; + /** + * @var integer application state + */ + private $_step; + /** + * @var IService current service instance + */ + private $_service; + /** + * @var array list of application modules + */ + private $_modules; + /** + * @var TMap list of application parameters + */ + private $_parameters; + /** + * @var string configuration file + */ + private $_configFile; + /** + * @var string cache file + */ + private $_cacheFile; + /** + * @var TErrorHandler error handler module + */ + private $_errorHandler=null; + /** + * @var THttpRequest request module + */ + private $_request=null; + /** + * @var THttpResponse response module + */ + private $_response=null; + /** + * @var THttpSession session module, could be null + */ + private $_session=null; + /** + * @var ICache cache module, could be null + */ + private $_cache=null; + /** + * @var IUser user instance, could be null + */ + private $_user=null; + /** + * @var TAuthorizationRuleCollection collection of authorization rules + */ + private $_authRules=null; + /** + * @var string application mode + */ + private $_mode='Debug'; + + /** + * Constructor. + * Initializes the application singleton. This method ensures that users can + * only create one application instance. + * @param string configuration file path (absolute or relative to current running script) + * @param string cache file path. This is optional. If it is present, it will + * be used to store and load parsed application configuration (to improve performance). + */ + public function __construct($configFile,$cacheFile=null) + { + parent::__construct(); + Prado::setApplication($this); + if(($this->_configFile=realpath($configFile))===false || !is_file($this->_configFile)) + throw new TIOException('application_configfile_inexistent',$configFile); + $this->_cacheFile=$cacheFile; + // generates unique ID by hashing the configuration file path + $this->_uniqueID=md5($this->_configFile); + } + + + /** + * Executes the lifecycles of the application. + * This is the main entry function that leads to the running of the whole + * Prado application. + */ + public function run() + { + //init the error handlers + $this->applyDefaultExceptionHandlers(); + try + { + $this->initApplication($this->_configFile,$this->_cacheFile); + $n=count(self::$_steps); + $this->_step=0; + $this->_requestCompleted=false; + while($this->_step<$n) + { + if($this->_mode==='Off') + throw new THttpException(503,'application_service_unavailable'); + $method='on'.self::$_steps[$this->_step]; + $this->$method($this); + if($this->_requestCompleted && $this->_step<$n-1) + $this->_step=$n-1; + else + $this->_step++; + } + } + catch(Exception $e) + { + $this->onError($e); + } + } + + /** + * Sets up error handler to convert PHP errors into exceptions that can be caught. + */ + protected function applyDefaultExceptionHandlers() + { + set_error_handler(array('Prado','phpErrorHandler'),error_reporting()); + set_exception_handler(array('Prado','exceptionHandler')); + } + + /** + * Completes current request processing. + * This method can be used to exit the application lifecycles after finishing + * the current cycle. + */ + public function completeRequest() + { + $this->_requestCompleted=true; + } + + /** + * @return string application ID + */ + public function getID() + { + return $this->_id; + } + + /** + * @param string application ID + */ + public function setID($value) + { + $this->_id=$value; + } + + /** + * @return string an ID that unique identifies this Prado application from the others + */ + public function getUniqueID() + { + return $this->_uniqueID; + } + + /** + * @return string application mode (Off|Debug|Normal|Peformance), defaults to Debug. + */ + public function getMode() + { + return $this->_mode; + } + + /** + * @param string application mode. Valid values include Off, Debug, Normal, or Peformance + */ + public function setMode($value) + { + $this->_mode=TPropertyValue::ensureEnum($value,array('Off','Debug','Normal','Performance')); + } + + /** + * @return string configuration file path + */ + public function getConfigurationFile() + { + return $this->_configFile; + } + + /** + * @return IService the currently requested service + */ + public function getService() + { + return $this->_service; + } + + /** + * Adds a module to application. + * Note, this method does not do module initialization. + * @param string ID of the module + * @param IModule module object + */ + public function setModule($id,IModule $module) + { + $this->_modules[$id]=$module; + } + + /** + * @return IModule the module with the specified ID, null if not found + */ + public function getModule($id) + { + return isset($this->_modules[$id])?$this->_modules[$id]:null; + } + + /** + * @return array list of loaded application modules, indexed by module IDs + */ + public function getModules() + { + return $this->_modules; + } + + /** + * Returns the list of application parameters. + * Since the parameters are returned as a {@link TMap} object, you may use + * the returned result to access, add or remove individual parameters. + * @return TMap the list of application parameters + */ + public function getParameters() + { + return $this->_parameters; + } + + /** + * @return THttpRequest the request module + */ + public function getRequest() + { + if(!$this->_request) + { + $this->_request=new THttpRequest; + $this->_request->init($this,null); + } + return $this->_request; + } + + /** + * @param THttpRequest the request module + */ + public function setRequest(THttpRequest $request) + { + $this->_request=$request; + } + + /** + * @return THttpResponse the response module + */ + public function getResponse() + { + if(!$this->_response) + { + $this->_response=new THttpResponse; + $this->_response->init($this,null); + } + return $this->_response; + } + + /** + * @param THttpRequest the request module + */ + public function setResponse(THttpResponse $response) + { + $this->_response=$response; + } + + /** + * @return THttpSession the session module, null if session module is not installed + */ + public function getSession() + { + if(!$this->_session) + { + $this->_session=new THttpSession; + $this->_session->init($this,null); + } + return $this->_session; + } + + /** + * @param THttpSession the session module + */ + public function setSession(THttpSession $session) + { + $this->_session=$session; + } + + /** + * @return TErrorHandler the error hanlder module + */ + public function getErrorHandler() + { + if(!$this->_errorHandler) + { + $this->_errorHandler=new TErrorHandler; + $this->_errorHandler->init($this,null); + } + return $this->_errorHandler; + } + + /** + * @param TErrorHandler the error hanlder module + */ + public function setErrorHandler(TErrorHandler $handler) + { + $this->_errorHandler=$handler; + } + + /** + * @return ICache the cache module, null if cache module is not installed + */ + public function getCache() + { + return $this->_cache; + } + + /** + * @param ICache the cache module + */ + public function setCache(ICache $cache) + { + $this->_cache=$cache; + } + + /** + * @return IUser the application user + */ + public function getUser() + { + return $this->_user; + } + + /** + * @param IUser the application user + */ + public function setUser(IUser $user) + { + $this->_user=$user; + } + + /** + * @return TAuthorizationRuleCollection list of authorization rules for the current request + */ + public function getAuthorizationRules() + { + if($this->_authRules===null) + $this->_authRules=new TAuthorizationRuleCollection; + return $this->_authRules; + } + + /** + * Loads configuration and initializes application. + * Configuration file will be read and parsed (if a valid cached version exists, + * it will be used instead). Then, modules are created and initialized; + * Afterwards, the requested service is created and initialized. + * @param string configuration file path (absolute or relative to current executing script) + * @param string cache file path, empty if no present or needed + * @throws TConfigurationException if module is redefined of invalid type, or service not defined or of invalid type + */ + protected function initApplication($configFile,$cacheFile) + { + if($cacheFile===null || @filemtime($cacheFile)<filemtime($configFile)) + { + $config=new TApplicationConfiguration; + $config->loadFromFile($configFile); + if($cacheFile!==null) + { + if(($fp=fopen($cacheFile,'wb'))!==false) + { + fputs($fp,Prado::serialize($config)); + fclose($fp); + } + else + syslog(LOG_WARNING,'Prado application config cache file "'.$cacheFile.'" cannot be created.'); + } + } + else + { + $config=Prado::unserialize(file_get_contents($cacheFile)); + } + + + // set path aliases and using namespaces + foreach($config->getAliases() as $alias=>$path) + Prado::setPathOfAlias($alias,$path); + foreach($config->getUsings() as $using) + Prado::using($using); + + // set application properties + foreach($config->getProperties() as $name=>$value) + $this->setSubProperty($name,$value); + + // load parameters + $this->_parameters=new TMap; + foreach($config->getParameters() as $id=>$parameter) + { + if(is_string($parameter)) + $this->_parameters->add($id,$parameter); + else + { + $component=Prado::createComponent($parameter[0]); + foreach($parameter[1] as $name=>$value) + $component->setSubProperty($name,$value); + $this->_parameters->add($id,$component); + } + } + + // load and init modules specified in app config + $this->_modules=array(); + foreach($config->getModules() as $id=>$moduleConfig) + { + $module=Prado::createComponent($moduleConfig[0]); + $this->_modules[$id]=$module; + foreach($moduleConfig[1] as $name=>$value) + $module->setSubProperty($name,$value); + $module->init($this,$moduleConfig[2]); + } + + if(($serviceID=$this->getRequest()->getServiceID())===null) + $serviceID=self::DEFAULT_SERVICE; + + if(($serviceConfig=$config->getService($serviceID))!==null) + { + $service=Prado::createComponent($serviceConfig[0]); + if(!($service instanceof IService)) + throw new TConfigurationException('application_service_invalid',$serviceID); + $this->_service=$service; + foreach($serviceConfig[1] as $name=>$value) + $service->setSubProperty($name,$value); + $service->init($this,$serviceConfig[2]); + $this->attachEventHandler('RunService',array($service,'run')); + } + else + throw new TConfigurationException('application_service_unknown',$serviceID); + } + + /** + * Raises Error event. + * This method is invoked when an exception is raised during the lifecycles + * of the application. + * @param mixed event parameter + */ + public function onError($param) + { + if($this->hasEventHandler('Error')) + $this->raiseEvent('Error',$this,$param); + else + $this->getErrorHandler()->handleError($this,$param); + } + + /** + * Raises BeginRequest event. + * At the time when this method is invoked, application modules are loaded + * and initialized, user request is resolved and the corresponding service + * is loaded and initialized. The application is about to start processing + * the user request. + * @param mixed event parameter + */ + public function onBeginRequest($param) + { + $this->raiseEvent('BeginRequest',$this,$param); + } + + /** + * Raises Authentication event. + * This method is invoked when the user request needs to be authenticated. + * @param mixed event parameter + */ + public function onAuthentication($param) + { + $this->raiseEvent('Authentication',$this,$param); + } + + /** + * Raises PostAuthentication event. + * This method is invoked right after the user request is authenticated. + * @param mixed event parameter + */ + public function onPostAuthentication($param) + { + $this->raiseEvent('PostAuthentication',$this,$param); + } + + /** + * Raises Authorization event. + * This method is invoked when the user request needs to be authorized. + * @param mixed event parameter + */ + public function onAuthorization($param) + { + $this->raiseEvent('Authorization',$this,$param); + } + + /** + * Raises PostAuthorization event. + * This method is invoked right after the user request is authorized. + * @param mixed event parameter + */ + public function onPostAuthorization($param) + { + $this->raiseEvent('PostAuthorization',$this,$param); + } + + /** + * Raises LoadState event. + * This method is invoked when the application needs to load state (probably stored in session). + * @param mixed event parameter + */ + public function onLoadState($param) + { + $this->raiseEvent('LoadState',$this,$param); + } + + /** + * Raises PostLoadState event. + * This method is invoked right after the application state has been loaded. + * @param mixed event parameter + */ + public function onPostLoadState($param) + { + $this->raiseEvent('PostLoadState',$this,$param); + } + + /** + * Raises PreRunService event. + * This method is invoked right before the service is to be run. + * @param mixed event parameter + */ + public function onPreRunService($param) + { + $this->raiseEvent('PreRunService',$this,$param); + } + + /** + * Raises RunService event. + * This method is invoked when the service runs. + * @param mixed event parameter + */ + public function onRunService($param) + { + $this->raiseEvent('RunService',$this,$param); + } + + /** + * Raises PostRunService event. + * This method is invoked right after the servie is run. + * @param mixed event parameter + */ + public function onPostRunService($param) + { + $this->raiseEvent('PostRunService',$this,$param); + } + + /** + * Raises SaveState event. + * This method is invoked when the application needs to save state (probably stored in session). + * @param mixed event parameter + */ + public function onSaveState($param) + { + $this->raiseEvent('SaveState',$this,$param); + } + + /** + * Raises PostSaveState event. + * This method is invoked right after the application state has been saved. + * @param mixed event parameter + */ + public function onPostSaveState($param) + { + $this->raiseEvent('PostSaveState',$this,$param); + } + + /** + * Raises EndRequest event. + * This method is invoked when the application completes the processing of the request. + * @param mixed event parameter + */ + public function onEndRequest($param) + { + $this->raiseEvent('EndRequest',$this,$param); + } +} + + +/** + * TApplicationConfiguration class. + * + * This class is used internally by TApplication to parse and represent application configuration. + * + * @author Qiang Xue <qiang.xue@gmail.com> + * @version $Revision: $ $Date: $ + * @package System + * @since 3.0 + */ +class TApplicationConfiguration extends TComponent +{ + /** + * @var array list of application initial property values, indexed by property names + */ + private $_properties=array(); + /** + * @var array list of namespaces to be used + */ + private $_usings=array(); + /** + * @var array list of path aliases, indexed by alias names + */ + private $_aliases=array(); + /** + * @var array list of module configurations + */ + private $_modules=array(); + /** + * @var array list of service configurations + */ + private $_services=array( + 'page'=>array('TPageService',array(),null) + ); + /** + * @var array list of parameters + */ + private $_parameters=array(); + + /** + * Parses the application configuration file. + * @param string configuration file name + * @throws TConfigurationException if there is any parsing error + */ + public function loadFromFile($fname) + { + $configPath=dirname($fname); + $dom=new TXmlDocument; + $dom->loadFromFile($fname); + + // application properties + foreach($dom->getAttributes() as $name=>$value) + $this->_properties[$name]=$value; + + // paths + if(($pathsNode=$dom->getElementByTagName('paths'))!==null) + { + foreach($pathsNode->getElementsByTagName('alias') as $aliasNode) + { + if(($id=$aliasNode->getAttribute('id'))!==null && ($path=$aliasNode->getAttribute('path'))!==null) + { + $path=str_replace('\\','/',$path); + if(preg_match('/^\\/|.:\\/|.:\\\\/',$path)) // if absolute path + $p=realpath($path); + else + $p=realpath($configPath.'/'.$path); + if($p===false || !is_dir($p)) + throw new TConfigurationException('appconfig_aliaspath_invalid',$id,$path); + if(isset($this->_aliases[$id])) + throw new TConfigurationException('appconfig_alias_redefined',$id); + $this->_aliases[$id]=$p; + } + else + throw new TConfigurationException('appconfig_alias_invalid'); + } + foreach($pathsNode->getElementsByTagName('using') as $usingNode) + { + if(($namespace=$usingNode->getAttribute('namespace'))!==null) + $this->_usings[]=$namespace; + else + throw new TConfigurationException('appconfig_using_invalid'); + } + } + + // application modules + if(($modulesNode=$dom->getElementByTagName('modules'))!==null) + { + foreach($modulesNode->getElementsByTagName('module') as $node) + { + $properties=$node->getAttributes(); + if(($id=$properties->itemAt('id'))===null) + throw new TConfigurationException('appconfig_moduleid_required'); + if(($type=$properties->remove('class'))===null && isset($this->_modules[$id]) && $this->_modules[$id][2]===null) + $type=$this->_modules[$id][0]; + if($type===null) + throw new TConfigurationException('appconfig_moduletype_required',$id); + $node->setParent(null); + $this->_modules[$id]=array($type,$properties->toArray(),$node); + } + } + + // services + if(($servicesNode=$dom->getElementByTagName('services'))!==null) + { + foreach($servicesNode->getElementsByTagName('service') as $node) + { + $properties=$node->getAttributes(); + if(($id=$properties->itemAt('id'))===null) + throw new TConfigurationException('appconfig_serviceid_required'); + if(($type=$properties->remove('class'))===null && isset($this->_services[$id]) && $this->_services[$id][2]===null) + $type=$this->_services[$id][0]; + if($type===null) + throw new TConfigurationException('appconfig_servicetype_required',$id); + $node->setParent(null); + $this->_services[$id]=array($type,$properties->toArray(),$node); + } + } + + // parameters + if(($parametersNode=$dom->getElementByTagName('parameters'))!==null) + { + foreach($parametersNode->getElementsByTagName('parameter') as $node) + { + $properties=$node->getAttributes(); + if(($id=$properties->remove('id'))===null) + throw new TConfigurationException('appconfig_parameterid_required'); + if(($type=$properties->remove('class'))===null) + $this->_parameters[$id]=$node->getValue(); + else + $this->_parameters[$id]=array($type,$properties->toArray()); + } + } + } + + /** + * @return array list of application initial property values, indexed by property names + */ + public function getProperties() + { + return $this->_properties; + } + + /** + * @return array list of path aliases, indexed by alias names + */ + public function getAliases() + { + return $this->_aliases; + } + + /** + * @return array list of namespaces to be used + */ + public function getUsings() + { + return $this->_usings; + } + + /** + * @return array list of module configurations + */ + public function getModules() + { + return $this->_modules; + } + + /** + * @return array list of service configurations + */ + public function getService($id) + { + return isset($this->_services[$id])?$this->_services[$id]:null; + } + + /** + * @return array list of parameters + */ + public function getParameters() + { + return $this->_parameters; + } +} + ?>
\ No newline at end of file diff --git a/framework/prado.php b/framework/prado.php index d4ecb8eb..a76f4d16 100644 --- a/framework/prado.php +++ b/framework/prado.php @@ -1,62 +1,57 @@ -<?php
-/**
- * Prado bootstrap file.
- *
- * This file is intended to be included in the entry script of Prado applications.
- * It defines Prado class by extending PradoBase, a static class providing globally
- * available functionalities to Prado applications. It also sets PHP error and
- * exception handler functions, and provides a __autoload function which automatically
- * loads a class file if the class is not defined.
- *
- * @author Qiang Xue <qiang.xue@gmail.com>
- * @link http://www.pradosoft.com/
- * @copyright Copyright © 2005 PradoSoft
- * @license http://www.pradosoft.com/license/
- * @version $Revision: $ $Date: $
- * @package System
- */
-
-/**
- * Includes the Prado core header file
- */
-require_once(dirname(__FILE__).'/core.php');
-
-/**
- * Defines Prado class if not defined.
- */
-if(!class_exists('Prado',false))
-{
- class Prado extends PradoBase
- {
- }
-}
-
-/**
- * Defines __autoload function if not defined.
- */
-if(!function_exists('__autoload'))
-{
- function __autoload($className)
- {
- include_once($className.Prado::CLASS_FILE_EXT);
- if(!class_exists($className,false))
- Prado::fatalError("Class file for '$className' cannot be found.");
- }
-}
-
-/**
- * Sets up error handler to convert PHP errors into exceptions that can be caught.
- */
-set_error_handler(array('Prado','phpErrorHandler'),error_reporting());
-
-/**
- * Sets up handler to handle uncaught exceptions.
- */
-set_exception_handler(array('Prado','exceptionHandler'));
-
-/**
- * Includes TApplication class file
- */
-require_once(dirname(__FILE__).'/TApplication.php');
-
+<?php +/** + * Prado bootstrap file. + * + * This file is intended to be included in the entry script of Prado applications. + * It defines Prado class by extending PradoBase, a static class providing globally + * available functionalities to Prado applications. It also sets PHP error and + * exception handler functions, and provides a __autoload function which automatically + * loads a class file if the class is not defined. + * + * @author Qiang Xue <qiang.xue@gmail.com> + * @link http://www.pradosoft.com/ + * @copyright Copyright © 2005 PradoSoft + * @license http://www.pradosoft.com/license/ + * @version $Revision: $ $Date: $ + * @package System + */ + +/** + * Includes the Prado core header file + */ +require_once(dirname(__FILE__).'/core.php'); + +/** + * Defines Prado class if not defined. + */ +if(!class_exists('Prado',false)) +{ + class Prado extends PradoBase + { + } +} + +/** + * Defines __autoload function if not defined. + */ +if(!function_exists('__autoload')) +{ + function __autoload($className) + { + include_once($className.Prado::CLASS_FILE_EXT); + if(!class_exists($className,false)) + Prado::fatalError("Class file for '$className' cannot be found."); + } +} + +//Error handlers are set during TApplication::run(), +//Exception stack is empty if set error handlers requires TApplication +//and TApplication then causes an exception during instantiation. +//see TApplication::initDefaultExceptionHandlers() + +/** + * Includes TApplication class file + */ +require_once(dirname(__FILE__).'/TApplication.php'); + ?>
\ No newline at end of file |