0
# Project Management
1
2
Core Project class for programmatic management of Pipfiles, lockfiles, and project metadata. The Project class serves as the central API for interacting with pipenv projects, handling file operations, package tracking, and project configuration.
3
4
## Capabilities
5
6
### Project Initialization
7
8
Create and initialize Project instances for managing pipenv projects.
9
10
```python { .api }
11
class Project:
12
def __init__(self, python_version=None, chdir=True):
13
"""
14
Initialize a Project instance.
15
16
Parameters:
17
python_version (str, optional): Specific Python version to use
18
chdir (bool): Whether to change to project directory
19
"""
20
```
21
22
Usage examples:
23
```python
24
from pipenv.project import Project
25
26
# Initialize project in current directory
27
project = Project()
28
29
# Initialize with specific Python version
30
project = Project(python_version="3.9")
31
32
# Initialize without changing directory
33
project = Project(chdir=False)
34
```
35
36
### Project Properties
37
38
Access project metadata and locations.
39
40
```python { .api }
41
class Project:
42
# Project identification
43
name: str # Project name
44
project_directory: str # Project root directory
45
46
# File locations
47
pipfile_location: str # Path to Pipfile
48
lockfile_location: str # Path to Pipfile.lock
49
virtualenv_location: str # Path to virtual environment
50
51
# Parsed content
52
parsed_pipfile: dict # Parsed Pipfile content
53
lockfile_content: dict # Parsed lockfile content
54
55
# Package collections
56
packages: dict # Regular packages from Pipfile
57
dev_packages: dict # Development packages from Pipfile
58
sources: list # Package sources/indexes
59
60
# Environment access
61
environment: Environment # Project's Environment instance
62
```
63
64
Usage examples:
65
```python
66
project = Project()
67
68
# Access project information
69
print(f"Project name: {project.name}")
70
print(f"Project directory: {project.project_directory}")
71
print(f"Pipfile location: {project.pipfile_location}")
72
print(f"Virtual environment: {project.virtualenv_location}")
73
74
# Check packages
75
print(f"Regular packages: {list(project.packages.keys())}")
76
print(f"Dev packages: {list(project.dev_packages.keys())}")
77
print(f"Package sources: {project.sources}")
78
79
# Access environment
80
env = project.environment
81
print(f"Python interpreter: {env.python}")
82
```
83
84
### Pipfile Management
85
86
Create, read, and modify Pipfile configurations.
87
88
```python { .api }
89
class Project:
90
def create_pipfile(self, python=None):
91
"""
92
Create a new Pipfile.
93
94
Parameters:
95
python (str, optional): Python version specification
96
"""
97
98
def get_pipfile_section(self, section):
99
"""
100
Get a specific section from the Pipfile.
101
102
Parameters:
103
section (str): Section name ('packages', 'dev-packages', 'requires', 'scripts')
104
105
Returns:
106
dict: Section content
107
"""
108
109
def write_toml(self, data, path=None):
110
"""
111
Write TOML data to Pipfile.
112
113
Parameters:
114
data (dict): TOML data to write
115
path (str, optional): Custom path for Pipfile
116
"""
117
```
118
119
Usage examples:
120
```python
121
project = Project()
122
123
# Create new Pipfile
124
project.create_pipfile(python="3.9")
125
126
# Get Pipfile sections
127
packages = project.get_pipfile_section("packages")
128
dev_packages = project.get_pipfile_section("dev-packages")
129
scripts = project.get_pipfile_section("scripts")
130
131
# Write modified Pipfile
132
pipfile_data = {
133
"packages": {"requests": "*"},
134
"dev-packages": {"pytest": "*"},
135
"requires": {"python_version": "3.9"}
136
}
137
project.write_toml(pipfile_data)
138
```
139
140
### Package Management
141
142
Add, remove, and modify packages in Pipfile.
143
144
```python { .api }
145
class Project:
146
def add_package_to_pipfile(self, package, pip_line, dev=False, category=None):
147
"""
148
Add a package to Pipfile.
149
150
Parameters:
151
package (str): Package name
152
pip_line (str): Package specification (version, VCS URL, etc.)
153
dev (bool): Add as development dependency
154
category (str, optional): Package category
155
"""
156
157
def remove_package_from_pipfile(self, package_name, category):
158
"""
159
Remove a package from Pipfile.
160
161
Parameters:
162
package_name (str): Name of package to remove
163
category (str): Package category ('packages' or 'dev-packages')
164
"""
165
166
def add_packages_to_pipfile_batch(self, packages_data, dev=False, categories=None):
167
"""
168
Add multiple packages to Pipfile in batch operation.
169
170
Parameters:
171
packages_data (list): List of package specifications
172
dev (bool): Add as development dependencies
173
categories (list, optional): Package categories
174
"""
175
```
176
177
Usage examples:
178
```python
179
project = Project()
180
181
# Add single package
182
project.add_package_to_pipfile("requests", "requests>=2.25.0")
183
project.add_package_to_pipfile("pytest", "pytest>=6.0.0", dev=True)
184
185
# Add package from VCS
186
project.add_package_to_pipfile("mypackage", "git+https://github.com/user/repo.git")
187
188
# Remove package
189
project.remove_package_from_pipfile("requests", "packages")
190
project.remove_package_from_pipfile("pytest", "dev-packages")
191
192
# Batch add packages
193
packages_data = [
194
("requests", "requests>=2.25.0"),
195
("click", "click>=7.0.0")
196
]
197
project.add_packages_to_pipfile_batch(packages_data)
198
```
199
200
### Lockfile Management
201
202
Handle Pipfile.lock operations for deterministic builds.
203
204
```python { .api }
205
class Project:
206
def load_lockfile(self, expand_env_vars=True):
207
"""
208
Load and parse Pipfile.lock.
209
210
Parameters:
211
expand_env_vars (bool): Expand environment variables in lockfile
212
213
Returns:
214
dict: Parsed lockfile content
215
"""
216
217
def write_lockfile(self, content):
218
"""
219
Write lockfile content to Pipfile.lock.
220
221
Parameters:
222
content (dict): Lockfile data to write
223
"""
224
225
def lockfile(self, categories=None):
226
"""
227
Get lockfile data for specific categories.
228
229
Parameters:
230
categories (list, optional): Specific categories to include
231
232
Returns:
233
dict: Lockfile data
234
"""
235
```
236
237
Usage examples:
238
```python
239
project = Project()
240
241
# Load existing lockfile
242
lockfile_data = project.load_lockfile()
243
print(f"Lockfile hash: {lockfile_data.get('_meta', {}).get('hash')}")
244
245
# Access locked packages
246
locked_packages = lockfile_data.get("default", {})
247
dev_locked = lockfile_data.get("develop", {})
248
249
# Write updated lockfile
250
new_lockfile = {
251
"_meta": {"hash": {"sha256": "..."}},
252
"default": {"requests": {"version": "==2.25.1"}},
253
"develop": {"pytest": {"version": "==6.2.2"}}
254
}
255
project.write_lockfile(new_lockfile)
256
257
# Get specific categories
258
production_lock = project.lockfile(categories=["default"])
259
```
260
261
### Package Categories
262
263
Manage package categories and organization.
264
265
```python { .api }
266
class Project:
267
def get_package_categories(self, for_lockfile=False):
268
"""
269
Get available package categories.
270
271
Parameters:
272
for_lockfile (bool): Get categories for lockfile format
273
274
Returns:
275
list: Available package categories
276
"""
277
```
278
279
Usage examples:
280
```python
281
project = Project()
282
283
# Get Pipfile categories
284
pipfile_categories = project.get_package_categories(for_lockfile=False)
285
print(f"Pipfile categories: {pipfile_categories}") # ['packages', 'dev-packages']
286
287
# Get lockfile categories
288
lockfile_categories = project.get_package_categories(for_lockfile=True)
289
print(f"Lockfile categories: {lockfile_categories}") # ['default', 'develop']
290
```
291
292
### Path Operations
293
294
Handle path resolution and file operations.
295
296
```python { .api }
297
class Project:
298
def path_to(self, p):
299
"""
300
Convert relative path to absolute path within project.
301
302
Parameters:
303
p (str): Relative path
304
305
Returns:
306
Path: Absolute path object
307
"""
308
```
309
310
Usage examples:
311
```python
312
from pathlib import Path
313
314
project = Project()
315
316
# Convert relative paths
317
abs_path = project.path_to("src/mymodule.py")
318
print(f"Absolute path: {abs_path}")
319
320
# Work with Path objects
321
config_path = project.path_to("config.ini")
322
if config_path.exists():
323
content = config_path.read_text()
324
```
325
326
### Environment Integration
327
328
Access and manage the project's virtual environment.
329
330
```python { .api }
331
class Project:
332
def get_environment(self, allow_global=False):
333
"""
334
Get the project's Environment instance.
335
336
Parameters:
337
allow_global (bool): Allow global Python environment
338
339
Returns:
340
Environment: Project's environment instance
341
"""
342
```
343
344
Usage examples:
345
```python
346
project = Project()
347
348
# Get project environment
349
env = project.get_environment()
350
print(f"Python executable: {env.python}")
351
print(f"Environment prefix: {env.prefix}")
352
353
# Check installed packages
354
installed = env.get_installed_packages()
355
for pkg in installed:
356
print(f"{pkg.project_name}: {pkg.version}")
357
358
# Use environment context
359
with env.activated():
360
# Operations within activated environment
361
import subprocess
362
result = subprocess.run(["python", "--version"], capture_output=True, text=True)
363
print(f"Active Python: {result.stdout.strip()}")
364
```
365
366
## Type Definitions
367
368
Data structures used by the Project class.
369
370
```python { .api }
371
# Type aliases from project.py
372
TSource = Dict[str, Union[str, bool]] # Package source definition
373
TPackageEntry = Dict[str, Union[bool, str, List[str]]] # Individual package entry
374
TPackage = Dict[str, TPackageEntry] # Package collection
375
TScripts = Dict[str, str] # Script definitions
376
TPipenv = Dict[str, bool] # Pipenv settings
377
TPipfile = Dict[str, Union[TPackage, TScripts, TPipenv, List[TSource]]] # Complete Pipfile
378
```
379
380
## Integration Examples
381
382
Complete examples showing Project class integration.
383
384
```python
385
from pipenv.project import Project
386
from pathlib import Path
387
388
# Initialize project and check state
389
project = Project()
390
391
if not Path(project.pipfile_location).exists():
392
# Create new project
393
project.create_pipfile(python="3.9")
394
print(f"Created new project: {project.name}")
395
else:
396
print(f"Using existing project: {project.name}")
397
398
# Add dependencies
399
project.add_package_to_pipfile("requests", "requests>=2.25.0")
400
project.add_package_to_pipfile("click", "click>=8.0.0")
401
project.add_package_to_pipfile("pytest", "pytest>=6.0.0", dev=True)
402
403
# Check project state
404
print(f"Production packages: {list(project.packages.keys())}")
405
print(f"Development packages: {list(project.dev_packages.keys())}")
406
407
# Work with environment
408
env = project.get_environment()
409
with env.activated():
410
# Environment is now active
411
installed = env.get_installed_packages()
412
print(f"Installed packages: {len(installed)}")
413
```