Autor Zpráva
snazimse
Profil
Zdravím všechny,

mám zde poměrně typický problém,při načtení větších php procesů,
standartně to bývá,memory limitem,ale mám na hostingu memory limit 128MB,což by mělo stačit,
atak se ptám je to tím? Ale zjevně ano,nesetkal jsem se nikdy s touto hláškou a vždy to bylo tím,dole přikládám parametry z php info,
např, post_max_size 20M se mi zdá málo,nebo max_input_time -1 atd.Je tam něco co by to mohlo způsobovat?Ať vím,zda si mám pořídit,lepší hosting.

Děkuji všem

Fatal error: Allowed memory size of 134217728 bytes exhausted (tried to allocate 25080 bytes)





Directive    Local Value    Master Value
allow_call_time_pass_reference    On    On
allow_url_fopen    On    On
allow_url_include    Off    Off
always_populate_raw_post_data    Off    Off
arg_separator.input    &    &
arg_separator.output    &    &
asp_tags    Off    Off
auto_append_file    no value    no value
auto_globals_jit    On    On
auto_prepend_file    no value    no value
browscap    no value    no value
default_charset    no value    no value
default_mimetype    text/html    text/html
define_syslog_variables    Off    Off
disable_classes    no value    no value
disable_functions    eval,apache_get_modules,apache_get_version,apache_getenv,apache_note,apache_setenv,ddisk_free_space,dddiskfreespace,dl,highlight_file,ini_alter,ini_restore,openlog,passthru,proc_nice,shell_exec,show_source,symlink,system,exec    eval,apache_get_modules,apache_get_version,apache_getenv,apache_note,apache_setenv,ddisk_free_space,dddiskfreespace,dl,highlight_file,ini_alter,ini_restore,openlog,passthru,proc_nice,shell_exec,show_source,symlink,system,exec
display_errors    On    On
display_startup_errors    Off    Off
doc_root    no value    no value
docref_ext    no value    no value
docref_root    no value    no value
enable_dl    On    On
error_append_string    no value    no value
error_log    /var/log/php.log    /var/log/php.log
error_prepend_string    no value    no value
error_reporting    30711    30711
exit_on_timeout    Off    Off
expose_php    On    On
extension_dir    /usr/lib64/php/modules    /usr/lib64/php/modules
file_uploads    On    On
highlight.bg    #FFFFFF    #FFFFFF
highlight.comment    #FF9900    #FF9900
highlight.default    #0000CC    #0000CC
highlight.html    #000000    #000000
highlight.keyword    #006600    #006600
highlight.string    #CC0000    #CC0000
html_errors    On    On
ignore_repeated_errors    Off    Off
ignore_repeated_source    Off    Off
ignore_user_abort    Off    Off
implicit_flush    Off    Off
include_path    .:/usr/lib/php    .:/php/includes:/usr/lib/php:/usr/share/php
log_errors    On    On
log_errors_max_len    1024    1024
magic_quotes_gpc    Off    Off
magic_quotes_runtime    Off    Off
magic_quotes_sybase    Off    Off
mail.add_x_header    Off    Off
mail.force_extra_parameters    no value    no value
mail.log    no value    no value
max_execution_time    130    130
max_file_uploads    20    20
max_input_nesting_level    64    64
max_input_time    -1    -1
max_input_vars    6800    6800
memory_limit    128M    256M
open_basedir    /tmp:/u2/www/mail:/usr/lib/php:/u2/www/moje123/data/    no value
output_buffering    no value    no value
output_handler    no value    no value
post_max_size    20M    20M
precision    12    12
realpath_cache_size    16K    16K
realpath_cache_ttl    120    120
register_argc_argv    On    On
register_globals    Off    Off
register_long_arrays    On    On
report_memleaks    On    On
report_zend_debug    On    On
request_order    no value    no value
safe_mode    Off    Off
safe_mode_exec_dir    no value    no value
safe_mode_gid    Off    Off
safe_mode_include_dir    no value    no value
sendmail_from    me@localhost.com    me@localhost.com
sendmail_path    /usr/sbin/sendmail -t -i -f php-mailer@ja1985.cz    /usr/sbin/sendmail -t -i 
serialize_precision    100    100
short_open_tag    On    On
SMTP    localhost    localhost
smtp_port    25    25
sql.safe_mode    Off    Off
track_errors    Off    Off
unserialize_callback_func    no value    no value
upload_max_filesize    64M    64M
upload_tmp_dir    /tmp    /tmp
user_dir    no value    no value
user_ini.cache_ttl    300    300
user_ini.filename    .user.ini    .user.ini
variables_order    EGPCS    EGPCS
xmlrpc_error_number    0    0
xmlrpc_errors    Off    Off
y2k_compliance    Off    Off
zend.enable_gc    On
Joker
Profil
snazimse:
standartně to bývá,memory limitem,ale mám na hostingu memory limit 128MB,což by mělo stačit,
No, nestačí.

