adobe / adobe/react-spectrum

Context Slots are not Extensible

Open
#6,992 1 comment 2 reactions 0 assignees View on GitHub
Dominant language
TypeScript
Stars
15.9k
Forks
1.6k
Avg merge
3d 9m
Merged PRs (30d)
59

Description

### Provide a general summary of the issue here

When it comes to expanding on the the slots that an RAC provides, it's impossible to maintain the parent context and implement new slots without running into errors.

I'm providing a concrete example based on a single RAC, but this pattern applies to all RAC. The overall concept of named slots is currently very hardcoded and inflexible

### 🤔 Expected Behavior?

It should be possible to add named slots to any context without errors being thrown within RAC. Conflicts between DS and RAC slot names should only result in warnings and should merge on all applicable props as intended

### 😯 Current Behavior

Given the scenario:
`DSButton` consumes a new `DSButtonContext` and is built on top of the RAC `Button`
`DSGridListItem` implements a `DSButtonContext` with named slots that don't match the RAC `GridListItem` `ButtonContext` named slots

An error is thrown or functionality is lost

For context, RAC GridListItem provides DEFAULT_SLOT and "drag" as a named slot

Error Thrown:

If the `DSGridListItem` implements a named slot of "foobar", and the `DSButton` attempts to utilize that slot, RAC will throw an error that only "drag" is a valid named slot and that "foobar" is an invalid named slot

It's also not possible to override the slot prop from the `DSButtonContext`, because local props always take precedence. For example, if the "foobar" slot were to try and pass `slot: DEAFULT_SLOT,`, the error is still thrown because the component has the higher precedence prop `slot="foobar"` already on it

Functionality Lost:

If the `DSGridListItem` were to implement the RAC `ButtonContext` with the named slot "foobar", then all props for the slots provided by RAC are lost

### 💁 Possible Solution

Make the RAC slot validation (https://github.com/adobe/react-spectrum/blob/a899bdfb6c4020c0ef17d87fe57ab2782e895c1c/packages/react-aria-components/src/utils.tsx#L172) dev environment only warnings instead of errors

### 🔦 Context

While we have had a workaround solution (https://github.com/adobe/react-spectrum/issues/6610), my team has been discussing how to align more closely with the guidance provided by RAC folks. The main guidance we've been provided is to utilize the new context for every DS component approach.

This is why we created a wrapper for all of the simple, low level components that are not receiving direct DS attention:
```typescript
function wrap

(
Component: (props: P & RefAttributes) => ReactElement | null
) {
const Context = createContext>(null);

return {
Component: forwardRef(function WrappedComponent(
props: P,
ref: ForwardedRef
) {
[props, ref] = useContextProps(props, ref, Context);

return ;
}),
Context,
};
}

export const { Component: AriaText, Context: AriaTextContext } = wrap(Text);
```

### 🖥️ Steps to Reproduce

https://codesandbox.io/p/sandbox/delicate-worker-9dmh72

### Version

"@react-aria/utils": "3.25.1", "@react-stately/utils": "3.10.1", "react-aria": "3.33.1", "react-aria-components": "1.2.1", "react-stately": "3.31.1",

### What browsers are you seeing the problem on?

Chrome

### If other, please specify.

_No response_

### What operating system are you using?

Mac & Windows

### 🧢 Your Company/Team

_No response_

### 🕷 Tracking Issue

_No response_

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.