Assuming the constructor runs in the client part of the code (the one that gets translated to javascript).
The callback method onSuccess does modify the instance variables of the class.
The callback is implemented as an anonymous class so the instance of the outer class can be accessed by using OuterClass.this.
Normally in plain Java we should not do something like this because by doing so, 'this' reference can escape before the object construction is finished.
But does it also hold for the case when Java code is translated to Javascript? I assume that javascript code is executed by a single thread in a web browser so this should not be an issue (single thread => no visibility problems)?
On the one hand, you're right - the problem cannot be triggered by a separate thread, because JavaScript is single threaded.
Callback events will definitely be handled by an event handler that starts after the current event handler (the one which constructs the current object) has finished. So they will only ever see the fully constructed object.
On the other hand, you generally don't need threads to exploit the basic problem. Here's a simple example:
final A a = new A();
final B b = new B(a);
public class A {
private B b;
public void setB(final B b) {
this.b = b;
}
public void letBSaySomething() {
b.saySomething();
}
}
public class B {
private A a;
private final int some;
public B(final A a) {
this.a = a;
a.setB(this);
a.letBSaySomething();
some = 55;
a.letBSaySomething();
}
public void saySomething() {
RootPanel.get().add(new Label("Hello " + some));
}
}
This results in the output
Hello 0
Hello 55
(although 'some' is final). This happens both in GWT (compiled/uncompiled) and plain Java programs.
AsyncCallback, by itself, is just a class. When you send an RPC request in production mode, you are guaranteed that the result will come in asynchronously through XmlHttpRequest; in compiled javascript it is 100% impossible to leak the reference before construction is finished, as the callback will get called in a separate javascript execution stack.
In gwt-dev mode, however, things that should be asynchronous aren't always so. Personally, I abandoned gwt-dev over super-dev-mode, and only use gwt-dev when I really need java debugger, so I can't tell you for sure if it will be immune to construction problems or not (test it and find out!).
If you are not sending any requests in the constructor, you will be 100% safe. Just creating the async callback will only lead to problems if you are subsequently accessing OuterClass.this in unsafe ways, regardless of the classes involved.
Related
I'm creating a networked game in Unity using tcp based sockets.
(I'm new to networking and threading stuff).
I'm using System.Net.Sockets async methods like socket.BeginReceive() and socket.EndReceive().
All the client-server connecting and messaging works. But as soon as I try access anything from a Monobehavior (so that I can actually have any effect on the Unity game), like a gameobject's transform, an exception is thrown telling me that I can only access these properties from the main thread.
My question is: why am I not back on the main thread in the callback to foo.beginRecieve(), or at least after I call foo.EndReceive()? How do I return to the main thread using the async socket api? Will I end up having to use the synchronous socket api and just handle the threading myself so I can properly resync with Unity's main thread?
Thanks!
Any help would be much appreciated.
//code which sets up the callbacks which are executed when a client receives a message from the server
void BeginReceive() => _clientSocket.BeginReceive(_messageReceivedBuffer, 0, _messageReceivedBuffer.Length, SocketFlags.None, ReceiveCallback, null);
void ReceiveCallback(IAsyncResult result)
{
_clientSocket.EndReceive(result);
var msg = _serializer.ByteArrayToObject<NetworkMessage>(_messageReceivedBuffer);
//this clientmanipulation manipulates the game grid and the gameobjects' which it references
//it's in this method that an exception gets thrown and the code breaks
msg.ClientManipulation(_gameGrid);
BeginReceive();
}
In general for EndReceive:
Before calling BeginReceive, you need to create a callback method that implements the AsyncCallback delegate. This callback method executes in a separate thread and is called by the system after BeginReceive returns. The callback method must accept the IAsyncResult returned by the BeginReceive method as a parameter.
[...]
The EndReceive method will block until data is available.
Usually you would use a pattern often referred to as Main Thread Dispatcher using a ConcurrentQueue. For Unity this is quite easy since you already have something that is surely always been executed in the main thread: Update
public class Example : MonoBehaviour
{
...
private ConcurrentQueue<Action> _mainThreadActions = new ConcurrentQueue<Action>();
private void Update()
{
// Handle all callbacks in main thread
while(_mainthreadActions.Count > 0 && _mainThreadActions.TryDequeue(out var action))
{
action?.Invoke();
}
}
void BeginReceive()
{
_clientSocket.BeginReceive(_messageReceivedBuffer, 0, _messageReceivedBuffer.Length, SocketFlags.None, ReceiveCallback, null);
}
void ReceiveCallback(IAsyncResult result)
{
_clientSocket.EndReceive(result);
var msg = _serializer.ByteArrayToObject<NetworkMessage>(_messageReceivedBuffer);
// On threads / possibly async code enqueue the action to be invoked in the main thread
_mainThreadActions.Enqueue(()=> {msg.ClientManipulation(_gameGrid)});
BeginReceive();
}
}
Note: My question is about the way of including/passing the dispatcher instance around, not about how the pattern is useful.
I am studying the Flux Architecture and I cannot get my head around the concept of the dispatcher (instance) potentially being included everywhere...
What if I want to trigger an Action from my Model Layer? It feels weird to me to include an instance of an object in my Model files... I feel like this is missing some injection pattern...
I have the impression that the exact PHP equivalent is something (that feels) horrible similar to:
<?php
$dispatcher = require '../dispatcher_instance.php';
class MyModel {
...
public function someMethod() {
...
$dispatcher->...
}
}
I think my question is not exactly only related to the Flux Architecture but more to the NodeJS "way of doing things"/practices in general.
TLDR:
No, it is not bad practice to pass around the instance of the dispatcher in your stores
All data stores should have a reference to the dispatcher
The invoking/consuming code (in React, this is usually the view) should only have references to the action-creators, not the dispatcher
Your code doesn't quite align with React because you are creating a public mutable function on your data store.
The ONLY way to communicate with a store in Flux is via message passing which always flows through the dispatcher.
For example:
var Dispatcher = require('MyAppDispatcher');
var ExampleActions = require('ExampleActions');
var _data = 10;
var ExampleStore = assign({}, EventEmitter.prototype, {
getData() {
return _data;
},
emitChange() {
this.emit('change');
},
dispatcherKey: Dispatcher.register(payload => {
var {action} = payload;
switch (action.type) {
case ACTIONS.ADD_1:
_data += 1;
ExampleStore.emitChange();
ExampleActions.doThatOtherThing();
break;
}
})
});
module.exports = ExampleStore;
By closing over _data instead of having a data property directly on the store, you can enforce the message passing rule. It's a private member.
Also important to note, although you can call Dispatcher.emit() directly, it's not a good idea.
There are two main reasons to go through the action-creators:
Consistency - This is how your views and other consuming code interacts with the stores
Easier Refactoring - If you ever remove the ADD_1 action from your app, this code will throw an exception rather than silently failing by sending a message that doesn't match any of the switch statements in any of the stores
Main Advantages to this Approach
Loose coupling - Adding and removing features is a breeze. Stores can respond to any event in the system with by adding one line of code.
Less complexity - One way data flow makes wrapping head around data flow a lot easier. Less interdependencies.
Easier debugging - You can debug every change in your system with a few lines of code.
debugging example:
var MyAppDispatcher = require('MyAppDispatcher');
MyAppDispatcher.register(payload => {
console.debug(payload);
});
I am new to multithreading in Android and I have a doubt. I have a AsyncTask instance which I call as BackGroundTask and I start this as:
BackGroundTask bgTask = new BackGroundTask();
bgTask.execute();
However I would like to wait until this call is finished its execution, before proceeding to the other statements of code without blocking UI thread and allowing user to navigate through application.
Please help me so that I can achieve this.
put your code inside onPostExecute method of AsyncTask, which you
wants to execute after work done By worker thread.
Try using bgTask.execute().get() this will wait for the background task to finish before moving to the next instruction in the called thread. (Please note that this will block the called thread until background task finishes)
I have found the answer at
How do I retrieve the data from AsyncTasks doInBackground()?
And the answer is to use callback as shown below which is copied from above shared link:
The only way to do this is using a CallBack. You can do something like this:
new CallServiceTask(this).execute(request, url);
Then in your CallServiceTask add a local class variable and class a method from that class in your onPostExecute:
private class CallServiceTask extends AsyncTask<Object, Void, Object[]>
{
RestClient caller;
CallServiceTask(RestClient caller) {
this.caller = caller;
}
protected Object[] doInBackground(Object... params)
{
HttpUriRequest req = (HttpUriRequest) params[0];
String url = (String) params[1];
return executeRequest(req, url);
}
protected onPostExecute(Object result) {
caller.onBackgroundTaskCompleted(result);
}
}
Then simply use the Object as you like in the onBackgroundTaskCompleted() method in your RestClient class.
A more elegant and extendible solution would be to use interfaces. For an example implementation see this library. I've just started it but it has an example of what you want.
Using simple injector with the command pattern described here and the query pattern described here. For one of the commands, I have 2 handler implementations. The first is a "normal" implementation that executes synchronously:
public class SendEmailMessageHandler
: IHandleCommands<SendEmailMessageCommand>
{
public SendEmailMessageHandler(IProcessQueries queryProcessor
, ISendMail mailSender
, ICommandEntities entities
, IUnitOfWork unitOfWork
, ILogExceptions exceptionLogger)
{
// save constructor args to private readonly fields
}
public void Handle(SendEmailMessageCommand command)
{
var emailMessageEntity = GetThisFromQueryProcessor(command);
var mailMessage = ConvertEntityToMailMessage(emailMessageEntity);
_mailSender.Send(mailMessage);
emailMessageEntity.SentOnUtc = DateTime.UtcNow;
_entities.Update(emailMessageEntity);
_unitOfWork.SaveChanges();
}
}
The other is like a command decorator, but explicitly wraps the previous class to execute the command in a separate thread:
public class SendAsyncEmailMessageHandler
: IHandleCommands<SendEmailMessageCommand>
{
public SendAsyncEmailMessageHandler(ISendMail mailSender,
ILogExceptions exceptionLogger)
{
// save constructor args to private readonly fields
}
public void Handle(SendEmailMessageCommand command)
{
var program = new SendAsyncEmailMessageProgram
(command, _mailSender, _exceptionLogger);
var thread = new Thread(program.Launch);
thread.Start();
}
private class SendAsyncEmailMessageProgram
{
internal SendAsyncEmailMessageProgram(
SendEmailMessageCommand command
, ISendMail mailSender
, ILogExceptions exceptionLogger)
{
// save constructor args to private readonly fields
}
internal void Launch()
{
// get new instances of DbContext and query processor
var uow = MyServiceLocator.Current.GetService<IUnitOfWork>();
var qp = MyServiceLocator.Current.GetService<IProcessQueries>();
var handler = new SendEmailMessageHandler(qp, _mailSender,
uow as ICommandEntities, uow, _exceptionLogger);
handler.Handle(_command);
}
}
}
For a while simpleinjector was yelling at me, telling me that it found 2 implementations of IHandleCommands<SendEmailMessageCommand>. I found that the following works, but not sure whether it is the best / optimal way. I want to explicitly register this one interface to use the Async implementation:
container.RegisterManyForOpenGeneric(typeof(IHandleCommands<>),
(type, implementations) =>
{
// register the async email handler
if (type == typeof(IHandleCommands<SendEmailMessageCommand>))
container.Register(type, implementations
.Single(i => i == typeof(SendAsyncEmailMessageHandler)));
else if (implementations.Length < 1)
throw new InvalidOperationException(string.Format(
"No implementations were found for type '{0}'.",
type.Name));
else if (implementations.Length > 1)
throw new InvalidOperationException(string.Format(
"{1} implementations were found for type '{0}'.",
type.Name, implementations.Length));
// register a single implementation (default behavior)
else
container.Register(type, implementations.Single());
}, assemblies);
My question: is this the right way, or is there something better? For example, I'd like to reuse the existing exceptions thrown by Simpleinjector for all other implementations instead of having to throw them explicitly in the callback.
Update reply to Steven's answer
I have updated my question to be more explicit. The reason I have implemented it this way is because as part of the operation, the command updates a System.Nullable<DateTime> property called SentOnUtc on a db entity after the MailMessage is successfully sent.
The ICommandEntities and IUnitOfWork are both implemented by an entity framework DbContext class.The DbContext is registered per http context, using the method described here:
container.RegisterPerWebRequest<MyDbContext>();
container.Register<IUnitOfWork>(container.GetInstance<MyDbContext>);
container.Register<IQueryEntities>(container.GetInstance<MyDbContext>);
container.Register<ICommandEntities>(container.GetInstance<MyDbContext>);
The default behavior of the RegisterPerWebRequest extension method in the simpleinjector wiki is to register a transient instance when the HttpContext is null (which it will be in the newly launched thread).
var context = HttpContext.Current;
if (context == null)
{
// No HttpContext: Let's create a transient object.
return _instanceCreator();
...
This is why the Launch method uses the service locator pattern to get a single instance of DbContext, then passes it directly to the synchronous command handler constructor. In order for the _entities.Update(emailMessageEntity) and _unitOfWork.SaveChanges() lines to work, both must be using the same DbContext instance.
NOTE: Ideally, sending the email should be handled by a separate polling worker. This command is basically a queue clearing house. The EmailMessage entities in the db already have all of the information needed to send the email. This command just grabs an unsent one from the database, sends it, then records the DateTime of the action. Such a command could be executed by polling from a different process / app, but I will not accept such an answer for this question. For now, we need to kick off this command when some kind of http request event triggers it.
There are indeed easier ways to do this. For instance, instead of registering a BatchRegistrationCallback as you did in your last code snippet, you can make use of the OpenGenericBatchRegistrationExtensions.GetTypesToRegister method. This method is used internally by the RegisterManyForOpenGeneric methods, and allows you to filter the returned types before you send them to an RegisterManyForOpenGeneric overload:
var types = OpenGenericBatchRegistrationExtensions
.GetTypesToRegister(typeof(IHandleCommands<>), assemblies)
.Where(t => !t.Name.StartsWith("SendAsync"));
container.RegisterManyForOpenGeneric(
typeof(IHandleCommands<>),
types);
But I think it would be better to make a few changes to your design. When you change your async command handler to a generic decorator, you completely remove the problem altogether. Such a generic decorator could look like this:
public class SendAsyncCommandHandlerDecorator<TCommand>
: IHandleCommands<TCommand>
{
private IHandleCommands<TCommand> decorated;
public SendAsyncCommandHandlerDecorator(
IHandleCommands<TCommand> decorated)
{
this.decorated = decorated;
}
public void Handle(TCommand command)
{
// WARNING: THIS CODE IS FLAWED!!
Task.Factory.StartNew(
() => this.decorated.Handle(command));
}
}
Note that this decorator is flawed because of reasons I'll explain later, but let's go with this for the sake of education.
Making this type generic, allows you to reuse this type for multiple commands. Because this type is generic, the RegisterManyForOpenGeneric will skip this (since it can't guess the generic type). This allows you to register the decorator as follows:
container.RegisterDecorator(
typeof(IHandleCommands<>),
typeof(SendAsyncCommandHandler<>));
In your case however, you don't want this decorator to be wrapped around all handlers (as the previous registration does). There is an RegisterDecorator overload that takes a predicate, that allows you to specify when to apply this decorator:
container.RegisterDecorator(
typeof(IHandleCommands<>),
typeof(SendAsyncCommandHandlerDecorator<>),
c => c.ServiceType == typeof(IHandleCommands<SendEmailMessageCommand>));
With this predicate applied, the SendAsyncCommandHandlerDecorator<T> will only be applied to the IHandleCommands<SendEmailMessageCommand> handler.
Another option (which I prefer) is to register a closed generic version of the SendAsyncCommandHandlerDecorator<T> version. This saves you from having to specify the predicate:
container.RegisterDecorator(
typeof(IHandleCommands<>),
typeof(SendAsyncCommandHandler<SendEmailMessageCommand>));
As I noted however, the code for the given decorator is flawed, because you should always build a new dependency graph on a new thread, and never pass on dependencies from thread to thread (which the original decorator does). More information about this in this article: How to work with dependency injection in multi-threaded applications.
So the answer is actually more complex, since this generic decorator should really be a proxy that replaces the original command handler (or possibly even a chain of decorators wrapping a handler). This proxy must be able to build up a new object graph in a new thread. This proxy would look like this:
public class SendAsyncCommandHandlerProxy<TCommand>
: IHandleCommands<TCommand>
{
Func<IHandleCommands<TCommand>> factory;
public SendAsyncCommandHandlerProxy(
Func<IHandleCommands<TCommand>> factory)
{
this.factory = factory;
}
public void Handle(TCommand command)
{
Task.Factory.StartNew(() =>
{
var handler = this.factory();
handler.Handle(command);
});
}
}
Although Simple Injector has no built-in support for resolving Func<T> factory, the RegisterDecorator methods are the exception. The reason for this is that it would be very tedious to register decorators with Func dependencies without framework support. In other words, when registering the SendAsyncCommandHandlerProxy with the RegisterDecorator method, Simple Injector will automatically inject a Func<T> delegate that can create new instances of the decorated type. Since the proxy only refences a (singleton) factory (and is stateless), we can even register it as singleton:
container.RegisterSingleDecorator(
typeof(IHandleCommands<>),
typeof(SendAsyncCommandHandlerProxy<SendEmailMessageCommand>));
Obviously, you can mix this registration with other RegisterDecorator registrations. Example:
container.RegisterManyForOpenGeneric(
typeof(IHandleCommands<>),
typeof(IHandleCommands<>).Assembly);
container.RegisterDecorator(
typeof(IHandleCommands<>),
typeof(TransactionalCommandHandlerDecorator<>));
container.RegisterSingleDecorator(
typeof(IHandleCommands<>),
typeof(SendAsyncCommandHandlerProxy<SendEmailMessageCommand>));
container.RegisterDecorator(
typeof(IHandleCommands<>),
typeof(ValidatableCommandHandlerDecorator<>));
This registration wraps any command handler with a TransactionalCommandHandlerDecorator<T>, optionally decorates it with the async proxy, and always wraps it with a ValidatableCommandHandlerDecorator<T>. This allows you to do the validation synchronously (on the same thread), and when validation succeeds, spin of handling of the command on a new thread, running in a transaction on that thread.
Since some of your dependencies are registered Per Web Request, this means that they would get a new (transient) instance an exception is thrown when there is no web request, which is they way this is implemented in the Simple Injector (as is the case when you start a new thread to run the code). As you are implementing multiple interfaces with your EF DbContext, this means Simple Injector will create a new instance for each constructor-injected interface, and as you said, this will be a problem.
You'll need to reconfigure the DbContext, since a pure Per Web Request will not do. There are several solutions, but I think the best is to make an hybrid PerWebRequest/PerLifetimeScope instance. You'll need the Per Lifetime Scope extension package for this. Also note that also is an extension package for Per Web Request, so you don't have to use any custom code. When you've done this, you can define the following registration:
container.RegisterPerWebRequest<DbContext, MyDbContext>();
container.RegisterPerLifetimeScope<IObjectContextAdapter,
MyDbContext>();
// Register as hybrid PerWebRequest / PerLifetimeScope.
container.Register<MyDbContext>(() =>
{
if (HttpContext.Current != null)
return (MyDbContext)container.GetInstance<DbContext>();
else
return (MyDbContext)container
.GetInstance<IObjectContextAdapter>();
});
UPDATE
Simple Injector 2 now has the explicit notion of lifestyles and this makes the previous registration much easier. The following registration is therefore adviced:
var hybrid = Lifestyle.CreateHybrid(
lifestyleSelector: () => HttpContext.Current != null,
trueLifestyle: new WebRequestLifestyle(),
falseLifestyle: new LifetimeScopeLifestyle());
// Register as hybrid PerWebRequest / PerLifetimeScope.
container.Register<MyDbContext, MyDbContext>(hybrid);
Since the Simple Injector only allows registering a type once (it doesn't support keyed registration), it is not possible to register a MyDbContext with both a PerWebRequest lifestyle, AND a PerLifetimeScope lifestyle. So we have to cheat a bit, so we make two registrations (one per lifestyle) and select different service types (DbContext and IObjectContextAdapter). The service type is not really important, except that MyDbContext must implement/inherit from that service type (feel free to implement dummy interfaces on your MyDbContext if this is convenient).
Besides these two registrations, we need a third registration, a mapping, that allows us to get the proper lifestyle back. This is the Register<MyDbContext> which gets the proper instance back based on whether the operation is executed inside a HTTP request or not.
Your AsyncCommandHandlerProxy will have to start a new lifetime scope, which is done as follows:
public class AsyncCommandHandlerProxy<T>
: IHandleCommands<T>
{
private readonly Func<IHandleCommands<T>> factory;
private readonly Container container;
public AsyncCommandHandlerProxy(
Func<IHandleCommands<T>> factory,
Container container)
{
this.factory = factory;
this.container = container;
}
public void Handle(T command)
{
Task.Factory.StartNew(() =>
{
using (this.container.BeginLifetimeScope())
{
var handler = this.factory();
handler.Handle(command);
}
});
}
}
Note that the container is added as dependency of the AsyncCommandHandlerProxy.
Now, any MyDbContext instance that is resolved when HttpContext.Current is null, will get a Per Lifetime Scope instance instead of a new transient instance.
Say we have the following method:
private MyObject foo = new MyObject();
// and later in the class
public void PotentialMemoryLeaker(){
int firedCount = 0;
foo.AnEvent += (o,e) => { firedCount++;Console.Write(firedCount);};
foo.MethodThatFiresAnEvent();
}
If the class with this method is instantiated and the PotentialMemoryLeaker method is called multiple times, do we leak memory?
Is there any way to unhook that lambda event handler after we're done calling MethodThatFiresAnEvent?
Yes, save it to a variable and unhook it.
DelegateType evt = (o, e) => { firedCount++; Console.Write(firedCount); };
foo.AnEvent += evt;
foo.MethodThatFiresAnEvent();
foo.AnEvent -= evt;
And yes, if you don't, you'll leak memory, as you'll hook up a new delegate object each time. You'll also notice this because each time you call this method, it'll dump to the console an increasing number of lines (not just an increasing number, but for one call to MethodThatFiresAnEvent it'll dump any number of items, once for each hooked up anonymous method).
You wont just leak memory, you will also get your lambda called multiple times. Each call of 'PotentialMemoryLeaker' will add another copy of the lambda to the event list, and every copy will be called when 'AnEvent' is fired.
Well you can extend what has been done here to make delegates safer to use (no memory leaks)
Your example just compiles to a compiler-named private inner class (with field firedCount and a compiler-named method). Each call to PotentialMemoryLeaker creates a new instance of the closure class to which where foo keeps a reference by way of a delegate to the single method.
If you don't reference the whole object that owns PotentialMemoryLeaker, then that will all be garbage collected. Otherwise, you can either set foo to null or empty foo's event handler list by writing this:
foreach (var handler in AnEvent.GetInvocationList()) AnEvent -= handler;
Of course, you'd need access to the MyObject class's private members.
Yes in the same way that normal event handlers can cause leaks. Because the lambda is actually changed to:
someobject.SomeEvent += () => ...;
someobject.SomeEvent += delegate () {
...
};
// unhook
Action del = () => ...;
someobject.SomeEvent += del;
someobject.SomeEvent -= del;
So basically it is just short hand for what we have been using in 2.0 all these years.