Looking in the debugger is not a good indication of what is and is not set
because jdo-enhanced classes perform lazy loading when the fields are
accessed.  If you call a getter method and System.out.println() the result
is it still null?  Feel free to send me your model objects and your
persistence code with some println()s showing me the problem and I'll have a
look.

Max

On Tue, Oct 27, 2009 at 5:28 PM, stanlick <stanl...@gmail.com> wrote:

>
> Hey Max --
>
> At what point are you validating this?  I am breaking after the commit
> and also after a subsequent query.execute().  Dude, it is about to
> make me jump off a bridge.
>
> P.S. I'm not a good swimmer, so please throw me a clue.
>
> Scott
>
> On Oct 27, 12:25 pm, "Max Ross (Google)" 
> <maxr+appeng...@google.com<maxr%2bappeng...@google.com>
> >
> wrote:
> > At what point are you checking to see if the parent property of the child
> is
> > populated?  I see that the newly created Chapter's Book property is
> > populated when addChapterToBook() completes.
> >
> > Max
> >
> > On Tue, Oct 27, 2009 at 8:31 AM, stanlick <stanl...@gmail.com> wrote:
> >
> > > This code saves the child for me, however, the parent property of the
> > > child (in your case "book") is null in the child.  I have tried
> > > deliberately setting this child "parent" property myself to the parent
> > > prior to commit, but nothing seems to work.
> >
> > > On Sep 28, 6:45 pm, Max Ross 
> > > <maxr+appeng...@google.com<maxr%2bappeng...@google.com>
> <maxr%2bappeng...@google.com <maxr%252bappeng...@google.com>>>
> > > wrote:
> > > > Hello again and welcome to Episode 3 of JDO/JPA Snippets That Work.
> > >  Today's
> > > > episode is called......
> >
> > > > Updating A Bidrectional Owned One-To-Many With A New Child
> >
> > > > All the way back in episode one we demonstrated how to create both a
> > > parent
> > > > and a child of a bidirectional, owned, one-to-many relationship
> > > > at the same time.  This week we're going to see how to add a child to
> an
> > > > existing parent.  We'll use the same model objects we used in episode
> > > one:
> >
> > > > JPA:
> > > > @Entity
> > > > public class Book {
> > > >     @Id
> > > >     @GeneratedValue(strategy=GenerationType.IDENTITY)
> > > >     private Key id;
> >
> > > >     private String title;
> >
> > > >     @OneToMany(mappedBy = "book", cascade = CascadeType.ALL)
> > > >     private List<Chapter> chapters = new ArrayList<Chapter>();
> >
> > > >     // getters and setters
> >
> > > > }
> >
> > > > @Entity
> > > > public class Chapter {
> > > >     @Id
> > > >     @GeneratedValue(strategy=GenerationType.IDENTITY)
> > > >     private Key id;
> >
> > > >     private String title;
> > > >     private int numPages;
> >
> > > >     @ManyToOne(fetch = FetchType.LAZY)
> > > >     private Book book;
> >
> > > >     // getters and setters
> >
> > > > }
> >
> > > > Now let's assume we've already created a book with a few chapters in
> the
> > > > datastore and we want to add a brand new chapter to a Book with a
> given
> > > id
> > > > (we'll assume someone else is creating and closing an EntityManager
> named
> > > > 'em' for us):
> >
> > > > public void addChapterToBook(EntityManager em, Key bookKey, Chapter
> > > chapter)
> > > > {
> > > >     em.getTransaction().begin();
> > > >     try {
> > > >         Book b = em.find(Book.class, bookKey);
> > > >         if (b == null) {
> > > >             throw new RuntimeException("Book " + bookKey + " not
> > > found!");
> > > >         }
> > > >         b.getChapters().add(chapter);
> > > >         em.getTransaction().commit();
> > > >     } finally {
> > > >         if (em.getTransaction().isActive()) {
> > > >             em.getTransaction().rollback();
> > > >         }
> > > >     }
> >
> > > > }
> >
> > > > JDO:
> >
> > > > @PersistenceCapable(identityType = IdentityType.APPLICATION,
> detachable =
> > > > "true")
> > > > public class Book {
> >
> > > >     @PrimaryKey
> > > >     @Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)
> > > >     private Key id;
> >
> > > >     private String title;
> >
> > > >     @Persistent(mappedBy = "book")
> > > >     @Element(dependent = "true")
> > > >     @Order(extensions = @Extension(vendorName="datanucleus", key=
> > > > "list-ordering", value="id asc"))
> > > >     private List<Chapter> chapters = new ArrayList<Chapter>();
> >
> > > >     // getters and setters
> >
> > > > }
> >
> > > > @PersistenceCapable(identityType = IdentityType.APPLICATION,
> detachable =
> > > > "true")
> > > > public class Chapter {
> > > >     @PrimaryKey
> > > >     @Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)
> > > >     private Key id;
> >
> > > >     private String title;
> > > >     private int numPages;
> >
> > > >     @Persistent
> > > >     private Book book;
> >
> > > >     // getters and setters
> >
> > > > }
> >
> > > > Now let's assume we've already created a book with a few chapters in
> the
> > > > datastore and we want to add a brand new chapter to a Book with a
> given
> > > id
> > > > (we'll assume someone else is creating and closing a
> PersistenceManager
> > > > named 'pm' for us):
> >
> > > > public void addChapterToBook(PersistenceManager pm, Key bookKey,
> Chapter
> > > > chapter) {
> > > >     pm.currentTransaction().begin();
> > > >     try {
> > > >         // throws a runtime exception if book is not found
> > > >         Book b = pm.getObjectById(Book.class, bookKey);
> > > >         b.getChapters().add(chapter);
> > > >         pm.currentTransaction().commit();
> > > >     } finally {
> > > >         if (pm.currentTransaction().isActive()) {
> > > >             pm.currentTransaction().rollback();
> > > >         }
> > > >     }}
> >
> > > > --------------------------------
> >
> > > > The interesting thing about both of these examples is that we're not
> > > making
> > > > any explicit calls to save the new Chapter.  We look up the Book
> > > identified
> > > > by the Key that was passed into the function and then we manipulate
> the
> > > > persistent state of the object by manipulating the POJO that was
> returned
> > > by
> > > > em.fetch/pm.getObjectById.  JPA and JDO both have mechanisms that
> allow
> > > them
> > > > to monitor the objects that you've looked up for changes.  Ever
> wonder
> > > what
> > > > exactly the enhancer is doing to your classes?  It's adding hooks so
> that
> > > > the persistence framework gets notified when things change (among
> other
> > > > things).  This allows JPA and JDO to automatically flush your changes
> to
> > > the
> > > > datastore when you commit your transaction.  If you wanted to modify
> the
> > > > title of the Book or the number of pages in an existing Chapter the
> > > approach
> > > > would be exactly the same: Start a transaction, look up the Book,
> make
> > > your
> > > > changes, commit your transaction.  Whether you're using JPA or JDO
> your
> > > > changes will be persisted for you without any explicit calls to
> change
> > > the
> > > > persistent state.  This is a prime example of how JPA and JDO
> facilitate
> > > > "transparent persistence."
> >
>

--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"Google App Engine for Java" group.
To post to this group, send email to google-appengine-java@googlegroups.com
To unsubscribe from this group, send email to 
google-appengine-java+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/google-appengine-java?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to