27using namespace kiapi::common::commands;
 
   46    if( std::optional<ApiResponseStatus> busy = 
checkForBusy() )
 
   47        return tl::unexpected( *busy );
 
   52        e.set_status( ApiStatusCode::AS_BAD_REQUEST );
 
   53        e.set_error_message( fmt::format( 
"the client {} already has a commit in progress",
 
   55        return tl::unexpected( e );
 
   60    BeginCommitResponse response;
 
   64    response.mutable_id()->set_value( 
id.AsStdString() );
 
 
   75    if( std::optional<ApiResponseStatus> busy = 
checkForBusy() )
 
   76        return tl::unexpected( *busy );
 
   81        e.set_status( ApiStatusCode::AS_BAD_REQUEST );
 
   82        e.set_error_message( fmt::format( 
"the client {} does not has a commit in progress",
 
   84        return tl::unexpected( e );
 
   90    const KIID& 
id = pair.first;
 
   91    const std::unique_ptr<COMMIT>& commit = pair.second;
 
   93    EndCommitResponse response;
 
   98    case kiapi::common::commands::CMA_DROP:
 
  106    case kiapi::common::commands::CMA_COMMIT:
 
  108        if( aCtx.
Request.id().value().compare( 
id.AsStdString() ) != 0 )
 
  111            e.set_status( ApiStatusCode::AS_BAD_REQUEST );
 
  112            e.set_error_message( fmt::format( 
"the id {} does not match the commit in progress",
 
  114            return tl::unexpected( e );
 
 
  137    return m_commits.at( aClientName ).second.get();
 
 
  142                                            const wxString& aMessage )
 
 
  160        e.set_status( ApiStatusCode::AS_BAD_REQUEST );
 
  161        e.set_error_message( fmt::format( 
"the requested document {} is not open",
 
  162                                          aDocument.board_filename() ) );
 
  163        return tl::unexpected( e );
 
 
  171        const types::ItemHeader& aHeader )
 
  173    if( !aHeader.has_document() || aHeader.document().type() != 
thisDocumentType() )
 
  176        e.set_status( ApiStatusCode::AS_UNHANDLED );
 
  178        return tl::unexpected( e );
 
  183    if( !documentValidation )
 
  184        return tl::unexpected( documentValidation.error() );
 
  189        e.set_status( ApiStatusCode::AS_BAD_REQUEST );
 
  190        e.set_error_message( fmt::format( 
"the requested document {} is not open",
 
  191                                          aHeader.document().board_filename() ) );
 
  192        return tl::unexpected( e );
 
  195    if( aHeader.has_container() )
 
  197        return KIID( aHeader.container().value() );
 
 
  207    if( !
m_frame->CanAcceptApiCommands() )
 
  210        e.set_status( ApiStatusCode::AS_BUSY );
 
  211        e.set_error_message( 
"KiCad is busy and cannot respond to API requests right now" );
 
 
  222    if( std::optional<ApiResponseStatus> busy = 
checkForBusy() )
 
  223        return tl::unexpected( *busy );
 
  225    CreateItemsResponse response;
 
  230            [&]( 
const ItemStatus& aStatus, 
const google::protobuf::Any& aItem )
 
  232                ItemCreationResult itemResult;
 
  233                itemResult.mutable_status()->CopyFrom( aStatus );
 
  234                itemResult.mutable_item()->CopyFrom( aItem );
 
  235                response.mutable_created_items()->Add( std::move( itemResult ) );
 
  239        return tl::unexpected( 
result.error() );
 
  241    response.set_status( *
result );
 
 
  249    if( std::optional<ApiResponseStatus> busy = 
checkForBusy() )
 
  250        return tl::unexpected( *busy );
 
  252    UpdateItemsResponse response;
 
  257            [&]( 
const ItemStatus& aStatus, 
const google::protobuf::Any& aItem )
 
  259                ItemUpdateResult itemResult;
 
  260                itemResult.mutable_status()->CopyFrom( aStatus );
 
  261                itemResult.mutable_item()->CopyFrom( aItem );
 
  262                response.mutable_updated_items()->Add( std::move( itemResult ) );
 
  266        return tl::unexpected( 
result.error() );
 
  268    response.set_status( *
result );
 
 
  276    if( std::optional<ApiResponseStatus> busy = 
checkForBusy() )
 
  277        return tl::unexpected( *busy );
 
  283        e.set_status( ApiStatusCode::AS_UNHANDLED );
 
  284        return tl::unexpected( e );
 
  287    std::map<KIID, ItemDeletionStatus> itemsToDelete;
 
  289    for( 
const kiapi::common::types::KIID& kiidBuf : aCtx.
Request.item_ids() )
 
  291        if( !kiidBuf.value().empty() )
 
  293            KIID kiid( kiidBuf.value() );
 
  294            itemsToDelete[kiid] = ItemDeletionStatus::IDS_NONEXISTENT;
 
  298    if( itemsToDelete.empty() )
 
  301        e.set_status( ApiStatusCode::AS_BAD_REQUEST );
 
  302        e.set_error_message( 
"no valid items to delete were given" );
 
  303        return tl::unexpected( e );
 
  308    DeleteItemsResponse response;
 
  310    for( 
const auto& [
id, status] : itemsToDelete )
 
  312        ItemDeletionResult 
result;
 
  313        result.mutable_id()->set_value( 
id.AsStdString() );
 
  314        result.set_status( status );
 
  317    response.set_status( kiapi::common::types::ItemRequestStatus::IRS_OK );
 
 
  325    if( std::optional<ApiResponseStatus> busy = 
checkForBusy() )
 
  326        return tl::unexpected( *busy );
 
  332        e.set_status( ApiStatusCode::AS_UNHANDLED );
 
  333        return tl::unexpected( e );
 
  336    HitTestResponse response;
 
  344        e.set_status( ApiStatusCode::AS_BAD_REQUEST );
 
  345        e.set_error_message( 
"the requested item ID is not present in the given document" );
 
  346        return tl::unexpected( e );
 
  350        response.set_result( HitTestResult::HTR_HIT );
 
  352        response.set_result( HitTestResult::HTR_NO_HIT );
 
 
tl::expected< T, ApiResponseStatus > HANDLER_RESULT
 
virtual std::unique_ptr< COMMIT > createCommit()=0
Override this to create an appropriate COMMIT subclass for the frame in question.
 
HANDLER_RESULT< bool > validateDocument(const DocumentSpecifier &aDocument)
 
HANDLER_RESULT< commands::DeleteItemsResponse > handleDeleteItems(const HANDLER_CONTEXT< commands::DeleteItems > &aCtx)
 
virtual std::optional< EDA_ITEM * > getItemFromDocument(const DocumentSpecifier &aDocument, const KIID &aId)=0
 
HANDLER_RESULT< std::optional< KIID > > validateItemHeaderDocument(const kiapi::common::types::ItemHeader &aHeader)
If the header is valid, returns the item container.
 
HANDLER_RESULT< commands::EndCommitResponse > handleEndCommit(const HANDLER_CONTEXT< commands::EndCommit > &aCtx)
 
API_HANDLER_EDITOR(EDA_BASE_FRAME *aFrame=nullptr)
 
HANDLER_RESULT< commands::CreateItemsResponse > handleCreateItems(const HANDLER_CONTEXT< commands::CreateItems > &aCtx)
 
COMMIT * getCurrentCommit(const std::string &aClientName)
 
virtual void pushCurrentCommit(const std::string &aClientName, const wxString &aMessage)
 
virtual HANDLER_RESULT< ItemRequestStatus > handleCreateUpdateItemsInternal(bool aCreate, const std::string &aClientName, const types::ItemHeader &aHeader, const google::protobuf::RepeatedPtrField< google::protobuf::Any > &aItems, std::function< void(commands::ItemStatus, google::protobuf::Any)> aItemHandler)=0
 
std::set< std::string > m_activeClients
 
std::map< std::string, std::pair< KIID, std::unique_ptr< COMMIT > > > m_commits
 
HANDLER_RESULT< commands::UpdateItemsResponse > handleUpdateItems(const HANDLER_CONTEXT< commands::UpdateItems > &aCtx)
 
virtual void deleteItemsInternal(std::map< KIID, ItemDeletionStatus > &aItemsToDelete, const std::string &aClientName)=0
 
virtual std::optional< ApiResponseStatus > checkForBusy()
Checks if the editor can accept commands.
 
virtual types::DocumentType thisDocumentType() const =0
Override this to specify which document type this editor handles.
 
HANDLER_RESULT< commands::BeginCommitResponse > handleBeginCommit(const HANDLER_CONTEXT< commands::BeginCommit > &aCtx)
 
HANDLER_RESULT< commands::HitTestResponse > handleHitTest(const HANDLER_CONTEXT< commands::HitTest > &aCtx)
 
virtual bool validateDocumentInternal(const DocumentSpecifier &aDocument) const =0
 
static const wxString m_defaultCommitMessage
 
void registerHandler(HANDLER_RESULT< ResponseType >(HandlerType::*aHandler)(const HANDLER_CONTEXT< RequestType > &))
Registers an API command handler for the given message types.
 
Represent a set of changes (additions, deletions or modifications) of a data model (e....
 
The base frame for deriving all KiCad main window classes.
 
Base window classes and related definitions.
 
KICOMMON_API VECTOR2I UnpackVector2(const types::Vector2 &aInput)
 
RequestMessageType Request
 
wxString result
Test unit parsing edge cases and error handling.