Skip to content

Commit 16eb018

Browse files
committed
Add just smoke while fix doc tests
- core: Add DbC for `Transition` via static_assert - core: Refactor `TransitionIterator` a bit - Fix deprecate trait-object without `dyn`
1 parent 0b58caf commit 16eb018

File tree

12 files changed

+94
-34
lines changed

12 files changed

+94
-34
lines changed

Cargo.lock

Lines changed: 7 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Justfile

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ check: clear
1818
watchexec --restart --clear 'just {{command}} {{args}}'
1919

2020
# Run all kind of tests
21-
test: unit integration
21+
test: unit integration smoke
2222

2323
# Generate and open the documentation
2424
docs +args='':
@@ -63,14 +63,20 @@ release version:
6363
build args='':
6464
cargo build {{args}}
6565

66-
# Run all unit test
66+
# Run all unit tests
6767
unit:
6868
cargo test --lib --all --exclude s-crap -- --test-threads=1
6969

70-
# Run all integration test
70+
# Run all integration tests
7171
integration:
7272
cargo test --tests -p s-crap -- --test-threads=1
7373

74+
# Run all examples and doc-tests
75+
smoke:
76+
cargo test --doc --all --exclude s-crap
77+
cargo test --examples
78+
# TODO: `mask --maskfile examples/xstate/nodejs/maskfile.md start` should link `scrap` to target/debug/scrap
79+
7480
# Show reports of macro-benchmark
7581
@stats git-flags='':
7682
./scripts/summary.sh {{git-flags}} | ./scripts/perfsum.py

packages/cli/Cargo.toml

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,8 @@ edition = "2018"
1212
[[bin]]
1313
name = "scrap"
1414
path = "src/main.rs"
15-
test = false
15+
test = false # TODO: remove integration test and replace it with evlish or bats
16+
# CLI tests should be readable and close to shell scripting environment
1617
doc = false
1718
doctest = false
1819

packages/core/Cargo.toml

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,10 +11,13 @@ categories = ["parsing"]
1111
edition = "2018"
1212

1313
[dependencies]
14+
# parser + context-free-grammar
1415
pest = "2"
1516
pest_derive = "2"
16-
lazy_static = "1"
17-
either = "1"
17+
# helper
18+
lazy_static = "1" # to define the global caches
19+
either = "1" # a workaround for iterator.filter that return Result<Vec, _>
20+
static_assertions = "0.3" # design-by-contract at compile time
1821

1922
[badges]
2023
maintenance = { status = "actively-developed" }

packages/core/src/core/builder.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ use crate::{cache, error::Error, external::Builder};
22
use pest_derive::Parser;
33
use std::collections::HashMap;
44

