Skip to content

Commit e4b523c

Browse files
committed
Add aiscript-common crate
1 parent bd8ee8d commit e4b523c

File tree

15 files changed

+160
-111
lines changed

15 files changed

+160
-111
lines changed

Cargo.lock

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

Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ members = [
33
"aiscript",
44
"aiscript-lexer",
55
"aiscript-arena",
6+
"aiscript-common",
67
"aiscript-derived",
78
"aiscript-directive",
89
"aiscript-runtime",

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -127,7 +127,7 @@ Configuration by `project.toml`:
127127
# use OpenAI
128128
[ai.openai]
129129
api_key = "YOUR_API_KEY"
130-
model = "gpt-3.5-turbo"
130+
model = "gpt-4"
131131

132132
# or use DeepSeek
133133
[ai.deepseek]

aiscript-common/Cargo.toml

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
[package]
2+
name = "aiscript-common"
3+
version.workspace = true
4+
edition.workspace = true
5+
homepage.workspace = true
6+
repository.workspace = true
7+
license.workspace = true
8+
authors.workspace = true
9+
keywords.workspace = true
10+
categories.workspace = true
11+
12+
[dependencies]
13+
serde.workspace = true

aiscript-common/src/lib.rs

Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
use std::{env, fmt::Display, ops::Deref};
2+
3+
use serde::Deserialize;
4+
5+
// Custom string type that handles environment variable substitution
6+
#[derive(Debug, Clone, Deserialize)]
7+
#[serde(from = "String")]
8+
pub struct EnvString(pub String);
9+
10+
impl From<String> for EnvString {
11+
fn from(s: String) -> Self {
12+
if let Some(env_key) = s.strip_prefix('$') {
13+
match env::var(env_key) {
14+
Ok(val) => EnvString(val),
15+
Err(_) => {
16+
// If env var is not found, use the original string
17+
// This allows for better error handling at runtime
18+
EnvString(s)
19+
}
20+
}
21+
} else {
22+
EnvString(s)
23+
}
24+
}
25+
}
26+
impl<'a> From<&'a str> for EnvString {
27+
fn from(s: &'a str) -> Self {
28+
if let Some(env_key) = s.strip_prefix('$') {
29+
match env::var(env_key) {
30+
Ok(val) => EnvString(val),
31+
Err(_) => {
32+
// If env var is not found, use the original string
33+
// This allows for better error handling at runtime
34+
EnvString(s.to_owned())
35+
}
36+
}
37+
} else {
38+
EnvString(s.to_owned())
39+
}
40+
}
41+
}
42+
43+
impl Display for EnvString {
44+
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
45+
write!(f, "{}", self.0)
46+
}
47+
}
48+
49+
impl From<EnvString> for String {
50+
fn from(s: EnvString) -> Self {
51+
s.0
52+
}
53+
}
54+
55+
impl Deref for EnvString {
56+
type Target = String;
57+
58+
fn deref(&self) -> &Self::Target {
59+
&self.0
60+
}
61+
}
62+
63+
impl AsRef<str> for EnvString {
64+
fn as_ref(&self) -> &str {
65+
&self.0
66+
}
67+
}
68+
69+
#[test]
70+
fn test_envstring_regular_value() {
71+
let regular = EnvString::from("regular_value".to_string());
72+
assert_eq!(regular.as_ref(), "regular_value");
73+
}
74+
75+
#[test]
76+
fn test_envstring_env_var_exists() {
77+
unsafe {
78+
env::set_var("TEST_ENV_VAR", "value_from_env");
79+
let env_string = EnvString::from("$TEST_ENV_VAR".to_string());
80+
assert_eq!(env_string.as_ref(), "value_from_env");
81+
env::remove_var("TEST_ENV_VAR");
82+
};
83+
}
84+
85+
#[test]
86+
fn test_envstring_env_var_not_exists() {
87+
unsafe { env::remove_var("NONEXISTENT_VAR") };
88+
let env_string = EnvString::from("$NONEXISTENT_VAR".to_string());
89+
assert_eq!(env_string.as_ref(), "$NONEXISTENT_VAR");
90+
}
91+
92+
#[test]
93+
fn test_envstring_dollar_in_middle() {
94+
let regular = EnvString::from("some$value".to_string());
95+
assert_eq!(regular.as_ref(), "some$value");
96+
}

aiscript-runtime/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ readme.workspace = true
1313

1414
[dependencies]
1515
aiscript-lexer = { path = "../aiscript-lexer", version = "0.2.0" }
16+
aiscript-common = { path = "../aiscript-common", version = "0.2.0" }
1617
aiscript-directive = { path = "../aiscript-directive", version = "0.2.0" }
1718
aiscript-vm = { path = "../aiscript-vm", version = "0.2.0" }
1819
hyper = "1.6"

aiscript-runtime/src/config/auth.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
use serde::Deserialize;
22

3-
use super::EnvString;
3+
use aiscript_common::EnvString;
44

