Uploaded image for project: 'OSAMES ORM'
  1. OSAMES ORM
  2. ORM-174

Typage pour la lecture avec un IDataReader ado.net

    XMLWordPrintable

    Details

    • Type: Improvement
    • Status: Analyzed
    • Priority: Critical
    • Resolution: Unresolved
    • Affects Version/s: 0.2.0
    • Fix Version/s: 0.3.0
    • Component/s: None
    • Labels:
      None

      Description

      Motivation

      Obtenir la valeur dans une variable typée automatiquement au lieu de devoir convertir/caster une valeur issues d'un data reader ADO.NET, quand on exécute une requête avec l'API de bas niveau. En effet, elle n'est rien de plus qu'un appel à ADO.NET une fois que l'ORM est initialisé et retourne donc les objets de l'API ADO.NET.

      Contexte

      Utilisation de l'API de bas niveau, lecture à travers un DataReader.

      L'idée est de faire un code, pour l'API de bas niveau, qui au lieu d'utiliser le type "dbValueType" (déterminé par le data reader) utilise le type paramètre générique T de la nouvelle méthode Read<T>(). Et fait la même gestion d'erreur que le code listé plus bas qui concerne l'api de haut niveau : vérifie que la colonne existe dans le data reader.

      La liste des types "simples" supportés (en test unitaire) correspond à la liste des méthodes Get*() du data reader ado.net.

      Existant pour l'API de haut niveau :
      Actuellement on lit dans un datareader avec conversion grâce à Convert.ChangeType() dans le code suivant (qui fait de la gestion d'erreur). Le code est interne à l'ORM et est utilisé par l'API de haut niveau :

      Unable to find source-code formatter for language: csharp. Available languages are: actionscript, ada, applescript, bash, c, c#, c++, cpp, css, erlang, go, groovy, haskell, html, java, javascript, js, json, lua, none, nyan, objc, perl, php, python, r, rainbow, ruby, scala, sh, sql, swift, visualbasic, xml, yaml
      try { 
          dataInReaderIndex = reader_.GetOrdinal(columnName); 
      }
      catch (IndexOutOfRangeException ex) { 
          throw new OOrmHandledException(HResultEnum.E_COLUMNDOESNOTEXIST, ex, "column name: '" + columnName + "'"); 
      }
      if (dataInReaderIndex == -1) { 
          throw new OOrmHandledException(HResultEnum.E_COLUMNDOESNOTEXIST, null, "column name: '" + columnName + "'"); 
      }
      object dbValue = reader_[dataInReaderIndex];
       Type dbValueType = reader_.GetFieldType(dataInReaderIndex);
      // sauf si System.DbNull (la propriété est déjà à null)
       if (dbValue is DBNull) return null;
      return Convert.ChangeType(dbValue, dbValueType);
      

      Propositions

      Proposition de nom de la méthode générique à implémenter :
      Read<T>(string columnName_, IDataReader dataReader_)
      avec comme contrainte sur T : type simple (string, int32) donc pas une classe... et nullable.

      Convert.ChangeType() est utilisé pour convertir vers le type T en question.

      Acteurs

      Code client de l'ORM utilisant l'API de bas niveau.

      Exemple de méthode à appeler sur DbManager qui renvoie le data reader. Sur ce data reader on va extraire les données typées en passant le type désiré et le nom de la colonne DB :

      Unable to find source-code formatter for language: csharp. Available languages are: actionscript, ada, applescript, bash, c, c#, c++, cpp, css, erlang, go, groovy, haskell, html, java, javascript, js, json, lua, none, nyan, objc, perl, php, python, r, rainbow, ruby, scala, sh, sql, swift, visualbasic, xml, yaml
      public DbDataReader ExecuteReader(OOrmDbTransactionWrapper transaction_, string cmdText_, object[,] cmdParams_, CommandType cmdType_ = CommandType.Text)
      

      Plan de test

      • Rédiger des tests unitaires de type "select avec l'api de bas niveau"
      • L'idéal serait de tester tous les types simples
      • Pour les exceptions, il serait sympa de gérer avec un message ou voir si le framework .NET gère déjà. Exemple typique : faire un Read<?int> d'une valeur correspondant à un long et non plus un int (Int32.MaxValue + 100). Si le message n'est pas assez clair, indiquer "Value <value> cannot be converted to an int, it's too big.".

      Plan de test supplémentaire - alternatif

      -

      Remarque - Commentaire

       

        Attachments

          Activity

            People

            • Assignee:
              Unassigned
              Reporter:
              babs Barbara Post
            • Watchers:
              2 Start watching this issue

              Dates

              • Created:
                Updated: