Search code examples
javascriptreactjsreact-proptypes

Reusing a common PropType shape with props required or not required depending on the component


I have a common proptype (in a lib) that multiple components import and use.

ListPropType = PropTypes.shape({
    name: PropTypes.string,
    creatorId: PropTypes.string.isRequired,
    ...
});

1) For some components, I want to make the name required and for some components, I don't.

2) Also, for some components, I want to add additional props in the shape.

Is there a simple or common way of handling these use cases that doesn't involve duplicating everything but the fields that differ?


Solution

  • Never had to do this, but I suppose you could write a factory method to generate the shape, this way you'd be able to add isRequired to fields on the fly.

    const getShape = (requiredFields, extraFields) => {
      const template = {
        name: PropTypes.string,
        creatorId: PropTypes.string.isRequired,
      };
      Object.keys(template).forEach(key => {
        if (requiredFields.includes(key)) {
          template[key] = template[key].isRequired;
        }
      });
      return PropTypes.shape({
        ...template,
        ...extraFields,
      });
    }
    
    // Create propType with 'name' required and extra date field
    ListPropType = getShape(
      ['name'],
      { date: PropTypes.string }
    );
    

    You could even abstract this further by taking the starting template as an argument to the getShape function.