SitePoint Sponsor

User Tag List

Results 1 to 3 of 3
  1. #1
    SitePoint Wizard bronze trophy
    Join Date
    Jul 2006
    Location
    Augusta, Georgia, United States
    Posts
    4,194
    Mentioned
    17 Post(s)
    Tagged
    5 Thread(s)

    ORM Field Cascading Update and Union Possibility

    Given the below schemas and their models I have been contemplating the best way to link field(s) of one model to another.

    User Schema
    • id (primary key)
    • name
    • status


    BlogEntry Schema
    • id (primary key)
    • user_id (foreign key => user => id )
    • title
    • entry
    • status


    BlogComment Schema
    • id (primary key)
    • blog_entry_id (foreign key => blog_entry => id )
    • user_id (foreign key => user => id )
    • message
    • status


    User Model
    PHP Code:
    class User {

        public static 
    $fields = array('id','name','status');
        
        public static 
    $hasMany = array('blog_entries','blog_comments');


    BlogEntry Model
    PHP Code:
    class BlogEntry {

        public static 
    $fields = array('id','user_id','title','entry','status');
        
        public static 
    $foreignKeys = array(
            
    'user_id'=>'User'
        
    );


    BlogComment Model
    PHP Code:
    class BlogComment {

        public static 
    $fields = array('id','user_id','title','entry','status');
        
        public static 
    $foreignKeys = array(
            
    'user_id'=>'User'
            
    ,'blog_entry_id'=>'BlogEntry'
        
    );


    This would be used so that if the status of the user where to changed then that change would cascade all dependencies on the linked column.

    PHP Code:
    $user = new User(1); // locate user with primary key of 1
    $user->status 0// set the status to 0
    $user->update(); // update user and cascade the changed value(s) to dependencies 
    The SQL that would be built from this procedure would be similar to the below.

    • Code SQL:
      UPDATE users SET STATUS = 0 WHERE id = 1
      • Code SQL:
        UPDATE blog_entries SET STATUS = 0 WHERE user_id = 1
        • Code SQL:
          UPDATE blog_comments SET STATUS = 0 WHERE blog_entry_id IN (SELECT DISTINCT id FROM blog_entries WHERE user_id = 1)
      • Code SQL:
        UPDATE blog_comments SET STATUS = 0 WHERE user_id = 1


    The result would be that all dependencies that shared a link with the changed property would be updated also.

    The model property I was considering using to declare links would be links.

    Thus, the previously discussed models would now be defined as below with the added links property.

    User Model (revised)
    PHP Code:
    class User {

        public static 
    $fields = array('id','name','status');
        
        public static 
    $hasMany = array('blog_entries','blog_comments');


    BlogEntry Model (revised)
    PHP Code:
    class BlogEntry {

        public static 
    $fields = array('id','user_id','title','entry','status');
        
        public static 
    $foreignKeys = array(
            
    'user_id'=>'User'
        
    );
        
        public static 
    $links = array(
            
    'User'=>array(
                
    'status'=>'status'
            
    )
        );


    BlogComment Model (revised)
    PHP Code:
    class BlogComment {

        public static 
    $fields = array('id','user_id','title','entry','status');
        
        public static 
    $foreignKeys = array(
            
    'user_id'=>'User'
            
    ,'blog_entry_id'=>'BlogEntry'
        
    );
        
        public static 
    $links = array(
            
    'BlogEntry'=>array(
                
    'status'=>'status'
            
    )
            ,
    'User'=>array(
                
    'status'=>'status'
            
    )
        );


    In the simplest of forms this seems to be the direction I'm heading.

    However, I'm unsure if I'm forgeting anything vitally important here. I think all I need to make this work would be to know that one models field can be directly linked to another.

    Using this approach I think it would also be possible to create unions between models. I haven't got this far yet but it seems like a definate possible which I haven't seen yet in other ORM libraries.

    • User(status) => BlogComment(status)
    • User(status) => BlogEntry(status)
    • BlogEntry(status) => BlogComment(status)


    Seems like that is all that would be needed to create a union. Although, then perhaps there would need to be some way to drop links. For instance if links were only declared for the purpose of creating a join.

    User Model (revised)
    PHP Code:
    class User {

        public static 
    $fields = array('id','name','status');
        
        public static 
    $hasMany = array('blog_entries','blog_comments');


    BlogEntry Model (revised)
    PHP Code:
    class BlogEntry {

        public static 
    $fields = array('id','user_id','title','entry','status');
        
        public static 
    $foreignKeys = array(
            
    'user_id'=>'User'
        
    );
        
        public static 
    $links = array(
            
    'User'=>array(
                
    'status'=>'status'
                
    ,'id'=>'id'
            
    )
        );


    BlogComment Model (revised)
    PHP Code:
    class BlogComment {

        public static 
    $fields = array('id','user_id','title','entry','status');
        
        public static 
    $foreignKeys = array(
            
    'user_id'=>'User'
            
    ,'blog_entry_id'=>'BlogEntry'
        
    );
        
        public static 
    $links = array(
            
    'BlogEntry'=>array(
                
    'status'=>'status'
                
    ,'id'=>'id'
            
    )
            ,
    'User'=>array(
                
    'status'=>'status'
                
    ,'id'=>'id'
            
    )
        );


    In the above scenario one wouldn't want to cascade the id so perhaps the update() method could take a argument list of valid links to cascade.

    PHP Code:
    $user = new User(1); // locate user with primary key of 1
    $user->status 0// set the status to 0
    $user->update(array('status')); // only cascading on status 
    Any thoughts, recommendations,insights or overlooks in the creation of this functionality appreciated.

    Have you seen anything like this before in a ORM and do you think its a feature worth integrating?

    I'm not even sure of a good name for this module/functionality as I've never seen something like it before. However,I think it has relevance and furthers the idea of managing a collection of related data through a simple interface which is the dominant purpose what I'm building.

    thanks

  2. #2
    Spirit Coder allspiritseve's Avatar
    Join Date
    Dec 2002
    Location
    Ann Arbor, MI (USA)
    Posts
    648
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by oddz View Post
    Have you seen anything like this before in a ORM and do you think its a feature worth integrating?
    Sorry, is this supposed to be an ORM? I don't see any mapping going on...

  3. #3
    SitePoint Wizard bronze trophy
    Join Date
    Jul 2006
    Location
    Augusta, Georgia, United States
    Posts
    4,194
    Mentioned
    17 Post(s)
    Tagged
    5 Thread(s)
    It's a ActiveRecord implementation although in the examples here I left out non essential code. For example, the models should extend ActiveRecord, but that isn't really important when talking conceptually. I'm just talking in regards to this specific functionality everything else works. I'm currently thinking about how to make the features discussed above a reality.

    PHP Code:
    $user User::find('one','id'=>1);
    $user->status 0;
    $user->update('status'); 
    In actuality its probably more appropriate to call it a hybrid between a gateway and active record.

    PHP Code:
    $blog = new BlogEntry(1// common active record implementation

    $user $blog->getUser(); // ActiveRecord object can be used as a gateway to retrieve related data 
    Although, that's not really the problem here considering that all works fine.


Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •