difftreelog
style fix clippy warnings
in: master
24 files changed
Cargo.lockdiffbeforeafterboth676676677[[package]]677[[package]]678name = "jrsonnet-gcmodule"678name = "jrsonnet-gcmodule"679version = "0.4.1"679version = "0.4.2"680source = "registry+https://github.com/rust-lang/crates.io-index"680source = "registry+https://github.com/rust-lang/crates.io-index"681checksum = "c33f4f6cdc60f5ae94ebae3dfe7f484ae79b364225d9b19601b24c804cfd8751"681checksum = "f95b976a79e4000bb9e07ff0709dca0ea27bcf1952d4c17d91fb7364d6145683"682dependencies = [682dependencies = [683 "jrsonnet-gcmodule-derive",683 "jrsonnet-gcmodule-derive",684]684]685685686[[package]]686[[package]]687name = "jrsonnet-gcmodule-derive"687name = "jrsonnet-gcmodule-derive"688version = "0.4.1"688version = "0.4.2"689source = "registry+https://github.com/rust-lang/crates.io-index"689source = "registry+https://github.com/rust-lang/crates.io-index"690checksum = "2b30c95b285f9bb6709f1b3e6fc69b3a25e39b32ff987587fd108f0f22be5fa3"690checksum = "51d928626220a310ff0cec815e80cf7fe104697184352ca21c40534e0b0d72d9"691dependencies = [691dependencies = [692 "proc-macro2",692 "proc-macro2",693 "quote",693 "quote",1602source = "registry+https://github.com/rust-lang/crates.io-index"1602source = "registry+https://github.com/rust-lang/crates.io-index"1603checksum = "c2a7b1c03c876122aa43f3020e6c3c3ee5c05081c9a00739faf7503aeba10d22"1603checksum = "c2a7b1c03c876122aa43f3020e6c3c3ee5c05081c9a00739faf7503aeba10d22"1604dependencies = [1604dependencies = [1605 "windows-sys 0.59.0",1605 "windows-sys 0.61.2",1606]1606]160716071608[[package]]1608[[package]]Cargo.tomldiffbeforeafterboth20jrsonnet-cli = { path = "./crates/jrsonnet-cli", version = "0.5.0-pre97" }20jrsonnet-cli = { path = "./crates/jrsonnet-cli", version = "0.5.0-pre97" }21jrsonnet-types = { path = "./crates/jrsonnet-types", version = "0.5.0-pre97" }21jrsonnet-types = { path = "./crates/jrsonnet-types", version = "0.5.0-pre97" }22jrsonnet-formatter = { path = "./crates/jrsonnet-formatter", version = "0.5.0-pre97" }22jrsonnet-formatter = { path = "./crates/jrsonnet-formatter", version = "0.5.0-pre97" }23jrsonnet-gcmodule = { version = "0.4.1" }23jrsonnet-gcmodule = { version = "0.4.2" }24# Diagnostics.24# Diagnostics.25# hi-doc is my library, which handles text formatting very well, but isn't polished enough yet25# hi-doc is my library, which handles text formatting very well, but isn't polished enough yet26# Previous implementation was based on annotate-snippets, which I don't like for many reasons.26# Previous implementation was based on annotate-snippets, which I don't like for many reasons.bindings/jsonnet/src/import.rsdiffbeforeafterboth66 base.as_ptr(),66 base.as_ptr(),67 rel.as_ptr(),67 rel.as_ptr(),68 &mut found_here.cast_const(),68 &mut found_here.cast_const(),69 &mut buf,69 &raw mut buf,70 &mut buf_len,70 &raw mut buf_len,71 )71 )72 };72 };73 let buf_slice: &[u8] = unsafe { std::slice::from_raw_parts(buf.cast(), buf_len) };73 let buf_slice: &[u8] = unsafe { std::slice::from_raw_parts(buf.cast(), buf_len) };crates/jrsonnet-evaluator/src/evaluate/destructure.rsdiffbeforeafterboth9 evaluate_method, evaluate_named_param, Context, Pending, Thunk, Val,9 evaluate_method, evaluate_named_param, Context, Pending, Thunk, Val,10};10};1112#[cfg(feature = "exp-preserve-order")]13use crate::evaluate;111412#[allow(clippy::too_many_lines)]15#[allow(clippy::too_many_lines)]13#[allow(unused_variables)]16#[allow(unused_variables)]crates/jrsonnet-evaluator/src/evaluate/mod.rsdiffbeforeafterboth143 false,143 false,144 ) {144 ) {145 let fctx = Pending::new();145 let fctx = Pending::new();146 let mut new_bindings = FxHashMap::with_capacity(var.capacity_hint());146 let mut new_bindings = FxHashMap::with_capacity(var.binds_len());147 let obj = obj.clone();147 let obj = obj.clone();148 let value = Thunk::evaluated(Val::Arr(ArrValue::lazy(vec![148 let value = Thunk::evaluated(Val::Arr(ArrValue::lazy(vec![149 Thunk::evaluated(Val::string(field.clone())),149 Thunk::evaluated(Val::string(field.clone())),crates/jrsonnet-evaluator/src/function/builtin.rsdiffbeforeafterboth989899 fn call(&self, _loc: CallLocation<'_>, args: &[Option<Thunk<Val>>]) -> Result<Val> {99 fn call(&self, _loc: CallLocation<'_>, args: &[Option<Thunk<Val>>]) -> Result<Val> {100 let args = args100 let args = args101 .into_iter()101 .iter()102 .map(|a| a.as_ref().expect("legacy natives have no default params"))102 .map(|a| a.as_ref().expect("legacy natives have no default params"))103 .map(|a| a.evaluate())103 .map(Thunk::evaluate)104 .collect::<Result<Vec<Val>>>()?;104 .collect::<Result<Vec<Val>>>()?;105 self.handler.call(&args)105 self.handler.call(&args)106 }106 }crates/jrsonnet-evaluator/src/obj/mod.rsdiffbeforeafterboth1use std::{1use std::{2 any::Any,2 any::Any, cell::{Cell, RefCell}, clone::Clone, cmp::Reverse, collections::hash_map::Entry, fmt::{self, Debug}, hash::{Hash, Hasher}, num::Saturating, ops::ControlFlow3 cell::{Cell, RefCell},4 clone::Clone,5 collections::hash_map::Entry,6 fmt::{self, Debug},7 hash::{Hash, Hasher},8 num::Saturating,9 ops::ControlFlow,10};3};11412use educe::Educe;5use educe::Educe;393240 use jrsonnet_gcmodule::Trace;33 use jrsonnet_gcmodule::Trace;413442 #[derive(Clone, Copy, Default, Debug, Trace)]35 #[derive(Clone, Copy, Default, Debug, Trace, PartialEq, Eq, PartialOrd, Ord)]43 pub struct FieldIndex(());36 pub struct FieldIndex(());44 impl FieldIndex {37 impl FieldIndex {45 pub fn absolute(_v: u32) -> Self {38 pub fn absolute(_v: u32) -> Self {46 Self(())39 Self(())47 }40 }41 #[must_use]48 pub const fn next(self) -> Self {42 pub const fn next(self) -> Self {49 Self(())43 Self(())50 }44 }51 }45 }524653 #[derive(Clone, Copy, Default, Debug, Trace)]47 #[derive(Clone, Copy, Default, Debug, Trace, PartialEq, Eq, PartialOrd, Ord)]54 pub struct SuperDepth(());48 pub struct SuperDepth(());55 impl SuperDepth {49 impl SuperDepth {56 pub(super) fn deepen(self) {}50 pub(super) fn deepen(self) {}595360#[cfg(feature = "exp-preserve-order")]54#[cfg(feature = "exp-preserve-order")]61pub mod ordering {55pub mod ordering {62 use std::cmp::Reverse;6364 use jrsonnet_gcmodule::Trace;56 use jrsonnet_gcmodule::Trace;655769 pub fn absolute(v: u32) -> Self {61 pub fn absolute(v: u32) -> Self {70 Self(v)62 Self(v)71 }63 }64 #[must_use]72 pub fn next(self) -> Self {65 pub fn next(self) -> Self {73 Self(self.0 + 1)66 Self(self.0 + 1)74 }67 }78 pub struct SuperDepth(u32);71 pub struct SuperDepth(u32);79 impl SuperDepth {72 impl SuperDepth {80 pub(super) fn deepen(&mut self) {73 pub(super) fn deepen(&mut self) {81 self.0 += 174 self.0 += 1;82 }75 }83 }76 }8485 #[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Debug)]86 pub struct FieldSortKey(Reverse<SuperDepth>, FieldIndex);87 impl FieldSortKey {88 pub fn new(depth: SuperDepth, index: FieldIndex) -> Self {89 Self(Reverse(depth), index)90 }91 }92}77}7879use ordering::{FieldIndex, SuperDepth};938094#[cfg(feature = "exp-preserve-order")]81#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Debug)]95use ordering::FieldSortKey;82pub struct FieldSortKey(Reverse<SuperDepth>, FieldIndex);96use ordering::{FieldIndex, SuperDepth};83impl FieldSortKey {84 pub fn new(depth: SuperDepth, index: FieldIndex) -> Self {85 Self(Reverse(depth), index)86 }87}978898// 0 - add89// 0 - add795struct FieldVisibilityData {786struct FieldVisibilityData {796 omitted_until: Saturating<usize>,787 omitted_until: Saturating<usize>,797 exists_visible: Option<Visibility>,788 exists_visible: Option<Visibility>,798 #[cfg(feature = "exp-preserve-order")]789 #[allow(dead_code, reason = "used for exp-object-ordering, ZST otherwise")]799 key: FieldSortKey,790 key: FieldSortKey,800}791}801impl FieldVisibilityData {792impl FieldVisibilityData {804 .expect("non-existing fields shall be dropped at the end of fn fields_visibility()")795 .expect("non-existing fields shall be dropped at the end of fn fields_visibility()")805 .is_visible()796 .is_visible()806 }797 }807 #[cfg(feature = "exp-preserve-order")]798 #[allow(dead_code, reason = "used for exp-object-ordering, ZST otherwise")]808 fn sort_key(&self) -> FieldSortKey {799 fn sort_key(&self) -> FieldSortKey {809 self.key800 self.key810 }801 }818 let mut omit_index = Saturating(0);809 let mut omit_index = Saturating(0);819 for core in self.0.cores.iter().rev() {810 for core in self.0.cores.iter().rev() {820 core.0811 core.0821 .enum_fields_core(&mut super_depth, &mut |_depth, _index, name, visibility| {812 .enum_fields_core(&mut super_depth, &mut |depth, index, name, visibility| {822 let entry = out.entry(name);813 let entry = out.entry(name);823 let data = entry.or_insert(FieldVisibilityData {814 let data = entry.or_insert_with(|| FieldVisibilityData {824 exists_visible: None,815 exists_visible: None,825 #[cfg(feature = "exp-preserve-order")]826 key: FieldSortKey::new(_depth, _index),816 key: FieldSortKey::new(depth, index),827 omitted_until: omit_index,817 omitted_until: omit_index,828 });818 });829 match visibility {819 match visibility {crates/jrsonnet-evaluator/src/typed/conversions.rsdiffbeforeafterboth61 }61 }62}62}636364#[diagnostic::on_unimplemented(65 note = "don't implement `ParseTypedObj` directly, it is automatically provided by `FromUntyped` derive"66)]64pub trait ParseTypedObj: Typed {67pub trait ParseTypedObj: Typed {65 fn parse(obj: &ObjValue) -> Result<Self>;68 fn parse(obj: &ObjValue) -> Result<Self>;66}69}7071#[diagnostic::on_unimplemented(72 note = "don't implement `SerializeTypedObj` directly, it is automatically provided by `IntoUntyped` derive"73)]67pub trait SerializeTypedObj: Typed {74pub trait SerializeTypedObj: Typed {68 fn serialize(self, out: &mut ObjValueBuilder) -> Result<()>;75 fn serialize(self, out: &mut ObjValueBuilder) -> Result<()>;69 fn into_object(self) -> Result<ObjValue> {76 fn into_object(self) -> Result<ObjValue> {crates/jrsonnet-formatter/src/comments.rsdiffbeforeafterboth136 }136 }137 line = new_line.to_string();137 line = new_line.to_string();138 }138 }139 p!(out, string(line.to_string()) nl);139 p!(out, string(line.clone()) nl);140 }140 }141 }141 }142 if doc {142 if doc {crates/jrsonnet-formatter/src/lib.rsdiffbeforeafterboth38 items.into_rc_path()38 items.into_rc_path()39 };39 };40 let items =40 let items = new_line_group(pi!(@i; items(o) items(end_comments_items.into()))).into_rc_path();41 new_line_group(pi!(@i; items(o.into()) items(end_comments_items.into()))).into_rc_path();424143 let indented = with_indent(pi!(@i; nl items(items.into())));42 let indented = with_indent(pi!(@i; nl items(items.into())));4443355}354}356impl Printable for ArgsDesc {355impl Printable for ArgsDesc {357 fn print(&self, out: &mut PrintItems) {356 fn print(&self, out: &mut PrintItems) {358 let start = LineNumber::new("args start line");359 let end = LineNumber::new("args end line");360 let multi_line = Rc::new(move |condition_context: &mut ConditionResolverContext| {361 is_multiple_lines(condition_context, start, end)362 });363364 let (children, end_comments) = children_between::<Arg>(365 self.syntax().clone(),366 self.l_paren_token().map(Into::into).as_ref(),367 self.r_paren_token().map(Into::into).as_ref(),368 None,369 );370371 fn gen_args(children: Vec<Child<Arg>>, multi_line: ConditionResolver) -> PrintItems {357 fn gen_args(children: Vec<Child<Arg>>, multi_line: ConditionResolver) -> PrintItems {372 let mut _out = PrintItems::new();358 let mut out = PrintItems::new();373 let out = &mut _out;374359375 let mut args = children.into_iter().peekable();360 let mut args = children.into_iter().peekable();376 while let Some(ele) = args.next() {361 while let Some(ele) = args.next() {377 if ele.should_start_with_newline {362 if ele.should_start_with_newline {378 p!(out, nl);363 p!(out, nl);379 }364 }380 format_comments(&ele.before_trivia, CommentLocation::AboveItem, out);365 format_comments(&ele.before_trivia, CommentLocation::AboveItem, &mut out);381 let arg = ele.value;366 let arg = ele.value;382 if arg.name().is_some() || arg.assign_token().is_some() {367 if arg.name().is_some() || arg.assign_token().is_some() {383 p!(out, {arg.name()} str(" = "));368 p!(&mut out, {arg.name()} str(" = "));384 }369 }385 p!(out, { arg.expr() });370 p!(&mut out, { arg.expr() });386 let has_more = args.peek().is_some();371 let has_more = args.peek().is_some();387 if has_more {372 if has_more {388 p!(out, str(","));373 p!(out, str(","));389 } else {374 } else {390 p!(out, if("trailing comma", multi_line, str(",")));375 p!(out, if("trailing comma", multi_line, str(",")));391 }376 }392 format_comments(&ele.inline_trivia, CommentLocation::ItemInline, out);377 format_comments(&ele.inline_trivia, CommentLocation::ItemInline, &mut out);393 if has_more {378 if has_more {394 p!(out, if_else("arg separator", multi_line, nl)(sonl));379 p!(out, if_else("arg separator", multi_line, nl)(sonl));395 }380 }396 }381 }397 _out382383 out398 }384 }385386 let start = LineNumber::new("args start line");387 let end = LineNumber::new("args end line");388 let multi_line = Rc::new(move |condition_context: &mut ConditionResolverContext| {389 is_multiple_lines(condition_context, start, end)390 });391392 let (children, end_comments) = children_between::<Arg>(393 self.syntax().clone(),394 self.l_paren_token().map(Into::into).as_ref(),395 self.r_paren_token().map(Into::into).as_ref(),396 None,397 );399398400 let args_items = new_line_group(gen_args(children, multi_line.clone())).into_rc_path();399 let args_items = new_line_group(gen_args(children, multi_line.clone())).into_rc_path();401 let args_indented = with_indent(pi!(@i; nl items(args_items.into())));400 let args_indented = with_indent(pi!(@i; nl items(args_items.into())));447}446}448447449impl Printable for ObjBody {448impl Printable for ObjBody {449 #[allow(clippy::too_many_lines)]450 fn print(&self, out: &mut PrintItems) {450 fn print(&self, out: &mut PrintItems) {451 match self {451 match self {452 Self::ObjBodyComp(l) => {452 Self::ObjBodyComp(l) => {507 p!(out, nl <i str("}"));507 p!(out, nl <i str("}"));508 }508 }509 Self::ObjBodyMemberList(l) => {509 Self::ObjBodyMemberList(l) => {510 fn gen_members(511 children: Vec<Child<Member>>,512 multi_line: ConditionResolver,513 ) -> PrintItems {514 let mut out = PrintItems::new();515 let mut members = children.into_iter().peekable();516 while let Some(mem) = members.next() {517 if mem.should_start_with_newline {518 p!(out, nl);519 }520 format_comments(&mem.before_trivia, CommentLocation::AboveItem, &mut out);521 p!(&mut out, { mem.value });522 let has_more = members.peek().is_some();523 if has_more {524 p!(out, str(","));525 } else {526 p!(out, if("trailing comma", multi_line, str(",")));527 }528 format_comments(&mem.inline_trivia, CommentLocation::ItemInline, &mut out);529 p!(out, if_else("member separator", multi_line, nl)(sonl));530 }531 out532 }533510 let (children, end_comments) = children_between::<Member>(534 let (children, end_comments) = children_between::<Member>(511 l.syntax().clone(),535 l.syntax().clone(),531 })555 })532 };556 };533534 fn gen_members(535 children: Vec<Child<Member>>,536 multi_line: ConditionResolver,537 ) -> PrintItems {538 let mut _out = PrintItems::new();539 let out = &mut _out;540 let mut members = children.into_iter().peekable();541 while let Some(mem) = members.next() {542 if mem.should_start_with_newline {543 p!(out, nl);544 }545 format_comments(&mem.before_trivia, CommentLocation::AboveItem, out);546 p!(out, { mem.value });547 let has_more = members.peek().is_some();548 if has_more {549 p!(out, str(","));550 } else {551 p!(out, if("trailing comma", multi_line, str(",")));552 }553 format_comments(&mem.inline_trivia, CommentLocation::ItemInline, out);554 p!(out, if_else("member separator", multi_line, nl)(sonl));555 }556 _out557 }558557559 let members_items =558 let members_items =560 new_line_group(gen_members(children, multi_line.clone())).into_rc_path();559 new_line_group(gen_members(children, multi_line.clone())).into_rc_path();718717719impl Printable for ExprArray {718impl Printable for ExprArray {720 fn print(&self, out: &mut PrintItems) {719 fn print(&self, out: &mut PrintItems) {720 fn gen_elements(children: Vec<Child<Expr>>, multi_line: ConditionResolver) -> PrintItems {721 let mut out = PrintItems::new();722 let mut els = children.into_iter().peekable();723 while let Some(el) = els.next() {724 if el.should_start_with_newline {725 p!(out, nl);726 }727 format_comments(&el.before_trivia, CommentLocation::AboveItem, &mut out);728 p!(&mut out, { el.value });729 let has_more = els.peek().is_some();730 if has_more {731 p!(out, str(","));732 } else {733 p!(out, if("trailing comma", multi_line, str(",")));734 }735 format_comments(&el.inline_trivia, CommentLocation::ItemInline, &mut out);736 p!(out, if_else("element separator", multi_line, nl)(sonl));737 }738 out739 }740721 let (children, end_comments) = children_between::<Expr>(741 let (children, end_comments) = children_between::<Expr>(722 self.syntax().clone(),742 self.syntax().clone(),740 Rc::new(move |ctx: &mut ConditionResolverContext| is_multiple_lines(ctx, start, end))760 Rc::new(move |ctx: &mut ConditionResolverContext| is_multiple_lines(ctx, start, end))741 };761 };742743 fn gen_elements(children: Vec<Child<Expr>>, multi_line: ConditionResolver) -> PrintItems {744 let mut _out = PrintItems::new();745 let out = &mut _out;746 let mut els = children.into_iter().peekable();747 while let Some(el) = els.next() {748 if el.should_start_with_newline {749 p!(out, nl);750 }751 format_comments(&el.before_trivia, CommentLocation::AboveItem, out);752 p!(out, { el.value });753 let has_more = els.peek().is_some();754 if has_more {755 p!(out, str(","));756 } else {757 p!(out, if("trailing comma", multi_line, str(",")));758 }759 format_comments(&el.inline_trivia, CommentLocation::ItemInline, out);760 p!(out, if_else("element separator", multi_line, nl)(sonl))761 }762 _out763 }764762765 let els_items = new_line_group(gen_elements(children, multi_line.clone())).into_rc_path();763 let els_items = new_line_group(gen_elements(children, multi_line.clone())).into_rc_path();766764800 Self::ExprString(s) => p!(out, { s.text() }),798 Self::ExprString(s) => p!(out, { s.text() }),801 Self::ExprNumber(n) => p!(out, { n.number() }),799 Self::ExprNumber(n) => p!(out, { n.number() }),802 Self::ExprArray(a) => {800 Self::ExprArray(a) => {803 p!(out, { a })801 p!(out, { a });804 }802 }805 Self::ExprObject(obj) => {803 Self::ExprObject(obj) => {806 p!(out, { obj.obj_body() });804 p!(out, { obj.obj_body() });861 pub indent: u8,859 pub indent: u8,862}860}861862#[allow(863 clippy::result_large_err,864 reason = "TODO: there should be an intermediate representation for such reports"865)]863pub fn format(input: &str, opts: &FormatOptions) -> Result<String, SnippetBuilder> {866pub fn format(input: &str, opts: &FormatOptions) -> Result<String, SnippetBuilder> {864 let (parsed, errors) = jrsonnet_rowan_parser::parse(input);867 let (parsed, errors) = jrsonnet_rowan_parser::parse(input);865 if !errors.is_empty() {868 if !errors.is_empty() {crates/jrsonnet-macros/src/typed.rsdiffbeforeafterboth156 // optional flatten is handled in same way as serde156 // optional flatten is handled in same way as serde157 if self.attr.flatten {157 if self.attr.flatten {158 return quote! {158 return quote! {159 #ident: <#ty as TypedObj>::parse(&obj).ok(),159 #ident: <#ty as ParseTypedObj>::parse(&obj).ok(),160 };160 };161 }161 }162162190 // optional flatten is handled in same way as serde190 // optional flatten is handled in same way as serde191 if self.attr.flatten {191 if self.attr.flatten {192 return quote! {192 return quote! {193 #ident: <#ty as TypedObj>::parse(&obj)?,193 #ident: <#ty as ParseTypedObj>::parse(&obj)?,194 };194 };195 }195 }196196232 if self.is_option {232 if self.is_option {233 quote! {233 quote! {234 if let Some(value) = self.#ident {234 if let Some(value) = self.#ident {235 <#ty as TypedObj>::serialize(value, out)?;235 <#ty as SerializeTypedObj>::serialize(value, out)?;236 }236 }237 }237 }238 } else {238 } else {239 quote! {239 quote! {240 <#ty as TypedObj>::serialize(self.#ident, out)?;240 <#ty as SerializeTypedObj>::serialize(self.#ident, out)?;241 }241 }242 }242 }243 },243 },crates/jrsonnet-parser/src/expr.rsdiffbeforeafterboth224 },224 },225 #[cfg(feature = "exp-destruct")]225 #[cfg(feature = "exp-destruct")]226 Object {226 Object {227 #[allow(clippy::type_complexity)]227 fields: Vec<(IStr, Option<Destruct>, Option<Spanned<Expr>>)>,228 fields: Vec<(IStr, Option<Destruct>, Option<Rc<Spanned<Expr>>>)>,228 rest: Option<DestructRest>,229 rest: Option<DestructRest>,229 },230 },230}231}261 let mut out = 0;262 let mut out = 0;262 for (_, into, _) in fields {263 for (_, into, _) in fields {263 match into {264 match into {264 Some(v) => out += v.capacity_hint(),265 Some(v) => out += v.binds_len(),265 // Field is destructured to default name266 // Field is destructured to default name266 None => out += 1,267 None => out += 1,267 }268 }crates/jrsonnet-parser/src/lib.rsdiffbeforeafterboth119 }119 }120 pub rule destruct_object(s: &ParserSettings) -> expr::Destruct120 pub rule destruct_object(s: &ParserSettings) -> expr::Destruct121 = "{" _121 = "{" _122 fields:(name:id() into:(_ ":" _ into:destruct(s) {into})? default:(_ "=" _ v:expr(s) {v})? {(name, into, default)})**comma()122 fields:(name:id() into:(_ ":" _ into:destruct(s) {into})? default:(_ "=" _ v:expr(s) {v})? {(name, into, default.map(Rc::new))})**comma()123 rest:(123 rest:(124 comma() rest:destruct_rest()? {rest}124 comma() rest:destruct_rest()? {rest}125 / comma()? {None}125 / comma()? {None}crates/jrsonnet-rowan-parser/src/ast.rsdiffbeforeafterboth223use crate::{SyntaxKind, SyntaxNode, SyntaxNodeChildren, SyntaxToken};3use crate::{SyntaxKind, SyntaxNode, SyntaxNodeChildren, SyntaxToken};445/// The main trait to go from untyped `SyntaxNode` to a typed ast. The5/// The main trait to go from untyped `SyntaxNode` to a typed ast.6///6/// conversion itself has zero runtime cost: ast and syntax nodes have exactly7/// The conversion itself has zero runtime cost: ast and syntax nodes have exactly7/// the same representation: a pointer to the tree root and a pointer to the8/// the same representation: a pointer to the tree root and a pointer to the8/// node itself.9/// node itself.9pub trait AstNode {10pub trait AstNode {crates/jrsonnet-rowan-parser/src/event.rsdiffbeforeafterboth56 fn text_offset(&self) -> TextSize {56 fn text_offset(&self) -> TextSize {57 if self.offset == 0 {57 if self.offset == 0 {58 return 0.into();58 return 0.into();59 };59 }60 self.lexemes.get(self.offset).map_or_else(60 self.lexemes.get(self.offset).map_or_else(61 || {61 || {62 self.lexemes62 self.lexemescrates/jrsonnet-rowan-parser/src/lib.rsdiffbeforeafterboth262627use self::{27use self::{28 ast::support,28 ast::support,29 generated::nodes::{Expr, ExprBinary, ExprObjExtend},29 generated::nodes::{Expr, ExprObjExtend},30};30};313132pub fn parse(input: &str) -> (SourceFile, Vec<LocatedSyntaxError>) {32pub fn parse(input: &str) -> (SourceFile, Vec<LocatedSyntaxError>) {crates/jrsonnet-rowan-parser/src/marker.rsdiffbeforeafterboth141 new_m141 new_m142 }142 }143 /// Create new node around existing marker143 /// Create new node around existing marker144 /// If previous_pos is set - the wrapping node would not include everything that happened between wrapped node end and the current position of the parser144 /// If `previous_pos` is set - the wrapping node would not include everything that happened between wrapped node end and the current position of the parser145 fn wrap_raw(145 fn wrap_raw(146 self,146 self,147 p: &mut Parser,147 p: &mut Parser,crates/jrsonnet-rowan-parser/src/parser.rsdiffbeforeafterboth52 write!(f, "unexpected {found:?}, expecting {expected}")52 write!(f, "unexpected {found:?}, expecting {expected}")53 }53 }54 SyntaxError::Missing { expected } => write!(f, "missing {expected}"),54 SyntaxError::Missing { expected } => write!(f, "missing {expected}"),55 SyntaxError::Custom { error } => write!(f, "{error}"),55 SyntaxError::Custom { error } | SyntaxError::Hint { error } => write!(f, "{error}"),56 SyntaxError::Hint { error } => write!(f, "{error}"),57 }56 }58 }57 }59}58}492 } else {491 } else {493 m.complete(p, MEMBER_FIELD_NORMAL)492 m.complete(p, MEMBER_FIELD_NORMAL)494 };493 };495 };494 }496 while p.at_ts(COMPSPEC) {495 while p.at_ts(COMPSPEC) {497 compspecs.push(compspec(p));496 compspecs.push(compspec(p));498 }497 }747 if p.at(T![:]) {746 if p.at(T![:]) {748 p.bump();747 p.bump();749 destruct(p);748 destruct(p);750 };749 }751 if p.at(T![=]) {750 if p.at(T![=]) {752 p.bump();751 p.bump();753 expr(p);752 expr(p);crates/jrsonnet-rowan-parser/src/string_block.rsdiffbeforeafterboth111112use crate::SyntaxKind;12use crate::SyntaxKind;131314pub(crate) fn lex_str_block_test<'d>(lex: &mut Lexer<'d, SyntaxKind>) {14pub(crate) fn lex_str_block_test(lex: &mut Lexer<'_, SyntaxKind>) {15 let _ = lex_str_block(lex);15 let _ = lex_str_block(lex);16}16}171748 }48 }494950 fn eat_if(&mut self, f: impl Fn(char) -> bool) -> usize {50 fn eat_if(&mut self, f: impl Fn(char) -> bool) -> usize {51 if self.peek().map(f).unwrap_or(false) {51 if self.peek().is_some_and(f) {52 self.index += 1;52 self.index += 1;53 return 1;53 return 1;54 }54 }141 }141 }142}142}143143144pub fn collect_lexed_str_block<'s>(144pub fn collect_lexed_str_block(input: &str) -> Result<CollectStrBlock<'_>, StringBlockError> {145 input: &'s str,146) -> Result<CollectStrBlock<'s>, StringBlockError> {147 let mut collect = CollectStrBlock {145 let mut collect = CollectStrBlock {148 truncate: false,146 truncate: false,149 lines: vec![],147 lines: vec![],179 }177 }180178181 fn mark_line(&mut self, line: &'d str) {179 fn mark_line(&mut self, line: &'d str) {182 self.lines.push(line)180 self.lines.push(line);183 }181 }184}182}185183crates/jrsonnet-rowan-parser/src/tests.rsdiffbeforeafterboth2#![cfg(test)]2#![cfg(test)]334use hi_doc::{Formatting, SnippetBuilder, Text};4use hi_doc::{Formatting, SnippetBuilder, Text};5use thiserror::Error;657use crate::{parse, AstNode};6use crate::{parse, AstNode};8714 if !errors.is_empty() && !text.is_empty() {13 if !errors.is_empty() && !text.is_empty() {15 writeln!(out, "===").unwrap();14 writeln!(out, "===").unwrap();16 for err in &errors {15 for err in &errors {17 writeln!(out, "{:?}", err).unwrap();16 writeln!(out, "{err:?}").unwrap();18 }17 }19 let mut code = text.to_string();18 let mut code = text.to_string();2019crates/jrsonnet-stdlib/src/regex.rsdiffbeforeafterboth4use jrsonnet_evaluator::{4use jrsonnet_evaluator::{5 error::{ErrorKind::*, Result},5 error::{ErrorKind::*, Result},6 rustc_hash::FxBuildHasher,6 rustc_hash::FxBuildHasher,7 typed::Typed,7 typed::{IntoUntyped, Typed},8 val::StrValue,8 val::StrValue,9 IStr, ObjValue, ObjValueBuilder,9 IStr, ObjValue, ObjValueBuilder,10};10};41 }41 }42}42}434344#[derive(Typed)]44#[derive(Typed, IntoUntyped)]45pub struct RegexMatch {45pub struct RegexMatch {46 string: IStr,46 string: IStr,47 captures: Vec<IStr>,47 captures: Vec<IStr>,tests/tests/common.rsdiffbeforeafterboth41}41}424243#[builtin]43#[builtin]44#[allow(dead_code)]44fn assert_throw(lazy: Thunk<Val>, message: String) -> Result<bool> {45fn assert_throw(lazy: Thunk<Val>, message: String) -> Result<bool> {45 match lazy.evaluate() {46 match lazy.evaluate() {46 Ok(_) => {47 Ok(_) => {55}56}565757#[builtin]58#[builtin]59#[allow(dead_code)]58fn param_names(fun: FuncVal) -> Vec<String> {60fn param_names(fun: FuncVal) -> Vec<String> {59 fun.params()61 fun.params()60 .iter()62 .iter()tests/tests/typed_obj.rsdiffbeforeafterboth9};9};10use jrsonnet_stdlib::ContextInitializer;10use jrsonnet_stdlib::ContextInitializer;111112#[derive(Clone, Typed, PartialEq, Debug)]12#[derive(Clone, Typed, FromUntyped, IntoUntyped, PartialEq, Debug)]13struct A {13struct A {14 a: u32,14 a: u32,15 b: u16,15 b: u16,39 Ok(())39 Ok(())40}40}414142#[derive(Clone, Typed, PartialEq, Debug)]42#[derive(Clone, Typed, FromUntyped, IntoUntyped, PartialEq, Debug)]43struct B {43struct B {44 a: u32,44 a: u32,45 #[typed(rename = "c")]45 #[typed(rename = "c")]62 Ok(())62 Ok(())63}63}646465#[derive(Clone, Typed, PartialEq, Debug)]65#[derive(Clone, Typed, FromUntyped, IntoUntyped, PartialEq, Debug)]66struct ObjectKind {66struct ObjectKind {67 #[typed(rename = "apiVersion")]67 #[typed(rename = "apiVersion")]68 api_version: String,68 api_version: String,69 #[typed(rename = "kind")]69 #[typed(rename = "kind")]70 kind: String,70 kind: String,71}71}727273#[derive(Clone, Typed, PartialEq, Debug)]73#[derive(Clone, Typed, FromUntyped, IntoUntyped, PartialEq, Debug)]74struct Object {74struct Object {75 #[typed(flatten)]75 #[typed(flatten)]76 kind: ObjectKind,76 kind: ObjectKind,104 Ok(())104 Ok(())105}105}106106107#[derive(Clone, Typed, PartialEq, Debug)]107#[derive(Clone, Typed, FromUntyped, IntoUntyped, PartialEq, Debug)]108struct C {108struct C {109 a: Option<u32>,109 a: Option<u32>,110 b: u16,110 b: u16,142 Ok(())142 Ok(())143}143}144144145#[derive(Clone, Typed, PartialEq, Debug)]145#[derive(Clone, Typed, FromUntyped, IntoUntyped, PartialEq, Debug)]146struct D {146struct D {147 #[typed(flatten(ok))]147 #[typed(flatten(ok))]148 e: Option<E>,148 e: Option<E>,149 b: u16,149 b: u16,150}150}151151152#[derive(Clone, Typed, PartialEq, Debug)]152#[derive(Clone, Typed, FromUntyped, IntoUntyped, PartialEq, Debug)]153struct E {153struct E {154 v: u32,154 v: u32,155}155}xtask/src/sourcegen/mod.rsdiffbeforeafterboth65 is_lexer_error: true,65 is_lexer_error: true,66 });66 });67 }67 }68 };68 }69 continue;69 continue;70 };70 }71 let name = to_upper_snake_case(token);71 let name = to_upper_snake_case(token);72 eprintln!("implicit kw: {token}");72 eprintln!("implicit kw: {token}");73 kinds.define_token(TokenKind::Keyword {73 kinds.define_token(TokenKind::Keyword {447 let trait_name = format_ident!("{}", trait_name);447 let trait_name = format_ident!("{}", trait_name);448 let kinds: Vec<_> = nodes448 let kinds: Vec<_> = nodes449 .iter()449 .iter()450 .map(|name| format_ident!("{}", to_upper_snake_case(&name.name.to_string())))450 .map(|name| format_ident!("{}", to_upper_snake_case(&name.name)))451 .collect();451 .collect();452452453 (453 (555 if "{}[]()$".contains(token) {555 if "{}[]()$".contains(token) {556 let c = token.chars().next().unwrap();556 let c = token.chars().next().unwrap();557 quote! { #c }557 quote! { #c }558 } else if token.contains(|v| v == '$') {558 } else if token.contains('$') {559 quote! { #token }559 quote! { #token }560 } else if token.chars().all(|v| ('a'..='z').contains(&v)) {560 } else if token.chars().all(|v: char| v.is_ascii_lowercase()) {561 let i = Ident::new(&token, Span::call_site());561 let i = Ident::new(token, Span::call_site());562 quote! { #i }562 quote! { #i }563 } else {563 } else {564 let cs = token.chars().map(|c| Punct::new(c, Spacing::Joint));564 let cs = token.chars().map(|c| Punct::new(c, Spacing::Joint));