Skip to content

Instantly share code, notes, and snippets.

@bennadel
Created March 25, 2014 12:14
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save bennadel/9760677 to your computer and use it in GitHub Desktop.
Save bennadel/9760677 to your computer and use it in GitHub Desktop.
Using jQuery Deferred To Create Compound Objects From Multiple Asynchronous Data Sources
// Define the Note gateway.
window.NoteGateway = (function( $ ){
// I return an initialized component.
function NoteGateway(){
// Return the initialize object.
return( this );
}
// Define the class methods.
NoteGateway.prototype = {
// I get the note data for the given contact ID.
getNotesByContactId: function( id ){
// Since the data access for notes is (eventually)
// going to be asynchronous, we have to define a
// promise to hold the result.
var result = $.Deferred(
function( deferred ){
// For demo pursposes, we are just going to
// return a static set of notes. We'll need
// to resolve the deferred result with this
// collection.
deferred.resolve(
[
"Her birthday is on the 24th.",
"She likes puppies more than kittens.",
"Favorite number is 24"
]
);
}
);
// Return the promise of a result.
return( result.promise() );
}
};
// ------------------------------------------------------ //
// ------------------------------------------------------ //
// Return the gateway constructor.
return( NoteGateway );
})( jQuery );
// Define the Contact gateway.
window.ContactGateway = (function( $ ){
// I return an initialized component.
function ContactGateway(){
// Return the initialize object.
return( this );
}
// Define the class methods.
ContactGateway.prototype = {
// I get the contact data with the given ID.
getContactById: function( id ){
// Since the data access for contacts is (eventually)
// going to be asynchronous, we have to define a
// promise to hold the result.
var result = $.Deferred(
function( deferred ){
// For demo pursposes, we are just going to
// return a static set of contact data. We'll
// need to resolve the deferred promise.
deferred.resolve(
{
id: 2,
name: "Joanna Smith",
title: "Senior Web Developer",
age: 37
}
);
}
);
// Return the promise of a result.
return( result.promise() );
}
};
// ------------------------------------------------------ //
// ------------------------------------------------------ //
// Return the gateway constructor.
return( ContactGateway );
})( jQuery );
// Define the Note service.
window.NoteService = (function( $ ){
// I return an initialized component.
function NoteService( noteGateway ){
// Store the gateway.
this.noteGateway = noteGateway;
// Return the initialize object.
return( this );
}
// Define the class methods.
NoteService.prototype = {
// I get the notes for the given contact.
getNotesByContactId: function( id ){
// Since the data access for notes is retrieved
// asynchronously, we have to define a promise object
// to hold the result.
var result = $.Deferred();
// Get the data from the note gateway.
var dataCollection = $.when(
this.noteGateway.getNotesByContactId( id )
);
// When the data is retrieved, let's resolve the notes.
dataCollection.done(
function( noteData ){
// Resolve the notes promise - just pass through
// the raw array of string values.
result.resolve( noteData );
}
);
// Return the promise of a result.
return( result.promise() );
}
};
// ------------------------------------------------------ //
// ------------------------------------------------------ //
// Return the service constructor.
return( NoteService );
})( jQuery );
// Define the Contact service.
window.ContactService = (function( $ ){
// I return an initialized component.
function ContactService( contactGateway, noteService ){
// Store the gateway.
this.contactGateway = contactGateway;
// Store the note service.
this.noteService = noteService;
// Return the initialize object.
return( this );
}
// Define the class methods.
ContactService.prototype = {
// I get the contact with the given ID.
getContactById: function( id ){
// Since the data access for contacts is retrieved
// asynchronously, we have to define a promise object
// to hold the result.
var result = $.Deferred();
// Get the contact data from the contact gateway and
// the note data from the note service.
var dataCollection = $.when(
this.contactGateway.getContactById( id ),
this.noteService.getNotesByContactId( id )
);
// When the data is retrieved, let's resolve the contact.
dataCollection.done(
function( contactData, notes ){
// For this demo, we'll create a simple Contact
// object rather than a true domain entity.
var contact = {
id: contactData.id,
name: contactData.name,
title: contactData.title,
age: contactData.age
};
// Now, append the notes that we got from the
// note service.
contact.notes = notes;
// Resolve the contact promise.
result.resolve( contact );
}
);
// Return the promise of a result.
return( result.promise() );
}
};
// ------------------------------------------------------ //
// ------------------------------------------------------ //
// Return the service constructor.
return( ContactService );
})( jQuery );
// Get the contact data from the contact gateway and
// the note data from the note service.
var dataCollection = $.when(
this.contactGateway.getContactById( id ),
this.noteService.getNotesByContactId( id )
);
<!DOCTYPE html>
<html>
<head>
<title>Creating Compound Objects From Multiple Asynchronous Data Sources</title>
<!-- Load and run demo scripts. -->
<script type="text/javascript" src="./jquery-1.7.1.min.js"></script>
<script type="text/javascript" src="./note-gateway.js"></script>
<script type="text/javascript" src="./note-service.js"></script>
<script type="text/javascript" src="./contact-gateway.js"></script>
<script type="text/javascript" src="./contact-service.js"></script>
<script type="text/javascript">
// Create Note access classes.
var noteGateway = new NoteGateway();
var noteService = new NoteService( noteGateway );
// Create Contact access classes.
var contactGateway = new ContactGateway();
var contactService = new ContactService( contactGateway, noteService );
// -------------------------------------------------- //
// -------------------------------------------------- //
// Get the contact with the given ID. Since this involves
// asynchronous data retrieval, we'll get a promise object
// as a response.
var contactResult = contactService.getContactById( 2 );
// When the contact comes back, log it.
contactResult.done(
function( contact ){
console.log( contact );
}
);
</script>
</head>
<body>
<!-- Left intentionally blank. -->
</body>
</html>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment