package org.theonefx.wcframework.ioc;
import org.theonefx.wcframework.core.exception.BeansException;
import org.theonefx.wcframework.ioc.exception.InvalidPropertyException;
import org.theonefx.wcframework.ioc.exception.PropertyAccessException;
import org.theonefx.wcframework.ioc.exception.PropertyBatchUpdateException;
/**
* 访问带名称的属性(例如Bean的Property或者是某个对象的field)的类的通用接口,是{@link BeanWrapper}的基本服务接口.
*/
public interface PropertyAccessor {
/**
* 嵌套属性的路径分隔符
* 遵循正常的Java规范: getFoo().getBar() 将被表示为 "foo.bar".
*/
String NESTED_PROPERTY_SEPARATOR = ".";
char NESTED_PROPERTY_SEPARATOR_CHAR = '.';
/**
* 标记一个表示索引或者映射属性的键的开始,例如"person.addresses[0]"
*/
String PROPERTY_KEY_PREFIX = "[";
char PROPERTY_KEY_PREFIX_CHAR = '[';
/**
* 标记一个表示索引或者映射属性的键的结束,例如"person.addresses[0]"
*/
String PROPERTY_KEY_SUFFIX = "]";
char PROPERTY_KEY_SUFFIX_CHAR = ']';
/**
* 获得指定属性的当前值.
* @param propertyName 要获取的属性的值的名称(可能是一个嵌套路径 和/或 基于索引号/键值对映射的属性)
* @return 属性的值
* @throws InvalidPropertyException 没有找到对应的属性或者这个属性不可读
* @throws PropertyAccessException 如果属性访问器本身是合法的,但是访问方法的调用却失败了
*/
Object getPropertyValue(String propertyName) throws BeansException;
/**
* 设置指定属性的当前值.
* @param propertyName 需要被设置值的属性的名称
* @param value 新的值
* @throws InvalidPropertyException 找不到指定的属性,或者属性不可写
* @throws PropertyAccessException 如果属性的访问器方法本身是有效的,但是该方法的调用失败或类型不匹配
*/
void setPropertyValue(String propertyName, Object value) throws BeansException;
/**
* 设置指定属性的当前值.
* @param pv 一个包含属性最新值的对象
* @throws InvalidPropertyException 找不到指定的属性,或者属性不可写
* @throws PropertyAccessException 如果属性的访问器方法本身是有效的,但是该方法的调用失败或类型不匹配
*/
void setPropertyValue(PropertyValue pv) throws BeansException;
/**
* 执行批量更新的首选方式.
* <p>需要注意的是,执行一个批量更新和执行一个单独更新是不同的,
* 因为,该方法的实现需要可以在发生了可恢复的错误(例如类型不匹配,而是不找不到属性的等错误)时继续更新后续的属性,
* 同时抛出一个{@link PropertyBatchUpdateException}异常用于包含所有个别属性更新的错误.
* 该异常将会在后续的处理中查看到所有绑定的错误信息.
* 已经被成功更新的属性的变化将是有效地.
* <p>不允许使用未知的属性和无效的属性.
* @param pvs 需要被设置到目标对象的PropertyValues
* @throws InvalidPropertyException 找不到指定的属性,或者属性不可写
* @throws PropertyBatchUpdateException 如果在批量更新指定属性时发生了一个或多个PropertyAccessExceptions则抛出此异常.
* 该异常帮顶了所有单独的PropertyAccessExceptions.
* 而其他没有发生异常的属性更新将会成功并且有效.
* @see #setPropertyValues(PropertyValues, boolean, boolean)
*/
void setPropertyValues(PropertyValues pvs) throws BeansException;
/**
* Perform a batch update with full control over behavior.
* <p>需要注意的是,执行一个批量更新和执行一个单独更新是不同的,
* 因为,该方法的实现需要可以在发生了可恢复的错误(例如类型不匹配,而是不找不到属性的等错误)时继续更新后续的属性,
* 同时抛出一个{@link PropertyBatchUpdateException}异常用于包含所有个别属性更新的错误.
* 该异常将会在后续的处理中查看到所有绑定的错误信息.
* 已经被成功更新的属性的变化将是有效地.
* @param pvs 需要被设置到目标对象的PropertyValues
* @param ignoreUnknown 是否忽略位置属性(在目标bean中找不到该属性)
* @param ignoreInvalid 是否忽略无效的属性(找到了,但是该属性却无法访问)
* @throws InvalidPropertyException 找不到指定的属性,或者属性不可写
* @throws PropertyBatchUpdateException 如果在批量更新指定属性时发生了一个或多个PropertyAccessExceptions则抛出此异常.
* 该异常帮顶了所有单独的PropertyAccessExceptions.
* 而其他没有发生异常的属性更新将会成功并且有效.
*/
void setPropertyValues(PropertyValues pvs, boolean ignoreUnknown, boolean ignoreInvalid) throws BeansException;
}