It's Not A Bug, It's A Feature Just another Developer weblog

26Oct/110

iPhone App Now Available


I just had my first iPhone app approved by apple

Performance Caluator iPhone App

App Micro Site

The App was built using the Phonegap framework, I will eventually have the app available on Android market place as well

25May/110

New Mobile Theme

Been fooling around with mobile layouts, if you have a smart phone, check out our new mobile theme.

Tagged as: No Comments
30Dec/100

Sorry for the Lack of response

I just noticed I had my notifications for comments set to an old no longer used email address, so those of you who posted comments a few weeks ago and got no response. I apologize. I have updated to my new email address and now will be notified and I will try and check back more often. Just been real busy the last few months and haven't spent much time on my own website...

29Jun/100

Backup a VisualSVN Repository with VBScript

Last week I had to make a backup of a VisualSVN Repository and trying backup each site individually would have taken me forever. so after a little digging on Google found this great little VB script file to backup all the repository's on a Windows server.

for some reason I cant find the original forum post were i found the script to give the original author credit for his work. but here is the script for anyone who would like to use it.

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
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
'Save File as : BackupSVN.vbs
Option Explicit

'loop through folders and use svnadmin to dump all repos to a backuplocation
'trying to run this type of command for each repo
'C:\Program Files\VisualSVN Server\bin>svnadmin dump C:\svnrepos\MyProject > \\nas\folder\MyProject.bak

Const ForReading = 1
Const ForWriting = 2
Const ForAppending = 8

Dim scriptPath, argCount, namedArgs
scriptPath = replace(wscript.scriptfullname, wscript.scriptname, "")
argCount= WScript.Arguments.Count
Set namedArgs = WScript.Arguments.Named

Dim fso, svnExePath, repoFolderPath, backupFolderPath

Set fso = CreateObject("Scripting.FileSystemObject")

'************* uncomment or edit for the correct path to svnadmin****************
svnExePath = "D:\SVN_Server\bin\svnadmin.exe"


'************* edit this line to match your backup destination****************
backupFolderPath = "D:\SvnBackup"

'only needs editing if you don't put it into the repos folder
repoFolderPath = scriptPath


If namedArgs.Exists("help") Or namedArgs.Exists("?") Then
 Wscript.Echo "Usage: "
 Wscript.Echo "/svn:<svn> is optional to enter the svnadmin executable full path & name."
 Wscript.Echo " - default is " & svnExePath
 Wscript.Echo
 Wscript.Echo "/repos:<repos> is optional to select the svn repositories folder."
 Wscript.Echo " - default is " & repoFolderPath
 Wscript.Echo
 Wscript.Echo "/backup:<backup> is optional to select the svn backupdestination folder."
 Wscript.Echo " - default is " & backupFolder
 Wscript.Quit
End If

If namedArgs.Exists("svn") Then
  svnExePath = Trim(namedArgs.Item("svn"))
End If

If namedArgs.Exists("repos") Then
 repoFolderPath= Trim(namedArgs.Item("path"))
End If

If namedArgs.Exists("backup") Then
 backupFolderPath= Trim(namedArgs.Item("backup"))
End If


DumpSvnRepos svnExePath, repoFolderPath, backupFolderPath


'create and execute a batch file to dump all of the repos
'for some reason running the dump command directly will not work
Function DumpSvnRepos(svnExePath, rootFolderPath, backupFolderPath)
    Dim rootFolder, subFolders, folder, file
    Dim logFileName, text

    Set rootFolder = fso.GetFolder(rootFolderPath)
    Set subFolders = rootFolder.SubFolders

    logFileName = Replace(wscript.ScriptFullName, ".vbs", ".bat")

    Set file = fso.OpenTextFile (logFileName, ForAppending, True)

    For Each folder in subFolders
      Wscript.Echo folder.Name
      text = Chr(34) & svnExePath & Chr(34) & " dump " & Chr(34) & repoFolderPath & "\" & folder.Name & Chr(34) & " > "  & Chr(34) & backupFolderPath & "\" & folder.Name & ".bak" & Chr(34)
      file.WriteLine(text)

    Next

  file.Close

  Wscript.Echo "Batch file created: " & logFileName
  runCommand logFileName

End Function



Function runCommand(commandLine)

        Dim shell, errorCode
        Set shell = CreateObject("WScript.shell")

        shell.Run commandLine, ,True 'command, WindowType, WaitOnReturn

        errorCode = err.Number
        If errorCode > 0 Then
                wscript.echo "runCommand Error " & err.Number & ": " & VbCrLf & commandLine & VbCrLf & err.Description
                logText "runCommand Error " & err.Number & ": " & vbTab & commandLine & vbTab & err.Description
                Err.Clear
        Else
                logText "runCommand Success : " & vbTab & commandLine
        End If

        runCommand = errorCode


End Function

Sub LogText(text)
    Dim file, logFile

    logFile = Replace(wscript.ScriptFullName, ".vbs", ".txt")

    Set file = fso.OpenTextFile (logFile, ForAppending , True)

    ' Writes Text every time you run this VBScript
    file.WriteLine(text)
    file.Close

End Sub
22Jun/100

Installing WordPress on MS SQL Server

Believe it or not, there are actually people out there who would like to run WordPress on SQL Server simply because MS SQL has many features MySQL can stand up to. I myself have WordPress running on my local machine using a MS SQL server 2005 database and have seen no ill effects from running it. Today I found a really nice walk through which I did not have the pleasure of reading before figuring it out all by myself.

http://wordpress.visitmix.com/development/installing-wordpress-on-sql-server

Tagged as: , , No Comments
21Jun/100

IOS4 for the IPhone Now Available For Download

The IOS4 upgrade is now officially available for download with over 100 new features, the free iOS 4 Software Update lets you do some amazing things.

  • App Multitasking
  • App Folders
  • Even better Mail
  • iBooks
  • Create playlists
  • 5x digital zoom
  • Tap to focus video
  • Faces and Places in Photos
  • Home screen wallpaper
  • Gift apps
  • Spell checking
  • Wireless keyboard support

iOS 4 works with iPhone 4, iPhone 3GS, and iPhone 3G. Not all features are compatible with all devices. For example, multitasking is available only with iPhone 4 and iPhone 3GS.

for full details on the IOS4 upgrade visit http://www.apple.com/iphone/softwareupdate/

Tagged as: , No Comments
21Jun/102

Classic ASP SmarterTrack Webservice Interface

smartertools-logo

In my first SmarterTrack article I discussed the building a Login Provider web service, In this article I am going to show you a simple implementation of of using Classic ASP to communicate with the SmarterTrack web services to enhance your current app. by proving a few simple methods for creating a ticket from a classic ASP page.

A perfect example would be a classic ASP shopping cart that displays past orders to a customer and you want to provide a quick way for your customers to create a customer service ticket without entering the customer service portal.

The example here was used with version 5.0.3813 of SmarterTrack installed locally on my machine. And you will also need the Microsoft 'SOAP Toolkit 3.0', it can be downloaded from Microsoft @ http://www.microsoft.com/downloads/details.aspx?familyid=c943c0dd-ceec-4088-9753-86f052ec8450&displaylang=en.

This is a simple method and does not provide any error handling or business logic, Ill leave that up to you to implement. this is only meant to show you the proper way to call the SmarterTrack web service's from classic ASP.

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
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
<%

Class SmarterTrack_svcTicket
'#####################################################################################################

