miniSql

创建
zgc123@gmail.com authored at 11/19/2023 1:40:15 AM
6136600
Tree
0 Parent(s)
Summary: 7 changed files with 970 additions and 0 deletions.
Added +39 -0
Added +37 -0
Added +0 -0
Added +531 -0
Added +171 -0
Added +155 -0
Added +37 -0
Added +39 -0
diff --git a/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/Commands/ViewTableFormCommand.cs b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/Commands/ViewTableFormCommand.cs
new file mode 100644
index 0000000..393a83a
--- /dev/null
+++ b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/Commands/ViewTableFormCommand.cs
@@ -0,0 +1,39 @@
+#region License
+
+// Copyright 2005-2019 Paul Kohler (https://github.com/paulkohler/minisqlquery). All rights reserved.
+// This source code is made available under the terms of the GNU Lesser General Public License v3.0
+// https://github.com/paulkohler/minisqlquery/blob/master/LICENSE
+#endregion
+
+using System.Windows.Forms;
+using MiniSqlQuery.Core;
+using MiniSqlQuery.Core.Commands;
+using WeifenLuo.WinFormsUI.Docking;
+
+namespace MiniSqlQuery.PlugIns.ViewTable.Commands
+{
+    /// <summary>The view table form command.</summary>
+    public class ViewTableFormCommand
+        : CommandBase
+    {
+        /// <summary>Initializes a new instance of the <see cref="ViewTableFormCommand"/> class.</summary>
+        public ViewTableFormCommand()
+            : base("&View table...")
+        {
+            ShortcutKeys = Keys.Control | Keys.T;
+        }
+
+        /// <summary>Execute the command.</summary>
+        public override void Execute()
+        {
+            IQueryEditor queryForm = HostWindow.Instance.ActiveMdiChild as IQueryEditor;
+            if (queryForm != null)
+            {
+                string tableName = queryForm.SelectedText;
+                IViewTable frm = Services.Resolve<IViewTable>();
+                frm.TableName = tableName;
+                HostWindow.DisplayDockedForm(frm as DockContent);
+            }
+        }
+    }
+}
\ No newline at end of file
Added +37 -0
diff --git a/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/Commands/ViewTableFromInspectorCommand.cs b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/Commands/ViewTableFromInspectorCommand.cs
new file mode 100644
index 0000000..80785c8
--- /dev/null
+++ b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/Commands/ViewTableFromInspectorCommand.cs
@@ -0,0 +1,37 @@
+#region License
+
+// Copyright 2005-2019 Paul Kohler (https://github.com/paulkohler/minisqlquery). All rights reserved.
+// This source code is made available under the terms of the GNU Lesser General Public License v3.0
+// https://github.com/paulkohler/minisqlquery/blob/master/LICENSE
+#endregion
+
+using MiniSqlQuery.Core;
+using MiniSqlQuery.Core.Commands;
+using WeifenLuo.WinFormsUI.Docking;
+
+namespace MiniSqlQuery.PlugIns.ViewTable.Commands
+{
+    /// <summary>The view table from inspector command.</summary>
+    public class ViewTableFromInspectorCommand
+        : CommandBase
+    {
+        /// <summary>Initializes a new instance of the <see cref="ViewTableFromInspectorCommand"/> class.</summary>
+        public ViewTableFromInspectorCommand()
+            : base("&View table data")
+        {
+            SmallImage = ImageResource.table_go;
+        }
+
+        /// <summary>Execute the command.</summary>
+        public override void Execute()
+        {
+            string tableName = HostWindow.DatabaseInspector.RightClickedTableName;
+            if (tableName != null)
+            {
+                IViewTable frm = Services.Resolve<IViewTable>();
+                frm.TableName = tableName;
+                HostWindow.DisplayDockedForm(frm as DockContent);
+            }
+        }
+    }
+}
\ No newline at end of file
Added +0 -0
diff --git a/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/table.ico b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/table.ico
new file mode 100644
index 0000000..a6650d4
Binary files /dev/null and b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/table.ico differ
Added +531 -0
diff --git a/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableForm.cs b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableForm.cs
new file mode 100644
index 0000000..7ccce01
--- /dev/null
+++ b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableForm.cs
@@ -0,0 +1,531 @@
+#region License
+
+// Copyright 2005-2019 Paul Kohler (https://github.com/paulkohler/minisqlquery). All rights reserved.
+// This source code is made available under the terms of the GNU Lesser General Public License v3.0
+// https://github.com/paulkohler/minisqlquery/blob/master/LICENSE
+#endregion
+
+using System;
+using System.Collections.Generic;
+using System.Data;
+using System.Data.Common;
+using System.Data.SqlClient;
+using System.Diagnostics;
+using System.IO;
+using System.Windows.Forms;
+using MiniSqlQuery.Core;
+using MiniSqlQuery.Core.DbModel;
+using MiniSqlQuery.Properties;
+using WeifenLuo.WinFormsUI.Docking;
+
+namespace MiniSqlQuery.PlugIns.ViewTable
+{
+    /// <summary>The view table form.</summary>
+    public partial class ViewTableForm : DockContent, IViewTable
+    {
+        /// <summary>The _batch.</summary>
+        private readonly QueryBatch _batch;
+
+        /// <summary>The _services.</summary>
+        private readonly IApplicationServices _services;
+
+        /// <summary>The _settings.</summary>
+        private readonly IApplicationSettings _settings;
+
+        /// <summary>The _sync lock.</summary>
+        private readonly object _syncLock = new object();
+
+        /// <summary>The _db connection.</summary>
+        private DbConnection _dbConnection;
+
+        /// <summary>The _is busy.</summary>
+        private bool _isBusy;
+
+        /// <summary>The _meta data service.</summary>
+        private IDatabaseSchemaService _metaDataService;
+
+        /// <summary>The _status.</summary>
+        private string _status = string.Empty;
+
+        private int? _rowCount;
+
+        /// <summary>Stores the widths of the columns for this window.</summary>
+        private Dictionary<string, int> _columnSizes = new Dictionary<string, int>();
+
+        /// <summary>When tru the grid is being resized on fill, used to avoid overriting column width values.</summary>
+        private bool _resizingGrid;
+
+        /// <summary>Initializes a new instance of the <see cref="ViewTableForm"/> class.</summary>
+        public ViewTableForm()
+        {
+            InitializeComponent();
+        }
+
+        /// <summary>Initializes a new instance of the <see cref="ViewTableForm"/> class.</summary>
+        /// <param name="services">The services.</param>
+        /// <param name="settings">The settings.</param>
+        public ViewTableForm(IApplicationServices services, IApplicationSettings settings)
+            : this()
+        {
+            _services = services;
+            _settings = settings;
+            _batch = new QueryBatch();
+            TableName = string.Empty;
+            Text = Resources.ViewData;
+
+            dataGridViewResult.DefaultCellStyle.NullValue = _settings.NullText;
+            dataGridViewResult.DataBindingComplete += DataGridViewResultDataBindingComplete;
+            dataGridViewResult.ColumnWidthChanged += OnColumnWidthChanged;
+            _services.Settings.DatabaseConnectionReset += SettingsDatabaseConnectionReset;
+            _services.SystemMessagePosted += ServicesSystemMessagePosted;
+        }
+
+        /// <summary>Gets a value indicating whether AutoReload.</summary>
+        public bool AutoReload
+        {
+            get { return chkAutoReload.Checked; }
+        }
+
+        /// <summary>Gets Batch.</summary>
+        public QueryBatch Batch
+        {
+            get { return _batch; }
+        }
+
+        /// <summary>Gets CursorColumn.</summary>
+        public int CursorColumn
+        {
+            get { return dataGridViewResult.SelectedCells.Count > 0 ? dataGridViewResult.SelectedCells[0].ColumnIndex : 0; }
+        }
+
+        /// <summary>Gets CursorLine.</summary>
+        public int CursorLine
+        {
+            get { return (dataGridViewResult.CurrentRow != null) ? dataGridViewResult.CurrentRow.Index : 0; }
+        }
+
+        /// <summary>Gets CursorOffset.</summary>
+        public int CursorOffset
+        {
+            get { return CursorLine; }
+        }
+
+        /// <summary>Gets or sets a value indicating whether IsBusy.</summary>
+        public bool IsBusy
+        {
+            get { return _isBusy; }
+            set
+            {
+                lock (_syncLock)
+                {
+                    _isBusy = value;
+                }
+            }
+        }
+
+        /// <summary>Gets or sets TableName.</summary>
+        public string TableName
+        {
+            get { return cboTableName.Text; }
+            set { cboTableName.Text = value; }
+        }
+
+        /// <summary>Gets or sets Text.</summary>
+        public override string Text
+        {
+            get { return base.Text; }
+            set
+            {
+                base.Text = value;
+                TabText = Text;
+            }
+        }
+
+        /// <summary>Gets TotalLines.</summary>
+        public int TotalLines
+        {
+            get { return (dataGridViewResult.DataSource != null) ? dataGridViewResult.Rows.Count : 0; }
+        }
+
+        /// <summary>The set status.</summary>
+        /// <param name="text">The text.</param>
+        public void SetStatus(string text)
+        {
+            _status = text;
+            UpdateHostStatus();
+        }
+
+        public void SetRowCount(int? rows)
+        {
+            _rowCount = rows;
+            UpdateHostStatus();
+        }
+
+        /// <summary>The set cursor by location.</summary>
+        /// <param name="line">The line.</param>
+        /// <param name="column">The column.</param>
+        /// <returns>The set cursor by location.</returns>
+        public bool SetCursorByLocation(int line, int column)
+        {
+            if (line > 0 && line <= TotalLines)
+            {
+                dataGridViewResult.FirstDisplayedScrollingRowIndex = line;
+                dataGridViewResult.Refresh();
+                dataGridViewResult.Rows[line].Selected = true;
+                return true;
+            }
+
+            return false;
+        }
+
+        /// <summary>The set cursor by offset.</summary>
+        /// <param name="offset">The offset.</param>
+        /// <returns>The set cursor by offset.</returns>
+        public bool SetCursorByOffset(int offset)
+        {
+            return SetCursorByLocation(offset, 0);
+        }
+
+        /// <summary>The cancel task.</summary>
+        public void CancelTask()
+        {
+            // not supported (yet?)
+        }
+
+        /// <summary>The execute task.</summary>
+        public void ExecuteTask()
+        {
+            LoadTableData();
+        }
+
+        /// <summary>The update host status.</summary>
+        protected void UpdateHostStatus()
+        {
+            _services.HostWindow.SetStatus(this, _status);
+            _services.HostWindow.SetResultCount(this, _rowCount);
+        }
+
+        /// <summary>The data grid view result data binding complete.</summary>
+        /// <param name="sender">The sender.</param>
+        /// <param name="e">The e.</param>
+        private void DataGridViewResultDataBindingComplete(object sender, DataGridViewBindingCompleteEventArgs e)
+        {
+            DataTable dt = dataGridViewResult.DataSource as DataTable;
+            if (dt == null)
+            {
+                return;
+            }
+
+            try
+            {
+                _resizingGrid = true;
+
+                // create a reasonable default max width for columns
+                int maxColWidth = Math.Max(dataGridViewResult.ClientSize.Width / 2, 100);
+
+                // Autosize the columns then change the widths, gleaned from SO - http://stackoverflow.com/a/1031871/276563
+                dataGridViewResult.AutoResizeColumns(DataGridViewAutoSizeColumnsMode.DisplayedCells);
+
+                string nullText = _settings.NullText;
+                string dateTimeFormat = _settings.DateTimeFormat;
+                for (int i = 0; i < dt.Columns.Count; i++)
+                {
+                    if (dt.Columns[i].DataType == typeof(DateTime))
+                    {
+                        DataGridViewCellStyle dateCellStyle = new DataGridViewCellStyle();
+                        dateCellStyle.NullValue = nullText;
+                        dateCellStyle.Format = dateTimeFormat;
+                        dataGridViewResult.Columns[i].DefaultCellStyle = dateCellStyle;
+                    }
+
+                    // sync column sizes:
+                    int columnWidth = dataGridViewResult.Columns[i].Width;
+                    dataGridViewResult.Columns[i].AutoSizeMode = DataGridViewAutoSizeColumnMode.None;
+
+                    string headerText = dataGridViewResult.Columns[i].HeaderText;
+                    if (!string.IsNullOrEmpty(headerText) && _columnSizes.ContainsKey(headerText))
+                    {
+                        // use the previous column size in case its been adjusted etc
+                        dataGridViewResult.Columns[i].Width = _columnSizes[headerText];
+                    }
+                    else
+                    {
+                        // reset to a the smaller of the 2 sizes, this is mainly for the bigger text columns that throw the size out
+                        dataGridViewResult.Columns[i].Width = Math.Min(columnWidth, maxColWidth);
+
+                        if (!string.IsNullOrEmpty(headerText))
+                        {
+                            _columnSizes[headerText] = dataGridViewResult.Columns[i].Width;
+                        }
+                    }
+                }
+            }
+            finally
+            {
+                _resizingGrid = false;
+            }
+        }
+
+        public void OnColumnWidthChanged(object sender, DataGridViewColumnEventArgs e)
+        {
+            if (_resizingGrid)
+            {
+                return;
+            }
+
+            string headerText = e.Column.HeaderText;
+            if (!string.IsNullOrEmpty(headerText))
+            {
+                _columnSizes[headerText] = e.Column.Width;
+            }
+        }
+
+        /// <summary>The get tables and views.</summary>
+        private void GetTablesAndViews()
+        {
+            if (_metaDataService == null)
+            {
+                _metaDataService = DatabaseMetaDataService.Create(_services.Settings.ConnectionDefinition.ProviderName);
+
+                DbModelInstance model = _metaDataService.GetDbObjectModel(_services.Settings.ConnectionDefinition.ConnectionString);
+                List<string> tableNames = new List<string>();
+                foreach (DbModelTable table in model.Tables)
+                {
+                    tableNames.Add(Utility.MakeSqlFriendly(table.FullName));
+                }
+
+                foreach (DbModelView view in model.Views)
+                {
+                    tableNames.Add(Utility.MakeSqlFriendly(view.FullName));
+                }
+
+                cboTableName.Items.AddRange(tableNames.ToArray());
+            }
+        }
+
+        /// <summary>The load table data.</summary>
+        private void LoadTableData()
+        {
+            if (_services.Settings.ConnectionDefinition == null)
+            {
+                _services.HostWindow.DisplaySimpleMessageBox(this, "Please select a connection.", "Select a Connection");
+                return;
+            }
+
+            GetTablesAndViews();
+
+            DbDataAdapter adapter = null;
+            DbCommand cmd = null;
+            DataTable dt = null;
+            Query query = new Query("SELECT * FROM " + Utility.MakeSqlFriendly(TableName));
+
+            if (string.IsNullOrEmpty(TableName))
+            {
+                Text = Resources.Table_none;
+                return;
+            }
+
+            try
+            {
+                IsBusy = true;
+                UseWaitCursor = true;
+                dataGridViewResult.DataSource = null;
+                Application.DoEvents();
+
+                if (_dbConnection == null)
+                {
+                    _dbConnection = _services.Settings.GetOpenConnection();
+                }
+
+                query.Result = new DataSet(TableName + " View");
+                _batch.Clear();
+                _batch.Add(query);
+
+                adapter = _services.Settings.ProviderFactory.CreateDataAdapter();
+                cmd = _dbConnection.CreateCommand();
+                cmd.CommandText = query.Sql;
+                cmd.CommandType = CommandType.Text;
+                SetCommandTimeout(cmd, _settings.CommandTimeout);
+                adapter.SelectCommand = cmd;
+                adapter.Fill(query.Result);
+                SetStatus(string.Format("Loaded table '{0}'", TableName));
+                Text = TableName;
+            }
+            catch (DbException dbExp)
+            {
+                // todo: improve!
+                _services.HostWindow.DisplaySimpleMessageBox(this, dbExp.Message, "View Table Error");
+                SetStatus(dbExp.Message);
+                Text = Resources.ViewDataError;
+            }
+            finally
+            {
+                if (adapter != null)
+                {
+                    adapter.Dispose();
+                }
+
+                if (cmd != null)
+                {
+                    cmd.Dispose();
+                }
+
+                UseWaitCursor = false;
+                IsBusy = false;
+            }
+
+            if (query.Result != null && query.Result.Tables.Count > 0)
+            {
+                dt = query.Result.Tables[0];
+                Text = Resources.Table_colon + TableName;
+            }
+
+            dataGridViewResult.DefaultCellStyle.NullValue = _settings.NullText;
+            dataGridViewResult.DataSource = dt;
+
+            if (dt != null)
+            {
+                SetRowCount(dt.Rows.Count);
+            }
+        }
+
+
+        /// <summary>
+        /// Sets the command timeout, currently only tested against MSSQL.
+        /// </summary>
+        /// <param name="cmd">The command.</param>
+        /// <param name="commandTimeout">The command timeout.</param>
+        private void SetCommandTimeout(IDbCommand cmd, int commandTimeout)
+        {
+            if (_services.Settings.ProviderFactory is SqlClientFactory)
+            {
+                if (cmd == null)
+                {
+                    throw new ArgumentNullException("cmd");
+                }
+                cmd.CommandTimeout = commandTimeout;
+            }
+            else
+            {
+                Trace.WriteLine("Command Timeout only supported by SQL Client (so far)");
+            }
+        }
+
+        /// <summary>The services system message posted.</summary>
+        /// <param name="sender">The sender.</param>
+        /// <param name="e">The e.</param>
+        private void ServicesSystemMessagePosted(object sender, SystemMessageEventArgs e)
+        {
+            if (e.Message == SystemMessage.TableTruncated)
+            {
+                if (AutoReload && TableName.Equals(e.Data))
+                {
+                    LoadTableData();
+                }
+            }
+        }
+
+        /// <summary>The settings database connection reset.</summary>
+        /// <param name="sender">The sender.</param>
+        /// <param name="e">The e.</param>
+        private void SettingsDatabaseConnectionReset(object sender, EventArgs e)
+        {
+            _dbConnection = null;
+        }
+
+        /// <summary>The update status.</summary>
+        /// <param name="msg">The msg.</param>
+        private void UpdateStatus(string msg)
+        {
+            _services.HostWindow.SetStatus(this, msg);
+            Application.DoEvents();
+        }
+
+        /// <summary>The view table form_ shown.</summary>
+        /// <param name="sender">The sender.</param>
+        /// <param name="e">The e.</param>
+        private void ViewTableForm_Shown(object sender, EventArgs e)
+        {
+            LoadTableData();
+        }
+
+        /// <summary>The data grid view result_ data error.</summary>
+        /// <param name="sender">The sender.</param>
+        /// <param name="e">The e.</param>
+        private void dataGridViewResult_DataError(object sender, DataGridViewDataErrorEventArgs e)
+        {
+            e.ThrowException = false;
+        }
+
+        /// <summary>The lnk export script_ link clicked.</summary>
+        /// <param name="sender">The sender.</param>
+        /// <param name="e">The e.</param>
+        private void lnkExportScript_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
+        {
+            DataTable dt = dataGridViewResult.DataSource as DataTable;
+
+            if (dt != null)
+            {
+                var stringWriter = new StringWriter();
+                var hostWindow = _services.HostWindow;
+                var dbModelTable = hostWindow.DatabaseInspector.DbSchema.FindTableOrView(TableName);
+                var sqlWriter = _services.Resolve<ISqlWriter>();
+                sqlWriter.IncludeComments = false;
+                sqlWriter.InsertLineBreaksBetweenColumns = false;
+                sqlWriter.IncludeReadOnlyColumnsInExport = _settings.IncludeReadOnlyColumnsInExport;
+
+                for (int i = 0; i < dt.Rows.Count; i++)
+                {
+                    DataRow dataRow = dt.Rows[i];
+
+                    foreach (var column in dbModelTable.Columns)
+                    {
+                        column.DbType.Value = dataRow[dt.Columns[column.Name]];
+                    }
+
+                    sqlWriter.WriteInsert(stringWriter, dbModelTable);
+                    if (_settings.EnableQueryBatching)
+                    {
+                        stringWriter.WriteLine("GO");
+                    }
+
+                    stringWriter.WriteLine();
+
+                    if (i % 10 == 0)
+                    {
+                        UpdateStatus(string.Format("Processing {0} of {1} rows", i + 1, dt.Rows.Count));
+                    }
+                }
+
+                UpdateStatus(string.Format("Processed {0} rows. Opening file...", dt.Rows.Count));
+
+                // HACK - need to clean up the values for now as the model is holding the last rows data  ;-)
+                // TODO - add a "deep clone" method to the table/columns
+                foreach (var column in dbModelTable.Columns)
+                {
+                    column.DbType.Value = null;
+                }
+
+                // create a new sql editor and push the sql into it
+                IEditor editor = _services.Resolve<IQueryEditor>();
+                editor.AllText = stringWriter.ToString();
+                hostWindow.DisplayDockedForm(editor as DockContent);
+
+                UpdateStatus(null);
+            }
+        }
+
+        /// <summary>The lnk refresh_ link clicked.</summary>
+        /// <param name="sender">The sender.</param>
+        /// <param name="e">The e.</param>
+        private void lnkRefresh_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
+        {
+            LoadTableData();
+        }
+
+        private void ViewTableForm_Activated(object sender, EventArgs e)
+        {
+            UpdateHostStatus();
+        }
+    }
+}
\ No newline at end of file
Added +171 -0
diff --git a/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableForm.Designer.cs b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableForm.Designer.cs
new file mode 100644
index 0000000..869349f
--- /dev/null
+++ b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableForm.Designer.cs
@@ -0,0 +1,171 @@
+namespace MiniSqlQuery.PlugIns.ViewTable
+{
+	partial class ViewTableForm
+	{
+		/// <summary>
+		/// Required designer variable.
+		/// </summary>
+		private System.ComponentModel.IContainer components = null;
+
+		/// <summary>
+		/// Clean up any resources being used.
+		/// </summary>
+		/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
+		protected override void Dispose(bool disposing)
+		{
+			if (disposing && (components != null))
+			{
+				components.Dispose();
+			}
+			base.Dispose(disposing);
+		}
+
+		#region Windows Form Designer generated code
+
+		/// <summary>
+		/// Required method for Designer support - do not modify
+		/// the contents of this method with the code editor.
+		/// </summary>
+		private void InitializeComponent()
+		{
+			this.components = new System.ComponentModel.Container();
+			System.Windows.Forms.DataGridViewCellStyle dataGridViewCellStyle1 = new System.Windows.Forms.DataGridViewCellStyle();
+			System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(ViewTableForm));
+			this.dataGridViewResult = new System.Windows.Forms.DataGridView();
+			this.groupBox1 = new System.Windows.Forms.GroupBox();
+			this.lnkExportScript = new System.Windows.Forms.LinkLabel();
+			this.chkAutoReload = new System.Windows.Forms.CheckBox();
+			this.lnkRefresh = new System.Windows.Forms.LinkLabel();
+			this.cboTableName = new System.Windows.Forms.ComboBox();
+			this.toolTip1 = new System.Windows.Forms.ToolTip(this.components);
+			this.contextMenuStrip = new System.Windows.Forms.ContextMenuStrip(this.components);
+			((System.ComponentModel.ISupportInitialize)(this.dataGridViewResult)).BeginInit();
+			this.groupBox1.SuspendLayout();
+			this.SuspendLayout();
+			// 
+			// dataGridViewResult
+			// 
+			this.dataGridViewResult.AllowUserToAddRows = false;
+			this.dataGridViewResult.AllowUserToDeleteRows = false;
+			this.dataGridViewResult.ColumnHeadersHeightSizeMode = System.Windows.Forms.DataGridViewColumnHeadersHeightSizeMode.AutoSize;
+			dataGridViewCellStyle1.Alignment = System.Windows.Forms.DataGridViewContentAlignment.MiddleLeft;
+			dataGridViewCellStyle1.BackColor = System.Drawing.SystemColors.Window;
+			dataGridViewCellStyle1.Font = new System.Drawing.Font("Courier New", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(0)));
+			dataGridViewCellStyle1.ForeColor = System.Drawing.SystemColors.ControlText;
+			dataGridViewCellStyle1.SelectionBackColor = System.Drawing.SystemColors.Highlight;
+			dataGridViewCellStyle1.SelectionForeColor = System.Drawing.SystemColors.HighlightText;
+			dataGridViewCellStyle1.WrapMode = System.Windows.Forms.DataGridViewTriState.False;
+			this.dataGridViewResult.DefaultCellStyle = dataGridViewCellStyle1;
+			this.dataGridViewResult.Dock = System.Windows.Forms.DockStyle.Fill;
+			this.dataGridViewResult.Location = new System.Drawing.Point(4, 69);
+			this.dataGridViewResult.Name = "dataGridViewResult";
+			this.dataGridViewResult.ReadOnly = true;
+			this.dataGridViewResult.Size = new System.Drawing.Size(562, 294);
+			this.dataGridViewResult.TabIndex = 0;
+			this.dataGridViewResult.DataError += new System.Windows.Forms.DataGridViewDataErrorEventHandler(this.dataGridViewResult_DataError);
+			// 
+			// groupBox1
+			// 
+			this.groupBox1.Controls.Add(this.lnkExportScript);
+			this.groupBox1.Controls.Add(this.chkAutoReload);
+			this.groupBox1.Controls.Add(this.lnkRefresh);
+			this.groupBox1.Controls.Add(this.cboTableName);
+			this.groupBox1.Dock = System.Windows.Forms.DockStyle.Top;
+			this.groupBox1.Location = new System.Drawing.Point(4, 4);
+			this.groupBox1.Name = "groupBox1";
+			this.groupBox1.Size = new System.Drawing.Size(562, 65);
+			this.groupBox1.TabIndex = 2;
+			this.groupBox1.TabStop = false;
+			this.groupBox1.Text = "Table Name";
+			// 
+			// lnkExportScript
+			// 
+			this.lnkExportScript.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
+			this.lnkExportScript.AutoSize = true;
+			this.lnkExportScript.Location = new System.Drawing.Point(469, 29);
+			this.lnkExportScript.Name = "lnkExportScript";
+			this.lnkExportScript.Size = new System.Drawing.Size(76, 13);
+			this.lnkExportScript.TabIndex = 4;
+			this.lnkExportScript.TabStop = true;
+			this.lnkExportScript.Text = "Export Script...";
+			this.toolTip1.SetToolTip(this.lnkExportScript, "Takes the current data and creates a script of insert statements in a new window." +
+        "");
+			this.lnkExportScript.LinkClicked += new System.Windows.Forms.LinkLabelLinkClickedEventHandler(this.lnkExportScript_LinkClicked);
+			// 
+			// chkAutoReload
+			// 
+			this.chkAutoReload.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
+			this.chkAutoReload.AutoSize = true;
+			this.chkAutoReload.Checked = true;
+			this.chkAutoReload.CheckState = System.Windows.Forms.CheckState.Checked;
+			this.chkAutoReload.Location = new System.Drawing.Point(471, 45);
+			this.chkAutoReload.Name = "chkAutoReload";
+			this.chkAutoReload.Size = new System.Drawing.Size(85, 17);
+			this.chkAutoReload.TabIndex = 2;
+			this.chkAutoReload.Text = "Auto Reload";
+			this.toolTip1.SetToolTip(this.chkAutoReload, "Automatically reload the table when a \'Truncate\' action is performed.");
+			this.chkAutoReload.UseVisualStyleBackColor = true;
+			// 
+			// lnkRefresh
+			// 
+			this.lnkRefresh.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
+			this.lnkRefresh.AutoSize = true;
+			this.lnkRefresh.Location = new System.Drawing.Point(469, 16);
+			this.lnkRefresh.Name = "lnkRefresh";
+			this.lnkRefresh.Size = new System.Drawing.Size(71, 13);
+			this.lnkRefresh.TabIndex = 1;
+			this.lnkRefresh.TabStop = true;
+			this.lnkRefresh.Text = "Reload Table";
+			this.toolTip1.SetToolTip(this.lnkRefresh, "Reload the selected table now.");
+			this.lnkRefresh.LinkClicked += new System.Windows.Forms.LinkLabelLinkClickedEventHandler(this.lnkRefresh_LinkClicked);
+			// 
+			// cboTableName
+			// 
+			this.cboTableName.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) 
+            | System.Windows.Forms.AnchorStyles.Right)));
+			this.cboTableName.FormattingEnabled = true;
+			this.cboTableName.Location = new System.Drawing.Point(12, 19);
+			this.cboTableName.MaxDropDownItems = 20;
+			this.cboTableName.Name = "cboTableName";
+			this.cboTableName.Size = new System.Drawing.Size(454, 21);
+			this.cboTableName.TabIndex = 0;
+			// 
+			// contextMenuStrip
+			// 
+			this.contextMenuStrip.Name = "contextMenuStrip";
+			this.contextMenuStrip.Size = new System.Drawing.Size(61, 4);
+			// 
+			// ViewTableForm
+			// 
+			this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
+			this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
+			this.ClientSize = new System.Drawing.Size(570, 367);
+			this.Controls.Add(this.dataGridViewResult);
+			this.Controls.Add(this.groupBox1);
+			this.Font = new System.Drawing.Font("Microsoft Sans Serif", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(0)));
+			this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
+			this.Name = "ViewTableForm";
+			this.Padding = new System.Windows.Forms.Padding(4);
+			this.TabText = "ViewTableForm";
+			this.Text = "ViewTableForm";
+			this.Activated += new System.EventHandler(this.ViewTableForm_Activated);
+			this.Shown += new System.EventHandler(this.ViewTableForm_Shown);
+			((System.ComponentModel.ISupportInitialize)(this.dataGridViewResult)).EndInit();
+			this.groupBox1.ResumeLayout(false);
+			this.groupBox1.PerformLayout();
+			this.ResumeLayout(false);
+
+		}
+
+		#endregion
+
+		private System.Windows.Forms.DataGridView dataGridViewResult;
+		private System.Windows.Forms.GroupBox groupBox1;
+		private System.Windows.Forms.ComboBox cboTableName;
+		private System.Windows.Forms.LinkLabel lnkRefresh;
+		private System.Windows.Forms.CheckBox chkAutoReload;
+		private System.Windows.Forms.ToolTip toolTip1;
+		private System.Windows.Forms.ContextMenuStrip contextMenuStrip;
+		private System.Windows.Forms.LinkLabel lnkExportScript;
+	}
+}
\ No newline at end of file
Added +155 -0
diff --git a/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableForm.resx b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableForm.resx
new file mode 100644
index 0000000..e58af44
--- /dev/null
+++ b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableForm.resx
@@ -0,0 +1,155 @@
+<?xml version="1.0" encoding="utf-8"?>
+<root>
+  <!-- 
+    Microsoft ResX Schema 
+    
+    Version 2.0
+    
+    The primary goals of this format is to allow a simple XML format 
+    that is mostly human readable. The generation and parsing of the 
+    various data types are done through the TypeConverter classes 
+    associated with the data types.
+    
+    Example:
+    
+    ... ado.net/XML headers & schema ...
+    <resheader name="resmimetype">text/microsoft-resx</resheader>
+    <resheader name="version">2.0</resheader>
+    <resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
+    <resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
+    <data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
+    <data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
+    <data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
+        <value>[base64 mime encoded serialized .NET Framework object]</value>
+    </data>
+    <data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
+        <value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
+        <comment>This is a comment</comment>
+    </data>
+                
+    There are any number of "resheader" rows that contain simple 
+    name/value pairs.
+    
+    Each data row contains a name, and value. The row also contains a 
+    type or mimetype. Type corresponds to a .NET class that support 
+    text/value conversion through the TypeConverter architecture. 
+    Classes that don't support this are serialized and stored with the 
+    mimetype set.
+    
+    The mimetype is used for serialized objects, and tells the 
+    ResXResourceReader how to depersist the object. This is currently not 
+    extensible. For a given mimetype the value must be set accordingly:
+    
+    Note - application/x-microsoft.net.object.binary.base64 is the format 
+    that the ResXResourceWriter will generate, however the reader can 
+    read any of the formats listed below.
+    
+    mimetype: application/x-microsoft.net.object.binary.base64
+    value   : The object must be serialized with 
+            : System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
+            : and then encoded with base64 encoding.
+    
+    mimetype: application/x-microsoft.net.object.soap.base64
+    value   : The object must be serialized with 
+            : System.Runtime.Serialization.Formatters.Soap.SoapFormatter
+            : and then encoded with base64 encoding.
+
+    mimetype: application/x-microsoft.net.object.bytearray.base64
+    value   : The object must be serialized into a byte array 
+            : using a System.ComponentModel.TypeConverter
+            : and then encoded with base64 encoding.
+    -->
+  <xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
+    <xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
+    <xsd:element name="root" msdata:IsDataSet="true">
+      <xsd:complexType>
+        <xsd:choice maxOccurs="unbounded">
+          <xsd:element name="metadata">
+            <xsd:complexType>
+              <xsd:sequence>
+                <xsd:element name="value" type="xsd:string" minOccurs="0" />
+              </xsd:sequence>
+              <xsd:attribute name="name" use="required" type="xsd:string" />
+              <xsd:attribute name="type" type="xsd:string" />
+              <xsd:attribute name="mimetype" type="xsd:string" />
+              <xsd:attribute ref="xml:space" />
+            </xsd:complexType>
+          </xsd:element>
+          <xsd:element name="assembly">
+            <xsd:complexType>
+              <xsd:attribute name="alias" type="xsd:string" />
+              <xsd:attribute name="name" type="xsd:string" />
+            </xsd:complexType>
+          </xsd:element>
+          <xsd:element name="data">
+            <xsd:complexType>
+              <xsd:sequence>
+                <xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
+                <xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
+              </xsd:sequence>
+              <xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
+              <xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
+              <xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
+              <xsd:attribute ref="xml:space" />
+            </xsd:complexType>
+          </xsd:element>
+          <xsd:element name="resheader">
+            <xsd:complexType>
+              <xsd:sequence>
+                <xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
+              </xsd:sequence>
+              <xsd:attribute name="name" type="xsd:string" use="required" />
+            </xsd:complexType>
+          </xsd:element>
+        </xsd:choice>
+      </xsd:complexType>
+    </xsd:element>
+  </xsd:schema>
+  <resheader name="resmimetype">
+    <value>text/microsoft-resx</value>
+  </resheader>
+  <resheader name="version">
+    <value>2.0</value>
+  </resheader>
+  <resheader name="reader">
+    <value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
+  </resheader>
+  <resheader name="writer">
+    <value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
+  </resheader>
+  <metadata name="toolTip1.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
+    <value>132, 17</value>
+  </metadata>
+  <metadata name="contextMenuStrip.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
+    <value>229, 17</value>
+  </metadata>
+  <assembly alias="System.Drawing" name="System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a" />
+  <data name="$this.Icon" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
+    <value>
+        AAABAAEAEBAAAAAAAABoBQAAFgAAACgAAAAQAAAAIAAAAAEACAAAAAAAQAEAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAA////AMOEUgCc1aUA78GiAHa+fADao3oA8OLYAOvRvQCHyY4AzpNkAOSyjAD38esA6MiwANSb
+        bwCQzpgA6bqWAMWKXQB+w4QA9OriAN+qggD79/QA6MSpAOrNtQDXoHQAy45eAILGiQDRl2oA676dAIvL
+        kwCU0J0A4a6HAMeHVgB6wYAAmNOhAPbt5gDy594A5rWQAPr08ADdqH4A6sesAMmKWwDnt5QA8eXbAOrP
+        ugDqy7IA67yaAO3AnwDIjV8A3KV9AOnDpgDEhlQA1p5yAOCshADr078A6smuAPr28gD58+4A05luAOnG
+        qgDIilkAxoxfANGWaADqzrcA6My1AN2pgADqybAA6MiuAOjHrADpupgA+PLtAMaGVQDr0LsA4q+IAOy/
+        ngDltI8A9/DqAMaKXADLj18AzpJjAOvSvgDXoXUA6syzANmkegDpx60A6casAO7BoQDrvZsA47GMAPv2
+        8gD69vEA+fPvAPPn3gDx5NsA69C6AOnJsADpya4A6setAOe3kwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+        AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA0Oj5PGSkgAgICAgICAAAAUUZMIxNcXQcHBwcHBxEAAFM5UAE2
+        AQEBYQEBAQc9AAAnW15ISEhICBcXFxcHTQAAFFs/AUgBAQEsWQEBBzAAAB8mLVJSUlI/REQNQwczAABY
+        WjcBQgEBAUQBAQErRwAASzg7VShUYF9EXw1AJDwAACoVMgEWAQEBRAEBAQxOAABFFTIyMjIyMjIyMjIV
+        CgAAVxUBAQEBAQEBAQEBFRsAAEoVAyIeDx0JGhIhBRUOAABWFRUVFRUVFRUVFRUVGAAAAAQvHC4QYiUL
+        STVBMQYAAAAAAAAAAAAAAAAAAAAAAP//AACAAwAAgAEAAIABAACAAQAAgAEAAIABAACAAQAAgAEAAIAB
+        AACAAQAAgAEAAIABAACAAQAAwAEAAP//AAA=
+</value>
+  </data>
+</root>
\ No newline at end of file
Added +37 -0
diff --git a/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableLoader.cs b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableLoader.cs
new file mode 100644
index 0000000..1fd6f8f
--- /dev/null
+++ b/minisqlquery-master/src/MiniSqlQuery/PlugIns/ViewTable/ViewTableLoader.cs
@@ -0,0 +1,37 @@
+#region License
+
+// Copyright 2005-2019 Paul Kohler (https://github.com/paulkohler/minisqlquery). All rights reserved.
+// This source code is made available under the terms of the GNU Lesser General Public License v3.0
+// https://github.com/paulkohler/minisqlquery/blob/master/LICENSE
+#endregion
+
+using MiniSqlQuery.Core;
+using MiniSqlQuery.PlugIns.ViewTable.Commands;
+
+namespace MiniSqlQuery.PlugIns.ViewTable
+{
+    /// <summary>The view table loader.</summary>
+    public class ViewTableLoader : PluginLoaderBase
+    {
+        /// <summary>Initializes a new instance of the <see cref="ViewTableLoader"/> class.</summary>
+        public ViewTableLoader()
+            : base("View Table Data", "A Mini SQL Query Plugin for viewing table data.", 50)
+        {
+        }
+
+        /// <summary>Iinitialize the plug in.</summary>
+        public override void InitializePlugIn()
+        {
+            Services.RegisterComponent<IViewTable, ViewTableForm>("ViewTableForm");
+
+            // the DB inspector may not be present
+            if (Services.HostWindow.DatabaseInspector != null)
+            {
+                Services.HostWindow.DatabaseInspector.TableMenu.Items.Insert(
+                    0, CommandControlBuilder.CreateToolStripMenuItem<ViewTableFromInspectorCommand>());
+            }
+
+            Services.HostWindow.AddPluginCommand<ViewTableFormCommand>();
+        }
+    }
+}
\ No newline at end of file