wechat_minapp/minapp_security/
mod.rs1mod msg_sec_check;
7
8use serde::{Deserialize, Serialize};
9use serde_repr::Deserialize_repr;
10use strum::Display;
11
12pub use msg_sec_check::{Args, MsgSecCheckResult, Scene};
13
14#[derive(Debug, Deserialize_repr, Display, Serialize, PartialEq, Clone)]
15#[repr(i32)]
16pub enum Label {
17 #[strum(serialize = "正常")]
18 Normal = 100,
19
20 #[strum(serialize = "广告")]
21 Ad = 10001,
22
23 #[strum(serialize = "时政")]
24 Politics = 20001,
25
26 #[strum(serialize = "色情")]
27 Porn = 20002,
28
29 #[strum(serialize = "辱骂")]
30 Abuse = 20003,
31
32 #[strum(serialize = "违法犯罪")]
33 Illegal = 20006,
34
35 #[strum(serialize = "欺诈")]
36 Fraud = 20008,
37
38 #[strum(serialize = "低俗")]
39 Vulgar = 20012,
40
41 #[strum(serialize = "版权")]
42 Copyright = 20013,
43
44 #[strum(serialize = "其他")]
45 Other = 21000,
46}
47
48impl Label {
50 pub fn from_value(value: i32) -> Option<Self> {
52 match value {
53 100 => Some(Label::Normal),
54 10001 => Some(Label::Ad),
55 20001 => Some(Label::Politics),
56 20002 => Some(Label::Porn),
57 20003 => Some(Label::Abuse),
58 20006 => Some(Label::Illegal),
59 20008 => Some(Label::Fraud),
60 20012 => Some(Label::Vulgar),
61 20013 => Some(Label::Copyright),
62 21000 => Some(Label::Other),
63 _ => None,
64 }
65 }
66
67 pub fn is_normal(&self) -> bool {
69 matches!(self, Label::Normal)
70 }
71
72 pub fn is_violation(&self) -> bool {
74 !self.is_normal()
75 }
76}
77
78#[derive(Debug, Deserialize, Serialize, Display, PartialEq, Clone)]
80pub enum Suggest {
81 #[strum(serialize = "risky")]
82 #[serde(rename = "risky")]
83 Risky,
84
85 #[strum(serialize = "pass")]
86 #[serde(rename = "pass")]
87 Pass,
88
89 #[strum(serialize = "review")]
90 #[serde(rename = "review")]
91 Review,
92}
93
94impl Suggest {
96 pub fn is_pass(&self) -> bool {
98 matches!(self, Suggest::Pass)
99 }
100
101 pub fn is_risky(&self) -> bool {
103 matches!(self, Suggest::Risky)
104 }
105
106 pub fn needs_review(&self) -> bool {
108 matches!(self, Suggest::Review)
109 }
110
111 pub fn priority(&self) -> u8 {
113 match self {
114 Suggest::Risky => 1, Suggest::Review => 2, Suggest::Pass => 3, }
118 }
119}
120
121impl From<&str> for Suggest {
122 fn from(s: &str) -> Self {
123 match s.to_lowercase().as_str() {
124 "risky" => Suggest::Risky,
125 "pass" => Suggest::Pass,
126 "review" => Suggest::Review,
127 _ => Suggest::Review,
128 }
129 }
130}
131
132#[cfg(test)]
133mod tests {
134 use super::*;
135
136 #[test]
137 fn test_suggest_enum() {
138 assert_eq!(Suggest::Risky.to_string(), "risky");
140 assert_eq!(Suggest::Pass.to_string(), "pass");
141 assert_eq!(Suggest::Review.to_string(), "review");
142
143 assert_eq!(Suggest::from("risky"), Suggest::Risky);
145 assert_eq!(Suggest::from("PASS"), Suggest::Pass);
146 assert_eq!(Suggest::from("ReViEw"), Suggest::Review);
147 assert_eq!(Suggest::from("invalid"), Suggest::Review);
148
149 assert!(Suggest::Pass.is_pass());
151 assert!(Suggest::Risky.is_risky());
152 assert!(Suggest::Review.needs_review());
153
154 assert_eq!(Suggest::Risky.priority(), 1);
156 assert_eq!(Suggest::Review.priority(), 2);
157 assert_eq!(Suggest::Pass.priority(), 3);
158 }
159
160 #[test]
161 fn test_serialization() {
162 let risky_json = serde_json::to_string(&Suggest::Risky).unwrap();
164 assert_eq!(risky_json, "\"risky\"");
165
166 let pass_json = serde_json::to_string(&Suggest::Pass).unwrap();
167 assert_eq!(pass_json, "\"pass\"");
168
169 let review: Suggest = serde_json::from_str("\"review\"").unwrap();
171 assert_eq!(review, Suggest::Review);
172 }
173}