Skip to content

MessageFormatter parse error improvements #6306

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 20 additions & 2 deletions ext/intl/msgformat/msgformat.c
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@ static int msgfmt_ctor(INTERNAL_FUNCTION_PARAMETERS)
int spattern_len = 0;
zval* object;
MessageFormatter_object* mfo;
UParseError parse_error;

intl_error_reset( NULL );

object = return_value;
Expand Down Expand Up @@ -74,12 +76,26 @@ static int msgfmt_ctor(INTERNAL_FUNCTION_PARAMETERS)
(mfo)->mf_data.orig_format_len = pattern_len;

/* Create an ICU message formatter. */
MSG_FORMAT_OBJECT(mfo) = umsg_open(spattern, spattern_len, locale, NULL, &INTL_DATA_ERROR_CODE(mfo));
MSG_FORMAT_OBJECT(mfo) = umsg_open(spattern, spattern_len, locale, &parse_error, &INTL_DATA_ERROR_CODE(mfo));

if(spattern) {
efree(spattern);
}

if (INTL_DATA_ERROR_CODE( mfo ) == U_PATTERN_SYNTAX_ERROR) {
char *msg = NULL;
smart_str parse_error_str;
parse_error_str = intl_parse_error_to_string( &parse_error );
spprintf( &msg, 0, "pattern syntax error (%s)", parse_error_str.s? ZSTR_VAL(parse_error_str.s) : "unknown parser error" );
smart_str_free( &parse_error_str );

intl_error_set_code( NULL, INTL_DATA_ERROR_CODE( mfo ) );
intl_errors_set_custom_msg( INTL_DATA_ERROR_P( mfo ), msg, 1 );

efree( msg );
return FAILURE;
}

INTL_CTOR_CHECK_STATUS(mfo, "msgfmt_create: message formatter creation failed");
return SUCCESS;
}
Expand All @@ -105,7 +121,9 @@ PHP_METHOD( MessageFormatter, __construct )
return_value = ZEND_THIS;
if (msgfmt_ctor(INTERNAL_FUNCTION_PARAM_PASSTHRU) == FAILURE) {
if (!EG(exception)) {
zend_throw_exception(IntlException_ce_ptr, "Constructor failed", 0);
zend_string *err = intl_error_get_message(NULL);
zend_throw_exception(IntlException_ce_ptr, ZSTR_VAL(err), intl_error_get_code(NULL));
zend_string_release_ex(err, 0);
}
}
zend_restore_error_handling(&error_handling);
Expand Down
18 changes: 17 additions & 1 deletion ext/intl/msgformat/msgformat_format.c
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,7 @@ PHP_FUNCTION( msgfmt_format_message )
size_t slocale_len = 0;
MessageFormatter_object mf;
MessageFormatter_object *mfo = &mf;
UParseError parse_error;

