Code:
/ Net / Net / 3.5.50727.3053 / DEVDIV / depot / DevDiv / releases / whidbey / netfxsp / ndp / fx / src / DataOracleClient / System / Data / OracleClient / OracleCommandSet.cs / 1 / OracleCommandSet.cs
//------------------------------------------------------------------------------
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//
// [....]
//-----------------------------------------------------------------------------
namespace System.Data.OracleClient {
using System;
using System.Collections;
using System.ComponentModel;
using System.Data;
using System.Data.Common;
using System.Diagnostics;
using System.Globalization;
using System.Text;
using System.Text.RegularExpressions;
internal sealed class OracleCommandSet : IDisposable{
static private readonly string _sqlTokenPattern =
@"[\s]+" // white space
+ @"|(?'([^']|'')*')" // single quoted literal or double quoted literal/identifier
+ @"|(?"
+ @"(/\*([^\*]|\*[^/])*\*/)" // c-style comment
+ @"|"
+ @"(--.*)" // ansi-sql style comment
+ @")"
+ @"|(?:[\p{Lo}\p{Lu}\p{Ll}\p{Lm}\p{Nd}\uff3f_#$]+)" // parameter-marker
+ @"|(?select)" // query statements
+ @"|(?"
+ @"([\p{Lo}\p{Lu}\p{Ll}\p{Lm}\p{Nd}\uff3f_#$]+)" // identifier
+ @"|"
+ "(\"([^\"]|\"\")*\")" // quoted identifier
+ @")"
+ @"|(?.)" // everything else
;
static private Regex _sqlTokenParser;
static private int _commentGroup;
static private int _identifierGroup;
static private int _parameterMarkerGroup;
static private int _queryGroup;
static private int _stringGroup;
static private int _otherGroup;
static private readonly string Declarations_Prefix = "declare\ntype refcursortype is ref cursor;\n";
static private readonly string Declarations_CursorType = " refcursortype;\n";
static private readonly string Body_Prefix = "begin\n" ;
static private readonly string Body_Suffix = "end;" ;
static private readonly string Command_QueryPrefix_Part1 = "open ";
static private readonly string Command_QueryPrefix_Part2 = " for ";
static private readonly string Command_Suffix_Part1 = ";\n:";
static private readonly string Command_NonQuerySuffix_Part2 = " := sql%rowcount;\n";
static private readonly string Command_QuerySuffix_Part2 = " := ";
static private readonly string Command_QuerySuffix_Part3 = ";\n";
private Hashtable _usedParameterNames = new Hashtable(StringComparer.OrdinalIgnoreCase);
private ArrayList _commandList = new ArrayList();
private OracleCommand _batchCommand;
private bool _dirty;
private sealed class LocalCommand {
internal readonly bool IsQuery;
internal readonly string CommandText;
internal readonly DbParameter[] Parameters;
internal readonly string[] ParameterNames;
internal readonly LocalParameter[] ParameterInsertionPoints;
internal OracleParameter ResultParameter;
internal LocalCommand(string commandText, bool isQuery, DbParameter[] parameters, string[] parameterNames, LocalParameter[] parameterInsertionPoints) {
Debug.Assert(0 <= commandText.Length, "no text");
this.CommandText = commandText;
this.IsQuery = isQuery;
this.Parameters = parameters;
this.ParameterNames = parameterNames;
this.ParameterInsertionPoints = parameterInsertionPoints;
}
}
private struct LocalParameter {
internal readonly int ParameterIndex;
internal readonly int InsertionPoint;
internal readonly int RemovalLength;
internal LocalParameter(int parameterIndex, int insertionPoint, int removalLength) {
Debug.Assert(0 <= parameterIndex, "negative index");
Debug.Assert(0 <= insertionPoint, "negative insert");
Debug.Assert(0 <= removalLength, "negative length");
this.ParameterIndex = parameterIndex;
this.InsertionPoint = insertionPoint;
this.RemovalLength = removalLength;
}
}
public OracleCommandSet() : this(null, null) {
}
public OracleCommandSet(OracleConnection connection, OracleTransaction transaction) : base() {
_batchCommand = new OracleCommand();
Connection = connection;
Transaction = transaction;
}
private OracleCommand BatchCommand {
get {
OracleCommand command = _batchCommand;
if (null == command) {
throw ADP.ObjectDisposed(this.GetType().Name);
}
return command;
}
}
/*/
public bool CanOptimizeSet {
get {
return true;
}
}
*/
public int CommandCount {
get {
return CommandList.Count;
}
}
private ArrayList CommandList {
get {
ArrayList commandList = _commandList;
if (null == commandList) {
throw ADP.ObjectDisposed(this.GetType().Name);
}
return commandList;
}
}
public int CommandTimeout {
set {
BatchCommand.CommandTimeout = value;
}
}
public OracleConnection Connection {
set {
BatchCommand.Connection = value;
}
}
internal OracleTransaction Transaction {
set {
BatchCommand.Transaction = (OracleTransaction)value;
}
}
public void Append(OracleCommand command) {
ADP.CheckArgumentNull(command, "command");
if (ADP.IsEmpty(command.CommandText)) {
throw ADP.CommandTextRequired("Append");
}
//
ICollection collection = command.Parameters;
OracleParameter[] parameters = new OracleParameter[collection.Count];
collection.CopyTo(parameters, 0);
string[] parameterNames = new string[parameters.Length];
if (0 < parameters.Length) {
for(int i = 0; i < parameters.Length; ++i) {
parameterNames[i] = parameters[i].ParameterName;
OracleParameter p = command.CreateParameter();
parameters[i].CopyTo(p);
// Deep clone the parameter value if byte[] or char[]
object obj = p.Value;
if (obj is byte[]) {
byte[] value = (byte[])obj;
int offset = p.Offset;
int size = p.Size;
int countOfBytes = value.Length - offset;
if ((0 != size) && (size < countOfBytes)) {
countOfBytes = size;
}
byte[] copy = new byte[Math.Max(countOfBytes, 0)];
Buffer.BlockCopy(value, offset, copy, 0, copy.Length);
p.Offset = 0;
p.Value = copy;
}
else if (obj is char[]) {
char[] value = (char[])obj;
int offset = p.Offset;
int size = p.Size;
int countOfChars = value.Length - offset;
if ((0 != size) && (size < countOfChars)) {
countOfChars = size;
}
char[] copy = new char[Math.Max(countOfChars, 0)];
Buffer.BlockCopy(value, offset, copy, 0, copy.Length*2);
p.Offset = 0;
p.Value = copy;
}
else if (obj is ICloneable) {
p.Value = ((ICloneable)obj).Clone();
}
parameters[i] = p;
}
}
string statementText = command.StatementText;
bool isQuery = false;
LocalParameter[] parameterInsertions = ParseText(command, statementText, out isQuery);
Debug.Assert(null != parameterInsertions, "null parameterInsertions");
#if TRACECOMMANDSET
foreach(LocalParameter local in parameterInsertions) {
Debug.WriteLine("\t\t<"+parameters[local.ParameterIndex].ParameterName+"> " + local.InsertionPoint.ToString(CultureInfo.InvariantCulture) + " " + local.RemovalLength.ToString(CultureInfo.InvariantCulture));
}
#endif //TRACECOMMANDSET
LocalCommand cmd = new LocalCommand(statementText, isQuery, parameters, parameterNames, parameterInsertions);
_dirty = true;
CommandList.Add(cmd);
}
public void Clear() {
DbCommand batchCommand = BatchCommand;
if (null != batchCommand) {
batchCommand.Parameters.Clear();
batchCommand.CommandText = null;
}
ArrayList commandList = _commandList;
if (null != commandList) {
commandList.Clear();
}
Hashtable usedParameterNames = _usedParameterNames;
if (null != usedParameterNames) {
usedParameterNames.Clear();
}
}
public void Dispose() {
DbCommand command = _batchCommand;
_batchCommand = null;
_commandList = null;
_usedParameterNames = null;
if (null != command) {
command.Dispose();
}
}
public int ExecuteNonQuery() {
GenerateBatchCommandText();
return BatchCommand.ExecuteNonQuery();
}
private void GenerateBatchCommandText() {
if (_dirty) {
DbCommand batchCommand = BatchCommand;
StringBuilder declarations = new StringBuilder();
StringBuilder body = new StringBuilder();
int resultIndex = 1;
int cursorIndex = 1;
int paramIndex = 1;
batchCommand.Parameters.Clear();
declarations.Append(Declarations_Prefix);
body.Append(Body_Prefix);
foreach (LocalCommand localCommand in CommandList) {
// Add each of the original commands parameters to the batch
// command, ensuring each parameter name is unique, ie. that
// there wasn't a parameter name somewhere in the original
// command text that we didn't have a bound parameter for.
foreach (DbParameter parameter in localCommand.Parameters) {
string parameterName;
do {
parameterName = "p" + paramIndex.ToString(CultureInfo.InvariantCulture);
paramIndex++;
} while (_usedParameterNames.ContainsKey(parameterName));
// Oracle doesn't care if multiple parameters are marked with ParameterDirection.ReturnValue
parameter.ParameterName = parameterName;
batchCommand.Parameters.Add(parameter);
}
// Generate a unique parameter name for the result parameter
// and add it to the batch command, indicating that it needs
// special processing by the execute to be put into the result
// set.
string resultName;
do {
resultName = "r" + resultIndex.ToString(CultureInfo.InvariantCulture)+"_"+paramIndex.ToString(CultureInfo.InvariantCulture);
paramIndex++;
} while (_usedParameterNames.ContainsKey(resultName));
OracleParameter resultParameter = new OracleParameter();
resultParameter.CommandSetResult = resultIndex++;
resultParameter.Direction = ParameterDirection.Output;
resultParameter.ParameterName = resultName;
batchCommand.Parameters.Add(resultParameter);
// Append the appropriate text to the declarations and the body
// sections, depending on whether an explicit cursor is needed
// or not.
int offset = body.Length;
if (localCommand.IsQuery) {
string cursorName = "c" + cursorIndex.ToString(CultureInfo.InvariantCulture);
cursorIndex++;
declarations.Append(cursorName);
declarations.Append(Declarations_CursorType);
body.Append(Command_QueryPrefix_Part1);
body.Append(cursorName);
body.Append(Command_QueryPrefix_Part2);
offset = body.Length;
body.Append(localCommand.CommandText);
body.Append(Command_Suffix_Part1);
body.Append(resultName);
body.Append(Command_QuerySuffix_Part2);
body.Append(cursorName);
body.Append(Command_QuerySuffix_Part3);
resultParameter.OracleType = OracleType.Cursor;
// don't cache ResultParameter, always has 'RecordsAffected == -1'
}
else {
string commandText = localCommand.CommandText;
body.Append(commandText.TrimEnd(';'));// remove extra semicolons, we're going to add our own...
body.Append(Command_Suffix_Part1);
body.Append(resultName);
body.Append(Command_NonQuerySuffix_Part2);
resultParameter.OracleType = OracleType.Int32;
localCommand.ResultParameter = resultParameter;
}
// Now perform the parameter name replacement in the statement
// text; we saved the start of this statement's text in the
// offset variable, and we simply do the replacement in the body
// text.
foreach (LocalParameter localParameter in localCommand.ParameterInsertionPoints) {
DbParameter parameter = localCommand.Parameters[localParameter.ParameterIndex];
string parameterMarker = ":" + parameter.ParameterName;
body.Remove(offset + localParameter.InsertionPoint, localParameter.RemovalLength);
body.Insert(offset + localParameter.InsertionPoint, parameterMarker);
offset += (parameterMarker.Length - localParameter.RemovalLength);
}
}
// Now we get tricky; we append the body to the declarations, and
// then we use the result as the actual command text for the batch
// command.
body.Append(Body_Suffix);
declarations.Append(body);
batchCommand.CommandText = declarations.ToString();
#if TRACECOMMANDSET
Debug.WriteLine(""+batchCommand.CommandText+" ");
#endif //TRACECOMMANDSET
_dirty = false;
}
}
internal bool GetBatchedRecordsAffected(int commandIndex, out int recordsAffected) {
OracleParameter resultParameter = ((LocalCommand)CommandList[commandIndex]).ResultParameter;
if (null != resultParameter) {
if (resultParameter.Value is Int32) {
recordsAffected = (int)resultParameter.Value; // the records affected
return true;
}
recordsAffected = -1;
return false; // batch didn't complete
}
recordsAffected = -1;
return true; // IsQuery == true
}
internal DbParameter GetParameter(int commandIndex, int parameterIndex) {
return ((LocalCommand)CommandList[commandIndex]).Parameters[parameterIndex];
}
public int GetParameterCount(int commandIndex) {
return ((LocalCommand)CommandList[commandIndex]).Parameters.Length;
}
static private Regex GetSqlTokenParser() {
Regex parser = _sqlTokenParser;
if (null == parser) {
// due to workingset size issues ~1.5MB, don't use RegexOptions.Compiled
parser = new Regex(_sqlTokenPattern, RegexOptions.ExplicitCapture);
_commentGroup= parser.GroupNumberFromName("comment");
_identifierGroup = parser.GroupNumberFromName("identifier");
_parameterMarkerGroup= parser.GroupNumberFromName("parametermarker");
_queryGroup = parser.GroupNumberFromName("query");
_stringGroup = parser.GroupNumberFromName("string");
_otherGroup = parser.GroupNumberFromName("other");
_sqlTokenParser = parser;
}
return parser;
}
private LocalParameter[] ParseText(OracleCommand command, string commandText, out bool isQuery) {
#if TRACECOMMANDSET
Debug.WriteLine(String.Format("\n\n{0}", commandText));
#endif //TRACECOMMANDSET
OracleParameterCollection parameters = command.Parameters;
ArrayList insertionPoints = new ArrayList();
Regex parser = GetSqlTokenParser();
isQuery = false;
bool keywordOrIdentiferFound = false;
for (Match match = parser.Match(commandText); Match.Empty != match; match = match.NextMatch()) {
if (match.Groups[_commentGroup].Success) {
// no effect, just eat
}
else if (match.Groups[_identifierGroup].Success
|| match.Groups[_stringGroup].Success
|| match.Groups[_otherGroup].Success) {
keywordOrIdentiferFound = true;
}
else if (match.Groups[_queryGroup].Success) {
if (!keywordOrIdentiferFound) {
isQuery = true;
#if TRACECOMMANDSET
Debug.WriteLine("...QueryStatementFound");
#endif //TRACECOMMANDSET
}
}
else if (match.Groups[_parameterMarkerGroup].Success) {
string parameterMarker = match.Groups[_parameterMarkerGroup].Value;
string parameterName = parameterMarker.Substring(1);
_usedParameterNames[parameterName] = null;
int parameterIndex = parameters.IndexOf(parameterName);
// SQLBUDT #289921 - some folks will put the ":" in the
// parameter name in the collection, so we need to take
// that into account.
if (0 > parameterIndex) {
string tempName = ":" + parameterName;
parameterIndex = parameters.IndexOf(tempName);
}
if (0 <= parameterIndex) {
#if TRACECOMMANDSET
Debug.WriteLine(String.Format("...IsParameter({0})", parameterIndex));
#endif
insertionPoints.Add(new LocalParameter(parameterIndex, match.Index, match.Length));
}
}
}
LocalParameter[] values = new LocalParameter[insertionPoints.Count];
insertionPoints.CopyTo(values, 0);
return values;
}
}
}
// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
//------------------------------------------------------------------------------
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//
// [....]
//-----------------------------------------------------------------------------
namespace System.Data.OracleClient {
using System;
using System.Collections;
using System.ComponentModel;
using System.Data;
using System.Data.Common;
using System.Diagnostics;
using System.Globalization;
using System.Text;
using System.Text.RegularExpressions;
internal sealed class OracleCommandSet : IDisposable{
static private readonly string _sqlTokenPattern =
@"[\s]+" // white space
+ @"|(?'([^']|'')*')" // single quoted literal or double quoted literal/identifier
+ @"|(?"
+ @"(/\*([^\*]|\*[^/])*\*/)" // c-style comment
+ @"|"
+ @"(--.*)" // ansi-sql style comment
+ @")"
+ @"|(?:[\p{Lo}\p{Lu}\p{Ll}\p{Lm}\p{Nd}\uff3f_#$]+)" // parameter-marker
+ @"|(?select)" // query statements
+ @"|(?"
+ @"([\p{Lo}\p{Lu}\p{Ll}\p{Lm}\p{Nd}\uff3f_#$]+)" // identifier
+ @"|"
+ "(\"([^\"]|\"\")*\")" // quoted identifier
+ @")"
+ @"|(?.)" // everything else
;
static private Regex _sqlTokenParser;
static private int _commentGroup;
static private int _identifierGroup;
static private int _parameterMarkerGroup;
static private int _queryGroup;
static private int _stringGroup;
static private int _otherGroup;
static private readonly string Declarations_Prefix = "declare\ntype refcursortype is ref cursor;\n";
static private readonly string Declarations_CursorType = " refcursortype;\n";
static private readonly string Body_Prefix = "begin\n" ;
static private readonly string Body_Suffix = "end;" ;
static private readonly string Command_QueryPrefix_Part1 = "open ";
static private readonly string Command_QueryPrefix_Part2 = " for ";
static private readonly string Command_Suffix_Part1 = ";\n:";
static private readonly string Command_NonQuerySuffix_Part2 = " := sql%rowcount;\n";
static private readonly string Command_QuerySuffix_Part2 = " := ";
static private readonly string Command_QuerySuffix_Part3 = ";\n";
private Hashtable _usedParameterNames = new Hashtable(StringComparer.OrdinalIgnoreCase);
private ArrayList _commandList = new ArrayList();
private OracleCommand _batchCommand;
private bool _dirty;
private sealed class LocalCommand {
internal readonly bool IsQuery;
internal readonly string CommandText;
internal readonly DbParameter[] Parameters;
internal readonly string[] ParameterNames;
internal readonly LocalParameter[] ParameterInsertionPoints;
internal OracleParameter ResultParameter;
internal LocalCommand(string commandText, bool isQuery, DbParameter[] parameters, string[] parameterNames, LocalParameter[] parameterInsertionPoints) {
Debug.Assert(0 <= commandText.Length, "no text");
this.CommandText = commandText;
this.IsQuery = isQuery;
this.Parameters = parameters;
this.ParameterNames = parameterNames;
this.ParameterInsertionPoints = parameterInsertionPoints;
}
}
private struct LocalParameter {
internal readonly int ParameterIndex;
internal readonly int InsertionPoint;
internal readonly int RemovalLength;
internal LocalParameter(int parameterIndex, int insertionPoint, int removalLength) {
Debug.Assert(0 <= parameterIndex, "negative index");
Debug.Assert(0 <= insertionPoint, "negative insert");
Debug.Assert(0 <= removalLength, "negative length");
this.ParameterIndex = parameterIndex;
this.InsertionPoint = insertionPoint;
this.RemovalLength = removalLength;
}
}
public OracleCommandSet() : this(null, null) {
}
public OracleCommandSet(OracleConnection connection, OracleTransaction transaction) : base() {
_batchCommand = new OracleCommand();
Connection = connection;
Transaction = transaction;
}
private OracleCommand BatchCommand {
get {
OracleCommand command = _batchCommand;
if (null == command) {
throw ADP.ObjectDisposed(this.GetType().Name);
}
return command;
}
}
/*/
public bool CanOptimizeSet {
get {
return true;
}
}
*/
public int CommandCount {
get {
return CommandList.Count;
}
}
private ArrayList CommandList {
get {
ArrayList commandList = _commandList;
if (null == commandList) {
throw ADP.ObjectDisposed(this.GetType().Name);
}
return commandList;
}
}
public int CommandTimeout {
set {
BatchCommand.CommandTimeout = value;
}
}
public OracleConnection Connection {
set {
BatchCommand.Connection = value;
}
}
internal OracleTransaction Transaction {
set {
BatchCommand.Transaction = (OracleTransaction)value;
}
}
public void Append(OracleCommand command) {
ADP.CheckArgumentNull(command, "command");
if (ADP.IsEmpty(command.CommandText)) {
throw ADP.CommandTextRequired("Append");
}
//
ICollection collection = command.Parameters;
OracleParameter[] parameters = new OracleParameter[collection.Count];
collection.CopyTo(parameters, 0);
string[] parameterNames = new string[parameters.Length];
if (0 < parameters.Length) {
for(int i = 0; i < parameters.Length; ++i) {
parameterNames[i] = parameters[i].ParameterName;
OracleParameter p = command.CreateParameter();
parameters[i].CopyTo(p);
// Deep clone the parameter value if byte[] or char[]
object obj = p.Value;
if (obj is byte[]) {
byte[] value = (byte[])obj;
int offset = p.Offset;
int size = p.Size;
int countOfBytes = value.Length - offset;
if ((0 != size) && (size < countOfBytes)) {
countOfBytes = size;
}
byte[] copy = new byte[Math.Max(countOfBytes, 0)];
Buffer.BlockCopy(value, offset, copy, 0, copy.Length);
p.Offset = 0;
p.Value = copy;
}
else if (obj is char[]) {
char[] value = (char[])obj;
int offset = p.Offset;
int size = p.Size;
int countOfChars = value.Length - offset;
if ((0 != size) && (size < countOfChars)) {
countOfChars = size;
}
char[] copy = new char[Math.Max(countOfChars, 0)];
Buffer.BlockCopy(value, offset, copy, 0, copy.Length*2);
p.Offset = 0;
p.Value = copy;
}
else if (obj is ICloneable) {
p.Value = ((ICloneable)obj).Clone();
}
parameters[i] = p;
}
}
string statementText = command.StatementText;
bool isQuery = false;
LocalParameter[] parameterInsertions = ParseText(command, statementText, out isQuery);
Debug.Assert(null != parameterInsertions, "null parameterInsertions");
#if TRACECOMMANDSET
foreach(LocalParameter local in parameterInsertions) {
Debug.WriteLine("\t\t<"+parameters[local.ParameterIndex].ParameterName+"> " + local.InsertionPoint.ToString(CultureInfo.InvariantCulture) + " " + local.RemovalLength.ToString(CultureInfo.InvariantCulture));
}
#endif //TRACECOMMANDSET
LocalCommand cmd = new LocalCommand(statementText, isQuery, parameters, parameterNames, parameterInsertions);
_dirty = true;
CommandList.Add(cmd);
}
public void Clear() {
DbCommand batchCommand = BatchCommand;
if (null != batchCommand) {
batchCommand.Parameters.Clear();
batchCommand.CommandText = null;
}
ArrayList commandList = _commandList;
if (null != commandList) {
commandList.Clear();
}
Hashtable usedParameterNames = _usedParameterNames;
if (null != usedParameterNames) {
usedParameterNames.Clear();
}
}
public void Dispose() {
DbCommand command = _batchCommand;
_batchCommand = null;
_commandList = null;
_usedParameterNames = null;
if (null != command) {
command.Dispose();
}
}
public int ExecuteNonQuery() {
GenerateBatchCommandText();
return BatchCommand.ExecuteNonQuery();
}
private void GenerateBatchCommandText() {
if (_dirty) {
DbCommand batchCommand = BatchCommand;
StringBuilder declarations = new StringBuilder();
StringBuilder body = new StringBuilder();
int resultIndex = 1;
int cursorIndex = 1;
int paramIndex = 1;
batchCommand.Parameters.Clear();
declarations.Append(Declarations_Prefix);
body.Append(Body_Prefix);
foreach (LocalCommand localCommand in CommandList) {
// Add each of the original commands parameters to the batch
// command, ensuring each parameter name is unique, ie. that
// there wasn't a parameter name somewhere in the original
// command text that we didn't have a bound parameter for.
foreach (DbParameter parameter in localCommand.Parameters) {
string parameterName;
do {
parameterName = "p" + paramIndex.ToString(CultureInfo.InvariantCulture);
paramIndex++;
} while (_usedParameterNames.ContainsKey(parameterName));
// Oracle doesn't care if multiple parameters are marked with ParameterDirection.ReturnValue
parameter.ParameterName = parameterName;
batchCommand.Parameters.Add(parameter);
}
// Generate a unique parameter name for the result parameter
// and add it to the batch command, indicating that it needs
// special processing by the execute to be put into the result
// set.
string resultName;
do {
resultName = "r" + resultIndex.ToString(CultureInfo.InvariantCulture)+"_"+paramIndex.ToString(CultureInfo.InvariantCulture);
paramIndex++;
} while (_usedParameterNames.ContainsKey(resultName));
OracleParameter resultParameter = new OracleParameter();
resultParameter.CommandSetResult = resultIndex++;
resultParameter.Direction = ParameterDirection.Output;
resultParameter.ParameterName = resultName;
batchCommand.Parameters.Add(resultParameter);
// Append the appropriate text to the declarations and the body
// sections, depending on whether an explicit cursor is needed
// or not.
int offset = body.Length;
if (localCommand.IsQuery) {
string cursorName = "c" + cursorIndex.ToString(CultureInfo.InvariantCulture);
cursorIndex++;
declarations.Append(cursorName);
declarations.Append(Declarations_CursorType);
body.Append(Command_QueryPrefix_Part1);
body.Append(cursorName);
body.Append(Command_QueryPrefix_Part2);
offset = body.Length;
body.Append(localCommand.CommandText);
body.Append(Command_Suffix_Part1);
body.Append(resultName);
body.Append(Command_QuerySuffix_Part2);
body.Append(cursorName);
body.Append(Command_QuerySuffix_Part3);
resultParameter.OracleType = OracleType.Cursor;
// don't cache ResultParameter, always has 'RecordsAffected == -1'
}
else {
string commandText = localCommand.CommandText;
body.Append(commandText.TrimEnd(';'));// remove extra semicolons, we're going to add our own...
body.Append(Command_Suffix_Part1);
body.Append(resultName);
body.Append(Command_NonQuerySuffix_Part2);
resultParameter.OracleType = OracleType.Int32;
localCommand.ResultParameter = resultParameter;
}
// Now perform the parameter name replacement in the statement
// text; we saved the start of this statement's text in the
// offset variable, and we simply do the replacement in the body
// text.
foreach (LocalParameter localParameter in localCommand.ParameterInsertionPoints) {
DbParameter parameter = localCommand.Parameters[localParameter.ParameterIndex];
string parameterMarker = ":" + parameter.ParameterName;
body.Remove(offset + localParameter.InsertionPoint, localParameter.RemovalLength);
body.Insert(offset + localParameter.InsertionPoint, parameterMarker);
offset += (parameterMarker.Length - localParameter.RemovalLength);
}
}
// Now we get tricky; we append the body to the declarations, and
// then we use the result as the actual command text for the batch
// command.
body.Append(Body_Suffix);
declarations.Append(body);
batchCommand.CommandText = declarations.ToString();
#if TRACECOMMANDSET
Debug.WriteLine(""+batchCommand.CommandText+" ");
#endif //TRACECOMMANDSET
_dirty = false;
}
}
internal bool GetBatchedRecordsAffected(int commandIndex, out int recordsAffected) {
OracleParameter resultParameter = ((LocalCommand)CommandList[commandIndex]).ResultParameter;
if (null != resultParameter) {
if (resultParameter.Value is Int32) {
recordsAffected = (int)resultParameter.Value; // the records affected
return true;
}
recordsAffected = -1;
return false; // batch didn't complete
}
recordsAffected = -1;
return true; // IsQuery == true
}
internal DbParameter GetParameter(int commandIndex, int parameterIndex) {
return ((LocalCommand)CommandList[commandIndex]).Parameters[parameterIndex];
}
public int GetParameterCount(int commandIndex) {
return ((LocalCommand)CommandList[commandIndex]).Parameters.Length;
}
static private Regex GetSqlTokenParser() {
Regex parser = _sqlTokenParser;
if (null == parser) {
// due to workingset size issues ~1.5MB, don't use RegexOptions.Compiled
parser = new Regex(_sqlTokenPattern, RegexOptions.ExplicitCapture);
_commentGroup= parser.GroupNumberFromName("comment");
_identifierGroup = parser.GroupNumberFromName("identifier");
_parameterMarkerGroup= parser.GroupNumberFromName("parametermarker");
_queryGroup = parser.GroupNumberFromName("query");
_stringGroup = parser.GroupNumberFromName("string");
_otherGroup = parser.GroupNumberFromName("other");
_sqlTokenParser = parser;
}
return parser;
}
private LocalParameter[] ParseText(OracleCommand command, string commandText, out bool isQuery) {
#if TRACECOMMANDSET
Debug.WriteLine(String.Format("\n\n{0}", commandText));
#endif //TRACECOMMANDSET
OracleParameterCollection parameters = command.Parameters;
ArrayList insertionPoints = new ArrayList();
Regex parser = GetSqlTokenParser();
isQuery = false;
bool keywordOrIdentiferFound = false;
for (Match match = parser.Match(commandText); Match.Empty != match; match = match.NextMatch()) {
if (match.Groups[_commentGroup].Success) {
// no effect, just eat
}
else if (match.Groups[_identifierGroup].Success
|| match.Groups[_stringGroup].Success
|| match.Groups[_otherGroup].Success) {
keywordOrIdentiferFound = true;
}
else if (match.Groups[_queryGroup].Success) {
if (!keywordOrIdentiferFound) {
isQuery = true;
#if TRACECOMMANDSET
Debug.WriteLine("...QueryStatementFound");
#endif //TRACECOMMANDSET
}
}
else if (match.Groups[_parameterMarkerGroup].Success) {
string parameterMarker = match.Groups[_parameterMarkerGroup].Value;
string parameterName = parameterMarker.Substring(1);
_usedParameterNames[parameterName] = null;
int parameterIndex = parameters.IndexOf(parameterName);
// SQLBUDT #289921 - some folks will put the ":" in the
// parameter name in the collection, so we need to take
// that into account.
if (0 > parameterIndex) {
string tempName = ":" + parameterName;
parameterIndex = parameters.IndexOf(tempName);
}
if (0 <= parameterIndex) {
#if TRACECOMMANDSET
Debug.WriteLine(String.Format("...IsParameter({0})", parameterIndex));
#endif
insertionPoints.Add(new LocalParameter(parameterIndex, match.Index, match.Length));
}
}
}
LocalParameter[] values = new LocalParameter[insertionPoints.Count];
insertionPoints.CopyTo(values, 0);
return values;
}
}
}
// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
Link Menu

This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- webproxy.cs
- ApplicationServicesHostFactory.cs
- ArrayHelper.cs
- SponsorHelper.cs
- ping.cs
- GZipDecoder.cs
- Models.cs
- BindingUtils.cs
- WebPartManagerDesigner.cs
- NamespaceCollection.cs
- OperationInvokerBehavior.cs
- dataprotectionpermission.cs
- PathTooLongException.cs
- TreeNodeBinding.cs
- OneOf.cs
- GZipStream.cs
- MenuItemAutomationPeer.cs
- HttpVersion.cs
- WebPartHeaderCloseVerb.cs
- ThreadPool.cs
- ListControl.cs
- ProjectionPathSegment.cs
- OneOfElement.cs
- EnumDataContract.cs
- DataExpression.cs
- ScalarOps.cs
- ObjectAssociationEndMapping.cs
- DbDataAdapter.cs
- ClientCultureInfo.cs
- WizardStepBase.cs
- AspProxy.cs
- ResourcesBuildProvider.cs
- ActivityContext.cs
- WebPartMinimizeVerb.cs
- XmlWriterSettings.cs
- EdmEntityTypeAttribute.cs
- MetaModel.cs
- DynamicRouteExpression.cs
- HashCryptoHandle.cs
- SimpleWorkerRequest.cs
- XmlDigitalSignatureProcessor.cs
- DataMisalignedException.cs
- SqlProcedureAttribute.cs
- NavigatingCancelEventArgs.cs
- Thread.cs
- SqlConnectionManager.cs
- ISFClipboardData.cs
- WebPartExportVerb.cs
- CheckPair.cs
- HostSecurityManager.cs
- TextRenderer.cs
- Random.cs
- UnmanagedMemoryStream.cs
- RegistryExceptionHelper.cs
- SQLBytesStorage.cs
- ScrollableControl.cs
- InvalidOperationException.cs
- SingleTagSectionHandler.cs
- InteropBitmapSource.cs
- ReliableChannelFactory.cs
- SapiRecoInterop.cs
- DesignerPainter.cs
- IPGlobalProperties.cs
- X509Extension.cs
- TimerEventSubscription.cs
- XamlReader.cs
- TextEditorTyping.cs
- OledbConnectionStringbuilder.cs
- MethodBody.cs
- Calendar.cs
- PropertyDescriptorGridEntry.cs
- Exceptions.cs
- BasePattern.cs
- GroupDescription.cs
- AndAlso.cs
- ListBox.cs
- EncryptedData.cs
- AttributeCollection.cs
- DeferredElementTreeState.cs
- AddInAttribute.cs
- AppDomainShutdownMonitor.cs
- DefaultAuthorizationContext.cs
- SafeRightsManagementHandle.cs
- AssemblyInfo.cs
- Style.cs
- datacache.cs
- QilXmlReader.cs
- ObjectSet.cs
- SafeRightsManagementEnvironmentHandle.cs
- ScrollData.cs
- DataGridViewColumnDividerDoubleClickEventArgs.cs
- XmlSortKeyAccumulator.cs
- BaseInfoTable.cs
- BookmarkCallbackWrapper.cs
- SafeEventHandle.cs
- DescendantBaseQuery.cs
- ContentControl.cs
- AuthenticationManager.cs
- SpeakProgressEventArgs.cs
- SapiInterop.cs