/* * Copyright 2004 Perforce Software. All rights reserved. * * Developed by Data Shades Ltd. */ #include "PerforceConnection.h" #include "PasswordDialog.h" #include "Translate.h" #include <i18napi.h> #include "debug.h" PerforceConnection::PerforceConnection( PluginOperations *ops ) : connected( false ), loginPassword( NULL ) { this->ops = ops; } PerforceConnection::~PerforceConnection() { if ( connected ) { Disconnect(); } } void PerforceConnection::Exec( PerforceCommand* cmd, PerforceResults* results ) { this->cmd = cmd; this->results = results; // Connect if not connected if ( !connected ) { Connect(); } // Check if we have got connection info if ( !ops->GotConnectionInfo() ) { GetInfo(); } while ( true ) { // Check if we have a previously entered password if ( ops->GetPassword().Length() > 0 ) { SetPassword( &ops->GetPassword() ); } // Clear any existing results results->Reset(); // Set the command args SetArgv( cmd->GetNumArgs(), (char *const *)cmd->GetArgs() ); // Execute the command Run( cmd->GetCommand(), this ); // Check for errors if ( results->HasErrors() ) { TCHAR *msg = results->GetText(); if ( _tcsncmp( msg, INVALID_PASSWORD_MSG, _tcslen( INVALID_PASSWORD_MSG ) ) == 0 || _tcsstr( msg, SESSION_EXPIRED_MSG ) != NULL ) { UniStrBuf user; Translate::ToWinChar( GetUser().Text(), &user ); UniStrBuf port; Translate::ToWinChar( GetPort().Text(), &port ); PasswordDialog dialog( ops, user.Text(), port.Text() ); if ( dialog.Show( ops->GetHost()->GetInstance(), ops->GetHost()->GetWin() ) == TRUE ) { if ( ops->GetUseLogin() ) { DoLogin( dialog.GetPassword() ); } else { ops->SetPassword( dialog.GetPassword() ); } continue; } } TCHAR *err = results->GetText(); StrBuf utf8; Translate::FromWinChar( err, &utf8 ); throw std::exception( utf8.Text() ); } else { break; } } } void PerforceConnection::Prompt( const StrPtr &msg, StrBuf &rsp, int noEcho, Error *e ) { if ( loginPassword != NULL ) { StrBuf buff; Translate::FromWinChar( loginPassword, &buff ); rsp << buff.Text(); } } void PerforceConnection::OutputStat( StrDict* varList ) { SpecDataTable specData; StrPtr *data = varList->GetVar( "data" ); StrPtr *spec = varList->GetVar( "specdef" ); StrDict *dict = varList; // Check if have form output if ( spec && data ) { // Parse the form data using the spec // and load the result into the SpecDataTable // That stores its contents in a StrDict. // Use that for our results Error e; Spec s( spec->Text(), "", &e ); if ( e.Test() ) { HandleError( &e ); return; } s.Parse( data->Text(), &specData, &e ); if ( e.Test() ) { HandleError( &e ); return; } dict = specData.Dict(); dict->SetVar( "data", data ); } // Append dictionary output to results results->Append( dict ); } void PerforceConnection::OutputInfo( char level, const char *data ) { // Append info output to results results->Append( level, data ); } void PerforceConnection::OutputError( const char *data ) { // Append error output to results results->AppendError( data ); } void PerforceConnection::InputData( StrBuf *strbuf, Error *e ) { StrRef var, val; StrDict *input = cmd->GetInput(); strbuf->Clear(); for( int i = 0; input->GetVar( i, var, val ); i++ ) { *strbuf << var << ":\t" << val << "\n"; } } void PerforceConnection::DoLogin( TCHAR *password ) { // Clear any existing results results->Reset(); // Set the command args SetArgv( 0, NULL ); loginPassword = password; Run( "login", this ); loginPassword = NULL; } void PerforceConnection::GetInfo() { // Clear any existing results results->Reset(); // Execute the "info" command Run( "info" , this ); // Check if server >= 2004.2 StrPtr *version = GetProtocol( "server2" ); if ( version != NULL ) { if ( atol( version->Text() ) >= SERVER_SECURITY_PROTOCOL ) { ops->SetUseLogin(); } } ops->SetGotConnectionInfo(); } void PerforceConnection::Connect() { Error err; SetProtocol( "specstring", "" ); SetProtocol( "tag", "" ); SetProtocol( "api", "57" ); // 2005.2 mode SetProtocol( "enableStreams", "yes" ); StrPtr cs = GetCharset(); if ( cs.Length() && CharSetApi::Lookup( cs.Text() ) > 0 ) { SetTrans( CharSetApi::UTF_8 ); } // Connect to server Init( &err ); if ( err.Test() ) { ThrowError( err ); } else { // Make sure we get english messages SetLanguage( "en" ); connected = true; } } void PerforceConnection::Disconnect() { Error err; Final( &err ); if ( err.Test() ) { // Ignore disconnect errors } else { connected = false; } } void PerforceConnection::ThrowError( Error &err ) { StrBuf buf; err.Fmt( buf, EF_NEWLINE ); throw std::exception( buf.Text() ); } const StrPtr &PerforceConnection::GetCwd() { StrPtr cd = ClientApi::GetCwd(); static UniStrBuf buff; Translate::ToWinChar( cd.Text(), &buff ); return buff; }
# | Change | User | Description | Committed | |
---|---|---|---|---|---|
#1 | 11314 | Robert Cowham | Initial population of perforce_software version of P4OFC | ||
//guest/robert_cowham/perforce/P4OFC/main/libp4gt/PerforceConnection.cpp | |||||
#2 | 11209 | Robert Cowham | Enable streams for browsing the depot | ||
#1 | 10843 | Robert Cowham |
Initial version of P4OFC source code. See README.txt (and LICENSE.txt and doc\P4OFC-Design.docx) |