Language Reference
This page contains a language reference with a complete overview of all language syntax available in hop.
Types
There are eight built-in types available in hop.
Bool
The Bool type represents booleans.
Boolean literals are constructed via the keywords true and false.
| Operation | Returns |
|---|---|
!Bool | Bool |
Bool && Bool | Bool |
Bool || Bool | Bool |
Bool != Bool | Bool |
Bool == Bool | Bool |
Int
The Int type represents a 64-bit signed integer.
Integer literals are constructed by writing a literal number without a decimal point.
| Operation | Returns |
|---|---|
-Int | Int |
Int + Int | Int |
Int - Int | Int |
Int < Int | Bool |
Int > Int | Bool |
Int <= Int | Bool |
Int >= Int | Bool |
Int == Int | Bool |
Int != Int | Bool |
Int.to_float() | Float |
Int.to_string() | String |
Float
The Float type represents a 64-bit floating point number.
Floating point literals are constructed by writing a literal number containing a decimal point.
| Operation | Returns |
|---|---|
-Float | Float |
Float + Float | Float |
Float - Float | Float |
Float < Float | Bool |
Float > Float | Bool |
Float <= Float | Bool |
Float >= Float | Bool |
Float == Float | Bool |
Float != Float | Bool |
Float.to_int() | Int |
Float.to_string() | String |
String
The String type represents a string of characters.
String literals are constructed by writing a string using "" as delimiters.
| Operation | Returns |
|---|---|
String + String | String |
String == String | Bool |
String != String | Bool |
String.is_empty() | Bool |
Array
The Array type represents an array of a given type.
| Operation | Returns |
|---|---|
Array.len() | Int |
Array.is_empty() | Bool |
Option
The Option type represents a container that either holds a value or not.
| Operation | Returns |
|---|---|
Option.is_some() | Bool |
Option.is_none() | Bool |
Record
The Record types represent a collection of named fields.
record User {
name: String,
}
view Main {
<let {
user: User = User {name: "Tobi"},
}>
The name of the user is {user.name}
</let>
}Open in playgroundEnum
The Enum types represent a value that can hold exactly one value of a given set of types.
enum LaundryRoomState {
Free,
Occupied {
available_at: String,
},
}
view Main {
<let {state: LaundryRoomState = LaundryRoomState::Free}>
<match {state}>
<case {LaundryRoomState::Free}>
<p>
The laundry room is available.
</p>
<button>
Book now
</button>
</case>
<case {LaundryRoomState::Occupied {available_at}}>
<p>
The laundry room is occupied.
</p>
<p>
It becomes available at {available_at}.
</p>
</case>
</match>
</let>
}Open in playgroundExpressions
Apart from the methods and operators available on values there is only one type of primitive expression available in hop. The match expression.
match
The match expression in hop is similar to the match expression in Rust and is used to destructure a value into different cases.
The match expression works on the Bool, Option and Enum type. Support for matching on other types is in progress.
record User {
name: String,
email: String,
}
enum Visibility {
Visible,
Hidden,
}
view Main {
<!-- Matching on Enum -->
<let {input: Visibility = Visibility::Visible}>
{match input {
Visibility::Visible => "It is visible",
Visibility::Hidden => "It is invisible",
}}
</let>
<!-- Matching on Option -->
<let {
current_user: Option[User] = Some(
User {name: "Loki", email: "loki@example.com"}
),
}>
{match current_user {
Some(User {
name,
email: _,
}) => "The current user is " + name,
None => "There is no current user",
}}
</let>
}Open in playgroundMacros
join!
The join! macro concatenates strings, adding a space between each string while filtering out empty strings. The idiomatic use case for the macro is to split long class strings into separate strings.
asset!
The asset! macro registers an asset and returns the string for its production url.
Tags
<let>
The <let> tag binds one or more variables to the value of the given expression.
view Main {
<let {
x: Int = 20,
y: Int = 5,
result: String = (x + y).to_string(),
}>
The result is {result}
</let>
}Open in playground<match>
The <match> tag is the cousin of the match expression. The <match> tag works just like the match expression but can be used when the purpose of matching is not to produce a value, but instead render different markup depending on which case is matched.
component LoggedInContent {
<div>
Welcome to the area for authenticated users.
</div>
}
component MustSignInMessage {
<div>
You need to sign in to view this content.
</div>
}
view Main {
<let {logged_in: Bool = true}>
<match {logged_in}>
<case {true}>
<LoggedInContent/>
</case>
<case {false}>
<MustSignInMessage/>
</case>
</match>
</let>
}Open in playground<for>
The <for> tag loops over the items of an array, rendering its contents once for each item of the array.
<if>
The <if> tag renders its contents when a given condition evaluates to true. It is a shorthand for a match tag on a Bool with an empty false case.
view Main {
<let {x: Int = 5, y: Int = 10}>
<if {x + y == 15}>
<div>
the math is mathing
</div>
</if>
</let>
}Open in playground