Multithreading Silverlight-限制应用程序一次只能调用一个WCF

Multithreading Silverlight-限制应用程序一次只能调用一个WCF,multithreading,silverlight,wcf,asynchronous,Multithreading,Silverlight,Wcf,Asynchronous,Silverlight一次只能同时发送一定数量的WCF请求。我正在尝试序列化应用程序特定部分正在执行的请求,因为我不需要它们同时运行 问题如下(总结如下): “Silverlight应用程序中的WCF代理使用启动web服务调用的线程的SynchronizationContext来计划接收响应时异步事件处理程序的调用。当从Silverlight应用程序的UI线程启动web服务调用时,异步事件处理程序代码也将执行用户界面线程上的“e” 概要:基本上,如果阻止调用异步方法的线程,它将永远不会被调用

Silverlight一次只能同时发送一定数量的WCF请求。我正在尝试序列化应用程序特定部分正在执行的请求,因为我不需要它们同时运行

问题如下(总结如下): “Silverlight应用程序中的WCF代理使用启动web服务调用的线程的SynchronizationContext来计划接收响应时异步事件处理程序的调用。当从Silverlight应用程序的UI线程启动web服务调用时,异步事件处理程序代码也将执行用户界面线程上的“e”

概要:基本上,如果阻止调用异步方法的线程,它将永远不会被调用

我无法找到正确的线程模型,这样可以以合理的方式满足我的需求

我唯一的另一个要求是我不希望UI线程阻塞

就我所见,如果UI线程有一个工作线程,它将调用作为
操作
委托进行排队,然后使用
自动resetEvent
在另一个工作线程中一次执行一个任务,那么应该工作。有两个问题: 1) 调用async的线程无法阻止,因为这样async就永远不会被调用。事实上,如果将该线程放入等待循环,我注意到它也不会被调用 2) 您需要一种方法从异步调用的已完成方法发出信号,表明它已完成


对不起,时间太长了,谢谢你的阅读。有什么想法吗?

有一些选择:

-您可以通过检查Agatha rrsl的实现或仅使用它而不是纯wcf来查看它。该框架允许您对请求进行排队。你可以读更多

-另一种选择是使用被动扩展。这里有一个SO示例和更多信息

-您可以尝试Jeffrey Richter提供的Power Thread库。他在他的书《CLR通过C#》中对此进行了描述。你可以找到图书馆。这会给你一些关于它的信息


-您可以随时滚动自己的实现。收益率报表在这里是一个很好的帮助。错误处理使解决方案变得非常困难。

我使用了一个我自己构建的类来执行加载操作。使用该类,您可以注册不同域上下文的多个加载操作,然后逐个执行它们。当所有操作完成(成功或失败)时,您可以向被调用的类的构造函数提供一个操作

