Skip to main content

SqlStore

Struct SqlStore 

Source
pub struct SqlStore { /* private fields */ }
Expand description

Runlight’s tables in a database: everything recorded, and every report read from it.

Implementations§

Source§

impl SqlStore

Source

pub fn new(db: Arc<dyn Db>) -> SqlStore

A store over a database, its tables named rl_ and something (or under the Db’s own prefix, for a Prefixed one).

Source

pub fn with_prefix(db: Arc<dyn Db>, prefix: &str) -> Result<SqlStore, DbError>

A store whose table and index names start with prefix in place of rl_, so two apps can each keep Runlight’s tables in one database: up to 32 letters, digits, and underscores, not starting with a digit. A Db that is already prefixed keeps its own.

Source

pub fn db(&self) -> &Arc<dyn Db> ⓘ

The database.

Source

pub fn prefix(&self) -> &str

What the store’s table and index names start with: rl_ unless it was given another.

Source

pub fn tables(&self) -> Vec<String>

The store’s tables as named in the database, for an app removing Runlight: each one by name, since another app’s tables may well start with the same letters.

Source

pub async fn migrate(&self) -> Result<(), DbError>

Creates the tables on first use. Safe to call any number of times.

Source

pub async fn optimize(&self, only_when_stale: bool)

Keeps SQLite’s planner statistics current, which it never gathers by itself. A sample of each index is enough, so this takes a few seconds at most even on a large database. Postgres gathers its own.

With only_when_stale, only when there are none, or the events have more than doubled since they were gathered. Statistics gathered on a new, empty database say every table is empty, and a goal over a million visits then took a minute rather than milliseconds.

Source

pub async fn close(&self)

Lets the database’s connections go.

Source

pub async fn transaction<T, F, Fut>(&self, f: F) -> Result<T, DbError>
where F: FnOnce(SqlStore) -> Fut, Fut: Future<Output = Result<T, DbError>>,

Runs f with a store whose every query is in one transaction.

Source

pub async fn upsert_site(&self, site: &SiteRow, now: i64) -> Result<(), DbError>

Records a site, leaving an unchanged one alone, so starting needs no write.

Source

pub async fn site_overrides( &self, ) -> Result<HashMap<String, SiteOverrides>, DbError>

Settings changed in the dashboard, by site. They win over the ones in code.

Source

pub async fn delete_site(&self, id: &str) -> Result<(), DbError>

Deletes a site and everything recorded for it. Its events and visits go a day at a time first, so a big site does not hold the database for minutes, and what is left goes in one transaction.

Source

pub async fn drop_before(&self, site: &str, ts: i64) -> Result<(), DbError>

Deletes a site’s visits and events from before a time, for its retention setting.

Source

pub async fn drop_orphans( &self, site: &str, from: i64, until: i64, ) -> Result<(), DbError>

Deletes a site’s events from from on whose visit no longer exists, a day at a time.

Source

pub async fn build_rollup_day( &self, site: &str, day: &str, start: i64, end: i64, ) -> Result<(), DbError>

Adds up one local day of a site: totals, each visit dimension, and pages. A visit belongs to the day it started. Visitor ids change every day, so the days of a range add up to exactly what counting the range would give.

Source

pub async fn rollup_days(&self, site: &str) -> Result<HashSet<String>, DbError>

The days of a site already built.

Source

pub async fn clear_rollups( &self, site: &str, before: Option<i64>, between: Option<(i64, i64)>, ) -> Result<(), DbError>

Forgets built days, all of a site’s (before and between both None), those starting before a time, or those touching a stretch of time, so they are built again.

Source

pub async fn set_site_overrides( &self, id: &str, overrides: &SiteOverrides, ) -> Result<(), DbError>

Saves the settings changed in the dashboard for a site.

Source

pub async fn last_seen(&self, site: &str) -> Result<Option<i64>, DbError>

When the site last recorded a visit, or None if it never has.

Source

pub async fn sites(&self) -> Result<Vec<SiteRow>, DbError>

Every site, by name.

Source

pub async fn salt(&self, day: &str, fresh: &str) -> Result<String, DbError>

The salt for a day, made on first ask. Two racing callers agree on one.

Source

pub async fn salt_if_exists(&self, day: &str) -> Result<Option<String>, DbError>

The salt for a day, if there is one.

Source

pub async fn drop_salts_except(&self, days: &[String]) -> Result<(), DbError>

Deletes every salt but those of these days, so the hashes made with them can never be made again.

Source

pub async fn visit_open( &self, sites: &[String], from: i64, to: i64, since: i64, ) -> Result<bool, DbError>

Whether a visit to one of these sites that started in a stretch of time was still going at since.

Source

pub async fn open_session( &self, site: &str, visitors: &[String], since: i64, ) -> Result<Option<(String, String)>, DbError>

The visitor’s open session: any of their hashes, active since since.

Source

pub async fn settle_open_session( &self, site: &str, visitors: &[String], since: i64, opened: (String, String), ) -> Result<(String, String), DbError>

After opening a visit: the visitor’s earliest visit still going, which is this one unless another process opened one for the same visitor at the same moment. Then both settle on the earliest, and the one that is not drops its own, before anything is counted into it.

Source

pub async fn insert_session(&self, row: &SessionRow) -> Result<(), DbError>

Records a new visit.

Source

pub async fn touch_session( &self, id: &str, ts: i64, kind: &str, path: &str, reopen: bool, ) -> Result<(), DbError>

Counts a row into its session. An event with reopen false, one that joins a visit already ended, counts without moving the session’s last activity.

Source

pub async fn add_engagement(&self, id: &str, ms: i64) -> Result<(), DbError>

Adds engaged time to a visit.

Source

pub async fn pageview( &self, site: &str, pageview: &str, ) -> Result<Option<PageviewInfo>, DbError>

The pageview an engagement ping or event belongs to, with when its visit started and was last active.

Source

pub async fn touched_old_visit( &self, site: &str, started: i64, before: i64, ) -> Result<(), DbError>

After a late event or engagement ping joins an old visit, the day that visit started may already be added up. Forget that day so the next check builds it again.

Source

pub async fn insert_event(&self, row: &EventRow) -> Result<(), DbError>

Records a row.

The live link with a slug. Slugs are unique across every domain.

The live link with an id.

Records a link.

Saves a link’s changes.

Hides a link and frees its slug; its clicks stay in the history.

Source

pub async fn shares(&self, site: &str) -> Result<Vec<ShareRow>, DbError>

A site’s share links, newest first.

Source

pub async fn share_by_id(&self, id: &str) -> Result<Option<ShareRow>, DbError>

A share link by its id.

Source

pub async fn insert_share(&self, share: &ShareRow) -> Result<(), DbError>

Records a share link.

Source

pub async fn rename_share(&self, id: &str, name: &str) -> Result<(), DbError>

Renames a share link.

Source

pub async fn delete_share(&self, id: &str) -> Result<(), DbError>

Deleting a share is how it is revoked: the link stops working at once.

Source

pub async fn funnels(&self, site: &str) -> Result<Vec<FunnelRow>, DbError>

A site’s funnels, oldest first.

Source

pub async fn save_funnel(&self, f: &FunnelRow) -> Result<(), DbError>

Records or changes a funnel.

Source

pub async fn delete_funnel(&self, id: &str) -> Result<(), DbError>

Deletes a funnel.

Source

pub fn funnel_visits(&self) -> i64

The most visits a funnel is counted over: FUNNEL_VISITS unless a test lowered it.

Source

pub async fn funnel_counts( &self, query: &Query, funnel: &FunnelRow, ) -> Result<(Vec<f64>, bool), DbError>

How many visits reached each step, in order, within the same visit, and whether only the newest funnel_visits visits in the range were counted. Step one is the first matching row in the range; each later step must come after the step before it.

Source

pub async fn journey_pages( &self, query: &Query, per_visit: i64, ) -> Result<(Vec<(String, String)>, bool), DbError>

Each visit’s pageviews in order, at most per_visit of them, for journeys. A window function keeps the first ones of each visit, so a long visit cannot crowd the rest out.

Source

pub async fn tokens(&self) -> Result<Vec<TokenRow>, DbError>

Every API token, newest first.

Source

pub async fn token_by_hash( &self, hash: &str, ) -> Result<Option<TokenRow>, DbError>

The token with this hash.

Source

pub async fn insert_token(&self, t: &TokenRow) -> Result<(), DbError>

Records a token.

Source

pub async fn touch_token(&self, id: &str, now: i64) -> Result<(), DbError>

Notes when a token was last used.

Source

pub async fn delete_token(&self, id: &str) -> Result<bool, DbError>

Deleting a token is how it is revoked: it stops working at once.

Source

pub async fn setting(&self, key: &str) -> Result<Option<String>, DbError>

A setting.

Source

pub async fn settings_starting_with( &self, prefix: &str, ) -> Result<Vec<(String, String)>, DbError>

Every setting whose key starts with a prefix, such as each connected install’s.

Source

pub async fn take_setting(&self, key: &str) -> Result<Option<String>, DbError>

Reads a setting and deletes it. Of two callers at once, only the one whose delete took the row gets its value.

Source

pub async fn add_setting(&self, key: &str, value: &str) -> Result<bool, DbError>

Writes a setting only if it is not there yet. Of two callers at once, only one gets true.

Source

pub async fn swap_setting( &self, key: &str, from: &str, to: &str, ) -> Result<bool, DbError>

Changes a setting only if it still holds from. Of two callers at once, only one gets true.

Source

pub async fn setting_or_add( &self, key: &str, make: impl Fn() -> String, ) -> Result<String, DbError>

A setting that is made the first time it is asked for. Every caller gets the value written first, however many ask at once.

Source

pub async fn set_setting( &self, key: &str, value: Option<&str>, ) -> Result<(), DbError>

Saves a setting, or deletes it with None.

Source

pub async fn reports( &self, site: Option<&str>, ) -> Result<Vec<ReportRow>, DbError>

Email reports, a site’s or all.

Source

pub async fn report_by( &self, by_token: bool, value: &str, ) -> Result<Option<ReportRow>, DbError>

A report by its id, or by its unsubscribe token.

Source

pub async fn insert_report(&self, r: &ReportRow) -> Result<(), DbError>

Records a report.

Source

pub async fn claim_report( &self, id: &str, period: &str, now: i64, ) -> Result<bool, DbError>

Records a period as sent. Only one caller wins, so two cron runs at once cannot both send it.

Source

pub async fn release_report( &self, id: &str, period: &str, previous: &str, ) -> Result<(), DbError>

Puts a period back when its email failed, so the next run tries again.

Source

pub async fn delete_report(&self, id: &str) -> Result<(), DbError>

Deletes a report.

Source

pub async fn goals(&self, site: Option<&str>) -> Result<Vec<GoalRow>, DbError>

Goals, a site’s or all, oldest first.

Source

pub async fn goal_by_id(&self, id: &str) -> Result<Option<GoalRow>, DbError>

A goal by its id.

Source

pub async fn save_goal( &self, g: &GoalRow, before: Option<&GoalRow>, ) -> Result<(), DbError>

Records or changes a goal.

Source

pub async fn delete_goal(&self, id: &str) -> Result<(), DbError>

Deletes a goal.

Source

pub async fn event_prop_keys( &self, query: &Query, event: &str, ) -> Result<Vec<(String, f64)>, DbError>

The property names sent with an event in a query’s range, most used first.

Source

pub async fn event_prop_values( &self, query: &Query, event: &str, key: &str, limit: i64, ) -> Result<Vec<(String, f64, f64)>, DbError>

The values one property of an event took, with how often and by how many visitors.

Source

pub async fn goal_totals_all( &self, query: &Query, goals: &[GoalRow], ) -> Result<HashMap<String, GoalTotals>, DbError>

Every goal’s totals in one pass over the range’s events, instead of a query per goal.

Source

pub async fn goal_totals( &self, query: &Query, goal: &GoalRow, ) -> Result<GoalTotals, DbError>

One goal’s conversions, converting visitors, and revenue for a query’s range and filters.

Source

pub async fn goal_breakdown( &self, query: &Query, goal: &GoalRow, by: &str, limit: i64, ) -> Result<Vec<(String, GoalTotals)>, DbError>

A goal’s conversions split by where the visit came from, or by the page it happened on.

Source

pub async fn goal_series( &self, site: &str, filters: &[Filter], goal: &GoalRow, buckets: &[Bucket], ) -> Result<Vec<(i64, f64, f64)>, DbError>

A goal’s conversions and revenue in each bucket, by when each visit started.

Every link domain and its site.

Adds a link domain.

Removes a domain. Its links keep it as their home and fall back to the app’s own link path until the domain is added again.

A site’s links, newest first, with their clicks in a range. Clicks imported as daily counts have no visitor, so they add to clicks only.

One link’s clicks per bucket.

One link’s clicks by a visit dimension.

Source

pub async fn first_own_visit(&self, site: &str) -> Result<Option<i64>, DbError>

When Runlight itself first counted a visit, leaving out imported history.

Source

pub async fn first_seen(&self, site: &str) -> Result<Option<i64>, DbError>

When the site’s first visit was recorded, or None with no data yet.

Source

pub async fn visitors(&self, query: &Query) -> Result<f64, DbError>

Just the visitor count from stats(), in one query, for conversion rates.

Source

pub async fn stats(&self, query: &Query) -> Result<Stats, DbError>

A range’s totals.

Source

pub async fn series( &self, site: &str, filters: &[Filter], buckets: &[Bucket], ) -> Result<Vec<Value>, DbError>

The chart: each bucket’s visitors, visits, pageviews, and the rest.

Source

pub async fn hostname_suggestions( &self, query: &Query, limit: i64, ) -> Result<Vec<Value>, DbError>

A breakdown of a range by a dimension, a page of rows at a time. Seek one matching event per hostname, skipping its remaining events before the next seek.

Source

pub async fn breakdown( &self, query: &Query, dimension: &str, limit: i64, offset: i64, ) -> Result<Vec<Value>, DbError>

Source

pub async fn hourly( &self, query: &Query, ) -> Result<Vec<(i64, f64, f64, f64, f64)>, DbError>

Visits by quarter hour since the epoch, which the caller folds into local weekdays and hours, keeping time zones out of SQL. Each is (quarter, visits, visitors, pageviews, bounced).

Source

pub async fn realtime(&self, site: &str, now: i64) -> Result<Value, DbError>

Who is on the site now: the last five minutes, and the last thirty by the minute.

Trait Implementations§

Source§

impl Clone for SqlStore

Source§

fn clone(&self) -> Self

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T> FromRef<T> for T
where T: Clone,

Source§

fn from_ref(input: &T) -> T

Converts to this type from a reference to the input type.
Source§

impl<A, B, T> HttpServerConnExec<A, B> for T
where B: Body,

Source§

impl<T> Instrument for T

Source§

fn instrument(self, span: Span) -> Instrumented<Self> ⓘ

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Source§

fn in_current_span(self) -> Instrumented<Self> ⓘ

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> PolicyExt for T
where T: ?Sized,

Source§

fn and<P, B, E>(self, other: P) -> And<T, P>
where T: Sized + Policy<B, E>, P: Policy<B, E>,

Create a new Policy that returns Action::Follow only if self and other return Action::Follow. Read more
Source§

fn or<P, B, E>(self, other: P) -> Or<T, P>
where T: Sized + Policy<B, E>, P: Policy<B, E>,

Create a new Policy that returns Action::Follow if either self or other returns Action::Follow. Read more
Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = !

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, !>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<T> WithSubscriber for T

Source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self> ⓘ
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

fn with_current_subscriber(self) -> WithDispatch<Self> ⓘ

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more