chitralverma commented on code in PR #7883:
URL: https://github.com/apache/opendal/pull/7883#discussion_r3563121164
##########
dev/src/generate/python.j2:
##########
@@ -81,3 +82,123 @@ impl_enum_to_str!(
{%- endfor %}
}
);
+
+pub trait ConfigBuilder: Send + Sync {
+ fn build(&self) -> PyResult<ocore::Operator>;
+ fn scheme(&self) -> &'static str;
+ fn to_map(&self) -> HashMap<String, String>;
+ fn is_picklable(&self) -> bool;
+}
+
+/// Base class for all service configs.
+#[pyclass(module = "opendal.services", subclass)]
+pub struct ServiceConfig(pub Box<dyn ConfigBuilder>);
+
+#[pymethods]
+impl ServiceConfig {
+ /// The service scheme this config targets, e.g. ``"s3"``.
+ #[getter]
+ pub fn scheme(&self) -> &'static str {
+ self.0.scheme()
+ }
+}
+{% for name in srvs %}
+#[cfg(feature = "{{ service_to_feature(name) }}")]
+{{ config_class_doc(name) }}
+#[pyclass(module = "opendal.services", extends = ServiceConfig, frozen,
skip_from_py_object)]
+#[derive(Clone)]
+pub struct {{ service_to_pascal(name) }}Config(ocore::services::{{
service_to_pascal(name) }}Config);
+
+#[cfg(feature = "{{ service_to_feature(name) }}")]
+#[allow(deprecated)]
+impl ConfigBuilder for {{ service_to_pascal(name) }}Config {
+ fn build(&self) -> PyResult<ocore::Operator> {
+ ocore::Operator::from_config(self.0.clone()).map_err(format_pyerr)
+ }
+ fn scheme(&self) -> &'static str {
+ "{{ snake_to_kebab_case(name) }}"
+ }
+ fn to_map(&self) -> HashMap<String, String> {
+ #[allow(unused_mut)]
+ let mut map = HashMap::new();
+{%- for field in srvs[name].config %}
+{%- set line = config_to_map(field) %}
+{%- if line %}
+ {{ line }}
+{%- endif %}
+{%- endfor %}
+ map
+ }
+ fn is_picklable(&self) -> bool {
+ #[allow(unused_mut)]
+ let mut ok = true;
+{%- for field in srvs[name].config %}
+{%- set line = config_picklable(field) %}
+{%- if line %}
+ {{ line }}
+{%- endif %}
+{%- endfor %}
+ ok
+ }
+}
+
+#[cfg(feature = "{{ service_to_feature(name) }}")]
+#[allow(deprecated)]
+#[pymethods]
+impl {{ service_to_pascal(name) }}Config {
+ #[new]
Review Comment:
PyO3 pyclasses are constructed via `#[new]` (`__new__`) — that's where the
Rust struct fields are populated and the `extends = ServiceConfig` subclass is
built. `__init__` runs after the Rust object already exists and can't set its
fields, so we can't emit a real `__init__` regardless of mutability.
The `__new__` → `__init__` rewrite is stub-only (cosmetic):
mkdocstrings-python 2.0.5 renders the constructor signature only from
`__init__`, not `__new__`. It doesn't affect runtime. Happy to drop it for a
cleaner docs approach if one exists.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]