How to pass a parameter across a contributed action call?

Jan 9, 2013 at 7:53 AM

Hi.

I have a repository action that returns an IQueryable<T>. It takes a parameter of type X that is populated by a choices method.

I have a Contributed action on IQueryable<T>. Obviously this is available to be invoked on the results of the repository action. It takes a parameter of type Y that is populated by a choices method filtering on X.

When the user invokes the contributed action on the returned entities that they have selected with checkboxes, I need to get hold of the X parameter the user selected on the repository action, in order to populate the filtered choices for Y.

But because the individual requests are stateless, I cannot think of a way to transfer the parameter from the first repository action to the contributed action.

Any ideas?

Coordinator
Jan 14, 2013 at 7:18 PM

I can' think of any simple or elegant way to do this.  

One  rather clunky option would be to give the contributed action both the parameters X and Y (in addition to the IQueryable<T>) and then add a conditional choices method, where they select X (again) and then get the appropriate filtered sub-set of Y.  OK the user has to select the same X a second time, but at least this would give them the reduced Y.

The only other option I can think of  -  extremely ugly  -  would be to cache the X value on the session and retrieve it from there for the second operation.

One other question:  can the value originally selected for X be inferred in any way from the results contained in the returned IQueryable ?

Jan 15, 2013 at 8:06 AM
Edited Jan 15, 2013 at 8:07 AM

One  rather clunky option would be to give the contributed action both the parameters X and Y (in addition to the IQueryable<T>) and then add a conditional choices method, where they select X (again) and then get the appropriate filtered sub-set of Y.  OK the user has to select the same X a second time, but at least this would give them the reduced Y.

Yes, I thought of that, but I promise you, the users will take one look and complain about having to select it after just having selected it. :)

Yeah, the session is ugly. Everything is stateless up to now.

One other question:  can the value originally selected for X be inferred in any way from the results contained in the returned IQueryable ?

Yes it can. But how to get hold of the results in the choices method of the contributed action?

Coordinator
Jan 15, 2013 at 8:24 AM

Try this:

public void ContributedActionName(IQueryable<Foo> foos, Bar bar) { }

//N.B.  Note the '1' below

public List<Bar> Choices1ContributedActionName(IQueryable<Foo> foos) {

  //process the foos to determine the bar choices

}

I have no idea whether this will in fact work or not  -  it is just a suggestion to try.  If it doesn't work then there's nothing else I can think of, sorry. 

Jan 15, 2013 at 8:59 AM

Awesome Richard! That actually worked.

Now I'll just have to process all of the selected Foo results to validate that they have the same Bar. This is because the contributed action for IQueryable<Foo> will appear for all instances, even results that came from another filter. And if they ar not the same across the board, I'll bomb out.

Thanx for the tip

Coordinator
Jan 15, 2013 at 10:55 AM

"Now I'll just have to process all of the selected Foo results to validate that they have the same Bar"

But you can do that with a very simple LINQ operation on the IQueryable<Foo>  -  without enumerating through them.  In fact you could (I'm inferring) just do a simple count on the number of Bars that appear within the IQueryable, and if it is more than one instance of Bar then ignore it for the purposes of filtering down the subsequent drop-down.

Jan 15, 2013 at 1:25 PM

Yes. I just did

 

			var numberOfSites = vehicles
				.GroupBy(v => v.Site_Id)
				.Count();
			if (numberOfSites > 1)
				this.Container.RaiseError("You cannot perform this action on vehicles from more than one branch. They must all be from the same branch.");