'#################################################################
'VERY IMPORTANT: When attempting to get this class to work we were getting the following error: '#################################################################
    'WSDLReader error '80020009'
    'WSDLReader:Loading of the WSDL file failed HRESULT=0x80040154: Class not registered -
    'Client:An unanticipated error occurred during the processing of this request. HRESULT=0x80040154: Class not registered
   
    'The error occurred the following line in "Class_Initialize":
    'oSOAP.mssoapinit WebserviceURL & "svcTickets.asmx?WSDL", "svcTickets"
   
    'To get this SOAP functionality to work, make sure that the following is installed on the machine (this fixed our error above):
    '1) SOAP Toolkit 3.0 (http://www.microsoft.com/downloads/en/details.aspx?FamilyId=C943C0DD-CEEC-4088-9753-86F052EC8450&displaylang=en)
    '2) MSXML 4.0 Service Pack 2 (Microsoft XML Core Services)
    '   - http://www.microsoft.com/downloads/en/details.aspx?familyid=3144b72b-b4f2-46da-b4b6-c5d7485f2b42&displaylang=en
    '   - install msxml.msi

    'Private Declarations
    Private oSOAP
    Private svcTicketsWDSL
    Private svcTicketsNamespace
    Private svcResponse
    'Public Declarations
    Public AgentUserName
    Public AgentPassword
    Public WebserviceURL
    Public WebServiceTimeout
    Public TicketNumber
    Public Result
    Public ResultCode
    Public RequestResult
    'Create & Destroy Methods
    Private Sub Class_Initialize
        WebserviceURL = "http://localhost:9996/services/" 'Default Value (DEV Address)
        AgentUserName = "admin"
        AgentPassword = "admin"
        WebServiceTimeout = 10000 '10 seconds
        Set oSOAP = Server.CreateObject("MSSOAP.SoapClient30")
        oSOAP.ClientProperty("ServerHTTPRequest") = True
        oSOAP.mssoapinit WebserviceURL & "svcTickets.asmx?WSDL", "svcTickets"
        oSoap.ConnectorProperty("Timeout") = WebServiceTimeout
    End Sub

    Private Sub Class_Terminate
        Set oSOAP = Nothing
    End Sub
    'Subroutines
    Public Function CreateTicket(byVal intDeptID,byVal UserEmailAddress, byVal Subject, byVal MessageBody, byVal SendAutoRespond)
        Response.Write "<hr>CreateTicket()<br>"
        Set svcResponse = oSOAP.CreateTicket(AgentUserName, AgentPassword, intDeptID, UserEmailAddress, Subject, MessageBody , false, SendAutoRespond)
        Call ProcessResponse()
        TicketNumber = RequestResult
    End Function
   
    Public Function GetTicketURL()
        'Response.Write "<hr>AddTicketNote('" & TicketNumber & "')<br>" 'For Debugging
        Set svcResponse = oSOAP.GetTicketURL(AgentUserName, AgentPassword, TicketNumber)
        Call ProcessResponse()
        GetTicketURl = RequestResult
    End Function

    Public Function ProcessResponse()
        For Each Node In svcResponse
            'Response.Write Node.tagName & " : " & Node.xml & "<br>"
            Select Case Node.tagName
                Case "RequestResult" 'Ticket Number
                    RequestResult = Node.Text
                Case "Message"
                    Message = Node.Text
                Case "Result"
                    Result = Node.Text
                Case "ResultCode"
                    ResultCode = Node.Text
                Case Else
                    'Response.write "CreateTicket : Unknown Response Node = " & Node.tagName & "<br>"
            End Select
        Next
    End Function
'#####################################################################################################
End Class
'Sample Usuage
Dim Ticket
Set Ticket = New SmarterTrack_svcTicket
Ticket.CreateTicket 1,"customer@summit-pro.com", "Missing Items On Order", "Customer reported they did not receive there widget", True
Response.Write ( Ticket.GetTicketURL() )
Set Ticket = Nothing
%>
15Jun/100

Submit form with Spry.DataUtils.ServerAction

Here is a quick and dirty example of using the Spry.DataUtils.ServerAction in the Adobe Spry 1.6.1 Framework. (Form post back without page refresh). Hopefully Adobe will get off there ass and continue work on this framework as it has great potential. And I really like using it.

Surprisingly there is very little in the documentation about this wonderful function, only after digging through the framework did I discover this great little feature. and it has come in very handy in many previous projects. for more info on this function feel free to dig thought the SpryDatUtils.js file found in the framework.

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
<%
Option Explicit
Dim FormAction : FormAction = Request.ServerVariables("URL")

