3 namespace App\TwitchBot;
5 use App\Models\ChatLog;
6 use Illuminate\Support\Arr;
7 use Illuminate\Support\Str;
9 class TokenizedMessage {
11 public function __construct($text, $tags = []) {
14 $this->raw = strtolower(preg_replace('/[^\w]/u', '', $text));
15 $this->tokens = preg_split('/\s+/', strtolower(trim($text)));
17 $this->emoteless = $this->text;
18 if (isset($this->tags['emotes']) && !empty($this->tags['emotes'])) {
19 $emotes = explode('/', $this->tags['emotes']);
20 foreach ($emotes as $emote) {
21 $set = explode(':', $emote);
22 $positions = explode(',', $set[1]);
23 foreach ($positions as $position) {
24 $coords = explode('-', $position);
25 $this->emotes[] = preg_replace('/\d+$/', '', strtolower(substr($this->text, $coords[0], $coords[1] - $coords[0] + 1)));
26 for ($i = intval($coords[0]); $i <= intval($coords[1]); ++$i) {
27 $this->emoteless[$i] = ' ';
31 $this->emoteless = trim(preg_replace('/\s+/', ' ', $this->emoteless));
33 $this->emoteless_raw = strtolower(preg_replace('/[^\w]/', '', $this->emoteless));
34 $this->emoteless_tokens = preg_split('/\s+/', strtolower($this->emoteless));
37 public static function fromIRC(IRCMessage $msg) {
38 return new self($msg->getText(), $msg->tags);
41 public static function fromLog(ChatLog $log) {
42 return new self($log->params[1], $log->tags);
45 public static function fromString($text, $tags = []) {
46 return new self($text, $tags);
50 public function contains($text) {
51 return Str::contains($this->text, $text);
54 public function containsEmoteless($text) {
55 return Str::contains($this->emoteless, $text);
58 public function containsRaw($text) {
59 return Str::contains($this->raw, $text);
62 public function endsWith($text) {
63 return Str::endsWith($this->text, $text);
66 public function endsWithEmoteless($text) {
67 return Str::endsWith($this->emoteless, $text);
70 public function endsWithRaw($text) {
71 return Str::endsWith($this->raw, $text);
74 public function getNumericValue() {
75 return intval($this->text);
78 public function hasEmote($text) {
79 if (is_array($text)) {
80 foreach ($text as $token) {
81 if (in_array($token, $this->emotes)) {
87 return in_array($text, $this->emotes);
90 public function hasEmoteThatContains($text) {
91 foreach ($this->emotes as $emote) {
92 if (Str::contains($emote, $text)) {
99 public function hasEmoteThatEndsWith($text) {
100 foreach ($this->emotes as $emote) {
101 if (Str::endsWith($emote, $text)) {
108 public function hasEmoteThatStartsOrEndsWith($text) {
109 foreach ($this->emotes as $emote) {
110 if (Str::startsWith($emote, $text) || Str::endsWith($emote, $text)) {
117 public function hasEmoteThatStartsWith($text) {
118 foreach ($this->emotes as $emote) {
119 if (Str::startsWith($emote, $text)) {
126 public function hasToken($text) {
127 if (is_array($text)) {
128 foreach ($text as $token) {
129 if (in_array($token, $this->tokens)) {
135 return in_array($text, $this->tokens);
138 public function hasTokenThatContains($text) {
139 foreach ($this->tokens as $token) {
140 if (Str::contains($token, $text)) {
147 public function hasTokenThatEndsWith($text) {
148 foreach ($this->tokens as $token) {
149 if (Str::endsWith($token, $text)) {
156 public function hasTokenThatStartsOrEndsWith($text) {
157 foreach ($this->tokens as $token) {
158 if (Str::startsWith($token, $text) || Str::endsWith($token, $text)) {
165 public function hasTokenThatStartsWith($text) {
166 foreach ($this->tokens as $token) {
167 if (Str::startsWith($token, $text)) {
174 public function startsOrEndsWith($text) {
175 return $this->startsWith($text) || $this->endsWith($text);
178 public function startsOrEndsWithRaw($text) {
179 return $this->startsWithRaw($text) || $this->endsWithRaw($text);
182 public function startsWith($text) {
183 return Str::startsWith($this->text, $text);
186 public function startsWithEmoteless($text) {
187 return Str::startsWith($this->emoteless, $text);
190 public function startsWithRaw($text) {
191 return Str::startsWith($this->raw, $text);
195 public function isSpammy() {
196 if ($this->startsWith('!')) {
199 if ($this->contains(['€', '$', '@', '://'])) {
202 if ($this->containsRaw(['followers', 'promotion', 'viewers'])) {
205 if ($this->containsRaw('horstie')) {
208 if ($this->containsRaw(['vielendankfürdenraid', 'thanksfortheraid', 'willkommenaufstarbase47'])) {
215 public function classify() {
216 if (is_null($this->classification)) {
217 if (empty($this->raw)) {
218 $this->classification = 'unclassified';
219 } else if ($this->startsWith('!')) {
220 $this->classification = 'cmd';
221 } else if (is_numeric($this->raw)) {
222 $this->classification = 'number';
223 } else if ($this->hasTokenThatStartsOrEndsWith(['gg']) || $this->hasEmoteThatEndsWith(['gg'])) {
224 $this->classification = 'gg';
225 } else if ($this->containsRaw(['glgl', 'glhf', 'goodluck', 'hfgl'])) {
226 $this->classification = 'gl';
227 } else if ($this->startsWithRaw(['ahoi', 'hallo', 'hello', 'hey', 'huhu', 'moin']) || $this->hasEmoteThatEndsWith(['hello', 'heyguys', 'hi', 'wave']) || $this->hasToken(['hi', 'hey']) || $this->containsRaw(['gutenmorgen', 'gutenabend'])) {
228 $this->classification = 'hi';
229 } else if ($this->hasTokenThatStartsOrEndsWith(['pog', 'wow'])) {
230 $this->classification = 'pog';
231 } else if ($this->containsRaw(['hype'])) {
232 $this->classification = 'hype';
233 } else if ($this->hasToken(['danke', 'thanks', 'thx', 'ty'])) {
234 $this->classification = 'thx';
235 } else if ($this->hasToken(['<3']) || $this->hasEmoteThatEndsWith(['herz', 'hug', 'love'])) {
236 $this->classification = 'love';
237 } else if ($this->hasToken(['wat', 'wat?']) || $this->hasTokenThatStartsWith(['wtf']) || $this->hasEmoteThatEndsWith(['wat', 'wtf'])) {
238 $this->classification = 'wtf';
239 } else if ($this->endsWithEmoteless('?')) {
240 $this->classification = 'question';
241 } else if ($this->startsOrEndsWithRaw(['o7']) || $this->hasEmoteThatContains('salut')) {
242 $this->classification = 'o7';
243 } else if ($this->containsRaw(['haha', 'hehe', 'hihi', 'kekw', 'lol', 'lul']) || $this->hasTokenThatStartsWith([':d', 'xd'])) {
244 $this->classification = 'lol';
246 $this->classification = 'unclassified';
249 return $this->classification;
258 private $emotes = [];
259 private $emoteless = '';
260 private $emoteless_raw = '';
261 private $emoteless_tokens = [];
263 private $classification = null;