SignalR を使用してリアルタイムのツイートをマップにブロードキャストするアプリケーションを作成しています。C# Tweetinvi ライブラリ ( tweetinvi.codeplex.com ) を使用して、Twitter ストリーミング API への接続に関連するすべてのロジックを処理しています。
Twitter API では、いつでも 1 つのストリーミング接続のみを Twitter に対して開くことができると指定されています。SignalR を使用しているため、ストリーミング接続とハブ クラスの間に依存関係があります。Hub クラスは一時的なものであり、クライアントが要求するたびに作成されることを知っているので、Hub クラスに挿入された Twitter Stream クラスのインスタンスがシングルトンであること、または少なくともIFilteredStream
1 回だけ作成されることを確認する必要があります。アプリケーションの存続期間中。API に接続する定型コードは次のとおりです。
public class TweetStream
{
private IFilteredStream _stream;
public TweetStream()
{
var consumerKey = ConfigurationManager.AppSettings.Get("twitter:ConsumerKey");
var consumerSecret = ConfigurationManager.AppSettings.Get("twitter:ConsumerSecret");
var accessKey = ConfigurationManager.AppSettings.Get("twitter:AccessKey");
var accessToken = ConfigurationManager.AppSettings.Get("twitter:AccessToken");
TwitterCredentials.SetCredentials(accessKey, accessToken, consumerKey, consumerSecret);
_stream = Stream.CreateFilteredStream();
}
// Return singular instance of _stream to Hub class for usage.
public IFilteredStream Instance
{
get { return _stream; }
}
}
IFilteredStream インターフェイスは、次のようにラムダ メソッドを公開します。これにより、リアルタイムでツイートを受信できるようになり、SignalR Hub クラス内からアクセスできるようになります。
_stream.MatchingTweetReceived += (sender, args) => {
Clients.All.broadcast(args.Tweet);
};
このメソッドのソースはここにあります
Autofac を実装しようとしましたが、Twitter API への接続は行われているようですが、それ以上は何も起こりません。これをデバッグしようとしましたが、依存性注入を使用してそのようなシナリオをデバッグする方法がわかりません。現在、私の Hub クラスは次のようになっています。
public class TwitterHub : Hub
{
private readonly ILifetimeScope _scope;
private readonly TweetStream _stream;
// Inject lifetime scope and resolve reference to TweetStream
public TwitterHub(ILifetimeScope scope)
{
_scope = scope.BeginLifetimeScope();
_stream = scope.Resolve<TweetStream>();
var i = _stream.Instance;
_stream.MatchingTweetReceived += (sender, args) => {
Clients.All.broadcast(args.Tweet);
};
i.StartStreamMatchingAllConditions();
}
}
そして最後に、依存関係とハブを Autofac に登録する OWIN スタートアップ クラス:
[assembly: OwinStartup(typeof(TwitterMap2015.App_Start.OwinStartup))]
namespace TwitterMap2015.App_Start
{
public class OwinStartup
{
public void Configuration(IAppBuilder app)
{
var builder = new ContainerBuilder();
// use hubconfig, not globalhost
var hubConfig = new HubConfiguration {EnableDetailedErrors = true};
builder.RegisterHubs(Assembly.GetExecutingAssembly()); // register all SignalR hubs
builder.Register(i => new TweetStream()).SingleInstance(); // is this the correct way of injecting a singleton instance of TweetStream?
var container = builder.Build();
hubConfig.Resolver = new AutofacDependencyResolver(container);
app.MapSignalR("/signalr", hubConfig);
}
}
}
この質問が少し混乱している場合は申し訳ありません。これを機能させるために実装する必要があるアーキテクチャの種類を理解するのに苦労しています! これをどのように改善できるか、またはどのように行うべきかについてのアドバイス/推奨事項をお待ちしています!