1 //
2 // LinqDataSource.cs
3 //
4 // Author:
5 //   Atsushi Enomoto  <atsushi@ximian.com>
6 //
7 // Copyright (C) 2008 Novell, Inc  http://novell.com
8 //
9 
10 //
11 // Permission is hereby granted, free of charge, to any person obtaining
12 // a copy of this software and associated documentation files (the
13 // "Software"), to deal in the Software without restriction, including
14 // without limitation the rights to use, copy, modify, merge, publish,
15 // distribute, sublicense, and/or sell copies of the Software, and to
16 // permit persons to whom the Software is furnished to do so, subject to
17 // the following conditions:
18 //
19 // The above copyright notice and this permission notice shall be
20 // included in all copies or substantial portions of the Software.
21 //
22 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
23 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
24 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
25 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
26 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
27 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
28 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 //
30 using System;
31 using System.Collections;
32 using System.ComponentModel;
33 using System.Security.Permissions;
34 using System.Web;
35 using System.Web.DynamicData;
36 using System.Web.UI;
37 
38 namespace System.Web.UI.WebControls
39 {
40 //	[ToolboxBitmap (typeof (LinqDataSource), "LinqDataSource.ico")]
41 	[PersistChildren (false)]
42 	[ParseChildren (true)]
43 	[Designer ("System.Web.UI.Design.WebControls.LinqDataSourceDesigner, System.Web.Extensions.Design, Version=3.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35")]
44 	[DefaultEvent ("Selecting")]
45 	[ToolboxItemFilter ("System.Web.Extensions, Version=3.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", ToolboxItemFilterType.Require)]
46 	[DefaultProperty ("ContextTypeName")]
47 	public class LinqDataSource : DataSourceControl, IDynamicDataSource
48 	{
49 		static readonly string [] empty_names = new string [] { "DefaultView" };
50 
LinqDataSource()51 		public LinqDataSource ()
52 		{
53 		}
54 
OnInit(EventArgs e)55 		protected internal override void OnInit (EventArgs e)
56 		{
57 			Page.LoadComplete += OnPageLoadComplete;
58 		}
59 
OnPageLoadComplete(object sender, EventArgs e)60 		void OnPageLoadComplete (object sender, EventArgs e)
61 		{
62 			SelectParameters.UpdateValues (Context, this);
63 			WhereParameters.UpdateValues (Context, this);
64 			GroupByParameters.UpdateValues (Context, this);
65 			OrderByParameters.UpdateValues (Context, this);
66 			OrderGroupsByParameters.UpdateValues (Context, this);
67 		}
68 
OnUnload(EventArgs e)69 		protected internal override void OnUnload (EventArgs e)
70 		{
71 			base.OnUnload (e);
72 
73 			// no further things to do?
74 		}
75 
76 		#region View
77 
78 		LinqDataSourceView view;
79 		LinqDataSourceView View {
80 			get {
81 				if (view == null) {
82 					view = CreateView ();
83 					if (IsTrackingViewState)
84 						((IStateManager) view).TrackViewState ();
85 				}
86 				return view;
87 			}
88 		}
89 
CreateView()90 		protected virtual LinqDataSourceView CreateView ()
91 		{
92 			var view = new LinqDataSourceView (this, Guid.NewGuid ().ToString (), HttpContext.Current);
93 			if (IsTrackingViewState)
94 				((IStateManager) view).TrackViewState ();
95 			return view;
96 		}
97 
GetView(string viewName)98 		protected override DataSourceView GetView (string viewName)
99 		{
100 			if (String.IsNullOrEmpty (viewName) || (String.Compare (viewName, empty_names [0], StringComparison.InvariantCultureIgnoreCase) == 0))
101 				return View;
102 			throw new ArgumentException ("viewName must be 'DefaultView' in LinqDataSource");
103 		}
104 
GetViewNames()105 		protected override ICollection GetViewNames ()
106 		{
107 			return empty_names;
108 		}
109 
110 		#endregion
111 
112 		[Category ("Behavior")]
113 		[DefaultValue (false)]
114 		public bool AutoGenerateOrderByClause {
115 			get { return View.AutoGenerateOrderByClause; }
116 			set { View.AutoGenerateOrderByClause = value; }
117 		}
118 
119 		[Category ("Behavior")]
120 		[DefaultValue (false)]
121 		public bool AutoGenerateWhereClause {
122 			get { return View.AutoGenerateWhereClause; }
123 			set { View.AutoGenerateWhereClause = value; }
124 		}
125 
126 		[Category ("Behavior")]
127 		[DefaultValue (true)]
128 		public bool AutoPage {
129 			get { return View.AutoPage; }
130 			set { View.AutoPage = value; }
131 		}
132 
133 		[Category ("Behavior")]
134 		[DefaultValue (true)]
135 		public bool AutoSort {
136 			get { return View.AutoSort; }
137 			set { View.AutoSort = value; }
138 		}
139 
140 		[Category ("Data")]
141 		[DefaultValue ("")]
142 		public string ContextTypeName { get; set; }
143 
144 		Type context_type;
145 
146 		[MonoTODO ("looks like we need System.Web.Query.Dynamic stuff or alternative")]
147 		Type IDynamicDataSource.ContextType {
148 			get {
149 				if (context_type != null && context_type.FullName == ContextTypeName)
150 					return context_type;
151 
152 				if (String.IsNullOrEmpty (ContextTypeName))
153 					return null;
154 
155 				// FIXME: retrieve type from BuildProvider or whatever.
156 				context_type = LoadType (ContextTypeName);
157 				if (context_type == null)
158 					throw new ArgumentException (String.Format ("Type '{0}' cannot be loaded", ContextTypeName));
159 				return context_type;
160 			}
161 			set {
162 				if (value == null)
163 					throw new ArgumentNullException ("value");
164 				context_type = value;
165 				ContextTypeName = context_type.FullName;
166 			}
167 		}
168 
LoadType(string name)169 		private Type LoadType (string name)
170 		{
171 			foreach (var ass in AppDomain.CurrentDomain.GetAssemblies ())
172 				foreach (var type in ass.GetTypes ())
173 					if (type.FullName == name)
174 						return type;
175 			return null;
176 		}
177 
178 		string IDynamicDataSource.EntitySetName {
179 			get { return TableName; }
180 			set { TableName = value; }
181 		}
182 
183 		[Category ("Data")]
184 		[DefaultValue ("")]
185 		public string TableName {
186 			get { return View.TableName; }
187 			set { View.TableName = value; }
188 		}
189 
190 		[Category ("Behavior")]
191 		[DefaultValue (false)]
192 		public bool EnableDelete {
193 			get { return View.EnableDelete; }
194 			set { View.EnableDelete = value; }
195 		}
196 
197 		[Category ("Behavior")]
198 		[DefaultValue (false)]
199 		public bool EnableInsert {
200 			get { return View.EnableInsert; }
201 			set { View.EnableInsert = value; }
202 		}
203 
204 		[Category ("Behavior")]
205 		[DefaultValue (false)]
206 		public bool EnableObjectTracking {
207 			get { return View.EnableObjectTracking; }
208 			set { View.EnableObjectTracking = value; }
209 		}
210 
211 		[Category ("Behavior")]
212 		[DefaultValue (false)]
213 		public bool EnableUpdate {
214 			get { return View.EnableUpdate; }
215 			set { View.EnableUpdate = value; }
216 		}
217 
218 		[Category ("Data")]
219 		[DefaultValue ("")]
220 		public string GroupBy {
221 			get { return View.GroupBy; }
222 			set { View.GroupBy = value; }
223 		}
224 
225 		[Category ("Data")]
226 		[DefaultValue ("")]
227 		public string OrderBy {
228 			get { return View.OrderBy; }
229 			set { View.OrderBy = value; }
230 		}
231 
232 		[Category ("Data")]
233 		[DefaultValue ("")]
234 		public string OrderGroupsBy {
235 			get { return View.OrderGroupsBy; }
236 			set { View.OrderGroupsBy = value; }
237 		}
238 
239 		[Category ("Data")]
240 		[DefaultValue ("")]
241 		public string Select {
242 			get { return View.SelectNew; }
243 			set { View.SelectNew = value; }
244 		}
245 
246 		[Category ("Data")]
247 		[DefaultValue ("")]
248 		public string Where {
249 			get { return View.Where; }
250 			set { View.Where = value; }
251 		}
252 
253 		[MergableProperty (false)]
254 		[Category ("Data")]
255 		[DefaultValue (null)]
256 		[PersistenceMode (PersistenceMode.InnerProperty)]
257 		[Browsable (false)]
258 		public ParameterCollection SelectParameters {
259 			get { return View.SelectNewParameters; }
260 		}
261 
262 		[MergableProperty (false)]
263 		[Category ("Data")]
264 		[DefaultValue (null)]
265 		[Browsable (false)]
266 		[PersistenceMode (PersistenceMode.InnerProperty)]
267 		public ParameterCollection WhereParameters {
268 			get { return View.WhereParameters; }
269 		}
270 
271 		[MergableProperty (false)]
272 		[Category ("Data")]
273 		[DefaultValue (null)]
274 		[Browsable (false)]
275 		[PersistenceMode (PersistenceMode.InnerProperty)]
276 		public ParameterCollection GroupByParameters {
277 			get { return View.GroupByParameters; }
278 		}
279 
280 		[MergableProperty (false)]
281 		[Category ("Data")]
282 		[DefaultValue (null)]
283 		[Browsable (false)]
284 		[PersistenceMode (PersistenceMode.InnerProperty)]
285 		public ParameterCollection OrderByParameters {
286 			get { return View.OrderByParameters; }
287 		}
288 
289 		[MergableProperty (false)]
290 		[Category ("Data")]
291 		[DefaultValue (null)]
292 		[PersistenceMode (PersistenceMode.InnerProperty)]
293 		[Browsable (false)]
294 		public ParameterCollection OrderGroupsByParameters {
295 			get { return View.OrderGroupsByParameters; }
296 		}
297 
298 		[MergableProperty (false)]
299 		[Category ("Data")]
300 		[DefaultValue (null)]
301 		[PersistenceMode (PersistenceMode.InnerProperty)]
302 		[Browsable (false)]
303 		public ParameterCollection DeleteParameters {
304 			get { return View.DeleteParameters; }
305 		}
306 
307 		[MergableProperty (false)]
308 		[Category ("Data")]
309 		[DefaultValue (null)]
310 		[PersistenceMode (PersistenceMode.InnerProperty)]
311 		[Browsable (false)]
312 		public ParameterCollection InsertParameters {
313 			get { return View.InsertParameters; }
314 		}
315 
316 		[MergableProperty (false)]
317 		[Category ("Data")]
318 		[DefaultValue (null)]
319 		[PersistenceMode (PersistenceMode.InnerProperty)]
320 		[Browsable (false)]
321 		public ParameterCollection UpdateParameters {
322 			get { return View.UpdateParameters; }
323 		}
324 
Delete(IDictionary keys, IDictionary oldValues)325 		public int Delete (IDictionary keys, IDictionary oldValues)
326 		{
327 			return View.Delete (keys, oldValues);
328 		}
329 
Insert(IDictionary values)330 		public int Insert (IDictionary values)
331 		{
332 			return View.Insert (values);
333 		}
334 
Update(IDictionary keys, IDictionary values, IDictionary oldValues)335 		public int Update (IDictionary keys, IDictionary values, IDictionary oldValues)
336 		{
337 			return View.Update (keys, values, oldValues);
338 		}
339 
340 		#region ViewState
341 
342 		[Category ("Behavior")]
343 		[DefaultValue (true)]
344 		public bool StoreOriginalValuesInViewState {
345 			get { return View.StoreOriginalValuesInViewState; }
346 			set { View.StoreOriginalValuesInViewState = value; }
347 		}
348 
LoadViewState(object savedState)349 		protected override void LoadViewState (object savedState)
350 		{
351 			Pair p = savedState as Pair;
352 			if (p != null) {
353 				base.LoadViewState (p.First);
354 				((IStateManager) View).LoadViewState (p.Second);
355 			}
356 		}
357 
SaveViewState()358 		protected override object SaveViewState ()
359 		{
360 			object me = base.SaveViewState (), view = ((IStateManager) View).SaveViewState ();
361 			if (me != null || view != null)
362 				return new Pair (me, view);
363 			else
364 				return null;
365 		}
366 
TrackViewState()367 		protected override void TrackViewState ()
368 		{
369 			base.TrackViewState ();
370 			if (view != null)
371 				((IStateManager) view).TrackViewState ();
372 		}
373 
374 		#endregion
375 
376 		#region Events (Dispatching)
377 
378 		public event EventHandler<LinqDataSourceStatusEventArgs> ContextCreated {
379 			add { View.ContextCreated += value; }
380 			remove { View.ContextCreated -= value; }
381 		}
382 
383 		public event EventHandler<LinqDataSourceContextEventArgs> ContextCreating {
384 			add { View.ContextCreating += value; }
385 			remove { View.ContextCreating -= value; }
386 		}
387 
388 		public event EventHandler<LinqDataSourceDisposeEventArgs> ContextDisposing {
389 			add { View.ContextDisposing += value; }
390 			remove { View.ContextDisposing -= value; }
391 		}
392 
393 		public event EventHandler<LinqDataSourceStatusEventArgs> Deleted {
394 			add { View.Deleted += value; }
395 			remove { View.Deleted -= value; }
396 		}
397 
398 		public event EventHandler<LinqDataSourceDeleteEventArgs> Deleting {
399 			add { View.Deleting += value; }
400 			remove { View.Deleting -= value; }
401 		}
402 
403 		event EventHandler<DynamicValidatorEventArgs> IDynamicDataSource.Exception {
404 			add { View.Exception += value; }
405 			remove { View.Exception -= value; }
406 		}
407 
408 		public event EventHandler<LinqDataSourceStatusEventArgs> Inserted {
409 			add { View.Inserted += value; }
410 			remove { View.Inserted -= value; }
411 		}
412 
413 		public event EventHandler<LinqDataSourceInsertEventArgs> Inserting {
414 			add { View.Inserting += value; }
415 			remove { View.Inserting -= value; }
416 		}
417 
418 		public event EventHandler<LinqDataSourceStatusEventArgs> Selected {
419 			add { View.Selected += value; }
420 			remove { View.Selected -= value; }
421 		}
422 
423 		public event EventHandler<LinqDataSourceSelectEventArgs> Selecting {
424 			add { View.Selecting += value; }
425 			remove { View.Selecting -= value; }
426 		}
427 
428 		public event EventHandler<LinqDataSourceStatusEventArgs> Updated {
429 			add { View.Updated += value; }
430 			remove { View.Updated -= value; }
431 		}
432 
433 		public event EventHandler<LinqDataSourceUpdateEventArgs> Updating {
434 			add { View.Updating += value; }
435 			remove { View.Updating -= value; }
436 		}
437 
438 		#endregion
439 	}
440 }
441