5-
#[derive(Parser, Default, Clone)] // 🤔 is it wise to derive from Copy&Clone ?
5+
#[derive(Debug, Parser, Default, Clone)] // 🤔 is it wise to derive from Copy&Clone ?
66
#[grammar = "grammar.pest"]
77
/** __Core__ parser and also [`Builder`].
88

packages/core/src/core/parser.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,12 @@ use std::{fmt, *};
1111
1212
# Examples
1313
```
14+
# use std::error::Error;
15+
use scdlang::parse;
16+
1417
let token_pairs = parse("A -> B")?;
15-
println("{:#?}", token_pairs);
18+
println!("{:#?}", token_pairs);
19+
# Ok::<(), Box<dyn Error>>(())
1620
``` */
1721
pub fn parse(source: &str) -> Result<Pairs<Rule>, RuleError> {
1822
<Scdlang as pest::Parser<Rule>>::parse(Rule::DescriptionFile, source)

packages/core/src/external.rs

Lines changed: 21 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,19 @@ Useful for creating transpiler, codegen, or even compiler.
55
66
1. Implement trait [`Parser`] on struct with [`Scdlang`] field (or any type that implement [`Builder`]).
77
```no_run
8-
#[derive(Default)]
8+
use scdlang::{*, prelude::*};
9+
use std::{error, fmt};
10+
pub mod prelude {
11+
pub use scdlang::external::*;
12+
}
13+
14+
#[derive(Debug, Default)]
15+
struct Schema {}
16+
17+
#[derive(Debug, Default)]
918
pub struct Machine<'a> {
1019
builder: Scdlang<'a>, // or any type that implmenet trait `Builder`
11-
schema: std::any::Any,
20+
schema: Schema,
1221
}
1322
1423
impl Machine<'_> {
@@ -20,12 +29,18 @@ impl Machine<'_> {
2029
}
2130
}
2231
32+
impl fmt::Display for Machine<'_> {
33+
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
34+
write!(f, "{:?}", self.schema)
35+
}
36+
}
37+
2338
impl<'a> Parser<'a> for Machine<'a> {
24-
fn configure(&mut self) -> &mut Builder<'a> {
39+
fn configure(&mut self) -> &mut dyn Builder<'a> {
2540
&mut self.builder
2641
}
2742
28-
fn parse(&mut self, source: &str) -> Result<(), DynError> {
43+
fn parse(&mut self, source: &str) -> Result<(), Box<dyn error::Error>> {
2944
self.clean_cache()?;
3045
unimplemented!();
3146
}
@@ -42,6 +57,8 @@ impl<'a> Parser<'a> for Machine<'a> {
4257
4358
2. Then it can be used like this:
4459
```ignore
60+
use scdlang::external::*;
61+
4562
let parser: Box<dyn Parser> = Box::new(match args {
4663
Some(text) => module_a::Machine::try_parse(text)?,
4764
None => module_b::Machine::new(),

packages/core/src/semantics/kind.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
use crate::{utils::naming::Name, Error};
22
use std::{any::Any, fmt::Debug};
33

4+
// TODO: test this in BDD style (possibly via cucumber-rust)
5+
46
#[derive(Debug)]
57
/// An enum returned by [Scdlang.iter_from](../struct.Scdlang.html#method.iter_from)
68
/// to access semantics type/kind
@@ -69,6 +71,6 @@ A |> doSomething
6971
or just a shorthand for writing a declaration in one line */
7072
pub trait Statement: Debug + Check {
7173
fn state(&self) -> Option<Name>;
72-
fn action(&self) -> Option<&Any /*👈TBD*/>;
74+
fn action(&self) -> Option<&dyn Any /*👈TBD*/>;
7375
fn event(&self) -> Option<Name>;
7476
}

packages/core/src/semantics/transition/iter.rs

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -9,26 +9,26 @@ impl<'i> IntoIterator for Transition<'i> {
99
fn into_iter(mut self) -> Self::IntoIter {
1010
TransitionIterator(match self.kind {
1111
/*FIXME: iterator for internal transition*/
12-
TransitionType::Normal | TransitionType::Internal => [self].to_vec(),
12+
TransitionType::Normal | TransitionType::Internal => vec![self],
1313
TransitionType::Toggle => {
1414
self.kind = TransitionType::Normal;
1515
let (mut left, right) = (self.clone(), self);
1616
left.from = right.to.clone().expect("not Internal");
17-
left.to = Some(right.from.clone());
18-
[left, right].to_vec()
17+
left.to = right.from.clone().into();
18+
vec![left, right]
1919
}
2020
TransitionType::Loop { transient } => {
2121
/* A ->> B @ C */
2222
if self.from.name != self.to.as_ref().expect("not Internal").name {
2323
let (mut self_loop, mut normal) = (self.clone(), self);
2424
self_loop.from = self_loop.to.as_ref().expect("not Internal").clone();
2525
normal.kind = TransitionType::Normal;
26-
normal.at = if transient { None } else { normal.at };
27-
[normal, self_loop].to_vec()
26+
normal.at = normal.at.filter(|_| !transient);
27+
vec![normal, self_loop]
2828
}
2929
/* ->> B @ C */
3030
else {
31-
[self].to_vec() // reason: see Symbol::double_arrow::right => (..) in convert.rs
31+
vec![self] // reason: see Symbol::double_arrow::right => (..) in convert.rs
3232
}
3333
}
3434
TransitionType::Inside { .. } => unreachable!("TODO: when support StateType::Compound"),
@@ -63,6 +63,6 @@ where
6363
where
6464
T: IntoIterator<Item = Transition<'i>>,
6565
{
66-
unimplemented!("TODO: on the next update")
66+
unimplemented!("TODO: on the next update when const generic is stabilized")
6767
}
6868
}

packages/core/src/semantics/transition/mod.rs

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,18 @@ mod helper;
44
mod iter;
55

66
use crate::{
7-
semantics::{analyze::SemanticCheck, Check, Expression, Found, Kind, Transition},
7+
semantics::{analyze::*, Check, Expression, Found, Kind, Transition},
88
utils::naming::Name,
99
Error,
1010
};
11+
use static_assertions::assert_impl_all;
12+
13+
assert_impl_all!(r#for; Transition,
14+
SemanticAnalyze<'static>,
15+
SemanticCheck,
16+
From<TokenPair<'static>>,
17+
IntoIterator // because `A <-> B` can be desugared into 2 transition
18+
);
1119

1220
impl Expression for Transition<'_> {
1321
fn current_state(&self) -> Name {
@@ -252,7 +260,7 @@ mod pair {
252260
A -> F @ D
253261
A -> C @ D[exist]
254262
"#,
255-
|expression| unimplemented!(),
263+
|_expression| unimplemented!(),
256264
)
257265
}
258266

@@ -265,7 +273,7 @@ mod pair {
265273
A -> F
266274
A -> C @ [exist]
267275
"#,
268-
|expression| unimplemented!(),
276+
|_expression| unimplemented!(),
269277
)
270278
}
271279

@@ -279,7 +287,7 @@ mod pair {
279287
A -> C @ [exist]
280288
A -> C @ E
281289
"#,
282-
|expression| unimplemented!(),
290+
|_expression| unimplemented!(),
283291
)
284292
}
285293

@@ -372,7 +380,7 @@ mod pair {
372380
A -> B @ D[valid]
373381
A -> B @ D
374382
"#,
375-
|expression| unimplemented!(),
383+
|_expression| unimplemented!(),
376384
)
377385
}
378386
}

0 commit comments

Comments
 (0)