/// Drives high-level blocking logic and is responsible for loading filter lists into an optimized /// format that can be queried efficiently. /// /// For performance optimization reasons, the [`Engine`] is not designed to have rules added or /// removed after its initial creation. Making changes to the rules loaded is accomplished by /// creating a new engine to replace it. /// /// ## Usage /// /// ### Initialization /// /// You'll first want to combine all of your filter lists in a [`FilterSet`], which will parse list /// header metadata. Once all lists have been composed together, you can call /// [`Engine::from_filter_set`] to start using them for blocking. /// /// You may also want to supply certain assets for `$redirect` filters and `##+js(...)` scriptlet /// injections. These are known as [`Resource`]s, and can be provided with /// [`Engine::use_resources`]. See the [`crate::resources`] module for more information. /// /// ### Network blocking /// /// Use the [`Engine::check_network_request`] method to determine how to handle a network request. /// /// If you _only_ need network blocking, consider using a [`Blocker`] directly. /// /// ### Cosmetic filtering /// /// Call [`Engine::url_cosmetic_resources`] to determine what actions should be taken to prepare a /// particular page before it starts loading. /// /// Once the page has been loaded, any new CSS classes or ids that appear on the page should be passed to /// [`Engine::hidden_class_id_selectors`] on an ongoing basis to determine additional elements that /// should be hidden dynamically. pubstruct Engine {
blocker: Blocker,
cosmetic_cache: CosmeticFilterCache,
resources: ResourceStorage,
filter_data_context: FilterDataContextRef,
}
/// Loads rules from the given `FilterSet`. It is recommended to use a `FilterSet` when adding /// rules from multiple sources. pubfn from_filter_set(set: FilterSet, optimize: bool) -> Self { let FilterSet {
network_filters,
cosmetic_filters,
..
} = set;
let memory = make_flatbuffer(network_filters, cosmetic_filters, optimize);
let filter_data_context = FilterDataContext::new(memory);
/// Check if a request for a network resource from `url`, of type `request_type`, initiated by /// `source_url`, should be blocked. pubfn check_network_request(&self, request: &Request) -> BlockerResult { self.blocker.check(request, &self.resources)
}
/// Returns a string containing any additional CSP directives that should be added to this /// request's response. Only applies to document and subdocument requests. /// /// If multiple policies are present from different rules, they will be joined by commas. pubfn get_csp_directives(&self, request: &Request) -> Option<String> { self.blocker.get_csp_directives(request)
}
/// Sets this engine's tags to be _only_ the ones provided in `tags`. /// /// Tags can be used to cheaply enable or disable network rules with a corresponding `$tag` /// option. pubfn use_tags(&mutself, tags: &[&str]) { self.blocker.use_tags(tags);
}
/// Sets this engine's tags to additionally include the ones provided in `tags`. /// /// Tags can be used to cheaply enable or disable network rules with a corresponding `$tag` /// option. pubfn enable_tags(&mutself, tags: &[&str]) { self.blocker.enable_tags(tags);
}
/// Sets this engine's tags to no longer include the ones provided in `tags`. /// /// Tags can be used to cheaply enable or disable network rules with a corresponding `$tag` /// option. pubfn disable_tags(&mutself, tags: &[&str]) { self.blocker.disable_tags(tags);
}
/// Checks if a given tag exists in this engine. /// /// Tags can be used to cheaply enable or disable network rules with a corresponding `$tag` /// option. pubfn tag_exists(&self, tag: &str) -> bool { self.blocker.tags_enabled().contains(&tag.to_owned())
}
/// Sets this engine's [Resource]s to be _only_ the ones provided in `resources`. /// /// The resources will be held in-memory. If you have special caching, management, or sharing /// requirements, consider [Engine::use_resource_storage] instead. pubfn use_resources(&mutself, resources: impl IntoIterator<Item = Resource>) { let storage = crate::resources::InMemoryResourceStorage::from_resources(resources); self.use_resource_storage(storage);
}
/// Sets this engine's backend for [Resource] storage to a custom implementation of /// [ResourceStorageBackend]. /// /// If you're okay with the [Engine] holding these resources in-memory, use /// [Engine::use_resources] instead. #[cfg(not(feature = "single-thread"))] pubfn use_resource_storage<R: ResourceStorageBackend + 'static + Sync + Send>(
&mutself,
resources: R,
) { self.resources = ResourceStorage::from_backend(resources);
}
/// Sets this engine's backend for [Resource] storage to a custom implementation of /// [ResourceStorageBackend]. /// /// If you're okay with the [Engine] holding these resources in-memory, use /// [Engine::use_resources] instead. #[cfg(feature = "single-thread")] pubfn use_resource_storage<R: ResourceStorageBackend + 'static>(&mut self, resources: R) { self.resources = ResourceStorage::from_backend(resources);
}
// Cosmetic filter functionality
/// If any of the provided CSS classes or ids could cause a certain generic CSS hide rule /// (i.e. `{ display: none !important; }`) to be required, this method will return a list of /// CSS selectors corresponding to rules referencing those classes or ids, provided that the /// corresponding rules are not excepted. /// /// `exceptions` should be passed directly from `UrlSpecificResources`. pubfn hidden_class_id_selectors(
&self,
classes: impl IntoIterator<Item = impl AsRef<str>>,
ids: impl IntoIterator<Item = impl AsRef<str>>,
exceptions: &HashSet<String>,
) -> Vec<String> { self.cosmetic_cache
.hidden_class_id_selectors(classes, ids, exceptions)
}
/// Returns a set of cosmetic filter resources required for a particular url. Once this has /// been called, all CSS ids and classes on a page should be passed to /// `hidden_class_id_selectors` to obtain any stylesheets consisting of generic rules (if the /// returned `generichide` value is false). pubfn url_cosmetic_resources(&self, url: &str) -> UrlSpecificResources { let request = iflet Ok(request) = Request::new(url, url, "document") {
request
} else { return UrlSpecificResources::empty();
};
let generichide = self.blocker.check_generic_hide(&request); self.cosmetic_cache.hostname_cosmetic_resources(
&self.resources,
&request.hostname,
generichide,
)
}
/// Serializes the `Engine` into a binary format so that it can be quickly reloaded later. pubfn serialize(&self) -> Vec<u8> { let data = self.filter_data_context.memory.data();
serialize_dat_file(data)
}
/// Deserialize the `Engine` from the binary format generated by `Engine::serialize`. /// /// Note that the binary format has a built-in version number that may be incremented. There is /// no guarantee that later versions of the format will be deserializable across minor versions /// of adblock-rust; the format is provided only as a caching optimization. pubfn deserialize(&mutself, serialized: &[u8]) -> Result<(), DeserializationError> { let current_tags = self.blocker.tags_enabled();
let data = deserialize_dat_file(serialized)?; let memory = VerifiedFlatbufferMemory::from_raw(data)
.map_err(DeserializationError::FlatBufferParsingError)?;
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.