cdornan / fmt Goto Github PK
View Code? Open in Web Editor NEWNew formatting library
License: BSD 3-Clause "New" or "Revised" License
New formatting library
License: BSD 3-Clause "New" or "Revised" License
Write here if you're interested in taking over.
Consider rewriting .travis.yml
to use stack
instead how it's done here:
https://github.com/serokell/universum/blob/master/.travis.yml
Now builds are failing:
https://travis-ci.org/aelve/fmt/jobs/218088641
Something like that:
wordsWrapF :: Int -> Text -> Builder
Behavior should be the following:
Int
.TODO: should we compress consequent spaces?
Like, should
wordWrapF 100 "foo bar"
result in
"foo bar"
?
I think it should.
@neongreen Please, comment.
Also, relevant to serokell/importify#90
https://www.reddit.com/r/haskell/comments/647qfj/fmt_a_new_formatting_library/dg0d2az/
For the IO thing I see two options
fmt |< action = fmap (\result -> print $ fmt <> result) action
fmt |< action = print fmt >> action
The first is closer to what you said..but the second has clearer order of effects.
And when done, ping this guy: https://www.reddit.com/r/haskell/comments/72ubj8/naive_format_strings_using_template_haskell/dnowzd5/
His complaint is pretty valid:
Then, I want to format some floating point number rounded:
>>> value = 5.1234 >>> f"the value is {value:.2f}" 'the value is 5.12'
I like this syntax because the formating part (i.e. .2f) is close to the one used by printf and a lot of unix tools I know and it does not clutter the readability of the string.
With fmt:
> putStrLn $ "the value is " +| fixedF 2 value the value is 5.12
I always forgot the trailing space after "is" and I had to look at the documentation to find fixedF, everytime.
Run stack repl
in a fresh clone of this repo:
ghci> pretty (0 :: Word) :: String
"-0"
That's a known problem in formatting
that's resolved in this PR: https://github.com/chrisdone/formatting/pull/61/files. However, formatting
is not maintained anymore, but is still used as a dependency. As a long term solution I think this dependency should be removed somehow, but in short term it would be nice to fix formatting of unsigned numbers at least.
Somehow the String -> Builder
machinery doesn't work:
$ cabal v2-repl all
...
*Load> import Fmt
*Load Fmt> "foo " +| 3 |+ "\n"
<interactive>:2:1: error:
• Couldn't match expected type ‘Builder’ with actual type ‘[Char]’
• In the first argument of ‘(+|)’, namely ‘"foo "’
In the expression: "foo " +| 3 |+ "\n"
In an equation for ‘it’: it = "foo " +| 3 |+ "\n"
Here's what Cabal had to say when I added fmt
to my dependency packages:
Starting fmt-0.6.1.2 (lib)
Building fmt-0.6.1.2 (lib)
Installing fmt-0.6.1.2 (lib)
Completed fmt-0.6.1.2 (lib)
So that I can just use fmt
instead of liftIO . fmt
.
Looks like display
package provides more efficient conversion. Also, text-show
is not maintained.
See this conversation for reference.
floatF 1.2 = "1.2"
floatF 12.2 = "12.2"
but
floatF (-1.2) = "-1.2e0"
floatF (-12.2) = "-1.22e1"
So I think floatF
should be defined something like
floatF :: Real a => a -> Builder
floatF a | d < 0 = "-" <> floatF (-d)
-- ... rest of definition
It's not easy to deal with ByteString
s in fmt
library, as I noticed there is no instance Buildable
for it...
UPD: I found byteString :: ByteString -> Builder
function from the bytestring
package.
Probably it can be reexported in fmt
?
Library won't build with GHC 9.0.0, please see log snipped below...
[ 35s] /usr/bin/ghc --make -fbuilding-cabal-package -O -static -dynamic-too -dynosuf dyn_o -dynhisuf dyn_hi -outputdir dist/build -odir dist/build -hidir dist/build -stubdir dist/build -i -idist/build -ilib -idist/build/autogen -idist/build/global-autogen -Idist/build/autogen -Idist/build/global-autogen -Idist/build -optP-include -optPdist/build/autogen/cabal_macros.h -this-unit-id fmt-0.6.1.2-5dfGrAr0oy5IbhTcMOmpY -hide-all-packages -Wmissing-home-modules -no-user-package-db -package-db dist/package.conf.inplace -package-id base-4.15.0.0 -package-id base64-bytestring-1.2.0.1-wMVwxdzWeX9EOWhIVqH1Y -package-id bytestring-0.10.12.0 -package-id call-stack-0.2.0-F3nLWnfeL064cC2St4eCDt -package-id containers-0.6.2.1 -package-id formatting-7.1.1-1BFIJ7rMS602NMTv9NRMBR -package-id microlens-0.4.12.0-IoK2ncpVKVzEwRUasmz5D3 -package-id text-1.2.4.0 -package-id time-1.9.3 -package-id time-locale-compat-0.1.1.5-6us7pZxstqD6EDxOHL8mgH -XHaskell2010 Fmt Fmt.Time Fmt.Internal Fmt.Internal.Core Fmt.Internal.Formatters Fmt.Internal.Template Fmt.Internal.Tuple Fmt.Internal.Numeric Fmt.Internal.Generic -Wall -fno-warn-unused-do-bind -Wno-redundant-constraints
[ 35s] [1 of 9] Compiling Fmt.Internal.Core ( lib/Fmt/Internal/Core.hs, dist/build/Fmt/Internal/Core.o, dist/build/Fmt/Internal/Core.dyn_o )
[ 36s] [2 of 9] Compiling Fmt.Internal.Formatters ( lib/Fmt/Internal/Formatters.hs, dist/build/Fmt/Internal/Formatters.o, dist/build/Fmt/Internal/Formatters.dyn_o )
[ 36s]
[ 36s] lib/Fmt/Internal/Formatters.hs:201:57: error:
[ 36s] Ambiguous occurrence ‘singleton’
[ 36s] It could refer to
[ 36s] either ‘Data.List.singleton’,
[ 36s] imported from ‘Data.List’ at lib/Fmt/Internal/Formatters.hs:12:1-16
[ 36s] (and originally defined in ‘base-4.15.0.0:Data.OldList’)
[ 36s] or ‘Data.Text.Lazy.Builder.singleton’,
[ 36s] imported from ‘Data.Text.Lazy.Builder’ at lib/Fmt/Internal/Formatters.hs:25:1-49
[ 36s] (and originally defined in ‘Data.Text.Internal.Builder’)
[ 36s] |
[ 36s] 201 | spaces = mconcat $ replicate (T.length bullet + 1) (singleton ' ')
[ 36s] | ^^^^^^^^^
[ 36s] error: Bad exit status from /var/tmp/rpm-tmp.OYC1Ku (%build)
[ 36s]
[ 36s]
[ 36s] RPM build errors:
[ 36s] Bad exit status from /var/tmp/rpm-tmp.OYC1Ku (%build)
I propose to add a function with type Buildable x => x -> Text
.
Like show
, but using Buildable
instead of Show
(and returning Text
instead of String
).
It's useful when you want to pretty print a single value of a type which is instance of Buildable
.
It's a bunch of failures like this:
tests/Main.hs:681:7:
21) formatters.'genericF', custom types, records
expected: "Qux:\n q1: 1\n q2: True\n q3: hi"
but got: "Qux:\n q1: 1\n q2: True\n q3: hi\n"
Where the only thing wrong is a trailing newline.
This works,
data Baz = Baz deriving (Show)
fmtLn $ "foo"+||Baz||+""+|(2::Int)|+"bar"
but this does not:
data Baz = Baz deriving (Show)
fmtLn $ "foo"+||Baz||++|(2::Int)|+"bar"
failing with a type error complaining about Baz
not being buildable.
λ> fmtLn $ commaizeF (-123)
-,123
This should output "-123" instead.
In the Stackage Nightly build:
> /tmp/stackage-build12/fmt-0.6.1.1$ dist/build/doctests/doctests
/tmp/stackage-build12/fmt-0.6.1.1/lib/Fmt.hs:327: failure in expression `(""+|show foo|++|show bar|+"") == (""+||foo||++||bar||+"")'
<interactive>:108:19: error:
Variable not in scope:
mkName
:: [Char]
-> template-haskell-2.14.0.0:Language.Haskell.TH.Syntax.Name
Examples: 142 Tried: 142 Errors: 0 Failures: 1
Will do once fmt
reaches 0.2. (I don't want people to be stuck with 0.1 for the duration of LTS 8; LTS releases add new packages but don't bump major versions of old ones.)
See details here:
I would really appreciate some formatter for ranges like 1w2d3h4m
like this one:
durationF :: Natural -> Builder
But I would like to have an ability to easily interpret 9623
as 9623 minutes
or 9623 seconds
and format in either 160h23m
or 160m23s
. Dunno how the resulting interface should look like...
/Users/yom/tmp/fmt-0.6.1.1/lib/Fmt.hs:327: failure in expression `(""+|show foo|++|show bar|+"") == (""+||foo||++||bar||+"")'
<interactive>:108:3: error:
Variable not in scope:
polyQuickCheck
:: Language.Haskell.TH.Syntax.Name
-> Language.Haskell.TH.Lib.Internal.ExpQ
Examples: 142 Tried: 142 Errors: 0 Failures: 1
Very often you want to write just
instance Buildable MyType where
build = genericF
It may be better to have default implementation of build
(which is not possible, because we don't use our own Buildable
). But still things should be easier...
This has been on my list of things to do for ages, but hadn't got round to it. I really like your solution — it is exactly the kind of thing that I was hoping to come up with.
(Also I think you have had some past involvement in the regex libraries — if you have any feedback or suggestions for regex please give me a shout.)
Is it real to implement decode16 function (see the link below) from base16 library using fmt features?
https://hackage.haskell.org/package/base16-bytestring-0.1.1.6/docs/Data-ByteString-Base16.html
base64-bytesting
has security issues:
It's better to use memory
package:
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.