104 lines
3.0 KiB
Rust
104 lines
3.0 KiB
Rust
|
use crate::{CalckeyDbError, CalckeyModel};
|
||
|
use ck::emoji;
|
||
|
use sea_orm::prelude::Expr;
|
||
|
use sea_orm::{ColumnTrait, EntityTrait, IntoSimpleExpr, QueryFilter, QueryOrder};
|
||
|
|
||
|
#[derive(Debug, Copy, Clone)]
|
||
|
pub struct EmojiTag<'a> {
|
||
|
pub name: &'a str,
|
||
|
pub host: Option<&'a str>,
|
||
|
}
|
||
|
|
||
|
pub struct EmojiResolver(CalckeyModel);
|
||
|
|
||
|
impl EmojiResolver {
|
||
|
pub fn new(db: CalckeyModel) -> Self {
|
||
|
EmojiResolver(db)
|
||
|
}
|
||
|
|
||
|
pub async fn get_local_emoji(&self) -> Result<Vec<emoji::Model>, CalckeyDbError> {
|
||
|
Ok(emoji::Entity::find()
|
||
|
.filter(emoji::Column::Host.is_null())
|
||
|
.order_by_asc(emoji::Column::Category)
|
||
|
.order_by_asc(emoji::Column::Name)
|
||
|
.all(self.0.inner())
|
||
|
.await?)
|
||
|
}
|
||
|
|
||
|
pub async fn fetch_emoji(
|
||
|
&self,
|
||
|
shortcode: &str,
|
||
|
host: Option<&str>,
|
||
|
) -> Result<Option<emoji::Model>, CalckeyDbError> {
|
||
|
let host_filter = if let Some(host) = host {
|
||
|
emoji::Column::Host.eq(host)
|
||
|
} else {
|
||
|
emoji::Column::Host.is_null()
|
||
|
};
|
||
|
|
||
|
let name_filter = emoji::Column::Name.eq(shortcode);
|
||
|
let filter = host_filter.and(name_filter);
|
||
|
|
||
|
Ok(emoji::Entity::find()
|
||
|
.filter(filter)
|
||
|
.one(self.0.inner())
|
||
|
.await?)
|
||
|
}
|
||
|
|
||
|
pub async fn fetch_many_emojis(
|
||
|
&self,
|
||
|
shortcodes: &[String],
|
||
|
host: Option<&str>,
|
||
|
) -> Result<Vec<emoji::Model>, CalckeyDbError> {
|
||
|
let host_filter = if let Some(host) = host {
|
||
|
emoji::Column::Host.eq(host)
|
||
|
} else {
|
||
|
emoji::Column::Host.is_null()
|
||
|
};
|
||
|
|
||
|
let name_filter = emoji::Column::Name.is_in(shortcodes);
|
||
|
let filter = host_filter.and(name_filter);
|
||
|
|
||
|
Ok(emoji::Entity::find()
|
||
|
.filter(filter)
|
||
|
.all(self.0.inner())
|
||
|
.await?)
|
||
|
}
|
||
|
|
||
|
pub async fn fetch_many_tagged_emojis(
|
||
|
&self,
|
||
|
shortcodes: &[EmojiTag<'_>],
|
||
|
) -> Result<Vec<emoji::Model>, CalckeyDbError> {
|
||
|
let remote_shortcode_host_pairs = shortcodes
|
||
|
.iter()
|
||
|
.filter_map(|s| {
|
||
|
s.host.map(|host| {
|
||
|
Expr::tuple([
|
||
|
Expr::value(s.name.to_string()),
|
||
|
Expr::value(host.to_string()),
|
||
|
])
|
||
|
})
|
||
|
})
|
||
|
.collect::<Vec<_>>();
|
||
|
let local_shortcodes = shortcodes
|
||
|
.iter()
|
||
|
.filter_map(|s| s.host.is_none().then_some(s.name.to_string()))
|
||
|
.collect::<Vec<_>>();
|
||
|
|
||
|
let remote_filter = Expr::tuple([
|
||
|
emoji::Column::Name.into_simple_expr(),
|
||
|
emoji::Column::Host.into_simple_expr(),
|
||
|
])
|
||
|
.is_in(remote_shortcode_host_pairs);
|
||
|
let local_filter = emoji::Column::Name
|
||
|
.is_in(local_shortcodes)
|
||
|
.and(emoji::Column::Host.is_null());
|
||
|
let filter = remote_filter.or(local_filter);
|
||
|
|
||
|
Ok(emoji::Entity::find()
|
||
|
.filter(filter)
|
||
|
.all(self.0.inner())
|
||
|
.await?)
|
||
|
}
|
||
|
}
|