Where communities thrive


  • Join over 1.5M+ people
  • Join over 100K+ communities
  • Free without limits
  • Create your own community
People
Activity
  • Sep 22 21:54
    valdisz commented #3889
  • Sep 22 21:53
    valdisz synchronize #3889
  • Sep 22 21:41
    valdisz synchronize #3889
  • Sep 22 20:02
    valdisz synchronize #3889
  • Sep 22 19:48
    valdisz commented #3904
  • Sep 22 19:48
    valdisz ready_for_review #3904
  • Sep 22 19:48
    valdisz edited #3904
  • Sep 22 19:44
    valdisz synchronize #3904
  • Sep 22 19:28
    valdisz synchronize #3904
  • Sep 22 17:57
    valdisz synchronize #3904
  • Sep 22 12:27
    valdisz synchronize #3904
  • Sep 22 11:43
    cptjazz commented #3925
  • Sep 22 11:40
    cptjazz synchronize #3925
  • Sep 22 11:02
    valdisz edited #3904
  • Sep 22 10:55
    Aaronontheweb synchronize #3926
  • Sep 22 10:45
    Aaronontheweb opened #3927
  • Sep 22 10:01
    valdisz synchronize #3904
  • Sep 22 06:22
    cptjazz commented #3925
  • Sep 21 19:33
    Aaronontheweb opened #3926
  • Sep 21 16:19
    valdisz synchronize #3904
Aaron Stannard
@Aaronontheweb
Context, the property, throws because it's not meant to be accessed outside the execution context of an actor
Alex Hofer
@alexhofer
Ah, dang. Do you have any tips for somehow getting a message back to Self from within a Callback?
Aaron Stannard
@Aaronontheweb
and we park the Context inside a ThreadStatic variable
closing over self is perfectly fine
I do that all the time when I'm doing TPL stuff
the way I'd rearchitect that code you included is to have the event handler send a message to self
which, in turn, causes self to create a child and forward the message
etc
does that make sense?
Alex Hofer
@alexhofer
Hmm, its throwing because there's no Actor Context inside there. This is inside a behavior if that matters.
Aaron Stannard
@Aaronontheweb
var self = Self
 var self = Self;

_watcher.Created += (sender, e) =>
{

    var message = new MyMessage(filePath);

    self.Tell(message, ActorRefs.NoSender);
};
does that throw?
because Self is just Context.Self
Alex Hofer
@alexhofer
So, at the point I am trying to do var self = Self Self is showing up as a NotSupportedException with this:
System.NotSupportedException: There is no active ActorContext, this is most likely due to use of async operations from within this actor.
   at Akka.Actor.ActorBase.get_Context()
   at Akka.Actor.ActorBase.get_Self()
Which is weird, because self shows up as the right actor. But when it never receives the message it tells itself.
Alex Hofer
@alexhofer
Maybe it just doesn't work in a unit test scenario?
Aaron Stannard
@Aaronontheweb
if the self = Self happening outside of the actor?
Alex Hofer
@alexhofer

Nope, this is basically what is running, minus some logging:

        private void Active()
        {
            Receive<MyMessage>(message =>
            {
                TellNewChild(message);
            });

            _watcher = new FileSystemWatcher("directory", "*.csv")
            {
                NotifyFilter = NotifyFilters.LastAccess
                               | NotifyFilters.LastWrite
                               | NotifyFilters.FileName
                               | NotifyFilters.DirectoryName,

                EnableRaisingEvents = true
            };

            var self = Self;

            _watcher.Created += (sender, e) =>
            {
                var message = new MyMessage(e.FullPath;
                self.Tell(message, ActorRefs.NoSender);
            };
        }

But it never hits the MyMessage receive handler. It is in this Active behavior.

Wellp, @Aaronontheweb it looks to be working now. I guess I just needed to...clean the solution and rebuild. D:
Aaron Stannard
@Aaronontheweb
:+1:
glad I could help
Alex Hofer
@alexhofer
Thanks @Aaronontheweb ! :)
Greatsamps
@Greatsamps

Have a question about killing actors. Is there a way to kill an actor, including the current message its processing? From looking at the docs, it appears that both the shutdown and kill functions send a message to the actor that would get processed after the current message.

we have a situation where sometimes some code within the actor can hang and block, so would like to be able to restart the actor from above. Or do we need to add timeouts etc to the actors message processing code?

Bartosz Sypytkowski
@Horusiath

@Greatsamps as you've probably noticed, an actor's Receive method is just a block of synchronous code. Once it started executing, it will run until completion. There's not much we can do here, as only operating system can interrupt code running on a given thread, and OS itself is not aware of existence of actors.

Usually the reason behind having long running blocking code is either trying to do synchronous I/O (which you should never do, pretty much every .NET API now exposes Async API for that) or long running loop. For the latter case one way is to split long running process into sequence of steps or batches and send them as operations to Self, eg. instead of having:

Receive<Msg>(msg => {
    var sum = 0;
    for (var i = 0; i < msg.Count; i++) {
        sum += DoSomething(i);
    }
    Sender.Tell(sum);
});

You can model it as:

Receive<Msg>(msg => {
    var sum = msg.State;
    // process message in batches of 1000 elements
    var until = Math.Min(msg.From + 1000, msg.Count);
    var i = msg.From;
    for (; i < until; i++) {
        sum += DoSomething(i);
    }
    if (i < msg.Count) {
        Self.Forward(new Msg(state: sum, from: i, count: msg.Count));
    } else {
        Sender.Tell(sum);
    }
});
This way a potentially long running sequence can be split into shorter steps, which can be interleaved with other messages, including stop signals.
mijoki
@mijoki

I've encountered this error whilst using Akka.Persistence.MongoDb and Akka.Cluster.Sharding

Exception in ReceiveRecover when replaying event type ["Akka.Cluster.Sharding.PersistentShardCoordinator+ShardRegionRegistered"] with sequence number [1] for persistenceId ["/system/sharding/TestCoordinator/singleton/coordinator"]
System.ArgumentNullException: Value cannot be null.
Parameter name: key
at System.Collections.Immutable.Requires.FailArgumentNullException(String parameterName)
at System.Collections.Immutable.ImmutableDictionary`2.ContainsKey(TKey key)
at Akka.Cluster.Sharding.PersistentShardCoordinator.State.Updated(IDomainEvent e)
at Akka.Cluster.Sharding.PersistentShardCoordinator.ReceiveRecover(Object message)
at Akka.Actor.ActorBase.AroundReceive(Receive receive, Object message)
at Akka.Persistence.Eventsourced.<>cDisplayClass92_0.<Recovering>b1(Receive receive, Object message)

This will only occur when state-store-mode is set to persistence and after the cluster has been created once. It seems that the ShardRegionRegistered object is unable to be serialized correctly (See below), presumably due to the fact that it contains an IActorRef.
This does not happen when state-store-mode is set to ddata, however I would ideally prefer to use remember-entities which I cannot get to work with ddata.
{
"_id" : "/system/sharding/TestCoordinator/singleton/coordinator_4",
"PersistenceId" : "/system/sharding/TestCoordinator/singleton/coordinator",
"SequenceNr" : NumberLong(4),
"IsDeleted" : false,
"Payload" : {
"_t" : "Akka.Cluster.Sharding.PersistentShardCoordinator+ShardRegionRegistered, Akka.Cluster.Sharding"
},
"Manifest" : "Akka.Persistence.Persistent, Akka.Persistence",
"Ordering" : Timestamp(1568893010, 1),
"Tags" : null,
"SerializerId" : null
}

Zetanova
@Zetanova

@Greatsamps dotnet has a feature Thread.Abort(), but its a rabbit hole and i dont know if its still supported in dotnet core. If there is really a situation where it a Thread.Abort seams required it is near always to restart the whole process else you can get so many bad side effects. If you realy need to abort some process and dont have any other option like CancellationToken or a timeout paramter, then u can just create a deticated Thread/Task inside the actor and Abort it from the actor thread there.

                Thread taskThread = null;
                var task = Task.Run(() => {
                    taskThread = Thread.CurrentThread;
                    Thread.Sleep(Timeout.Infinite);
                });

                Thread.Sleep(2000); //wait to start the new thread

                taskThread.Abort();

But it should realy only be used for a 3th libery API where there is no other option to cancel the process. to make a GC.Collect() after the abort is a good idea too.

Zetanova
@Zetanova
@Aaronontheweb Yes, i can run "build.cmd multinodetests" inside the cmd, but how to run it inside Visual Studio to step into the excution or is it not possible? I just always getting "Test Skipped"
image.png
Aaron Stannard
@Aaronontheweb
you'd want to set Akka.MultiNodeTestRunner as the startup project
and pass in some commandline parameters in as debug objects
one possibility that came up today (I was doing a lot of work with the MNTR)
right now we have our own custom XUnit runner
wonder if it's possible to accomplish the same thing using XUnit fixtures / collections
and not need a separate runner at all
that would solve that problem
haven't looked into doing that at all
just an idea that occurred to me - we've been doing a lot of work on Akka.Streams.Kafka and Akka.Persistence.Sql using those types of IAsyncLifetime fixtures to keep Docker containers alive while the entire test suite runs
might be possible to keep the other remote processes alive too
Greatsamps
@Greatsamps
@Horusiath Thanks for the advice! Issue here is a 3rd party SSH library that does not expose Async and seems to have some bugs in it to say the least! I am thinking of wrapping it in a Task.Run so at least i can keep an eye on it from the actor. Your examples are interesting for some other bits i am working on, so thanks!
@Zetanova Thanks for your input here, i had pretty much arrived at same conclusion!
Zetanova
@Zetanova
@Aaronontheweb yes, i saw it in other projects too, specialy with integration test, should work. I didnt fought to simply run the Akka.MultiNodeTestRunner project, will try it
Zetanova
@Zetanova
@Greatsamps Maybe u can find a good c# managed libery but, in my experience is to use OpenSSH client "ssh.exe" as child process. override input, output and error streams for text processing or make a tunnel and a proxy port.
50% of the SSH clients in nuget are doing it like this and most of them have a old OpenSSH exe version embedded. You could just update it. The other half made a managed implementation but they were all unstable. But i tested them 3-4years ago
Zetanova
@Zetanova
@Greatsamps Maybe if possible/wanted u could use >PowerShellCore6.2. If u can instell it on the remote linux box, then u can work with System.Management.Automation / powershell scripts and connect to the remote site over SSH (pwsh is using ssh.exe for it too). This method is in my opinion one of the best method to work on linux systems from c#.
Aaron Stannard
@Aaronontheweb
@/all https://twitter.com/petabridge/status/1175065890213322763 - emailed this out to the Petabridge mailing list this morning, but if you're not on it: we're doing a survey regarding Akka.NET platform usage and want your feedback. This is going to directly impact the Akka.NET v1.4.0 release on issues such as akkadotnet/akka.net#3851 - we would appreciate your feedback if you're open to sharing.
Direct link to the survey: https://akkadotnet.typeform.com/to/YwCV7O
also, expect to see an update from the project later today - going to be pushing a new 1.3.15 release of Akka.NET and a v1.4.0-beta2 this afternoon as well. We'll include some snippets from the release notes here.
Greatsamps
@Greatsamps
@Zetanova Thanks for the suggestions. It is indeed a library that is 3-4 years old and not touched for over a year. I think i am actually going to use Ansible for this particular use case as starting to seem like i'm building out an entire orchestration engine!