source: BMXNET_RPMS_dotNET_UTILITIES-BMX/trunk/cs/bmx_0200scr/BMX2/BMXNet/BMXNetDataReader.cs

Last change on this file was 815, checked in by Sam Habiel, 15 years ago

Initial commit of C# Source Code. Now to try to get it to compile.

File size: 10.6 KB
Line 
1using System;
2using System.Data;
3using System.Globalization;
4
5namespace IndianHealthService.BMXNet
6{
7 public class BMXNetDataReader : IDataReader
8 {
9 // The DataReader should always be open when returned to the user.
10 private bool m_fOpen = true;
11
12 // Keep track of the results and position
13 // within the resultset (starts prior to first record).
14 private RPMSDb.RPMSDbResultSet m_resultset;
15 private static int m_STARTPOS = -1;
16 private int m_nPos = m_STARTPOS;
17
18 /*
19 * Keep track of the connection in order to implement the
20 * CommandBehavior.CloseConnection flag. A null reference means
21 * normal behavior (do not automatically close).
22 */
23 private BMXNetConnection m_connection = null;
24
25 /*
26 * Because the user should not be able to directly create a
27 * DataReader object, the constructors are
28 * marked as internal.
29 */
30 internal BMXNetDataReader(RPMSDb.RPMSDbResultSet resultset)
31 {
32 m_resultset = resultset;
33 }
34
35 internal BMXNetDataReader(RPMSDb.RPMSDbResultSet resultset, BMXNetConnection connection)
36 {
37 m_resultset = resultset;
38 m_connection = connection;
39 }
40
41 /****
42 * METHODS / PROPERTIES FROM IDataReader.
43 ****/
44 public int Depth
45 {
46 /*
47 * Always return a value of zero if nesting is not supported.
48 */
49 get { return 0; }
50 }
51
52 public bool IsClosed
53 {
54 /*
55 * Keep track of the reader state - some methods should be
56 * disallowed if the reader is closed.
57 */
58 get { return !m_fOpen; }
59 }
60
61 public int RecordsAffected
62 {
63 /*
64 * RecordsAffected is only applicable to batch statements
65 * that include inserts/updates/deletes. BMXNet always
66 * returns -1.
67 */
68 get { return -1; }
69 }
70
71 public void Close()
72 {
73 /*
74 * Close the reader. BMXNet only changes the state,
75 * but an actual implementation would also clean up any
76 * resources used by the operation. For example,
77 * cleaning up any resources waiting for data to be
78 * returned by the server.
79 */
80 m_fOpen = false;
81 }
82
83 public bool NextResult()
84 {
85 // BMXNet only returns a single resultset. However,
86 // DbDataAdapter expects NextResult to return a value.
87 return false;
88 }
89
90 public bool Read()
91 {
92 // Return true if it is possible to advance and if you are still positioned
93 // on a valid row. Because the data array in the resultset
94 // is two-dimensional, you must divide by the number of columns.
95 if (++m_nPos >= m_resultset.data.Length / m_resultset.metaData.Length)
96 return false;
97 else
98 return true;
99 }
100
101 public DataTable GetSchemaTable()
102 {
103 DataTable dtSchema = new DataTable();
104
105 dtSchema.Columns.Add("ColumnName", typeof(System.String));
106 dtSchema.Columns.Add("ColumnSize", typeof(Int32));
107 dtSchema.Columns.Add("ColumnOrdinal", typeof(Int32));
108 dtSchema.Columns.Add("NumericPrecision", typeof(Int16));
109 dtSchema.Columns.Add("NumericScale", typeof(Int16));
110 dtSchema.Columns.Add("DataType", typeof(System.Type));
111 dtSchema.Columns.Add("AllowDBNull", typeof(bool));
112 dtSchema.Columns.Add("IsReadOnly", typeof(bool));
113 dtSchema.Columns.Add("IsUnique", typeof(bool));
114 dtSchema.Columns.Add("IsRowVersion", typeof(bool));
115 dtSchema.Columns.Add("IsKey", typeof(bool));
116 dtSchema.Columns.Add("IsAutoIncrement", typeof(bool));
117 dtSchema.Columns.Add("IsLong", typeof(bool));
118 dtSchema.Columns.Add("BaseTableName", typeof(System.String));
119 dtSchema.Columns.Add("BaseColumnName", typeof(System.String));
120
121 dtSchema.ExtendedProperties.Add("BMXTable", m_resultset.fmFileID);
122 dtSchema.ExtendedProperties.Add("BMXKey", m_resultset.fmKeyField);
123
124 for (int i=0; i < m_resultset.metaData.GetLength(0); i++)
125 {
126 DataRow r = dtSchema.NewRow();
127 r["BaseTableName"] = m_resultset.fmFileID;
128 r["BaseColumnName"] = m_resultset.metaData[i].fmFieldID;
129 r["ColumnName"] = m_resultset.metaData[i].name;
130 r["ColumnSize"] = m_resultset.metaData[i].maxSize;
131 r["ColumnOrdinal"] = i;
132 r["NumericPrecision"] = 0;
133 r["NumericScale"] = 0;
134 r["DataType"] = m_resultset.metaData[i].type;
135 r["AllowDBNull"] = false;
136 r["IsReadOnly"] = m_resultset.metaData[i].fmReadOnly;
137 r["IsUnique"] = false;
138 if (m_resultset.metaData[i].name == "BMXIEN")
139 r["IsUnique"] = true;
140 r["IsRowVersion"] = false;
141 r["IsKey"] = m_resultset.metaData[i].fmKeyField;
142 r["IsAutoIncrement"] = false;
143 r["IsLong"] = false;
144
145 dtSchema.Rows.Add(r);
146 }
147 return dtSchema;
148 }
149
150 /****
151 * METHODS / PROPERTIES FROM IDataRecord.
152 ****/
153 public int FieldCount
154 {
155 // Return the count of the number of columns, which in
156 // this case is the size of the column metadata
157 // array.
158 get { return m_resultset.metaData.Length; }
159 }
160
161 public String GetName(int i)
162 {
163 return m_resultset.metaData[i].name;
164 }
165
166 public String GetDataTypeName(int i)
167 {
168 /*
169 * Usually this would return the name of the type
170 * as used on the back end, for example 'smallint' or 'varchar'.
171 * BMXNet returns the simple name of the .NET Framework type.
172 */
173 return m_resultset.metaData[i].type.Name;
174 }
175
176 public Type GetFieldType(int i)
177 {
178 // Return the actual Type class for the data type.
179 return m_resultset.metaData[i].type;
180 }
181
182 public Object GetValue(int i)
183 {
184 return m_resultset.data[m_nPos, i];
185 }
186
187 public int GetValues(object[] values)
188 {
189 int i = 0, j = 0;
190 for ( ; i < values.Length && j < m_resultset.metaData.Length; i++, j++)
191 {
192 values[i] = m_resultset.data[m_nPos, j];
193 }
194
195 return i;
196 }
197
198 public int GetOrdinal(string name)
199 {
200 // Look for the ordinal of the column with the same name and return it.
201 for (int i = 0; i < m_resultset.metaData.Length; i++)
202 {
203 if (0 == _cultureAwareCompare(name, m_resultset.metaData[i].name))
204 {
205 return i;
206 }
207 }
208
209 // Throw an exception if the ordinal cannot be found.
210 throw new IndexOutOfRangeException("Could not find specified column in results");
211 }
212
213 public object this [ int i ]
214 {
215 get { return m_resultset.data[m_nPos, i]; }
216 }
217
218 public object this [ String name ]
219 {
220 // Look up the ordinal and return
221 // the value at that position.
222 get { return this[GetOrdinal(name)]; }
223 }
224
225 public bool GetBoolean(int i)
226 {
227 /*
228 * Force the cast to return the type. InvalidCastException
229 * should be thrown if the data is not already of the correct type.
230 */
231 return (bool)m_resultset.data[m_nPos, i];
232 }
233
234 public byte GetByte(int i)
235 {
236 /*
237 * Force the cast to return the type. InvalidCastException
238 * should be thrown if the data is not already of the correct type.
239 */
240 return (byte)m_resultset.data[m_nPos, i];
241 }
242
243 public long GetBytes(int i, long fieldOffset, byte[] buffer, int bufferoffset, int length)
244 {
245 // BMXNet does not support this method.
246 throw new NotSupportedException("GetBytes not supported.");
247 }
248
249 public char GetChar(int i)
250 {
251 /*
252 * Force the cast to return the type. InvalidCastException
253 * should be thrown if the data is not already of the correct type.
254 */
255 return (char)m_resultset.data[m_nPos, i];
256 }
257
258 public long GetChars(int i, long fieldoffset, char[] buffer, int bufferoffset, int length)
259 {
260 // BMXNet does not support this method.
261 throw new NotSupportedException("GetChars not supported.");
262 }
263
264 public Guid GetGuid(int i)
265 {
266 /*
267 * Force the cast to return the type. InvalidCastException
268 * should be thrown if the data is not already of the correct type.
269 */
270 return (Guid)m_resultset.data[m_nPos, i];
271 }
272
273 public Int16 GetInt16(int i)
274 {
275 /*
276 * Force the cast to return the type. InvalidCastException
277 * should be thrown if the data is not already of the correct type.
278 */
279 return (Int16)m_resultset.data[m_nPos, i];
280 }
281
282 public Int32 GetInt32(int i)
283 {
284 /*
285 * Force the cast to return the type. InvalidCastException
286 * should be thrown if the data is not already of the correct type.
287 */
288 return (Int32)m_resultset.data[m_nPos, i];
289 }
290
291 public Int64 GetInt64(int i)
292 {
293 /*
294 * Force the cast to return the type. InvalidCastException
295 * should be thrown if the data is not already of the correct type.
296 */
297 return (Int64)m_resultset.data[m_nPos, i];
298 }
299
300 public float GetFloat(int i)
301 {
302 /*
303 * Force the cast to return the type. InvalidCastException
304 * should be thrown if the data is not already of the correct type.
305 */
306 return (float)m_resultset.data[m_nPos, i];
307 }
308
309 public double GetDouble(int i)
310 {
311 /*
312 * Force the cast to return the type. InvalidCastException
313 * should be thrown if the data is not already of the correct type.
314 */
315 return (double)m_resultset.data[m_nPos, i];
316 }
317
318 public String GetString(int i)
319 {
320 /*
321 * Force the cast to return the type. InvalidCastException
322 * should be thrown if the data is not already of the correct type.
323 */
324 return (String)m_resultset.data[m_nPos, i];
325 }
326
327 public Decimal GetDecimal(int i)
328 {
329 /*
330 * Force the cast to return the type. InvalidCastException
331 * should be thrown if the data is not already of the correct type.
332 */
333 return (Decimal)m_resultset.data[m_nPos, i];
334 }
335
336 public DateTime GetDateTime(int i)
337 {
338 /*
339 * Force the cast to return the type. InvalidCastException
340 * should be thrown if the data is not already of the correct type.
341 */
342 return (DateTime)m_resultset.data[m_nPos, i];
343 }
344
345 public IDataReader GetData(int i)
346 {
347 /*
348 * BMXNet code does not support this method. Need,
349 * to implement this in order to expose nested tables and
350 * other hierarchical data.
351 */
352 throw new NotSupportedException("GetData not supported.");
353 }
354
355 public bool IsDBNull(int i)
356 {
357 return m_resultset.data[m_nPos, i] == DBNull.Value;
358 }
359
360 /*
361 * Implementation specific methods.
362 */
363 private int _cultureAwareCompare(string strA, string strB)
364 {
365 return CultureInfo.CurrentCulture.CompareInfo.Compare(strA, strB, CompareOptions.IgnoreKanaType | CompareOptions.IgnoreWidth | CompareOptions.IgnoreCase);
366 }
367
368 void IDisposable.Dispose()
369 {
370 this.Dispose(true);
371 System.GC.SuppressFinalize(this);
372 }
373
374 private void Dispose(bool disposing)
375 {
376 if (disposing)
377 {
378 try
379 {
380 this.Close();
381 }
382 catch (Exception e)
383 {
384 throw new SystemException("An exception of type " + e.GetType() +
385 " was encountered while closing the BMXNetDataReader.");
386 }
387 }
388 }
389
390 }
391}
Note: See TracBrowser for help on using the repository browser.