use std::ops::Range;
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub struct FileSpan {
pub start: usize,
pub end: usize,
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum LintSpan {
Global(nu_protocol::Span),
File(FileSpan),
}
impl FileSpan {
#[must_use]
pub const fn new(start: usize, end: usize) -> Self {
Self { start, end }
}
#[must_use]
pub fn to_global_span(self, file_offset: usize) -> nu_protocol::Span {
nu_protocol::Span::new(self.start + file_offset, self.end + file_offset)
}
#[must_use]
pub fn merge(self, other: Self) -> Self {
Self {
start: self.start.min(other.start),
end: self.end.max(other.end),
}
}
#[must_use]
pub const fn len(&self) -> usize {
self.end.saturating_sub(self.start)
}
#[must_use]
pub const fn is_empty(&self) -> bool {
self.start >= self.end
}
#[must_use]
pub const fn as_range(&self) -> Range<usize> {
self.start..self.end
}
}
impl LintSpan {
#[must_use]
pub const fn to_file_span(self, file_offset: usize) -> FileSpan {
match self {
Self::Global(g) => FileSpan {
start: g.start.saturating_sub(file_offset),
end: g.end.saturating_sub(file_offset),
},
Self::File(f) => f,
}
}
#[must_use]
pub fn file_span(&self) -> FileSpan {
match self {
Self::File(f) => *f,
Self::Global(_) => panic!("Span not normalized - call normalize_spans first"),
}
}
}
impl From<nu_protocol::Span> for LintSpan {
fn from(span: nu_protocol::Span) -> Self {
Self::Global(span)
}
}
impl From<FileSpan> for LintSpan {
fn from(span: FileSpan) -> Self {
Self::File(span)
}
}
impl From<FileSpan> for nu_protocol::Span {
fn from(span: FileSpan) -> Self {
Self::new(span.start, span.end)
}
}