mirror of
https://github.com/LemmyNet/lemmy.git
synced 2024-09-27 14:00:17 +00:00
allow plugins to alter request/response
This commit is contained in:
parent
9f2366474a
commit
bc7331b613
3 changed files with 41 additions and 21 deletions
|
@ -764,13 +764,14 @@ test("Fetch post with redirect", async () => {
|
||||||
expect(gammaPost2.post).toBeDefined();
|
expect(gammaPost2.post).toBeDefined();
|
||||||
});
|
});
|
||||||
|
|
||||||
test("Create a post", async () => {
|
test.only("Plugin test", async () => {
|
||||||
let community = await createCommunity(epsilon);
|
let community = await createCommunity(epsilon);
|
||||||
let postRes = createPost(
|
let postRes = createPost(
|
||||||
epsilon,
|
epsilon,
|
||||||
community.community_view.community.id,
|
community.community_view.community.id,
|
||||||
"https://example.com/",
|
"https://example.com/",
|
||||||
"plugin should block this",
|
"body",
|
||||||
|
"foobar",
|
||||||
);
|
);
|
||||||
await expect(postRes).rejects.toStrictEqual(Error("plugin_error"));
|
expect((await postRes).post_view.post.name).toBe("Hello plugin!");
|
||||||
});
|
});
|
||||||
|
|
|
@ -55,10 +55,12 @@ use webmention::{Webmention, WebmentionError};
|
||||||
|
|
||||||
#[tracing::instrument(skip(context))]
|
#[tracing::instrument(skip(context))]
|
||||||
pub async fn create_post(
|
pub async fn create_post(
|
||||||
data: Json<CreatePost>,
|
mut data: Json<CreatePost>,
|
||||||
context: Data<LemmyContext>,
|
context: Data<LemmyContext>,
|
||||||
local_user_view: LocalUserView,
|
local_user_view: LocalUserView,
|
||||||
) -> LemmyResult<Json<PostResponse>> {
|
) -> LemmyResult<Json<PostResponse>> {
|
||||||
|
plugin_hook("api_before_create_post", &mut (*data))?;
|
||||||
|
|
||||||
let local_site = LocalSite::read(&mut context.pool()).await?;
|
let local_site = LocalSite::read(&mut context.pool()).await?;
|
||||||
|
|
||||||
honeypot_check(&data.honeypot)?;
|
honeypot_check(&data.honeypot)?;
|
||||||
|
@ -126,8 +128,6 @@ pub async fn create_post(
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
plugin_hook("api_before_create_post", data.clone())?;
|
|
||||||
|
|
||||||
let post_form = PostInsertForm::builder()
|
let post_form = PostInsertForm::builder()
|
||||||
.name(data.name.trim().to_string())
|
.name(data.name.trim().to_string())
|
||||||
.url(url)
|
.url(url)
|
||||||
|
@ -161,8 +161,6 @@ pub async fn create_post(
|
||||||
.await
|
.await
|
||||||
.with_lemmy_type(LemmyErrorType::CouldntCreatePost)?;
|
.with_lemmy_type(LemmyErrorType::CouldntCreatePost)?;
|
||||||
|
|
||||||
plugin_hook("api_after_create_post", updated_post.clone())?;
|
|
||||||
|
|
||||||
generate_post_link_metadata(
|
generate_post_link_metadata(
|
||||||
updated_post.clone(),
|
updated_post.clone(),
|
||||||
custom_thumbnail,
|
custom_thumbnail,
|
||||||
|
@ -207,11 +205,17 @@ pub async fn create_post(
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
build_post_response(&context, community_id, &local_user_view.person, post_id).await
|
let mut res = build_post_response(&context, community_id, &local_user_view.person, post_id)
|
||||||
|
.await?
|
||||||
|
.0;
|
||||||
|
|
||||||
|
plugin_hook("api_after_create_post", &mut res)?;
|
||||||
|
Ok(Json(res))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn load_plugins() -> LemmyResult<Plugin> {
|
fn load_plugins() -> LemmyResult<Plugin> {
|
||||||
// TODO: make dir configurable via env var
|
// TODO: make dir configurable via env var
|
||||||
|
// TODO: should only read fs once at startup for performance
|
||||||
let plugin_paths = read_dir("example_plugin")?;
|
let plugin_paths = read_dir("example_plugin")?;
|
||||||
|
|
||||||
let mut wasm_files = vec![];
|
let mut wasm_files = vec![];
|
||||||
|
@ -226,13 +230,20 @@ fn load_plugins() -> LemmyResult<Plugin> {
|
||||||
Ok(plugin)
|
Ok(plugin)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn plugin_hook<T: Serialize>(name: &'static str, data: T) -> LemmyResult<()> {
|
fn plugin_hook<T: Serialize + for<'de> serde::Deserialize<'de> + Clone>(
|
||||||
|
name: &'static str,
|
||||||
|
data: &mut T,
|
||||||
|
) -> LemmyResult<()> {
|
||||||
let mut plugin = load_plugins()?;
|
let mut plugin = load_plugins()?;
|
||||||
if plugin.function_exists(name) {
|
if plugin.function_exists(name) {
|
||||||
let res = plugin
|
*data = plugin
|
||||||
.call::<extism_convert::Json<T>, &str>(name, data.into())
|
.call::<extism_convert::Json<T>, extism_convert::Json<T>>(name, (*data).clone().into())
|
||||||
.map_err(|e| LemmyErrorType::PluginError(e.to_string()));
|
.map_err(|e| {
|
||||||
println!("{}", res?);
|
dbg!(&e);
|
||||||
|
LemmyErrorType::PluginError(e.to_string())
|
||||||
|
})?
|
||||||
|
.0
|
||||||
|
.into();
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,13 +2,18 @@ package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/extism/go-pdk"
|
"github.com/extism/go-pdk"
|
||||||
"errors"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type CreatePost struct {
|
type CreatePost struct {
|
||||||
Name string `json:"name"`
|
Name string `json:"name"`
|
||||||
Body string `json:"body"`
|
Body *string `json:"body,omitempty"`
|
||||||
// skipping other fields for now
|
Community_id int32 `json:"community_id"`
|
||||||
|
Url *string `json:"url,omitempty"`
|
||||||
|
Alt_text *string `json:"alt_text,omitempty"`
|
||||||
|
Honeypot *string `json:"honeypot,omitempty"`
|
||||||
|
Nsfw *bool `json:"nsfw,omitempty"`
|
||||||
|
Language_id *int32 `json:"language_id,omitempty"`
|
||||||
|
Custom_thumbnail *string `json:"custom_thumbnail,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
//export api_before_create_post
|
//export api_before_create_post
|
||||||
|
@ -20,12 +25,15 @@ func api_before_create_post() int32 {
|
||||||
pdk.SetError(err)
|
pdk.SetError(err)
|
||||||
return 1
|
return 1
|
||||||
}
|
}
|
||||||
if params.Body == "plugin should block this" {
|
if params.Name == "foobar" {
|
||||||
pdk.SetError(errors.New("blocked by plugin"))
|
params.Name = "Hello plugin!"
|
||||||
|
}
|
||||||
|
// use json output helper, which automatically marshals your struct to the plugin output
|
||||||
|
err = pdk.OutputJSON(params)
|
||||||
|
if err != nil {
|
||||||
|
pdk.SetError(err)
|
||||||
return 1
|
return 1
|
||||||
}
|
}
|
||||||
greeting := `Created post "` + params.Name + `"!`
|
|
||||||
pdk.OutputString(greeting)
|
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue