use std::fmt;
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub struct Span {
pub start: usize,
pub end: usize,
}
#[derive(Clone, Debug, Eq, PartialEq)]
pub enum TokenKind {
Name,
Keyword,
Number,
String,
FString,
TemplateString,
Operator,
Newline,
Indent,
Dedent,
Trivia,
End,
}
#[derive(Clone, Debug, Eq, PartialEq)]
pub struct Token {
pub kind: TokenKind,
pub span: Span,
pub line: usize,
pub column: usize,
}
#[derive(Clone, Debug, Eq, PartialEq)]
pub enum NodeKind {
Module,
Statement,
Suite,
Group,
Expression,
}
#[derive(Clone, Debug, Eq, PartialEq)]
pub struct Node {
pub kind: NodeKind,
pub tokens: std::ops::Range<usize>,
pub children: Vec<Node>,
}
#[derive(Clone, Debug, Eq, PartialEq)]
pub struct SyntaxTree {
source: String,
pub tokens: Vec<Token>,
pub root: Node,
}
impl SyntaxTree {
#[must_use]
pub fn source(&self) -> &str {
&self.source
}
#[must_use]
pub fn preserve_source(&self) -> String {
self.source.clone()
}
pub(crate) fn new(source: &str, tokens: Vec<Token>, root: Node) -> Self {
Self {
source: source.to_owned(),
tokens,
root,
}
}
}
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub struct Limits {
pub max_bytes: usize,
pub max_tokens: usize,
pub max_nesting: usize,
pub max_lines: usize,
}
impl Default for Limits {
fn default() -> Self {
Self {
max_bytes: 4 * 1024 * 1024,
max_tokens: 1_000_000,
max_nesting: 256,
max_lines: 250_000,
}
}
}
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub enum DiagnosticCode {
ResourceLimit,
InvalidIndentation,
AmbiguousIndentation,
UnterminatedLiteral,
InvalidCharacter,
UnmatchedDelimiter,
InvalidSyntax,
}
#[derive(Clone, Debug, Eq, PartialEq)]
pub struct Diagnostic {
pub code: DiagnosticCode,
pub span: Span,
pub line: usize,
pub column: usize,
pub message: String,
}
impl fmt::Display for Diagnostic {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{}:{}: {}", self.line, self.column, self.message)
}
}
impl std::error::Error for Diagnostic {}