• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
Re: How to fetch eo with a specific relationship
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: How to fetch eo with a specific relationship


  • Subject: Re: How to fetch eo with a specific relationship
  • From: Robert Walker <email@hidden>
  • Date: Wed, 6 Feb 2008 14:42:52 -0500

Yea, the reason I like to have the to-many in the model but not as a class property is so that I can do this.....

-------------------------
User model
-------------------------
public void validateForDelete() throws NSValidation.ValidationException {
    super.validateForDelete();

    // Deny delete rule for driverLogs relationship
    if (Utilities.countRelatedEnterpriseObjects(this, "driverLogs").intValue() > 0) {
        throw new NSValidation.ValidationException("Delete was denied!  This user has related driver logs.  Disable login instead.");
    }

}


-------------------------

Utility class

-------------------------


/**
 * Convenience method that returns the count of related records using raw SQL
 */
public static Number countRelatedEnterpriseObjects(EOEnterpriseObject sourceEO, String relationshipKey) {
    // First make sure the relationship is to-many and has unary keys
    EOEntity sourceEntity = EOModelGroup.defaultGroup().entityForObject(sourceEO);
    String modelName = sourceEntity.model().name();
    EORelationship rel = sourceEntity.relationshipNamed(relationshipKey);
    NSArray destAttributes = rel.destinationAttributes();
    if (rel == null || !rel.isToMany()) {
        throw new RuntimeException("No to-many relationship found for key: " + relationshipKey);
    }
    if (destAttributes.count() != 1) {
        throw new RuntimeException("This method can only be used with entities having unary primary keys.");
    }


    //--------------------------------------------------
    // Count the number of related rows using raw SQL
    //--------------------------------------------------
    EOEntity destEntity = rel.destinationEntity();
    NSArray destPKAttributes = destEntity.primaryKeyAttributes();
    String destPK = ((EOAttribute)destPKAttributes.lastObject()).columnName();
    String destFK = ((EOAttribute)destAttributes.lastObject()).columnName();


    // Build the SQL statement to return the row count
    String sql = "SELECT COUNT(" + destPK + ") FROM " + destEntity.externalName() +
        " WHERE " + destFK + " = " + unaryPKValueForObject(sourceEO) + ";";
    NSArray rows = EOUtilities.rawRowsForSQL(sourceEO.editingContext(), modelName, sql, new NSArray("rowCount"));
    if (rows.count() > 0) {
        Number rowCount = (Number)((NSDictionary)rows.lastObject()).objectForKey("rowCount");
        return rowCount;
    }
    return null;
}

/**
 * Returns the PK of the object as a string value.
 */
public static String unaryPKValueForObject(EOEnterpriseObject eo){
    NSDictionary d = EOUtilities.primaryKeyForObject(eo.editingContext(), eo);
    Number n = (Number)d.objectForKey("oid");
    return n.toString();
}


On Feb 6, 2008, at 1:56 PM, David Avendasora wrote:

I agree with this completely. WO will load ALL the to-many-related objects from the database when you try to set the inverse to-one relationship on a new object, which when there are thousands of related objects, this can cause a huge delay, especially in Java Client applications where the client then requests all the objects be sent to the client from the server. Ouch.

I have always just not modeled the inverse, unless I discovered a compelling reason to _expect_ all the related objects to be in memory. I didn't realize that if the relationship isn't marked as a class attribute that it wouldn't fetch them. That is interesting and would make the model much more intuitive.

Using a FetchSpec to go get the to-many-related objects manually has worked well for me as it only incurs the often substantial overhead if and when I explicitly ask it to.

Dave


On Feb 6, 2008, at 11:32 AM, Robert Walker wrote:

At least if using standard EOF classes, having the reverse to-many relationship as a class properly on the EO can cause very major performance problems because the to-many fault can get fired when you don't expect it. This can happen even if you never directly access the to-many relationship. I've had nightmares about this very problem in the past. I now consider the implication of adding the to-many side as a class property. If I expect it could return more than a few hundred objects then I don't use it. I still model the to-many side, I just don't set it as a class property. It's entirely possible that Project WOnder classes take care of this problem. I just wanted to make sure you were aware of it.



--
Robert Walker
email@hidden



 _______________________________________________
Do not post admin requests to the list. They will be ignored.
Webobjects-dev mailing list      (email@hidden)
Help/Unsubscribe/Update your Subscription:

This email sent to email@hidden

References: 
 >How to fetch eo with a specific relationship (From: Louis Demers <email@hidden>)
 >Re: How to fetch eo with a specific relationship (From: "Daniele Corti" <email@hidden>)
 >Re: How to fetch eo with a specific relationship (From: Robert Walker <email@hidden>)
 >Re: How to fetch eo with a specific relationship (From: David Avendasora <email@hidden>)

  • Prev by Date: Re: Illegal Lock usage
  • Next by Date: Re: recurring events
  • Previous by thread: Re: How to fetch eo with a specific relationship
  • Next by thread: Re: How to fetch eo with a specific relationship
  • Index(es):
    • Date
    • Thread