Details

    • Type: Bug Bug
    • Status: Resolved
    • Priority: Major Major
    • Resolution: Fixed
    • Affects Version/s: 1.0.0ALPHA2
    • Fix Version/s: 1.0.0BETA2
    • Component/s: Persister
    • Labels:
      None
    • Environment:
      PHP 5.3.2+, Mongodb, recent (varies by developer but all experiencing the same issue)

      Description

      Unable to find source-code formatter for language: php. Available languages are: actionscript, html, java, javascript, none, sql, xhtml, xml
      // Article
      namespace Bundle\ArticleBundle\Document;
      
      use Bundle\CommentBundle\Document\Comment;
      use Bundle\ExerciseCommonBundle\Document\Repository;
      
      /**
       * @Document(
       *   collection="article",
       *   indexes={
       *     @Index(keys={"createdAt"="asc"})
       *   },
       *   repositoryClass="Bundle\ArticleBundle\Document\ArticleRepository"
       * )
       * @HasLifecycleCallbacks
       */
      class Article
      {
          /**
           * @Id
           */
          protected $id;
          /**
           * @ReferenceOne(targetDocument="Bundle\AccountBundle\Document\User")
           */
          protected $user;
          /**
           * @ReferenceOne(targetDocument="Bundle\ArticleBundle\Document\ArticleCategory")
           * @Validation({
           *      @NotBlank (message="Please select a category.")
           * })
           */
          protected $category;
          /**
           * @Field(type="string")
           */
          protected $slug;
          /**
           * @Field(type="string")
           * @Validation({
           *      @NotBlank (message="You forgot a Title?"),
           *      @MinLength(limit=4, message="Just a little too short.")
           * })
           */
          protected $title;
          /**
           * @Field(type="string")
           * @Validation({
           *      @NotBlank (message="Please summarize your article."),
           *      @MinLength(limit=100, message="Not long enough!"),
           *      @MaxLength(limit=200, message="A wee bit too long.")
           * })
           */
          protected $summary;
          /**
           * @Field(type="string")
           * @Validation({
           *      @NotBlank (message="Where's the beef?")
           * })
           */
          protected $body;
          
      	/** 
      	 * @EmbedMany(targetDocument="Bundle\CommentBundle\Document\Comment") 
      	 * */
      	protected $comments = array();
      	
          /**
           * @Field(type="boolean")
           */
          protected $published = false;
          /**
           * @Field(type="date", nullable=false)
           */
          protected $createdAt;
          /**
           * @Field(type="date", nullable=false)
           */
          protected $updatedAt;
      
          public function getId()
          {
              return $this->id;
          }
      
          public function isNew() {
              return empty($this->id);
          }
      
          public function getUser()
          {
              return $this->user;
          }
      
          public function getCategory()
          {
              return $this->category;
          }
      
          public function getSlug()
          {
              return $this->slug;
          }
      
          public function setSlug($slug)
          {
              $this->slug = $slug;
          }
      
          public function setUniqueSlug()
          {
              $this->slug = Repository::Slugify($this->title);
          }
      
          public function isPublished()
          {
              if($this->published) {
                  return true;
              }
              return false;
          }
      
          public function publish()
          {
              $this->published = true;
          }
      
          public function unpublish()
          {
              $this->published = false;
          }
      
          public function getSummary()
          {
              return $this->summary;
          }
      
          public function setSummary($summary)
          {
              $this->summary = $summary;
          }
      
          public function getTitle()
          {
              return $this->title;
          }
      
          public function setTitle($title)
          {
              $this->title = $title;
          }
      
          public function getBody()
          {
              return $this->body;
          }
      
      
      
          public function setBody($body)
          {
              $this->body = $body;
          }
      
          public function setUser($user) {
              $this->user = $user;
          }
      
          public function setCategory($category) {
              $this->category = $category;
          }
      
          public function getCreatedAt()
          {
              return $this->createdAt;
          }
      
          /**
           * It can be useful when writing fixtures
           * @param \DateTime $date
           * @return void
           */
          public function setCreatedAt(\DateTime $date)
          {
              $this->createdAt = $date;
          }
      
          public function getUpdatedAt()
          {
              return $this->updatedAt;
          }
      
          public function __toString()
          {
              return $this->title();
          }
          
          
      	/**
      	 * @return the $comments
      	 */
      	public function getComments() {
      		return $this->comments;
      	}    
          
      	/**
      	 * @param $comments the $comments to set
      	 */
      	public function setComments($comments) {
      		$this->comments = $comments;
      	}
          /** @PrePersist */
          public function incrementCreatedAt()
          {
              if(null === $this->createdAt) {
                  $this->createdAt = new \DateTime();
              }
              $this->updatedAt = new \DateTime();
          }
      
          /** @PreUpdate */
          public function incrementUpdatedAt() {
              $this->updatedAt = new \DateTime();
          }
      
          public function fromArray(array $array)
          {
              foreach($array as $property => $value) {
                  $this->$property = $value;
              }
          }
      }
      
      Unable to find source-code formatter for language: php. Available languages are: actionscript, html, java, javascript, none, sql, xhtml, xml
      // Comment
      <?php
      
      namespace Bundle\CommentBundle\Document;
      
      /**
       * @EmbeddedDocument
       */
      class Comment
      {
      	
      	/**
           * @Id
           */
          protected $id;
      	
          /**
           * @Field(type="date", nullable=true)
           */
          protected $createdAt;
      
          /**
           * @Field(type="string", nullable=true)
           */
          protected $message;
      
          /**
           * @ReferenceOne(targetDocument="Bundle\AccountBundle\Document\User")
           */
          protected $user;
      
          /**
           * @return the $createdAt
           */
          public function getCreatedAt() {
              return $this->createdAt;
          }
      
          /**
           * @return the $message
           */
          public function getMessage() {
              return $this->message;
          }
      
          /**
           * @return the $user
           */
          public function getUser() {
              return $this->user;
          }
      
          /**
           * @param $createdAt the $createdAt to set
           */
          public function setCreatedAt($createdAt) {
              $this->createdAt = $createdAt;
          }
      
      //    /** @PrePersist */
      //    public function incrementCreatedAt()
      //    {
      //        if(null === $this->createdAt) {
      //            $this->createdAt = new \DateTime();
      //        }
      //        $this->updatedAt = new \DateTime();
      //    }
      //
      //    /** @PreUpdate */
      //    public function incrementUpdatedAt() {
      //        $this->updatedAt = new \DateTime();
      //    }
      
          /**
           * @param $message the $message to set
           */
          public function setMessage($message) {
              $this->message = $message;
          }
      
          /**
           * @param $by_user_id the $by_user_id to set
           */
          public function setUser($user) {
              $this->user = $user;
          }
      }
      
      Unable to find source-code formatter for language: php. Available languages are: actionscript, html, java, javascript, none, sql, xhtml, xml
                      $article = $this->odm->getRepository('Bundle\ArticleBundle\Document\Article')->find("someID");
      
      		$newComment = new Comment();
      		$newComment->setUser($user);
      		$newComment->setMessage("PPPPOOOOOPPPP");
      		$newComment->setCreatedAt(new \DateTime());
      		
      		$comments = $article->getComments();
      		$comments[] = $newComment;
      		$article->setComments($comments);
      		
      		$this->odm->persist($article);
                      // With or without the args to flush
      		$this->odm->flush(array('safe' => true));
      

      With the above - no exception or error is thrown. It appears that the comment is added - but checking the collection in mongo and there's nothing added to the document.
      Removing the PreUpdate on the Article method allows the embedded document to be saved into Article.

        Activity

        D Ashwood created issue -
        D Ashwood made changes -
        Field Original Value New Value
        Description {quote}
        // Article
        namespace Bundle\ArticleBundle\Document;

        use Bundle\CommentBundle\Document\Comment;
        use Bundle\ExerciseCommonBundle\Document\Repository;

        /**
         * @Document(
         * collection="article",
         * indexes={
         * @Index(keys={"createdAt"="asc"})
         * },
         * repositoryClass="Bundle\ArticleBundle\Document\ArticleRepository"
         * )
         * @HasLifecycleCallbacks
         */
        class Article
        {
            /**
             * @Id
             */
            protected $id;
            /**
             * @ReferenceOne(targetDocument="Bundle\AccountBundle\Document\User")
             */
            protected $user;
            /**
             * @ReferenceOne(targetDocument="Bundle\ArticleBundle\Document\ArticleCategory")
             * @Validation({
             * @NotBlank (message="Please select a category.")
             * })
             */
            protected $category;
            /**
             * @Field(type="string")
             */
            protected $slug;
            /**
             * @Field(type="string")
             * @Validation({
             * @NotBlank (message="You forgot a Title?"),
             * @MinLength(limit=4, message="Just a little too short.")
             * })
             */
            protected $title;
            /**
             * @Field(type="string")
             * @Validation({
             * @NotBlank (message="Please summarize your article."),
             * @MinLength(limit=100, message="Not long enough!"),
             * @MaxLength(limit=200, message="A wee bit too long.")
             * })
             */
            protected $summary;
            /**
             * @Field(type="string")
             * @Validation({
             * @NotBlank (message="Where's the beef?")
             * })
             */
            protected $body;
            
        /**
        * @EmbedMany(targetDocument="Bundle\CommentBundle\Document\Comment")
        * */
        protected $comments = array();

            /**
             * @Field(type="boolean")
             */
            protected $published = false;
            /**
             * @Field(type="date", nullable=false)
             */
            protected $createdAt;
            /**
             * @Field(type="date", nullable=false)
             */
            protected $updatedAt;

            public function getId()
            {
                return $this->id;
            }

            public function isNew() {
                return empty($this->id);
            }

            public function getUser()
            {
                return $this->user;
            }

            public function getCategory()
            {
                return $this->category;
            }

            public function getSlug()
            {
                return $this->slug;
            }

            public function setSlug($slug)
            {
                $this->slug = $slug;
            }

            public function setUniqueSlug()
            {
                $this->slug = Repository::Slugify($this->title);
            }

            public function isPublished()
            {
                if($this->published) {
                    return true;
                }
                return false;
            }

            public function publish()
            {
                $this->published = true;
            }

            public function unpublish()
            {
                $this->published = false;
            }

            public function getSummary()
            {
                return $this->summary;
            }

            public function setSummary($summary)
            {
                $this->summary = $summary;
            }

            public function getTitle()
            {
                return $this->title;
            }

            public function setTitle($title)
            {
                $this->title = $title;
            }

            public function getBody()
            {
                return $this->body;
            }



            public function setBody($body)
            {
                $this->body = $body;
            }

            public function setUser($user) {
                $this->user = $user;
            }

            public function setCategory($category) {
                $this->category = $category;
            }

            public function getCreatedAt()
            {
                return $this->createdAt;
            }

            /**
             * It can be useful when writing fixtures
             * @param \DateTime $date
             * @return void
             */
            public function setCreatedAt(\DateTime $date)
            {
                $this->createdAt = $date;
            }

            public function getUpdatedAt()
            {
                return $this->updatedAt;
            }

            public function __toString()
            {
                return $this->title();
            }
            
            
        /**
        * @return the $comments
        */
        public function getComments() {
        return $this->comments;
        }
            
        /**
        * @param $comments the $comments to set
        */
        public function setComments($comments) {
        $this->comments = $comments;
        }
            /** @PrePersist */
            public function incrementCreatedAt()
            {
                if(null === $this->createdAt) {
                    $this->createdAt = new \DateTime();
                }
                $this->updatedAt = new \DateTime();
            }

            /** @PreUpdate */
            public function incrementUpdatedAt() {
                $this->updatedAt = new \DateTime();
            }

            public function fromArray(array $array)
            {
                foreach($array as $property => $value) {
                    $this->$property = $value;
                }
            }
        }
        {quote}

        {quote}
        // Comment
        <?php

        namespace Bundle\CommentBundle\Document;

        /**
         * @EmbeddedDocument
         */
        class Comment
        {

        /**
             * @Id
             */
            protected $id;

            /**
             * @Field(type="date", nullable=true)
             */
            protected $createdAt;

            /**
             * @Field(type="string", nullable=true)
             */
            protected $message;

            /**
             * @ReferenceOne(targetDocument="Bundle\AccountBundle\Document\User")
             */
            protected $user;

            /**
             * @return the $createdAt
             */
            public function getCreatedAt() {
                return $this->createdAt;
            }

            /**
             * @return the $message
             */
            public function getMessage() {
                return $this->message;
            }

            /**
             * @return the $user
             */
            public function getUser() {
                return $this->user;
            }

            /**
             * @param $createdAt the $createdAt to set
             */
            public function setCreatedAt($createdAt) {
                $this->createdAt = $createdAt;
            }

        // /** @PrePersist */
        // public function incrementCreatedAt()
        // {
        // if(null === $this->createdAt) {
        // $this->createdAt = new \DateTime();
        // }
        // $this->updatedAt = new \DateTime();
        // }
        //
        // /** @PreUpdate */
        // public function incrementUpdatedAt() {
        // $this->updatedAt = new \DateTime();
        // }

            /**
             * @param $message the $message to set
             */
            public function setMessage($message) {
                $this->message = $message;
            }

            /**
             * @param $by_user_id the $by_user_id to set
             */
            public function setUser($user) {
                $this->user = $user;
            }
        }
        {quote}

        {quote}
                        $article = $this->odm->getRepository('Bundle\ArticleBundle\Document\Article')->find("someID");

        $newComment = new Comment();
        $newComment->setUser($user);
        $newComment->setMessage("PPPPOOOOOPPPP");
        $newComment->setCreatedAt(new \DateTime());

        $comments = $article->getComments();
        $comments[] = $newComment;
        $article->setComments($comments);

        $this->odm->persist($article);
                        // With or without the args to flush
        $this->odm->flush(array('safe' => true));
        {quote}

        With the above - no exception or error is thrown. It appears that the comment is added - but checking the collection in mongo and there's nothing added to the document.
        Removing the PreUpdate on the Article method allows the embedded document to be saved into Article.
        {code:php}
        // Article
        namespace Bundle\ArticleBundle\Document;

        use Bundle\CommentBundle\Document\Comment;
        use Bundle\ExerciseCommonBundle\Document\Repository;

        /**
         * @Document(
         * collection="article",
         * indexes={
         * @Index(keys={"createdAt"="asc"})
         * },
         * repositoryClass="Bundle\ArticleBundle\Document\ArticleRepository"
         * )
         * @HasLifecycleCallbacks
         */
        class Article
        {
            /**
             * @Id
             */
            protected $id;
            /**
             * @ReferenceOne(targetDocument="Bundle\AccountBundle\Document\User")
             */
            protected $user;
            /**
             * @ReferenceOne(targetDocument="Bundle\ArticleBundle\Document\ArticleCategory")
             * @Validation({
             * @NotBlank (message="Please select a category.")
             * })
             */
            protected $category;
            /**
             * @Field(type="string")
             */
            protected $slug;
            /**
             * @Field(type="string")
             * @Validation({
             * @NotBlank (message="You forgot a Title?"),
             * @MinLength(limit=4, message="Just a little too short.")
             * })
             */
            protected $title;
            /**
             * @Field(type="string")
             * @Validation({
             * @NotBlank (message="Please summarize your article."),
             * @MinLength(limit=100, message="Not long enough!"),
             * @MaxLength(limit=200, message="A wee bit too long.")
             * })
             */
            protected $summary;
            /**
             * @Field(type="string")
             * @Validation({
             * @NotBlank (message="Where's the beef?")
             * })
             */
            protected $body;
            
        /**
        * @EmbedMany(targetDocument="Bundle\CommentBundle\Document\Comment")
        * */
        protected $comments = array();

            /**
             * @Field(type="boolean")
             */
            protected $published = false;
            /**
             * @Field(type="date", nullable=false)
             */
            protected $createdAt;
            /**
             * @Field(type="date", nullable=false)
             */
            protected $updatedAt;

            public function getId()
            {
                return $this->id;
            }

            public function isNew() {
                return empty($this->id);
            }

            public function getUser()
            {
                return $this->user;
            }

            public function getCategory()
            {
                return $this->category;
            }

            public function getSlug()
            {
                return $this->slug;
            }

            public function setSlug($slug)
            {
                $this->slug = $slug;
            }

            public function setUniqueSlug()
            {
                $this->slug = Repository::Slugify($this->title);
            }

            public function isPublished()
            {
                if($this->published) {
                    return true;
                }
                return false;
            }

            public function publish()
            {
                $this->published = true;
            }

            public function unpublish()
            {
                $this->published = false;
            }

            public function getSummary()
            {
                return $this->summary;
            }

            public function setSummary($summary)
            {
                $this->summary = $summary;
            }

            public function getTitle()
            {
                return $this->title;
            }

            public function setTitle($title)
            {
                $this->title = $title;
            }

            public function getBody()
            {
                return $this->body;
            }



            public function setBody($body)
            {
                $this->body = $body;
            }

            public function setUser($user) {
                $this->user = $user;
            }

            public function setCategory($category) {
                $this->category = $category;
            }

            public function getCreatedAt()
            {
                return $this->createdAt;
            }

            /**
             * It can be useful when writing fixtures
             * @param \DateTime $date
             * @return void
             */
            public function setCreatedAt(\DateTime $date)
            {
                $this->createdAt = $date;
            }

            public function getUpdatedAt()
            {
                return $this->updatedAt;
            }

            public function __toString()
            {
                return $this->title();
            }
            
            
        /**
        * @return the $comments
        */
        public function getComments() {
        return $this->comments;
        }
            
        /**
        * @param $comments the $comments to set
        */
        public function setComments($comments) {
        $this->comments = $comments;
        }
            /** @PrePersist */
            public function incrementCreatedAt()
            {
                if(null === $this->createdAt) {
                    $this->createdAt = new \DateTime();
                }
                $this->updatedAt = new \DateTime();
            }

            /** @PreUpdate */
            public function incrementUpdatedAt() {
                $this->updatedAt = new \DateTime();
            }

            public function fromArray(array $array)
            {
                foreach($array as $property => $value) {
                    $this->$property = $value;
                }
            }
        }
        {code}

        {code:php}
        // Comment
        <?php

        namespace Bundle\CommentBundle\Document;

        /**
         * @EmbeddedDocument
         */
        class Comment
        {

        /**
             * @Id
             */
            protected $id;

            /**
             * @Field(type="date", nullable=true)
             */
            protected $createdAt;

            /**
             * @Field(type="string", nullable=true)
             */
            protected $message;

            /**
             * @ReferenceOne(targetDocument="Bundle\AccountBundle\Document\User")
             */
            protected $user;

            /**
             * @return the $createdAt
             */
            public function getCreatedAt() {
                return $this->createdAt;
            }

            /**
             * @return the $message
             */
            public function getMessage() {
                return $this->message;
            }

            /**
             * @return the $user
             */
            public function getUser() {
                return $this->user;
            }

            /**
             * @param $createdAt the $createdAt to set
             */
            public function setCreatedAt($createdAt) {
                $this->createdAt = $createdAt;
            }

        // /** @PrePersist */
        // public function incrementCreatedAt()
        // {
        // if(null === $this->createdAt) {
        // $this->createdAt = new \DateTime();
        // }
        // $this->updatedAt = new \DateTime();
        // }
        //
        // /** @PreUpdate */
        // public function incrementUpdatedAt() {
        // $this->updatedAt = new \DateTime();
        // }

            /**
             * @param $message the $message to set
             */
            public function setMessage($message) {
                $this->message = $message;
            }

            /**
             * @param $by_user_id the $by_user_id to set
             */
            public function setUser($user) {
                $this->user = $user;
            }
        }
        {code}

        {code:php}
                        $article = $this->odm->getRepository('Bundle\ArticleBundle\Document\Article')->find("someID");

        $newComment = new Comment();
        $newComment->setUser($user);
        $newComment->setMessage("PPPPOOOOOPPPP");
        $newComment->setCreatedAt(new \DateTime());

        $comments = $article->getComments();
        $comments[] = $newComment;
        $article->setComments($comments);

        $this->odm->persist($article);
                        // With or without the args to flush
        $this->odm->flush(array('safe' => true));
        {code}

        With the above - no exception or error is thrown. It appears that the comment is added - but checking the collection in mongo and there's nothing added to the document.
        Removing the PreUpdate on the Article method allows the embedded document to be saved into Article.
        Hide
        Jonathan H. Wage added a comment -

        Hi, can you provide a consolidated PHPUnit test case?

        Show
        Jonathan H. Wage added a comment - Hi, can you provide a consolidated PHPUnit test case?
        Hide
        D Ashwood added a comment - - edited

        Just to clarify:

        $parent = new ParentDocument();
        $odm->persist($parent);
        $odm->flush();
        
        // count(parent->getChildren() ) = 0
        
        // Add some children
        $childOne = new childEmbededDocument();
        
        $children = $parent->getChildren();
        $children[] = $childOne;
        $parent->setChildren($children);
        $odm->persist($parent);
        
        $childTwo = new childEmbededDocument();
        
        $children = $parent->getChildren();
        $children[] = $childTwo;
        $parent->setChildren($children);
        $odm->persist($parent);
        
        // Results
        // When $parent has lifeCycle callbacks - specifically @PreUpdate - count(parent->getChildren() ) = 0
        // When $parent doesn't have lifeCycle callbacks - count(parent->getChildren() ) = 2
        

        So the issue isn't so much about lifeCycle cascading to the children - it's that the parent lifeCycle callback @PreUpdate affects adding embedded children.

        Show
        D Ashwood added a comment - - edited Just to clarify: $parent = new ParentDocument(); $odm->persist($parent); $odm->flush(); // count(parent->getChildren() ) = 0 // Add some children $childOne = new childEmbededDocument(); $children = $parent->getChildren(); $children[] = $childOne; $parent->setChildren($children); $odm->persist($parent); $childTwo = new childEmbededDocument(); $children = $parent->getChildren(); $children[] = $childTwo; $parent->setChildren($children); $odm->persist($parent); // Results // When $parent has lifeCycle callbacks - specifically @PreUpdate - count(parent->getChildren() ) = 0 // When $parent doesn't have lifeCycle callbacks - count(parent->getChildren() ) = 2 So the issue isn't so much about lifeCycle cascading to the children - it's that the parent lifeCycle callback @PreUpdate affects adding embedded children.
        Hide
        Jonathan H. Wage added a comment -

        I am still not clear on what the problem is Jay said you were trying to use lifecycle callbacks on embedded documents which is not supported. You all seem to be talking about 2 different things?

        Show
        Jonathan H. Wage added a comment - I am still not clear on what the problem is Jay said you were trying to use lifecycle callbacks on embedded documents which is not supported. You all seem to be talking about 2 different things?
        Show
        Jonathan H. Wage added a comment - Fixed by http://github.com/doctrine/mongodb-odm/commit/faf85a281b1562d184b44261a6e4dcdb13e03c5e
        Hide
        Jonathan H. Wage added a comment -

        The callbacks will also work on embedded documents now.

        Show
        Jonathan H. Wage added a comment - The callbacks will also work on embedded documents now.
        Jonathan H. Wage made changes -
        Status Open [ 1 ] Resolved [ 5 ]
        Fix Version/s 1.0.0BETA2 [ 10092 ]
        Resolution Fixed [ 1 ]

        This list may be incomplete, as errors occurred whilst retrieving source from linked applications:

        • Request to http://www.doctrine-project.org/fisheye/ failed: Error in remote call to 'FishEye 0 (http://www.doctrine-project.org/fisheye/)' (http://www.doctrine-project.org/fisheye) [AbstractRestCommand{path='/rest-service-fe/search-v1/crossRepositoryQuery', params={query=MODM-56, expand=changesets[0:20].revisions[0:29],reviews}, methodType=GET}] : Received status code 503 (Service Temporarily Unavailable)

          People

          • Assignee:
            Jonathan H. Wage
            Reporter:
            D Ashwood
          • Votes:
            0 Vote for this issue
            Watchers:
            0 Start watching this issue

            Dates

            • Created:
              Updated:
              Resolved: