source: trunk/src/allmydata/test/storage_plugin.py

Last change on this file was 0985468, checked in by Itamar Turner-Trauring <itamar@…>, at 2024-03-01T18:08:09Z

Remove another future import.

  • Property mode set to 100644
File size: 3.1 KB
Line 
1"""
2A storage server plugin the test suite can use to validate the
3functionality.
4
5Ported to Python 3.
6"""
7
8from six import ensure_str
9
10import attr
11
12from zope.interface import (
13    implementer,
14)
15
16from twisted.internet.defer import (
17    succeed,
18)
19from twisted.web.resource import (
20    Resource,
21)
22from twisted.web.static import (
23    Data,
24)
25from foolscap.api import (
26    RemoteInterface,
27)
28
29from allmydata.interfaces import (
30    IFoolscapStoragePlugin,
31    IStorageServer,
32)
33from allmydata.client import (
34    AnnounceableStorageServer,
35)
36from allmydata.util.jsonbytes import (
37    dumps,
38)
39
40
41class RIDummy(RemoteInterface):
42    __remote_name__ = "RIDummy.tahoe.allmydata.com"
43
44    def just_some_method():
45        """
46        Just some method so there is something callable on this object.  We won't
47        pretend to actually offer any storage capabilities.
48        """
49
50
51# type ignored due to missing stubs for Twisted
52# https://twistedmatrix.com/trac/ticket/9717
53@implementer(IFoolscapStoragePlugin)  # type: ignore
54@attr.s
55class DummyStorage(object):
56    name = attr.ib()
57
58    @property
59    def _client_section_name(self):
60        return u"storageclient.plugins.{}".format(self.name)
61
62    def get_storage_server(self, configuration, get_anonymous_storage_server):
63        if u"invalid" in configuration:
64            raise Exception("The plugin is unhappy.")
65
66        announcement = {u"value": configuration.get(u"some", u"default-value")}
67        storage_server = DummyStorageServer(get_anonymous_storage_server)
68        return succeed(
69            AnnounceableStorageServer(
70                announcement,
71                storage_server,
72            ),
73        )
74
75    def get_storage_client(self, configuration, announcement, get_rref):
76        return DummyStorageClient(
77            get_rref,
78            dict(configuration.items(self._client_section_name, [])),
79            announcement,
80        )
81
82    def get_client_resource(self, configuration):
83        """
84        :return: A static data resource that produces the given configuration when
85            rendered, as an aid to testing.
86        """
87        items = configuration.items(self._client_section_name, [])
88        resource = Data(
89            dumps(dict(items)).encode("utf-8"),
90            ensure_str("text/json"),
91        )
92        # Give it some dynamic stuff too.
93        resource.putChild(b"counter", GetCounter())
94        return resource
95
96
97class GetCounter(Resource, object):
98    """
99    ``GetCounter`` is a resource that returns a count of the number of times
100    it has rendered a response to a GET request.
101
102    :ivar int value: The number of ``GET`` requests rendered so far.
103    """
104    value = 0
105    def render_GET(self, request):
106        self.value += 1
107        return dumps({"value": self.value}).encode("utf-8")
108
109
110@implementer(RIDummy)
111@attr.s(frozen=True)
112class DummyStorageServer(object):  # type: ignore # warner/foolscap#78
113    get_anonymous_storage_server = attr.ib()
114
115    def remote_just_some_method(self):
116        pass
117
118
119@implementer(IStorageServer)
120@attr.s
121class DummyStorageClient(object):  # type: ignore # incomplete implementation
122    get_rref = attr.ib()
123    configuration = attr.ib()
124    announcement = attr.ib()
Note: See TracBrowser for help on using the repository browser.