or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

clients.mdexceptions.mdindex.mdintegration.mdmanagers.mdnamespaces.mdservers.md

namespaces.mddocs/

0

# Namespace Classes

1

2

Class-based event handlers that organize Socket.IO communication into logical namespaces. Namespaces enable modular application design by separating different functional areas and providing inheritance-based event handling patterns.

3

4

## Capabilities

5

6

### Namespace

7

8

Server-side base class for creating class-based event handlers in synchronous applications. Provides method-based event handling and access to server functionality through inheritance.

9

10

```python { .api }

11

class Namespace:

12

"""

13

Base class for server-side class-based namespaces (synchronous).

14

15

Inherits from: BaseServerNamespace

16

17

Attributes:

18

namespace (str): Namespace path (default: '/')

19

server: Reference to the Socket.IO server instance

20

"""

21

22

def __init__(self, namespace='/'):

23

"""

24

Initialize the namespace.

25

26

Args:

27

namespace (str): Namespace path (default: '/')

28

"""

29

30

def trigger_event(self, event, *args):

31

"""

32

Dispatch events to handler methods.

33

34

Args:

35

event (str): Event name

36

*args: Event arguments

37

38

Returns:

39

Handler method return value

40

"""

41

42

def emit(self, event, data=None, to=None, room=None, skip_sid=None, namespace=None, callback=None):

43

"""

44

Emit an event to connected clients.

45

46

Args:

47

event (str): Event name

48

data: Event data to send

49

to (str or list): Target client session ID(s)

50

room (str or list): Target room name(s)

51

skip_sid (str): Skip this client session ID

52

namespace (str): Target namespace (defaults to this namespace)

53

callback (callable): Callback function for response

54

"""

55

56

def send(self, data, to=None, room=None, skip_sid=None, namespace=None, callback=None):

57

"""

58

Send a message event to connected clients.

59

60

Args:

61

data: Message data to send

62

to (str or list): Target client session ID(s)

63

room (str or list): Target room name(s)

64

skip_sid (str): Skip this client session ID

65

namespace (str): Target namespace (defaults to this namespace)

66

callback (callable): Callback function for response

67

"""

68

69

def call(self, event, data=None, to=None, sid=None, namespace=None, timeout=60):

70

"""

71

Emit an event and wait for a response from a specific client.

72

73

Args:

74

event (str): Event name

75

data: Event data to send

76

to (str): Target client session ID (deprecated, use sid)

77

sid (str): Target client session ID

78

namespace (str): Target namespace (defaults to this namespace)

79

timeout (int): Response timeout in seconds

80

81

Returns:

82

Response data from client

83

84

Raises:

85

TimeoutError: No response received within timeout

86

"""

87

88

def enter_room(self, sid, room, namespace=None):

89

"""

90

Add a client to a room.

91

92

Args:

93

sid (str): Client session ID

94

room (str): Room name

95

namespace (str): Target namespace (defaults to this namespace)

96

"""

97

98

def leave_room(self, sid, room, namespace=None):

99

"""

100

Remove a client from a room.

101

102

Args:

103

sid (str): Client session ID

104

room (str): Room name

105

namespace (str): Target namespace (defaults to this namespace)

106

"""

107

108

def close_room(self, room, namespace=None):

109

"""

110

Remove all clients from a room and delete the room.

111

112

Args:

113

room (str): Room name

114

namespace (str): Target namespace (defaults to this namespace)

115

"""

116

117

def rooms(self, sid, namespace=None):

118

"""

119

Get the list of rooms a client has joined.

120

121

Args:

122

sid (str): Client session ID

123

namespace (str): Target namespace (defaults to this namespace)

124

125

Returns:

126

list: Room names the client has joined

127

"""

128

129

def get_session(self, sid, namespace=None):

130

"""

131

Get the session data for a client.

132

133

Args:

134

sid (str): Client session ID

135

namespace (str): Target namespace (defaults to this namespace)

136

137

Returns:

138

dict: Session data

139

"""

140

141

def save_session(self, sid, session, namespace=None):

142

"""

143

Save session data for a client.

144

145

Args:

146

sid (str): Client session ID

147

session (dict): Session data to save

148

namespace (str): Target namespace (defaults to this namespace)

149

"""

150

151

def session(self, sid, namespace=None):

152

"""

153

Access client session data with context manager.

154

155

Args:

156

sid (str): Client session ID

157

namespace (str): Target namespace (defaults to this namespace)

158

159

Returns:

160

Context manager for session access

161

"""

162

163

def disconnect(self, sid, namespace=None):

164

"""

165

Disconnect a client.

166

167

Args:

168

sid (str): Client session ID

169

namespace (str): Target namespace (defaults to this namespace)

170

"""

171

172

# Event handler methods (override in subclass)

173

def on_connect(self, sid, environ):

174

"""

175

Called when a client connects.

176

177

Args:

178

sid (str): Client session ID

179

environ (dict): WSGI environ dictionary

180

"""

181

pass

182

183

def on_disconnect(self, sid):

184

"""

185

Called when a client disconnects.

186

187

Args:

188

sid (str): Client session ID

189

"""

190

pass

191

192

def on_message(self, sid, data):

193

"""

194

Called when a client sends a message event.

195

196

Args:

197

sid (str): Client session ID

198

data: Message data

199

"""

200

pass

201

```

202

203

#### Usage Example

204

205

```python

206

import socketio

207

208

class ChatNamespace(socketio.Namespace):

209

def on_connect(self, sid, environ):

210

print(f'Client {sid} connected to chat namespace')

211

self.enter_room(sid, 'lobby')

212

self.emit('welcome', {'message': 'Welcome to chat!'}, room=sid)

213

214

def on_disconnect(self, sid):

215

print(f'Client {sid} disconnected from chat')

216

217

def on_join_room(self, sid, data):

218

room = data['room']

219

self.enter_room(sid, room)

220

self.emit('status', {'message': f'Joined {room}'}, room=sid)

221

self.emit('user_joined', {'sid': sid}, room=room, skip_sid=sid)

222

223

def on_leave_room(self, sid, data):

224

room = data['room']

225

self.leave_room(sid, room)

226

self.emit('user_left', {'sid': sid}, room=room)

227

228

def on_chat_message(self, sid, data):

229

# Get user info from session

230

with self.session(sid) as session:

231

username = session.get('username', 'Anonymous')

232

233

room = data.get('room', 'lobby')

234

message = {

235

'username': username,

236

'message': data['message'],

237

'timestamp': time.time()

238

}

239

240

# Broadcast to room

241

self.emit('message', message, room=room)

242

243

def on_set_username(self, sid, data):

244

with self.session(sid) as session:

245

session['username'] = data['username']

246

247

self.emit('username_set', {'success': True}, room=sid)

248

249

class GameNamespace(socketio.Namespace):

250

def __init__(self):

251

super().__init__('/game')

252

self.games = {}

253

254

def on_connect(self, sid, environ):

255

print(f'Player {sid} connected to game namespace')

256

257

def on_create_game(self, sid, data):

258

game_id = data['game_id']

259

self.games[game_id] = {'players': [sid], 'status': 'waiting'}

260

self.enter_room(sid, game_id)

261

self.emit('game_created', {'game_id': game_id}, room=sid)

262

263

def on_join_game(self, sid, data):

264

game_id = data['game_id']

265

if game_id in self.games:

266

self.games[game_id]['players'].append(sid)

267

self.enter_room(sid, game_id)

268

self.emit('player_joined', {'sid': sid}, room=game_id)

269

270

# Start game if enough players

271

if len(self.games[game_id]['players']) >= 2:

272

self.games[game_id]['status'] = 'playing'

273

self.emit('game_started', room=game_id)

274

275

# Register namespaces with server

276

sio = socketio.Server()

277

sio.register_namespace(ChatNamespace('/chat'))

278

sio.register_namespace(GameNamespace())

279

```

280

281

### AsyncNamespace

282

283

Asynchronous version of the Namespace class for server-side class-based event handlers in asyncio applications.

284

285

