Skip to content

Commit a3369e1

Browse files
committed
Database: Query support for DataSet [STUD-77624]
Query should return also DataSet Update unittests
1 parent 549a28f commit a3369e1

7 files changed

Lines changed: 79 additions & 6 deletions

File tree

Activities/Database/UiPath.Database.Activities/DatabaseExecute.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,11 +52,13 @@ public abstract class DatabaseExecute : AsyncTaskCodeActivity
5252
[Browsable(true)]
5353
public Dictionary<string, Argument> Parameters { get; set; } = new Dictionary<string, Argument>();
5454

55+
[DefaultValue(null)]
5556
[LocalizedCategory(nameof(Resources.Common))]
5657
[LocalizedDisplayName(nameof(Resources.Activity_DatabaseExecute_Property_ContinueOnError_Name))]
5758
[LocalizedDescription(nameof(Resources.Activity_DatabaseExecute_Property_ContinueOnError_Description))]
5859
public InArgument<bool> ContinueOnError { get; set; }
5960

61+
[DefaultValue(null)]
6062
[LocalizedCategory(nameof(Resources.Common))]
6163
[LocalizedDisplayName(nameof(Resources.Activity_DatabaseExecute_Property_TimeoutMS_Name))]
6264
[LocalizedDescription(nameof(Resources.Activity_DatabaseExecute_Property_TimeoutMS_Description))]

Activities/Database/UiPath.Database.Activities/ExecuteQuery.cs

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,12 @@ public partial class ExecuteQuery : DatabaseExecute
2929
[LocalizedDescription(nameof(Resources.Activity_ExecuteQuery_Property_DataTable_Description))]
3030
public OutArgument<DataTable> DataTable { get; set; }
3131

32+
[LocalizedCategory(nameof(Resources.Output))]
33+
[DefaultValue(null)]
34+
[LocalizedDisplayName(nameof(Resources.Activity_ExecuteQuery_Property_DataSet_Name))]
35+
[LocalizedDescription(nameof(Resources.Activity_ExecuteQuery_Property_DataSet_Description))]
36+
public OutArgument<DataSet> DataSet { get; set; }
37+
3238
public ExecuteQuery()
3339
{
3440
CommandType = CommandType.Text;
@@ -95,7 +101,8 @@ protected async override Task<Action<AsyncCodeActivityContext>> ExecuteInternalA
95101
{
96102
return null;
97103
}
98-
return new DBExecuteQueryResult(DbConnection.ExecuteQuery(sql, parameters, commandTimeout, CommandType), parameters);
104+
var (dataTable, dataSet) = DbConnection.ExecuteQuery(sql, parameters, commandTimeout, CommandType);
105+
return new DBExecuteQueryResult(dataTable, dataSet, parameters);
99106
});
100107
}
101108
catch (Exception ex)
@@ -119,6 +126,7 @@ protected async override Task<Action<AsyncCodeActivityContext>> ExecuteInternalA
119126
if (dt == null) return;
120127

121128
DataTable.Set(asyncCodeActivityContext, dt);
129+
DataSet.Set(asyncCodeActivityContext, affectedRecords.DataSetResult);
122130
foreach (var param in affectedRecords.ParametersBind)
123131
{
124132
var currentParam = Parameters[param.Key];
@@ -144,17 +152,20 @@ protected async override Task<Action<AsyncCodeActivityContext>> ExecuteInternalA
144152
private class DBExecuteQueryResult
145153
{
146154
public DataTable Result { get; }
155+
public DataSet DataSetResult { get; }
147156
public Dictionary<string, ParameterInfo> ParametersBind { get; }
148157

149158
public DBExecuteQueryResult()
150159
{
151160
this.Result = new DataTable();
161+
this.DataSetResult = new DataSet();
152162
this.ParametersBind = new Dictionary<string, ParameterInfo>();
153163
}
154164

155-
public DBExecuteQueryResult(DataTable result, Dictionary<string, ParameterInfo> parametersBind)
165+
public DBExecuteQueryResult(DataTable result, DataSet dataSetResult, Dictionary<string, ParameterInfo> parametersBind)
156166
{
157167
this.Result = result;
168+
this.DataSetResult = dataSetResult;
158169
this.ParametersBind = parametersBind;
159170
}
160171
}

Activities/Database/UiPath.Database.Activities/NetCore/ViewModels/ExecuteQueryViewModel.cs

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
using System.Security;
88
using System.Threading.Tasks;
99
using UiPath.Database.Activities.NetCore.ViewModels;
10+
using UiPath.Database.Activities.Properties;
1011

1112
namespace UiPath.Database.Activities
1213
{
@@ -66,17 +67,24 @@ public ExecuteQueryViewModel(IDesignServices services) : base(services)
6667
/// </summary>
6768
public DesignOutArgument<DataTable> DataTable { get; set; } = new DesignOutArgument<DataTable>();
6869

70+
/// <summary>
71+
/// The result of the execution of the sql command as a DataSet.
72+
/// </summary>
73+
public DesignOutArgument<DataSet> DataSet { get; set; } = new DesignOutArgument<DataSet>();
74+
6975
protected override void InitializeModel()
7076
{
7177
base.InitializeModel();
7278
int propertyOrderIndex = 1;
7379
int propertyColumnIndex = 1;
7480

81+
ExistingDbConnection.DisplayName = Resources.Activity_DatabaseExecute_Property_ExistingDbConnection_Name;
7582
ExistingDbConnection.IsPrincipal = true;
7683
ExistingDbConnection.IsRequired = true;
7784
ExistingDbConnection.OrderIndex = propertyOrderIndex++;
7885
ExistingDbConnection.Widget = new DefaultWidget { Type = ViewModelWidgetType.Input };
7986

87+
CommandType.DisplayName = Resources.Activity_DatabaseExecute_Property_CommandType_Name;
8088
CommandType.OrderIndex = propertyOrderIndex++;
8189
CommandType.IsPrincipal = true;
8290
CommandType.IsRequired = true;
@@ -88,24 +96,35 @@ protected override void InitializeModel()
8896
.Build();
8997
CommandType.Widget = new DefaultWidget { Type = ViewModelWidgetType.Dropdown };
9098

99+
Sql.DisplayName = Resources.Activity_ExecuteQuery_Property_Sql_Name;
91100
Sql.IsPrincipal = true;
92101
Sql.IsRequired = true;
93102
Sql.OrderIndex = propertyOrderIndex++;
94103
Sql.Widget = new DefaultWidget { Type = ViewModelWidgetType.TextComposer };
95104

105+
Parameters.DisplayName = Resources.Activity_DatabaseExecute_Property_Parameters_Name;
96106
Parameters.OrderIndex = propertyOrderIndex++;
97107
Parameters.Widget = new DefaultWidget { Type = ViewModelWidgetType.Dictionary };
98108

109+
TimeoutMS.DisplayName = Resources.Activity_DatabaseExecute_Property_TimeoutMS_Name;
99110
TimeoutMS.OrderIndex = propertyOrderIndex;
100111
TimeoutMS.ColumnOrder = propertyColumnIndex++;
101112
TimeoutMS.Widget = new DefaultWidget { Type = ViewModelWidgetType.Input };
102113

114+
ContinueOnError.DisplayName = Resources.Activity_DatabaseExecute_Property_ContinueOnError_Name;
103115
ContinueOnError.OrderIndex = propertyOrderIndex++;
104116
ContinueOnError.ColumnOrder = propertyColumnIndex;
105117
ContinueOnError.Widget = new DefaultWidget { Type = ViewModelWidgetType.NullableBoolean };
106118

119+
DataTable.DisplayName = Resources.Activity_ExecuteQuery_Property_DataTable_Name;
107120
DataTable.OrderIndex = propertyOrderIndex++;
108121
DataTable.Widget = new DefaultWidget { Type = ViewModelWidgetType.Input };
122+
123+
DataSet.DisplayName = Resources.Activity_ExecuteQuery_Property_DataSet_Name;
124+
DataSet.OrderIndex = propertyOrderIndex++;
125+
DataSet.Category = Resources.Output;
126+
DataSet.Tooltip = Resources.Activity_ExecuteQuery_Property_DataSet_Description;
127+
DataSet.Widget = new DefaultWidget { Type = ViewModelWidgetType.Input };
109128
}
110129

111130
protected override async ValueTask InitializeModelAsync()

Activities/Database/UiPath.Database.Activities/Properties/UiPath.Database.Activities.Designer.cs

Lines changed: 18 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Activities/Database/UiPath.Database.Activities/Properties/UiPath.Database.Activities.resx

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -580,6 +580,14 @@ If UseTransaction is set to True, the contained operations are executed in a sin
580580
<value>Data table</value>
581581
<comment>property name</comment>
582582
</data>
583+
<data name="Activity_ExecuteQuery_Property_DataSet_Description" xml:space="preserve">
584+
<value>The output of the SQL command wrapped in a DataSet variable.</value>
585+
<comment>property description</comment>
586+
</data>
587+
<data name="Activity_ExecuteQuery_Property_DataSet_Name" xml:space="preserve">
588+
<value>Data set</value>
589+
<comment>property name</comment>
590+
</data>
583591
<data name="Activity_DatabaseExecute_Property_ExistingDbConnection_Description" xml:space="preserve">
584592
<value>An already opened database connection obtained from the Connect or Start Transaction activities. If such a connection is provided, the ConnectionString and SecureConnectionString properties are ignored.</value>
585593
<comment>property description</comment>

Activities/Database/UiPath.Database.Tests/DatabaseConnectionTests.cs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -93,6 +93,10 @@ public void TestSize(string provider)
9393
param.SetupAllProperties();
9494
param.SetReturnsDefault(ParameterDirection.InputOutput);
9595

96+
var readerClosed = false;
97+
dataReader.Setup(r => r.IsClosed).Returns(() => readerClosed);
98+
dataReader.Setup(r => r.Close()).Callback(() => readerClosed = true);
99+
96100
var databaseConnection = new DatabaseConnection().Initialize(con.Object);
97101
var parameters = new Dictionary<string, ParameterInfo>() {
98102
{ "param1", new ParameterInfo() {Value = "", Direction = ArgumentDirection.Out}

Activities/Database/UiPath.Database/DatabaseConnection.cs

Lines changed: 15 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -64,13 +64,24 @@ public virtual void BeginTransaction()
6464
_transaction = _connection.BeginTransaction();
6565
}
6666

67-
public virtual DataTable ExecuteQuery(string sql, Dictionary<string, ParameterInfo> parameters, int commandTimeout, CommandType commandType = CommandType.Text)
67+
public virtual (DataTable, DataSet) ExecuteQuery(string sql, Dictionary<string, ParameterInfo> parameters, int commandTimeout, CommandType commandType = CommandType.Text)
6868
{
6969
OpenConnection();
7070
SetupCommand(sql, parameters, commandTimeout, commandType);
7171
_command.Transaction = _transaction;
72-
DataTable dt = new DataTable();
73-
dt.Load(_command.ExecuteReader());
72+
DataSet ds = new DataSet();
73+
DataTable dt;
74+
using (var reader = _command.ExecuteReader())
75+
{
76+
do
77+
{
78+
var table = new DataTable();
79+
table.Load(reader);
80+
ds.Tables.Add(table);
81+
} while (!reader.IsClosed);
82+
83+
dt = ds.Tables.Count > 0 ? ds.Tables[0] : new DataTable();
84+
}
7485
foreach (var param in _command.Parameters)
7586
{
7687
var dbParam = param as DbParameter;
@@ -80,7 +91,7 @@ public virtual DataTable ExecuteQuery(string sql, Dictionary<string, ParameterIn
8091
Direction = WokflowParameterDirectionToDbParameter(dbParam.Direction)
8192
};
8293
}
83-
return dt;
94+
return (dt, ds);
8495
}
8596

8697
public virtual int Execute(string sql, Dictionary<string, ParameterInfo> parameters, int commandTimeout, CommandType commandType = CommandType.Text)

0 commit comments

Comments
 (0)