intuicio_frontend_simpleton/library/
net.rs1use super::bytes::Bytes;
2use crate::{Boolean, Integer, Reference, Text};
3use intuicio_core::{registry::Registry, IntuicioStruct};
4use intuicio_derive::{intuicio_method, intuicio_methods, IntuicioStruct};
5use std::{
6 io::{Read, Write},
7 net::{TcpListener, TcpStream},
8};
9
10#[derive(IntuicioStruct, Default)]
11#[intuicio(name = "Server", module_name = "net_server")]
12pub struct Server {
13 #[intuicio(ignore)]
14 listener: Option<TcpListener>,
15}
16
17#[intuicio_methods(module_name = "net_server")]
18impl Server {
19 #[allow(clippy::new_ret_no_self)]
20 #[intuicio_method(use_registry)]
21 pub fn new(registry: &Registry, address: Reference) -> Reference {
22 let address = address.read::<Text>().unwrap();
23 Reference::new(
24 Server {
25 listener: Some(TcpListener::bind(address.as_str()).unwrap()),
26 },
27 registry,
28 )
29 }
30
31 #[intuicio_method(use_registry)]
32 pub fn set_nonblocking(registry: &Registry, server: Reference, mode: Reference) -> Reference {
33 let server = server.read::<Server>().unwrap();
34 let mode = *mode.read::<Boolean>().unwrap();
35 Reference::new_boolean(
36 server
37 .listener
38 .as_ref()
39 .unwrap()
40 .set_nonblocking(mode)
41 .is_ok(),
42 registry,
43 )
44 }
45
46 #[intuicio_method(use_registry)]
47 pub fn accept(registry: &Registry, server: Reference) -> Reference {
48 let server = server.read::<Server>().unwrap();
49 if let Ok((stream, _)) = server.listener.as_ref().unwrap().accept() {
50 Reference::new(
51 Channel {
52 stream: Some(stream),
53 },
54 registry,
55 )
56 } else {
57 Reference::null()
58 }
59 }
60}
61
62#[derive(IntuicioStruct, Default)]
63#[intuicio(name = "Channel", module_name = "net_channel")]
64pub struct Channel {
65 #[intuicio(ignore)]
66 stream: Option<TcpStream>,
67}
68
69#[intuicio_methods(module_name = "net_channel")]
70impl Channel {
71 #[intuicio_method(use_registry)]
72 pub fn connect(registry: &Registry, address: Reference) -> Reference {
73 let address = address.read::<Text>().unwrap();
74 let stream = TcpStream::connect(address.as_str()).unwrap();
75 Reference::new(
76 Channel {
77 stream: Some(stream),
78 },
79 registry,
80 )
81 }
82
83 #[intuicio_method(use_registry)]
84 pub fn set_nonblocking(registry: &Registry, channel: Reference, mode: Reference) -> Reference {
85 let channel = channel.read::<Channel>().unwrap();
86 let mode = *mode.read::<Boolean>().unwrap();
87 Reference::new_boolean(
88 channel
89 .stream
90 .as_ref()
91 .unwrap()
92 .set_nonblocking(mode)
93 .is_ok(),
94 registry,
95 )
96 }
97
98 #[intuicio_method(use_registry)]
99 pub fn set_no_delay(registry: &Registry, channel: Reference, mode: Reference) -> Reference {
100 let channel = channel.read::<Channel>().unwrap();
101 let mode = *mode.read::<Boolean>().unwrap();
102 Reference::new_boolean(
103 channel.stream.as_ref().unwrap().set_nodelay(mode).is_ok(),
104 registry,
105 )
106 }
107
108 #[intuicio_method(use_registry)]
109 pub fn read(registry: &Registry, mut channel: Reference, size: Reference) -> Reference {
110 let mut channel = channel.write::<Channel>().unwrap();
111 let size = *size.read::<Integer>().unwrap() as usize;
112 let mut result = vec![0; size];
113 if channel.stream.as_mut().unwrap().read(&mut result).is_ok() {
114 Reference::new(Bytes::new_raw(result), registry)
115 } else {
116 Reference::null()
117 }
118 }
119
120 #[intuicio_method(use_registry)]
121 pub fn write(registry: &Registry, mut channel: Reference, buffer: Reference) -> Reference {
122 let mut channel = channel.write::<Channel>().unwrap();
123 let buffer = buffer.read::<Bytes>().unwrap();
124 Reference::new_boolean(
125 channel
126 .stream
127 .as_mut()
128 .unwrap()
129 .write(buffer.get_ref())
130 .is_ok(),
131 registry,
132 )
133 }
134}
135
136pub fn install(registry: &mut Registry) {
137 registry.add_type(Server::define_struct(registry));
138 registry.add_function(Server::new__define_function(registry));
139 registry.add_function(Server::set_nonblocking__define_function(registry));
140 registry.add_function(Server::accept__define_function(registry));
141 registry.add_type(Channel::define_struct(registry));
142 registry.add_function(Channel::connect__define_function(registry));
143 registry.add_function(Channel::set_nonblocking__define_function(registry));
144 registry.add_function(Channel::set_no_delay__define_function(registry));
145 registry.add_function(Channel::read__define_function(registry));
146 registry.add_function(Channel::write__define_function(registry));
147}