Efficiently Managing Types in TypeScript - reactjs

I've been working on a large TS project for work and absolutely love it. When the project started we stored all of our custom-defined interfaces and types in a single types.ts file, which just exported each of them. That way, we could import only the types we needed in each module (in our case, React components). In this sense, we essentially have a global.d.ts file as defined here with the added benefit of it actually being a module because of the export syntax in types.ts.
Of course, the project has scaled and it's really time to move these definitions elsewhere. My question is how to actually build out separate .d.ts files to do this. Should I have separate .d.ts files for each component (or perhaps component group) and then reference them in a single index.d.ts? Should I just stick with what I have? Other suggestions? Really I'm just looking for advice on how other devs manage type definitions in a scalable, maintainable way. We are using TS 2.4.2 with React, Redux, redux-saga, and webpack.

Related

How are React apps structured?

I'm getting started with React and I'm having a hard time wrapping my head around the actual "flow" of a project.
I've googled and searched around on this site regarding the structure or architecture of a React app, but most of them address file structure and often end with some variant of "There's no one right way to structure the files".
But I'm looking for something more high level than that. I'm just trying to grasp how all the pieces React provides fit together. I can't even begin worrying about how I organize my files if I don't even know entirely how each file relates to one another.
As an example of what I mean - when working with an MVC app, you have three "high level" components: model, view, and controller. Their purposes and relationships to each other are distinct. A view handles the display, a model handles the data, a controller handles the connection between them. You can find easy reference diagrams to keep track of this organization.
Of course React isn't it's own paradigm, and I know it's entirely focused on front-end, but I'm curious if there's a similar way of describing the pieces of a typical React app. How containers, components, reducers, actions, etc. all work together to make an end result.
I would agree with Marko Grešak's comment. You learn as you do and understand the code.
But, if you fill lost (which I was also), I can tell you about some architectures I saw :
A teacher of mine split the logic and the view. In one folder, you find your components, in one folder, classic JS classes that contains all the functions that handle the logic behind what the components print. Each component imported its own css file, with only the styles for this one component. We used this with MobX..
At work, we have a js folder, containing a components folder, for components that are at the 'end of the line', a containers folder, for components that have other components in them, a store folder for everything Redux, an asset folder for images and such, and a utility folder for other functions we might want to call. At the same level as the js folder, we have a sass folder. This is in no way a 'correct' or 'recommanded' way of doing things.
In general, you'll find a lot of tutorials and other things referring to dumb and smart components - splitting between the ones that just receive props and print them, and the ones accessing data and manipulating it. It's a bit like our container/component system in the end.
In the end, you're free to do how you want. Just try to keep a certain logic in how you split things so that it makes sense overall, but there is no set rules.

Naming convention for react component directories

I wonder what is the naming convention for directories and components in react. I have the main components directory and type of components (presentational, containers, hoc, views) under it.
I also have higher order component named DifferentReportsComparison. He lives in "components/hoc/differentreportscomparison/DifferentReportsComparison.js" path, but I think that the name of directory he is a child of can be confusing because of it long name.
I would like to know how you organize your components, especially these with long names.
First off, there is no best way to organize your components. In fact, unless you're working in a team of people, the best way to organize your components is what makes sense to you.
If you look at how NextJS works, they have broken up most likely what you refer to as 'views' into a folder called pages.
But if you're worried about the long name of a component, you could either (a). figure out a shorter name. Or sometimes people will name the component file in the folder index.js. So in the case of differentreportcomparison, it would go components/hocs/DifferentReportsComparison/index.js.
When you go to import that file you can import it by just doing
import DifferentReportsComparison from 'components/hocs/DifferentReportsComparison'
But as I said there is no perfect way to organize your components, and chances are as your projects grows, you will possibly change the structure a couple times.
It is worth taking a look at popular react projects and their take on it. E.g.
Material UI and Antd. There is no absolute standard. Just try to stick to one schema.

What is the best way to write flowtype definitions for private modules?

What is the best way to write flowtype definitions for a module?
I am aware of the flow-typed project, is this the best way to write definitions even if you own the library? The documentation is not very clear about this.
flow-typed approach does not work for private modules. What is the recommendation in this case?
I'd recommend reading through Authoring and publishing JavaScript modules with Flow.
The short answer is that you can distribute your module with .js.flow files that Flow will read to get type information. Usually these are just copies of your original source code from before the type annotations were deleted, created using the flow-copy-source package.
flow-typed exists to provide definitions for modules that do not provide them automatically, but you can include the type definitions right inside your own modules.

Using Flow js, where do you keep your Type Aliases?

I'm new to using Flow js, and find myself creating a lot of custom type aliases for the different API call responses and other functions. Currently I keep the type alias in the same file where I need it, and export it if I need it elsewhere in the program. But, I'm quickly finding this to become unwieldy / messy. Is there a certain recommended structure of how to organize all of the type aliases?
Thanks.
You can use flow-typed directory to define global types and modules like explained in documentation. Other way would be to make some index file on top of some folder structure where you would export all related to this directory types. In my project I have global redux types declared in flow-typed directory and other types exported from commons directory.

How do you manage several ReactJS projects?

Background: My company's web-app is in fact several completely separated apps that have minimal effect on one another. That's why it doesn't make any sense to keep them under a single project - so I'm using separate projects. However, since I started migrating and writing new apps in ReactJS (using Webpack for bundling) I find many opportunities for reuse, in order to avoid code duplication and to avoid downloading common resources again after another app already fetched them:
I'm using specific versions of 3rd party npm modules - so no reason to bundle them over and over again - and no reason to upload them to the server more than once (for all the projects).
How do you share package.json fixed versions across projects?
Do you bundle all/groups of npm modules together or each separately? I want to get everything from the server for cases of on-premise deployment.
What measures to you take to make sure you don't forget to re-bundle the node modules in case you decided to update one of them?
Similar question goes for font files (keeping the font on the server and another font for icons)
common style sheets
common JS code - like utils & common
common web.config configurations
common images (currently some of them are inline in different bundles)
and last - common components - how do you share them? Do you use a separate project and publish to npm? symlink?
Or maybe, after all, I should go with a monorepo? And how?
You could create a separate project, my_modules, which is just a manifest of the shared, common packages. You'd have a package.json with all the common modules, and a single index.js which does something like:
import React, { Component, PropTypes } from 'react';
import moment from 'moment';
export { React, Component, PropTypes, moment };
Then, you'd publish this new my_modules project to github, and install that in your other projects.
import { React, Component, PropTypes } from 'my-modules';
Every time you change a package, you'd increment the version, and then update that version in your projects (which is still a bit of a pain, but you could use something like greenkeeper.io to ensure they don't get stale).
Similarly, you can do the same thing for just about everything else you've mentioned, although you don't want to go overboard with this; you should only share standard assets that doesn't change very often, and keep project-specific assets in their own repo.
EDIT: wanted to add, for React components, this is actually a really good practice, because it forces you to write generalized, independent components. You can use something like React Storybook to create these components in isolation. You can publish one master package with all the packages, individual components as packages, or somewhere in between (eg. all Form components in one package). Either way, though, they can still share a repo for convenience.

Resources