#ifndef MYX_REDIS_PARSER_INL_HPP_ #define MYX_REDIS_PARSER_INL_HPP_ #pragma once #ifndef MYXLIB_HEADER_ONLY #include #endif namespace myx { namespace redis { Parser::Parser( Lexer* lexer, QObject* parent ) : QObject( parent ) { connect( lexer, &Lexer::character, this, &Parser::readCharacter ); connect( lexer, &Lexer::unsafeString, this, &Parser::readUnsafeString ); connect( lexer, &Lexer::safeString, this, &Parser::readSafeString ); } void Parser::readCharacter( const char c ) { switch ( c ) { case '+': stack.append( Task( Reply::Status ) ); break; case '-': stack.append( Task( Reply::Error ) ); break; case ':': stack.append( Task( Reply::Integer ) ); break; case '$': stack.append( Task( Reply::Bulk ) ); break; case '*': stack.append( Task( Reply::MultiBulk ) ); break; default: break; } } void Parser::readUnsafeString( const QString& value ) { if ( tos().reply.type() == Reply::MultiBulk ) { tos().count = value.toInt(); } else { tos().reply.value() = value; } descend(); } void Parser::readSafeString( const QByteArray& value ) { tos().reply.value() = value; descend(); } void Parser::descend() { while ( true ) { if ( ( tos().reply.type() == Reply::MultiBulk ) && ( tos().reply.value().toList().count() < tos().count ) ) { return; } if ( stack.count() == 1 ) { auto r = stack.takeLast().reply; Q_EMIT reply( r ); return; } auto r = stack.takeLast().reply; tos().reply.value().toList().append( QVariant::fromValue( r ) ); } } } // namespace redis } // namespace myx #endif // ifndef MYX_REDIS_PARSER_INL_HPP_