55
#[derive(Debug, Deserialize, Default)]
66
pub struct AuthConfig {

aiscript-runtime/src/config/db.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
use serde::Deserialize;
22

3-
use super::EnvString;
3+
use aiscript_common::EnvString;
44

55
#[derive(Debug, Deserialize, Default)]
66
pub struct DatabaseConfig {

aiscript-runtime/src/config/mod.rs

Lines changed: 1 addition & 49 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use std::{env, fmt::Display, fs, ops::Deref, path::Path, sync::OnceLock};
1+
use std::{fs, path::Path, sync::OnceLock};
22

33
use auth::AuthConfig;
44
use serde::Deserialize;
@@ -15,54 +15,6 @@ mod tests;
1515

1616
static CONFIG: OnceLock<Config> = OnceLock::new();
1717

18-
// Custom string type that handles environment variable substitution
19-
#[derive(Debug, Clone, Deserialize)]
20-
#[serde(from = "String")]
21-
pub struct EnvString(String);
22-
23-
impl From<String> for EnvString {
24-
fn from(s: String) -> Self {
25-
if let Some(env_key) = s.strip_prefix('$') {
26-
match env::var(env_key) {
27-
Ok(val) => EnvString(val),
28-
Err(_) => {
29-
// If env var is not found, use the original string
30-
// This allows for better error handling at runtime
31-
EnvString(s)
32-
}
33-
}
34-
} else {
35-
EnvString(s)
36-
}
37-
}
38-
}
39-
40-
impl Display for EnvString {
41-
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
42-
write!(f, "{}", self.0)
43-
}
44-
}
45-
46-
impl From<EnvString> for String {
47-
fn from(s: EnvString) -> Self {
48-
s.0
49-
}
50-
}
51-
52-
impl Deref for EnvString {
53-
type Target = String;
54-
55-
fn deref(&self) -> &Self::Target {
56-
&self.0
57-
}
58-
}
59-
60-
impl AsRef<str> for EnvString {
61-
fn as_ref(&self) -> &str {
62-
&self.0
63-
}
64-
}
65-
6618
#[derive(Debug, Deserialize, Default)]
6719
pub struct Config {
6820
#[serde(default)]

aiscript-runtime/src/config/sso.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
11
use std::collections::HashMap;
22

3+
use aiscript_common::EnvString;
34
use aiscript_directive::route::SsoProvider;
45
use serde::Deserialize;
56

6-
use super::{Config, EnvString};
7+
use super::Config;
78

89
#[derive(Debug, Deserialize, Default)]
910
pub struct SsoConfig {

aiscript-runtime/src/config/tests.rs

Lines changed: 1 addition & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -1,35 +1,6 @@
1-
use crate::{Config, config::EnvString};
1+
use crate::Config;
22
use std::env;
33

4-
#[test]
5-
fn test_envstring_regular_value() {
6-
let regular = EnvString::from("regular_value".to_string());
7-
assert_eq!(regular.as_ref(), "regular_value");
8-
}
9-
10-
#[test]
11-
fn test_envstring_env_var_exists() {
12-
unsafe {
13-
env::set_var("TEST_ENV_VAR", "value_from_env");
14-
let env_string = EnvString::from("$TEST_ENV_VAR".to_string());
15-
assert_eq!(env_string.as_ref(), "value_from_env");
16-
env::remove_var("TEST_ENV_VAR");
17-
};
18-
}
19-
20-
#[test]
21-
fn test_envstring_env_var_not_exists() {
22-
unsafe { env::remove_var("NONEXISTENT_VAR") };
23-
let env_string = EnvString::from("$NONEXISTENT_VAR".to_string());
24-
assert_eq!(env_string.as_ref(), "$NONEXISTENT_VAR");
25-
}
26-
27-
#[test]
28-
fn test_envstring_dollar_in_middle() {
29-
let regular = EnvString::from("some$value".to_string());
30-
assert_eq!(regular.as_ref(), "some$value");
31-
}
32-
334
#[test]
345
fn test_config_with_env_vars() {
356
unsafe {

aiscript-vm/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ readme.workspace = true
1313

1414
[dependencies]
1515
aiscript-lexer = { path = "../aiscript-lexer", version = "0.2.0" }
16+
aiscript-common = { path = "../aiscript-common", version = "0.2.0" }
1617
aiscript-directive = { path = "../aiscript-directive", version = "0.2.0" }
1718
aiscript-arena = { path = "../aiscript-arena", version = "0.1.0", features = [
1819
"allocator-api2",

aiscript-vm/src/ai/agent.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -293,7 +293,7 @@ pub async fn _run_agent<'gc>(
293293
loop {
294294
let mut messages = vec![agent.get_instruction_message()];
295295
messages.extend(history.clone());
296-
let mut req = ChatCompletionRequest::new(model.clone(), messages);
296+
let mut req = ChatCompletionRequest::new(model.0.clone(), messages);
297297
let tools = agent.get_tools();
298298
if !tools.is_empty() {
299299
req = req

0 commit comments

Comments
 (0)