From e79e44c0dff0010d702b22d9ec2c4df8d86b711c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jonas=20R=C3=B6ger?= Date: Sun, 10 Nov 2024 16:14:37 +0100 Subject: [PATCH] feat: add repl bin --- .envrc | 18 +++++++- Cargo.toml | 8 ++++ flake.nix | 91 +++++++++++++++++++++++----------------- src/{main.rs => demo.rs} | 0 src/repl.rs | 33 +++++++++++++++ 5 files changed, 111 insertions(+), 39 deletions(-) rename src/{main.rs => demo.rs} (100%) create mode 100644 src/repl.rs diff --git a/.envrc b/.envrc index 3550a30..412cbef 100644 --- a/.envrc +++ b/.envrc @@ -1 +1,17 @@ -use flake +#!/usr/bin/env bash +# ^ make editor happy + +# +# Use https://direnv.net/ to automatically load the dev shell. +# + +if ! has nix_direnv_version || ! nix_direnv_version 3.0.4; then + source_url "https://raw.githubusercontent.com/nix-community/nix-direnv/3.0.4/direnvrc" "sha256-DzlYZ33mWF/Gs8DDeyjr8mnVmQGx7ASYqA5WlxwvBG4=" +fi + +watch_file nix/** +watch_file -- **/*.nix +# Adding files to git includes them in a flake +# But it is also a bit much reloading. +# watch_file .git/index .git/HEAD +use flake . --show-trace diff --git a/Cargo.toml b/Cargo.toml index 1eeca67..0298a59 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -6,6 +6,14 @@ version = "0.1.0" edition = "2021" +[[bin]] +name = "demo" +path = "src/demo.rs" + +[[bin]] +name = "repl" +path = "src/repl.rs" + [dependencies] as-any = "0.3.1" futures = "0.3.30" diff --git a/flake.nix b/flake.nix index 9750be3..7419e88 100644 --- a/flake.nix +++ b/flake.nix @@ -18,17 +18,20 @@ }; nixConfig = { + extra-trusted-public-keys = "eigenvalue.cachix.org-1:ykerQDDa55PGxU25CETy9wF6uVDpadGGXYrFNJA3TUs="; + extra-substituters = "https://eigenvalue.cachix.org"; allow-import-from-derivation = true; }; - outputs = - inputs @ { self - , nixpkgs - , flake-parts - , rust-overlay - , crate2nix - , ... - }: flake-parts.lib.mkFlake { inherit inputs; } { + outputs = inputs @ { + self, + nixpkgs, + flake-parts, + rust-overlay, + crate2nix, + ... + }: + flake-parts.lib.mkFlake {inherit inputs;} { systems = [ "x86_64-linux" "aarch64-linux" @@ -41,37 +44,49 @@ ./nix/devshell/flake-module.nix ]; - perSystem = { system, pkgs, lib, inputs', ... }: - let - # If you dislike IFD, you can also generate it with `crate2nix generate` - # on each dependency change and import it here with `import ./Cargo.nix`. - cargoNix = inputs.crate2nix.tools.${system}.appliedCargoNix { - name = "rustnix"; - src = ./.; - }; - in - rec { - checks = { - rustnix = cargoNix.rootCrate.build.override { - runTests = true; - }; - }; - - packages = rec { - rustnix = cargoNix.rootCrate.build; - default = packages.rustnix; - dockerImage = pkgs.dockerTools.buildImage { - name = "lispers"; - config = { Cmd = [ "${rustnix}/bin/lispers" ]; }; - }; - - inherit (pkgs) rust-toolchain; - - rust-toolchain-versions = pkgs.writeScriptBin "rust-toolchain-versions" '' - ${pkgs.rust-toolchain}/bin/cargo --version - ${pkgs.rust-toolchain}/bin/rustc --version - ''; + perSystem = { + system, + pkgs, + lib, + inputs', + ... + }: let + # If you dislike IFD, you can also generate it with `crate2nix generate` + # on each dependency change and import it here with `import ./Cargo.nix`. + cargoNix = inputs.crate2nix.tools.${system}.appliedCargoNix { + name = "rustnix"; + src = ./.; + }; + in rec { + checks = { + rustnix = cargoNix.rootCrate.build.override { + runTests = true; }; }; + + apps = rec { + demo = { + type = "app"; + program = "${packages.default}/bin/demo"; + }; + repl = { + type = "app"; + program = "${packages.default}/bin/repl"; + }; + default = demo; + }; + + packages = { + rustnix = cargoNix.rootCrate.build; + default = packages.rustnix; + + inherit (pkgs) rust-toolchain; + + rust-toolchain-versions = pkgs.writeScriptBin "rust-toolchain-versions" '' + ${pkgs.rust-toolchain}/bin/cargo --version + ${pkgs.rust-toolchain}/bin/rustc --version + ''; + }; + }; }; } diff --git a/src/main.rs b/src/demo.rs similarity index 100% rename from src/main.rs rename to src/demo.rs diff --git a/src/repl.rs b/src/repl.rs new file mode 100644 index 0000000..0d22f28 --- /dev/null +++ b/src/repl.rs @@ -0,0 +1,33 @@ +use lisp::Expression; +use parser::ParserError; + +use std::io::Write; +mod parser; +mod lisp; + +fn main() { + let env = lisp::Environment::default(); + + loop { + print!("> "); + std::io::stdout().flush().unwrap(); + + let mut input = String::new(); + if std::io::stdin().read_line(&mut input).unwrap() == 0 { + println!("Exiting REPL..."); + break; + } + + match parser::ExpressionStream::from_char_stream(input.chars()).collect::, ParserError>>() { + Err(e) => println!("Parser Error: {:?}", e), + Ok(exprs) => { + for expr in exprs { + match lisp::eval(&env, expr) { + Err(e) => println!("Eval Error: {}", e), + Ok(val) => println!("{}", val), + } + } + } + } + } +}