Skip to content

Commit

Permalink
Merge pull request #163 from MartinFillon/add-proc-macros
Browse files Browse the repository at this point in the history
Add bean proc macros
  • Loading branch information
MartinFillon authored Jun 4, 2024
2 parents 187fb5e + 3ebbcb5 commit 5b62050
Show file tree
Hide file tree
Showing 7 changed files with 89 additions and 43 deletions.
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
[workspace]

members = ["server/tests/server-tester", "ai"]
members = ["server/tests/server-tester", "ai", "rust-macros/"]
resolver = "2"
1 change: 1 addition & 0 deletions ai/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,4 @@ tokio = { version = "1", features = ["full"] }
async-trait = "0.1.8"
env_logger = "0.11"
log = "0.4"
rust-macros = { path = "../rust-macros" }
45 changes: 6 additions & 39 deletions ai/src/flags.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,52 +17,19 @@ use std::fmt;
use std::fmt::{Display, Formatter};

use log::info;
use rust_macros::Bean;

const LOCALHOST: &str = "127.0.0.1";

const SUCCESS_CODE: i32 = 0;

#[derive(Debug, Clone)]
#[derive(Debug, Clone, Bean)]
pub struct Flags {
port: Option<usize>,
name: Option<String>,
machine: String,
}

impl Flags {
fn set_port(&mut self, port: usize) {
self.port = Some(port)
}

fn set_name(&mut self, name: String) {
self.name = Some(name)
}

fn set_machine(&mut self, machine: String) {
self.machine = machine
}

fn is_port_none(&self) -> bool {
self.port.is_none()
}

fn is_name_none(&self) -> bool {
self.name.is_none()
}

pub fn get_name(self) -> String {
self.name.unwrap_or_default()
}

pub fn get_port(self) -> usize {
self.port.unwrap_or_default()
}

pub fn get_machine(self) -> String {
self.machine
}
}

impl Default for Flags {
fn default() -> Flags {
Flags {
Expand Down Expand Up @@ -106,7 +73,7 @@ fn get_port_from_args(
) -> Result<(), String> {
let port: usize = parse_arg(arg_type, args.next())?;
info!("Setting port to: {}.", port);
flags_struct.set_port(port);
flags_struct.set_port(Some(port));
Ok(())
}

Expand All @@ -117,7 +84,7 @@ fn get_name_from_args(
) -> Result<(), String> {
let name: String = parse_arg(arg_type, args.next())?;
info!("Setting name to: {}.", name);
flags_struct.set_name(name);
flags_struct.set_name(Some(name));
Ok(())
}

Expand Down Expand Up @@ -158,10 +125,10 @@ fn get_flags() -> Result<Flags, String> {

pub fn check_flags() -> Result<Flags, String> {
let flags = get_flags()?;
if flags.is_port_none() {
if flags.port().is_none() {
return Err(String::from("Port is not set."));
}
if flags.is_name_none() {
if flags.name().is_none() {
return Err(String::from("Name is not set."));
}
Ok(flags)
Expand Down
9 changes: 6 additions & 3 deletions ai/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,12 @@ async fn main() {
match flags::check_flags() {
Ok(res) => {
info!("Arguments set:\n{}", res.clone());
let address: String =
format!("{}:{}", res.clone().get_machine(), res.clone().get_port());
match ai::launch(address, res.get_name()).await {
let address: String = format!(
"{}:{}",
res.clone().machine(),
res.clone().port().unwrap_or_default()
);
match ai::launch(address, res.name().clone().unwrap_or_default()).await {
Ok(_) => process::exit(SUCCESS_CODE),
Err(e) => {
eprintln!("Error: {}.", e);
Expand Down
2 changes: 2 additions & 0 deletions ai/src/tcp.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@

#![allow(dead_code)]

use rust_macros::Bean;
use std::io::{Error, ErrorKind};
use tokio::io::{self, AsyncReadExt, AsyncWriteExt, BufReader};
use tokio::net::tcp::{OwnedReadHalf, OwnedWriteHalf};
Expand All @@ -19,6 +20,7 @@ use log::{debug, info};

pub mod command_handle;

#[derive(Debug, Bean)]
pub struct TcpClient {
addr: String,
request_sender: Option<Sender<String>>,
Expand Down
14 changes: 14 additions & 0 deletions rust-macros/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
[package]
name = "rust-macros"
version = "0.1.0"
edition = "2021"

# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html

[lib]
proc-macro = true

[dependencies]
syn = {}
quote = {}
proc-macro2 = {}
59 changes: 59 additions & 0 deletions rust-macros/src/lib.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
extern crate proc_macro;

use proc_macro::TokenStream;
use quote::quote;
use syn::{Data, DeriveInput, Fields, FieldsNamed};

fn get_fields(data: &Data) -> FieldsNamed {
if let Data::Struct(strct) = data {
if let Fields::Named(fields) = &strct.fields {
fields.to_owned()
} else {
panic!("Can only handle named fields")
}
} else {
panic!("Can only handle structs");
}
}

fn impl_bean(ast: DeriveInput) -> TokenStream {
let ident = ast.ident;
let fields = get_fields(&ast.data);
let setters = fields.named.iter().map(|field| {
let name = field.ident.as_ref().unwrap();
let ty = &field.ty;
let f_name: proc_macro2::TokenStream = format!("set_{}", name).parse().unwrap();
let function_signature = quote!(pub fn #f_name (&mut self, input: #ty));
quote!(
#function_signature {
self.#name = input;
}
)
});

let getters = fields.named.iter().map(|field| {
let name = field.ident.as_ref().unwrap();
let ty = &field.ty;
let function_signature = quote!(pub fn #name (&self) -> &#ty);
quote!(
#function_signature {
&self.#name
}
)
});

quote! {
impl #ident {
#(#setters)*
#(#getters)*
}
}
.into()
}

#[proc_macro_derive(Bean)]
pub fn my_macro_here_derive(input: TokenStream) -> TokenStream {
let ast: DeriveInput = syn::parse(input).unwrap();

impl_bean(ast)
}

0 comments on commit 5b62050

Please sign in to comment.