(DISTFILES): Comment out a few missing files.
[mono-project.git] / mcs / class / System.Web / System.Web.UI.WebControls / AdRotator.cs
blobbf9066c3a83608d6ea4e993737819ea7943d2b80
1 //
2 // System.Web.UI.WebControls.AdRotator.cs
3 //
4 // Authors:
5 // Gaurav Vaish (gvaish@iitk.ac.in)
6 // Gonzalo Paniagua Javier (gonzalo@ximian.com)
7 // Andreas Nahr (ClassDevelopment@A-SoftTech.com)
8 // Sanjay Gupta (gsanjay@novell.com)
9 //
10 // (c) 2002 Ximian, Inc. (http://www.ximian.com)
11 // (C) Gaurav Vaish (2002)
12 // (C) 2003 Andreas Nahr
13 // (C) 2004 Novell, Inc. (http://www.novell.com)
17 // Permission is hereby granted, free of charge, to any person obtaining
18 // a copy of this software and associated documentation files (the
19 // "Software"), to deal in the Software without restriction, including
20 // without limitation the rights to use, copy, modify, merge, publish,
21 // distribute, sublicense, and/or sell copies of the Software, and to
22 // permit persons to whom the Software is furnished to do so, subject to
23 // the following conditions:
24 //
25 // The above copyright notice and this permission notice shall be
26 // included in all copies or substantial portions of the Software.
27 //
28 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
29 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
30 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
31 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
32 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
33 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
34 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
37 using System;
38 using System.IO;
39 using System.Collections;
40 using System.Collections.Specialized;
41 using System.Web;
42 using System.Web.Caching;
43 using System.Web.UI;
44 using System.Xml;
45 using System.Web.Util;
46 using System.ComponentModel;
47 using System.ComponentModel.Design;
49 namespace System.Web.UI.WebControls
51 [DefaultEvent("AdCreated")]
52 [DefaultProperty("AdvertisementFile")]
53 [Designer ("System.Web.UI.Design.WebControls.AdRotatorDesigner, " + Consts.AssemblySystem_Design, typeof (IDesigner))]
54 [ToolboxData("<{0}:AdRotator runat=\"server\" Height=\"60px\" "
55 + "Width=\"468\"></{0}:AdRotator>")]
56 public class AdRotator: WebControl
58 string advertisementFile;
59 static readonly object AdCreatedEvent = new object();
61 // Will be set values during (On)PreRender-ing
62 string alternateText;
63 string imageUrl;
64 string navigateUrl;
65 string fileDirectory;
66 Random random;
68 public AdRotator ()
70 advertisementFile = "";
71 fileDirectory = null;
74 AdRecord[] LoadAdFile (string file)
76 Stream fStream;
77 try {
78 fStream = new FileStream (file, FileMode.Open, FileAccess.Read, FileShare.Read);
79 } catch (Exception e) {
80 throw new HttpException("AdRotator: Unable to open file", e);
83 ArrayList list = new ArrayList ();
84 try {
85 IDictionary hybridDict = null;
86 XmlDocument document = new XmlDocument ();
87 document.Load (fStream);
89 XmlElement docElem = document.DocumentElement;
91 if (docElem == null)
92 throw new HttpException ("No advertisements found");
94 if (docElem.LocalName != "Advertisements")
95 throw new HttpException ("No advertisements found: invalid document element");
97 XmlNode node = docElem.FirstChild;
98 while (node != null) {
99 if (node.LocalName == "Ad") {
100 XmlNode innerNode = node.FirstChild;
101 while (innerNode != null) {
102 if (node.NodeType == XmlNodeType.Element) {
103 if (hybridDict == null)
104 hybridDict = new HybridDictionary ();
106 hybridDict.Add (innerNode.LocalName, innerNode.InnerText);
108 innerNode = innerNode.NextSibling;
111 if (hybridDict != null) {
112 list.Add (hybridDict);
113 hybridDict = null;
116 node = node.NextSibling;
119 } catch(Exception e) {
120 throw new HttpException("Parse error:" + file, e);
121 } finally {
122 if (fStream != null)
123 fStream.Close();
126 if (list.Count == 0)
127 throw new HttpException ("No advertisements found");
129 AdRecord [] adsArray = new AdRecord [list.Count];
130 int count = list.Count;
131 for (int i = 0; i < count; i++)
132 adsArray [i] = new AdRecord ((IDictionary) list [i]);
134 return adsArray;
137 AdRecord [] GetData (string file)
139 string physPath = MapPathSecure (file);
140 string AdKey = "AdRotatorCache: " + physPath;
141 fileDirectory = UrlUtils.GetDirectory (UrlUtils.Combine (TemplateSourceDirectory, file));
142 Cache cache = HttpRuntime.Cache;
143 AdRecord[] records = (AdRecord[]) cache [AdKey];
144 if (records == null) {
145 records = LoadAdFile (physPath);
146 cache.Insert (AdKey, records, new CacheDependency (physPath));
149 return records;
152 IDictionary SelectAd ()
154 AdRecord[] records = GetData (AdvertisementFile);
155 if (records == null || records.Length ==0)
156 return null;
158 int impressions = 0;
159 int rlength = records.Length;
160 for (int i=0 ; i < rlength; i++) {
161 if (IsAdMatching (records [i]))
162 impressions += records [i].Hits;
165 if (impressions == 0)
166 return null;
168 if (random == null)
169 random = new Random ();
171 int rnd = random.Next (impressions) + 1;
172 int counter = 0;
173 int index = 0;
174 for (int i = 0; i < rlength; i++) {
175 if(IsAdMatching(records[i])) {
176 if (rnd <= (counter + records [i].Hits)) {
177 index = i;
178 break;
180 counter += records [i].Hits;
184 return records [index].Properties;
187 private bool IsAdMatching (AdRecord currAd)
189 if (KeywordFilter != String.Empty)
190 return (0 == String.Compare (currAd.Keyword, KeywordFilter, true));
192 return true;
195 private string ResolveAdUrl (string relativeUrl)
197 if (relativeUrl.Length==0 || !UrlUtils.IsRelativeUrl (relativeUrl))
198 return relativeUrl;
200 string fullUrl;
201 if (fileDirectory != null)
202 fullUrl = fileDirectory;
203 else
204 fullUrl = TemplateSourceDirectory;
206 if (fullUrl.Length == 0)
207 return relativeUrl;
209 return UrlUtils.Combine (fullUrl, relativeUrl);
212 [WebCategory("Action")]
213 [WebSysDescription("AdRotator_OnAdCreated")]
214 public event AdCreatedEventHandler AdCreated {
215 add { Events.AddHandler (AdCreatedEvent, value); }
216 remove { Events.RemoveHandler (AdCreatedEvent, value); }
219 [Bindable(true)]
220 [DefaultValue("")]
221 [Editor ("System.Web.UI.Design.XmlUrlEditor, " + Consts.AssemblySystem_Design, typeof (System.Drawing.Design.UITypeEditor))]
222 [WebCategory("Behavior")]
223 [WebSysDescription("AdRotator_AdvertisementFile")]
224 #if NET_2_0
225 [Localizable (true)]
226 [UrlProperty ()]
227 #endif
228 public string AdvertisementFile {
229 get { return ((advertisementFile != null) ? advertisementFile : ""); }
230 set { advertisementFile = value; }
233 [Browsable (false), EditorBrowsable (EditorBrowsableState.Never)]
234 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
235 public override FontInfo Font {
236 get { return base.Font; }
239 [Bindable(true)]
240 [DefaultValue("")]
241 [WebCategory("Behavior")]
242 [WebSysDescription("AdRotator_KeywordFilter")]
243 public string KeywordFilter {
244 get {
245 object o = ViewState ["KeywordFilter"];
246 if (o != null)
247 return (string) o;
249 return String.Empty;
251 set {
252 if(value != null)
253 ViewState ["KeywordFilter"] = value.Trim ();
257 [Bindable(true)]
258 [DefaultValue("")]
259 [TypeConverter(typeof(TargetConverter))]
260 [WebCategory("Behavior")]
261 [WebSysDescription("AdRotator_Target")]
262 public string Target {
263 get {
264 object o = ViewState ["Target"];
265 if (o != null)
266 return (string) o;
268 return "_top";
270 set {
271 ViewState["Target"] = value;
275 protected override ControlCollection CreateControlCollection ()
277 return new EmptyControlCollection (this);
280 protected virtual void OnAdCreated (AdCreatedEventArgs e)
282 if (Events == null)
283 return;
285 AdCreatedEventHandler aceh = (AdCreatedEventHandler) Events [AdCreatedEvent];
286 if (aceh != null)
287 aceh (this, e);
290 protected override void OnPreRender (EventArgs e)
292 if(AdvertisementFile == String.Empty)
293 return;
295 AdCreatedEventArgs acea = new AdCreatedEventArgs (SelectAd ());
296 OnAdCreated (acea);
297 imageUrl = acea.ImageUrl;
298 navigateUrl = acea.NavigateUrl;
299 alternateText = acea.AlternateText;
302 [MonoTODO ("Update method with net 2.0 properties added for AdRotator class")]
303 protected override void Render (HtmlTextWriter writer)
305 HyperLink hLink = new HyperLink ();
306 Image adImage = new Image();
307 foreach (string current in Attributes.Keys)
308 hLink.Attributes [current] = Attributes [current];
310 if (ID != null && ID.Length > 0)
311 hLink.ID = ID;
313 hLink.Target = Target;
314 hLink.AccessKey = AccessKey;
315 hLink.Enabled = Enabled;
316 hLink.TabIndex = TabIndex;
317 if (navigateUrl != null && navigateUrl.Length != 0)
318 hLink.NavigateUrl = ResolveAdUrl (navigateUrl);
320 hLink.RenderBeginTag (writer);
321 if (ControlStyleCreated)
322 adImage.ApplyStyle(ControlStyle);
324 if(imageUrl!=null && imageUrl.Length > 0)
325 adImage.ImageUrl = ResolveAdUrl (imageUrl);
327 adImage.AlternateText = alternateText;
328 adImage.ToolTip = ToolTip;
329 adImage.RenderControl (writer);
330 hLink.RenderEndTag (writer);
333 #if NET_2_0
334 AdType adType;
336 [DefaultValueAttribute ("Banner")]
337 [WebCategoryAttribute ("Behavior")]
338 [WebSysDescriptionAttribute ("Advertisement of specific type is created by specified value")]
339 public AdType AdType {
340 get { return adType; }
341 set { adType = value; }
344 string alternateTextField;
346 [DefaultValueAttribute ("AlternateText")]
347 [WebCategoryAttribute ("Behavior")]
348 [WebSysDescriptionAttribute ("Alternate text is retrieved from the elmenet name specified.")]
349 //[VerificationAttribute ()]
350 public string AlternateTextField {
351 get { return alternateTextField; }
352 set { alternateTextField = value; }
355 bool countClicks;
357 [DefaultValueAttribute (false)]
358 [WebCategoryAttribute ("Site Counters")]
359 [WebSysDescriptionAttribute ("On clicking an advertisement, click-through events should be counted.")]
360 public bool CountClicks {
361 get { return countClicks; }
362 set { countClicks = value; }
365 string counterGroup;
367 [DefaultValueAttribute ("AdRotator")]
368 [WebCategoryAttribute ("Site Counters")]
369 [WebSysDescriptionAttribute ("Name of the group which takes care of counting.")]
370 public string CounterGroup {
371 get { return counterGroup; }
372 set { counterGroup = value; }
375 string counterName;
377 [DefaultValueAttribute ("")]
378 [WebCategoryAttribute ("Site Counters")]
379 [WebSysDescriptionAttribute ("Name of the group which takes care of counting.")]
380 public string CounterName {
381 get { return counterName; }
382 set { counterName = value; }
385 bool countViews;
387 [DefaultValueAttribute (false)]
388 [WebCategoryAttribute ("Site Counters")]
389 [WebSysDescriptionAttribute ("On creation of an advertisement, view events should be counted.")]
390 public bool CountViews {
391 get { return countViews; }
392 set { countViews = value; }
395 string imageUrlField;
397 [DefaultValueAttribute ("ImageUrl")]
398 [WebCategoryAttribute ("Behavior")]
399 [WebSysDescriptionAttribute ("Image URL is retrieved from the elmenet name specified.")]
400 public string ImageUrlField {
401 get { return imageUrlField; }
402 set { imageUrlField = value; }
405 string navigateUrlField;
407 [DefaultValueAttribute ("NavigateUrl")]
408 [WebCategoryAttribute ("Behavior")]
409 [WebSysDescriptionAttribute ("Advertisement Web page URL is retrieved from the elmenet name specified.")]
410 public string NavigateUrlField {
411 get { return navigateUrlField; }
412 set { navigateUrlField = value; }
415 int popFrequency;
417 [DefaultValueAttribute ("100")]
418 [WebCategoryAttribute ("Behavior")]
419 [WebSysDescriptionAttribute ("Frequency in percentage for creation of Popup or PopUnder advertisement.")]
420 public int PopFrequency {
421 get { return popFrequency; }
422 set { popFrequency = value; }
425 int popPositionLeft;
427 [DefaultValueAttribute ("-1")]
428 [WebCategoryAttribute ("Appearance")]
429 [WebSysDescriptionAttribute ("Specifies X-coordinate in pixels of Popunder or Popup advertisements top-left corner.")]
430 public int PopPositionLeft {
431 get { return popPositionLeft; }
432 set { popPositionLeft = value; }
435 int popPositionTop;
437 [DefaultValueAttribute ("-1")]
438 [WebCategoryAttribute ("Appearance")]
439 [WebSysDescriptionAttribute ("Specifies Y-coordinate in pixels of Popunder or Popup advertisements top-left corner.")]
440 public int PopPositionTop {
441 get { return popPositionTop; }
442 set { popPositionTop = value; }
445 int rowsPerDay;
447 [DefaultValueAttribute ("-1")]
448 [WebCategoryAttribute ("Site Counters")]
449 [WebSysDescriptionAttribute ("On a given day this many number of rows of data needs to be collected.")]
450 public int RowsPerDay {
451 get { return rowsPerDay; }
452 set { rowsPerDay = value; }
455 string siteCountersProvider;
457 [DefaultValueAttribute ("")]
458 [WebCategoryAttribute ("Site Counters")]
459 [WebSysDescriptionAttribute ("Control uses the specified provider.")]
460 public string SiteCountersProvider {
461 get { return siteCountersProvider; }
462 set { siteCountersProvider = value; }
465 bool trackApplicationName;
467 [DefaultValueAttribute (true)]
468 [WebCategoryAttribute ("Site Counters")]
469 [WebSysDescriptionAttribute ("SiteCounters service tracks and stores the specified application name in a database.")]
470 public bool TrackApplicationName {
471 get { return trackApplicationName; }
472 set { trackApplicationName = value; }
475 bool trackNavigateUrl;
477 [DefaultValueAttribute (true)]
478 [WebCategoryAttribute ("Site Counters")]
479 [WebSysDescriptionAttribute ("SiteCounters service tracks and stores the destination URL of click through event in a database.")]
480 public bool TrackNavigateUrl {
481 get { return trackNavigateUrl; }
482 set { trackNavigateUrl = value; }
485 bool trackPageUrl;
487 [DefaultValueAttribute (true)]
488 [WebCategoryAttribute ("Site Counters")]
489 [WebSysDescriptionAttribute ("SiteCounters service tracks and stores the originating page URL in a database.")]
490 public bool TrackPageUrl {
491 get { return trackPageUrl; }
492 set { trackPageUrl = value; }
494 #endif
496 class AdRecord
498 public IDictionary Properties;
499 public int Hits; // or impressions or clicks
500 public string Keyword;
502 public AdRecord (IDictionary adProps)
504 this.Properties = adProps;
505 Keyword = Properties ["Keyword"] as string;
506 if (Keyword == null)
507 Keyword = "";
509 string imp = Properties ["Impressions"] as string;
510 Hits = 1;
511 if (imp != null) {
512 try {
513 Hits = Int32.Parse (imp);
514 } catch {