ASP.NET AJAX & ExtJS 4 Grid (4)

Read Previous Example First!

In this example, we’ll improve our ExtJS 4 model to include an “association” that it will read from XML produced by AJAX call to ASP.NET. Most common association is one to many, for example: your Client can place multiple Orders. An ExtJS 4 data store and model can accommodate this.

The new XML data packet will look like this; notice hiddenAttributes:

<?xml version="1.0" encoding="utf-8"?>
<matches>
	<match>
		<id>0</id>
		<name>Number 0</name>
		<hiddenAttributes>
			<attr>
				<name>hidden1</name>
				<value>val1</value>
			</attr>
			<attr>
				<name>hidden2</name>
				<value>val2</value>
			</attr>
		</hiddenAttributes>
	</match>
	<match><id>1</id><name>Number 1</name></match>
	...
</matches>

We will add an associations attribute to our model. Also, we introduce a new model, for the “many” portion of one-to-many relationship:

// Model
Ext.define('MyOrg.model.SearchResult', {
	extend: 'Ext.data.Model'
	, fields: ['id','name']
	, associations:
	[{ // Hidden Attributes
		type: 'hasMany'
		, model: 'MyOrg.model.SearchResult_HiddenAttribute'
		, associationKey: 'hiddenAttributes' // inner XML node name
		, name: 'hiddenAttributes' 	// Name of the parent store's record's method; if not
									// specified, it will be lower-cased model with "s" at end
		, reader: { type: 'xml', record: 'attr' }
	}] // eo associations
});
 
// Model of hidden attributes
Ext.define('MyOrg.model.SearchResult_HiddenAttribute', {
	extend: 'Ext.data.Model',
	fields: ['name','value']
});

No changes to ExtJS Store are needed! Model takes care of it all! You will now have association data available in the ExtJS 4 data store:

store.data.each(function(item,index,length) {
 
	// No popup if there are no popup attributes
	var hiddenAttriubtes = item.hiddenAttriubtes();
	if ( hiddenAttriubtes.getCount() == 0 ) return;
 
	// Build popup HTML
	var popupHtml = '<table>';
	hiddenAttriubtes.data.each(function(hiddenAttriubte){
		popupHtml += '<tr><td>'
			+ Ext.htmlEncode(hiddenAttriubte.data.name)
			+ '</td><td>'
			+ Ext.htmlEncode(hiddenAttriubte.data.value)
			+ '</td></tr>'
	});
	popupHtml += '</table>';
 
	Ext.Msg.alert('Hidden Attributes', popupHtml);
});

Here’s the corresponding changes to our XML generation script in ASP.NET:

/// <summary>
/// Returns XML  matches/match[id,name]
/// </summary>
/// <param name="query">Search query</param>
[WebMethod(EnableSession = true)]
[ScriptMethod(ResponseFormat=ResponseFormat.Xml,UseHttpGet = false,XmlSerializeString = false)]
public static XmlDocument Search( string query )
{
	XmlDocument doc = new XmlDocument();
	using (XmlWriter writer = doc.CreateNavigator().AppendChild())
	{
		writer.WriteStartDocument();
		writer.WriteStartElement("matches");
 
		// Some postback JSON data { LDAPFilter: '...', MoreData: '...' }
		Dictionary<string,object> JSONData = new Dictionary<string,object>();
		JSONData["LDAPFilter"] = "(&(sAMAccountName=*))";
		JSONData["MoreData"] = "Another var could be DateTime, etc.";
		string XMLData = new System.Web.Script.Serialization.JavaScriptSerializer().Serialize(JSONData);
		writer.WriteElementString("jsonData", XMLData);
 
		for (int i = 0; i < 100; i++)
		{
			writer.WriteStartElement("match");
 
			writer.WriteElementString("id", i);
			writer.WriteElementString("name", "Number " + i);
 
			writer.WriteStartElement("hiddenAttributes");
 
				writer.WriteStartElement("attr");
					writer.WriteElementString("name", "Order ID");
					writer.WriteElementString("value", "1");
				writer.WriteEndElement();
 
				writer.WriteStartElement("attr");
					writer.WriteElementString("name", "Order Name" );
					writer.WriteElementString("value", "First Order");
				writer.WriteEndElement();
 
			writer.WriteEndElement(); // eo hiddenAttributes
 
			writer.WriteEndElement(); // eo match
		}
 
		writer.WriteEndElement(); // eo matches
		writer.WriteEndDocument();
	}
 
	return doc;
}
VN:F [1.9.22_1171]
Rating: 6.8/10 (5 votes cast)
ASP.NET AJAX & ExtJS 4 Grid (4), 6.8 out of 10 based on 5 ratings

Leave a Reply

Your email address will not be published. Required fields are marked *

* Copy This Password *

* Type Or Paste Password Here *