0
# Application Startup
1
2
Application lifecycle management providing the main entry point for absl-based Python applications. Handles automatic flag parsing, exception handling, initialization callbacks, and proper program termination.
3
4
## Capabilities
5
6
### Main Application Runner
7
8
The primary entry point for absl applications that automatically parses command-line flags, handles exceptions, and manages the application lifecycle.
9
10
```python { .api }
11
def run(main, argv=None, flags_parser=parse_flags_with_usage):
12
"""
13
Run the main function with automatic flag parsing and exception handling.
14
15
This function serves as the entry point for absl applications. It automatically
16
parses command-line flags, calls initialization callbacks, handles exceptions,
17
and ensures proper program termination.
18
19
Args:
20
main: Main function that takes argv as its single argument
21
argv: Command line arguments (defaults to sys.argv if None)
22
flags_parser: Function to parse flags (defaults to parse_flags_with_usage)
23
24
The main function should have signature: main(argv: List[str]) -> None
25
"""
26
```
27
28
### Usage and Help
29
30
Functions for displaying usage information and handling help requests.
31
32
```python { .api }
33
def usage(shorthelp=False, writeto_stdout=False, detailed_error=None, exitcode=None):
34
"""
35
Write usage information to stderr and optionally exit.
36
37
Args:
38
shorthelp (bool): If True, print short help instead of full help
39
writeto_stdout (bool): If True, write to stdout instead of stderr
40
detailed_error (str): Detailed error message to include in output
41
exitcode (int): Exit code to use when exiting (if None, don't exit)
42
"""
43
```
44
45
### Initialization Callbacks
46
47
Register callbacks to be executed after flag parsing but before the main function.
48
49
```python { .api }
50
def call_after_init(callback):
51
"""
52
Register a callback to be called after flag parsing.
53
54
Callbacks are executed in the order they were registered, after flags
55
have been parsed but before the main function is called.
56
57
Args:
58
callback: Function to call after initialization, takes no arguments
59
"""
60
```
61
62
### Exception Handling
63
64
Custom exception types and exception handler registration for application-specific error handling.
65
66
```python { .api }
67
class Error(Exception):
68
"""Base exception class for the app module."""
69
70
class UsageError(Error):
71
"""
72
Exception indicating a usage error (bad command-line arguments).
73
74
When raised in the main function, automatically displays usage
75
information and exits with code 1.
76
"""
77
78
def install_exception_handler(handler):
79
"""
80
Install a custom exception handler.
81
82
Args:
83
handler: ExceptionHandler instance or callable that takes an exception
84
"""
85
86
class ExceptionHandler:
87
"""
88
Base class for custom exception handlers.
89
90
Subclass this to create custom exception handling behavior.
91
"""
92
93
def wants(self, exc):
94
"""
95
Determine if this handler wants to handle an exception.
96
97
Args:
98
exc: The exception to potentially handle
99
100
Returns:
101
bool: True if this handler wants to handle the exception
102
"""
103
104
def handle(self, exc):
105
"""
106
Handle an exception.
107
108
Args:
109
exc: The exception to handle
110
111
Returns:
112
bool: True if the exception was handled, False otherwise
113
"""
114
```
115
116
### Flag Integration
117
118
Functions for integrating with the flags system, including help flag definitions and flag parsing with usage error handling.
119
120
```python { .api }
121
def parse_flags_with_usage(args):
122
"""
123
Parse flags and display usage on error.
124
125
Args:
126
args: Command-line arguments to parse
127
128
Returns:
129
List of remaining non-flag arguments
130
131
Raises:
132
SystemExit: On flag parsing errors with usage information
133
"""
134
135
def define_help_flags():
136
"""Define standard help flags (--help, --helpshort, --helpfull, --helpxml)."""
137
138
# Help flag classes for advanced usage
139
class HelpFlag(flags.BooleanFlag):
140
"""Special boolean flag that displays usage and raises SystemExit."""
141
NAME = 'help'
142
SHORT_NAME = '?'
143
144
class HelpshortFlag(HelpFlag):
145
"""Flag for displaying short help information."""
146
NAME = 'helpshort'
147
148
class HelpfullFlag(flags.BooleanFlag):
149
"""Flag for displaying full help information."""
150
NAME = 'helpfull'
151
152
class HelpXMLFlag(flags.BooleanFlag):
153
"""Flag for displaying help in XML format."""
154
NAME = 'helpxml'
155
```
156
157
## Usage Examples
158
159
### Basic Application Structure
160
161
```python
162
from absl import app
163
from absl import flags
164
from absl import logging
165
166
FLAGS = flags.FLAGS
167
flags.DEFINE_string('input_file', None, 'Input file to process.')
168
flags.DEFINE_boolean('verbose', False, 'Enable verbose output.')
169
170
def main(argv):
171
if len(argv) > 1:
172
raise app.UsageError('Too many command-line arguments.')
173
174
if FLAGS.verbose:
175
logging.set_verbosity(logging.DEBUG)
176
177
if FLAGS.input_file is None:
178
raise app.UsageError('--input_file is required.')
179
180
# Application logic here
181
logging.info('Processing file: %s', FLAGS.input_file)
182
183
if __name__ == '__main__':
184
app.run(main)
185
```
186
187
### Custom Exception Handling
188
189
```python
190
from absl import app
191
import logging
192
193
class CustomExceptionHandler(app.ExceptionHandler):
194
def handle(self, exc):
195
if isinstance(exc, FileNotFoundError):
196
logging.error('File not found: %s', exc.filename)
197
return True # Exception handled
198
return False # Not handled
199
200
def main(argv):
201
app.install_exception_handler(CustomExceptionHandler())
202
# Application logic that might raise FileNotFoundError
203
204
if __name__ == '__main__':
205
app.run(main)
206
```
207
208
### Initialization Callbacks
209
210
```python
211
from absl import app
212
from absl import flags
213
import logging
214
215
FLAGS = flags.FLAGS
216
flags.DEFINE_string('config_file', None, 'Configuration file.')
217
218
def initialize_config():
219
"""Initialize configuration after flags are parsed."""
220
if FLAGS.config_file:
221
logging.info('Loading config from: %s', FLAGS.config_file)
222
# Load configuration logic here
223
224
def main(argv):
225
# Configuration is already loaded via callback
226
logging.info('Starting application with loaded config.')
227
228
if __name__ == '__main__':
229
app.call_after_init(initialize_config)
230
app.run(main)
231
```