PHPFixing
  • Privacy Policy
  • TOS
  • Ask Question
  • Contact Us
  • Home
  • PHP
  • Programming
  • SQL Injection
  • Web3.0

Monday, November 14, 2022

[FIXED] How to pattern match for a True/False within a function in Haskell?

 November 14, 2022     error-handling, functional-programming, haskell, if-statement, switch-statement     No comments   

Issue

I am trying to handle file errors manually so I can print my own message and currently I have this code:

handleFileError :: FileError -> IO a
handleFileError (FileError errorKind) = do
  case errorKind of
    NotFound -> undefined
    NoPermission -> undefined
    IsDirectory -> undefined

fileRead :: String -> IO String
fileRead file = do
  pathExists <- doesPathExist file
  notDirectory <- doesFileExist file

  -- These two must be handled before `System.Directory.getPermissions` is called
  -- or else it will error.

  permissions <- getPermissions file
  let hasReadPermissions = readable permissions

  if hasReadPermissions then undefined -- This is the success case
  else handleFileError $ FileError NoPermissions

I would like to check if any of the 3 booleans (pathExists, notDirectory, and hasReadPermissions) are false, and then act accordingly. I tried to implement this using a case with False, however this just always runs the first branch.


Solution

One way would be to use MultiWayIf:

do
  pathExists <- doesPathExist file
  notDirectory <- doesFileExist file
  permissions <- unsafeInterleaveIO (getPermissions file)
  if
    | not pathExists -> -- ...
    | not notDirectory -> -- ...
    | not permissions -> -- ...
    | otherwise -> -- ...

If you're allergic to extensions, the old-fashioned way to get this feature is using guards, as in:

  case () of
    _ | not pathExists -> -- ...
      | not notDirectory -> -- ...
      | not permissions -> -- ...
      | otherwise -> -- ...

But I recommend neither of these. Instead, just do something with the file, and catch the exception; otherwise there are race conditions with the file system changing out from under you between the check and the file use. Like this:

fileRead :: String -> IO String
fileRead = catch (undefined {- success case -}) $ \e -> if
  | isDoesNotExistError e -> -- ...
  | isPermissionError e -> -- ...
  | otherwise -> throw e


Answered By - Daniel Wagner
Answer Checked By - Clifford M. (PHPFixing Volunteer)
  • Share This:  
  •  Facebook
  •  Twitter
  •  Stumble
  •  Digg
Newer Post Older Post Home

0 Comments:

Post a Comment

Note: Only a member of this blog may post a comment.

Total Pageviews

Featured Post

Why Learn PHP Programming

Why Learn PHP Programming A widely-used open source scripting language PHP is one of the most popular programming languages in the world. It...

Subscribe To

Posts
Atom
Posts
Comments
Atom
Comments

Copyright © PHPFixing