difftreelog
feat string interning
in: master
20 files changed
bindings/jsonnet/Cargo.tomldiffbeforeafterboth5edition = "2018"5edition = "2018"667[dependencies]7[dependencies]8jrsonnet-interner = { path = "../../crates/jrsonnet-interner", version = "0.3.3" }8jrsonnet-evaluator = { path = "../../crates/jrsonnet-evaluator", version = "0.3.3" }9jrsonnet-evaluator = { path = "../../crates/jrsonnet-evaluator", version = "0.3.3" }9jrsonnet-parser = { path = "../../crates/jrsonnet-parser", version = "0.3.3" }10jrsonnet-parser = { path = "../../crates/jrsonnet-parser", version = "0.3.3" }1011bindings/jsonnet/src/import.rsdiffbeforeafterboth4 error::{Error::*, Result},4 error::{Error::*, Result},5 throw, EvaluationState, ImportResolver,5 throw, EvaluationState, ImportResolver,6};6};7use jrsonnet_interner::IStr;7use std::{8use std::{8 any::Any,9 any::Any,9 cell::RefCell,10 cell::RefCell,30 cb: JsonnetImportCallback,31 cb: JsonnetImportCallback,31 ctx: *mut c_void,32 ctx: *mut c_void,323333 out: RefCell<HashMap<PathBuf, Rc<str>>>,34 out: RefCell<HashMap<PathBuf, IStr>>,34}35}35impl ImportResolver for CallbackImportResolver {36impl ImportResolver for CallbackImportResolver {36 fn resolve_file(&self, from: &PathBuf, path: &PathBuf) -> Result<Rc<PathBuf>> {37 fn resolve_file(&self, from: &PathBuf, path: &PathBuf) -> Result<Rc<PathBuf>> {757676 Ok(Rc::new(found_here_buf))77 Ok(Rc::new(found_here_buf))77 }78 }78 fn load_file_contents(&self, resolved: &PathBuf) -> Result<Rc<str>> {79 fn load_file_contents(&self, resolved: &PathBuf) -> Result<IStr> {79 Ok(self.out.borrow().get(resolved).unwrap().clone())80 Ok(self.out.borrow().get(resolved).unwrap().clone())80 }81 }81 unsafe fn as_any(&self) -> &dyn Any {82 unsafe fn as_any(&self) -> &dyn Any {124 throw!(ImportFileNotFound(from.clone(), path.clone()))125 throw!(ImportFileNotFound(from.clone(), path.clone()))125 }126 }126 }127 }127 fn load_file_contents(&self, id: &PathBuf) -> Result<Rc<str>> {128 fn load_file_contents(&self, id: &PathBuf) -> Result<IStr> {128 let mut file = File::open(id).map_err(|_e| ResolvedFileNotFound(id.clone()))?;129 let mut file = File::open(id).map_err(|_e| ResolvedFileNotFound(id.clone()))?;129 let mut out = String::new();130 let mut out = String::new();130 file.read_to_string(&mut out)131 file.read_to_string(&mut out)bindings/jsonnet/src/lib.rsdiffbeforeafterboth889use import::NativeImportResolver;9use import::NativeImportResolver;10use jrsonnet_evaluator::{EvaluationState, ManifestFormat, Val};10use jrsonnet_evaluator::{EvaluationState, ManifestFormat, Val};11use jrsonnet_interner::IStr;11use std::{12use std::{12 alloc::Layout,13 alloc::Layout,13 ffi::{CStr, CString},14 ffi::{CStr, CString},161 })162 })162}163}163164164fn multi_to_raw(multi: Vec<(Rc<str>, Rc<str>)>) -> *const c_char {165fn multi_to_raw(multi: Vec<(IStr, IStr)>) -> *const c_char {165 let mut out = Vec::new();166 let mut out = Vec::new();166 for (i, (k, v)) in multi.iter().enumerate() {167 for (i, (k, v)) in multi.iter().enumerate() {167 if i != 0 {168 if i != 0 {237 })238 })238}239}239240240fn stream_to_raw(multi: Vec<Rc<str>>) -> *const c_char {241fn stream_to_raw(multi: Vec<IStr>) -> *const c_char {241 let mut out = Vec::new();242 let mut out = Vec::new();242 for (i, v) in multi.iter().enumerate() {243 for (i, v) in multi.iter().enumerate() {243 if i != 0 {244 if i != 0 {crates/jrsonnet-evaluator/Cargo.tomldiffbeforeafterboth12serialized-stdlib = ["serde", "bincode", "jrsonnet-parser/deserialize"]12serialized-stdlib = ["serde", "bincode", "jrsonnet-parser/deserialize"]13# Allow to convert Val into serde_json::Value and backwards13# Allow to convert Val into serde_json::Value and backwards14serde-json = ["serde", "serde_json"]14serde-json = ["serde", "serde_json"]15# Same as above, but with generated code instead of serde. Reduces memory usage, but increases binary size and compilation time16codegenerated-stdlib = []17# Replace some standard library functions with faster implementations (I.e manifestJsonEx)15# Replace some standard library functions with faster implementations (I.e manifestJsonEx)18# Library works fine without this feature, but requires more memory and time for std function calls16# Library works fine without this feature, but requires more memory and time for std function calls19faster = []17faster = []24unstable = []22unstable = []252326[dependencies]24[dependencies]25jrsonnet-interner = { path = "../jrsonnet-interner" }27jrsonnet-parser = { path = "../jrsonnet-parser", version = "0.3.3" }26jrsonnet-parser = { path = "../jrsonnet-parser", version = "0.3.3" }28jrsonnet-stdlib = { path = "../jrsonnet-stdlib", version = "0.3.3" }27jrsonnet-stdlib = { path = "../jrsonnet-stdlib", version = "0.3.3" }29jrsonnet-types = { path = "../jrsonnet-types", version = "0.3.3" }28jrsonnet-types = { path = "../jrsonnet-types", version = "0.3.3" }58optional = true57optional = true595860[build-dependencies]59[build-dependencies]61jrsonnet-parser = { path = "../jrsonnet-parser", features = ["dump", "serialize", "deserialize"], version = "0.3.3" }60jrsonnet-parser = { path = "../jrsonnet-parser", features = ["serialize", "deserialize"], version = "0.3.3" }62jrsonnet-stdlib = { path = "../jrsonnet-stdlib", version = "0.3.3" }61jrsonnet-stdlib = { path = "../jrsonnet-stdlib", version = "0.3.3" }63structdump = "0.1.2"64serde = "1.0"62serde = "1.0"65bincode = "1.3.1"63bincode = "1.3.1"6664crates/jrsonnet-evaluator/build.rsdiffbeforeafterboth10 path::{Path, PathBuf},10 path::{Path, PathBuf},11 rc::Rc,11 rc::Rc,12};12};13use structdump::CodegenResult;141315fn main() {14fn main() {16 let parsed = parse(15 let parsed = parse(36 name: FieldName::Fixed(name),35 name: FieldName::Fixed(name),37 ..36 ..38 })37 })39 if **name == *"join" || **name == *"manifestJsonEx" ||38 if name == "join" || name == "manifestJsonEx" ||40 **name == *"escapeStringJson" || **name == *"equals" ||39 name == "escapeStringJson" || name == "equals" ||41 **name == *"base64" || **name == *"foldl" || **name == *"foldr" ||40 name == "base64" || name == "foldl" || name == "foldr" ||42 **name == *"sortImpl" || **name == *"format" || **name == *"range" ||41 name == "sortImpl" || name == "format" || name == "range" ||43 **name == *"reverse" || **name == *"slice" || **name == *"mod"42 name == "reverse" || name == "slice" || name == "mod"44 )43 )45 })44 })46 .collect(),45 .collect(),52 } else {51 } else {53 parsed52 parsed54 };53 };55 {56 let mut codegen = CodegenResult::default();57 let code = codegen.codegen(&parsed);5859 let out_dir = env::var("OUT_DIR").unwrap();60 let dest_path = Path::new(&out_dir).join("stdlib.rs");61 let mut f = File::create(&dest_path).unwrap();62 f.write_all(&code.as_bytes()).unwrap();63 }64 {54 {65 let out_dir = env::var("OUT_DIR").unwrap();55 let out_dir = env::var("OUT_DIR").unwrap();66 let dest_path = Path::new(&out_dir).join("stdlib.bincode");56 let dest_path = Path::new(&out_dir).join("stdlib.bincode");crates/jrsonnet-evaluator/src/builtin/format.rsdiffbeforeafterboth2#![allow(clippy::too_many_arguments)]2#![allow(clippy::too_many_arguments)]334use crate::{error::Error::*, throw, LocError, ObjValue, Result, Val};4use crate::{error::Error::*, throw, LocError, ObjValue, Result, Val};5use jrsonnet_interner::IStr;5use jrsonnet_types::ValType;6use jrsonnet_types::ValType;6use thiserror::Error;7use thiserror::Error;7820 #[error("mapping keys required")]21 #[error("mapping keys required")]21 MappingKeysRequired,22 MappingKeysRequired,22 #[error("no such format field: {0}")]23 #[error("no such format field: {0}")]23 NoSuchFormatField(Rc<str>),24 NoSuchFormatField(IStr),24}25}252626impl From<FormatError> for LocError {27impl From<FormatError> for LocError {29 }30 }30}31}313232use std::rc::Rc;33use FormatError::*;33use FormatError::*;343435type ParseResult<'t, T> = std::result::Result<(T, &'t str), FormatError>;35type ParseResult<'t, T> = std::result::Result<(T, &'t str), FormatError>;680 }680 }681 Element::Code(c) => {681 Element::Code(c) => {682 // TODO: Operate on ref682 // TODO: Operate on ref683 let f: Rc<str> = c.mkey.into();683 let f: IStr = c.mkey.into();684 let width = match c.width {684 let width = match c.width {685 Width::Star => {685 Width::Star => {686 throw!(CannotUseStarWidthWithObject);686 throw!(CannotUseStarWidthWithObject);crates/jrsonnet-evaluator/src/builtin/mod.rsdiffbeforeafterboth6 with_state, ArrValue, Context, FuncVal, LazyVal, Val,6 with_state, ArrValue, Context, FuncVal, LazyVal, Val,7};7};8use format::{format_arr, format_obj};8use format::{format_arr, format_obj};9use jrsonnet_interner::IStr;9use jrsonnet_parser::{ArgsDesc, BinaryOpType, ExprLocation};10use jrsonnet_parser::{ArgsDesc, BinaryOpType, ExprLocation};10use jrsonnet_types::ty;11use jrsonnet_types::ty;11use std::{collections::HashMap, path::PathBuf, rc::Rc};12use std::{collections::HashMap, path::PathBuf, rc::Rc};19pub mod manifest;20pub mod manifest;20pub mod sort;21pub mod sort;212222fn std_format(str: Rc<str>, vals: Val) -> Result<Val> {23fn std_format(str: IStr, vals: Val) -> Result<Val> {23 push(24 push(24 &Some(ExprLocation(Rc::from(PathBuf::from("std.jsonnet")), 0, 0)),25 &Some(ExprLocation(Rc::from(PathBuf::from("std.jsonnet")), 0, 0)),25 || format!("std.format of {}", str),26 || format!("std.format of {}", str),crates/jrsonnet-evaluator/src/ctx.rsdiffbeforeafterboth2 error::Error::*, future_wrapper, map::LayeredHashMap, rc_fn_helper, resolved_lazy_val,2 error::Error::*, future_wrapper, map::LayeredHashMap, rc_fn_helper, resolved_lazy_val,3 LazyBinding, LazyVal, ObjValue, Result, Val,3 LazyBinding, LazyVal, ObjValue, Result, Val,4};4};5use jrsonnet_interner::IStr;5use rustc_hash::FxHashMap;6use rustc_hash::FxHashMap;6use std::hash::BuildHasherDefault;7use std::hash::BuildHasherDefault;7use std::{cell::RefCell, collections::HashMap, fmt::Debug, rc::Rc};8use std::{cell::RefCell, collections::HashMap, fmt::Debug, rc::Rc};18 dollar: Option<ObjValue>,19 dollar: Option<ObjValue>,19 this: Option<ObjValue>,20 this: Option<ObjValue>,20 super_obj: Option<ObjValue>,21 super_obj: Option<ObjValue>,21 bindings: LayeredHashMap<Rc<str>, LazyVal>,22 bindings: LayeredHashMap<IStr, LazyVal>,22}23}23impl Debug for ContextInternals {24impl Debug for ContextInternals {24 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {25 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {57 }))58 }))58 }59 }596060 pub fn binding(&self, name: Rc<str>) -> Result<LazyVal> {61 pub fn binding(&self, name: IStr) -> Result<LazyVal> {61 Ok(self62 Ok(self62 .063 .063 .bindings64 .bindings72 ctx.unwrap()73 ctx.unwrap()73 }74 }747575 pub fn with_var(self, name: Rc<str>, value: Val) -> Self {76 pub fn with_var(self, name: IStr, value: Val) -> Self {76 let mut new_bindings =77 let mut new_bindings =77 FxHashMap::with_capacity_and_hasher(1, BuildHasherDefault::default());78 FxHashMap::with_capacity_and_hasher(1, BuildHasherDefault::default());78 new_bindings.insert(name, resolved_lazy_val!(value));79 new_bindings.insert(name, resolved_lazy_val!(value));818282 pub fn extend(83 pub fn extend(83 self,84 self,84 new_bindings: FxHashMap<Rc<str>, LazyVal>,85 new_bindings: FxHashMap<IStr, LazyVal>,85 new_dollar: Option<ObjValue>,86 new_dollar: Option<ObjValue>,86 new_this: Option<ObjValue>,87 new_this: Option<ObjValue>,87 new_super_obj: Option<ObjValue>,88 new_super_obj: Option<ObjValue>,123 }124 }124 pub fn extend_unbound(125 pub fn extend_unbound(125 self,126 self,126 new_bindings: HashMap<Rc<str>, LazyBinding>,127 new_bindings: HashMap<IStr, LazyBinding>,127 new_dollar: Option<ObjValue>,128 new_dollar: Option<ObjValue>,128 new_this: Option<ObjValue>,129 new_this: Option<ObjValue>,129 new_super_obj: Option<ObjValue>,130 new_super_obj: Option<ObjValue>,crates/jrsonnet-evaluator/src/error.rsdiffbeforeafterboth2 builtin::{format::FormatError, sort::SortError},2 builtin::{format::FormatError, sort::SortError},3 typed::TypeLocError,3 typed::TypeLocError,4};4};5use jrsonnet_interner::IStr;5use jrsonnet_parser::{BinaryOpType, ExprLocation, UnaryOpType};6use jrsonnet_parser::{BinaryOpType, ExprLocation, UnaryOpType};6use jrsonnet_types::ValType;7use jrsonnet_types::ValType;7use std::{path::PathBuf, rc::Rc};8use std::{path::PathBuf, rc::Rc};10#[derive(Error, Debug, Clone)]11#[derive(Error, Debug, Clone)]11pub enum Error {12pub enum Error {12 #[error("intrinsic not found: {0}")]13 #[error("intrinsic not found: {0}")]13 IntrinsicNotFound(Rc<str>),14 IntrinsicNotFound(IStr),14 #[error("argument reordering in intrisics not supported yet")]15 #[error("argument reordering in intrisics not supported yet")]15 IntrinsicArgumentReorderingIsNotSupportedYet,16 IntrinsicArgumentReorderingIsNotSupportedYet,161733 ArrayBoundsError(usize, usize),34 ArrayBoundsError(usize, usize),343535 #[error("assert failed: {0}")]36 #[error("assert failed: {0}")]36 AssertionFailed(Rc<str>),37 AssertionFailed(IStr),373838 #[error("variable is not defined: {0}")]39 #[error("variable is not defined: {0}")]39 VariableIsNotDefined(Rc<str>),40 VariableIsNotDefined(IStr),40 #[error("type mismatch: expected {}, got {2} {0}", .1.iter().map(|e| format!("{}", e)).collect::<Vec<_>>().join(", "))]41 #[error("type mismatch: expected {}, got {2} {0}", .1.iter().map(|e| format!("{}", e)).collect::<Vec<_>>().join(", "))]41 TypeMismatch(&'static str, Vec<ValType>, ValType),42 TypeMismatch(&'static str, Vec<ValType>, ValType),42 #[error("no such field: {0}")]43 #[error("no such field: {0}")]43 NoSuchField(Rc<str>),44 NoSuchField(IStr),444545 #[error("only functions can be called, got {0}")]46 #[error("only functions can be called, got {0}")]46 OnlyFunctionsCanBeCalledGot(ValType),47 OnlyFunctionsCanBeCalledGot(ValType),47 #[error("parameter {0} is not defined")]48 #[error("parameter {0} is not defined")]48 UnknownFunctionParameter(String),49 UnknownFunctionParameter(String),49 #[error("argument {0} is already bound")]50 #[error("argument {0} is already bound")]50 BindingParameterASecondTime(Rc<str>),51 BindingParameterASecondTime(IStr),51 #[error("too many args, function has {0}")]52 #[error("too many args, function has {0}")]52 TooManyArgsFunctionHas(usize),53 TooManyArgsFunctionHas(usize),53 #[error("founction argument is not passed: {0}")]54 #[error("founction argument is not passed: {0}")]54 FunctionParameterNotBoundInCall(Rc<str>),55 FunctionParameterNotBoundInCall(IStr),555656 #[error("external variable is not defined: {0}")]57 #[error("external variable is not defined: {0}")]57 UndefinedExternalVariable(Rc<str>),58 UndefinedExternalVariable(IStr),58 #[error("native is not defined: {0}")]59 #[error("native is not defined: {0}")]59 UndefinedExternalFunction(Rc<str>),60 UndefinedExternalFunction(IStr),606161 #[error("field name should be string, got {0}")]62 #[error("field name should be string, got {0}")]62 FieldMustBeStringGot(ValType),63 FieldMustBeStringGot(ValType),636464 #[error("attempted to index array with string {0}")]65 #[error("attempted to index array with string {0}")]65 AttemptedIndexAnArrayWithString(Rc<str>),66 AttemptedIndexAnArrayWithString(IStr),66 #[error("{0} index type should be {1}, got {2}")]67 #[error("{0} index type should be {1}, got {2}")]67 ValueIndexMustBeTypeGot(ValType, ValType, ValType),68 ValueIndexMustBeTypeGot(ValType, ValType, ValType),68 #[error("cant index into {0}")]69 #[error("cant index into {0}")]86 )]87 )]87 ImportSyntaxError {88 ImportSyntaxError {88 path: Rc<PathBuf>,89 path: Rc<PathBuf>,89 source_code: Rc<str>,90 source_code: IStr,90 error: Box<jrsonnet_parser::ParseError>,91 error: Box<jrsonnet_parser::ParseError>,91 },92 },929393 #[error("runtime error: {0}")]94 #[error("runtime error: {0}")]94 RuntimeError(Rc<str>),95 RuntimeError(IStr),95 #[error("stack overflow, try to reduce recursion, or set --max-stack to bigger value")]96 #[error("stack overflow, try to reduce recursion, or set --max-stack to bigger value")]96 StackOverflow,97 StackOverflow,97 #[error("tried to index by fractional value")]98 #[error("tried to index by fractional value")]crates/jrsonnet-evaluator/src/evaluate.rsdiffbeforeafterboth3 ContextCreator, FuncDesc, FuncVal, LazyBinding, LazyVal, ObjMember, ObjValue, Result, Val,3 ContextCreator, FuncDesc, FuncVal, LazyBinding, LazyVal, ObjMember, ObjValue, Result, Val,4};4};5use closure::closure;5use closure::closure;6use jrsonnet_interner::IStr;6use jrsonnet_parser::{7use jrsonnet_parser::{7 ArgsDesc, AssertStmt, BinaryOpType, BindSpec, CompSpec, Expr, ExprLocation, FieldMember,8 ArgsDesc, AssertStmt, BinaryOpType, BindSpec, CompSpec, Expr, ExprLocation, FieldMember,8 ForSpecData, IfSpecData, LiteralType, LocExpr, Member, ObjBody, ParamsDesc, UnaryOpType,9 ForSpecData, IfSpecData, LiteralType, LocExpr, Member, ObjBody, ParamsDesc, UnaryOpType,12use rustc_hash::FxHashMap;13use rustc_hash::FxHashMap;13use std::{collections::HashMap, rc::Rc};14use std::{collections::HashMap, rc::Rc};141515pub fn evaluate_binding(b: &BindSpec, context_creator: ContextCreator) -> (Rc<str>, LazyBinding) {16pub fn evaluate_binding(b: &BindSpec, context_creator: ContextCreator) -> (IStr, LazyBinding) {16 let b = b.clone();17 let b = b.clone();17 if let Some(params) = &b.params {18 if let Some(params) = &b.params {18 let params = params.clone();19 let params = params.clone();45 }46 }46}47}474848pub fn evaluate_method(ctx: Context, name: Rc<str>, params: ParamsDesc, body: LocExpr) -> Val {49pub fn evaluate_method(ctx: Context, name: IStr, params: ParamsDesc, body: LocExpr) -> Val {49 Val::Func(Rc::new(FuncVal::Normal(FuncDesc {50 Val::Func(Rc::new(FuncVal::Normal(FuncDesc {50 name,51 name,51 ctx,52 ctx,57pub fn evaluate_field_name(58pub fn evaluate_field_name(58 context: Context,59 context: Context,59 field_name: &jrsonnet_parser::FieldName,60 field_name: &jrsonnet_parser::FieldName,60) -> Result<Option<Rc<str>>> {61) -> Result<Option<IStr>> {61 Ok(match field_name {62 Ok(match field_name {62 jrsonnet_parser::FieldName::Fixed(n) => Some(n.clone()),63 jrsonnet_parser::FieldName::Fixed(n) => Some(n.clone()),63 jrsonnet_parser::FieldName::Dyn(expr) => {64 jrsonnet_parser::FieldName::Dyn(expr) => {182 })183 })183}184}184185185future_wrapper!(HashMap<Rc<str>, LazyBinding>, FutureNewBindings);186future_wrapper!(HashMap<IStr, LazyBinding>, FutureNewBindings);186future_wrapper!(ObjValue, FutureObjValue);187future_wrapper!(ObjValue, FutureObjValue);187188188pub fn evaluate_comp<T>(189pub fn evaluate_comp<T>(230 })231 })231 );232 );232 {233 {233 let mut bindings: HashMap<Rc<str>, LazyBinding> = HashMap::new();234 let mut bindings: HashMap<IStr, LazyBinding> = HashMap::new();234 for (n, b) in members235 for (n, b) in members235 .iter()236 .iter()236 .filter_map(|m| match m {237 .filter_map(|m| match m {334 )?)335 )?)335 })336 })336 );337 );337 let mut bindings: HashMap<Rc<str>, LazyBinding> = HashMap::new();338 let mut bindings: HashMap<IStr, LazyBinding> = HashMap::new();338 for (n, b) in obj339 for (n, b) in obj339 .pre_locals340 .pre_locals340 .iter()341 .iter()401 })402 })402}403}403404404pub fn evaluate_named(context: Context, lexpr: &LocExpr, name: Rc<str>) -> Result<Val> {405pub fn evaluate_named(context: Context, lexpr: &LocExpr, name: IStr) -> Result<Val> {405 use Expr::*;406 use Expr::*;406 let LocExpr(expr, _loc) = lexpr;407 let LocExpr(expr, _loc) = lexpr;407 Ok(match &**expr {408 Ok(match &**expr {498 }499 }499 }500 }500 LocalExpr(bindings, returned) => {501 LocalExpr(bindings, returned) => {501 let mut new_bindings: HashMap<Rc<str>, LazyBinding> = HashMap::new();502 let mut new_bindings: HashMap<IStr, LazyBinding> = HashMap::new();502 let future_context = Context::new_future();503 let future_context = Context::new_future();503504504 let context_creator = context_creator!(505 let context_creator = context_creator!(crates/jrsonnet-evaluator/src/function.rsdiffbeforeafterboth1use crate::{error::Error::*, evaluate, lazy_val, resolved_lazy_val, throw, Context, Result, Val};1use crate::{error::Error::*, evaluate, lazy_val, resolved_lazy_val, throw, Context, Result, Val};2use closure::closure;2use closure::closure;3use jrsonnet_interner::IStr;3use jrsonnet_parser::{ArgsDesc, ParamsDesc};4use jrsonnet_parser::{ArgsDesc, ParamsDesc};4use rustc_hash::FxHashMap;5use rustc_hash::FxHashMap;5use std::{collections::HashMap, hash::BuildHasherDefault, rc::Rc};6use std::{collections::HashMap, hash::BuildHasherDefault};677const NO_DEFAULT_CONTEXT: &str =8const NO_DEFAULT_CONTEXT: &str =8 "no default context set for call with defined default parameter value";9 "no default context set for call with defined default parameter value";66 ctx: Context,67 ctx: Context,67 body_ctx: Option<Context>,68 body_ctx: Option<Context>,68 params: &ParamsDesc,69 params: &ParamsDesc,69 args: &HashMap<Rc<str>, Val>,70 args: &HashMap<IStr, Val>,70 tailstrict: bool,71 tailstrict: bool,71) -> Result<Context> {72) -> Result<Context> {72 let mut out = FxHashMap::with_capacity_and_hasher(params.len(), BuildHasherDefault::default());73 let mut out = FxHashMap::with_capacity_and_hasher(params.len(), BuildHasherDefault::default());crates/jrsonnet-evaluator/src/import.rsdiffbeforeafterboth3 throw,3 throw,4};4};5use fs::File;5use fs::File;6use jrsonnet_interner::IStr;6use std::fs;7use std::fs;7use std::io::Read;8use std::io::Read;8use std::{any::Any, cell::RefCell, collections::HashMap, path::PathBuf, rc::Rc};9use std::{any::Any, cell::RefCell, collections::HashMap, path::PathBuf, rc::Rc};15 fn resolve_file(&self, from: &PathBuf, path: &PathBuf) -> Result<Rc<PathBuf>>;16 fn resolve_file(&self, from: &PathBuf, path: &PathBuf) -> Result<Rc<PathBuf>>;161717 /// Reads file from filesystem, should be used only with path received from `resolve_file`18 /// Reads file from filesystem, should be used only with path received from `resolve_file`18 fn load_file_contents(&self, resolved: &PathBuf) -> Result<Rc<str>>;19 fn load_file_contents(&self, resolved: &PathBuf) -> Result<IStr>;192020 /// # Safety21 /// # Safety21 ///22 ///32 throw!(ImportNotSupported(from.clone(), path.clone()))33 throw!(ImportNotSupported(from.clone(), path.clone()))33 }34 }343535 fn load_file_contents(&self, _resolved: &PathBuf) -> Result<Rc<str>> {36 fn load_file_contents(&self, _resolved: &PathBuf) -> Result<IStr> {36 // Can be only caused by library direct consumer, not by supplied jsonnet37 // Can be only caused by library direct consumer, not by supplied jsonnet37 panic!("dummy resolver can't load any file")38 panic!("dummy resolver can't load any file")38 }39 }72 throw!(ImportFileNotFound(from.clone(), path.clone()))73 throw!(ImportFileNotFound(from.clone(), path.clone()))73 }74 }74 }75 }75 fn load_file_contents(&self, id: &PathBuf) -> Result<Rc<str>> {76 fn load_file_contents(&self, id: &PathBuf) -> Result<IStr> {76 let mut file = File::open(id).map_err(|_e| ResolvedFileNotFound(id.clone()))?;77 let mut file = File::open(id).map_err(|_e| ResolvedFileNotFound(id.clone()))?;77 let mut out = String::new();78 let mut out = String::new();78 file.read_to_string(&mut out)79 file.read_to_string(&mut out)89/// Caches results of the underlying resolver90/// Caches results of the underlying resolver90pub struct CachingImportResolver {91pub struct CachingImportResolver {91 resolution_cache: RefCell<HashMap<ResolutionData, Result<Rc<PathBuf>>>>,92 resolution_cache: RefCell<HashMap<ResolutionData, Result<Rc<PathBuf>>>>,92 loading_cache: RefCell<HashMap<PathBuf, Result<Rc<str>>>>,93 loading_cache: RefCell<HashMap<PathBuf, Result<IStr>>>,93 inner: Box<dyn ImportResolver>,94 inner: Box<dyn ImportResolver>,94}95}95impl ImportResolver for CachingImportResolver {96impl ImportResolver for CachingImportResolver {101 .clone()102 .clone()102 }103 }103104104 fn load_file_contents(&self, resolved: &PathBuf) -> Result<Rc<str>> {105 fn load_file_contents(&self, resolved: &PathBuf) -> Result<IStr> {105 self.loading_cache106 self.loading_cache106 .borrow_mut()107 .borrow_mut()107 .entry(resolved.clone())108 .entry(resolved.clone())crates/jrsonnet-evaluator/src/lib.rsdiffbeforeafterboth23pub use evaluate::*;23pub use evaluate::*;24pub use function::parse_function_call;24pub use function::parse_function_call;25pub use import::*;25pub use import::*;26use jrsonnet_interner::IStr;26use jrsonnet_parser::*;27use jrsonnet_parser::*;27use native::NativeCallback;28use native::NativeCallback;28pub use obj::*;29pub use obj::*;63 /// Limits amount of stack trace items preserved64 /// Limits amount of stack trace items preserved64 pub max_trace: usize,65 pub max_trace: usize,65 /// Used for s`td.extVar`66 /// Used for s`td.extVar`66 pub ext_vars: HashMap<Rc<str>, Val>,67 pub ext_vars: HashMap<IStr, Val>,67 /// Used for ext.native68 /// Used for ext.native68 pub ext_natives: HashMap<Rc<str>, Rc<NativeCallback>>,69 pub ext_natives: HashMap<IStr, Rc<NativeCallback>>,69 /// TLA vars70 /// TLA vars70 pub tla_vars: HashMap<Rc<str>, Val>,71 pub tla_vars: HashMap<IStr, Val>,71 /// Global variables are inserted in default context72 /// Global variables are inserted in default context72 pub globals: HashMap<Rc<str>, Val>,73 pub globals: HashMap<IStr, Val>,73 /// Used to resolve file locations/contents74 /// Used to resolve file locations/contents74 pub import_resolver: Box<dyn ImportResolver>,75 pub import_resolver: Box<dyn ImportResolver>,75 /// Used in manifestification functions76 /// Used in manifestification functions102 stack_depth: usize,103 stack_depth: usize,103 /// Contains file source codes and evaluation results for imports and pretty-printed stacktraces104 /// Contains file source codes and evaluation results for imports and pretty-printed stacktraces104 files: HashMap<Rc<PathBuf>, FileData>,105 files: HashMap<Rc<PathBuf>, FileData>,105 str_files: HashMap<Rc<PathBuf>, Rc<str>>,106 str_files: HashMap<Rc<PathBuf>, IStr>,106}107}107108108pub struct FileData {109pub struct FileData {109 source_code: Rc<str>,110 source_code: IStr,110 parsed: LocExpr,111 parsed: LocExpr,111 evaluated: Option<Val>,112 evaluated: Option<Val>,112}113}144145145impl EvaluationState {146impl EvaluationState {146 /// Parses and adds file as loaded147 /// Parses and adds file as loaded147 pub fn add_file(&self, path: Rc<PathBuf>, source_code: Rc<str>) -> Result<()> {148 pub fn add_file(&self, path: Rc<PathBuf>, source_code: IStr) -> Result<()> {148 self.add_parsed_file(149 self.add_parsed_file(149 path.clone(),150 path.clone(),150 source_code.clone(),151 source_code.clone(),169 pub fn add_parsed_file(170 pub fn add_parsed_file(170 &self,171 &self,171 name: Rc<PathBuf>,172 name: Rc<PathBuf>,172 source_code: Rc<str>,173 source_code: IStr,173 parsed: LocExpr,174 parsed: LocExpr,174 ) -> Result<()> {175 ) -> Result<()> {175 self.data_mut().files.insert(176 self.data_mut().files.insert(183184184 Ok(())185 Ok(())185 }186 }186 pub fn get_source(&self, name: &PathBuf) -> Option<Rc<str>> {187 pub fn get_source(&self, name: &PathBuf) -> Option<IStr> {187 let ro_map = &self.data().files;188 let ro_map = &self.data().files;188 ro_map.get(name).map(|value| value.source_code.clone())189 ro_map.get(name).map(|value| value.source_code.clone())189 }190 }205 self.add_file(file_path.clone(), contents)?;206 self.add_file(file_path.clone(), contents)?;206 self.evaluate_loaded_file_raw(&file_path)207 self.evaluate_loaded_file_raw(&file_path)207 }208 }208 pub(crate) fn import_file_str(&self, from: &PathBuf, path: &PathBuf) -> Result<Rc<str>> {209 pub(crate) fn import_file_str(&self, from: &PathBuf, path: &PathBuf) -> Result<IStr> {209 let path = self.resolve_file(from, path)?;210 let path = self.resolve_file(from, path)?;210 if !self.data().str_files.contains_key(&path) {211 if !self.data().str_files.contains_key(&path) {211 let file_str = self.load_file_contents(&path)?;212 let file_str = self.load_file_contents(&path)?;257 /// Creates context with all passed global variables258 /// Creates context with all passed global variables258 pub fn create_default_context(&self) -> Result<Context> {259 pub fn create_default_context(&self) -> Result<Context> {259 let globals = &self.settings().globals;260 let globals = &self.settings().globals;260 let mut new_bindings: HashMap<Rc<str>, LazyBinding> = HashMap::new();261 let mut new_bindings: HashMap<IStr, LazyBinding> = HashMap::new();261 for (name, value) in globals.iter() {262 for (name, value) in globals.iter() {262 new_bindings.insert(263 new_bindings.insert(263 name.clone(),264 name.clone(),321 out322 out322 }323 }323324324 pub fn manifest(&self, val: Val) -> Result<Rc<str>> {325 pub fn manifest(&self, val: Val) -> Result<IStr> {325 self.run_in_state(|| val.manifest(&self.manifest_format()))326 self.run_in_state(|| val.manifest(&self.manifest_format()))326 }327 }327 pub fn manifest_multi(&self, val: Val) -> Result<Vec<(Rc<str>, Rc<str>)>> {328 pub fn manifest_multi(&self, val: Val) -> Result<Vec<(IStr, IStr)>> {328 self.run_in_state(|| val.manifest_multi(&self.manifest_format()))329 self.run_in_state(|| val.manifest_multi(&self.manifest_format()))329 }330 }330 pub fn manifest_stream(&self, val: Val) -> Result<Vec<Rc<str>>> {331 pub fn manifest_stream(&self, val: Val) -> Result<Vec<IStr>> {331 self.run_in_state(|| val.manifest_stream(&self.manifest_format()))332 self.run_in_state(|| val.manifest_stream(&self.manifest_format()))332 }333 }333334371 self.run_in_state(|| self.import_file(&PathBuf::from("."), name))372 self.run_in_state(|| self.import_file(&PathBuf::from("."), name))372 }373 }373 /// Parses and evaluates the given snippet374 /// Parses and evaluates the given snippet374 pub fn evaluate_snippet_raw(&self, source: Rc<PathBuf>, code: Rc<str>) -> Result<Val> {375 pub fn evaluate_snippet_raw(&self, source: Rc<PathBuf>, code: IStr) -> Result<Val> {375 let parsed = parse(376 let parsed = parse(376 &code,377 &code,377 &ParserSettings {378 &ParserSettings {391392392/// Settings utilities393/// Settings utilities393impl EvaluationState {394impl EvaluationState {394 pub fn add_ext_var(&self, name: Rc<str>, value: Val) {395 pub fn add_ext_var(&self, name: IStr, value: Val) {395 self.settings_mut().ext_vars.insert(name, value);396 self.settings_mut().ext_vars.insert(name, value);396 }397 }397 pub fn add_ext_str(&self, name: Rc<str>, value: Rc<str>) {398 pub fn add_ext_str(&self, name: IStr, value: IStr) {398 self.add_ext_var(name, Val::Str(value));399 self.add_ext_var(name, Val::Str(value));399 }400 }400 pub fn add_ext_code(&self, name: Rc<str>, code: Rc<str>) -> Result<()> {401 pub fn add_ext_code(&self, name: IStr, code: IStr) -> Result<()> {401 let value =402 let value =402 self.evaluate_snippet_raw(Rc::new(PathBuf::from(format!("ext_code {}", name))), code)?;403 self.evaluate_snippet_raw(Rc::new(PathBuf::from(format!("ext_code {}", name))), code)?;403 self.add_ext_var(name, value);404 self.add_ext_var(name, value);404 Ok(())405 Ok(())405 }406 }406407407 pub fn add_tla(&self, name: Rc<str>, value: Val) {408 pub fn add_tla(&self, name: IStr, value: Val) {408 self.settings_mut().tla_vars.insert(name, value);409 self.settings_mut().tla_vars.insert(name, value);409 }410 }410 pub fn add_tla_str(&self, name: Rc<str>, value: Rc<str>) {411 pub fn add_tla_str(&self, name: IStr, value: IStr) {411 self.add_tla(name, Val::Str(value));412 self.add_tla(name, Val::Str(value));412 }413 }413 pub fn add_tla_code(&self, name: Rc<str>, code: Rc<str>) -> Result<()> {414 pub fn add_tla_code(&self, name: IStr, code: IStr) -> Result<()> {414 let value =415 let value =415 self.evaluate_snippet_raw(Rc::new(PathBuf::from(format!("tla_code {}", name))), code)?;416 self.evaluate_snippet_raw(Rc::new(PathBuf::from(format!("tla_code {}", name))), code)?;416 self.add_tla(name, value);417 self.add_tla(name, value);420 pub fn resolve_file(&self, from: &PathBuf, path: &PathBuf) -> Result<Rc<PathBuf>> {421 pub fn resolve_file(&self, from: &PathBuf, path: &PathBuf) -> Result<Rc<PathBuf>> {421 Ok(self.settings().import_resolver.resolve_file(from, path)?)422 Ok(self.settings().import_resolver.resolve_file(from, path)?)422 }423 }423 pub fn load_file_contents(&self, path: &PathBuf) -> Result<Rc<str>> {424 pub fn load_file_contents(&self, path: &PathBuf) -> Result<IStr> {424 Ok(self.settings().import_resolver.load_file_contents(path)?)425 Ok(self.settings().import_resolver.load_file_contents(path)?)425 }426 }426427431 self.settings_mut().import_resolver = resolver;432 self.settings_mut().import_resolver = resolver;432 }433 }433434434 pub fn add_native(&self, name: Rc<str>, cb: Rc<NativeCallback>) {435 pub fn add_native(&self, name: IStr, cb: Rc<NativeCallback>) {435 self.settings_mut().ext_natives.insert(name, cb);436 self.settings_mut().ext_natives.insert(name, cb);436 }437 }437438468pub mod tests {469pub mod tests {469 use super::Val;470 use super::Val;470 use crate::{error::Error::*, primitive_equals, EvaluationState};471 use crate::{error::Error::*, primitive_equals, EvaluationState};472 use jrsonnet_interner::IStr;471 use jrsonnet_parser::*;473 use jrsonnet_parser::*;472 use std::{path::PathBuf, rc::Rc};474 use std::{path::PathBuf, rc::Rc};473475905 Ok(())907 Ok(())906 }908 }907909908 struct TestImportResolver(Rc<str>);910 struct TestImportResolver(IStr);909 impl crate::import::ImportResolver for TestImportResolver {911 impl crate::import::ImportResolver for TestImportResolver {910 fn resolve_file(&self, _: &PathBuf, _: &PathBuf) -> crate::error::Result<Rc<PathBuf>> {912 fn resolve_file(&self, _: &PathBuf, _: &PathBuf) -> crate::error::Result<Rc<PathBuf>> {911 Ok(Rc::new(PathBuf::from("/test")))913 Ok(Rc::new(PathBuf::from("/test")))912 }914 }913915914 fn load_file_contents(&self, _: &PathBuf) -> crate::error::Result<Rc<str>> {916 fn load_file_contents(&self, _: &PathBuf) -> crate::error::Result<IStr> {915 Ok(self.0.clone())917 Ok(self.0.clone())916 }918 }917919crates/jrsonnet-evaluator/src/obj.rsdiffbeforeafterboth1use crate::{evaluate_add_op, LazyBinding, Result, Val};1use crate::{evaluate_add_op, LazyBinding, Result, Val};2use indexmap::IndexMap;2use indexmap::IndexMap;3use jrsonnet_interner::IStr;3use jrsonnet_parser::{ExprLocation, Visibility};4use jrsonnet_parser::{ExprLocation, Visibility};4use std::{cell::RefCell, collections::HashMap, fmt::Debug, rc::Rc};5use std::{cell::RefCell, collections::HashMap, fmt::Debug, rc::Rc};5612}13}131414// Field => This15// Field => This15type CacheKey = (Rc<str>, usize);16type CacheKey = (IStr, usize);16#[derive(Debug)]17#[derive(Debug)]17pub struct ObjValueInternals {18pub struct ObjValueInternals {18 super_obj: Option<ObjValue>,19 super_obj: Option<ObjValue>,19 this_entries: Rc<HashMap<Rc<str>, ObjMember>>,20 this_entries: Rc<HashMap<IStr, ObjMember>>,20 value_cache: RefCell<HashMap<CacheKey, Option<Val>>>,21 value_cache: RefCell<HashMap<CacheKey, Option<Val>>>,21}22}22#[derive(Clone)]23#[derive(Clone)]33 }34 }34 let mut debug = f.debug_struct("ObjValue");35 let mut debug = f.debug_struct("ObjValue");35 for (name, member) in self.0.this_entries.iter() {36 for (name, member) in self.0.this_entries.iter() {36 debug.field(name, member);37 debug.field(&name, member);37 }38 }38 #[cfg(feature = "unstable")]39 #[cfg(feature = "unstable")]39 {40 {47}48}484949impl ObjValue {50impl ObjValue {50 pub fn new(super_obj: Option<Self>, this_entries: Rc<HashMap<Rc<str>, ObjMember>>) -> Self {51 pub fn new(super_obj: Option<Self>, this_entries: Rc<HashMap<IStr, ObjMember>>) -> Self {51 Self(Rc::new(ObjValueInternals {52 Self(Rc::new(ObjValueInternals {52 super_obj,53 super_obj,53 this_entries,54 this_entries,63 Some(v) => Self::new(Some(v.with_super(super_obj)), self.0.this_entries.clone()),64 Some(v) => Self::new(Some(v.with_super(super_obj)), self.0.this_entries.clone()),64 }65 }65 }66 }66 pub fn enum_fields(&self, handler: &impl Fn(&Rc<str>, &Visibility)) {67 pub fn enum_fields(&self, handler: &impl Fn(&IStr, &Visibility)) {67 if let Some(s) = &self.0.super_obj {68 if let Some(s) = &self.0.super_obj {68 s.enum_fields(handler);69 s.enum_fields(handler);69 }70 }70 for (name, member) in self.0.this_entries.iter() {71 for (name, member) in self.0.this_entries.iter() {71 handler(name, &member.visibility);72 handler(name, &member.visibility);72 }73 }73 }74 }74 pub fn fields_visibility(&self) -> IndexMap<Rc<str>, bool> {75 pub fn fields_visibility(&self) -> IndexMap<IStr, bool> {75 let out = Rc::new(RefCell::new(IndexMap::new()));76 let out = Rc::new(RefCell::new(IndexMap::new()));76 self.enum_fields(&|name, visibility| {77 self.enum_fields(&|name, visibility| {77 let mut out = out.borrow_mut();78 let mut out = out.borrow_mut();91 });92 });92 Rc::try_unwrap(out).unwrap().into_inner()93 Rc::try_unwrap(out).unwrap().into_inner()93 }94 }94 pub fn visible_fields(&self) -> Vec<Rc<str>> {95 pub fn visible_fields(&self) -> Vec<IStr> {95 let mut visible_fields: Vec<_> = self96 let mut visible_fields: Vec<_> = self96 .fields_visibility()97 .fields_visibility()97 .into_iter()98 .into_iter()101 visible_fields.sort();102 visible_fields.sort();102 visible_fields103 visible_fields103 }104 }104 pub fn get(&self, key: Rc<str>) -> Result<Option<Val>> {105 pub fn get(&self, key: IStr) -> Result<Option<Val>> {105 Ok(self.get_raw(key, None)?)106 Ok(self.get_raw(key, None)?)106 }107 }107 pub(crate) fn get_raw(&self, key: Rc<str>, real_this: Option<&Self>) -> Result<Option<Val>> {108 pub(crate) fn get_raw(&self, key: IStr, real_this: Option<&Self>) -> Result<Option<Val>> {108 let real_this = real_this.unwrap_or(self);109 let real_this = real_this.unwrap_or(self);109 let cache_key = (key.clone(), Rc::as_ptr(&real_this.0) as usize);110 let cache_key = (key.clone(), Rc::as_ptr(&real_this.0) as usize);110111crates/jrsonnet-evaluator/src/val.rsdiffbeforeafterboth9 native::NativeCallback,9 native::NativeCallback,10 throw, with_state, Context, ObjValue, Result,10 throw, with_state, Context, ObjValue, Result,11};11};12use jrsonnet_interner::IStr;12use jrsonnet_parser::{el, Arg, ArgsDesc, Expr, ExprLocation, LiteralType, LocExpr, ParamsDesc};13use jrsonnet_parser::{el, Arg, ArgsDesc, Expr, ExprLocation, LiteralType, LocExpr, ParamsDesc};13use jrsonnet_types::ValType;14use jrsonnet_types::ValType;14use std::{cell::RefCell, collections::HashMap, fmt::Debug, rc::Rc};15use std::{cell::RefCell, collections::HashMap, fmt::Debug, rc::Rc};616262#[derive(Debug, PartialEq)]63#[derive(Debug, PartialEq)]63pub struct FuncDesc {64pub struct FuncDesc {64 pub name: Rc<str>,65 pub name: IStr,65 pub ctx: Context,66 pub ctx: Context,66 pub params: ParamsDesc,67 pub params: ParamsDesc,67 pub body: LocExpr,68 pub body: LocExpr,72 /// Plain function implemented in jsonnet73 /// Plain function implemented in jsonnet73 Normal(FuncDesc),74 Normal(FuncDesc),74 /// Standard library function75 /// Standard library function75 Intrinsic(Rc<str>),76 Intrinsic(IStr),76 /// Library functions implemented in native77 /// Library functions implemented in native77 NativeExt(Rc<str>, Rc<NativeCallback>),78 NativeExt(IStr, Rc<NativeCallback>),78}79}798080impl PartialEq for FuncVal {81impl PartialEq for FuncVal {91 pub fn is_ident(&self) -> bool {92 pub fn is_ident(&self) -> bool {92 matches!(&self, Self::Intrinsic(n) if n as &str == "id")93 matches!(&self, Self::Intrinsic(n) if n as &str == "id")93 }94 }94 pub fn name(&self) -> Rc<str> {95 pub fn name(&self) -> IStr {95 match self {96 match self {96 Self::Normal(normal) => normal.name.clone(),97 Self::Normal(normal) => normal.name.clone(),97 Self::Intrinsic(name) => format!("std.{}", name).into(),98 Self::Intrinsic(name) => format!("std.{}", name).into(),131 pub fn evaluate_map(132 pub fn evaluate_map(132 &self,133 &self,133 call_ctx: Context,134 call_ctx: Context,134 args: &HashMap<Rc<str>, Val>,135 args: &HashMap<IStr, Val>,135 tailstrict: bool,136 tailstrict: bool,136 ) -> Result<Val> {137 ) -> Result<Val> {137 match self {138 match self {270pub enum Val {271pub enum Val {271 Bool(bool),272 Bool(bool),272 Null,273 Null,273 Str(Rc<str>),274 Str(IStr),274 Num(f64),275 Num(f64),275 Arr(ArrValue),276 Arr(ArrValue),276 Obj(ObjValue),277 Obj(ObjValue),314 self.assert_type(context, ValType::Bool)?;315 self.assert_type(context, ValType::Bool)?;315 Ok(matches_unwrap!(self, Self::Bool(v), v))316 Ok(matches_unwrap!(self, Self::Bool(v), v))316 }317 }317 pub fn try_cast_str(self, context: &'static str) -> Result<Rc<str>> {318 pub fn try_cast_str(self, context: &'static str) -> Result<IStr> {318 self.assert_type(context, ValType::Str)?;319 self.assert_type(context, ValType::Str)?;319 Ok(matches_unwrap!(self, Self::Str(v), v))320 Ok(matches_unwrap!(self, Self::Str(v), v))320 }321 }334 }335 }335 }336 }336337337 pub fn to_string(&self) -> Result<Rc<str>> {338 pub fn to_string(&self) -> Result<IStr> {338 Ok(match self {339 Ok(match self {339 Self::Bool(true) => "true".into(),340 Self::Bool(true) => "true".into(),340 Self::Bool(false) => "false".into(),341 Self::Bool(false) => "false".into(),352 }353 }353354354 /// Expects value to be object, outputs (key, manifested value) pairs355 /// Expects value to be object, outputs (key, manifested value) pairs355 pub fn manifest_multi(&self, ty: &ManifestFormat) -> Result<Vec<(Rc<str>, Rc<str>)>> {356 pub fn manifest_multi(&self, ty: &ManifestFormat) -> Result<Vec<(IStr, IStr)>> {356 let obj = match self {357 let obj = match self {357 Self::Obj(obj) => obj,358 Self::Obj(obj) => obj,358 _ => throw!(MultiManifestOutputIsNotAObject),359 _ => throw!(MultiManifestOutputIsNotAObject),370 }371 }371372372 /// Expects value to be array, outputs manifested values373 /// Expects value to be array, outputs manifested values373 pub fn manifest_stream(&self, ty: &ManifestFormat) -> Result<Vec<Rc<str>>> {374 pub fn manifest_stream(&self, ty: &ManifestFormat) -> Result<Vec<IStr>> {374 let arr = match self {375 let arr = match self {375 Self::Arr(a) => a,376 Self::Arr(a) => a,376 _ => throw!(StreamManifestOutputIsNotAArray),377 _ => throw!(StreamManifestOutputIsNotAArray),382 Ok(out)383 Ok(out)383 }384 }384385385 pub fn manifest(&self, ty: &ManifestFormat) -> Result<Rc<str>> {386 pub fn manifest(&self, ty: &ManifestFormat) -> Result<IStr> {386 Ok(match ty {387 Ok(match ty {387 ManifestFormat::YamlStream(format) => {388 ManifestFormat::YamlStream(format) => {388 let arr = match self {389 let arr = match self {419 }420 }420421421 /// For manifestification422 /// For manifestification422 pub fn to_json(&self, padding: usize) -> Result<Rc<str>> {423 pub fn to_json(&self, padding: usize) -> Result<IStr> {423 manifest_json_ex(424 manifest_json_ex(424 self,425 self,425 &ManifestJsonOptions {426 &ManifestJsonOptions {471 .try_cast_str("to json")?)472 .try_cast_str("to json")?)472 })473 })473 }474 }474 pub fn to_yaml(&self, padding: usize) -> Result<Rc<str>> {475 pub fn to_yaml(&self, padding: usize) -> Result<IStr> {475 with_state(|s| {476 with_state(|s| {476 let ctx = s477 let ctx = s477 .create_default_context()?478 .create_default_context()?crates/jrsonnet-interner/.gitignorediffbeforeafterbothno changes
crates/jrsonnet-interner/Cargo.tomldiffbeforeafterbothno changes
crates/jrsonnet-interner/src/lib.rsdiffbeforeafterbothno changes
crates/jrsonnet-parser/Cargo.tomldiffbeforeafterboth10default = []10default = []11serialize = ["serde"]11serialize = ["serde"]12deserialize = ["serde"]12deserialize = ["serde"]13# Adds ability to dump AST as source code for easy embedding14dump = ["structdump", "structdump-derive"]151316[dependencies]14[dependencies]15jrsonnet-interner = { path = "../jrsonnet-interner" }1617peg = "0.6.3"17peg = "0.6.3"18unescape = "0.1.0"18unescape = "0.1.0"191920serde = { version = "1.0", features = ["derive", "rc"], optional = true }20serde = { version = "1.0", features = ["derive", "rc"], optional = true }21structdump = { version = "0.1.2", optional = true }22structdump-derive = { version = "0.1.2", optional = true }232124[dev-dependencies]22[dev-dependencies]25jrsonnet-stdlib = { path = "../jrsonnet-stdlib", version = "0.3.3" }23jrsonnet-stdlib = { path = "../jrsonnet-stdlib", version = "0.3.3" }crates/jrsonnet-parser/src/expr.rsdiffbeforeafterboth1use jrsonnet_interner::IStr;1#[cfg(feature = "deserialize")]2#[cfg(feature = "deserialize")]2use serde::Deserialize;3use serde::Deserialize;3#[cfg(feature = "serialize")]4#[cfg(feature = "serialize")]8 path::PathBuf,9 path::PathBuf,9 rc::Rc,10 rc::Rc,10};11};11#[cfg(feature = "dump")]1212use structdump_derive::Codegen;1314#[cfg_attr(feature = "dump", derive(Codegen))]15#[cfg_attr(feature = "serialize", derive(Serialize))]13#[cfg_attr(feature = "serialize", derive(Serialize))]16#[cfg_attr(feature = "deserialize", derive(Deserialize))]14#[cfg_attr(feature = "deserialize", derive(Deserialize))]17#[derive(Debug, PartialEq)]15#[derive(Debug, PartialEq)]18pub enum FieldName {16pub enum FieldName {19 /// {fixed: 2}17 /// {fixed: 2}20 Fixed(Rc<str>),18 Fixed(IStr),21 /// {["dyn"+"amic"]: 3}19 /// {["dyn"+"amic"]: 3}22 Dyn(LocExpr),20 Dyn(LocExpr),23}21}242225#[cfg_attr(feature = "dump", derive(Codegen))]26#[cfg_attr(feature = "serialize", derive(Serialize))]23#[cfg_attr(feature = "serialize", derive(Serialize))]27#[cfg_attr(feature = "deserialize", derive(Deserialize))]24#[cfg_attr(feature = "deserialize", derive(Deserialize))]28#[derive(Debug, Clone, Copy, PartialEq)]25#[derive(Debug, Clone, Copy, PartialEq)]35 Unhide,32 Unhide,36}33}373438#[cfg_attr(feature = "dump", derive(Codegen))]39#[cfg_attr(feature = "serialize", derive(Serialize))]35#[cfg_attr(feature = "serialize", derive(Serialize))]40#[cfg_attr(feature = "deserialize", derive(Deserialize))]36#[cfg_attr(feature = "deserialize", derive(Deserialize))]41#[derive(Debug, PartialEq)]37#[derive(Debug, PartialEq)]42pub struct AssertStmt(pub LocExpr, pub Option<LocExpr>);38pub struct AssertStmt(pub LocExpr, pub Option<LocExpr>);433944#[cfg_attr(feature = "dump", derive(Codegen))]45#[cfg_attr(feature = "serialize", derive(Serialize))]40#[cfg_attr(feature = "serialize", derive(Serialize))]46#[cfg_attr(feature = "deserialize", derive(Deserialize))]41#[cfg_attr(feature = "deserialize", derive(Deserialize))]47#[derive(Debug, PartialEq)]42#[derive(Debug, PartialEq)]53 pub value: LocExpr,48 pub value: LocExpr,54}49}555056#[cfg_attr(feature = "dump", derive(Codegen))]57#[cfg_attr(feature = "serialize", derive(Serialize))]51#[cfg_attr(feature = "serialize", derive(Serialize))]58#[cfg_attr(feature = "deserialize", derive(Deserialize))]52#[cfg_attr(feature = "deserialize", derive(Deserialize))]59#[derive(Debug, PartialEq)]53#[derive(Debug, PartialEq)]63 AssertStmt(AssertStmt),57 AssertStmt(AssertStmt),64}58}655966#[cfg_attr(feature = "dump", derive(Codegen))]67#[cfg_attr(feature = "serialize", derive(Serialize))]60#[cfg_attr(feature = "serialize", derive(Serialize))]68#[cfg_attr(feature = "deserialize", derive(Deserialize))]61#[cfg_attr(feature = "deserialize", derive(Deserialize))]69#[derive(Debug, Clone, Copy, PartialEq)]62#[derive(Debug, Clone, Copy, PartialEq)]89 }82 }90}83}918492#[cfg_attr(feature = "dump", derive(Codegen))]93#[cfg_attr(feature = "serialize", derive(Serialize))]85#[cfg_attr(feature = "serialize", derive(Serialize))]94#[cfg_attr(feature = "deserialize", derive(Deserialize))]86#[cfg_attr(feature = "deserialize", derive(Deserialize))]95#[derive(Debug, Clone, Copy, PartialEq)]87#[derive(Debug, Clone, Copy, PartialEq)]147}139}148140149/// name, default value141/// name, default value150#[cfg_attr(feature = "dump", derive(Codegen))]151#[cfg_attr(feature = "serialize", derive(Serialize))]142#[cfg_attr(feature = "serialize", derive(Serialize))]152#[cfg_attr(feature = "deserialize", derive(Deserialize))]143#[cfg_attr(feature = "deserialize", derive(Deserialize))]153#[derive(Debug, PartialEq)]144#[derive(Debug, PartialEq)]154pub struct Param(pub Rc<str>, pub Option<LocExpr>);145pub struct Param(pub IStr, pub Option<LocExpr>);155146156/// Defined function parameters147/// Defined function parameters157#[cfg_attr(feature = "dump", derive(Codegen))]158#[cfg_attr(feature = "serialize", derive(Serialize))]148#[cfg_attr(feature = "serialize", derive(Serialize))]159#[cfg_attr(feature = "deserialize", derive(Deserialize))]149#[cfg_attr(feature = "deserialize", derive(Deserialize))]160#[derive(Debug, Clone, PartialEq)]150#[derive(Debug, Clone, PartialEq)]166 }156 }167}157}168158169#[cfg_attr(feature = "dump", derive(Codegen))]170#[cfg_attr(feature = "serialize", derive(Serialize))]159#[cfg_attr(feature = "serialize", derive(Serialize))]171#[cfg_attr(feature = "deserialize", derive(Deserialize))]160#[cfg_attr(feature = "deserialize", derive(Deserialize))]172#[derive(Debug, PartialEq)]161#[derive(Debug, PartialEq)]173pub struct Arg(pub Option<String>, pub LocExpr);162pub struct Arg(pub Option<String>, pub LocExpr);174163175#[cfg_attr(feature = "dump", derive(Codegen))]176#[cfg_attr(feature = "serialize", derive(Serialize))]164#[cfg_attr(feature = "serialize", derive(Serialize))]177#[cfg_attr(feature = "deserialize", derive(Deserialize))]165#[cfg_attr(feature = "deserialize", derive(Deserialize))]178#[derive(Debug, PartialEq)]166#[derive(Debug, PartialEq)]184 }172 }185}173}186174187#[cfg_attr(feature = "dump", derive(Codegen))]188#[cfg_attr(feature = "serialize", derive(Serialize))]175#[cfg_attr(feature = "serialize", derive(Serialize))]189#[cfg_attr(feature = "deserialize", derive(Deserialize))]176#[cfg_attr(feature = "deserialize", derive(Deserialize))]190#[derive(Debug, Clone, PartialEq)]177#[derive(Debug, Clone, PartialEq)]191pub struct BindSpec {178pub struct BindSpec {192 pub name: Rc<str>,179 pub name: IStr,193 pub params: Option<ParamsDesc>,180 pub params: Option<ParamsDesc>,194 pub value: LocExpr,181 pub value: LocExpr,195}182}196183197#[cfg_attr(feature = "dump", derive(Codegen))]198#[cfg_attr(feature = "serialize", derive(Serialize))]184#[cfg_attr(feature = "serialize", derive(Serialize))]199#[cfg_attr(feature = "deserialize", derive(Deserialize))]185#[cfg_attr(feature = "deserialize", derive(Deserialize))]200#[derive(Debug, PartialEq)]186#[derive(Debug, PartialEq)]201pub struct IfSpecData(pub LocExpr);187pub struct IfSpecData(pub LocExpr);202188203#[cfg_attr(feature = "dump", derive(Codegen))]204#[cfg_attr(feature = "serialize", derive(Serialize))]189#[cfg_attr(feature = "serialize", derive(Serialize))]205#[cfg_attr(feature = "deserialize", derive(Deserialize))]190#[cfg_attr(feature = "deserialize", derive(Deserialize))]206#[derive(Debug, PartialEq)]191#[derive(Debug, PartialEq)]207pub struct ForSpecData(pub Rc<str>, pub LocExpr);192pub struct ForSpecData(pub IStr, pub LocExpr);208193209#[cfg_attr(feature = "dump", derive(Codegen))]210#[cfg_attr(feature = "serialize", derive(Serialize))]194#[cfg_attr(feature = "serialize", derive(Serialize))]211#[cfg_attr(feature = "deserialize", derive(Deserialize))]195#[cfg_attr(feature = "deserialize", derive(Deserialize))]212#[derive(Debug, PartialEq)]196#[derive(Debug, PartialEq)]215 ForSpec(ForSpecData),199 ForSpec(ForSpecData),216}200}217201218#[cfg_attr(feature = "dump", derive(Codegen))]219#[cfg_attr(feature = "serialize", derive(Serialize))]202#[cfg_attr(feature = "serialize", derive(Serialize))]220#[cfg_attr(feature = "deserialize", derive(Deserialize))]203#[cfg_attr(feature = "deserialize", derive(Deserialize))]221#[derive(Debug, PartialEq)]204#[derive(Debug, PartialEq)]227 pub compspecs: Vec<CompSpec>,210 pub compspecs: Vec<CompSpec>,228}211}229212230#[cfg_attr(feature = "dump", derive(Codegen))]231#[cfg_attr(feature = "serialize", derive(Serialize))]213#[cfg_attr(feature = "serialize", derive(Serialize))]232#[cfg_attr(feature = "deserialize", derive(Deserialize))]214#[cfg_attr(feature = "deserialize", derive(Deserialize))]233#[derive(Debug, PartialEq)]215#[derive(Debug, PartialEq)]236 ObjComp(ObjComp),218 ObjComp(ObjComp),237}219}238220239#[cfg_attr(feature = "dump", derive(Codegen))]240#[cfg_attr(feature = "serialize", derive(Serialize))]221#[cfg_attr(feature = "serialize", derive(Serialize))]241#[cfg_attr(feature = "deserialize", derive(Deserialize))]222#[cfg_attr(feature = "deserialize", derive(Deserialize))]242#[derive(Debug, PartialEq, Clone, Copy)]223#[derive(Debug, PartialEq, Clone, Copy)]257}238}258239259/// Syntax base240/// Syntax base260#[cfg_attr(feature = "dump", derive(Codegen))]261#[cfg_attr(feature = "serialize", derive(Serialize))]241#[cfg_attr(feature = "serialize", derive(Serialize))]262#[cfg_attr(feature = "deserialize", derive(Deserialize))]242#[cfg_attr(feature = "deserialize", derive(Deserialize))]263#[derive(Debug, PartialEq)]243#[derive(Debug, PartialEq)]264pub enum Expr {244pub enum Expr {265 Literal(LiteralType),245 Literal(LiteralType),266246267 /// String value: "hello"247 /// String value: "hello"268 Str(Rc<str>),248 Str(IStr),269 /// Number: 1, 2.0, 2e+20249 /// Number: 1, 2.0, 2e+20270 Num(f64),250 Num(f64),271 /// Variable name: test251 /// Variable name: test272 Var(Rc<str>),252 Var(IStr),273253274 /// Array of expressions: [1, 2, "Hello"]254 /// Array of expressions: [1, 2, "Hello"]275 Arr(Vec<LocExpr>),255 Arr(Vec<LocExpr>),316 /// function(x) x296 /// function(x) x317 Function(ParamsDesc, LocExpr),297 Function(ParamsDesc, LocExpr),318 /// std.primitiveEquals298 /// std.primitiveEquals319 Intrinsic(Rc<str>),299 Intrinsic(IStr),320 /// if true == false then 1 else 2300 /// if true == false then 1 else 2321 IfElse {301 IfElse {322 cond: IfSpecData,302 cond: IfSpecData,326}306}327307328/// file, begin offset, end offset308/// file, begin offset, end offset329#[cfg_attr(feature = "dump", derive(Codegen))]330#[cfg_attr(feature = "serialize", derive(Serialize))]309#[cfg_attr(feature = "serialize", derive(Serialize))]331#[cfg_attr(feature = "deserialize", derive(Deserialize))]310#[cfg_attr(feature = "deserialize", derive(Deserialize))]332#[derive(Clone, PartialEq)]311#[derive(Clone, PartialEq)]338}317}339318340/// Holds AST expression and its location in source file319/// Holds AST expression and its location in source file341#[cfg_attr(feature = "dump", derive(Codegen))]342#[cfg_attr(feature = "serialize", derive(Serialize))]320#[cfg_attr(feature = "serialize", derive(Serialize))]343#[cfg_attr(feature = "deserialize", derive(Deserialize))]321#[cfg_attr(feature = "deserialize", derive(Deserialize))]344#[derive(Clone, PartialEq)]322#[derive(Clone, PartialEq)]