or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

channel-management.mddns-queries.mderror-handling.mdhost-resolution.mdindex.mdutilities.md

host-resolution.mddocs/

0

# Host Resolution

1

2

Traditional host resolution functions providing asynchronous versions of standard socket library operations. These functions offer familiar interfaces for hostname-to-address and address-to-hostname resolution with callback-based completion.

3

4

## Capabilities

5

6

### Forward Resolution

7

8

Resolve hostnames to IP addresses using traditional gethostbyname-style operations.

9

10

```python { .api }

11

def gethostbyname(self, name: str, family, callback) -> None:

12

"""

13

Resolve a hostname to IP addresses for the specified address family.

14

15

Args:

16

name: str - Hostname to resolve

17

family: socket.AddressFamily - Address family (socket.AF_INET or socket.AF_INET6)

18

callback: Callable - Function called with (result, error) when complete

19

20

Raises:

21

TypeError: If callback is not callable

22

RuntimeError: If channel is destroyed

23

"""

24

```

25

26

**Usage Example:**

27

28

```python

29

import socket

30

import pycares

31

32

def host_callback(result, error):

33

if error:

34

print(f'Error: {pycares.errno.strerror(error)}')

35

return

36

37

print(f'Hostname: {result.name}')

38

print(f'Addresses: {result.addresses}')

39

if result.aliases:

40

print(f'Aliases: {result.aliases}')

41

42

channel = pycares.Channel()

43

44

# Resolve IPv4 addresses

45

channel.gethostbyname('google.com', socket.AF_INET, host_callback)

46

47

# Resolve IPv6 addresses

48

channel.gethostbyname('google.com', socket.AF_INET6, host_callback)

49

```

50

51

### Reverse Resolution

52

53

Resolve IP addresses back to hostnames.

54

55

```python { .api }

56

def gethostbyaddr(self, addr: str, callback) -> None:

57

"""

58

Resolve an IP address to hostname(s).

59

60

Args:

61

addr: str - IP address to resolve (IPv4 or IPv6)

62

callback: Callable - Function called with (result, error) when complete

63

64

Raises:

65

ValueError: If IP address format is invalid

66

TypeError: If callback is not callable

67

RuntimeError: If channel is destroyed

68

"""

69

```

70

71

**Usage Example:**

72

73

```python

74

def addr_callback(result, error):

75

if error:

76

print(f'Error: {pycares.errno.strerror(error)}')

77

return

78

79

print(f'Primary hostname: {result.name}')

80

if result.aliases:

81

print(f'Aliases: {result.aliases}')

82

print(f'Addresses: {result.addresses}')

83

84

channel = pycares.Channel()

85

86

# Reverse resolve IPv4 address

87

channel.gethostbyaddr('8.8.8.8', addr_callback)

88

89

# Reverse resolve IPv6 address

90

channel.gethostbyaddr('2001:4860:4860::8888', addr_callback)

91

```

92

93

### Address Info Resolution

94

95

Modern getaddrinfo-style resolution supporting service names, protocol specifications, and comprehensive address information.

96

97

```python { .api }

98

def getaddrinfo(

99

self,

100

host: str,

101

port, # Union[int, str, None]

102

callback,

103

family=0, # socket.AddressFamily

104

type=0, # int (socket type)

105

proto=0, # int (protocol)

106

flags=0 # int (AI_* flags)

107

) -> None:

108

"""

109

Resolve hostname and service to socket addresses with detailed information.

110

111

Args:

112

host: str - Hostname to resolve

113

port: Union[int, str, None] - Port number or service name (e.g., 'http', 80, None)

114

callback: Callable - Function called with (result, error) when complete

115

family: socket.AddressFamily - Address family filter (0 for any)

116

type: int - Socket type (socket.SOCK_STREAM, socket.SOCK_DGRAM, etc.)

117

proto: int - Protocol (socket.IPPROTO_TCP, socket.IPPROTO_UDP, etc.)

118

flags: int - Additional flags for resolution behavior

119

120

Raises:

121

TypeError: If callback is not callable

122

RuntimeError: If channel is destroyed

123

"""

124

```

125

126

**Usage Example:**

127

128

```python

129

import socket

130

131

def addrinfo_callback(result, error):

132

if error:

133

print(f'Error: {pycares.errno.strerror(error)}')

134

return

135

136

print('CNAME records:')

137

for cname in result.cnames:

138

print(f' {cname.alias} -> {cname.name} (TTL: {cname.ttl})')

139

140

print('Address records:')

141

for node in result.nodes:

142

addr = node.addr

143

if node.family == socket.AF_INET:

144

print(f' IPv4: {addr[0]}:{addr[1]} (TTL: {node.ttl})')

145

elif node.family == socket.AF_INET6:

146

print(f' IPv6: [{addr[0]}]:{addr[1]} (TTL: {node.ttl})')

147

148

channel = pycares.Channel()

149

150

# Resolve with port number

151

channel.getaddrinfo('google.com', 80, addrinfo_callback)

152

153

# Resolve with service name

154

channel.getaddrinfo('google.com', 'http', addrinfo_callback)

155

156

# Resolve with family filter

157

channel.getaddrinfo('google.com', 443, addrinfo_callback, family=socket.AF_INET6)

158

159

# Resolve without port

160

channel.getaddrinfo('google.com', None, addrinfo_callback)

161

```

162

163

### Name Info Resolution

164

165

Resolve socket addresses back to hostname and service names.

166

167

```python { .api }

168

def getnameinfo(self, address, flags: int, callback) -> None:

169

"""

170

Resolve socket address to hostname and service name.

171

172

Args:

173

address: Union[tuple[str, int], tuple[str, int, int, int]] - Socket address

174

IPv4: (host, port) tuple

175

IPv6: (host, port, flowinfo, scope_id) tuple

176

flags: int - Bitwise OR of ARES_NI_* flags controlling resolution behavior

177

callback: Callable - Function called with (result, error) when complete

178

179

Raises:

180

ValueError: If address format is invalid

181

TypeError: If callback is not callable

182

RuntimeError: If channel is destroyed

183

"""

184

```

185

186

**Usage Example:**

187

188

```python

189

def nameinfo_callback(result, error):

190

if error:

191

print(f'Error: {pycares.errno.strerror(error)}')

192

return

193

194

print(f'Hostname: {result.node}')

195

if result.service:

196

print(f'Service: {result.service}')

197

198

channel = pycares.Channel()

199

200

# Resolve IPv4 address and port

201

channel.getnameinfo(

202

('8.8.8.8', 53),

203

pycares.ARES_NI_LOOKUPHOST | pycares.ARES_NI_LOOKUPSERVICE,

204

nameinfo_callback

205

)

206

207

# Resolve IPv6 address

208

channel.getnameinfo(

209

('2001:4860:4860::8888', 53, 0, 0),

210

pycares.ARES_NI_LOOKUPHOST,

211

nameinfo_callback

212

)

213

214

# Get numeric host only

215

channel.getnameinfo(

216

('192.168.1.1', 80),

217

pycares.ARES_NI_NUMERICHOST | pycares.ARES_NI_NUMERICSERV,

218

nameinfo_callback

219

)

220

```

221

222

## Result Types

223

224

### Host Result

225

226

Result object for gethostbyname and gethostbyaddr operations.

227

228

```python { .api }

229

class ares_host_result:

230

"""Host resolution result."""

231

name: str # Primary hostname

232

aliases: list[str] # List of hostname aliases

233

addresses: list[str] # List of IP addresses

234

```

235

236

### Address Info Result

237

238

Comprehensive result object for getaddrinfo operations.

239

240

```python { .api }

241

class ares_addrinfo_result:

242

"""Address info resolution result."""

243

cnames: list[ares_addrinfo_cname_result] # CNAME chain information

244

nodes: list[ares_addrinfo_node_result] # Address information nodes

245

246

class ares_addrinfo_cname_result:

247

"""CNAME information in address resolution."""

248

ttl: int # Time to live

249

alias: str # Alias name

250

name: str # Canonical name

251

252

class ares_addrinfo_node_result:

253

"""Individual address node in getaddrinfo result."""

254

ttl: int # Time to live

255

flags: int # Address flags

256

family: int # Address family (AF_INET or AF_INET6)

257

socktype: int # Socket type

258

protocol: int # Protocol number

259

addr: tuple # Address tuple (format depends on family)

260

# IPv4: (address_str, port)

261

# IPv6: (address_str, port, flowinfo, scope_id)

262

```

263

264

### Name Info Result

265

266

Result object for getnameinfo operations.

267

268

```python { .api }

269

class ares_nameinfo_result:

270

"""Name info resolution result."""

271

node: str # Hostname (may be None if not requested)

272

service: str # Service name (may be None if not requested or unavailable)

273

```

274

275

## Name Info Flags

276

277

Flags controlling getnameinfo behavior:

278

279

```python { .api }

280

# Don't return fully qualified domain name

281

ARES_NI_NOFQDN = 1

282

283

# Return numeric host address instead of name

284

ARES_NI_NUMERICHOST = 2

285

286

# Require hostname (fail if not available)

287

ARES_NI_NAMEREQD = 4

288

289

# Return numeric service instead of name

290

ARES_NI_NUMERICSERV = 8

291

292

# Datagram service (affects service name lookup)

293

ARES_NI_DGRAM = 16

294

295

# TCP service

296

ARES_NI_TCP = 32

297

298

# UDP service

299

ARES_NI_UDP = 64

300

301

# SCTP service

302

ARES_NI_SCTP = 128

303

304

# DCCP service

305

ARES_NI_DCCP = 256

306

307

# Return numeric scope identifier

308

ARES_NI_NUMERICSCOPE = 512

309

310

# Lookup hostname

311

ARES_NI_LOOKUPHOST = 1024

312

313

# Lookup service name

314

ARES_NI_LOOKUPSERVICE = 2048

315

316

# Use IDNA encoding

317

ARES_NI_IDN = 4096

318

319

# Allow unassigned code points in IDNA

320

ARES_NI_IDN_ALLOW_UNASSIGNED = 8192

321

322

# Use STD3 ASCII rules for IDNA

323

ARES_NI_IDN_USE_STD3_ASCII_RULES = 16384

324

```

325

326

## Type Aliases

327

328

Type definitions for address tuples:

329

330

```python { .api }

331

# IPv4 address tuple: (address, port)

332

IP4 = tuple[str, int]

333

334

# IPv6 address tuple: (address, port, flowinfo, scope_id)

335

IP6 = tuple[str, int, int, int]

336

```

337

338

## Advanced Usage Examples

339

340

### Parallel Resolution

341

342

```python

343

import socket

344

import pycares

345

346

results = {}

347

pending = 0

348

349

def collect_result(name, result, error):

350

global pending

351

results[name] = (result, error)

352

pending -= 1

353

354

def resolve_multiple_hosts(channel, hostnames):

355

global pending

356

pending = len(hostnames)

357

358

for hostname in hostnames:

359

channel.gethostbyname(hostname, socket.AF_INET,

360

lambda r, e, h=hostname: collect_result(h, r, e))

361

362

# Wait for all to complete

363

while pending > 0:

364

wait_channel(channel)

365

366

return results

367

368

channel = pycares.Channel()

369

hosts = ['google.com', 'github.com', 'stackoverflow.com']

370

results = resolve_multiple_hosts(channel, hosts)

371

372

for host, (result, error) in results.items():

373

if error:

374

print(f'{host}: Error - {pycares.errno.strerror(error)}')

375

else:

376

print(f'{host}: {result.addresses[0]}')

377

```

378

379

### Service Discovery

380

381

```python

382

def discover_service(hostname, service_port):

383

"""Discover service endpoints for a hostname."""

384

def addrinfo_cb(result, error):

385

if error:

386

print(f'Service discovery failed: {pycares.errno.strerror(error)}')

387

return

388

389

print(f'Service endpoints for {hostname}:')

390

for node in result.nodes:

391

family = 'IPv4' if node.family == socket.AF_INET else 'IPv6'

392

addr_str = f'[{node.addr[0]}]' if node.family == socket.AF_INET6 else node.addr[0]

393

print(f' {family}: {addr_str}:{node.addr[1]} (TTL: {node.ttl})')

394

395

channel = pycares.Channel()

396

channel.getaddrinfo(hostname, service_port, addrinfo_cb,

397

type=socket.SOCK_STREAM, proto=socket.IPPROTO_TCP)

398

wait_channel(channel)

399

400

discover_service('www.google.com', 'https')

401

```