Silnik skryptowy Pythona dla CODESYS – Programowanie Claude SONNET – Część 1

controlbyte.pl 6 dni temu

Integracja sztucznej inteligencji (AI) z programowaniem sterowników PLC rewolucjonizuje automatykę przemysłową, zwiększając efektywność, elastyczność oraz możliwości predykcyjne. Wykorzystanie narzędzi takich jak silnik skryptów Python w środowisku CODESYS oraz usług AI opartych na chmurze oferuje inżynierom nowatorskie podejścia do projektowania i zarządzania aplikacjami PLC.

Silnik skryptów Python w środowisku CODESYS

Silnik skryptów Python w środowisku CODESYS to zaawłansowane narzylędzie umożliwiające automatyzację różnorodnych zadań związanych z rozwojem oraz zarządzaniem projektami w środowisku CODESYS. Dzięki integracji skryptów IronPython, programiści mogą usprawniać procesy takie jak tworzenie projektów, konfiguracja urządzeń oraz generowanie kodu, co znacząco zwiększa efektywność i precyzję pracy.

Key functionalities accessible through the Python Script Engine include:

  • System: Access to general CODESYS functionalities, such as exiting the application and handling the user interface.
  • Projects: Management of projects, including loading, creating, saving, and closing projects.
  • Online: Online functions like logging into devices and applications, managing access data, performing network scans, and gateway management.
  • LibraryManager: Management of library repositories, including viewing, installation, and removal of libraries.
  • DeviceRepository: Handling of device repositories, including import and export of device descriptions.

Skrypty mogą być wykonywane bezpośrednio z interfejsu systemu CODESYS Development lub dzięki wiersza poleceń, co pozwala na elastyczną integrację procesów automatyzacji z istniejącymi przepływami pracy.

Aby ułatwić tworzenie i edytowanie skryptów, CODESYS oferuje wtyczkę Python Editor. Narzędzie to zapewnia funkcje takie jak autouzupełnianie, podświetlanie składni, strukturyzacja kodu oraz inteligentne wcięcia, zwiększając tym samym produktywność podczas opracowywania rozwiązań automatyzacyjnych opartych na skryptach Pythona.

Dzięki wykorzystaniu silnika skryptowego Python, programiści mogą osiągnąć wyższy poziom automatyzacji i precyzji w zarządzaniu projektami w środowisku CODESYS, co przekłada się na bardziej wydajne i niezawodne procesy rozwoju.

Dla profesjonalistów z dziedziny automatyki przemysłowej precyzja oraz spójność są kluczowe. Silnik skryptowy Python w CODESYS oferuje zaawansowane możliwości automatyzacji powtarzalnych zadań, takich jak dodawanie urządzeń, tworzenie programów, importowanie bibliotek czy konfiguracja projektów — wszystko z chirurgiczną precyzją.

Domyślna ścieżka do plików stub silnika skryptowego to:

C:\Program Files\CODESYS 3.5.xx.xx\CODESYS\ScriptLib\Stubs\scriptengine

Ten folder zawiera wszystkie pliki stub języka Python niezbędne do interakcji ze skryptowym API środowiska CODESYS. Pliki te pełnią rolę interfejsu między twoim kodem Pythona a wewnętrznymi obiektami środowiska CODESYS.

Jak używać w VS Code

Aby włączyć funkcje takie jak autouzupełnianie kodu, podświetlanie składni oraz podpowiedzi typów podczas pisania skryptów CODESYS w Visual Studio Code, możesz zrobić następujące rzeczy:

Skopiuj folder scriptengine z domyślnej ścieżki:

C:\Program Files\CODESYS 3.5.xx.xx\CODESYS\ScriptLib\Stubs\scriptengine

Wklej go do katalogu twojego projektu Pythonowego, na przykład:

my-codesys-scripts/
├── scriptengine/
├── my_script.py

Takie ustawienie pozwala VS Code rozpoznać moduły specyficzne dla CODESYS, co pomaga efektywniej pisać, testować i debugować twoje skrypty automatyzacji — choćby poza środowiskiem CODESYS.

Przykładowe programy w silniku skryptowym Python do interakcji z CODESYS

Przykładowy program:

devId = None devices = device_repository.get_all_devices("CODESYS Control Win V3") for device in devices: devId = device.device_id proj = projects.primary # delete existing testdev device existing = proj.find('testdev') if len(existing) > 0: existing[0].remove() # add device proj.add('testdev', devId) apps = proj.find('Application', True) if len(apps) > 0: app = apps[0] tc = app.create_task_configuration()

Co robi skrypt

Ten skrypt służy do tego, aby:

  • Pobrać identyfikator urządzenia dla CODESYS Control Win V3,
  • Usunąć z projektu dowolne istniejące urządzenie o nazwie „testdev”,
  • Dodać nowe urządzenie, używając pobranego identyfikatora urządzenia,
  • Utworzyć konfigurację zadań (Task Configuration) dla aplikacji w projekcie.

Wyjaśnienie skryptu – linia po linii

devId = None devices = device_repository.get_all_devices("CODESYS Control Win V3") for device in devices: devId = device.device_id
  • Pobiera wszystkie dostępne urządzenia z repozytorium urządzeń (Device Repository) pasujące do typu „CODESYS Control Win V3”.
  • W pętli przechodzi przez wyniki i zapisuje identyfikator urządzenia (device_id) ostatniego pasującego urządzenia do zmiennej devId.

W skryptach produkcyjnych zwykle należy wybrać konkretną wersję lub urządzenie, zamiast brać ostatnie urządzenie bez dokładnej kontroli.

proj = projects.primary Gets the currently opened CODESYS project — this is the project that the script will modify. # delete existing testdev device existing = proj.find('testdev') if len(existing) > 0: existing[0].remove()
  • Przeszukuje projekt w celu znalezienia dowolnego urządzenia o nazwie testdev.
  • Jeśli zostanie znalezione, usuwa istniejące urządzenie, aby uniknąć duplikatów.
  • Dzięki temu skrypt jest idempotentny — bezpieczny do wielokrotnego uruchamiania.
# add device proj.add('testdev', devId) Adds a new device to the project with the name testdev, using the device_id fetched earlier. apps = proj.find('Application', True) if len(apps) > 0: app = apps[0] tc = app.create_task_configuration()
  • Przeszukuje projekt, aby znaleźć obiekt Application (z opcją recursive = True).
  • Jeśli zostanie znaleziony, pobiera pierwszy znaleziony obiekt i tworzy w nim konfigurację zadań (Task Configuration).
  • Konfiguracje zadań są potrzebne do definiowania zadań cyklicznych, takich jak MainTask lub VISU_TASK.

Podsumowanie

Ten skrypt:

  • Dynamicznie znajduje urządzenie CODESYS,
  • Zapewnia, iż projekt nie zawiera duplikatów,
  • Czysto dodaje nowe urządzenie,
  • Przygotowuje projekt poprzez utworzenie nowej konfiguracji zadań – gotowej do dodawania programów.

Więcej przykładowych skryptów:

Dodanie urządzenia wraz z konfiguracją zadań

# add device with a task configuration proj.add('PLC', devId) apps = proj.find('Application', True) if len(apps) > 0: tc = apps[0].create_task_configuration() # add task task = tc.create_task('Task') task.pous.add('PLC_PRG') # proj = projects.open("C:\Users\Administrator\Documents\PL Przepompownia AI\Untitled1.project") # devId = None # devices = device_repository.get_all_devices("CODESYS Control Win V3") # for device in devices: # devId = device.device_id # proj = projects.primary # # add device # proj.add('PLC', devId) # apps = proj.find('Application', True) # if len(apps) > 0: # tc = apps[0].create_task_configuration() # # add task # task = tc.create_task('Task') # task.pous.add('PLC_PRG')

Utwórz POU

proj = projects.primary # current project found = proj.find("Application", True) app = found[0] # Create FB mypou = app.create_pou("MyPou") # Change declaration of the FB implementation = mypou.textual_declaration.replace("""FUNCTION_BLOCK MyPou VAR_INPUT iValue : INT; END_VAR VAR_OUTPUT END_VAR VAR END_VAR""") # Change implementation of the FB mypou.textual_implementation.replace("""iValue := iValue + 1;""") # Add method to FB dosomething = mypou.create_method("DoSomething", "INT") # Change declaration of the method dosomething.textual_declaration.replace("""METHOD DoSomething : INT VAR_INPUT iVal1 : INT; iVal2 : INT; END_VAR""") # Change implementation of the method dosomething.textual_implementation.replace("""DoSomething := iVal1 + iVal2;""") # # Find the pou and delete it # found = app.find("MyPou") # if found and len(found) == 1: # found[0].remove() # else: # print("POU 'MyPou' was not found")

Utwórz listę zmiennych globalnych i trwałych:

# Get the primary project or open a project proj = projects.primary # Use the currently open project # Find the Application object found = proj.find("Application", True) app = found[0] # Create a Global Variable List (GVL) gvl = app.create_gvl("GVL_Process") # Define the global variables in the GVL gvl.textual_declaration.replace("""VAR_GLOBAL // System Configuration g_xSystemEnabled : BOOL := TRUE; // System enable flag g_xEmergencyStop : BOOL := FALSE; // Emergency stop status g_xMaintenanceMode : BOOL := FALSE; // Maintenance mode flag // Process Variables g_rTemperature : REAL; // Process temperature g_rPressure : REAL; // Process pressure g_rFlowRate : REAL; // Flow rate g_rLevel : REAL; // Tank level // Control Parameters g_rTempSetpoint : REAL := 25.0; // Temperature setpoint g_rPressSetpoint : REAL := 2.5; // Pressure setpoint g_rFlowSetpoint : REAL := 100.0; // Flow rate setpoint g_rLevelSetpoint : REAL := 50.0; // Level setpoint // Alarms g_xTempAlarm : BOOL; // Temperature alarm g_xPressAlarm : BOOL; // Pressure alarm g_xFlowAlarm : BOOL; // Flow rate alarm g_xLevelAlarm : BOOL; // Level alarm // Timers g_tCycleTime : TIME := T#100MS; // Control cycle time g_tAlarmDelay : TIME := T#5S; // Alarm delay time END_VAR""") # Create a persistent Global Variable List persistent_gvl = app.create_persistentvars("GVL_Settings") # Define the persistent global variables persistent_gvl.textual_declaration.replace("""VAR_GLOBAL PERSISTENT // System Settings p_xAutoStartEnabled : BOOL := TRUE; // Auto-start on power up p_tStartupDelay : TIME := T#30S; // Startup delay time // Control Parameters p_rTempKp : REAL := 1.5; // Temperature controller P gain p_rTempKi : REAL := 0.2; // Temperature controller I gain p_rTempKd : REAL := 0.1; // Temperature controller D gain p_rPressKp : REAL := 2.0; // Pressure controller P gain p_rPressKi : REAL := 0.3; // Pressure controller I gain p_rPressKd : REAL := 0.05; // Pressure controller D gain p_rFlowKp : REAL := 1.0; // Flow controller P gain p_rFlowKi : REAL := 0.15; // Flow controller I gain p_rFlowKd : REAL := 0.0; // Flow controller D gain p_rLevelKp : REAL := 3.0; // Level controller P gain p_rLevelKi : REAL := 0.25; // Level controller I gain p_rLevelKd : REAL := 0.1; // Level controller D gain // Alarm Thresholds p_rTempHighLimit : REAL := 80.0; // Temperature high limit p_rTempLowLimit : REAL := 5.0; // Temperature low limit p_rPressHighLimit : REAL := 5.0; // Pressure high limit p_rPressLowLimit : REAL := 0.5; // Pressure low limit p_rFlowHighLimit : REAL := 200.0; // Flow high limit p_rFlowLowLimit : REAL := 10.0; // Flow low limit p_rLevelHighLimit : REAL := 90.0; // Level high limit p_rLevelLowLimit : REAL := 10.0; // Level low limit END_VAR""") # Create a constant Global Variable List const_gvl = app.create_gvl("GVL_Constants") # Define the constant global variables const_gvl.textual_declaration.replace("""VAR_GLOBAL CONSTANT // System Constants c_iMaxDevices : INT := 10; // Maximum number of devices c_iMaxAlarms : INT := 100; // Maximum number of alarms // Physical Constants c_rGravity : REAL := 9.81; // Gravity acceleration (m/s²) c_rWaterDensity : REAL := 1000.0; // Water density (kg/mł) c_rAirDensity : REAL := 1.225; // Air density at sea level (kg/mł) // Conversion Factors c_rPa_To_Bar : REAL := 0.00001; // Pascal to Bar conversion c_rBar_To_PSI : REAL := 14.5038; // Bar to PSI conversion c_rLiter_To_M3 : REAL := 0.001; // Liter to cubic meter conversion // Time Constants c_tMaxRunTime : TIME := T#24H; // Maximum continuous run time c_tMaintenanceInterval : TIME := T#720H; // Maintenance interval (30 days) END_VAR""") print("Global Variable Lists created successfully!")

Tryb symulacji:

# set device to simulation mode - this only check Simulation mark in the online tab devs = proj.find('testdev') # type here project name up to Application devs[0].set_simulation_mode(True) # alternatively check the sim is enabled beforehand and turn it on if not yet enabled devs = proj.find('testdev') if len(devs) > 0: # check if sim is enabled cur_sim_mode = devs[0].get_simulation_mode() print(cur_sim_mode) # enable sim conditionally if not cur_sim_mode: devs[0].set_simulation_mode(True)

Jeśli chcesz w pełni odkryć potencjał silnika skryptowego Python w CODESYS oraz dowiedzieć się, jak usprawnić automatyzację procesów dzięki wskazówkom Claude’a Sonneta, koniecznie zapoznaj się z częścią 2 tego artykułu. Znajdziesz tam informacje, jak zastosować zdobytą wiedzę w praktyce oraz wykorzystać zaawansowane możliwości tego narzędzia.

Idź do oryginalnego materiału