maybe migration

This commit is contained in:
me 2025-12-19 13:05:08 +02:00
parent 08cb1109c7
commit c51a7fd0fc
6 changed files with 113 additions and 15 deletions

View file

@ -204,7 +204,8 @@ impl Record {
}
}
pub const UNIT: Expr = Expr::Value(Value::Record(Record(BTreeMap::new())));
pub const UNIT_VALUE: Value = Value::Record(Record(BTreeMap::new()));
pub const UNIT: Expr = Expr::Value(UNIT_VALUE);
#[derive(PartialEq, Debug, thiserror::Error)]
pub enum Error {

View file

@ -5,29 +5,44 @@ use std::collections::BTreeMap;
use crate::ast;
pub fn run(
program: ast::Program,
pub fn global_env_name() -> ast::EnvName {
ast::EnvName("global".to_string())
}
pub fn setup(program: ast::Program) -> Result<State, Error> {
let mut state = State::new(global_env_name().0.clone());
defs_to_env(program.0, &global_env_name(), &mut state)?;
Ok(state)
}
pub fn interpret(
state: &mut State,
func: ast::Name,
args: Vec<ast::Expr>,
) -> Result<ast::Value, Error> {
let env_name = ast::EnvName("global".to_string());
let mut state = State::new("global".into());
defs_to_env(program.0, &env_name, &mut state)?;
let main = ast::Expr::Value(state.envs.get(&env_name)?.get(&func)?.clone());
let main = ast::Expr::Value(state.envs.get(&global_env_name())?.get(&func)?.clone());
let expr = ast::Expr::FunCall {
func: Box::new(main),
args,
};
let env: Env = state.envs.get(&env_name)?.clone();
let result = eval_expr(&env, &mut state, &expr)?;
let env: Env = state.envs.get(&global_env_name())?.clone();
let result = eval_expr(&env, state, &expr)?;
Ok(result)
}
pub fn run(
program: ast::Program,
func: ast::Name,
args: Vec<ast::Expr>,
) -> Result<ast::Value, Error> {
let mut state = setup(program)?;
interpret(&mut state, func, args)
}
enum StatementResult {
Result(ast::Value),
Return(ast::Value),
@ -230,6 +245,33 @@ fn defs_to_env(
Ok(())
}
pub fn value_to_stadnalone_expr(state: &State, value: ast::Value) -> Result<ast::Expr, String> {
match value {
ast::Value::Ref(reference) => {
let value = state.variables.get(&reference).clone();
value_to_stadnalone_expr(state, value)
}
ast::Value::Vector(vector) => {
let mut vec = Vec::with_capacity(vector.0.len());
for reference in vector.0 {
let expr = value_to_stadnalone_expr(state, ast::Value::Ref(reference))?;
vec.push(expr);
}
Ok(ast::Expr::Vector(vec))
}
ast::Value::Record(record) => {
let mut map = BTreeMap::new();
for (field, reference) in record.0 {
let expr = value_to_stadnalone_expr(state, ast::Value::Ref(reference))?;
map.insert(field.clone(), expr);
}
Ok(ast::Expr::Record(map))
}
ast::Value::Closure { .. } => Err("Closure migration not supported".into()),
_ => Ok(ast::Expr::Value(value)),
}
}
#[cfg(test)]
mod tests {
use super::*;

View file

@ -4,3 +4,4 @@ pub mod interpret;
pub mod types;
pub use interpret::*;
pub use types::*;

View file

@ -1,3 +1,4 @@
use ayin::ast;
use ayin::runtime::*;
use macroquad::prelude::*;
@ -16,7 +17,7 @@ async fn main() {
env_logger::init();
info!("Hello, 👁️‍🗨️!");
let mut state = setup().await;
let mut state = setup(ast::Program(vec![])).await;
loop {
let events = fetch_events();

View file

@ -1,13 +1,64 @@
use super::types::*;
use crate::ast;
use crate::interpret;
use macroquad::prelude::*;
pub async fn setup() -> State {
pub async fn setup(code: ast::Program) -> State {
let font = load_ttf_font("./assets/fonts/monogram.ttf").await.unwrap();
let mut state = match interpret::setup(code) {
Ok(state) => state,
Err(err) => {
println!("Error: {}", err);
interpret::State::new("game".into())
}
};
let game_state = match interpret::interpret(&mut state, "setup".into(), vec![]) {
Ok(result) => result,
Err(err) => {
println!("Error: {}", err);
ast::UNIT_VALUE
}
};
State {
assets: Assets { font },
code: ast::Program(vec![]),
state,
game_state,
}
}
pub async fn migrate(mut state: State, code: ast::Program) -> State {
match interpret::setup(code) {
Err(err) => {
println!("Error: {}", err);
state
}
Ok(mut new_program_state) => {
match interpret::value_to_stadnalone_expr(&state.state, state.game_state.clone()) {
Err(err) => {
println!("Error: {}", err);
state
}
Ok(expanded_game_state) => {
match interpret::interpret(
&mut new_program_state,
"migrate".into(),
vec![expanded_game_state],
) {
Err(err) => {
println!("Error: {}", err);
state
}
Ok(result) => {
state.game_state = result;
state.state = new_program_state;
state
}
}
}
}
}
}
}

View file

@ -1,9 +1,11 @@
use crate::ast;
use crate::interpret;
use macroquad::prelude::*;
pub struct State {
pub assets: Assets,
pub code: ast::Program,
pub state: interpret::types::State,
pub game_state: ast::Value,
}
pub struct Assets {