Home liberachat/#haskell: Logs Calendar

Logs: liberachat/#haskell

←Prev  Next→ 1,804,010 events total
2025-09-24 09:53:11 <Enrico63> Confirm. It is Applicative, but isn't a Monad.
2025-09-24 09:54:13 <Leary> Enrico63: How about `hasThreeWords :: String -> Validation ()`?
2025-09-24 09:54:16 <Enrico63> Yeah, I thought the same. As in, I feel like I'd need Monad for doing what is requested, but Validation is definitely not a Monad.
2025-09-24 09:54:25 <tomsmeding> oh maybe the idea is that you use `orElse`?
2025-09-24 09:55:04 <tomsmeding> perhaps not orElse since that throws away the error if it's a failure
2025-09-24 09:55:38 <Enrico63> Leary,  I've tried that, but I don't get, in the case of that failing, how to prevent the rest of the validation from running
2025-09-24 09:56:02 <tomsmeding> I've never worked with Validation specifically, but `Validation e a -> a -> (a -> Validation e b) -> Validation e b` is implementable, I think -- where the loose 'a' argument is a default for when the first argument is a failure
2025-09-24 09:56:13 <tomsmeding> not sure if Validation has a function with that functionality
2025-09-24 09:56:52 <Leary> Enrico63: Are you sure you don't want it to keep running?
2025-09-24 09:58:20 <tomsmeding> yeah what Leary says is the key point I think
2025-09-24 09:58:26 <Enrico63> Leary, I'm gonna try
2025-09-24 09:58:41 <Leary> (collecting as many warnings/errors as possible from the input is kinda the point of validation)
2025-09-24 09:59:02 <Unhammer> So as a workaround to my TH woes I can put all my tests in src/, putting them in the main library. Is it possible to have two libraries in one .cabal file? stack doesn't seem to let me build project:lib:library2, only project:lib
2025-09-24 09:59:09 <Enrico63> So you're saying that I should fire an error in case there's more than 3 words, but then I should disregard those additional words, rather than hard erroring, when doing the rest of the validation.
2025-09-24 09:59:43 <Leary> Probably. It's a reasonable option anyway.
2025-09-24 10:00:03 <tomsmeding> Unhammer: it is definitely possible to have multiple libraries in one .cabal file; at most one of them will be the "main" library (headed by `library`), the others will be sublibraries (headed by `library some-name`)
2025-09-24 10:00:21 <tomsmeding> Unhammer: whether stack is happy with that I dunno, but cabal supports that first-class
2025-09-24 10:00:22 <Enrico63> Leary, I see. In this case I just had the solution in front of me for the whole time. Let me try.
2025-09-24 10:01:29 <tomsmeding> Enrico63: and do not there is bindValidation
2025-09-24 10:01:53 <tomsmeding> which allows you, if I understand correctly, to "stop progressing" if an error occurred
2025-09-24 10:02:05 <tomsmeding> but you may or may not want to actually use that, as Leary argued
2025-09-24 10:05:02 × mud quits (~mud@user/kadoban) (Ping timeout: 258 seconds)
2025-09-24 10:06:24 CiaoSen joins (~Jura@2a02:8071:64e1:da0:5a47:caff:fe78:33db)
2025-09-24 10:06:39 mud joins (~mud@user/kadoban)
2025-09-24 10:10:47 <Enrico63> Leary, but regarding the "keep running" approach, how am I gonna do that? If there's 3 words, I want to run `parseOp op <*> parseIntOrVar a <*> parseIntOrVar b`, being a, op, b the 3 words. But if there aren't 3 words... how am I gonna parse what's left? I could ignore the aditional words. But what if there are less, say 1 word. How do I proceed
2025-09-24 10:10:47 <Enrico63> with the computations?
2025-09-24 10:10:56 <Unhammer> OK, so `stack build project:lib` actually builds all libraries of the .cabal file. But for some reason, the linker error shows up again if I have `library testlib\nbuild-depends: applib` (where applib uses that C function).
2025-09-24 10:11:18 <Unhammer> oh https://discourse.haskell.org/t/adding-template-haskell-library-produces-linker-error-on-alpine/13000
2025-09-24 10:11:27 <Enrico63> Leary, indeed, the testcase
2025-09-24 10:11:27 <Enrico63> ```
2025-09-24 10:11:28 <Enrico63> parseExpression "k +"
2025-09-24 10:11:28 <Enrico63> ```
2025-09-24 10:11:29 <Enrico63> expects this error
2025-09-24 10:11:29 <Enrico63> ```
2025-09-24 10:11:30 <Enrico63>   Expected: Errors ["Invalid expression: k +"]
2025-09-24 10:11:30 <Enrico63> ```
2025-09-24 10:11:47 <Enrico63> So the parsing of `k` and `+` is not meant to have a chance to run
2025-09-24 10:14:10 × infinity0 quits (~infinity0@pwned.gg) (Ping timeout: 255 seconds)
2025-09-24 10:15:20 <Enrico63> Oh. I think the key is to use `empty`..
2025-09-24 10:15:42 × Vajb quits (~Vajb@n7nfchy4dz4j3x4yypz-1.v6.elisa-mobile.fi) (Ping timeout: 256 seconds)
2025-09-24 10:16:13 <Leary> Neither `k` nor `+` are erroneous, so they wouldn't contribute to the error set either way; it's ambiguous whether parsing should proceed or not (perhaps intentionally so).
2025-09-24 10:18:03 <Enrico63> Ok, I have a solution. This is the validator you suggested:
2025-09-24 10:18:03 <Enrico63> ```
2025-09-24 10:18:04 <Enrico63> hasThreeWords :: String -> Validation ()
2025-09-24 10:18:04 <Enrico63> hasThreeWords s = case words s of
2025-09-24 10:18:05 <Enrico63>                     (a:op:b:[]) -> pure ()
2025-09-24 10:18:05 <Enrico63>                     _ -> invalid $ "Invalid expression: " ++ s
2025-09-24 10:18:06 <Enrico63> ```
2025-09-24 10:18:06 <Enrico63> and together with the others I've defined above, it can be used like this:
2025-09-24 10:18:07 <Enrico63> ```
2025-09-24 10:18:07 <Enrico63> parseExpression :: String -> Validation Expression
2025-09-24 10:18:08 <Enrico63> parseExpression str = hasThreeWords str *>
2025-09-24 10:18:08 <Enrico63>                       case words str of
2025-09-24 10:18:09 <Enrico63>                          (a:op:b:_) -> parseOp op <*> parseIntOrVar a <*> parseIntOrVar b
2025-09-24 10:18:09 <Enrico63>                          _ -> empty
2025-09-24 10:18:10 <Enrico63> ```
2025-09-24 10:19:14 <Enrico63> So if `hasThreeWords` passed, the computation proceeds as I had alrady done. The trick is that if that fails, then we just return `empty`, so we don't contribute to the list of errors, yet we don't hard-error nor we give a meaningless Ok.
2025-09-24 10:20:41 arandombit joins (~arandombi@2603:7000:4600:ffbe:15f4:44c6:cf8f:dc61)
2025-09-24 10:20:41 × arandombit quits (~arandombi@2603:7000:4600:ffbe:15f4:44c6:cf8f:dc61) (Changing host)
2025-09-24 10:20:41 arandombit joins (~arandombi@user/arandombit)
2025-09-24 10:25:52 <Enrico63> Thanks Leary and tomsmeding
2025-09-24 10:33:10 <Enrico63> Ok, the solution from the site is a bit simpler, ahah:
2025-09-24 10:33:11 <Enrico63> ```
2025-09-24 10:33:11 <Enrico63> parseExpression :: String -> Validation Expression
2025-09-24 10:33:12 <Enrico63> parseExpression e = parse (words e)
2025-09-24 10:33:12 <Enrico63>   where parse [a1,op,a2] = parseOp op <*> parseArg a1 <*> parseArg a2
2025-09-24 10:33:13 <Enrico63>         parse _ = invalid ("Invalid expression: " ++ e)
2025-09-24 10:33:13 <Enrico63> ```
2025-09-24 10:34:35 infinity0 joins (~infinity0@pwned.gg)
2025-09-24 10:38:16 wootehfoot joins (~wootehfoo@user/wootehfoot)
2025-09-24 10:41:21 Vajb joins (~Vajb@n73ytrjjz36ldo55g3k-1.v6.elisa-mobile.fi)
2025-09-24 10:43:06 × wootehfoot quits (~wootehfoo@user/wootehfoot) (Ping timeout: 248 seconds)
2025-09-24 10:45:46 × Vajb quits (~Vajb@n73ytrjjz36ldo55g3k-1.v6.elisa-mobile.fi) (Ping timeout: 248 seconds)
2025-09-24 10:49:14 × trickard quits (~trickard@cpe-49-98-47-163.wireline.com.au) (Read error: Connection reset by peer)
2025-09-24 10:49:27 trickard_ joins (~trickard@cpe-49-98-47-163.wireline.com.au)
2025-09-24 10:49:50 × mulk quits (~mulk@pd95144c3.dip0.t-ipconnect.de) (Remote host closed the connection)
2025-09-24 10:51:42 michalz joins (~michalz@185.246.207.197)
2025-09-24 10:52:56 × michalz_ quits (~michalz@185.246.207.203) (Ping timeout: 258 seconds)
2025-09-24 10:55:05 Vajb joins (~Vajb@85-76-47-114-nat.elisa-mobile.fi)
2025-09-24 10:58:37 × Enrico63 quits (~Enrico63@2a0b:e541:10d0:0:9efc:e8ff:fe24:3213) (Quit: Client closed)
2025-09-24 11:03:40 × merijn quits (~merijn@77.242.116.146) (Ping timeout: 258 seconds)
2025-09-24 11:06:21 × Vajb quits (~Vajb@85-76-47-114-nat.elisa-mobile.fi) (Ping timeout: 258 seconds)
2025-09-24 11:06:44 merijn joins (~merijn@77.242.116.146)
2025-09-24 11:07:58 × CiaoSen quits (~Jura@2a02:8071:64e1:da0:5a47:caff:fe78:33db) (Ping timeout: 265 seconds)
2025-09-24 11:10:59 × Athas quits (athas@2a01:7c8:aaac:1cf:d153:5501:dd03:4891) (Quit: ZNC 1.9.1 - https://znc.in)
2025-09-24 11:11:11 Athas joins (athas@sigkill.dk)
2025-09-24 11:23:59 craunts79 joins (~craunts@136.158.7.194)
2025-09-24 11:24:44 trickard___ joins (~trickard@cpe-51-98-47-163.wireline.com.au)
2025-09-24 11:24:52 × arandombit quits (~arandombi@user/arandombit) (Ping timeout: 244 seconds)
2025-09-24 11:25:23 × trickard_ quits (~trickard@cpe-49-98-47-163.wireline.com.au) (Ping timeout: 244 seconds)
2025-09-24 11:26:13 trickard___ is now known as trickard
2025-09-24 11:26:47 CiaoSen joins (~Jura@2a02:8071:64e1:da0:5a47:caff:fe78:33db)
2025-09-24 11:28:25 Square joins (~Square4@user/square)
2025-09-24 11:31:13 Lord_of_Life_ joins (~Lord@user/lord-of-life/x-2819915)
2025-09-24 11:31:14 × Inline quits (~Inline@ip-005-146-196-132.um05.pools.vodafone-ip.de) (Quit: Leaving)
2025-09-24 11:31:35 × Lord_of_Life quits (~Lord@user/lord-of-life/x-2819915) (Ping timeout: 244 seconds)
2025-09-24 11:32:32 Lord_of_Life_ is now known as Lord_of_Life
2025-09-24 11:32:37 × gabiruh quits (~gabiruh@vps19177.publiccloud.com.br) (Ping timeout: 244 seconds)
2025-09-24 11:34:41 × xff0x quits (~xff0x@fsb6a9491c.tkyc517.ap.nuro.jp) (Ping timeout: 244 seconds)
2025-09-24 11:35:43 × acidjnk quits (~acidjnk@p200300d6e71719544593b070e4f06c0e.dip0.t-ipconnect.de) (Ping timeout: 244 seconds)

All times are in UTC.