Home > Back-end >  Typescript error Type '{ }[]' is not assignable to type '[]' When passing an arr
Typescript error Type '{ }[]' is not assignable to type '[]' When passing an arr

Time:12-16

I defined an array of objects in my react project

const tabs = [
        {
            id: "1",
            tabTitle: "In Progress",
        },
        {
            id: "2",
            tabTitle: "Shipped",
        },
        {
            id: "3",
            tabTitle: "Canceled",
        },
    ];

It is an MVC pattern and I have defined an array in my controller which I pass as a props to my child component and maps it inside that component. However, Typescript complains about it.

Type '{ id: string; tabTitle: string; }[]' is not assignable to type '[]'.
  Target allows only 0 element(s) but source may have more.ts(2322)

I pass it to component like this: <UserOrdersTemplate tabs={tabs} /> and map inside child component:

interface UserOrdersTemplateTypes {
    tabOpen?: (e: any) => void;
    currentTab: string;
    tabs: []
}

const UserOrdersTemplate: React.FC<UserOrdersTemplateTypes> = ({
    tabOpen,
    currentTab,
    tabs,
}) => {
    return (
        <>
            <ul id="tabs-tab">
                {tabs.map((tab, i) => (
                    <li className="nav-item" role="presentation" key={i}>
                        <button
                            id={tab.id}
                            onClick={tabOpen}>
                            {tab.tabTitle}
                        </button>
                    </li>
                ))}
            </ul>
        </>
    );
};

What can I do to resolve this issue?

CodePudding user response:

The way you have given the example there isn't any issue

import * as React from 'react';
import './style.css';

export default function App() {
  const tabs = [
    {
        id: 1,
        tabTitle: "In Progress",
    },
    {
        id: 2,
        tabTitle: "Shipped",
    },
    {
        id: 3,
        tabTitle: "Cancled",
    },
];
  return (
    <div>
      {
        tabs.map((tab, i) => (
          <li className="nav-item" role="presentation" key={i}>
            <button id={tab.id.toString()} onClick={()=>{}} >  {tab.tabTitle} </button>
          </li>
        ))
      }
    </div>
  );
}

But, If you are using a separate component for it then,

import * as React from 'react';
import './style.css';

const Element = ({ id, tabTitle }) => (
  <li className="nav-item" role="presentation">
    <button id={id.toString()} onClick={() => {}}>
      {tabTitle}
    </button>
  </li>
);

export default function App() {
  const tabs = [
    {
      id: 1,
      tabTitle: 'In Progress',
    },
    {
      id: 2,
      tabTitle: 'Shipped',
    },
    {
      id: 3,
      tabTitle: 'Cancled',
    },
  ];
  return (
    <div>
      {tabs.map((tab, i) => (
        <Element {...tab} key={i} />
      ))}
    </div>
  );
}

//If you want to give explicit type then

import * as React from 'react';
import './style.css';

type Tab = {
  id: number;
  tabTitle: string;
};

const Element: React.FC<Tab> = ({ id, tabTitle }) => (
  <li className="nav-item" role="presentation">
    <button id={id.toString()} onClick={() => {}}>
      {tabTitle}
    </button>
  </li>
);

export default function App() {
  const tabs: Tab[] = [
    {
      id: 1,
      tabTitle: 'In Progress',
    },
    {
      id: 2,
      tabTitle: 'Shipped',
    },
    {
      id: 3,
      tabTitle: 'Cancled',
    },
  ];
  return (
    <div>
      {tabs.map((tab, i) => (
        <Element {...tab} key={i} />
      ))}
    </div>
  );
}

CodePudding user response:

The problem was with the type of tab array. I defined a type for tab

type TabType = {
  id: string;
  tabTitle: string;
};

and give that type to the array like this:

const tabs: TabType[] = [
  {
    id: "1",
    tabTitle: "In Progress",
  },
  {
    id: "2",
    tabTitle: "Shipped",
  },
  {
    id: "3",
    tabTitle: "Canceled",
  },
];

and map that array as follows:

<ul id="tabs-tab">
    {tabs && tabs.map((tab, i) => (
        <li className="nav-item" role="presentation" key={i}>
            <button
                id={tab.id}
                onClick={tabOpen}>
                {tab.tabTitle}
            </button>
        </li>
    ))}
</ul>

it resolved the problem.

CodePudding user response:

The problem is that you're not defining the type of tabs inside the UserOrdersTemplateTypes interface.

To fix this create a type for Tab:

type Tab = {
    id: number;
    tabTitle: string;
};
    

Then inside UserOrdersTemplateTypes interface update the tabs definition to:

tabs: Tab[]
  • Related