Castle DynamicProxy2:在拦截器内获取目标?

发布于 2024-07-18 17:03:48 字数 1127 浏览 12 评论 0原文

我正在使用 Castle DynamicProxy2 来“附加”接口以从字典中检索字段。 例如,给定以下类:

public class DataContainer : IDataContainer
{
    private Dictionary<string, object> _Fields = null;

    public Dictionary<string, object> Data
    {
        get { return _Fields ?? (_Fields = new Dictionary<string, object>()); }
    }
}

我想使用以下接口作为接口代理,从 Fields 字典中提取“Name”值:

public interface IContrivedExample
{
    string Name { get; }
}

从拦截器中,我想获取“目标”DataContainer,并返回“名称”值:

public void Intercept(IInvocation invocation)
{
    object fieldName = omitted; // get field name based on invocation information

    DataContainer container = ???; // this is what I'm trying to figure out
    invocation.ReturnValue = container.Fields[fieldName];
}

// Somewhere in code
var c = new DataContainer();
c.Fields.Add("Name", "Jordan");

var pg = new ProxyGenerator();
IContrivedExample ice = (IContrivedExample) pg.CreateInterfaceProxyWithTarget(..., c, ...);
Debug.Assert(ice.Name == "Jordan");

关于如何获取潜在目标的任何想法

注意:这是一个人为的示例,我用来围绕我的问题建立一些上下文。

I'm using Castle DynamicProxy2 to "tack on" interfaces to retrieve fields from a dictionary. For example, given the following class:

public class DataContainer : IDataContainer
{
    private Dictionary<string, object> _Fields = null;

    public Dictionary<string, object> Data
    {
        get { return _Fields ?? (_Fields = new Dictionary<string, object>()); }
    }
}

I want to use the following interface as an interface proxy to extract the "Name" value out of the Fields dictionary:

public interface IContrivedExample
{
    string Name { get; }
}

From an interceptor, I want to get the "target" DataContainer, and return the "Name" value:

public void Intercept(IInvocation invocation)
{
    object fieldName = omitted; // get field name based on invocation information

    DataContainer container = ???; // this is what I'm trying to figure out
    invocation.ReturnValue = container.Fields[fieldName];
}

// Somewhere in code
var c = new DataContainer();
c.Fields.Add("Name", "Jordan");

var pg = new ProxyGenerator();
IContrivedExample ice = (IContrivedExample) pg.CreateInterfaceProxyWithTarget(..., c, ...);
Debug.Assert(ice.Name == "Jordan");

Any thoughts on how to get the underlying target

Note: this is a contrived example I'm using to establish some context around the question I have.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

毁梦 2024-07-25 17:03:48

我想到了。 您必须将代理强制转换为 IProxyTargetAccessor:

public void Intercept(IInvocation invocation)
{
    object fieldName = omitted; // get field name based on invocation information

    var accessor = invocation.Proxy as IProxyTargetAccessor;

    DataContainer container = (DataContainer) accessor.DynProxyGetTarget();
    invocation.ReturnValue = container.Fields[fieldName];
}

I figured it out. You have to cast the Proxy to IProxyTargetAccessor:

public void Intercept(IInvocation invocation)
{
    object fieldName = omitted; // get field name based on invocation information

    var accessor = invocation.Proxy as IProxyTargetAccessor;

    DataContainer container = (DataContainer) accessor.DynProxyGetTarget();
    invocation.ReturnValue = container.Fields[fieldName];
}
亢潮 2024-07-25 17:03:48

为什么这么麻烦?

使用

var container = invocation.InvocationTarget as DataContainer;

BTW,IIUC,您正在尝试实现 已经提供的内容Castle DictionaryAdapter。 为什么不使用已有的东西呢?

Why the hassle?

use

var container = invocation.InvocationTarget as DataContainer;

BTW, IIUC, you're trying to implement what is already provided by Castle DictionaryAdapter. Why not use what's already out there?

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文