/* Parse parameters. */
if( zend_parse_method_parameters( ZEND_NUM_ARGS(), getThis(), "ssa",
Expand Down Expand Up @@ -119,10 +120,25 @@ PHP_FUNCTION( msgfmt_format_message )
#endif

/* Create an ICU message formatter. */
MSG_FORMAT_OBJECT(mfo) = umsg_open(spattern, spattern_len, slocale, NULL, &INTL_DATA_ERROR_CODE(mfo));
MSG_FORMAT_OBJECT(mfo) = umsg_open(spattern, spattern_len, slocale, &parse_error, &INTL_DATA_ERROR_CODE(mfo));
if(spattern && spattern_len) {
efree(spattern);
}

if (INTL_DATA_ERROR_CODE( mfo ) == U_PATTERN_SYNTAX_ERROR) {
char *msg = NULL;
smart_str parse_error_str;
parse_error_str = intl_parse_error_to_string( &parse_error );
spprintf( &msg, 0, "pattern syntax error (%s)", parse_error_str.s? ZSTR_VAL(parse_error_str.s) : "unknown parser error" );
smart_str_free( &parse_error_str );

intl_error_set_code( NULL, INTL_DATA_ERROR_CODE( mfo ) );
intl_errors_set_custom_msg( INTL_DATA_ERROR_P( mfo ), msg, 1 );

efree( msg );
RETURN_FALSE;
}

INTL_METHOD_CHECK_STATUS(mfo, "Creating message formatter failed");

msgfmt_do_format(mfo, args, return_value);
Expand Down
16 changes: 8 additions & 8 deletions ext/intl/tests/msgfmt_fail2.phpt
Original file line number Diff line number Diff line change
Expand Up @@ -126,12 +126,12 @@ ArgumentCountError: msgfmt_create() expects exactly 2 arguments, 1 given in %s o
ArgumentCountError: MessageFormatter::create() expects exactly 2 arguments, 1 given in %s on line %d
'U_ZERO_ERROR'

IntlException: Constructor failed in %s on line %d
IntlException: msgfmt_create: message formatter creation failed: U_ILLEGAL_ARGUMENT_ERROR in %s on line %d
'msgfmt_create: message formatter creation failed: U_ILLEGAL_ARGUMENT_ERROR'
'msgfmt_create: message formatter creation failed: U_ILLEGAL_ARGUMENT_ERROR'
'msgfmt_create: message formatter creation failed: U_ILLEGAL_ARGUMENT_ERROR'

IntlException: Constructor failed in %s on line %d
IntlException: msgfmt_create: message formatter creation failed: U_ILLEGAL_ARGUMENT_ERROR in %s on line %d
'msgfmt_create: message formatter creation failed: U_ILLEGAL_ARGUMENT_ERROR'
'msgfmt_create: message formatter creation failed: U_ILLEGAL_ARGUMENT_ERROR'
'msgfmt_create: message formatter creation failed: U_ILLEGAL_ARGUMENT_ERROR'
Expand All @@ -145,17 +145,17 @@ TypeError: MessageFormatter::create(): Argument #1 ($locale) must be of type str
TypeError: msgfmt_create(): Argument #1 ($locale) must be of type string, array given in %s on line %d
'U_ZERO_ERROR'

IntlException: Constructor failed in %s on line %d
'msgfmt_create: message formatter creation failed: U_PATTERN_SYNTAX_ERROR'
'msgfmt_create: message formatter creation failed: U_PATTERN_SYNTAX_ERROR'
'msgfmt_create: message formatter creation failed: U_PATTERN_SYNTAX_ERROR'
IntlException: pattern syntax error (parse error at offset 1, after "{", before or at "0,choice}"): U_PATTERN_SYNTAX_ERROR in %s on line %d
'pattern syntax error (parse error at offset 1, after "{", before or at "0,choice}"): U_PATTERN_SYNTAX_ERROR'
'pattern syntax error (parse error at offset 1, after "{", before or at "0,choice}"): U_PATTERN_SYNTAX_ERROR'
'pattern syntax error (parse error at offset 1, after "{", before or at "0,choice}"): U_PATTERN_SYNTAX_ERROR'

IntlException: Constructor failed in %s on line %d
IntlException: msgfmt_create: message formatter creation failed: U_UNMATCHED_BRACES in %s on line %d
'msgfmt_create: message formatter creation failed: U_UNMATCHED_BRACES'
'msgfmt_create: message formatter creation failed: U_UNMATCHED_BRACES'
'msgfmt_create: message formatter creation failed: U_UNMATCHED_BRACES'

IntlException: Constructor failed in %s on line %d
IntlException: msgfmt_create: error converting pattern to UTF-16: U_INVALID_CHAR_FOUND in %s on line %d
'msgfmt_create: error converting pattern to UTF-16: U_INVALID_CHAR_FOUND'
'msgfmt_create: error converting pattern to UTF-16: U_INVALID_CHAR_FOUND'
'msgfmt_create: error converting pattern to UTF-16: U_INVALID_CHAR_FOUND'