```python { .api }

286

class AsyncNamespace:

287

"""

288

Base class for asyncio server-side class-based namespaces.

289

290

Inherits from: BaseServerNamespace

291

292

Attributes:

293

namespace (str): Namespace path (default: '/')

294

server: Reference to the AsyncServer instance

295

"""

296

297

def __init__(self, namespace='/'):

298

"""

299

Initialize the async namespace.

300

301

Args:

302

namespace (str): Namespace path (default: '/')

303

"""

304

305

async def trigger_event(self, event, *args):

306

"""

307

Dispatch events to async handler methods.

308

309

Args:

310

event (str): Event name

311

*args: Event arguments

312

313

Returns:

314

Handler method return value

315

"""

316

317

async def emit(self, event, data=None, to=None, room=None, skip_sid=None, namespace=None, callback=None):

318

"""

319

Emit an event to connected clients.

320

321

Args:

322

event (str): Event name

323

data: Event data to send

324

to (str or list): Target client session ID(s)

325

room (str or list): Target room name(s)

326

skip_sid (str): Skip this client session ID

327

namespace (str): Target namespace (defaults to this namespace)

328

callback (coroutine): Async callback function for response

329

"""

330

331

async def send(self, data, to=None, room=None, skip_sid=None, namespace=None, callback=None):

332

"""

333

Send a message event to connected clients.

334

335

Args:

336

data: Message data to send

337

to (str or list): Target client session ID(s)

338

room (str or list): Target room name(s)

339

skip_sid (str): Skip this client session ID

340

namespace (str): Target namespace (defaults to this namespace)

341

callback (coroutine): Async callback function for response

342

"""

343

344

async def call(self, event, data=None, to=None, sid=None, namespace=None, timeout=60):

345

"""

346

Emit an event and wait for a response from a specific client.

347

348

Args:

349

event (str): Event name

350

data: Event data to send

351

to (str): Target client session ID (deprecated, use sid)

352

sid (str): Target client session ID

353

namespace (str): Target namespace (defaults to this namespace)

354

timeout (int): Response timeout in seconds

355

356

Returns:

357

Response data from client

358

359

Raises:

360

TimeoutError: No response received within timeout

361

"""

362

363

async def enter_room(self, sid, room, namespace=None):

364

"""

365

Add a client to a room.

366

367

Args:

368

sid (str): Client session ID

369

room (str): Room name

370

namespace (str): Target namespace (defaults to this namespace)

371

"""

372

373

async def leave_room(self, sid, room, namespace=None):

374

"""

375

Remove a client from a room.

376

377

Args:

378

sid (str): Client session ID

379

room (str): Room name

380

namespace (str): Target namespace (defaults to this namespace)

381

"""

382

383

async def close_room(self, room, namespace=None):

384

"""

385

Remove all clients from a room and delete the room.

386

387

Args:

388

room (str): Room name

389

namespace (str): Target namespace (defaults to this namespace)

390

"""

391

392

async def rooms(self, sid, namespace=None):

393

"""

394

Get the list of rooms a client has joined.

395

396

Args:

397

sid (str): Client session ID

398

namespace (str): Target namespace (defaults to this namespace)

399

400

Returns:

401

list: Room names the client has joined

402

"""

403

404

async def get_session(self, sid, namespace=None):

405

"""

406

Get the session data for a client.

407

408

Args:

409

sid (str): Client session ID

410

namespace (str): Target namespace (defaults to this namespace)

411

412

Returns:

413

dict: Session data

414

"""

415

416

async def save_session(self, sid, session, namespace=None):

417

"""

418

Save session data for a client.

419

420

Args:

421

sid (str): Client session ID

422

session (dict): Session data to save

423

namespace (str): Target namespace (defaults to this namespace)

424

"""

425

426

def session(self, sid, namespace=None):

427

"""

428

Access client session data with async context manager.

429

430

Args:

431

sid (str): Client session ID

432

namespace (str): Target namespace (defaults to this namespace)

433

434

Returns:

435

Async context manager for session access

436

"""

437

438

async def disconnect(self, sid, namespace=None):

439

"""

440

Disconnect a client.

441

442

Args:

443

sid (str): Client session ID

444

namespace (str): Target namespace (defaults to this namespace)

445

"""

446

447

# Async event handler methods (override in subclass)

448

async def on_connect(self, sid, environ):

449

"""

450

Called when a client connects.

451

452

Args:

453

sid (str): Client session ID

454

environ (dict): WSGI environ dictionary

455

"""

456

pass

457

458

async def on_disconnect(self, sid):

459

"""

460

Called when a client disconnects.

461

462

Args:

463

sid (str): Client session ID

464

"""

465

pass

466

467

async def on_message(self, sid, data):

468

"""

469

Called when a client sends a message event.

470

471

Args:

472

sid (str): Client session ID

473

data: Message data

474

"""

475

pass

476

```

477

478

#### Usage Example

479

480

```python

481

import asyncio

482

import socketio

483

484

class AsyncChatNamespace(socketio.AsyncNamespace):

485

def __init__(self):

486

super().__init__('/chat')

487

self.user_cache = {}

488

489

async def on_connect(self, sid, environ):

490

print(f'Client {sid} connected to async chat namespace')

491

await self.enter_room(sid, 'lobby')

492

await self.emit('welcome', {'message': 'Welcome!'}, room=sid)

493

494

async def on_disconnect(self, sid):

495

print(f'Client {sid} disconnected from async chat')

496

# Clean up user cache

497

if sid in self.user_cache:

498

del self.user_cache[sid]

499

500

async def on_join_room(self, sid, data):

501

room = data['room']

502

await self.enter_room(sid, room)

503

await self.emit('status', {'message': f'Joined {room}'}, room=sid)

504

await self.emit('user_joined', {'sid': sid}, room=room, skip_sid=sid)

505

506

async def on_chat_message(self, sid, data):

507

# Async session access

508

async with self.session(sid) as session:

509

username = session.get('username', 'Anonymous')

510

511

# Simulate async processing (e.g., content filtering)

512

await asyncio.sleep(0.01)

513

514

room = data.get('room', 'lobby')

515

message = {

516

'username': username,

517

'message': data['message'],

518

'timestamp': time.time()

519

}

520

521

# Broadcast to room

522

await self.emit('message', message, room=room)

523

524

async def on_get_user_info(self, sid, data):

525

# Simulate async database lookup

526

user_id = data['user_id']

527

user_info = await self.fetch_user_info(user_id)

528

return {'user_info': user_info}

529

530

async def fetch_user_info(self, user_id):

531

# Simulate async database call

532

await asyncio.sleep(0.1)

533

return {'id': user_id, 'name': f'User {user_id}', 'status': 'online'}

534

535

class AsyncGameNamespace(socketio.AsyncNamespace):

536

def __init__(self):

537

super().__init__('/game')

538

self.games = {}

539

self.game_lock = asyncio.Lock()

540

541

async def on_connect(self, sid, environ):

542

print(f'Player {sid} connected to async game namespace')

543

544

async def on_create_game(self, sid, data):

545

game_id = data['game_id']

546

547

async with self.game_lock:

548

self.games[game_id] = {

549

'players': [sid],

550

'status': 'waiting',

551

'created_at': time.time()

552

}

553

554

await self.enter_room(sid, game_id)

555

await self.emit('game_created', {'game_id': game_id}, room=sid)

556

557

async def on_join_game(self, sid, data):

558

game_id = data['game_id']

559

560

async with self.game_lock:

561

if game_id in self.games:

562

self.games[game_id]['players'].append(sid)

563

await self.enter_room(sid, game_id)

564

await self.emit('player_joined', {'sid': sid}, room=game_id)

565

566

# Start game if enough players

567

if len(self.games[game_id]['players']) >= 2:

568

self.games[game_id]['status'] = 'playing'

569

await self.emit('game_started', room=game_id)

570

571

# Start game logic asynchronously

572

asyncio.create_task(self.run_game(game_id))

573

574

async def run_game(self, game_id):

575

# Simulate async game logic

576

await asyncio.sleep(1)

577

await self.emit('game_update', {'status': 'running'}, room=game_id)

578

579

# Register namespaces with async server

580

sio = socketio.AsyncServer()

581

sio.register_namespace(AsyncChatNamespace())

582

sio.register_namespace(AsyncGameNamespace())

583

```

584

585

### ClientNamespace

586

587

Base class for client-side class-based event handlers in synchronous client applications.

588

589

