mirror of
https://github.com/Eyre-S/Coeur-Morny-Cono.git
synced 2024-11-22 11:14:55 +08:00
添加了 morny login/exit 的报告,*msg 现在支持了只包含发送 id 不包含发送体
- 为 MornyCoeur 添加了 whileExitReason (exit/getExitReason) 接口,用于安全退出时指定推出原因 - MornyConfig 添加了一个 Sensitive 注解用于标明字段值属于敏感字段不应该被打印 -
This commit is contained in:
parent
01b4eea917
commit
3689962cb3
@ -5,7 +5,7 @@ MORNY_ARCHIVE_NAME = morny-coeur
|
||||
MORNY_CODE_STORE = https://github.com/Eyre-S/Coeur-Morny-Cono
|
||||
MORNY_COMMIT_PATH = https://github.com/Eyre-S/Coeur-Morny-Cono/commit/%s
|
||||
|
||||
VERSION = 1.0.0-alpha5
|
||||
VERSION = 1.0.0-alpha6
|
||||
|
||||
USE_DELTA = false
|
||||
VERSION_DELTA =
|
||||
|
@ -60,6 +60,8 @@ public class MornyCoeur {
|
||||
*/
|
||||
public static final long coeurStartTimestamp = ServerMain.systemStartupTime;
|
||||
|
||||
private Object whileExitReason = null;
|
||||
|
||||
private record LogInResult(TelegramBot account, String username, long userid) { }
|
||||
|
||||
/**
|
||||
@ -152,7 +154,6 @@ public class MornyCoeur {
|
||||
* 用于退出时进行缓存的任务处理等进行安全退出
|
||||
*/
|
||||
private void exitCleanup () {
|
||||
logger.info("clean:save tracker data.");
|
||||
MornyDaemons.stop();
|
||||
if (config.commandLogoutClear) {
|
||||
commandManager.automaticRemoveList();
|
||||
@ -304,4 +305,13 @@ public class MornyCoeur {
|
||||
|
||||
public static long getUserid () { return INSTANCE.userid; }
|
||||
|
||||
public static void exit (int status, Object reason) {
|
||||
INSTANCE.whileExitReason = reason;
|
||||
System.exit(status);
|
||||
}
|
||||
|
||||
public static Object getExitReason () {
|
||||
return INSTANCE.whileExitReason;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -2,11 +2,20 @@ package cc.sukazyo.cono.morny;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
import java.lang.annotation.*;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
|
||||
public class MornyConfig {
|
||||
|
||||
/**
|
||||
* 表示一个字段的值属于敏感数据,不应该被执行打印等操作。
|
||||
*/
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Documented
|
||||
@Target({ElementType.FIELD, ElementType.METHOD})
|
||||
public @interface Sensitive {}
|
||||
|
||||
/* ======================================= *
|
||||
* Config props Names Definition *
|
||||
* ======================================= */
|
||||
@ -37,7 +46,7 @@ public class MornyConfig {
|
||||
* <p>
|
||||
* 这个值必须设定。
|
||||
*/
|
||||
@Nonnull public final String telegramBotKey;
|
||||
@Nonnull @Sensitive public final String telegramBotKey;
|
||||
/**
|
||||
* morny 所使用的 bot 的 username.
|
||||
* <p>
|
||||
|
@ -213,7 +213,7 @@ public class MornyCommands {
|
||||
).replyToMessageId(event.message().messageId())
|
||||
);
|
||||
logger.info("Morny exited by user " + TGToString.as(event.message().from()).toStringLogTag());
|
||||
System.exit(0);
|
||||
MornyCoeur.exit(0, event.message().from());
|
||||
} else {
|
||||
MornyCoeur.extra().exec(new SendSticker(
|
||||
event.message().chat().id(),
|
||||
|
@ -27,12 +27,12 @@ import static cc.sukazyo.cono.morny.util.tgapi.formatting.MsgEscape.escapeHtml;
|
||||
|
||||
public class OnCallMsgSend extends EventListener {
|
||||
|
||||
private static final Pattern REGEX_MSG_SENDREQ_DATA_HEAD = Pattern.compile("^\\*msg([\\d-]+)(\\*\\S+)?\\n([\\s\\S]+)$");
|
||||
private static final Pattern REGEX_MSG_SENDREQ_DATA_HEAD = Pattern.compile("^\\*msg(-?\\d+)(\\*\\S+)?(?:\\n([\\s\\S]+))?$");
|
||||
|
||||
private record MessageToSend (
|
||||
String message,
|
||||
MessageEntity[] entities,
|
||||
ParseMode parseMode,
|
||||
@Nullable String message,
|
||||
@Nullable MessageEntity[] entities,
|
||||
@Nullable ParseMode parseMode,
|
||||
long targetId
|
||||
) { }
|
||||
|
||||
@ -62,7 +62,7 @@ public class OnCallMsgSend extends EventListener {
|
||||
// 发送体处理
|
||||
if (update.message().replyToMessage() == null) return answer404(update);
|
||||
msgsendReqBody = parseRequest(update.message().replyToMessage());
|
||||
if (msgsendReqBody == null) return answer404(update);
|
||||
if (msgsendReqBody == null || msgsendReqBody.message == null) return answer404(update);
|
||||
// 执行发送任务
|
||||
SendResponse sendResponse = MornyCoeur.getAccount().execute(parseMessageToSend(msgsendReqBody));
|
||||
if (!sendResponse.isOk()) { // 发送失败
|
||||
@ -150,7 +150,8 @@ public class OnCallMsgSend extends EventListener {
|
||||
).replyToMessageId(update.message().messageId()).parseMode(ParseMode.HTML));
|
||||
}
|
||||
// 发送文本测试
|
||||
SendResponse testSendResp = MornyCoeur.getAccount().execute(
|
||||
if (msgsendReqBody.message == null) return true;
|
||||
final SendResponse testSendResp = MornyCoeur.getAccount().execute(
|
||||
parseMessageToSend(msgsendReqBody, update.message().chat().id()).replyToMessageId(update.message().messageId())
|
||||
);
|
||||
if (!testSendResp.isOk()) {
|
||||
|
@ -1,5 +1,7 @@
|
||||
package cc.sukazyo.cono.morny.daemon;
|
||||
|
||||
import cc.sukazyo.cono.morny.MornyCoeur;
|
||||
|
||||
import static cc.sukazyo.cono.morny.Log.logger;
|
||||
|
||||
public class MornyDaemons {
|
||||
@ -10,6 +12,7 @@ public class MornyDaemons {
|
||||
logger.info("ALL Morny Daemons starting...");
|
||||
// TrackerDataManager.init();
|
||||
medicationTimerInstance.start();
|
||||
MornyReport.onMornyLogIn();
|
||||
logger.info("Morny Daemons started.");
|
||||
}
|
||||
|
||||
@ -23,6 +26,7 @@ public class MornyDaemons {
|
||||
// TrackerDataManager.trackingLock.lock();
|
||||
try { medicationTimerInstance.join(); } catch (InterruptedException e) { e.printStackTrace(System.out); }
|
||||
|
||||
MornyReport.onMornyExit(MornyCoeur.getExitReason());
|
||||
logger.info("ALL Morny Daemons STOPPED.");
|
||||
|
||||
}
|
||||
|
@ -2,6 +2,7 @@ package cc.sukazyo.cono.morny.daemon;
|
||||
|
||||
import cc.sukazyo.cono.morny.Log;
|
||||
import cc.sukazyo.cono.morny.MornyCoeur;
|
||||
import cc.sukazyo.cono.morny.MornyConfig;
|
||||
import cc.sukazyo.cono.morny.util.tgapi.event.EventRuntimeException;
|
||||
import cc.sukazyo.cono.morny.util.tgapi.formatting.TGToString;
|
||||
import com.google.gson.GsonBuilder;
|
||||
@ -14,6 +15,9 @@ import com.pengrad.telegrambot.response.BaseResponse;
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
|
||||
import static cc.sukazyo.cono.morny.Log.logger;
|
||||
import static cc.sukazyo.cono.morny.util.tgapi.formatting.MsgEscape.escapeHtml;
|
||||
|
||||
public class MornyReport {
|
||||
@ -23,8 +27,10 @@ public class MornyReport {
|
||||
try {
|
||||
MornyCoeur.extra().exec(report);
|
||||
} catch (EventRuntimeException.ActionFailed e) {
|
||||
Log.logger.warn("cannot execute report to telegram:");
|
||||
Log.logger.warn(Log.exceptionLog(e));
|
||||
logger.warn("cannot execute report to telegram:");
|
||||
logger.warn(Log.exceptionLog(e).indent(4));
|
||||
logger.warn("tg-api response:");
|
||||
logger.warn(e.getResponse().toString().indent(4));
|
||||
}
|
||||
}
|
||||
|
||||
@ -64,4 +70,85 @@ public class MornyReport {
|
||||
).parseMode(ParseMode.HTML));
|
||||
}
|
||||
|
||||
/**
|
||||
* morny 登陆时的报告发送,包含已登录的账号 id 以及启动配置。
|
||||
* @since 1.0.0-alpha6
|
||||
*/
|
||||
public static void onMornyLogIn () {
|
||||
executeReport(new SendMessage(
|
||||
MornyCoeur.config().reportToChat,
|
||||
String.format("""
|
||||
<b>▌Morny Logged in</b>
|
||||
as user @%s
|
||||
|
||||
as config fields:
|
||||
%s
|
||||
""",
|
||||
MornyCoeur.getUsername(),
|
||||
sectionConfigFields(MornyCoeur.config())
|
||||
)
|
||||
).parseMode(ParseMode.HTML));
|
||||
}
|
||||
|
||||
/**
|
||||
* 返回一个 config 字段与值的列表,可以作为 telegram html 格式输出
|
||||
* @since 1.0.0-alpha6
|
||||
*/
|
||||
private static String sectionConfigFields (@Nonnull MornyConfig config) {
|
||||
final StringBuilder echo = new StringBuilder();
|
||||
for (Field field : config.getClass().getFields()) {
|
||||
echo.append("- <i><u>").append(field.getName()).append("</u></i> ");
|
||||
try {
|
||||
if (field.isAnnotationPresent(MornyConfig.Sensitive.class)) {
|
||||
echo.append(": <i>sensitive_field</i>");
|
||||
} else {
|
||||
final Object fieldValue = field.get(config);
|
||||
echo.append("= ");
|
||||
if (fieldValue == null)
|
||||
echo.append("null");
|
||||
else echo.append("<code>").append(escapeHtml(fieldValue.toString())).append("</code>");
|
||||
}
|
||||
} catch (IllegalAccessException | IllegalArgumentException | NullPointerException e) {
|
||||
echo.append(": <i>").append(escapeHtml("<read-error>")).append("</i>");
|
||||
logger.error("error while reading config field " + field.getName());
|
||||
logger.error(Log.exceptionLog(e));
|
||||
exception(e, "error while reading config field " + field.getName());
|
||||
}
|
||||
echo.append("\n");
|
||||
}
|
||||
return echo.substring(0, echo.length()-1);
|
||||
}
|
||||
|
||||
/**
|
||||
* morny 关闭/登出时发送的报告.
|
||||
* <p>
|
||||
* 基于 java 的程序关闭钩子,因此仍然无法在意外宕机的情况下发送报告.
|
||||
* @param causedBy
|
||||
* 关闭的原因。
|
||||
* 可以使用 {@link User Telegram 用户对象} 表示由一个用户执行了关闭,
|
||||
* 传入其它数据将使用 {@code #toString} 输出其内容。
|
||||
* 传入 {@link null} 则表示不表明原因。
|
||||
*/
|
||||
static void onMornyExit (@Nullable Object causedBy) {
|
||||
if (!MornyCoeur.available()) return;
|
||||
String causedTag = null;
|
||||
if (causedBy != null) {
|
||||
if (causedBy instanceof User)
|
||||
causedTag = TGToString.as((User)causedBy).fullnameRefHtml();
|
||||
else
|
||||
causedTag = "<code>" + escapeHtml(causedBy.toString()) + "</code>";
|
||||
}
|
||||
executeReport(new SendMessage(
|
||||
MornyCoeur.config().reportToChat,
|
||||
String.format("""
|
||||
<b>▌Morny Exited</b>
|
||||
from user @%s
|
||||
%s
|
||||
""",
|
||||
MornyCoeur.getUsername(),
|
||||
causedBy == null ? "with UNKNOWN reason" : "\nby " + causedTag
|
||||
)
|
||||
).parseMode(ParseMode.HTML));
|
||||
}
|
||||
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user