|
|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Announcements
Chapters
Services
Feature Zones
|
IntroductionThis little ASP.NET utility lets you run SQL queries against databases accessible to the web server. Initially, this started as a script to run queries against an Access database, without having to download it. Every now and then, you might need to do maintenance chores, or retrieve some raw data to check something. This utility facilitates that by allowing queries to be saved as a favourite, as well as keeping the history of previous queries. Features
DetailsThis utility is not meant to replace database admin tools like phpMyAdmin. Rather, it was built to be simple and light-weight, allowing it to be integrated into other web applications. It's meant to provide quick and easy access to your data, and allow you to test queries, as well as modify your databases. You can configure multiple connections (not necessarily of the same database type), which gives you a common interface regardless of which database you need to query. The history and favourites-list remembers which database a query was executed against, and will select the appropriate radio button when you click on a query in those lists. It also generates schema details for OLEDB, SQL Server, and MySQL connections. In the schema popup, you can click on the column names or table name headings to insert the name into the query textbox (replacing the current selection). The schema popup does not reload when you click the Schema link if that schema is already open in the popup. The popup will merely get focused to the forefront.
The Execute button, in addition to the obvious, adds the query to the history, and if the "Add to favourites" checkbox is checked, adds the query to the favourites. The shortcut key for this button is Alt-E. Multiple queries can be submitted simultaneously - separated by The INSERTs button will generate SET IDENTITY_INSERT table_name ON
--- INSERT QUERIES ---
SET IDENTITY_INSERT table_name OFF
The DataSet XML button will let you download the The CSV button will let you download a single CSV, with each result set underneath the other. The HTML encode results checkbox escapes any HTML characters in your result set. The Wrap query textbox checkbox changes the text-wrapping on the query textbox (i.e., horizontal scrollbar on/off for long lines). This was a major headache to implement for Firefox (v1.5) - which required coming up with a complete workaround since setting the Initially, the SQL page shows the Favourites "tab" selected. But once a query is executed, the History "tab" becomes selected by default. They're not really tabs, visually, but the bold text shows which list is selected. The History list has a "Complete History" link underneath which will be shown queries executed for previous sessions in a popup. This is useful to keep a record of queries run by yourself or anybody else. If you suddenly have 1000 rows missing from your database, you can investigate the query history for the potential cause. The popup has delete links to clear a particular history session, or all of them. ConfigurationThere is a custom configuration section that lets you customise this utility. Here is an example: <DbUtilConfig>
<Connections>
<Connection name="Access" type="oledb" cs="" csAppKey="AccessDb" />
<Connection name="SQL Server" type="mssql" cs=""
csConfKey="SqlServerConnStringIAM" />
<Connection name="MySQL" type="odbc"
cs="DRIVER={MySQL ODBC 3.51 Driver}; SERVER=localhost;
USER=test; PASSWORD=test; DATABASE=test" />
</Connections>
<FavouritesFile>data/SqlFavourites.xml</FavouritesFile>
<HistoryFolder>data/SqlHistory</HistoryFolder>
<QuerySeparator>;;;</QuerySeparator>
<ResultGridColors Border="#777" HeaderBg="#ffc"
Header="#000" ItemBg="#fff" AltItemBg="#eee" />
</DbUtilConfig>
Connection
FavouritesFilePath to the XML file where favourite queries are stored.
HistoryFolderPath to the directory where history XML files are stored. QuerySeparatorThis is the string used to delimit multiple queries. When executing, if there are any occurrences of this string, the query will be split with this string. If there are no occurrences of this string, the code will attempt to split the query with ResultGridColorsLets you change the colour scheme of the result
CodeSnippet 1 (JavaScript)The JavaScript code to replace the selection in the if (document.all) // IE
window.opener.document.selection.createRange().text = o.innerHTML
else // FF
{
var selStart = queryTextArea.selectionStart
queryTextArea.value =
queryTextArea.value.substring(0, selStart) + o.innerHTML +
queryTextArea.value.substring(queryTextArea.selectionEnd)
queryTextArea.selectionStart = selStart + o.innerHTML.length
queryTextArea.selectionEnd = queryTextArea.selectionStart
}
As you can see, Firefox gives you access to the selection positions, not the selection itself. So you have to use string manipulation to create the new value. Then, I set the selection start/end to select the string that was just inserted. Snippet 2 (C#)Where possible, the IDbConnection conn = conf.GetConnection(RblWhichDb.SelectedValue);
cmd = conn.CreateCommand();
cmd.CommandText = query;
conn.Open();
try
{
IDataReader reader = cmd.ExecuteReader();
bool hasRows = false;
if (conn is OleDbConnection)
hasRows = ((OleDbDataReader)reader).HasRows;
else if (conn is SqlConnection)
hasRows = ((SqlDataReader)reader).HasRows;
else if (conn is OdbcConnection)
hasRows = ((OdbcDataReader)reader).HasRows;
Snippet 3 (JavaScript)As I mentioned earlier, a workaround was required for Firefox to toggle the wrapping of the query This HTML gives you a <textarea wrap="false" rows="7" cols="80" id="TxtQuery">
But this JavaScript has no effect on the wrapping: document.getElementById("TxtQuery").wrap = true
Nor does this: document.getElementById("TxtQuery").setAttribute("wrap", "true")
I found this really peculiar, but I didn't give up there. I came up with a workaround to re-create the HTML, and assign it as the function toggleWrap(checked)
{
if (window.navigator.userAgent.indexOf("Gecko") != -1)
{
// workaround for Firefox because setting
// 'wrap' attribute just doesn't work :(
var val = document.getElementById("TxtQuery").value
var html = document.getElementById("TxtQuery").parentNode.innerHTML
html = html.replace('wrap="off"', '')
if (!checked)
html = html.substring(0, html.indexOf('
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||