Skript vyžadoval více, než 128MB paměti.
snazimse
Profil
Takže 256M,by mělo stačit? Nebo jak to propočítat? Díky
Rfilip
Profil
Záleží na tom co v PHP děláte ale obecně jsou paměťově nejnáročnější změny velikostí obrázku, Spotřebovaná paměť na změnu velkosti se dá odhadnout vzorcem (výška obrázku v pixelech X šířka obrázku v pixelech X 3 X 1.6) , výsledek je v bytech.
snazimse
Profil
Jasně,nejedná s o obrázky,jde o automatické vygenerování xml feed hodně produktů, jedná se o načtení 2500produktů. Díky
Tori
Profil
snazimse:
V jakém e-shopu to je? 2500 produktů by se mělo vejít do 128 M, nezůstávají vám někde viset nějaká data v paměti (nějaké cache apod.)? Skládáte feed v paměti, nebo ukládáte data na disk průběžně po kouskách?
snazimse
Profil
Jedná se o export xml heureka,zbozi.cz pro Opencart.Nevím o tom,ale netuším. Díky
Joker
Profil
snazimse:
Takže 256M,by mělo stačit? Nebo jak to propočítat?
Z dostupných informací víme jen, že to je „víc než 128 MB“. Může to být 129 MB, může to být třeba 3 GB.

Ale taky mi to na generování XML připadá hodně.
pcmanik
Profil
snazimse:
Spravujem jeden obchod, ktorý je postavený na open carte a xml feed sa aktuálne generuje z 2160 produktov, pričom bohate stačí 48MB. Takže chyba bude vo vašom skripte na generovanie xml.
snazimse
Profil
V skriptu chyba tutově nebude,je to official script,nebude tam ,mám to odzkoušené jinde,při méně,produktů.

Maximálně bych připustil reakci od Toriho, data se ukládají na disk,má to asi 1gb,a co jsem se díval celkově celý web,evidentně to dost cachuje na disku v image je nějakých 400mb.Ovšem v hl.system/cache pouze 128kb.Ale nejsem si jistý zda ty obrázky načítá z toho cache ten xml feed? Myslíte,že by to tím mohlo být? Ale opencart automaticky cachuje,a používá ho x lidí,nemyslím si ,že by to tím bylo,nedává to smysl.


Děkuji všem za příspěvky
Tori
Profil
snazimse:
V skriptu chyba tutově nebude,je to official script
Opencart neznám, ale kdybychom se bavili o PrestaShopu, tak ten (alespoň v rok staré verzi) za určitých podmínek může zahlcovat paměť. Běžné metody typu zjištění URL nebo ceny produktu jsou nejspíš optimalizované pro běžný provoz, tj. když pracujete během jednoho skriptu buď s jedním produktem s kompletními údaji, nebo s cca třiceti produkty a jen základními údaji o nich. Ale když pak chcete těmi samými funkcemi exportovat kompletní údaje o několika tisících produktů, tak může vzniknout problém s pamětí a/nebo rychlostí. Při běžném provozu se to ale neprojeví. (Podobný modul do PS jsem dělala a část původních funkcí jsem si musela přepsat.)

Neřešil to už někdo na opencart fóru? 2k produktů není moc, asi nebudete první, kdo narazil na podobný zádrhel. Jakou má OC zákaznickou podporu - nedalo by se jim to nahlásit jako bug, aby provedli nějakou optimalizaci modulu?

edit: K tomu cachování - nemyslela jsem ukládání na disk, ale spíš to, se do nějaké proměnné ukládají výsledky časově náročného výpočtu a už se odtamtud nedají smazat.

reakci od Toriho
Raději "od Tori" prosím, vnímám to jako nesklonné jméno.
Davex
Profil
Joker:
Ale taky mi to na generování XML připadá hodně.
Ten XML export modul, co jsem jednou viděl, si XML vytvářel v paměti nějak takhle:

foreach ($products as $product) {
    if ($product['description']) {
        $output .= '<SHOPITEM>';
        $output .= '<ITEM_ID>' . $product['product_id'] . '</ITEM_ID>';
        $output .= // a asi dalších sto spojování řetězců;
// ...
    }
}

// ...
            
$this->response->addHeader('Content-Type: application/rss+xml');
$this->response->setOutput($output);

Takže efektivita žádná a spotřeba paměti dost drastická.
Clint
Profil
256 MB budeš potřebovat u 2500 produktů, u 3500 ti to nebude stačit. Taky jsem dělal feed a xml, pro zboží a heureku - doporučuji to předělat do třídy s metodami a po každém zpracovaném produktu uvolňovat paměť pomocí unset() u proměnné a věřím, že ti bude stačit i 64 MB. Nejvíc v paměti zabere asi dotaz, ale pokud jej napíšeš optimalizovaně, tak pak v tom nevidím problém. Pomocí foreach budeš volat fci, které předáš data, fce je zpracuje a nasetuje do nějaké proměnné a zánikem té fce se uvolní paměť.

Já jsem nedávno řešit generování personalizovaných mailů kterých bylo kolem 800 000 a když jsem měl jeden foreach ve skriptu, tak mi nestačilo ani 5 GB, předělal jsem to objektově a teď si vystačím s 512 MB a to chci jít ještě níž aspoň na 256 MB s možností vygenerování min.2-2,5 mil mailů.
snazimse
Profil
Takže jedná se o tento xml feed http://www.opencart.com/index.php?route=extension/extension/info&extension_id=5532 a co jsem se díval,skutečně v kodu je samé spojování pod proměnnou output cca +- 20krát viz vložím celý kod
<?php 
class ControllerFeedZboziCz extends Controller {
    public function index() {
        if ($this->config->get('zbozi_cz_status')) { 
            $output  = '<?xml version="1.0" encoding="UTF-8" ?>';
      $output .= '<SHOP>';
            
            $this->load->model('catalog/category');
            
            $this->load->model('catalog/product');
            
            $this->load->model('tool/image');
            
            $products = $this->model_catalog_product->getProducts();
            
            foreach ($products as $product) {
                if ($product['description']) {
                    $output .= '<SHOPITEM>';
                    $output .= '<PRODUCT>' . $product['name'] . '</PRODUCT>';
                    $output .= '<DESCRIPTION>' . $product['description'] . '</DESCRIPTION>';
                    $output .= '<URL>' . $this->url->link('product/product', 'product_id=' . $product['product_id']) . '</URL>';
                    
                    if ($product['image']) {
                        $output .= '<IMGURL>' . $this->model_tool_image->resize($product['image'], 500, 500) . '</IMGURL>';
                    }
                    
          $currency = 'CZK';
                    if ((float)$product['special']) {
              $output .= '<PRICE_VAT>' .  $this->currency->format($this->tax->calculate($product['special'], $product['tax_class_id']), $currency, false, false) . '</PRICE_VAT>';
          } else {
              $output .= '<PRICE_VAT>' . $this->currency->format($this->tax->calculate($product['price'], $product['tax_class_id']), $currency, false, false) . '</PRICE_VAT>';
          }
               
                    $output .= '<DELIVERY_DATE>' . ($product['quantity'] ? '0' : '-1') . '</DELIVERY_DATE>';
                    $output .= '<ITEM_TYPE>new</ITEM_TYPE>';
                    $output .= '<MANUFACTURER>' . html_entity_decode($product['manufacturer'], ENT_QUOTES, 'UTF-8') . '</MANUFACTURER>';

                    $categories = $this->model_catalog_product->getCategories($product['product_id']);
                    
                    foreach ($categories as $category) {
                        $path = $this->getPath($category['category_id']);
                        
                        if ($path) {
                            $string = '';
                            
                            foreach (explode('_', $path) as $path_id) {
                                $category_info = $this->model_catalog_category->getCategory($path_id);
                                
                                if ($category_info) {
                                    if (!$string) {
                                        $string = $category_info['name'];
                                    } else {
                                        $string .= ' &gt; ' . $category_info['name'];
                                    }
                                }
                            }
                         
                            $output .= '<CATEGORYTEXT>' . $string . '</CATEGORYTEXT>';
                        }
                    }
                    
                    if ($product['upc']) {
              $output .= '<EAN>' . $product['upc'] . '</EAN>'; 
          }
                    $output .= '<PRODUCTNO>' . $product['model'] . '</PRODUCTNO>';

          // VARIANT
                  $options = $this->model_catalog_product->getProductOptions($product['product_id']);
                  if ($options) {
                    foreach ($options as $option) {
                $output .= '<VARIANT>';
                if ($option['type'] == 'select' || $option['type'] == 'radio' || $option['type'] == 'checkbox' || $option['type'] == 'image') {
                  foreach($option['option_value'] as $option_value) {
                      if ($option_value['quantity']) {
                          $output .= '<PRODUCTNAMEEXT>' . $option['name'] . ' ' . $option_value['name'] . '</PRODUCTNAMEEXT>';
                      }
                  }
                } else {
                  $output .= '<PRODUCTNAMEEXT>' . $option['name'] . ' ' . $option['option_value'] . '</PRODUCTNAMEEXT>';
                }
                $output .= '</VARIANT>';
            }
          }
          
                    $output .= '</SHOPITEM>';
                }
            }
            
            $output .= '</SHOP>'; 
            
            $this->response->addHeader('Content-Type: application/rss+xml');
            $this->response->setOutput($output);
        }
    }
    
    protected function getPath($parent_id, $current_path = '') {
        $category_info = $this->model_catalog_category->getCategory($parent_id);
    
        if ($category_info) {
            if (!$current_path) {
                $new_path = $category_info['category_id'];
            } else {
                $new_path = $category_info['category_id'] . '_' . $current_path;
            }    
        
            $path = $this->getPath($category_info['parent_id'], $new_path);
                    
            if ($path) {
                return $path;
            } else {
                return $new_path;
            }
        }
    }        
}
?>
Jinak Tori omlouvám se,za nesprávné vyjádření,podporu opencart má,prolezl jsem,ale řešil se jen memory limit,taky co jiného,že,nic víc jsem nenašel.Davex souhlasím viz kod.Clint,chápu to,je to jasné,že se to zahltí,když se neuvolní paměť.Tady je více foreach funkcí.Přesto si myslím,že těch 256MB by mohlo stačit.Budu muset odzkoušet.Ale nejsem si jistý.Díky všem !

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: