@@ -27,33 +27,69 @@ public MySqlBulkCopy(MySqlConnection connection, MySqlTransaction? transaction =
27
27
public string ? DestinationTableName { get ; set ; }
28
28
29
29
#if ! NETSTANDARD1_3
30
- public void WriteToServer ( DataTable dataTable ) => WriteToServerAsync ( DataRowsValuesEnumerator . Create ( dataTable ) , IOBehavior . Synchronous , CancellationToken . None ) . GetAwaiter ( ) . GetResult ( ) ;
30
+ public void WriteToServer ( DataTable dataTable )
31
+ {
32
+ m_valuesEnumerator = DataRowsValuesEnumerator . Create ( dataTable ?? throw new ArgumentNullException ( nameof ( dataTable ) ) ) ;
33
+ WriteToServerAsync ( IOBehavior . Synchronous , CancellationToken . None ) . GetAwaiter ( ) . GetResult ( ) ;
34
+ }
31
35
32
36
#if ! NETSTANDARD2_1 && ! NETCOREAPP3_0
33
- public Task WriteToServerAsync ( DataTable dataTable , CancellationToken cancellationToken = default ) => WriteToServerAsync ( DataRowsValuesEnumerator . Create ( dataTable ) , IOBehavior . Synchronous , CancellationToken . None ) . AsTask ( ) ;
37
+ public async Task WriteToServerAsync ( DataTable dataTable , CancellationToken cancellationToken = default )
38
+ {
39
+ m_valuesEnumerator = DataRowsValuesEnumerator . Create ( dataTable ?? throw new ArgumentNullException ( nameof ( dataTable ) ) ) ;
40
+ await WriteToServerAsync ( IOBehavior . Asynchronous , CancellationToken . None ) . ConfigureAwait ( false ) ;
41
+ }
34
42
#else
35
- public ValueTask WriteToServerAsync ( DataTable dataTable , CancellationToken cancellationToken = default ) => WriteToServerAsync ( DataRowsValuesEnumerator . Create ( dataTable ) , IOBehavior . Synchronous , CancellationToken . None ) ;
43
+ public async ValueTask WriteToServerAsync ( DataTable dataTable , CancellationToken cancellationToken = default )
44
+ {
45
+ m_valuesEnumerator = DataRowsValuesEnumerator . Create ( dataTable ?? throw new ArgumentNullException ( nameof ( dataTable ) ) ) ;
46
+ await WriteToServerAsync ( IOBehavior . Asynchronous , cancellationToken ) . ConfigureAwait ( false ) ;
47
+ }
36
48
#endif
37
49
38
- public void WriteToServer ( IEnumerable < DataRow > dataRows , int columnCount ) => WriteToServerAsync ( new DataRowsValuesEnumerator ( dataRows , columnCount ) , IOBehavior . Synchronous , CancellationToken . None ) . GetAwaiter ( ) . GetResult ( ) ;
50
+ public void WriteToServer ( IEnumerable < DataRow > dataRows , int columnCount )
51
+ {
52
+ m_valuesEnumerator = new DataRowsValuesEnumerator ( dataRows ?? throw new ArgumentNullException ( nameof ( dataRows ) ) , columnCount ) ;
53
+ WriteToServerAsync ( IOBehavior . Synchronous , CancellationToken . None ) . GetAwaiter ( ) . GetResult ( ) ;
54
+ }
39
55
#if ! NETSTANDARD2_1 && ! NETCOREAPP3_0
40
- public Task WriteToServerAsync ( IEnumerable < DataRow > dataRows , int columnCount , CancellationToken cancellationToken = default ) => WriteToServerAsync ( new DataRowsValuesEnumerator ( dataRows , columnCount ) , IOBehavior . Asynchronous , cancellationToken ) . AsTask ( ) ;
56
+ public async Task WriteToServerAsync ( IEnumerable < DataRow > dataRows , int columnCount , CancellationToken cancellationToken = default )
57
+ {
58
+ m_valuesEnumerator = new DataRowsValuesEnumerator ( dataRows ?? throw new ArgumentNullException ( nameof ( dataRows ) ) , columnCount ) ;
59
+ await WriteToServerAsync ( IOBehavior . Asynchronous , cancellationToken ) . ConfigureAwait ( false ) ;
60
+ }
41
61
#else
42
- public ValueTask WriteToServerAsync ( IEnumerable < DataRow > dataRows , int columnCount , CancellationToken cancellationToken = default ) => WriteToServerAsync ( new DataRowsValuesEnumerator ( dataRows , columnCount ) , IOBehavior . Asynchronous , cancellationToken ) ;
62
+ public async ValueTask WriteToServerAsync ( IEnumerable < DataRow > dataRows , int columnCount , CancellationToken cancellationToken = default )
63
+ {
64
+ m_valuesEnumerator = new DataRowsValuesEnumerator ( dataRows ?? throw new ArgumentNullException ( nameof ( dataRows ) ) , columnCount ) ;
65
+ await WriteToServerAsync ( IOBehavior . Asynchronous , cancellationToken ) . ConfigureAwait ( false ) ;
66
+ }
43
67
#endif
44
68
#endif
45
69
46
- public void WriteToServer ( IDataReader dataReader ) => WriteToServerAsync ( DataReaderValuesEnumerator . Create ( dataReader ) , IOBehavior . Synchronous , CancellationToken . None ) . GetAwaiter ( ) . GetResult ( ) ;
70
+ public void WriteToServer ( IDataReader dataReader )
71
+ {
72
+ m_valuesEnumerator = DataReaderValuesEnumerator . Create ( dataReader ?? throw new ArgumentNullException ( nameof ( dataReader ) ) ) ;
73
+ WriteToServerAsync ( IOBehavior . Synchronous , CancellationToken . None ) . GetAwaiter ( ) . GetResult ( ) ;
74
+ }
47
75
#if ! NETSTANDARD2_1 && ! NETCOREAPP3_0
48
- public Task WriteToServerAsync ( IDataReader dataReader , CancellationToken cancellationToken = default ) => WriteToServerAsync ( DataReaderValuesEnumerator . Create ( dataReader ) , IOBehavior . Asynchronous , cancellationToken ) . AsTask ( ) ;
76
+ public async Task WriteToServerAsync ( IDataReader dataReader , CancellationToken cancellationToken = default )
77
+ {
78
+ m_valuesEnumerator = DataReaderValuesEnumerator . Create ( dataReader ?? throw new ArgumentNullException ( nameof ( dataReader ) ) ) ;
79
+ await WriteToServerAsync ( IOBehavior . Asynchronous , cancellationToken ) . ConfigureAwait ( false ) ;
80
+ }
49
81
#else
50
- public ValueTask WriteToServerAsync ( IDataReader dataReader , CancellationToken cancellationToken = default ) => WriteToServerAsync ( DataReaderValuesEnumerator . Create ( dataReader ) , IOBehavior . Asynchronous , cancellationToken ) ;
82
+ public async ValueTask WriteToServerAsync ( IDataReader dataReader , CancellationToken cancellationToken = default )
83
+ {
84
+ m_valuesEnumerator = DataReaderValuesEnumerator . Create ( dataReader ?? throw new ArgumentNullException ( nameof ( dataReader ) ) ) ;
85
+ await WriteToServerAsync ( IOBehavior . Asynchronous , cancellationToken ) . ConfigureAwait ( false ) ;
86
+ }
51
87
#endif
52
88
53
89
#if ! NETSTANDARD2_1 && ! NETCOREAPP3_0
54
- private async ValueTask < int > WriteToServerAsync ( IValuesEnumerator values , IOBehavior ioBehavior , CancellationToken cancellationToken )
90
+ private async ValueTask < int > WriteToServerAsync ( IOBehavior ioBehavior , CancellationToken cancellationToken )
55
91
#else
56
- private async ValueTask WriteToServerAsync ( IValuesEnumerator values , IOBehavior ioBehavior , CancellationToken cancellationToken )
92
+ private async ValueTask WriteToServerAsync ( IOBehavior ioBehavior , CancellationToken cancellationToken )
57
93
#endif
58
94
{
59
95
var tableName = DestinationTableName ?? throw new InvalidOperationException ( "DestinationTableName must be set before calling WriteToServer" ) ;
@@ -68,7 +104,7 @@ private async ValueTask WriteToServerAsync(IValuesEnumerator values, IOBehavior
68
104
LineTerminator = "\n " ,
69
105
Local = true ,
70
106
NumberOfLinesToSkip = 0 ,
71
- Source = values ?? throw new ArgumentNullException ( nameof ( values ) ) ,
107
+ Source = this ,
72
108
TableName = tableName ,
73
109
Timeout = BulkCopyTimeout ,
74
110
} ;
@@ -124,7 +160,7 @@ private async ValueTask WriteToServerAsync(IValuesEnumerator values, IOBehavior
124
160
static string QuoteIdentifier ( string identifier ) => "`" + identifier . Replace ( "`" , "``" ) + "`" ;
125
161
}
126
162
127
- internal static async Task SendDataReaderAsync ( MySqlConnection connection , IValuesEnumerator valuesEnumerator , IOBehavior ioBehavior , CancellationToken cancellationToken )
163
+ internal async Task SendDataReaderAsync ( IOBehavior ioBehavior , CancellationToken cancellationToken )
128
164
{
129
165
// rent a buffer that can fit in one packet
130
166
const int maxLength = 16_777_200 ;
@@ -133,16 +169,16 @@ internal static async Task SendDataReaderAsync(MySqlConnection connection, IValu
133
169
134
170
try
135
171
{
136
- var values = new object ? [ valuesEnumerator . FieldCount ] ;
172
+ var values = new object ? [ m_valuesEnumerator ! . FieldCount ] ;
137
173
while ( true )
138
174
{
139
175
var hasMore = ioBehavior == IOBehavior . Asynchronous ?
140
- await valuesEnumerator . MoveNextAsync ( ) . ConfigureAwait ( false ) :
141
- valuesEnumerator . MoveNext ( ) ;
176
+ await m_valuesEnumerator . MoveNextAsync ( ) . ConfigureAwait ( false ) :
177
+ m_valuesEnumerator . MoveNext ( ) ;
142
178
if ( ! hasMore )
143
179
break ;
144
180
145
- valuesEnumerator . GetValues ( values ) ;
181
+ m_valuesEnumerator . GetValues ( values ) ;
146
182
retryRow :
147
183
var startOutputIndex = outputIndex ;
148
184
var wroteRow = true ;
@@ -154,7 +190,7 @@ await valuesEnumerator.MoveNextAsync().ConfigureAwait(false) :
154
190
else
155
191
shouldAppendSeparator = true ;
156
192
157
- if ( outputIndex >= maxLength || ! WriteValue ( connection , value , buffer . AsSpan ( 0 , maxLength ) . Slice ( outputIndex ) , out var bytesWritten ) )
193
+ if ( outputIndex >= maxLength || ! WriteValue ( m_connection , value , buffer . AsSpan ( 0 , maxLength ) . Slice ( outputIndex ) , out var bytesWritten ) )
158
194
{
159
195
wroteRow = false ;
160
196
break ;
@@ -167,7 +203,7 @@ await valuesEnumerator.MoveNextAsync().ConfigureAwait(false) :
167
203
if ( startOutputIndex == 0 )
168
204
throw new NotSupportedException ( "Total row length must be less than 16MiB." ) ;
169
205
var payload = new PayloadData ( new ArraySegment < byte > ( buffer , 0 , startOutputIndex ) ) ;
170
- await connection . Session . SendReplyAsync ( payload , ioBehavior , cancellationToken ) . ConfigureAwait ( false ) ;
206
+ await m_connection . Session . SendReplyAsync ( payload , ioBehavior , cancellationToken ) . ConfigureAwait ( false ) ;
171
207
outputIndex = 0 ;
172
208
goto retryRow ;
173
209
}
@@ -180,7 +216,7 @@ await valuesEnumerator.MoveNextAsync().ConfigureAwait(false) :
180
216
if ( outputIndex != 0 )
181
217
{
182
218
var payload2 = new PayloadData ( new ArraySegment < byte > ( buffer , 0 , outputIndex ) ) ;
183
- await connection . Session . SendReplyAsync ( payload2 , ioBehavior , cancellationToken ) . ConfigureAwait ( false ) ;
219
+ await m_connection . Session . SendReplyAsync ( payload2 , ioBehavior , cancellationToken ) . ConfigureAwait ( false ) ;
184
220
}
185
221
}
186
222
finally
@@ -412,5 +448,6 @@ static bool WriteBytes(ReadOnlySpan<byte> value, Span<byte> output, out int byte
412
448
413
449
readonly MySqlConnection m_connection ;
414
450
readonly MySqlTransaction ? m_transaction ;
451
+ IValuesEnumerator ? m_valuesEnumerator ;
415
452
}
416
453
}
0 commit comments