If Request.ServerVariables("REQUEST_METHOD") = "POST" And Request.Form("Password") > "" Then
    'Here is where you would write your logic for processing the form values posted
    'You could easily put this code in a seprate file/directory. that is just for
    'processing script posts from your ajax forms.
    Response.Write("You posted the form, notice the page did'nt change?")
    Response.End
End If
%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<title>Submit Form With Spry.DataUtils.ServerAction</title>
<script language="JavaScript" type="text/JavaScript">
<!--
function beforeOnSubmit(form){
    //var theForm = document.getElementById(form);
    alert(form);
    //var ret = false; //Spry.Widget.Form.validate(form);
    Spry.DataUtils.ServerAction('Login','SupportResponse','SubmitError',true,'','');
    //}
    //return ret;
}
function SupportResponse(req){
    alert("SUCCESS: " + req.xhRequest.responseText);
    //var response = req.xhRequest.responseText;
}
function SubmitError(req){
    alert("ERROR: The server did not respond, Please resubmit your request.");
}
//-->
</script>
<script src="SpryDataUtils.js" type="text/javascript"></script>
</head>

<body>
<form action="<%= FormAction %>" method="POST" name="Login" id="Login" onSubmit="beforeOnSubmit(this.name); return false;">
<input type="text" name="Password"><input type="submit" name="Submit Form" id="Submit Form" value="Login">
</form>
</body>
</html>

You can find out more about the spry framework @ http://labs.adobe.com/technologies/spry/home.html
Adobe Spry Documentation: http://labs.adobe.com/technologies/spry/docs.html
Adobe Spry Download: http://www.macromedia.com/go/labs_spry_download

14Jun/100

List All Stored Proc Parameters for a Stored Procedure

Here is a simple little script that will list all of a stored procedures parameters. making it easy for you to write your execution code.

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
<table>
    <tr>
        <td>Param Name</td>
        <td>Param Type</td>
        <td>Param Dir</td>
        <td>Param Size</td>
    </tr>
    <%
    Set Conn = Server.CreateObject("ADODB.Connection")
    ' The following line must be changed to reflect your data source info
    Conn.Open "PROVIDER=SQLOLEDB;Data Source=127.0.0.1;UID=MyUsername;PWD=MyPassword;DATABASE=MyDataBase"
    set cmd = Server.CreateObject("ADODB.Command")
    cmd.ActiveConnection = Conn
    'Specify the name of the stored procedure you wish to call
    cmd.CommandText = "MyStoreProcedure"
    cmd.CommandType = 4
    cmd.Execute
    ' Query the server for what the parameters are
    cmd.Parameters.Refresh
    For Each param In cmd.Parameters
   %>
    <tr>
        <TD><%= param.name %></TD><TD> <%= param.type %></TD><TD> <%= param.direction %></TD><TD><%= param.size %></TD>
    </tr>
   <%
    Next
    Conn.Close
   %>
   </TABLE>
12Jun/101

SmarterTrack VB.Net Login Provider Webservice

Here is a sample VB.Net web service for use with the Smarter Tools Smarter Track Customer Service Portal. I Looked around the net for a working VB.Net version of this since we are using this software were I work and wanted to allow our customers to login to the portal with thier existing user name and password so they would not have to remember or register a separate account to interact with our customer service department.

Unfortunately it seems there are more C# programmers than us die hard VB programmers (coming from a background of writing Classic VB script for 15 years, I have no desire on learning to write C#). So after getting this to work I thought I would pass it along to the community to use an abuse.

One import note about this code, for some reason the programmers at Smater Tools decided it was mandatory for the Login Provider web service to use the Namespace 'http://tempuri.org/' so if you change it in the sample code, It wont work. Don't ask me why, it just wont.

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
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
Imports System.Web.Services
Imports System.Web.Services.Protocols
Imports System.ComponentModel
Imports SmarterTrack.Connector
Imports System.Data
Imports System.Data.SqlClient

