PHP include függvény használata

PHP include függvény használata
2021-02-11T10:11:35+01:00
2021-03-06T16:33:50+01:00
2022-12-06T18:05:39+01:00
*deleted_23419333
Sziasztok!

Van egy config.php fájl, ami adott és tilos szerkesztenem:

define ('DB','mysqli'); $host = 'localhost'; // stb. require_once 'modules.php';

A modules.php és egyéb fájlok nem léteznek, viszont nekem szükségem van a config.php fájlban található változókra (pl. $host) és define függvényekkel meghatározott értékekre.

A kérdésem. Hogyan tudnám úgy beinclude-olni a config.php fájlt, hogy ne kapjak hibaüzenetet például a modules.php fájl hiányából fakadóan vagy van-e valakinek jobb ötlete?

Az index.php fájlom:

<?php include('config.php'); if(DB == 'mysqli'){ $mysqli = new mysqli($host, ...
Mutasd a teljes hozzászólást!
Hali!

Viszont ami biztos, hogy nekem csak a define függvények kellenek.

Egy „hevenyészett” megoldás, iránymutatónak:
$configText = file_get_contents('path/to/config.php'); $pattern = '/define\s*\(\s*([\'\"])(?<name>.+?)\1\s*,\s*(?<value>([\'\"]).*?\4|[^,)]+)\s*(?:,\s*(?<ci>[^)]+))?\)/isu'; $consts = []; if (preg_match_all($pattern, $configText, $m)) { foreach ($m['name'] as $i => $name) { eval(sprintf('$value = %s; $ci = %s;', $m['value'][$i], ($m['ci'][$i] ?: 'false'))); $consts[$name] = ['value' => $value, 'ci' => $ci]; } }
A lefutás után a $consts asszociatív tömbben találhatod a konstansok értékét és azt, hogy case-insensitive módon is elérhetők-e. Az eval()-t kilőheted (habár ekkor picit bonyolódik a tényleges érték és típus meghatározása), ha tutira csak konstans értékek (és konstans – true/falsecase-insensitive flag-ek) vannak a define()-okban.

Mutasd a teljes hozzászólást!

  • Készíts egy üres modules.php fájlt !

    Viccet félretéve... ha nem léteznek azok a fájlok, akkor mi a búbánatért akarja behúzni a config (vagy bármi más)?
    Mutasd a teljes hozzászólást!
  • Olvasd be stringbe a configot és szedd ki belőle.
    Mutasd a teljes hozzászólást!
  • Nem rossz elgondolás, csak szerintem túl bonyolult. Gondolom a file_get_contents függvénnyel tudnám beolvasni string-ként a fájlt, aztán:

    - define (kis- és nagybetű)
    - lehet szóköz, tabulátor, sortörés és bekezdéstörés vagy semmi
    - (
    - lehet szóköz, tabulátor, sortörés és bekezdéstörés vagy semmi
    - ' vagy "
    - 1. adat
    - ' vagy " (figyelembe kéne azt is venni, hogy az 1. adat előtt milyen karakter volt)
    - lehet szóköz, tabulátor, sortörés és bekezdéstörés vagy semmi
    - ,
    - lehet szóköz, tabulátor, sortörés és bekezdéstörés vagy semmi
    - ' vagy "
    - 2. adat
    - ' vagy " (figyelembe kéne azt is venni, hogy a 2. adat előtt milyen karakter volt)
    - lehet szóköz, tabulátor, sortörés és bekezdéstörés vagy semmi
    - )
    - lehet szóköz, tabulátor, sortörés és bekezdéstörés vagy semmi
    - ;

    (Ez így igaz lenne egyáltalán?)
    Mutasd a teljes hozzászólást!
  • Egy új rendszert készítek és a megrendelő kérése, hogy a config.php fájlhoz ne nyúljak mert a régi rendszerükkel ennek a fájlnak kompatibilisnek kell lennie, ha esetleg azt vissza akarják majd állítani stb. Ugyanígy a MySQL táblákhoz se nyúlhatok, de azzal nincs problémám.
    Mutasd a teljes hozzászólást!
  • Ha ez most egy haldokló rendszer statikus része akkor csak egyszer kiolvasod és beilleszted.
    Ha meg darabolás mellett döntesz:
    strtoupper - a define vizsgálatához
    str_replace - az aposztróf "szabványosításához"
    explode(",",   - az értékpárok kinyeréséhez
    trim - mindig jól jön

    Szerencsére nem kell minden lehetséges variációt leprogramozni, csak amit az elődöd használt.
    Mutasd a teljes hozzászólást!
  • A strtoupper függvényt nem használhatom mert akkor a változók értékeit is felnagyítja, például a kis- és nagybetűs jelszavaknál.

    A config.php jelenleg is használatban van a régi rendszerrel, így ez még változhat. Amit most megkaptam, az nem kizárt, hogy változni fog. Ezért is lenne jó mindenre felkészülni. Viszont ami biztos, hogy nekem csak a define függvények kellenek. A sima változók nem, mint például a $host sem fog kelleni. Ezek csak benne maradtak a fájlban mert később tértek át a csak define fv. használatára. Tehát a $host is meg van így: define('HOST','localhost');
    Mutasd a teljes hozzászólást!
  • A strtouppert csak rutinból írtam, a keresés egyszerűsítésére, természetesen a változókat az eredet formájú sorból kell kibányászni.
    A feladat és a jelenlegi környezet ismerete nélkül többet mondani nehéz.
    Azért arra lehet számítani, hogy nem fognak variálni a megszokott stílusukon.

    Talán érdemes figyelni a kritikus változók meglétét, változását is.
    Számít, hogy milyen időhosszon kell párhuzamos működéssel számolni, érzékelhető-e egy változó hiánya, milyen problémát okoz.
    Mindenképpen a feldolgozást preferálnám, mert a betöltés esetleg mást is átdeffiniálhat nálad.
    Mutasd a teljes hozzászólást!
  • Hali!

    Viszont ami biztos, hogy nekem csak a define függvények kellenek.

    Egy „hevenyészett” megoldás, iránymutatónak:
    $configText = file_get_contents('path/to/config.php'); $pattern = '/define\s*\(\s*([\'\"])(?<name>.+?)\1\s*,\s*(?<value>([\'\"]).*?\4|[^,)]+)\s*(?:,\s*(?<ci>[^)]+))?\)/isu'; $consts = []; if (preg_match_all($pattern, $configText, $m)) { foreach ($m['name'] as $i => $name) { eval(sprintf('$value = %s; $ci = %s;', $m['value'][$i], ($m['ci'][$i] ?: 'false'))); $consts[$name] = ['value' => $value, 'ci' => $ci]; } }
    A lefutás után a $consts asszociatív tömbben találhatod a konstansok értékét és azt, hogy case-insensitive módon is elérhetők-e. Az eval()-t kilőheted (habár ekkor picit bonyolódik a tényleges érték és típus meghatározása), ha tutira csak konstans értékek (és konstans – true/falsecase-insensitive flag-ek) vannak a define()-okban.

    Mutasd a teljes hozzászólást!
  • Néhány dolgot nem értek...
    A "régi" rendszerükben gondolom megvan a modules.php, ellenkező esetben ugye ott sem működne a dolog.

    Ezt a config.php-t az eredeti helyén birizgálod, vagy egy másolaton dolgozol "magadnál", ahol nincs meg a többi (számodra szükségtelen) fájl?
    Mutasd a teljes hozzászólást!
  • > Készíts egy üres modules.php fájlt

    Ebben a helyzetben ez a kézenfekvő megoldás.
    Mutasd a teljes hozzászólást!
  • Ez a megoldás vicces, de a helyzet is az.

    Mellesleg továbbra sem értem a dolgot...

    Ha az eredeti környezetben van a config.php, akkor a többi fájlnak is ott kellene lennie (ergo mehet az include/require), ha pedig egy másolaton dolgozik, akkor meg nem mindegy, hogy belenyúl-e vagy sem?

    Ha az első eset áll fent, akkor így látatlanban azt a problémát tudom elképzelni, hogy más a current working directory, de ezt meg ugye lehetne orvosolni... de ez is csak találgatás.
    Mutasd a teljes hozzászólást!
  • Úgy tudom elképzelni, hogy szoftlinkkel vagy hasonlóval emeli be ezt config.php-t a saját fájlait tartalmazó könyvtárba; esetleg kiegészítve azzal, hogy nemhogy módosítani nem szabad, de (az éles változatban) nem is láthatja a tartalmát, mert azonosítók+jelszavak vannak benne.
    Mutasd a teljes hozzászólást!
  • Lehet...
    Ha így van, akkor pedig kapásból egyszerűbb lenne egy saját konfig a dev/test környezetre, amit a prod-ra nem küld ki és kész. Ez esetben inkább deployment/buildscript jellegű a témakör
    Mutasd a teljes hozzászólást!
  • Szia!
    Ha zavarnak a hibaüzenetek, akkor tiltsd le :

    error_reporting(0);
    Mutasd a teljes hozzászólást!
  • Ettől továbbra is el fog romlani az egész, csak nem látszik majd, hogy miért...
    Mutasd a teljes hozzászólást!
  • Egy új rendszert készítek és a megrendelő kérése, hogy a config.php fájlhoz ne nyúljak

    Az illeszkedéshez lehet szükséges bizonyos változók aktuális értékére az élő rendszerből.
    Amit nem használok azt nem is keresem mert minek. Lehetne erre is gyúrni.

    Egyébként Netangel megoldása szép és működik is -gondolom.

    (Más változó config.php-ját látatlanba nem futtatnám, de ez az én paranoiám.)
    Mutasd a teljes hozzászólást!
  • Még 1 utolsó javaslat:
    Ez is elég gané, de ha legalább annyira rá tudod venni őket, hogy a config.php-ban require helyett include-ot használjanak, akkor az elméletileg nem fog "fatal" hibát dobni, a script le fog futni (és így meg tudod szerezni a config-ban definiált dolgokat).
    Warning ugyan lesz, de azt meg lenyelheted a saját oldaladon pl. egy kukacos include-dal.
    Mutasd a teljes hozzászólást!
  • Köszönöm a segítséget és elnézést, hogy csak most reagálok. Sikerült lefixálni a részleteket a céggel.

    Összefoglalva:

    1. Minden define(); új sorban kezdődik.
    2. A define( után van egy szóköz, de előtte semmi.
    3. Egy ' karakter.
    4. Nagybetűs konstans név, például: ABC_XYZ (csak az angol ABC nagybetűi és alsóvonal, de mindig nagybetűvel kezdődik és végződik, tehát az első és az utolsó karakter nem lehet alsóvonal)
    5. Egy ' karakter.
    6. Vessző: ,
    7. Egy vagy több szóköz.
    8. Egy ' karakter.
    9. A változó értéke ami vegyesen tartalmaz kis- és nagybetűket, számokat és mindenféle karaktert a szóköz kivételével.
    10. Egy ' karakter.
    11. Egy szóköz.
    12. );

    Példák:

    define( 'SQL_CHAR', 'utf8' ); define( 'X_KEY', 'jP9#vD6!dW2_dF7!' );

    Ennek a leírásnak is megfelel a $pattern, illetve a fenti 12 pontot figyelembe véve nem lehetne egyszerűsíteni azt, hogy én, mint földi halandó is jobban átlássam és értsem?

    Továbbá sajnos változók is lehetnek a fájlban.

    Példák:

    $dt = 'est_'; $n_x = 13;
    Ezek minden esetben:

    1. Minden változó új sorban kezdődik.
    2. A $ karakter előtt nincs semmi.
    3. A változó nevében csak az angol ABC kisbetűi szerepelhetnek. Mindig betűvel kezdődik és arra is végződik, de lehet benne egy vagy több alsóvonal is.
    4. Az egyenlőség jel előtt és után mindig van egy-egy szóköz, több nem fordulhat elő.
    5a. A változó értéke előtt és után van egy-egy ' karakter (ha string) vagy
    5b. A változó értéke előtt és után nincs semmi mert az érték egy szám.
    6. Ha string, akkor az angol ABC kisbetűiből, számokból, kötőjelből, alsóvonalból és pontból állhat.
    7. Ha szám, akkor csak számokat tartalmaz, tehát pontot, vesszőt és más egyebet nem.
    8. Ha string, akkor a második aposztróf után mindig ; karakter következik, illetve ha szám, akkor a szám után következik ez.

    Erre egy egyszerűbb valamit még ki lehetne találni?

    Sajnos nem tudom felbecsülni, hogy mekkora munka két ilyen reguláris kifejezést megírni, viszont muszáj így megoldanom a dolgot, mármint, hogy a PHP fájlt string-ként beolvasni és abban bányászni. Én csak explode függvénnyel tudnék gányolni valamit, amit viszont nem szeretnék.
    Mutasd a teljes hozzászólást!
  • Azt a részt nem olvastad, hogy csinálj egy üres modules.php fájlt, vagy csak átsiklott rajta a figyelmed?
    Mutasd a teljes hozzászólást!
  • A régi és az új rendszer között .htaccess fájllal váltanak, valahogy így:

    <IfModule mod_env.c> SetEnv rendszer uj SetEnv rendszer regi </IfModule>

    És ráadásul még több alkalmazás is használja ezt a config.php fájlt. Megtehetném, hogy @ karakterrel vagy máshogy figyelmen kívül hagyom a hibákat, de jobb lenne beolvasni a fájlt karakterláncként és azt feldolgozni.
    Mutasd a teljes hozzászólást!
  • Nem, nem lenne jobb. Ugye a gond az, hogy egy olyan config-fájlt kell használnod, amit kiemeltek az eredeti környezetéből, és áttették az új környezetbe, ahol viszont a hivatkozolott elemei (modules.php) hiányoznak. Normálisan ugye ki kellene szervezni belőle azokat a részeket, amik az újhoz is kellenek, mondjuk `config_core.php` néven (és persze a `config.php` is include-dal emelné be a `config_core.php`-t).
    Namostan ha ez nem megy, akkor az ésszerű megoldás az, amit rögtön a legelső hsz-ben javasoltak neked: odatenni egy üres modules.php-t.
    Mutasd a teljes hozzászólást!
  • Azóta mióta kiírtam a kérdést változott néhány dolog vagyis inkább csak pontosítva lettek ezek. Van, illetve inkább úgy írnám, hogy vagy van vagy nincs modules.php fájl, de én nem hozhatom létre. Attól függ, hogy ők fent hagyják-e vagy sem. Én csak az uj mappába dolgozhatok és a gyökérkönyvtárból csak olvasási jogom van a config.php fájlhoz, semmi egyéb.

    A régi rendszer a gyökérkönyvtárba van telepítve:

    ~/index.php ~/.htaccess ~/config.php ~/modules.php

    Az új rendszer, amit én fejlesztek az az uj mappában van:

    ~/uj/index.php

    A régi és az új rendszer közti váltáshoz a kulcs a .htaccess fájl.

    A régi rendszer esetén:

    SetEnv rendszer regi RewriteEngine On RewriteCond %{REQUEST_FILENAME} !-f RewriteRule ^ index.php [L]

    Az új rendszer esetén:

    SetEnv rendszer uj RewriteEngine On RewriteBase /uj RewriteCond %{REQUEST_FILENAME} !-f RewriteRule ^ index.php [L]

    A getenv függvényt használva tudom meg, hogy melyik épp az éles rendszer. A .htaccess fájlt esetleg nem lehetne úgy szerkeszteni, hogy amikor az új rendszer az éles, akkor a ~/modules.php fájlt ráirányítani az ~/uj/modules.php üres fájlra? Ezt még megtudnám beszélni velük, hogy módosítsuk a .htaccess fájlt amikor az én rendszerem van aktiválva.

    Mivel kitudja még mi kerül a config.php fájlba, így szerintem mindenképp jobb lenne beolvasni azt string-ként és kinyerni belőle a konstansokat meg a változókat mert az legalább már le lett fixálva, hogy milyen formátumúak lehetnek.
    Mutasd a teljes hozzászólást!
  • Tudnál segíteni?

    Ez működik:

    define\( '(?<name>.+?)',(\s*)'(?<value>.+?)' \);

    Ez is, de sajnos nem úgy ahogy szeretném:

    \$(?<name>.+?) = (?<value>.+?);

    Utóbbival sajnos hiába szenvedek, nem jövök rá a megoldásra.

    $abc = 123; $cba = '321';

    A $abc esetén tökéletes, de az aposztrófok miatt a $cba nem jó mert '321' helyett csak 321-et szeretnék kapni.
    Mutasd a teljes hozzászólást!
  • > A .htaccess fájlt esetleg nem lehetne úgy szerkeszteni, hogy amikor az új rendszer az éles, akkor a ~/modules.php fájlt ráirányítani az ~/uj/modules.php üres fájlra?

    A php include és require művelete nem használja a .httaccess-t, azt csak az httpd használja.
    Neked valami ilyesmi kellene:

    +-------------------------------+ | ezthivduser.php | +-------------------------------+ | if (...) { | | chdir ('uj'); | | require './index.php'; | | } else { | | chdir ('regi'); | | require './index.php'; | | } | +-------------------------------+
    tehát regi alatt lennének a régi fájlok, köztük a regi/config.php és a regi/modules.php; uj alatt pedig az új fájlok; de az uj/config.php egy szimlink lenne a ../regi/config.php-re, az uj/modules.php pedig egy üres fájl.
    Mutasd a teljes hozzászólást!
  • Hali!

    … viszont muszáj így megoldanom a dolgot, mármint, hogy a PHP fájlt string-ként beolvasni és abban bányászni.

    Pedig én is csak azt tudom mondani – csatlakozván az előttem szólókhoz –, hogy más megoldás után kellene nézned. Te most kvázi egy PHP-interpretert (-szerűséget) szeretnél készíteni, még hogy ha csak egy egyszerűt is.

    Irányadónak itt egy – szintén „hevenyészett” – megvalósítás. Direkt nem reguláris kifejezésekkel, hanem tokenizálással megoldva:
    $configText = file_get_contents('path/to/config.php'); // A PHP-s nyitó- és záró-tag, valamint a whitespace-ek tokenjeinek kiszűrése $tokens = array_values(array_filter(token_get_all($configText, TOKEN_PARSE), function($t) { return !is_array($t) || !in_array($t[0], [T_OPEN_TAG, T_CLOSE_TAG, T_WHITESPACE]); })); // Érték meghatározása function getValue($token) { $value = null; if (is_array($token)) { switch ($token[0]) { case T_LNUMBER: $pattern = '/^(?<s>[+-])?\s*0(?:x(?<x>[0-9a-f]+)|b(?<b>[01]+)|(?<o>[0-7]+)|(?<d>[0-9]+))$/i'; if (preg_match($pattern, $token[1], $m)) { $m = array_merge(['s' => '+', 'x' => 0, 'b' => 0, 'o' => 0, 'd' => 0], $m); $value = ($m['s'] === '-' ? -1 : 1) * ($m['x'] ? hexdec($m['x']) : ($m['b'] ? bindec($m['b']) : ($m['o'] ? octdec($m['o']) : 0))); } else { $value = intval($token[1]); } break; case T_DNUMBER: $value = floatval($token[1]); break; case T_CONSTANT_ENCAPSED_STRING: $value = mb_substr($token[1], 1, -1); break; case T_STRING: switch (mb_strtolower($token[1])) { case 'true': $value = true; break; case 'false': $value = false; break; default: $value = null; break; } break; } } return $value; } // Konstans feldolgozása function parseConstant(&$symTable, $nameToken, $valueToken, $closeToken = '', $ciToken = '') { $advance = 4; $parsed = [ //'type' => token_name(T_CONST), 'type' => T_CONST, 'name' => $nameToken[1], 'value' => getValue($valueToken), 'ci' => false ]; if ($nameToken[0] === T_CONSTANT_ENCAPSED_STRING) { $parsed['name'] = mb_substr($nameToken[1], 1, -1); $advance += 2; } if ($closeToken === ',' && $ciToken[0] === T_STRING) { $parsed['ci'] = mb_strtolower($ciToken[1]) === 'true'; $advance += 2; } $symTable[] = $parsed; return $advance; } // Változó feldolgozása function parseVariable(&$symTable, $nameToken, $valueToken) { $advance = 3; $parsed = [ //'type' => token_name(T_VARIABLE), 'type' => T_VARIABLE, 'name' => mb_substr($nameToken[1], 1), 'value' => getValue($valueToken), 'ci' => false ]; $symTable[] = $parsed; return $advance; } // Szimbólum-tábla, a konstansokat és változókat tartalmazza $symTable = []; $tokPtr = 0; $numOfToks = count($tokens); while ($tokPtr < $numOfToks) { if (is_array($tokens[$tokPtr])) { $func = ''; switch ($tokens[$tokPtr][0]) { case T_CONST: $func = 'parseConstant'; $params = [&$symTable, $tokens[$tokPtr + 1], $tokens[$tokPtr + 3]]; break; case T_VARIABLE: $func = 'parseVariable'; $params = [&$symTable, $tokens[$tokPtr], $tokens[$tokPtr + 2]]; break; case T_STRING: if (preg_match('/^define$/i', $tokens[$tokPtr][1]) && $tokens[$tokPtr + 1] === '(') { $func = 'parseConstant'; $params = [&$symTable, $tokens[$tokPtr + 2], $tokens[$tokPtr + 4], $tokens[$tokPtr + 5], $tokens[$tokPtr + 6]]; } break; } $tokPtr += $func ? call_user_func_array($func, $params) : 0; } $tokPtr++; } var_dump($symTable);
    A lefutás után a $symTable tömb minden egyes elem egy asszociatív tömb az adatokkal: változó vagy konstans – T_VARIABLE/T_CONST –, neve, értéke és hogy lehet-e használni case-insensitive módon (értelemszerűen, csak konstansoknál van értelme). A jellemzők/korlátok:
    – csak hibamentes PHP-kód esetén működik,
    – csak önmagában megadott változók lehetnek (változóval megadott – pl.: $$var = …; – nem),
    – konstansoknál mind a const …, mind a define() megadás lehetséges,
    – nem lehet felsorolás, minden értékadás külön – pontosvesszővel elválasztott – utasítás,
    – értékek csak skaláris értékek lehetnek (tömb, objektum, ill. műveletekkel meghatározott nem).

    Mutasd a teljes hozzászólást!
  • Köszönöm a hozzászólásokat. Még nem hallottam ezekről a tokenekről, így örülök, hogy tanulhatok valami újat, viszont hétfőn rácsapok az asztalra. Igaz, hogy home office-ban, de na... Szóval NevemTeve hozzászólása alapján kérni fogom, hogy legyen egy config_core.php fájl vagy részemről ennyi volt ez a történet.
    Mutasd a teljes hozzászólást!
Tetszett amit olvastál? Szeretnél a jövőben is értesülni a hasonló érdekességekről?
abcd