Language reference
Chattscript is deliberately small. This page is all of it.
Lines and comments
One statement per line. No semicolons, no braces.
let name = event.user # a comment runs to the end of the line
A # followed by hex digits is a colour, not a comment: #9b8cff. Anything else after # is a comment.
Values
| Kind | Examples |
|---|---|
| Number | 3, 2.5, 0 |
| Duration | 30 seconds, 5 minutes, 2 hours, 1 day |
| Text | "hello", "line one\nline two" |
| Yes or no | true, false |
| Nothing | nothing |
| List | ["a", "b", "c"], [1, 2, 3] |
| Colour | #9b8cff |
Durations are just numbers of milliseconds with a friendlier spelling: 5 minutes is 300000. That means count(key, 5 minutes) and count(key, 300000) are the same thing.
Variables
let total = 0 # make one
set total = total + 1 # change it
let and set both work anywhere; the two words exist so a script reads the way you meant it. A variable made inside an if or a loop stays available for the rest of that handler.
Settings declared with setting are variables too, shared by every handler in the file.
Doing things only sometimes
if event.viewers > 100 then
alert("big raid")
else if event.viewers > 10 then
alert("decent raid")
else
alert("small raid")
end
else if chains as far as you like and the whole chain closes with one end.
Repeating
repeat 3 times do
chime()
end
for each word in ["free", "gift", "bit.ly"] do
if event.text contains word then
alert("spam word: " + word)
end
end
times and do are optional decoration - repeat 3 and for each word in words parse the same. A single loop stops after 1,000 turns no matter what you ask for.
Leaving early
on message do
if not event.is_first then
stop
end
alert("first message from " + event.user)
end
stop ends the handler. It is the tidiest way to write "I am not interested in this one".
Functions
define shouting(what) do
if length(what) < 10 then
return false
end
return what = upper(what)
end
on message do
if shouting(event.text) then
alert(event.user + " is shouting")
end
end
A function returns nothing unless it hits a return. Functions may call other functions up to sixteen deep, which is enough for anything sensible and stops a script calling itself forever.
Operators
Maths
1 + 2 3 - 1 2 * 4 10 / 2
Dividing by zero gives 0 rather than stopping the plugin.
Joining text
+ joins text when either side is text:
alert(event.user + " sent " + count(event.user, 1 minute) + " messages")
Comparing
a = b a != b a > b a < b a >= b a <= b
= compares; assignment is always let or set, so there is no way to confuse the two. Text comparisons ignore case: "HELLO" = "hello" is true.
Text tests
event.text contains "free"
event.user starts with "bot"
event.text ends with "?"
All three ignore case. contains also works on a list, where it asks whether the list holds that value:
if event.types contains "ban_evader" then
Yes-and-no logic
if event.is_mod and not event.is_first then
if event.viewers > 100 or event.user = "bigstreamer" then
Events
on message do
# event.user, event.text, ...
end
The name after on is one of the events. A file can have several blocks, including more than one for the same event. event is only available inside a handler.
Reading something that is not there gives nothing rather than an error, so a typo like event.usr quietly gives you an empty value. If a script does nothing at all, check the spelling first.
The top of the file
plugin "Name" # required
description "One line."
author "You"
setting key = default "Label"
These are ordinary words, not reserved ones: a variable called setting or plugin is allowed, if odd.
Reserved words
on do end if then else let set repeat for in and or not true false nothing contains starts ends stop
Everything else - including plugin, description, author, setting, define, return, times, each, with, theme and base - is an ordinary name that only means something in the place it appears.
Errors
Mistakes are reported with a line number and never crash Chattler:
Line 7: Expected "then", found "alert"
Line 12: There is no function called "alrt"
Line 3: This plugin took too long and was stopped
A plugin that will not compile stays off. A plugin that fails ten times while running turns itself off. Both show in Settings with the message.