' To allow this Web Service to be called from script, using ASP.NET AJAX, uncomment the following line.
' <System.Web.Script.Services.ScriptService()> _
<System.Web.Services.WebService(Namespace:="http://tempuri.org/")>
<System.Web.Services.WebServiceBinding(ConformsTo:=WsiProfiles.BasicProfile1_1)> _
<ToolboxItem(False)> _
Public Class LoginProvider
    Inherits System.Web.Services.WebService
    Implements IExternalLoginProvider

    Private Const WebServiceAuth As String = "myPassword"

#Region "Login Provider"
    '###############################################################

    <WebMethod()> _
    Public Function Authenticate(ByVal inputs As SmarterTrack.Connector.ExternalLoginProviderInputs) As SmarterTrack.Connector.ExternalLoginProviderResult Implements SmarterTrack.Connector.IExternalLoginProvider.Authenticate
        Dim iData As New ParsedLoginInputData(inputs)
        Dim result As New ExternalLoginProviderResult()
        Dim SQLConn As New SqlConnection()
        Dim SQLCmd As New SqlCommand()

        ' Verify that all necessary criteria to call this function are met
        If iData.WebServiceAuthorizationCode <> WebServiceAuth Then
            Return New ExternalLoginProviderResult(False, "Permission Denied")
        End If
        If String.IsNullOrEmpty(iData.LoginUsername) OrElse String.IsNullOrEmpty(iData.LoginPassword) Then
            Return New ExternalLoginProviderResult(False, "Required Input Missing")
        End If

        SQLConn = New SqlConnection(System.Configuration.ConfigurationManager.ConnectionStrings("Conn").ToString())
        SQLConn.Open()
        SQLCmd = New SqlCommand("SELECT TOP 1 Email, Name FROM Accounts WHERE Email = @Email and Password = @Password", SQLConn)
        SQLCmd.Parameters.Add("@Email", SqlDbType.VarChar)
        SQLCmd.Parameters("@Email").Value = iData.LoginUsername
        SQLCmd.Parameters.Add("@Password", SqlDbType.VarChar)
        SQLCmd.Parameters("@Password").Value = iData.LoginPassword
        Dim AccountInfo As SqlDataReader = SQLCmd.ExecuteReader()
        If AccountInfo.HasRows Then
            While AccountInfo.Read()
                result.Success = True
                result.Message = "Login Successful"
                result.OutputVariables.Add("Authentication=OK")
                result.OutputVariables.Add("EmailAddress=" & AccountInfo.Item("Email"))
                ' optional
                result.OutputVariables.Add("DisplayName=" & AccountInfo.Item("Name"))
            End While
        Else
            result.Success = False
            result.Message = "Login Failed"
        End If
        AccountInfo.Close()
        SQLCmd.Dispose()
        SQLConn.Dispose()
        Return result
    End Function

    <WebMethod()> _
    Public Function GetSignInCookieInfo(ByVal inputs As SmarterTrack.Connector.ExternalLoginProviderInputs) As SmarterTrack.Connector.ExternalLoginProviderResult Implements SmarterTrack.Connector.IExternalLoginProvider.GetSignInCookieInfo
        Dim result As New ExternalLoginProviderResult()
        Return New ExternalLoginProviderResult(False, "Method Not Implemented")
        Return result
    End Function
#End Region
End Class

I have to say I have been impressed with the Smarter Track Software, we have been using the customer service chat side of the system for about a year now and has had a tremendous impact on our business. Only recently did I discover its full potential. mainly because the software was installed and configured by our previous IT director who never mentioned it had a complete ticketing system along with the chat. and When I had to re-new our license a couple of months ago realized what we had.

So now I am in the process of integrating it with our existing systems to be implemented fully in the next few weeks. Since our current sites are all written in Classic ASP, I did not implement the 'GetSignInCookieInfo' functionality since it it meant to be used with a DOT.NET site and we just don't have the need for it.

If you have any need for a Customer Service portal and don't want to spend tens of thousands of dollars you should really look into this system. Obviously you will need a copy of the Smarter Track software installed to use and test this webservice.

But one of the really great things about Smarter Track is that you can install it on a server without a license key (developer mode). and it will allow you full access to all the features of the system, but only allows you to have have one customer service Representative account. Feel free to download it and check it out.