fix(api): malformed entries aren't parsed as invariants during PUT

feat/type-attributes
Tomáš Mládek 2023-01-04 21:16:59 +01:00
parent d5f6a615ba
commit 89bca64d23
1 changed files with 45 additions and 30 deletions

View File

@ -324,12 +324,18 @@ pub async fn get_object(
}))) })))
} }
#[derive(Debug, Clone, Deserialize)]
pub struct InEntry {
pub entity: Option<Address>,
pub attribute: String,
pub value: EntryValue,
}
#[derive(Debug, Clone, Deserialize)] #[derive(Debug, Clone, Deserialize)]
#[serde(untagged)] #[serde(untagged)]
pub enum InEntry { pub enum PutInput {
Entry(Entry), Entry(InEntry),
EntryList(Vec<Entry>), EntryList(Vec<Entry>),
Invariant(InvariantEntry),
Address { entity: InAddress }, Address { entity: InAddress },
} }
@ -367,7 +373,7 @@ impl TryInto<Address> for InAddress {
pub async fn put_object( pub async fn put_object(
req: HttpRequest, req: HttpRequest,
state: web::Data<State>, state: web::Data<State>,
payload: Either<web::Json<InEntry>, Multipart>, payload: Either<web::Json<PutInput>, Multipart>,
) -> Result<HttpResponse, Error> { ) -> Result<HttpResponse, Error> {
check_auth(&req, &state)?; check_auth(&req, &state)?;
@ -379,28 +385,23 @@ pub async fn put_object(
debug!("PUTting {in_entry:?}"); debug!("PUTting {in_entry:?}");
match in_entry { match in_entry {
InEntry::Entry(entry) => Ok(web::block::<_, _, anyhow::Error>(move || { PutInput::Entry(in_entry) => {
if let Some(entity) = in_entry.entity {
let entry = Entry {
entity,
attribute: in_entry.attribute,
value: in_entry.value,
};
Ok(web::block::<_, _, anyhow::Error>(move || {
Ok(( Ok((
Some(connection.insert_entry(entry.clone())?), Some(connection.insert_entry(entry.clone())?),
Some(entry.entity), Some(entry.entity),
)) ))
}) })
.await .await
.map_err(ErrorInternalServerError)?), .map_err(ErrorInternalServerError)?)
InEntry::EntryList(entries) => { } else {
web::block(move || {
connection.transaction::<_, anyhow::Error, _>(|| {
for entry in entries {
connection.insert_entry(entry)?;
}
Ok(())
})
})
.await
.map_err(ErrorInternalServerError)?;
Ok((None, None))
}
InEntry::Invariant(in_entry) => {
let invariant = Entry::try_from(&InvariantEntry { let invariant = Entry::try_from(&InvariantEntry {
attribute: in_entry.attribute, attribute: in_entry.attribute,
value: in_entry.value, value: in_entry.value,
@ -416,7 +417,21 @@ pub async fn put_object(
.await .await
.map_err(ErrorInternalServerError)?) .map_err(ErrorInternalServerError)?)
} }
InEntry::Address { entity: in_address } => { }
PutInput::EntryList(entries) => {
web::block(move || {
connection.transaction::<_, anyhow::Error, _>(|| {
for entry in entries {
connection.insert_entry(entry)?;
}
Ok(())
})
})
.await
.map_err(ErrorInternalServerError)?;
Ok((None, None))
}
PutInput::Address { entity: in_address } => {
let address = in_address.try_into().map_err(ErrorBadRequest)?; let address = in_address.try_into().map_err(ErrorBadRequest)?;
let label_entry = match &address { let label_entry = match &address {