Author: wyoung
Date: Sat Nov  8 11:00:45 2008
New Revision: 2401

URL: http://svn.gna.org/viewcvs/mysqlpp?rev=2401&view=rev
Log:
Row::at() (and therefore Row::operator[](int)) throws new BadIndex
exception on out of range indices now, unconditionally.  Updated docs to
reflect this, and added a test to ensure it happens, and to test related
exception throwing behavior.

Modified:
    trunk/Wishlist
    trunk/doc/userman/tutorial.dbx
    trunk/lib/exceptions.h
    trunk/lib/row.cpp
    trunk/lib/row.h
    trunk/mysql++.bkl

Modified: trunk/Wishlist
URL: 
http://svn.gna.org/viewcvs/mysqlpp/trunk/Wishlist?rev=2401&r1=2400&r2=2401&view=diff
==============================================================================
--- trunk/Wishlist (original)
+++ trunk/Wishlist Sat Nov  8 11:00:45 2008
@@ -3,14 +3,6 @@
 
 Any Version
 -----------
-    o Configure script should try to get MySQL C API directories
-      from mysql_config.
-
-    o If pkg-config is available, register ourselves with it using
-      information discovered by configure.  Also, write out a
-      mysql++-config script, which either wraps pkg-config or
-      reinvents it, poorly, for systems that don't have it.
-
     o Any time you must hand-roll some SQL code in your program,
       consider whether it could be generalized to a widely-useful
       API feature.
@@ -18,10 +10,8 @@
 
 v3.0.7
 ------
-    o Sort out the differences in Row subscripting: some rely on
-      vector::at(), some on vector::operator[], some do their
-      own index checking, some rely on at(), some throw MySQL++
-      exceptions, some cause the underlying STL to throw...
+       o Throw BadIndex from all operator[]'s and at() methods on bad
+         indices, and add them to test/array_index.cpp.
 
 
 v3.1 Tentative Plan
@@ -117,6 +107,14 @@
 
       http://lists.mysql.com/plusplus/7999
 
+    o Configure script should try to get MySQL C API directories
+      from mysql_config.
+
+    o If pkg-config is available, register ourselves with it using
+      information discovered by configure.  Also, write out a
+      mysql++-config script, which either wraps pkg-config or
+      reinvents it, poorly, for systems that don't have it.
+
 
 v4.0 or Later
 -------------

Modified: trunk/doc/userman/tutorial.dbx
URL: 
http://svn.gna.org/viewcvs/mysqlpp/trunk/doc/userman/tutorial.dbx?rev=2401&r1=2400&r2=2401&view=diff
==============================================================================
--- trunk/doc/userman/tutorial.dbx (original)
+++ trunk/doc/userman/tutorial.dbx Sat Nov  8 11:00:45 2008
@@ -225,21 +225,21 @@
     or <classname>std::exception</classname> to act as a
     &ldquo;catch-all&rdquo; for unexpected exceptions.</para>
 
-    <para>It&rsquo;s possible to suppress most MySQL++ exceptions.
-    MySQL++ still signals errors in this state, but it&rsquo;s done by
-    returning an error code or setting an error flag instead of with
-    exceptions. Classes that support this feature derive from the <ulink
-    type="classref" url="OptionalExceptions"/> interface. When an
-    <classname>OptionalExceptions</classname> derivative creates another
-    object that also derives from this interface, it passes on its
-    exception flag. Since everything flows from the <ulink
-    type="classref" url="Connection"/> object, disabling exceptions on
-    it at the start of the program disables all optional exceptions.
-    This is why passing <symbol>false</symbol> for the
+    <para>When exceptions are suppressed, MySQL++ signals errors
+    by returning either an error code or an object that tests
+    as false, or by setting an error flag on the object. Classes
+    that allow you to suppress exceptions derive from the <ulink
+    type="classref" url="OptionalExceptions"/> interface. When
+    an <classname>OptionalExceptions</classname> derivative
+    creates another object that also derives from this interface,
+    it passes on its exception flag. Since everything flows from
+    the <ulink type="classref" url="Connection"/> object, disabling
+    exceptions on it at the start of the program disables all optional
+    exceptions. This is why passing <symbol>false</symbol> for the
     <classname>Connection</classname> constructor&rsquo;s &ldquo;throw
-    exceptions&rdquo; parameter suppresses all optional exceptions in
-    the <filename>simple[1-3]</filename> examples. It keeps them, well,
-    simple.</para>
+    exceptions&rdquo; parameter suppresses all optional exceptions
+    in the <filename>simple[1-3]</filename> examples. It keeps them,
+    well, simple.</para>
 
     <para>This exception suppression mechanism is quite granular.
     It&rsquo;s possible to leave exceptions enabled most of the time,
@@ -279,15 +279,19 @@
     <para>MySQL++ throws some exceptions unconditionally:</para>
 
     <itemizedlist>
-      <listitem><para>The largest set of non-optional exceptions are
-      those from the Standard C++ Library. For instance, if your code
-      said &ldquo;<varname>row[21]</varname>&rdquo; on a row containing
-      only 5 fields, the <classname>std::vector</classname> underlying
-      the row object will throw an exception. (It will, that is, if it
-      conforms to the standard.) You might consider wrapping your
-      program&rsquo;s main loop in a try block catching
-      <classname>std::exception</classname>s, just in case you trigger
-      one of these exceptions.</para></listitem>
+      <listitem><para>MySQL++ checks array indices,
+      always.  For instance, if your code said
+      &ldquo;<varname>row[21]</varname>&rdquo; on a
+      row containing only 5 fields, you&rsquo;d get a
+      <classname>BadIndex</classname> exception. If you
+      say &ldquo;<varname>row["fred"]</varname>&rdquo;
+      on a row without a &ldquo;fred&rdquo; field, you get
+      a <classname>BadFieldName</classname> exception. In
+      the past, MySQL++ delegated some of its index checking
+      to the STL containers underpinning it, so you could get
+      <classname>std::range_error</classname> instead. As of MySQL++
+      v3.0.7, this should no longer happen, but there may be instances
+      where it still does.</para></listitem>
 
       <listitem><para><ulink type="classref" url="String"/> will always
       throw <ulink type="classref" url="BadConversion"/> when you ask it

Modified: trunk/lib/exceptions.h
URL: 
http://svn.gna.org/viewcvs/mysqlpp/trunk/lib/exceptions.h?rev=2401&r1=2400&r2=2401&view=diff
==============================================================================
--- trunk/lib/exceptions.h (original)
+++ trunk/lib/exceptions.h Sat Nov  8 11:00:45 2008
@@ -35,6 +35,7 @@
 
 #include <exception>
 #include <string>
+#include <sstream>
 
 namespace mysqlpp {
 
@@ -172,6 +173,30 @@
 };
 
 
+/// \brief Exception thrown when an object with operator [] or an
+/// at() method gets called with a bad index.
+
+class MYSQLPP_EXPORT BadIndex : public Exception
+{
+public:
+       /// \brief Create exception object
+       ///
+       /// \param bad_index type of object bad index tried on
+       /// \param bad_index index value the container didn't like
+       explicit BadIndex(const char* what, int bad_index) :
+       Exception()
+       {
+               std::ostringstream outs;
+               outs << "Index " << bad_index << " on " << what <<
+                               " out of range";
+               what_ = outs.str();
+       }
+
+       /// \brief Destroy exception
+       ~BadIndex() throw() { }
+};
+
+
 /// \brief Exception thrown when you pass an unrecognized option to
 /// Connection::set_option().
 

Modified: trunk/lib/row.cpp
URL: 
http://svn.gna.org/viewcvs/mysqlpp/trunk/lib/row.cpp?rev=2401&r1=2400&r2=2401&view=diff
==============================================================================
--- trunk/lib/row.cpp (original)
+++ trunk/lib/row.cpp Sat Nov  8 11:00:45 2008
@@ -62,6 +62,18 @@
 }
 
 
+Row::const_reference
+Row::at(size_type i) const
+{
+       if (i >= 0 && i < size()) {
+               return data_[i];
+       }
+       else {
+               throw BadIndex("Row", i);
+       }
+}
+
+
 equal_list_ba<FieldNames, Row, quote_type0>
 Row::equal_list(const char* d, const char* e) const
 {

Modified: trunk/lib/row.h
URL: 
http://svn.gna.org/viewcvs/mysqlpp/trunk/lib/row.h?rev=2401&r1=2400&r2=2401&view=diff
==============================================================================
--- trunk/lib/row.h (original)
+++ trunk/lib/row.h Sat Nov  8 11:00:45 2008
@@ -144,7 +144,7 @@
        ///
        /// If the index value is bad, the underlying std::vector is
        /// supposed to throw an exception, according to the Standard.
-       const_reference at(size_type i) const { return data_.at(i); }
+       const_reference at(size_type i) const;
 
        /// \brief Get a reference to the last element of the vector
        const_reference back() const { return data_.back(); }

Modified: trunk/mysql++.bkl
URL: 
http://svn.gna.org/viewcvs/mysqlpp/trunk/mysql%2B%2B.bkl?rev=2401&r1=2400&r2=2401&view=diff
==============================================================================
--- trunk/mysql++.bkl (original)
+++ trunk/mysql++.bkl Sat Nov  8 11:00:45 2008
@@ -195,6 +195,9 @@
 
     <!-- Define library testing programs' output targets, if enabled -->
     <if cond="BUILDTEST=='yes'">
+        <exe id="test_array_index" template="programs">
+            <sources>test/array_index.cpp</sources>
+        </exe>
         <exe id="test_cpool" template="programs">
             <sources>test/cpool.cpp</sources>
         </exe>


_______________________________________________
Mysqlpp-commits mailing list
[email protected]
https://mail.gna.org/listinfo/mysqlpp-commits

Reply via email to