1use std::any::TypeId;
2use std::cell::RefCell;
3use std::fmt;
4use std::fmt::{Debug, Formatter, Result};
5use std::hash::{Hash, Hasher};
6use std::marker::PhantomData;
7use std::sync::{Arc, RwLock};
8
9use super::*;
10
11#[derive(Clone)]
12pub struct DefaultRawPropertyConfig {
13 key: ImmutableKey,
14 value_type: TypeId,
15 default_value: Option<ImmutableValue>,
16 value_converters: Arc<Vec<Box<dyn RawTypeConverter>>>,
17 value_filter: Option<Box<dyn RawValueFilter>>,
18 doc: Option<String>,
19 _static: bool,
20 required: bool,
21}
22
23impl DefaultRawPropertyConfig {
24 pub fn check_valid(&self) {
25 if self.default_value.is_none() || self.value_filter.is_none() {
26 return;
27 }
28
29 let new_value = self
30 .value_filter
31 .as_ref()
32 .unwrap()
33 .filter_raw(self.default_value.as_ref().unwrap().raw_boxed());
34 if new_value.is_none() {
35 panic!(
36 "None is returned when the value filter filters the default value, \
37 you should either fix the default value or fix the value filter!\n\
38 Property Config: {:?}",
39 self
40 );
41 }
42 }
43}
44
45impl RawPropertyConfig for DefaultRawPropertyConfig {
46 fn get_raw_key(&self) -> Box<dyn Key> {
47 self.key.raw_boxed()
48 }
49
50 fn get_value_type(&self) -> TypeId {
51 self.value_type
52 }
53
54 fn get_raw_default_value(&self) -> Option<Box<dyn Value>> {
55 self.default_value.as_ref().map(|v| v.raw_boxed())
56 }
57
58 fn get_value_converters(&self) -> &[Box<dyn RawTypeConverter>] {
59 self.value_converters.as_ref().as_slice()
60 }
61
62 fn get_value_filter(&self) -> Option<&dyn RawValueFilter> {
63 self.value_filter.as_ref().map(|f| f.as_ref())
64 }
65
66 fn get_doc(&self) -> Option<&str> {
67 self.doc.as_ref().map(|v| v.as_str())
68 }
69
70 fn is_static(&self) -> bool {
71 self._static
72 }
73
74 fn is_required(&self) -> bool {
75 self.required
76 }
77
78 as_boxed!(impl RawPropertyConfig);
79 as_trait!(impl RawPropertyConfig);
80}
81
82impl Hash for DefaultRawPropertyConfig {
83 fn hash<H: Hasher>(&self, state: &mut H) {
84 self.key.hash(state);
85 }
86}
87
88impl PartialEq for DefaultRawPropertyConfig {
89 fn eq(&self, other: &Self) -> bool {
90 self.key == other.key
91 && self.value_type == other.value_type
92 && self.default_value == other.default_value
93 && self.value_converters.as_ref() == other.value_converters.as_ref()
94 && self.value_filter == other.value_filter
95 && self.doc == other.doc
96 && self._static == other._static
97 && self.required == other.required
98 }
99}
100
101impl Eq for DefaultRawPropertyConfig {}
102
103impl Debug for DefaultRawPropertyConfig {
104 fn fmt(&self, f: &mut Formatter) -> Result {
105 write!(
106 f,
107 "{} {{\n\tkey: {:?},\n\tvalue_type: {:?},\n\tdefault_value: {:?},\n\t\
108 value_converters: {:?},\n\tvalue_filter: {:?},\n\tdoc: {:?},\n\tstatic: {:?},\n\t\
109 required: {:?}\n}}",
110 self.type_name(),
111 self.key,
112 self.value_type,
113 self.default_value,
114 self.value_converters,
115 self.value_filter.type_name(),
116 self.doc,
117 self._static,
118 self.required
119 )
120 }
121}
122
123unsafe impl Sync for DefaultRawPropertyConfig {}
124unsafe impl Send for DefaultRawPropertyConfig {}
125
126#[derive(Clone)]
127pub struct DefaultPropertyConfig<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> {
128 raw: Arc<Box<dyn RawPropertyConfig>>,
129 k: PhantomData<K>,
130 v: PhantomData<V>,
131}
132
133impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> DefaultPropertyConfig<K, V> {
134 pub fn from_raw(config: &dyn RawPropertyConfig) -> Self {
135 DefaultPropertyConfig {
136 raw: Arc::new(RawPropertyConfig::clone_boxed(config)),
137 k: PhantomData::<K>,
138 v: PhantomData::<V>,
139 }
140 }
141}
142
143impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Hash for DefaultPropertyConfig<K, V> {
144 fn hash<H: Hasher>(&self, state: &mut H) {
145 self.raw.as_ref().hash(state);
146 }
147}
148
149impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> PartialEq
150 for DefaultPropertyConfig<K, V>
151{
152 fn eq(&self, other: &Self) -> bool {
153 self.raw.as_ref() == other.raw.as_ref()
154 }
155}
156
157impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Eq for DefaultPropertyConfig<K, V> {}
158
159impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> fmt::Debug
160 for DefaultPropertyConfig<K, V>
161{
162 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
163 write!(
164 f,
165 "{} {{\n\tkey: {:?},\n\tvalue_type: {:?},\n\tdefault_value: {:?},\n\t\
166 value_converters: {:?},\n\tvalue_filter: {:?},\n\tdoc: {:?},\n\tstatic: {:?},\n\t\
167 required: {:?}\n}}",
168 self.type_name(),
169 self.get_raw_key(),
170 self.get_value_type(),
171 self.get_raw_default_value(),
172 self.get_value_converters(),
173 self.get_value_filter().type_name(),
174 self.get_doc(),
175 self.is_static(),
176 self.is_required()
177 )
178 }
179}
180
181unsafe impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Sync
182 for DefaultPropertyConfig<K, V>
183{
184}
185unsafe impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Send
186 for DefaultPropertyConfig<K, V>
187{
188}
189
190impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> RawPropertyConfig
191 for DefaultPropertyConfig<K, V>
192{
193 fn get_raw_key(&self) -> Box<dyn Key> {
194 self.raw.get_raw_key()
195 }
196
197 fn get_value_type(&self) -> TypeId {
198 self.raw.get_value_type()
199 }
200
201 fn get_raw_default_value(&self) -> Option<Box<dyn Value>> {
202 self.raw.get_raw_default_value()
203 }
204
205 fn get_value_converters(&self) -> &[Box<dyn RawTypeConverter>] {
206 self.raw.get_value_converters()
207 }
208
209 fn get_value_filter(&self) -> Option<&dyn RawValueFilter> {
210 self.raw.get_value_filter()
211 }
212
213 fn get_doc(&self) -> Option<&str> {
214 self.raw.get_doc()
215 }
216
217 fn is_static(&self) -> bool {
218 self.raw.is_static()
219 }
220
221 fn is_required(&self) -> bool {
222 self.raw.is_required()
223 }
224
225 as_boxed!(impl RawPropertyConfig);
226 as_trait!(impl RawPropertyConfig);
227}
228
229impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> PropertyConfig<K, V>
230 for DefaultPropertyConfig<K, V>
231{
232 fn get_key(&self) -> Box<K> {
233 Box::new(
234 self.raw
235 .get_raw_key()
236 .as_ref()
237 .as_any_ref()
238 .downcast_ref::<K>()
239 .unwrap()
240 .clone(),
241 )
242 }
243
244 fn get_default_value(&self) -> Option<Box<V>> {
245 self.raw
246 .get_raw_default_value()
247 .map(|v| Box::new(v.as_ref().as_any_ref().downcast_ref::<V>().unwrap().clone()))
248 }
249
250 as_boxed!(impl PropertyConfig<K, V>);
251}
252
253pub struct DefaultPropertyConfigBuilder<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> {
254 key: Option<Box<K>>,
255 value_type: TypeId,
256 default_value: Option<Box<V>>,
257 value_converters: Vec<Box<dyn RawTypeConverter>>,
258 value_filter: Option<Box<dyn ValueFilter<V>>>,
259 doc: Option<String>,
260 _static: bool,
261 required: bool,
262}
263
264impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> DefaultPropertyConfigBuilder<K, V> {
265 pub fn new() -> Self {
266 Self {
267 key: None,
268 value_type: TypeId::of::<V>(),
269 default_value: None,
270 value_converters: Vec::new(),
271 value_filter: None,
272 doc: None,
273 _static: false,
274 required: false,
275 }
276 }
277}
278
279impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> PropertyConfigBuilder<K, V>
280 for DefaultPropertyConfigBuilder<K, V>
281{
282 fn set_key(&mut self, key: Box<K>) -> &mut dyn PropertyConfigBuilder<K, V> {
283 self.key = Some(key);
284 self
285 }
286
287 fn set_default_value(&mut self, default_value: Box<V>) -> &mut dyn PropertyConfigBuilder<K, V> {
288 self.default_value = Some(default_value);
289 self
290 }
291
292 fn add_value_converter(
293 &mut self,
294 value_converter: Box<dyn RawTypeConverter>,
295 ) -> &mut dyn PropertyConfigBuilder<K, V> {
296 self.value_converters.push(value_converter);
297 self
298 }
299
300 fn add_value_converters(
301 &mut self,
302 value_converters: Vec<Box<dyn RawTypeConverter>>,
303 ) -> &mut dyn PropertyConfigBuilder<K, V> {
304 let mut value_converters = value_converters;
305 self.value_converters.append(&mut value_converters);
306 self
307 }
308
309 fn set_value_filter(
310 &mut self,
311 value_filter: Box<dyn ValueFilter<V>>,
312 ) -> &mut dyn PropertyConfigBuilder<K, V> {
313 self.value_filter = Some(value_filter);
314 self
315 }
316
317 fn set_doc(&mut self, doc: &str) -> &mut dyn PropertyConfigBuilder<K, V> {
318 self.doc = Some(doc.to_string());
319 self
320 }
321
322 fn set_static(&mut self, is_static: bool) -> &mut dyn PropertyConfigBuilder<K, V> {
323 self._static = is_static;
324 self
325 }
326
327 fn set_required(&mut self, required: bool) -> &mut dyn PropertyConfigBuilder<K, V> {
328 self.required = required;
329 self
330 }
331
332 fn build(&self) -> Box<dyn PropertyConfig<K, V>> {
333 let raw = DefaultRawPropertyConfig {
334 key: ImmutableKey::wrap(self.key.clone().unwrap()),
335 value_type: self.value_type,
336 default_value: self
337 .default_value
338 .as_ref()
339 .map(|v| v.clone())
340 .map(|v| ImmutableValue::wrap(v)),
341 value_converters: Arc::new(self.value_converters.clone()),
342 value_filter: self
343 .value_filter
344 .as_ref()
345 .map(|f| RawValueFilter::clone_boxed(f.as_ref())),
346 doc: self.doc.clone(),
347 _static: self._static,
348 required: self.required,
349 };
350 raw.check_valid();
351 Box::new(DefaultPropertyConfig {
352 raw: Arc::new(RawPropertyConfig::clone_boxed(&raw)),
353 k: PhantomData::<K>,
354 v: PhantomData::<V>,
355 })
356 }
357}
358
359#[derive(Clone)]
360pub struct DefaultRawProperty {
361 config: Arc<Box<dyn RawPropertyConfig>>,
362 value: Arc<RwLock<RefCell<Option<ImmutableValue>>>>,
363 source: Arc<RwLock<RefCell<Option<Box<dyn ConfigurationSource>>>>>,
364 change_listeners: Arc<RwLock<Vec<RawPropertyChangeListener>>>,
365}
366
367impl DefaultRawProperty {
368 pub fn new(config: &dyn RawPropertyConfig) -> Self {
369 DefaultRawProperty {
370 config: Arc::new(RawPropertyConfig::clone_boxed(config)),
371 value: Arc::new(RwLock::new(RefCell::new(None))),
372 source: Arc::new(RwLock::new(RefCell::new(None))),
373 change_listeners: Arc::new(RwLock::new(Vec::new())),
374 }
375 }
376
377 pub fn update(
378 &self,
379 value: Option<Box<dyn Value>>,
380 source: Option<Box<dyn ConfigurationSource>>,
381 ) {
382 let value_lock = self.value.write().unwrap();
383 value_lock.replace(value.map(|v| ImmutableValue::wrap(v)));
384 let source_lock = self.source.write().unwrap();
385 source_lock.replace(source);
386 }
387
388 pub fn raise_change_event(&self, event: &dyn RawPropertyChangeEvent) {
389 let listeners = self.change_listeners.read().unwrap();
390 for listener in listeners.iter() {
391 listener(event);
392 }
393 }
394}
395
396impl RawProperty for DefaultRawProperty {
397 fn get_raw_config(&self) -> &dyn RawPropertyConfig {
398 self.config.as_ref().as_ref()
399 }
400
401 fn get_raw_value(&self) -> Option<Box<dyn Value>> {
402 let cell = self.value.read().unwrap();
403 let r = cell.borrow();
404 r.as_ref().map(|v| v.raw_boxed())
405 }
406
407 fn add_raw_change_listener(&self, listener: RawPropertyChangeListener) {
408 self.change_listeners.write().unwrap().push(listener);
409 }
410
411 fn get_source(&self) -> Option<Box<dyn ConfigurationSource>> {
412 let cell = self.source.read().unwrap();
413 let r = cell.borrow();
414 r.as_ref().map(|v| v.clone())
415 }
416
417 as_boxed!(impl RawProperty);
418 as_trait!(impl RawProperty);
419}
420
421impl PartialEq for DefaultRawProperty {
422 fn eq(&self, other: &Self) -> bool {
423 self.value.as_ref().reference_equals(other.value.as_ref())
424 }
425}
426
427impl Eq for DefaultRawProperty {}
428
429impl fmt::Debug for DefaultRawProperty {
430 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
431 write!(
432 f,
433 "{} {{\n\tconfig: {:?},\n\tvalue: {:?},\n\tsource: {:?}\n}}",
434 self.type_name(),
435 self.get_raw_config(),
436 self.get_raw_value(),
437 self.get_source()
438 .map(|v| v.get_config().get_name().to_string())
439 )
440 }
441}
442
443unsafe impl Sync for DefaultRawProperty {}
444unsafe impl Send for DefaultRawProperty {}
445
446#[derive(Clone)]
447pub struct DefaultProperty<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> {
448 config: Arc<Box<dyn PropertyConfig<K, V>>>,
449 raw: Arc<Box<dyn RawProperty>>,
450}
451
452impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> DefaultProperty<K, V> {
453 pub fn from_raw(property: &dyn RawProperty) -> Self {
454 DefaultProperty {
455 config: Arc::new(Box::new(DefaultPropertyConfig::from_raw(
456 property.get_raw_config(),
457 ))),
458 raw: Arc::new(RawProperty::clone_boxed(property)),
459 }
460 }
461}
462
463impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> PartialEq for DefaultProperty<K, V> {
464 fn eq(&self, other: &Self) -> bool {
465 self.raw.as_ref() == other.raw.as_ref()
466 }
467}
468
469impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Eq for DefaultProperty<K, V> {}
470
471impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> fmt::Debug for DefaultProperty<K, V> {
472 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
473 write!(
474 f,
475 "{} {{\n\tvalue: {:?},\n\tsource: {:?},\n\tconfig: {:?}\n}}",
476 self.type_name(),
477 self.get_raw_config(),
478 self.get_raw_value(),
479 self.get_source()
480 .map(|v| v.get_config().get_name().to_string())
481 )
482 }
483}
484
485unsafe impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Sync for DefaultProperty<K, V> {}
486unsafe impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Send for DefaultProperty<K, V> {}
487
488impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> RawProperty for DefaultProperty<K, V> {
489 fn get_raw_config(&self) -> &dyn RawPropertyConfig {
490 self.raw.get_raw_config()
491 }
492
493 fn get_raw_value(&self) -> Option<Box<dyn Value>> {
494 self.raw.get_raw_value()
495 }
496
497 fn add_raw_change_listener(&self, listener: RawPropertyChangeListener) {
498 self.raw.add_raw_change_listener(listener);
499 }
500
501 fn get_source(&self) -> Option<Box<dyn ConfigurationSource>> {
502 self.raw.get_source()
503 }
504
505 as_boxed!(impl RawProperty);
506 as_trait!(impl RawProperty);
507}
508
509impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Property<K, V>
510 for DefaultProperty<K, V>
511{
512 fn get_config(&self) -> &dyn PropertyConfig<K, V> {
513 self.config.as_ref().as_ref()
514 }
515
516 fn get_value(&self) -> Option<Box<V>> {
517 self.raw
518 .get_raw_value()
519 .map(|v| Box::new(v.as_ref().as_any_ref().downcast_ref::<V>().unwrap().clone()))
520 }
521
522 fn add_change_listener(&self, listener: PropertyChangeListener<K, V>) {
523 self.raw
524 .add_raw_change_listener(Arc::new(Box::new(move |e| {
525 listener(&DefaultPropertyChangeEvent::from_raw(e));
526 })));
527 }
528
529 as_boxed!(impl Property<K, V>);
530}
531
532#[derive(Clone, Debug)]
533pub struct DefaultRawPropertyChangeEvent {
534 property: Arc<Box<dyn RawProperty>>,
535 old_value: Option<ImmutableValue>,
536 new_value: Option<ImmutableValue>,
537 change_time: u128,
538}
539
540impl DefaultRawPropertyChangeEvent {
541 pub fn new(
542 property: Arc<Box<dyn RawProperty>>,
543 old_value: Option<ImmutableValue>,
544 new_value: Option<ImmutableValue>,
545 change_time: u128,
546 ) -> Self {
547 DefaultRawPropertyChangeEvent {
548 property,
549 old_value,
550 new_value,
551 change_time,
552 }
553 }
554}
555
556impl PartialEq for DefaultRawPropertyChangeEvent {
557 fn eq(&self, other: &Self) -> bool {
558 self.property.as_ref() == other.property.as_ref()
559 && self.old_value == other.old_value
560 && self.new_value == other.new_value
561 && self.change_time == other.change_time
562 }
563}
564
565impl Eq for DefaultRawPropertyChangeEvent {}
566
567unsafe impl Sync for DefaultRawPropertyChangeEvent {}
568unsafe impl Send for DefaultRawPropertyChangeEvent {}
569
570impl RawPropertyChangeEvent for DefaultRawPropertyChangeEvent {
571 fn get_raw_property(&self) -> &dyn RawProperty {
572 self.property.as_ref().as_ref()
573 }
574
575 fn get_raw_old_value(&self) -> Option<Box<dyn Value>> {
576 self.old_value.as_ref().map(|v| v.raw_boxed())
577 }
578
579 fn get_raw_new_value(&self) -> Option<Box<dyn Value>> {
580 self.new_value.as_ref().map(|v| v.raw_boxed())
581 }
582
583 fn get_change_time(&self) -> u128 {
584 self.change_time
585 }
586
587 as_boxed!(impl RawPropertyChangeEvent);
588 as_trait!(impl RawPropertyChangeEvent);
589}
590
591#[derive(Clone)]
592pub struct DefaultPropertyChangeEvent<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> {
593 property: Arc<Box<dyn Property<K, V>>>,
594 raw: Arc<Box<dyn RawPropertyChangeEvent>>,
595}
596
597impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> DefaultPropertyChangeEvent<K, V> {
598 pub fn from_raw(event: &dyn RawPropertyChangeEvent) -> Self {
599 let property = DefaultProperty::<K, V>::from_raw(event.get_raw_property());
600 DefaultPropertyChangeEvent {
601 property: Arc::new(Box::new(property)),
602 raw: Arc::new(RawPropertyChangeEvent::clone_boxed(event)),
603 }
604 }
605}
606
607impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> PartialEq
608 for DefaultPropertyChangeEvent<K, V>
609{
610 fn eq(&self, other: &Self) -> bool {
611 self.raw.as_ref() == other.raw.as_ref()
612 }
613}
614
615impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Eq
616 for DefaultPropertyChangeEvent<K, V>
617{
618}
619
620impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> fmt::Debug
621 for DefaultPropertyChangeEvent<K, V>
622{
623 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
624 write!(
625 f,
626 "{} {{\n\tproperty: {:?},\n\told_value: {:?},\n\tnew_value: {:?},\n\t\
627 change_time: {:?}\n}}",
628 self.type_name(),
629 self.get_property(),
630 self.get_old_value(),
631 self.get_new_value(),
632 self.get_change_time()
633 )
634 }
635}
636
637unsafe impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Sync
638 for DefaultPropertyChangeEvent<K, V>
639{
640}
641unsafe impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> Send
642 for DefaultPropertyChangeEvent<K, V>
643{
644}
645
646impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> RawPropertyChangeEvent
647 for DefaultPropertyChangeEvent<K, V>
648{
649 fn get_raw_property(&self) -> &dyn RawProperty {
650 self.raw.get_raw_property()
651 }
652
653 fn get_raw_old_value(&self) -> Option<Box<dyn Value>> {
654 self.raw.get_raw_old_value()
655 }
656
657 fn get_raw_new_value(&self) -> Option<Box<dyn Value>> {
658 self.raw.get_raw_new_value()
659 }
660
661 fn get_change_time(&self) -> u128 {
662 self.raw.get_change_time()
663 }
664
665 as_boxed!(impl RawPropertyChangeEvent);
666 as_trait!(impl RawPropertyChangeEvent);
667}
668
669impl<K: ?Sized + KeyConstraint, V: ?Sized + ValueConstraint> PropertyChangeEvent<K, V>
670 for DefaultPropertyChangeEvent<K, V>
671{
672 fn get_property(&self) -> &dyn Property<K, V> {
673 self.property.as_ref().as_ref()
674 }
675
676 fn get_old_value(&self) -> Option<Box<V>> {
677 self.raw
678 .get_raw_old_value()
679 .map(|v| Box::new(v.as_ref().as_any_ref().downcast_ref::<V>().unwrap().clone()))
680 }
681
682 fn get_new_value(&self) -> Option<Box<V>> {
683 self.raw
684 .get_raw_new_value()
685 .map(|v| Box::new(v.as_ref().as_any_ref().downcast_ref::<V>().unwrap().clone()))
686 }
687
688 as_boxed!(impl PropertyChangeEvent<K, V>);
689}
690
691#[cfg(test)]
692mod test {
693
694 use super::*;
695 use std::any::Any;
696 use std::thread::*;
697 use std::time::*;
698
699 fn new_converter() -> DefaultTypeConverter<String, i32> {
700 DefaultTypeConverter::<String, i32>::new(Box::new(move |v| match v.parse::<i32>() {
701 Ok(v) => Ok(Box::new(v)),
702 Err(err) => Err(Box::new(err)),
703 }))
704 }
705
706 fn new_filter() -> DefaultValueFilter<i32> {
707 DefaultValueFilter::new(Box::new(move |v| {
708 if *v > 10 {
709 Some(Box::new(*v + 1))
710 } else if *v > 0 {
711 Some(v)
712 } else {
713 None
714 }
715 }))
716 }
717
718 fn new_config() -> Box<dyn PropertyConfig<i32, i32>> {
719 let c = new_converter();
720 let f = new_filter();
721
722 new_config_with(&c, &f)
723 }
724
725 fn new_config_with(
726 c: &DefaultTypeConverter<String, i32>,
727 f: &DefaultValueFilter<i32>,
728 ) -> Box<dyn PropertyConfig<i32, i32>> {
729 DefaultPropertyConfigBuilder::new()
730 .set_key(Box::new(1))
731 .set_default_value(Box::new(2))
732 .add_value_converter(RawTypeConverter::clone_boxed(c))
733 .set_value_filter(Box::new(f.clone()))
734 .set_doc("test property")
735 .build()
736 }
737
738 #[test]
739 fn property_config_test() {
740 let c = new_converter();
741 let f = new_filter();
742 let config = new_config_with(&c, &f);
743 println!("{:?}", config);
744 assert_eq!(1, *config.get_key());
745 assert_eq!(2.type_id(), config.get_value_type());
746 assert_eq!(Some(Box::new(2)), config.get_default_value());
747 assert_eq!(Some("test property"), config.get_doc());
748 assert_eq!(false, config.is_static());
749 assert_eq!(false, config.is_required());
750
751 assert_eq!(&config, &config.clone());
752 let boxed_config = RawPropertyConfig::clone_boxed(config.as_ref());
753 assert_eq!(&boxed_config, &boxed_config.clone());
754
755 let s = "1".to_string();
756 let s2 = "xx1".to_string();
757 let rc = config.get_value_converters().get(0).unwrap().as_ref();
758 assert_eq!(
759 Ok(Value::to_boxed(1)),
760 rc.convert_raw(Value::as_trait_ref(&s))
761 );
762 assert_ne!(
763 Ok(Value::to_boxed(2)),
764 rc.convert_raw(Value::as_trait_ref(&s))
765 );
766 assert!(rc.convert_raw(Value::as_trait_ref(&s2)).is_err());
767 assert!(rc.convert_raw(Value::as_trait_ref(&true)).is_err());
768 let rf = config.get_value_filter().unwrap();
769 assert_eq!(Some(Value::to_boxed(1)), rf.filter_raw(Value::to_boxed(1)));
770 assert_eq!(
771 Some(Value::to_boxed(12)),
772 rf.filter_raw(Value::to_boxed(11))
773 );
774 assert_eq!(None, rf.filter_raw(Value::to_boxed(0)));
775 assert_eq!(None, rf.filter_raw(Value::to_boxed(s2)));
776
777 let config2 = new_config_with(&c, &f);
778 assert!(!config.reference_equals(&config2));
779 assert!(
780 !config
781 .as_ref()
782 .reference_equals(config2.as_ref().as_any_ref())
783 );
784 assert!(config.as_ref().equals(config2.as_ref().as_any_ref()));
785 assert!(
786 RawPropertyConfig::as_trait_ref(config.as_ref())
787 .equals(RawPropertyConfig::as_trait_ref(config2.as_ref()).as_any_ref())
788 );
789 assert_eq!(
790 &RawPropertyConfig::clone_boxed(config.as_ref()),
791 &RawPropertyConfig::clone_boxed(config2.as_ref())
792 );
793 }
794
795 #[should_panic]
796 #[test]
797 fn invalid_property_config_test() {
798 let f = new_filter();
799 DefaultPropertyConfigBuilder::new()
800 .set_key(Box::new(1))
801 .set_default_value(Box::new(0))
802 .set_value_filter(Box::new(f.clone()))
803 .set_doc("test property")
804 .build();
805 }
806
807 #[test]
808 fn property_test() {
809 let config = new_config();
810 let property = DefaultRawProperty::new(RawPropertyConfig::as_trait_ref(config.as_ref()));
811 println!("property: {:?}", property);
812 assert!(
813 property
814 .get_raw_config()
815 .equals(config.as_ref().as_any_ref())
816 );
817 assert_eq!(None, property.get_raw_value());
818 property.update(Some(Box::new(0)), None);
819 assert_eq!(Some(Value::to_boxed(0)), property.get_raw_value());
820 assert_eq!(None, property.get_source());
821
822 assert_eq!(&property, &property.clone());
823 let boxed_property = RawProperty::clone_boxed(&property);
824 assert_eq!(&boxed_property, &boxed_property.clone());
825
826 let changed = Arc::new(RwLock::new(Box::new(false)));
827 let changed_clone = changed.clone();
828 property.add_raw_change_listener(Arc::new(Box::new(move |e| {
829 println!(
830 "property: {:?}, old_value: {:?}, new_value: {:?}, change_time: {:?}",
831 e.get_raw_property(),
832 e.get_raw_old_value(),
833 e.get_raw_new_value(),
834 e.get_change_time()
835 );
836 let mut v = changed_clone.write().unwrap();
837 **v = true;
838 })));
839 property.update(Some(Box::new(1)), None);
840 let arc_property = Arc::new(RawProperty::to_boxed(property.clone()));
841 let start = SystemTime::now();
842 let since_the_epoch = start.duration_since(UNIX_EPOCH).unwrap();
843 let event = DefaultRawPropertyChangeEvent::new(
844 arc_property,
845 Some(ImmutableValue::new(0)),
846 Some(ImmutableValue::new(0)),
847 since_the_epoch.as_millis(),
848 );
849 assert_eq!(false, **changed.read().unwrap());
850 property.raise_change_event(&event);
851 sleep(Duration::from_millis(100));
852 assert_eq!(true, **changed.read().unwrap());
853
854 let property2 = DefaultProperty::<i32, i32>::from_raw(&property);
855 println!("property: {:?}", property2);
856 assert_eq!(Some(Box::new(1)), property2.get_value());
857 property.update(Some(Box::new(2)), None);
858 assert_eq!(Some(Box::new(2)), property2.get_value());
859 let changed2 = Arc::new(RwLock::new(Box::new(false)));
860 let changed2_clone = changed2.clone();
861 property2.add_change_listener(Arc::new(Box::new(move |e| {
862 println!(
863 "property: {:?}, old_value: {:?}, new_value: {:?}, change_time: {:?}",
864 e.get_property(),
865 e.get_old_value(),
866 e.get_new_value(),
867 e.get_change_time()
868 );
869 let mut v = changed2_clone.write().unwrap();
870 **v = true;
871 })));
872
873 assert_eq!(&property2, &property2.clone());
874 let boxed_property2 = Property::<i32, i32>::clone_boxed(&property2);
875 assert_eq!(&boxed_property2, &boxed_property2.clone());
876
877 let arc_property = Arc::new(RawProperty::to_boxed(property.clone()));
878 let start = SystemTime::now();
879 let since_the_epoch = start.duration_since(UNIX_EPOCH).unwrap();
880 let event = DefaultRawPropertyChangeEvent::new(
881 arc_property,
882 Some(ImmutableValue::new(0)),
883 Some(ImmutableValue::new(0)),
884 since_the_epoch.as_millis(),
885 );
886 assert_eq!(false, **changed2.read().unwrap());
887 property.raise_change_event(&event);
888 sleep(Duration::from_millis(100));
889 assert_eq!(true, **changed2.read().unwrap());
890 }
891
892 #[test]
893 fn property_change_event_test() {
894 let config = DefaultPropertyConfigBuilder::new()
895 .set_key(Box::new(1))
896 .set_default_value(Box::new(2))
897 .build();
898 let property = DefaultRawProperty::new(RawPropertyConfig::as_trait_ref(config.as_ref()));
899 let arc_property = Arc::new(RawProperty::to_boxed(property.clone()));
900 let start = SystemTime::now();
901 let since_the_epoch = start.duration_since(UNIX_EPOCH).unwrap();
902 let event = DefaultRawPropertyChangeEvent::new(
903 arc_property,
904 Some(ImmutableValue::new(0)),
905 Some(ImmutableValue::new(1)),
906 since_the_epoch.as_millis(),
907 );
908
909 assert_eq!(&event, &event.clone());
910 let boxed_event = RawPropertyChangeEvent::clone_boxed(&event);
911 assert_eq!(&boxed_event, &boxed_event.clone());
912
913 println!("property event: {:?}", event);
914 assert!(property.equals(event.get_raw_property().as_any_ref()));
915 assert_eq!(Some(Value::to_boxed(0)), event.get_raw_old_value());
916 assert_eq!(Some(Value::to_boxed(1)), event.get_raw_new_value());
917 assert_eq!(since_the_epoch.as_millis(), event.get_change_time());
918 assert_eq!(event, event.clone());
919
920 let event2 = DefaultPropertyChangeEvent::<i32, i32>::from_raw(&event);
921 println!("property event: {:?}", event2);
922 assert_eq!(&event2, &event2.clone());
923 let boxed_event2 = RawPropertyChangeEvent::clone_boxed(&event2);
924 assert_eq!(&boxed_event2, &boxed_event2.clone());
925 assert_eq!(1, *event2.get_property().get_config().get_key());
926 assert_eq!(Some(Value::to_boxed(0)), event2.get_raw_old_value());
927 assert_eq!(Some(Value::to_boxed(1)), event2.get_raw_new_value());
928 assert_eq!(Some(Box::new(0)), event2.get_old_value());
929 assert_eq!(Some(Box::new(1)), event2.get_new_value());
930 assert_eq!(since_the_epoch.as_millis(), event2.get_change_time());
931 assert_eq!(event2, event2.clone());
932 }
933}