
(sorry for the delay in replying to this...)
No problem, though you seem to be restating your opinion intead of addressing my concrete points? For those who, like me, have lost the thread in the meantime, here is a link to the message you reply to: http://www.haskell.org/pipermail/libraries/2008-September/010623.html
.., the only sensible way to think about instances is as global properties. ..it has nothing to do with bugs or misfeatures in GHC, it's a fact of Haskell 98.
I thought my example demonstrated quite clearly that instances are *not* global in Haskell.
A type class specifies a relation between types. Both the types and the class are named, and if instances are placed in separate modules, the modules are named as well. The combination of module, class and type names gives quite a bit of control over instance import/export, even if it is terribly cumbersome and limited (and easily defeated by just one library importing all instances "for convenience"). Neither the relation (class), nor its domain (types), nor its extent (instances) are "global".
The point is that instances are unconditionally re-exported,
Yes, and I'm not disputing that point. What I am disputing are its consequences/interpretation. As I said, instances accumulate upwards along the import hierarchy. But they do not propagate downwards, so they do not have global scope, and one can exert some control over all of type relation (class), domain (types), and extent (instances). What one cannot do (in Haskell 98) is to have two instances of the same class, for the same types, in the same import hierarchy.
If we consider instances to be part of the API of a module, then the API of a module is changed simply by changing what is imported.
That is true, whether we like it or not. The language does not give the programmer a way to control this part of the API by limiting re-export of locally visible instances. The programmers may not like it, but those instances are visible to importers even if they distribute warning labels stating "these instances are not part of our intended API".
This is even worse at the level of packages. We can hide modules that are used internally to a package's implementation, but we can't hide the fact that a package used some non-standard instances internally, and furthermore we can't change this aspect of its implementation without changing the API.
How do packages make a difference here? As long as I don't import base:Control.Monad.Error, the base:Control.Monad.Instances instances of Functor, say, are not visible in base:Control.Monad.
So thinking of instances as part of the API of a module is wrong, because it leads to the aforementioned abstraction failures. The only sensible way to think of instances is as global properties - one instance per class/type pair.
I'm afraid that is the wrong way round: the abstracton failures occur because of lack of control over the API - trying to wish away the offending instances ("don't think of them as part of the API") won't help. And trying to think of instances as global fails to account for the limited control we do have, by arranging code inside the import hierarchy, as in the example I gave. So this interpretation is unhelpful, demonstrably wrong, and prevents more detailed analysis. There may be real theory reasons why the extent of type relations has to increase monotonically as one walks up the import hierarchy, and such reasons might invalidate the proposal I made about providing more control over instance re-export. I'd certainly be interested in hearing about such real arguments (the fact that moving code downwards in the import hierarchy, away from the branch that provides the instances, has the same effect, suggests that such reasons either do not exist or already point to issues with the current language definition). But simply jumping from "we don't have full control" to "we don't have any control, and we never will" is unhelpful. We need to understand these issues better, so that we can discuss whether the language can be improved, and so that we can see what needs to change so that Ghc and Haddock start supporting the existing language. Clarity of language precedes better understanding, I hope.
Orphan instances are usually wrong unless the orphans are also exported via the standard API for either the class or the type. That is, orphans are ok in the implementation of a package, but not in the exposed API, because that makes it possible for a client to import both the class and type without getting the instance, which is what we have to avoid.
Sadly, that has all been discussed to death already, and again, it is a matter of being precise. "Orphan" instances are not wrong per se - they encode and name the extent of type relations via modules, but one needs to think carefully about their intended use and whether that use is really supported by the language or just an illusion. Of the top of my head, I can think of two uses: (a) having two instances of the same class for the same types in the same program only works by "virtue" of #2356, so should be avoided unless and until the positive aspects of #2356 are moved from accident to design decision (b) giving clients control over which instances they want to use (eg, use set A or set B, or neither) should work, and mostly does, but may run into ghc #2182 and haddock #54. Also, it is advisable only for client applications, not for client libraries, as long as their users might run into unresolved aspect of (a). My preference would be to see ghc #2182, #2356 (for Haskell 98 mode) and haddock #54 fixed. #2356 (for Ghc mode) is documented behaviour, I believe, inherited from Ghc's handling of overlapping instances, but there is no LANGUAGE extension specifying this behaviour, so it isn't portable. Next, I'd like to see whether more control over instance re-export is permissible in theory and -if yes- would like to see it implemented and standardised. Currently, I see no reason why we couldn't support (a) and (b). Claus