Autor Zpráva
watchick
Profil
Dobrý den,
chtěl bych se zeptat, jak by se dala udělat následující věc:
mám text, například:
Dobrý den,
dneska je {program:den} a ve 12 hodin bude zatmění slunce (právě je {program:hodiny24} hodin)
Zde je tabulka s minulými zatměními, můžete se pokochat a předpovědět si, kdy to zase přijde:
{program:zatmeni_history}
Upozornění, nekoukat do přímého slunce!

Potřebuji, aby se místo každého programu naincludoval soubor "plugins/%nazev%.php";
tedy například namísto: {program:zatmeni_history} by se zobrazil výsledek scriptu z "plugins/zatmeni_history.php"
Já bych to asi dělal hloupě přes explode, následně pak získal nějak ten keyword a provedl to přes ob_flush bych zachytil obsah a pak ho tam vložil. na ten ob_get to vidím tak či tak. Nemohli byste mi prosím napsat kód se kterým se zachytí ten "program" element a získá se z něj ten keyword?

Děkuji
Watchick
mckay
Profil
watchick:
function getBuffer($file) {
            ob_start();

            include($file) ;
            
            $buffer = ob_get_contents(); 

            ob_end_clean();

            return $buffer;
        }

$text  = "Dobrý den,
dneska je {program:den} a ve 12 hodin bude zatmění slunce (právě je {program:hodiny24} hodin)
Zde je tabulka s minulými zatměními, můžete se pokochat a předpovědět si, kdy to zase přijde:
{program:zatmeni_history}
Upozornění, nekoukat do přímého slunce!";

