asp.net

Pittsburgh Code Camp 2011.1

When: 
Saturday, April 30, 2011 - 9:00am - 5:00pm

http://pghdotnet.org/?page_id=46

Registration Now Open for April 30, 2011 Code Camp!

Pittsburgh .Net Code Camp 2011.1 will be held April 30, 2011 on the campus of Robert Morris University from 9:00 am to 5:00 pm. Registration will open at 8:30. The schedule of presentations will be available soon after we close the call for speakers. Please note that the schedule will be subject to change, as sometimes unforeseen events prevent a presentation from taking place.

Directions to RMU can be found here. Parking is free in the Upper Massey Lot (#4 on the parking map, found here) and the event itself will be in the Hale Center, northwest of the Upper Massey Lot. Most sessions will be on the second floor – handicap access is available via the elevator on the third floor (you pass the third floor entrance of the building first). The second floor can be access via stairways on the third floor or by entering around the building, which enters at the second floor. Lunch will be provided, and we are hoping to make coffee available in the morning.

Asp.Net MVC Calendar Helper

What it looks like

MVC3 Calendar

Recently while working on a project with Asp.Net MVC 3 there was a need for a small calendar similar to the asp.net calendar control. After some searching I decided that the easiest method to get this done would be to write a Html Helper. Below is the code that seems to work nicely. This works even if the browser does not support javascript. For added functionality you could add an extra parameter to show highlighted dates or extend it to fill a page and add content to the cells.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Text;
using System.Web;
using System.Web.Mvc;
 
namespace AntiYes.Helpers
{
    public static class CalendarExtensions
    {
        public static IHtmlString Calendar(this HtmlHelper helper, DateTime dateToShow)
        {
            DateTimeFormatInfo cinfo = DateTimeFormatInfo.CurrentInfo;
            StringBuilder sb = new StringBuilder();
            DateTime date = new DateTime(dateToShow.Year, dateToShow.Month, 1);
            int emptyCells = ((int)date.DayOfWeek + 7 - (int)cinfo.FirstDayOfWeek) % 7;
            int days = DateTime.DaysInMonth(dateToShow.Year, dateToShow.Month);
            sb.Append("<table class='cal'><tr><th colspan='7'>" + cinfo.MonthNames[date.Month - 1] + " " + dateToShow.Year + "</th></tr>");
            for (int i = 0; i < ((days + emptyCells) > 35 ? 42 : 35); i++)
            {
                if (i % 7 == 0)
                {
                    if (i > 0) sb.Append("</tr>");
                    sb.Append("<tr>");
                }
 
                if (i < emptyCells || i >= emptyCells + days)
                {
                    sb.Append("<td class='cal-empty'>&nbsp;</td>");
                }
                else
                {
                    sb.Append("<td class='cal-day'>" + date.Day + "</td>");
                    date = date.AddDays(1);
                }
            }
            sb.Append("</tr></table>");
            return helper.Raw(sb.ToString());
        }
    }
}

Asp.net: File Download Handler

Recently I had the need to make a file download page where statistics could be collected and saved on each individual download. After a little research I found a nice way to get this task done easily.

Because it is only collecting stats about the download and then sending the file to the browser, I decided to use an Asp.net Generic Handler.


Download.ashx.cs:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Services;
using System.IO;
 
namespace WriteFileTest
{
    [WebService(Namespace = "http://tempuri.org/")]
    [WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
    public class Download : IHttpHandler
    {
 
        private string FilesPath
        {
            get
            {
                return @"C:\Users\John Boker\Documents\Visual Studio 2008\Projects\WriteFileTest\Files\";
            }
        }
 
        public void ProcessRequest(HttpContext context)
        {
            string filename = context.Request.QueryString["file"];
            if (!string.IsNullOrEmpty(filename) && File.Exists(FilesPath + filename))
            {
                context.Response.ContentType = "application/octet-stream";
                context.Response.AddHeader("Content-Disposition", string.Format("attachment; filename=\"{0}\"", filename));
                context.Response.WriteFile(FilesPath + filename);
            }
            else
            {
                context.Response.ContentType = "text/plain";
                context.Response.Write("Invalid filename");
            }
        }
 
        public bool IsReusable
        {
            get
            {
                return false;
            }
        }
    }
}

One advantage to this method is the files do not have to be in the website directories and public, extra authentication can be done and the download can be disallowed if necessary.


To test this i created a small Default.aspx page containing:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="Default.aspx.cs" Inherits="WriteFileTest._Default" %>
 
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
    <title></title>
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <a href="Download.ashx?file=FileZilla_3.3.0.1_win32-setup.exe&d=<%= DateTime.Now.Ticks %>">FileZilla_3.3.0.1_win32-setup.exe</a>
        <br />
        <a href="Download.ashx?file=gimp-2.6.7-i686-setup.exe&d=<%= DateTime.Now.Ticks %>">gimp-2.6.7-i686-setup.exe</a>
        <br />
        <a href="Download.ashx?file=jdk-6u17-windows-x64.exe&d=<%= DateTime.Now.Ticks %>">jdk-6u17-windows-x64.exe</a>
        <br />
        <a href="Download.ashx?file=WampServer2.0i.exe&d=<%= DateTime.Now.Ticks %>">WampServer2.0i.exe</a>
    </div>
    </form>
</body>
</html>

As you can see i added another argument to the QueryString; this is to keep the browser from caching files with the same link and filename.

WriteFile Default Page Image

The results after clicking the filezilla link:

WriteFile Save Dialog

This was a very simple method to take care of multiple issues including:

  1. Download Tracking
  2. Alternate File Locations
  3. Browser Caching Issues
  4. Extra Authentication

Asp.net Nested Repeater with Linq2sql

Using nested repeaters with Linq2Sql is very easy as it turns out.
Here is a short example of how it can be done.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
<asp:Repeater runat="server" ID="rptCategories">
    <HeaderTemplate>
        <dl>
    </HeaderTemplate>
    <ItemTemplate>
        <dt>
            <strong><%# Eval("CategoryName") %></strong>
        </dt>
        <asp:Repeater runat="server" DataSource='<%# Eval("Products") %>'>
            <ItemTemplate>
                <dd>
                    <%# Eval("ProductName") %>
                </dd>
            </ItemTemplate>
        </asp:Repeater>
    </ItemTemplate>
    <FooterTemplate>
        </dl>
    </FooterTemplate>
</asp:Repeater>

Then in the codebehind somewhere we have to get our data.
For this example I used the Northwind Database.

1
2
3
4
5
6
7
8
9
NorthwindDataContext dc = new NorthwindDataContext();
var data = (from c in dc.Categories
            select new 
            { 
                CategoryName = c.CategoryName,
                Products = c.Products
            });
rptCategories.DataSource = data;
rptCategories.DataBind();


Results Here are the results, as you can see the categories are listed out with the products listed under them.

This concludes the post on nested repeaters.


Devlink

When: 
Thursday, August 13, 2009 (All day) - Saturday, August 15, 2009 (All day)

http://www.devlink.net/

When:
August 13 - 15, 2009

Registration Opens:
April 1, 2009

Registration Closes:
July 30, 2009 (CLOSED)

Cost:
Standard Ticket - $100

Where:
Lipscomb University
One University Park Drive
Nashville, TN 37204