Tuesday, August 31, 2010

Using MySql with WebMatrix

There's a small problem that affects any attempt to connect to a database through a connection string using WebMatrix : there's an error in the documentation that leads you to try to use Database.OpenConnectionString when you should be using the currently undocumented Database.Open (as shown below).
If you install the MySql.Data.MySqlClient dll to the GAC then you won't need the dbproviderfactories entry shown below. If you don't install it to the GAC, create a bin directory in your application and drop the dll in there.

See also: Useful information on WebMatrix from Rick Strahl


1. web.config:



<?xml version="1.0"?>


<configuration>
<connectionStrings>
<add name="myconnection" connectionString="server=localhost;user id=dimanuser; password=; database=diman; pooling=false; charset=utf8;" providerName="MySql.Data.MySqlClient"/>
</connectionStrings>
    <system.web>
        <compilation debug="false" targetFramework="4.0" />
    </system.web>
<system.data>
<DbProviderFactories>
<add name="MySQL Data Provider" invariant="MySql.Data.MySqlClient" description=".Net Framework Data Provider for MySQL" type="MySql.Data.MySqlClient.MySqlClientFactory, MySql.Data, Version=6.2.2.0, Culture=neutral, PublicKeyToken=c5687fc88969c44d"/>
</DbProviderFactories>
</system.data>
</configuration>


2. Code:


<!DOCTYPE html>
<html>
    <head>
        <title></title>
    </head>
    <body>
@{   
    var db = Database.Open("myconnection");
    string sql = "select * from standard_text where rank <  @0 order by rank"; 
} 
    <ul> 
@foreach(var row in db.Query(sql,30)){ 
        <li> @row.rank - @row.title</li> 
} 
    </ul> 
    </body>
</html> 
  

Sunday, August 29, 2010

Export GridView to Excel

After researching this for some time I found an excellent article that provides a convenient solution from Matt Berseth: http://mattberseth.com/blog/2007/04/export_gridview_to_excel_1.html

Like most solutions to this problem, this article describes how to make ASP.NET re-render the GridView in a cleaned-up HTML format and then serve that rendering as a download. The downside to this is that it doesn't work with OpenOffice (this would require the Grid to be re-rendered as CSV rather than HTML).

The nice thing about this solution is that code can be easily customized. My GridViews contain images (as HTML images, not ImageButtons), so I added code to either eliminate them or render them in text.

Friday, August 27, 2010

ASP.NET and the annoying DropDownList problem...

'ddlxxxxx' has a SelectedValue which is invalid because it does not exist in the list of items.

Many people complain about this untrappable error, but if you search hard enough, you will eventually find the fix: http://forums.devx.com/showthread.php?t=155180


So, it turns out that it's very easy to create your own DropDownList control inheriting all the behaviour of the original except this error.  Now, if the value in your database doesn't match one of the values in the pull-down it will display the default value (1st in the list) - rather more friendly behaviour.  There's much more about this at http://aspddlsucks.spaces.live.com/ - I think it's annoying that a failure to enforce referential integrity in your database is punished in such a brutal way, so that you can't even catch the violation in a try/catch in your application code.  The official Microsoft response is certainly patronising: "just make sure your data is always correct".

1. Using Visual Basic 2008 Express (or similar, I'm sure C#-ers can work it out), compile the following code as a Class (be sure to add a reference to 'System.Web')

Imports Microsoft.VisualBasic
Imports System.Web

Namespace FixedDDL
    Public Class DropDownList
        Inherits System.Web.UI.WebControls.DropDownList

        Protected Overrides Sub PerformDataBinding(ByVal dataSource As System.Collections.IEnumerable)
            Try
                MyBase.PerformDataBinding(dataSource)
            Catch OutOfRangeEx As System.ArgumentOutOfRangeException
                ' Ignore exception
            End Try
        End Sub

    End Class
End Namespace

2. Grab the FixedDDL.dll and put it in the Bin directory of your web application

3. Add the following lines into your web.config:
<system.web>
<pages>
<tagMapping>
<add mappedTagType="FixedDDL.FixedDDL.DropDownList" tagType="System.Web.UI.WebControls.DropDownList">
</add>
</tagMapping>
</pages>

...
</system.web>





4. Job done

ASP.NET, databases, localization and the problem with Turkish...

This is one of the craziest problems ever:

1. You have a database field called 'CustomerId'
2. so you refer to this field as myrow("CustomerId")
3. this works for all users worldwide but fails for Turkish users
4. change the code to refer to myrow("Customerid") and it works

Reason:  Turkish has an i character without a dot.

So, in Turkish, 'i' and 'I' are not related in any way: they are not upper and lower case versions of the same character, but completely different characters.  There's a capital 'i' with a dot above it that is the upper case version of 'i' (with a dot).  Of course, 'I' without the dot is the upper case version of i without the dot. Clear?

When you switch on localization support in ASP.NET, this doesn't just affect the things that the user sees in their browser depending on the language settings, it also affects your programming!


Rick Strahl found this same issue back in 2005: http://www.west-wind.com/weblog/posts/2204.aspx