
How do people who like unit testing / property testing deal with export lists? I often find that I do want an export list to reduce clutter in the finished code, but for testing I'd like to expose everything in a module. Is there a nice way to deal with this (using the C pre-processor would not qualify as "nice" ;-)? Maybe there's a switch that causes GHC to simply ignore the export list of a module and export everything? /M -- Magnus Therning (OpenPGP: 0xAB4DFBA4) magnus@therning.org Jabber: magnus@therning.org http://therning.org/magnus identi.ca|twitter: magthe

On 24 February 2010 20:17, Magnus Therning
I often find that I do want an export list to reduce clutter in the finished code, but for testing I'd like to expose everything in a module. Is there a nice way to deal with this (using the C pre-processor would not qualify as "nice" ;-)? Maybe there's a switch that causes GHC to simply ignore the export list of a module and export everything?
If you start a function name with an underscore, it is "implicitly exported" by GHC (I can't find the actual documentation page at the moment however). Whilst it may not appear in the export list, you are still able to call it from outside the module. This will, however, result in "ugly" function names as well as possibly still have those items appear in the haddock documentation... -- Ivan Lazar Miljenovic Ivan.Miljenovic@gmail.com IvanMiljenovic.wordpress.com Joan Crawford - "I, Joan Crawford, I believe in the dollar. Everything I earn, I spend." - http://www.brainyquote.com/quotes/authors/j/joan_crawford.html

On Wed, Feb 24, 2010 at 3:10 PM, Ivan Miljenovic
On 24 February 2010 20:17, Magnus Therning
wrote: I often find that I do want an export list to reduce clutter in the finished code, but for testing I'd like to expose everything in a module. Is there a nice way to deal with this (using the C pre-processor would not qualify as "nice" ;-)? Maybe there's a switch that causes GHC to simply ignore the export list of a module and export everything?
If you start a function name with an underscore, it is "implicitly exported" by GHC (I can't find the actual documentation page at the moment however). Whilst it may not appear in the export list, you are still able to call it from outside the module.
This will, however, result in "ugly" function names as well as possibly still have those items appear in the haddock documentation...
Wow, I'd never heard of that feature. I currently export everything because under development it's too much hassle to maintain export lists. However when modules stabilize I think export lists are a good idea because then GHC can warn about unused functions and and hopefully eliminate internal bindings if they are all inlined. However, testing individual functions is much easier to understand and leads to shorter and less brittle tests, with clearer failures. So when the time comes I'll probably use #ifdef. That way I can run presumably ghci with -DTESTING as well and bypass the other annoying thing about export lists, which is that you have to get ghci to byte compile to see the internal symbols. It's not that much work to add #ifdef to each export list especially compared to the work of writing it in the first place, but it would still be nicer if there were a compiler flag that did this explicitly. The underscore thing seems sub-optimal to me because it doesn't help you with unused functions or dead code elimination.

On 25 February 2010 10:21, Evan Laforge
On Wed, Feb 24, 2010 at 3:10 PM, Ivan Miljenovic
wrote: If you start a function name with an underscore, it is "implicitly exported" by GHC (I can't find the actual documentation page at the moment however). Whilst it may not appear in the export list, you are still able to call it from outside the module.
Wow, I'd never heard of that feature.
Neither had I, until Curt Sampson asked me to support it in SourceGraph. Anyway, I've tracked down the documentation page: http://www.haskell.org/ghc/docs/latest/html/users_guide/options-sanity.html . It's not listed explicitly anywhere; different items have different documentation regarding it throughout the page. -- Ivan Lazar Miljenovic Ivan.Miljenovic@gmail.com IvanMiljenovic.wordpress.com Samuel Goldwyn - "I don't think anyone should write their autobiography until after they're dead." - http://www.brainyquote.com/quotes/authors/s/samuel_goldwyn.html

ivan.miljenovic:
On 24 February 2010 20:17, Magnus Therning
wrote: I often find that I do want an export list to reduce clutter in the finished code, but for testing I'd like to expose everything in a module. Is there a nice way to deal with this (using the C pre-processor would not qualify as "nice" ;-)? Maybe there's a switch that causes GHC to simply ignore the export list of a module and export everything?
If you start a function name with an underscore, it is "implicitly exported" by GHC (I can't find the actual documentation page at the moment however). Whilst it may not appear in the export list, you are still able to call it from outside the module.
Seriously?? Doesn't that break the module system? So this should work? Z.hs module Z () where _secret = "10" M.hs import Z main = print _secret $ runhaskell M.hs M.hs:3:14: Not in scope: `_secret'

On 25 February 2010 11:24, Don Stewart
Seriously?? Doesn't that break the module system?
Maybe I misunderstood it; all I know is that Curt Sampson says he uses this kind of stuff for testing purposes by not having to export functions. See the -fwarn-unused-binds section at http://www.haskell.org/ghc/docs/latest/html/users_guide/options-sanity.html . -- Ivan Lazar Miljenovic Ivan.Miljenovic@gmail.com IvanMiljenovic.wordpress.com Charles de Gaulle - "The better I get to know men, the more I find myself loving dogs." - http://www.brainyquote.com/quotes/authors/c/charles_de_gaulle.html

On Feb 24, 2010, at 20:51 , Ivan Miljenovic wrote:
On 25 February 2010 11:24, Don Stewart
wrote: Seriously?? Doesn't that break the module system?
Maybe I misunderstood it; all I know is that Curt Sampson says he uses this kind of stuff for testing purposes by not having to export functions.
See the -fwarn-unused-binds section at http://www.haskell.org/ghc/docs/latest/html/users_guide/options-sanity.html
As I read that, the leading underscore doesn't export anything; it just suppresses any "unused" warning for the symbol (which is consistent with the other uses of leading underscore in warnings; it's also consistent with binding to _ to throw a result away). -- brandon s. allbery [solaris,freebsd,perl,pugs,haskell] allbery@kf8nh.com system administrator [openafs,heimdal,too many hats] allbery@ece.cmu.edu electrical and computer engineering, carnegie mellon university KF8NH

On 27 February 2010 04:44, Brandon S. Allbery KF8NH
As I read that, the leading underscore doesn't export anything; it just suppresses any "unused" warning for the symbol (which is consistent with the other uses of leading underscore in warnings; it's also consistent with binding to _ to throw a result away).
OK, I _must_ have misunderstood what Curt was saying :s -- Ivan Lazar Miljenovic Ivan.Miljenovic@gmail.com IvanMiljenovic.wordpress.com

What I usually do in such a case is create a separate internal
module. The internal module exports everything. Then create a
module which defines the public interface. This module simple
reexports symbols from the internal module. Now you can create a
Test module which has full access to all internal symbols.
module Internal where
a = 1
b = 2
secret = 42
module Public ( a, b ) where
import Internal ( a, b )
module Test where
import Internal ( secret )
test = assert $ isUltimateAnswer secret
On Wed, Feb 24, 2010 at 10:17 AM, Magnus Therning
How do people who like unit testing / property testing deal with export lists?
I often find that I do want an export list to reduce clutter in the finished code, but for testing I'd like to expose everything in a module. Is there a nice way to deal with this (using the C pre-processor would not qualify as "nice" ;-)? Maybe there's a switch that causes GHC to simply ignore the export list of a module and export everything?
/M
participants (6)
-
Brandon S. Allbery KF8NH
-
Don Stewart
-
Evan Laforge
-
Ivan Miljenovic
-
Magnus Therning
-
Roel van Dijk