tiny_tds 0.4.2 → 0.4.3

Sign up to get free protection for your applications and to get access to all the features.
data/CHANGELOG CHANGED
@@ -1,4 +1,13 @@
1
1
 
2
+ * 0.4.3 *
3
+
4
+ * New Client#active? method to check for good connection. Always use this abstract method.
5
+
6
+ * Better SYBEWRIT "Write to SQL Server failed." error handling. New Client#dead? check.
7
+
8
+ * Azure tested using latest FreeTDS with submitted patch. https://gist.github.com/889190
9
+
10
+
2
11
  * 0.4.2 *
3
12
 
4
13
  * Iconv is a dep only when compiling locally. However, left in the ability to configure it for native gem installation but you must use --enable-iconv before using --with-iconv-dir=/some/dir
data/README.rdoc CHANGED
@@ -30,7 +30,7 @@ Although we search for FreeTDS's libraries and headers, you may have to specify
30
30
 
31
31
  == FreeTDS Compatibility
32
32
 
33
- TinyTDS is developed for FreeTDS 0.82 & 0.83.dev. It is tested with SQL Server 2000, 2005, and 2008 using TDS Version 8.0. We utilize FreeTDS's db-lib client library. We compile against sybdb.h and define MSDBLIB which means that our client enables Microsoft behavior in the db-lib API where it diverges from Sybase's. You do NOT need to compile FreeTDS with the "--enable-msdblib" option for our client to work properly. However, please make sure to compile FreeTDS with libiconv support for encodings to work at their best. Run "tsql -C" in your console and check for "iconv library: yes".
33
+ TinyTDS is developed for FreeTDS 0.82 & 0.83.dev. It is tested with SQL Server 2000, 2005, 2008 and Azure using TDS Version 8.0. We utilize FreeTDS's db-lib client library. We compile against sybdb.h, undefine MSDBLIB and define SYBDBLIB which means that internally we conform to sybase API to db-lib. TinyTDS will work for both Sybase & Miscrosoft SQL Server. You do NOT need to compile FreeTDS with the "--enable-msdblib" option for our client to work properly. However, please make sure to compile FreeTDS with libiconv support for encodings to work at their best. Run "tsql -C" in your console and check for "iconv library: yes".
34
34
 
35
35
 
36
36
 
@@ -64,11 +64,20 @@ Creating a new client takes a hash of options. For valid iconv encoding options,
64
64
  * :login_timeout - Seconds to wait for login. Default to 60 seconds.
65
65
  * :timeout - Seconds to wait for a response to a SQL command. Default 5 seconds.
66
66
  * :encoding - Any valid iconv value like CP1251 or ISO-8859-1. Default UTF-8.
67
+ * :azure - Pass true to signal that you are connecting to azure.
67
68
 
68
- Close and free a clients connection.
69
-
69
+ Use the #active? method to determine if a connection is good. The implementation of this method may change but it should always guarantee that a connection is good. Current it checks for either a closed or dead connection.
70
+
71
+ client.dead? # => false
72
+ client.closed? # => false
73
+ client.active? # => true
74
+ client.execute("SQL TO A DEAD SERVER")
75
+ client.dead? # => true
76
+ client.closed? # => false
77
+ client.active? # => false
70
78
  client.close
71
- client.closed? # => true
79
+ client.closed? # => true
80
+ client.active? # => false
72
81
 
73
82
  Escape strings.
74
83
 
@@ -95,7 +104,7 @@ Calling #each on the result will lazily load each row from the database.
95
104
 
96
105
  A result object has a #fields accessor. It can be called before the result rows are iterated over. Even if no rows are returned, #fields will still return the column names you expected. Any SQL that does not return columned data will always return an empty array for #fields. It is important to remember that if you access the #fields before iterating over the results, the columns will always follow the default query option's :symbolize_keys setting at the client's level and will ignore the query options passed to each.
97
106
 
98
- result = client.execute("USE [tinytds_test]")
107
+ result = client.execute("USE [tinytdstest]")
99
108
  result.fields # => []
100
109
  result.do
101
110
 
@@ -219,9 +228,15 @@ http://github.com/rails-sqlserver/activerecord-sqlserver-adapter/wiki/Using-Tiny
219
228
 
220
229
 
221
230
 
231
+ == Using TinyTDS with Azure
232
+
233
+ TinyTDS is fully tested with the Azure platform. You must set the :azure => true connection option when connecting. This is needed to specify the default in the login packet since Azure has no notion of "USE [database]". You must use the latest FreeTDS 0.83.dev and it must be compiled with OpenSSL.
234
+
235
+
236
+
222
237
  == Development & Testing
223
238
 
224
- We use bundler for development. Simply run "bundle install" then "rake" to build the gem and run the unit tests. The tests assume you have created a database named "tinytds_test" accessible by a database owner named "tinytds". Before running the test rake task, you may need to define a pair of environment variables that help the client connect to your specific FreeTDS database server name and which schema (2000, 2005 or 2008) to use. For example:
239
+ We use bundler for development. Simply run "bundle install" then "rake" to build the gem and run the unit tests. The tests assume you have created a database named "tinytdstest" accessible by a database owner named "tinytds". Before running the test rake task, you may need to define a pair of environment variables that help the client connect to your specific FreeTDS database server name and which schema (2000, 2005, 2008 or azure) to use. For example:
225
240
 
226
241
  $ rake TINYTDS_UNIT_DATASERVER=mydbserver TINYTDS_SCHEMA=sqlserver_2008
227
242
 
@@ -244,7 +259,7 @@ Current to do list.
244
259
 
245
260
  == About Me
246
261
 
247
- My name is Ken Collins and to avoid confusion – I have no love for Microsoft nor do I work on Windows or have I ever owned a PC, just so we know :) – I currently maintain the SQL Server adapter for ActiveRecord and wrote this library as my first cut into learning ruby C extensions. Hopefully it will help promote the power of ruby and the rails framework to those that have not yet discovered it. My blog is http://metaskills.net and I can be found on twitter as @metaskills. Enjoy!
262
+ My name is Ken Collins and I currently maintain the SQL Server adapter for ActiveRecord and wrote this library as my first cut into learning ruby C extensions. Hopefully it will help promote the power of ruby and the rails framework to those that have not yet discovered it. My blog is http://metaskills.net and I can be found on twitter as @metaskills. Enjoy!
248
263
 
249
264
 
250
265
 
@@ -4,7 +4,7 @@
4
4
 
5
5
  VALUE cTinyTdsClient;
6
6
  extern VALUE mTinyTds, cTinyTdsError;
7
- static ID sym_username, sym_password, sym_dataserver, sym_database, sym_appname, sym_tds_version, sym_login_timeout, sym_timeout, sym_encoding;
7
+ static ID sym_username, sym_password, sym_dataserver, sym_database, sym_appname, sym_tds_version, sym_login_timeout, sym_timeout, sym_encoding, sym_azure;
8
8
  static ID intern_source_eql, intern_severity_eql, intern_db_error_number_eql, intern_os_error_number_eql;
9
9
  static ID intern_new, intern_dup, intern_transpose_iconv_encoding, intern_local_offset, intern_gsub;
10
10
  VALUE opt_escape_regex, opt_escape_dblquote;
@@ -66,6 +66,8 @@ int tinytds_err_handler(DBPROCESS *dbproc, int severity, int dberr, int oserr, c
66
66
  case SYBESEOF: {
67
67
  if (userdata && userdata->timing_out)
68
68
  return_value = INT_TIMEOUT;
69
+ return INT_CANCEL;
70
+ break;
69
71
  }
70
72
  case SYBETIME: {
71
73
  if (userdata) {
@@ -78,6 +80,12 @@ int tinytds_err_handler(DBPROCESS *dbproc, int severity, int dberr, int oserr, c
78
80
  cancel = 1;
79
81
  break;
80
82
  }
83
+ case SYBEWRIT: {
84
+ if (userdata && (userdata->dbsqlok_sent || userdata->dbcancel_sent))
85
+ return INT_CANCEL;
86
+ cancel = 1;
87
+ break;
88
+ }
81
89
  case SYBEREAD:
82
90
  cancel = 1;
83
91
  break;
@@ -150,6 +158,11 @@ static VALUE rb_tinytds_close(VALUE self) {
150
158
  return Qtrue;
151
159
  }
152
160
 
161
+ static VALUE rb_tinytds_dead(VALUE self) {
162
+ GET_CLIENT_WRAPPER(self);
163
+ return dbdead(cwrap->client) ? Qtrue : Qfalse;
164
+ }
165
+
153
166
  static VALUE rb_tinytds_closed(VALUE self) {
154
167
  GET_CLIENT_WRAPPER(self);
155
168
  return (cwrap->closed || cwrap->userdata->closed) ? Qtrue : Qfalse;
@@ -224,7 +237,7 @@ static VALUE rb_tinytds_return_code(VALUE self) {
224
237
 
225
238
  static VALUE rb_tinytds_connect(VALUE self, VALUE opts) {
226
239
  /* Parsing options hash to local vars. */
227
- VALUE user, pass, dataserver, database, app, version, ltimeout, timeout, charset;
240
+ VALUE user, pass, dataserver, database, app, version, ltimeout, timeout, charset, azure;
228
241
  user = rb_hash_aref(opts, sym_username);
229
242
  pass = rb_hash_aref(opts, sym_password);
230
243
  dataserver = rb_hash_aref(opts, sym_dataserver);
@@ -234,6 +247,7 @@ static VALUE rb_tinytds_connect(VALUE self, VALUE opts) {
234
247
  ltimeout = rb_hash_aref(opts, sym_login_timeout);
235
248
  timeout = rb_hash_aref(opts, sym_timeout);
236
249
  charset = rb_hash_aref(opts, sym_encoding);
250
+ azure = rb_hash_aref(opts, sym_azure);
237
251
  /* Dealing with options. */
238
252
  if (dbinit() == FAIL) {
239
253
  rb_raise(cTinyTdsError, "failed dbinit() function");
@@ -257,14 +271,22 @@ static VALUE rb_tinytds_connect(VALUE self, VALUE opts) {
257
271
  dbsettime(NUM2INT(timeout));
258
272
  if (!NIL_P(charset))
259
273
  DBSETLCHARSET(cwrap->login, StringValuePtr(charset));
274
+ if (!NIL_P(database) && (azure == Qtrue)) {
275
+ #ifdef DBSETLDBNAME
276
+ DBSETLDBNAME(cwrap->login, StringValuePtr(database));
277
+ #else
278
+ rb_warn("TinyTds: Azure connections not supported in this version of FreeTDS.\n");
279
+ #endif
280
+ }
260
281
  cwrap->client = dbopen(cwrap->login, StringValuePtr(dataserver));
261
282
  if (cwrap->client) {
262
283
  cwrap->closed = 0;
263
284
  cwrap->charset = charset;
264
285
  dbsetuserdata(cwrap->client, (BYTE*)cwrap->userdata);
265
286
  cwrap->userdata->closed = 0;
266
- if (!NIL_P(database))
287
+ if (!NIL_P(database) && (azure != Qtrue)) {
267
288
  dbuse(cwrap->client, StringValuePtr(database));
289
+ }
268
290
  #ifdef HAVE_RUBY_ENCODING_H
269
291
  VALUE transposed_encoding = rb_funcall(cTinyTdsClient, intern_transpose_iconv_encoding, 1, charset);
270
292
  cwrap->encoding = rb_enc_find(StringValuePtr(transposed_encoding));
@@ -284,6 +306,7 @@ void init_tinytds_client() {
284
306
  rb_define_method(cTinyTdsClient, "close", rb_tinytds_close, 0);
285
307
  rb_define_method(cTinyTdsClient, "closed?", rb_tinytds_closed, 0);
286
308
  rb_define_method(cTinyTdsClient, "canceled?", rb_tinytds_canceled, 0);
309
+ rb_define_method(cTinyTdsClient, "dead?", rb_tinytds_dead, 0);
287
310
  rb_define_method(cTinyTdsClient, "sqlsent?", rb_tinytds_sqlsent, 0);
288
311
  rb_define_method(cTinyTdsClient, "execute", rb_tinytds_execute, 1);
289
312
  rb_define_method(cTinyTdsClient, "charset", rb_tinytds_charset, 0);
@@ -302,6 +325,7 @@ void init_tinytds_client() {
302
325
  sym_login_timeout = ID2SYM(rb_intern("login_timeout"));
303
326
  sym_timeout = ID2SYM(rb_intern("timeout"));
304
327
  sym_encoding = ID2SYM(rb_intern("encoding"));
328
+ sym_azure = ID2SYM(rb_intern("azure"));
305
329
  /* Intern TinyTds::Error Accessors */
306
330
  intern_source_eql = rb_intern("source=");
307
331
  intern_severity_eql = rb_intern("severity=");
data/lib/tiny_tds.rb CHANGED
@@ -14,5 +14,5 @@ require 'tiny_tds/tiny_tds'
14
14
  #
15
15
  # Tiny Ruby Wrapper For FreeTDS Using DB-Library
16
16
  module TinyTds
17
- VERSION = '0.4.2'
17
+ VERSION = '0.4.3'
18
18
  end
@@ -62,6 +62,9 @@ module TinyTds
62
62
  "#{info[:name]} - #{info[:description]}" if info
63
63
  end
64
64
 
65
+ def active?
66
+ !closed? && !dead?
67
+ end
65
68
 
66
69
  private
67
70
 
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: tiny_tds
3
3
  version: !ruby/object:Gem::Version
4
- hash: 11
4
+ hash: 9
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
8
  - 4
9
- - 2
10
- version: 0.4.2
9
+ - 3
10
+ version: 0.4.3
11
11
  platform: ruby
12
12
  authors:
13
13
  - Ken Collins
@@ -16,7 +16,7 @@ autorequire:
16
16
  bindir: bin
17
17
  cert_chain: []
18
18
 
19
- date: 2011-03-24 00:00:00 -04:00
19
+ date: 2011-04-01 00:00:00 -04:00
20
20
  default_executable:
21
21
  dependencies: []
22
22