```python { .api }

590

class ClientNamespace:

591

"""

592

Base class for client-side class-based namespaces (synchronous).

593

594

Inherits from: BaseClientNamespace

595

596

Attributes:

597

namespace (str): Namespace path (default: '/')

598

client: Reference to the Client instance

599

"""

600

601

def __init__(self, namespace='/'):

602

"""

603

Initialize the client namespace.

604

605

Args:

606

namespace (str): Namespace path (default: '/')

607

"""

608

609

def trigger_event(self, event, *args):

610

"""

611

Dispatch events to handler methods.

612

613

Args:

614

event (str): Event name

615

*args: Event arguments

616

617

Returns:

618

Handler method return value

619

"""

620

621

def emit(self, event, data=None, namespace=None, callback=None):

622

"""

623

Emit an event to the server.

624

625

Args:

626

event (str): Event name

627

data: Event data to send

628

namespace (str): Target namespace (defaults to this namespace)

629

callback (callable): Callback function for response

630

"""

631

632

def send(self, data, namespace=None, callback=None):

633

"""

634

Send a message event to the server.

635

636

Args:

637

data: Message data to send

638

namespace (str): Target namespace (defaults to this namespace)

639

callback (callable): Callback function for response

640

"""

641

642

def call(self, event, data=None, namespace=None, timeout=60):

643

"""

644

Emit an event and wait for a response from the server.

645

646

Args:

647

event (str): Event name

648

data: Event data to send

649

namespace (str): Target namespace (defaults to this namespace)

650

timeout (int): Response timeout in seconds

651

652

Returns:

653

Response data from server

654

655

Raises:

656

TimeoutError: No response received within timeout

657

"""

658

659

def disconnect(self):

660

"""

661

Disconnect from the server.

662

"""

663

664

# Event handler methods (override in subclass)

665

def on_connect(self):

666

"""Called when connected to the server."""

667

pass

668

669

def on_disconnect(self):

670

"""Called when disconnected from the server."""

671

pass

672

673

def on_message(self, data):

674

"""Called when receiving a message event from the server."""

675

pass

676

```

677

678

#### Usage Example

679

680

```python

681

import socketio

682

683

class ChatClientNamespace(socketio.ClientNamespace):

684

def __init__(self):

685

super().__init__('/chat')

686

self.username = None

687

688

def on_connect(self):

689

print('Connected to chat namespace')

690

self.emit('set_username', {'username': 'Alice'})

691

692

def on_disconnect(self):

693

print('Disconnected from chat namespace')

694

695

def on_welcome(self, data):

696

print(f'Welcome message: {data["message"]}')

697

698

def on_message(self, data):

699

print(f'{data["username"]}: {data["message"]}')

700

701

def on_username_set(self, data):

702

if data['success']:

703

print('Username set successfully')

704

self.emit('join_room', {'room': 'general'})

705

706

def send_message(self, message, room='general'):

707

self.emit('chat_message', {

708

'message': message,

709

'room': room

710

})

711

712

# Use with client

713

sio = socketio.Client()

714

chat_ns = ChatClientNamespace()

715

sio.register_namespace(chat_ns)

716

717

sio.connect('http://localhost:5000')

718

719

# Send messages through namespace

720

chat_ns.send_message('Hello everyone!')

721

722

sio.wait()

723

```

724

725

### AsyncClientNamespace

726

727

Asynchronous version of ClientNamespace for client-side class-based event handlers in asyncio client applications.

728

729

```python { .api }

730

class AsyncClientNamespace:

731

"""

732

Base class for asyncio client-side class-based namespaces.

733

734

Inherits from: BaseClientNamespace

735

736

Attributes:

737

namespace (str): Namespace path (default: '/')

738

client: Reference to the AsyncClient instance

739

"""

740

741

def __init__(self, namespace='/'):

742

"""

743

Initialize the async client namespace.

744

745

Args:

746

namespace (str): Namespace path (default: '/')

747

"""

748

749

async def trigger_event(self, event, *args):

750

"""

751

Dispatch events to async handler methods.

752

753

Args:

754

event (str): Event name

755

*args: Event arguments

756

757

Returns:

758

Handler method return value

759

"""

760

761

async def emit(self, event, data=None, namespace=None, callback=None):

762

"""

763

Emit an event to the server.

764

765

Args:

766

event (str): Event name

767

data: Event data to send

768

namespace (str): Target namespace (defaults to this namespace)

769

callback (coroutine): Async callback function for response

770

"""

771

772

async def send(self, data, namespace=None, callback=None):

773

"""

774

Send a message event to the server.

775

776

Args:

777

data: Message data to send

778

namespace (str): Target namespace (defaults to this namespace)

779

callback (coroutine): Async callback function for response

780

"""

781

782

async def call(self, event, data=None, namespace=None, timeout=60):

783

"""

784

Emit an event and wait for a response from the server.

785

786

Args:

787

event (str): Event name

788

data: Event data to send

789

namespace (str): Target namespace (defaults to this namespace)

790

timeout (int): Response timeout in seconds

791

792

Returns:

793

Response data from server

794

795

Raises:

796

TimeoutError: No response received within timeout

797

"""

798

799

async def disconnect(self):

800

"""

801

Disconnect from the server.

802

"""

803

804

# Async event handler methods (override in subclass)

805

async def on_connect(self):

806

"""Called when connected to the server."""

807

pass

808

809

async def on_disconnect(self):

810

"""Called when disconnected from the server."""

811

pass

812

813

async def on_message(self, data):

814

"""Called when receiving a message event from the server."""

815

pass

816

```

817

818

#### Usage Example

819

820

```python

821

import asyncio

822

import socketio

823

824

class AsyncChatClientNamespace(socketio.AsyncClientNamespace):

825

def __init__(self):

826

super().__init__('/chat')

827

self.message_queue = asyncio.Queue()

828

829

async def on_connect(self):

830

print('Connected to async chat namespace')

831

await self.emit('set_username', {'username': 'Bob'})

832

833

async def on_disconnect(self):

834

print('Disconnected from async chat namespace')

835

836

async def on_welcome(self, data):

837

print(f'Welcome message: {data["message"]}')

838

839

async def on_message(self, data):

840

print(f'{data["username"]}: {data["message"]}')

841

# Add to processing queue

842

await self.message_queue.put(data)

843

844

async def on_username_set(self, data):

845

if data['success']:

846

print('Username set successfully')

847

await self.emit('join_room', {'room': 'general'})

848

849

async def send_message(self, message, room='general'):

850

await self.emit('chat_message', {

851

'message': message,

852

'room': room

853

})

854

855

async def process_messages(self):

856

"""Background task to process incoming messages"""

857

while True:

858

try:

859

message = await asyncio.wait_for(

860

self.message_queue.get(), timeout=1.0

861

)

862

# Process message asynchronously

863

await self.handle_message(message)

864

except asyncio.TimeoutError:

865

continue

866

867

async def handle_message(self, message):

868

# Simulate async message processing

869

await asyncio.sleep(0.1)

870

print(f'Processed message from {message["username"]}')

871

872

async def main():

873

sio = socketio.AsyncClient()

874

chat_ns = AsyncChatClientNamespace()

875

sio.register_namespace(chat_ns)

876

877

await sio.connect('http://localhost:5000')

878

879

# Start message processing task

880

process_task = asyncio.create_task(chat_ns.process_messages())

881

882

# Send some messages

883

await chat_ns.send_message('Hello async world!')

884

await asyncio.sleep(1)

885

await chat_ns.send_message('How is everyone?')

886

887

# Wait for events

888

await sio.wait()

889

890

# Run the async client

891

asyncio.run(main())

892

```

893

894

## Namespace Registration

895

896

Namespaces must be registered with their respective servers or clients:

897

898

```python

899

# Server namespace registration

900

sio = socketio.Server()

901

sio.register_namespace(ChatNamespace('/chat'))

902

sio.register_namespace(GameNamespace('/game'))

903

904

# Client namespace registration

905

client = socketio.Client()

906

client.register_namespace(ChatClientNamespace('/chat'))

907

client.register_namespace(GameClientNamespace('/game'))

908

909

# Async server namespace registration

910

async_sio = socketio.AsyncServer()

911

async_sio.register_namespace(AsyncChatNamespace('/chat'))

912

913

# Async client namespace registration

914

async_client = socketio.AsyncClient()

915

async_client.register_namespace(AsyncChatClientNamespace('/chat'))

916

```