这是课程的代码。我认为它不完整,你必须改变它以符合你的期望。也许它能帮助你解决你的处境

  public class DomainContextQueryLoader {
    private List<LoadOperation> _failedOperations;
    private Action<DomainContextQueryLoader> _completeAction;
    private List<QueuedQuery> _pendingQueries = new List<QueuedQuery>();

    public DomainContextQueryLoader(Action<DomainContextQueryLoader> completeAction) {
        if (completeAction == null) {
            throw new ArgumentNullException("completeAction", "completeAction is null.");
        }
        this._completeAction = completeAction;
    }

    /// <summary>
    /// Expose the count of failed operations
    /// </summary>
    public int FailedOperationCount {
        get {
            if (_failedOperations == null) {
                return 0;
            }
            return _failedOperations.Count;
        }
    }

    /// <summary>
    /// Expose an enumerator for all of the failed operations
    /// </summary>
    public IList<LoadOperation> FailedOperations {
        get {
            if (_failedOperations == null) {
                _failedOperations = new List<LoadOperation>();
            }
            return _failedOperations;
        }
    }

    public IEnumerable<QueuedQuery> QueuedQueries {
        get {
            return _pendingQueries;
        }
    }

    public bool IsExecuting {
        get;
        private set;
    }

    public void EnqueueQuery<T>(DomainContext context, EntityQuery<T> query) where T : Entity {
        if (IsExecuting) {
            throw new InvalidOperationException("Query cannot be queued, cause execution of queries is in progress");
        }
        var loadBatch = new QueuedQuery() {
            Callback = null,
            Context = context,
            Query = query,
            LoadOption = LoadBehavior.KeepCurrent,
            UserState = null
        };

        _pendingQueries.Add(loadBatch);
    }

    public void ExecuteQueries() {
        if (IsExecuting) {
            throw new InvalidOperationException("Executing of queries is in progress");
        }

        if (_pendingQueries.Count == 0) {
            throw new InvalidOperationException("No queries are queued to execute");
        }

        IsExecuting = true;
        var query = DequeueQuery();
        ExecuteQuery(query);
    }

    private void ExecuteQuery(QueuedQuery query) {
        System.Diagnostics.Debug.WriteLine("Load data {0}", query.Query.EntityType);
        var loadOperation = query.Load();
        loadOperation.Completed += new EventHandler(OnOperationCompleted);
    }

    private QueuedQuery DequeueQuery() {
        var query = _pendingQueries[0];
        _pendingQueries.RemoveAt(0);
        return query;
    }

    private void OnOperationCompleted(object sender, EventArgs e) {
        LoadOperation loadOperation = sender as LoadOperation;
        loadOperation.Completed -= new EventHandler(OnOperationCompleted);

        if (loadOperation.HasError) {
            FailedOperations.Add(loadOperation);
        }

        if (_pendingQueries.Count > 0) {
            var query = DequeueQuery();
            ExecuteQuery(query);
        }
        else {
            IsExecuting = false;
            System.Diagnostics.Debug.WriteLine("All data loaded");
            if (_completeAction != null) {
                _completeAction(this);
                _completeAction = null;
            }
        }
    }

}
公共类DomainContextQueryLoader{
私有列表\u失败的操作;
私人行动(完成行动);;
私有列表_pendingQueries=新列表();
公共域ContextQueryLoader(操作完成操作){
if(completeAction==null){
抛出新ArgumentNullException(“completeAction”,“completeAction为null”);
}
这个._completeAction=completeAction;
}
/// 
///公开失败操作的计数
/// 
公共整数失败操作计数{
得到{
如果(_failedOperations==null){
返回0;
}
返回_failedOperations.Count;
}
}
/// 
///公开所有失败操作的枚举数
/// 
公共IList失败操作{
得到{
如果(_failedOperations==null){
_failedOperations=新列表();
}
返回失败的操作;
}
}
公共IEnumerable QueuedQuery{
得到{
返回待处理查询;
}
}
公共事业执行{
得到;
私人设置;
}
公共void排队查询(DomainContext上下文,EntityQuery查询),其中T:Entity{
如果(正在执行){
抛出新的InvalidOperationException(“查询无法排队,因为正在执行查询”);
}
var loadBatch=new QueuedQuery(){
Callback=null,
上下文=上下文,
Query=Query,
LoadOption=LoadBehavior.KeepCurrent,
UserState=null
};
_pendingQueries.Add(loadBatch);
}
public void ExecuteQueries(){
如果(正在执行){
抛出新的InvalidOperationException(“正在执行查询”);
}
如果(_pendingQueries.Count==0){
抛出新的InvalidOperationException(“没有排队执行的查询”);
}
IsExecuting=true;
var query=DequeueQuery();
执行(查询);
}
私有void ExecuteQuery(QueuedQuery){
System.Diagnostics.Debug.WriteLine(“加载数据{0}”,query.query.EntityType);
var loadOperation=query.Load();
loadOperation.Completed+=新事件处理程序(OnOperationCompleted);
}
private QueuedQuery DequeueQuery(){
var query=_pendingquerys[0];
_pendingQueries.RemoveAt(0);
返回查询;
}
私有void操作已完成(对象发送方,事件参数e){
LoadOperation LoadOperation=发送方作为LoadOperation;
loadOperation.Completed-=新事件处理程序(OnOperationCompleted);
if(loadOperation.HasError){
失败操作。添加(加载操作);
}
如果(_pendingQueries.Count>0){
var query=DequeueQuery();
执行(查询);
}
否则{
IsExecuting=false;
System.Diagnostics.Debug.WriteLine(“加载的所有数据”);
如果(_completeAction!=null){
_完成动作(本);
_completeAction=null;
}
}
}
}
更新: 我刚刚注意到你不是