14

What's the difference between import React from 'react' and import React { Fragment } from 'react' in context of <React.Fragment>, <Fragment> and <>?

I mean what happen when we import React and { Fragment } in the same line from a module?

Do we create instance of <Fragment> and this is just another few hundreds lines of code under the hood?

Or this is just normal and everybody can do that withouth performance downsides?

Official React blogpost mention that you can do this const Fragment = React.Fragment and they use in in their examples.

But why?

Kamil Dzieniszewski
  • 475
  • 1
  • 5
  • 15

4 Answers4

17

So assume you have an object.

let object = {
   foo: '1',
   bar: '2',
};

In order to use the value foo you can do the following

  • object.foo
  • let { foo } = object

These both are the same, the later mentioned way is called destructing which was introduced in javascript ES6 version.

Now coming to topic for

What's the difference between import React from 'react' and import React { Fragment } from 'react' in context of , and <>?

imagine React as object which has the following features e.g Fragment in this case. You can access it the following ways

1- First way

 import React from 'react';
 <React.Fragment></React.Fragment>

2-

import React, { Fragment } from 'react';
<Fragment></Fragment>

Now in the second way this is basically importing all React features and also destructing a feature from React which is Fragment. SO you don't have to write React.Fragment again and again.

3-

<></>

This is a babel feature, babel when compiling will convert <></> this into <React.Fragment></React.Fragment>

CupawnTae
  • 14,192
  • 3
  • 29
  • 60
Adeel Imran
  • 13,166
  • 8
  • 62
  • 77
4

This is basically syntactic sugar:

import React, { Fragment } from 'react'

Will allow you to write the following:

class MyComponent extends React.Component {

 render () {
   return (
     <Fragment>
       <div className="fragment1">Fragment 1</div>
       <div className="fragment2">Fragment 2</div>
     <Fragment>
   ) 
 }
}

Instead of having to write explicitly React.Fragment. Note that you could also write the following if the only imports that you need are React.Component and React.Fragment:

import { Component, Fragment } from 'react' 

class MyComponent extends Component {

 render () {
   return (
     <Fragment>
       <div className="fragment1">Fragment 1</div>
       <div className="fragment2">Fragment 2</div>
     <Fragment>
   ) 
 }
}

This may also become relevant when using module bundler such as Webpack, so your bundler will only import the required dependencies and it may result in a smaller bundle (AKA your app loads faster). Take a look at Tree Shaking for more details. This ultimately depends on how the imported package exports its modules, as mentioned in the reply above it may have no benefit for React - at the moment - but other libraries may leverage that mechanism. It is usually a good practice to try to keep your imports as strict minimum.

Felipe
  • 4,325
  • 1
  • 14
  • 19
3

<></> syntax doesn’t support keys or attributes. When element is iterated it will throw the warning message 'Each child in a list should have a unique "key" prop'.

For Example :

{props.items.map(item => (
    <>
      <dt>{item.term}</dt>
      <dd>{item.description}</dd>
    </>
))}

See docs here https://reactjs.org/docs/fragments.html#keyed-fragments

rajesh kumar
  • 1,578
  • 16
  • 14
1

Well there are no performance downsides, This is just have to do with extra markup. We do named export Fragment like Component that we usually do. As long as if you're concerned about performance, we're already importing from react which means complete react package Because there are not just Component, Fragment we need while exporting component in React Tree. There are under hood dependencies in react package we don't actually import but they are used in our component

Sakhi Mansoor
  • 7,832
  • 5
  • 22
  • 37