
Security News
npm Adopts OIDC for Trusted Publishing in CI/CD Workflows
npm now supports Trusted Publishing with OIDC, enabling secure package publishing directly from CI/CD workflows without relying on long-lived tokens.
@blac/react
Advanced tools
A powerful React integration for the Blac state management library, providing seamless integration between React components and Blac's reactive state management system.
A powerful React integration for the Blac state management library, providing seamless integration between React components and Blac's reactive state management system.
All methods in Bloc or Cubit classes must use arrow function syntax (method = () => {}
) instead of the traditional method syntax (method() {}
). This is because arrow functions automatically bind this
to the class instance. Without this binding, methods called from React components would lose their context and could not access instance properties like this.state
or this.emit()
.
// Correct way to define methods in your Bloc/Cubit classes
class CounterBloc extends Cubit<CounterState> {
increment = () => {
this.emit({ ...this.state, count: this.state.count + 1 });
}
decrement = () => {
this.emit({ ...this.state, count: this.state.count - 1 });
}
}
// Incorrect way (will cause issues when called from React):
class CounterBloc extends Cubit<CounterState> {
increment() { // ❌ Will lose 'this' context when called from components
this.emit({ ...this.state, count: this.state.count + 1 });
}
}
npm install @blac/react
# or
yarn add @blac/react
# or
pnpm add @blac/react
import { useBloc } from '@blac/react';
import { CounterBloc } from './CounterBloc';
function Counter() {
const [state, counterBloc] = useBloc(CounterBloc);
return (
<div>
<p>Count: {state.count}</p>
<button onClick={() => counterBloc.increment()}>Increment</button>
</div>
);
}
The useBloc
hook provides a simple way to connect your React components to Blac's state management system:
const [state, bloc] = useBloc(YourBloc);
The hook accepts configuration options for more control:
const [state, bloc] = useBloc(YourBloc, {
id: 'custom-id', // Optional: Custom identifier for the bloc
props: { /* ... */ }, // Optional: Props to pass to the bloc
onMount: (bloc) => { /* ... */ }, // Optional: Callback when bloc is mounted (similar to useEffect(<>, []))
dependencySelector: (newState, oldState) => [/* ... */], // Optional: Custom dependency tracking
});
The hook automatically tracks which state properties are accessed in your component and only triggers re-renders when those specific properties change:
function UserProfile() {
const [state, userBloc] = useBloc(UserBloc);
// Only re-renders when state.name changes
return <h1>{state.name}</h1>;
}
This also works for getters on the Bloc or Cubit class:
function UserProfile() {
const [, userBloc] = useBloc(UserBloc);
// Only re-renders when the return value from the getter formattedName changes
return <h1>{userBloc.formattedName}</h1>;
}
For more control over when your component re-renders, you can provide a custom dependency selector:
const [state, bloc] = useBloc(YourBloc, {
dependencySelector: (newState, oldState) => [
newState.specificField,
newState.anotherField
]
});
function useBloc<B extends BlocConstructor<BlocGeneric>>(
bloc: B,
options?: BlocHookOptions<InstanceType<B>>
): [BlocState<InstanceType<B>>, InstanceType<B>]
id?: string
- Custom identifier for the bloc instanceprops?: InferPropsFromGeneric<B>
- Props to pass to the bloconMount?: (bloc: B) => void
- Callback function invoked when the react component (the consumer) is connected to the bloc instancedependencySelector?: BlocHookDependencyArrayFn<B>
- Function to select dependencies for re-rendersUse Isolated Blocs: When you need component-specific state, use isolated blocs:
class MyIsolatedBloc extends BlocBase {
static isolated = true;
// ... rest of your bloc implementation
}
Use Custom Identifiers: When you need multiple independent instances of the same Bloc type, use custom identifiers to manage different state contexts:
// In a chat application with multiple chat rooms
function ChatRoom({ roomId }: { roomId: string }) {
const [state, chatBloc] = useBloc(ChatBloc, {
id: `chat-${roomId}`, // Each room gets its own instance
props: { roomId }
});
return (
<div>
<h2>Room: {roomId}</h2>
{state.messages.map(msg => (
<Message key={msg.id} message={msg} />
))}
</div>
);
}
// Usage:
function ChatApp() {
return (
<div>
<ChatRoom roomId="general" />
<ChatRoom roomId="support" />
</div>
);
}
Optimize Re-renders: Let the hook track dependencies automatically unless you have a specific need for custom dependency tracking.
Type Safety: Take advantage of TypeScript's type inference for better development experience and catch errors early.
Contributions are welcome! Please feel free to submit a Pull Request.
MIT
FAQs
Demo [https://blac-react-demo.vercel.app/](https://blac-react-demo.vercel.app/)
We found that @blac/react demonstrated a not healthy version release cadence and project activity because the last version was released a year ago. It has 0 open source maintainers collaborating on the project.
Did you know?
Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.
Security News
npm now supports Trusted Publishing with OIDC, enabling secure package publishing directly from CI/CD workflows without relying on long-lived tokens.
Research
/Security News
A RubyGems malware campaign used 60 malicious packages posing as automation tools to steal credentials from social media and marketing tool users.
Security News
The CNA Scorecard ranks CVE issuers by data completeness, revealing major gaps in patch info and software identifiers across thousands of vulnerabilities.