Skip to content

Feat/basis html commands #4

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 10 commits into from
Jun 13, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
138 changes: 138 additions & 0 deletions src/code.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,138 @@
use std::{fs::File, io::Read};

use brack_sdk_rs::{MetaData, Type, Value};
use extism_pdk::{plugin_fn, FnResult, Json, WithReturnCode};

#[plugin_fn]
pub fn metadata_inline_code() -> FnResult<Json<MetaData>> {
Ok(Json(MetaData {
command_name: "$".to_string(),
call_name: "inline_code".to_string(),
argument_types: vec![
("src".to_string(), Type::TInline),
(
"language".to_string(),
Type::TOption(Box::new(Type::TInline)),
),
],
return_type: Type::TInline,
}))
}

#[plugin_fn]
pub fn metadata_block_code() -> FnResult<Json<MetaData>> {
Ok(Json(MetaData {
command_name: "$".to_string(),
call_name: "block_quote".to_string(),
argument_types: vec![
("src".to_string(), Type::TInline),
(
"language".to_string(),
Type::TOption(Box::new(Type::TInline)),
),
],
return_type: Type::TBlock,
}))
}

#[plugin_fn]
pub fn inline_code(Json(args): Json<Vec<Value>>) -> FnResult<String> {
if args.len() != 2 {
return Err(WithReturnCode::new(
anyhow::anyhow!(
"Usage:
1. [std.$ src]
2. [std.$ src, language]"
),
1,
));
}
let src = match &args[0] {
Value::Text(t) => t,
_ => {
return Err(WithReturnCode::new(
anyhow::anyhow!("src must be Value::Text"),
1,
))
}
};
let language = match &args[1] {
Value::TextOption(t) => t,
_ => {
return Err(WithReturnCode::new(
anyhow::anyhow!("language must be Value::TextOption"),
1,
))
}
};
let file = File::open(src);
if file.is_err() {
return Err(WithReturnCode::new(anyhow::anyhow!("file not found"), 1));
}
let mut file = file?;
let mut code = String::new();
if let Err(_) = file.read_to_string(&mut code) {
return Err(WithReturnCode::new(
anyhow::anyhow!("something went wrong reading the file"),
1,
));
}
match language {
Some(language) => Ok(format!(
"<code class=\"language-{}\">{}</code>",
language, code
)),
None => Ok(format!("<code>{}</code>", code)),
}
}

#[plugin_fn]
pub fn block_code(Json(args): Json<Vec<Value>>) -> FnResult<String> {
if args.len() != 2 {
return Err(WithReturnCode::new(
anyhow::anyhow!(
"Usage:
1. {{std.$ src}}
2. {{std.$ src, language}}"
),
1,
));
};
let src = match &args[0] {
Value::Text(t) => t,
_ => {
return Err(WithReturnCode::new(
anyhow::anyhow!("src must be Value::Text"),
1,
))
}
};
let language = match &args[1] {
Value::TextOption(t) => t,
_ => {
return Err(WithReturnCode::new(
anyhow::anyhow!("language must be Value::TextOption"),
1,
))
}
};
let file = File::open(src);
if file.is_err() {
return Err(WithReturnCode::new(anyhow::anyhow!("file not found"), 1));
}
let mut file = file?;
let mut code = String::new();
if let Err(_) = file.read_to_string(&mut code) {
return Err(WithReturnCode::new(
anyhow::anyhow!("something went wrong reading the file"),
1,
));
}
match language {
Some(language) => Ok(format!(
"<pre><code class=\"language-{}\">{}</code></pre>",
language, code
)),
None => Ok(format!("<pre><code>{}</code></pre>", code)),
}
}
70 changes: 70 additions & 0 deletions src/image.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
use brack_sdk_rs::{MetaData, Type, Value};
use extism_pdk::{plugin_fn, FnResult, Json, WithReturnCode};

#[plugin_fn]
pub fn metadata_image() -> FnResult<Json<MetaData>> {
Ok(Json(MetaData {
command_name: "img".to_string(),
call_name: "image".to_string(),
argument_types: vec![
("src".to_string(), Type::TInline),
("alt".to_string(), Type::TInline),
(
"caption".to_string(),
Type::TOption(Box::new(Type::TInline)),
),
],
return_type: Type::TBlock,
}))
}

