or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

analytics.mdcore-queries.mddialects.mdfunctions.mdindex.mdparameters-types.mdtables-schema.mdterms-expressions.md

parameters-types.mddocs/

0

# Parameters and Types

1

2

Parameter handling for prepared statements supporting multiple parameter styles (qmark, named, format), along with specialized data types for JSON operations, intervals, and database-specific types. These components enable safe parameter binding and advanced data type operations.

3

4

## Capabilities

5

6

### Parameter Types

7

8

Different parameter styles for prepared statements and parameterized queries.

9

10

```python { .api }

11

class Parameter:

12

"""Base class for SQL parameters."""

13

14

class QmarkParameter(Parameter):

15

def __init__(self, key):

16

"""

17

Question mark style parameter: ?

18

19

Parameters:

20

- key: Parameter identifier

21

"""

22

23

class NamedParameter(Parameter):

24

def __init__(self, key):

25

"""

26

Named style parameter: :name

27

28

Parameters:

29

- key: Parameter name

30

"""

31

32

class NumericParameter(Parameter):

33

def __init__(self, key):

34

"""

35

Numeric style parameter: :1, :2, etc.

36

37

Parameters:

38

- key: Parameter number

39

"""

40

41

class FormatParameter(Parameter):

42

def __init__(self, key):

43

"""

44

ANSI C printf style parameter: %s, %d, etc.

45

46

Parameters:

47

- key: Parameter format specifier

48

"""

49

50

class PyformatParameter(Parameter):

51

def __init__(self, key):

52

"""

53

Python format style parameter: %(name)s

54

55

Parameters:

56

- key: Parameter name

57

"""

58

```

59

60

**Usage Examples:**

61

62

```python

63

from pypika import Query, Table

64

from pypika.terms import QmarkParameter, NamedParameter, PyformatParameter

65

66

users = Table('users')

67

orders = Table('orders')

68

69

# Question mark parameters (SQLite, MySQL)

70

qmark_query = (Query.from_(users)

71

.select('*')

72

.where(users.age > QmarkParameter('age'))

73

.where(users.status == QmarkParameter('status')))

74

75

print(qmark_query.get_sql())

76

# SELECT * FROM "users" WHERE "age">? AND "status"=?

77

78

# Named parameters (PostgreSQL, Oracle)

79

named_query = (Query.from_(users)

80

.select('*')

81

.where(users.age > NamedParameter('min_age'))

82

.where(users.status == NamedParameter('user_status')))

83

84

print(named_query.get_sql())

85

# SELECT * FROM "users" WHERE "age">:min_age AND "status"=:user_status

86

87

# Python format parameters

88

pyformat_query = (Query.from_(users)

89

.select('*')

90

.where(users.age > PyformatParameter('min_age'))

91

.where(users.status == PyformatParameter('status')))

92

93

print(pyformat_query.get_sql())

94

# SELECT * FROM "users" WHERE "age">%(min_age)s AND "status"=%(status)s

95

96

# INSERT with parameters

97

insert_query = (Query.into(users)

98

.columns(users.name, users.email, users.age)

99

.insert(

100

NamedParameter('name'),

101

NamedParameter('email'),

102

NamedParameter('age')

103

))

104

105

# UPDATE with parameters

106

update_query = (Query.update(users)

107

.set(users.email, NamedParameter('new_email'))

108

.set(users.updated_at, NamedParameter('timestamp'))

109

.where(users.id == NamedParameter('user_id')))

110

```

111

112

### JSON Data Type

113

114

JSON field operations and path-based access for advanced JSON manipulation.

115

116

