or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

actions.mdindex.mdmiddleware.mdreducer-composition.mdstore-management.mdutilities.md

actions.mddocs/

0

# Action Management

1

2

Action creators and binding utilities for managing action dispatch. Actions are the only way to send data to the store, and action creators provide a clean way to create and dispatch actions with automatic binding to the store's dispatch function.

3

4

## Capabilities

5

6

### Bind Action Creators

7

8

Wraps action creators with dispatch calls so they can be invoked directly without manually calling dispatch.

9

10

```typescript { .api }

11

/**

12

* Wraps a single action creator with dispatch

13

* @param actionCreator - A function that creates actions

14

* @param dispatch - The dispatch function from your Redux store

15

* @returns The action creator wrapped with dispatch call

16

*/

17

function bindActionCreators<A, C extends ActionCreator<A>>(

18

actionCreator: C,

19

dispatch: Dispatch

20

): C;

21

22

/**

23

* Wraps multiple action creators with dispatch

24

* @param actionCreators - Object whose values are action creator functions

25

* @param dispatch - The dispatch function from your Redux store

26

* @returns Object with same keys, but action creators wrapped with dispatch

27

*/

28

function bindActionCreators<A, M extends ActionCreatorsMapObject<A>>(

29

actionCreators: M,

30

dispatch: Dispatch

31

): M;

32

33

/**

34

* Wraps a single action creator with flexible typing

35

* @param actionCreator - A function that creates actions

36

* @param dispatch - The dispatch function from your Redux store

37

* @returns The action creator wrapped with dispatch call

38

*/

39

function bindActionCreators<A extends ActionCreator<any>, B extends ActionCreator<any>>(

40

actionCreator: A,

41

dispatch: Dispatch

42

): B;

43

44

function bindActionCreators<M extends ActionCreatorsMapObject, N extends ActionCreatorsMapObject>(

45

actionCreators: M,

46

dispatch: Dispatch

47

): N;

48

```

49

50

**Usage Examples:**

51

52

```typescript

53

import { bindActionCreators } from "redux";

54

55

// Action creators

56

const increment = () => ({ type: "INCREMENT" });

57

const decrement = () => ({ type: "DECREMENT" });

58

const addTodo = (text: string) => ({ type: "ADD_TODO", payload: { text } });

59

60

// Bind single action creator

61

const boundIncrement = bindActionCreators(increment, store.dispatch);

62

boundIncrement(); // Automatically dispatches the action

63

64

// Bind multiple action creators

65

const actionCreators = { increment, decrement, addTodo };

66

const boundActionCreators = bindActionCreators(actionCreators, store.dispatch);

67

68

// Use bound action creators directly

69

boundActionCreators.increment(); // Dispatches increment action

70

boundActionCreators.addTodo("Learn Redux"); // Dispatches add todo action

71

72

// Common pattern in React components

73

const mapDispatchToProps = (dispatch) => bindActionCreators({

74

increment,

75

decrement,

76

addTodo

77

}, dispatch);

78

```

79

80

### Action Creator Interface

81

82

The interface that action creator functions must implement.

83

84

```typescript { .api }

85

/**

86

* An action creator is a function that creates an action

87

* @template A - The type of action returned

88

* @template P - The parameter types accepted by the action creator

89

*/

90

interface ActionCreator<A, P extends any[] = any[]> {

91

(...args: P): A;

92

}

93

94

/**

95

* Object whose values are action creator functions

96

* @template A - The type of actions created

97

* @template P - The parameter types accepted by action creators

98

*/

99

interface ActionCreatorsMapObject<A = any, P extends any[] = any[]> {

100

[key: string]: ActionCreator<A, P>;

101

}

102

```

103

104

**Usage Examples:**

105

106

```typescript

107

// Simple action creators

108

const reset: ActionCreator<{ type: "RESET" }> = () => ({ type: "RESET" });

109

110

const setCount: ActionCreator<{ type: "SET_COUNT"; payload: number }, [number]> = (

111

count: number

112

) => ({ type: "SET_COUNT", payload: count });

113

114

// Action creators with multiple parameters

115

const updateUser: ActionCreator<

116

{ type: "UPDATE_USER"; payload: { id: string; name: string } },

117

[string, string]

118

> = (id: string, name: string) => ({

119

type: "UPDATE_USER",

120

payload: { id, name }

121

});

122

123

// Action creator map

124

const userActionCreators: ActionCreatorsMapObject = {

125

login: (username: string, password: string) => ({

126

type: "LOGIN",

127

payload: { username, password }

128

}),

129

logout: () => ({ type: "LOGOUT" }),

130

updateProfile: (profile: object) => ({

131

type: "UPDATE_PROFILE",

132

payload: profile

133

})

134

};

135

```

136

137

## Action Types

138

139

### Base Action Types

140

141

