Skip to content

ActiveRow: Trying to get property of non-object & Selection: Invalid argument supplied for foreach() #15

Open

Description

@hranicka

In some cases (delete of cache files, access to one page and then access to another page) Nette\Database\Table\ActiveRow::accessColumn generates Notice.

I can't write test case because bug is unpredictable.

My temporary solution is edit Nette\Database\Table\Selection::offsetGet, but it's only a hack IMHO (and is applied only to ::offsetGet).

public function offsetGet($key)
{
    $this->execute();

    // solves strange cache bug
    $rows = ($this->rows) ? : $this->data;

    return $rows[$key];
}

Another hack is edit Nette\Database\Table\ActiveRow::accessColumn like this:

protected function accessColumn($key, $selectColumn = TRUE)
{
    $this->table->accessColumn($key, $selectColumn);
    if ($this->table->getDataRefreshed() && !$this->dataRefreshed) {
        $row = ($this->table[$this->getSignature()]) ? : $this->table->get($this->getSignature());
        $this->data = $row->data;
        $this->dataRefreshed = TRUE;
    }
}

Related topic in forum:


I can't reproduce issue artifically so I can't write tests and create full pull-request at the moment :(
Codes above are only my "hacks" until we found right cause of the issue.

Activity

  1. hrach commented on Jul 10, 2014

    @hrach
    Contributor

    @hranicka Sadly, I really need the reproducible usecase. On forum you have written that it appears, if .... -> so is it reproducible on your project, but you can it reproduce on sandbox? Would you accept sending privately your project with the bug to my email?

  2. nechutny commented on Jul 10, 2014

    @nechutny
    Contributor

    I have same problem. After cleaning temp dir first page render is ok, refresh throw this error and next refresh fix it to next cleaning temp dir.

    Error is throwing code:

    {foreach $fb_galleries as $gal}
        <div class="album">
            <a href="{plink Gallery:facebook $gal->url}" title="{$gal->name}">
                {var $photo = $gal->related('facebook_photo')->order('id')->limit(1)->fetch()}
    
                {if is_object($photo)}
                    {var $url = 'FB-'.$photo->url}
                {else}
                    {var $url = "none"}
                {/if}
                <img src="{plink Gallery:image $url,208,150,'crop'}" alt="{$gal->name}">
                <h2>
                    <strong>{$gal->name}</strong><br>{$gal->created|date:'d. m. Y'} | Fotek: {$gal->related('facebook_photo')->count()}
                </h2>
            </a>
        </div>
    {/foreach}
    

    and error is throwing {var $url = 'FB-'.$photo->url} even if it pass through if(is_object())

  3. mishak87 commented on Jul 10, 2014

    @mishak87
    Contributor

    I think I have encountered something similar while back. I found out that in cache was incomplete row from partial select and on full select that cache was used leaving some properties empty.

  4. added a commit that references this issue on Jul 10, 2014
    0152fc7
  5. dg commented on Jul 10, 2014

    @dg
    Member

    @hrach is finer caching granularity correct fix for this issue? Partial row should re-execute query and not to throw error.

  6. hrach commented on Jul 11, 2014

    @hrach
    Contributor

    @dg yes, definitelly not, however, fi they weren't able to reproduci it untill now, I thing there will never be.

  7. reopened this on Jul 11, 2014
  8. hranicka commented on Jul 11, 2014

    @hranicka
    ContributorAuthor

    @hrach 408925f really fixes the problem. However if I'll try reproduce the bug on nette/sandbox v2.2.2, will be it still useful for you (you've written tests for it in 408925f )?

    Because our project is huge monster for this purpose, so I can try reproduce the bug on clean sandbox...

  9. hrach commented on Jul 11, 2014

    @hrach
    Contributor

    @hranicka It would be awesome If you be able to reproduce it. No, it's not the test for that...it's just rewritten old one.

  10. hranicka commented on Jul 12, 2014

    @hranicka
    ContributorAuthor

    @hrach I'm trying evoke the bug in simple situation in nette/sandbox v2.2.2 but there it works fine. It's really strange :( I'll try it again later with more comlex DB structure. Until I can't help more, because I can't reproduce the bug on simple project when I need... it maybe appears only in some situations on larger projects :( During week I'll try create a buggy environment in nette/sandbox, but I'm sceptic that I succeed. But hope...

  11. hrach commented on Jul 12, 2014

    @hrach
    Contributor

    @hranicka thanks! :)

  12. hranicka commented on Jul 20, 2014

    @hranicka
    ContributorAuthor

    @hrach So I've tried envoke the bug on nette/sandbox v2.2.2 with custom DB structures but everything worked fine. Sorry, I can't reproduce test case for the bug when I need :(

  13. hrach commented on Jul 20, 2014

    @hrach
    Contributor

    @hranicka that's the sad story... the system is quite complex and I believe I have fiexed almost everything what I could fixed :)

  14. hranicka commented on Feb 19, 2015

    @hranicka
    ContributorAuthor

    I got it! Or no? ...

    See:

    1. I have a problem with ::offsetGet:
    1. Another problem is Invalid argument supplied for foreach() here:

    And maybe the core of the problem GroupedSelection!

    What is the purpose of $rows and $data properties?

    For the current implementation I use fix like this:

    // Nette\Database\Table\Selection
    
        public function offsetGet($key)
        {
            $this->execute();
    
            // solves strange cache bug
            if ($this->rows === NULL) {
                $this->cache = NULL;
                return $this->data[$key];
            }
    
            return $this->rows[$key];
        }

    It helps in most cases (first problem).
    But sometimes I get the second described error and I haven't any fix for that.

    But maybe right way for the fix can be overriden ::execute method in GroupedSelection & $this->rows vs. $this->data.

    I can try fix the problem, but can you please explain me differences between $this->rows and $this->data?

  15. hrach commented on Feb 19, 2015

    @hrach
    Contributor

    One holds all fetched rows, the second holds aggregated rows (makes sence only in context of GroupedSelection)

  16. changed the title [-]Database/Table/ActiveRow.php:315 generates Notice: Trying to get property of non-object[/-] [+]ActiveRow: Trying to get property of non-object & Selection: Invalid argument supplied for foreach()[/+] on Feb 19, 2015
  17. hranicka commented on Feb 20, 2015

    @hranicka
    ContributorAuthor

    Very strange problem. I've spent several hours and I can't still reproduce the bug purposely :(
    Everything looks fine in Nette\Database. Maybe the problem could be in currupted cache.

    I will try reproduce it maybe later again.

  18. hranicka commented on Feb 20, 2015

    @hranicka
    ContributorAuthor

    For the first HTTP request the error is produced but for the next request everything works fine.

    I'll try conditionally copy cached files immediatelly when error occurs and again try to find the problem. It may take some time.

  19. temistokles commented on Apr 22, 2015

    @temistokles

    This (#15 (comment)) seems to have solved the issue for me:

    public function offsetGet($key)
    {
        $this->execute();
    
        // solves strange cache bug
        if ($this->rows === NULL) {
            $this->cache = NULL;
            return $this->data[$key];
        }
    
        return $this->rows[$key];
    }
    
  20. reopened this on Apr 22, 2015
  21. hranicka commented on Apr 22, 2015

    @hranicka
    ContributorAuthor

    @dg I don't like 3c44de6 nowadays 😞
    It solves the problem only partially (::offsetGet only) and the way is ugly and very strange.
    I would like revert the commit 3c44de6 .

    Sorry for that.
    But I wrote:

    It helps in most cases (first problem).
    But sometimes I get the second described error and I haven't any fix for that.

    3c44de6 solves only the ActiveRow: Notice: Trying to get property of non-object.
    Despite the fix I've sometimes got another problem: Selection: Invalid argument supplied for foreach().

    @dg @temistokles For last few weeks I use another and more clear fix: #59

    @temistokles Can you try #59 please instead of the ugly "offsetGet workaround"?

    We use it on several projects where previous solution (3c44de6) wasn't enough.
    With #15 everything is fine now - till today without problems.

  22. hranicka commented on Apr 22, 2015

    @hranicka
    ContributorAuthor

    @dg Please reopen the issue, it was closed via 615803d's commit message 😏

  23. reopened this on Apr 22, 2015
  24. temistokles commented on Apr 23, 2015

    @temistokles

    I have applied the code as well (before trying the fix above) and it did not work by itself. Because I cannot reproduce this issue anymore at the moment, I am not sure if the patch to GroupedSelection was critical or not (anyway the problematic query does not use any grouping).

  25. temistokles commented on Feb 1, 2016

    @temistokles

    This issue could be related to #115, because this mainly happens on heavy-traffic, not in testing environments, the multiple accesses to the "same" data could be the key.

    Also I confirm the issue is still present, although not that often in my case, as before.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions