[Haskell-cafe] re: Oracle stored procedures

2010-09-10 Thread Leonel Fonseca
Hi, Peter

I did and uploaded some examples regarding Oracle and Takusen and the
intended approach you would employ.

Example 01: Create table and some tuples.
http://hpaste.org/fastcgi/hpaste.fcgi/view?id=29883#a29883

Example 02: Create a package with procedures to mantain the table.
http://hpaste.org/fastcgi/hpaste.fcgi/view?id=29884#a29884

Example 03: Optional. See how it works in Oracle sqlplus.
http://hpaste.org/fastcgi/hpaste.fcgi/view?id=29885#a29885

Example 04: The Takusen-Haskell program. It follows the scheme of example #03.
http://hpaste.org/fastcgi/hpaste.fcgi/view?id=29894#a29894

Some comments on the topic:

This approach has limitations. Takusen (if not use in conjunction with
Template Haskell) will be bound up to iteratees of eight values. I
(and I'm pretty sure some other people) have successfully used
Template Haskell to overcome this limitation.
(I've been working in removing some boilerplate).

The all stored procedure approach is not a limitation as you can see
from example #04, unless these procedures return values these types:
Record Of , complex objects (PL/SQL tables, objects, etc),
Boolean.

Oracle has several programatic interfaces, some that I remember: JDBC,
ODBC, OCI, OCCI and those for Windows .NET.

Takusen is a wrapper for OCI (Oracle Call Interface) which seems to me
pretty low level. Yet, I don't know if you can specify just the name
of the procedure.

Please note that if there is a procedure named close_accounts, by
writing "begin close_accounts; end;" you are not wrapping it in a SQL
statement. It actually is an anonymous PL/SQL block and it is needed
in that form to be processed by the server.

Oracle offers for Windows .NET: ODT (Oracle Developer Tools for Visual
Studio), ODP (Oracle Data Provider) and ODE (Oracle Database
Extensions). I did test (and taste) a bit of .NET tools with F#. It
was nice. Maybe you wish to try hs-dotnet with these.

A final remark, I have used Takusen both on Windows and Linux. The
given example was developed and tested actually on Windows.


Regards,

Leonel Fonseca.
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] re: Oracle stored procedures

2010-09-08 Thread Leonel Fonseca
Hi Peter,

Yes, from Takusen you can call Oracle stored procedures, functions,
packaged stored procedures or functions, or execute an arbitrary
pl/sql block.

In the Takusen software release there is a directory called
"Database\Oracle\Test". There,  Enumerator.lhs, among other code has
these helpers you may want to use:


>wrapPLSQLFunc funcname parms =
>  let sqltext = "begin " ++ (head args) ++ " := " ++ funcname
> ++ "(" ++ placeholders ++ "); end;"
>  placeholders = concat (intersperse "," (tail args))
>  args = take (length parms) (map (\n -> ":x" ++ show n) [1..])
>  in  cmdbind sqltext parms

>wrapPLSQLProc procname parms =
>  let sqltext = "begin " ++ procname
> ++ "(" ++ placeholders ++ "); end;"
>  placeholders = concat (intersperse "," args)
>  args = take (length parms) (map (\n -> ":x" ++ show n) [1..])
>  in  cmdbind sqltext parms


Please, be aware of the following points:

1) If the pl/sql code doesn't need parameters and has no results, you
can use "execDDL". (execDML returns a counter of affected rows).
2) If the procedure/function receives parameter, you'll need to use
"cmdbind" (or similar to "cmdbind") to pass the parameters.
3) If the pl/sql code returns values, you have this options:
    3.a) The returned value is a reference (cursor): Takusen supports
this very fine. Use "doQuery" or similar.
    3.b) The return value is an scalar value: You can collect the
result with an iteratee, even if it is a single value.
    3.c) The return value is a complex oracle object: As of Takusen
0.8.5 there is no support for table of records of ...
3.d) The return value is Boolean. You'll get an error.

Little examples:

For case #1:

> -- Example 1.a:  We set nls_language to  american english.
> set_NlsLang_Eng :: DBM mark Session ()
> set_NlsLang_Eng =  execDDL $ sql
>  "alter session set nls_language='AMERICAN'"

> -- Example #1.b: Now we set session language parameter to spanish.
> set_NlsLang_Esp :: DBM mark Session ()
> set_NlsLang_Esp =  execDDL $ sql
>  "alter session set nls_language='LATIN AMERICAN SPANISH'"

For case #2:

> -- Example 2.a: We use database string "concat" function
>concat'  ::  String -> String -> DBM mark Session String
>concat' a b  =   do
>   let ite :: Monad m => String -> IterAct m String
>   ite v _ = return $ Left v
>   sqlcmd = wrapPLSQLFunc "concat"
>  [bindP $ Out (""::String), bindP a, bindP b]
>   doQuery sqlcmd ite undefined
>
> -- later on the program, you'd have...
> some_string <- concat' "a" "b"

For case #3:

> -- Case 3.b: We collect a single scalar value.
> qNlsLang   ::  DBM mark Session [String]
> qNlsLang   =   doQuery s ite []
>  where
>  s   =   "select value from nls_session_parameters \
>  \ where parameter = 'NLS_LANGUAGE'"
>  ite ::  (Monad m) => String ->  IterAct m [String]
>  ite a acc = result' ( a:acc )

> mostrar_NlsLang  ::  DBM mark Session ()
> mostrar_NlsLang  =   qNlsLang >>= liftIO . print . head

> -- Another example for Case 3.b
> -- This time we don't use a list to accumulate results.
> s1 =  sql "select systimestamp from dual"
>
> sysTSasCTQ   ::  DBM mark Session CalendarTime
> sysTSasCTQ=  do
>
>let ite :: (Monad m) => CalendarTime -> IterAct m CalendarTime
>ite x  _  =  result' x
>
>t <-  liftIO ( getClockTime >>= toCalendarTime)
>doQuery s1 ite t


--

Leonel Fonseca.
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] help me evangelize haskell

2010-09-04 Thread Leonel Fonseca
Michael:

Hi. I take the risk to mention some facts you might already be working on.

I speculate on three perceptions in the mind of decision makers
related to the adoption of a new language in a shop.
This perceptions can be modified in stages.

First Stage: Awareness. Why programming in that language matters?
Once you can justified this, advance to the following stage.

Haskell is nice, quick to develop, brings tools to make abstractions
at any level and has tools and libraries.
And community support is really awesome!

If you invest more in learning, you can strive to use it  as formal
programming method and earn safety guarantees.

Please, see elsewere for success stories that help you to motivate and
encourage management to test the new alternative.



Second Stage: Small term engagment.

Why your shop should do little investment in trying a new language in
a small but representative project?

Here you can make two arguments to gain support in this stage:

   2.A) The shortcommings of the current tools/languages.

   2.B) Small concept programs of how your current language/tool would
fail where the new one would success.
   You can gain credibility by showing how your new tool could
be short on some aspect that it's well mastered in the old one.
   (i.e. be impartial).

   Someone has already pointed how fragile interpreted programs are.

In this stage you must gain both decision makers and peers recognition
of the problem the shop is facing with the current language versus the
improvements of using the new language.

A project must be acomplished and reviewed, so a decision can be made
over the facts of costs and benefits.


Third Stage: Adoption.

Is it really better to adopt a new language?

At this point you have evidence of possible benefits and costs. And a
decision is made.

Among other costs, please take in account that embracing any new
language in a shop will require formalised (funded, time alloted to,
machines, any other resource) learning  and coaching activities.

Haskell has long learning curve. And you must consider this cost of
being less productive than in your current language.
There's too the risk of hitting walls in a tight-schedule situation.
You can lower this risk of failure if you arrange to have a mentor
(master) who can lead, provide hints to co-workers, discuss approaches
and solve hard issues whenever they appear.

Counter-arguments that you must deal with:

c1) Why not...
 Erlang?
 F#?  See Jon Harrop's claims.
 Scala or Clojure?

c2) Performance predictability.

c3) On the fly script generation and execution.

c4) Will your co-workers be happy of embracing a new paradigm of
solving problems?
  Will type signatures appear as pain or a valuable thing to them?


--
Leonel Fonseca.
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Merge hsql and HDBC -- there can only be one!

2010-07-08 Thread Leonel Fonseca
On the subject of bridging relational persistence and fucntional
programming I wish to communicate on what I'm working on (Tránsito
Abierto Library) (or Open Transit):

1) Whole objective: To disminish to gap between functional and
relational paradigms.

2) Specific objetive: Illustrate and explore the gap.

3) Narrow focus: I'm using Takusen and Oracle and Haskell (á la GHC).
  And Template Haskell (TH).

4) Hypothesis: There'll be always a gap because you're using distinct
nature beasts, but you
a bit more of convinience would yield great improvements.

4.1) Another thought on this is: A mapping always needs to be
specified between data shapes (types/representations).

5) Findings/Achievements(?):

5.1) Generation of Haskell types and iterator code given the shape of
relational table.
 This is not very useful itself. Because of (4.1), using SQL
is an effective way to: (1) convey such mapping and (2) specify
queries that involve more than one table.

5.2) Given a sql query text, use the facilities on Oracle database to
describe the query.
With such description, use Template Haskell to generate Haskell types
and iterator code. Let us call Geco to this generated code that is
built by means of an AST.

5.3) As 5.2 (spliced Geco) but saving the Geco AST. What for?
   It turns out that later, during program execution you can
regenerate a fresh AST code
  and compare it to Geco AST. If there's a difference it means
your database environment is changed and it is likely that your code
is no longer safe.
   The idea here, your program reacts to the enviroment detecting
if its unsafe to run.

5.4) Takusen covers many database datatypes but not all.

5.5) I was about to automate pl/sql bindings using a inspired Takusen
wrapper found on the enumerator tests directory . It follows scheme
5.2.  But it is uncomplete.

5.6) Takusen is limited to iterators up to 8 fields. By using TH,
easily you can have any number of columns in your query.

5.7) I wrote a serialiser library on the DB side and a deserialiser
library on Haskell side. The idea it's to push *any* pl/sql result
onto a string and recover it on the Haskell side. Needs schemes 5.2
and 5.5 to work. Status: Not working.

6) I believe intelligent schema generation is possible following the
scheme above. What you would get is a whole module that would enforce
constraints (cardinality, restrictions, etc).

7) I haven't try the way Haskell -> DB. Neither the storing of
functional values as it was done before in Persistent Haskell and
others.


Cheers,

-- 

Leonel Fonseca.
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] Fun Facts: A lazy bill

2010-06-17 Thread Leonel Fonseca
I share this just for the sake of fun.

In Costa Rica (Central America) a new series of bills are to be
emitted and to celebrate bio-diversity some animal drawings are going
to be used. Look at the new 10.000 colones bill:

http://www.bccr.fi.cr/WebPages/PaginaInicio/NuevaFamilia/10.html

Choose "reverso" in order to see the other side.
-- 

Leonel Fonseca.
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Would it be evil to add "deriving Typeable" to newtype Q?

2010-05-06 Thread Leonel Fonseca
Hey, the hint provided by Ben worked like a charm.

I've also tried Ivan suggestions both on my windows and linux installations.
DrIFT-cabalized couldn't install at all at windows since I don't use MinGW.
So, I ghc'ed --make  DrIFT.

Both, windows and linux, refused to complete work with this error:
drift: can't find module Control/Monad

Thank you.

> {-# LANGUAGE DeriveDataTypeable, StandaloneDeriving #-}
>
> import Data.Typeable
> import Language.Haskell.TH
>
> deriving instance Typeable1 Q



-- 

Leonel Fonseca.
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] Would it be evil to add "deriving Typeable" to newtype Q?

2010-05-05 Thread Leonel Fonseca
Hi everybody,

Is it reasonable to add "deriving Typeable" to newtype Q?

In case you wonder why I want to do that, it is because I've constructed a Q
[Dec] inside a monad, I want to extract  it from the monad (via runIO) and
the monad has constraint "Typeable" over this parameter.

I've also tried to write the Typeable instance in my own module (not
Language.Haskell.TH.Syntax). But I've got no luck since the Q type
constructor is exported but the data constructor is not.

Thanks.
--
Leonel Fonseca.
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe