mirror of
https://github.com/lennart-k/rustical.git
synced 2026-01-30 17:38:22 +00:00
Tests: Fix scope of store
This commit is contained in:
@@ -5,32 +5,27 @@ use crate::{
|
|||||||
use rstest::rstest;
|
use rstest::rstest;
|
||||||
use rustical_dav::resource::{Resource, ResourceService};
|
use rustical_dav::resource::{Resource, ResourceService};
|
||||||
use rustical_store::auth::{Principal, PrincipalType::Individual};
|
use rustical_store::auth::{Principal, PrincipalType::Individual};
|
||||||
use rustical_store_sqlite::{
|
use rustical_store_sqlite::tests::{TestStoreContext, test_store_context};
|
||||||
SqliteStore,
|
|
||||||
calendar_store::SqliteCalendarStore,
|
|
||||||
principal_store::SqlitePrincipalStore,
|
|
||||||
tests::{get_test_calendar_store, get_test_principal_store, get_test_subscription_store},
|
|
||||||
};
|
|
||||||
use rustical_xml::XmlSerializeRoot;
|
use rustical_xml::XmlSerializeRoot;
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
|
|
||||||
#[rstest]
|
#[rstest]
|
||||||
#[tokio::test]
|
#[tokio::test]
|
||||||
async fn test_principal_resource(
|
async fn test_principal_resource(
|
||||||
#[from(get_test_calendar_store)]
|
|
||||||
#[future]
|
#[future]
|
||||||
cal_store: SqliteCalendarStore,
|
#[from(test_store_context)]
|
||||||
#[from(get_test_principal_store)]
|
context: TestStoreContext,
|
||||||
#[future]
|
|
||||||
auth_provider: SqlitePrincipalStore,
|
|
||||||
#[from(get_test_subscription_store)]
|
|
||||||
#[future]
|
|
||||||
sub_store: SqliteStore,
|
|
||||||
) {
|
) {
|
||||||
|
let TestStoreContext {
|
||||||
|
cal_store,
|
||||||
|
sub_store,
|
||||||
|
principal_store: auth_provider,
|
||||||
|
..
|
||||||
|
} = context.await;
|
||||||
let service = PrincipalResourceService {
|
let service = PrincipalResourceService {
|
||||||
cal_store: Arc::new(cal_store.await),
|
cal_store: Arc::new(cal_store),
|
||||||
sub_store: Arc::new(sub_store.await),
|
sub_store: Arc::new(sub_store),
|
||||||
auth_provider: Arc::new(auth_provider.await),
|
auth_provider: Arc::new(auth_provider),
|
||||||
simplified_home_set: false,
|
simplified_home_set: false,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -1,12 +1,12 @@
|
|||||||
use criterion::{Criterion, criterion_group, criterion_main};
|
use criterion::{Criterion, criterion_group, criterion_main};
|
||||||
use rustical_ical::{CalendarObject, CalendarObjectType};
|
use rustical_ical::{CalendarObject, CalendarObjectType};
|
||||||
use rustical_store::{Calendar, CalendarMetadata, CalendarStore};
|
use rustical_store::{Calendar, CalendarMetadata, CalendarStore};
|
||||||
use rustical_store_sqlite::tests::get_test_calendar_store;
|
use rustical_store_sqlite::tests::test_store_context;
|
||||||
|
|
||||||
fn benchmark(c: &mut Criterion) {
|
fn benchmark(c: &mut Criterion) {
|
||||||
let runtime = tokio::runtime::Runtime::new().unwrap();
|
let runtime = tokio::runtime::Runtime::new().unwrap();
|
||||||
let cal_store = runtime.block_on(async {
|
let cal_store = runtime.block_on(async {
|
||||||
let cal_store = get_test_calendar_store().await;
|
let cal_store = test_store_context().await.cal_store;
|
||||||
|
|
||||||
cal_store
|
cal_store
|
||||||
.insert_calendar(Calendar {
|
.insert_calendar(Calendar {
|
||||||
|
|||||||
@@ -27,7 +27,7 @@ impl TryFrom<AddressObjectRow> for AddressObject {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Constructor)]
|
#[derive(Debug, Clone, Constructor)]
|
||||||
pub struct SqliteAddressbookStore {
|
pub struct SqliteAddressbookStore {
|
||||||
db: SqlitePool,
|
db: SqlitePool,
|
||||||
sender: Sender<CollectionOperation>,
|
sender: Sender<CollectionOperation>,
|
||||||
|
|||||||
@@ -87,7 +87,7 @@ impl From<CalendarRow> for Calendar {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Constructor)]
|
#[derive(Debug, Clone, Constructor)]
|
||||||
pub struct SqliteCalendarStore {
|
pub struct SqliteCalendarStore {
|
||||||
db: SqlitePool,
|
db: SqlitePool,
|
||||||
sender: Sender<CollectionOperation>,
|
sender: Sender<CollectionOperation>,
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ pub(crate) enum ChangeOperation {
|
|||||||
Delete,
|
Delete,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug, Clone)]
|
||||||
pub struct SqliteStore {
|
pub struct SqliteStore {
|
||||||
db: SqlitePool,
|
db: SqlitePool,
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ impl TryFrom<PrincipalRow> for Principal {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Constructor)]
|
#[derive(Debug, Clone, Constructor)]
|
||||||
pub struct SqlitePrincipalStore {
|
pub struct SqlitePrincipalStore {
|
||||||
db: SqlitePool,
|
db: SqlitePool,
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,17 +1,17 @@
|
|||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use crate::{addressbook_store::SqliteAddressbookStore, tests::get_test_addressbook_store};
|
use crate::tests::{TestStoreContext, test_store_context};
|
||||||
use rstest::rstest;
|
use rstest::rstest;
|
||||||
use rustical_store::{Addressbook, AddressbookStore};
|
use rustical_store::{Addressbook, AddressbookStore};
|
||||||
|
|
||||||
#[rstest]
|
#[rstest]
|
||||||
#[tokio::test]
|
#[tokio::test]
|
||||||
async fn test_addressbook_store(
|
async fn test_addressbook_store(
|
||||||
#[from(get_test_addressbook_store)]
|
#[from(test_store_context)]
|
||||||
#[future]
|
#[future]
|
||||||
addr_store: SqliteAddressbookStore,
|
context: TestStoreContext,
|
||||||
) {
|
) {
|
||||||
let addr_store = addr_store.await;
|
let addr_store = context.await.addr_store;
|
||||||
|
|
||||||
let cal = Addressbook {
|
let cal = Addressbook {
|
||||||
id: "addr".to_string(),
|
id: "addr".to_string(),
|
||||||
|
|||||||
@@ -1,17 +1,19 @@
|
|||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use crate::{calendar_store::SqliteCalendarStore, tests::get_test_calendar_store};
|
use crate::tests::{TestStoreContext, test_store_context};
|
||||||
use rstest::rstest;
|
use rstest::rstest;
|
||||||
use rustical_store::{Calendar, CalendarMetadata, CalendarStore};
|
use rustical_store::{Calendar, CalendarMetadata, CalendarStore};
|
||||||
|
|
||||||
#[rstest]
|
#[rstest]
|
||||||
#[tokio::test]
|
#[tokio::test]
|
||||||
async fn test_calendar_store(
|
async fn test_calendar_store(
|
||||||
#[from(get_test_calendar_store)]
|
|
||||||
#[future]
|
#[future]
|
||||||
cal_store: SqliteCalendarStore,
|
#[from(test_store_context)]
|
||||||
|
context: TestStoreContext,
|
||||||
) {
|
) {
|
||||||
let cal_store = cal_store.await;
|
let TestStoreContext { cal_store, .. } = context.await;
|
||||||
|
|
||||||
|
let cal_store = cal_store;
|
||||||
|
|
||||||
let cal = Calendar {
|
let cal = Calendar {
|
||||||
principal: "fake-user".to_string(),
|
principal: "fake-user".to_string(),
|
||||||
|
|||||||
@@ -2,61 +2,59 @@ use crate::{
|
|||||||
SqliteStore, addressbook_store::SqliteAddressbookStore, calendar_store::SqliteCalendarStore,
|
SqliteStore, addressbook_store::SqliteAddressbookStore, calendar_store::SqliteCalendarStore,
|
||||||
principal_store::SqlitePrincipalStore,
|
principal_store::SqlitePrincipalStore,
|
||||||
};
|
};
|
||||||
|
use rstest::fixture;
|
||||||
use rustical_store::auth::{AuthenticationProvider, Principal, PrincipalType};
|
use rustical_store::auth::{AuthenticationProvider, Principal, PrincipalType};
|
||||||
use sqlx::SqlitePool;
|
use sqlx::SqlitePool;
|
||||||
use tokio::sync::OnceCell;
|
|
||||||
|
|
||||||
static DB: OnceCell<SqlitePool> = OnceCell::const_new();
|
|
||||||
|
|
||||||
mod addressbook_store;
|
mod addressbook_store;
|
||||||
mod calendar_store;
|
mod calendar_store;
|
||||||
|
|
||||||
async fn get_test_db() -> SqlitePool {
|
async fn get_test_db() -> SqlitePool {
|
||||||
DB.get_or_init(async || {
|
let db = SqlitePool::connect("sqlite::memory:").await.unwrap();
|
||||||
let db = SqlitePool::connect("sqlite::memory:").await.unwrap();
|
sqlx::migrate!("./migrations").run(&db).await.unwrap();
|
||||||
sqlx::migrate!("./migrations").run(&db).await.unwrap();
|
|
||||||
|
|
||||||
// Populate with test data
|
// Populate with test data
|
||||||
let principal_store = SqlitePrincipalStore::new(db.clone());
|
let principal_store = SqlitePrincipalStore::new(db.clone());
|
||||||
principal_store
|
principal_store
|
||||||
.insert_principal(
|
.insert_principal(
|
||||||
Principal {
|
Principal {
|
||||||
id: "user".to_owned(),
|
id: "user".to_owned(),
|
||||||
displayname: None,
|
displayname: None,
|
||||||
memberships: vec![],
|
memberships: vec![],
|
||||||
password: None,
|
password: None,
|
||||||
principal_type: PrincipalType::Individual,
|
principal_type: PrincipalType::Individual,
|
||||||
},
|
},
|
||||||
false,
|
false,
|
||||||
)
|
)
|
||||||
.await
|
.await
|
||||||
.unwrap();
|
.unwrap();
|
||||||
principal_store
|
principal_store
|
||||||
.add_app_token("user", "test".to_string(), "pass".to_string())
|
.add_app_token("user", "test".to_string(), "pass".to_string())
|
||||||
.await
|
.await
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
db
|
db
|
||||||
})
|
|
||||||
.await
|
|
||||||
.clone()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#[rstest::fixture]
|
#[derive(Debug, Clone)]
|
||||||
pub async fn get_test_addressbook_store() -> SqliteAddressbookStore {
|
pub struct TestStoreContext {
|
||||||
let (send, _recv) = tokio::sync::mpsc::channel(1000);
|
pub db: SqlitePool,
|
||||||
SqliteAddressbookStore::new(get_test_db().await, send)
|
pub addr_store: SqliteAddressbookStore,
|
||||||
|
pub cal_store: SqliteCalendarStore,
|
||||||
|
pub principal_store: SqlitePrincipalStore,
|
||||||
|
pub sub_store: SqliteStore,
|
||||||
}
|
}
|
||||||
#[rstest::fixture]
|
|
||||||
pub async fn get_test_calendar_store() -> SqliteCalendarStore {
|
#[fixture]
|
||||||
let (send, _recv) = tokio::sync::mpsc::channel(1000);
|
pub async fn test_store_context() -> TestStoreContext {
|
||||||
SqliteCalendarStore::new(get_test_db().await, send)
|
let (send_addr, _recv) = tokio::sync::mpsc::channel(1);
|
||||||
}
|
let (send_cal, _recv) = tokio::sync::mpsc::channel(1);
|
||||||
#[rstest::fixture]
|
let db = get_test_db().await;
|
||||||
pub async fn get_test_subscription_store() -> SqliteStore {
|
TestStoreContext {
|
||||||
SqliteStore::new(get_test_db().await)
|
db: db.clone(),
|
||||||
}
|
addr_store: SqliteAddressbookStore::new(db.clone(), send_addr),
|
||||||
#[rstest::fixture]
|
cal_store: SqliteCalendarStore::new(db.clone(), send_cal),
|
||||||
pub async fn get_test_principal_store() -> SqlitePrincipalStore {
|
principal_store: SqlitePrincipalStore::new(db.clone()),
|
||||||
SqlitePrincipalStore::new(get_test_db().await)
|
sub_store: SqliteStore::new(db),
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ use headers::{Authorization, HeaderMapExt};
|
|||||||
use http::{HeaderValue, StatusCode};
|
use http::{HeaderValue, StatusCode};
|
||||||
use rstest::rstest;
|
use rstest::rstest;
|
||||||
use rustical_store::{CalendarMetadata, CalendarStore};
|
use rustical_store::{CalendarMetadata, CalendarStore};
|
||||||
use rustical_store_sqlite::{calendar_store::SqliteCalendarStore, tests::get_test_calendar_store};
|
use rustical_store_sqlite::tests::{TestStoreContext, test_store_context};
|
||||||
use tower::ServiceExt;
|
use tower::ServiceExt;
|
||||||
|
|
||||||
fn mkcalendar_template(
|
fn mkcalendar_template(
|
||||||
@@ -48,15 +48,13 @@ fn mkcalendar_template(
|
|||||||
#[rstest]
|
#[rstest]
|
||||||
#[tokio::test]
|
#[tokio::test]
|
||||||
async fn test_caldav_calendar(
|
async fn test_caldav_calendar(
|
||||||
#[from(get_app)]
|
#[from(test_store_context)]
|
||||||
#[future]
|
#[future]
|
||||||
app: axum::Router,
|
context: TestStoreContext,
|
||||||
#[from(get_test_calendar_store)]
|
|
||||||
#[future]
|
|
||||||
cal_store: SqliteCalendarStore,
|
|
||||||
) {
|
) {
|
||||||
let app = app.await;
|
let context = context.await;
|
||||||
let cal_store = cal_store.await;
|
let app = get_app(context.clone());
|
||||||
|
let cal_store = context.cal_store;
|
||||||
|
|
||||||
let mut calendar_meta = CalendarMetadata {
|
let mut calendar_meta = CalendarMetadata {
|
||||||
displayname: Some("Calendar".to_string()),
|
displayname: Some("Calendar".to_string()),
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ use axum::extract::Request;
|
|||||||
use headers::{Authorization, HeaderMapExt};
|
use headers::{Authorization, HeaderMapExt};
|
||||||
use http::{HeaderValue, StatusCode};
|
use http::{HeaderValue, StatusCode};
|
||||||
use rstest::rstest;
|
use rstest::rstest;
|
||||||
|
use rustical_store_sqlite::tests::{TestStoreContext, test_store_context};
|
||||||
use tower::ServiceExt;
|
use tower::ServiceExt;
|
||||||
|
|
||||||
mod calendar;
|
mod calendar;
|
||||||
@@ -11,11 +12,11 @@ mod calendar;
|
|||||||
#[rstest]
|
#[rstest]
|
||||||
#[tokio::test]
|
#[tokio::test]
|
||||||
async fn test_caldav_root(
|
async fn test_caldav_root(
|
||||||
#[from(get_app)]
|
#[from(test_store_context)]
|
||||||
#[future]
|
#[future]
|
||||||
app: axum::Router,
|
context: TestStoreContext,
|
||||||
) {
|
) {
|
||||||
let app = app.await;
|
let app = get_app(context.await);
|
||||||
|
|
||||||
let request_template = || {
|
let request_template = || {
|
||||||
Request::builder()
|
Request::builder()
|
||||||
@@ -53,11 +54,11 @@ async fn test_caldav_root(
|
|||||||
#[rstest]
|
#[rstest]
|
||||||
#[tokio::test]
|
#[tokio::test]
|
||||||
async fn test_caldav_principal(
|
async fn test_caldav_principal(
|
||||||
#[from(get_app)]
|
#[from(test_store_context)]
|
||||||
#[future]
|
#[future]
|
||||||
app: axum::Router,
|
context: TestStoreContext,
|
||||||
) {
|
) {
|
||||||
let app = app.await;
|
let app = get_app(context.await);
|
||||||
|
|
||||||
let request_template = || {
|
let request_template = || {
|
||||||
Request::builder()
|
Request::builder()
|
||||||
|
|||||||
@@ -50,192 +50,4 @@ expression: body
|
|||||||
<status>HTTP/1.1 200 OK</status>
|
<status>HTTP/1.1 200 OK</status>
|
||||||
</propstat>
|
</propstat>
|
||||||
</response>
|
</response>
|
||||||
<response xmlns="DAV:" xmlns:CAL="urn:ietf:params:xml:ns:caldav" xmlns:CARD="urn:ietf:params:xml:ns:carddav" xmlns:CS="http://calendarserver.org/ns/" xmlns:PUSH="https://bitfire.at/webdav-push">
|
|
||||||
<href>/caldav/principal/user/calendar/</href>
|
|
||||||
<propstat>
|
|
||||||
<prop>
|
|
||||||
<calendar-color xmlns="http://apple.com/ns/ical/">#00FF00</calendar-color>
|
|
||||||
<CAL:calendar-description>Description</CAL:calendar-description>
|
|
||||||
<CAL:calendar-timezone>BEGIN:VCALENDAR
|
|
||||||
PRODID:-//github.com/lennart-k/vzic-rs//RustiCal Calendar server//EN
|
|
||||||
VERSION:2.0
|
|
||||||
BEGIN:VTIMEZONE
|
|
||||||
TZID:Europe/Berlin
|
|
||||||
LAST-MODIFIED:20250723T190331Z
|
|
||||||
X-LIC-LOCATION:Europe/Berlin
|
|
||||||
X-PROLEPTIC-TZNAME:LMT
|
|
||||||
BEGIN:STANDARD
|
|
||||||
TZNAME:CET
|
|
||||||
TZOFFSETFROM:+005328
|
|
||||||
TZOFFSETTO:+0100
|
|
||||||
DTSTART:18930401T000000
|
|
||||||
END:STANDARD
|
|
||||||
BEGIN:DAYLIGHT
|
|
||||||
TZNAME:CEST
|
|
||||||
TZOFFSETFROM:+0100
|
|
||||||
TZOFFSETTO:+0200
|
|
||||||
DTSTART:19160430T230000
|
|
||||||
RDATE:19400401T020000
|
|
||||||
RDATE:19430329T020000
|
|
||||||
RDATE:19460414T020000
|
|
||||||
RDATE:19470406T030000
|
|
||||||
RDATE:19480418T020000
|
|
||||||
RDATE:19490410T020000
|
|
||||||
RDATE:19800406T020000
|
|
||||||
END:DAYLIGHT
|
|
||||||
BEGIN:STANDARD
|
|
||||||
TZNAME:CET
|
|
||||||
TZOFFSETFROM:+0200
|
|
||||||
TZOFFSETTO:+0100
|
|
||||||
DTSTART:19161001T010000
|
|
||||||
RDATE:19421102T030000
|
|
||||||
RDATE:19431004T030000
|
|
||||||
RDATE:19441002T030000
|
|
||||||
RDATE:19451118T030000
|
|
||||||
RDATE:19461007T030000
|
|
||||||
END:STANDARD
|
|
||||||
BEGIN:DAYLIGHT
|
|
||||||
TZNAME:CEST
|
|
||||||
TZOFFSETFROM:+0100
|
|
||||||
TZOFFSETTO:+0200
|
|
||||||
DTSTART:19170416T020000
|
|
||||||
RRULE:FREQ=YEARLY;BYMONTH=4;BYDAY=3MO;UNTIL=19180415T010000Z
|
|
||||||
END:DAYLIGHT
|
|
||||||
BEGIN:STANDARD
|
|
||||||
TZNAME:CET
|
|
||||||
TZOFFSETFROM:+0200
|
|
||||||
TZOFFSETTO:+0100
|
|
||||||
DTSTART:19170917T030000
|
|
||||||
RRULE:FREQ=YEARLY;BYMONTH=9;BYDAY=3MO;UNTIL=19180916T010000Z
|
|
||||||
END:STANDARD
|
|
||||||
BEGIN:DAYLIGHT
|
|
||||||
TZNAME:CEST
|
|
||||||
TZOFFSETFROM:+0100
|
|
||||||
TZOFFSETTO:+0200
|
|
||||||
DTSTART:19440403T020000
|
|
||||||
RRULE:FREQ=YEARLY;BYMONTH=4;BYDAY=1MO;UNTIL=19450402T010000Z
|
|
||||||
END:DAYLIGHT
|
|
||||||
BEGIN:DAYLIGHT
|
|
||||||
TZNAME:CEMT
|
|
||||||
TZOFFSETFROM:+0200
|
|
||||||
TZOFFSETTO:+0300
|
|
||||||
DTSTART:19450524T020000
|
|
||||||
RDATE:19470511T030000
|
|
||||||
END:DAYLIGHT
|
|
||||||
BEGIN:DAYLIGHT
|
|
||||||
TZNAME:CEST
|
|
||||||
TZOFFSETFROM:+0300
|
|
||||||
TZOFFSETTO:+0200
|
|
||||||
DTSTART:19450924T030000
|
|
||||||
RDATE:19470629T030000
|
|
||||||
END:DAYLIGHT
|
|
||||||
BEGIN:STANDARD
|
|
||||||
TZNAME:CET
|
|
||||||
TZOFFSETFROM:+0100
|
|
||||||
TZOFFSETTO:+0100
|
|
||||||
DTSTART:19460101T000000
|
|
||||||
RDATE:19800101T000000
|
|
||||||
END:STANDARD
|
|
||||||
BEGIN:STANDARD
|
|
||||||
TZNAME:CET
|
|
||||||
TZOFFSETFROM:+0200
|
|
||||||
TZOFFSETTO:+0100
|
|
||||||
DTSTART:19471005T030000
|
|
||||||
RRULE:FREQ=YEARLY;BYMONTH=10;BYDAY=1SU;UNTIL=19491002T010000Z
|
|
||||||
END:STANDARD
|
|
||||||
BEGIN:STANDARD
|
|
||||||
TZNAME:CET
|
|
||||||
TZOFFSETFROM:+0200
|
|
||||||
TZOFFSETTO:+0100
|
|
||||||
DTSTART:19800928T030000
|
|
||||||
RRULE:FREQ=YEARLY;BYMONTH=9;BYDAY=-1SU;UNTIL=19950924T010000Z
|
|
||||||
END:STANDARD
|
|
||||||
BEGIN:DAYLIGHT
|
|
||||||
TZNAME:CEST
|
|
||||||
TZOFFSETFROM:+0100
|
|
||||||
TZOFFSETTO:+0200
|
|
||||||
DTSTART:19810329T020000
|
|
||||||
RRULE:FREQ=YEARLY;BYMONTH=3;BYDAY=-1SU
|
|
||||||
END:DAYLIGHT
|
|
||||||
BEGIN:STANDARD
|
|
||||||
TZNAME:CET
|
|
||||||
TZOFFSETFROM:+0200
|
|
||||||
TZOFFSETTO:+0100
|
|
||||||
DTSTART:19961027T030000
|
|
||||||
RRULE:FREQ=YEARLY;BYMONTH=10;BYDAY=-1SU
|
|
||||||
END:STANDARD
|
|
||||||
END:VTIMEZONE
|
|
||||||
END:VCALENDAR
|
|
||||||
</CAL:calendar-timezone>
|
|
||||||
<CAL:timezone-service-set>
|
|
||||||
<href>https://www.iana.org/time-zones</href>
|
|
||||||
</CAL:timezone-service-set>
|
|
||||||
<CAL:calendar-timezone-id>Europe/Berlin</CAL:calendar-timezone-id>
|
|
||||||
<calendar-order xmlns="http://apple.com/ns/ical/">0</calendar-order>
|
|
||||||
<CAL:supported-calendar-component-set>
|
|
||||||
<CAL:comp name="VEVENT"/>
|
|
||||||
<CAL:comp name="VTODO"/>
|
|
||||||
<CAL:comp name="VJOURNAL"/>
|
|
||||||
</CAL:supported-calendar-component-set>
|
|
||||||
<CAL:supported-calendar-data>
|
|
||||||
<CAL:calendar-data content-type="text/calendar" version="2.0"/>
|
|
||||||
</CAL:supported-calendar-data>
|
|
||||||
<CAL:supported-collation-set>
|
|
||||||
<CAL:supported-collation>i;ascii-casemap</CAL:supported-collation>
|
|
||||||
<CAL:supported-collation>i;octet</CAL:supported-collation>
|
|
||||||
</CAL:supported-collation-set>
|
|
||||||
<max-resource-size>10000000</max-resource-size>
|
|
||||||
<supported-report-set>
|
|
||||||
<supported-report>
|
|
||||||
<report>
|
|
||||||
<CAL:calendar-query/>
|
|
||||||
</report>
|
|
||||||
</supported-report>
|
|
||||||
<supported-report>
|
|
||||||
<report>
|
|
||||||
<CAL:calendar-multiget/>
|
|
||||||
</report>
|
|
||||||
</supported-report>
|
|
||||||
<supported-report>
|
|
||||||
<report>
|
|
||||||
<sync-collection/>
|
|
||||||
</report>
|
|
||||||
</supported-report>
|
|
||||||
</supported-report-set>
|
|
||||||
<CAL:min-date-time>-2621430101T000000Z</CAL:min-date-time>
|
|
||||||
<CAL:max-date-time>+2621421231T235959Z</CAL:max-date-time>
|
|
||||||
<sync-token>github.com/lennart-k/rustical/ns/0</sync-token>
|
|
||||||
<CS:getctag>github.com/lennart-k/rustical/ns/0</CS:getctag>
|
|
||||||
<PUSH:transports>
|
|
||||||
<PUSH:web-push/>
|
|
||||||
</PUSH:transports>
|
|
||||||
<PUSH:topic>[PUSH_TOPIC]</PUSH:topic>
|
|
||||||
<PUSH:supported-triggers>
|
|
||||||
<PUSH:content-update>
|
|
||||||
<depth>1</depth>
|
|
||||||
</PUSH:content-update>
|
|
||||||
<PUSH:property-update>
|
|
||||||
<depth>1</depth>
|
|
||||||
</PUSH:property-update>
|
|
||||||
</PUSH:supported-triggers>
|
|
||||||
<resourcetype>
|
|
||||||
<collection/>
|
|
||||||
<CAL:calendar/>
|
|
||||||
</resourcetype>
|
|
||||||
<displayname>Calendar</displayname>
|
|
||||||
<current-user-principal>
|
|
||||||
<href>/caldav/principal/user/</href>
|
|
||||||
</current-user-principal>
|
|
||||||
<current-user-privilege-set>
|
|
||||||
<privilege>
|
|
||||||
<all/>
|
|
||||||
</privilege>
|
|
||||||
</current-user-privilege-set>
|
|
||||||
<owner>
|
|
||||||
<href>/caldav/principal/user/</href>
|
|
||||||
</owner>
|
|
||||||
</prop>
|
|
||||||
<status>HTTP/1.1 200 OK</status>
|
|
||||||
</propstat>
|
|
||||||
</response>
|
|
||||||
</multistatus>
|
</multistatus>
|
||||||
|
|||||||
@@ -4,16 +4,17 @@ use axum::extract::Request;
|
|||||||
use headers::{Authorization, HeaderMapExt};
|
use headers::{Authorization, HeaderMapExt};
|
||||||
use http::StatusCode;
|
use http::StatusCode;
|
||||||
use rstest::rstest;
|
use rstest::rstest;
|
||||||
|
use rustical_store_sqlite::tests::{TestStoreContext, test_store_context};
|
||||||
use tower::ServiceExt;
|
use tower::ServiceExt;
|
||||||
|
|
||||||
#[rstest]
|
#[rstest]
|
||||||
#[tokio::test]
|
#[tokio::test]
|
||||||
async fn test_carddav_root(
|
async fn test_carddav_root(
|
||||||
#[from(get_app)]
|
#[from(test_store_context)]
|
||||||
#[future]
|
#[future]
|
||||||
app: axum::Router,
|
context: TestStoreContext,
|
||||||
) {
|
) {
|
||||||
let app = app.await;
|
let app = get_app(context.await);
|
||||||
|
|
||||||
let request_template = || {
|
let request_template = || {
|
||||||
Request::builder()
|
Request::builder()
|
||||||
|
|||||||
@@ -3,44 +3,24 @@ use axum::extract::Request;
|
|||||||
use axum::{body::Body, response::Response};
|
use axum::{body::Body, response::Response};
|
||||||
use rstest::rstest;
|
use rstest::rstest;
|
||||||
use rustical_frontend::FrontendConfig;
|
use rustical_frontend::FrontendConfig;
|
||||||
use rustical_store_sqlite::{
|
use rustical_store_sqlite::tests::{TestStoreContext, test_store_context};
|
||||||
SqliteStore,
|
|
||||||
addressbook_store::SqliteAddressbookStore,
|
|
||||||
calendar_store::SqliteCalendarStore,
|
|
||||||
principal_store::SqlitePrincipalStore,
|
|
||||||
tests::{
|
|
||||||
get_test_addressbook_store, get_test_calendar_store, get_test_principal_store,
|
|
||||||
get_test_subscription_store,
|
|
||||||
},
|
|
||||||
};
|
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
use tower::ServiceExt;
|
use tower::ServiceExt;
|
||||||
|
|
||||||
#[rstest::fixture]
|
pub fn get_app(context: TestStoreContext) -> axum::Router {
|
||||||
pub async fn get_app(
|
let TestStoreContext {
|
||||||
#[from(get_test_calendar_store)]
|
|
||||||
#[future]
|
|
||||||
cal_store: SqliteCalendarStore,
|
|
||||||
#[from(get_test_addressbook_store)]
|
|
||||||
#[future]
|
|
||||||
addr_store: SqliteAddressbookStore,
|
|
||||||
#[from(get_test_principal_store)]
|
|
||||||
#[future]
|
|
||||||
principal_store: SqlitePrincipalStore,
|
|
||||||
#[from(get_test_subscription_store)]
|
|
||||||
#[future]
|
|
||||||
sub_store: SqliteStore,
|
|
||||||
) -> axum::Router {
|
|
||||||
let addr_store = Arc::new(addr_store.await);
|
|
||||||
let cal_store = Arc::new(cal_store.await);
|
|
||||||
let sub_store = Arc::new(sub_store.await);
|
|
||||||
let principal_store = Arc::new(principal_store.await);
|
|
||||||
|
|
||||||
make_app(
|
|
||||||
addr_store,
|
addr_store,
|
||||||
cal_store,
|
cal_store,
|
||||||
sub_store,
|
|
||||||
principal_store,
|
principal_store,
|
||||||
|
sub_store,
|
||||||
|
..
|
||||||
|
} = context;
|
||||||
|
|
||||||
|
make_app(
|
||||||
|
Arc::new(addr_store),
|
||||||
|
Arc::new(cal_store),
|
||||||
|
Arc::new(sub_store),
|
||||||
|
Arc::new(principal_store),
|
||||||
FrontendConfig {
|
FrontendConfig {
|
||||||
enabled: true,
|
enabled: true,
|
||||||
allow_password_login: true,
|
allow_password_login: true,
|
||||||
@@ -70,11 +50,11 @@ impl ResponseExtractString for Response {
|
|||||||
#[rstest]
|
#[rstest]
|
||||||
#[tokio::test]
|
#[tokio::test]
|
||||||
async fn test_ping(
|
async fn test_ping(
|
||||||
#[from(get_app)]
|
#[from(test_store_context)]
|
||||||
#[future]
|
#[future]
|
||||||
app: axum::Router,
|
context: TestStoreContext,
|
||||||
) {
|
) {
|
||||||
let app = app.await;
|
let app = get_app(context.await);
|
||||||
|
|
||||||
let response = app
|
let response = app
|
||||||
.oneshot(Request::builder().uri("/ping").body(Body::empty()).unwrap())
|
.oneshot(Request::builder().uri("/ping").body(Body::empty()).unwrap())
|
||||||
|
|||||||
Reference in New Issue
Block a user