The fundamental action types that all Redux actions must extend.

142

143

```typescript { .api }

144

/**

145

* An action is a plain object that represents an intention to change the state

146

* @template T - The type of the action's type tag

147

*/

148

type Action<T extends string = string> = {

149

type: T;

150

};

151

152

/**

153

* An Action type which accepts any other properties

154

* This is mainly for the use of the Reducer type

155

*/

156

interface UnknownAction extends Action {

157

[extraProps: string]: unknown;

158

}

159

160

/**

161

* An Action type which accepts any other properties

162

* @deprecated Use Action or UnknownAction instead

163

*/

164

interface AnyAction extends Action {

165

[extraProps: string]: any;

166

}

167

```

168

169

**Usage Examples:**

170

171

```typescript

172

// Basic action

173

const basicAction: Action = { type: "BASIC_ACTION" };

174

175

// Action with specific type

176

const specificAction: Action<"SPECIFIC_TYPE"> = { type: "SPECIFIC_TYPE" };

177

178

// Action with payload using UnknownAction

179

const actionWithPayload: UnknownAction = {

180

type: "WITH_PAYLOAD",

181

payload: { data: "some data" },

182

meta: { timestamp: Date.now() }

183

};

184

185

// Typed action interface

186

interface CounterAction extends Action {

187

type: "INCREMENT" | "DECREMENT" | "SET_COUNT";

188

payload?: number;

189

}

190

191

const counterActions: CounterAction[] = [

192

{ type: "INCREMENT" },

193

{ type: "DECREMENT" },

194

{ type: "SET_COUNT", payload: 10 }

195

];

196

```

197

198

## Advanced Patterns

199

200

### Async Action Creators

201

202

Action creators that return functions (thunks) for async operations:

203

204

```typescript

205

// Async action creator (requires redux-thunk middleware)

206

const fetchUser = (userId: string) => {

207

return async (dispatch: Dispatch, getState: () => any) => {

208

dispatch({ type: "FETCH_USER_START" });

209

210

try {

211

const user = await api.getUser(userId);

212

dispatch({ type: "FETCH_USER_SUCCESS", payload: user });

213

} catch (error) {

214

dispatch({ type: "FETCH_USER_ERROR", payload: error.message });

215

}

216

};

217

};

218

219

// Bind async action creators

220

const boundAsyncActions = bindActionCreators({

221

fetchUser,

222

fetchPosts: (userId: string) => async (dispatch: Dispatch) => {

223

// async logic

224

}

225

}, store.dispatch);

226

```

227

228

### Action Creator Factories

229

230

Functions that create action creators:

231

232

```typescript

233

// Action creator factory

234

const createAsyncActionCreators = (entityName: string) => ({

235

request: () => ({ type: `${entityName.toUpperCase()}_REQUEST` }),

236

success: (data: any) => ({

237

type: `${entityName.toUpperCase()}_SUCCESS`,

238

payload: data

239

}),

240

failure: (error: string) => ({

241

type: `${entityName.toUpperCase()}_FAILURE`,

242

payload: error

243

})

244

});

245

246

// Create action creators for different entities

247

const userActions = createAsyncActionCreators("user");

248

const postActions = createAsyncActionCreators("post");

249

250

// Bind them to dispatch

251

const boundUserActions = bindActionCreators(userActions, store.dispatch);

252

```

253

254

### Conditional Action Binding

255

256

Selectively bind action creators based on conditions:

257

258

```typescript

259

const createBoundActions = (user: User, dispatch: Dispatch) => {

260

const baseActions = { logout, updateProfile };

261

262

if (user.role === "admin") {

263

return bindActionCreators({

264

...baseActions,

265

deleteUser,

266

banUser,

267

promoteUser

268

}, dispatch);

269

}

270

271

return bindActionCreators(baseActions, dispatch);

272

};

273

```

274

275

### Type-Safe Action Creators

276

277

Creating fully type-safe action creators with TypeScript:

278

279

```typescript

280

// Define action types

281

type UserActionTypes =

282

| { type: "SET_USER"; payload: User }

283

| { type: "CLEAR_USER" }

284

| { type: "UPDATE_USER_FIELD"; payload: { field: keyof User; value: any } };

285

286

// Type-safe action creators

287

const userActionCreators = {

288

setUser: (user: User): UserActionTypes => ({

289

type: "SET_USER",

290

payload: user

291

}),

292

clearUser: (): UserActionTypes => ({

293

type: "CLEAR_USER"

294

}),

295

updateUserField: <K extends keyof User>(

296

field: K,

297

value: User[K]

298

): UserActionTypes => ({

299

type: "UPDATE_USER_FIELD",

300

payload: { field, value }

301

})

302

};

303

304

// Bind with full type safety

305

const boundUserActions = bindActionCreators(userActionCreators, store.dispatch);

306

```