$text = str_replace("{program:den}", getBuffer("cesta/k_souboru.php"), $text);
Třeba takhle by to šlo.
Alphard
Profil
[#2] mckay
Dovolím si nepovažovat to za šťastnou implementaci. Ten 19. řádek by se volal samostatně pro každou funkci?

watchick:
Je problém ty vaše pluginy vytvořit jako funkce/metody, které nic nevypisují, ale vrací řetězce přes return? Pak by to šlo elegantně vložit do šablony.
mckay
Profil
Alphard:
To už záleží na něm - já to mám podobně, ale přes preg_replace_callback(); ještě s nějakou metodou. A také mám trochu jinou strukturu {proměnné}.
watchick
Profil
Tak jestli by to nějakým způsobem pomohlo, tak by třeba mohla být v každém pluginu stejně nazvaná funkce která by vracela string přes return, především co potřebuji je získat všechny ty keywods, které v textu jsou, popřípadě, kdybych měl seznam všech těch "program"ů, které se v textu vyskytují, tak to mohu znova projet přes str_replace
[#2] mckay
Díky, ale tohle jsem úplně neměl na mysli, tohle bych samozřejmě dokázal napsat také. Jde mi to to, abych, jak podotknul Alphard, nemusel pro každý program vypisovat str_replace
Alphard
Profil
watchick:
Tak jestli by to nějakým způsobem pomohlo, tak by třeba mohla být v každém pluginu stejně nazvaná funkce která by vracela string přes return,
Byl by to mnohem lepší návrh. Vyhnul byste se ob_get_contents(). Navíc by pro každou drobnost nemusel být samostatný soubor.

Makra by mohla vypadat třeba takhle {plugin:Cas::den} a obsah by se bral ze třídy Cas a statické metody den(). Je to mírně složitější, ale zřejmě lepší řešení.

především co potřebuji je získat všechny ty keywods
Už to bylo naznačeno v [#4], seznam vše maker můžete snadno vytáhnout funkcí preg_match_all() případně s preg_replace_callback() ihned nahrazovat.
watchick
Profil
<?php
$line = "Dobrý den,
dneska je {program:den} a ve 12 hodin bude zatmění slunce (právě je {program:hodiny24} hodin)
Zde je tabulka s minulými zatměními, můžete se pokochat a předpovědět si, kdy to zase přijde:
{program:zatmeni_history}
Upozornění, nekoukat do přímého slunce!";
function replacer($matches)
{
  if($matches[1]=="program")
  { //budu mít pak ještě jiné pluginy, než "program"
    if(file_exists("../plugins/".$matches[2].".php"))
    {
      ob_start();
      include  "../plugins/".$matches[2].".php";
      $return = ob_get_contents();
      ob_end_clean();
    }
  }
return $return;
}
echo preg_replace_callback("|{(.*):(.*)}|U","replacer",$line);
?>

Nakone to dopadlo takhle.
Přijde mi to prostě hrozně jednoduché v tom směru, že když budu potřebovat udělat nějakou blbost, tak prostě vložím php soubor do adresáře a normálně to vypíšu.
Je ten regulární výraz špatně?

Momentálně mi to funguje, ale to také nemusí znamenat, že je to v pořádku.
Díky moc na pomoc
Mastodont
Profil
      ob_start();
      include  "../plugins/".$matches[2].".php";
      $return = ob_get_contents();
      ob_end_clean();
      ...
      return $return;


Pokud v tom includovaném souboru použiješ return (viz Example #5 include() and the return() statement v manuálu k include), můžeš to zkrátit na:
return include  "../plugins/".$matches[2].".php";
watchick
Profil
Mastodont:
pravděpodobně tam nechám echo
AM_
Profil
watchick:
Přijde mi to prostě hrozně jednoduché v tom směru, že když budu potřebovat udělat nějakou blbost, tak prostě vložím php soubor do adresáře a normálně to vypíšu.
- velké množství include má značný dopad na rychlost vykonávání skriptu, a ve tvém návrhu není velký problém dostat se klidně na stovky include, což může být výkonově problém. Proto Alphard radil psát "pluginy" jako funkce.
- řešení s echo a output bufferem sice funguje, ale řešení přes návratovou hodnotu funkce je o 100% elegantnější.
watchick
Profil
[#10] AM
- řešení s echo a output bufferem sice funguje, ale řešení přes návratovou hodnotu funkce je o 100% elegantnější.
a rychlejší?
watchick
Profil
<?php
$line = "Dobrý den,
dneska je {program:den} a ve 12 hodin bude zatmění slunce (právě je {program:hodiny24} hodin)
Zde je tabulka s minulými zatměními, můžete se pokochat a předpovědět si, kdy to zase přijde:
{program:zatmeni_history}
Upozornění, nekoukat do přímého slunce!";
$includelist = array();
function replacer($matches)
{
  global $includelist;
  if($matches[1]=="program")
  { //budu mít pak ještě jiné pluginy, než "program"
    if(file_exists("../plugins/".$matches[2].".php"))
    {
      if(!$includelist[$matches[2]]){
        include  "../plugins/".$matches[2].".php";
      }
      return "incl_".$matches[2]();
    }
  }
}
echo preg_replace_callback("|{(.*):(.*)}|U","replacer",$line);
?>

tedy samozřejmě za předpokladu, že při makru "{program:den}" bude obsah den.php:
<?php
  function incl_den()
  {
    return date("l");
  }
?>

Za předpokladu, že v každém pluginu, tedy souboru, bude stejnojmenná funkce, a když nebudu chtít nahrávat všechny pluginy, ale jen ty, které jsou v textu skutečně použity, tak když to provedu tímto způsobem, tak se obsah naincludovaného souboru použije pouze pro tuto funkci a při jejím dalším volání by se musel použít znovu, není-liž pravda?
tiso
Profil
watchick: príliš si to komplikuješ…
watchick
Profil
[#13] tiso
Možná.
Ale v případě že to není až tak moc na úkor výkonu, což doufám, že ten poslední návrh není, tak radši si to zkomplikuju teď, a pak mít snadné psaní pluginů
Mastodont
Profil
if(!$includelist[$matches[2]]){
   include  "../plugins/".$matches[2].".php";


To je nějaká fikaná náhrada za include_once? :-)
tiso
Profil
watchick: koľko tých "pluginov" budeš používať pri výpise jednej stránky?
Čo v prípade, keď chceš použiť na jednej stránke 2x {program:den}?
AM_
Profil
watchick:
a rychlejší?
o něco možná ano, to bude zcela zanedbatelné, rozdíl bude možná v řádu stovek nanosekund, pomalejší to téměř jistě nebude. v dnešní době se stejně hraje spíše na čistý, než na nanosekundově optimální kód.
watchick
Profil
bylo to myšleno tak, že v tom souboru bude funkce, a pokud se ta funkce bude opakovat, stačí to nahrát pouze jednou.
To na co se ptám je, zda-li když tu funkci, která je v tom souboru naincluduju v té funkci replace, jestli to, pokud znovu přijde na řadu stejně znějící plugin, bude includovat znovu, nebo jestli to uz bude mít jednou naincludovane
watchick
Profil
tiso:
0-20? víc než 20 asi ne
to je prave ta otazka, jak to z funkce naincludovat do normalniho behu stránky
tiso
Profil
watchick: to je práve dôkaz, že to máš zle vymyslené…
watchick
Profil
tiso:
co je důkaz?
tiso
Profil
watchick: toto: „to je prave ta otazka, jak to z funkce naincludovat do normalniho behu stránky
watchick
Profil
ja jsem se prave ptal, jestli to jde, nebo ten text muzu těma regulárama projet 2krát....
nejprve naincludovat ty soubory, a pomtom akorát nahrát ty funkce

Vaše odpověď

Mohlo by se hodit


Prosím používejte diakritiku a interpunkci.

Ochrana proti spamu. Napište prosím číslo dvě-sta čtyřicet-sedm:

0