summaryrefslogtreecommitdiff
path: root/src/syntax
diff options
context:
space:
mode:
Diffstat (limited to 'src/syntax')
-rw-r--r--src/syntax/expr.rs35
-rw-r--r--src/syntax/token.rs12
-rw-r--r--src/syntax/visit.rs15
3 files changed, 59 insertions, 3 deletions
diff --git a/src/syntax/expr.rs b/src/syntax/expr.rs
index 97361fc3..fd106eb8 100644
--- a/src/syntax/expr.rs
+++ b/src/syntax/expr.rs
@@ -56,6 +56,10 @@ pub enum Expr {
While(WhileExpr),
/// A for loop expression: `for x in y { z }`.
For(ForExpr),
+ /// An import expression: `import "utils.typ" using a, b, c`.
+ Import(ImportExpr),
+ /// An include expression: `include "chapter1.typ"`.
+ Include(IncludeExpr),
}
impl Expr {
@@ -85,6 +89,8 @@ impl Expr {
Self::If(ref v) => v.span,
Self::While(ref v) => v.span,
Self::For(ref v) => v.span,
+ Self::Import(ref v) => v.span,
+ Self::Include(ref v) => v.span,
}
}
@@ -432,6 +438,35 @@ pub struct LetExpr {
pub init: Option<Box<Expr>>,
}
+/// An import expression: `import "utils.typ" using a, b, c`.
+#[derive(Debug, Clone, PartialEq)]
+pub struct ImportExpr {
+ /// The source code location.
+ pub span: Span,
+ /// The items to be imported.
+ pub imports: Imports,
+ /// The location of the importable file.
+ pub path: Box<Expr>,
+}
+
+/// The items that ought to be imported from a file.
+#[derive(Debug, Clone, PartialEq)]
+pub enum Imports {
+ /// All items in the scope of the file should be imported.
+ Wildcard,
+ /// The specified identifiers from the file should be imported.
+ Idents(Vec<Ident>),
+}
+
+/// An include expression: `include "chapter1.typ"`.
+#[derive(Debug, Clone, PartialEq)]
+pub struct IncludeExpr {
+ /// The source code location.
+ pub span: Span,
+ /// The location of the file to be included.
+ pub path: Box<Expr>,
+}
+
/// An if-else expression: `if x { y } else { z }`.
#[derive(Debug, Clone, PartialEq)]
pub struct IfExpr {
diff --git a/src/syntax/token.rs b/src/syntax/token.rs
index 40e1d6d2..3484536d 100644
--- a/src/syntax/token.rs
+++ b/src/syntax/token.rs
@@ -32,8 +32,6 @@ pub enum Token<'s> {
Semicolon,
/// A colon: `:`.
Colon,
- /// A pipe: `|`.
- Pipe,
/// A plus: `+`.
Plus,
/// A hyphen: `-`.
@@ -90,6 +88,12 @@ pub enum Token<'s> {
Continue,
/// The `return` keyword.
Return,
+ /// The `import` keyword.
+ Import,
+ /// The `include` keyword.
+ Include,
+ /// The `using` keyword.
+ Using,
/// One or more whitespace characters.
///
/// The contained `usize` denotes the number of newlines that were contained
@@ -201,7 +205,6 @@ impl<'s> Token<'s> {
Self::Comma => "comma",
Self::Semicolon => "semicolon",
Self::Colon => "colon",
- Self::Pipe => "pipe",
Self::Plus => "plus",
Self::Hyph => "minus",
Self::Slash => "slash",
@@ -231,6 +234,9 @@ impl<'s> Token<'s> {
Self::Break => "keyword `break`",
Self::Continue => "keyword `continue`",
Self::Return => "keyword `return`",
+ Self::Import => "keyword `import`",
+ Self::Include => "keyword `include`",
+ Self::Using => "keyword `using`",
Self::Space(_) => "space",
Self::Text(_) => "text",
Self::Raw(_) => "raw block",
diff --git a/src/syntax/visit.rs b/src/syntax/visit.rs
index 9c1272ee..40d8e664 100644
--- a/src/syntax/visit.rs
+++ b/src/syntax/visit.rs
@@ -87,6 +87,8 @@ visit! {
Expr::If(e) => v.visit_if(e),
Expr::While(e) => v.visit_while(e),
Expr::For(e) => v.visit_for(e),
+ Expr::Import(e) => v.visit_import(e),
+ Expr::Include(e) => v.visit_include(e),
}
}
@@ -189,4 +191,17 @@ visit! {
v.visit_expr(&node.iter);
v.visit_expr(&node.body);
}
+
+ fn visit_import(v, node: &ImportExpr) {
+ v.visit_expr(&node.path);
+ if let Imports::Idents(idents) = &node.imports {
+ for ident in idents {
+ v.visit_binding(ident);
+ }
+ }
+ }
+
+ fn visit_include(v, node: &IncludeExpr) {
+ v.visit_expr(&node.path);
+ }
}