summaryrefslogtreecommitdiff
path: root/csharp/test/Ice/admin/TestI.cs
blob: ae7c1fbd5e850a2d9cdd82e06d36a1ad97854ad1 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
// Copyright (c) ZeroC, Inc. All rights reserved.

using System.Collections.Generic;
using System.Threading;
using ZeroC.Test;

namespace ZeroC.Ice.Test.Admin
{
    public class TestFacet : ITestFacet
    {
        public void Op(Current current, CancellationToken cancel)
        {
        }
    }

    public class RemoteCommunicator : IRemoteCommunicator
    {
        private volatile IReadOnlyDictionary<string, string>? _changes;
        private readonly Communicator _communicator;

        public RemoteCommunicator(Communicator communicator) => _communicator = communicator;

        public IObjectPrx? GetAdmin(Current current, CancellationToken cancel) =>
            _communicator.GetAdminAsync(cancel: cancel).GetAwaiter().GetResult();

        public IReadOnlyDictionary<string, string> GetChanges(Current current, CancellationToken cancel) =>
            new Dictionary<string, string>(_changes!);

        public void Print(string message, Current current, CancellationToken cancel) =>
            _communicator.Logger.Print(message);

        public void Trace(string category, string message, Current current, CancellationToken cancel) =>
            _communicator.Logger.Trace(category, message);

        public void Warning(string message, Current current, CancellationToken cancel) =>
            _communicator.Logger.Warning(message);

        public void Error(string message, Current current, CancellationToken cancel) =>
            _communicator.Logger.Error(message);

        public void Shutdown(Current current, CancellationToken cancel) => _ = _communicator.ShutdownAsync();

        // Note that we are executing in a thread of the *main* communicator, not the one that is being shut down.
        public void WaitForShutdown(Current current, CancellationToken cancel) =>
            _communicator.ShutdownComplete.Wait(cancel);

        public void Destroy(Current current, CancellationToken cancel) => _communicator.Dispose();

        public void Updated(IReadOnlyDictionary<string, string> changes) => _changes = changes;
    }

    public class RemoteCommunicatorFactoryI : IRemoteCommunicatorFactory
    {
        public IRemoteCommunicatorPrx CreateCommunicator(
            Dictionary<string, string> props,
            Current current,
            CancellationToken cancel)
        {
            // Prepare the property set using the given properties.
            ILogger? logger = null;
            if (props.TryGetValue("NullLogger", out string? value) &&
                int.TryParse(value, out int nullLogger) && nullLogger > 0)
            {
                logger = new NullLogger();
            }

            // Initialize a new communicator.
            var communicator = new Communicator(props, logger: logger);

            // Install a custom admin facet.
            try
            {
                var testFacet = new TestFacet();
                communicator.AddAdminFacet("TestFacet", testFacet);
            }
            catch (System.ArgumentException)
            {
            }

            // The RemoteCommunicator servant also implements PropertiesAdminUpdateCallback.
            var servant = new RemoteCommunicator(communicator);

            if (communicator.FindAdminFacet("Properties") is IAsyncPropertiesAdmin admin)
            {
                admin.Updated += (_, updates) => servant.Updated(updates);
            }

            return current.Adapter.AddWithUUID(servant, IRemoteCommunicatorPrx.Factory);
        }

        public void Shutdown(Current current, CancellationToken cancel) => current.Communicator.ShutdownAsync();

        private class NullLogger : ILogger
        {
            public void Print(string message)
            {
            }

            public void Trace(string category, string message)
            {
            }

            public void Warning(string message)
            {
            }

            public void Error(string message)
            {
            }

            public string Prefix => "NullLogger";

            public ILogger CloneWithPrefix(string prefix) => this;
        }
    }
}