The more precise answer to your question is that an explicit type signature is taken as exact. If the type needed is some (Ctx a => a), as here, but your type signature just says a, you will get a type error exactly as you did.

"a" there does not mean "figure out a type for me". It means *any type at all*. Including Void, (), Int, etc., which one would not expect to work there.

On Fri, Apr 20, 2018 at 2:33 PM, Marc Busqué <marc@lamarciana.com> wrote:
Hi!

I'm using [selda](https://hackage.haskell.org/package/selda) package in
order to deal with database backends.

Selda uses `TypeOperators` language extension, and it introduces  `:*:`
type operator constructor which take concrete types like `RowID` or
`Text` . It also has a `Table` type constructor which takes anything
built with `:*:`). On the other hand, `SeldaM` is selda custom monad
transformer with `IO` at the bottom.

I have following helper function which just wraps a call to the SQLite
backend. `dBPath` is just the database file path:

```
withDB :: SeldaM a -> IO a
withDB act = do
  path <- dBPath
  withSQLite path act
```

I want to wrap selda API in custom functions to be more resilient to
changes. Right now I'm trying to abstract selecting all rows for a given
table (maybe it seems brittle, but it is just a toy project in order to
learn Haskell):

```
list table = withDB $ query (select table) ```

Not adding a type signature to `list` produces following compilation
error:

```
• Non type-variable argument
    in the constraint: selda-0.1.12.1:Database.Selda.Column.Columns
                         (selda-0.1.12.1:Database.Selda.Column.Cols s a)
  (Use FlexibleContexts to permit this)
• When checking the inferred type
    list :: forall s a.
            (selda-0.1.12.1:Database.Selda.Column.Columns
               (selda-0.1.12.1:Database.Selda.Column.Cols s a),
             selda-0.1.12.1:Database.Selda.Compile.Result
               (selda-0.1.12.1:Database.Selda.Column.Cols s a)) =>
            Table a
            -> IO
                 [selda-0.1.12.1:Database.Selda.Compile.Res
                    (selda-0.1.12.1:Database.Selda.Column.Cols s a)]
```

If I try to add what I think would be the correct signature:

```
list :: Table a -> IO [a]
```

The error changes to:

```
• Couldn't match type ‘a’
                 with ‘selda-0.1.12.1:Database.Selda.Compile.Res
                         (selda-0.1.12.1:Database.Selda.Column.Cols s0 a)’
  ‘a’ is a rigid type variable bound by
    the type signature for:
      list :: forall a. Table a -> IO [a]
    at src/Hedger/Category.hs:35:1-25
  Expected type: SeldaM [a]
    Actual type: selda-0.1.12.1:Database.Selda.Backend.Internal.SeldaT
                   IO
                   [selda-0.1.12.1:Database.Selda.Compile.Res
                      (selda-0.1.12.1:Database.Selda.Column.Cols s0 a)]
• In the second argument of ‘($)’, namely ‘query (select table)’
  In the expression: withDB $ query (select table)
  In an equation for ‘list’:
      list table = withDB $ query (select table)
• Relevant bindings include
    table :: Table a (bound at src/Hedger/Category.hs:36:6)
    list :: Table a -> IO [a] (bound at src/Hedger/Category.hs:36:1)
   |
36 | list table = withDB $ query (select table)
```

However, if I constraint the type signature to act just for a given
table, it compiles without errors:

```
type CategoriesSchema = RowID:*:Text
list :: Table CategoriesSchema -> IO [CategoriesSchema]
```

Why is that it works with concrete types but not with a type variable
that takes the same concrete type in its both placeholders?

Thanks in advance,

Marc Busqué
http://waiting-for-dev.github.io/about/
_______________________________________________
Haskell-Cafe mailing list
To (un)subscribe, modify options or view archives go to:
http://mail.haskell.org/cgi-bin/mailman/listinfo/haskell-cafe
Only members subscribed via the mailman list are allowed to post.



--
brandon s allbery kf8nh                               sine nomine associates
allbery.b@gmail.com                                  ballbery@sinenomine.net
unix, openafs, kerberos, infrastructure, xmonad        http://sinenomine.net