1+ import asyncio
2+ from typing import Any
3+ from asyncio .queues import Queue
4+ from starlette .applications import Starlette
5+ from starlette .endpoints import WebSocketEndpoint
6+ from starlette .routing import WebSocketRoute
7+ from starlette .websockets import WebSocket
8+
9+ from olink .core .types import Name
10+ from olink .net .server import RemoteEndpoint
11+ from olink .remotenode import IObjectSource , RemoteNode
12+
13+
14+ class Counter :
15+ count = 0
16+ _node : RemoteNode
17+ def increment (self ):
18+ self .count += 1
19+ self ._node .notify_property_change ('demo.Counter/count' , self .count )
20+
21+ class CounterAdapter (IObjectSource ):
22+ node : RemoteNode = None
23+ def __init__ (self , impl ):
24+ self .impl = impl
25+ RemoteNode .add_object_source (self )
26+
27+ def olink_object_name (self ):
28+ return 'demo.Counter'
29+
30+ def olink_invoke (self , name : str , args : list [Any ]) -> Any :
31+ path = Name .path_from_name (name )
32+ func = getattr (self .impl , path )
33+ func ()
34+
35+ def olink_set_property (self , name : str , value : Any ):
36+ path = Name .path_from_name (name )
37+ setattr (self , self .impl , value )
38+
39+ def olink_linked (self , name : str , node : "RemoteNode" ):
40+ self .impl ._node = node
41+
42+ def olink_collect_properties (self ) -> object :
43+ return {k : getattr (self .impl , k ) for k in ['count' ]}
44+
45+ counter = Counter ()
46+ adapter = CounterAdapter (counter )
47+
48+
49+
50+
51+ class RemoteEndpoint (WebSocketEndpoint ):
52+ encoding = "text"
53+ node = RemoteNode ()
54+ queue = Queue ()
55+
56+ async def sender (self , ws ):
57+ print ('start sender' )
58+ while True :
59+ print ('001' )
60+ msg = await self .queue .get ()
61+ print ('send' , msg )
62+ await ws .send_text (msg )
63+ self .queue .task_done ()
64+
65+ async def on_connect (self , ws : WebSocket ):
66+ print ('on_connect' )
67+ asyncio .create_task (self .sender (ws ))
68+
69+ def writer (msg : str ):
70+ print ('writer' , msg )
71+ self .queue .put_nowait (msg )
72+ self .node .on_write (writer )
73+ await super ().on_connect (ws )
74+
75+
76+ async def on_receive (self , ws : WebSocket , data : Any ) -> None :
77+ print ('on_receive' , data )
78+ self .node .handle_message (data )
79+
80+ async def on_disconnect (self , websocket : WebSocket , close_code : int ) -> None :
81+ await super ().on_disconnect (websocket , close_code )
82+ self .node .on_write (None )
83+ await self .queue .join ()
84+
85+
86+
87+ routes = [
88+ WebSocketRoute ("/ws" , RemoteEndpoint )
89+ ]
90+
91+ app = Starlette (routes = routes )
0 commit comments