<SYSTEM_TASK:>
Given the following text description, write Python code to implement the functionality described below step by step
<END_TASK>
<USER_TASK:>
Description:
 rtc_handle.py（basic）
this ipnb shows a basic usage of rtc_handle.py
precondition
Step1:  setup user environmet
path for rtc_handle 
path for rtcs and user tools
nameservers
you may provide a file (ex. set_env.py) for this.
Step2:  import user tools
path is modified temporaly to import tools
stubs for rtc service ports might be imported (this will be explained another example).
Step3:  RtmEnv
Step4:  NameSpace
NameSpace.env.list_obj() retrieves a list of corba objects in the nameserver 
and put them into the NameSpace.obj_list dictionary.
if an object is an rtc, its proxy object(RtcHandl) is created 
and put into the NameSpace.rtc_handle dictionary.
Step5:  RtcHandle
Step6:  activate and deactivate rtcs
Step7:  deactivation of some rtcs may fail. 
those rtcs may wait for resorces(ex. waiting for user input) in onExecute loop.
for example,
Step8:  but it usually recovers after the resorce is available. please input something at the cin console. then,
Step9:  direct access to Inports and Outports
if the interface_type of the ports is corba_cdr,
you can put data to inports and get data from outpors by using rtc_handle.py.
put data to inport
Step10:  get data from outport
by connecting to outport with setting 'datapot.dataflow_type' 
Step11:  IOConnector 
Step12:  default properties of the connector is as follows
Step13:  connect ports
Step14:  disconnect ports
Step15:  change properties
you can change properties by giving prop_dict
Step16:  conflict of connections
only one connection is permitted between the same ports.
so, if another connection exists, you can not control the connection by your connector.
for example,
Step17:  you can handle this situation by forcing connect/disconnect operation
<ASSISTANT_TASK:>
Python Code:
#!/usr/bin/env python
# -*- Python -*-
import sys
import time
import subprocess
Explanation: rtc_handle.py（basic）
this ipnb shows a basic usage of rtc_handle.py
precondition: rtcs(cin and cout) are prelaunched separetely
you can monitor the behavior of the system with openrtp
you can access and control rtcs of OpenRTM-aist (written in any languages, ie., c++, python, java) 
by using rtc_handle.py
End of explanation
#
# set up user environment
#  RtmToolsDir, MyRtcDir, etc.
#
# from set_env import *   : you may provide a setup file like this
#
RtmToolsDir="../.."
MyRtcDir=".."
NS0="localhost:9876"
Explanation: setup user environmet
path for rtc_handle 
path for rtcs and user tools
nameservers
you may provide a file (ex. set_env.py) for this.
End of explanation
#
# import user tools
#
sys.path.append(".")
save_path = sys.path[:]
sys.path.append(RtmToolsDir+'/rtc_handle')
from rtc_handle import *
# from rtc_handle_util import *
# sys.path.append(RtmToolsDir+'/embryonic_rtc')
# from EmbryonicRtc import *
sys.path = save_path
#
# import stub files
# 
#import _GlobalIDL
Explanation: import user tools
path is modified temporaly to import tools
stubs for rtc service ports might be imported (this will be explained another example).
End of explanation
#
# user program 
# 
#
env = RtmEnv(sys.argv,[NS0])
Explanation: RtmEnv: rtm environment holder
RtmEnv class object contains an orb, name-servers, rtcs, connectors and other rtm environment information.
the second arg is a list of cos nameservers.
End of explanation
env.name_space[NS0].list_obj()
env.name_space[NS0].obj_list
env.name_space[NS0].rtc_handles
Explanation: NameSpace
NameSpace.env.list_obj() retrieves a list of corba objects in the nameserver 
and put them into the NameSpace.obj_list dictionary.
if an object is an rtc, its proxy object(RtcHandl) is created 
and put into the NameSpace.rtc_handle dictionary.
End of explanation
cin=env.name_space[NS0].rtc_handles['cin0.rtc']
cout=env.name_space[NS0].rtc_handles['cout0.rtc']
Explanation: RtcHandle: proxy of rtc
RtcHandle is a proxy class of rtc and the center object of this module. 
an rtc can be accessed by its object reference and information of the rtc can be gathered throug the reference.
an RtcHandle object holds those information and proxy the rtc.
assign rtc proxies to valiables
to ease access to rtc proxies, it may be a good idea assigning them to valiables.
End of explanation
cout.activate()
cout.deactivate()
cout.activate()
Explanation: activate and deactivate rtcs
End of explanation
cin.activate()
cin.deactivate()
Explanation: deactivation of some rtcs may fail. 
those rtcs may wait for resorces(ex. waiting for user input) in onExecute loop.
for example,
End of explanation
cin.activate()
Explanation: but it usually recovers after the resorce is available. please input something at the cin console. then,
End of explanation
cout.inports
cout.inports['str_in'].open()
cout.inports['str_in'].write('abc')
cout.inports['str_in'].close()
Explanation: direct access to Inports and Outports
if the interface_type of the ports is corba_cdr,
you can put data to inports and get data from outpors by using rtc_handle.py.
put data to inport
End of explanation
cin.outports
cin.outports['str_out'].open()
cin.outports['str_out'].con.prop_dict
cin.outports['str_out'].read()
cin.outports['str_out'].close()
Explanation: get data from outport
by connecting to outport with setting 'datapot.dataflow_type' : 'pull' ,
you can get 'dataport.corba_cdr.outport_ref'.
you can directly get the last data (and if not consumed other rtcs) by the ref.
End of explanation
con = IOConnector([cin.outports['str_out'], cout.inports['str_in']])
Explanation: IOConnector : connect and disconnect io-ports
IOConnector contains information for connecting io-ports
create a connector between cin.outports['str_out'] and cout.inports['str_in']
End of explanation
con.def_prop
Explanation: default properties of the connector is as follows
End of explanation
con.connect()
con.profile
con.prop_dict
Explanation: connect ports
End of explanation
con.disconnect()
Explanation: disconnect ports
End of explanation
con = IOConnector([cin.outports['str_out'], cout.inports['str_in']], 
                  prop_dict={'dataport.inport.buffer.length': '8'})
con.prop_dict_req
con.connect()
con.prop_dict
con.disconnect()
Explanation: change properties
you can change properties by giving prop_dict
End of explanation
b = IOConnector([cin.outports['str_out'], cout.inports['str_in']])
b.connect()
con.connect()
con.disconnect()
Explanation: conflict of connections
only one connection is permitted between the same ports.
so, if another connection exists, you can not control the connection by your connector.
for example,
End of explanation
con.connect(force=True)
Explanation: you can handle this situation by forcing connect/disconnect operation
End of explanation
<END_TASK>