-- Turns an NFADef with String labels into a NFADef with NFAWBLabel labels, if
-- its possible to do so.
toNFAWBDef :: NFADef String -> Either String (NFADef NFAWBLabel)
toNFAWBDef = modifyNFADef transformLabel
  where
    transformLabel lbl = case break (== '/') lbl of
        (l, '/' : r) -> toLabel l r
        _ -> Left $ "invalid NFAWB label: " ++ show lbl

    toLabel l r = NFAWBLabel <$> mapM convert l <*> mapM convert r

    convert '0' = Right Zero
    convert '1' = Right One
    convert '*' = Right Star
    convert c = Left $ "Unknown NFA label part: " ++ show c
toNFAWBDef :: NFADef String -> Either String (NFADef NFAWBLabel)
toNFAWBDef = modifyNFADef transformLabel
  where
    transformLabel lbl = case break (== '/') lbl of
        (l, '/' : r) -> toLabel l r
        _ -> Left $ "invalid NFAWB label: " ++ show lbl

    toLabel l r = NFAWBLabel <$> mapM convert l <*> mapM convert r

    convert '0' = Right Zero
    convert '1' = Right One
    convert '*' = Right Star
    convert c = Left $ "Unknown NFA label part: " ++ show c
toNFAWBDef = modifyNFADef transformLabel
  where
    transformLabel lbl = case break (== '/') lbl of
        (l, '/' : r) -> toLabel l r
        _ -> Left $ "invalid NFAWB label: " ++ show lbl

    toLabel l r = NFAWBLabel <$> mapM convert l <*> mapM convert r

    convert '0' = Right Zero
    convert '1' = Right One
    convert '*' = Right Star
    convert c = Left $ "Unknown NFA label part: " ++ show c