簡體   English   中英

檢測更新消息失敗

[英]Detecting failure to update a message

我正在開發一個不和諧的機器人,如果它不存在,應該更新或創建一個特定的消息。 如果消息已被具有訪問權限的人刪除,則會出現問題... 創建一個懸空引用,並在需要更新時引發異常。 如何檢測當前頻道中是否不存在具有特定 ID 的消息?

這是當前的代碼:

    TextChannel scoreChannel = channel.getGuild().getTextChannelsByName(gameType + "-ladder", true).get(0);
    String id = ScoreboardController.getScoreboardMessageId(gameType);
    if (id == null)
        scoreChannel.sendMessage(eb.build()).queue();
    else {
        scoreChannel.editMessageById(id, eb.build()).queue(); // this part can fail
    }

請注意, getScoreboardMessageId 從數據庫中獲取先前存儲的 id。

我需要按標題查詢消息或通過其他方式查找消息是否丟失。


我嘗試像這樣檢索嵌入的消息,但沒有成功:

    List<Message> messages = scoreChannel.getHistory().getRetrievedHistory();

After some more searching I managed to do this which works but is not Async:

 TextChannel scoreChannel = channel.getGuild().getTextChannelsByName(gameType + "-ladder", true).get(0);
        List<Message> messages = new MessageHistory(scoreChannel).retrievePast(10).complete();
        boolean wasUpdated = false;
        for (Message msg : messages) {
            if (msg.getEmbeds().get(0).getTitle().equals(content[0])) {
                scoreChannel.editMessageById(msg.getId(), eb.build()).queue();
                wasUpdated = true;
            }
        }
        if (!wasUpdated)
            scoreChannel.sendMessage(eb.build()).queue();

您可以使用隊列的失敗回調:

channel.editMessageById(messageId, embed).queue(
    (success) -> {
        System.out.printf("[%#s] %s (edited)\n",
                   success.getAuthor(), success.getContentDisplay()); // its a Message
    },
    (failure) -> {
        failure.printStackTrace(); // its a throwable
    }
);

被調用的失敗回調意味着編輯失敗。 如果消息不再存在或出現某些連接問題,就會發生這種情況。 請注意,您可以為這些回調中的任何一個傳遞 null 以簡化僅應處理失敗或僅應處理成功的情況。

正如文檔所建議的那樣, getRetrievedHistory()方法返回一個空列表,除非您之前使用過retrievePastretrieveFuture ,它們都返回RestAction<List<Message>> 這意味着您必須使用:

history.retrievePast(amount).queue((messages) -> {
    /* use messages here */
});

該數量限制為每次呼叫最多 100 條消息。 channel.getIterableHistory().takeAsync(amount)提供了一個沒有這個限制的更簡單的 API,它返回一個CompletableFuture並且可以與thenAccept結合使用。

更好的是使用channel.retrieveMessageById(messageId) ,它只檢索消息,如果消息不存在則失敗。 然而,這在您的情況下是不需要的,因為您通過 id 編輯消息並且可以只使用它的失敗響應而不是遇到TOCTOU Problem

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM