From 8b13dbcef179975d976729f940451e347ea4f511 Mon Sep 17 00:00:00 2001 From: Kristian Bendiksen Date: Tue, 20 Jan 2026 14:03:49 +0100 Subject: [PATCH] #12940 Fix empty vector parsing and ReadPastEnd handling for Python GRPC - Handle empty arrays [] in std::vector parser - Only treat ReadCorruptData as error in generic template (ReadPastEnd is expected for types like caf::FilePath that consume all input) - Use strict mode (allowExtraCharacters=false) for Python GRPC parsing --- .../cafPdmFieldScriptingCapability.h | 20 ++++--------------- ...cafPdmFieldScriptingCapabilityCvfVec3d.cpp | 11 +++++++++- GrpcInterface/RiaGrpcServiceInterface.cpp | 2 +- 3 files changed, 15 insertions(+), 18 deletions(-) diff --git a/Fwk/AppFwk/cafPdmScripting/cafPdmFieldScriptingCapability.h b/Fwk/AppFwk/cafPdmScripting/cafPdmFieldScriptingCapability.h index f17c0a07a0..12c0d5b404 100644 --- a/Fwk/AppFwk/cafPdmScripting/cafPdmFieldScriptingCapability.h +++ b/Fwk/AppFwk/cafPdmScripting/cafPdmFieldScriptingCapability.h @@ -210,23 +210,11 @@ struct PdmFieldScriptingCapabilityIOHandler bool allowExtraCharacters = true ) { inputStream >> fieldValue; - if ( inputStream.status() != QTextStream::Ok ) + // Only report ReadCorruptData as an error. ReadPastEnd just means the stream was fully + // consumed, which is expected for types like caf::FilePath that read all available input. + if ( inputStream.status() == QTextStream::ReadCorruptData ) { - QString errorMessage; - if ( inputStream.status() == QTextStream::ReadPastEnd ) - { - errorMessage = "Read past end of argument"; - } - else if ( inputStream.status() == QTextStream::ReadCorruptData ) - { - errorMessage = "Argument value is unreadable"; - } - else - { - errorMessage = "Unknown read error"; - } - - errorMessageContainer->addError( errorMessage + ": \"" + errorMessageContainer->currentArgument + + errorMessageContainer->addError( "Argument value is unreadable: \"" + errorMessageContainer->currentArgument + "\" in the command: \"" + errorMessageContainer->currentCommand + "\"" ); inputStream.setStatus( QTextStream::Ok ); } diff --git a/Fwk/AppFwk/cafPdmScripting/cafPdmFieldScriptingCapabilityCvfVec3d.cpp b/Fwk/AppFwk/cafPdmScripting/cafPdmFieldScriptingCapabilityCvfVec3d.cpp index d300d53697..d259cf874d 100644 --- a/Fwk/AppFwk/cafPdmScripting/cafPdmFieldScriptingCapabilityCvfVec3d.cpp +++ b/Fwk/AppFwk/cafPdmScripting/cafPdmFieldScriptingCapabilityCvfVec3d.cpp @@ -99,6 +99,15 @@ void PdmFieldScriptingCapabilityIOHandler>>::wr { while ( !inputStream.atEnd() ) { + // Check for closing bracket first (handles empty array case) + errorMessageContainer->skipWhiteSpaceWithLineNumberCount( inputStream ); + QChar nextChar = errorMessageContainer->peekNextChar( inputStream ); + if ( nextChar == QChar( ']' ) ) + { + nextChar = errorMessageContainer->readCharWithLineNumberCount( inputStream ); + break; + } + std::vector fieldVectorValue; PdmFieldScriptingCapabilityIOHandler>::writeToField( fieldVectorValue, @@ -120,7 +129,7 @@ void PdmFieldScriptingCapabilityIOHandler>>::wr } errorMessageContainer->skipWhiteSpaceWithLineNumberCount( inputStream ); - QChar nextChar = errorMessageContainer->peekNextChar( inputStream ); + nextChar = errorMessageContainer->peekNextChar( inputStream ); if ( nextChar == QChar( ']' ) ) { nextChar = errorMessageContainer->readCharWithLineNumberCount( inputStream ); diff --git a/GrpcInterface/RiaGrpcServiceInterface.cpp b/GrpcInterface/RiaGrpcServiceInterface.cpp index 58e66245f2..e83a25c33e 100644 --- a/GrpcInterface/RiaGrpcServiceInterface.cpp +++ b/GrpcInterface/RiaGrpcServiceInterface.cpp @@ -282,7 +282,7 @@ std::expected RiaGrpcServiceInterface::assignFieldValue( const QS // Step 1: Save old value for potential rollback if ( valueField ) *oldValue = valueField->toQVariant(); - // Step 2: Parse and set new value + // Step 2: Parse and set new value (strict mode for GRPC) QTextStream stream( stringValue.toLatin1() ); scriptability->writeToField( stream, nullptr, messages, false, RimProject::current(), false );