-
-
Notifications
You must be signed in to change notification settings - Fork 503
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Naming convention for qualified imports in the fp-ts eco system #1415
Comments
I don't think point 2 is correct, "scale" is used without context. Generally speaking, any rule you want to enforce for everything will be painful most of the time (like the verbosity of using It is correct that sometimes you find yourself with 2 (or more types) that start with The only pattern that can "scale" is: "do the thing that works best for your problem, don't try to find a rule that covers everything" |
AFAIK you can achieve similar behavior like you showed in PureScript example in TS: import * as E from "fp-ts/Either"
type Either = E.Either [UPDATE] Invalid syntax above. That's a valid one: import * as E from "fp-ts/Either"
import Either = E.Either IMO it's pretty convenient to import everything just from fp-ts: import { either, option } from "fp-ts" You would still have to write |
This is invalid syntax: import * as E from 'fp-ts/Either'
type Either = E.Either // Generic type 'Either' requires 2 type argument(s) However this is valid: import * as E from 'fp-ts/Either'
import Either = E.Either The following style is fine for tree shakeability: import { either } from 'fp-ts'
import { Either } from 'fp-ts/Either'
const foo: Either<string, string> = either.left('') as long as you are using rollup or webpack 5.
Just a note: "mega" instances like import { either, option } from 'fp-ts'
// deprecated
const sequence = option.sequence(either.either)
// ok
const sequence = option.sequence(either.Applicative) |
@mikearnaldi you're right. i was not specific enough about "scaling". And indeed, I agree, in the end it counts what works best for your problem. However, what you describe with "Exit" and "Either" is want I want to avoid. Of course it's not about to find one golden rule, just to sort out different approaches and their implications. Personally the import { either } from 'fp-ts'
import { Either } from 'fp-ts/Either' The above looks like a good way to go then, if you opt for verbose aliases. One complaint I hear a lot from people starting with functional programming: There are so many imports! An in deed, it's a bit annoying. so, why not:? import * as fp from "fp-ts" As far as I see, according to this document, it should be tree-shaking save, too. Maybe import * as fp from "fp-ts"
import { Either, Option, State } from "fp-ts" Then you'd have only two import lines, the types not qualified, which is convenient and to me writing things like |
I stumbled across this several times and maybe it has been discussed as well. How to name qualified imports in the fp-ts ecosystem?
Situation in PureScript/Haskell
In languages like Haskell or PureScript qualified import aliases don't share the same namespace as types.
So e.g. in PureScript you can import and use the Either module and type like this:
Limitation in TypeScript
In TypeScript the import is just a plain object and theoretically it should not conflict with the type
Either
, even if the newimport type
is used:This produces as
TS2300: Duplicate identifier 'Either'.
I could not find reason for this, as this works with no complains:
Proposals, Ideas
In most code I see capital character abbreviations used for module aliases, like:
import * as E from 'fp-ts/Either'
. I really think that this is confusing and does not scale. Suddenly you have another type that starts with "E" and many questions arise.I started to use the lower case alternative for a while now:
import * as either from "fp-ts/Either"
Traditionally JS modules used to be named lower case (
fs
,child_process
) but since ES6 this seems to be replaced with an upper case convention (import * as React
, ...)Also it's a bit silly that now one has to write
either.either
to reference the instance record.Another approach was to postfix the modules
Either_
orEither$
, but that also a bit ugly. or prefix$Either
,_Either
, I don't know.fpEither
,fptsEither
fpTsEither
,FpTsEither
,FpTsEither
... The downside of this is that you'll have a lot of "fp"s in the code, but on the other hand it may be useful for newcomers to see which modules follow the fp-ts patterns and which not.Further reading: http://blog.haskell-exists.com/yuras/posts/namespaces-modules-qualified-imports-and-a-constant-pain.html
The text was updated successfully, but these errors were encountered: