python opcua_OPCUA-Python

该博客演示了如何使用Python的opcua库创建一个OPCUA服务器,包括设置端点、安全策略、注册命名空间、创建设备对象和变量、订阅数据变化以及触发事件。示例代码展示了如何创建和更新变量、定义方法以及处理数据改变和事件通知。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

from threading import Thread

import copy

import logging

from datetime import datetime

import time

from math import sin

import sys

sys.path.insert(0, "..")

try:

from IPython import embed

except ImportError:

import code

def embed():

myvars = globals()

myvars.update(locals())

shell = code.InteractiveConsole(myvars)

shell.interact()

from opcua import ua, uamethod, Server

class SubHandler(object):

"""

Subscription Handler. To receive events from server for a subscription

"""

def datachange_notification(self, node, val, data):

print("Python: New data change event", node, val)

def event_notification(self, event):

print("Python: New event", event)

# method to be exposed through server

def func(parent, variant):

ret = False

if variant.Value % 2 == 0:

ret = True

return [ua.Variant(ret, ua.VariantType.Boolean)]

# method to be exposed through server

# uses a decorator to automatically convert to and from variants

@uamethod

def multiply(parent, x, y):

print("multiply method call with parameters: ", x, y)

return x * y

class VarUpdater(Thread):

def __init__(self, var):

Thread.__init__(self)

self._stopev = False

self.var = var

def stop(self):

self._stopev = True

def run(self):

while not self._stopev:

v = sin(time.time() / 10)

self.var.set_value(v)

time.sleep(0.1)

if __name__ == "__main__":

# optional: setup logging

logging.basicConfig(level=logging.WARN)

#logger = logging.getLogger("opcua.address_space")

# logger.setLevel(logging.DEBUG)

#logger = logging.getLogger("opcua.internal_server")

# logger.setLevel(logging.DEBUG)

#logger = logging.getLogger("opcua.binary_server_asyncio")

# logger.setLevel(logging.DEBUG)

#logger = logging.getLogger("opcua.uaprocessor")

# logger.setLevel(logging.DEBUG)

# now setup our server

server = Server()

#server.disable_clock()

#server.set_endpoint("opc.tcp://localhost:4840/freeopcua/server/")

server.set_endpoint("opc.tcp://0.0.0.0:4841/freeopcua/server/")

server.set_server_name("FreeOpcUa Example Server")

# set all possible endpoint policies for clients to connect through

server.set_security_policy([

ua.SecurityPolicyType.NoSecurity,

# ua.SecurityPolicyType.Basic256Sha256_SignAndEncrypt,

# ua.SecurityPolicyType.Basic256Sha256_Sign

])

# setup our own namespace

uri = "http://examples.freeopcua.github.io"

idx = server.register_namespace(uri)

# create a new node type we can instantiate in our address space

dev = server.nodes.base_object_type.add_object_type(0, "MyDevice")

dev.add_variable(0, "sensor1", 1.0).set_modelling_rule(True)

dev.add_property(0, "device_id", "0340").set_modelling_rule(True)

ctrl = dev.add_object(0, "controller")

ctrl.set_modelling_rule(True)

ctrl.add_property(0, "state", "Idle").set_modelling_rule(True)

# populating our address space

# First a folder to organise our nodes

myfolder = server.nodes.objects.add_folder(idx, "myEmptyFolder")

# instanciate one instance of our device

mydevice = server.nodes.objects.add_object(idx, "Device0001", dev)

mydevice_var = mydevice.get_child(["0:controller", "0:state"])  # get proxy to our device state variable

# create directly some objects and variables

myobj = server.nodes.objects.add_object(idx, "MyObject")

myvar = myobj.add_variable(idx, "MyVariable", 6.7)

mysin = myobj.add_variable(idx, "MySin", 0, ua.VariantType.Float)

myvar.set_writable()    # Set MyVariable to be writable by clients

mystringvar = myobj.add_variable(idx, "MyStringVariable", "Really nice string")

mystringvar.set_writable()    # Set MyVariable to be writable by clients

mydtvar = myobj.add_variable(idx, "MyDateTimeVar", datetime.utcnow())

mydtvar.set_writable()    # Set MyVariable to be writable by clients

myarrayvar = myobj.add_variable(idx, "myarrayvar", [6.7, 7.9])

myarrayvar = myobj.add_variable(idx, "myStronglytTypedVariable", ua.Variant([], ua.VariantType.UInt32))

myprop = myobj.add_property(idx, "myproperty", "I am a property")

mymethod = myobj.add_method(idx, "mymethod", func, [ua.VariantType.Int64], [ua.VariantType.Boolean])

multiply_node = myobj.add_method(idx, "multiply", multiply, [ua.VariantType.Int64, ua.VariantType.Int64], [ua.VariantType.Int64])

# import some nodes from xml

# server.import_xml("custom_nodes.xml")

# creating a default event object

# The event object automatically will have members for all events properties

# you probably want to create a custom event type, see other examples

myevgen = server.get_event_generator()

myevgen.event.Severity = 300

# starting!

server.start()

print("Available loggers are: ", logging.Logger.manager.loggerDict.keys())

vup = VarUpdater(mysin)  # just  a stupide class update a variable

vup.start()

try:

# enable following if you want to subscribe to nodes on server side

#handler = SubHandler()

#sub = server.create_subscription(500, handler)

#handle = sub.subscribe_data_change(myvar)

# trigger event, all subscribed clients wil receive it

var = myarrayvar.get_value()  # return a ref to value in db server side! not a copy!

var = copy.copy(var)  # WARNING: we need to copy before writting again otherwise no data change event will be generated

var.append(9.3)

myarrayvar.set_value(var)

mydevice_var.set_value("Running")

myevgen.trigger(message="This is BaseEvent")

server.set_attribute_value(myvar.nodeid, ua.DataValue(9.9))  # Server side write method which is a but faster than using set_value

embed()

finally:

vup.stop()

server.stop()

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值