Archives

Archives / 2003 / September
  • Issues with a lambda expression

    In javascript you can use a function to as an argument to the string.replace function when matching against a regex pattern - this is often referred to as a lambda expression.  For example, in the following piece of code, the function is invoked for each match.  The result is that the letters in the word "foo" are alerted in sequence:

  • Windows Authentication with Role based authorization

    I've done a fair bit with ASP.NET security using the FormsAuthentication provider but not much at all with Windows authentication.  I'm currently building an app. “out-of-hours” that needed to use integrated Windows authentication and also use Role based authorization based on the users Windows Group membership.  Here is a little piece of code that I put together to hook the Windows groups into the roles of the IPrincipal in the application:

  • Application.DoStuff

    I nice little post by Eric Gunnerson that talked how to add an odd-shaped splash screen to an application.  The most interesting thing that came out of this post for me was that he mentioned having to call Application.DoEvents to allow Windows to process the necessary messages to get the splash form to render properly.  Being a web-guy Application.DoEvents is something that I've never really come to terms with.  If you were to go under the hood of some of my winforms apps you would undoubtedly uncover a shot-gun approach to calling this method - i.e.:  sprayed at random.

  • Regex Reminders [1] - Replacement Operations

    A common application for regular expressions is to find and replace strings within a body of text. These operations range from something as simple as finding some text and removing it to locating and re-writing Hmtl tags. Let's take a quick look at the signatures of the .NET Regular Expression Replace overloads.

  • Regex Reminders #0 - Commenting Regular Expressions

    Free spacing and comment mode
    .NET Regular Expressions allow you to embed comments and whitespace within pattern strings making them clearer to 
    read (because of the whitespace), and easier to maintain (due to the modularity). To use this feature you must turn on the RegexOptions.IgnorePatternWhitespace flag. This can be achieved
    either by using the RegexOptions enumerated datatype or, via the (?x) mode modifier. Therefore the following
    two examples are functionally identical: Regex re = new Regex( @" # This pattern matches Foo (?i) # turn on insensitivity # The Foo bit \b(Foo)\b " , RegexOptions.IgnorePatternWhitespace ) ; Regex re = new Regex( @"(?x) # This pattern matches Foo (?i) # turn on insensitivity # The Foo bit \b(Foo)\b " ) ; Using IgnorePatternWhitespace option, comments can be embedded in one of two ways. Firstly, a raw '#'
    character can be used to mark the beginning of a comment and the comment runs up to the first NEWLINE
    (\n) character that is encountered. This can be easily achieved in C# with verbatim strings @"..."
    or in VB by appending newline characters within the string using Chr(10), vbCrLf or Environment.NewLine.
    Comments can also be declared using the (?#...) syntax. The following 3 snippets demonstrate examples of each of these methods... C# Verbatim Strings. using System; using System.Collections; using System.Text.RegularExpressions ; namespace Regex Snippets.Tests { public class CommentedCSharp { public static void Main() { Regex re = new Regex( @" # This pattern matches Foo (?i) # turn on insensitivity # The Foo bit \b(Foo)\b " , RegexOptions.IgnorePatternWhitespace ) ; for ( Match m = re.Match( "foo bar Foo" ) ; m.Success ; m = m.NextMatch() ) Console.WriteLine( m.Value + Environment.NewLine ) ; Console.ReadLine(); } } } VB.NET using (?#...) syntax. Option Strict On Imports System.Text.RegularExpressions Namespace Regex Snippets.Tests Module CommentedVBOne Public Sub Main() ' Demonstrates a VB Whitespace pattern using the '" (?#...) " & _ ' syntax Dim re As New Regex( _ " (?# This pattern matches Foo ) " & _ " (?i) (?# turn on insensitivity ) " & _ " (?# The Foo bit ) " & _ " \b(Foo)\b " _ , RegexOptions.IgnorePatternWhitespace) Dim m As Match = re.Match("foo bar foo") Dim s As String = "" While m.Success s &= (m.Value & Environment.NewLine) m = m.NextMatch() End While MessageBox.Show(s) End Sub End Module End Namespace VB.NET using appended newlines. Option Strict On Imports System.Text.RegularExpressions Namespace Regex Snippets.Tests Module CommentedVBTwo Public Sub Main() ' Demonstrates a VB Whitespace pattern using the '" (?#...) " & _ ' syntax Dim re As New Regex( _ " # This pattern matches Foo " & vbCrLf & _ " (?i) # turn on insensitivity " & vbCrLf & _ " # The Foo bit " & vbCrLf & _ " \b(Foo)\b " _ , RegexOptions.IgnorePatternWhitespace) Dim m As Match = re.Match("foo bar foo") Dim s As String = "" While m.Success s &= (m.Value & Environment.NewLine) m = m.NextMatch() End While MessageBox.Show(s) End Sub End Module End Namespace

  • Regex Reminders - A brief explanation

    Over the next couple weeks I'm going to post a series of regular expression examinations; each one will be a code intensive focus on a certain operations such as "Replace" or "Working with Matches and Groups".  The goal of the Regex Reminders is to end up with a lot of code for working with regex's that people can just use to "grab and go".  The series will also spend time looking at common regex techniques such as alternation and grouping techniques.

  • Redefining Boundaries - \b and \B

    \b and \B are useful metacharacters; they provide a simple syntax to easily find items that exist around word boundaries (or, in the case of \B, non-word boundaries).  For example, to find the word "per" you can wrap the actual text inside \b's to ensure that the phrase is not inadvertantly matched when found inside of "person" or "Supercalif", i.e.:

  • MarkItUp.WebControls.Timer

    I've finally finished my first server control that is targetted as a public release.  The control is a Timer control that generates optional client-side events and performs a server postback after a specified duration.

  • \G - match at the end of the previous match.

    Over the next few days I'd like to spend a bit of time looking at using \G in the .NET "flavour" of regular expressions.  I'd love to hear from anyone that has *had* to use \G in a real-world application (.NET only).

  • KPI ServerControl Source

    Option Strict On
    
    
    Imports System
    Imports System.ComponentModel
    Imports System.Configuration
    Imports System.Data
    Imports System.Drawing
    Imports System.Web.UI
    Imports System.Web.UI.WebControls
    
    
    
    '*********************************************************************
    '
    ' KPIs Class
    '
    ' WebControl that displays a listing of KPIs for a given Category/Month. 
    '
    '*********************************************************************
    
    < _
     Description("WebControl that displays a listing of KPIs for a given Category/Month."), _
     DefaultProperty("DataSource"), _
     Designer(GetType(KPIsDesigner)), _
     ToolboxData("<{0}:KPIs runat=server></{0}:KPIs>") _
    > _
    Public Class KPIs
        Inherits Web.UI.WebControls.Table
        Implements INamingContainer
    
        Private mstrCategoryName As String = String.Empty
        Private mstrNavigateUrl As String = String.Empty
        Private mstrBaseImagePath As String = String.Empty
        Private mdtmSelectedMonth As DateTime = DateTime.MinValue
        Private mDatasource As DataTable
    
        '*********************************************************************
        '
        ' BaseImagePath Property
        '
        ' The directory to look in to find the images.
        '
        '*********************************************************************
        < _
            Browsable(True), _
            Description("The directory to look in to find the images."), _
            Category("Data") _
        > _
        Public Property BaseImagePath() As String
            Get
                Return Me.mstrBaseImagePath
            End Get
            Set(ByVal Value As String)
                Me.mstrBaseImagePath = Value
            End Set
        End Property
    
    
        '*********************************************************************
        '
        ' CategoryName Property
        '
        ' The CategoryName to filterBy.
        '
        '*********************************************************************
        < _
            Browsable(True), _
            Description("The name of the current category being displayed."), _
            Category("Data") _
        > _
        Public Property CategoryName() As String
            Get
                Return Me.mstrCategoryName
            End Get
            Set(ByVal Value As String)
                Me.mstrCategoryName = Value
            End Set
        End Property
    
    
        < _
            Browsable(True), _
            Description("The foreground color for alternating items in the table."), _
            Category("Appearance") _
        > _
        Public Property AlternatingForeColor() As Color
            Get
                If ViewState("AlternatingForeColor") Is Nothing Then
                    Return Me.ForeColor
                Else
                    Return CType(ViewState("AlternatingForeColor"), Color)
                End If
            End Get
            Set(ByVal Value As Color)
                ViewState("AlternatingForeColor") = Value
            End Set
        End Property
    
    
        < _
            Browsable(True), _
            Description("The background color for alternating items in the table."), _
            Category("Appearance") _
        > _
        Public Property AlternatingBackColor() As Color
            Get
                If ViewState("AlternatingBackColor") Is Nothing Then
                    Return Me.ForeColor
                Else
                    Return CType(ViewState("AlternatingBackColor"), Color)
                End If
            End Get
            Set(ByVal Value As Color)
                ViewState("AlternatingBackColor") = Value
            End Set
        End Property
    
    
        < _
            Browsable(True), _
            Description("The DataTable to use as a datasource."), _
            Category("Data") _
        > _
        Public Property DataSource() As DataTable
            Get
                Return Me.mDatasource
            End Get
            Set(ByVal Value As DataTable)
                Me.mDatasource = Value
            End Set
        End Property
    
    
    
    
        '*********************************************************************
        '
        ' NavigateUrl Property
        '
        ' The Url to navigate to to display the details for a given KPI
        '
        '*********************************************************************
        < _
            Browsable(True), _
            Description("The Url to navigate to to display the details for a given KPI.  Uses a {0} placeholder to insert the Id of the KPI."), _
            Category("Data") _
        > _
        Public Property NavigateUrl() As String
            Get
                Return Me.mstrNavigateUrl
            End Get
            Set(ByVal Value As String)
                Me.mstrNavigateUrl = Value
            End Set
        End Property
    
    
        '*********************************************************************
        '
        ' Controls Property
        '
        ' Make sure that when you access a child control, the
        ' CreateChildControls method has been called.
        '
        '*********************************************************************
        Public Overrides ReadOnly Property Controls() As ControlCollection
            Get
                EnsureChildControls()
                Return MyBase.Controls
            End Get
        End Property
    
    
        '*********************************************************************
        '
        ' SelectedMonth Property
        '
        ' The SelectedMonth to filterBy.
        '
        '*********************************************************************
        < _
            Browsable(True), _
            Description("The resultset is filtered by the Month of the DateTime that is passed in."), _
            Category("Data") _
        > _
        Public Property SelectedMonth() As DateTime
            Get
                Return Me.mdtmSelectedMonth
            End Get
            Set(ByVal Value As DateTime)
                Me.mdtmSelectedMonth = Value
            End Set
        End Property
    
    
    
        Protected Overrides Sub CreateChildControls()
            Controls.Clear()
    
            If mDatasource Is Nothing Then
                mDatasource = GetData()
            End If
    
            If Not mDatasource Is Nothing Then
                Me.Rows.Add(BuildHeaderRow())
    
                For Each row As DataRow In mDatasource.Rows
                    Dim KPIId As Integer = Convert.ToInt32(row.Item("kpiId"))
                    Dim KPIDescription As String = row.Item("kpiDescription").ToString
    
                    Dim mtdRaw As Double = Convert.ToDouble(row.Item("mtdRawValue"))
                    Dim ytdRaw As Double = Convert.ToDouble(row.Item("ytdRawValue"))
                    Dim mtdDisplay As Integer = Convert.ToInt32(row.Item("mtdDisplayFlag"))
                    Dim ytdDisplay As Integer = Convert.ToInt32(row.Item("ytdDisplayFlag"))
    
                    Dim alternating As Boolean = (Me.Rows.Count Mod 2 = 0)
                    Me.Rows.Add(BuildRow(KPIId, KPIDescription, mtdRaw, ytdRaw, mtdDisplay, ytdDisplay, alternating))
                Next
            End If
        End Sub
    
    
        '*********************************************************************
        '
        ' Render Method
        '
        '*********************************************************************
        Protected Overrides Sub Render(ByVal tw As HtmlTextWriter)
            MyBase.Render(tw)
        End Sub ' Render
    
    
        Private Function BuildRow(ByVal kpiId As Integer, ByVal kpiDescription As String, ByVal mtdRaw As Double, _
                ByVal ytdRaw As Double, ByVal mtdDisplay As Integer, ByVal ytdDisplay As Integer, ByVal isAlternatingItem As Boolean) As TableRow
            Dim cell As TableCell
            Dim row As New TableRow
    
            If isAlternatingItem Then
                row.ForeColor = Me.AlternatingForeColor
                row.BackColor = Me.AlternatingBackColor
            End If
    
            Dim link As New HyperLink
            link.Text = kpiDescription
            If Not Me.mstrNavigateUrl Is String.Empty Then
                link.NavigateUrl = String.Format(Me.NavigateUrl, kpiId)
            End If
    
            cell = New TableCell
            cell.Controls.Add(link)
            row.Cells.Add(cell)
    
    
            cell = New TableCell
            cell.Controls.Add(GetImage(mtdDisplay, mtdRaw, "MTD"))
            row.Cells.Add(cell)
    
    
            cell = New TableCell
            cell.Controls.Add(GetImage(ytdDisplay, ytdRaw, "YTD"))
            row.Cells.Add(cell)
    
            Return row
        End Function
    
    
        Private Function BuildHeaderRow() As TableRow
            Dim cell As TableCell
            Dim row As New TableRow
    
            cell = New TableHeaderCell
            cell.Text = "&nbsp;"
            row.Cells.Add(cell)
    
            cell = New TableHeaderCell
            cell.Text = "MTD"
            row.Cells.Add(cell)
    
            cell = New TableHeaderCell
            cell.Text = "YTD"
            row.Cells.Add(cell)
    
            Return row
        End Function
    
    
        Private Function GetData() As DataTable
            Return Nothing
        End Function
    
    
        '*********************************************************************
        '
        ' GetImage Method
        '
        ' Returns the appropriate image for a particular rating.
        '
        '*********************************************************************
        Friend Function GetImage(ByVal ratingNumber As Integer, ByVal rawVal As Double, ByVal desc As String) As Web.UI.WebControls.Image
            Dim img As New Web.UI.WebControls.Image
    
            If Me.mstrBaseImagePath <> String.Empty Then
                If ratingNumber = 1 Then
                    img.ImageUrl = Page.ResolveUrl(String.Format("{0}/Green.gif", Me.mstrBaseImagePath))
                ElseIf ratingNumber = 2 Then
                    img.ImageUrl = Page.ResolveUrl(String.Format("{0}/Yellow.gif", Me.mstrBaseImagePath))
                ElseIf ratingNumber = 3 Then
                    img.ImageUrl = Page.ResolveUrl(String.Format("{0}/Red.gif", Me.mstrBaseImagePath))
                Else
                    img.ImageUrl = Page.ResolveUrl(String.Format("{0}/Spacer.gif", Me.mstrBaseImagePath))
                End If
            End If
    
            img.AlternateText = String.Format("{1} : {0}", rawVal, desc)
            Return img
        End Function 'GetImage 
    
    
    End Class
    

  • using C# and unlocking some secrets

    Recently, I've made a decision that all of the code that I write "out of hours" (which is most of the code that I write these days) will be written in C#; and what I'm finding is that switching languages is a very tricky affair.  There's so many little pieces of the language that you have to get used to.  Take the using statement - as opposed to the using directive - for example.  At first sight it seems interesting, according to the docco. it allows me to use an IDisposable type and the call to dispose will get handled under the covers; GREAT!  Or is it?  First of all, methinks that, by the very nature of IDisposable, anything that implemented that interface would be worth putting in a try{}catch{} because you are relying on an "external" resource being available!  So it appears that a statement such as:

  • Conditional matching

    Today, while proving what a prat I am, I added some conditional testing to a pattern which I had written.  Conditional matching allows you to perform a test based on if...then[...else] logic.  The syntax is (?if then | else ) - with the 'else' part being optional.

  • Good VBScript reference

    I never really did much VB6 programming - built a couple of insignificant apps but that was about it - and today a friend asked me to package some VBScript routines into an ActiveX Library project.  It all went pretty well except for the fact that I couldn't work out which .dll to reference to get the VBScript ESCAPE and UNESCAPE functions in my VB6 code.  While looking around Msdn for version numbers etc. I came across this neat little VBScript reference:

  • Using backreferences in a Match

    You can reference backreferences within a regular expression to keep the length and complexity of patterns to a minimum.  Backreferences can be referenced with the \1..\N or \k'name' notation.  To highlight where this is useful consider a simple-minded pattern for matching Dates.  Dates can (potentially) be delimited by either a space, a dot, a hyphen or a slash - that is, any of the following might be allowed:

  • Find words NOT IN text

    I'm currently writing a series of articles (that will hopefully get published {grin}) titled "Regex Reminders" that will provide dozens of code snippets that demonstrate how to perform common - and some not-so-common - operations using regex.

  • Date Regex - [ Note To Self ]

    While scouring through the pile of comments that have been left on RegexLib.com I noticed a pattern which purports to validate Dates in dmy format.  I couldn't help but notice that all of the comments which have been left have been highly favourable of this expression.