```python { .api }

117

class JSON:

118

def get_json_value(self, key_or_index) -> BasicCriterion:

119

"""

120

JSON -> operator: extract JSON value.

121

122

Parameters:

123

- key_or_index: Object key or array index

124

"""

125

126

def get_text_value(self, key_or_index) -> BasicCriterion:

127

"""

128

JSON ->> operator: extract JSON value as text.

129

130

Parameters:

131

- key_or_index: Object key or array index

132

"""

133

134

def get_path_json_value(self, path_json) -> BasicCriterion:

135

"""

136

JSON #> operator: extract JSON value at path.

137

138

Parameters:

139

- path_json: JSON path array

140

"""

141

142

def get_path_text_value(self, path_json) -> BasicCriterion:

143

"""

144

JSON #>> operator: extract JSON value at path as text.

145

146

Parameters:

147

- path_json: JSON path array

148

"""

149

150

def has_key(self, key) -> BasicCriterion:

151

"""

152

JSON ? operator: check if key exists.

153

154

Parameters:

155

- key: Key to check for existence

156

"""

157

158

def contains(self, other) -> BasicCriterion:

159

"""

160

JSON @> operator: check if contains value.

161

162

Parameters:

163

- other: JSON value to check containment

164

"""

165

166

def contained_by(self, other) -> BasicCriterion:

167

"""

168

JSON <@ operator: check if contained by value.

169

170

Parameters:

171

- other: JSON value to check containment by

172

"""

173

174

def has_keys(self, keys) -> BasicCriterion:

175

"""

176

JSON ?& operator: check if has all keys.

177

178

Parameters:

179

- keys: Array of keys to check

180

"""

181

182

def has_any_keys(self, keys) -> BasicCriterion:

183

"""

184

JSON ?| operator: check if has any keys.

185

186

Parameters:

187

- keys: Array of keys to check

188

"""

189

```

190

191

**Usage Examples:**

192

193

```python

194

from pypika import PostgreSQLQuery, Table, JSON

195

196

# PostgreSQL table with JSON columns

197

users = Table('users')

198

events = Table('events')

199

200

# JSON field operations

201

profile = users.profile # Assuming JSON/JSONB column

202

metadata = events.metadata

203

204

# Extract JSON values

205

query = (PostgreSQLQuery.from_(users)

206

.select(

207

users.id,

208

profile.get_text_value('name').as_('profile_name'),

209

profile.get_json_value('preferences').as_('user_prefs'),

210

profile.get_text_value('email').as_('profile_email')

211

))

212

213

# Path-based JSON extraction

214

query = (PostgreSQLQuery.from_(users)

215

.select(

216

users.id,

217

profile.get_path_text_value(['address', 'street']).as_('street'),

218

profile.get_path_text_value(['address', 'city']).as_('city'),

219

profile.get_path_json_value(['contact', 'phones']).as_('phone_numbers')

220

))

221

222

# JSON key existence checks

223

query = (PostgreSQLQuery.from_(users)

224

.select(users.id, users.name)

225

.where(profile.has_key('email'))

226

.where(profile.has_key('phone')))

227

228

# Multiple key checks

229

query = (PostgreSQLQuery.from_(users)

230

.select('*')

231

.where(profile.has_keys(['name', 'email', 'address']))

232

.where(profile.has_any_keys(['twitter', 'facebook', 'linkedin'])))

233

234

# JSON containment operations

235

query = (PostgreSQLQuery.from_(users)

236

.select('*')

237

.where(profile.contains({'subscription': 'premium'}))

238

.where(profile.contains({'preferences': {'newsletter': True}})))

239

240

# Complex JSON queries

241

query = (PostgreSQLQuery.from_(events)

242

.select(

243

events.id,

244

events.event_type,

245

metadata.get_text_value('source').as_('event_source'),

246

metadata.get_path_text_value(['device', 'type']).as_('device_type'),

247

metadata.get_path_json_value(['location', 'coordinates']).as_('coordinates')

248

)

249

.where(metadata.has_key('user_id'))

250

.where(metadata.get_text_value('status') == 'completed'))

251

252

# JSON aggregations

253

from pypika.functions import Count

254

query = (PostgreSQLQuery.from_(users)

255

.select(

256

profile.get_text_value('country').as_('country'),

257

Count('*').as_('user_count')

258

)

259

.where(profile.has_key('country'))

260

.groupby(profile.get_text_value('country')))

261

```

