PDA

View Full Version : سوال: Class PHP Template Engine



pasargadteam
یک شنبه 14 مهر 1392, 13:17 عصر
سلام و درود بیکران

من خیلی سرچ کردم اما به نتیجه خاصی نرسیدم.
در سیستمی که دارم مینویسم میخواهم طرف کاربری به صورت تمپلیت با پسوند tpl باشه. درون فایل مخصولات HTML و PHP باشه.
برنامه های مختلفی مثل Smarty , Rain TPL دیدم اما مثل اینا نه.
میخواهم کلاسش رو از بیس خودم بنویسم. اما نمیدونم از کجا شروع کنم. منبع خاصی هم پیدا نکردم.
یکی از دوستانم این کارو کرده در سیستم خودش اما دقیقاً سر در نمیارم چطوری این کارو کرده. خودشم در دسترس نیست بتونم ازش بپرسم.
اگر منبعی هست که کامل توضیح بده ممنون میشم کمک کنید یا کسی میتونه کمک کنه من این کار رو انجام بدم ممنون میشم.
نمونه کدی که دوست من نوشته میزارم اینجا یه تیکه اش رو:




<?php
################################################## ################################################## ################### CMS Start
class CMS {
var $root_templates_folder= 'templates/';
var $template_js='js/';
var $template_css='css/';
var $template_images='images/';
var $selected_template;

function CurrentFullUrl(){
if(!isset($_SERVER['REQUEST_URI'])){ $serverrequri = $_SERVER['PHP_SELF']; }
else{ $serverrequri = $_SERVER['REQUEST_URI']; }
$s = empty($_SERVER["HTTPS"]) ? '' : ($_SERVER["HTTPS"] == "on") ? "s" : "";
$protocol = CMS::strleft(strtolower($_SERVER["SERVER_PROTOCOL"]), "/").$s;
$port = ($_SERVER["SERVER_PORT"] == "80") ? "" : (":".$_SERVER["SERVER_PORT"]);
$final=$protocol."://".$_SERVER['SERVER_NAME'].$port.$serverrequri;
// remove error code from RwMod url:
$final=str_replace('error.13/','/',$final);
return $final;
}


function GetSetting($name){
/**
* read a system setting parameter
**/
if($name!="selected_template"){
$row=@mysql_fetch_array(mysql_query("select `sitetemplate` from `settings` where `sitetemplate`='".$name."'"));
return $row['sitetemplate'];
}else{
//if($_SESSION['url_selected_template']!=""){
//return $_SESSION['url_selected_template'];
//}else{
$row=@mysql_fetch_array(mysql_query("select `sitetemplate` from `settings` where `sitetemplate`='".$name."'"));
return $row['sitetemplate'];
//}
}
}

function TemplateFolder($folder_name=''){
if(CMS::GetSetting('rwmod_status')==1){
return CMS::GetRootBackStepsInRwMod().'templates/'. CMS::GetSetting('selected_template').'/'.$folder_name;
}else{

return 'templates/'. CMS::GetSetting('selected_template').'/'.$folder_name;
}
}

function TemplatesRoot($page_name){
include('templates/'.$page_name);
}

function Template($page_name,$type,$only_root=true){
if(!$only_root){
if(CMS::GetSetting('rwmod_status')==1){
if(file_exists('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type)){
echo '<script>alert(\'found !!\');</script>';
}else{
echo '<script>alert(\'not found !!\');</script>';
}
include('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);
}else{
include('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);
}
}else{
include('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);
}
}
}
################################################## ################################################## ############################
?>



یه موضوعی که هست یکم این نام جدول هاش ویرایش شده تا به سیستم من سازگار بشه.
الان فایل index.tpl رو میشناسه اما از درون پوشه templates.
من میخواهم که درون پوشه ای که در جدول دیتابیس مشخص شده رو هم بره نشون بده. یعنی اونجا مینویسه defaults.
آدرس بشه: templates/defaults

پیشاپیش از کمکتون ممنون.

mbf5923
دوشنبه 15 مهر 1392, 01:07 صبح
یه راه ساده برای این کار استفاده از file_get_contents هست تحقیق کنید به نتیجه های خوبی میرسید

pasargadteam
دوشنبه 15 مهر 1392, 01:20 صبح
ممنون بابت راهنماییتون. حتماً و خبرش رو در ادامه در اینجا میگم. اما اگر دوست دیگری نظری داره بهم بگه ممنون میشم.

pasargadteam
دوشنبه 15 مهر 1392, 16:36 عصر
در کلاس زیر کجای کار مشکل داره:



function GetSetting($name){
if($name!="selected_template"){
$row=@mysql_fetch_array(mysql_query("select * from settings where sitetemplate='".$name."'"));
return $row['sitetemplate'];
}else{
$row=@mysql_fetch_array(mysql_query("select * from settings where sitetemplate='".$name."'"));
return $row['sitetemplate'];
}
}


که در کلاس زیر خطا میده؟



function Template($page_name,$type,$only_root=true){
if(!$only_root){
if(CMS::GetSetting('rwmod_status')==1){
if(file_exists('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type)){
echo '<script>alert(\'یافت شد !!\');</script>';
}else{
echo '<script>alert(\'یافت نشد !!\');</script>';
}
include('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);
}else{
include('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);
}
}else{
include('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);
}
}


خطاش هم اینو میزنه:



Warning: include(templates//index.tpl) [function.include (http://localhost/PCMS/pesc/function.include)]: failed to open stream: No such file or directory in C:\wamp\www\CMS\inc\cms.template.inc.php on line 46


خط 46 میشه آخرین انکلود در کلاس تمپلیت که هست:



include('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);


ممنون میشم کسی اینو بررسی کنه و بهم بگه.

MRmoon
دوشنبه 15 مهر 1392, 16:58 عصر
ميگه فايل اينكلود شده موجود نيست!

mbf5923
دوشنبه 15 مهر 1392, 18:18 عصر
این خط رو تغییر بدید البته ویندوز به این گیر نمیده اما...

include('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);
به

include('templates'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);

pasargadteam
دوشنبه 15 مهر 1392, 21:04 عصر
ميگه فايل اينكلود شده موجود نيست!
بله این رو کاملاً واضح میگه اما مشکل اینجاست که فایل index.tpl درون پوشه templates وقتی هست کار میکنه اما وقتی میزارم در پوشه ای که defaults در دیتابیس معرفی شده نمیره پوشه رو بخونه.
یعنی در اصل میخام با کدی که نوشته شده بره از پوشه defaults در پوشه اصلی قالب که templates هست فایل ها رو بخونه اما نمیخونه.
امیدوارم واضح گفته باشم.


این خط رو تغییر بدید البته ویندوز به این گیر نمیده اما...

include('templates/'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);
به

include('templates'.$this->GetSetting('selected_template').'/'.$page_name.'.'.$type);

این کاری که شما فرمودید فقط templates//index.tpl به templates/index.tpl تبدیل میشه. مشکل من عدم خوندن فایل از درون پوشه ای که در دیتابیس اعلام شده هست.

mbf5923
دوشنبه 15 مهر 1392, 22:08 عصر
اصلا این تابع

function GetSetting($name){
if($name!="selected_template"){
$row=@mysql_fetch_array(mysql_quer y("select * from settings where sitetemplate='".$name."'"));
return $row['sitetemplate'];
}else{
$row=@mysql_fetch_array(my sql_query("select * from settings where sitetemplate='".$name."'"));
return $row['sitetemplate'];
}
}
قراره چه کاری انجام بد؟
شما توی این تابع میگین هرجا sitetemplate=$name و بعد همین خونه رو واکشی میکنید!!!
خوب این که میشه همون $name !!!

pasargadteam
سه شنبه 16 مهر 1392, 15:21 عصر
اصلا این تابع

function GetSetting($name){
if($name!="selected_template"){
$row=@mysql_fetch_array(mysql_query("select * from settings where sitetemplate='".$name."'"));
return $row['sitetemplate'];
}else{
$row=@mysql_fetch_array(mysql_query("select * from settings where sitetemplate='".$name."'"));
return $row['sitetemplate'];
}
}
قراره چه کاری انجام بد؟
شما توی این تابع میگین هرجا sitetemplate=$name و بعد همین خونه رو واکشی میکنید!!!
خوب این که میشه همون $name !!!

داخل دیتابیس جدولی هست به نام settings و داخل اون یک Row هست که نامش sitetemplate است. الان دستی داخلش زدم defaults که اسم پوشه اصلی مربوط به قالب است.
حالا این کلاس میخواهم بره و از این مورد ها که گفته بخونه و جای $name بیاد defaults رو بنویسه.
امیدوارم درست نوشته باشم کلاسش رو اگر نه ممنون میشم بهم بگید باید چه کنم.

mbf5923
سه شنبه 16 مهر 1392, 15:27 عصر
اینی که شما الان نوشتی در حقیقت اینکار رو میکنه یعنی با این تابع هیچ تفاوتی نداره:


function GetSetting($name){
return $name;
}
ساختار تیبل مورد نظر رو بگین تا اصلاحش کنیم

pasargadteam
سه شنبه 16 مهر 1392, 15:31 عصر
اینی که شما الان نوشتی در حقیقت اینکار رو میکنه یعنی با این تابع هیچ تفاوتی نداره:


function GetSetting($name){
return $name;
}
ساختار تیبل مورد نظر رو بگین تا اصلاحش کنیم

اینم ساختار جدول.




CREATE TABLE IF NOT EXISTS `settings` (
`sitetemplate` text NOT NULL,
`sitetitle` text NOT NULL,
`sitekeywords` text NOT NULL,
`sitedescription` text NOT NULL,
`siteheadcode` text NOT NULL,
`sitefavicon` text NOT NULL,
`sitetelephone` text NOT NULL,
`sitefax` text NOT NULL,
`mobile` text NOT NULL,
`siteemail` text NOT NULL,
`siteaddress` text NOT NULL,
`siteyahooid` text NOT NULL,
`sitegtalkid` text NOT NULL,
`livesupports` text NOT NULL,
`siteskype` text NOT NULL,
`sitefacebook` text NOT NULL,
`sitetwitter` text NOT NULL,
`sitegoogleplus` text NOT NULL,
`siteyoutube` text NOT NULL,
`sitelinkedin` text NOT NULL,
`adminid` int(11) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=latin1;

mbf5923
سه شنبه 16 مهر 1392, 15:57 عصر
خوب این تیبیل که همیشه یه row بیشتر نداره و شما فقط کافیه مقدار همون یک row رو چک کنید


function GetSetting(){

$row=@mysql_fetch_array(mysql_query("select * from settings"));
return $row['sitetemplate'];

}

pasargadteam
سه شنبه 16 مهر 1392, 16:03 عصر
خوب این تیبیل که همیشه یه row بیشتر نداره و شما فقط کافیه مقدار همون یک row رو چک کنید


function GetSetting(){

$row=@mysql_fetch_array(mysql_query("select * from settings"));
return $row['sitetemplate'];

}

به دلیل اینکه نحوه فراخوانی در فایل index.php به شرح ذیل بود:


$cms=new CMS;
$cms->root_templates_folder = 'templates/';
$cms->selected_template = $cms-> GetSetting('selected_template');
$cms->Template('index','tpl');

کد رو اینطور نوشتم و درست شد:


function GetSetting($name){
if($name!="selected_template"){
$row=@mysql_fetch_array(mysql_query("select * from settings where sitetemplate='".$name."'"));
return $row['sitetemplate'];
}else{
$row=@mysql_fetch_array(mysql_query("select * from settings where sitetemplate='".$name."'"));
return $row['sitetemplate'];
}
}


حالا نحوه کدم و فراخوانیم درسته؟
اگر مشکلی هست بفرمایید ممنون میشم در غیر این صورت که هیچ.
در نهایت از همکاری و حمایت و لطف شما صمیمانه سپاسگذارم.

thacker
سه شنبه 16 مهر 1392, 16:20 عصر
بی زحمت کد کامل رو اینجا بزارید ما هم استفاده کنیم.
تشکر ...

mbf5923
سه شنبه 16 مهر 1392, 16:35 عصر
آخه توی این کد شما دارید چیزی رو از دیتابیس select میکنید که مقدارش رو میدونید

$row=@mysql_fetch_array(mysql_query("select * from settings where sitetemplate='".$name."'"));
return $row['sitetemplate'];
مثلا اگه $name برابر 1 باشه return $row['sitetemplate'] هم همسن مقدار رو برمیگردونه و اگه 2 باشه 2 برمیگردونه و....
یعنی عملا این select کار خاصی نمیکنه

pasargadteam
پنج شنبه 18 مهر 1392, 00:58 صبح
ممنون از پاسخگوییتون.
الان یک مشکل دارم , برای فایل ها میخواهم که TemplateFolder پشت هر فایل مینویسم خودش اتوماتیک بنویسه: templates/defaults و یا هر فودر دیگه ای که در دیتابیس نام قالب داده شده بود و در نهایت پوشه css , JS و ... رو بشه آدرس دهی کرد.
این رو چطور بنویسم نمیدونم.
مثلاً:


<?php CMS::TemplateFolder('css');?>/styles.css

بشه:


templates/defaults/css/styles.css

pasargadteam
پنج شنبه 18 مهر 1392, 16:25 عصر
ممنون از دوستانی که کمک کردند. مشکل مرتفع شد.