The OPTIONAL keyword in COBOL is used to indicate that a file or parameter may or may not be present during program execution. For files, it allows the program to handle missing files gracefully without terminating. For parameters, it enables flexible subprogram interfaces where some arguments may be omitted.
Files that may not exist without causing program failure
Settings files that use defaults when missing
Logging that can be disabled when file is absent
Reference files that may not always be required
ENVIRONMENT DIVISION.
INPUT-OUTPUT SECTION.
FILE-CONTROL.
SELECT CUSTOMER-FILE ASSIGN TO "CUSTOMER.DAT"
ORGANIZATION IS SEQUENTIAL
ACCESS MODE IS SEQUENTIAL
FILE STATUS IS WS-CUSTOMER-STATUS.
SELECT OPTIONAL CONFIG-FILE ASSIGN TO "CONFIG.INI"
ORGANIZATION IS SEQUENTIAL
ACCESS MODE IS SEQUENTIAL
FILE STATUS IS WS-CONFIG-STATUS.
SELECT OPTIONAL AUDIT-LOG ASSIGN TO "AUDIT.LOG"
ORGANIZATION IS SEQUENTIAL
ACCESS MODE IS SEQUENTIAL
FILE STATUS IS WS-AUDIT-STATUS.
DATA DIVISION.
FILE SECTION.
FD CUSTOMER-FILE.
01 CUSTOMER-RECORD.
05 CUST-ID PIC X(8).
05 CUST-NAME PIC X(30).
05 CUST-BALANCE PIC S9(8)V99.
FD CONFIG-FILE.
01 CONFIG-RECORD PIC X(80).
FD AUDIT-LOG.
01 AUDIT-RECORD PIC X(120).
WORKING-STORAGE SECTION.
01 WS-FILE-STATUS.
05 WS-CUSTOMER-STATUS PIC XX.
05 WS-CONFIG-STATUS PIC XX.
05 WS-AUDIT-STATUS PIC XX.Declaring files as optional using the OPTIONAL keyword.
WORKING-STORAGE SECTION.
01 WS-CONFIG-SETTINGS.
05 WS-DEBUG-MODE PIC X VALUE 'N'.
05 WS-LOG-LEVEL PIC 9 VALUE 1.
05 WS-MAX-RECORDS PIC 9(6) VALUE 10000.
05 WS-TIMEOUT-SECONDS PIC 9(3) VALUE 30.
05 WS-CONFIG-LOADED PIC X VALUE 'N'.
PROCEDURE DIVISION.
LOAD-CONFIGURATION.
*> Set default values first
MOVE 'N' TO WS-DEBUG-MODE.
MOVE 1 TO WS-LOG-LEVEL.
MOVE 10000 TO WS-MAX-RECORDS.
MOVE 30 TO WS-TIMEOUT-SECONDS.
MOVE 'N' TO WS-CONFIG-LOADED.
*> Try to open optional configuration file
OPEN INPUT CONFIG-FILE.
EVALUATE WS-CONFIG-STATUS
WHEN "00"
*> File exists and opened successfully
DISPLAY "CONFIGURATION FILE FOUND"
PERFORM READ-CONFIG-SETTINGS
MOVE 'Y' TO WS-CONFIG-LOADED
CLOSE CONFIG-FILE
WHEN "05"
*> File is optional and not present
DISPLAY "CONFIGURATION FILE NOT FOUND - USING DEFAULTS"
MOVE 'N' TO WS-CONFIG-LOADED
WHEN "35"
*> File exists but cannot be opened
DISPLAY "CONFIGURATION FILE EXISTS BUT CANNOT BE OPENED"
DISPLAY "USING DEFAULT SETTINGS"
MOVE 'N' TO WS-CONFIG-LOADED
WHEN OTHER
DISPLAY "ERROR ACCESSING CONFIGURATION FILE: " WS-CONFIG-STATUS
DISPLAY "USING DEFAULT SETTINGS"
MOVE 'N' TO WS-CONFIG-LOADED
END-EVALUATE.
PERFORM DISPLAY-CURRENT-SETTINGS.
READ-CONFIG-SETTINGS.
PERFORM UNTIL WS-CONFIG-STATUS NOT = "00"
READ CONFIG-FILE
AT END
EXIT PERFORM
NOT AT END
PERFORM PARSE-CONFIG-LINE
END-READ
END-PERFORM.
PARSE-CONFIG-LINE.
IF CONFIG-RECORD(1:12) = "DEBUG_MODE="
MOVE CONFIG-RECORD(13:1) TO WS-DEBUG-MODE
DISPLAY "LOADED: DEBUG_MODE=" WS-DEBUG-MODE
END-IF.
IF CONFIG-RECORD(1:11) = "LOG_LEVEL="
MOVE CONFIG-RECORD(12:1) TO WS-LOG-LEVEL
DISPLAY "LOADED: LOG_LEVEL=" WS-LOG-LEVEL
END-IF.
IF CONFIG-RECORD(1:12) = "MAX_RECORDS="
MOVE CONFIG-RECORD(13:6) TO WS-MAX-RECORDS
DISPLAY "LOADED: MAX_RECORDS=" WS-MAX-RECORDS
END-IF.
IF CONFIG-RECORD(1:16) = "TIMEOUT_SECONDS="
MOVE CONFIG-RECORD(17:3) TO WS-TIMEOUT-SECONDS
DISPLAY "LOADED: TIMEOUT_SECONDS=" WS-TIMEOUT-SECONDS
END-IF.
DISPLAY-CURRENT-SETTINGS.
DISPLAY "CURRENT CONFIGURATION:".
DISPLAY " DEBUG MODE: " WS-DEBUG-MODE.
DISPLAY " LOG LEVEL: " WS-LOG-LEVEL.
DISPLAY " MAX RECORDS: " WS-MAX-RECORDS.
DISPLAY " TIMEOUT: " WS-TIMEOUT-SECONDS " SECONDS".
IF WS-CONFIG-LOADED = 'Y'
DISPLAY " SOURCE: CONFIGURATION FILE"
ELSE
DISPLAY " SOURCE: DEFAULT VALUES"
END-IF.Loading configuration from optional file with defaults.
WORKING-STORAGE SECTION.
01 WS-AUDIT-CONTROL.
05 WS-AUDIT-ENABLED PIC X VALUE 'N'.
05 WS-AUDIT-ENTRIES PIC 9(6) VALUE 0.
PROCEDURE DIVISION.
INITIALIZE-AUDIT-LOGGING.
OPEN EXTEND AUDIT-LOG.
EVALUATE WS-AUDIT-STATUS
WHEN "00"
MOVE 'Y' TO WS-AUDIT-ENABLED
DISPLAY "AUDIT LOGGING ENABLED"
PERFORM WRITE-AUDIT-STARTUP
WHEN "05"
MOVE 'N' TO WS-AUDIT-ENABLED
DISPLAY "AUDIT LOGGING DISABLED - LOG FILE NOT CONFIGURED"
WHEN OTHER
MOVE 'N' TO WS-AUDIT-ENABLED
DISPLAY "AUDIT LOGGING DISABLED - ERROR: " WS-AUDIT-STATUS
END-EVALUATE.
WRITE-AUDIT-ENTRY.
IF WS-AUDIT-ENABLED = 'Y'
PERFORM WRITE-AUDIT-RECORD
ADD 1 TO WS-AUDIT-ENTRIES
END-IF.
WRITE-AUDIT-STARTUP.
ACCEPT WS-CURRENT-TIMESTAMP FROM TIMESTAMP.
STRING "STARTUP " WS-CURRENT-TIMESTAMP
" APPLICATION INITIALIZED"
DELIMITED BY SIZE
INTO AUDIT-RECORD.
WRITE AUDIT-RECORD.
IF WS-AUDIT-STATUS = "00"
ADD 1 TO WS-AUDIT-ENTRIES
DISPLAY "STARTUP AUDIT ENTRY WRITTEN"
ELSE
DISPLAY "ERROR WRITING STARTUP AUDIT: " WS-AUDIT-STATUS
MOVE 'N' TO WS-AUDIT-ENABLED
END-IF.
WRITE-AUDIT-RECORD.
*> Format audit record with timestamp and details
ACCEPT WS-CURRENT-TIMESTAMP FROM TIMESTAMP.
STRING WS-CURRENT-TIMESTAMP " " WS-AUDIT-MESSAGE
DELIMITED BY SIZE
INTO AUDIT-RECORD.
WRITE AUDIT-RECORD.
IF WS-AUDIT-STATUS NOT = "00"
DISPLAY "AUDIT WRITE ERROR: " WS-AUDIT-STATUS
*> Continue processing even if audit fails
END-IF.
CLOSE-AUDIT-LOGGING.
IF WS-AUDIT-ENABLED = 'Y'
PERFORM WRITE-AUDIT-SHUTDOWN
CLOSE AUDIT-LOG
DISPLAY "AUDIT LOGGING CLOSED - ENTRIES WRITTEN: " WS-AUDIT-ENTRIES
END-IF.Optional audit logging that degrades gracefully.
ENVIRONMENT DIVISION.
INPUT-OUTPUT SECTION.
FILE-CONTROL.
SELECT TRANSACTION-FILE ASSIGN TO "TRANS.DAT"
ORGANIZATION IS SEQUENTIAL
FILE STATUS IS WS-TRANS-STATUS.
SELECT OPTIONAL VALIDATION-FILE ASSIGN TO "VALID.REF"
ORGANIZATION IS INDEXED
ACCESS MODE IS RANDOM
RECORD KEY IS VALID-CODE
FILE STATUS IS WS-VALID-STATUS.
DATA DIVISION.
FILE SECTION.
FD TRANSACTION-FILE.
01 TRANSACTION-RECORD.
05 TRANS-ID PIC X(10).
05 TRANS-CODE PIC X(6).
05 TRANS-AMOUNT PIC 9(8)V99.
FD VALIDATION-FILE.
01 VALIDATION-RECORD.
05 VALID-CODE PIC X(6).
05 VALID-DESC PIC X(30).
05 VALID-LIMITS.
10 MIN-AMOUNT PIC 9(8)V99.
10 MAX-AMOUNT PIC 9(8)V99.
WORKING-STORAGE SECTION.
01 WS-VALIDATION-CONTROL.
05 WS-VALIDATION-AVAILABLE PIC X VALUE 'N'.
05 WS-STRICT-MODE PIC X VALUE 'N'.
PROCEDURE DIVISION.
INITIALIZE-VALIDATION.
OPEN INPUT VALIDATION-FILE.
EVALUATE WS-VALID-STATUS
WHEN "00"
MOVE 'Y' TO WS-VALIDATION-AVAILABLE
MOVE 'Y' TO WS-STRICT-MODE
DISPLAY "VALIDATION FILE LOADED - STRICT MODE ENABLED"
WHEN "05"
MOVE 'N' TO WS-VALIDATION-AVAILABLE
MOVE 'N' TO WS-STRICT-MODE
DISPLAY "VALIDATION FILE NOT FOUND - LENIENT MODE"
WHEN OTHER
MOVE 'N' TO WS-VALIDATION-AVAILABLE
MOVE 'N' TO WS-STRICT-MODE
DISPLAY "VALIDATION FILE ERROR: " WS-VALID-STATUS
DISPLAY "CONTINUING IN LENIENT MODE"
END-EVALUATE.
VALIDATE-TRANSACTION.
IF WS-VALIDATION-AVAILABLE = 'Y'
PERFORM STRICT-VALIDATION
ELSE
PERFORM BASIC-VALIDATION
END-IF.
STRICT-VALIDATION.
MOVE TRANS-CODE TO VALID-CODE.
READ VALIDATION-FILE
INVALID KEY
DISPLAY "INVALID TRANSACTION CODE: " TRANS-CODE
MOVE 'N' TO WS-TRANSACTION-VALID
NOT INVALID KEY
IF TRANS-AMOUNT < MIN-AMOUNT OR
TRANS-AMOUNT > MAX-AMOUNT
DISPLAY "AMOUNT OUT OF RANGE FOR CODE: " TRANS-CODE
DISPLAY " AMOUNT: " TRANS-AMOUNT
DISPLAY " RANGE: " MIN-AMOUNT " TO " MAX-AMOUNT
MOVE 'N' TO WS-TRANSACTION-VALID
ELSE
MOVE 'Y' TO WS-TRANSACTION-VALID
DISPLAY "TRANSACTION VALIDATED: " TRANS-ID
END-IF
END-READ.
BASIC-VALIDATION.
*> Basic validation without reference file
IF TRANS-CODE = SPACES OR TRANS-AMOUNT <= 0
DISPLAY "BASIC VALIDATION FAILED: " TRANS-ID
MOVE 'N' TO WS-TRANSACTION-VALID
ELSE
MOVE 'Y' TO WS-TRANSACTION-VALID
DISPLAY "BASIC VALIDATION PASSED: " TRANS-ID
END-IF.Validation logic that adapts based on optional reference files.
ENVIRONMENT DIVISION.
INPUT-OUTPUT SECTION.
FILE-CONTROL.
SELECT DATA-FILE ASSIGN TO "DATA.DAT"
ORGANIZATION IS SEQUENTIAL
FILE STATUS IS WS-DATA-STATUS.
SELECT OPTIONAL SUMMARY-REPORT ASSIGN TO "SUMMARY.RPT"
ORGANIZATION IS SEQUENTIAL
FILE STATUS IS WS-SUMMARY-STATUS.
SELECT OPTIONAL DETAIL-REPORT ASSIGN TO "DETAIL.RPT"
ORGANIZATION IS SEQUENTIAL
FILE STATUS IS WS-DETAIL-STATUS.
SELECT OPTIONAL ERROR-REPORT ASSIGN TO "ERRORS.RPT"
ORGANIZATION IS SEQUENTIAL
FILE STATUS IS WS-ERROR-STATUS.
WORKING-STORAGE SECTION.
01 WS-REPORT-CONTROL.
05 WS-SUMMARY-ENABLED PIC X VALUE 'N'.
05 WS-DETAIL-ENABLED PIC X VALUE 'N'.
05 WS-ERROR-ENABLED PIC X VALUE 'N'.
05 WS-REPORTS-GENERATED PIC 9(2) VALUE 0.
PROCEDURE DIVISION.
INITIALIZE-REPORTS.
PERFORM SETUP-SUMMARY-REPORT.
PERFORM SETUP-DETAIL-REPORT.
PERFORM SETUP-ERROR-REPORT.
DISPLAY "REPORT GENERATION SETUP COMPLETE".
DISPLAY " SUMMARY REPORT: " WS-SUMMARY-ENABLED.
DISPLAY " DETAIL REPORT: " WS-DETAIL-ENABLED.
DISPLAY " ERROR REPORT: " WS-ERROR-ENABLED.
SETUP-SUMMARY-REPORT.
OPEN OUTPUT SUMMARY-REPORT.
EVALUATE WS-SUMMARY-STATUS
WHEN "00"
MOVE 'Y' TO WS-SUMMARY-ENABLED
ADD 1 TO WS-REPORTS-GENERATED
PERFORM WRITE-SUMMARY-HEADER
WHEN "05"
MOVE 'N' TO WS-SUMMARY-ENABLED
DISPLAY "SUMMARY REPORT DISABLED - FILE NOT CONFIGURED"
WHEN OTHER
MOVE 'N' TO WS-SUMMARY-ENABLED
DISPLAY "SUMMARY REPORT DISABLED - ERROR: " WS-SUMMARY-STATUS
END-EVALUATE.
PROCESS-DATA-WITH-REPORTS.
OPEN INPUT DATA-FILE.
PERFORM READ-DATA-RECORD.
PERFORM UNTIL WS-DATA-STATUS = "10"
PERFORM PROCESS-RECORD
IF WS-RECORD-VALID = 'Y'
IF WS-SUMMARY-ENABLED = 'Y'
PERFORM UPDATE-SUMMARY-TOTALS
END-IF
IF WS-DETAIL-ENABLED = 'Y'
PERFORM WRITE-DETAIL-LINE
END-IF
ELSE
IF WS-ERROR-ENABLED = 'Y'
PERFORM WRITE-ERROR-LINE
END-IF
END-IF
PERFORM READ-DATA-RECORD
END-PERFORM.
PERFORM FINALIZE-REPORTS.
WRITE-SUMMARY-LINE.
IF WS-SUMMARY-ENABLED = 'Y'
MOVE WS-SUMMARY-LINE TO SUMMARY-RECORD
WRITE SUMMARY-RECORD
IF WS-SUMMARY-STATUS NOT = "00"
DISPLAY "ERROR WRITING SUMMARY: " WS-SUMMARY-STATUS
MOVE 'N' TO WS-SUMMARY-ENABLED
END-IF
END-IF.
FINALIZE-REPORTS.
IF WS-SUMMARY-ENABLED = 'Y'
PERFORM WRITE-SUMMARY-TOTALS
CLOSE SUMMARY-REPORT
END-IF.
IF WS-DETAIL-ENABLED = 'Y'
CLOSE DETAIL-REPORT
END-IF.
IF WS-ERROR-ENABLED = 'Y'
CLOSE ERROR-REPORT
END-IF.
CLOSE DATA-FILE.
DISPLAY "PROCESSING COMPLETE".
DISPLAY " REPORTS GENERATED: " WS-REPORTS-GENERATED.Flexible report generation with optional output files.
WORKING-STORAGE SECTION.
01 WS-OPTIONAL-FEATURES.
05 WS-FEATURE-COUNT PIC 9(2) VALUE 0.
05 WS-FEATURES-TABLE.
10 WS-FEATURE-ENTRY OCCURS 10 TIMES.
15 WS-FEATURE-NAME PIC X(20).
15 WS-FEATURE-STATUS PIC X.
88 FEATURE-ENABLED VALUE 'Y'.
88 FEATURE-DISABLED VALUE 'N'.
PROCEDURE DIVISION.
CHECK-OPTIONAL-COMPONENTS.
MOVE 0 TO WS-FEATURE-COUNT.
*> Check configuration file
PERFORM CHECK-CONFIG-FILE.
*> Check audit logging
PERFORM CHECK-AUDIT-LOG.
*> Check validation reference
PERFORM CHECK-VALIDATION-REF.
*> Check backup facility
PERFORM CHECK-BACKUP-FACILITY.
PERFORM DISPLAY-FEATURE-STATUS.
CHECK-CONFIG-FILE.
ADD 1 TO WS-FEATURE-COUNT.
MOVE "CONFIGURATION" TO WS-FEATURE-NAME (WS-FEATURE-COUNT).
OPEN INPUT CONFIG-FILE.
IF WS-CONFIG-STATUS = "00" OR WS-CONFIG-STATUS = "05"
SET FEATURE-ENABLED (WS-FEATURE-COUNT) TO TRUE
IF WS-CONFIG-STATUS = "00"
CLOSE CONFIG-FILE
END-IF
ELSE
SET FEATURE-DISABLED (WS-FEATURE-COUNT) TO TRUE
DISPLAY "WARNING: CONFIG FILE ERROR - " WS-CONFIG-STATUS
END-IF.
DISPLAY-FEATURE-STATUS.
DISPLAY "OPTIONAL FEATURE STATUS:".
PERFORM VARYING WS-INDEX FROM 1 BY 1
UNTIL WS-INDEX > WS-FEATURE-COUNT
DISPLAY " " WS-FEATURE-NAME (WS-INDEX) ": "
IF FEATURE-ENABLED (WS-INDEX)
DISPLAY "ENABLED"
ELSE
DISPLAY "DISABLED"
END-IF
END-PERFORM.
DISPLAY " ".
DISPLAY "APPLICATION WILL CONTINUE WITH AVAILABLE FEATURES".
SAFE-OPTIONAL-OPERATION.
*> Template for safe optional operations
EVALUATE TRUE
WHEN FEATURE-ENABLED (WS-CONFIG-FEATURE)
PERFORM ENHANCED-PROCESSING
WHEN FEATURE-DISABLED (WS-CONFIG-FEATURE)
PERFORM STANDARD-PROCESSING
WHEN OTHER
PERFORM MINIMAL-PROCESSING
DISPLAY "RUNNING IN MINIMAL MODE"
END-EVALUATE.Systematic checking and graceful degradation of optional features.
| Status | Meaning | Action |
|---|---|---|
| 00 | File opened successfully | Proceed with file operations |
| 05 | Optional file not present | Use default behavior |
| 35 | File exists but cannot open | Handle error or use defaults |
| 37 | Wrong access mode | Check file permissions |
Load settings from optional file with defaults
Enable logging only when log file is available
Enhanced validation with optional reference data
Enable features based on optional file presence
Checking status code 05 for missing optional files
Opening files with proper error handling
File declaration in Environment Division
Graceful degradation and default behaviors