262

263

### Interval Data Type

264

265

Time and date interval expressions for temporal calculations and date arithmetic.

266

267

```python { .api }

268

class Interval:

269

def __init__(self, years=0, months=0, days=0, hours=0, minutes=0,

270

seconds=0, microseconds=0, quarters=0, weeks=0, dialect=None):

271

"""

272

Create time interval for date arithmetic.

273

274

Parameters:

275

- years: Number of years

276

- months: Number of months

277

- days: Number of days

278

- hours: Number of hours

279

- minutes: Number of minutes

280

- seconds: Number of seconds

281

- microseconds: Number of microseconds

282

- quarters: Number of quarters

283

- weeks: Number of weeks

284

- dialect: Database dialect for formatting

285

"""

286

```

287

288

**Usage Examples:**

289

290

```python

291

from pypika import Query, Table, Interval

292

from pypika.functions import Now, CurDate

293

294

users = Table('users')

295

subscriptions = Table('subscriptions')

296

events = Table('events')

297

298

# Basic interval operations

299

one_day = Interval(days=1)

300

one_week = Interval(weeks=1)

301

one_month = Interval(months=1)

302

one_year = Interval(years=1)

303

thirty_minutes = Interval(minutes=30)

304

305

# Date arithmetic with intervals

306

query = (Query.from_(users)

307

.select(

308

users.name,

309

users.created_at,

310

(users.created_at + one_year).as_('anniversary_date'),

311

(Now() - users.created_at).as_('account_age'),

312

(users.created_at + Interval(days=30)).as_('trial_end_date')

313

))

314

315

# Filter by time ranges

316

recent_users = (Query.from_(users)

317

.select('*')

318

.where(users.created_at > (Now() - Interval(days=30))))

319

320

old_users = (Query.from_(users)

321

.select('*')

322

.where(users.created_at < (Now() - Interval(years=2))))

323

324

# Subscription management

325

query = (Query.from_(subscriptions)

326

.select(

327

subscriptions.user_id,

328

subscriptions.start_date,

329

(subscriptions.start_date + Interval(months=12)).as_('renewal_date'),

330

subscriptions.trial_start,

331

(subscriptions.trial_start + Interval(days=14)).as_('trial_end')

332

))

333

334

# Complex interval calculations

335

quarterly_intervals = Interval(quarters=1)

336

semi_annual = Interval(months=6)

337

bi_weekly = Interval(weeks=2)

338

339

query = (Query.from_(events)

340

.select(

341

events.event_date,

342

(events.event_date + quarterly_intervals).as_('next_quarter'),

343

(events.event_date - semi_annual).as_('six_months_ago'),

344

(events.event_date + bi_weekly).as_('two_weeks_later')

345

))

346

347

# Time-based grouping and analysis

348

from pypika.functions import Extract, DatePart

349

query = (Query.from_(users)

350

.select(

351

Extract(DatePart.year, users.created_at).as_('signup_year'),

352

Extract(DatePart.month, users.created_at).as_('signup_month'),

353

Count('*').as_('signups')

354

)

355

.where(users.created_at > (Now() - Interval(years=2)))

356

.groupby(

357

Extract(DatePart.year, users.created_at),

358

Extract(DatePart.month, users.created_at)

359

))

360

361

# Interval comparisons

362

active_sessions = (Query.from_(events)

363

.select('*')

364

.where(events.session_end - events.session_start > Interval(minutes=5)))

365

366

# Database-specific interval usage

367

from pypika import PostgreSQLQuery

368

pg_query = (PostgreSQLQuery.from_(users)

369

.select(

370

users.name,

371

(users.created_at + Interval(months=1, dialect='postgresql')).as_('plus_month')

372

))

373

```

374

375

### Array Data Types

376

377

SQL array operations for databases that support array types.

378

379

```python { .api }

380

class Array:

381

def __init__(self, *items):

382

"""

383

Create SQL array literal.

384

385

Parameters:

386

- items: Array elements

387

"""

388

389

def contains(self, item) -> BasicCriterion:

390

"""Check if array contains item."""

391

392

def overlap(self, other_array) -> BasicCriterion:

393

"""Check if arrays overlap."""

394

395

def length(self) -> Function:

396

"""Get array length."""

397

```

398

399

**Usage Examples:**

400

401

```python

402

from pypika import PostgreSQLQuery, Table, Array

403

404

# PostgreSQL arrays

405

users = Table('users')

406

posts = Table('posts')

407

408

# Array operations

409

tags_array = Array('python', 'sql', 'database')

410

colors_array = Array('red', 'blue', 'green')

411

412

# Array containment

413

query = (PostgreSQLQuery.from_(posts)

414

.select('*')

415

.where(posts.tags.contains('python')))

416

417

# Array overlap

418

query = (PostgreSQLQuery.from_(posts)

419

.select('*')

420

.where(posts.tags.overlap(tags_array)))

421

422

# Array functions

423

from pypika.functions import ArrayLength, ArrayAppend

424

query = (PostgreSQLQuery.from_(posts)

425

.select(

426

posts.title,

427

posts.tags,

428

ArrayLength(posts.tags).as_('tag_count')

429

))

430

431

# Complex array queries

432

query = (PostgreSQLQuery.from_(users)

433

.select(

434

users.name,

435

users.skills,

436

ArrayLength(users.skills).as_('skill_count')

437

)

438

.where(users.skills.overlap(Array('python', 'java', 'javascript')))

439

.where(ArrayLength(users.skills) >= 3))

440

```

441

442

### Tuple Data Type

443

444

SQL tuple operations for multi-value comparisons and row constructors.

445

446

```python { .api }

447

class Tuple:

448

def __init__(self, *items):

449

"""

450

Create SQL tuple literal.

451

452

Parameters:

453

- items: Tuple elements

454

"""

455

456

def isin(self, *values) -> BasicCriterion:

457

"""Check if tuple is in list of values."""

458

```

459

460

**Usage Examples:**

461

462

```python

463

from pypika import Query, Table, Tuple

464

465

users = Table('users')

466

coordinates = Table('coordinates')

467

468

# Multi-column comparisons

469

name_tuple = Tuple(users.first_name, users.last_name)

470

valid_names = Tuple(

471

Tuple('John', 'Doe'),

472

Tuple('Jane', 'Smith'),

473

Tuple('Bob', 'Johnson')

474

)

475

476

query = (Query.from_(users)

477

.select('*')

478

.where(name_tuple.isin(valid_names)))

479

480

# Coordinate comparisons

481

location_tuple = Tuple(coordinates.latitude, coordinates.longitude)

482

valid_locations = Tuple(

483

Tuple(40.7128, -74.0060), # New York

484

Tuple(34.0522, -118.2437), # Los Angeles

485

Tuple(41.8781, -87.6298) # Chicago

486

)

487

488

query = (Query.from_(coordinates)

489

.select('*')

490

.where(location_tuple.isin(valid_locations)))

491

492

# Complex tuple operations

493

user_status_tuple = Tuple(users.status, users.role, users.department)

494

admin_combinations = Tuple(

495

Tuple('active', 'admin', 'IT'),

496

Tuple('active', 'admin', 'Security'),

497

Tuple('pending', 'admin', 'IT')

498

)

499

500

query = (Query.from_(users)

501

.select('*')

502

.where(user_status_tuple.isin(admin_combinations)))

503

```

504

505

### Special Value Types

506

507

Special SQL values and constants for various database operations.