#[plugin_fn]
pub fn image(Json(args): Json<Vec<Value>>) -> FnResult<String> {
if args.len() != 3 {
return Err(WithReturnCode::new(
anyhow::anyhow!(
"Usage:
1. {{std.img src, alt}}
2. {{std.img src, alt, caption}}"
),
1,
));
}
let src = match &args[0] {
Value::Text(t) => t,
_ => {
return Err(WithReturnCode::new(
anyhow::anyhow!("src must be Value::Text"),
1,
))
}
};
let alt = match &args[1] {
Value::Text(t) => t,
_ => {
return Err(WithReturnCode::new(
anyhow::anyhow!("alt must be Value::Text"),
1,
))
}
};
let caption = match &args[2] {
Value::TextOption(to) => to,
_ => {
return Err(WithReturnCode::new(
anyhow::anyhow!("caption must be Value::TextOption"),
1,
))
}
};
match caption {
Some(cap) => Ok(format!(
"<figure><img src=\"{}\" alt=\"{}\" /><figcaption>{}</figcaption></figire>",
src, alt, cap
)),
None => Ok(format!(
"<figure><img src=\"{}\" alt=\"{}\" /></figire>",
src, alt
)),
}
}
9 changes: 8 additions & 1 deletion src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,12 @@
pub mod anchor;
pub mod bold;
pub mod headings;
pub mod code;
pub mod footnote;
pub mod headings;
pub mod image;
pub mod italic;
pub mod list;
pub mod quote;
pub mod rules;
pub mod strike;
pub mod table;
84 changes: 84 additions & 0 deletions src/list.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
use brack_sdk_rs::{MetaData, Type, Value};
use extism_pdk::{plugin_fn, FnResult, Json, WithReturnCode};

#[plugin_fn]
pub fn metadata_unordered_list() -> FnResult<Json<MetaData>> {
Ok(Json(MetaData {
command_name: "-list".to_string(),
call_name: "unordered_list".to_string(),
argument_types: vec![("elems".to_string(), Type::TArray(Box::new(Type::TInline)))],
return_type: Type::TBlock,
}))
}

#[plugin_fn]
pub fn metadata_ordered_list() -> FnResult<Json<MetaData>> {
Ok(Json(MetaData {
command_name: "#list".to_string(),
call_name: "ordered_list".to_string(),
argument_types: vec![("elems".to_string(), Type::TArray(Box::new(Type::TInline)))],
return_type: Type::TBlock,
}))
}

fn is_list(text: &str) -> bool {
let is_unordered_list = text.starts_with("<ul>") && text.ends_with("</ul>");
let is_ordered_list = text.starts_with("<ol>") && text.ends_with("</ol>");
return is_unordered_list && is_ordered_list;
}

#[plugin_fn]
pub fn unordered_list(Json(args): Json<Vec<Value>>) -> FnResult<String> {
if args.len() != 1 {
return Err(WithReturnCode::new(
anyhow::anyhow!("Usage: {{std.-list elem1, elem2, ..., elemN}}"),
1,
));
}
let elems = match &args[0] {
Value::TextArray(t) => t,
_ => {
return Err(WithReturnCode::new(
anyhow::anyhow!("elems must be Value::TextArray"),
1,
))
}
};
let mut result = String::new();
for elem in elems {
if is_list(elem) {
result += elem;
continue;
}
result += &format!("<li>{}</li>", elem);
}
Ok(format!("<ul>{}</ul>", result))
}

#[plugin_fn]
pub fn ordered_list(Json(args): Json<Vec<Value>>) -> FnResult<String> {
if args.len() != 1 {
return Err(WithReturnCode::new(
anyhow::anyhow!("Usage: {{std.#list elem1, elem2, ..., elemN}}"),
1,
));
}
let elems = match &args[0] {
Value::TextArray(t) => t,
_ => {
return Err(WithReturnCode::new(
anyhow::anyhow!("elems must be Value::TextArray"),
1,
))
}
};
let mut result = String::new();
for elem in elems {
if is_list(elem) {
result += elem;
continue;
}
result += &format!("<li>{}</li>", elem);
}
Ok(format!("<ol>{}</ol>", result))
}
Loading