Skip to content

Commit 7dcad9c

Browse files
Document GHC-77539 (#518)
Fixes #432.
1 parent ae7ed42 commit 7dcad9c

File tree

4 files changed

+52
-0
lines changed

4 files changed

+52
-0
lines changed
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
---
2+
title: Illegal tuple constraint
3+
summary: A tuple of constraints was used without enabling the ConstraintKinds extension
4+
extension: ConstraintKinds
5+
introduced: 9.6.1
6+
severity: error
7+
---
8+
9+
Constraints are the part of a signature that defines the type classes that must be implemented for the types used to instantiate the type variables, found to the left of the double arrow (`=>`).
10+
In [Haskell 2010](https://www.haskell.org/onlinereport/haskell2010/haskellch4.html#x10-630004.1), type class constraints are either:
11+
12+
* a single constraint that consists of a named class applied to arguments, or
13+
14+
* multiple constraints in parentheses, separated by commas.
15+
16+
This strict syntax is necessary because type classes do not themselves form types in Haskell 2010.
17+
This syntax does not admit nested parentheses or tuples.
18+
19+
With GHC's [`ConstraintKinds` extension](https://ghc.gitlab.haskell.org/ghc/doc/users_guide/exts/constraint_kind.html), type classes form types that have kind `Constraint`, and instead of checking for a specific syntactic form, the type checker ensures that the constraint section of a signature has kind `Constraint`.
20+
Because tuples of types that have kind `Constraint` themselves have kind `Constraint`, nested tuples are allowed.
21+
This is especially convenient when defining type synonyms that stand for tuples of constraints.
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{-# LANGUAGE ConstraintKinds #-}
2+
module TupleConstraint where
3+
4+
addFromString :: ((Read a, Show a), Num a) => String -> a -> String
5+
addFromString x y = show (read x + y)
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{-# LANGUAGE Haskell2010 #-}
2+
module TupleConstraint where
3+
4+
addFromString :: ((Read a, Show a), Num a) => String -> a -> String
5+
addFromString x y = show (read x + y)
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
---
2+
title: Use of a tuple constraint
3+
---
4+
5+
## Message
6+
```
7+
TupleConstraint.hs:4:18: error: [GHC-77539]
8+
• Illegal tuple constraint: (Read a, Show a)
9+
• In the type signature:
10+
addFromString :: ((Read a, Show a), Num a) => String -> a -> String
11+
Suggested fix: Perhaps you intended to use ConstraintKinds
12+
|
13+
4 | addFromString :: ((Read a, Show a), Num a) => String -> a -> String
14+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
15+
```
16+
17+
## Explanation
18+
19+
This file is written in Haskell 2010, which does not have `ConstraintKinds`.
20+
This means that a syntactic check is used to ensure that type class constraints form a single-level tuple, and this file does not satisfy that requirement.
21+
Either de-nesting the tuple or enabling `ConstraintKinds` fixes the issue.

0 commit comments

Comments
 (0)