508

509

```python { .api }

510

class NullValue:

511

"""SQL NULL value representation."""

512

513

class SystemTimeValue:

514

"""SQL SYSTEM_TIME value for temporal tables."""

515

516

class Not:

517

def __init__(self, term):

518

"""

519

NOT operator wrapper.

520

521

Parameters:

522

- term: Expression to negate

523

"""

524

525

class Bracket:

526

def __init__(self, term):

527

"""

528

Parentheses wrapper for expressions.

529

530

Parameters:

531

- term: Expression to wrap in parentheses

532

"""

533

534

class Index:

535

def __init__(self, name: str):

536

"""

537

Database index reference.

538

539

Parameters:

540

- name: Index name

541

"""

542

```

543

544

**Usage Examples:**

545

546

```python

547

from pypika import Query, Table, NULL, SYSTEM_TIME, Not, Bracket, Index

548

549

users = Table('users')

550

orders = Table('orders')

551

552

# NULL operations

553

query = (Query.from_(users)

554

.select('*')

555

.where(users.phone != NULL)

556

.where(users.deleted_at == NULL))

557

558

# NOT operations

559

not_admin = Not(users.role == 'admin')

560

query = Query.from_(users).select('*').where(not_admin)

561

562

# Complex conditions with parentheses

563

complex_condition = Bracket(

564

(users.age >= 18) & (users.status == 'active')

565

) | Bracket(

566

(users.role == 'admin') & (users.verified == True)

567

)

568

569

query = Query.from_(users).select('*').where(complex_condition)

570

571

# Index hints (MySQL-specific)

572

user_email_idx = Index('idx_user_email')

573

# Usage would depend on dialect-specific implementation

574

575

# Temporal table operations

576

historical_users = users.for_(SYSTEM_TIME.between('2023-01-01', '2023-12-31'))

577

query = Query.from_(historical_users).select('*')

578

579

# Combining special values

580

query = (Query.from_(users)

581

.select('*')

582

.where(

583

Not(users.email == NULL) &

584

Bracket(

585

(users.created_at > '2023-01-01') |

586

(users.status == 'premium')

587

)

588

))

589

```

590

591

### Type Conversion Utilities

592

593

Utilities for handling type conversions and value wrapping.

594

595

```python { .api }

596

class ValueWrapper:

597

def __init__(self, value):

598

"""

599

Wrap Python values for SQL usage.

600

601

Parameters:

602

- value: Python value to wrap

603

"""

604

605

class LiteralValue:

606

def __init__(self, value):

607

"""

608

Create literal SQL value.

609

610

Parameters:

611

- value: Literal value

612

"""

613

```

614

615

**Usage Examples:**

616

617

```python

618

from pypika import Query, Table, ValueWrapper, LiteralValue

619

620

users = Table('users')

621

622

# Value wrapping for safe SQL generation

623

python_list = [1, 2, 3, 4, 5]

624

wrapped_list = ValueWrapper(python_list)

625

626

query = Query.from_(users).select('*').where(users.id.isin(wrapped_list))

627

628

# Literal values

629

current_timestamp = LiteralValue('CURRENT_TIMESTAMP')

630

query = (Query.into(users)

631

.columns(users.name, users.email, users.created_at)

632

.insert('John Doe', 'john@example.com', current_timestamp))

633

634

# Safe parameter handling

635

def build_user_query(min_age=None, status=None, roles=None):

636

query = Query.from_(users).select('*')

637

638

if min_age is not None:

639

query = query.where(users.age >= ValueWrapper(min_age))

640

641

if status is not None:

642

query = query.where(users.status == ValueWrapper(status))

643

644

if roles is not None:

645

query = query.where(users.role.isin(ValueWrapper(roles)))

646

647

return query

648

649

# Usage

650

user_query = build_user_query(min_age=18, status='active', roles=['admin', 'user'])

651

```